/****************************************************************//** Creates the sys_added_cols_default table inside InnoDB at database creation or database start if they are not found or are not of the right form. @return DB_SUCCESS or error code */ UNIV_INTERN ulint dict_create_or_check_added_cols_default_tables(void) /*================================================*/ { dict_table_t* table1; ulint error; trx_t* trx; mutex_enter(&(dict_sys->mutex)); table1 = dict_table_get_low("SYS_ADDED_COLS_DEFAULT"); if (table1 && UT_LIST_GET_LEN(table1->indexes) == 1) { /* sys_added_cols_default table have already been created, and it's ok */ mutex_exit(&(dict_sys->mutex)); #ifdef DEBUG fprintf(stderr, "SYS_ADDED_COLS_DEFAULT table have created success!!!!\n"); #endif return(DB_SUCCESS); } #ifdef DEBUG fprintf(stderr, "SYS_ADDED_COLS_DEFAULT table have not created yet!!!\n"); #endif mutex_exit(&(dict_sys->mutex)); trx = trx_allocate_for_mysql(); trx->op_info = "creating added cols default"; row_mysql_lock_data_dictionary(trx); /* sys_added_cols_default table have been created,but not OK, drop it and then recreate */ if (table1) { fprintf(stderr, "InnoDB: dropping incompletely created" " SYS_ADDED_COLS_DEFAULT table\n"); row_drop_table_for_mysql("SYS_ADDED_COLS_DEFAULT", trx, TRUE); } fprintf(stderr, "InnoDB: Creating sys_added_cols_default for fast add colums with default value\n"); /* NOTE: We create the added cols default here. sys_added_cols_default( table_id int, //table id pos int, // column id def_val varbinary, //default value def_val_len int //default value's length ) */ error = que_eval_sql(NULL, "PROCEDURE CREATE_ADDED_COLS_DEFAULT_SYS_TABLES_PROC () IS\n" "BEGIN\n" "CREATE TABLE\n" "SYS_ADDED_COLS_DEFAULT(TABLE_ID BINARY(8), POS INT," " DEF_VAL BINARY(65535), DEF_VAL_LEN INT);\n" "CREATE UNIQUE CLUSTERED INDEX TID_POS" " ON SYS_ADDED_COLS_DEFAULT (TABLE_ID,POS);\n" "END;\n" , FALSE, trx); if (error != DB_SUCCESS) { fprintf(stderr, "InnoDB: error %lu in creation\n", (ulong) error); ut_a(error == DB_OUT_OF_FILE_SPACE || error == DB_TOO_MANY_CONCURRENT_TRXS); fprintf(stderr, "InnoDB: creation failed\n" "InnoDB: tablespace is full\n" "InnoDB: dropping incompletely created" " SYS_FOREIGN tables\n"); row_drop_table_for_mysql("SYS_ADDED_COLS_DEFAULT", trx, TRUE); error = DB_MUST_GET_MORE_FILE_SPACE; } trx_commit_for_mysql(trx); row_mysql_unlock_data_dictionary(trx); trx_free_for_mysql(trx); if (error == DB_SUCCESS) { fprintf(stderr, "InnoDB: Added columns default system tables" " created\n"); } return(error); }
ulint dict_create_or_check_foreign_constraint_tables(void) /*================================================*/ /* out: DB_SUCCESS or error code */ { dict_table_t* table1; dict_table_t* table2; ulint error; trx_t* trx; mutex_enter(&(dict_sys->mutex)); table1 = dict_table_get_low("SYS_FOREIGN"); table2 = dict_table_get_low("SYS_FOREIGN_COLS"); if (table1 && table2 && UT_LIST_GET_LEN(table1->indexes) == 3 && UT_LIST_GET_LEN(table2->indexes) == 1) { /* Foreign constraint system tables have already been created, and they are ok */ mutex_exit(&(dict_sys->mutex)); return(DB_SUCCESS); } mutex_exit(&(dict_sys->mutex)); trx = trx_allocate_for_mysql(); trx->op_info = "creating foreign key sys tables"; row_mysql_lock_data_dictionary(trx); if (table1) { fprintf(stderr, "InnoDB: dropping incompletely created" " SYS_FOREIGN table\n"); row_drop_table_for_mysql("SYS_FOREIGN", trx, TRUE); } if (table2) { fprintf(stderr, "InnoDB: dropping incompletely created" " SYS_FOREIGN_COLS table\n"); row_drop_table_for_mysql("SYS_FOREIGN_COLS", trx, TRUE); } fprintf(stderr, "InnoDB: Creating foreign key constraint system tables\n"); /* NOTE: in dict_load_foreigns we use the fact that there are 2 secondary indexes on SYS_FOREIGN, and they are defined just like below */ /* NOTE: when designing InnoDB's foreign key support in 2001, we made an error and made the table names and the foreign key id of type 'CHAR' (internally, really a VARCHAR). We should have made the type VARBINARY, like in other InnoDB system tables, to get a clean design. */ error = que_eval_sql(NULL, "PROCEDURE CREATE_FOREIGN_SYS_TABLES_PROC () IS\n" "BEGIN\n" "CREATE TABLE\n" "SYS_FOREIGN(ID CHAR, FOR_NAME CHAR," " REF_NAME CHAR, N_COLS INT);\n" "CREATE UNIQUE CLUSTERED INDEX ID_IND" " ON SYS_FOREIGN (ID);\n" "CREATE INDEX FOR_IND" " ON SYS_FOREIGN (FOR_NAME);\n" "CREATE INDEX REF_IND" " ON SYS_FOREIGN (REF_NAME);\n" "CREATE TABLE\n" "SYS_FOREIGN_COLS(ID CHAR, POS INT," " FOR_COL_NAME CHAR, REF_COL_NAME CHAR);\n" "CREATE UNIQUE CLUSTERED INDEX ID_IND" " ON SYS_FOREIGN_COLS (ID, POS);\n" "COMMIT WORK;\n" "END;\n" , FALSE, trx); if (error != DB_SUCCESS) { fprintf(stderr, "InnoDB: error %lu in creation\n", (ulong) error); ut_a(error == DB_OUT_OF_FILE_SPACE || error == DB_TOO_MANY_CONCURRENT_TRXS); fprintf(stderr, "InnoDB: creation failed\n" "InnoDB: tablespace is full\n" "InnoDB: dropping incompletely created" " SYS_FOREIGN tables\n"); row_drop_table_for_mysql("SYS_FOREIGN", trx, TRUE); row_drop_table_for_mysql("SYS_FOREIGN_COLS", trx, TRUE); error = DB_MUST_GET_MORE_FILE_SPACE; } trx->op_info = ""; row_mysql_unlock_data_dictionary(trx); trx_free_for_mysql(trx); if (error == DB_SUCCESS) { fprintf(stderr, "InnoDB: Foreign key constraint system tables" " created\n"); } return(error); }
/****************************************************************//** Creates the foreign key constraints system tables inside InnoDB at database creation or database start if they are not found or are not of the right form. @return DB_SUCCESS or error code */ UNIV_INTERN ulint dict_create_or_check_foreign_constraint_tables(void) /*================================================*/ { dict_table_t* table1; dict_table_t* table2; ulint error; trx_t* trx; mutex_enter(&(dict_sys->mutex)); table1 = dict_table_get_low("SYS_FOREIGN"); table2 = dict_table_get_low("SYS_FOREIGN_COLS"); if (table1 && table2 && UT_LIST_GET_LEN(table1->indexes) == 3 && UT_LIST_GET_LEN(table2->indexes) == 1) { /* Foreign constraint system tables have already been created, and they are ok */ mutex_exit(&(dict_sys->mutex)); return(DB_SUCCESS); } mutex_exit(&(dict_sys->mutex)); trx = trx_allocate_for_mysql(); trx->op_info = "creating foreign key sys tables"; row_mysql_lock_data_dictionary(trx); if (table1) { fprintf(stderr, "InnoDB: dropping incompletely created" " SYS_FOREIGN table\n"); row_drop_table_for_mysql("SYS_FOREIGN", trx, TRUE); } if (table2) { fprintf(stderr, "InnoDB: dropping incompletely created" " SYS_FOREIGN_COLS table\n"); row_drop_table_for_mysql("SYS_FOREIGN_COLS", trx, TRUE); } fprintf(stderr, "InnoDB: Creating foreign key constraint system tables\n"); /* NOTE: in dict_load_foreigns we use the fact that there are 2 secondary indexes on SYS_FOREIGN, and they are defined just like below */ /* NOTE: when designing InnoDB's foreign key support in 2001, we made an error and made the table names and the foreign key id of type 'CHAR' (internally, really a VARCHAR). We should have made the type VARBINARY, like in other InnoDB system tables, to get a clean design. */ #if 0 error = que_eval_sql(NULL, "PROCEDURE CREATE_FOREIGN_SYS_TABLES_PROC () IS\n" "BEGIN\n" "CREATE TABLE\n" "SYS_FOREIGN(ID CHAR, FOR_NAME CHAR," " REF_NAME CHAR, N_COLS INT);\n" "CREATE UNIQUE CLUSTERED INDEX ID_IND" " ON SYS_FOREIGN (ID);\n" "CREATE INDEX FOR_IND" " ON SYS_FOREIGN (FOR_NAME);\n" "CREATE INDEX REF_IND" " ON SYS_FOREIGN (REF_NAME);\n" "CREATE TABLE\n" "SYS_FOREIGN_COLS(ID CHAR, POS INT," " FOR_COL_NAME CHAR, REF_COL_NAME CHAR);\n" "CREATE UNIQUE CLUSTERED INDEX ID_IND" " ON SYS_FOREIGN_COLS (ID, POS);\n" "END;\n" , FALSE, trx); #endif //zlqlxm //2011-10-13 /* [ [ (gdb) info break Num Type Disp Enb Address What 1 breakpoint keep y 0x08108861 in innobase_start_or_create_for_mysql at srv0start.c:2279 breakpoint already hit 1 time 2 breakpoint keep y 0x080b3796 in recv_recovery_from_checkpoint_start_func at log0recv.c:2925 breakpoint already hit 1 time 3 breakpoint keep y 0x08108886 in innobase_start_or_create_for_mysql at srv0start.c:2356 breakpoint already hit 1 time 4 breakpoint keep y 0x08075911 in dict_boot at dict0boot.c:260 breakpoint already hit 1 time 5 breakpoint keep y 0x08075994 in dict_boot at dict0boot.c:286 breakpoint already hit 1 time 6 breakpoint keep y 0x08076414 in dict_boot at dict0boot.c:446 breakpoint already hit 1 time 7 breakpoint keep y 0x0809e2f7 in ibuf_init_at_db_start at ibuf0ibuf.c:548 breakpoint already hit 1 time 8 breakpoint keep y 0x080953a7 in fseg_n_reserved_pages at fsp0fsp.c:2434 breakpoint already hit 1 time 9 breakpoint keep y 0x08094c8c in fseg_inode_try_get at fsp0fsp.c:2073 10 breakpoint keep y 0x08094cbe in fseg_inode_try_get at fsp0fsp.c:2075 (gdb) ]/dict0boot => / ***************************************************************** // ** Creates the file page for the dictionary header. This function is called only at the database creation. @return TRUE if succeed * / static ibool dict_hdr_create( / *============* / mtr_t* mtr) / *!< in: mtr * / => dict_create [ os0file.c: } else if (create_mode == OS_FILE_CREATE) { mode_str = "CREATE"; create_flag = O_RDWR | O_CREAT | O_EXCL; ] [os0file.h: #ifdef UNIV_PFS_IO # define os_file_create(key, name, create, purpose, type, success) \ pfs_os_file_create_func(key, name, create, purpose, type, \ success, __FILE__, __LINE__) ... #else / * If UNIV_PFS_IO is not defined, these I/O APIs point to original un-instrumented file I/O APIs * / # define os_file_create(key, name, create, purpose, type, success) \ os_file_create_func(name, create, purpose, type, success) //=>“... create_flag = O_RDWR | O_CREAT | O_EXCL; ... file = open(name, create_flag, os_innodb_umask); ...” ... #endif ] ] [root@server01 InnoSQL-5.5.8]# grep "define UNIV_LIKELY" ./ -r ./storage/innobase/include/univ.i:# define UNIV_LIKELY_NULL(ptr) __builtin_expect((ulint) ptr, 0) ./storage/innobase/include/univ.i:# define UNIV_LIKELY_NULL(expr) (expr) ./storage/innobase/include/univ.i:# define UNIV_LIKELY_NULL(expr) (expr) ./storage/innobase/include/univ.i:#define UNIV_LIKELY(cond) UNIV_EXPECT(cond, TRUE) [srv0start.c: if (create_new_db) { mtr_start(&mtr); fsp_header_init(0, sum_of_new_sizes, &mtr); //=>mlog_write_ulint... mtr_commit(&mtr); //=>把文件空间头写入文件!!;; ] [fsp0fsp.c: / ** Initializes the space header of a new created space and creates also the insert buffer tree root if space == 0. * / UNIV_INTERN void fsp_header_init( / *============* / ulint space, / *!< in: space id * / ulint size, / *!< in: current size in blocks * / mtr_t* mtr) / *!< in: mini-transaction handle * / ] [srv0start.c:/p1253: PROCEDURE CREATE_FOREIGN_SYS_TABLES_PROC () IS BEGIN CREATE TABLE SYS_FOREIGN( ID CHAR, FOR_NAME CHAR, REF_NAME CHAR, N_COLS INT ); CREATE UNIQUE CLUSTERED INDEX ID_IND ON SYS_FOREIGN (ID); CREATE INDEX FOR_IND ON SYS_FOREIGN (FOR_NAME); CREATE INDEX REF_IND ON SYS_FOREIGN (REF_NAME); CREATE TABLE SYS_FOREIGN_COLS( ID CHAR, POS INT, FOR_COL_NAME CHAR, REF_COL_NAME CHAR ); CREATE UNIQUE CLUSTERED INDEX ID_IND ON SYS_FOREIGN_COLS (ID, POS); END; ]//----2011-10-09-21-13;+--21-17:R; */ error=DB_SUCCESS; //z+ //zlqlxm //--2011-10-09-21-30:OK;+--21-34:R; //-2011-10-12-20-14去除此句!!!;;; //+z//lqlxm //2011-10-13 if (error != DB_SUCCESS) { fprintf(stderr, "InnoDB: error %lu in creation\n", (ulong) error); ut_a(error == DB_OUT_OF_FILE_SPACE || error == DB_TOO_MANY_CONCURRENT_TRXS); fprintf(stderr, "InnoDB: creation failed\n" "InnoDB: tablespace is full\n" "InnoDB: dropping incompletely created" " SYS_FOREIGN tables\n"); row_drop_table_for_mysql("SYS_FOREIGN", trx, TRUE); row_drop_table_for_mysql("SYS_FOREIGN_COLS", trx, TRUE); error = DB_MUST_GET_MORE_FILE_SPACE; } trx_commit_for_mysql(trx); row_mysql_unlock_data_dictionary(trx); trx_free_for_mysql(trx); if (error == DB_SUCCESS) { fprintf(stderr, "InnoDB: Foreign key constraint system tables" " created\n"); } return(error); }