]> git.pld-linux.org Git - packages/percona-server.git/blame - innodb_separate_doublewrite.patch
- symbolic-links=0 from fedora
[packages/percona-server.git] / innodb_separate_doublewrite.patch
CommitLineData
b4e1fa2c
AM
1# name : innodb_separate_doublewrite.patch
2# introduced : 11 or before
3# maintainer : Yasufumi
4#
5#!!! notice !!!
6# Any small change to this file in the main branch
7# should be done or reviewed by the maintainer!
8diff -ruN a/storage/innobase/buf/buf0buf.c b/storage/innobase/buf/buf0buf.c
9--- a/storage/innobase/buf/buf0buf.c 2010-12-03 17:49:11.574962867 +0900
10+++ b/storage/innobase/buf/buf0buf.c 2010-12-04 15:35:58.624514033 +0900
d8778560 11@@ -4248,7 +4248,8 @@
b4e1fa2c
AM
12 read_space_id = mach_read_from_4(
13 frame + FIL_PAGE_ARCH_LOG_NO_OR_SPACE_ID);
14
15- if (bpage->space == TRX_SYS_SPACE
16+ if ((bpage->space == TRX_SYS_SPACE
17+ || (srv_doublewrite_file && bpage->space == TRX_DOUBLEWRITE_SPACE))
18 && trx_doublewrite_page_inside(bpage->offset)) {
19
20 ut_print_timestamp(stderr);
21diff -ruN a/storage/innobase/buf/buf0flu.c b/storage/innobase/buf/buf0flu.c
22--- a/storage/innobase/buf/buf0flu.c 2010-12-03 15:49:59.179956111 +0900
23+++ b/storage/innobase/buf/buf0flu.c 2010-12-04 15:35:58.624514033 +0900
d8778560 24@@ -791,7 +791,8 @@
b4e1fa2c
AM
25 write_buf = trx_doublewrite->write_buf;
26 i = 0;
27
28- fil_io(OS_FILE_WRITE, TRUE, TRX_SYS_SPACE, 0,
29+ fil_io(OS_FILE_WRITE, TRUE,
30+ (srv_doublewrite_file ? TRX_DOUBLEWRITE_SPACE : TRX_SYS_SPACE), 0,
31 trx_doublewrite->block1, 0, len,
32 (void*) write_buf, NULL);
33
d8778560 34@@ -828,7 +829,8 @@
b4e1fa2c
AM
35 + TRX_SYS_DOUBLEWRITE_BLOCK_SIZE * UNIV_PAGE_SIZE;
36 ut_ad(i == TRX_SYS_DOUBLEWRITE_BLOCK_SIZE);
37
38- fil_io(OS_FILE_WRITE, TRUE, TRX_SYS_SPACE, 0,
39+ fil_io(OS_FILE_WRITE, TRUE,
40+ (srv_doublewrite_file ? TRX_DOUBLEWRITE_SPACE : TRX_SYS_SPACE), 0,
41 trx_doublewrite->block2, 0, len,
42 (void*) write_buf, NULL);
43
d8778560 44@@ -858,7 +860,7 @@
b4e1fa2c
AM
45 flush:
46 /* Now flush the doublewrite buffer data to disk */
47
48- fil_flush(TRX_SYS_SPACE);
49+ fil_flush(srv_doublewrite_file ? TRX_DOUBLEWRITE_SPACE : TRX_SYS_SPACE);
50
51 /* We know that the writes have been flushed to disk now
52 and in recovery we will find them in the doublewrite buffer
53diff -ruN a/storage/innobase/buf/buf0rea.c b/storage/innobase/buf/buf0rea.c
54--- a/storage/innobase/buf/buf0rea.c 2010-12-04 15:35:29.138514157 +0900
55+++ b/storage/innobase/buf/buf0rea.c 2010-12-04 15:35:58.626486771 +0900
56@@ -88,7 +88,9 @@
57 wake_later = mode & OS_AIO_SIMULATED_WAKE_LATER;
58 mode = mode & ~OS_AIO_SIMULATED_WAKE_LATER;
59
60- if (trx_doublewrite && space == TRX_SYS_SPACE
61+ if (trx_doublewrite
62+ && (space == TRX_SYS_SPACE
63+ || (srv_doublewrite_file && space == TRX_DOUBLEWRITE_SPACE))
64 && ( (offset >= trx_doublewrite->block1
65 && offset < trx_doublewrite->block1
66 + TRX_SYS_DOUBLEWRITE_BLOCK_SIZE)
67diff -ruN a/storage/innobase/dict/dict0load.c b/storage/innobase/dict/dict0load.c
68--- a/storage/innobase/dict/dict0load.c 2010-12-03 17:30:16.252956569 +0900
69+++ b/storage/innobase/dict/dict0load.c 2010-12-04 15:35:58.627482825 +0900
d8778560
AM
70@@ -41,6 +41,7 @@
71 #include "srv0start.h"
72 #include "srv0srv.h"
73 #include "ha_prototypes.h" /* innobase_casedn_str() */
74+#include "trx0sys.h"
75
76
77 /** Following are six InnoDB system tables */
78@@ -797,7 +798,7 @@
b4e1fa2c
AM
79
80 mtr_commit(&mtr);
81
82- if (space_id == 0) {
83+ if (trx_sys_sys_space(space_id)) {
84 /* The system tablespace always exists. */
85 } else if (in_crash_recovery) {
86 /* Check that the tablespace (the .ibd file) really
d8778560 87@@ -1594,7 +1595,7 @@
b4e1fa2c
AM
88 space = mach_read_from_4(field);
89
90 /* Check if the tablespace exists and has the right name */
91- if (space != 0) {
92+ if (!trx_sys_sys_space(space)) {
93 flags = dict_sys_tables_get_flags(rec);
94
95 if (UNIV_UNLIKELY(flags == ULINT_UNDEFINED)) {
d8778560 96@@ -1744,7 +1745,7 @@
b4e1fa2c
AM
97 goto err_exit;
98 }
99
100- if (table->space == 0) {
101+ if (trx_sys_sys_space(table->space)) {
102 /* The system tablespace is always available. */
103 } else if (!fil_space_for_table_exists_in_mem(
104 table->space, name,
105diff -ruN a/storage/innobase/fil/fil0fil.c b/storage/innobase/fil/fil0fil.c
106--- a/storage/innobase/fil/fil0fil.c 2010-12-04 15:35:29.143813775 +0900
107+++ b/storage/innobase/fil/fil0fil.c 2010-12-04 15:35:58.628498870 +0900
d8778560 108@@ -655,7 +655,7 @@
b4e1fa2c
AM
109
110 UT_LIST_ADD_LAST(chain, space->chain, node);
111
112- if (id < SRV_LOG_SPACE_FIRST_ID && fil_system->max_assigned_id < id) {
113+ if (id < SRV_EXTRA_SYS_SPACE_FIRST_ID && fil_system->max_assigned_id < id) {
114
115 fil_system->max_assigned_id = id;
116 }
d8778560 117@@ -719,14 +719,14 @@
b4e1fa2c
AM
118 size_bytes = (((ib_int64_t)size_high) << 32)
119 + (ib_int64_t)size_low;
120 #ifdef UNIV_HOTBACKUP
121- if (space->id == 0) {
122+ if (trx_sys_sys_space(space->id)) {
123 node->size = (ulint) (size_bytes / UNIV_PAGE_SIZE);
124 os_file_close(node->handle);
125 goto add_size;
126 }
127 #endif /* UNIV_HOTBACKUP */
128 ut_a(space->purpose != FIL_LOG);
129- ut_a(space->id != 0);
130+ ut_a(!trx_sys_sys_space(space->id));
131
132 if (size_bytes < FIL_IBD_FILE_INITIAL_SIZE * UNIV_PAGE_SIZE) {
133 fprintf(stderr,
d8778560 134@@ -772,7 +772,7 @@
b4e1fa2c
AM
135 }
136
137 if (UNIV_UNLIKELY(space_id == ULINT_UNDEFINED
138- || space_id == 0)) {
139+ || trx_sys_sys_space(space_id))) {
140 fprintf(stderr,
141 "InnoDB: Error: tablespace id %lu"
142 " in file %s is not sensible\n",
d8778560 143@@ -840,7 +840,7 @@
b4e1fa2c
AM
144
145 system->n_open++;
146
147- if (space->purpose == FIL_TABLESPACE && space->id != 0) {
148+ if (space->purpose == FIL_TABLESPACE && !trx_sys_sys_space(space->id)) {
149 /* Put the node to the LRU list */
150 UT_LIST_ADD_FIRST(LRU, system->LRU, node);
151 }
d8778560 152@@ -873,7 +873,7 @@
b4e1fa2c
AM
153 ut_a(system->n_open > 0);
154 system->n_open--;
155
156- if (node->space->purpose == FIL_TABLESPACE && node->space->id != 0) {
157+ if (node->space->purpose == FIL_TABLESPACE && !trx_sys_sys_space(node->space->id)) {
158 ut_a(UT_LIST_GET_LEN(system->LRU) > 0);
159
160 /* The node is in the LRU list, remove it */
d8778560 161@@ -959,7 +959,7 @@
b4e1fa2c
AM
162 retry:
163 mutex_enter(&fil_system->mutex);
164
165- if (space_id == 0 || space_id >= SRV_LOG_SPACE_FIRST_ID) {
166+ if (trx_sys_sys_space(space_id) || space_id >= SRV_LOG_SPACE_FIRST_ID) {
167 /* We keep log files and system tablespace files always open;
168 this is important in preventing deadlocks in this module, as
169 a page read completion often performs another read from the
d8778560 170@@ -1190,7 +1190,7 @@
b4e1fa2c
AM
171 " tablespace memory cache!\n",
172 (ulong) space->id);
173
174- if (id == 0 || purpose != FIL_TABLESPACE) {
175+ if (trx_sys_sys_space(id) || purpose != FIL_TABLESPACE) {
176
177 mutex_exit(&fil_system->mutex);
178
d8778560 179@@ -1252,6 +1252,7 @@
b4e1fa2c
AM
180 space->mark = FALSE;
181
182 if (UNIV_LIKELY(purpose == FIL_TABLESPACE && !recv_recovery_on)
183+ && UNIV_UNLIKELY(id < SRV_EXTRA_SYS_SPACE_FIRST_ID)
184 && UNIV_UNLIKELY(id > fil_system->max_assigned_id)) {
185 if (!fil_system->space_id_reuse_warned) {
186 fil_system->space_id_reuse_warned = TRUE;
d8778560 187@@ -1335,7 +1336,7 @@
b4e1fa2c
AM
188 (ulong) SRV_LOG_SPACE_FIRST_ID);
189 }
190
191- success = (id < SRV_LOG_SPACE_FIRST_ID);
192+ success = (id < SRV_EXTRA_SYS_SPACE_FIRST_ID);
193
194 if (success) {
195 *space_id = fil_system->max_assigned_id = id;
d8778560 196@@ -1598,6 +1599,8 @@
b4e1fa2c
AM
197 UT_LIST_INIT(fil_system->LRU);
198
199 fil_system->max_n_open = max_n_open;
200+
201+ fil_system->max_assigned_id = TRX_SYS_SPACE_MAX;
202 }
203
204 /*******************************************************************//**
d8778560 205@@ -1619,7 +1622,7 @@
b4e1fa2c
AM
206 space = UT_LIST_GET_FIRST(fil_system->space_list);
207
208 while (space != NULL) {
209- if (space->purpose != FIL_TABLESPACE || space->id == 0) {
210+ if (space->purpose != FIL_TABLESPACE || trx_sys_sys_space(space->id)) {
211 node = UT_LIST_GET_FIRST(space->chain);
212
213 while (node != NULL) {
d8778560 214@@ -1709,6 +1712,10 @@
b4e1fa2c
AM
215 ut_error;
216 }
217
218+ if (max_id >= SRV_EXTRA_SYS_SPACE_FIRST_ID) {
219+ return;
220+ }
221+
222 mutex_enter(&fil_system->mutex);
223
224 if (fil_system->max_assigned_id < max_id) {
d8778560 225@@ -1727,6 +1734,7 @@
b4e1fa2c
AM
226 ulint
227 fil_write_lsn_and_arch_no_to_file(
228 /*==============================*/
229+ ulint space_id,
230 ulint sum_of_sizes, /*!< in: combined size of previous files
231 in space, in database pages */
232 ib_uint64_t lsn, /*!< in: lsn to write */
d8778560 233@@ -1736,14 +1744,16 @@
b4e1fa2c
AM
234 byte* buf1;
235 byte* buf;
236
237+ ut_a(trx_sys_sys_space(space_id));
238+
239 buf1 = mem_alloc(2 * UNIV_PAGE_SIZE);
240 buf = ut_align(buf1, UNIV_PAGE_SIZE);
241
242- fil_read(TRUE, 0, 0, sum_of_sizes, 0, UNIV_PAGE_SIZE, buf, NULL);
243+ fil_read(TRUE, space_id, 0, sum_of_sizes, 0, UNIV_PAGE_SIZE, buf, NULL);
244
245 mach_write_to_8(buf + FIL_PAGE_FILE_FLUSH_LSN, lsn);
246
247- fil_write(TRUE, 0, 0, sum_of_sizes, 0, UNIV_PAGE_SIZE, buf, NULL);
248+ fil_write(TRUE, space_id, 0, sum_of_sizes, 0, UNIV_PAGE_SIZE, buf, NULL);
249
250 mem_free(buf1);
251
d8778560 252@@ -1779,7 +1789,7 @@
b4e1fa2c
AM
253 always open. */
254
255 if (space->purpose == FIL_TABLESPACE
256- && space->id == 0) {
257+ && trx_sys_sys_space(space->id)) {
258 sum_of_sizes = 0;
259
260 node = UT_LIST_GET_FIRST(space->chain);
d8778560 261@@ -1787,7 +1797,7 @@
b4e1fa2c
AM
262 mutex_exit(&fil_system->mutex);
263
264 err = fil_write_lsn_and_arch_no_to_file(
265- sum_of_sizes, lsn, arch_log_no);
266+ space->id, sum_of_sizes, lsn, arch_log_no);
267 if (err != DB_SUCCESS) {
268
269 return(err);
d8778560 270@@ -3834,7 +3844,7 @@
b4e1fa2c
AM
271 }
272
273 #ifndef UNIV_HOTBACKUP
274- if (space_id == ULINT_UNDEFINED || space_id == 0) {
275+ if (space_id == ULINT_UNDEFINED || trx_sys_sys_space(space_id)) {
276 fprintf(stderr,
277 "InnoDB: Error: tablespace id %lu in file %s"
278 " is not sensible\n",
d8778560 279@@ -3843,7 +3853,7 @@
b4e1fa2c
AM
280 goto func_exit;
281 }
282 #else
283- if (space_id == ULINT_UNDEFINED || space_id == 0) {
284+ if (space_id == ULINT_UNDEFINED || trx_sys_sys_space(space_id)) {
285 char* new_path;
286
287 fprintf(stderr,
d8778560 288@@ -4664,7 +4674,7 @@
b4e1fa2c
AM
289 }
290
291 if (node->n_pending == 0 && space->purpose == FIL_TABLESPACE
292- && space->id != 0) {
293+ && !trx_sys_sys_space(space->id)) {
294 /* The node is in the LRU list, remove it */
295
296 ut_a(UT_LIST_GET_LEN(system->LRU) > 0);
d8778560 297@@ -4710,7 +4720,7 @@
b4e1fa2c
AM
298 }
299
300 if (node->n_pending == 0 && node->space->purpose == FIL_TABLESPACE
301- && node->space->id != 0) {
302+ && !trx_sys_sys_space(node->space->id)) {
303 /* The node must be put back to the LRU list */
304 UT_LIST_ADD_FIRST(LRU, system->LRU, node);
305 }
d8778560 306@@ -5318,7 +5328,7 @@
b4e1fa2c
AM
307 ut_a(fil_node->n_pending == 0);
308 ut_a(fil_node->open);
309 ut_a(fil_node->space->purpose == FIL_TABLESPACE);
310- ut_a(fil_node->space->id != 0);
311+ ut_a(!trx_sys_sys_space(fil_node->space->id));
312
313 fil_node = UT_LIST_GET_NEXT(LRU, fil_node);
314 }
315diff -ruN a/storage/innobase/fsp/fsp0fsp.c b/storage/innobase/fsp/fsp0fsp.c
316--- a/storage/innobase/fsp/fsp0fsp.c 2010-11-03 07:01:13.000000000 +0900
317+++ b/storage/innobase/fsp/fsp0fsp.c 2010-12-04 15:35:58.632513243 +0900
318@@ -48,7 +48,7 @@
319 # include "log0log.h"
320 #endif /* UNIV_HOTBACKUP */
321 #include "dict0mem.h"
322-
323+#include "trx0sys.h"
324
325 #define FSP_HEADER_OFFSET FIL_PAGE_DATA /* Offset of the space header
326 within a file page */
327@@ -999,10 +999,10 @@
328 flst_init(header + FSP_SEG_INODES_FREE, mtr);
329
330 mlog_write_ull(header + FSP_SEG_ID, 1, mtr);
331- if (space == 0) {
332+ if (space == TRX_SYS_SPACE || space == TRX_DOUBLEWRITE_SPACE) {
333 fsp_fill_free_list(FALSE, space, header, mtr);
334 btr_create(DICT_CLUSTERED | DICT_UNIVERSAL | DICT_IBUF,
335- 0, 0, DICT_IBUF_ID_MIN + space,
336+ space, 0, DICT_IBUF_ID_MIN + space,
337 dict_ind_redundant, mtr);
338 } else {
339 fsp_fill_free_list(TRUE, space, header, mtr);
340diff -ruN a/storage/innobase/handler/ha_innodb.cc b/storage/innobase/handler/ha_innodb.cc
341--- a/storage/innobase/handler/ha_innodb.cc 2010-12-04 15:35:29.153514047 +0900
342+++ b/storage/innobase/handler/ha_innodb.cc 2010-12-04 15:35:58.636549909 +0900
343@@ -163,6 +163,7 @@
344 static char* innobase_log_group_home_dir = NULL;
345 static char* innobase_file_format_name = NULL;
346 static char* innobase_change_buffering = NULL;
347+static char* innobase_doublewrite_file = NULL;
348
349 /* The highest file format being used in the database. The value can be
350 set by user, however, it will be adjusted to the newer file format if
d8778560 351@@ -2426,6 +2427,8 @@
b4e1fa2c
AM
352 goto error;
353 }
354
355+ srv_doublewrite_file = innobase_doublewrite_file;
356+
357 srv_use_sys_stats_table = (ibool) innobase_use_sys_stats_table;
358
359 /* -------------- Log files ---------------------------*/
d8778560 360@@ -11556,6 +11559,11 @@
b4e1fa2c
AM
361 "Path to individual files and their sizes.",
362 NULL, NULL, NULL);
363
364+static MYSQL_SYSVAR_STR(doublewrite_file, innobase_doublewrite_file,
365+ PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
366+ "Path to special datafile for doublewrite buffer. (default is "": not used) ### ONLY FOR EXPERTS!!! ###",
367+ NULL, NULL, NULL);
368+
369 static MYSQL_SYSVAR_LONG(autoinc_lock_mode, innobase_autoinc_lock_mode,
370 PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
371 "The AUTOINC lock modes supported by InnoDB: "
d8778560 372@@ -11721,6 +11729,7 @@
b4e1fa2c
AM
373 MYSQL_SYSVAR(commit_concurrency),
374 MYSQL_SYSVAR(concurrency_tickets),
375 MYSQL_SYSVAR(data_file_path),
376+ MYSQL_SYSVAR(doublewrite_file),
377 MYSQL_SYSVAR(data_home_dir),
378 MYSQL_SYSVAR(doublewrite),
379 MYSQL_SYSVAR(recovery_stats),
380diff -ruN a/storage/innobase/include/mtr0log.ic b/storage/innobase/include/mtr0log.ic
381--- a/storage/innobase/include/mtr0log.ic 2010-11-03 07:01:13.000000000 +0900
382+++ b/storage/innobase/include/mtr0log.ic 2010-12-04 15:35:58.644607059 +0900
383@@ -27,8 +27,8 @@
384 #include "ut0lst.h"
385 #include "buf0buf.h"
386 #include "fsp0types.h"
387+#include "srv0srv.h"
388 #include "trx0sys.h"
389-
390 /********************************************************//**
391 Opens a buffer to mlog. It must be closed with mlog_close.
392 @return buffer, NULL if log mode MTR_LOG_NONE */
393@@ -201,7 +201,8 @@
394 the doublewrite buffer is located in pages
395 FSP_EXTENT_SIZE, ..., 3 * FSP_EXTENT_SIZE - 1 in the
396 system tablespace */
397- if (space == TRX_SYS_SPACE
398+ if ((space == TRX_SYS_SPACE
399+ || (srv_doublewrite_file && space == TRX_DOUBLEWRITE_SPACE))
400 && offset >= FSP_EXTENT_SIZE && offset < 3 * FSP_EXTENT_SIZE) {
401 if (trx_doublewrite_buf_is_being_created) {
402 /* Do nothing: we only come to this branch in an
403diff -ruN a/storage/innobase/include/srv0srv.h b/storage/innobase/include/srv0srv.h
404--- a/storage/innobase/include/srv0srv.h 2010-12-04 15:35:29.177480351 +0900
405+++ b/storage/innobase/include/srv0srv.h 2010-12-04 15:35:58.646556250 +0900
406@@ -132,6 +132,8 @@
407 extern ulint* srv_data_file_sizes;
408 extern ulint* srv_data_file_is_raw_partition;
409
410+extern char* srv_doublewrite_file;
411+
412 extern ibool srv_recovery_stats;
413
414 extern ibool srv_auto_extend_last_data_file;
415diff -ruN a/storage/innobase/include/srv0start.h b/storage/innobase/include/srv0start.h
416--- a/storage/innobase/include/srv0start.h 2010-11-03 07:01:13.000000000 +0900
417+++ b/storage/innobase/include/srv0start.h 2010-12-08 17:15:07.602605797 +0900
418@@ -127,4 +127,7 @@
419 /** Log 'spaces' have id's >= this */
420 #define SRV_LOG_SPACE_FIRST_ID 0xFFFFFFF0UL
421
422+/** reserved for extra system tables */
423+#define SRV_EXTRA_SYS_SPACE_FIRST_ID 0xFFFFFFE0UL
424+
425 #endif
426diff -ruN a/storage/innobase/include/trx0sys.h b/storage/innobase/include/trx0sys.h
427--- a/storage/innobase/include/trx0sys.h 2010-12-03 15:41:52.047049291 +0900
428+++ b/storage/innobase/include/trx0sys.h 2010-12-04 15:35:58.647551222 +0900
429@@ -124,6 +124,22 @@
430 /*=============*/
431 ulint space, /*!< in: space */
432 ulint page_no);/*!< in: page number */
433+/***************************************************************//**
434+Checks if a space is the system tablespaces.
435+@return TRUE if system tablespace */
436+UNIV_INLINE
437+ibool
438+trx_sys_sys_space(
439+/*==============*/
440+ ulint space); /*!< in: space */
441+/***************************************************************//**
442+Checks if a space is the doublewrite tablespace.
443+@return TRUE if doublewrite tablespace */
444+UNIV_INLINE
445+ibool
446+trx_sys_doublewrite_space(
447+/*======================*/
448+ ulint space); /*!< in: space */
449 /*****************************************************************//**
450 Creates and initializes the central memory structures for the transaction
451 system. This is called when the database is started. */
452@@ -137,6 +153,13 @@
453 void
454 trx_sys_create(void);
455 /*================*/
456+/*****************************************************************//**
457+Creates and initializes the dummy transaction system page for tablespace. */
458+UNIV_INTERN
459+void
460+trx_sys_dummy_create(
461+/*=================*/
462+ ulint space);
463 /****************************************************************//**
464 Looks for a free slot for a rollback segment in the trx system file copy.
465 @return slot index or ULINT_UNDEFINED if not found */
466@@ -448,6 +471,8 @@
467
468 /* Space id and page no where the trx system file copy resides */
469 #define TRX_SYS_SPACE 0 /* the SYSTEM tablespace */
470+#define TRX_DOUBLEWRITE_SPACE 0xFFFFFFE0UL /* the doublewrite buffer tablespace if used */
471+#define TRX_SYS_SPACE_MAX 9 /* reserved max space id for system tablespaces */
472 #include "fsp0fsp.h"
473 #define TRX_SYS_PAGE_NO FSP_TRX_SYS_PAGE_NO
474
475diff -ruN a/storage/innobase/include/trx0sys.ic b/storage/innobase/include/trx0sys.ic
476--- a/storage/innobase/include/trx0sys.ic 2010-11-03 07:01:13.000000000 +0900
477+++ b/storage/innobase/include/trx0sys.ic 2010-12-04 15:35:58.649473284 +0900
478@@ -71,6 +71,40 @@
479 }
480
481 /***************************************************************//**
482+Checks if a space is the system tablespaces.
483+@return TRUE if system tablespace */
484+UNIV_INLINE
485+ibool
486+trx_sys_sys_space(
487+/*==============*/
488+ ulint space) /*!< in: space */
489+{
490+ if (srv_doublewrite_file) {
491+ /* several spaces are reserved */
492+ return((ibool)(space == TRX_SYS_SPACE || space == TRX_DOUBLEWRITE_SPACE));
493+ } else {
494+ return((ibool)(space == TRX_SYS_SPACE));
495+ }
496+}
497+
498+/***************************************************************//**
499+Checks if a space is the doublewrite tablespace.
500+@return TRUE if doublewrite tablespace */
501+UNIV_INLINE
502+ibool
503+trx_sys_doublewrite_space(
504+/*======================*/
505+ ulint space) /*!< in: space */
506+{
507+ if (srv_doublewrite_file) {
508+ /* doublewrite buffer is separated */
509+ return((ibool)(space == TRX_DOUBLEWRITE_SPACE));
510+ } else {
511+ return((ibool)(space == TRX_SYS_SPACE));
512+ }
513+}
514+
515+/***************************************************************//**
516 Gets the pointer in the nth slot of the rseg array.
517 @return pointer to rseg object, NULL if slot not in use */
518 UNIV_INLINE
519diff -ruN a/storage/innobase/row/row0mysql.c b/storage/innobase/row/row0mysql.c
520--- a/storage/innobase/row/row0mysql.c 2010-12-03 17:30:16.334989510 +0900
521+++ b/storage/innobase/row/row0mysql.c 2010-12-04 15:35:58.652496484 +0900
d8778560 522@@ -3421,7 +3421,7 @@
b4e1fa2c
AM
523 /* Do not drop possible .ibd tablespace if something went
524 wrong: we do not want to delete valuable data of the user */
525
526- if (err == DB_SUCCESS && space_id > 0) {
527+ if (err == DB_SUCCESS && !trx_sys_sys_space(space_id)) {
528 if (!fil_space_for_table_exists_in_mem(space_id,
529 name_or_path,
530 is_temp, FALSE,
531diff -ruN a/storage/innobase/srv/srv0srv.c b/storage/innobase/srv/srv0srv.c
532--- a/storage/innobase/srv/srv0srv.c 2010-12-04 15:35:29.180483212 +0900
533+++ b/storage/innobase/srv/srv0srv.c 2010-12-04 15:35:58.656550107 +0900
d8778560 534@@ -170,6 +170,8 @@
b4e1fa2c
AM
535 /* size in database pages */
536 UNIV_INTERN ulint* srv_data_file_sizes = NULL;
537
538+UNIV_INTERN char* srv_doublewrite_file = NULL;
539+
540 UNIV_INTERN ibool srv_recovery_stats = FALSE;
541
542 /* if TRUE, then we auto-extend the last data file */
543diff -ruN a/storage/innobase/srv/srv0start.c b/storage/innobase/srv/srv0start.c
544--- a/storage/innobase/srv/srv0start.c 2010-12-04 15:35:29.183481330 +0900
545+++ b/storage/innobase/srv/srv0start.c 2010-12-04 15:35:58.661550545 +0900
546@@ -715,6 +715,7 @@
547 /*======================*/
548 ibool* create_new_db, /*!< out: TRUE if new database should be
549 created */
550+ ibool* create_new_doublewrite_file,
551 #ifdef UNIV_LOG_ARCHIVE
552 ulint* min_arch_log_no,/*!< out: min of archived log
553 numbers in data files */
554@@ -747,6 +748,7 @@
555 *sum_of_new_sizes = 0;
556
557 *create_new_db = FALSE;
558+ *create_new_doublewrite_file = FALSE;
559
560 srv_normalize_path_for_win(srv_data_home);
561
562@@ -984,6 +986,142 @@
563 srv_data_file_is_raw_partition[i] != 0);
564 }
565
566+ /* special file for doublewrite buffer */
567+ if (srv_doublewrite_file)
568+ {
569+ srv_normalize_path_for_win(srv_doublewrite_file);
570+
571+ fprintf(stderr,
d8778560
AM
572+ "InnoDB: Note: The innodb_doublewrite_file option has been specified.\n"
573+ "InnoDB: This option is for experts only. Don't use it unless you understand WELL what it is.\n"
574+ "InnoDB: ### Don't specify a file older than the last checkpoint. ###\n"
575+ "InnoDB: Otherwise, the older doublewrite buffer will break your data during recovery!\n");
b4e1fa2c
AM
576+
577+ strcpy(name, srv_doublewrite_file);
578+
579+ /* First we try to create the file: if it already
580+ exists, ret will get value FALSE */
581+
582+ files[i] = os_file_create(innodb_file_data_key, name, OS_FILE_CREATE,
583+ OS_FILE_NORMAL,
584+ OS_DATA_FILE, &ret);
585+
586+ if (ret == FALSE && os_file_get_last_error(FALSE)
587+ != OS_FILE_ALREADY_EXISTS
588+#ifdef UNIV_AIX
589+ /* AIX 5.1 after security patch ML7 may have
590+ errno set to 0 here, which causes our function
591+ to return 100; work around that AIX problem */
592+ && os_file_get_last_error(FALSE) != 100
593+#endif
594+ ) {
595+ fprintf(stderr,
596+ "InnoDB: Error in creating"
597+ " or opening %s\n",
598+ name);
599+
600+ return(DB_ERROR);
601+ }
602+
603+ if (ret == FALSE) {
604+ /* We open the data file */
605+
606+ files[i] = os_file_create(innodb_file_data_key,
607+ name, OS_FILE_OPEN, OS_FILE_NORMAL,
608+ OS_DATA_FILE, &ret);
609+
610+ if (!ret) {
611+ fprintf(stderr,
612+ "InnoDB: Error in opening %s\n", name);
613+ os_file_get_last_error(TRUE);
614+
615+ return(DB_ERROR);
616+ }
617+
618+ ret = os_file_get_size(files[i], &size, &size_high);
619+ ut_a(ret);
620+ /* Round size downward to megabytes */
621+
622+ rounded_size_pages
623+ = (size / (1024 * 1024) + 4096 * size_high)
624+ << (20 - UNIV_PAGE_SIZE_SHIFT);
625+
626+ if (rounded_size_pages != TRX_SYS_DOUBLEWRITE_BLOCK_SIZE * 9) {
627+
628+ fprintf(stderr,
629+ "InnoDB: Warning: doublewrite buffer file %s"
630+ " is of a different size\n"
631+ "InnoDB: %lu pages"
632+ " (rounded down to MB)\n"
633+ "InnoDB: than intended size"
634+ " %lu pages...\n",
635+ name,
636+ (ulong) rounded_size_pages,
637+ (ulong) TRX_SYS_DOUBLEWRITE_BLOCK_SIZE * 9);
638+ }
639+
640+ fil_read_flushed_lsn_and_arch_log_no(
641+ files[i], one_opened,
642+#ifdef UNIV_LOG_ARCHIVE
643+ min_arch_log_no, max_arch_log_no,
644+#endif /* UNIV_LOG_ARCHIVE */
645+ min_flushed_lsn, max_flushed_lsn);
646+ one_opened = TRUE;
647+ } else {
648+ /* We created the data file and now write it full of
649+ zeros */
650+
651+ *create_new_doublewrite_file = TRUE;
652+
653+ ut_print_timestamp(stderr);
654+ fprintf(stderr,
655+ " InnoDB: Doublewrite buffer file %s did not"
d8778560 656+ " exist. It will be be created.\n",
b4e1fa2c
AM
657+ name);
658+
659+ if (*create_new_db == FALSE) {
660+ fprintf(stderr,
a9ee80b9 661+ "InnoDB: Notice: Previous version's ibdata files may cause crash.\n"
b4e1fa2c
AM
662+ " If you use that, please use the ibdata files of this version.\n");
663+ }
664+
665+ ut_print_timestamp(stderr);
666+ fprintf(stderr,
667+ " InnoDB: Setting file %s size to %lu MB\n",
668+ name,
669+ (ulong) ((TRX_SYS_DOUBLEWRITE_BLOCK_SIZE * 9)
670+ >> (20 - UNIV_PAGE_SIZE_SHIFT)));
671+
672+ fprintf(stderr,
673+ "InnoDB: Database physically writes the"
674+ " file full: wait...\n");
675+
676+ ret = os_file_set_size(
677+ name, files[i],
678+ srv_calc_low32(TRX_SYS_DOUBLEWRITE_BLOCK_SIZE * 9),
679+ srv_calc_high32(TRX_SYS_DOUBLEWRITE_BLOCK_SIZE * 9));
680+
681+ if (!ret) {
682+ fprintf(stderr,
683+ "InnoDB: Error in creating %s:"
684+ " probably out of disk space\n", name);
685+
686+ return(DB_ERROR);
687+ }
688+ }
689+
690+ ret = os_file_close(files[i]);
691+ ut_a(ret);
692+
693+ fil_space_create(name, TRX_DOUBLEWRITE_SPACE, 0, FIL_TABLESPACE);
694+
695+ ut_a(fil_validate());
696+
697+ fil_node_create(name, TRX_SYS_DOUBLEWRITE_BLOCK_SIZE * 9, TRX_DOUBLEWRITE_SPACE, FALSE);
698+
699+ i++;
700+ }
701+
702 return(DB_SUCCESS);
703 }
704
705@@ -997,6 +1135,7 @@
706 /*====================================*/
707 {
708 ibool create_new_db;
709+ ibool create_new_doublewrite_file;
710 ibool log_file_created;
711 ibool log_created = FALSE;
712 ibool log_opened = FALSE;
d8778560 713@@ -1453,6 +1592,7 @@
b4e1fa2c
AM
714 }
715
716 err = open_or_create_data_files(&create_new_db,
717+ &create_new_doublewrite_file,
718 #ifdef UNIV_LOG_ARCHIVE
719 &min_arch_log_no, &max_arch_log_no,
720 #endif /* UNIV_LOG_ARCHIVE */
d8778560 721@@ -1620,6 +1760,14 @@
b4e1fa2c
AM
722 after the double write buffer has been created. */
723 trx_sys_create();
724
725+ if (create_new_doublewrite_file) {
726+ mtr_start(&mtr);
727+ fsp_header_init(TRX_DOUBLEWRITE_SPACE, TRX_SYS_DOUBLEWRITE_BLOCK_SIZE * 9, &mtr);
728+ mtr_commit(&mtr);
729+
730+ trx_sys_dummy_create(TRX_DOUBLEWRITE_SPACE);
731+ }
732+
733 dict_create();
734
735 srv_startup_is_before_trx_rollback_phase = FALSE;
d8778560 736@@ -1653,6 +1801,13 @@
b4e1fa2c
AM
737 recv_recovery_from_archive_finish();
738 #endif /* UNIV_LOG_ARCHIVE */
739 } else {
740+ char* save_srv_doublewrite_file = NULL;
741+
742+ if (create_new_doublewrite_file) {
743+ /* doublewrite_file cannot be used for recovery yet. */
744+ save_srv_doublewrite_file = srv_doublewrite_file;
745+ srv_doublewrite_file = NULL;
746+ }
747
748 /* Check if we support the max format that is stamped
749 on the system tablespace.
d8778560 750@@ -1739,6 +1894,17 @@
b4e1fa2c
AM
751 we have finished the recovery process so that the
752 image of TRX_SYS_PAGE_NO is not stale. */
753 trx_sys_file_format_tag_init();
754+
755+ if (create_new_doublewrite_file) {
756+ /* restore the value */
757+ srv_doublewrite_file = save_srv_doublewrite_file;
758+
759+ mtr_start(&mtr);
760+ fsp_header_init(TRX_DOUBLEWRITE_SPACE, TRX_SYS_DOUBLEWRITE_BLOCK_SIZE * 9, &mtr);
761+ mtr_commit(&mtr);
762+
763+ trx_sys_dummy_create(TRX_DOUBLEWRITE_SPACE);
764+ }
765 }
766
767 if (!create_new_db && sum_of_new_sizes > 0) {
768diff -ruN a/storage/innobase/trx/trx0sys.c b/storage/innobase/trx/trx0sys.c
769--- a/storage/innobase/trx/trx0sys.c 2010-12-03 17:32:15.651024019 +0900
770+++ b/storage/innobase/trx/trx0sys.c 2010-12-04 15:35:58.664550291 +0900
771@@ -414,6 +414,152 @@
772
773 goto start_again;
774 }
775+
776+ if (srv_doublewrite_file) {
777+ /* the same doublewrite buffer to TRX_SYS_SPACE should exist.
778+ check and create if not exist.*/
779+
780+ mtr_start(&mtr);
781+ trx_doublewrite_buf_is_being_created = TRUE;
782+
783+ block = buf_page_get(TRX_DOUBLEWRITE_SPACE, 0, TRX_SYS_PAGE_NO,
784+ RW_X_LATCH, &mtr);
785+ buf_block_dbg_add_level(block, SYNC_NO_ORDER_CHECK);
786+
787+ doublewrite = buf_block_get_frame(block) + TRX_SYS_DOUBLEWRITE;
788+
789+ if (mach_read_from_4(doublewrite + TRX_SYS_DOUBLEWRITE_MAGIC)
790+ == TRX_SYS_DOUBLEWRITE_MAGIC_N) {
791+ /* The doublewrite buffer has already been created:
792+ just read in some numbers */
793+
794+ mtr_commit(&mtr);
795+ } else {
796+ fprintf(stderr,
797+ "InnoDB: Doublewrite buffer not found in the doublewrite file:"
d8778560 798+ " creating new doublewrite buffer.\n");
b4e1fa2c
AM
799+
800+ if (buf_pool_get_curr_size()
801+ < ((2 * TRX_SYS_DOUBLEWRITE_BLOCK_SIZE
802+ + FSP_EXTENT_SIZE / 2 + 100)
803+ * UNIV_PAGE_SIZE)) {
804+ fprintf(stderr,
d8778560
AM
805+ "InnoDB: Cannot create the doublewrite buffer:"
806+ " You must\n"
b4e1fa2c 807+ "InnoDB: increase your buffer pool size.\n"
d8778560 808+ "InnoDB: Cannot continue processing.\n");
b4e1fa2c
AM
809+
810+ exit(1);
811+ }
812+
813+ block2 = fseg_create(TRX_DOUBLEWRITE_SPACE, TRX_SYS_PAGE_NO,
814+ TRX_SYS_DOUBLEWRITE
815+ + TRX_SYS_DOUBLEWRITE_FSEG, &mtr);
816+
817+ /* fseg_create acquires a second latch on the page,
818+ therefore we must declare it: */
819+
820+ buf_block_dbg_add_level(block2, SYNC_NO_ORDER_CHECK);
821+
822+ if (block2 == NULL) {
823+ fprintf(stderr,
d8778560
AM
824+ "InnoDB: Cannot create the doublewrite buffer:"
825+ " You must\n"
b4e1fa2c 826+ "InnoDB: increase your tablespace size.\n"
d8778560 827+ "InnoDB: Cannot continue processing.\n");
b4e1fa2c
AM
828+
829+ /* We exit without committing the mtr to prevent
830+ its modifications to the database getting to disk */
831+
832+ exit(1);
833+ }
834+
835+ fseg_header = buf_block_get_frame(block)
836+ + TRX_SYS_DOUBLEWRITE + TRX_SYS_DOUBLEWRITE_FSEG;
837+ prev_page_no = 0;
838+
839+ for (i = 0; i < 2 * TRX_SYS_DOUBLEWRITE_BLOCK_SIZE
840+ + FSP_EXTENT_SIZE / 2; i++) {
841+ page_no = fseg_alloc_free_page(fseg_header,
842+ prev_page_no + 1,
843+ FSP_UP, &mtr);
844+ if (page_no == FIL_NULL) {
845+ fprintf(stderr,
d8778560
AM
846+ "InnoDB: Cannot create the doublewrite"
847+ " buffer: You must\n"
b4e1fa2c
AM
848+ "InnoDB: increase your"
849+ " tablespace size.\n"
850+ "InnoDB: Cannot continue operation.\n"
851+ );
852+
853+ exit(1);
854+ }
855+
856+ /* We read the allocated pages to the buffer pool;
857+ when they are written to disk in a flush, the space
858+ id and page number fields are also written to the
859+ pages. When we at database startup read pages
860+ from the doublewrite buffer, we know that if the
861+ space id and page number in them are the same as
862+ the page position in the tablespace, then the page
863+ has not been written to in doublewrite. */
864+
865+#ifdef UNIV_SYNC_DEBUG
866+ new_block =
867+#endif /* UNIV_SYNC_DEBUG */
868+ buf_page_get(TRX_DOUBLEWRITE_SPACE, 0, page_no,
869+ RW_X_LATCH, &mtr);
870+ buf_block_dbg_add_level(new_block,
871+ SYNC_NO_ORDER_CHECK);
872+
873+ if (i == FSP_EXTENT_SIZE / 2) {
874+ ut_a(page_no == FSP_EXTENT_SIZE);
875+ mlog_write_ulint(doublewrite
876+ + TRX_SYS_DOUBLEWRITE_BLOCK1,
877+ page_no, MLOG_4BYTES, &mtr);
878+ mlog_write_ulint(doublewrite
879+ + TRX_SYS_DOUBLEWRITE_REPEAT
880+ + TRX_SYS_DOUBLEWRITE_BLOCK1,
881+ page_no, MLOG_4BYTES, &mtr);
882+ } else if (i == FSP_EXTENT_SIZE / 2
883+ + TRX_SYS_DOUBLEWRITE_BLOCK_SIZE) {
884+ ut_a(page_no == 2 * FSP_EXTENT_SIZE);
885+ mlog_write_ulint(doublewrite
886+ + TRX_SYS_DOUBLEWRITE_BLOCK2,
887+ page_no, MLOG_4BYTES, &mtr);
888+ mlog_write_ulint(doublewrite
889+ + TRX_SYS_DOUBLEWRITE_REPEAT
890+ + TRX_SYS_DOUBLEWRITE_BLOCK2,
891+ page_no, MLOG_4BYTES, &mtr);
892+ } else if (i > FSP_EXTENT_SIZE / 2) {
893+ ut_a(page_no == prev_page_no + 1);
894+ }
895+
896+ prev_page_no = page_no;
897+ }
898+
899+ mlog_write_ulint(doublewrite + TRX_SYS_DOUBLEWRITE_MAGIC,
900+ TRX_SYS_DOUBLEWRITE_MAGIC_N,
901+ MLOG_4BYTES, &mtr);
902+ mlog_write_ulint(doublewrite + TRX_SYS_DOUBLEWRITE_MAGIC
903+ + TRX_SYS_DOUBLEWRITE_REPEAT,
904+ TRX_SYS_DOUBLEWRITE_MAGIC_N,
905+ MLOG_4BYTES, &mtr);
906+
907+ mlog_write_ulint(doublewrite
908+ + TRX_SYS_DOUBLEWRITE_SPACE_ID_STORED,
909+ TRX_SYS_DOUBLEWRITE_SPACE_ID_STORED_N,
910+ MLOG_4BYTES, &mtr);
911+ mtr_commit(&mtr);
912+
913+ /* Flush the modified pages to disk and make a checkpoint */
914+ log_make_checkpoint_at(IB_ULONGLONG_MAX, TRUE);
915+
916+ fprintf(stderr, "InnoDB: Doublewrite buffer created in the doublewrite file\n");
917+ trx_sys_multiple_tablespace_format = TRUE;
918+ }
919+ trx_doublewrite_buf_is_being_created = FALSE;
920+ }
921 }
922
923 /****************************************************************//**
924@@ -437,10 +583,19 @@
925 ulint source_page_no;
926 byte* page;
927 byte* doublewrite;
928+ ulint doublewrite_space_id;
929 ulint space_id;
930 ulint page_no;
931 ulint i;
932
933+ doublewrite_space_id = (srv_doublewrite_file ? TRX_DOUBLEWRITE_SPACE : TRX_SYS_SPACE);
934+
935+ if (srv_doublewrite_file) {
936+ fprintf(stderr,
937+ "InnoDB: doublewrite file '%s' is used.\n",
938+ srv_doublewrite_file);
939+ }
940+
941 /* We do the file i/o past the buffer pool */
942
943 unaligned_read_buf = ut_malloc(2 * UNIV_PAGE_SIZE);
944@@ -449,7 +604,7 @@
945 /* Read the trx sys header to check if we are using the doublewrite
946 buffer */
947
948- fil_io(OS_FILE_READ, TRUE, TRX_SYS_SPACE, 0, TRX_SYS_PAGE_NO, 0,
949+ fil_io(OS_FILE_READ, TRUE, doublewrite_space_id, 0, TRX_SYS_PAGE_NO, 0,
950 UNIV_PAGE_SIZE, read_buf, NULL);
951 doublewrite = read_buf + TRX_SYS_DOUBLEWRITE;
952
953@@ -487,10 +642,10 @@
954
955 /* Read the pages from the doublewrite buffer to memory */
956
957- fil_io(OS_FILE_READ, TRUE, TRX_SYS_SPACE, 0, block1, 0,
958+ fil_io(OS_FILE_READ, TRUE, doublewrite_space_id, 0, block1, 0,
959 TRX_SYS_DOUBLEWRITE_BLOCK_SIZE * UNIV_PAGE_SIZE,
960 buf, NULL);
961- fil_io(OS_FILE_READ, TRUE, TRX_SYS_SPACE, 0, block2, 0,
962+ fil_io(OS_FILE_READ, TRUE, doublewrite_space_id, 0, block2, 0,
963 TRX_SYS_DOUBLEWRITE_BLOCK_SIZE * UNIV_PAGE_SIZE,
964 buf + TRX_SYS_DOUBLEWRITE_BLOCK_SIZE * UNIV_PAGE_SIZE,
965 NULL);
966@@ -546,7 +701,8 @@
967 " doublewrite buf.\n",
968 (ulong) space_id, (ulong) page_no, (ulong) i);
969
970- } else if (space_id == TRX_SYS_SPACE
971+ } else if ((space_id == TRX_SYS_SPACE
972+ || (srv_doublewrite_file && space_id == TRX_DOUBLEWRITE_SPACE))
973 && ((page_no >= block1
974 && page_no
975 < block1 + TRX_SYS_DOUBLEWRITE_BLOCK_SIZE)
976@@ -990,6 +1146,83 @@
977 }
978
979 /*****************************************************************//**
980+Creates dummy of the file page for the transaction system. */
981+static
982+void
983+trx_sysf_dummy_create(
984+/*==================*/
985+ ulint space,
986+ mtr_t* mtr)
987+{
988+ buf_block_t* block;
989+ page_t* page;
990+
991+ ut_ad(mtr);
992+
993+ /* Note that below we first reserve the file space x-latch, and
994+ then enter the kernel: we must do it in this order to conform
995+ to the latching order rules. */
996+
997+ mtr_x_lock(fil_space_get_latch(space, NULL), mtr);
998+ mutex_enter(&kernel_mutex);
999+
1000+ /* Create the trx sys file block in a new allocated file segment */
1001+ block = fseg_create(space, 0, TRX_SYS + TRX_SYS_FSEG_HEADER,
1002+ mtr);
1003+ buf_block_dbg_add_level(block, SYNC_TRX_SYS_HEADER);
1004+
1005+ fprintf(stderr, "%lu\n", buf_block_get_page_no(block));
1006+ ut_a(buf_block_get_page_no(block) == TRX_SYS_PAGE_NO);
1007+
1008+ page = buf_block_get_frame(block);
1009+
1010+ mlog_write_ulint(page + FIL_PAGE_TYPE, FIL_PAGE_TYPE_TRX_SYS,
1011+ MLOG_2BYTES, mtr);
1012+
1013+ /* Reset the doublewrite buffer magic number to zero so that we
1014+ know that the doublewrite buffer has not yet been created (this
1015+ suppresses a Valgrind warning) */
1016+
1017+ mlog_write_ulint(page + TRX_SYS_DOUBLEWRITE
1018+ + TRX_SYS_DOUBLEWRITE_MAGIC, 0, MLOG_4BYTES, mtr);
1019+
1020+#ifdef UNDEFINED
1021+ /* TODO: REMOVE IT: The bellow is not needed, I think */
1022+ sys_header = trx_sysf_get(mtr);
1023+
1024+ /* Start counting transaction ids from number 1 up */
1025+ mlog_write_dulint(sys_header + TRX_SYS_TRX_ID_STORE,
1026+ ut_dulint_create(0, 1), mtr);
1027+
1028+ /* Reset the rollback segment slots */
1029+ for (i = 0; i < TRX_SYS_N_RSEGS; i++) {
1030+
1031+ trx_sysf_rseg_set_space(sys_header, i, ULINT_UNDEFINED, mtr);
1032+ trx_sysf_rseg_set_page_no(sys_header, i, FIL_NULL, mtr);
1033+ }
1034+
1035+ /* The remaining area (up to the page trailer) is uninitialized.
1036+ Silence Valgrind warnings about it. */
1037+ UNIV_MEM_VALID(sys_header + (TRX_SYS_RSEGS
1038+ + TRX_SYS_N_RSEGS * TRX_SYS_RSEG_SLOT_SIZE
1039+ + TRX_SYS_RSEG_SPACE),
1040+ (UNIV_PAGE_SIZE - FIL_PAGE_DATA_END
1041+ - (TRX_SYS_RSEGS
1042+ + TRX_SYS_N_RSEGS * TRX_SYS_RSEG_SLOT_SIZE
1043+ + TRX_SYS_RSEG_SPACE))
1044+ + page - sys_header);
1045+
1046+ /* Create the first rollback segment in the SYSTEM tablespace */
1047+ page_no = trx_rseg_header_create(space, 0, ULINT_MAX, &slot_no,
1048+ mtr);
1049+ ut_a(slot_no == TRX_SYS_SYSTEM_RSEG_ID);
1050+ ut_a(page_no != FIL_NULL);
1051+#endif
1052+
1053+ mutex_exit(&kernel_mutex);
1054+}
1055+
1056+/*****************************************************************//**
1057 Creates and initializes the central memory structures for the transaction
1058 system. This is called when the database is started. */
1059 UNIV_INTERN
1060@@ -1351,6 +1584,26 @@
1061 /* Does nothing at the moment */
1062 }
1063
1064+/*****************************************************************//**
1065+Creates and initializes the dummy transaction system page for tablespace. */
1066+UNIV_INTERN
1067+void
1068+trx_sys_dummy_create(
1069+/*=================*/
1070+ ulint space)
1071+{
1072+ mtr_t mtr;
1073+
1074+ /* This function is only for doublewrite file for now */
1075+ ut_a(space == TRX_DOUBLEWRITE_SPACE);
1076+
1077+ mtr_start(&mtr);
1078+
1079+ trx_sysf_dummy_create(space, &mtr);
1080+
1081+ mtr_commit(&mtr);
1082+}
1083+
1084 /*********************************************************************
1085 Creates the rollback segments */
1086 UNIV_INTERN
This page took 0.150344 seconds and 4 git commands to generate.