~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to plugin/innobase/srv/srv0start.c

  • Committer: Brian Aker
  • Date: 2010-12-18 18:24:57 UTC
  • mfrom: (1999.6.3 trunk)
  • Revision ID: brian@tangent.org-20101218182457-yi1wd0so2hml1k1w
Merge in Lee's copyright header fix

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/*****************************************************************************
 
2
 
 
3
Copyright (C) 1996, 2010, Innobase Oy. All Rights Reserved.
 
4
Copyright (C) 2008, Google Inc.
 
5
Copyright (C) 2009, Percona Inc.
 
6
 
 
7
Portions of this file contain modifications contributed and copyrighted by
 
8
Google, Inc. Those modifications are gratefully acknowledged and are described
 
9
briefly in the InnoDB documentation. The contributions by Google are
 
10
incorporated with their permission, and subject to the conditions contained in
 
11
the file COPYING.Google.
 
12
 
 
13
Portions of this file contain modifications contributed and copyrighted
 
14
by Percona Inc.. Those modifications are
 
15
gratefully acknowledged and are described briefly in the InnoDB
 
16
documentation. The contributions by Percona Inc. are incorporated with
 
17
their permission, and subject to the conditions contained in the file
 
18
COPYING.Percona.
 
19
 
 
20
This program is free software; you can redistribute it and/or modify it under
 
21
the terms of the GNU General Public License as published by the Free Software
 
22
Foundation; version 2 of the License.
 
23
 
 
24
This program is distributed in the hope that it will be useful, but WITHOUT
 
25
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
 
26
FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
 
27
 
 
28
You should have received a copy of the GNU General Public License along with
 
29
this program; if not, write to the Free Software Foundation, Inc., 51 Franklin
 
30
St, Fifth Floor, Boston, MA 02110-1301 USA
 
31
 
 
32
*****************************************************************************/
 
33
 
 
34
/********************************************************************//**
 
35
@file srv/srv0start.c
 
36
Starts the InnoDB database server
 
37
 
 
38
Created 2/16/1996 Heikki Tuuri
 
39
*************************************************************************/
 
40
 
 
41
#include "ut0mem.h"
 
42
#include "mem0mem.h"
 
43
#include "data0data.h"
 
44
#include "data0type.h"
 
45
#include "dict0dict.h"
 
46
#include "buf0buf.h"
 
47
#include "os0file.h"
 
48
#include "os0thread.h"
 
49
#include "fil0fil.h"
 
50
#include "fsp0fsp.h"
 
51
#include "rem0rec.h"
 
52
#include "mtr0mtr.h"
 
53
#include "log0log.h"
 
54
#include "log0recv.h"
 
55
#include "page0page.h"
 
56
#include "page0cur.h"
 
57
#include "trx0trx.h"
 
58
#include "trx0sys.h"
 
59
#include "btr0btr.h"
 
60
#include "btr0cur.h"
 
61
#include "rem0rec.h"
 
62
#include "ibuf0ibuf.h"
 
63
#include "srv0start.h"
 
64
#include "srv0srv.h"
 
65
#ifndef UNIV_HOTBACKUP
 
66
# include "os0proc.h"
 
67
# include "sync0sync.h"
 
68
# include "buf0flu.h"
 
69
# include "buf0rea.h"
 
70
# include "dict0boot.h"
 
71
# include "dict0load.h"
 
72
# include "que0que.h"
 
73
# include "usr0sess.h"
 
74
# include "lock0lock.h"
 
75
# include "trx0roll.h"
 
76
# include "trx0purge.h"
 
77
# include "lock0lock.h"
 
78
# include "pars0pars.h"
 
79
# include "btr0sea.h"
 
80
# include "rem0cmp.h"
 
81
# include "dict0crea.h"
 
82
# include "row0ins.h"
 
83
# include "row0sel.h"
 
84
# include "row0upd.h"
 
85
# include "row0row.h"
 
86
# include "row0mysql.h"
 
87
# include "btr0pcur.h"
 
88
# include "thr0loc.h"
 
89
# include "os0sync.h" /* for INNODB_RW_LOCKS_USE_ATOMICS */
 
90
# include "zlib.h" /* for ZLIB_VERSION */
 
91
 
 
92
#include <errno.h>
 
93
#include <unistd.h>
 
94
 
 
95
/** Log sequence number immediately after startup */
 
96
UNIV_INTERN ib_uint64_t srv_start_lsn;
 
97
/** Log sequence number at shutdown */
 
98
UNIV_INTERN ib_uint64_t srv_shutdown_lsn;
 
99
 
 
100
#ifdef HAVE_DARWIN_THREADS
 
101
# include <sys/utsname.h>
 
102
/** TRUE if the F_FULLFSYNC option is available */
 
103
UNIV_INTERN ibool       srv_have_fullfsync = FALSE;
 
104
#endif
 
105
 
 
106
/** TRUE if a raw partition is in use */
 
107
UNIV_INTERN ibool       srv_start_raw_disk_in_use = FALSE;
 
108
 
 
109
/** TRUE if the server is being started, before rolling back any
 
110
incomplete transactions */
 
111
UNIV_INTERN ibool       srv_startup_is_before_trx_rollback_phase = FALSE;
 
112
/** TRUE if the server is being started */
 
113
UNIV_INTERN ibool       srv_is_being_started = FALSE;
 
114
/** TRUE if the server was successfully started */
 
115
UNIV_INTERN ibool       srv_was_started = FALSE;
 
116
/** TRUE if innobase_start_or_create_for_mysql() has been called */
 
117
static ibool    srv_start_has_been_called = FALSE;
 
118
 
 
119
/** At a shutdown this value climbs from SRV_SHUTDOWN_NONE to
 
120
SRV_SHUTDOWN_CLEANUP and then to SRV_SHUTDOWN_LAST_PHASE, and so on */
 
121
UNIV_INTERN enum srv_shutdown_state     srv_shutdown_state = SRV_SHUTDOWN_NONE;
 
122
 
 
123
/** Files comprising the system tablespace */
 
124
static os_file_t        files[1000];
 
125
 
 
126
/** Mutex protecting the ios count */
 
127
static mutex_t          ios_mutex;
 
128
/** Count of I/O operations in io_handler_thread() */
 
129
static ulint            ios;
 
130
 
 
131
/** io_handler_thread parameters for thread identification */
 
132
static ulint            n[SRV_MAX_N_IO_THREADS + 6];
 
133
/** io_handler_thread identifiers */
 
134
static os_thread_id_t   thread_ids[SRV_MAX_N_IO_THREADS + 6];
 
135
 
 
136
/** We use this mutex to test the return value of pthread_mutex_trylock
 
137
   on successful locking. HP-UX does NOT return 0, though Linux et al do. */
 
138
static os_fast_mutex_t  srv_os_test_mutex;
 
139
 
 
140
/** Name of srv_monitor_file */
 
141
static char*    srv_monitor_file_name;
 
142
#endif /* !UNIV_HOTBACKUP */
 
143
 
 
144
/** */
 
145
#define SRV_N_PENDING_IOS_PER_THREAD    OS_AIO_N_PENDING_IOS_PER_THREAD
 
146
#define SRV_MAX_N_PENDING_SYNC_IOS      100
 
147
 
 
148
#ifdef UNIV_PFS_THREAD
 
149
/* Keys to register InnoDB threads with performance schema */
 
150
UNIV_INTERN mysql_pfs_key_t     io_handler_thread_key;
 
151
UNIV_INTERN mysql_pfs_key_t     srv_lock_timeout_thread_key;
 
152
UNIV_INTERN mysql_pfs_key_t     srv_error_monitor_thread_key;
 
153
UNIV_INTERN mysql_pfs_key_t     srv_monitor_thread_key;
 
154
UNIV_INTERN mysql_pfs_key_t     srv_master_thread_key;
 
155
#endif /* UNIV_PFS_THREAD */
 
156
 
 
157
#ifdef UNIV_PFS_MUTEX
 
158
/* Key to register ios_mutex_key with performance schema */
 
159
UNIV_INTERN mysql_pfs_key_t     ios_mutex_key;
 
160
#endif /* UNIV_PFS_MUTEX */
 
161
 
 
162
/*********************************************************************//**
 
163
Convert a numeric string that optionally ends in G or M, to a number
 
164
containing megabytes.
 
165
@return next character in string */
 
166
static
 
167
char*
 
168
srv_parse_megabytes(
 
169
/*================*/
 
170
        char*   str,    /*!< in: string containing a quantity in bytes */
 
171
        ulint*  megs)   /*!< out: the number in megabytes */
 
172
{
 
173
        char*   endp;
 
174
        ulint   size;
 
175
 
 
176
        size = strtoul(str, &endp, 10);
 
177
 
 
178
        str = endp;
 
179
 
 
180
        switch (*str) {
 
181
        case 'G': case 'g':
 
182
                size *= 1024;
 
183
                /* fall through */
 
184
        case 'M': case 'm':
 
185
                str++;
 
186
                break;
 
187
        default:
 
188
                size /= 1024 * 1024;
 
189
                break;
 
190
        }
 
191
 
 
192
        *megs = size;
 
193
        return(str);
 
194
}
 
195
 
 
196
/*********************************************************************//**
 
197
Reads the data files and their sizes from a character string given in
 
198
the .cnf file.
 
199
@return TRUE if ok, FALSE on parse error */
 
200
UNIV_INTERN
 
201
ibool
 
202
srv_parse_data_file_paths_and_sizes(
 
203
/*================================*/
 
204
        char*   str)    /*!< in/out: the data file path string */
 
205
{
 
206
        char*   input_str;
 
207
        char*   path;
 
208
        ulint   size;
 
209
        ulint   i       = 0;
 
210
 
 
211
        srv_auto_extend_last_data_file = FALSE;
 
212
        srv_last_file_size_max = 0;
 
213
        srv_data_file_names = NULL;
 
214
        srv_data_file_sizes = NULL;
 
215
        srv_data_file_is_raw_partition = NULL;
 
216
 
 
217
        input_str = str;
 
218
 
 
219
        /* First calculate the number of data files and check syntax:
 
220
        path:size[M | G];path:size[M | G]... . Note that a Windows path may
 
221
        contain a drive name and a ':'. */
 
222
 
 
223
        while (*str != '\0') {
 
224
                path = str;
 
225
 
 
226
                while ((*str != ':' && *str != '\0')
 
227
                       || (*str == ':'
 
228
                           && (*(str + 1) == '\\' || *(str + 1) == '/'
 
229
                               || *(str + 1) == ':'))) {
 
230
                        str++;
 
231
                }
 
232
 
 
233
                if (*str == '\0') {
 
234
                        return(FALSE);
 
235
                }
 
236
 
 
237
                str++;
 
238
 
 
239
                str = srv_parse_megabytes(str, &size);
 
240
 
 
241
                if (0 == strncmp(str, ":autoextend",
 
242
                                 (sizeof ":autoextend") - 1)) {
 
243
 
 
244
                        str += (sizeof ":autoextend") - 1;
 
245
 
 
246
                        if (0 == strncmp(str, ":max:",
 
247
                                         (sizeof ":max:") - 1)) {
 
248
 
 
249
                                str += (sizeof ":max:") - 1;
 
250
 
 
251
                                str = srv_parse_megabytes(str, &size);
 
252
                        }
 
253
 
 
254
                        if (*str != '\0') {
 
255
 
 
256
                                return(FALSE);
 
257
                        }
 
258
                }
 
259
 
 
260
                if (strlen(str) >= 6
 
261
                    && *str == 'n'
 
262
                    && *(str + 1) == 'e'
 
263
                    && *(str + 2) == 'w') {
 
264
                        str += 3;
 
265
                }
 
266
 
 
267
                if (*str == 'r' && *(str + 1) == 'a' && *(str + 2) == 'w') {
 
268
                        str += 3;
 
269
                }
 
270
 
 
271
                if (size == 0) {
 
272
                        return(FALSE);
 
273
                }
 
274
 
 
275
                i++;
 
276
 
 
277
                if (*str == ';') {
 
278
                        str++;
 
279
                } else if (*str != '\0') {
 
280
 
 
281
                        return(FALSE);
 
282
                }
 
283
        }
 
284
 
 
285
        if (i == 0) {
 
286
                /* If innodb_data_file_path was defined it must contain
 
287
                at least one data file definition */
 
288
 
 
289
                return(FALSE);
 
290
        }
 
291
 
 
292
        srv_data_file_names = malloc(i * sizeof *srv_data_file_names);
 
293
        srv_data_file_sizes = malloc(i * sizeof *srv_data_file_sizes);
 
294
        srv_data_file_is_raw_partition = malloc(
 
295
                i * sizeof *srv_data_file_is_raw_partition);
 
296
 
 
297
        srv_n_data_files = i;
 
298
 
 
299
        /* Then store the actual values to our arrays */
 
300
 
 
301
        str = input_str;
 
302
        i = 0;
 
303
 
 
304
        while (*str != '\0') {
 
305
                path = str;
 
306
 
 
307
                /* Note that we must step over the ':' in a Windows path;
 
308
                a Windows path normally looks like C:\ibdata\ibdata1:1G, but
 
309
                a Windows raw partition may have a specification like
 
310
                \\.\C::1Gnewraw or \\.\PHYSICALDRIVE2:1Gnewraw */
 
311
 
 
312
                while ((*str != ':' && *str != '\0')
 
313
                       || (*str == ':'
 
314
                           && (*(str + 1) == '\\' || *(str + 1) == '/'
 
315
                               || *(str + 1) == ':'))) {
 
316
                        str++;
 
317
                }
 
318
 
 
319
                if (*str == ':') {
 
320
                        /* Make path a null-terminated string */
 
321
                        *str = '\0';
 
322
                        str++;
 
323
                }
 
324
 
 
325
                str = srv_parse_megabytes(str, &size);
 
326
 
 
327
                srv_data_file_names[i] = path;
 
328
                srv_data_file_sizes[i] = size;
 
329
 
 
330
                if (0 == strncmp(str, ":autoextend",
 
331
                                 (sizeof ":autoextend") - 1)) {
 
332
 
 
333
                        srv_auto_extend_last_data_file = TRUE;
 
334
 
 
335
                        str += (sizeof ":autoextend") - 1;
 
336
 
 
337
                        if (0 == strncmp(str, ":max:",
 
338
                                         (sizeof ":max:") - 1)) {
 
339
 
 
340
                                str += (sizeof ":max:") - 1;
 
341
 
 
342
                                str = srv_parse_megabytes(
 
343
                                        str, &srv_last_file_size_max);
 
344
                        }
 
345
 
 
346
                        if (*str != '\0') {
 
347
 
 
348
                                return(FALSE);
 
349
                        }
 
350
                }
 
351
 
 
352
                (srv_data_file_is_raw_partition)[i] = 0;
 
353
 
 
354
                if (strlen(str) >= 6
 
355
                    && *str == 'n'
 
356
                    && *(str + 1) == 'e'
 
357
                    && *(str + 2) == 'w') {
 
358
                        str += 3;
 
359
                        (srv_data_file_is_raw_partition)[i] = SRV_NEW_RAW;
 
360
                }
 
361
 
 
362
                if (*str == 'r' && *(str + 1) == 'a' && *(str + 2) == 'w') {
 
363
                        str += 3;
 
364
 
 
365
                        if ((srv_data_file_is_raw_partition)[i] == 0) {
 
366
                                (srv_data_file_is_raw_partition)[i] = SRV_OLD_RAW;
 
367
                        }
 
368
                }
 
369
 
 
370
                i++;
 
371
 
 
372
                if (*str == ';') {
 
373
                        str++;
 
374
                }
 
375
        }
 
376
 
 
377
        return(TRUE);
 
378
}
 
379
 
 
380
/*********************************************************************//**
 
381
Reads log group home directories from a character string given in
 
382
the .cnf file.
 
383
@return TRUE if ok, FALSE on parse error */
 
384
UNIV_INTERN
 
385
ibool
 
386
srv_parse_log_group_home_dirs(
 
387
/*==========================*/
 
388
        char*   str)    /*!< in/out: character string */
 
389
{
 
390
        char*   input_str;
 
391
        char*   path;
 
392
        ulint   i       = 0;
 
393
 
 
394
        srv_log_group_home_dirs = NULL;
 
395
 
 
396
        input_str = str;
 
397
 
 
398
        /* First calculate the number of directories and check syntax:
 
399
        path;path;... */
 
400
 
 
401
        while (*str != '\0') {
 
402
                path = str;
 
403
 
 
404
                while (*str != ';' && *str != '\0') {
 
405
                        str++;
 
406
                }
 
407
 
 
408
                i++;
 
409
 
 
410
                if (*str == ';') {
 
411
                        str++;
 
412
                } else if (*str != '\0') {
 
413
 
 
414
                        return(FALSE);
 
415
                }
 
416
        }
 
417
 
 
418
        if (i != 1) {
 
419
                /* If innodb_log_group_home_dir was defined it must
 
420
                contain exactly one path definition under current MySQL */
 
421
 
 
422
                return(FALSE);
 
423
        }
 
424
 
 
425
        srv_log_group_home_dirs = malloc(i * sizeof *srv_log_group_home_dirs);
 
426
 
 
427
        /* Then store the actual values to our array */
 
428
 
 
429
        str = input_str;
 
430
        i = 0;
 
431
 
 
432
        while (*str != '\0') {
 
433
                path = str;
 
434
 
 
435
                while (*str != ';' && *str != '\0') {
 
436
                        str++;
 
437
                }
 
438
 
 
439
                if (*str == ';') {
 
440
                        *str = '\0';
 
441
                        str++;
 
442
                }
 
443
 
 
444
                srv_log_group_home_dirs[i] = path;
 
445
 
 
446
                i++;
 
447
        }
 
448
 
 
449
        return(TRUE);
 
450
}
 
451
 
 
452
/*********************************************************************//**
 
453
Frees the memory allocated by srv_parse_data_file_paths_and_sizes()
 
454
and srv_parse_log_group_home_dirs(). */
 
455
UNIV_INTERN
 
456
void
 
457
srv_free_paths_and_sizes(void)
 
458
/*==========================*/
 
459
{
 
460
        free(srv_data_file_names);
 
461
        srv_data_file_names = NULL;
 
462
        free(srv_data_file_sizes);
 
463
        srv_data_file_sizes = NULL;
 
464
        free(srv_data_file_is_raw_partition);
 
465
        srv_data_file_is_raw_partition = NULL;
 
466
        free(srv_log_group_home_dirs);
 
467
        srv_log_group_home_dirs = NULL;
 
468
}
 
469
 
 
470
#ifndef UNIV_HOTBACKUP
 
471
/********************************************************************//**
 
472
I/o-handler thread function.
 
473
@return OS_THREAD_DUMMY_RETURN */
 
474
static
 
475
os_thread_ret_t
 
476
io_handler_thread(
 
477
/*==============*/
 
478
        void*   arg)    /*!< in: pointer to the number of the segment in
 
479
                        the aio array */
 
480
{
 
481
        ulint   segment;
 
482
 
 
483
        segment = *((ulint*)arg);
 
484
 
 
485
#ifdef UNIV_DEBUG_THREAD_CREATION
 
486
        fprintf(stderr, "Io handler thread %lu starts, id %lu\n", segment,
 
487
                os_thread_pf(os_thread_get_curr_id()));
 
488
#endif
 
489
 
 
490
#ifdef UNIV_PFS_THREAD
 
491
        pfs_register_thread(io_handler_thread_key);
 
492
#endif /* UNIV_PFS_THREAD */
 
493
 
 
494
        while (srv_shutdown_state != SRV_SHUTDOWN_EXIT_THREADS) {
 
495
                fil_aio_wait(segment);
 
496
 
 
497
                mutex_enter(&ios_mutex);
 
498
                ios++;
 
499
                mutex_exit(&ios_mutex);
 
500
        }
 
501
 
 
502
        thr_local_free(os_thread_get_curr_id());
 
503
 
 
504
        /* We count the number of threads in os_thread_exit(). A created
 
505
        thread should always use that to exit and not use return() to exit.
 
506
        The thread actually never comes here because it is exited in an
 
507
        os_event_wait(). */
 
508
        return 0;
 
509
}
 
510
#endif /* !UNIV_HOTBACKUP */
 
511
 
 
512
#ifdef __WIN__
 
513
#define SRV_PATH_SEPARATOR      '\\'
 
514
#else
 
515
#define SRV_PATH_SEPARATOR      '/'
 
516
#endif
 
517
 
 
518
/*********************************************************************//**
 
519
Normalizes a directory path for Windows: converts slashes to backslashes. */
 
520
UNIV_INTERN
 
521
void
 
522
srv_normalize_path_for_win(
 
523
/*=======================*/
 
524
        char*   str __attribute__((unused)))    /*!< in/out: null-terminated
 
525
                                                character string */
 
526
{
 
527
#ifdef __WIN__
 
528
        for (; *str; str++) {
 
529
 
 
530
                if (*str == '/') {
 
531
                        *str = '\\';
 
532
                }
 
533
        }
 
534
#endif
 
535
}
 
536
 
 
537
#ifndef UNIV_HOTBACKUP
 
538
/*********************************************************************//**
 
539
Calculates the low 32 bits when a file size which is given as a number
 
540
database pages is converted to the number of bytes.
 
541
@return low 32 bytes of file size when expressed in bytes */
 
542
static
 
543
ulint
 
544
srv_calc_low32(
 
545
/*===========*/
 
546
        ulint   file_size)      /*!< in: file size in database pages */
 
547
{
 
548
        return(0xFFFFFFFFUL & (file_size << UNIV_PAGE_SIZE_SHIFT));
 
549
}
 
550
 
 
551
/*********************************************************************//**
 
552
Calculates the high 32 bits when a file size which is given as a number
 
553
database pages is converted to the number of bytes.
 
554
@return high 32 bytes of file size when expressed in bytes */
 
555
static
 
556
ulint
 
557
srv_calc_high32(
 
558
/*============*/
 
559
        ulint   file_size)      /*!< in: file size in database pages */
 
560
{
 
561
        return(file_size >> (32 - UNIV_PAGE_SIZE_SHIFT));
 
562
}
 
563
 
 
564
/*********************************************************************//**
 
565
Creates or opens the log files and closes them.
 
566
@return DB_SUCCESS or error code */
 
567
static
 
568
ulint
 
569
open_or_create_log_file(
 
570
/*====================*/
 
571
        ibool   create_new_db,          /*!< in: TRUE if we should create a
 
572
                                        new database */
 
573
        ibool*  log_file_created,       /*!< out: TRUE if new log file
 
574
                                        created */
 
575
        ibool   log_file_has_been_opened,/*!< in: TRUE if a log file has been
 
576
                                        opened before: then it is an error
 
577
                                        to try to create another log file */
 
578
        ulint   k,                      /*!< in: log group number */
 
579
        ulint   i)                      /*!< in: log file number in group */
 
580
{
 
581
        ibool   ret;
 
582
        ulint   size;
 
583
        ulint   size_high;
 
584
        char    name[10000];
 
585
        ulint   dirnamelen;
 
586
 
 
587
        UT_NOT_USED(create_new_db);
 
588
 
 
589
        *log_file_created = FALSE;
 
590
 
 
591
        srv_normalize_path_for_win(srv_log_group_home_dirs[k]);
 
592
 
 
593
        dirnamelen = strlen(srv_log_group_home_dirs[k]);
 
594
        ut_a(dirnamelen < (sizeof name) - 10 - sizeof "ib_logfile");
 
595
        memcpy(name, srv_log_group_home_dirs[k], dirnamelen);
 
596
 
 
597
        /* Add a path separator if needed. */
 
598
        if (dirnamelen && name[dirnamelen - 1] != SRV_PATH_SEPARATOR) {
 
599
                name[dirnamelen++] = SRV_PATH_SEPARATOR;
 
600
        }
 
601
 
 
602
        sprintf(name + dirnamelen, "%s%lu", "ib_logfile", (ulong) i);
 
603
 
 
604
        files[i] = os_file_create(innodb_file_log_key, name,
 
605
                                  OS_FILE_CREATE, OS_FILE_NORMAL,
 
606
                                  OS_LOG_FILE, &ret);
 
607
        if (ret == FALSE) {
 
608
                if (os_file_get_last_error(FALSE) != OS_FILE_ALREADY_EXISTS
 
609
#ifdef UNIV_AIX
 
610
                    /* AIX 5.1 after security patch ML7 may have errno set
 
611
                    to 0 here, which causes our function to return 100;
 
612
                    work around that AIX problem */
 
613
                    && os_file_get_last_error(FALSE) != 100
 
614
#endif
 
615
                    ) {
 
616
                        fprintf(stderr,
 
617
                                "InnoDB: Error in creating"
 
618
                                " or opening %s\n", name);
 
619
 
 
620
                        return(DB_ERROR);
 
621
                }
 
622
 
 
623
                files[i] = os_file_create(innodb_file_log_key, name,
 
624
                                          OS_FILE_OPEN, OS_FILE_AIO,
 
625
                                          OS_LOG_FILE, &ret);
 
626
                if (!ret) {
 
627
                        fprintf(stderr,
 
628
                                "InnoDB: Error in opening %s\n", name);
 
629
 
 
630
                        return(DB_ERROR);
 
631
                }
 
632
 
 
633
                ret = os_file_get_size(files[i], &size, &size_high);
 
634
                ut_a(ret);
 
635
 
 
636
                if (size != srv_calc_low32(srv_log_file_size)
 
637
                    || size_high != srv_calc_high32(srv_log_file_size)) {
 
638
 
 
639
                        fprintf(stderr,
 
640
                                "InnoDB: Error: log file %s is"
 
641
                                " of different size %lu %lu bytes\n"
 
642
                                "InnoDB: than specified in the .cnf"
 
643
                                " file %lu %lu bytes!\n",
 
644
                                name, (ulong) size_high, (ulong) size,
 
645
                                (ulong) srv_calc_high32(srv_log_file_size),
 
646
                                (ulong) srv_calc_low32(srv_log_file_size));
 
647
 
 
648
                        return(DB_ERROR);
 
649
                }
 
650
        } else {
 
651
                *log_file_created = TRUE;
 
652
 
 
653
                ut_print_timestamp(stderr);
 
654
 
 
655
                fprintf(stderr,
 
656
                        "  InnoDB: Log file %s did not exist:"
 
657
                        " new to be created\n",
 
658
                        name);
 
659
                if (log_file_has_been_opened) {
 
660
 
 
661
                        return(DB_ERROR);
 
662
                }
 
663
 
 
664
                fprintf(stderr, "InnoDB: Setting log file %s size to %lu MB\n",
 
665
                        name, (ulong) srv_log_file_size
 
666
                        >> (20 - UNIV_PAGE_SIZE_SHIFT));
 
667
 
 
668
                fprintf(stderr,
 
669
                        "InnoDB: Database physically writes the file"
 
670
                        " full: wait...\n");
 
671
 
 
672
                ret = os_file_set_size(name, files[i],
 
673
                                       srv_calc_low32(srv_log_file_size),
 
674
                                       srv_calc_high32(srv_log_file_size));
 
675
                if (!ret) {
 
676
                        fprintf(stderr,
 
677
                                "InnoDB: Error in creating %s:"
 
678
                                " probably out of disk space\n",
 
679
                                name);
 
680
 
 
681
                        return(DB_ERROR);
 
682
                }
 
683
        }
 
684
 
 
685
        ret = os_file_close(files[i]);
 
686
        ut_a(ret);
 
687
 
 
688
        if (i == 0) {
 
689
                /* Create in memory the file space object
 
690
                which is for this log group */
 
691
 
 
692
                fil_space_create(name,
 
693
                                 2 * k + SRV_LOG_SPACE_FIRST_ID, 0, FIL_LOG);
 
694
        }
 
695
 
 
696
        ut_a(fil_validate());
 
697
 
 
698
        fil_node_create(name, srv_log_file_size,
 
699
                        2 * k + SRV_LOG_SPACE_FIRST_ID, FALSE);
 
700
#ifdef UNIV_LOG_ARCHIVE
 
701
        /* If this is the first log group, create the file space object
 
702
        for archived logs.
 
703
        Under MySQL, no archiving ever done. */
 
704
 
 
705
        if (k == 0 && i == 0) {
 
706
                arch_space_id = 2 * k + 1 + SRV_LOG_SPACE_FIRST_ID;
 
707
 
 
708
                fil_space_create("arch_log_space", arch_space_id, 0, FIL_LOG);
 
709
        } else {
 
710
                arch_space_id = ULINT_UNDEFINED;
 
711
        }
 
712
#endif /* UNIV_LOG_ARCHIVE */
 
713
        if (i == 0) {
 
714
                log_group_init(k, srv_n_log_files,
 
715
                               srv_log_file_size * UNIV_PAGE_SIZE,
 
716
                               2 * k + SRV_LOG_SPACE_FIRST_ID,
 
717
                               SRV_LOG_SPACE_FIRST_ID + 1); /* dummy arch
 
718
                                                            space id */
 
719
        }
 
720
 
 
721
        return(DB_SUCCESS);
 
722
}
 
723
 
 
724
/*********************************************************************//**
 
725
Creates or opens database data files and closes them.
 
726
@return DB_SUCCESS or error code */
 
727
static
 
728
ulint
 
729
open_or_create_data_files(
 
730
/*======================*/
 
731
        ibool*          create_new_db,  /*!< out: TRUE if new database should be
 
732
                                        created */
 
733
#ifdef UNIV_LOG_ARCHIVE
 
734
        ulint*          min_arch_log_no,/*!< out: min of archived log
 
735
                                        numbers in data files */
 
736
        ulint*          max_arch_log_no,/*!< out: max of archived log
 
737
                                        numbers in data files */
 
738
#endif /* UNIV_LOG_ARCHIVE */
 
739
        ib_uint64_t*    min_flushed_lsn,/*!< out: min of flushed lsn
 
740
                                        values in data files */
 
741
        ib_uint64_t*    max_flushed_lsn,/*!< out: max of flushed lsn
 
742
                                        values in data files */
 
743
        ulint*          sum_of_new_sizes)/*!< out: sum of sizes of the
 
744
                                        new files added */
 
745
{
 
746
        ibool   ret;
 
747
        ulint   i;
 
748
        ibool   one_opened      = FALSE;
 
749
        ibool   one_created     = FALSE;
 
750
        ulint   size;
 
751
        ulint   size_high;
 
752
        ulint   rounded_size_pages;
 
753
        char    name[10000];
 
754
 
 
755
        if (srv_n_data_files >= 1000) {
 
756
                fprintf(stderr, "InnoDB: can only have < 1000 data files\n"
 
757
                        "InnoDB: you have defined %lu\n",
 
758
                        (ulong) srv_n_data_files);
 
759
                return(DB_ERROR);
 
760
        }
 
761
 
 
762
        *sum_of_new_sizes = 0;
 
763
 
 
764
        *create_new_db = FALSE;
 
765
 
 
766
        srv_normalize_path_for_win(srv_data_home);
 
767
 
 
768
        for (i = 0; i < srv_n_data_files; i++) {
 
769
                ulint   dirnamelen;
 
770
 
 
771
                srv_normalize_path_for_win(srv_data_file_names[i]);
 
772
                dirnamelen = strlen(srv_data_home);
 
773
 
 
774
                ut_a(dirnamelen + strlen(srv_data_file_names[i])
 
775
                     < (sizeof name) - 1);
 
776
                memcpy(name, srv_data_home, dirnamelen);
 
777
                /* Add a path separator if needed. */
 
778
                if (dirnamelen && name[dirnamelen - 1] != SRV_PATH_SEPARATOR) {
 
779
                        name[dirnamelen++] = SRV_PATH_SEPARATOR;
 
780
                }
 
781
 
 
782
                strcpy(name + dirnamelen, srv_data_file_names[i]);
 
783
 
 
784
                if (srv_data_file_is_raw_partition[i] == 0) {
 
785
 
 
786
                        /* First we try to create the file: if it already
 
787
                        exists, ret will get value FALSE */
 
788
 
 
789
                        files[i] = os_file_create(innodb_file_data_key,
 
790
                                                  name, OS_FILE_CREATE,
 
791
                                                  OS_FILE_NORMAL,
 
792
                                                  OS_DATA_FILE, &ret);
 
793
 
 
794
                        if (ret == FALSE && os_file_get_last_error(FALSE)
 
795
                            != OS_FILE_ALREADY_EXISTS
 
796
#ifdef UNIV_AIX
 
797
                            /* AIX 5.1 after security patch ML7 may have
 
798
                            errno set to 0 here, which causes our function
 
799
                            to return 100; work around that AIX problem */
 
800
                            && os_file_get_last_error(FALSE) != 100
 
801
#endif
 
802
                            ) {
 
803
                                fprintf(stderr,
 
804
                                        "InnoDB: Error in creating"
 
805
                                        " or opening %s\n",
 
806
                                        name);
 
807
 
 
808
                                return(DB_ERROR);
 
809
                        }
 
810
                } else if (srv_data_file_is_raw_partition[i] == SRV_NEW_RAW) {
 
811
                        /* The partition is opened, not created; then it is
 
812
                        written over */
 
813
 
 
814
                        srv_start_raw_disk_in_use = TRUE;
 
815
                        srv_created_new_raw = TRUE;
 
816
 
 
817
                        files[i] = os_file_create(innodb_file_data_key,
 
818
                                                  name, OS_FILE_OPEN_RAW,
 
819
                                                  OS_FILE_NORMAL,
 
820
                                                  OS_DATA_FILE, &ret);
 
821
                        if (!ret) {
 
822
                                fprintf(stderr,
 
823
                                        "InnoDB: Error in opening %s\n", name);
 
824
 
 
825
                                return(DB_ERROR);
 
826
                        }
 
827
                } else if (srv_data_file_is_raw_partition[i] == SRV_OLD_RAW) {
 
828
                        srv_start_raw_disk_in_use = TRUE;
 
829
 
 
830
                        ret = FALSE;
 
831
                } else {
 
832
                        ut_a(0);
 
833
                }
 
834
 
 
835
                if (ret == FALSE) {
 
836
                        /* We open the data file */
 
837
 
 
838
                        if (one_created) {
 
839
                                fprintf(stderr,
 
840
                                        "InnoDB: Error: data files can only"
 
841
                                        " be added at the end\n");
 
842
                                fprintf(stderr,
 
843
                                        "InnoDB: of a tablespace, but"
 
844
                                        " data file %s existed beforehand.\n",
 
845
                                        name);
 
846
                                return(DB_ERROR);
 
847
                        }
 
848
 
 
849
                        if (srv_data_file_is_raw_partition[i] == SRV_OLD_RAW) {
 
850
                                files[i] = os_file_create(
 
851
                                        innodb_file_data_key,
 
852
                                        name, OS_FILE_OPEN_RAW,
 
853
                                        OS_FILE_NORMAL, OS_DATA_FILE, &ret);
 
854
                        } else if (i == 0) {
 
855
                                files[i] = os_file_create(
 
856
                                        innodb_file_data_key,
 
857
                                        name, OS_FILE_OPEN_RETRY,
 
858
                                        OS_FILE_NORMAL, OS_DATA_FILE, &ret);
 
859
                        } else {
 
860
                                files[i] = os_file_create(
 
861
                                        innodb_file_data_key,
 
862
                                        name, OS_FILE_OPEN, OS_FILE_NORMAL,
 
863
                                        OS_DATA_FILE, &ret);
 
864
                        }
 
865
 
 
866
                        if (!ret) {
 
867
                                fprintf(stderr,
 
868
                                        "InnoDB: Error in opening %s\n", name);
 
869
                                os_file_get_last_error(TRUE);
 
870
 
 
871
                                return(DB_ERROR);
 
872
                        }
 
873
 
 
874
                        if (srv_data_file_is_raw_partition[i] == SRV_OLD_RAW) {
 
875
 
 
876
                                goto skip_size_check;
 
877
                        }
 
878
 
 
879
                        ret = os_file_get_size(files[i], &size, &size_high);
 
880
                        ut_a(ret);
 
881
                        /* Round size downward to megabytes */
 
882
 
 
883
                        rounded_size_pages
 
884
                                = (size / (1024 * 1024) + 4096 * size_high)
 
885
                                        << (20 - UNIV_PAGE_SIZE_SHIFT);
 
886
 
 
887
                        if (i == srv_n_data_files - 1
 
888
                            && srv_auto_extend_last_data_file) {
 
889
 
 
890
                                if (srv_data_file_sizes[i] > rounded_size_pages
 
891
                                    || (srv_last_file_size_max > 0
 
892
                                        && srv_last_file_size_max
 
893
                                        < rounded_size_pages)) {
 
894
 
 
895
                                        fprintf(stderr,
 
896
                                                "InnoDB: Error: auto-extending"
 
897
                                                " data file %s is"
 
898
                                                " of a different size\n"
 
899
                                                "InnoDB: %lu pages (rounded"
 
900
                                                " down to MB) than specified"
 
901
                                                " in the .cnf file:\n"
 
902
                                                "InnoDB: initial %lu pages,"
 
903
                                                " max %lu (relevant if"
 
904
                                                " non-zero) pages!\n",
 
905
                                                name,
 
906
                                                (ulong) rounded_size_pages,
 
907
                                                (ulong) srv_data_file_sizes[i],
 
908
                                                (ulong)
 
909
                                                srv_last_file_size_max);
 
910
 
 
911
                                        return(DB_ERROR);
 
912
                                }
 
913
 
 
914
                                srv_data_file_sizes[i] = rounded_size_pages;
 
915
                        }
 
916
 
 
917
                        if (rounded_size_pages != srv_data_file_sizes[i]) {
 
918
 
 
919
                                fprintf(stderr,
 
920
                                        "InnoDB: Error: data file %s"
 
921
                                        " is of a different size\n"
 
922
                                        "InnoDB: %lu pages"
 
923
                                        " (rounded down to MB)\n"
 
924
                                        "InnoDB: than specified"
 
925
                                        " in the .cnf file %lu pages!\n",
 
926
                                        name,
 
927
                                        (ulong) rounded_size_pages,
 
928
                                        (ulong) srv_data_file_sizes[i]);
 
929
 
 
930
                                return(DB_ERROR);
 
931
                        }
 
932
skip_size_check:
 
933
                        fil_read_flushed_lsn_and_arch_log_no(
 
934
                                files[i], one_opened,
 
935
#ifdef UNIV_LOG_ARCHIVE
 
936
                                min_arch_log_no, max_arch_log_no,
 
937
#endif /* UNIV_LOG_ARCHIVE */
 
938
                                min_flushed_lsn, max_flushed_lsn);
 
939
                        one_opened = TRUE;
 
940
                } else {
 
941
                        /* We created the data file and now write it full of
 
942
                        zeros */
 
943
 
 
944
                        one_created = TRUE;
 
945
 
 
946
                        if (i > 0) {
 
947
                                ut_print_timestamp(stderr);
 
948
                                fprintf(stderr,
 
949
                                        "  InnoDB: Data file %s did not"
 
950
                                        " exist: new to be created\n",
 
951
                                        name);
 
952
                        } else {
 
953
                                fprintf(stderr,
 
954
                                        "InnoDB: The first specified"
 
955
                                        " data file %s did not exist:\n"
 
956
                                        "InnoDB: a new database"
 
957
                                        " to be created!\n", name);
 
958
                                *create_new_db = TRUE;
 
959
                        }
 
960
 
 
961
                        ut_print_timestamp(stderr);
 
962
                        fprintf(stderr,
 
963
                                "  InnoDB: Setting file %s size to %lu MB\n",
 
964
                                name,
 
965
                                (ulong) (srv_data_file_sizes[i]
 
966
                                         >> (20 - UNIV_PAGE_SIZE_SHIFT)));
 
967
 
 
968
                        fprintf(stderr,
 
969
                                "InnoDB: Database physically writes the"
 
970
                                " file full: wait...\n");
 
971
 
 
972
                        ret = os_file_set_size(
 
973
                                name, files[i],
 
974
                                srv_calc_low32(srv_data_file_sizes[i]),
 
975
                                srv_calc_high32(srv_data_file_sizes[i]));
 
976
 
 
977
                        if (!ret) {
 
978
                                fprintf(stderr,
 
979
                                        "InnoDB: Error in creating %s:"
 
980
                                        " probably out of disk space\n", name);
 
981
 
 
982
                                return(DB_ERROR);
 
983
                        }
 
984
 
 
985
                        *sum_of_new_sizes = *sum_of_new_sizes
 
986
                                + srv_data_file_sizes[i];
 
987
                }
 
988
 
 
989
                ret = os_file_close(files[i]);
 
990
                ut_a(ret);
 
991
 
 
992
                if (i == 0) {
 
993
                        fil_space_create(name, 0, 0, FIL_TABLESPACE);
 
994
                }
 
995
 
 
996
                ut_a(fil_validate());
 
997
 
 
998
                fil_node_create(name, srv_data_file_sizes[i], 0,
 
999
                                srv_data_file_is_raw_partition[i] != 0);
 
1000
        }
 
1001
 
 
1002
        ios = 0;
 
1003
 
 
1004
        mutex_create(ios_mutex_key, &ios_mutex, SYNC_NO_ORDER_CHECK);
 
1005
 
 
1006
        return(DB_SUCCESS);
 
1007
}
 
1008
 
 
1009
/********************************************************************
 
1010
Starts InnoDB and creates a new database if database files
 
1011
are not found and the user wants.
 
1012
@return DB_SUCCESS or error code */
 
1013
UNIV_INTERN
 
1014
int
 
1015
innobase_start_or_create_for_mysql(void)
 
1016
/*====================================*/
 
1017
{
 
1018
        ibool           create_new_db;
 
1019
        ibool           log_file_created;
 
1020
        ibool           log_created     = FALSE;
 
1021
        ibool           log_opened      = FALSE;
 
1022
        ib_uint64_t     min_flushed_lsn;
 
1023
        ib_uint64_t     max_flushed_lsn;
 
1024
#ifdef UNIV_LOG_ARCHIVE
 
1025
        ulint           min_arch_log_no;
 
1026
        ulint           max_arch_log_no;
 
1027
#endif /* UNIV_LOG_ARCHIVE */
 
1028
        ulint           sum_of_new_sizes;
 
1029
        ulint           sum_of_data_file_sizes;
 
1030
        ulint           tablespace_size_in_header;
 
1031
        ulint           err;
 
1032
        ulint           i;
 
1033
        ulint           io_limit;
 
1034
        my_bool         srv_file_per_table_original_value
 
1035
                = srv_file_per_table;
 
1036
        mtr_t           mtr;
 
1037
#ifdef HAVE_DARWIN_THREADS
 
1038
# ifdef F_FULLFSYNC
 
1039
        /* This executable has been compiled on Mac OS X 10.3 or later.
 
1040
        Assume that F_FULLFSYNC is available at run-time. */
 
1041
        srv_have_fullfsync = TRUE;
 
1042
# else /* F_FULLFSYNC */
 
1043
        /* This executable has been compiled on Mac OS X 10.2
 
1044
        or earlier.  Determine if the executable is running
 
1045
        on Mac OS X 10.3 or later. */
 
1046
        struct utsname utsname;
 
1047
        if (uname(&utsname)) {
 
1048
                fputs("InnoDB: cannot determine Mac OS X version!\n", stderr);
 
1049
        } else {
 
1050
                srv_have_fullfsync = strcmp(utsname.release, "7.") >= 0;
 
1051
        }
 
1052
        if (!srv_have_fullfsync) {
 
1053
                fputs("InnoDB: On Mac OS X, fsync() may be"
 
1054
                      " broken on internal drives,\n"
 
1055
                      "InnoDB: making transactions unsafe!\n", stderr);
 
1056
        }
 
1057
# endif /* F_FULLFSYNC */
 
1058
#endif /* HAVE_DARWIN_THREADS */
 
1059
 
 
1060
        if (sizeof(ulint) != sizeof(void*)) {
 
1061
                fprintf(stderr,
 
1062
                        "InnoDB: Error: size of InnoDB's ulint is %lu,"
 
1063
                        " but size of void* is %lu.\n"
 
1064
                        "InnoDB: The sizes should be the same"
 
1065
                        " so that on a 64-bit platform you can\n"
 
1066
                        "InnoDB: allocate more than 4 GB of memory.",
 
1067
                        (ulong)sizeof(ulint), (ulong)sizeof(void*));
 
1068
        }
 
1069
 
 
1070
        /* System tables are created in tablespace 0.  Thus, we must
 
1071
        temporarily clear srv_file_per_table.  This is ok, because the
 
1072
        server will not accept connections (which could modify
 
1073
        innodb_file_per_table) until this function has returned. */
 
1074
        srv_file_per_table = FALSE;
 
1075
#ifdef UNIV_DEBUG
 
1076
        fprintf(stderr,
 
1077
                "InnoDB: !!!!!!!! UNIV_DEBUG switched on !!!!!!!!!\n");
 
1078
#endif
 
1079
 
 
1080
#ifdef UNIV_IBUF_DEBUG
 
1081
        fprintf(stderr,
 
1082
                "InnoDB: !!!!!!!! UNIV_IBUF_DEBUG switched on !!!!!!!!!\n"
 
1083
# ifdef UNIV_IBUF_COUNT_DEBUG
 
1084
                "InnoDB: !!!!!!!! UNIV_IBUF_COUNT_DEBUG switched on !!!!!!!!!\n"
 
1085
                "InnoDB: Crash recovery will fail with UNIV_IBUF_COUNT_DEBUG\n"
 
1086
# endif
 
1087
                );
 
1088
#endif
 
1089
 
 
1090
#ifdef UNIV_SYNC_DEBUG
 
1091
        fprintf(stderr,
 
1092
                "InnoDB: !!!!!!!! UNIV_SYNC_DEBUG switched on !!!!!!!!!\n");
 
1093
#endif
 
1094
 
 
1095
#ifdef UNIV_SEARCH_DEBUG
 
1096
        fprintf(stderr,
 
1097
                "InnoDB: !!!!!!!! UNIV_SEARCH_DEBUG switched on !!!!!!!!!\n");
 
1098
#endif
 
1099
 
 
1100
#ifdef UNIV_LOG_LSN_DEBUG
 
1101
        fprintf(stderr,
 
1102
                "InnoDB: !!!!!!!! UNIV_LOG_LSN_DEBUG switched on !!!!!!!!!\n");
 
1103
#endif /* UNIV_LOG_LSN_DEBUG */
 
1104
#ifdef UNIV_MEM_DEBUG
 
1105
        fprintf(stderr,
 
1106
                "InnoDB: !!!!!!!! UNIV_MEM_DEBUG switched on !!!!!!!!!\n");
 
1107
#endif
 
1108
 
 
1109
        if (UNIV_LIKELY(srv_use_sys_malloc)) {
 
1110
                fprintf(stderr,
 
1111
                        "InnoDB: The InnoDB memory heap is disabled\n");
 
1112
        }
 
1113
 
 
1114
        fputs("InnoDB: " IB_ATOMICS_STARTUP_MSG
 
1115
              "\nInnoDB: Compressed tables use zlib " ZLIB_VERSION
 
1116
#ifdef UNIV_ZIP_DEBUG
 
1117
              " with validation"
 
1118
#endif /* UNIV_ZIP_DEBUG */
 
1119
#ifdef UNIV_ZIP_COPY
 
1120
              " and extra copying"
 
1121
#endif /* UNIV_ZIP_COPY */
 
1122
              "\n" , stderr);
 
1123
 
 
1124
 
 
1125
        /* Since InnoDB does not currently clean up all its internal data
 
1126
        structures in MySQL Embedded Server Library server_end(), we
 
1127
        print an error message if someone tries to start up InnoDB a
 
1128
        second time during the process lifetime. */
 
1129
 
 
1130
        if (srv_start_has_been_called) {
 
1131
                fprintf(stderr,
 
1132
                        "InnoDB: Error: startup called second time"
 
1133
                        " during the process lifetime.\n"
 
1134
                        "InnoDB: In the MySQL Embedded Server Library"
 
1135
                        " you cannot call server_init()\n"
 
1136
                        "InnoDB: more than once during"
 
1137
                        " the process lifetime.\n");
 
1138
        }
 
1139
 
 
1140
        srv_start_has_been_called = TRUE;
 
1141
 
 
1142
#ifdef UNIV_DEBUG
 
1143
        log_do_write = TRUE;
 
1144
#endif /* UNIV_DEBUG */
 
1145
        /*      yydebug = TRUE; */
 
1146
 
 
1147
        srv_is_being_started = TRUE;
 
1148
        srv_startup_is_before_trx_rollback_phase = TRUE;
 
1149
 
 
1150
#ifdef __WIN__
 
1151
        switch (os_get_os_version()) {
 
1152
        case OS_WIN95:
 
1153
        case OS_WIN31:
 
1154
        case OS_WINNT:
 
1155
                /* On Win 95, 98, ME, Win32 subsystem for Windows 3.1,
 
1156
                and NT use simulated aio. In NT Windows provides async i/o,
 
1157
                but when run in conjunction with InnoDB Hot Backup, it seemed
 
1158
                to corrupt the data files. */
 
1159
 
 
1160
                srv_use_native_aio = FALSE;
 
1161
                break;
 
1162
 
 
1163
        case OS_WIN2000:
 
1164
        case OS_WINXP:
 
1165
                /* On 2000 and XP, async IO is available. */
 
1166
                srv_use_native_aio = TRUE;
 
1167
                break;
 
1168
 
 
1169
        default:
 
1170
                /* Vista and later have both async IO and condition variables */
 
1171
                srv_use_native_aio = TRUE;
 
1172
                srv_use_native_conditions = TRUE;
 
1173
                break;
 
1174
        }
 
1175
 
 
1176
#elif defined(LINUX_NATIVE_AIO)
 
1177
 
 
1178
        if (srv_use_native_aio) {
 
1179
                ut_print_timestamp(stderr);
 
1180
                fprintf(stderr,
 
1181
                        "  InnoDB: Using Linux native AIO\n");
 
1182
        }
 
1183
#else
 
1184
        /* Currently native AIO is supported only on windows and linux
 
1185
        and that also when the support is compiled in. In all other
 
1186
        cases, we ignore the setting of innodb_use_native_aio. */
 
1187
        srv_use_native_aio = FALSE;
 
1188
 
 
1189
#endif
 
1190
 
 
1191
        if (srv_file_flush_method_str == NULL) {
 
1192
                /* These are the default options */
 
1193
 
 
1194
                srv_unix_file_flush_method = SRV_UNIX_FSYNC;
 
1195
 
 
1196
                srv_win_file_flush_method = SRV_WIN_IO_UNBUFFERED;
 
1197
#ifndef __WIN__
 
1198
        } else if (0 == ut_strcmp(srv_file_flush_method_str, "fsync")) {
 
1199
                srv_unix_file_flush_method = SRV_UNIX_FSYNC;
 
1200
 
 
1201
        } else if (0 == ut_strcmp(srv_file_flush_method_str, "O_DSYNC")) {
 
1202
                srv_unix_file_flush_method = SRV_UNIX_O_DSYNC;
 
1203
 
 
1204
        } else if (0 == ut_strcmp(srv_file_flush_method_str, "O_DIRECT")) {
 
1205
                srv_unix_file_flush_method = SRV_UNIX_O_DIRECT;
 
1206
 
 
1207
        } else if (0 == ut_strcmp(srv_file_flush_method_str, "littlesync")) {
 
1208
                srv_unix_file_flush_method = SRV_UNIX_LITTLESYNC;
 
1209
 
 
1210
        } else if (0 == ut_strcmp(srv_file_flush_method_str, "nosync")) {
 
1211
                srv_unix_file_flush_method = SRV_UNIX_NOSYNC;
 
1212
#else
 
1213
        } else if (0 == ut_strcmp(srv_file_flush_method_str, "normal")) {
 
1214
                srv_win_file_flush_method = SRV_WIN_IO_NORMAL;
 
1215
                srv_use_native_aio = FALSE;
 
1216
 
 
1217
        } else if (0 == ut_strcmp(srv_file_flush_method_str, "unbuffered")) {
 
1218
                srv_win_file_flush_method = SRV_WIN_IO_UNBUFFERED;
 
1219
                srv_use_native_aio = FALSE;
 
1220
 
 
1221
        } else if (0 == ut_strcmp(srv_file_flush_method_str,
 
1222
                                  "async_unbuffered")) {
 
1223
                srv_win_file_flush_method = SRV_WIN_IO_UNBUFFERED;
 
1224
#endif
 
1225
        } else {
 
1226
                fprintf(stderr,
 
1227
                        "InnoDB: Unrecognized value %s for"
 
1228
                        " innodb_flush_method\n",
 
1229
                        srv_file_flush_method_str);
 
1230
                return(DB_ERROR);
 
1231
        }
 
1232
 
 
1233
        /* Note that the call srv_boot() also changes the values of
 
1234
        some variables to the units used by InnoDB internally */
 
1235
 
 
1236
        /* Set the maximum number of threads which can wait for a semaphore
 
1237
        inside InnoDB: this is the 'sync wait array' size, as well as the
 
1238
        maximum number of threads that can wait in the 'srv_conc array' for
 
1239
        their time to enter InnoDB. */
 
1240
 
 
1241
        if (srv_buf_pool_size >= 1000 * 1024 * 1024) {
 
1242
                /* If buffer pool is less than 1000 MB,
 
1243
                assume fewer threads. Also use only one
 
1244
                buffer pool instance */
 
1245
                srv_max_n_threads = 50000;
 
1246
 
 
1247
        } else if (srv_buf_pool_size >= 8 * 1024 * 1024) {
 
1248
 
 
1249
                srv_buf_pool_instances = 1;
 
1250
                srv_max_n_threads = 10000;
 
1251
        } else {
 
1252
                srv_buf_pool_instances = 1;
 
1253
                srv_max_n_threads = 1000;       /* saves several MB of memory,
 
1254
                                                especially in 64-bit
 
1255
                                                computers */
 
1256
        }
 
1257
 
 
1258
        err = srv_boot();
 
1259
 
 
1260
        if (err != DB_SUCCESS) {
 
1261
 
 
1262
                return((int) err);
 
1263
        }
 
1264
 
 
1265
        mutex_create(srv_monitor_file_mutex_key,
 
1266
                     &srv_monitor_file_mutex, SYNC_NO_ORDER_CHECK);
 
1267
 
 
1268
        if (srv_innodb_status) {
 
1269
                srv_monitor_file_name = mem_alloc(
 
1270
                        strlen(fil_path_to_mysql_datadir)
 
1271
                        + 20 + sizeof "/innodb_status.");
 
1272
                sprintf(srv_monitor_file_name, "%s/innodb_status.%lu",
 
1273
                        fil_path_to_mysql_datadir, os_proc_get_number());
 
1274
                srv_monitor_file = fopen(srv_monitor_file_name, "w+");
 
1275
                if (!srv_monitor_file) {
 
1276
                        fprintf(stderr, "InnoDB: unable to create %s: %s\n",
 
1277
                                srv_monitor_file_name, strerror(errno));
 
1278
                        return(DB_ERROR);
 
1279
                }
 
1280
        } else {
 
1281
                srv_monitor_file_name = NULL;
 
1282
                srv_monitor_file = os_file_create_tmpfile();
 
1283
                if (!srv_monitor_file) {
 
1284
                        return(DB_ERROR);
 
1285
                }
 
1286
        }
 
1287
 
 
1288
        mutex_create(srv_dict_tmpfile_mutex_key,
 
1289
                     &srv_dict_tmpfile_mutex, SYNC_DICT_OPERATION);
 
1290
 
 
1291
        srv_dict_tmpfile = os_file_create_tmpfile();
 
1292
        if (!srv_dict_tmpfile) {
 
1293
                return(DB_ERROR);
 
1294
        }
 
1295
 
 
1296
        mutex_create(srv_misc_tmpfile_mutex_key,
 
1297
                     &srv_misc_tmpfile_mutex, SYNC_ANY_LATCH);
 
1298
 
 
1299
        srv_misc_tmpfile = os_file_create_tmpfile();
 
1300
        if (!srv_misc_tmpfile) {
 
1301
                return(DB_ERROR);
 
1302
        }
 
1303
 
 
1304
        /* innodb_file_io_threads used to be user settable.
 
1305
           It is now just a combination of read_io_threads and
 
1306
           write_io_threads that is set by innodb internally. */
 
1307
 
 
1308
        /* Now overwrite the value on srv_n_file_io_threads */
 
1309
        srv_n_file_io_threads = 2 + srv_n_read_io_threads
 
1310
                                + srv_n_write_io_threads;
 
1311
 
 
1312
        ut_a(srv_n_file_io_threads <= SRV_MAX_N_IO_THREADS);
 
1313
 
 
1314
        /* TODO: Investigate if SRV_N_PENDING_IOS_PER_THREAD (32) limit
 
1315
        still applies to windows. */
 
1316
        if (!srv_use_native_aio) {
 
1317
                io_limit = 8 * SRV_N_PENDING_IOS_PER_THREAD;
 
1318
        } else {
 
1319
                io_limit = SRV_N_PENDING_IOS_PER_THREAD;
 
1320
        }
 
1321
 
 
1322
        os_aio_init(io_limit,
 
1323
                    srv_n_read_io_threads,
 
1324
                    srv_n_write_io_threads,
 
1325
                    SRV_MAX_N_PENDING_SYNC_IOS);
 
1326
 
 
1327
        fil_init(srv_file_per_table ? 50000 : 5000,
 
1328
                 srv_max_n_open_files);
 
1329
 
 
1330
        /* Print time to initialize the buffer pool */
 
1331
        ut_print_timestamp(stderr);
 
1332
        fprintf(stderr,
 
1333
                "  InnoDB: Initializing buffer pool, size =");
 
1334
 
 
1335
        if (srv_buf_pool_size >= 1024 * 1024 * 1024) {
 
1336
                fprintf(stderr,
 
1337
                        " %.1fG\n",
 
1338
                        ((double) srv_buf_pool_size) / (1024 * 1024 * 1024));
 
1339
        } else {
 
1340
                fprintf(stderr,
 
1341
                        " %.1fM\n",
 
1342
                        ((double) srv_buf_pool_size) / (1024 * 1024));
 
1343
        }
 
1344
 
 
1345
        err = buf_pool_init(srv_buf_pool_size, srv_buf_pool_instances);
 
1346
 
 
1347
        ut_print_timestamp(stderr);
 
1348
        fprintf(stderr,
 
1349
                "  InnoDB: Completed initialization of buffer pool\n");
 
1350
 
 
1351
        if (err != DB_SUCCESS) {
 
1352
                fprintf(stderr,
 
1353
                        "InnoDB: Fatal error: cannot allocate the memory"
 
1354
                        " for the buffer pool\n");
 
1355
 
 
1356
                return(DB_ERROR);
 
1357
        }
 
1358
 
 
1359
#ifdef UNIV_DEBUG
 
1360
        /* We have observed deadlocks with a 5MB buffer pool but
 
1361
        the actual lower limit could very well be a little higher. */
 
1362
 
 
1363
        if (srv_buf_pool_size <= 5 * 1024 * 1024) {
 
1364
 
 
1365
                fprintf(stderr, "InnoDB: Warning: Small buffer pool size "
 
1366
                        "(%luM), the flst_validate() debug function "
 
1367
                        "can cause a deadlock if the buffer pool fills up.\n",
 
1368
                        srv_buf_pool_size / 1024 / 1024);
 
1369
        }
 
1370
#endif
 
1371
 
 
1372
        fsp_init();
 
1373
        log_init();
 
1374
 
 
1375
        lock_sys_create(srv_lock_table_size);
 
1376
 
 
1377
        /* Create i/o-handler threads: */
 
1378
 
 
1379
        for (i = 0; i < srv_n_file_io_threads; i++) {
 
1380
                n[i] = i;
 
1381
 
 
1382
                os_thread_create(io_handler_thread, n + i, thread_ids + i);
 
1383
        }
 
1384
 
 
1385
#ifdef UNIV_LOG_ARCHIVE
 
1386
        if (0 != ut_strcmp(srv_log_group_home_dirs[0], srv_arch_dir)) {
 
1387
                fprintf(stderr,
 
1388
                        "InnoDB: Error: you must set the log group"
 
1389
                        " home dir in my.cnf the\n"
 
1390
                        "InnoDB: same as log arch dir.\n");
 
1391
 
 
1392
                return(DB_ERROR);
 
1393
        }
 
1394
#endif /* UNIV_LOG_ARCHIVE */
 
1395
 
 
1396
        if (srv_n_log_files * srv_log_file_size >= 262144) {
 
1397
                fprintf(stderr,
 
1398
                        "InnoDB: Error: combined size of log files"
 
1399
                        " must be < 4 GB\n");
 
1400
 
 
1401
                return(DB_ERROR);
 
1402
        }
 
1403
 
 
1404
        sum_of_new_sizes = 0;
 
1405
 
 
1406
        for (i = 0; i < srv_n_data_files; i++) {
 
1407
#ifndef __WIN__
 
1408
                if (sizeof(off_t) < 5 && srv_data_file_sizes[i] >= 262144) {
 
1409
                        fprintf(stderr,
 
1410
                                "InnoDB: Error: file size must be < 4 GB"
 
1411
                                " with this MySQL binary\n"
 
1412
                                "InnoDB: and operating system combination,"
 
1413
                                " in some OS's < 2 GB\n");
 
1414
 
 
1415
                        return(DB_ERROR);
 
1416
                }
 
1417
#endif
 
1418
                sum_of_new_sizes += srv_data_file_sizes[i];
 
1419
        }
 
1420
 
 
1421
        if (sum_of_new_sizes < 10485760 / UNIV_PAGE_SIZE) {
 
1422
                fprintf(stderr,
 
1423
                        "InnoDB: Error: tablespace size must be"
 
1424
                        " at least 10 MB\n");
 
1425
 
 
1426
                return(DB_ERROR);
 
1427
        }
 
1428
 
 
1429
        err = open_or_create_data_files(&create_new_db,
 
1430
#ifdef UNIV_LOG_ARCHIVE
 
1431
                                        &min_arch_log_no, &max_arch_log_no,
 
1432
#endif /* UNIV_LOG_ARCHIVE */
 
1433
                                        &min_flushed_lsn, &max_flushed_lsn,
 
1434
                                        &sum_of_new_sizes);
 
1435
        if (err != DB_SUCCESS) {
 
1436
                fprintf(stderr,
 
1437
                        "InnoDB: Could not open or create data files.\n"
 
1438
                        "InnoDB: If you tried to add new data files,"
 
1439
                        " and it failed here,\n"
 
1440
                        "InnoDB: you should now edit innodb_data_file_path"
 
1441
                        " in my.cnf back\n"
 
1442
                        "InnoDB: to what it was, and remove the"
 
1443
                        " new ibdata files InnoDB created\n"
 
1444
                        "InnoDB: in this failed attempt. InnoDB only wrote"
 
1445
                        " those files full of\n"
 
1446
                        "InnoDB: zeros, but did not yet use them in any way."
 
1447
                        " But be careful: do not\n"
 
1448
                        "InnoDB: remove old data files"
 
1449
                        " which contain your precious data!\n");
 
1450
 
 
1451
                return((int) err);
 
1452
        }
 
1453
 
 
1454
#ifdef UNIV_LOG_ARCHIVE
 
1455
        srv_normalize_path_for_win(srv_arch_dir);
 
1456
        srv_arch_dir = srv_add_path_separator_if_needed(srv_arch_dir);
 
1457
#endif /* UNIV_LOG_ARCHIVE */
 
1458
 
 
1459
        for (i = 0; i < srv_n_log_files; i++) {
 
1460
                err = open_or_create_log_file(create_new_db, &log_file_created,
 
1461
                                              log_opened, 0, i);
 
1462
                if (err != DB_SUCCESS) {
 
1463
 
 
1464
                        return((int) err);
 
1465
                }
 
1466
 
 
1467
                if (log_file_created) {
 
1468
                        log_created = TRUE;
 
1469
                } else {
 
1470
                        log_opened = TRUE;
 
1471
                }
 
1472
                if ((log_opened && create_new_db)
 
1473
                    || (log_opened && log_created)) {
 
1474
                        fprintf(stderr,
 
1475
                                "InnoDB: Error: all log files must be"
 
1476
                                " created at the same time.\n"
 
1477
                                "InnoDB: All log files must be"
 
1478
                                " created also in database creation.\n"
 
1479
                                "InnoDB: If you want bigger or smaller"
 
1480
                                " log files, shut down the\n"
 
1481
                                "InnoDB: database and make sure there"
 
1482
                                " were no errors in shutdown.\n"
 
1483
                                "InnoDB: Then delete the existing log files."
 
1484
                                " Edit the .cnf file\n"
 
1485
                                "InnoDB: and start the database again.\n");
 
1486
 
 
1487
                        return(DB_ERROR);
 
1488
                }
 
1489
        }
 
1490
 
 
1491
        /* Open all log files and data files in the system tablespace: we
 
1492
        keep them open until database shutdown */
 
1493
 
 
1494
        fil_open_log_and_system_tablespace_files();
 
1495
 
 
1496
        if (log_created && !create_new_db
 
1497
#ifdef UNIV_LOG_ARCHIVE
 
1498
            && !srv_archive_recovery
 
1499
#endif /* UNIV_LOG_ARCHIVE */
 
1500
            ) {
 
1501
                if (max_flushed_lsn != min_flushed_lsn
 
1502
#ifdef UNIV_LOG_ARCHIVE
 
1503
                    || max_arch_log_no != min_arch_log_no
 
1504
#endif /* UNIV_LOG_ARCHIVE */
 
1505
                    ) {
 
1506
                        fprintf(stderr,
 
1507
                                "InnoDB: Cannot initialize created"
 
1508
                                " log files because\n"
 
1509
                                "InnoDB: data files were not in sync"
 
1510
                                " with each other\n"
 
1511
                                "InnoDB: or the data files are corrupt.\n");
 
1512
 
 
1513
                        return(DB_ERROR);
 
1514
                }
 
1515
 
 
1516
                if (max_flushed_lsn < (ib_uint64_t) 1000) {
 
1517
                        fprintf(stderr,
 
1518
                                "InnoDB: Cannot initialize created"
 
1519
                                " log files because\n"
 
1520
                                "InnoDB: data files are corrupt,"
 
1521
                                " or new data files were\n"
 
1522
                                "InnoDB: created when the database"
 
1523
                                " was started previous\n"
 
1524
                                "InnoDB: time but the database"
 
1525
                                " was not shut down\n"
 
1526
                                "InnoDB: normally after that.\n");
 
1527
 
 
1528
                        return(DB_ERROR);
 
1529
                }
 
1530
 
 
1531
                mutex_enter(&(log_sys->mutex));
 
1532
 
 
1533
#ifdef UNIV_LOG_ARCHIVE
 
1534
                /* Do not + 1 arch_log_no because we do not use log
 
1535
                archiving */
 
1536
                recv_reset_logs(max_flushed_lsn, max_arch_log_no, TRUE);
 
1537
#else
 
1538
                recv_reset_logs(max_flushed_lsn, TRUE);
 
1539
#endif /* UNIV_LOG_ARCHIVE */
 
1540
 
 
1541
                mutex_exit(&(log_sys->mutex));
 
1542
        }
 
1543
 
 
1544
        trx_sys_file_format_init();
 
1545
 
 
1546
        if (create_new_db) {
 
1547
                mtr_start(&mtr);
 
1548
 
 
1549
                fsp_header_init(0, sum_of_new_sizes, &mtr);
 
1550
 
 
1551
                mtr_commit(&mtr);
 
1552
 
 
1553
                /* To maintain backward compatibility we create only
 
1554
                the first rollback segment before the double write buffer.
 
1555
                All the remaining rollback segments will be created later,
 
1556
                after the double write buffer has been created. */
 
1557
                trx_sys_create();
 
1558
 
 
1559
                dict_create();
 
1560
 
 
1561
                srv_startup_is_before_trx_rollback_phase = FALSE;
 
1562
 
 
1563
#ifdef UNIV_LOG_ARCHIVE
 
1564
        } else if (srv_archive_recovery) {
 
1565
                fprintf(stderr,
 
1566
                        "InnoDB: Starting archive"
 
1567
                        " recovery from a backup...\n");
 
1568
                err = recv_recovery_from_archive_start(
 
1569
                        min_flushed_lsn, srv_archive_recovery_limit_lsn,
 
1570
                        min_arch_log_no);
 
1571
                if (err != DB_SUCCESS) {
 
1572
 
 
1573
                        return(DB_ERROR);
 
1574
                }
 
1575
                /* Since ibuf init is in dict_boot, and ibuf is needed
 
1576
                in any disk i/o, first call dict_boot */
 
1577
 
 
1578
                dict_boot();
 
1579
 
 
1580
                trx_sys_init_at_db_start();
 
1581
 
 
1582
                srv_startup_is_before_trx_rollback_phase = FALSE;
 
1583
 
 
1584
                /* Initialize the fsp free limit global variable in the log
 
1585
                system */
 
1586
                fsp_header_get_free_limit();
 
1587
 
 
1588
                recv_recovery_from_archive_finish();
 
1589
#endif /* UNIV_LOG_ARCHIVE */
 
1590
        } else {
 
1591
 
 
1592
                /* Check if we support the max format that is stamped
 
1593
                on the system tablespace. 
 
1594
                Note:  We are NOT allowed to make any modifications to
 
1595
                the TRX_SYS_PAGE_NO page before recovery  because this
 
1596
                page also contains the max_trx_id etc. important system
 
1597
                variables that are required for recovery.  We need to
 
1598
                ensure that we return the system to a state where normal
 
1599
                recovery is guaranteed to work. We do this by
 
1600
                invalidating the buffer cache, this will force the
 
1601
                reread of the page and restoration to its last known
 
1602
                consistent state, this is REQUIRED for the recovery
 
1603
                process to work. */
 
1604
                err = trx_sys_file_format_max_check(
 
1605
                        srv_max_file_format_at_startup);
 
1606
 
 
1607
                if (err != DB_SUCCESS) {
 
1608
                        return(err);
 
1609
                }
 
1610
 
 
1611
                /* Invalidate the buffer pool to ensure that we reread
 
1612
                the page that we read above, during recovery.
 
1613
                Note that this is not as heavy weight as it seems. At
 
1614
                this point there will be only ONE page in the buf_LRU
 
1615
                and there must be no page in the buf_flush list. */
 
1616
                buf_pool_invalidate();
 
1617
 
 
1618
                /* We always try to do a recovery, even if the database had
 
1619
                been shut down normally: this is the normal startup path */
 
1620
 
 
1621
                err = recv_recovery_from_checkpoint_start(LOG_CHECKPOINT,
 
1622
                                                          IB_ULONGLONG_MAX,
 
1623
                                                          min_flushed_lsn,
 
1624
                                                          max_flushed_lsn);
 
1625
                if (err != DB_SUCCESS) {
 
1626
 
 
1627
                        return(DB_ERROR);
 
1628
                }
 
1629
 
 
1630
                /* Since the insert buffer init is in dict_boot, and the
 
1631
                insert buffer is needed in any disk i/o, first we call
 
1632
                dict_boot(). Note that trx_sys_init_at_db_start() only needs
 
1633
                to access space 0, and the insert buffer at this stage already
 
1634
                works for space 0. */
 
1635
 
 
1636
                dict_boot();
 
1637
                trx_sys_init_at_db_start();
 
1638
 
 
1639
                /* Initialize the fsp free limit global variable in the log
 
1640
                system */
 
1641
                fsp_header_get_free_limit();
 
1642
 
 
1643
                /* recv_recovery_from_checkpoint_finish needs trx lists which
 
1644
                are initialized in trx_sys_init_at_db_start(). */
 
1645
 
 
1646
                recv_recovery_from_checkpoint_finish();
 
1647
                if (srv_force_recovery < SRV_FORCE_NO_IBUF_MERGE) {
 
1648
                        /* The following call is necessary for the insert
 
1649
                        buffer to work with multiple tablespaces. We must
 
1650
                        know the mapping between space id's and .ibd file
 
1651
                        names.
 
1652
 
 
1653
                        In a crash recovery, we check that the info in data
 
1654
                        dictionary is consistent with what we already know
 
1655
                        about space id's from the call of
 
1656
                        fil_load_single_table_tablespaces().
 
1657
 
 
1658
                        In a normal startup, we create the space objects for
 
1659
                        every table in the InnoDB data dictionary that has
 
1660
                        an .ibd file.
 
1661
 
 
1662
                        We also determine the maximum tablespace id used. */
 
1663
 
 
1664
                        dict_check_tablespaces_and_store_max_id(
 
1665
                                recv_needed_recovery);
 
1666
                }
 
1667
 
 
1668
                srv_startup_is_before_trx_rollback_phase = FALSE;
 
1669
                recv_recovery_rollback_active();
 
1670
 
 
1671
                /* It is possible that file_format tag has never
 
1672
                been set. In this case we initialize it to minimum
 
1673
                value.  Important to note that we can do it ONLY after
 
1674
                we have finished the recovery process so that the
 
1675
                image of TRX_SYS_PAGE_NO is not stale. */
 
1676
                trx_sys_file_format_tag_init();
 
1677
        }
 
1678
 
 
1679
        if (!create_new_db && sum_of_new_sizes > 0) {
 
1680
                /* New data file(s) were added */
 
1681
                mtr_start(&mtr);
 
1682
 
 
1683
                fsp_header_inc_size(0, sum_of_new_sizes, &mtr);
 
1684
 
 
1685
                mtr_commit(&mtr);
 
1686
 
 
1687
                /* Immediately write the log record about increased tablespace
 
1688
                size to disk, so that it is durable even if mysqld would crash
 
1689
                quickly */
 
1690
 
 
1691
                log_buffer_flush_to_disk();
 
1692
        }
 
1693
 
 
1694
#ifdef UNIV_LOG_ARCHIVE
 
1695
        /* Archiving is always off under MySQL */
 
1696
        if (!srv_log_archive_on) {
 
1697
                ut_a(DB_SUCCESS == log_archive_noarchivelog());
 
1698
        } else {
 
1699
                mutex_enter(&(log_sys->mutex));
 
1700
 
 
1701
                start_archive = FALSE;
 
1702
 
 
1703
                if (log_sys->archiving_state == LOG_ARCH_OFF) {
 
1704
                        start_archive = TRUE;
 
1705
                }
 
1706
 
 
1707
                mutex_exit(&(log_sys->mutex));
 
1708
 
 
1709
                if (start_archive) {
 
1710
                        ut_a(DB_SUCCESS == log_archive_archivelog());
 
1711
                }
 
1712
        }
 
1713
#endif /* UNIV_LOG_ARCHIVE */
 
1714
 
 
1715
        /* fprintf(stderr, "Max allowed record size %lu\n",
 
1716
        page_get_free_space_of_empty() / 2); */
 
1717
 
 
1718
        if (trx_doublewrite == NULL) {
 
1719
                /* Create the doublewrite buffer to a new tablespace */
 
1720
 
 
1721
                trx_sys_create_doublewrite_buf();
 
1722
        }
 
1723
 
 
1724
        /* Here the double write buffer has already been created and so
 
1725
        any new rollback segments will be allocated after the double
 
1726
        write buffer. The default segment should already exist.
 
1727
        We create the new segments only if it's a new database or
 
1728
        the database was shutdown cleanly. */
 
1729
 
 
1730
        /* Note: When creating the extra rollback segments during an upgrade
 
1731
        we violate the latching order, even if the change buffer is empty.
 
1732
        We make an exception in sync0sync.c and check srv_is_being_started
 
1733
        for that violation. It cannot create a deadlock because we are still
 
1734
        running in single threaded mode essentially. Only the IO threads
 
1735
        should be running at this stage. */
 
1736
 
 
1737
        trx_sys_create_rsegs(TRX_SYS_N_RSEGS - 1);
 
1738
 
 
1739
        /* Create the thread which watches the timeouts for lock waits */
 
1740
        os_thread_create(&srv_lock_timeout_thread, NULL,
 
1741
                         thread_ids + 2 + SRV_MAX_N_IO_THREADS);
 
1742
 
 
1743
        /* Create the thread which warns of long semaphore waits */
 
1744
        os_thread_create(&srv_error_monitor_thread, NULL,
 
1745
                         thread_ids + 3 + SRV_MAX_N_IO_THREADS);
 
1746
 
 
1747
        /* Create the thread which prints InnoDB monitor info */
 
1748
        os_thread_create(&srv_monitor_thread, NULL,
 
1749
                         thread_ids + 4 + SRV_MAX_N_IO_THREADS);
 
1750
 
 
1751
        srv_is_being_started = FALSE;
 
1752
 
 
1753
        err = dict_create_or_check_foreign_constraint_tables();
 
1754
 
 
1755
        if (err != DB_SUCCESS) {
 
1756
                return((int)DB_ERROR);
 
1757
        }
 
1758
 
 
1759
        /* Create the master thread which does purge and other utility
 
1760
        operations */
 
1761
 
 
1762
        os_thread_create(&srv_master_thread, NULL, thread_ids
 
1763
                         + (1 + SRV_MAX_N_IO_THREADS));
 
1764
 
 
1765
        /* Currently we allow only a single purge thread. */
 
1766
        ut_a(srv_n_purge_threads == 0 || srv_n_purge_threads == 1);
 
1767
 
 
1768
        /* If the user has requested a separate purge thread then
 
1769
        start the purge thread. */
 
1770
        if (srv_n_purge_threads == 1) {
 
1771
                os_thread_create(&srv_purge_thread, NULL, NULL);
 
1772
        }
 
1773
 
 
1774
#ifdef UNIV_DEBUG
 
1775
        /* buf_debug_prints = TRUE; */
 
1776
#endif /* UNIV_DEBUG */
 
1777
        sum_of_data_file_sizes = 0;
 
1778
 
 
1779
        for (i = 0; i < srv_n_data_files; i++) {
 
1780
                sum_of_data_file_sizes += srv_data_file_sizes[i];
 
1781
        }
 
1782
 
 
1783
        tablespace_size_in_header = fsp_header_get_tablespace_size();
 
1784
 
 
1785
        if (!srv_auto_extend_last_data_file
 
1786
            && sum_of_data_file_sizes != tablespace_size_in_header) {
 
1787
 
 
1788
                fprintf(stderr,
 
1789
                        "InnoDB: Error: tablespace size"
 
1790
                        " stored in header is %lu pages, but\n"
 
1791
                        "InnoDB: the sum of data file sizes is %lu pages\n",
 
1792
                        (ulong) tablespace_size_in_header,
 
1793
                        (ulong) sum_of_data_file_sizes);
 
1794
 
 
1795
                if (srv_force_recovery == 0
 
1796
                    && sum_of_data_file_sizes < tablespace_size_in_header) {
 
1797
                        /* This is a fatal error, the tail of a tablespace is
 
1798
                        missing */
 
1799
 
 
1800
                        fprintf(stderr,
 
1801
                                "InnoDB: Cannot start InnoDB."
 
1802
                                " The tail of the system tablespace is\n"
 
1803
                                "InnoDB: missing. Have you edited"
 
1804
                                " innodb_data_file_path in my.cnf in an\n"
 
1805
                                "InnoDB: inappropriate way, removing"
 
1806
                                " ibdata files from there?\n"
 
1807
                                "InnoDB: You can set innodb_force_recovery=1"
 
1808
                                " in my.cnf to force\n"
 
1809
                                "InnoDB: a startup if you are trying"
 
1810
                                " to recover a badly corrupt database.\n");
 
1811
 
 
1812
                        return(DB_ERROR);
 
1813
                }
 
1814
        }
 
1815
 
 
1816
        if (srv_auto_extend_last_data_file
 
1817
            && sum_of_data_file_sizes < tablespace_size_in_header) {
 
1818
 
 
1819
                fprintf(stderr,
 
1820
                        "InnoDB: Error: tablespace size stored in header"
 
1821
                        " is %lu pages, but\n"
 
1822
                        "InnoDB: the sum of data file sizes"
 
1823
                        " is only %lu pages\n",
 
1824
                        (ulong) tablespace_size_in_header,
 
1825
                        (ulong) sum_of_data_file_sizes);
 
1826
 
 
1827
                if (srv_force_recovery == 0) {
 
1828
 
 
1829
                        fprintf(stderr,
 
1830
                                "InnoDB: Cannot start InnoDB. The tail of"
 
1831
                                " the system tablespace is\n"
 
1832
                                "InnoDB: missing. Have you edited"
 
1833
                                " innodb_data_file_path in my.cnf in an\n"
 
1834
                                "InnoDB: inappropriate way, removing"
 
1835
                                " ibdata files from there?\n"
 
1836
                                "InnoDB: You can set innodb_force_recovery=1"
 
1837
                                " in my.cnf to force\n"
 
1838
                                "InnoDB: a startup if you are trying to"
 
1839
                                " recover a badly corrupt database.\n");
 
1840
 
 
1841
                        return(DB_ERROR);
 
1842
                }
 
1843
        }
 
1844
 
 
1845
        /* Check that os_fast_mutexes work as expected */
 
1846
        os_fast_mutex_init(&srv_os_test_mutex);
 
1847
 
 
1848
        if (0 != os_fast_mutex_trylock(&srv_os_test_mutex)) {
 
1849
                fprintf(stderr,
 
1850
                        "InnoDB: Error: pthread_mutex_trylock returns"
 
1851
                        " an unexpected value on\n"
 
1852
                        "InnoDB: success! Cannot continue.\n");
 
1853
                exit(1);
 
1854
        }
 
1855
 
 
1856
        os_fast_mutex_unlock(&srv_os_test_mutex);
 
1857
 
 
1858
        os_fast_mutex_lock(&srv_os_test_mutex);
 
1859
 
 
1860
        os_fast_mutex_unlock(&srv_os_test_mutex);
 
1861
 
 
1862
        os_fast_mutex_free(&srv_os_test_mutex);
 
1863
 
 
1864
        if (srv_print_verbose_log) {
 
1865
                ut_print_timestamp(stderr);
 
1866
                fprintf(stderr,
 
1867
                        "  InnoDB %s started; "
 
1868
                        "log sequence number %"PRIu64"\n",
 
1869
                        INNODB_VERSION_STR, srv_start_lsn);
 
1870
        }
 
1871
 
 
1872
        if (srv_force_recovery > 0) {
 
1873
                fprintf(stderr,
 
1874
                        "InnoDB: !!! innodb_force_recovery"
 
1875
                        " is set to %lu !!!\n",
 
1876
                        (ulong) srv_force_recovery);
 
1877
        }
 
1878
 
 
1879
        fflush(stderr);
 
1880
 
 
1881
        if (trx_doublewrite_must_reset_space_ids) {
 
1882
                /* Actually, we did not change the undo log format between
 
1883
                4.0 and 4.1.1, and we would not need to run purge to
 
1884
                completion. Note also that the purge algorithm in 4.1.1
 
1885
                can process the the history list again even after a full
 
1886
                purge, because our algorithm does not cut the end of the
 
1887
                history list in all cases so that it would become empty
 
1888
                after a full purge. That mean that we may purge 4.0 type
 
1889
                undo log even after this phase.
 
1890
 
 
1891
                The insert buffer record format changed between 4.0 and
 
1892
                4.1.1. It is essential that the insert buffer is emptied
 
1893
                here! */
 
1894
 
 
1895
                fprintf(stderr,
 
1896
                        "InnoDB: You are upgrading to an"
 
1897
                        " InnoDB version which allows multiple\n"
 
1898
                        "InnoDB: tablespaces. Wait that purge"
 
1899
                        " and insert buffer merge run to\n"
 
1900
                        "InnoDB: completion...\n");
 
1901
                for (;;) {
 
1902
                        os_thread_sleep(1000000);
 
1903
 
 
1904
                        if (0 == strcmp(srv_main_thread_op_info,
 
1905
                                        "waiting for server activity")) {
 
1906
 
 
1907
                                ut_a(ibuf_is_empty());
 
1908
 
 
1909
                                break;
 
1910
                        }
 
1911
                }
 
1912
                fprintf(stderr,
 
1913
                        "InnoDB: Full purge and insert buffer merge"
 
1914
                        " completed.\n");
 
1915
 
 
1916
                trx_sys_mark_upgraded_to_multiple_tablespaces();
 
1917
 
 
1918
                fprintf(stderr,
 
1919
                        "InnoDB: You have now successfully upgraded"
 
1920
                        " to the multiple tablespaces\n"
 
1921
                        "InnoDB: format. You should NOT DOWNGRADE"
 
1922
                        " to an earlier version of\n"
 
1923
                        "InnoDB: InnoDB! But if you absolutely need to"
 
1924
                        " downgrade, see\n"
 
1925
                        "InnoDB: " REFMAN "multiple-tablespaces.html\n"
 
1926
                        "InnoDB: for instructions.\n");
 
1927
        }
 
1928
 
 
1929
        if (srv_force_recovery == 0) {
 
1930
                /* In the insert buffer we may have even bigger tablespace
 
1931
                id's, because we may have dropped those tablespaces, but
 
1932
                insert buffer merge has not had time to clean the records from
 
1933
                the ibuf tree. */
 
1934
 
 
1935
                ibuf_update_max_tablespace_id();
 
1936
        }
 
1937
 
 
1938
        srv_file_per_table = srv_file_per_table_original_value;
 
1939
 
 
1940
        srv_was_started = TRUE;
 
1941
 
 
1942
        return((int) DB_SUCCESS);
 
1943
}
 
1944
 
 
1945
/****************************************************************//**
 
1946
Shuts down the InnoDB database.
 
1947
@return DB_SUCCESS or error code */
 
1948
UNIV_INTERN
 
1949
int
 
1950
innobase_shutdown_for_mysql(void)
 
1951
/*=============================*/
 
1952
{
 
1953
        ulint   i;
 
1954
        if (!srv_was_started) {
 
1955
                if (srv_is_being_started) {
 
1956
                        ut_print_timestamp(stderr);
 
1957
                        fprintf(stderr,
 
1958
                                "  InnoDB: Warning: shutting down"
 
1959
                                " a not properly started\n"
 
1960
                                "InnoDB: or created database!\n");
 
1961
                }
 
1962
 
 
1963
                return(DB_SUCCESS);
 
1964
        }
 
1965
 
 
1966
        /* 1. Flush the buffer pool to disk, write the current lsn to
 
1967
        the tablespace header(s), and copy all log data to archive.
 
1968
        The step 1 is the real InnoDB shutdown. The remaining steps 2 - ...
 
1969
        just free data structures after the shutdown. */
 
1970
 
 
1971
 
 
1972
        if (srv_fast_shutdown == 2) {
 
1973
                ut_print_timestamp(stderr);
 
1974
                fprintf(stderr,
 
1975
                        "  InnoDB: MySQL has requested a very fast shutdown"
 
1976
                        " without flushing "
 
1977
                        "the InnoDB buffer pool to data files."
 
1978
                        " At the next mysqld startup "
 
1979
                        "InnoDB will do a crash recovery!\n");
 
1980
        }
 
1981
 
 
1982
        logs_empty_and_mark_files_at_shutdown();
 
1983
 
 
1984
        if (srv_conc_n_threads != 0) {
 
1985
                fprintf(stderr,
 
1986
                        "InnoDB: Warning: query counter shows %ld queries"
 
1987
                        " still\n"
 
1988
                        "InnoDB: inside InnoDB at shutdown\n",
 
1989
                        srv_conc_n_threads);
 
1990
        }
 
1991
 
 
1992
        /* 2. Make all threads created by InnoDB to exit */
 
1993
 
 
1994
        srv_shutdown_state = SRV_SHUTDOWN_EXIT_THREADS;
 
1995
 
 
1996
        /* In a 'very fast' shutdown, we do not need to wait for these threads
 
1997
        to die; all which counts is that we flushed the log; a 'very fast'
 
1998
        shutdown is essentially a crash. */
 
1999
 
 
2000
        if (srv_fast_shutdown == 2) {
 
2001
                return(DB_SUCCESS);
 
2002
        }
 
2003
 
 
2004
        /* All threads end up waiting for certain events. Put those events
 
2005
        to the signaled state. Then the threads will exit themselves in
 
2006
        os_thread_event_wait(). */
 
2007
 
 
2008
        for (i = 0; i < 1000; i++) {
 
2009
                /* NOTE: IF YOU CREATE THREADS IN INNODB, YOU MUST EXIT THEM
 
2010
                HERE OR EARLIER */
 
2011
 
 
2012
                /* a. Let the lock timeout thread exit */
 
2013
                os_event_set(srv_lock_timeout_thread_event);
 
2014
 
 
2015
                /* b. srv error monitor thread exits automatically, no need
 
2016
                to do anything here */
 
2017
 
 
2018
                /* c. We wake the master thread so that it exits */
 
2019
                srv_wake_master_thread();
 
2020
 
 
2021
                /* d. We wake the purge thread so that it exits */
 
2022
                srv_wake_purge_thread();
 
2023
 
 
2024
                /* e. Exit the i/o threads */
 
2025
 
 
2026
                os_aio_wake_all_threads_at_shutdown();
 
2027
 
 
2028
                os_mutex_enter(os_sync_mutex);
 
2029
 
 
2030
                if (os_thread_count == 0) {
 
2031
                        /* All the threads have exited or are just exiting;
 
2032
                        NOTE that the threads may not have completed their
 
2033
                        exit yet. Should we use pthread_join() to make sure
 
2034
                        they have exited? If we did, we would have to
 
2035
                        remove the pthread_detach() from
 
2036
                        os_thread_exit().  Now we just sleep 0.1
 
2037
                        seconds and hope that is enough! */
 
2038
 
 
2039
                        os_mutex_exit(os_sync_mutex);
 
2040
 
 
2041
                        os_thread_sleep(100000);
 
2042
 
 
2043
                        break;
 
2044
                }
 
2045
 
 
2046
                os_mutex_exit(os_sync_mutex);
 
2047
 
 
2048
                os_thread_sleep(100000);
 
2049
        }
 
2050
 
 
2051
        if (i == 1000) {
 
2052
                fprintf(stderr,
 
2053
                        "InnoDB: Warning: %lu threads created by InnoDB"
 
2054
                        " had not exited at shutdown!\n",
 
2055
                        (ulong) os_thread_count);
 
2056
        }
 
2057
 
 
2058
        if (srv_monitor_file) {
 
2059
                fclose(srv_monitor_file);
 
2060
                srv_monitor_file = 0;
 
2061
                if (srv_monitor_file_name) {
 
2062
                        unlink(srv_monitor_file_name);
 
2063
                        mem_free(srv_monitor_file_name);
 
2064
                }
 
2065
        }
 
2066
        if (srv_dict_tmpfile) {
 
2067
                fclose(srv_dict_tmpfile);
 
2068
                srv_dict_tmpfile = 0;
 
2069
        }
 
2070
 
 
2071
        if (srv_misc_tmpfile) {
 
2072
                fclose(srv_misc_tmpfile);
 
2073
                srv_misc_tmpfile = 0;
 
2074
        }
 
2075
 
 
2076
        /* This must be disabled before closing the buffer pool
 
2077
        and closing the data dictionary.  */
 
2078
        btr_search_disable();
 
2079
 
 
2080
        ibuf_close();
 
2081
        log_shutdown();
 
2082
        lock_sys_close();
 
2083
        thr_local_close();
 
2084
        trx_sys_file_format_close();
 
2085
        trx_sys_close();
 
2086
 
 
2087
        mutex_free(&srv_monitor_file_mutex);
 
2088
        mutex_free(&srv_dict_tmpfile_mutex);
 
2089
        mutex_free(&srv_misc_tmpfile_mutex);
 
2090
        dict_close();
 
2091
        btr_search_sys_free();
 
2092
 
 
2093
        /* 3. Free all InnoDB's own mutexes and the os_fast_mutexes inside
 
2094
        them */
 
2095
        os_aio_free();
 
2096
        sync_close();
 
2097
        srv_free();
 
2098
        fil_close();
 
2099
 
 
2100
        /* 4. Free the os_conc_mutex and all os_events and os_mutexes */
 
2101
 
 
2102
        os_sync_free();
 
2103
 
 
2104
        /* 5. Free all allocated memory */
 
2105
 
 
2106
        pars_lexer_close();
 
2107
        log_mem_free();
 
2108
        buf_pool_free(srv_buf_pool_instances);
 
2109
        mem_close();
 
2110
 
 
2111
        /* ut_free_all_mem() frees all allocated memory not freed yet
 
2112
        in shutdown, and it will also free the ut_list_mutex, so it
 
2113
        should be the last one for all operation */
 
2114
        ut_free_all_mem();
 
2115
 
 
2116
        if (os_thread_count != 0
 
2117
            || os_event_count != 0
 
2118
            || os_mutex_count != 0
 
2119
            || os_fast_mutex_count != 0) {
 
2120
                fprintf(stderr,
 
2121
                        "InnoDB: Warning: some resources were not"
 
2122
                        " cleaned up in shutdown:\n"
 
2123
                        "InnoDB: threads %lu, events %lu,"
 
2124
                        " os_mutexes %lu, os_fast_mutexes %lu\n",
 
2125
                        (ulong) os_thread_count, (ulong) os_event_count,
 
2126
                        (ulong) os_mutex_count, (ulong) os_fast_mutex_count);
 
2127
        }
 
2128
 
 
2129
        if (dict_foreign_err_file) {
 
2130
                fclose(dict_foreign_err_file);
 
2131
        }
 
2132
        if (lock_latest_err_file) {
 
2133
                fclose(lock_latest_err_file);
 
2134
        }
 
2135
 
 
2136
        if (srv_print_verbose_log) {
 
2137
                ut_print_timestamp(stderr);
 
2138
                fprintf(stderr,
 
2139
                        "  InnoDB: Shutdown completed;"
 
2140
                        " log sequence number %"PRIu64"\n",
 
2141
                        srv_shutdown_lsn);
 
2142
        }
 
2143
 
 
2144
        srv_was_started = FALSE;
 
2145
        srv_start_has_been_called = FALSE;
 
2146
 
 
2147
        return((int) DB_SUCCESS);
 
2148
}
 
2149
#endif /* !UNIV_HOTBACKUP */