diff options
Diffstat (limited to 'storage/innodb_plugin')
162 files changed, 5098 insertions, 14738 deletions
diff --git a/storage/innodb_plugin/CMakeLists.txt b/storage/innodb_plugin/CMakeLists.txt index 36e157ae736..87318ceec78 100644 --- a/storage/innodb_plugin/CMakeLists.txt +++ b/storage/innodb_plugin/CMakeLists.txt @@ -78,9 +78,11 @@ SET(INNODB_PLUGIN_SOURCES btr/btr0btr.c btr/btr0cur.c btr/btr0pcur.c btr/btr0sea trx/trx0i_s.c trx/trx0purge.c trx/trx0rec.c trx/trx0roll.c trx/trx0rseg.c trx/trx0sys.c trx/trx0trx.c trx/trx0undo.c usr/usr0sess.c - ut/ut0byte.c ut/ut0dbg.c ut/ut0mem.c ut/ut0rnd.c ut/ut0ut.c ut/ut0vec.c + ut/ut0byte.c ut/ut0dbg.c ut/ut0mem.c ut/ut0rbt.c ut/ut0rnd.c ut/ut0ut.c ut/ut0vec.c ut/ut0list.c ut/ut0wqueue.c) -ADD_DEFINITIONS(-DHAVE_WINDOWS_ATOMICS -DIB_HAVE_PAUSE_INSTRUCTION) +# Windows atomics do not perform well. Disable Windows atomics by default. +# See bug#52102 for details. +#ADD_DEFINITIONS(-DHAVE_WINDOWS_ATOMICS -DINNODB_RW_LOCKS_USE_ATOMICS -DHAVE_IB_PAUSE_INSTRUCTION) +ADD_DEFINITIONS(-DHAVE_IB_PAUSE_INSTRUCTION) -#Disable storage engine, as we are using XtraDB -#MYSQL_STORAGE_ENGINE(INNODB_PLUGIN) +MYSQL_STORAGE_ENGINE(INNODB_PLUGIN) diff --git a/storage/innodb_plugin/ChangeLog b/storage/innodb_plugin/ChangeLog index 1a6e07fd147..bc69aaca96a 100644 --- a/storage/innodb_plugin/ChangeLog +++ b/storage/innodb_plugin/ChangeLog @@ -1,3 +1,262 @@ +2010-05-03 The InnoDB Team + + * buf0buf.c: + Fix Bug#53248 compressed tables page checksum mismatch after + re-enabling innodb_checksums + +2010-04-28 The InnoDB Team + + * log/log0recv.h, log/log0recv.c: + Fix Bug#53122 InnoDB recovery uses too big a hash table for redo + log records + +2010-04-27 The InnoDB Team + + * handler/ha_innodb.cc, lock/lock0lock.c, row/row0mysql.c, + row/row0sel.c: + Fix Bug#48607 READ UNCOMMITTED uses more locks than READ COMMITTED + in InnoDB 5.1+ + +2010-04-26 The InnoDB Team + + * row/row0sel.c: + Fix Bug#52663 Lost update incrementing column value under + READ COMMITTED isolation level + +2010-04-22 The InnoDB Team + + * include/dict0boot.h, dict/dict0boot.c: + Fix a bug that prevented the crash recovery of fast CREATE INDEX + from dropping partially created indexes. + +2010-04-21 The InnoDB Team + + * btr/btr0btr.c: + Fix Bug#52964 Infinite loop in btr_page_split_and_insert() + in ROW_FORMAT=COMPRESSED + +2010-04-21 The InnoDB Team + + * data/data0data.c: + Fix Bug#52745 Failing assertion: blob_no < page_zip->n_blobs + +2010-04-20 The InnoDB Team + + * dict/dict0crea.c, handler/ha_innodb.cc, include/trx0trx.h: + Fix Bug#50495 'Row size too large' for plugin, but works for + built-in InnoDB + Only check the record size at index creation time when + innodb_strict_mode is set or when ROW_FORMAT is DYNAMIC or COMPRESSED. + +2010-04-20 The InnoDB Team + + * btr/btr0btr.c, include/univ.i: + Implement UNIV_BTR_AVOID_COPY, for avoiding writes when a B-tree + node is split at the first or last record. + +2010-04-15 The InnoDB Team + + * trx/trx0rec.c: + Fix Bug#52746 InnoDB purge thread crashed with table containing + prefix indexed blobs + +2010-03-31 The InnoDB Team + + * mysql-test/innodb_bug51920.test, mysql-test/innodb_bug51920.result, + srv/srv0srv.c: + Fix Bug#51920 InnoDB connections in row lock wait ignore KILL + until lock wait timeout + +2010-03-31 The InnoDB Team + + * mysql-test/innodb_bug38231.test: + Remove non-determinism in the test case. + +2010-03-18 The InnoDB Team + + * CMakeLists.txt: + Fix Bug#52102 InnoDB Plugin shows performance drop compared to + InnoDB (Windows) + +2010-03-18 The InnoDB Team + + * buf0buf.ic: + When comparing the time of the first access to a block against + innodb_old_blocks_time, use 32-bit arithmetics. The comparison was + incorrect on 64-bit systems. + +2010-03-11 The InnoDB Team + + * buf0buf.h, buf0buf.ic: + Fix and clarify the latching of some buf_block_t members. + Note that check_index_page_at_flush is not protected by any mutex. + Note and assert that lock_hash_val is protected by the rw-latch. + +2010-03-10 The InnoDB Team + + * trx/trx0sys.c: + Fix Bug#51653 outdated reference to set-variable + +2010-03-10 The InnoDB Team + + * handler/ha_innodb.cc, mysql-test/innodb_bug21704.result, + mysql-test/innodb_bug47621.result, mysql-test/innodb_bug47621.test: + Fix Bug#47621 MySQL and InnoDB data dictionaries will become out of + sync when renaming columns + +2010-03-10 The InnoDB Team + + * handler/ha_innodb.cc: + Fix Bug#51356 Many Valgrind errors in error messages + with concurrent DDL + +2010-03-10 The InnoDB Team + + * handler/ha_innodb.cc, handler/handler0alter.cc, + mysql-test/innodb_bug51378.result, mysql-test/innodb_bug51378.test: + Fix Bug#51378 Init 'ref_length' to correct value, in case an out + of bound MySQL primary_key + +2010-03-10 The InnoDB Team + + * log/log0recv.c: + Remove a bogus assertion about page numbers exceeding 0x90000000 + in the redo log. Abort when encountering a corrupted redo log + record, unless innodb_force_recovery is set. + +2010-03-09 The InnoDB Team + + * handler/ha_innodb.cc: + Make SHOW ENGINE INNODB MUTEX STATUS display SUM(os_waits) + for the buffer pool block mutexes and locks. + +2010-03-08 The InnoDB Team + + * fil/fil0fil.c: + Fix ALTER TABLE ... IMPORT TABLESPACE of compressed tables. + +2010-03-03 The InnoDB Team + + * handler/handler0alter.cc, innodb-index.result, innodb-index.test, + innodb.result, innodb.test: + Disallow a duplicate index name when creating an index. + +2010-02-11 The InnoDB Team + + * include/mem0mem.h, include/mem0mem.ic, mem/mem0mem.c: + Fix Bug#49535 Available memory check slows down crash + recovery tens of times + +2010-02-09 The InnoDB Team + + * buf/buf0buf.c: + Fix Bug#38901 InnoDB logs error repeatedly when trying to load + page into buffer pool + +2010-02-09 The InnoDB Team + + * srv/srv0srv.c: + Let the master thread sleep if the amount of work to be done is + calibrated as taking less than a second. + +2010-02-04 The InnoDB Team + + * btr/btr0btr.c, btr/btr0cur.c, btr/btr0pcur.c, buf/buf0buf.c, + include/btr0btr.h, include/btr0cur.h, include/btr0pcur.h, + include/btr0pcur.ic, include/buf0buf.h, row/row0ins.c, row/row0sel.c: + Pass the file name and line number of the caller of the + b-tree cursor functions to the buffer pool requests, in order + to make the latch diagnostics more accurate. + +2010-02-03 The InnoDB Team + + * lock/lock0lock.c: + Fix Bug#49001 SHOW INNODB STATUS deadlock info incorrect + when deadlock detection aborts + +2010-02-03 The InnoDB Team + + * buf/buf0lru.c: + Fix Bug#35077 Very slow DROP TABLE (ALTER TABLE, OPTIMIZE TABLE) + on compressed tables + +2010-02-03 The InnoDB Team + + * handler/ha_innodb.cc, include/row0mysql.h, row/row0mysql.c: + Clean up CHECK TABLE error handling. + +2010-02-01 The InnoDB Team + + * handler/ha_innodb.cc, mysql-test/innodb-autoinc.test, + mysql-test/innodb-autoinc.result, + mysql-test/innodb-autoinc-44030.test, + mysql-test/innodb-autoinc-44030.result: + Fix Bug#49497 Error 1467 (ER_AUTOINC_READ_FAILED) on inserting + a negative value + +2010-01-27 The InnoDB Team + + * include/row0mysql.h, log/log0recv.c, row/row0mysql.c: + Drop temporary tables at startup. + This addresses the third aspect of + Bug#41609 Crash recovery does not work for InnoDB temporary tables. + +2010-01-21 The InnoDB Team + + * buf/buf0buf.c: + Do not merge buffered inserts to compressed pages before + the redo log has been applied in crash recovery. + +2010-01-13 The InnoDB Team + + * row/row0sel.c: + On the READ UNCOMMITTED isolation level, do not attempt to access + a clustered index record that has been marked for deletion. The + built-in InnoDB in MySQL 5.1 and earlier would attempt to retrieve + a previous version of the record in this case. + +2010-01-13 The InnoDB Team + + * buf/buf0buf.c: + When disabling the adaptive hash index, check the block state + before checking block->is_hashed, because the latter may be + uninitialized right after server startup. + +2010-01-12 The InnoDB Team + + * handler/ha_innodb.cc, handler/ha_innodb.h: + Fix Bug#46193 crash when accessing tables after enabling + innodb_force_recovery option + +2010-01-12 The InnoDB Team + + * row/row0mysql.c: + Fix Bug#49238 Creating/Dropping a temporary table while at 1023 + transactions will cause assert. + +2009-12-02 The InnoDB Team + + * srv/srv0start.c: + Display the zlib version number at startup. + InnoDB compressed tables use zlib, and the implementation depends + on the zlib function compressBound(), whose definition was slightly + changed in zlib version 1.2.3.1 in 2006. MySQL bundles zlib 1.2.3 + from 2005, but some installations use a more recent zlib. + +2009-11-30 The InnoDB Team + + * dict/dict0crea.c, dict/dict0mem.c, dict/dict0load.c, + dict/dict0boot.c, fil/fil0fil.c, handler/ha_innodb.cc, + include/dict0mem.h, row/row0mysql.c: + Fix the bogus warning messages for non-existing temporary + tables that were reported in + Bug#41609 Crash recovery does not work for InnoDB temporary tables. + The actual crash recovery bug was corrected on 2009-04-29. + +2009-11-27 The InnoDB Team + + InnoDB Plugin 1.0.6 released + 2009-11-20 The InnoDB Team * handler/ha_innodb.cc: @@ -79,8 +338,8 @@ sync/sync0arr.c, sync/sync0sync.c, thr/thr0loc.c, trx/trx0i_s.c, trx/trx0purge.c, trx/trx0rseg.c, trx/trx0sys.c, trx/trx0undo.c, usr/usr0sess.c, ut/ut0mem.c: - Fix Bug #45992 innodb memory not freed after shutdown - Fix Bug #46656 InnoDB plugin: memory leaks (Valgrind) + Fix Bug#45992 innodb memory not freed after shutdown + Fix Bug#46656 InnoDB plugin: memory leaks (Valgrind) 2009-10-29 The InnoDB Team @@ -422,7 +681,7 @@ * dict/dict0dict.c: When an index column cannot be found in the table during index creation, display additional diagnostic before an assertion failure. - This does NOT fix Bug #44571 InnoDB Plugin crashes on ADD INDEX, + This does NOT fix Bug#44571 InnoDB Plugin crashes on ADD INDEX, but it helps understand the reason of the crash. 2009-06-17 The InnoDB Team @@ -535,6 +794,12 @@ Fix Bug#44320 InnoDB: missing DB_ROLL_PTR in Table Monitor COLUMNS output +2009-04-29 The InnoDB Team + + * fil/fil0fil.c, include/fil0fil.h, include/mtr0mtr.h, + log/log0recv.c: + Fix Bug#41609 Crash recovery does not work for InnoDB temporary tables + 2009-04-23 The InnoDB Team * row/row0mysql.c: diff --git a/storage/innodb_plugin/Makefile.am b/storage/innodb_plugin/Makefile.am index 5c71fe18d14..1d0dd936895 100644 --- a/storage/innodb_plugin/Makefile.am +++ b/storage/innodb_plugin/Makefile.am @@ -217,6 +217,7 @@ noinst_HEADERS= \ include/ut0lst.h \ include/ut0mem.h \ include/ut0mem.ic \ + include/ut0rbt.h \ include/ut0rnd.h \ include/ut0rnd.ic \ include/ut0sort.h \ @@ -318,6 +319,7 @@ libinnobase_a_SOURCES= \ ut/ut0dbg.c \ ut/ut0list.c \ ut/ut0mem.c \ + ut/ut0rbt.c \ ut/ut0rnd.c \ ut/ut0ut.c \ ut/ut0vec.c \ diff --git a/storage/innodb_plugin/btr/btr0btr.c b/storage/innodb_plugin/btr/btr0btr.c index 086b3a0a599..96fcc2ed821 100644 --- a/storage/innodb_plugin/btr/btr0btr.c +++ b/storage/innodb_plugin/btr/btr0btr.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1994, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1994, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -592,13 +592,15 @@ an x-latch on the tree. @return rec_get_offsets() of the node pointer record */ static ulint* -btr_page_get_father_node_ptr( -/*=========================*/ +btr_page_get_father_node_ptr_func( +/*==============================*/ ulint* offsets,/*!< in: work area for the return value */ mem_heap_t* heap, /*!< in: memory heap to use */ btr_cur_t* cursor, /*!< in: cursor pointing to user record, out: cursor on node pointer record, its page x-latched */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr) /*!< in: mtr */ { dtuple_t* tuple; @@ -622,7 +624,8 @@ btr_page_get_father_node_ptr( tuple = dict_index_build_node_ptr(index, user_rec, 0, heap, level); btr_cur_search_to_nth_level(index, level + 1, tuple, PAGE_CUR_LE, - BTR_CONT_MODIFY_TREE, cursor, 0, mtr); + BTR_CONT_MODIFY_TREE, cursor, 0, + file, line, mtr); node_ptr = btr_cur_get_rec(cursor); ut_ad(!page_rec_is_comp(node_ptr) @@ -670,6 +673,9 @@ btr_page_get_father_node_ptr( return(offsets); } +#define btr_page_get_father_node_ptr(of,heap,cur,mtr) \ + btr_page_get_father_node_ptr_func(of,heap,cur,__FILE__,__LINE__,mtr) + /************************************************************//** Returns the upper level node pointer to a page. It is assumed that mtr holds an x-latch on the tree. @@ -1445,11 +1451,11 @@ Calculates a split record such that the tuple will certainly fit on its half-page when the split is performed. We assume in this function only that the cursor page has at least one user record. @return split record, or NULL if tuple will be the first record on -upper half-page */ +the lower or upper half-page (determined by btr_page_tuple_smaller()) */ static rec_t* -btr_page_get_sure_split_rec( -/*========================*/ +btr_page_get_split_rec( +/*===================*/ btr_cur_t* cursor, /*!< in: cursor at which insert should be made */ const dtuple_t* tuple, /*!< in: tuple to insert */ ulint n_ext) /*!< in: number of externally stored columns */ @@ -1662,11 +1668,13 @@ Inserts a data tuple to a tree on a non-leaf level. It is assumed that mtr holds an x-latch on the tree. */ UNIV_INTERN void -btr_insert_on_non_leaf_level( -/*=========================*/ +btr_insert_on_non_leaf_level_func( +/*==============================*/ dict_index_t* index, /*!< in: index */ ulint level, /*!< in: level, must be > 0 */ dtuple_t* tuple, /*!< in: the record to be inserted */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr) /*!< in: mtr */ { big_rec_t* dummy_big_rec; @@ -1678,7 +1686,7 @@ btr_insert_on_non_leaf_level( btr_cur_search_to_nth_level(index, level, tuple, PAGE_CUR_LE, BTR_CONT_MODIFY_TREE, - &cursor, 0, mtr); + &cursor, 0, file, line, mtr); err = btr_cur_pessimistic_insert(BTR_NO_LOCKING_FLAG | BTR_KEEP_SYS_FLAG @@ -1824,6 +1832,37 @@ btr_attach_half_pages( } /*************************************************************//** +Determine if a tuple is smaller than any record on the page. +@return TRUE if smaller */ +static +ibool +btr_page_tuple_smaller( +/*===================*/ + btr_cur_t* cursor, /*!< in: b-tree cursor */ + const dtuple_t* tuple, /*!< in: tuple to consider */ + ulint* offsets,/*!< in/out: temporary storage */ + ulint n_uniq, /*!< in: number of unique fields + in the index page records */ + mem_heap_t** heap) /*!< in/out: heap for offsets */ +{ + buf_block_t* block; + const rec_t* first_rec; + page_cur_t pcur; + + /* Read the first user record in the page. */ + block = btr_cur_get_block(cursor); + page_cur_set_before_first(block, &pcur); + page_cur_move_to_next(&pcur); + first_rec = page_cur_get_rec(&pcur); + + offsets = rec_get_offsets( + first_rec, cursor->index, offsets, + n_uniq, heap); + + return(cmp_dtuple_rec(tuple, first_rec, offsets) < 0); +} + +/*************************************************************//** Splits an index page to halves and inserts the tuple. It is assumed that mtr holds an x-latch to the index tree. NOTE: the tree x-latch is released within this function! NOTE that the operation of this @@ -1893,12 +1932,17 @@ func_start: /* 1. Decide the split record; split_rec == NULL means that the tuple to be inserted should be the first record on the upper half-page */ + insert_left = FALSE; if (n_iterations > 0) { direction = FSP_UP; hint_page_no = page_no + 1; - split_rec = btr_page_get_sure_split_rec(cursor, tuple, n_ext); + split_rec = btr_page_get_split_rec(cursor, tuple, n_ext); + if (UNIV_UNLIKELY(split_rec == NULL)) { + insert_left = btr_page_tuple_smaller( + cursor, tuple, offsets, n_uniq, &heap); + } } else if (btr_page_get_split_rec_to_right(cursor, &split_rec)) { direction = FSP_UP; hint_page_no = page_no + 1; @@ -1906,37 +1950,24 @@ func_start: } else if (btr_page_get_split_rec_to_left(cursor, &split_rec)) { direction = FSP_DOWN; hint_page_no = page_no - 1; + ut_ad(split_rec); } else { direction = FSP_UP; hint_page_no = page_no + 1; - if (page_get_n_recs(page) == 1) { - page_cur_t pcur; - - /* There is only one record in the index page - therefore we can't split the node in the middle - by default. We need to determine whether the - new record will be inserted to the left or right. */ - - /* Read the first (and only) record in the page. */ - page_cur_set_before_first(block, &pcur); - page_cur_move_to_next(&pcur); - first_rec = page_cur_get_rec(&pcur); + /* If there is only one record in the index page, we + can't split the node in the middle by default. We need + to determine whether the new record will be inserted + to the left or right. */ - offsets = rec_get_offsets( - first_rec, cursor->index, offsets, - n_uniq, &heap); - - /* If the new record is less than the existing record - the split in the middle will copy the existing - record to the new node. */ - if (cmp_dtuple_rec(tuple, first_rec, offsets) < 0) { - split_rec = page_get_middle_rec(page); - } else { - split_rec = NULL; - } - } else { + if (page_get_n_recs(page) > 1) { split_rec = page_get_middle_rec(page); + } else if (btr_page_tuple_smaller(cursor, tuple, + offsets, n_uniq, &heap)) { + split_rec = page_rec_get_next( + page_get_infimum_rec(page)); + } else { + split_rec = NULL; } } @@ -1966,11 +1997,15 @@ func_start: avoid further splits by inserting the record to an empty page. */ split_rec = NULL; - goto insert_right; + goto insert_empty; } + } else if (UNIV_UNLIKELY(insert_left)) { + first_rec = page_rec_get_next(page_get_infimum_rec(page)); + move_limit = page_rec_get_next(btr_cur_get_rec(cursor)); } else { -insert_right: - insert_left = FALSE; +insert_empty: + ut_ad(!split_rec); + ut_ad(!insert_left); buf = mem_alloc(rec_get_converted_size(cursor->index, tuple, n_ext)); @@ -1994,7 +2029,11 @@ insert_right: && btr_page_insert_fits(cursor, split_rec, offsets, tuple, n_ext, heap); } else { - mem_free(buf); + if (!insert_left) { + mem_free(buf); + buf = NULL; + } + insert_will_fit = !new_page_zip && btr_page_insert_fits(cursor, NULL, NULL, tuple, n_ext, heap); @@ -2007,7 +2046,17 @@ insert_right: } /* 5. Move then the records to the new page */ - if (direction == FSP_DOWN) { + if (direction == FSP_DOWN +#ifdef UNIV_BTR_AVOID_COPY + && page_rec_is_supremum(move_limit)) { + /* Instead of moving all records, make the new page + the empty page. */ + + left_block = block; + right_block = new_block; + } else if (direction == FSP_DOWN +#endif /* UNIV_BTR_AVOID_COPY */ + ) { /* fputs("Split left\n", stderr); */ if (0 @@ -2050,6 +2099,14 @@ insert_right: right_block = block; lock_update_split_left(right_block, left_block); +#ifdef UNIV_BTR_AVOID_COPY + } else if (!split_rec) { + /* Instead of moving all records, make the new page + the empty page. */ + + left_block = new_block; + right_block = block; +#endif /* UNIV_BTR_AVOID_COPY */ } else { /* fputs("Split right\n", stderr); */ diff --git a/storage/innodb_plugin/btr/btr0cur.c b/storage/innodb_plugin/btr/btr0cur.c index 46dfb5d1a46..0e603fdca8f 100644 --- a/storage/innodb_plugin/btr/btr0cur.c +++ b/storage/innodb_plugin/btr/btr0cur.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1994, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1994, 2010, Innobase Oy. All Rights Reserved. Copyright (c) 2008, Google Inc. Portions of this file contain modifications contributed and copyrighted by @@ -342,6 +342,8 @@ btr_cur_search_to_nth_level( ulint has_search_latch,/*!< in: info on the latch mode the caller currently has on btr_search_latch: RW_S_LATCH, or 0 */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr) /*!< in: mtr */ { page_cur_t* page_cursor; @@ -520,7 +522,7 @@ btr_cur_search_to_nth_level( retry_page_get: block = buf_page_get_gen(space, zip_size, page_no, rw_latch, guess, buf_mode, - __FILE__, __LINE__, mtr); + file, line, mtr); if (block == NULL) { /* This must be a search to perform an insert; try insert to the insert buffer */ @@ -677,13 +679,15 @@ func_exit: Opens a cursor at either end of an index. */ UNIV_INTERN void -btr_cur_open_at_index_side( -/*=======================*/ +btr_cur_open_at_index_side_func( +/*============================*/ ibool from_left, /*!< in: TRUE if open to the low end, FALSE if to the high end */ dict_index_t* index, /*!< in: index */ ulint latch_mode, /*!< in: latch mode */ btr_cur_t* cursor, /*!< in: cursor */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr) /*!< in: mtr */ { page_cur_t* page_cursor; @@ -728,7 +732,7 @@ btr_cur_open_at_index_side( page_t* page; block = buf_page_get_gen(space, zip_size, page_no, RW_NO_LATCH, NULL, BUF_GET, - __FILE__, __LINE__, mtr); + file, line, mtr); page = buf_block_get_frame(block); ut_ad(0 == ut_dulint_cmp(index->id, btr_page_get_index_id(page))); @@ -808,11 +812,13 @@ btr_cur_open_at_index_side( Positions a cursor at a randomly chosen position within a B-tree. */ UNIV_INTERN void -btr_cur_open_at_rnd_pos( -/*====================*/ +btr_cur_open_at_rnd_pos_func( +/*=========================*/ dict_index_t* index, /*!< in: index */ ulint latch_mode, /*!< in: BTR_SEARCH_LEAF, ... */ btr_cur_t* cursor, /*!< in/out: B-tree cursor */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr) /*!< in: mtr */ { page_cur_t* page_cursor; @@ -847,7 +853,7 @@ btr_cur_open_at_rnd_pos( block = buf_page_get_gen(space, zip_size, page_no, RW_NO_LATCH, NULL, BUF_GET, - __FILE__, __LINE__, mtr); + file, line, mtr); page = buf_block_get_frame(block); ut_ad(0 == ut_dulint_cmp(index->id, btr_page_get_index_id(page))); @@ -1058,7 +1064,6 @@ btr_cur_optimistic_insert( ibool inherit; ulint zip_size; ulint rec_size; - mem_heap_t* heap = NULL; ulint err; *big_rec = NULL; @@ -1138,10 +1143,6 @@ btr_cur_optimistic_insert( index, entry, big_rec_vec); } - if (heap) { - mem_heap_free(heap); - } - return(DB_TOO_BIG_RECORD); } } @@ -1164,15 +1165,11 @@ fail_err: dtuple_convert_back_big_rec(index, entry, big_rec_vec); } - if (UNIV_LIKELY_NULL(heap)) { - mem_heap_free(heap); - } - return(err); } if (UNIV_UNLIKELY(max_size < BTR_CUR_PAGE_REORGANIZE_LIMIT - || max_size < rec_size) + || max_size < rec_size) && UNIV_LIKELY(page_get_n_recs(page) > 1) && page_get_max_insert_size(page, 1) < rec_size) { @@ -1238,10 +1235,6 @@ fail_err: } } - if (UNIV_LIKELY_NULL(heap)) { - mem_heap_free(heap); - } - #ifdef BTR_CUR_HASH_ADAPT if (!reorg && leaf && (cursor->flag == BTR_CUR_HASH)) { btr_search_update_hash_node_on_insert(cursor); @@ -3100,7 +3093,8 @@ btr_estimate_n_rows_in_range( btr_cur_search_to_nth_level(index, 0, tuple1, mode1, BTR_SEARCH_LEAF | BTR_ESTIMATE, - &cursor, 0, &mtr); + &cursor, 0, + __FILE__, __LINE__, &mtr); } else { btr_cur_open_at_index_side(TRUE, index, BTR_SEARCH_LEAF | BTR_ESTIMATE, @@ -3117,7 +3111,8 @@ btr_estimate_n_rows_in_range( btr_cur_search_to_nth_level(index, 0, tuple2, mode2, BTR_SEARCH_LEAF | BTR_ESTIMATE, - &cursor, 0, &mtr); + &cursor, 0, + __FILE__, __LINE__, &mtr); } else { btr_cur_open_at_index_side(FALSE, index, BTR_SEARCH_LEAF | BTR_ESTIMATE, @@ -3361,6 +3356,8 @@ btr_estimate_number_of_different_key_vals( also the pages used for external storage of fields (those pages are included in index->stat_n_leaf_pages) */ + dict_index_stat_mutex_enter(index); + for (j = 0; j <= n_cols; j++) { index->stat_n_diff_key_vals[j] = ((n_diff[j] @@ -3390,6 +3387,8 @@ btr_estimate_number_of_different_key_vals( index->stat_n_diff_key_vals[j] += add_on; } + dict_index_stat_mutex_exit(index); + mem_free(n_diff); if (UNIV_LIKELY_NULL(heap)) { mem_heap_free(heap); @@ -4252,7 +4251,7 @@ btr_free_externally_stored_field( /* In the rollback of uncommitted transactions, we may encounter a clustered index record whose BLOBs have not been written. There is nothing to free then. */ - ut_a(rb_ctx == RB_RECOVERY); + ut_a(rb_ctx == RB_RECOVERY || rb_ctx == RB_RECOVERY_PURGE_REC); return; } @@ -4298,7 +4297,7 @@ btr_free_externally_stored_field( || (mach_read_from_1(field_ref + BTR_EXTERN_LEN) & BTR_EXTERN_OWNER_FLAG) /* Rollback and inherited field */ - || (rb_ctx != RB_NONE + || ((rb_ctx == RB_NORMAL || rb_ctx == RB_RECOVERY) && (mach_read_from_1(field_ref + BTR_EXTERN_LEN) & BTR_EXTERN_INHERITED_FLAG))) { diff --git a/storage/innodb_plugin/btr/btr0pcur.c b/storage/innodb_plugin/btr/btr0pcur.c index ec98692c35b..658901208ef 100644 --- a/storage/innodb_plugin/btr/btr0pcur.c +++ b/storage/innodb_plugin/btr/btr0pcur.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -205,10 +205,12 @@ record and it can be restored on a user record whose ordering fields are identical to the ones of the original user record */ UNIV_INTERN ibool -btr_pcur_restore_position( -/*======================*/ +btr_pcur_restore_position_func( +/*===========================*/ ulint latch_mode, /*!< in: BTR_SEARCH_LEAF, ... */ btr_pcur_t* cursor, /*!< in: detached persistent cursor */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr) /*!< in: mtr */ { dict_index_t* index; @@ -217,6 +219,9 @@ btr_pcur_restore_position( ulint old_mode; mem_heap_t* heap; + ut_ad(mtr); + ut_ad(mtr->state == MTR_ACTIVE); + index = btr_cur_get_index(btr_pcur_get_btr_cur(cursor)); if (UNIV_UNLIKELY(cursor->old_stored != BTR_PCUR_OLD_STORED) @@ -257,7 +262,8 @@ btr_pcur_restore_position( if (UNIV_LIKELY(buf_page_optimistic_get( latch_mode, cursor->block_when_stored, - cursor->modify_clock, mtr))) { + cursor->modify_clock, + file, line, mtr))) { cursor->pos_state = BTR_PCUR_IS_POSITIONED; buf_block_dbg_add_level(btr_pcur_get_block(cursor), @@ -312,8 +318,8 @@ btr_pcur_restore_position( mode = PAGE_CUR_L; } - btr_pcur_open_with_no_init(index, tuple, mode, latch_mode, - cursor, 0, mtr); + btr_pcur_open_with_no_init_func(index, tuple, mode, latch_mode, + cursor, 0, file, line, mtr); /* Restore the old search mode */ cursor->search_mode = old_mode; @@ -553,8 +559,8 @@ before first in tree. The latching mode must be BTR_SEARCH_LEAF or BTR_MODIFY_LEAF. */ UNIV_INTERN void -btr_pcur_open_on_user_rec( -/*======================*/ +btr_pcur_open_on_user_rec_func( +/*===========================*/ dict_index_t* index, /*!< in: index */ const dtuple_t* tuple, /*!< in: tuple on which search done */ ulint mode, /*!< in: PAGE_CUR_L, ... */ @@ -562,9 +568,12 @@ btr_pcur_open_on_user_rec( BTR_MODIFY_LEAF */ btr_pcur_t* cursor, /*!< in: memory buffer for persistent cursor */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr) /*!< in: mtr */ { - btr_pcur_open(index, tuple, mode, latch_mode, cursor, mtr); + btr_pcur_open_func(index, tuple, mode, latch_mode, cursor, + file, line, mtr); if ((mode == PAGE_CUR_GE) || (mode == PAGE_CUR_G)) { diff --git a/storage/innodb_plugin/buf/buf0buddy.c b/storage/innodb_plugin/buf/buf0buddy.c index f0e1395c307..66d802f8a36 100644 --- a/storage/innodb_plugin/buf/buf0buddy.c +++ b/storage/innodb_plugin/buf/buf0buddy.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 2006, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 2006, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -391,6 +391,8 @@ buf_buddy_relocate_block( UT_LIST_ADD_FIRST(list, buf_pool->zip_clean, dpage); } + UNIV_MEM_INVALID(bpage, sizeof *bpage); + mutex_exit(&buf_pool_zip_mutex); return(TRUE); } diff --git a/storage/innodb_plugin/buf/buf0buf.c b/storage/innodb_plugin/buf/buf0buf.c index 111d396fbc5..f299c2df969 100644 --- a/storage/innodb_plugin/buf/buf0buf.c +++ b/storage/innodb_plugin/buf/buf0buf.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. Copyright (c) 2008, Google Inc. Portions of this file contain modifications contributed and copyrighted by @@ -242,6 +242,8 @@ the read requests for the whole area. #ifndef UNIV_HOTBACKUP /** Value in microseconds */ static const int WAIT_FOR_READ = 5000; +/** Number of attemtps made to read in a page in the buffer pool */ +static const ulint BUF_PAGE_READ_MAX_RETRIES = 100; /** The buffer buf_pool of the database */ UNIV_INTERN buf_pool_t* buf_pool = NULL; @@ -1058,7 +1060,9 @@ buf_pool_drop_hash_index(void) when we have an x-latch on btr_search_latch; see the comment in buf0buf.h */ - if (!block->is_hashed) { + if (buf_block_get_state(block) + != BUF_BLOCK_FILE_PAGE + || !block->is_hashed) { continue; } @@ -1187,8 +1191,6 @@ buf_relocate( HASH_DELETE(buf_page_t, hash, buf_pool->page_hash, fold, bpage); HASH_INSERT(buf_page_t, hash, buf_pool->page_hash, fold, dpage); - - UNIV_MEM_INVALID(bpage, sizeof *bpage); } /********************************************************************//** @@ -1818,14 +1820,14 @@ buf_zip_decompress( buf_block_t* block, /*!< in/out: block */ ibool check) /*!< in: TRUE=verify the page checksum */ { - const byte* frame = block->page.zip.data; + const byte* frame = block->page.zip.data; + ulint stamp_checksum = mach_read_from_4( + frame + FIL_PAGE_SPACE_OR_CHKSUM); ut_ad(buf_block_get_zip_size(block)); ut_a(buf_block_get_space(block) != 0); - if (UNIV_LIKELY(check)) { - ulint stamp_checksum = mach_read_from_4( - frame + FIL_PAGE_SPACE_OR_CHKSUM); + if (UNIV_LIKELY(check && stamp_checksum != BUF_NO_CHECKSUM_MAGIC)) { ulint calc_checksum = page_zip_calc_checksum( frame, page_zip_get_size(&block->page.zip)); @@ -2034,8 +2036,10 @@ buf_page_get_gen( unsigned access_time; ulint fix_type; ibool must_read; + ulint retries = 0; ut_ad(mtr); + ut_ad(mtr->state == MTR_ACTIVE); ut_ad((rw_latch == RW_S_LATCH) || (rw_latch == RW_X_LATCH) || (rw_latch == RW_NO_LATCH)); @@ -2088,7 +2092,29 @@ loop2: return(NULL); } - buf_read_page(space, zip_size, offset); + if (buf_read_page(space, zip_size, offset)) { + retries = 0; + } else if (retries < BUF_PAGE_READ_MAX_RETRIES) { + ++retries; + } else { + fprintf(stderr, "InnoDB: Error: Unable" + " to read tablespace %lu page no" + " %lu into the buffer pool after" + " %lu attempts\n" + "InnoDB: The most probable cause" + " of this error may be that the" + " table has been corrupted.\n" + "InnoDB: You can try to fix this" + " problem by using" + " innodb_force_recovery.\n" + "InnoDB: Please see reference manual" + " for more details.\n" + "InnoDB: Aborting...\n", + space, offset, + BUF_PAGE_READ_MAX_RETRIES); + + ut_error; + } #if defined UNIV_DEBUG || defined UNIV_BUF_DEBUG ut_a(++buf_dbg_counter % 37 || buf_validate()); @@ -2196,22 +2222,8 @@ wait_until_unfixed: ut_ad(!block->page.in_flush_list); } else { /* Relocate buf_pool->flush_list. */ - buf_page_t* b; - - b = UT_LIST_GET_PREV(list, &block->page); - ut_ad(block->page.in_flush_list); - UT_LIST_REMOVE(list, buf_pool->flush_list, - &block->page); - - if (b) { - UT_LIST_INSERT_AFTER( - list, buf_pool->flush_list, b, - &block->page); - } else { - UT_LIST_ADD_FIRST( - list, buf_pool->flush_list, - &block->page); - } + buf_flush_relocate_on_flush_list(bpage, + &block->page); } /* Buffer-fix, I/O-fix, and X-latch the block @@ -2225,6 +2237,9 @@ wait_until_unfixed: block->page.buf_fix_count = 1; buf_block_set_io_fix(block, BUF_IO_READ); rw_lock_x_lock(&block->lock); + + UNIV_MEM_INVALID(bpage, sizeof *bpage); + mutex_exit(&block->mutex); mutex_exit(&buf_pool_zip_mutex); buf_pool->n_pend_unzip++; @@ -2236,8 +2251,9 @@ wait_until_unfixed: /* Decompress the page and apply buffered operations while not holding buf_pool_mutex or block->mutex. */ success = buf_zip_decompress(block, srv_use_checksums); + ut_a(success); - if (UNIV_LIKELY(success)) { + if (UNIV_LIKELY(!recv_no_ibuf_operations)) { ibuf_merge_or_delete_for_page(block, space, offset, zip_size, TRUE); } @@ -2250,13 +2266,6 @@ wait_until_unfixed: mutex_exit(&block->mutex); buf_pool->n_pend_unzip--; rw_lock_x_unlock(&block->lock); - - if (UNIV_UNLIKELY(!success)) { - - buf_pool_mutex_exit(); - return(NULL); - } - break; case BUF_BLOCK_ZIP_FREE: @@ -2356,8 +2365,8 @@ page. @return TRUE if success */ UNIV_INTERN ibool -buf_page_optimistic_get_func( -/*=========================*/ +buf_page_optimistic_get( +/*====================*/ ulint rw_latch,/*!< in: RW_S_LATCH, RW_X_LATCH */ buf_block_t* block, /*!< in: guessed buffer block */ ib_uint64_t modify_clock,/*!< in: modify clock value if mode is @@ -2370,7 +2379,9 @@ buf_page_optimistic_get_func( ibool success; ulint fix_type; - ut_ad(mtr && block); + ut_ad(block); + ut_ad(mtr); + ut_ad(mtr->state == MTR_ACTIVE); ut_ad((rw_latch == RW_S_LATCH) || (rw_latch == RW_X_LATCH)); mutex_enter(&block->mutex); @@ -2482,6 +2493,7 @@ buf_page_get_known_nowait( ulint fix_type; ut_ad(mtr); + ut_ad(mtr->state == MTR_ACTIVE); ut_ad((rw_latch == RW_S_LATCH) || (rw_latch == RW_X_LATCH)); mutex_enter(&block->mutex); @@ -2581,6 +2593,9 @@ buf_page_try_get_func( ibool success; ulint fix_type; + ut_ad(mtr); + ut_ad(mtr->state == MTR_ACTIVE); + buf_pool_mutex_enter(); block = buf_block_hash_get(space_id, page_no); @@ -2954,6 +2969,7 @@ buf_page_create( ulint time_ms = ut_time_ms(); ut_ad(mtr); + ut_ad(mtr->state == MTR_ACTIVE); ut_ad(space || !zip_size); free_block = buf_LRU_get_free_block(0); diff --git a/storage/innodb_plugin/buf/buf0flu.c b/storage/innodb_plugin/buf/buf0flu.c index 8b614ce90e5..f2b07492470 100644 --- a/storage/innodb_plugin/buf/buf0flu.c +++ b/storage/innodb_plugin/buf/buf0flu.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -88,6 +88,140 @@ buf_flush_validate_low(void); #endif /* UNIV_DEBUG || UNIV_BUF_DEBUG */ /********************************************************************//** +Insert a block in the flush_rbt and returns a pointer to its +predecessor or NULL if no predecessor. The ordering is maintained +on the basis of the <oldest_modification, space, offset> key. +@return pointer to the predecessor or NULL if no predecessor. */ +static +buf_page_t* +buf_flush_insert_in_flush_rbt( +/*==========================*/ + buf_page_t* bpage) /*!< in: bpage to be inserted. */ +{ + buf_page_t* prev = NULL; + const ib_rbt_node_t* c_node; + const ib_rbt_node_t* p_node; + + ut_ad(buf_pool_mutex_own()); + + /* Insert this buffer into the rbt. */ + c_node = rbt_insert(buf_pool->flush_rbt, &bpage, &bpage); + ut_a(c_node != NULL); + + /* Get the predecessor. */ + p_node = rbt_prev(buf_pool->flush_rbt, c_node); + + if (p_node != NULL) { + prev = *rbt_value(buf_page_t*, p_node); + ut_a(prev != NULL); + } + + return(prev); +} + +/********************************************************************//** +Delete a bpage from the flush_rbt. */ +static +void +buf_flush_delete_from_flush_rbt( +/*============================*/ + buf_page_t* bpage) /*!< in: bpage to be removed. */ +{ + + ibool ret = FALSE; + + ut_ad(buf_pool_mutex_own()); + ret = rbt_delete(buf_pool->flush_rbt, &bpage); + ut_ad(ret); +} + +/********************************************************************//** +Compare two modified blocks in the buffer pool. The key for comparison +is: +key = <oldest_modification, space, offset> +This comparison is used to maintian ordering of blocks in the +buf_pool->flush_rbt. +Note that for the purpose of flush_rbt, we only need to order blocks +on the oldest_modification. The other two fields are used to uniquely +identify the blocks. +@return < 0 if b2 < b1, 0 if b2 == b1, > 0 if b2 > b1 */ +static +int +buf_flush_block_cmp( +/*================*/ + const void* p1, /*!< in: block1 */ + const void* p2) /*!< in: block2 */ +{ + int ret; + const buf_page_t* b1; + const buf_page_t* b2; + + ut_ad(p1 != NULL); + ut_ad(p2 != NULL); + + b1 = *(const buf_page_t**) p1; + b2 = *(const buf_page_t**) p2; + + ut_ad(b1 != NULL); + ut_ad(b2 != NULL); + + ut_ad(b1->in_flush_list); + ut_ad(b2->in_flush_list); + + if (b2->oldest_modification + > b1->oldest_modification) { + return(1); + } + + if (b2->oldest_modification + < b1->oldest_modification) { + return(-1); + } + + /* If oldest_modification is same then decide on the space. */ + ret = (int)(b2->space - b1->space); + + /* Or else decide ordering on the offset field. */ + return(ret ? ret : (int)(b2->offset - b1->offset)); +} + +/********************************************************************//** +Initialize the red-black tree to speed up insertions into the flush_list +during recovery process. Should be called at the start of recovery +process before any page has been read/written. */ +UNIV_INTERN +void +buf_flush_init_flush_rbt(void) +/*==========================*/ +{ + buf_pool_mutex_enter(); + + /* Create red black tree for speedy insertions in flush list. */ + buf_pool->flush_rbt = rbt_create(sizeof(buf_page_t*), + buf_flush_block_cmp); + buf_pool_mutex_exit(); +} + +/********************************************************************//** +Frees up the red-black tree. */ +UNIV_INTERN +void +buf_flush_free_flush_rbt(void) +/*==========================*/ +{ + buf_pool_mutex_enter(); + +#if defined UNIV_DEBUG || defined UNIV_BUF_DEBUG + ut_a(buf_flush_validate_low()); +#endif /* UNIV_DEBUG || UNIV_BUF_DEBUG */ + + rbt_free(buf_pool->flush_rbt); + buf_pool->flush_rbt = NULL; + + buf_pool_mutex_exit(); +} + +/********************************************************************//** Inserts a modified block into the flush list. */ UNIV_INTERN void @@ -100,6 +234,13 @@ buf_flush_insert_into_flush_list( || (UT_LIST_GET_FIRST(buf_pool->flush_list)->oldest_modification <= block->page.oldest_modification)); + /* If we are in the recovery then we need to update the flush + red-black tree as well. */ + if (UNIV_LIKELY_NULL(buf_pool->flush_rbt)) { + buf_flush_insert_sorted_into_flush_list(block); + return; + } + ut_ad(buf_block_get_state(block) == BUF_BLOCK_FILE_PAGE); ut_ad(block->page.in_LRU_list); ut_ad(block->page.in_page_hash); @@ -136,12 +277,27 @@ buf_flush_insert_sorted_into_flush_list( ut_d(block->page.in_flush_list = TRUE); prev_b = NULL; - b = UT_LIST_GET_FIRST(buf_pool->flush_list); - while (b && b->oldest_modification > block->page.oldest_modification) { - ut_ad(b->in_flush_list); - prev_b = b; - b = UT_LIST_GET_NEXT(list, b); + /* For the most part when this function is called the flush_rbt + should not be NULL. In a very rare boundary case it is possible + that the flush_rbt has already been freed by the recovery thread + before the last page was hooked up in the flush_list by the + io-handler thread. In that case we'll just do a simple + linear search in the else block. */ + if (buf_pool->flush_rbt) { + + prev_b = buf_flush_insert_in_flush_rbt(&block->page); + + } else { + + b = UT_LIST_GET_FIRST(buf_pool->flush_list); + + while (b && b->oldest_modification + > block->page.oldest_modification) { + ut_ad(b->in_flush_list); + prev_b = b; + b = UT_LIST_GET_NEXT(list, b); + } } if (prev_b == NULL) { @@ -237,7 +393,6 @@ buf_flush_remove( ut_ad(buf_pool_mutex_own()); ut_ad(mutex_own(buf_page_get_mutex(bpage))); ut_ad(bpage->in_flush_list); - ut_d(bpage->in_flush_list = FALSE); switch (buf_page_get_state(bpage)) { case BUF_BLOCK_ZIP_PAGE: @@ -259,6 +414,15 @@ buf_flush_remove( break; } + /* If the flush_rbt is active then delete from it as well. */ + if (UNIV_LIKELY_NULL(buf_pool->flush_rbt)) { + buf_flush_delete_from_flush_rbt(bpage); + } + + /* Must be done after we have removed it from the flush_rbt + because we assert on in_flush_list in comparison function. */ + ut_d(bpage->in_flush_list = FALSE); + bpage->oldest_modification = 0; ut_d(UT_LIST_VALIDATE(list, buf_page_t, buf_pool->flush_list, @@ -266,6 +430,63 @@ buf_flush_remove( } /********************************************************************//** +Relocates a buffer control block on the flush_list. +Note that it is assumed that the contents of bpage has already been +copied to dpage. */ +UNIV_INTERN +void +buf_flush_relocate_on_flush_list( +/*=============================*/ + buf_page_t* bpage, /*!< in/out: control block being moved */ + buf_page_t* dpage) /*!< in/out: destination block */ +{ + buf_page_t* prev; + buf_page_t* prev_b = NULL; + + ut_ad(buf_pool_mutex_own()); + + ut_ad(mutex_own(buf_page_get_mutex(bpage))); + + ut_ad(bpage->in_flush_list); + ut_ad(dpage->in_flush_list); + + /* If recovery is active we must swap the control blocks in + the flush_rbt as well. */ + if (UNIV_LIKELY_NULL(buf_pool->flush_rbt)) { + buf_flush_delete_from_flush_rbt(bpage); + prev_b = buf_flush_insert_in_flush_rbt(dpage); + } + + /* Must be done after we have removed it from the flush_rbt + because we assert on in_flush_list in comparison function. */ + ut_d(bpage->in_flush_list = FALSE); + + prev = UT_LIST_GET_PREV(list, bpage); + UT_LIST_REMOVE(list, buf_pool->flush_list, bpage); + + if (prev) { + ut_ad(prev->in_flush_list); + UT_LIST_INSERT_AFTER( + list, + buf_pool->flush_list, + prev, dpage); + } else { + UT_LIST_ADD_FIRST( + list, + buf_pool->flush_list, + dpage); + } + + /* Just an extra check. Previous in flush_list + should be the same control block as in flush_rbt. */ + ut_a(!buf_pool->flush_rbt || prev_b == prev); + +#if defined UNIV_DEBUG || defined UNIV_BUF_DEBUG + ut_a(buf_flush_validate_low()); +#endif /* UNIV_DEBUG || UNIV_BUF_DEBUG */ +} + +/********************************************************************//** Updates the flush system data structures when a write is completed. */ UNIV_INTERN void @@ -1367,24 +1588,45 @@ ibool buf_flush_validate_low(void) /*========================*/ { - buf_page_t* bpage; + buf_page_t* bpage; + const ib_rbt_node_t* rnode = NULL; UT_LIST_VALIDATE(list, buf_page_t, buf_pool->flush_list, ut_ad(ut_list_node_313->in_flush_list)); bpage = UT_LIST_GET_FIRST(buf_pool->flush_list); + /* If we are in recovery mode i.e.: flush_rbt != NULL + then each block in the flush_list must also be present + in the flush_rbt. */ + if (UNIV_LIKELY_NULL(buf_pool->flush_rbt)) { + rnode = rbt_first(buf_pool->flush_rbt); + } + while (bpage != NULL) { const ib_uint64_t om = bpage->oldest_modification; ut_ad(bpage->in_flush_list); ut_a(buf_page_in_file(bpage)); ut_a(om > 0); + if (UNIV_LIKELY_NULL(buf_pool->flush_rbt)) { + ut_a(rnode); + buf_page_t* rpage = *rbt_value(buf_page_t*, + rnode); + ut_a(rpage); + ut_a(rpage == bpage); + rnode = rbt_next(buf_pool->flush_rbt, rnode); + } + bpage = UT_LIST_GET_NEXT(list, bpage); ut_a(!bpage || om >= bpage->oldest_modification); } + /* By this time we must have exhausted the traversal of + flush_rbt (if active) as well. */ + ut_a(rnode == NULL); + return(TRUE); } diff --git a/storage/innodb_plugin/buf/buf0lru.c b/storage/innodb_plugin/buf/buf0lru.c index 4f19fd13fa5..9cfa02ba3ac 100644 --- a/storage/innodb_plugin/buf/buf0lru.c +++ b/storage/innodb_plugin/buf/buf0lru.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -350,17 +350,31 @@ scan_again: bpage = UT_LIST_GET_LAST(buf_pool->LRU); while (bpage != NULL) { - mutex_t* block_mutex = buf_page_get_mutex(bpage); buf_page_t* prev_bpage; + ibool prev_bpage_buf_fix = FALSE; ut_a(buf_page_in_file(bpage)); - mutex_enter(block_mutex); prev_bpage = UT_LIST_GET_PREV(LRU, bpage); - if (buf_page_get_space(bpage) == id) { - if (bpage->buf_fix_count > 0 - || buf_page_get_io_fix(bpage) != BUF_IO_NONE) { + /* bpage->space and bpage->io_fix are protected by + buf_pool_mutex and block_mutex. It is safe to check + them while holding buf_pool_mutex only. */ + + if (buf_page_get_space(bpage) != id) { + /* Skip this block, as it does not belong to + the space that is being invalidated. */ + } else if (buf_page_get_io_fix(bpage) != BUF_IO_NONE) { + /* We cannot remove this page during this scan + yet; maybe the system is currently reading it + in, or flushing the modifications to the file */ + + all_freed = FALSE; + } else { + mutex_t* block_mutex = buf_page_get_mutex(bpage); + mutex_enter(block_mutex); + + if (bpage->buf_fix_count > 0) { /* We cannot remove this page during this scan yet; maybe the system is @@ -380,8 +394,40 @@ scan_again: (ulong) buf_page_get_page_no(bpage)); } #endif - if (buf_page_get_state(bpage) == BUF_BLOCK_FILE_PAGE - && ((buf_block_t*) bpage)->is_hashed) { + if (buf_page_get_state(bpage) != BUF_BLOCK_FILE_PAGE) { + /* This is a compressed-only block + descriptor. Ensure that prev_bpage + cannot be relocated when bpage is freed. */ + if (UNIV_LIKELY(prev_bpage != NULL)) { + switch (buf_page_get_state( + prev_bpage)) { + case BUF_BLOCK_FILE_PAGE: + /* Descriptors of uncompressed + blocks will not be relocated, + because we are holding the + buf_pool_mutex. */ + break; + case BUF_BLOCK_ZIP_PAGE: + case BUF_BLOCK_ZIP_DIRTY: + /* Descriptors of compressed- + only blocks can be relocated, + unless they are buffer-fixed. + Because both bpage and + prev_bpage are protected by + buf_pool_zip_mutex, it is + not necessary to acquire + further mutexes. */ + ut_ad(&buf_pool_zip_mutex + == block_mutex); + ut_ad(mutex_own(block_mutex)); + prev_bpage_buf_fix = TRUE; + prev_bpage->buf_fix_count++; + break; + default: + ut_error; + } + } + } else if (((buf_block_t*) bpage)->is_hashed) { ulint page_no; ulint zip_size; @@ -405,7 +451,8 @@ scan_again: buf_flush_remove(bpage); } - /* Remove from the LRU list */ + /* Remove from the LRU list. */ + if (buf_LRU_block_remove_hashed_page(bpage, TRUE) != BUF_BLOCK_ZIP_FREE) { buf_LRU_block_free_hashed_page((buf_block_t*) @@ -417,18 +464,27 @@ scan_again: ut_ad(block_mutex == &buf_pool_zip_mutex); ut_ad(!mutex_own(block_mutex)); - /* The compressed block descriptor - (bpage) has been deallocated and - block_mutex released. Also, - buf_buddy_free() may have relocated - prev_bpage. Rescan the LRU list. */ + if (prev_bpage_buf_fix) { + /* We temporarily buffer-fixed + prev_bpage, so that + buf_buddy_free() could not + relocate it, in case it was a + compressed-only block + descriptor. */ + + mutex_enter(block_mutex); + ut_ad(prev_bpage->buf_fix_count > 0); + prev_bpage->buf_fix_count--; + mutex_exit(block_mutex); + } - bpage = UT_LIST_GET_LAST(buf_pool->LRU); - continue; + goto next_page_no_mutex; } - } next_page: - mutex_exit(block_mutex); + mutex_exit(block_mutex); + } + +next_page_no_mutex: bpage = prev_bpage; } @@ -1474,26 +1530,8 @@ alloc: if (b->state == BUF_BLOCK_ZIP_PAGE) { buf_LRU_insert_zip_clean(b); } else { - buf_page_t* prev; - - ut_ad(b->in_flush_list); - ut_d(bpage->in_flush_list = FALSE); - - prev = UT_LIST_GET_PREV(list, b); - UT_LIST_REMOVE(list, buf_pool->flush_list, b); - - if (prev) { - ut_ad(prev->in_flush_list); - UT_LIST_INSERT_AFTER( - list, - buf_pool->flush_list, - prev, b); - } else { - UT_LIST_ADD_FIRST( - list, - buf_pool->flush_list, - b); - } + /* Relocate on buf_pool->flush_list. */ + buf_flush_relocate_on_flush_list(bpage, b); } bpage->zip.data = NULL; diff --git a/storage/innodb_plugin/buf/buf0rea.c b/storage/innodb_plugin/buf/buf0rea.c index dd98ea17eb5..81f788baac2 100644 --- a/storage/innodb_plugin/buf/buf0rea.c +++ b/storage/innodb_plugin/buf/buf0rea.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -608,14 +608,14 @@ buf_read_recv_pages( while (buf_pool->n_pend_reads >= recv_n_pool_free_frames / 2) { os_aio_simulated_wake_handler_threads(); - os_thread_sleep(500000); + os_thread_sleep(10000); count++; - if (count > 100) { + if (count > 1000) { fprintf(stderr, "InnoDB: Error: InnoDB has waited for" - " 50 seconds for pending\n" + " 10 seconds for pending\n" "InnoDB: reads to the buffer pool to" " be finished.\n" "InnoDB: Number of pending reads %lu," diff --git a/storage/innodb_plugin/data/data0data.c b/storage/innodb_plugin/data/data0data.c index e3c1f1b4f23..0715b49bf9c 100644 --- a/storage/innodb_plugin/data/data0data.c +++ b/storage/innodb_plugin/data/data0data.c @@ -666,6 +666,21 @@ dtuple_convert_big_rec( goto skip_field; } + /* In DYNAMIC and COMPRESSED format, store + locally any non-BLOB columns whose maximum + length does not exceed 256 bytes. This is + because there is no room for the "external + storage" flag when the maximum length is 255 + bytes or less. This restriction trivially + holds in REDUNDANT and COMPACT format, because + there we always store locally columns whose + length is up to local_len == 788 bytes. + @see rec_init_offsets_comp_ordinary */ + if (ifield->col->mtype != DATA_BLOB + && ifield->col->len < 256) { + goto skip_field; + } + longest_i = i; longest = savings; diff --git a/storage/innodb_plugin/dict/dict0boot.c b/storage/innodb_plugin/dict/dict0boot.c index e55de30481b..45d57b8c619 100644 --- a/storage/innodb_plugin/dict/dict0boot.c +++ b/storage/innodb_plugin/dict/dict0boot.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -274,6 +274,9 @@ dict_boot(void) and (TYPE & DICT_TF_FORMAT_MASK) are nonzero and TYPE = table->flags */ dict_mem_table_add_col(table, heap, "TYPE", DATA_INT, 0, 4); dict_mem_table_add_col(table, heap, "MIX_ID", DATA_BINARY, 0, 0); + /* MIX_LEN may contain additional table flags when + ROW_FORMAT!=REDUNDANT. Currently, these flags include + DICT_TF2_TEMPORARY. */ dict_mem_table_add_col(table, heap, "MIX_LEN", DATA_INT, 0, 4); dict_mem_table_add_col(table, heap, "CLUSTER_NAME", DATA_BINARY, 0, 0); dict_mem_table_add_col(table, heap, "SPACE", DATA_INT, 0, 4); @@ -355,7 +358,7 @@ dict_boot(void) dict_mem_table_add_col(table, heap, "SPACE", DATA_INT, 0, 4); dict_mem_table_add_col(table, heap, "PAGE_NO", DATA_INT, 0, 4); - /* The '+ 2' below comes from the 2 system fields */ + /* The '+ 2' below comes from the fields DB_TRX_ID, DB_ROLL_PTR */ #if DICT_SYS_INDEXES_PAGE_NO_FIELD != 6 + 2 #error "DICT_SYS_INDEXES_PAGE_NO_FIELD != 6 + 2" #endif @@ -365,6 +368,9 @@ dict_boot(void) #if DICT_SYS_INDEXES_TYPE_FIELD != 4 + 2 #error "DICT_SYS_INDEXES_TYPE_FIELD != 4 + 2" #endif +#if DICT_SYS_INDEXES_NAME_FIELD != 2 + 2 +#error "DICT_SYS_INDEXES_NAME_FIELD != 2 + 2" +#endif table->id = DICT_INDEXES_ID; dict_table_add_to_cache(table, heap); diff --git a/storage/innodb_plugin/dict/dict0crea.c b/storage/innodb_plugin/dict/dict0crea.c index 96a9bd8152e..653bff4bef6 100644 --- a/storage/innodb_plugin/dict/dict0crea.c +++ b/storage/innodb_plugin/dict/dict0crea.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -51,16 +51,18 @@ static dtuple_t* dict_create_sys_tables_tuple( /*=========================*/ - dict_table_t* table, /*!< in: table */ - mem_heap_t* heap) /*!< in: memory heap from which the memory for - the built tuple is allocated */ + const dict_table_t* table, /*!< in: table */ + mem_heap_t* heap) /*!< in: memory heap from + which the memory for the built + tuple is allocated */ { dict_table_t* sys_tables; dtuple_t* entry; dfield_t* dfield; byte* ptr; - ut_ad(table && heap); + ut_ad(table); + ut_ad(heap); sys_tables = dict_sys->sys_tables; @@ -69,18 +71,18 @@ dict_create_sys_tables_tuple( dict_table_copy_types(entry, sys_tables); /* 0: NAME -----------------------------*/ - dfield = dtuple_get_nth_field(entry, 0); + dfield = dtuple_get_nth_field(entry, 0/*NAME*/); dfield_set_data(dfield, table->name, ut_strlen(table->name)); /* 3: ID -------------------------------*/ - dfield = dtuple_get_nth_field(entry, 1); + dfield = dtuple_get_nth_field(entry, 1/*ID*/); ptr = mem_heap_alloc(heap, 8); mach_write_to_8(ptr, table->id); dfield_set_data(dfield, ptr, 8); /* 4: N_COLS ---------------------------*/ - dfield = dtuple_get_nth_field(entry, 2); + dfield = dtuple_get_nth_field(entry, 2/*N_COLS*/); #if DICT_TF_COMPACT != 1 #error @@ -91,40 +93,41 @@ dict_create_sys_tables_tuple( | ((table->flags & DICT_TF_COMPACT) << 31)); dfield_set_data(dfield, ptr, 4); /* 5: TYPE -----------------------------*/ - dfield = dtuple_get_nth_field(entry, 3); + dfield = dtuple_get_nth_field(entry, 3/*TYPE*/); ptr = mem_heap_alloc(heap, 4); - if (table->flags & ~DICT_TF_COMPACT) { + if (table->flags & (~DICT_TF_COMPACT & ~(~0 << DICT_TF_BITS))) { ut_a(table->flags & DICT_TF_COMPACT); ut_a(dict_table_get_format(table) >= DICT_TF_FORMAT_ZIP); ut_a((table->flags & DICT_TF_ZSSIZE_MASK) <= (DICT_TF_ZSSIZE_MAX << DICT_TF_ZSSIZE_SHIFT)); - ut_a(!(table->flags & (~0 << DICT_TF_BITS))); - mach_write_to_4(ptr, table->flags); + ut_a(!(table->flags & (~0 << DICT_TF2_BITS))); + mach_write_to_4(ptr, table->flags & ~(~0 << DICT_TF_BITS)); } else { mach_write_to_4(ptr, DICT_TABLE_ORDINARY); } dfield_set_data(dfield, ptr, 4); /* 6: MIX_ID (obsolete) ---------------------------*/ - dfield = dtuple_get_nth_field(entry, 4); + dfield = dtuple_get_nth_field(entry, 4/*MIX_ID*/); ptr = mem_heap_zalloc(heap, 8); dfield_set_data(dfield, ptr, 8); - /* 7: MIX_LEN (obsolete) --------------------------*/ + /* 7: MIX_LEN (additional flags) --------------------------*/ - dfield = dtuple_get_nth_field(entry, 5); + dfield = dtuple_get_nth_field(entry, 5/*MIX_LEN*/); - ptr = mem_heap_zalloc(heap, 4); + ptr = mem_heap_alloc(heap, 4); + mach_write_to_4(ptr, table->flags >> DICT_TF2_SHIFT); dfield_set_data(dfield, ptr, 4); /* 8: CLUSTER_NAME ---------------------*/ - dfield = dtuple_get_nth_field(entry, 6); + dfield = dtuple_get_nth_field(entry, 6/*CLUSTER_NAME*/); dfield_set_null(dfield); /* not supported */ /* 9: SPACE ----------------------------*/ - dfield = dtuple_get_nth_field(entry, 7); + dfield = dtuple_get_nth_field(entry, 7/*SPACE*/); ptr = mem_heap_alloc(heap, 4); mach_write_to_4(ptr, table->space); @@ -143,19 +146,21 @@ static dtuple_t* dict_create_sys_columns_tuple( /*==========================*/ - dict_table_t* table, /*!< in: table */ - ulint i, /*!< in: column number */ - mem_heap_t* heap) /*!< in: memory heap from which the memory for - the built tuple is allocated */ + const dict_table_t* table, /*!< in: table */ + ulint i, /*!< in: column number */ + mem_heap_t* heap) /*!< in: memory heap from + which the memory for the built + tuple is allocated */ { dict_table_t* sys_columns; dtuple_t* entry; const dict_col_t* column; dfield_t* dfield; byte* ptr; - const char* col_name; + const char* col_name; - ut_ad(table && heap); + ut_ad(table); + ut_ad(heap); column = dict_table_get_nth_col(table, i); @@ -166,47 +171,47 @@ dict_create_sys_columns_tuple( dict_table_copy_types(entry, sys_columns); /* 0: TABLE_ID -----------------------*/ - dfield = dtuple_get_nth_field(entry, 0); + dfield = dtuple_get_nth_field(entry, 0/*TABLE_ID*/); ptr = mem_heap_alloc(heap, 8); mach_write_to_8(ptr, table->id); dfield_set_data(dfield, ptr, 8); /* 1: POS ----------------------------*/ - dfield = dtuple_get_nth_field(entry, 1); + dfield = dtuple_get_nth_field(entry, 1/*POS*/); ptr = mem_heap_alloc(heap, 4); mach_write_to_4(ptr, i); dfield_set_data(dfield, ptr, 4); /* 4: NAME ---------------------------*/ - dfield = dtuple_get_nth_field(entry, 2); + dfield = dtuple_get_nth_field(entry, 2/*NAME*/); col_name = dict_table_get_col_name(table, i); dfield_set_data(dfield, col_name, ut_strlen(col_name)); /* 5: MTYPE --------------------------*/ - dfield = dtuple_get_nth_field(entry, 3); + dfield = dtuple_get_nth_field(entry, 3/*MTYPE*/); ptr = mem_heap_alloc(heap, 4); mach_write_to_4(ptr, column->mtype); dfield_set_data(dfield, ptr, 4); /* 6: PRTYPE -------------------------*/ - dfield = dtuple_get_nth_field(entry, 4); + dfield = dtuple_get_nth_field(entry, 4/*PRTYPE*/); ptr = mem_heap_alloc(heap, 4); mach_write_to_4(ptr, column->prtype); dfield_set_data(dfield, ptr, 4); /* 7: LEN ----------------------------*/ - dfield = dtuple_get_nth_field(entry, 5); + dfield = dtuple_get_nth_field(entry, 5/*LEN*/); ptr = mem_heap_alloc(heap, 4); mach_write_to_4(ptr, column->len); dfield_set_data(dfield, ptr, 4); /* 8: PREC ---------------------------*/ - dfield = dtuple_get_nth_field(entry, 6); + dfield = dtuple_get_nth_field(entry, 6/*PREC*/); ptr = mem_heap_alloc(heap, 4); mach_write_to_4(ptr, 0/* unused */); @@ -230,6 +235,7 @@ dict_build_table_def_step( dict_table_t* table; dtuple_t* row; ulint error; + ulint flags; const char* path_or_name; ibool is_path; mtr_t mtr; @@ -268,9 +274,10 @@ dict_build_table_def_step( ut_ad(!dict_table_zip_size(table) || dict_table_get_format(table) >= DICT_TF_FORMAT_ZIP); + flags = table->flags & ~(~0 << DICT_TF_BITS); error = fil_create_new_single_table_tablespace( &space, path_or_name, is_path, - table->flags == DICT_TF_COMPACT ? 0 : table->flags, + flags == DICT_TF_COMPACT ? 0 : flags, FIL_IBD_FILE_INITIAL_SIZE); table->space = (unsigned int) space; @@ -286,7 +293,7 @@ dict_build_table_def_step( mtr_commit(&mtr); } else { /* Create in the system tablespace: disallow new features */ - table->flags &= DICT_TF_COMPACT; + table->flags &= (~0 << DICT_TF_BITS) | DICT_TF_COMPACT; } row = dict_create_sys_tables_tuple(table, node->heap); @@ -322,9 +329,10 @@ static dtuple_t* dict_create_sys_indexes_tuple( /*==========================*/ - dict_index_t* index, /*!< in: index */ - mem_heap_t* heap) /*!< in: memory heap from which the memory for - the built tuple is allocated */ + const dict_index_t* index, /*!< in: index */ + mem_heap_t* heap) /*!< in: memory heap from + which the memory for the built + tuple is allocated */ { dict_table_t* sys_indexes; dict_table_t* table; @@ -333,7 +341,8 @@ dict_create_sys_indexes_tuple( byte* ptr; ut_ad(mutex_own(&(dict_sys->mutex))); - ut_ad(index && heap); + ut_ad(index); + ut_ad(heap); sys_indexes = dict_sys->sys_indexes; @@ -344,32 +353,32 @@ dict_create_sys_indexes_tuple( dict_table_copy_types(entry, sys_indexes); /* 0: TABLE_ID -----------------------*/ - dfield = dtuple_get_nth_field(entry, 0); + dfield = dtuple_get_nth_field(entry, 0/*TABLE_ID*/); ptr = mem_heap_alloc(heap, 8); mach_write_to_8(ptr, table->id); dfield_set_data(dfield, ptr, 8); /* 1: ID ----------------------------*/ - dfield = dtuple_get_nth_field(entry, 1); + dfield = dtuple_get_nth_field(entry, 1/*ID*/); ptr = mem_heap_alloc(heap, 8); mach_write_to_8(ptr, index->id); dfield_set_data(dfield, ptr, 8); /* 4: NAME --------------------------*/ - dfield = dtuple_get_nth_field(entry, 2); + dfield = dtuple_get_nth_field(entry, 2/*NAME*/); dfield_set_data(dfield, index->name, ut_strlen(index->name)); /* 5: N_FIELDS ----------------------*/ - dfield = dtuple_get_nth_field(entry, 3); + dfield = dtuple_get_nth_field(entry, 3/*N_FIELDS*/); ptr = mem_heap_alloc(heap, 4); mach_write_to_4(ptr, index->n_fields); dfield_set_data(dfield, ptr, 4); /* 6: TYPE --------------------------*/ - dfield = dtuple_get_nth_field(entry, 4); + dfield = dtuple_get_nth_field(entry, 4/*TYPE*/); ptr = mem_heap_alloc(heap, 4); mach_write_to_4(ptr, index->type); @@ -381,7 +390,7 @@ dict_create_sys_indexes_tuple( #error "DICT_SYS_INDEXES_SPACE_NO_FIELD != 7" #endif - dfield = dtuple_get_nth_field(entry, 5); + dfield = dtuple_get_nth_field(entry, 5/*SPACE*/); ptr = mem_heap_alloc(heap, 4); mach_write_to_4(ptr, index->space); @@ -393,7 +402,7 @@ dict_create_sys_indexes_tuple( #error "DICT_SYS_INDEXES_PAGE_NO_FIELD != 8" #endif - dfield = dtuple_get_nth_field(entry, 6); + dfield = dtuple_get_nth_field(entry, 6/*PAGE_NO*/); ptr = mem_heap_alloc(heap, 4); mach_write_to_4(ptr, FIL_NULL); @@ -412,10 +421,11 @@ static dtuple_t* dict_create_sys_fields_tuple( /*=========================*/ - dict_index_t* index, /*!< in: index */ - ulint i, /*!< in: field number */ - mem_heap_t* heap) /*!< in: memory heap from which the memory for - the built tuple is allocated */ + const dict_index_t* index, /*!< in: index */ + ulint i, /*!< in: field number */ + mem_heap_t* heap) /*!< in: memory heap from + which the memory for the built + tuple is allocated */ { dict_table_t* sys_fields; dtuple_t* entry; @@ -425,7 +435,8 @@ dict_create_sys_fields_tuple( ibool index_contains_column_prefix_field = FALSE; ulint j; - ut_ad(index && heap); + ut_ad(index); + ut_ad(heap); for (j = 0; j < index->n_fields; j++) { if (dict_index_get_nth_field(index, j)->prefix_len > 0) { @@ -443,7 +454,7 @@ dict_create_sys_fields_tuple( dict_table_copy_types(entry, sys_fields); /* 0: INDEX_ID -----------------------*/ - dfield = dtuple_get_nth_field(entry, 0); + dfield = dtuple_get_nth_field(entry, 0/*INDEX_ID*/); ptr = mem_heap_alloc(heap, 8); mach_write_to_8(ptr, index->id); @@ -451,7 +462,7 @@ dict_create_sys_fields_tuple( dfield_set_data(dfield, ptr, 8); /* 1: POS + PREFIX LENGTH ----------------------------*/ - dfield = dtuple_get_nth_field(entry, 1); + dfield = dtuple_get_nth_field(entry, 1/*POS*/); ptr = mem_heap_alloc(heap, 4); @@ -471,7 +482,7 @@ dict_create_sys_fields_tuple( dfield_set_data(dfield, ptr, 4); /* 4: COL_NAME -------------------------*/ - dfield = dtuple_get_nth_field(entry, 2); + dfield = dtuple_get_nth_field(entry, 2/*COL_NAME*/); dfield_set_data(dfield, field->name, ut_strlen(field->name)); @@ -602,6 +613,7 @@ dict_create_index_tree_step( dict_table_t* sys_indexes; dict_table_t* table; dtuple_t* search_tuple; + ulint zip_size; btr_pcur_t pcur; mtr_t mtr; @@ -626,8 +638,9 @@ dict_create_index_tree_step( btr_pcur_move_to_next_user_rec(&pcur, &mtr); - node->page_no = btr_create(index->type, index->space, - dict_table_zip_size(index->table), + zip_size = dict_table_zip_size(index->table); + + node->page_no = btr_create(index->type, index->space, zip_size, index->id, index, &mtr); /* printf("Created a new index tree in space %lu root page %lu\n", index->space, index->page_no); */ @@ -1092,8 +1105,11 @@ dict_create_index_step( dulint index_id = node->index->id; - err = dict_index_add_to_cache(node->table, node->index, - FIL_NULL, TRUE); + err = dict_index_add_to_cache( + node->table, node->index, FIL_NULL, + trx_is_strict(trx) + || dict_table_get_format(node->table) + >= DICT_TF_FORMAT_ZIP); node->index = dict_index_get_if_in_cache_low(index_id); ut_a(!node->index == (err != DB_SUCCESS)); diff --git a/storage/innodb_plugin/dict/dict0dict.c b/storage/innodb_plugin/dict/dict0dict.c index 2e524a5a2e3..83438231689 100644 --- a/storage/innodb_plugin/dict/dict0dict.c +++ b/storage/innodb_plugin/dict/dict0dict.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -80,6 +80,10 @@ UNIV_INTERN rw_lock_t dict_operation_lock; /** Identifies generated InnoDB foreign key names */ static char dict_ibfk[] = "_ibfk_"; +/** array of mutexes protecting dict_index_t::stat_n_diff_key_vals[] */ +#define DICT_INDEX_STAT_MUTEX_SIZE 32 +mutex_t dict_index_stat_mutex[DICT_INDEX_STAT_MUTEX_SIZE]; + /*******************************************************************//** Tries to find column names for the index and sets the col field of the index. @@ -140,7 +144,7 @@ static void dict_field_print_low( /*=================*/ - dict_field_t* field); /*!< in: field */ + const dict_field_t* field); /*!< in: field */ /*********************************************************************//** Frees a foreign key struct. */ static @@ -239,6 +243,45 @@ dict_mutex_exit_for_mysql(void) mutex_exit(&(dict_sys->mutex)); } +/** Get the mutex that protects index->stat_n_diff_key_vals[] */ +#define GET_INDEX_STAT_MUTEX(index) \ + (&dict_index_stat_mutex[ut_fold_dulint(index->id) \ + % DICT_INDEX_STAT_MUTEX_SIZE]) + +/**********************************************************************//** +Lock the appropriate mutex to protect index->stat_n_diff_key_vals[]. +index->id is used to pick the right mutex and it should not change +before dict_index_stat_mutex_exit() is called on this index. */ +UNIV_INTERN +void +dict_index_stat_mutex_enter( +/*========================*/ + const dict_index_t* index) /*!< in: index */ +{ + ut_ad(index != NULL); + ut_ad(index->magic_n == DICT_INDEX_MAGIC_N); + ut_ad(index->cached); + ut_ad(!index->to_be_dropped); + + mutex_enter(GET_INDEX_STAT_MUTEX(index)); +} + +/**********************************************************************//** +Unlock the appropriate mutex that protects index->stat_n_diff_key_vals[]. */ +UNIV_INTERN +void +dict_index_stat_mutex_exit( +/*=======================*/ + const dict_index_t* index) /*!< in: index */ +{ + ut_ad(index != NULL); + ut_ad(index->magic_n == DICT_INDEX_MAGIC_N); + ut_ad(index->cached); + ut_ad(!index->to_be_dropped); + + mutex_exit(GET_INDEX_STAT_MUTEX(index)); +} + /********************************************************************//** Decrements the count of open MySQL handles to a table. */ UNIV_INTERN @@ -605,6 +648,8 @@ void dict_init(void) /*===========*/ { + int i; + dict_sys = mem_alloc(sizeof(dict_sys_t)); mutex_create(&dict_sys->mutex, SYNC_DICT); @@ -625,6 +670,10 @@ dict_init(void) ut_a(dict_foreign_err_file); mutex_create(&dict_foreign_err_mutex, SYNC_ANY_LATCH); + + for (i = 0; i < DICT_INDEX_STAT_MUTEX_SIZE; i++) { + mutex_create(&dict_index_stat_mutex[i], SYNC_INDEX_TREE); + } } /**********************************************************************//** @@ -1460,6 +1509,7 @@ dict_index_add_to_cache( if (!dict_index_find_cols(table, index)) { + dict_mem_index_free(index); return(DB_CORRUPTION); } @@ -4170,9 +4220,13 @@ dict_update_statistics_low( index = dict_table_get_first_index(table); + dict_index_stat_mutex_enter(index); + table->stat_n_rows = index->stat_n_diff_key_vals[ dict_index_get_n_unique(index)]; + dict_index_stat_mutex_exit(index); + table->stat_clustered_index_size = index->stat_index_size; table->stat_sum_of_other_index_sizes = sum_of_index_sizes @@ -4350,6 +4404,8 @@ dict_index_print_low( ut_ad(mutex_own(&(dict_sys->mutex))); + dict_index_stat_mutex_enter(index); + if (index->n_user_defined_cols > 0) { n_vals = index->stat_n_diff_key_vals[ index->n_user_defined_cols]; @@ -4357,6 +4413,8 @@ dict_index_print_low( n_vals = index->stat_n_diff_key_vals[1]; } + dict_index_stat_mutex_exit(index); + if (dict_index_is_clust(index)) { type_string = "clustered index"; } else if (dict_index_is_unique(index)) { @@ -4402,7 +4460,7 @@ static void dict_field_print_low( /*=================*/ - dict_field_t* field) /*!< in: field */ + const dict_field_t* field) /*!< in: field */ { ut_ad(mutex_own(&(dict_sys->mutex))); @@ -4766,8 +4824,10 @@ UNIV_INTERN void dict_table_check_for_dup_indexes( /*=============================*/ - const dict_table_t* table) /*!< in: Check for dup indexes + const dict_table_t* table, /*!< in: Check for dup indexes in this table */ + ibool tmp_ok) /*!< in: TRUE=allow temporary + index names */ { /* Check for duplicates, ignoring indexes that are marked as to be dropped */ @@ -4775,13 +4835,17 @@ dict_table_check_for_dup_indexes( const dict_index_t* index1; const dict_index_t* index2; + ut_ad(mutex_own(&dict_sys->mutex)); + /* The primary index _must_ exist */ ut_a(UT_LIST_GET_LEN(table->indexes) > 0); index1 = UT_LIST_GET_FIRST(table->indexes); - index2 = UT_LIST_GET_NEXT(indexes, index1); - while (index1 && index2) { + do { + ut_ad(tmp_ok || *index1->name != TEMP_INDEX_PREFIX); + + index2 = UT_LIST_GET_NEXT(indexes, index1); while (index2) { @@ -4793,8 +4857,7 @@ dict_table_check_for_dup_indexes( } index1 = UT_LIST_GET_NEXT(indexes, index1); - index2 = UT_LIST_GET_NEXT(indexes, index1); - } + } while (index1); } #endif /* UNIV_DEBUG */ @@ -4847,5 +4910,9 @@ dict_close(void) mem_free(dict_sys); dict_sys = NULL; + + for (i = 0; i < DICT_INDEX_STAT_MUTEX_SIZE; i++) { + mutex_free(&dict_index_stat_mutex[i]); + } } #endif /* !UNIV_HOTBACKUP */ diff --git a/storage/innodb_plugin/dict/dict0load.c b/storage/innodb_plugin/dict/dict0load.c index 842a129c1a6..377818308c5 100644 --- a/storage/innodb_plugin/dict/dict0load.c +++ b/storage/innodb_plugin/dict/dict0load.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -260,7 +260,7 @@ dict_sys_tables_get_flags( return(0); } - field = rec_get_nth_field_old(rec, 4, &len); + field = rec_get_nth_field_old(rec, 4/*N_COLS*/, &len); n_cols = mach_read_from_4(field); if (UNIV_UNLIKELY(!(n_cols & 0x80000000UL))) { @@ -390,15 +390,35 @@ loop: mtr_commit(&mtr); - if (space_id != 0 && in_crash_recovery) { + if (space_id == 0) { + /* The system tablespace always exists. */ + } else if (in_crash_recovery) { /* Check that the tablespace (the .ibd file) really - exists; print a warning to the .err log if not */ - - fil_space_for_table_exists_in_mem(space_id, name, - FALSE, TRUE, TRUE); - } + exists; print a warning to the .err log if not. + Do not print warnings for temporary tables. */ + ibool is_temp; + + field = rec_get_nth_field_old(rec, 4, &len); + if (0x80000000UL & mach_read_from_4(field)) { + /* ROW_FORMAT=COMPACT: read the is_temp + flag from SYS_TABLES.MIX_LEN. */ + field = rec_get_nth_field_old(rec, 7, &len); + is_temp = mach_read_from_4(field) + & DICT_TF2_TEMPORARY; + } else { + /* For tables created with old versions + of InnoDB, SYS_TABLES.MIX_LEN may contain + garbage. Such tables would always be + in ROW_FORMAT=REDUNDANT. Pretend that + all such tables are non-temporary. That is, + do not suppress error printouts about + temporary tables not being found. */ + is_temp = FALSE; + } - if (space_id != 0 && !in_crash_recovery) { + fil_space_for_table_exists_in_mem( + space_id, name, is_temp, TRUE, !is_temp); + } else { /* It is a normal database startup: create the space object and check that the .ibd file exists. */ @@ -894,43 +914,72 @@ err_exit: (ulong) flags); goto err_exit; } + } else { + flags = 0; + } - if (fil_space_for_table_exists_in_mem(space, name, FALSE, - FALSE, FALSE)) { - /* Ok; (if we did a crash recovery then the tablespace - can already be in the memory cache) */ - } else { - /* In >= 4.1.9, InnoDB scans the data dictionary also - at a normal mysqld startup. It is an error if the - space object does not exist in memory. */ + ut_a(name_of_col_is(sys_tables, sys_index, 4, "N_COLS")); + field = rec_get_nth_field_old(rec, 4, &len); + n_cols = mach_read_from_4(field); + + /* The high-order bit of N_COLS is the "compact format" flag. + For tables in that format, MIX_LEN may hold additional flags. */ + if (n_cols & 0x80000000UL) { + ulint flags2; + + flags |= DICT_TF_COMPACT; + + ut_a(name_of_col_is(sys_tables, sys_index, 7, "MIX_LEN")); + field = rec_get_nth_field_old(rec, 7, &len); + + flags2 = mach_read_from_4(field); + + if (flags2 & (~0 << (DICT_TF2_BITS - DICT_TF2_SHIFT))) { + ut_print_timestamp(stderr); + fputs(" InnoDB: Warning: table ", stderr); + ut_print_filename(stderr, name); + fprintf(stderr, "\n" + "InnoDB: in InnoDB data dictionary" + " has unknown flags %lx.\n", + (ulong) flags2); + + flags2 &= ~(~0 << (DICT_TF2_BITS - DICT_TF2_SHIFT)); + } + + flags |= flags2 << DICT_TF2_SHIFT; + } + + /* See if the tablespace is available. */ + if (space == 0) { + /* The system tablespace is always available. */ + } else if (!fil_space_for_table_exists_in_mem( + space, name, + (flags >> DICT_TF2_SHIFT) & DICT_TF2_TEMPORARY, + FALSE, FALSE)) { + + if ((flags >> DICT_TF2_SHIFT) & DICT_TF2_TEMPORARY) { + /* Do not bother to retry opening temporary tables. */ + ibd_file_missing = TRUE; + } else { ut_print_timestamp(stderr); fprintf(stderr, - " InnoDB: error: space object of table %s,\n" + " InnoDB: error: space object of table"); + ut_print_filename(stderr, name); + fprintf(stderr, ",\n" "InnoDB: space id %lu did not exist in memory." " Retrying an open.\n", - name, (ulong)space); + (ulong) space); /* Try to open the tablespace */ if (!fil_open_single_table_tablespace( - TRUE, space, flags, name)) { - /* We failed to find a sensible tablespace - file */ + TRUE, space, + flags & ~(~0 << DICT_TF_BITS), name)) { + /* We failed to find a sensible + tablespace file */ ibd_file_missing = TRUE; } } - } else { - flags = 0; - } - - ut_a(name_of_col_is(sys_tables, sys_index, 4, "N_COLS")); - - field = rec_get_nth_field_old(rec, 4, &len); - n_cols = mach_read_from_4(field); - - /* The high-order bit of N_COLS is the "compact format" flag. */ - if (n_cols & 0x80000000UL) { - flags |= DICT_TF_COMPACT; } table = dict_mem_table_create(name, space, n_cols & ~0x80000000UL, diff --git a/storage/innodb_plugin/dict/dict0mem.c b/storage/innodb_plugin/dict/dict0mem.c index 6458cbab92d..66b4b43f296 100644 --- a/storage/innodb_plugin/dict/dict0mem.c +++ b/storage/innodb_plugin/dict/dict0mem.c @@ -59,7 +59,7 @@ dict_mem_table_create( mem_heap_t* heap; ut_ad(name); - ut_a(!(flags & (~0 << DICT_TF_BITS))); + ut_a(!(flags & (~0 << DICT_TF2_BITS))); heap = mem_heap_create(DICT_HEAP_SIZE); diff --git a/storage/innodb_plugin/fil/fil0fil.c b/storage/innodb_plugin/fil/fil0fil.c index 112a0e27d50..963e306c00c 100644 --- a/storage/innodb_plugin/fil/fil0fil.c +++ b/storage/innodb_plugin/fil/fil0fil.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -38,6 +38,7 @@ Created 10/25/1995 Heikki Tuuri #include "mtr0mtr.h" #include "mtr0log.h" #include "dict0dict.h" +#include "page0page.h" #include "page0zip.h" #ifndef UNIV_HOTBACKUP # include "buf0lru.h" @@ -1097,10 +1098,13 @@ fil_space_create( fil_space_t* space; /* The tablespace flags (FSP_SPACE_FLAGS) should be 0 for - ROW_FORMAT=COMPACT (table->flags == DICT_TF_COMPACT) and + ROW_FORMAT=COMPACT + ((table->flags & ~(~0 << DICT_TF_BITS)) == DICT_TF_COMPACT) and ROW_FORMAT=REDUNDANT (table->flags == 0). For any other - format, the tablespace flags should equal table->flags. */ + format, the tablespace flags should equal + (table->flags & ~(~0 << DICT_TF_BITS)). */ ut_a(flags != DICT_TF_COMPACT); + ut_a(!(flags & (~0UL << DICT_TF_BITS))); try_again: /*printf( @@ -2582,10 +2586,13 @@ fil_create_new_single_table_tablespace( ut_a(size >= FIL_IBD_FILE_INITIAL_SIZE); /* The tablespace flags (FSP_SPACE_FLAGS) should be 0 for - ROW_FORMAT=COMPACT (table->flags == DICT_TF_COMPACT) and + ROW_FORMAT=COMPACT + ((table->flags & ~(~0 << DICT_TF_BITS)) == DICT_TF_COMPACT) and ROW_FORMAT=REDUNDANT (table->flags == 0). For any other - format, the tablespace flags should equal table->flags. */ + format, the tablespace flags should equal + (table->flags & ~(~0 << DICT_TF_BITS)). */ ut_a(flags != DICT_TF_COMPACT); + ut_a(!(flags & (~0UL << DICT_TF_BITS))); path = fil_make_ibd_name(tablename, is_temp); @@ -2786,6 +2793,7 @@ fil_reset_too_high_lsns( ib_int64_t offset; ulint zip_size; ibool success; + page_zip_des_t page_zip; filepath = fil_make_ibd_name(name, FALSE); @@ -2833,6 +2841,12 @@ fil_reset_too_high_lsns( space_id = fsp_header_get_space_id(page); zip_size = fsp_header_get_zip_size(page); + page_zip_des_init(&page_zip); + page_zip_set_size(&page_zip, zip_size); + if (zip_size) { + page_zip.data = page + UNIV_PAGE_SIZE; + } + ut_print_timestamp(stderr); fprintf(stderr, " InnoDB: Flush lsn in the tablespace file %lu" @@ -2867,20 +2881,23 @@ fil_reset_too_high_lsns( /* We have to reset the lsn */ if (zip_size) { - memcpy(page + UNIV_PAGE_SIZE, page, zip_size); + memcpy(page_zip.data, page, zip_size); buf_flush_init_for_writing( - page, page + UNIV_PAGE_SIZE, - current_lsn); + page, &page_zip, current_lsn); + success = os_file_write( + filepath, file, page_zip.data, + (ulint) offset & 0xFFFFFFFFUL, + (ulint) (offset >> 32), zip_size); } else { buf_flush_init_for_writing( page, NULL, current_lsn); + success = os_file_write( + filepath, file, page, + (ulint)(offset & 0xFFFFFFFFUL), + (ulint)(offset >> 32), + UNIV_PAGE_SIZE); } - success = os_file_write(filepath, file, page, - (ulint)(offset & 0xFFFFFFFFUL), - (ulint)(offset >> 32), - zip_size - ? zip_size - : UNIV_PAGE_SIZE); + if (!success) { goto func_exit; @@ -2956,10 +2973,13 @@ fil_open_single_table_tablespace( filepath = fil_make_ibd_name(name, FALSE); /* The tablespace flags (FSP_SPACE_FLAGS) should be 0 for - ROW_FORMAT=COMPACT (table->flags == DICT_TF_COMPACT) and + ROW_FORMAT=COMPACT + ((table->flags & ~(~0 << DICT_TF_BITS)) == DICT_TF_COMPACT) and ROW_FORMAT=REDUNDANT (table->flags == 0). For any other - format, the tablespace flags should equal table->flags. */ + format, the tablespace flags should equal + (table->flags & ~(~0 << DICT_TF_BITS)). */ ut_a(flags != DICT_TF_COMPACT); + ut_a(!(flags & (~0UL << DICT_TF_BITS))); file = os_file_create_simple_no_error_handling( filepath, OS_FILE_OPEN, OS_FILE_READ_ONLY, &success); @@ -3011,7 +3031,8 @@ fil_open_single_table_tablespace( ut_free(buf2); - if (UNIV_UNLIKELY(space_id != id || space_flags != flags)) { + if (UNIV_UNLIKELY(space_id != id + || space_flags != (flags & ~(~0 << DICT_TF_BITS)))) { ut_print_timestamp(stderr); fputs(" InnoDB: Error: tablespace id and flags in file ", @@ -4781,8 +4802,10 @@ void fil_close(void) /*===========*/ { +#ifndef UNIV_HOTBACKUP /* The mutex should already have been freed. */ ut_ad(fil_system->mutex.magic_n == 0); +#endif /* !UNIV_HOTBACKUP */ hash_table_free(fil_system->spaces); diff --git a/storage/innodb_plugin/fsp/fsp0fsp.c b/storage/innodb_plugin/fsp/fsp0fsp.c index 3cc4318fc06..c7f1a299d8a 100644 --- a/storage/innodb_plugin/fsp/fsp0fsp.c +++ b/storage/innodb_plugin/fsp/fsp0fsp.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -386,11 +386,11 @@ UNIV_INLINE ibool xdes_get_bit( /*=========*/ - xdes_t* descr, /*!< in: descriptor */ - ulint bit, /*!< in: XDES_FREE_BIT or XDES_CLEAN_BIT */ - ulint offset, /*!< in: page offset within extent: - 0 ... FSP_EXTENT_SIZE - 1 */ - mtr_t* mtr) /*!< in: mtr */ + const xdes_t* descr, /*!< in: descriptor */ + ulint bit, /*!< in: XDES_FREE_BIT or XDES_CLEAN_BIT */ + ulint offset, /*!< in: page offset within extent: + 0 ... FSP_EXTENT_SIZE - 1 */ + mtr_t* mtr) /*!< in: mtr */ { ulint index; ulint byte_index; @@ -527,8 +527,8 @@ UNIV_INLINE ulint xdes_get_n_used( /*============*/ - xdes_t* descr, /*!< in: descriptor */ - mtr_t* mtr) /*!< in: mtr */ + const xdes_t* descr, /*!< in: descriptor */ + mtr_t* mtr) /*!< in: mtr */ { ulint i; ulint count = 0; @@ -551,8 +551,8 @@ UNIV_INLINE ibool xdes_is_free( /*=========*/ - xdes_t* descr, /*!< in: descriptor */ - mtr_t* mtr) /*!< in: mtr */ + const xdes_t* descr, /*!< in: descriptor */ + mtr_t* mtr) /*!< in: mtr */ { if (0 == xdes_get_n_used(descr, mtr)) { @@ -569,8 +569,8 @@ UNIV_INLINE ibool xdes_is_full( /*=========*/ - xdes_t* descr, /*!< in: descriptor */ - mtr_t* mtr) /*!< in: mtr */ + const xdes_t* descr, /*!< in: descriptor */ + mtr_t* mtr) /*!< in: mtr */ { if (FSP_EXTENT_SIZE == xdes_get_n_used(descr, mtr)) { @@ -586,7 +586,7 @@ UNIV_INLINE void xdes_set_state( /*===========*/ - xdes_t* descr, /*!< in: descriptor */ + xdes_t* descr, /*!< in/out: descriptor */ ulint state, /*!< in: state to set */ mtr_t* mtr) /*!< in: mtr handle */ { @@ -605,8 +605,8 @@ UNIV_INLINE ulint xdes_get_state( /*===========*/ - xdes_t* descr, /*!< in: descriptor */ - mtr_t* mtr) /*!< in: mtr handle */ + const xdes_t* descr, /*!< in: descriptor */ + mtr_t* mtr) /*!< in: mtr handle */ { ulint state; @@ -705,7 +705,7 @@ UNIV_INLINE xdes_t* xdes_get_descriptor_with_space_hdr( /*===============================*/ - fsp_header_t* sp_header,/*!< in: space header, x-latched */ + fsp_header_t* sp_header,/*!< in/out: space header, x-latched */ ulint space, /*!< in: space id */ ulint offset, /*!< in: page offset; if equal to the free limit, @@ -869,9 +869,7 @@ fsp_init_file_page_low( return; } -#ifdef UNIV_BASIC_LOG_DEBUG - memset(page, 0xff, UNIV_PAGE_SIZE); -#endif + UNIV_MEM_INVALID(page, UNIV_PAGE_SIZE); mach_write_to_4(page + FIL_PAGE_OFFSET, buf_block_get_page_no(block)); memset(page + FIL_PAGE_LSN, 0, 8); mach_write_to_4(page + FIL_PAGE_ARCH_LOG_NO_OR_SPACE_ID, @@ -1342,7 +1340,7 @@ fsp_fill_free_list( descriptor page and ibuf bitmap page; then we do not allocate more extents */ ulint space, /*!< in: space */ - fsp_header_t* header, /*!< in: space header */ + fsp_header_t* header, /*!< in/out: space header */ mtr_t* mtr) /*!< in: mtr */ { ulint limit; diff --git a/storage/innodb_plugin/ha/ha0ha.c b/storage/innodb_plugin/ha/ha0ha.c index cb5e541b55d..9d9d341ad39 100644 --- a/storage/innodb_plugin/ha/ha0ha.c +++ b/storage/innodb_plugin/ha/ha0ha.c @@ -101,6 +101,8 @@ ha_clear( ulint i; ulint n; + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); #ifdef UNIV_SYNC_DEBUG ut_ad(rw_lock_own(&btr_search_latch, RW_LOCK_EXCLUSIVE)); #endif /* UNIV_SYNC_DEBUG */ @@ -146,7 +148,9 @@ ha_insert_for_fold_func( ha_node_t* prev_node; ulint hash; - ut_ad(table && data); + ut_ad(data); + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); #if defined UNIV_AHI_DEBUG || defined UNIV_DEBUG ut_a(block->frame == page_align(data)); #endif /* UNIV_AHI_DEBUG || UNIV_DEBUG */ @@ -237,6 +241,8 @@ ha_delete_hash_node( hash_table_t* table, /*!< in: hash table */ ha_node_t* del_node) /*!< in: node to be deleted */ { + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); #if defined UNIV_AHI_DEBUG || defined UNIV_DEBUG # ifndef UNIV_HOTBACKUP if (table->adaptive) { @@ -267,6 +273,8 @@ ha_search_and_update_if_found_func( { ha_node_t* node; + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); ASSERT_HASH_MUTEX_OWN(table, fold); #if defined UNIV_AHI_DEBUG || defined UNIV_DEBUG ut_a(new_block->frame == page_align(new_data)); @@ -304,6 +312,8 @@ ha_remove_all_nodes_to_page( { ha_node_t* node; + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); ASSERT_HASH_MUTEX_OWN(table, fold); node = ha_chain_get_first(table, fold); @@ -353,6 +363,8 @@ ha_validate( ibool ok = TRUE; ulint i; + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); ut_a(start_index <= end_index); ut_a(start_index < hash_get_n_cells(table)); ut_a(end_index < hash_get_n_cells(table)); @@ -404,6 +416,8 @@ builds, see http://bugs.mysql.com/36941 */ #endif /* PRINT_USED_CELLS */ ulint n_bufs; + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); #ifdef PRINT_USED_CELLS for (i = 0; i < hash_get_n_cells(table); i++) { diff --git a/storage/innodb_plugin/ha/hash0hash.c b/storage/innodb_plugin/ha/hash0hash.c index 2800d7793f8..30c304dafcd 100644 --- a/storage/innodb_plugin/ha/hash0hash.c +++ b/storage/innodb_plugin/ha/hash0hash.c @@ -119,7 +119,7 @@ hash_create( table->heaps = NULL; #endif /* !UNIV_HOTBACKUP */ table->heap = NULL; - table->magic_n = HASH_TABLE_MAGIC_N; + ut_d(table->magic_n = HASH_TABLE_MAGIC_N); /* Initialize the cell array */ hash_table_clear(table); @@ -135,6 +135,8 @@ hash_table_free( /*============*/ hash_table_t* table) /*!< in, own: hash table */ { + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); #ifndef UNIV_HOTBACKUP ut_a(table->mutexes == NULL); #endif /* !UNIV_HOTBACKUP */ @@ -160,6 +162,8 @@ hash_create_mutexes_func( { ulint i; + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); ut_a(n_mutexes > 0); ut_a(ut_is_2pow(n_mutexes)); diff --git a/storage/innodb_plugin/handler/ha_innodb.cc b/storage/innodb_plugin/handler/ha_innodb.cc index 47b8203091c..0fc6e786f4c 100644 --- a/storage/innodb_plugin/handler/ha_innodb.cc +++ b/storage/innodb_plugin/handler/ha_innodb.cc @@ -1,7 +1,8 @@ /***************************************************************************** -Copyright (c) 2000, 2009, MySQL AB & Innobase Oy. All Rights Reserved. +Copyright (c) 2000, 2010, MySQL AB & Innobase Oy. All Rights Reserved. Copyright (c) 2008, 2009 Google Inc. +Copyright (c) 2009, Percona Inc. Portions of this file contain modifications contributed and copyrighted by Google, Inc. Those modifications are gratefully acknowledged and are described @@ -9,6 +10,13 @@ briefly in the InnoDB documentation. The contributions by Google are incorporated with their permission, and subject to the conditions contained in the file COPYING.Google. +Portions of this file contain modifications contributed and copyrighted +by Percona Inc.. Those modifications are +gratefully acknowledged and are described briefly in the InnoDB +documentation. The contributions by Percona Inc. are incorporated with +their permission, and subject to the conditions contained in the file +COPYING.Percona. + This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; version 2 of the License. @@ -22,32 +30,6 @@ this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA *****************************************************************************/ -/*********************************************************************** - -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. -Copyright (c) 2009, Percona Inc. - -Portions of this file contain modifications contributed and copyrighted -by Percona Inc.. Those modifications are -gratefully acknowledged and are described briefly in the InnoDB -documentation. The contributions by Percona Inc. are incorporated with -their permission, and subject to the conditions contained in the file -COPYING.Percona. - -This program is free software; you can redistribute it and/or modify it -under the terms of the GNU General Public License as published by the -Free Software Foundation; version 2 of the License. - -This program is distributed in the hope that it will be useful, but -WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General -Public License for more details. - -You should have received a copy of the GNU General Public License along -with this program; if not, write to the Free Software Foundation, Inc., -59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -***********************************************************************/ /* TODO list for the InnoDB handler in 5.0: - Remove the flag trx->active_trans and look at trx->conc_state @@ -126,7 +108,6 @@ static ulong commit_threads = 0; static pthread_mutex_t commit_threads_m; static pthread_cond_t commit_cond; static pthread_mutex_t commit_cond_m; -static pthread_mutex_t analyze_mutex; static bool innodb_inited = 0; #define INSIDE_HA_INNOBASE_CC @@ -334,7 +315,7 @@ static MYSQL_THDVAR_ULONG(lock_wait_timeout, PLUGIN_VAR_RQCMDARG, static handler *innobase_create_handler(handlerton *hton, - TABLE_SHARE *table, + TABLE_SHARE *table, MEM_ROOT *mem_root) { return new (mem_root) ha_innobase(hton, table); @@ -447,8 +428,9 @@ static int innobase_start_trx_and_assign_read_view( /*====================================*/ - handlerton* hton, /*!< in: Innodb handlerton */ - THD* thd); /*!< in: MySQL thread handle of the user for whom + /* out: 0 */ + handlerton* hton, /* in: Innodb handlerton */ + THD* thd); /* in: MySQL thread handle of the user for whom the transaction should be committed */ /****************************************************************//** Flushes InnoDB logs to disk and makes a checkpoint. Really, a commit flushes @@ -1833,6 +1815,19 @@ trx_is_interrupted( return(trx && trx->mysql_thd && thd_killed((THD*) trx->mysql_thd)); } +/**********************************************************************//** +Determines if the currently running transaction is in strict mode. +@return TRUE if strict */ +extern "C" UNIV_INTERN +ibool +trx_is_strict( +/*==========*/ + trx_t* trx) /*!< in: transaction */ +{ + return(trx && trx->mysql_thd + && THDVAR((THD*) trx->mysql_thd, strict_mode)); +} + /**************************************************************//** Resets some fields of a prebuilt struct. The template is used in fast retrieval of just those column values MySQL needs in its processing. */ @@ -2152,7 +2147,7 @@ mem_free_and_error: } sql_print_error("InnoDB: invalid value " - "innodb_file_format_check=%s", + "innodb_change_buffering=%s", innobase_change_buffering); goto mem_free_and_error; } @@ -2241,7 +2236,6 @@ innobase_change_buffering_inited_ok: pthread_mutex_init(&prepare_commit_mutex, MY_MUTEX_INIT_FAST); pthread_mutex_init(&commit_threads_m, MY_MUTEX_INIT_FAST); pthread_mutex_init(&commit_cond_m, MY_MUTEX_INIT_FAST); - pthread_mutex_init(&analyze_mutex, MY_MUTEX_INIT_FAST); pthread_cond_init(&commit_cond, NULL); innodb_inited= 1; #ifdef MYSQL_DYNAMIC_PLUGIN @@ -2296,7 +2290,6 @@ innobase_end( pthread_mutex_destroy(&prepare_commit_mutex); pthread_mutex_destroy(&commit_threads_m); pthread_mutex_destroy(&commit_cond_m); - pthread_mutex_destroy(&analyze_mutex); pthread_cond_destroy(&commit_cond); } @@ -3006,59 +2999,370 @@ normalize_table_name( } /********************************************************************//** +Get the upper limit of the MySQL integral and floating-point type. +@return maximum allowed value for the field */ +static +ulonglong +innobase_get_int_col_max_value( +/*===========================*/ + const Field* field) /*!< in: MySQL field */ +{ + ulonglong max_value = 0; + + switch(field->key_type()) { + /* TINY */ + case HA_KEYTYPE_BINARY: + max_value = 0xFFULL; + break; + case HA_KEYTYPE_INT8: + max_value = 0x7FULL; + break; + /* SHORT */ + case HA_KEYTYPE_USHORT_INT: + max_value = 0xFFFFULL; + break; + case HA_KEYTYPE_SHORT_INT: + max_value = 0x7FFFULL; + break; + /* MEDIUM */ + case HA_KEYTYPE_UINT24: + max_value = 0xFFFFFFULL; + break; + case HA_KEYTYPE_INT24: + max_value = 0x7FFFFFULL; + break; + /* LONG */ + case HA_KEYTYPE_ULONG_INT: + max_value = 0xFFFFFFFFULL; + break; + case HA_KEYTYPE_LONG_INT: + max_value = 0x7FFFFFFFULL; + break; + /* BIG */ + case HA_KEYTYPE_ULONGLONG: + max_value = 0xFFFFFFFFFFFFFFFFULL; + break; + case HA_KEYTYPE_LONGLONG: + max_value = 0x7FFFFFFFFFFFFFFFULL; + break; + case HA_KEYTYPE_FLOAT: + /* We use the maximum as per IEEE754-2008 standard, 2^24 */ + max_value = 0x1000000ULL; + break; + case HA_KEYTYPE_DOUBLE: + /* We use the maximum as per IEEE754-2008 standard, 2^53 */ + max_value = 0x20000000000000ULL; + break; + default: + ut_error; + } + + return(max_value); +} + +/*******************************************************************//** +This function checks whether the index column information +is consistent between KEY info from mysql and that from innodb index. +@return TRUE if all column types match. */ +static +ibool +innobase_match_index_columns( +/*=========================*/ + const KEY* key_info, /*!< in: Index info + from mysql */ + const dict_index_t* index_info) /*!< in: Index info + from Innodb */ +{ + const KEY_PART_INFO* key_part; + const KEY_PART_INFO* key_end; + const dict_field_t* innodb_idx_fld; + const dict_field_t* innodb_idx_fld_end; + + DBUG_ENTER("innobase_match_index_columns"); + + /* Check whether user defined index column count matches */ + if (key_info->key_parts != index_info->n_user_defined_cols) { + DBUG_RETURN(FALSE); + } + + key_part = key_info->key_part; + key_end = key_part + key_info->key_parts; + innodb_idx_fld = index_info->fields; + innodb_idx_fld_end = index_info->fields + index_info->n_fields; + + /* Check each index column's datatype. We do not check + column name because there exists case that index + column name got modified in mysql but such change does not + propagate to InnoDB. + One hidden assumption here is that the index column sequences + are matched up between those in mysql and Innodb. */ + for (; key_part != key_end; ++key_part) { + ulint col_type; + ibool is_unsigned; + ulint mtype = innodb_idx_fld->col->mtype; + + /* Need to translate to InnoDB column type before + comparison. */ + col_type = get_innobase_type_from_mysql_type(&is_unsigned, + key_part->field); + + /* Ignore Innodb specific system columns. */ + while (mtype == DATA_SYS) { + innodb_idx_fld++; + + if (innodb_idx_fld >= innodb_idx_fld_end) { + DBUG_RETURN(FALSE); + } + } + + if (col_type != mtype) { + /* Column Type mismatches */ + DBUG_RETURN(FALSE); + } + + innodb_idx_fld++; + } + + DBUG_RETURN(TRUE); +} + +/*******************************************************************//** +This function builds a translation table in INNOBASE_SHARE +structure for fast index location with mysql array number from its +table->key_info structure. This also provides the necessary translation +between the key order in mysql key_info and Innodb ib_table->indexes if +they are not fully matched with each other. +Note we do not have any mutex protecting the translation table +building based on the assumption that there is no concurrent +index creation/drop and DMLs that requires index lookup. All table +handle will be closed before the index creation/drop. +@return TRUE if index translation table built successfully */ +static +ibool +innobase_build_index_translation( +/*=============================*/ + const TABLE* table, /*!< in: table in MySQL data + dictionary */ + dict_table_t* ib_table, /*!< in: table in Innodb data + dictionary */ + INNOBASE_SHARE* share) /*!< in/out: share structure + where index translation table + will be constructed in. */ +{ + ulint mysql_num_index; + ulint ib_num_index; + dict_index_t** index_mapping; + ibool ret = TRUE; + + DBUG_ENTER("innobase_build_index_translation"); + + mysql_num_index = table->s->keys; + ib_num_index = UT_LIST_GET_LEN(ib_table->indexes); + + index_mapping = share->idx_trans_tbl.index_mapping; + + /* If there exists inconsistency between MySQL and InnoDB dictionary + (metadata) information, the number of index defined in MySQL + could exceed that in InnoDB, do not build index translation + table in such case */ + if (UNIV_UNLIKELY(ib_num_index < mysql_num_index)) { + ret = FALSE; + goto func_exit; + } + + /* If index entry count is non-zero, nothing has + changed since last update, directly return TRUE */ + if (share->idx_trans_tbl.index_count) { + /* Index entry count should still match mysql_num_index */ + ut_a(share->idx_trans_tbl.index_count == mysql_num_index); + goto func_exit; + } + + /* The number of index increased, rebuild the mapping table */ + if (mysql_num_index > share->idx_trans_tbl.array_size) { + index_mapping = (dict_index_t**) my_realloc(index_mapping, + mysql_num_index * + sizeof(*index_mapping), + MYF(MY_ALLOW_ZERO_PTR)); + + if (!index_mapping) { + ret = FALSE; + goto func_exit; + } + + share->idx_trans_tbl.array_size = mysql_num_index; + } + + + /* For each index in the mysql key_info array, fetch its + corresponding InnoDB index pointer into index_mapping + array. */ + for (ulint count = 0; count < mysql_num_index; count++) { + + /* Fetch index pointers into index_mapping according to mysql + index sequence */ + index_mapping[count] = dict_table_get_index_on_name( + ib_table, table->key_info[count].name); + + if (!index_mapping[count]) { + sql_print_error("Cannot find index %s in InnoDB " + "index dictionary.", + table->key_info[count].name); + ret = FALSE; + goto func_exit; + } + + /* Double check fetched index has the same + column info as those in mysql key_info. */ + if (!innobase_match_index_columns(&table->key_info[count], + index_mapping[count])) { + sql_print_error("Found index %s whose column info " + "does not match that of MySQL.", + table->key_info[count].name); + ret = FALSE; + goto func_exit; + } + } + + /* Successfully built the translation table */ + share->idx_trans_tbl.index_count = mysql_num_index; + +func_exit: + if (!ret) { + /* Build translation table failed. */ + my_free(index_mapping, MYF(MY_ALLOW_ZERO_PTR)); + + share->idx_trans_tbl.array_size = 0; + share->idx_trans_tbl.index_count = 0; + index_mapping = NULL; + } + + share->idx_trans_tbl.index_mapping = index_mapping; + + DBUG_RETURN(ret); +} + +/*******************************************************************//** +This function uses index translation table to quickly locate the +requested index structure. +Note we do not have mutex protection for the index translatoin table +access, it is based on the assumption that there is no concurrent +translation table rebuild (fter create/drop index) and DMLs that +require index lookup. +@return dict_index_t structure for requested index. NULL if +fail to locate the index structure. */ +static +dict_index_t* +innobase_index_lookup( +/*==================*/ + INNOBASE_SHARE* share, /*!< in: share structure for index + translation table. */ + uint keynr) /*!< in: index number for the requested + index */ +{ + if (!share->idx_trans_tbl.index_mapping + || keynr >= share->idx_trans_tbl.index_count) { + return(NULL); + } + + return(share->idx_trans_tbl.index_mapping[keynr]); +} + +/************************************************************************ Set the autoinc column max value. This should only be called once from -ha_innobase::open(). Therefore there's no need for a covering lock. -@return DB_SUCCESS or error code */ +ha_innobase::open(). Therefore there's no need for a covering lock. */ UNIV_INTERN -ulint +void ha_innobase::innobase_initialize_autoinc() /*======================================*/ { - dict_index_t* index; ulonglong auto_inc; - const char* col_name; - ulint error; + const Field* field = table->found_next_number_field; - col_name = table->found_next_number_field->field_name; - index = innobase_get_index(table->s->next_number_index); + if (field != NULL) { + auto_inc = innobase_get_int_col_max_value(field); + } else { + /* We have no idea what's been passed in to us as the + autoinc column. We set it to the 0, effectively disabling + updates to the table. */ + auto_inc = 0; - /* Execute SELECT MAX(col_name) FROM TABLE; */ - error = row_search_max_autoinc(index, col_name, &auto_inc); + ut_print_timestamp(stderr); + fprintf(stderr, " InnoDB: Unable to determine the AUTOINC " + "column name\n"); + } - switch (error) { - case DB_SUCCESS: + if (srv_force_recovery >= SRV_FORCE_NO_IBUF_MERGE) { + /* If the recovery level is set so high that writes + are disabled we force the AUTOINC counter to 0 + value effectively disabling writes to the table. + Secondly, we avoid reading the table in case the read + results in failure due to a corrupted table/index. + + We will not return an error to the client, so that the + tables can be dumped with minimal hassle. If an error + were returned in this case, the first attempt to read + the table would fail and subsequent SELECTs would succeed. */ + auto_inc = 0; + } else if (field == NULL) { + /* This is a far more serious error, best to avoid + opening the table and return failure. */ + my_error(ER_AUTOINC_READ_FAILED, MYF(0)); + } else { + dict_index_t* index; + const char* col_name; + ulonglong read_auto_inc; + ulint err; - /* At the this stage we don't know the increment - or the offset, so use default inrement of 1. */ - ++auto_inc; - break; + update_thd(ha_thd()); - case DB_RECORD_NOT_FOUND: - ut_print_timestamp(stderr); - fprintf(stderr, " InnoDB: MySQL and InnoDB data " - "dictionaries are out of sync.\n" - "InnoDB: Unable to find the AUTOINC column %s in the " - "InnoDB table %s.\n" - "InnoDB: We set the next AUTOINC column value to the " - "maximum possible value,\n" - "InnoDB: in effect disabling the AUTOINC next value " - "generation.\n" - "InnoDB: You can either set the next AUTOINC value " - "explicitly using ALTER TABLE\n" - "InnoDB: or fix the data dictionary by recreating " - "the table.\n", - col_name, index->table->name); - - auto_inc = 0xFFFFFFFFFFFFFFFFULL; - break; + ut_a(prebuilt->trx == thd_to_trx(user_thd)); - default: - return(error); + col_name = field->field_name; + index = innobase_get_index(table->s->next_number_index); + + /* Execute SELECT MAX(col_name) FROM TABLE; */ + err = row_search_max_autoinc(index, col_name, &read_auto_inc); + + switch (err) { + case DB_SUCCESS: + /* At the this stage we do not know the increment + or the offset, so use a default increment of 1. */ + auto_inc = read_auto_inc + 1; + break; + + case DB_RECORD_NOT_FOUND: + ut_print_timestamp(stderr); + fprintf(stderr, " InnoDB: MySQL and InnoDB data " + "dictionaries are out of sync.\n" + "InnoDB: Unable to find the AUTOINC column " + "%s in the InnoDB table %s.\n" + "InnoDB: We set the next AUTOINC column " + "value to 0,\n" + "InnoDB: in effect disabling the AUTOINC " + "next value generation.\n" + "InnoDB: You can either set the next " + "AUTOINC value explicitly using ALTER TABLE\n" + "InnoDB: or fix the data dictionary by " + "recreating the table.\n", + col_name, index->table->name); + + /* This will disable the AUTOINC generation. */ + auto_inc = 0; + + /* We want the open to succeed, so that the user can + take corrective action. ie. reads should succeed but + updates should fail. */ + err = DB_SUCCESS; + break; + default: + /* row_search_max_autoinc() should only return + one of DB_SUCCESS or DB_RECORD_NOT_FOUND. */ + ut_error; + } } dict_table_autoinc_initialize(prebuilt->table, auto_inc); - - return(DB_SUCCESS); } /*****************************************************************//** @@ -3192,6 +3496,11 @@ retry: primary_key = table->s->primary_key; key_used_on_scan = primary_key; + if (!innobase_build_index_translation(table, ib_table, share)) { + sql_print_error("Build InnoDB index translation table for" + " Table %s failed", name); + } + /* Allocate a buffer for a 'row reference'. A row reference is a string of bytes of length ref_length which uniquely specifies a row in our table. Note that MySQL may also compare two row @@ -3199,31 +3508,86 @@ retry: of length ref_length! */ if (!row_table_got_default_clust_index(ib_table)) { - if (primary_key >= MAX_KEY) { - sql_print_error("Table %s has a primary key in InnoDB data " - "dictionary, but not in MySQL!", name); - } prebuilt->clust_index_was_generated = FALSE; - /* MySQL allocates the buffer for ref. key_info->key_length - includes space for all key columns + one byte for each column - that may be NULL. ref_length must be as exact as possible to - save space, because all row reference buffers are allocated - based on ref_length. */ + if (UNIV_UNLIKELY(primary_key >= MAX_KEY)) { + sql_print_error("Table %s has a primary key in " + "InnoDB data dictionary, but not " + "in MySQL!", name); - ref_length = table->key_info[primary_key].key_length; + /* This mismatch could cause further problems + if not attended, bring this to the user's attention + by printing a warning in addition to log a message + in the errorlog */ + push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_WARN, + ER_NO_SUCH_INDEX, + "InnoDB: Table %s has a " + "primary key in InnoDB data " + "dictionary, but not in " + "MySQL!", name); + + /* If primary_key >= MAX_KEY, its (primary_key) + value could be out of bound if continue to index + into key_info[] array. Find InnoDB primary index, + and assign its key_length to ref_length. + In addition, since MySQL indexes are sorted starting + with primary index, unique index etc., initialize + ref_length to the first index key length in + case we fail to find InnoDB cluster index. + + Please note, this will not resolve the primary + index mismatch problem, other side effects are + possible if users continue to use the table. + However, we allow this table to be opened so + that user can adopt necessary measures for the + mismatch while still being accessible to the table + date. */ + ref_length = table->key_info[0].key_length; + + /* Find correspoinding cluster index + key length in MySQL's key_info[] array */ + for (ulint i = 0; i < table->s->keys; i++) { + dict_index_t* index; + index = innobase_get_index(i); + if (dict_index_is_clust(index)) { + ref_length = + table->key_info[i].key_length; + } + } + } else { + /* MySQL allocates the buffer for ref. + key_info->key_length includes space for all key + columns + one byte for each column that may be + NULL. ref_length must be as exact as possible to + save space, because all row reference buffers are + allocated based on ref_length. */ + + ref_length = table->key_info[primary_key].key_length; + } } else { if (primary_key != MAX_KEY) { - sql_print_error("Table %s has no primary key in InnoDB data " - "dictionary, but has one in MySQL! If you " - "created the table with a MySQL version < " - "3.23.54 and did not define a primary key, " - "but defined a unique key with all non-NULL " - "columns, then MySQL internally treats that " - "key as the primary key. You can fix this " - "error by dump + DROP + CREATE + reimport " - "of the table.", name); + sql_print_error( + "Table %s has no primary key in InnoDB data " + "dictionary, but has one in MySQL! If you " + "created the table with a MySQL version < " + "3.23.54 and did not define a primary key, " + "but defined a unique key with all non-NULL " + "columns, then MySQL internally treats that " + "key as the primary key. You can fix this " + "error by dump + DROP + CREATE + reimport " + "of the table.", name); + + /* This mismatch could cause further problems + if not attended, bring this to the user attention + by printing a warning in addition to log a message + in the errorlog */ + push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_WARN, + ER_NO_SUCH_INDEX, + "InnoDB: Table %s has no " + "primary key in InnoDB data " + "dictionary, but has one in " + "MySQL!", name); } prebuilt->clust_index_was_generated = TRUE; @@ -3265,8 +3629,6 @@ retry: /* Only if the table has an AUTOINC column. */ if (prebuilt->table != NULL && table->found_next_number_field != NULL) { - ulint error; - dict_table_autoinc_lock(prebuilt->table); /* Since a table can already be "open" in InnoDB's internal @@ -3275,8 +3637,7 @@ retry: autoinc value from a previous MySQL open. */ if (dict_table_autoinc_read(prebuilt->table) == 0) { - error = innobase_initialize_autoinc(); - ut_a(error == DB_SUCCESS); + innobase_initialize_autoinc(); } dict_table_autoinc_unlock(prebuilt->table); @@ -4093,67 +4454,6 @@ skip_field: } /********************************************************************//** -Get the upper limit of the MySQL integral and floating-point type. */ -UNIV_INTERN -ulonglong -ha_innobase::innobase_get_int_col_max_value( -/*========================================*/ - const Field* field) -{ - ulonglong max_value = 0; - - switch(field->key_type()) { - /* TINY */ - case HA_KEYTYPE_BINARY: - max_value = 0xFFULL; - break; - case HA_KEYTYPE_INT8: - max_value = 0x7FULL; - break; - /* SHORT */ - case HA_KEYTYPE_USHORT_INT: - max_value = 0xFFFFULL; - break; - case HA_KEYTYPE_SHORT_INT: - max_value = 0x7FFFULL; - break; - /* MEDIUM */ - case HA_KEYTYPE_UINT24: - max_value = 0xFFFFFFULL; - break; - case HA_KEYTYPE_INT24: - max_value = 0x7FFFFFULL; - break; - /* LONG */ - case HA_KEYTYPE_ULONG_INT: - max_value = 0xFFFFFFFFULL; - break; - case HA_KEYTYPE_LONG_INT: - max_value = 0x7FFFFFFFULL; - break; - /* BIG */ - case HA_KEYTYPE_ULONGLONG: - max_value = 0xFFFFFFFFFFFFFFFFULL; - break; - case HA_KEYTYPE_LONGLONG: - max_value = 0x7FFFFFFFFFFFFFFFULL; - break; - case HA_KEYTYPE_FLOAT: - /* We use the maximum as per IEEE754-2008 standard, 2^24 */ - max_value = 0x1000000ULL; - break; - case HA_KEYTYPE_DOUBLE: - /* We use the maximum as per IEEE754-2008 standard, 2^53 */ - max_value = 0x20000000000000ULL; - break; - default: - ut_error; - } - - return(max_value); -} - -/********************************************************************//** This special handling is really to overcome the limitations of MySQL's binlogging. We need to eliminate the non-determinism that will arise in INSERT ... SELECT type of statements, since MySQL binlog only stores the @@ -4378,11 +4678,17 @@ no_commit: prebuilt->autoinc_error = DB_SUCCESS; if ((error = update_auto_increment())) { - /* We don't want to mask autoinc overflow errors. */ - if (prebuilt->autoinc_error != DB_SUCCESS) { - error = (int) prebuilt->autoinc_error; + /* Handle the case where the AUTOINC sub-system + failed during initialization. */ + if (prebuilt->autoinc_error == DB_UNSUPPORTED) { + error_result = ER_AUTOINC_READ_FAILED; + /* Set the error message to report too. */ + my_error(ER_AUTOINC_READ_FAILED, MYF(0)); + goto func_exit; + } else if (prebuilt->autoinc_error != DB_SUCCESS) { + error = (int) prebuilt->autoinc_error; goto report_error; } @@ -4463,24 +4769,29 @@ no_commit: update the table upper limit. Note: last_value will be 0 if get_auto_increment() was not called.*/ - if (auto_inc <= col_max_value - && auto_inc >= prebuilt->autoinc_last_value) { + if (auto_inc >= prebuilt->autoinc_last_value) { set_max_autoinc: - ut_a(prebuilt->autoinc_increment > 0); + /* This should filter out the negative + values set explicitly by the user. */ + if (auto_inc <= col_max_value) { + ut_a(prebuilt->autoinc_increment > 0); - ulonglong need; - ulonglong offset; + ulonglong need; + ulonglong offset; - offset = prebuilt->autoinc_offset; - need = prebuilt->autoinc_increment; + offset = prebuilt->autoinc_offset; + need = prebuilt->autoinc_increment; - auto_inc = innobase_next_autoinc( - auto_inc, need, offset, col_max_value); + auto_inc = innobase_next_autoinc( + auto_inc, + need, offset, col_max_value); - err = innobase_set_max_autoinc(auto_inc); + err = innobase_set_max_autoinc( + auto_inc); - if (err != DB_SUCCESS) { - error = err; + if (err != DB_SUCCESS) { + error = err; + } } } break; @@ -4826,7 +5137,7 @@ ha_innobase::unlock_row(void) case ROW_READ_WITH_LOCKS: if (!srv_locks_unsafe_for_binlog && prebuilt->trx->isolation_level - != TRX_ISO_READ_COMMITTED) { + > TRX_ISO_READ_COMMITTED) { break; } /* fall through */ @@ -4865,7 +5176,7 @@ ha_innobase::try_semi_consistent_read(bool yes) if (yes && (srv_locks_unsafe_for_binlog - || prebuilt->trx->isolation_level == TRX_ISO_READ_COMMITTED)) { + || prebuilt->trx->isolation_level <= TRX_ISO_READ_COMMITTED)) { prebuilt->row_read_type = ROW_READ_TRY_SEMI_CONSISTENT; } else { prebuilt->row_read_type = ROW_READ_WITH_LOCKS; @@ -5160,14 +5471,30 @@ ha_innobase::innobase_get_index( DBUG_ENTER("innobase_get_index"); ha_statistic_increment(&SSV::ha_read_key_count); - ut_ad(user_thd == ha_thd()); - ut_a(prebuilt->trx == thd_to_trx(user_thd)); - if (keynr != MAX_KEY && table->s->keys > 0) { key = table->key_info + keynr; - index = dict_table_get_index_on_name(prebuilt->table, - key->name); + index = innobase_index_lookup(share, keynr); + + if (index) { + ut_a(ut_strcmp(index->name, key->name) == 0); + } else { + /* Can't find index with keynr in the translation + table. Only print message if the index translation + table exists */ + if (share->idx_trans_tbl.index_mapping) { + sql_print_error("InnoDB could not find " + "index %s key no %u for " + "table %s through its " + "index translation table", + key ? key->name : "NULL", + keynr, + prebuilt->table->name); + } + + index = dict_table_get_index_on_name(prebuilt->table, + key->name); + } } else { index = dict_table_get_first_index(prebuilt->table); } @@ -5228,7 +5555,7 @@ ha_innobase::change_active_index( dtuple_set_n_fields(prebuilt->search_tuple, prebuilt->index->n_fields); dict_index_copy_types(prebuilt->search_tuple, prebuilt->index, - prebuilt->index->n_fields); + prebuilt->index->n_fields); /* MySQL changes the active index for a handle also during some queries, for example SELECT MAX(a), SUM(a) first retrieves the MAX() @@ -5729,9 +6056,11 @@ create_table_def( if (error == DB_DUPLICATE_KEY) { char buf[100]; - innobase_convert_identifier(buf, sizeof buf, - table_name, strlen(table_name), - trx->mysql_thd, TRUE); + char* buf_end = innobase_convert_identifier( + buf, sizeof buf - 1, table_name, strlen(table_name), + trx->mysql_thd, TRUE); + + *buf_end = '\0'; my_error(ER_TABLE_EXISTS_ERROR, MYF(0), buf); } @@ -6333,6 +6662,10 @@ ha_innobase::create( goto cleanup; } + if (create_info->options & HA_LEX_CREATE_TMP_TABLE) { + flags |= DICT_TF2_TEMPORARY << DICT_TF2_SHIFT; + } + error = create_table_def(trx, form, norm_name, create_info->options & HA_LEX_CREATE_TMP_TABLE ? name2 : NULL, flags); @@ -6854,10 +7187,15 @@ ha_innobase::records_in_range( key = table->key_info + active_index; - index = dict_table_get_index_on_name(prebuilt->table, key->name); + index = innobase_get_index(keynr); - /* MySQL knows about this index and so we must be able to find it.*/ - ut_a(index); + /* There exists possibility of not being able to find requested + index due to inconsistency between MySQL and InoDB dictionary info. + Necessary message should have been printed in innobase_get_index() */ + if (UNIV_UNLIKELY(!index)) { + n_rows = HA_POS_ERROR; + goto func_exit; + } heap = mem_heap_create(2 * (key->key_parts * sizeof(dfield_t) + sizeof(dtuple_t))); @@ -6902,6 +7240,7 @@ ha_innobase::records_in_range( mem_heap_free(heap); +func_exit: my_free(key_val_buff2, MYF(0)); prebuilt->trx->op_info = (char*)""; @@ -7043,6 +7382,7 @@ ha_innobase::info( char path[FN_REFLEN]; os_file_stat_t stat_info; + DBUG_ENTER("info"); /* If we are forcing recovery at a high level, we will suppress @@ -7203,13 +7543,29 @@ ha_innobase::info( } if (flag & HA_STATUS_CONST) { - index = dict_table_get_first_index(ib_table); - - if (prebuilt->clust_index_was_generated) { - index = dict_table_get_next_index(index); + /* Verify the number of index in InnoDB and MySQL + matches up. If prebuilt->clust_index_was_generated + holds, InnoDB defines GEN_CLUST_INDEX internally */ + ulint num_innodb_index = UT_LIST_GET_LEN(ib_table->indexes) + - prebuilt->clust_index_was_generated; + + if (table->s->keys != num_innodb_index) { + sql_print_error("Table %s contains %lu " + "indexes inside InnoDB, which " + "is different from the number of " + "indexes %u defined in the MySQL ", + ib_table->name, num_innodb_index, + table->s->keys); } for (i = 0; i < table->s->keys; i++) { + /* We could get index quickly through internal + index mapping with the index translation table. + The identity of index (match up index name with + that of table->key_info[i]) is already verified in + innobase_get_index(). */ + index = innobase_get_index(i); + if (index == NULL) { sql_print_error("Table %s contains fewer " "indexes inside InnoDB than " @@ -7238,6 +7594,8 @@ ha_innobase::info( break; } + dict_index_stat_mutex_enter(index); + if (index->stat_n_diff_key_vals[j + 1] == 0) { rec_per_key = stats.records; @@ -7246,6 +7604,8 @@ ha_innobase::info( index->stat_n_diff_key_vals[j + 1]); } + dict_index_stat_mutex_exit(index); + /* Since MySQL seems to favor table scans too much over index searches, we pretend index selectivity is 2 times better than @@ -7261,8 +7621,6 @@ ha_innobase::info( rec_per_key >= ~(ulong) 0 ? ~(ulong) 0 : (ulong) rec_per_key; } - - index = dict_table_get_next_index(index); } } @@ -7302,15 +7660,9 @@ ha_innobase::analyze( THD* thd, /*!< in: connection thread handle */ HA_CHECK_OPT* check_opt) /*!< in: currently ignored */ { - /* Serialize ANALYZE TABLE inside InnoDB, see - Bug#38996 Race condition in ANALYZE TABLE */ - pthread_mutex_lock(&analyze_mutex); - /* Simply call ::info() with all the flags */ info(HA_STATUS_TIME | HA_STATUS_CONST | HA_STATUS_VARIABLE); - pthread_mutex_unlock(&analyze_mutex); - return(0); } @@ -7340,8 +7692,13 @@ ha_innobase::check( HA_CHECK_OPT* check_opt) /*!< in: check options, currently ignored */ { - ulint ret; + dict_index_t* index; + ulint n_rows; + ulint n_rows_in_table = ULINT_UNDEFINED; + ibool is_ok = TRUE; + ulint old_isolation_level; + DBUG_ENTER("ha_innobase::check"); DBUG_ASSERT(thd == ha_thd()); ut_a(prebuilt->trx); ut_a(prebuilt->trx->magic_n == TRX_MAGIC_N); @@ -7354,17 +7711,140 @@ ha_innobase::check( build_template(prebuilt, NULL, table, ROW_MYSQL_WHOLE_ROW); } - ret = row_check_table_for_mysql(prebuilt); + if (prebuilt->table->ibd_file_missing) { + sql_print_error("InnoDB: Error:\n" + "InnoDB: MySQL is trying to use a table handle" + " but the .ibd file for\n" + "InnoDB: table %s does not exist.\n" + "InnoDB: Have you deleted the .ibd file" + " from the database directory under\n" + "InnoDB: the MySQL datadir, or have you" + " used DISCARD TABLESPACE?\n" + "InnoDB: Please refer to\n" + "InnoDB: " REFMAN "innodb-troubleshooting.html\n" + "InnoDB: how you can resolve the problem.\n", + prebuilt->table->name); + DBUG_RETURN(HA_ADMIN_CORRUPT); + } + + prebuilt->trx->op_info = "checking table"; - switch (ret) { - case DB_SUCCESS: - return(HA_ADMIN_OK); - case DB_INTERRUPTED: + old_isolation_level = prebuilt->trx->isolation_level; + + /* We must run the index record counts at an isolation level + >= READ COMMITTED, because a dirty read can see a wrong number + of records in some index; to play safe, we use always + REPEATABLE READ here */ + + prebuilt->trx->isolation_level = TRX_ISO_REPEATABLE_READ; + + /* Enlarge the fatal lock wait timeout during CHECK TABLE. */ + mutex_enter(&kernel_mutex); + srv_fatal_semaphore_wait_threshold += 7200; /* 2 hours */ + mutex_exit(&kernel_mutex); + + for (index = dict_table_get_first_index(prebuilt->table); + index != NULL; + index = dict_table_get_next_index(index)) { +#if 0 + fputs("Validating index ", stderr); + ut_print_name(stderr, trx, FALSE, index->name); + putc('\n', stderr); +#endif + + if (!btr_validate_index(index, prebuilt->trx)) { + is_ok = FALSE; + push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_WARN, + ER_NOT_KEYFILE, + "InnoDB: The B-tree of" + " index '%-.200s' is corrupted.", + index->name); + continue; + } + + /* Instead of invoking change_active_index(), set up + a dummy template for non-locking reads, disabling + access to the clustered index. */ + prebuilt->index = index; + + prebuilt->index_usable = row_merge_is_index_usable( + prebuilt->trx, prebuilt->index); + + if (UNIV_UNLIKELY(!prebuilt->index_usable)) { + push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_WARN, + HA_ERR_TABLE_DEF_CHANGED, + "InnoDB: Insufficient history for" + " index '%-.200s'", + index->name); + continue; + } + + prebuilt->sql_stat_start = TRUE; + prebuilt->template_type = ROW_MYSQL_DUMMY_TEMPLATE; + prebuilt->n_template = 0; + prebuilt->need_to_access_clustered = FALSE; + + dtuple_set_n_fields(prebuilt->search_tuple, 0); + + prebuilt->select_lock_type = LOCK_NONE; + + if (!row_check_index_for_mysql(prebuilt, index, &n_rows)) { + push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_WARN, + ER_NOT_KEYFILE, + "InnoDB: The B-tree of" + " index '%-.200s' is corrupted.", + index->name); + is_ok = FALSE; + } + + if (thd_killed(user_thd)) { + break; + } + +#if 0 + fprintf(stderr, "%lu entries in index %s\n", n_rows, + index->name); +#endif + + if (index == dict_table_get_first_index(prebuilt->table)) { + n_rows_in_table = n_rows; + } else if (n_rows != n_rows_in_table) { + push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_WARN, + ER_NOT_KEYFILE, + "InnoDB: Index '%-.200s'" + " contains %lu entries," + " should be %lu.", + index->name, + (ulong) n_rows, + (ulong) n_rows_in_table); + is_ok = FALSE; + } + } + + /* Restore the original isolation level */ + prebuilt->trx->isolation_level = old_isolation_level; + + /* We validate also the whole adaptive hash index for all tables + at every CHECK TABLE */ + + if (!btr_search_validate()) { + push_warning(thd, MYSQL_ERROR::WARN_LEVEL_WARN, + ER_NOT_KEYFILE, + "InnoDB: The adaptive hash index is corrupted."); + is_ok = FALSE; + } + + /* Restore the fatal lock wait timeout after CHECK TABLE. */ + mutex_enter(&kernel_mutex); + srv_fatal_semaphore_wait_threshold -= 7200; /* 2 hours */ + mutex_exit(&kernel_mutex); + + prebuilt->trx->op_info = ""; + if (thd_killed(user_thd)) { my_error(ER_QUERY_INTERRUPTED, MYF(0)); - return(-1); - default: - return(HA_ADMIN_CORRUPT); } + + DBUG_RETURN(is_ok ? HA_ADMIN_OK : HA_ADMIN_CORRUPT); } /*************************************************************//** @@ -8187,8 +8667,8 @@ innodb_show_status( mutex_enter(&srv_monitor_file_mutex); rewind(srv_monitor_file); - srv_printf_innodb_monitor(srv_monitor_file, - &trx_list_start, &trx_list_end); + srv_printf_innodb_monitor(srv_monitor_file, FALSE, + &trx_list_start, &trx_list_end); flen = ftell(srv_monitor_file); os_file_set_eof(srv_monitor_file); @@ -8245,19 +8725,25 @@ innodb_show_status( } /************************************************************************//** -Implements the SHOW MUTEX STATUS command. . */ +Implements the SHOW MUTEX STATUS command. +@return TRUE on failure, FALSE on success. */ static bool innodb_mutex_show_status( /*=====================*/ - handlerton* hton, /*!< in: the innodb handlerton */ + handlerton* hton, /*!< in: the innodb handlerton */ THD* thd, /*!< in: the MySQL query thread of the caller */ - stat_print_fn* stat_print) + stat_print_fn* stat_print) /*!< in: function for printing + statistics */ { char buf1[IO_SIZE], buf2[IO_SIZE]; mutex_t* mutex; rw_lock_t* lock; + ulint block_mutex_oswait_count = 0; + ulint block_lock_oswait_count = 0; + mutex_t* block_mutex = NULL; + rw_lock_t* block_lock = NULL; #ifdef UNIV_DEBUG ulint rw_lock_count= 0; ulint rw_lock_count_spin_loop= 0; @@ -8272,12 +8758,16 @@ innodb_mutex_show_status( mutex_enter(&mutex_list_mutex); - mutex = UT_LIST_GET_FIRST(mutex_list); + for (mutex = UT_LIST_GET_FIRST(mutex_list); mutex != NULL; + mutex = UT_LIST_GET_NEXT(list, mutex)) { + if (mutex->count_os_wait == 0) { + continue; + } - while (mutex != NULL) { - if (mutex->count_os_wait == 0 - || buf_pool_is_block_mutex(mutex)) { - goto next_mutex; + if (buf_pool_is_block_mutex(mutex)) { + block_mutex = mutex; + block_mutex_oswait_count += mutex->count_os_wait; + continue; } #ifdef UNIV_DEBUG if (mutex->mutex_type != 1) { @@ -8304,8 +8794,7 @@ innodb_mutex_show_status( DBUG_RETURN(1); } } - } - else { + } else { rw_lock_count += mutex->count_using; rw_lock_count_spin_loop += mutex->count_spin_loop; rw_lock_count_spin_rounds += mutex->count_spin_rounds; @@ -8317,7 +8806,7 @@ innodb_mutex_show_status( buf1len= (uint) my_snprintf(buf1, sizeof(buf1), "%s:%lu", mutex->cfile_name, (ulong) mutex->cline); buf2len= (uint) my_snprintf(buf2, sizeof(buf2), "os_waits=%lu", - mutex->count_os_wait); + (ulong) mutex->count_os_wait); if (stat_print(thd, innobase_hton_name, hton_name_len, buf1, buf1len, @@ -8326,45 +8815,83 @@ innodb_mutex_show_status( DBUG_RETURN(1); } #endif /* UNIV_DEBUG */ + } + + if (block_mutex) { + buf1len = (uint) my_snprintf(buf1, sizeof buf1, + "combined %s:%lu", + block_mutex->cfile_name, + (ulong) block_mutex->cline); + buf2len = (uint) my_snprintf(buf2, sizeof buf2, + "os_waits=%lu", + (ulong) block_mutex_oswait_count); -next_mutex: - mutex = UT_LIST_GET_NEXT(list, mutex); + if (stat_print(thd, innobase_hton_name, + hton_name_len, buf1, buf1len, + buf2, buf2len)) { + mutex_exit(&mutex_list_mutex); + DBUG_RETURN(1); + } } mutex_exit(&mutex_list_mutex); mutex_enter(&rw_lock_list_mutex); - lock = UT_LIST_GET_FIRST(rw_lock_list); - - while (lock != NULL) { - if (lock->count_os_wait - && !buf_pool_is_block_lock(lock)) { - buf1len= my_snprintf(buf1, sizeof(buf1), "%s:%lu", - lock->cfile_name, (ulong) lock->cline); - buf2len= my_snprintf(buf2, sizeof(buf2), - "os_waits=%lu", lock->count_os_wait); - - if (stat_print(thd, innobase_hton_name, - hton_name_len, buf1, buf1len, - buf2, buf2len)) { - mutex_exit(&rw_lock_list_mutex); - DBUG_RETURN(1); - } + for (lock = UT_LIST_GET_FIRST(rw_lock_list); lock != NULL; + lock = UT_LIST_GET_NEXT(list, lock)) { + if (lock->count_os_wait == 0) { + continue; + } + + if (buf_pool_is_block_lock(lock)) { + block_lock = lock; + block_lock_oswait_count += lock->count_os_wait; + continue; + } + + buf1len = my_snprintf(buf1, sizeof buf1, "%s:%lu", + lock->cfile_name, (ulong) lock->cline); + buf2len = my_snprintf(buf2, sizeof buf2, "os_waits=%lu", + (ulong) lock->count_os_wait); + + if (stat_print(thd, innobase_hton_name, + hton_name_len, buf1, buf1len, + buf2, buf2len)) { + mutex_exit(&rw_lock_list_mutex); + DBUG_RETURN(1); + } + } + + if (block_lock) { + buf1len = (uint) my_snprintf(buf1, sizeof buf1, + "combined %s:%lu", + block_lock->cfile_name, + (ulong) block_lock->cline); + buf2len = (uint) my_snprintf(buf2, sizeof buf2, + "os_waits=%lu", + (ulong) block_lock_oswait_count); + + if (stat_print(thd, innobase_hton_name, + hton_name_len, buf1, buf1len, + buf2, buf2len)) { + mutex_exit(&rw_lock_list_mutex); + DBUG_RETURN(1); } - lock = UT_LIST_GET_NEXT(list, lock); } mutex_exit(&rw_lock_list_mutex); #ifdef UNIV_DEBUG - buf2len= my_snprintf(buf2, sizeof(buf2), - "count=%lu, spin_waits=%lu, spin_rounds=%lu, " - "os_waits=%lu, os_yields=%lu, os_wait_times=%lu", - rw_lock_count, rw_lock_count_spin_loop, - rw_lock_count_spin_rounds, - rw_lock_count_os_wait, rw_lock_count_os_yield, - (ulong) (rw_lock_wait_time/1000)); + buf2len = my_snprintf(buf2, sizeof buf2, + "count=%lu, spin_waits=%lu, spin_rounds=%lu, " + "os_waits=%lu, os_yields=%lu, os_wait_times=%lu", + (ulong) rw_lock_count, + (ulong) rw_lock_count_spin_loop, + (ulong) rw_lock_count_spin_rounds, + (ulong) rw_lock_count_os_wait, + (ulong) rw_lock_count_os_yield, + (ulong) (rw_lock_wait_time / 1000)); if (stat_print(thd, innobase_hton_name, hton_name_len, STRING_WITH_LEN("rw_lock_mutexes"), buf2, buf2len)) { @@ -8426,6 +8953,11 @@ static INNOBASE_SHARE* get_share(const char* table_name) innobase_open_tables, fold, share); thr_lock_init(&share->lock); + + /* Index translation table initialization */ + share->idx_trans_tbl.index_mapping = NULL; + share->idx_trans_tbl.index_count = 0; + share->idx_trans_tbl.array_size = 0; } share->use_count++; @@ -8456,6 +8988,11 @@ static void free_share(INNOBASE_SHARE* share) HASH_DELETE(INNOBASE_SHARE, table_name_hash, innobase_open_tables, fold, share); thr_lock_delete(&share->lock); + + /* Free any memory from index translation table */ + my_free(share->idx_trans_tbl.index_mapping, + MYF(MY_ALLOW_ZERO_PTR)); + my_free(share, MYF(0)); /* TODO: invoke HASH_MIGRATE if innobase_open_tables @@ -8558,7 +9095,7 @@ ha_innobase::store_lock( isolation_level = trx->isolation_level; if ((srv_locks_unsafe_for_binlog - || isolation_level == TRX_ISO_READ_COMMITTED) + || isolation_level <= TRX_ISO_READ_COMMITTED) && isolation_level != TRX_ISO_SERIALIZABLE && (lock_type == TL_READ || lock_type == TL_READ_NO_INSERT) && (sql_command == SQLCOM_INSERT_SELECT @@ -8690,7 +9227,10 @@ ha_innobase::innobase_get_autoinc( *value = dict_table_autoinc_read(prebuilt->table); /* It should have been initialized during open. */ - ut_a(*value != 0); + if (*value == 0) { + prebuilt->autoinc_error = DB_UNSUPPORTED; + dict_table_autoinc_unlock(prebuilt->table); + } } return(prebuilt->autoinc_error); @@ -8770,6 +9310,11 @@ ha_innobase::get_auto_increment( invoking this method. So we are not sure if it's guaranteed to be 0 or not. */ + /* We need the upper limit of the col type to check for + whether we update the table autoinc counter or not. */ + ulonglong col_max_value = innobase_get_int_col_max_value( + table->next_number_field); + /* Called for the first time ? */ if (trx->n_autoinc_rows == 0) { @@ -8786,6 +9331,11 @@ ha_innobase::get_auto_increment( /* Not in the middle of a mult-row INSERT. */ } else if (prebuilt->autoinc_last_value == 0) { set_if_bigger(*first_value, autoinc); + /* Check for -ve values. */ + } else if (*first_value > col_max_value && trx->n_autoinc_rows > 0) { + /* Set to next logical value. */ + ut_a(autoinc > trx->n_autoinc_rows); + *first_value = (autoinc - trx->n_autoinc_rows) - 1; } *nb_reserved_values = trx->n_autoinc_rows; @@ -8796,12 +9346,6 @@ ha_innobase::get_auto_increment( ulonglong need; ulonglong current; ulonglong next_value; - ulonglong col_max_value; - - /* We need the upper limit of the col type to check for - whether we update the table autoinc counter or not. */ - col_max_value = innobase_get_int_col_max_value( - table->next_number_field); current = *first_value > col_max_value ? autoinc : *first_value; need = *nb_reserved_values * increment; @@ -9298,33 +9842,60 @@ innobase_set_cursor_view( (cursor_view_t*) curview); } +/*******************************************************************//** +If col_name is not NULL, check whether the named column is being +renamed in the table. If col_name is not provided, check +whether any one of columns in the table is being renamed. +@return true if the column is being renamed */ +static +bool +check_column_being_renamed( +/*=======================*/ + const TABLE* table, /*!< in: MySQL table */ + const char* col_name) /*!< in: name of the column */ +{ + uint k; + Field* field; + + for (k = 0; k < table->s->fields; k++) { + field = table->field[k]; -/*********************************************************************** -Check whether any of the given columns is being renamed in the table. */ + if (field->flags & FIELD_IS_RENAMED) { + + /* If col_name is not provided, return + if the field is marked as being renamed. */ + if (!col_name) { + return(true); + } + + /* If col_name is provided, return only + if names match */ + if (innobase_strcasecmp(field->field_name, + col_name) == 0) { + return(true); + } + } + } + + return(false); +} + +/*******************************************************************//** +Check whether any of the given columns is being renamed in the table. +@return true if any of col_names is being renamed in table */ static bool column_is_being_renamed( /*====================*/ - /* out: true if any of col_names is - being renamed in table */ - TABLE* table, /* in: MySQL table */ - uint n_cols, /* in: number of columns */ - const char** col_names) /* in: names of the columns */ + TABLE* table, /*!< in: MySQL table */ + uint n_cols, /*!< in: number of columns */ + const char** col_names) /*!< in: names of the columns */ { uint j; - uint k; - Field* field; - const char* col_name; for (j = 0; j < n_cols; j++) { - col_name = col_names[j]; - for (k = 0; k < table->s->fields; k++) { - field = table->field[k]; - if ((field->flags & FIELD_IS_RENAMED) - && innobase_strcasecmp(field->field_name, - col_name) == 0) { - return(true); - } + if (check_column_being_renamed(table, col_names[j])) { + return(true); } } @@ -9408,6 +9979,15 @@ ha_innobase::check_if_incompatible_data( return(COMPATIBLE_DATA_NO); } + /* For column rename operation, MySQL does not supply enough + information (new column name etc.) for InnoDB to make appropriate + system metadata change. To avoid system metadata inconsistency, + currently we can just request a table rebuild/copy by returning + COMPATIBLE_DATA_NO */ + if (check_column_being_renamed(table, NULL)) { + return COMPATIBLE_DATA_NO; + } + /* Check if a column participating in a foreign key is being renamed. There is no mechanism for updating InnoDB foreign key definitions. */ if (foreign_key_column_is_being_renamed(prebuilt, table)) { @@ -10153,13 +10733,13 @@ static MYSQL_SYSVAR_BOOL(use_sys_malloc, srv_use_sys_malloc, static MYSQL_SYSVAR_STR(change_buffering, innobase_change_buffering, PLUGIN_VAR_RQCMDARG, "Buffer changes to reduce random access: " - "OFF, ON, inserting, deleting, changing, or purging.", + "OFF, ON, none, inserts.", innodb_change_buffering_validate, innodb_change_buffering_update, NULL); static MYSQL_SYSVAR_ULONG(read_ahead_threshold, srv_read_ahead_threshold, PLUGIN_VAR_RQCMDARG, - "Number of pages that must be accessed sequentially for InnoDB to" + "Number of pages that must be accessed sequentially for InnoDB to " "trigger a readahead.", NULL, NULL, 56, 0, 64, 0); diff --git a/storage/innodb_plugin/handler/ha_innodb.h b/storage/innodb_plugin/handler/ha_innodb.h index 31e88ed8530..8a3e1ccff82 100644 --- a/storage/innodb_plugin/handler/ha_innodb.h +++ b/storage/innodb_plugin/handler/ha_innodb.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 2000, 2009, MySQL AB & Innobase Oy. All Rights Reserved. +Copyright (c) 2000, 2010, MySQL AB & Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -27,15 +27,31 @@ Place, Suite 330, Boston, MA 02111-1307 USA #pragma interface /* gcc class implementation */ #endif +/* Structure defines translation table between mysql index and innodb +index structures */ +typedef struct innodb_idx_translate_struct { + ulint index_count; /*!< number of valid index entries + in the index_mapping array */ + ulint array_size; /*!< array size of index_mapping */ + dict_index_t** index_mapping; /*!< index pointer array directly + maps to index in Innodb from MySQL + array index */ +} innodb_idx_translate_t; + + /** InnoDB table share */ typedef struct st_innobase_share { - THR_LOCK lock; /*!< MySQL lock protecting - this structure */ - const char* table_name; /*!< InnoDB table name */ - uint use_count; /*!< reference count, - incremented in get_share() - and decremented in free_share() */ - void* table_name_hash;/*!< hash table chain node */ + THR_LOCK lock; /*!< MySQL lock protecting + this structure */ + const char* table_name; /*!< InnoDB table name */ + uint use_count; /*!< reference count, + incremented in get_share() + and decremented in + free_share() */ + void* table_name_hash;/*!< hash table chain node */ + innodb_idx_translate_t idx_trans_tbl; /*!< index translation + table between MySQL and + Innodb */ } INNOBASE_SHARE; @@ -91,9 +107,8 @@ class ha_innobase: public handler ulint innobase_reset_autoinc(ulonglong auto_inc); ulint innobase_get_autoinc(ulonglong* value); ulint innobase_update_autoinc(ulonglong auto_inc); - ulint innobase_initialize_autoinc(); + void innobase_initialize_autoinc(); dict_index_t* innobase_get_index(uint keynr); - ulonglong innobase_get_int_col_max_value(const Field* field); /* Init values for the class: */ public: diff --git a/storage/innodb_plugin/handler/handler0alter.cc b/storage/innodb_plugin/handler/handler0alter.cc index a5008991400..e474c318c58 100644 --- a/storage/innodb_plugin/handler/handler0alter.cc +++ b/storage/innodb_plugin/handler/handler0alter.cc @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 2005, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 2005, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -229,9 +229,11 @@ static int innobase_check_index_keys( /*======================*/ - const KEY* key_info, /*!< in: Indexes to be created */ - ulint num_of_keys) /*!< in: Number of indexes to - be created */ + const KEY* key_info, /*!< in: Indexes to be + created */ + ulint num_of_keys, /*!< in: Number of + indexes to be created */ + const dict_table_t* table) /*!< in: Existing indexes */ { ulint key_num; @@ -248,9 +250,22 @@ innobase_check_index_keys( const KEY& key2 = key_info[i]; if (0 == strcmp(key.name, key2.name)) { - sql_print_error("InnoDB: key name `%s` appears" - " twice in CREATE INDEX\n", - key.name); + my_error(ER_WRONG_NAME_FOR_INDEX, MYF(0), + key.name); + + return(ER_WRONG_NAME_FOR_INDEX); + } + } + + /* Check that the same index name does not already exist. */ + + for (const dict_index_t* index + = dict_table_get_first_index(table); + index; index = dict_table_get_next_index(index)) { + + if (0 == strcmp(key.name, index->name)) { + my_error(ER_WRONG_NAME_FOR_INDEX, MYF(0), + key.name); return(ER_WRONG_NAME_FOR_INDEX); } @@ -258,7 +273,7 @@ innobase_check_index_keys( /* Check that MySQL does not try to create a column prefix index field on an inappropriate data type and - that the same colum does not appear twice in the index. */ + that the same column does not appear twice in the index. */ for (ulint i = 0; i < key.key_parts; i++) { const KEY_PART_INFO& key_part1 @@ -289,14 +304,8 @@ innobase_check_index_keys( } } - sql_print_error("InnoDB: MySQL is trying to" - " create a column prefix" - " index field on an" - " inappropriate data type." - " column `%s`," - " index `%s`.\n", - field->field_name, - key.name); + my_error(ER_WRONG_KEY_COLUMN, MYF(0), + field->field_name); return(ER_WRONG_KEY_COLUMN); } @@ -309,11 +318,8 @@ innobase_check_index_keys( continue; } - sql_print_error("InnoDB: column `%s`" - " is not allowed to occur" - " twice in index `%s`.\n", - key_part1.field->field_name, - key.name); + my_error(ER_WRONG_KEY_COLUMN, MYF(0), + key_part1.field->field_name); return(ER_WRONG_KEY_COLUMN); } } @@ -522,12 +528,14 @@ innobase_create_key_def( key_info->name, "PRIMARY"); /* If there is a UNIQUE INDEX consisting entirely of NOT NULL - columns, MySQL will treat it as a PRIMARY KEY unless the - table already has one. */ + columns and if the index does not contain column prefix(es) + (only prefix/part of the column is indexed), MySQL will treat the + index as a PRIMARY KEY unless the table already has one. */ if (!new_primary && (key_info->flags & HA_NOSAME) + && (!(key_info->flags & HA_KEY_HAS_PART_KEY_SEG)) && row_table_got_default_clust_index(table)) { - uint key_part = key_info->key_parts; + uint key_part = key_info->key_parts; new_primary = TRUE; @@ -656,12 +664,18 @@ ha_innobase::add_index( innodb_table = indexed_table = dict_table_get(prebuilt->table->name, FALSE); + if (UNIV_UNLIKELY(!innodb_table)) { + error = HA_ERR_NO_SUCH_TABLE; + goto err_exit; + } + /* Check if the index name is reserved. */ if (innobase_index_name_is_reserved(trx, key_info, num_of_keys)) { error = -1; } else { /* Check that index keys are sensible */ - error = innobase_check_index_keys(key_info, num_of_keys); + error = innobase_check_index_keys(key_info, num_of_keys, + innodb_table); } if (UNIV_UNLIKELY(error)) { @@ -708,6 +722,8 @@ err_exit: row_mysql_lock_data_dictionary(trx); dict_locked = TRUE; + ut_d(dict_table_check_for_dup_indexes(innodb_table, FALSE)); + /* If a new primary key is defined for the table we need to drop the original table and rebuild all indexes. */ @@ -740,6 +756,8 @@ err_exit: user_thd); } + ut_d(dict_table_check_for_dup_indexes(innodb_table, + FALSE)); row_mysql_unlock_data_dictionary(trx); goto err_exit; } @@ -764,6 +782,10 @@ err_exit: ut_ad(error == DB_SUCCESS); + /* We will need to rebuild index translation table. Set + valid index entry count in the translation table to zero */ + share->idx_trans_tbl.index_count = 0; + /* Commit the data dictionary transaction in order to release the table locks on the system tables. This means that if MySQL crashes while creating a new primary key inside @@ -799,18 +821,6 @@ err_exit: index, num_of_idx, table); error_handling: -#ifdef UNIV_DEBUG - /* TODO: At the moment we can't handle the following statement - in our debugging code below: - - alter table t drop index b, add index (b); - - The fix will have to parse the SQL and note that the index - being added has the same name as the one being dropped and - ignore that in the dup index check.*/ - //dict_table_check_for_dup_indexes(prebuilt->table); -#endif - /* After an error, remove all those index definitions from the dictionary which were defined. */ @@ -822,6 +832,8 @@ error_handling: row_mysql_lock_data_dictionary(trx); dict_locked = TRUE; + ut_d(dict_table_check_for_dup_indexes(prebuilt->table, TRUE)); + if (!new_primary) { error = row_merge_rename_indexes(trx, indexed_table); @@ -909,6 +921,7 @@ convert_error: } if (dict_locked) { + ut_d(dict_table_check_for_dup_indexes(innodb_table, FALSE)); row_mysql_unlock_data_dictionary(trx); } @@ -951,6 +964,7 @@ ha_innobase::prepare_drop_index( /* Test and mark all the indexes to be dropped */ row_mysql_lock_data_dictionary(trx); + ut_d(dict_table_check_for_dup_indexes(prebuilt->table, FALSE)); /* Check that none of the indexes have previously been flagged for deletion. */ @@ -1116,6 +1130,7 @@ func_exit: } while (index); } + ut_d(dict_table_check_for_dup_indexes(prebuilt->table, FALSE)); row_mysql_unlock_data_dictionary(trx); DBUG_RETURN(err); @@ -1162,6 +1177,7 @@ ha_innobase::final_drop_index( prebuilt->table->flags, user_thd); row_mysql_lock_data_dictionary(trx); + ut_d(dict_table_check_for_dup_indexes(prebuilt->table, FALSE)); if (UNIV_UNLIKELY(err)) { @@ -1198,11 +1214,12 @@ ha_innobase::final_drop_index( ut_a(!index->to_be_dropped); } -#ifdef UNIV_DEBUG - dict_table_check_for_dup_indexes(prebuilt->table); -#endif + /* We will need to rebuild index translation table. Set + valid index entry count in the translation table to zero */ + share->idx_trans_tbl.index_count = 0; func_exit: + ut_d(dict_table_check_for_dup_indexes(prebuilt->table, FALSE)); trx_commit_for_mysql(trx); trx_commit_for_mysql(prebuilt->trx); row_mysql_unlock_data_dictionary(trx); diff --git a/storage/innodb_plugin/handler/i_s.cc b/storage/innodb_plugin/handler/i_s.cc index 6ae1d09a7d2..524fe696de2 100644 --- a/storage/innodb_plugin/handler/i_s.cc +++ b/storage/innodb_plugin/handler/i_s.cc @@ -455,59 +455,6 @@ UNIV_INTERN struct st_mysql_plugin i_s_innodb_trx = STRUCT_FLD(__reserved1, NULL) }; -UNIV_INTERN struct st_maria_plugin i_s_innodb_trx_maria = -{ - /* the plugin type (a MYSQL_XXX_PLUGIN value) */ - /* int */ - STRUCT_FLD(type, MYSQL_INFORMATION_SCHEMA_PLUGIN), - - /* pointer to type-specific plugin descriptor */ - /* void* */ - STRUCT_FLD(info, &i_s_info), - - /* plugin name */ - /* const char* */ - STRUCT_FLD(name, "INNODB_TRX"), - - /* plugin author (for SHOW PLUGINS) */ - /* const char* */ - STRUCT_FLD(author, plugin_author), - - /* general descriptive text (for SHOW PLUGINS) */ - /* const char* */ - STRUCT_FLD(descr, "InnoDB transactions"), - - /* the plugin license (PLUGIN_LICENSE_XXX) */ - /* int */ - STRUCT_FLD(license, PLUGIN_LICENSE_GPL), - - /* the function to invoke when plugin is loaded */ - /* int (*)(void*); */ - STRUCT_FLD(init, innodb_trx_init), - - /* the function to invoke when plugin is unloaded */ - /* int (*)(void*); */ - STRUCT_FLD(deinit, i_s_common_deinit), - - /* plugin version (for SHOW PLUGINS) */ - /* unsigned int */ - STRUCT_FLD(version, INNODB_VERSION_SHORT), - - /* struct st_mysql_show_var* */ - STRUCT_FLD(status_vars, NULL), - - /* struct st_mysql_sys_var** */ - STRUCT_FLD(system_vars, NULL), - - /* string version */ - /* const char * */ - STRUCT_FLD(version_info, "1.0"), - - /* Maturity */ - /* int */ - STRUCT_FLD(maturity, MariaDB_PLUGIN_MATURITY_STABLE) -}; - /* Fields of the dynamic table INFORMATION_SCHEMA.innodb_locks */ static ST_FIELD_INFO innodb_locks_fields_info[] = { @@ -783,59 +730,6 @@ UNIV_INTERN struct st_mysql_plugin i_s_innodb_locks = STRUCT_FLD(__reserved1, NULL) }; -UNIV_INTERN struct st_maria_plugin i_s_innodb_locks_maria = -{ - /* the plugin type (a MYSQL_XXX_PLUGIN value) */ - /* int */ - STRUCT_FLD(type, MYSQL_INFORMATION_SCHEMA_PLUGIN), - - /* pointer to type-specific plugin descriptor */ - /* void* */ - STRUCT_FLD(info, &i_s_info), - - /* plugin name */ - /* const char* */ - STRUCT_FLD(name, "INNODB_LOCKS"), - - /* plugin author (for SHOW PLUGINS) */ - /* const char* */ - STRUCT_FLD(author, plugin_author), - - /* general descriptive text (for SHOW PLUGINS) */ - /* const char* */ - STRUCT_FLD(descr, "InnoDB conflicting locks"), - - /* the plugin license (PLUGIN_LICENSE_XXX) */ - /* int */ - STRUCT_FLD(license, PLUGIN_LICENSE_GPL), - - /* the function to invoke when plugin is loaded */ - /* int (*)(void*); */ - STRUCT_FLD(init, innodb_locks_init), - - /* the function to invoke when plugin is unloaded */ - /* int (*)(void*); */ - STRUCT_FLD(deinit, i_s_common_deinit), - - /* plugin version (for SHOW PLUGINS) */ - /* unsigned int */ - STRUCT_FLD(version, INNODB_VERSION_SHORT), - - /* struct st_mysql_show_var* */ - STRUCT_FLD(status_vars, NULL), - - /* struct st_mysql_sys_var** */ - STRUCT_FLD(system_vars, NULL), - - /* string version */ - /* const char * */ - STRUCT_FLD(version_info, "1.0"), - - /* Maturity */ - /* int */ - STRUCT_FLD(maturity, MariaDB_PLUGIN_MATURITY_STABLE) -}; - /* Fields of the dynamic table INFORMATION_SCHEMA.innodb_lock_waits */ static ST_FIELD_INFO innodb_lock_waits_fields_info[] = { @@ -1019,59 +913,6 @@ UNIV_INTERN struct st_mysql_plugin i_s_innodb_lock_waits = STRUCT_FLD(__reserved1, NULL) }; -UNIV_INTERN struct st_maria_plugin i_s_innodb_lock_waits_maria = -{ - /* the plugin type (a MYSQL_XXX_PLUGIN value) */ - /* int */ - STRUCT_FLD(type, MYSQL_INFORMATION_SCHEMA_PLUGIN), - - /* pointer to type-specific plugin descriptor */ - /* void* */ - STRUCT_FLD(info, &i_s_info), - - /* plugin name */ - /* const char* */ - STRUCT_FLD(name, "INNODB_LOCK_WAITS"), - - /* plugin author (for SHOW PLUGINS) */ - /* const char* */ - STRUCT_FLD(author, "Innobase Oy"), - - /* general descriptive text (for SHOW PLUGINS) */ - /* const char* */ - STRUCT_FLD(descr, "InnoDB which lock is blocking which"), - - /* the plugin license (PLUGIN_LICENSE_XXX) */ - /* int */ - STRUCT_FLD(license, PLUGIN_LICENSE_GPL), - - /* the function to invoke when plugin is loaded */ - /* int (*)(void*); */ - STRUCT_FLD(init, innodb_lock_waits_init), - - /* the function to invoke when plugin is unloaded */ - /* int (*)(void*); */ - STRUCT_FLD(deinit, i_s_common_deinit), - - /* plugin version (for SHOW PLUGINS) */ - /* unsigned int */ - STRUCT_FLD(version, INNODB_VERSION_SHORT), - - /* struct st_mysql_show_var* */ - STRUCT_FLD(status_vars, NULL), - - /* struct st_mysql_sys_var** */ - STRUCT_FLD(system_vars, NULL), - - /* string version */ - /* const char * */ - STRUCT_FLD(version_info, "1.0"), - - /* Maturity */ - /* int */ - STRUCT_FLD(maturity, MariaDB_PLUGIN_MATURITY_STABLE) -}; - /*******************************************************************//** Common function to fill any of the dynamic tables: INFORMATION_SCHEMA.innodb_trx @@ -1404,59 +1245,6 @@ UNIV_INTERN struct st_mysql_plugin i_s_innodb_cmp = STRUCT_FLD(__reserved1, NULL) }; -UNIV_INTERN struct st_mysql_plugin i_s_innodb_cmp_maria = -{ - /* the plugin type (a MYSQL_XXX_PLUGIN value) */ - /* int */ - STRUCT_FLD(type, MYSQL_INFORMATION_SCHEMA_PLUGIN), - - /* pointer to type-specific plugin descriptor */ - /* void* */ - STRUCT_FLD(info, &i_s_info), - - /* plugin name */ - /* const char* */ - STRUCT_FLD(name, "INNODB_CMP"), - - /* plugin author (for SHOW PLUGINS) */ - /* const char* */ - STRUCT_FLD(author, plugin_author), - - /* general descriptive text (for SHOW PLUGINS) */ - /* const char* */ - STRUCT_FLD(descr, "Statistics for the InnoDB compression"), - - /* the plugin license (PLUGIN_LICENSE_XXX) */ - /* int */ - STRUCT_FLD(license, PLUGIN_LICENSE_GPL), - - /* the function to invoke when plugin is loaded */ - /* int (*)(void*); */ - STRUCT_FLD(init, i_s_cmp_init), - - /* the function to invoke when plugin is unloaded */ - /* int (*)(void*); */ - STRUCT_FLD(deinit, i_s_common_deinit), - - /* plugin version (for SHOW PLUGINS) */ - /* unsigned int */ - STRUCT_FLD(version, INNODB_VERSION_SHORT), - - /* struct st_mysql_show_var* */ - STRUCT_FLD(status_vars, NULL), - - /* struct st_mysql_sys_var** */ - STRUCT_FLD(system_vars, NULL), - - /* string version */ - /* const char * */ - STRUCT_FLD(version_info, "1.0"), - - /* Maturity */ - /* int */ - STRUCT_FLD(maturity, MariaDB_PLUGIN_MATURITY_STABLE) -}; - UNIV_INTERN struct st_mysql_plugin i_s_innodb_cmp_reset = { /* the plugin type (a MYSQL_XXX_PLUGIN value) */ @@ -1507,60 +1295,6 @@ UNIV_INTERN struct st_mysql_plugin i_s_innodb_cmp_reset = STRUCT_FLD(__reserved1, NULL) }; -UNIV_INTERN struct st_maria_plugin i_s_innodb_cmp_reset_maria = -{ - /* the plugin type (a MYSQL_XXX_PLUGIN value) */ - /* int */ - STRUCT_FLD(type, MYSQL_INFORMATION_SCHEMA_PLUGIN), - - /* pointer to type-specific plugin descriptor */ - /* void* */ - STRUCT_FLD(info, &i_s_info), - - /* plugin name */ - /* const char* */ - STRUCT_FLD(name, "INNODB_CMP_RESET"), - - /* plugin author (for SHOW PLUGINS) */ - /* const char* */ - STRUCT_FLD(author, plugin_author), - - /* general descriptive text (for SHOW PLUGINS) */ - /* const char* */ - STRUCT_FLD(descr, "Statistics for the InnoDB compression;" - " reset cumulated counts"), - - /* the plugin license (PLUGIN_LICENSE_XXX) */ - /* int */ - STRUCT_FLD(license, PLUGIN_LICENSE_GPL), - - /* the function to invoke when plugin is loaded */ - /* int (*)(void*); */ - STRUCT_FLD(init, i_s_cmp_reset_init), - - /* the function to invoke when plugin is unloaded */ - /* int (*)(void*); */ - STRUCT_FLD(deinit, i_s_common_deinit), - - /* plugin version (for SHOW PLUGINS) */ - /* unsigned int */ - STRUCT_FLD(version, INNODB_VERSION_SHORT), - - /* struct st_mysql_show_var* */ - STRUCT_FLD(status_vars, NULL), - - /* struct st_mysql_sys_var** */ - STRUCT_FLD(system_vars, NULL), - - /* string version */ - /* const char * */ - STRUCT_FLD(version_info, "1.0"), - - /* Maturity */ - /* int */ - STRUCT_FLD(maturity, MariaDB_PLUGIN_MATURITY_STABLE) -}; - /* Fields of the dynamic table information_schema.innodb_cmpmem. */ static ST_FIELD_INFO i_s_cmpmem_fields_info[] = { @@ -1777,59 +1511,6 @@ UNIV_INTERN struct st_mysql_plugin i_s_innodb_cmpmem = STRUCT_FLD(__reserved1, NULL) }; -UNIV_INTERN struct st_maria_plugin i_s_innodb_cmpmem_maria = -{ - /* the plugin type (a MYSQL_XXX_PLUGIN value) */ - /* int */ - STRUCT_FLD(type, MYSQL_INFORMATION_SCHEMA_PLUGIN), - - /* pointer to type-specific plugin descriptor */ - /* void* */ - STRUCT_FLD(info, &i_s_info), - - /* plugin name */ - /* const char* */ - STRUCT_FLD(name, "INNODB_CMPMEM"), - - /* plugin author (for SHOW PLUGINS) */ - /* const char* */ - STRUCT_FLD(author, plugin_author), - - /* general descriptive text (for SHOW PLUGINS) */ - /* const char* */ - STRUCT_FLD(descr, "Statistics for the InnoDB compressed buffer pool"), - - /* the plugin license (PLUGIN_LICENSE_XXX) */ - /* int */ - STRUCT_FLD(license, PLUGIN_LICENSE_GPL), - - /* the function to invoke when plugin is loaded */ - /* int (*)(void*); */ - STRUCT_FLD(init, i_s_cmpmem_init), - - /* the function to invoke when plugin is unloaded */ - /* int (*)(void*); */ - STRUCT_FLD(deinit, i_s_common_deinit), - - /* plugin version (for SHOW PLUGINS) */ - /* unsigned int */ - STRUCT_FLD(version, INNODB_VERSION_SHORT), - - /* struct st_mysql_show_var* */ - STRUCT_FLD(status_vars, NULL), - - /* struct st_mysql_sys_var** */ - STRUCT_FLD(system_vars, NULL), - - /* string version */ - /* const char * */ - STRUCT_FLD(version_info, "1.0"), - - /* Maturity */ - /* int */ - STRUCT_FLD(maturity, MariaDB_PLUGIN_MATURITY_STABLE) -}; - UNIV_INTERN struct st_mysql_plugin i_s_innodb_cmpmem_reset = { /* the plugin type (a MYSQL_XXX_PLUGIN value) */ @@ -1880,60 +1561,6 @@ UNIV_INTERN struct st_mysql_plugin i_s_innodb_cmpmem_reset = STRUCT_FLD(__reserved1, NULL) }; -UNIV_INTERN struct st_maria_plugin i_s_innodb_cmpmem_reset_maria = -{ - /* the plugin type (a MYSQL_XXX_PLUGIN value) */ - /* int */ - STRUCT_FLD(type, MYSQL_INFORMATION_SCHEMA_PLUGIN), - - /* pointer to type-specific plugin descriptor */ - /* void* */ - STRUCT_FLD(info, &i_s_info), - - /* plugin name */ - /* const char* */ - STRUCT_FLD(name, "INNODB_CMPMEM_RESET"), - - /* plugin author (for SHOW PLUGINS) */ - /* const char* */ - STRUCT_FLD(author, plugin_author), - - /* general descriptive text (for SHOW PLUGINS) */ - /* const char* */ - STRUCT_FLD(descr, "Statistics for the InnoDB compressed buffer pool;" - " reset cumulated counts"), - - /* the plugin license (PLUGIN_LICENSE_XXX) */ - /* int */ - STRUCT_FLD(license, PLUGIN_LICENSE_GPL), - - /* the function to invoke when plugin is loaded */ - /* int (*)(void*); */ - STRUCT_FLD(init, i_s_cmpmem_reset_init), - - /* the function to invoke when plugin is unloaded */ - /* int (*)(void*); */ - STRUCT_FLD(deinit, i_s_common_deinit), - - /* plugin version (for SHOW PLUGINS) */ - /* unsigned int */ - STRUCT_FLD(version, INNODB_VERSION_SHORT), - - /* struct st_mysql_show_var* */ - STRUCT_FLD(status_vars, NULL), - - /* struct st_mysql_sys_var** */ - STRUCT_FLD(system_vars, NULL), - - /* string version */ - /* const char * */ - STRUCT_FLD(version_info, "1.0"), - - /* Maturity */ - /* int */ - STRUCT_FLD(maturity, MariaDB_PLUGIN_MATURITY_STABLE) -}; - /*******************************************************************//** Unbind a dynamic INFORMATION_SCHEMA table. @return 0 on success */ diff --git a/storage/innodb_plugin/ibuf/ibuf0ibuf.c b/storage/innodb_plugin/ibuf/ibuf0ibuf.c index 08986fac0ef..5e9b4b27611 100644 --- a/storage/innodb_plugin/ibuf/ibuf0ibuf.c +++ b/storage/innodb_plugin/ibuf/ibuf0ibuf.c @@ -730,24 +730,41 @@ page containing the descriptor bits for the file page; the bitmap page is x-latched */ static page_t* -ibuf_bitmap_get_map_page( -/*=====================*/ - ulint space, /*!< in: space id of the file page */ - ulint page_no,/*!< in: page number of the file page */ - ulint zip_size,/*!< in: compressed page size in bytes; - 0 for uncompressed pages */ - mtr_t* mtr) /*!< in: mtr */ +ibuf_bitmap_get_map_page_func( +/*==========================*/ + ulint space, /*!< in: space id of the file page */ + ulint page_no,/*!< in: page number of the file page */ + ulint zip_size,/*!< in: compressed page size in bytes; + 0 for uncompressed pages */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ + mtr_t* mtr) /*!< in: mtr */ { buf_block_t* block; - block = buf_page_get(space, zip_size, - ibuf_bitmap_page_no_calc(zip_size, page_no), - RW_X_LATCH, mtr); + block = buf_page_get_gen(space, zip_size, + ibuf_bitmap_page_no_calc(zip_size, page_no), + RW_X_LATCH, NULL, BUF_GET, + file, line, mtr); buf_block_dbg_add_level(block, SYNC_IBUF_BITMAP); return(buf_block_get_frame(block)); } +/********************************************************************//** +Gets the ibuf bitmap page where the bits describing a given file page are +stored. +@return bitmap page where the file page is mapped, that is, the bitmap +page containing the descriptor bits for the file page; the bitmap page +is x-latched +@param space in: space id of the file page +@param page_no in: page number of the file page +@param zip_size in: compressed page size in bytes; 0 for uncompressed pages +@param mtr in: mini-transaction */ +#define ibuf_bitmap_get_map_page(space, page_no, zip_size, mtr) \ + ibuf_bitmap_get_map_page_func(space, page_no, zip_size, \ + __FILE__, __LINE__, mtr) + /************************************************************************//** Sets the free bits of the page in the ibuf bitmap. This is done in a separate mini-transaction, hence this operation does not restrict further work to only diff --git a/storage/innodb_plugin/include/btr0btr.h b/storage/innodb_plugin/include/btr0btr.h index d5c8258513c..5e6a76c7d21 100644 --- a/storage/innodb_plugin/include/btr0btr.h +++ b/storage/innodb_plugin/include/btr0btr.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1994, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1994, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -193,6 +193,10 @@ btr_leaf_page_release( mtr_t* mtr); /*!< in: mtr */ /**************************************************************//** Gets the child node file address in a node pointer. +NOTE: the offsets array must contain all offsets for the record since +we read the last field according to offsets and assume that it contains +the child page number. In other words offsets must have been retrieved +with rec_get_offsets(n_fields=ULINT_UNDEFINED). @return child node address */ UNIV_INLINE ulint @@ -317,12 +321,16 @@ Inserts a data tuple to a tree on a non-leaf level. It is assumed that mtr holds an x-latch on the tree. */ UNIV_INTERN void -btr_insert_on_non_leaf_level( -/*=========================*/ +btr_insert_on_non_leaf_level_func( +/*==============================*/ dict_index_t* index, /*!< in: index */ ulint level, /*!< in: level, must be > 0 */ dtuple_t* tuple, /*!< in: the record to be inserted */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr); /*!< in: mtr */ +# define btr_insert_on_non_leaf_level(i,l,t,m) \ + btr_insert_on_non_leaf_level_func(i,l,t,__FILE__,__LINE__,m) #endif /* !UNIV_HOTBACKUP */ /****************************************************************//** Sets a record as the predefined minimum record. */ diff --git a/storage/innodb_plugin/include/btr0btr.ic b/storage/innodb_plugin/include/btr0btr.ic index 2259d22c9a6..97944cc2e26 100644 --- a/storage/innodb_plugin/include/btr0btr.ic +++ b/storage/innodb_plugin/include/btr0btr.ic @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1994, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1994, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -255,6 +255,10 @@ btr_page_set_prev( /**************************************************************//** Gets the child node file address in a node pointer. +NOTE: the offsets array must contain all offsets for the record since +we read the last field according to offsets and assume that it contains +the child page number. In other words offsets must have been retrieved +with rec_get_offsets(n_fields=ULINT_UNDEFINED). @return child node address */ UNIV_INLINE ulint diff --git a/storage/innodb_plugin/include/btr0cur.h b/storage/innodb_plugin/include/btr0cur.h index 480a3877e54..716f15c4267 100644 --- a/storage/innodb_plugin/include/btr0cur.h +++ b/storage/innodb_plugin/include/btr0cur.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1994, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1994, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -152,29 +152,39 @@ btr_cur_search_to_nth_level( ulint has_search_latch,/*!< in: latch mode the caller currently has on btr_search_latch: RW_S_LATCH, or 0 */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr); /*!< in: mtr */ /*****************************************************************//** Opens a cursor at either end of an index. */ UNIV_INTERN void -btr_cur_open_at_index_side( -/*=======================*/ +btr_cur_open_at_index_side_func( +/*============================*/ ibool from_left, /*!< in: TRUE if open to the low end, FALSE if to the high end */ dict_index_t* index, /*!< in: index */ ulint latch_mode, /*!< in: latch mode */ btr_cur_t* cursor, /*!< in: cursor */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr); /*!< in: mtr */ +#define btr_cur_open_at_index_side(f,i,l,c,m) \ + btr_cur_open_at_index_side_func(f,i,l,c,__FILE__,__LINE__,m) /**********************************************************************//** Positions a cursor at a randomly chosen position within a B-tree. */ UNIV_INTERN void -btr_cur_open_at_rnd_pos( -/*====================*/ +btr_cur_open_at_rnd_pos_func( +/*=========================*/ dict_index_t* index, /*!< in: index */ ulint latch_mode, /*!< in: BTR_SEARCH_LEAF, ... */ btr_cur_t* cursor, /*!< in/out: B-tree cursor */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr); /*!< in: mtr */ +#define btr_cur_open_at_rnd_pos(i,l,c,m) \ + btr_cur_open_at_rnd_pos_func(i,l,c,__FILE__,__LINE__,m) /*************************************************************//** Tries to perform an insert to a page in an index tree, next to cursor. It is assumed that mtr holds an x-latch on the page. The operation does diff --git a/storage/innodb_plugin/include/btr0pcur.h b/storage/innodb_plugin/include/btr0pcur.h index 12b1375d8b7..2334a266280 100644 --- a/storage/innodb_plugin/include/btr0pcur.h +++ b/storage/innodb_plugin/include/btr0pcur.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -82,8 +82,8 @@ Initializes and opens a persistent cursor to an index tree. It should be closed with btr_pcur_close. */ UNIV_INLINE void -btr_pcur_open( -/*==========*/ +btr_pcur_open_func( +/*===============*/ dict_index_t* index, /*!< in: index */ const dtuple_t* tuple, /*!< in: tuple on which search done */ ulint mode, /*!< in: PAGE_CUR_L, ...; @@ -94,14 +94,18 @@ btr_pcur_open( record! */ ulint latch_mode,/*!< in: BTR_SEARCH_LEAF, ... */ btr_pcur_t* cursor, /*!< in: memory buffer for persistent cursor */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr); /*!< in: mtr */ +#define btr_pcur_open(i,t,md,l,c,m) \ + btr_pcur_open_func(i,t,md,l,c,__FILE__,__LINE__,m) /**************************************************************//** Opens an persistent cursor to an index tree without initializing the cursor. */ UNIV_INLINE void -btr_pcur_open_with_no_init( -/*=======================*/ +btr_pcur_open_with_no_init_func( +/*============================*/ dict_index_t* index, /*!< in: index */ const dtuple_t* tuple, /*!< in: tuple on which search done */ ulint mode, /*!< in: PAGE_CUR_L, ...; @@ -119,7 +123,12 @@ btr_pcur_open_with_no_init( ulint has_search_latch,/*!< in: latch mode the caller currently has on btr_search_latch: RW_S_LATCH, or 0 */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr); /*!< in: mtr */ +#define btr_pcur_open_with_no_init(ix,t,md,l,cur,has,m) \ + btr_pcur_open_with_no_init_func(ix,t,md,l,cur,has,__FILE__,__LINE__,m) + /*****************************************************************//** Opens a persistent cursor at either end of an index. */ UNIV_INLINE @@ -160,8 +169,8 @@ before first in tree. The latching mode must be BTR_SEARCH_LEAF or BTR_MODIFY_LEAF. */ UNIV_INTERN void -btr_pcur_open_on_user_rec( -/*======================*/ +btr_pcur_open_on_user_rec_func( +/*===========================*/ dict_index_t* index, /*!< in: index */ const dtuple_t* tuple, /*!< in: tuple on which search done */ ulint mode, /*!< in: PAGE_CUR_L, ... */ @@ -169,17 +178,25 @@ btr_pcur_open_on_user_rec( BTR_MODIFY_LEAF */ btr_pcur_t* cursor, /*!< in: memory buffer for persistent cursor */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr); /*!< in: mtr */ +#define btr_pcur_open_on_user_rec(i,t,md,l,c,m) \ + btr_pcur_open_on_user_rec_func(i,t,md,l,c,__FILE__,__LINE__,m) /**********************************************************************//** Positions a cursor at a randomly chosen position within a B-tree. */ UNIV_INLINE void -btr_pcur_open_at_rnd_pos( -/*=====================*/ +btr_pcur_open_at_rnd_pos_func( +/*==========================*/ dict_index_t* index, /*!< in: index */ ulint latch_mode, /*!< in: BTR_SEARCH_LEAF, ... */ btr_pcur_t* cursor, /*!< in/out: B-tree pcur */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr); /*!< in: mtr */ +#define btr_pcur_open_at_rnd_pos(i,l,c,m) \ + btr_pcur_open_at_rnd_pos_func(i,l,c,__FILE__,__LINE__,m) /**************************************************************//** Frees the possible old_rec_buf buffer of a persistent cursor and sets the latch mode of the persistent cursor to BTR_NO_LATCHES. */ @@ -218,11 +235,15 @@ record and it can be restored on a user record whose ordering fields are identical to the ones of the original user record */ UNIV_INTERN ibool -btr_pcur_restore_position( -/*======================*/ +btr_pcur_restore_position_func( +/*===========================*/ ulint latch_mode, /*!< in: BTR_SEARCH_LEAF, ... */ btr_pcur_t* cursor, /*!< in: detached persistent cursor */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr); /*!< in: mtr */ +#define btr_pcur_restore_position(l,cur,mtr) \ + btr_pcur_restore_position_func(l,cur,__FILE__,__LINE__,mtr) /**************************************************************//** If the latch mode of the cursor is BTR_LEAF_SEARCH or BTR_LEAF_MODIFY, releases the page latch and bufferfix reserved by the cursor. @@ -260,20 +281,13 @@ btr_pcur_get_mtr( /*=============*/ btr_pcur_t* cursor); /*!< in: persistent cursor */ /**************************************************************//** -Commits the pcur mtr and sets the pcur latch mode to BTR_NO_LATCHES, +Commits the mtr and sets the pcur latch mode to BTR_NO_LATCHES, that is, the cursor becomes detached. If there have been modifications to the page where pcur is positioned, this can be used instead of btr_pcur_release_leaf. Function btr_pcur_store_position should be used before calling this, if restoration of cursor is wanted later. */ UNIV_INLINE void -btr_pcur_commit( -/*============*/ - btr_pcur_t* pcur); /*!< in: persistent cursor */ -/**************************************************************//** -Differs from btr_pcur_commit in that we can specify the mtr to commit. */ -UNIV_INLINE -void btr_pcur_commit_specify_mtr( /*========================*/ btr_pcur_t* pcur, /*!< in: persistent cursor */ diff --git a/storage/innodb_plugin/include/btr0pcur.ic b/storage/innodb_plugin/include/btr0pcur.ic index 0ca7223f861..0c38797e6c5 100644 --- a/storage/innodb_plugin/include/btr0pcur.ic +++ b/storage/innodb_plugin/include/btr0pcur.ic @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -395,30 +395,13 @@ btr_pcur_move_to_next( } /**************************************************************//** -Commits the pcur mtr and sets the pcur latch mode to BTR_NO_LATCHES, +Commits the mtr and sets the pcur latch mode to BTR_NO_LATCHES, that is, the cursor becomes detached. If there have been modifications to the page where pcur is positioned, this can be used instead of btr_pcur_release_leaf. Function btr_pcur_store_position should be used before calling this, if restoration of cursor is wanted later. */ UNIV_INLINE void -btr_pcur_commit( -/*============*/ - btr_pcur_t* pcur) /*!< in: persistent cursor */ -{ - ut_a(pcur->pos_state == BTR_PCUR_IS_POSITIONED); - - pcur->latch_mode = BTR_NO_LATCHES; - - mtr_commit(pcur->mtr); - - pcur->pos_state = BTR_PCUR_WAS_POSITIONED; -} - -/**************************************************************//** -Differs from btr_pcur_commit in that we can specify the mtr to commit. */ -UNIV_INLINE -void btr_pcur_commit_specify_mtr( /*========================*/ btr_pcur_t* pcur, /*!< in: persistent cursor */ @@ -483,8 +466,8 @@ Initializes and opens a persistent cursor to an index tree. It should be closed with btr_pcur_close. */ UNIV_INLINE void -btr_pcur_open( -/*==========*/ +btr_pcur_open_func( +/*===============*/ dict_index_t* index, /*!< in: index */ const dtuple_t* tuple, /*!< in: tuple on which search done */ ulint mode, /*!< in: PAGE_CUR_L, ...; @@ -495,6 +478,8 @@ btr_pcur_open( record! */ ulint latch_mode,/*!< in: BTR_SEARCH_LEAF, ... */ btr_pcur_t* cursor, /*!< in: memory buffer for persistent cursor */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr) /*!< in: mtr */ { btr_cur_t* btr_cursor; @@ -511,7 +496,7 @@ btr_pcur_open( btr_cursor = btr_pcur_get_btr_cur(cursor); btr_cur_search_to_nth_level(index, 0, tuple, mode, latch_mode, - btr_cursor, 0, mtr); + btr_cursor, 0, file, line, mtr); cursor->pos_state = BTR_PCUR_IS_POSITIONED; cursor->trx_if_known = NULL; @@ -522,8 +507,8 @@ Opens an persistent cursor to an index tree without initializing the cursor. */ UNIV_INLINE void -btr_pcur_open_with_no_init( -/*=======================*/ +btr_pcur_open_with_no_init_func( +/*============================*/ dict_index_t* index, /*!< in: index */ const dtuple_t* tuple, /*!< in: tuple on which search done */ ulint mode, /*!< in: PAGE_CUR_L, ...; @@ -541,6 +526,8 @@ btr_pcur_open_with_no_init( ulint has_search_latch,/*!< in: latch mode the caller currently has on btr_search_latch: RW_S_LATCH, or 0 */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr) /*!< in: mtr */ { btr_cur_t* btr_cursor; @@ -553,7 +540,8 @@ btr_pcur_open_with_no_init( btr_cursor = btr_pcur_get_btr_cur(cursor); btr_cur_search_to_nth_level(index, 0, tuple, mode, latch_mode, - btr_cursor, has_search_latch, mtr); + btr_cursor, has_search_latch, + file, line, mtr); cursor->pos_state = BTR_PCUR_IS_POSITIONED; cursor->old_stored = BTR_PCUR_OLD_NOT_STORED; @@ -600,11 +588,13 @@ btr_pcur_open_at_index_side( Positions a cursor at a randomly chosen position within a B-tree. */ UNIV_INLINE void -btr_pcur_open_at_rnd_pos( -/*=====================*/ +btr_pcur_open_at_rnd_pos_func( +/*==========================*/ dict_index_t* index, /*!< in: index */ ulint latch_mode, /*!< in: BTR_SEARCH_LEAF, ... */ btr_pcur_t* cursor, /*!< in/out: B-tree pcur */ + const char* file, /*!< in: file name */ + ulint line, /*!< in: line where called */ mtr_t* mtr) /*!< in: mtr */ { /* Initialize the cursor */ @@ -614,8 +604,9 @@ btr_pcur_open_at_rnd_pos( btr_pcur_init(cursor); - btr_cur_open_at_rnd_pos(index, latch_mode, - btr_pcur_get_btr_cur(cursor), mtr); + btr_cur_open_at_rnd_pos_func(index, latch_mode, + btr_pcur_get_btr_cur(cursor), + file, line, mtr); cursor->pos_state = BTR_PCUR_IS_POSITIONED; cursor->old_stored = BTR_PCUR_OLD_NOT_STORED; diff --git a/storage/innodb_plugin/include/buf0buf.h b/storage/innodb_plugin/include/buf0buf.h index 927ff893e39..cd4ee5906f0 100644 --- a/storage/innodb_plugin/include/buf0buf.h +++ b/storage/innodb_plugin/include/buf0buf.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -33,6 +33,7 @@ Created 11/5/1995 Heikki Tuuri #include "hash0hash.h" #include "ut0byte.h" #include "page0types.h" +#include "ut0rbt.h" #ifndef UNIV_HOTBACKUP #include "os0proc.h" @@ -202,20 +203,14 @@ with care. */ #define buf_page_get_with_no_latch(SP, ZS, OF, MTR) buf_page_get_gen(\ SP, ZS, OF, RW_NO_LATCH, NULL,\ BUF_GET_NO_LATCH, __FILE__, __LINE__, MTR) -/**************************************************************//** -NOTE! The following macros should be used instead of -buf_page_optimistic_get_func, to improve debugging. Only values RW_S_LATCH and -RW_X_LATCH are allowed as LA! */ -#define buf_page_optimistic_get(LA, BL, MC, MTR) \ - buf_page_optimistic_get_func(LA, BL, MC, __FILE__, __LINE__, MTR) /********************************************************************//** This is the general function used to get optimistic access to a database page. @return TRUE if success */ UNIV_INTERN ibool -buf_page_optimistic_get_func( -/*=========================*/ +buf_page_optimistic_get( +/*====================*/ ulint rw_latch,/*!< in: RW_S_LATCH, RW_X_LATCH */ buf_block_t* block, /*!< in: guessed block */ ib_uint64_t modify_clock,/*!< in: modify clock value if mode is @@ -1185,15 +1180,21 @@ struct buf_block_struct{ rw_lock_t lock; /*!< read-write lock of the buffer frame */ unsigned lock_hash_val:32;/*!< hashed value of the page address - in the record lock hash table */ - unsigned check_index_page_at_flush:1; + in the record lock hash table; + protected by buf_block_t::lock + (or buf_block_t::mutex, buf_pool_mutex + in buf_page_get_gen(), + buf_page_init_for_read() + and buf_page_create()) */ + ibool check_index_page_at_flush; /*!< TRUE if we know that this is an index page, and want the database to check its consistency before flush; note that there may be pages in the buffer pool which are index pages, but this flag is not set because - we do not keep track of all pages */ + we do not keep track of all pages; + NOT protected by any mutex */ /* @} */ /** @name Optimistic search field */ /* @{ */ @@ -1359,6 +1360,19 @@ struct buf_pool_struct{ /*!< this is in the set state when there is no flush batch of the given type running */ + ib_rbt_t* flush_rbt; /* !< a red-black tree is used + exclusively during recovery to + speed up insertions in the + flush_list. This tree contains + blocks in order of + oldest_modification LSN and is + kept in sync with the + flush_list. + Each member of the tree MUST + also be on the flush_list. + This tree is relevant only in + recovery and is set to NULL + once the recovery is over. */ ulint freed_page_clock;/*!< a sequence number used to count the number of buffer blocks removed from the end of diff --git a/storage/innodb_plugin/include/buf0buf.ic b/storage/innodb_plugin/include/buf0buf.ic index 0f92a59a1c7..378c3590181 100644 --- a/storage/innodb_plugin/include/buf0buf.ic +++ b/storage/innodb_plugin/include/buf0buf.ic @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. Copyright (c) 2008, Google Inc. Portions of this file contain modifications contributed and copyrighted by @@ -81,7 +81,7 @@ buf_page_peek_if_too_old( unsigned access_time = buf_page_is_accessed(bpage); if (access_time > 0 - && (ut_time_ms() - access_time) + && ((ib_uint32_t) (ut_time_ms() - access_time)) >= buf_LRU_old_threshold_ms) { return(TRUE); } @@ -705,6 +705,12 @@ buf_block_get_lock_hash_val( /*========================*/ const buf_block_t* block) /*!< in: block */ { + ut_ad(block); + ut_ad(buf_page_in_file(&block->page)); +#ifdef UNIV_SYNC_DEBUG + ut_ad(rw_lock_own(&(((buf_block_t*) block)->lock), RW_LOCK_EXCLUSIVE) + || rw_lock_own(&(((buf_block_t*) block)->lock), RW_LOCK_SHARED)); +#endif /* UNIV_SYNC_DEBUG */ return(block->lock_hash_val); } diff --git a/storage/innodb_plugin/include/buf0flu.h b/storage/innodb_plugin/include/buf0flu.h index 6c751852f54..c996f6eaab4 100644 --- a/storage/innodb_plugin/include/buf0flu.h +++ b/storage/innodb_plugin/include/buf0flu.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -40,6 +40,16 @@ buf_flush_remove( /*=============*/ buf_page_t* bpage); /*!< in: pointer to the block in question */ /********************************************************************//** +Relocates a buffer control block on the flush_list. +Note that it is assumed that the contents of bpage has already been +copied to dpage. */ +UNIV_INTERN +void +buf_flush_relocate_on_flush_list( +/*=============================*/ + buf_page_t* bpage, /*!< in/out: control block being moved */ + buf_page_t* dpage); /*!< in/out: destination block */ +/********************************************************************//** Updates the flush system data structures when a write is completed. */ UNIV_INTERN void @@ -139,8 +149,8 @@ how much redo the workload is generating and at what rate. */ struct buf_flush_stat_struct { - ib_uint64_t redo; /**< amount of redo generated. */ - ulint n_flushed; /**< number of pages flushed. */ + ib_uint64_t redo; /*!< amount of redo generated. */ + ulint n_flushed; /*!< number of pages flushed. */ }; /** Statistics for selecting flush rate of dirty pages. */ @@ -175,6 +185,22 @@ buf_flush_validate(void); /*====================*/ #endif /* UNIV_DEBUG || UNIV_BUF_DEBUG */ +/******************************************************************//** +Initialize the red-black tree to speed up insertions into the flush_list +during recovery process. Should be called at the start of recovery +process before any page has been read/written. */ +UNIV_INTERN +void +buf_flush_init_flush_rbt(void); +/*==========================*/ + +/******************************************************************//** +Frees up the red-black tree. */ +UNIV_INTERN +void +buf_flush_free_flush_rbt(void); +/*==========================*/ + /** When buf_flush_free_margin is called, it tries to make this many blocks available to replacement in the free list and at the end of the LRU list (to make sure that a read-ahead batch can be read efficiently in a single diff --git a/storage/innodb_plugin/include/data0type.ic b/storage/innodb_plugin/include/data0type.ic index 240b4288f39..2bf67a941bd 100644 --- a/storage/innodb_plugin/include/data0type.ic +++ b/storage/innodb_plugin/include/data0type.ic @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -285,6 +285,10 @@ dtype_new_store_for_order_and_null_size( #endif ulint len; + ut_ad(type); + ut_ad(type->mtype >= DATA_VARCHAR); + ut_ad(type->mtype <= DATA_MYSQL); + buf[0] = (byte)(type->mtype & 0xFFUL); if (type->prtype & DATA_BINARY_TYPE) { diff --git a/storage/innodb_plugin/include/dict0boot.h b/storage/innodb_plugin/include/dict0boot.h index 51d37ee98d1..1a13bd1503a 100644 --- a/storage/innodb_plugin/include/dict0boot.h +++ b/storage/innodb_plugin/include/dict0boot.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -137,6 +137,7 @@ clustered index */ #define DICT_SYS_INDEXES_PAGE_NO_FIELD 8 #define DICT_SYS_INDEXES_SPACE_NO_FIELD 7 #define DICT_SYS_INDEXES_TYPE_FIELD 6 +#define DICT_SYS_INDEXES_NAME_FIELD 4 /* When a row id which is zero modulo this number (which must be a power of two) is assigned, the field DICT_HDR_ROW_ID on the dictionary header page is diff --git a/storage/innodb_plugin/include/dict0dict.h b/storage/innodb_plugin/include/dict0dict.h index 12396556c2d..79dcbb30de2 100644 --- a/storage/innodb_plugin/include/dict0dict.h +++ b/storage/innodb_plugin/include/dict0dict.h @@ -928,9 +928,10 @@ UNIV_INTERN void dict_table_check_for_dup_indexes( /*=============================*/ - const dict_table_t* table); /*!< in: Check for dup indexes + const dict_table_t* table, /*!< in: Check for dup indexes in this table */ - + ibool tmp_ok);/*!< in: TRUE=allow temporary + index names */ #endif /* UNIV_DEBUG */ /**********************************************************************//** Builds a node pointer out of a physical record and a page number. @@ -1060,6 +1061,22 @@ UNIV_INTERN void dict_mutex_exit_for_mysql(void); /*===========================*/ +/**********************************************************************//** +Lock the appropriate mutex to protect index->stat_n_diff_key_vals[]. +index->id is used to pick the right mutex and it should not change +before dict_index_stat_mutex_exit() is called on this index. */ +UNIV_INTERN +void +dict_index_stat_mutex_enter( +/*========================*/ + const dict_index_t* index); /*!< in: index */ +/**********************************************************************//** +Unlock the appropriate mutex that protects index->stat_n_diff_key_vals[]. */ +UNIV_INTERN +void +dict_index_stat_mutex_exit( +/*=======================*/ + const dict_index_t* index); /*!< in: index */ /********************************************************************//** Checks if the database name in two table names is the same. @return TRUE if same db name */ diff --git a/storage/innodb_plugin/include/dict0mem.h b/storage/innodb_plugin/include/dict0mem.h index 2d001111938..9996fb59a75 100644 --- a/storage/innodb_plugin/include/dict0mem.h +++ b/storage/innodb_plugin/include/dict0mem.h @@ -80,21 +80,39 @@ combination of types */ /** File format */ /* @{ */ #define DICT_TF_FORMAT_SHIFT 5 /* file format */ -#define DICT_TF_FORMAT_MASK (127 << DICT_TF_FORMAT_SHIFT) +#define DICT_TF_FORMAT_MASK \ +((~(~0 << (DICT_TF_BITS - DICT_TF_FORMAT_SHIFT))) << DICT_TF_FORMAT_SHIFT) #define DICT_TF_FORMAT_51 0 /*!< InnoDB/MySQL up to 5.1 */ #define DICT_TF_FORMAT_ZIP 1 /*!< InnoDB plugin for 5.1: compressed tables, new BLOB treatment */ /** Maximum supported file format */ #define DICT_TF_FORMAT_MAX DICT_TF_FORMAT_ZIP - +/* @} */ #define DICT_TF_BITS 6 /*!< number of flag bits */ #if (1 << (DICT_TF_BITS - DICT_TF_FORMAT_SHIFT)) <= DICT_TF_FORMAT_MAX # error "DICT_TF_BITS is insufficient for DICT_TF_FORMAT_MAX" #endif /* @} */ + +/** @brief Additional table flags. + +These flags will be stored in SYS_TABLES.MIX_LEN. All unused flags +will be written as 0. The column may contain garbage for tables +created with old versions of InnoDB that only implemented +ROW_FORMAT=REDUNDANT. */ +/* @{ */ +#define DICT_TF2_SHIFT DICT_TF_BITS + /*!< Shift value for + table->flags. */ +#define DICT_TF2_TEMPORARY 1 /*!< TRUE for tables from + CREATE TEMPORARY TABLE. */ +#define DICT_TF2_BITS (DICT_TF2_SHIFT + 1) + /*!< Total number of bits + in table->flags. */ /* @} */ + /**********************************************************************//** Creates a table memory object. @return own: table object */ @@ -374,7 +392,7 @@ struct dict_table_struct{ unsigned space:32; /*!< space where the clustered index of the table is placed */ - unsigned flags:DICT_TF_BITS;/*!< DICT_TF_COMPACT, ... */ + unsigned flags:DICT_TF2_BITS;/*!< DICT_TF_COMPACT, ... */ unsigned ibd_file_missing:1; /*!< TRUE if this is in a single-table tablespace and the .ibd file is missing; then diff --git a/storage/innodb_plugin/include/fil0fil.h b/storage/innodb_plugin/include/fil0fil.h index 74d0fbcdacd..de8ef9e9687 100644 --- a/storage/innodb_plugin/include/fil0fil.h +++ b/storage/innodb_plugin/include/fil0fil.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -110,9 +110,10 @@ extern fil_addr_t fil_addr_null; contents of this field is valid for all uncompressed pages. */ #define FIL_PAGE_FILE_FLUSH_LSN 26 /*!< this is only defined for the - first page in a data file: the file - has been flushed to disk at least up - to this lsn */ + first page in a system tablespace + data file (ibdata*, not *.ibd): + the file has been flushed to disk + at least up to this lsn */ #define FIL_PAGE_ARCH_LOG_NO_OR_SPACE_ID 34 /*!< starting from 4.1.x this contains the space id of the page */ #define FIL_PAGE_DATA 38 /*!< start of the data on the page */ diff --git a/storage/innodb_plugin/include/hash0hash.h b/storage/innodb_plugin/include/hash0hash.h index 977cb829f35..b17c21a45ef 100644 --- a/storage/innodb_plugin/include/hash0hash.h +++ b/storage/innodb_plugin/include/hash0hash.h @@ -434,11 +434,12 @@ struct hash_table_struct { these heaps */ #endif /* !UNIV_HOTBACKUP */ mem_heap_t* heap; +#ifdef UNIV_DEBUG ulint magic_n; +# define HASH_TABLE_MAGIC_N 76561114 +#endif /* UNIV_DEBUG */ }; -#define HASH_TABLE_MAGIC_N 76561114 - #ifndef UNIV_NONINL #include "hash0hash.ic" #endif diff --git a/storage/innodb_plugin/include/hash0hash.ic b/storage/innodb_plugin/include/hash0hash.ic index 19da2d50701..0b437894e2e 100644 --- a/storage/innodb_plugin/include/hash0hash.ic +++ b/storage/innodb_plugin/include/hash0hash.ic @@ -35,6 +35,8 @@ hash_get_nth_cell( hash_table_t* table, /*!< in: hash table */ ulint n) /*!< in: cell index */ { + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); ut_ad(n < table->n_cells); return(table->array + n); @@ -48,6 +50,8 @@ hash_table_clear( /*=============*/ hash_table_t* table) /*!< in/out: hash table */ { + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); memset(table->array, 0x0, table->n_cells * sizeof(*table->array)); } @@ -61,6 +65,8 @@ hash_get_n_cells( /*=============*/ hash_table_t* table) /*!< in: table */ { + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); return(table->n_cells); } @@ -74,6 +80,8 @@ hash_calc_hash( ulint fold, /*!< in: folded value */ hash_table_t* table) /*!< in: hash table */ { + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); return(ut_hash_ulint(fold, table->n_cells)); } @@ -88,6 +96,8 @@ hash_get_mutex_no( hash_table_t* table, /*!< in: hash table */ ulint fold) /*!< in: fold */ { + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); ut_ad(ut_is_2pow(table->n_mutexes)); return(ut_2pow_remainder(hash_calc_hash(fold, table), table->n_mutexes)); @@ -103,6 +113,8 @@ hash_get_nth_heap( hash_table_t* table, /*!< in: hash table */ ulint i) /*!< in: index of the heap */ { + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); ut_ad(i < table->n_mutexes); return(table->heaps[i]); @@ -120,6 +132,9 @@ hash_get_heap( { ulint i; + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); + if (table->heap) { return(table->heap); } @@ -139,6 +154,8 @@ hash_get_nth_mutex( hash_table_t* table, /*!< in: hash table */ ulint i) /*!< in: index of the mutex */ { + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); ut_ad(i < table->n_mutexes); return(table->mutexes + i); @@ -156,6 +173,9 @@ hash_get_mutex( { ulint i; + ut_ad(table); + ut_ad(table->magic_n == HASH_TABLE_MAGIC_N); + i = hash_get_mutex_no(table, fold); return(hash_get_nth_mutex(table, i)); diff --git a/storage/innodb_plugin/include/lock0lock.h b/storage/innodb_plugin/include/lock0lock.h index 82e4c9bd976..7d76cbe3c75 100644 --- a/storage/innodb_plugin/include/lock0lock.h +++ b/storage/innodb_plugin/include/lock0lock.h @@ -613,13 +613,16 @@ lock_rec_print( FILE* file, /*!< in: file where to print */ const lock_t* lock); /*!< in: record type lock */ /*********************************************************************//** -Prints info of locks for all transactions. */ +Prints info of locks for all transactions. +@return FALSE if not able to obtain kernel mutex +and exits without printing info */ UNIV_INTERN -void +ibool lock_print_info_summary( /*====================*/ - FILE* file); /*!< in: file where to print */ -/*********************************************************************//** + FILE* file, /*!< in: file where to print */ + ibool nowait);/*!< in: whether to wait for the kernel mutex */ +/************************************************************************* Prints info of locks for each transaction. */ UNIV_INTERN void diff --git a/storage/innodb_plugin/include/log0log.h b/storage/innodb_plugin/include/log0log.h index 135aeb69e2d..8fce4ef96bc 100644 --- a/storage/innodb_plugin/include/log0log.h +++ b/storage/innodb_plugin/include/log0log.h @@ -1,23 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. - -This program is free software; you can redistribute it and/or modify it under -the terms of the GNU General Public License as published by the Free Software -Foundation; version 2 of the License. - -This program is distributed in the hope that it will be useful, but WITHOUT -ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS -FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. - -You should have received a copy of the GNU General Public License along with -this program; if not, write to the Free Software Foundation, Inc., 59 Temple -Place, Suite 330, Boston, MA 02111-1307 USA - -*****************************************************************************/ -/***************************************************************************** - -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. Copyright (c) 2009, Google Inc. Portions of this file contain modifications contributed and copyrighted by @@ -825,7 +808,17 @@ struct log_struct{ written to some log group; for this to be advanced, it is enough that the write i/o has been completed for all - log groups */ + log groups. + Note that since InnoDB currently + has only one log group therefore + this value is redundant. Also it + is possible that this value + falls behind the + flushed_to_disk_lsn transiently. + It is appropriate to use either + flushed_to_disk_lsn or + write_lsn which are always + up-to-date and accurate. */ ib_uint64_t write_lsn; /*!< end lsn for the current running write */ ulint write_end_offset;/*!< the data in buffer has diff --git a/storage/innodb_plugin/include/log0log.ic b/storage/innodb_plugin/include/log0log.ic index 36d151a3064..139f4041a36 100644 --- a/storage/innodb_plugin/include/log0log.ic +++ b/storage/innodb_plugin/include/log0log.ic @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -314,12 +314,15 @@ log_reserve_and_write_fast( ulint data_len; #ifdef UNIV_LOG_LSN_DEBUG /* length of the LSN pseudo-record */ - ulint lsn_len = 1 - + mach_get_compressed_size(log_sys->lsn >> 32) - + mach_get_compressed_size(log_sys->lsn & 0xFFFFFFFFUL); + ulint lsn_len; #endif /* UNIV_LOG_LSN_DEBUG */ mutex_enter(&log_sys->mutex); +#ifdef UNIV_LOG_LSN_DEBUG + lsn_len = 1 + + mach_get_compressed_size(log_sys->lsn >> 32) + + mach_get_compressed_size(log_sys->lsn & 0xFFFFFFFFUL); +#endif /* UNIV_LOG_LSN_DEBUG */ data_len = len #ifdef UNIV_LOG_LSN_DEBUG diff --git a/storage/innodb_plugin/include/log0recv.h b/storage/innodb_plugin/include/log0recv.h index a3d2bd050f5..9f334a34b44 100644 --- a/storage/innodb_plugin/include/log0recv.h +++ b/storage/innodb_plugin/include/log0recv.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1997, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1997, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -176,6 +176,12 @@ UNIV_INTERN void recv_recovery_from_checkpoint_finish(void); /*======================================*/ +/********************************************************//** +Initiates the rollback of active transactions. */ +UNIV_INTERN +void +recv_recovery_rollback_active(void); +/*===============================*/ /*******************************************************//** Scans log from a buffer and stores new log data to the parsing buffer. Parses and hashes the log records if new data found. Unless @@ -258,12 +264,14 @@ void recv_sys_init( /*==========*/ ulint available_memory); /*!< in: available memory in bytes */ +#ifndef UNIV_HOTBACKUP /********************************************************//** Reset the state of the recovery system variables. */ UNIV_INTERN void recv_sys_var_init(void); /*===================*/ +#endif /* !UNIV_HOTBACKUP */ /*******************************************************************//** Empties the hash table of stored log records, applying them to appropriate pages. */ @@ -360,8 +368,8 @@ typedef struct recv_addr_struct recv_addr_t; struct recv_addr_struct{ enum recv_addr_state state; /*!< recovery state of the page */ - ulint space; /*!< space id */ - ulint page_no;/*!< page number */ + unsigned space:32;/*!< space id */ + unsigned page_no:32;/*!< page number */ UT_LIST_BASE_NODE_T(recv_t) rec_list;/*!< list of log records for this page */ hash_node_t addr_hash;/*!< hash node in the hash bucket chain */ diff --git a/storage/innodb_plugin/include/mem0dbg.h b/storage/innodb_plugin/include/mem0dbg.h index a064af5c678..d81e1418b2b 100644 --- a/storage/innodb_plugin/include/mem0dbg.h +++ b/storage/innodb_plugin/include/mem0dbg.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1994, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1994, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -28,6 +28,13 @@ Created 6/9/1994 Heikki Tuuri check fields whose sizes are given below */ #ifdef UNIV_MEM_DEBUG +# ifndef UNIV_HOTBACKUP +/* The mutex which protects in the debug version the hash table +containing the list of live memory heaps, and also the global +variables in mem0dbg.c. */ +extern mutex_t mem_hash_mutex; +# endif /* !UNIV_HOTBACKUP */ + #define MEM_FIELD_HEADER_SIZE ut_calc_align(2 * sizeof(ulint),\ UNIV_MEM_ALIGNMENT) #define MEM_FIELD_TRAILER_SIZE sizeof(ulint) diff --git a/storage/innodb_plugin/include/mem0dbg.ic b/storage/innodb_plugin/include/mem0dbg.ic index cb9245411dc..b0c8178a623 100644 --- a/storage/innodb_plugin/include/mem0dbg.ic +++ b/storage/innodb_plugin/include/mem0dbg.ic @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1994, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1994, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -25,9 +25,6 @@ Created 6/8/1994 Heikki Tuuri *************************************************************************/ #ifdef UNIV_MEM_DEBUG -# ifndef UNIV_HOTBACKUP -extern mutex_t mem_hash_mutex; -# endif /* !UNIV_HOTBACKUP */ extern ulint mem_current_allocated_memory; /******************************************************************//** diff --git a/storage/innodb_plugin/include/mem0mem.h b/storage/innodb_plugin/include/mem0mem.h index 98f8748e529..ee28cf7b225 100644 --- a/storage/innodb_plugin/include/mem0mem.h +++ b/storage/innodb_plugin/include/mem0mem.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1994, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1994, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -359,6 +359,9 @@ struct mem_block_info_struct { to the heap is also the first block in this list, though it also contains the base node of the list. */ ulint len; /*!< physical length of this block in bytes */ + ulint total_size; /* physical length in bytes of all blocks + in the heap. This is defined only in the base + node and is set to ULINT_UNDEFINED in others. */ ulint type; /*!< type of heap: MEM_HEAP_DYNAMIC, or MEM_HEAP_BUF possibly ORed to MEM_HEAP_BTR_SEARCH */ ulint free; /*!< offset in bytes of the first free position for diff --git a/storage/innodb_plugin/include/mem0mem.ic b/storage/innodb_plugin/include/mem0mem.ic index e7080d8c508..cbce2edc661 100644 --- a/storage/innodb_plugin/include/mem0mem.ic +++ b/storage/innodb_plugin/include/mem0mem.ic @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1994, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1994, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -579,18 +579,12 @@ mem_heap_get_size( /*==============*/ mem_heap_t* heap) /*!< in: heap */ { - mem_block_t* block; ulint size = 0; ut_ad(mem_heap_check(heap)); - block = heap; - - while (block != NULL) { + size = heap->total_size; - size += mem_block_get_len(block); - block = UT_LIST_GET_NEXT(list, block); - } #ifndef UNIV_HOTBACKUP if (heap->free_block) { size += UNIV_PAGE_SIZE; diff --git a/storage/innodb_plugin/include/mtr0mtr.ic b/storage/innodb_plugin/include/mtr0mtr.ic index 310c7c4117f..18f8e87b3cf 100644 --- a/storage/innodb_plugin/include/mtr0mtr.ic +++ b/storage/innodb_plugin/include/mtr0mtr.ic @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -70,6 +70,7 @@ mtr_memo_push( ut_ad(type <= MTR_MEMO_X_LOCK); ut_ad(mtr); ut_ad(mtr->magic_n == MTR_MAGIC_N); + ut_ad(mtr->state == MTR_ACTIVE); memo = &(mtr->memo); @@ -92,6 +93,7 @@ mtr_set_savepoint( ut_ad(mtr); ut_ad(mtr->magic_n == MTR_MAGIC_N); + ut_ad(mtr->state == MTR_ACTIVE); memo = &(mtr->memo); @@ -149,6 +151,7 @@ mtr_memo_contains( ut_ad(mtr); ut_ad(mtr->magic_n == MTR_MAGIC_N); + ut_ad(mtr->state == MTR_ACTIVE || mtr->state == MTR_COMMITTING); memo = &(mtr->memo); diff --git a/storage/innodb_plugin/include/os0file.h b/storage/innodb_plugin/include/os0file.h index 16568579f31..d645cae38bb 100644 --- a/storage/innodb_plugin/include/os0file.h +++ b/storage/innodb_plugin/include/os0file.h @@ -1,23 +1,6 @@ -/***************************************************************************** - -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. - -This program is free software; you can redistribute it and/or modify it under -the terms of the GNU General Public License as published by the Free Software -Foundation; version 2 of the License. - -This program is distributed in the hope that it will be useful, but WITHOUT -ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS -FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. - -You should have received a copy of the GNU General Public License along with -this program; if not, write to the Free Software Foundation, Inc., 59 Temple -Place, Suite 330, Boston, MA 02111-1307 USA - -*****************************************************************************/ /*********************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. Copyright (c) 2009, Percona Inc. Portions of this file contain modifications contributed and copyrighted diff --git a/storage/innodb_plugin/include/que0que.h b/storage/innodb_plugin/include/que0que.h index 420f34550e2..39f8d07af89 100644 --- a/storage/innodb_plugin/include/que0que.h +++ b/storage/innodb_plugin/include/que0que.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -30,6 +30,7 @@ Created 5/27/1996 Heikki Tuuri #include "data0data.h" #include "dict0types.h" #include "trx0trx.h" +#include "trx0roll.h" #include "srv0srv.h" #include "usr0types.h" #include "que0types.h" @@ -215,6 +216,16 @@ trx_t* thr_get_trx( /*========*/ que_thr_t* thr); /*!< in: query thread */ +/*******************************************************************//** +Determines if this thread is rolling back an incomplete transaction +in crash recovery. +@return TRUE if thr is rolling back an incomplete transaction in crash +recovery */ +UNIV_INLINE +ibool +thr_is_recv( +/*========*/ + const que_thr_t* thr); /*!< in: query thread */ /***********************************************************************//** Gets the type of a graph node. */ UNIV_INLINE diff --git a/storage/innodb_plugin/include/que0que.ic b/storage/innodb_plugin/include/que0que.ic index a1c0dc1e77a..bd936670e1e 100644 --- a/storage/innodb_plugin/include/que0que.ic +++ b/storage/innodb_plugin/include/que0que.ic @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -38,6 +38,20 @@ thr_get_trx( return(thr->graph->trx); } +/*******************************************************************//** +Determines if this thread is rolling back an incomplete transaction +in crash recovery. +@return TRUE if thr is rolling back an incomplete transaction in crash +recovery */ +UNIV_INLINE +ibool +thr_is_recv( +/*========*/ + const que_thr_t* thr) /*!< in: query thread */ +{ + return(trx_is_recv(thr->graph->trx)); +} + /***********************************************************************//** Gets the first thr in a fork. */ UNIV_INLINE diff --git a/storage/innodb_plugin/include/row0mysql.h b/storage/innodb_plugin/include/row0mysql.h index b05241f00f8..d2a8734c61f 100644 --- a/storage/innodb_plugin/include/row0mysql.h +++ b/storage/innodb_plugin/include/row0mysql.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 2000, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 2000, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -451,6 +451,12 @@ row_drop_table_for_mysql( const char* name, /*!< in: table name */ trx_t* trx, /*!< in: transaction handle */ ibool drop_db);/*!< in: TRUE=dropping whole database */ +/*********************************************************************//** +Drop all temporary tables during crash recovery. */ +UNIV_INTERN +void +row_mysql_drop_temp_tables(void); +/*============================*/ /*********************************************************************//** Discards the tablespace of a table which stored in an .ibd file. Discarding @@ -494,14 +500,19 @@ row_rename_table_for_mysql( trx_t* trx, /*!< in: transaction handle */ ibool commit); /*!< in: if TRUE then commit trx */ /*********************************************************************//** -Checks a table for corruption. -@return DB_ERROR or DB_SUCCESS */ +Checks that the index contains entries in an ascending order, unique +constraint is not broken, and calculates the number of index entries +in the read view of the current transaction. +@return DB_SUCCESS if ok */ UNIV_INTERN ulint -row_check_table_for_mysql( +row_check_index_for_mysql( /*======================*/ - row_prebuilt_t* prebuilt); /*!< in: prebuilt struct in MySQL - handle */ + row_prebuilt_t* prebuilt, /*!< in: prebuilt struct + in MySQL handle */ + const dict_index_t* index, /*!< in: index */ + ulint* n_rows); /*!< out: number of entries + seen in the consistent read */ /*********************************************************************//** Determines if a table is a magic monitor table. diff --git a/storage/innodb_plugin/include/row0sel.h b/storage/innodb_plugin/include/row0sel.h index 01a5afaa23e..8544b9d08ba 100644 --- a/storage/innodb_plugin/include/row0sel.h +++ b/storage/innodb_plugin/include/row0sel.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1997, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1997, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -105,17 +105,6 @@ row_fetch_print( /*============*/ void* row, /*!< in: sel_node_t* */ void* user_arg); /*!< in: not used */ -/****************************************************************//** -Callback function for fetch that stores an unsigned 4 byte integer to the -location pointed. The column's type must be DATA_INT, DATA_UNSIGNED, length -= 4. -@return always returns NULL */ -UNIV_INTERN -void* -row_fetch_store_uint4( -/*==================*/ - void* row, /*!< in: sel_node_t* */ - void* user_arg); /*!< in: data pointer */ /***********************************************************//** Prints a row in a select result. @return query thread to run next or NULL */ diff --git a/storage/innodb_plugin/include/srv0srv.h b/storage/innodb_plugin/include/srv0srv.h index 228c9f6600a..7aa2ce74720 100644 --- a/storage/innodb_plugin/include/srv0srv.h +++ b/storage/innodb_plugin/include/srv0srv.h @@ -1,7 +1,8 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. Copyright (c) 2008, 2009, Google Inc. +Copyright (c) 2009, Percona Inc. Portions of this file contain modifications contributed and copyrighted by Google, Inc. Those modifications are gratefully acknowledged and are described @@ -9,6 +10,13 @@ briefly in the InnoDB documentation. The contributions by Google are incorporated with their permission, and subject to the conditions contained in the file COPYING.Google. +Portions of this file contain modifications contributed and copyrighted +by Percona Inc.. Those modifications are +gratefully acknowledged and are described briefly in the InnoDB +documentation. The contributions by Percona Inc. are incorporated with +their permission, and subject to the conditions contained in the file +COPYING.Percona. + This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; version 2 of the License. @@ -22,32 +30,6 @@ this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA *****************************************************************************/ -/*********************************************************************** - -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. -Copyright (c) 2009, Percona Inc. - -Portions of this file contain modifications contributed and copyrighted -by Percona Inc.. Those modifications are -gratefully acknowledged and are described briefly in the InnoDB -documentation. The contributions by Percona Inc. are incorporated with -their permission, and subject to the conditions contained in the file -COPYING.Percona. - -This program is free software; you can redistribute it and/or modify it -under the terms of the GNU General Public License as published by the -Free Software Foundation; version 2 of the License. - -This program is distributed in the hope that it will be useful, but -WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General -Public License for more details. - -You should have received a copy of the GNU General Public License along -with this program; if not, write to the Free Software Foundation, Inc., -59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -***********************************************************************/ /**************************************************//** @file include/srv0srv.h @@ -227,7 +209,8 @@ extern ibool srv_print_innodb_tablespace_monitor; extern ibool srv_print_verbose_log; extern ibool srv_print_innodb_table_monitor; -extern ibool srv_lock_timeout_and_monitor_active; +extern ibool srv_lock_timeout_active; +extern ibool srv_monitor_active; extern ibool srv_error_monitor_active; extern ulong srv_n_spin_wait_rounds; @@ -540,15 +523,23 @@ srv_release_mysql_thread_if_suspended( MySQL OS thread */ /*********************************************************************//** A thread which wakes up threads whose lock wait may have lasted too long. -This also prints the info output by various InnoDB monitors. @return a dummy parameter */ UNIV_INTERN os_thread_ret_t -srv_lock_timeout_and_monitor_thread( -/*================================*/ +srv_lock_timeout_thread( +/*====================*/ void* arg); /*!< in: a dummy parameter required by os_thread_create */ /*********************************************************************//** +A thread which prints the info output by various InnoDB monitors. +@return a dummy parameter */ +UNIV_INTERN +os_thread_ret_t +srv_monitor_thread( +/*===============*/ + void* arg); /*!< in: a dummy parameter required by + os_thread_create */ +/************************************************************************* A thread which prints warnings about semaphore waits which have lasted too long. These can be used to track bugs which cause hangs. @return a dummy parameter */ @@ -559,12 +550,15 @@ srv_error_monitor_thread( void* arg); /*!< in: a dummy parameter required by os_thread_create */ /******************************************************************//** -Outputs to a file the output of the InnoDB Monitor. */ +Outputs to a file the output of the InnoDB Monitor. +@return FALSE if not all information printed +due to failure to obtain necessary mutex */ UNIV_INTERN -void +ibool srv_printf_innodb_monitor( /*======================*/ FILE* file, /*!< in: output stream */ + ibool nowait, /*!< in: whether to wait for kernel mutex */ ulint* trx_start, /*!< out: file position of the start of the list of active transactions */ ulint* trx_end); /*!< out: file position of the end of diff --git a/storage/innodb_plugin/include/sync0rw.h b/storage/innodb_plugin/include/sync0rw.h index aedfd5f3f86..6f7e13220c1 100644 --- a/storage/innodb_plugin/include/sync0rw.h +++ b/storage/innodb_plugin/include/sync0rw.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. Copyright (c) 2008, Google Inc. Portions of this file contain modifications contributed and copyrighted by @@ -429,8 +429,9 @@ ibool rw_lock_own( /*========*/ rw_lock_t* lock, /*!< in: rw-lock */ - ulint lock_type); /*!< in: lock type: RW_LOCK_SHARED, + ulint lock_type) /*!< in: lock type: RW_LOCK_SHARED, RW_LOCK_EX */ + __attribute__((warn_unused_result)); #endif /* UNIV_SYNC_DEBUG */ /******************************************************************//** Checks if somebody has locked the rw-lock in the specified mode. */ diff --git a/storage/innodb_plugin/include/sync0sync.h b/storage/innodb_plugin/include/sync0sync.h index df990823cc4..d470b823fc3 100644 --- a/storage/innodb_plugin/include/sync0sync.h +++ b/storage/innodb_plugin/include/sync0sync.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. Copyright (c) 2008, Google Inc. Portions of this file contain modifications contributed and copyrighted by @@ -206,7 +206,8 @@ UNIV_INTERN ibool mutex_own( /*======*/ - const mutex_t* mutex); /*!< in: mutex */ + const mutex_t* mutex) /*!< in: mutex */ + __attribute__((warn_unused_result)); #endif /* UNIV_DEBUG */ #ifdef UNIV_SYNC_DEBUG /******************************************************************//** @@ -238,16 +239,27 @@ ibool sync_thread_levels_empty(void); /*==========================*/ /******************************************************************//** -Checks that the level array for the current thread is empty. -@return TRUE if empty except the exceptions specified below */ +Checks if the level array for the current thread contains a +mutex or rw-latch at the specified level. +@return a matching latch, or NULL if not found */ UNIV_INTERN -ibool -sync_thread_levels_empty_gen( -/*=========================*/ +void* +sync_thread_levels_contains( +/*========================*/ + ulint level); /*!< in: latching order level + (SYNC_DICT, ...)*/ +/******************************************************************//** +Checks if the level array for the current thread is empty. +@return a latch, or NULL if empty except the exceptions specified below */ +UNIV_INTERN +void* +sync_thread_levels_nonempty_gen( +/*============================*/ ibool dict_mutex_allowed); /*!< in: TRUE if dictionary mutex is allowed to be owned by the thread, also purge_is_running mutex is allowed */ +#define sync_thread_levels_empty_gen(d) (!sync_thread_levels_nonempty_gen(d)) /******************************************************************//** Gets the debug information for a reserved mutex. */ UNIV_INTERN diff --git a/storage/innodb_plugin/include/trx0rseg.h b/storage/innodb_plugin/include/trx0rseg.h index ba1fc88b6c4..a25d84f1e84 100644 --- a/storage/innodb_plugin/include/trx0rseg.h +++ b/storage/innodb_plugin/include/trx0rseg.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -114,17 +114,6 @@ trx_rseg_list_and_array_init( /*=========================*/ trx_sysf_t* sys_header, /*!< in: trx system header */ mtr_t* mtr); /*!< in: mtr */ -/****************************************************************//** -Creates a new rollback segment to the database. -@return the created segment object, NULL if fail */ -UNIV_INTERN -trx_rseg_t* -trx_rseg_create( -/*============*/ - ulint space, /*!< in: space id */ - ulint max_size, /*!< in: max size in pages */ - ulint* id, /*!< out: rseg id */ - mtr_t* mtr); /*!< in: mtr */ /*************************************************************************** Free's an instance of the rollback segment in memory. */ UNIV_INTERN diff --git a/storage/innodb_plugin/include/trx0sys.h b/storage/innodb_plugin/include/trx0sys.h index a53296a06d9..cbb89689748 100644 --- a/storage/innodb_plugin/include/trx0sys.h +++ b/storage/innodb_plugin/include/trx0sys.h @@ -333,12 +333,14 @@ UNIV_INTERN void trx_sys_file_format_tag_init(void); /*==============================*/ +#ifndef UNIV_HOTBACKUP /*****************************************************************//** Shutdown/Close the transaction system. */ UNIV_INTERN void trx_sys_close(void); /*===============*/ +#endif /* !UNIV_HOTBACKUP */ /*****************************************************************//** Get the name representation of the file format from its id. @return pointer to the name */ @@ -495,7 +497,6 @@ this contains the same fields as TRX_SYS_MYSQL_LOG_INFO below */ within that file */ #define TRX_SYS_MYSQL_LOG_NAME 12 /*!< MySQL log file name */ -#ifndef UNIV_HOTBACKUP /** Doublewrite buffer */ /* @{ */ /** The offset of the doublewrite buffer header on the trx system header page */ @@ -547,6 +548,7 @@ FIL_PAGE_ARCH_LOG_NO_OR_SPACE_NO. */ #define TRX_SYS_DOUBLEWRITE_BLOCK_SIZE FSP_EXTENT_SIZE /* @} */ +#ifndef UNIV_HOTBACKUP /** File format tag */ /* @{ */ /** The offset of the file format tag on the trx system header page diff --git a/storage/innodb_plugin/include/trx0trx.h b/storage/innodb_plugin/include/trx0trx.h index 5f2c1246f37..6872fb463c0 100644 --- a/storage/innodb_plugin/include/trx0trx.h +++ b/storage/innodb_plugin/include/trx0trx.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -349,7 +349,7 @@ trx_print( use the default max length */ /** Type of data dictionary operation */ -enum trx_dict_op { +typedef enum trx_dict_op { /** The transaction is not modifying the data dictionary. */ TRX_DICT_OP_NONE = 0, /** The transaction is creating a table or an index, or @@ -361,7 +361,7 @@ enum trx_dict_op { existing table. In crash recovery, the data dictionary must be locked, but the table must not be dropped. */ TRX_DICT_OP_INDEX = 2 -}; +} trx_dict_op_t; /**********************************************************************//** Determine if a transaction is a dictionary operation. @@ -391,6 +391,14 @@ ibool trx_is_interrupted( /*===============*/ trx_t* trx); /*!< in: transaction */ +/**********************************************************************//** +Determines if the currently running transaction is in strict mode. +@return TRUE if strict */ +UNIV_INTERN +ibool +trx_is_strict( +/*==========*/ + trx_t* trx); /*!< in: transaction */ #else /* !UNIV_HOTBACKUP */ #define trx_is_interrupted(trx) FALSE #endif /* !UNIV_HOTBACKUP */ @@ -463,69 +471,79 @@ rolling back after a database recovery */ struct trx_struct{ ulint magic_n; - /* All the next fields are protected by the kernel mutex, except the - undo logs which are protected by undo_mutex */ + + /* These fields are not protected by any mutex. */ const char* op_info; /*!< English text describing the current operation, or an empty string */ - unsigned is_purge:1; /*!< 0=user transaction, 1=purge */ - unsigned is_recovered:1; /*!< 0=normal transaction, - 1=recovered, must be rolled back */ - unsigned conc_state:2; /*!< state of the trx from the point + ulint conc_state; /*!< state of the trx from the point of view of concurrency control: TRX_ACTIVE, TRX_COMMITTED_IN_MEMORY, ... */ - unsigned que_state:2; /*!< valid when conc_state == TRX_ACTIVE: - TRX_QUE_RUNNING, TRX_QUE_LOCK_WAIT, - ... */ - unsigned isolation_level:2;/* TRX_ISO_REPEATABLE_READ, ... */ - unsigned check_foreigns:1;/* normally TRUE, but if the user + ulint isolation_level;/* TRX_ISO_REPEATABLE_READ, ... */ + ulint check_foreigns; /* normally TRUE, but if the user wants to suppress foreign key checks, (in table imports, for example) we set this FALSE */ - unsigned check_unique_secondary:1; + ulint check_unique_secondary; /* normally TRUE, but if the user wants to speed up inserts by suppressing unique key checks for secondary indexes when we decide if we can use the insert buffer for them, we set this FALSE */ - unsigned support_xa:1; /*!< normally we do the XA two-phase + ulint support_xa; /*!< normally we do the XA two-phase commit steps, but by setting this to FALSE, one can save CPU time and about 150 bytes in the undo log size as then we skip XA steps */ - unsigned flush_log_later:1;/* In 2PC, we hold the + ulint flush_log_later;/* In 2PC, we hold the prepare_commit mutex across both phases. In that case, we defer flush of the logs to disk until after we release the mutex. */ - unsigned must_flush_log_later:1;/* this flag is set to TRUE in + ulint must_flush_log_later;/* this flag is set to TRUE in trx_commit_off_kernel() if flush_log_later was TRUE, and there were modifications by the transaction; in that case we must flush the log in trx_commit_complete_for_mysql() */ - unsigned dict_operation:2;/**< @see enum trx_dict_op */ - unsigned duplicates:2; /*!< TRX_DUP_IGNORE | TRX_DUP_REPLACE */ - unsigned active_trans:2; /*!< 1 - if a transaction in MySQL + ulint duplicates; /*!< TRX_DUP_IGNORE | TRX_DUP_REPLACE */ + ulint active_trans; /*!< 1 - if a transaction in MySQL is active. 2 - if prepare_commit_mutex was taken */ - unsigned has_search_latch:1; + ulint has_search_latch; /* TRUE if this trx has latched the search system latch in S-mode */ - unsigned declared_to_be_inside_innodb:1; + ulint deadlock_mark; /*!< a mark field used in deadlock + checking algorithm. */ + trx_dict_op_t dict_operation; /**< @see enum trx_dict_op */ + + /* Fields protected by the srv_conc_mutex. */ + ulint declared_to_be_inside_innodb; /* this is TRUE if we have declared this transaction in srv_conc_enter_innodb to be inside the InnoDB engine */ - unsigned handling_signals:1;/* this is TRUE as long as the trx - is handling signals */ - unsigned dict_operation_lock_mode:2; - /* 0, RW_S_LATCH, or RW_X_LATCH: + + /* Fields protected by dict_operation_lock. The very latch + it is used to track. */ + ulint dict_operation_lock_mode; + /*!< 0, RW_S_LATCH, or RW_X_LATCH: the latch mode trx currently holds on dict_operation_lock */ + + /* All the next fields are protected by the kernel mutex, except the + undo logs which are protected by undo_mutex */ + ulint is_purge; /*!< 0=user transaction, 1=purge */ + ulint is_recovered; /*!< 0=normal transaction, + 1=recovered, must be rolled back */ + ulint que_state; /*!< valid when conc_state + == TRX_ACTIVE: TRX_QUE_RUNNING, + TRX_QUE_LOCK_WAIT, ... */ + ulint handling_signals;/* this is TRUE as long as the trx + is handling signals */ time_t start_time; /*!< time the trx object was created or the state last time became TRX_ACTIVE */ @@ -640,11 +658,6 @@ struct trx_struct{ wait_thrs; /*!< query threads belonging to this trx that are in the QUE_THR_LOCK_WAIT state */ - ulint deadlock_mark; /*!< a mark field used in deadlock - checking algorithm. This must be - in its own machine word, because - it can be changed by other - threads while holding kernel_mutex. */ /*------------------------------*/ mem_heap_t* lock_heap; /*!< memory heap for the locks of the transaction */ diff --git a/storage/innodb_plugin/include/trx0types.h b/storage/innodb_plugin/include/trx0types.h index 24cf57d53d5..40a7256cbfd 100644 --- a/storage/innodb_plugin/include/trx0types.h +++ b/storage/innodb_plugin/include/trx0types.h @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -70,6 +70,13 @@ typedef struct trx_named_savept_struct trx_named_savept_t; enum trx_rb_ctx { RB_NONE = 0, /*!< no rollback */ RB_NORMAL, /*!< normal rollback */ + RB_RECOVERY_PURGE_REC, + /*!< rolling back an incomplete transaction, + in crash recovery, rolling back an + INSERT that was performed by updating a + delete-marked record; if the delete-marked record + no longer exists in an active read view, it will + be purged */ RB_RECOVERY /*!< rolling back an incomplete transaction, in crash recovery */ }; diff --git a/storage/innodb_plugin/include/univ.i b/storage/innodb_plugin/include/univ.i index 2081e136590..49717760456 100644 --- a/storage/innodb_plugin/include/univ.i +++ b/storage/innodb_plugin/include/univ.i @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1994, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1994, 2010, Innobase Oy. All Rights Reserved. Copyright (c) 2008, Google Inc. Copyright (c) 2009, Sun Microsystems, Inc. @@ -46,7 +46,7 @@ Created 1/20/1994 Heikki Tuuri #define INNODB_VERSION_MAJOR 1 #define INNODB_VERSION_MINOR 0 -#define INNODB_VERSION_BUGFIX 6 +#define INNODB_VERSION_BUGFIX 8 /* The following is the InnoDB version as shown in SELECT plugin_version FROM information_schema.plugins; @@ -115,7 +115,7 @@ if we are compiling on Windows. */ /* Include <sys/stat.h> to get S_I... macros defined for os0file.c */ # include <sys/stat.h> -# if !defined(__NETWARE__) && !defined(__WIN__) +# if !defined(__NETWARE__) && !defined(__WIN__) # include <sys/mman.h> /* mmap() for os0proc.c */ # endif @@ -165,6 +165,9 @@ command. Not tested on Windows. */ #define UNIV_COMPILE_TEST_FUNCS */ +#ifdef HAVE_purify +# define UNIV_DEBUG_VALGRIND +#endif /* HAVE_purify */ #if 0 #define UNIV_DEBUG_VALGRIND /* Enable extra Valgrind instrumentation */ @@ -202,6 +205,10 @@ operations (very slow); also UNIV_DEBUG must be defined */ adaptive hash index */ #define UNIV_SRV_PRINT_LATCH_WAITS /* enable diagnostic output in sync0sync.c */ +#define UNIV_BTR_AVOID_COPY /* when splitting B-tree nodes, + do not move any records when + all the records would + be moved */ #define UNIV_BTR_PRINT /* enable functions for printing B-trees */ #define UNIV_ZIP_DEBUG /* extensive consistency checks @@ -229,11 +236,6 @@ by one. */ /* the above option prevents forcing of log to disk at a buffer page write: it should be tested with this option off; also some ibuf tests are suppressed */ -/* -#define UNIV_BASIC_LOG_DEBUG -*/ - /* the above option enables basic recovery debugging: - new allocated file pages are reset */ /* Linkage specifier for non-static InnoDB symbols (variables and functions) that are only referenced from within InnoDB, not from MySQL */ diff --git a/storage/innodb_plugin/include/ut0rbt.h b/storage/innodb_plugin/include/ut0rbt.h new file mode 100644 index 00000000000..6fd050acfe7 --- /dev/null +++ b/storage/innodb_plugin/include/ut0rbt.h @@ -0,0 +1,309 @@ +/***************************************************************************** +Copyright (c) 2006, 2009, Innobase Oy. All Rights Reserved. + +This program is free software; you can redistribute it and/or modify it under +the terms of the GNU General Public License as published by the Free Software +Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, but WITHOUT +ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS +FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. + +You should have received a copy of the GNU General Public License along with +this program; if not, write to the Free Software Foundation, Inc., 59 Temple +Place, Suite 330, Boston, MA 02111-1307 USA + +*****************************************************************************/ + +/*******************************************************************//** +@file include/ut0rbt.h +Red-Black tree implementation. + +Created 2007-03-20 Sunny Bains +************************************************************************/ + +#ifndef INNOBASE_UT0RBT_H +#define INNOBASE_UT0RBT_H + +#if !defined(IB_RBT_TESTING) +#include "univ.i" +#include "ut0mem.h" +#else +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <assert.h> + +#define ut_malloc malloc +#define ut_free free +#define ulint unsigned long +#define ut_a(c) assert(c) +#define ut_error assert(0) +#define ibool unsigned int +#define TRUE 1 +#define FALSE 0 +#endif + +/* Red black tree typedefs */ +typedef struct ib_rbt_struct ib_rbt_t; +typedef struct ib_rbt_node_struct ib_rbt_node_t; +/* FIXME: Iterator is a better name than _bound_ */ +typedef struct ib_rbt_bound_struct ib_rbt_bound_t; +typedef void (*ib_rbt_print_node)(const ib_rbt_node_t* node); +typedef int (*ib_rbt_compare)(const void* p1, const void* p2); + +/* Red black tree color types */ +enum ib_rbt_color_enum { + IB_RBT_RED, + IB_RBT_BLACK +}; + +typedef enum ib_rbt_color_enum ib_rbt_color_t; + +/* Red black tree node */ +struct ib_rbt_node_struct { + ib_rbt_color_t color; /* color of this node */ + + ib_rbt_node_t* left; /* points left child */ + ib_rbt_node_t* right; /* points right child */ + ib_rbt_node_t* parent; /* points parent node */ + + char value[1]; /* Data value */ +}; + +/* Red black tree instance.*/ +struct ib_rbt_struct { + ib_rbt_node_t* nil; /* Black colored node that is + used as a sentinel. This is + pre-allocated too.*/ + + ib_rbt_node_t* root; /* Root of the tree, this is + pre-allocated and the first + data node is the left child.*/ + + ulint n_nodes; /* Total number of data nodes */ + + ib_rbt_compare compare; /* Fn. to use for comparison */ + ulint sizeof_value; /* Sizeof the item in bytes */ +}; + +/* The result of searching for a key in the tree, this is useful for +a speedy lookup and insert if key doesn't exist.*/ +struct ib_rbt_bound_struct { + const ib_rbt_node_t* + last; /* Last node visited */ + + int result; /* Result of comparing with + the last non-nil node that + was visited */ +}; + +/* Size in elements (t is an rb tree instance) */ +#define rbt_size(t) (t->n_nodes) + +/* Check whether the rb tree is empty (t is an rb tree instance) */ +#define rbt_empty(t) (rbt_size(t) == 0) + +/* Get data value (t is the data type, n is an rb tree node instance) */ +#define rbt_value(t, n) ((t*) &n->value[0]) + +/* Compare a key with the node value (t is tree, k is key, n is node)*/ +#define rbt_compare(t, k, n) (t->compare(k, n->value)) + +/****************************************************************//** +Free an instance of a red black tree */ +UNIV_INTERN +void +rbt_free( +/*=====*/ + ib_rbt_t* tree); /*!< in: rb tree to free */ +/****************************************************************//** +Create an instance of a red black tree +@return rb tree instance */ +UNIV_INTERN +ib_rbt_t* +rbt_create( +/*=======*/ + size_t sizeof_value, /*!< in: size in bytes */ + ib_rbt_compare compare); /*!< in: comparator */ +/****************************************************************//** +Delete a node from the red black tree, identified by key. +@return TRUE if success FALSE if not found */ +UNIV_INTERN +ibool +rbt_delete( +/*=======*/ + ib_rbt_t* tree, /*!< in: rb tree */ + const void* key); /*!< in: key to delete */ +/****************************************************************//** +Remove a node from the rb tree, the node is not free'd, that is the +callers responsibility. +@return the deleted node with the const. */ +UNIV_INTERN +ib_rbt_node_t* +rbt_remove_node( +/*============*/ + ib_rbt_t* tree, /*!< in: rb tree */ + const ib_rbt_node_t* + node); /*!< in: node to delete, this + is a fudge and declared const + because the caller has access + only to const nodes.*/ +/****************************************************************//** +Find a matching node in the rb tree. +@return node if found else return NULL */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_lookup( +/*=======*/ + const ib_rbt_t* tree, /*!< in: rb tree to search */ + const void* key); /*!< in: key to lookup */ +/****************************************************************//** +Generic insert of a value in the rb tree. +@return inserted node */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_insert( +/*=======*/ + ib_rbt_t* tree, /*!< in: rb tree */ + const void* key, /*!< in: key for ordering */ + const void* value); /*!< in: data that will be + copied to the node.*/ +/****************************************************************//** +Add a new node to the tree, useful for data that is pre-sorted. +@return appended node */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_add_node( +/*=========*/ + ib_rbt_t* tree, /*!< in: rb tree */ + ib_rbt_bound_t* parent, /*!< in: parent */ + const void* value); /*!< in: this value is copied + to the node */ +/****************************************************************//** +Return the left most data node in the tree +@return left most node */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_first( +/*======*/ + const ib_rbt_t* tree); /*!< in: rb tree */ +/****************************************************************//** +Return the right most data node in the tree +@return right most node */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_last( +/*=====*/ + const ib_rbt_t* tree); /*!< in: rb tree */ +/****************************************************************//** +Return the next node from current. +@return successor node to current that is passed in. */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_next( +/*=====*/ + const ib_rbt_t* tree, /*!< in: rb tree */ + const ib_rbt_node_t* /*!< in: current node */ + current); +/****************************************************************//** +Return the prev node from current. +@return precedessor node to current that is passed in */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_prev( +/*=====*/ + const ib_rbt_t* tree, /*!< in: rb tree */ + const ib_rbt_node_t* /*!< in: current node */ + current); +/****************************************************************//** +Find the node that has the lowest key that is >= key. +@return node that satisfies the lower bound constraint or NULL */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_lower_bound( +/*============*/ + const ib_rbt_t* tree, /*!< in: rb tree */ + const void* key); /*!< in: key to search */ +/****************************************************************//** +Find the node that has the greatest key that is <= key. +@return node that satisifies the upper bound constraint or NULL */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_upper_bound( +/*============*/ + const ib_rbt_t* tree, /*!< in: rb tree */ + const void* key); /*!< in: key to search */ +/****************************************************************//** +Search for the key, a node will be retuned in parent.last, whether it +was found or not. If not found then parent.last will contain the +parent node for the possibly new key otherwise the matching node. +@return result of last comparison */ +UNIV_INTERN +int +rbt_search( +/*=======*/ + const ib_rbt_t* tree, /*!< in: rb tree */ + ib_rbt_bound_t* parent, /*!< in: search bounds */ + const void* key); /*!< in: key to search */ +/****************************************************************//** +Search for the key, a node will be retuned in parent.last, whether it +was found or not. If not found then parent.last will contain the +parent node for the possibly new key otherwise the matching node. +@return result of last comparison */ +UNIV_INTERN +int +rbt_search_cmp( +/*===========*/ + const ib_rbt_t* tree, /*!< in: rb tree */ + ib_rbt_bound_t* parent, /*!< in: search bounds */ + const void* key, /*!< in: key to search */ + ib_rbt_compare compare); /*!< in: comparator */ +/****************************************************************//** +Clear the tree, deletes (and free's) all the nodes. */ +UNIV_INTERN +void +rbt_clear( +/*======*/ + ib_rbt_t* tree); /*!< in: rb tree */ +/****************************************************************//** +Merge the node from dst into src. Return the number of nodes merged. +@return no. of recs merged */ +UNIV_INTERN +ulint +rbt_merge_uniq( +/*===========*/ + ib_rbt_t* dst, /*!< in: dst rb tree */ + const ib_rbt_t* src); /*!< in: src rb tree */ +/****************************************************************//** +Merge the node from dst into src. Return the number of nodes merged. +Delete the nodes from src after copying node to dst. As a side effect +the duplicates will be left untouched in the src, since we don't support +duplicates (yet). NOTE: src and dst must be similar, the function doesn't +check for this condition (yet). +@return no. of recs merged */ +UNIV_INTERN +ulint +rbt_merge_uniq_destructive( +/*=======================*/ + ib_rbt_t* dst, /*!< in: dst rb tree */ + ib_rbt_t* src); /*!< in: src rb tree */ +/****************************************************************//** +Verify the integrity of the RB tree. For debugging. 0 failure else height +of tree (in count of black nodes). +@return TRUE if OK FALSE if tree invalid. */ +UNIV_INTERN +ibool +rbt_validate( +/*=========*/ + const ib_rbt_t* tree); /*!< in: tree to validate */ +/****************************************************************//** +Iterate over the tree in depth first order. */ +UNIV_INTERN +void +rbt_print( +/*======*/ + const ib_rbt_t* tree, /*!< in: tree to traverse */ + ib_rbt_print_node print); /*!< in: print function */ + +#endif /* INNOBASE_UT0RBT_H */ diff --git a/storage/innodb_plugin/include/ut0rnd.ic b/storage/innodb_plugin/include/ut0rnd.ic index 763469142ec..c3dbd86923c 100644 --- a/storage/innodb_plugin/include/ut0rnd.ic +++ b/storage/innodb_plugin/include/ut0rnd.ic @@ -152,6 +152,7 @@ ut_hash_ulint( ulint key, /*!< in: value to be hashed */ ulint table_size) /*!< in: hash table size */ { + ut_ad(table_size); key = key ^ UT_HASH_RANDOM_MASK2; return(key % table_size); diff --git a/storage/innodb_plugin/lock/lock0lock.c b/storage/innodb_plugin/lock/lock0lock.c index 1fce8002bdf..04e5fe1a65a 100644 --- a/storage/innodb_plugin/lock/lock0lock.c +++ b/storage/innodb_plugin/lock/lock0lock.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -376,6 +376,7 @@ UNIV_INTERN FILE* lock_latest_err_file; /* Flags for recursive deadlock search */ #define LOCK_VICTIM_IS_START 1 #define LOCK_VICTIM_IS_OTHER 2 +#define LOCK_EXCEED_MAX_DEPTH 3 /********************************************************************//** Checks if a lock request results in a deadlock. @@ -394,24 +395,25 @@ Looks recursively for a deadlock. deadlock and we chose 'start' as the victim, LOCK_VICTIM_IS_OTHER if a deadlock was found and we chose some other trx as a victim: we must do the search again in this last case because there may be another -deadlock! */ +deadlock! +LOCK_EXCEED_MAX_DEPTH if the lock search exceeds max steps or max depth. */ static ulint lock_deadlock_recursive( /*====================*/ trx_t* start, /*!< in: recursion starting point */ trx_t* trx, /*!< in: a transaction waiting for a lock */ - lock_t* wait_lock, /*!< in: the lock trx is waiting to be granted */ + lock_t* wait_lock, /*!< in: lock that is waiting to be granted */ ulint* cost, /*!< in/out: number of calculation steps thus far: if this exceeds LOCK_MAX_N_STEPS_... - we return LOCK_VICTIM_IS_START */ + we return LOCK_EXCEED_MAX_DEPTH */ ulint depth); /*!< in: recursion depth: if this exceeds LOCK_MAX_DEPTH_IN_DEADLOCK_CHECK, we - return LOCK_VICTIM_IS_START */ + return LOCK_EXCEED_MAX_DEPTH */ /*********************************************************************//** Gets the nth bit of a record lock. -@return TRUE if bit set */ +@return TRUE if bit set also if i == ULINT_UNDEFINED return FALSE*/ UNIV_INLINE ibool lock_rec_get_nth_bit( @@ -1222,7 +1224,7 @@ lock_rec_get_first_on_page( /*********************************************************************//** Gets the next explicit lock request on a record. -@return next lock, NULL if none exists */ +@return next lock, NULL if none exists or if heap_no == ULINT_UNDEFINED */ UNIV_INLINE lock_t* lock_rec_get_next( @@ -2398,7 +2400,7 @@ lock_rec_inherit_to_gap( if (!lock_rec_get_insert_intention(lock) && !((srv_locks_unsafe_for_binlog || lock->trx->isolation_level - == TRX_ISO_READ_COMMITTED) + <= TRX_ISO_READ_COMMITTED) && lock_get_mode(lock) == LOCK_X)) { lock_rec_add_to_queue(LOCK_REC | LOCK_GAP @@ -3261,8 +3263,6 @@ lock_deadlock_occurs( lock_t* lock, /*!< in: lock the transaction is requesting */ trx_t* trx) /*!< in: transaction */ { - dict_table_t* table; - dict_index_t* index; trx_t* mark_trx; ulint ret; ulint cost = 0; @@ -3284,31 +3284,50 @@ retry: ret = lock_deadlock_recursive(trx, trx, lock, &cost, 0); - if (ret == LOCK_VICTIM_IS_OTHER) { + switch (ret) { + case LOCK_VICTIM_IS_OTHER: /* We chose some other trx as a victim: retry if there still is a deadlock */ - goto retry; - } - if (UNIV_UNLIKELY(ret == LOCK_VICTIM_IS_START)) { - if (lock_get_type_low(lock) & LOCK_TABLE) { - table = lock->un_member.tab_lock.table; - index = NULL; + case LOCK_EXCEED_MAX_DEPTH: + /* If the lock search exceeds the max step + or the max depth, the current trx will be + the victim. Print its information. */ + rewind(lock_latest_err_file); + ut_print_timestamp(lock_latest_err_file); + + fputs("TOO DEEP OR LONG SEARCH IN THE LOCK TABLE" + " WAITS-FOR GRAPH, WE WILL ROLL BACK" + " FOLLOWING TRANSACTION \n", + lock_latest_err_file); + + fputs("\n*** TRANSACTION:\n", lock_latest_err_file); + trx_print(lock_latest_err_file, trx, 3000); + + fputs("*** WAITING FOR THIS LOCK TO BE GRANTED:\n", + lock_latest_err_file); + + if (lock_get_type(lock) == LOCK_REC) { + lock_rec_print(lock_latest_err_file, lock); } else { - index = lock->index; - table = index->table; + lock_table_print(lock_latest_err_file, lock); } + break; - lock_deadlock_found = TRUE; - + case LOCK_VICTIM_IS_START: fputs("*** WE ROLL BACK TRANSACTION (2)\n", lock_latest_err_file); + break; - return(TRUE); + default: + /* No deadlock detected*/ + return(FALSE); } - return(FALSE); + lock_deadlock_found = TRUE; + + return(TRUE); } /********************************************************************//** @@ -3317,25 +3336,26 @@ Looks recursively for a deadlock. deadlock and we chose 'start' as the victim, LOCK_VICTIM_IS_OTHER if a deadlock was found and we chose some other trx as a victim: we must do the search again in this last case because there may be another -deadlock! */ +deadlock! +LOCK_EXCEED_MAX_DEPTH if the lock search exceeds max steps or max depth. */ static ulint lock_deadlock_recursive( /*====================*/ trx_t* start, /*!< in: recursion starting point */ trx_t* trx, /*!< in: a transaction waiting for a lock */ - lock_t* wait_lock, /*!< in: the lock trx is waiting to be granted */ + lock_t* wait_lock, /*!< in: lock that is waiting to be granted */ ulint* cost, /*!< in/out: number of calculation steps thus far: if this exceeds LOCK_MAX_N_STEPS_... - we return LOCK_VICTIM_IS_START */ + we return LOCK_EXCEED_MAX_DEPTH */ ulint depth) /*!< in: recursion depth: if this exceeds LOCK_MAX_DEPTH_IN_DEADLOCK_CHECK, we - return LOCK_VICTIM_IS_START */ + return LOCK_EXCEED_MAX_DEPTH */ { + ulint ret; lock_t* lock; - ulint bit_no = ULINT_UNDEFINED; trx_t* lock_trx; - ulint ret; + ulint heap_no = ULINT_UNDEFINED; ut_a(trx); ut_a(start); @@ -3351,27 +3371,44 @@ lock_deadlock_recursive( *cost = *cost + 1; - lock = wait_lock; - if (lock_get_type_low(wait_lock) == LOCK_REC) { + ulint space; + ulint page_no; + + heap_no = lock_rec_find_set_bit(wait_lock); + ut_a(heap_no != ULINT_UNDEFINED); + + space = wait_lock->un_member.rec_lock.space; + page_no = wait_lock->un_member.rec_lock.page_no; + + lock = lock_rec_get_first_on_page_addr(space, page_no); + + /* Position the iterator on the first matching record lock. */ + while (lock != NULL + && lock != wait_lock + && !lock_rec_get_nth_bit(lock, heap_no)) { + + lock = lock_rec_get_next_on_page(lock); + } - bit_no = lock_rec_find_set_bit(wait_lock); + if (lock == wait_lock) { + lock = NULL; + } + + ut_ad(lock == NULL || lock_rec_get_nth_bit(lock, heap_no)); - ut_a(bit_no != ULINT_UNDEFINED); + } else { + lock = wait_lock; } /* Look at the locks ahead of wait_lock in the lock queue */ for (;;) { - if (lock_get_type_low(lock) & LOCK_TABLE) { - - lock = UT_LIST_GET_PREV(un_member.tab_lock.locks, - lock); - } else { - ut_ad(lock_get_type_low(lock) == LOCK_REC); - ut_a(bit_no != ULINT_UNDEFINED); + /* Get previous table lock. */ + if (heap_no == ULINT_UNDEFINED) { - lock = (lock_t*) lock_rec_get_prev(lock, bit_no); + lock = UT_LIST_GET_PREV( + un_member.tab_lock.locks, lock); } if (lock == NULL) { @@ -3389,7 +3426,7 @@ lock_deadlock_recursive( lock_trx = lock->trx; - if (lock_trx == start || too_far) { + if (lock_trx == start) { /* We came back to the recursion starting point: a deadlock detected; or we have @@ -3436,19 +3473,10 @@ lock_deadlock_recursive( } #ifdef UNIV_DEBUG if (lock_print_waits) { - fputs("Deadlock detected" - " or too long search\n", + fputs("Deadlock detected\n", stderr); } #endif /* UNIV_DEBUG */ - if (too_far) { - - fputs("TOO DEEP OR LONG SEARCH" - " IN THE LOCK TABLE" - " WAITS-FOR GRAPH\n", ef); - - return(LOCK_VICTIM_IS_START); - } if (trx_weight_cmp(wait_lock->trx, start) >= 0) { @@ -3484,6 +3512,21 @@ lock_deadlock_recursive( return(LOCK_VICTIM_IS_OTHER); } + if (too_far) { + +#ifdef UNIV_DEBUG + if (lock_print_waits) { + fputs("Deadlock search exceeds" + " max steps or depth.\n", + stderr); + } +#endif /* UNIV_DEBUG */ + /* The information about transaction/lock + to be rolled back is available in the top + level. Do not print anything here. */ + return(LOCK_EXCEED_MAX_DEPTH); + } + if (lock_trx->que_state == TRX_QUE_LOCK_WAIT) { /* Another trx ahead has requested lock in an @@ -3493,12 +3536,28 @@ lock_deadlock_recursive( ret = lock_deadlock_recursive( start, lock_trx, lock_trx->wait_lock, cost, depth + 1); + if (ret != 0) { return(ret); } } } + /* Get the next record lock to check. */ + if (heap_no != ULINT_UNDEFINED) { + + ut_a(lock != NULL); + + do { + lock = lock_rec_get_next_on_page(lock); + } while (lock != NULL + && lock != wait_lock + && !lock_rec_get_nth_bit(lock, heap_no)); + + if (lock == wait_lock) { + lock = NULL; + } + } }/* end of the 'for (;;)'-loop */ } @@ -3694,9 +3753,10 @@ lock_table_enqueue_waiting( /*********************************************************************//** Checks if other transactions have an incompatible mode lock request in -the lock queue. */ +the lock queue. +@return lock or NULL */ UNIV_INLINE -ibool +lock_t* lock_table_other_has_incompatible( /*==============================*/ trx_t* trx, /*!< in: transaction, or NULL if all @@ -3718,13 +3778,13 @@ lock_table_other_has_incompatible( && (!lock_mode_compatible(lock_get_mode(lock), mode)) && (wait || !(lock_get_wait(lock)))) { - return(TRUE); + return(lock); } lock = UT_LIST_GET_PREV(un_member.tab_lock.locks, lock); } - return(FALSE); + return(NULL); } /*********************************************************************//** @@ -4249,28 +4309,29 @@ lock_rec_print( block = buf_page_try_get(space, page_no, &mtr); - if (block) { - for (i = 0; i < lock_rec_get_n_bits(lock); i++) { + for (i = 0; i < lock_rec_get_n_bits(lock); ++i) { - if (lock_rec_get_nth_bit(lock, i)) { + if (!lock_rec_get_nth_bit(lock, i)) { + continue; + } - const rec_t* rec - = page_find_rec_with_heap_no( - buf_block_get_frame(block), i); - offsets = rec_get_offsets( - rec, lock->index, offsets, - ULINT_UNDEFINED, &heap); + fprintf(file, "Record lock, heap no %lu", (ulong) i); - fprintf(file, "Record lock, heap no %lu ", - (ulong) i); - rec_print_new(file, rec, offsets); - putc('\n', file); - } - } - } else { - for (i = 0; i < lock_rec_get_n_bits(lock); i++) { - fprintf(file, "Record lock, heap no %lu\n", (ulong) i); + if (block) { + const rec_t* rec; + + rec = page_find_rec_with_heap_no( + buf_block_get_frame(block), i); + + offsets = rec_get_offsets( + rec, lock->index, offsets, + ULINT_UNDEFINED, &heap); + + putc(' ', file); + rec_print_new(file, rec, offsets); } + + putc('\n', file); } mtr_commit(&mtr); @@ -4317,14 +4378,26 @@ lock_get_n_rec_locks(void) #endif /* PRINT_NUM_OF_LOCK_STRUCTS */ /*********************************************************************//** -Prints info of locks for all transactions. */ +Prints info of locks for all transactions. +@return FALSE if not able to obtain kernel mutex +and exits without printing info */ UNIV_INTERN -void +ibool lock_print_info_summary( /*====================*/ - FILE* file) /*!< in: file where to print */ + FILE* file, /*!< in: file where to print */ + ibool nowait) /*!< in: whether to wait for the kernel mutex */ { - lock_mutex_enter_kernel(); + /* if nowait is FALSE, wait on the kernel mutex, + otherwise return immediately if fail to obtain the + mutex. */ + if (!nowait) { + lock_mutex_enter_kernel(); + } else if (mutex_enter_nowait(&kernel_mutex)) { + fputs("FAIL TO OBTAIN KERNEL MUTEX, " + "SKIP LOCK INFO PRINTING\n", file); + return(FALSE); + } if (lock_deadlock_found) { fputs("------------------------\n" @@ -4356,6 +4429,7 @@ lock_print_info_summary( "Total number of lock structs in row lock hash table %lu\n", (ulong) lock_get_n_rec_locks()); #endif /* PRINT_NUM_OF_LOCK_STRUCTS */ + return(TRUE); } /*********************************************************************//** @@ -4636,6 +4710,7 @@ lock_rec_queue_validate( ut_a(lock_rec_has_expl(LOCK_X | LOCK_REC_NOT_GAP, block, heap_no, impl_trx)); } +#if 0 } else { /* The kernel mutex may get released temporarily in the @@ -4646,6 +4721,27 @@ lock_rec_queue_validate( (fil_space_t::latch), the following check WILL break latching order and may cause a deadlock of threads. */ + /* NOTE: This is a bogus check that would fail in the + following case: Our transaction is updating a + row. After it has updated the clustered index record, + it goes to a secondary index record and finds someone + else holding an explicit S- or X-lock on that + secondary index record, presumably from a locking + read. Our transaction cannot update the secondary + index immediately, but places a waiting X-lock request + on the secondary index record. There is nothing + illegal in this. The assertion is simply too strong. */ + + /* From the locking point of view, each secondary + index is a separate table. A lock that is held on + secondary index rec does not give any rights to modify + or read the clustered index rec. Therefore, we can + think of the sec index as a separate 'table' from the + clust index 'table'. Conversely, a transaction that + has acquired a lock on and modified a clustered index + record may need to wait for a lock on the + corresponding record in a secondary index. */ + impl_trx = lock_sec_rec_some_has_impl_off_kernel( rec, index, offsets); @@ -4656,6 +4752,7 @@ lock_rec_queue_validate( ut_a(lock_rec_has_expl(LOCK_X | LOCK_REC_NOT_GAP, block, heap_no, impl_trx)); } +#endif } lock = lock_rec_get_first(block, heap_no); @@ -4753,6 +4850,13 @@ loop: || lock->trx->conc_state == TRX_PREPARED || lock->trx->conc_state == TRX_COMMITTED_IN_MEMORY); +# ifdef UNIV_SYNC_DEBUG + /* Only validate the record queues when this thread is not + holding a space->latch. Deadlocks are possible due to + latching order violation when UNIV_DEBUG is defined while + UNIV_SYNC_DEBUG is not. */ + if (!sync_thread_levels_contains(SYNC_FSP)) +# endif /* UNIV_SYNC_DEBUG */ for (i = nth_bit; i < lock_rec_get_n_bits(lock); i++) { if (i == 1 || lock_rec_get_nth_bit(lock, i)) { @@ -4918,7 +5022,7 @@ lock_rec_insert_check_and_lock( } trx = thr_get_trx(thr); - next_rec = page_rec_get_next((rec_t*) rec); + next_rec = page_rec_get_next_const(rec); next_rec_heap_no = page_rec_get_heap_no(next_rec); lock_mutex_enter_kernel(); diff --git a/storage/innodb_plugin/log/log0log.c b/storage/innodb_plugin/log/log0log.c index d5b696074b3..183c24d2147 100644 --- a/storage/innodb_plugin/log/log0log.c +++ b/storage/innodb_plugin/log/log0log.c @@ -1,23 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. - -This program is free software; you can redistribute it and/or modify it under -the terms of the GNU General Public License as published by the Free Software -Foundation; version 2 of the License. - -This program is distributed in the hope that it will be useful, but WITHOUT -ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS -FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. - -You should have received a copy of the GNU General Public License along with -this program; if not, write to the Free Software Foundation, Inc., 59 Temple -Place, Suite 330, Boston, MA 02111-1307 USA - -*****************************************************************************/ -/***************************************************************************** - -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. Copyright (c) 2009, Google Inc. Portions of this file contain modifications contributed and copyrighted by @@ -2013,7 +1996,7 @@ log_checkpoint( return(TRUE); } - ut_ad(log_sys->written_to_all_lsn >= oldest_lsn); + ut_ad(log_sys->flushed_to_disk_lsn >= oldest_lsn); if (log_sys->n_pending_checkpoint_writes > 0) { /* A checkpoint write is running */ @@ -3095,7 +3078,7 @@ loop: if (srv_fast_shutdown < 2 && (srv_error_monitor_active - || srv_lock_timeout_and_monitor_active)) { + || srv_lock_timeout_active || srv_monitor_active)) { mutex_exit(&kernel_mutex); diff --git a/storage/innodb_plugin/log/log0recv.c b/storage/innodb_plugin/log/log0recv.c index ddbc71d4b71..a727d6be768 100644 --- a/storage/innodb_plugin/log/log0recv.c +++ b/storage/innodb_plugin/log/log0recv.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1997, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1997, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -138,7 +138,9 @@ UNIV_INTERN ulint recv_max_parsed_page_no; /** This many frames must be left free in the buffer pool when we scan the log and store the scanned log records in the buffer pool: we will use these free frames to read in pages when we start applying the -log records to the database. */ +log records to the database. +This is the default value. If the actual size of the buffer pool is +larger than 10 MB we'll set this value to 512. */ UNIV_INTERN ulint recv_n_pool_free_frames; /** The maximum lsn we see for a page during the recovery process. If this @@ -239,6 +241,7 @@ recv_sys_mem_free(void) } } +#ifndef UNIV_HOTBACKUP /************************************************************ Reset the state of the recovery system variables. */ UNIV_INTERN @@ -278,6 +281,7 @@ recv_sys_var_init(void) recv_max_page_lsn = 0; } +#endif /* !UNIV_HOTBACKUP */ /************************************************************ Inits the recovery system for a recovery operation. */ @@ -292,20 +296,32 @@ recv_sys_init( return; } + /* Initialize red-black tree for fast insertions into the + flush_list during recovery process. + As this initialization is done while holding the buffer pool + mutex we perform it before acquiring recv_sys->mutex. */ +#ifndef UNIV_HOTBACKUP + buf_flush_init_flush_rbt(); + mutex_enter(&(recv_sys->mutex)); -#ifndef UNIV_HOTBACKUP recv_sys->heap = mem_heap_create_in_buffer(256); #else /* !UNIV_HOTBACKUP */ recv_sys->heap = mem_heap_create(256); recv_is_from_backup = TRUE; #endif /* !UNIV_HOTBACKUP */ + /* Set appropriate value of recv_n_pool_free_frames. */ + if (buf_pool_get_curr_size() >= (10 * 1024 * 1024)) { + /* Buffer pool of size greater than 10 MB. */ + recv_n_pool_free_frames = 512; + } + recv_sys->buf = ut_malloc(RECV_PARSING_BUF_SIZE); recv_sys->len = 0; recv_sys->recovered_offset = 0; - recv_sys->addr_hash = hash_create(available_memory / 64); + recv_sys->addr_hash = hash_create(available_memory / 512); recv_sys->n_addrs = 0; recv_sys->apply_log_recs = FALSE; @@ -345,7 +361,7 @@ recv_sys_empty_hash(void) hash_table_free(recv_sys->addr_hash); mem_heap_empty(recv_sys->heap); - recv_sys->addr_hash = hash_create(buf_pool_get_curr_size() / 256); + recv_sys->addr_hash = hash_create(buf_pool_get_curr_size() / 512); } #ifndef UNIV_HOTBACKUP @@ -370,6 +386,9 @@ recv_sys_debug_free(void) recv_sys->last_block_buf_start = NULL; mutex_exit(&(recv_sys->mutex)); + + /* Free up the flush_rbt. */ + buf_flush_free_flush_rbt(); } # endif /* UNIV_LOG_DEBUG */ @@ -2050,15 +2069,6 @@ recv_parse_log_rec( } #endif /* UNIV_LOG_LSN_DEBUG */ - /* Check that page_no is sensible */ - - if (UNIV_UNLIKELY(*page_no > 0x8FFFFFFFUL)) { - - recv_sys->found_corrupt_log = TRUE; - - return(0); - } - new_ptr = recv_parse_or_apply_log_rec_body(*type, new_ptr, end_ptr, NULL, NULL); if (UNIV_UNLIKELY(new_ptr == NULL)) { @@ -2167,6 +2177,14 @@ recv_report_corrupt_log( putc('\n', stderr); } +#ifndef UNIV_HOTBACKUP + if (!srv_force_recovery) { + fputs("InnoDB: Set innodb_force_recovery" + " to ignore this error.\n", stderr); + ut_error; + } +#endif /* !UNIV_HOTBACKUP */ + fputs("InnoDB: WARNING: the log file may have been corrupt and it\n" "InnoDB: is possible that the log scan did not proceed\n" "InnoDB: far enough in recovery! Please run CHECK TABLE\n" @@ -2556,7 +2574,7 @@ recv_scan_log_recs( ut_ad(start_lsn % OS_FILE_LOG_BLOCK_SIZE == 0); ut_ad(len % OS_FILE_LOG_BLOCK_SIZE == 0); - ut_ad(len > 0); + ut_ad(len >= OS_FILE_LOG_BLOCK_SIZE); ut_a(store_to_hash <= TRUE); finished = FALSE; @@ -2681,6 +2699,16 @@ recv_scan_log_recs( recv_sys->found_corrupt_log = TRUE; +#ifndef UNIV_HOTBACKUP + if (!srv_force_recovery) { + fputs("InnoDB: Set" + " innodb_force_recovery" + " to ignore this error.\n", + stderr); + ut_error; + } +#endif /* !UNIV_HOTBACKUP */ + } else if (!recv_sys->found_corrupt_log) { more_data = recv_sys_add_to_parsing_buf( log_block, scanned_lsn); @@ -3210,8 +3238,6 @@ void recv_recovery_from_checkpoint_finish(void) /*======================================*/ { - int i; - /* Apply the hashed log records to the respective file pages */ if (srv_force_recovery < SRV_FORCE_NO_LOG_REDO) { @@ -3259,9 +3285,16 @@ recv_recovery_from_checkpoint_finish(void) The data dictionary latch should guarantee that there is at most one data dictionary transaction active at a time. */ trx_rollback_or_clean_recovered(FALSE); +} - /* Drop partially created indexes. */ - row_merge_drop_temp_indexes(); +/********************************************************//** +Initiates the rollback of active transactions. */ +UNIV_INTERN +void +recv_recovery_rollback_active(void) +/*===============================*/ +{ + int i; #ifdef UNIV_SYNC_DEBUG /* Wait for a while so that created threads have time to suspend @@ -3271,6 +3304,11 @@ recv_recovery_from_checkpoint_finish(void) /* Switch latching order checks on in sync0sync.c */ sync_order_checks_on = TRUE; #endif + /* Drop partially created indexes. */ + row_merge_drop_temp_indexes(); + /* Drop temporary tables. */ + row_mysql_drop_temp_tables(); + if (srv_force_recovery < SRV_FORCE_NO_TRX_UNDO) { /* Rollback the uncommitted transactions which have no user session */ diff --git a/storage/innodb_plugin/mem/mem0dbg.c b/storage/innodb_plugin/mem/mem0dbg.c index 01eda20ec45..1cd2ff15bab 100644 --- a/storage/innodb_plugin/mem/mem0dbg.c +++ b/storage/innodb_plugin/mem/mem0dbg.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1994, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1994, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -180,6 +180,10 @@ mem_close(void) { mem_pool_free(mem_comm_pool); mem_comm_pool = NULL; +#ifdef UNIV_MEM_DEBUG + mutex_free(&mem_hash_mutex); + mem_hash_initialized = FALSE; +#endif /* UNIV_MEM_DEBUG */ } #endif /* !UNIV_HOTBACKUP */ diff --git a/storage/innodb_plugin/mem/mem0mem.c b/storage/innodb_plugin/mem/mem0mem.c index ccb2fd8a7b4..c0ce8a3e1ac 100644 --- a/storage/innodb_plugin/mem/mem0mem.c +++ b/storage/innodb_plugin/mem/mem0mem.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1994, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1994, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -383,6 +383,20 @@ mem_heap_create_block( mem_block_set_free(block, MEM_BLOCK_HEADER_SIZE); mem_block_set_start(block, MEM_BLOCK_HEADER_SIZE); + if (UNIV_UNLIKELY(heap == NULL)) { + /* This is the first block of the heap. The field + total_size should be initialized here */ + block->total_size = len; + } else { + /* Not the first allocation for the heap. This block's + total_length field should be set to undefined. */ + ut_d(block->total_size = ULINT_UNDEFINED); + UNIV_MEM_INVALID(&block->total_size, + sizeof block->total_size); + + heap->total_size += len; + } + ut_ad((ulint)MEM_BLOCK_HEADER_SIZE < len); return(block); @@ -471,6 +485,10 @@ mem_heap_block_free( mem_pool_mutex_exit(); #endif + + ut_ad(heap->total_size >= block->len); + heap->total_size -= block->len; + type = heap->type; len = block->len; block->magic_n = MEM_FREED_BLOCK_MAGIC_N; diff --git a/storage/innodb_plugin/mysql-test/ctype_innodb_like.inc b/storage/innodb_plugin/mysql-test/ctype_innodb_like.inc deleted file mode 100644 index ae43342885a..00000000000 --- a/storage/innodb_plugin/mysql-test/ctype_innodb_like.inc +++ /dev/null @@ -1,21 +0,0 @@ -# -# Bug#11650: LIKE pattern matching using prefix index -# doesn't return correct result -# ---disable_warnings -# -# This query creates a column using -# character_set_connection and -# collation_connection. -# -create table t1 engine=innodb select repeat('a',50) as c1; ---enable_warnings -alter table t1 add index(c1(5)); - -insert into t1 values ('abcdefg'),('abcde100'),('abcde110'),('abcde111'); -select collation(c1) from t1 limit 1; -select c1 from t1 where c1 like 'abcdef%' order by c1; -select c1 from t1 where c1 like 'abcde1%' order by c1; -select c1 from t1 where c1 like 'abcde11%' order by c1; -select c1 from t1 where c1 like 'abcde111%' order by c1; -drop table t1; diff --git a/storage/innodb_plugin/mysql-test/have_innodb.inc b/storage/innodb_plugin/mysql-test/have_innodb.inc deleted file mode 100644 index 8944cc46f3e..00000000000 --- a/storage/innodb_plugin/mysql-test/have_innodb.inc +++ /dev/null @@ -1,4 +0,0 @@ -disable_query_log; ---require r/true.require -select (support = 'YES' or support = 'DEFAULT' or support = 'ENABLED') as `TRUE` from information_schema.engines where engine = 'innodb'; -enable_query_log; diff --git a/storage/innodb_plugin/mysql-test/innodb-analyze.result b/storage/innodb_plugin/mysql-test/innodb-analyze.result deleted file mode 100644 index 2aee004a2d6..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-analyze.result +++ /dev/null @@ -1,2 +0,0 @@ -Variable_name Value -innodb_stats_sample_pages 1 diff --git a/storage/innodb_plugin/mysql-test/innodb-analyze.test b/storage/innodb_plugin/mysql-test/innodb-analyze.test deleted file mode 100644 index 9bdb9db697c..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-analyze.test +++ /dev/null @@ -1,65 +0,0 @@ -# -# Test that mysqld does not crash when running ANALYZE TABLE with -# different values of the parameter innodb_stats_sample_pages. -# - --- source include/have_innodb.inc - -# we care only that the following SQL commands do not produce errors -# and do not crash the server --- disable_query_log --- disable_result_log --- enable_warnings - -let $sample_pages=`select @@innodb_stats_sample_pages`; -SET GLOBAL innodb_stats_sample_pages=0; - -# check that the value has been adjusted to 1 --- enable_result_log -SHOW VARIABLES LIKE 'innodb_stats_sample_pages'; --- disable_result_log - -CREATE TABLE innodb_analyze ( - a INT, - b INT, - KEY(a), - KEY(b,a) -) ENGINE=InnoDB; - -# test with empty table - -ANALYZE TABLE innodb_analyze; - -SET GLOBAL innodb_stats_sample_pages=2; -ANALYZE TABLE innodb_analyze; - -SET GLOBAL innodb_stats_sample_pages=4; -ANALYZE TABLE innodb_analyze; - -SET GLOBAL innodb_stats_sample_pages=8; -ANALYZE TABLE innodb_analyze; - -SET GLOBAL innodb_stats_sample_pages=16; -ANALYZE TABLE innodb_analyze; - -INSERT INTO innodb_analyze VALUES -(1,1), (1,1), (1,2), (1,3), (1,4), (1,5), -(8,1), (8,8), (8,2), (7,1), (1,4), (3,5); - -SET GLOBAL innodb_stats_sample_pages=1; -ANALYZE TABLE innodb_analyze; - -SET GLOBAL innodb_stats_sample_pages=2; -ANALYZE TABLE innodb_analyze; - -SET GLOBAL innodb_stats_sample_pages=4; -ANALYZE TABLE innodb_analyze; - -SET GLOBAL innodb_stats_sample_pages=8; -ANALYZE TABLE innodb_analyze; - -SET GLOBAL innodb_stats_sample_pages=16; -ANALYZE TABLE innodb_analyze; - -DROP TABLE innodb_analyze; -EVAL SET GLOBAL innodb_stats_sample_pages=$sample_pages; diff --git a/storage/innodb_plugin/mysql-test/innodb-autoinc.result b/storage/innodb_plugin/mysql-test/innodb-autoinc.result deleted file mode 100644 index d2e8eb19e0c..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-autoinc.result +++ /dev/null @@ -1,891 +0,0 @@ -drop table if exists t1; -CREATE TABLE t1 (c1 BIGINT PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (9223372036854775807, null); -INSERT INTO t1 (c2) VALUES ('innodb'); -Got one of the listed errors -SELECT * FROM t1; -c1 c2 -9223372036854775807 NULL -DROP TABLE t1; -CREATE TABLE t1 (c1 TINYINT PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (127, null); -INSERT INTO t1 (c2) VALUES ('innodb'); -Got one of the listed errors -SELECT * FROM t1; -c1 c2 -127 NULL -DROP TABLE t1; -CREATE TABLE t1 (c1 TINYINT UNSIGNED PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (255, null); -INSERT INTO t1 (c2) VALUES ('innodb'); -Got one of the listed errors -SELECT * FROM t1; -c1 c2 -255 NULL -DROP TABLE t1; -CREATE TABLE t1 (c1 SMALLINT PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (32767, null); -INSERT INTO t1 (c2) VALUES ('innodb'); -Got one of the listed errors -SELECT * FROM t1; -c1 c2 -32767 NULL -DROP TABLE t1; -CREATE TABLE t1 (c1 SMALLINT UNSIGNED PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (65535, null); -INSERT INTO t1 (c2) VALUES ('innodb'); -Got one of the listed errors -SELECT * FROM t1; -c1 c2 -65535 NULL -DROP TABLE t1; -CREATE TABLE t1 (c1 MEDIUMINT PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (8388607, null); -INSERT INTO t1 (c2) VALUES ('innodb'); -Got one of the listed errors -SELECT * FROM t1; -c1 c2 -8388607 NULL -DROP TABLE t1; -CREATE TABLE t1 (c1 MEDIUMINT UNSIGNED PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (16777215, null); -INSERT INTO t1 (c2) VALUES ('innodb'); -Got one of the listed errors -SELECT * FROM t1; -c1 c2 -16777215 NULL -DROP TABLE t1; -CREATE TABLE t1 (c1 INT PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (2147483647, null); -INSERT INTO t1 (c2) VALUES ('innodb'); -Got one of the listed errors -SELECT * FROM t1; -c1 c2 -2147483647 NULL -DROP TABLE t1; -CREATE TABLE t1 (c1 INT UNSIGNED PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (4294967295, null); -INSERT INTO t1 (c2) VALUES ('innodb'); -Got one of the listed errors -SELECT * FROM t1; -c1 c2 -4294967295 NULL -DROP TABLE t1; -CREATE TABLE t1 (c1 BIGINT PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (9223372036854775807, null); -INSERT INTO t1 (c2) VALUES ('innodb'); -Got one of the listed errors -SELECT * FROM t1; -c1 c2 -9223372036854775807 NULL -DROP TABLE t1; -CREATE TABLE t1 (c1 BIGINT UNSIGNED PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (18446744073709551615, null); -INSERT INTO t1 (c2) VALUES ('innodb'); -Got one of the listed errors -SELECT * FROM t1; -c1 c2 -18446744073709551615 NULL -DROP TABLE t1; -CREATE TABLE t1(c1 INT PRIMARY KEY AUTO_INCREMENT) ENGINE=InnoDB; -INSERT INTO t1 VALUES (1), (2), (3); -INSERT INTO t1 VALUES (NULL), (NULL), (NULL); -SELECT c1 FROM t1; -c1 -1 -2 -3 -4 -5 -6 -SHOW CREATE TABLE t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `c1` int(11) NOT NULL AUTO_INCREMENT, - PRIMARY KEY (`c1`) -) ENGINE=InnoDB AUTO_INCREMENT=7 DEFAULT CHARSET=latin1 -TRUNCATE TABLE t1; -SHOW CREATE TABLE t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `c1` int(11) NOT NULL AUTO_INCREMENT, - PRIMARY KEY (`c1`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -INSERT INTO t1 VALUES (1), (2), (3); -INSERT INTO t1 VALUES (NULL), (NULL), (NULL); -SELECT c1 FROM t1; -c1 -1 -2 -3 -4 -5 -6 -SHOW CREATE TABLE t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `c1` int(11) NOT NULL AUTO_INCREMENT, - PRIMARY KEY (`c1`) -) ENGINE=InnoDB AUTO_INCREMENT=7 DEFAULT CHARSET=latin1 -DROP TABLE t1; -CREATE TABLE t1(c1 INT PRIMARY KEY AUTO_INCREMENT) ENGINE=InnoDB; -INSERT INTO t1 VALUES (1), (2), (3); -INSERT INTO t1 VALUES (NULL), (NULL), (NULL); -SELECT c1 FROM t1; -c1 -1 -2 -3 -4 -5 -6 -SHOW CREATE TABLE t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `c1` int(11) NOT NULL AUTO_INCREMENT, - PRIMARY KEY (`c1`) -) ENGINE=InnoDB AUTO_INCREMENT=7 DEFAULT CHARSET=latin1 -DELETE FROM t1; -SHOW CREATE TABLE t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `c1` int(11) NOT NULL AUTO_INCREMENT, - PRIMARY KEY (`c1`) -) ENGINE=InnoDB AUTO_INCREMENT=7 DEFAULT CHARSET=latin1 -INSERT INTO t1 VALUES (1), (2), (3); -INSERT INTO t1 VALUES (NULL), (NULL), (NULL); -SELECT c1 FROM t1; -c1 -1 -2 -3 -7 -8 -9 -SHOW CREATE TABLE t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `c1` int(11) NOT NULL AUTO_INCREMENT, - PRIMARY KEY (`c1`) -) ENGINE=InnoDB AUTO_INCREMENT=10 DEFAULT CHARSET=latin1 -DROP TABLE t1; -DROP TABLE IF EXISTS t1; -Warnings: -Note 1051 Unknown table 't1' -CREATE TABLE t1 (c1 INT AUTO_INCREMENT, c2 INT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (NULL, 1); -DELETE FROM t1 WHERE c1 = 1; -INSERT INTO t1 VALUES (2,1); -INSERT INTO t1 VALUES (NULL,8); -SELECT * FROM t1; -c1 c2 -2 1 -3 8 -DROP TABLE t1; -DROP TABLE IF EXISTS t1; -Warnings: -Note 1051 Unknown table 't1' -CREATE TABLE t1 (c1 INT AUTO_INCREMENT, c2 INT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (NULL, 1); -DELETE FROM t1 WHERE c1 = 1; -INSERT INTO t1 VALUES (2,1), (NULL, 8); -INSERT INTO t1 VALUES (NULL,9); -SELECT * FROM t1; -c1 c2 -2 1 -3 8 -5 9 -DROP TABLE t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=100, @@SESSION.AUTO_INCREMENT_OFFSET=10; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 100 -auto_increment_offset 10 -DROP TABLE IF EXISTS t1; -Warnings: -Note 1051 Unknown table 't1' -CREATE TABLE t1 (c1 INT AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (NULL),(5),(NULL); -INSERT INTO t1 VALUES (250),(NULL); -SELECT * FROM t1; -c1 -5 -10 -110 -250 -310 -INSERT INTO t1 VALUES (1000); -SET @@INSERT_ID=400; -INSERT INTO t1 VALUES(NULL),(NULL); -SELECT * FROM t1; -c1 -5 -10 -110 -250 -310 -400 -410 -1000 -DROP TABLE t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 1 -auto_increment_offset 1 -DROP TABLE IF EXISTS t1; -Warnings: -Note 1051 Unknown table 't1' -CREATE TABLE t1 (c1 INT AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES(0); -SELECT * FROM t1; -c1 -1 -SET @@SESSION.AUTO_INCREMENT_INCREMENT=100, @@SESSION.AUTO_INCREMENT_OFFSET=10; -INSERT INTO t1 VALUES (-1), (NULL),(2),(NULL); -INSERT INTO t1 VALUES (250),(NULL); -SELECT * FROM t1; -c1 --1 -1 -2 -10 -110 -250 -410 -SET @@INSERT_ID=400; -INSERT INTO t1 VALUES(NULL),(NULL); -Got one of the listed errors -SELECT * FROM t1; -c1 --1 -1 -2 -10 -110 -250 -410 -DROP TABLE t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 1 -auto_increment_offset 1 -DROP TABLE IF EXISTS t1; -Warnings: -Note 1051 Unknown table 't1' -CREATE TABLE t1 (c1 INT AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES(-1); -SELECT * FROM t1; -c1 --1 -SET @@SESSION.AUTO_INCREMENT_INCREMENT=100, @@SESSION.AUTO_INCREMENT_OFFSET=10; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 100 -auto_increment_offset 10 -INSERT INTO t1 VALUES (-2), (NULL),(2),(NULL); -INSERT INTO t1 VALUES (250),(NULL); -SELECT * FROM t1; -c1 --2 --1 -1 -2 -10 -250 -310 -INSERT INTO t1 VALUES (1000); -SET @@INSERT_ID=400; -INSERT INTO t1 VALUES(NULL),(NULL); -SELECT * FROM t1; -c1 --2 --1 -1 -2 -10 -250 -310 -400 -410 -1000 -DROP TABLE t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 1 -auto_increment_offset 1 -DROP TABLE IF EXISTS t1; -Warnings: -Note 1051 Unknown table 't1' -CREATE TABLE t1 (c1 INT UNSIGNED AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES(-1); -Warnings: -Warning 1264 Out of range value for column 'c1' at row 1 -SELECT * FROM t1; -c1 -1 -SET @@SESSION.AUTO_INCREMENT_INCREMENT=100, @@SESSION.AUTO_INCREMENT_OFFSET=10; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 100 -auto_increment_offset 10 -INSERT INTO t1 VALUES (-2); -Warnings: -Warning 1264 Out of range value for column 'c1' at row 1 -INSERT INTO t1 VALUES (NULL); -INSERT INTO t1 VALUES (2); -INSERT INTO t1 VALUES (NULL); -INSERT INTO t1 VALUES (250); -INSERT INTO t1 VALUES (NULL); -SELECT * FROM t1; -c1 -1 -2 -10 -110 -210 -250 -310 -INSERT INTO t1 VALUES (1000); -SET @@INSERT_ID=400; -INSERT INTO t1 VALUES(NULL); -INSERT INTO t1 VALUES(NULL); -SELECT * FROM t1; -c1 -1 -2 -10 -110 -210 -250 -310 -400 -1000 -1010 -DROP TABLE t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 1 -auto_increment_offset 1 -DROP TABLE IF EXISTS t1; -Warnings: -Note 1051 Unknown table 't1' -CREATE TABLE t1 (c1 INT UNSIGNED AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES(-1); -Warnings: -Warning 1264 Out of range value for column 'c1' at row 1 -SELECT * FROM t1; -c1 -1 -SET @@SESSION.AUTO_INCREMENT_INCREMENT=100, @@SESSION.AUTO_INCREMENT_OFFSET=10; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 100 -auto_increment_offset 10 -INSERT INTO t1 VALUES (-2),(NULL),(2),(NULL); -Warnings: -Warning 1264 Out of range value for column 'c1' at row 1 -INSERT INTO t1 VALUES (250),(NULL); -SELECT * FROM t1; -c1 -1 -2 -10 -110 -210 -250 -410 -INSERT INTO t1 VALUES (1000); -SET @@INSERT_ID=400; -INSERT INTO t1 VALUES(NULL),(NULL); -Got one of the listed errors -SELECT * FROM t1; -c1 -1 -2 -10 -110 -210 -250 -410 -1000 -DROP TABLE t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 1 -auto_increment_offset 1 -DROP TABLE IF EXISTS t1; -Warnings: -Note 1051 Unknown table 't1' -CREATE TABLE t1 (c1 BIGINT AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES(NULL); -INSERT INTO t1 VALUES (9223372036854775794); -SELECT * FROM t1; -c1 -1 -9223372036854775794 -SET @@SESSION.AUTO_INCREMENT_INCREMENT=2, @@SESSION.AUTO_INCREMENT_OFFSET=10; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 2 -auto_increment_offset 10 -INSERT INTO t1 VALUES (NULL),(NULL),(NULL),(NULL),(NULL),(NULL); -SELECT * FROM t1; -c1 -1 -9223372036854775794 -9223372036854775796 -9223372036854775798 -9223372036854775800 -9223372036854775802 -9223372036854775804 -9223372036854775806 -DROP TABLE t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 1 -auto_increment_offset 1 -DROP TABLE IF EXISTS t1; -Warnings: -Note 1051 Unknown table 't1' -CREATE TABLE t1 (c1 BIGINT UNSIGNED AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES(NULL); -INSERT INTO t1 VALUES (18446744073709551603); -SELECT * FROM t1; -c1 -1 -18446744073709551603 -SET @@SESSION.AUTO_INCREMENT_INCREMENT=2, @@SESSION.AUTO_INCREMENT_OFFSET=10; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 2 -auto_increment_offset 10 -INSERT INTO t1 VALUES (NULL),(NULL),(NULL),(NULL),(NULL),(NULL); -SELECT * FROM t1; -c1 -1 -18446744073709551603 -18446744073709551604 -18446744073709551606 -18446744073709551608 -18446744073709551610 -18446744073709551612 -18446744073709551614 -DROP TABLE t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 1 -auto_increment_offset 1 -DROP TABLE IF EXISTS t1; -Warnings: -Note 1051 Unknown table 't1' -CREATE TABLE t1 (c1 BIGINT UNSIGNED AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES(NULL); -INSERT INTO t1 VALUES (18446744073709551603); -SELECT * FROM t1; -c1 -1 -18446744073709551603 -SET @@SESSION.AUTO_INCREMENT_INCREMENT=5, @@SESSION.AUTO_INCREMENT_OFFSET=7; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 5 -auto_increment_offset 7 -INSERT INTO t1 VALUES (NULL),(NULL); -SELECT * FROM t1; -c1 -1 -18446744073709551603 -18446744073709551607 -18446744073709551612 -DROP TABLE t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 1 -auto_increment_offset 1 -DROP TABLE IF EXISTS t1; -Warnings: -Note 1051 Unknown table 't1' -CREATE TABLE t1 (c1 BIGINT AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES(NULL); -INSERT INTO t1 VALUES(-9223372036854775806); -INSERT INTO t1 VALUES(-9223372036854775807); -INSERT INTO t1 VALUES(-9223372036854775808); -SELECT * FROM t1; -c1 --9223372036854775808 --9223372036854775807 --9223372036854775806 -1 -SET @@SESSION.AUTO_INCREMENT_INCREMENT=3, @@SESSION.AUTO_INCREMENT_OFFSET=3; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 3 -auto_increment_offset 3 -INSERT INTO t1 VALUES (NULL),(NULL), (NULL); -SELECT * FROM t1; -c1 --9223372036854775808 --9223372036854775807 --9223372036854775806 -1 -3 -6 -9 -DROP TABLE t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 1 -auto_increment_offset 1 -DROP TABLE IF EXISTS t1; -Warnings: -Note 1051 Unknown table 't1' -CREATE TABLE t1 (c1 BIGINT UNSIGNED AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES(NULL); -INSERT INTO t1 VALUES (18446744073709551610); -SELECT * FROM t1; -c1 -1 -18446744073709551610 -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1152921504606846976, @@SESSION.AUTO_INCREMENT_OFFSET=1152921504606846976; -Warnings: -Warning 1292 Truncated incorrect auto_increment_increment value: '1152921504606846976' -Warning 1292 Truncated incorrect auto_increment_offset value: '1152921504606846976' -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 65535 -auto_increment_offset 65535 -INSERT INTO t1 VALUES (NULL); -SELECT * FROM t1; -c1 -1 -18446744073709551610 -18446744073709551615 -DROP TABLE t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -Variable_name Value -auto_increment_increment 1 -auto_increment_offset 1 -CREATE TABLE t1 (c1 DOUBLE NOT NULL AUTO_INCREMENT, c2 INT, PRIMARY KEY (c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES(NULL, 1); -INSERT INTO t1 VALUES(NULL, 2); -SELECT * FROM t1; -c1 c2 -1 1 -2 2 -ALTER TABLE t1 CHANGE c1 c1 SERIAL; -SELECT * FROM t1; -c1 c2 -1 1 -2 2 -INSERT INTO t1 VALUES(NULL, 3); -INSERT INTO t1 VALUES(NULL, 4); -SELECT * FROM t1; -c1 c2 -1 1 -2 2 -3 3 -4 4 -DROP TABLE IF EXISTS t1; -CREATE TABLE t1 (c1 FLOAT NOT NULL AUTO_INCREMENT, c2 INT, PRIMARY KEY (c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES(NULL, 1); -INSERT INTO t1 VALUES(NULL, 2); -SELECT * FROM t1; -c1 c2 -1 1 -2 2 -ALTER TABLE t1 CHANGE c1 c1 SERIAL; -SELECT * FROM t1; -c1 c2 -1 1 -2 2 -INSERT INTO t1 VALUES(NULL, 3); -INSERT INTO t1 VALUES(NULL, 4); -SELECT * FROM t1; -c1 c2 -1 1 -2 2 -3 3 -4 4 -DROP TABLE t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=5; -DROP TABLE IF EXISTS t1; -Warnings: -Note 1051 Unknown table 't1' -DROP TABLE IF EXISTS t2; -Warnings: -Note 1051 Unknown table 't2' -CREATE TABLE t1 ( -a INT(11) UNSIGNED NOT NULL AUTO_INCREMENT, -b INT(10) UNSIGNED NOT NULL, -c ENUM('FALSE','TRUE') DEFAULT NULL, -PRIMARY KEY (a)) ENGINE = InnoDB; -CREATE TABLE t2 ( -m INT(11) UNSIGNED NOT NULL AUTO_INCREMENT, -n INT(10) UNSIGNED NOT NULL, -o enum('FALSE','TRUE') DEFAULT NULL, -PRIMARY KEY (m)) ENGINE = InnoDB; -INSERT INTO t2 (n,o) VALUES -(1 , 'true'), (1 , 'false'), (2 , 'true'), (2 , 'false'), (3 , 'true'), -(3 , 'false'), (4 , 'true'), (4 , 'false'), (5 , 'true'), (5 , 'false'); -SHOW CREATE TABLE t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `m` int(11) unsigned NOT NULL AUTO_INCREMENT, - `n` int(10) unsigned NOT NULL, - `o` enum('FALSE','TRUE') DEFAULT NULL, - PRIMARY KEY (`m`) -) ENGINE=InnoDB AUTO_INCREMENT=15 DEFAULT CHARSET=latin1 -INSERT INTO t1 (b,c) SELECT n,o FROM t2 ; -SHOW CREATE TABLE t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) unsigned NOT NULL AUTO_INCREMENT, - `b` int(10) unsigned NOT NULL, - `c` enum('FALSE','TRUE') DEFAULT NULL, - PRIMARY KEY (`a`) -) ENGINE=InnoDB AUTO_INCREMENT=13 DEFAULT CHARSET=latin1 -INSERT INTO t1 (b,c) SELECT n,o FROM t2 ; -SELECT * FROM t1; -a b c -1 1 TRUE -2 1 FALSE -3 2 TRUE -4 2 FALSE -5 3 TRUE -6 3 FALSE -7 4 TRUE -8 4 FALSE -9 5 TRUE -10 5 FALSE -13 1 TRUE -14 1 FALSE -15 2 TRUE -16 2 FALSE -17 3 TRUE -18 3 FALSE -19 4 TRUE -20 4 FALSE -21 5 TRUE -22 5 FALSE -SHOW CREATE TABLE t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) unsigned NOT NULL AUTO_INCREMENT, - `b` int(10) unsigned NOT NULL, - `c` enum('FALSE','TRUE') DEFAULT NULL, - PRIMARY KEY (`a`) -) ENGINE=InnoDB AUTO_INCREMENT=23 DEFAULT CHARSET=latin1 -INSERT INTO t1 (b,c) SELECT n,o FROM t2 WHERE o = 'false'; -SELECT * FROM t1; -a b c -1 1 TRUE -2 1 FALSE -3 2 TRUE -4 2 FALSE -5 3 TRUE -6 3 FALSE -7 4 TRUE -8 4 FALSE -9 5 TRUE -10 5 FALSE -13 1 TRUE -14 1 FALSE -15 2 TRUE -16 2 FALSE -17 3 TRUE -18 3 FALSE -19 4 TRUE -20 4 FALSE -21 5 TRUE -22 5 FALSE -23 1 FALSE -24 2 FALSE -25 3 FALSE -26 4 FALSE -27 5 FALSE -SHOW CREATE TABLE t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) unsigned NOT NULL AUTO_INCREMENT, - `b` int(10) unsigned NOT NULL, - `c` enum('FALSE','TRUE') DEFAULT NULL, - PRIMARY KEY (`a`) -) ENGINE=InnoDB AUTO_INCREMENT=30 DEFAULT CHARSET=latin1 -INSERT INTO t1 (b,c) SELECT n,o FROM t2 WHERE o = 'false'; -SELECT * FROM t1; -a b c -1 1 TRUE -2 1 FALSE -3 2 TRUE -4 2 FALSE -5 3 TRUE -6 3 FALSE -7 4 TRUE -8 4 FALSE -9 5 TRUE -10 5 FALSE -13 1 TRUE -14 1 FALSE -15 2 TRUE -16 2 FALSE -17 3 TRUE -18 3 FALSE -19 4 TRUE -20 4 FALSE -21 5 TRUE -22 5 FALSE -23 1 FALSE -24 2 FALSE -25 3 FALSE -26 4 FALSE -27 5 FALSE -30 1 FALSE -31 2 FALSE -32 3 FALSE -33 4 FALSE -34 5 FALSE -SHOW CREATE TABLE t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) unsigned NOT NULL AUTO_INCREMENT, - `b` int(10) unsigned NOT NULL, - `c` enum('FALSE','TRUE') DEFAULT NULL, - PRIMARY KEY (`a`) -) ENGINE=InnoDB AUTO_INCREMENT=37 DEFAULT CHARSET=latin1 -INSERT INTO t1 (b,c) SELECT n,o FROM t2 WHERE o = 'false'; -SHOW CREATE TABLE t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) unsigned NOT NULL AUTO_INCREMENT, - `b` int(10) unsigned NOT NULL, - `c` enum('FALSE','TRUE') DEFAULT NULL, - PRIMARY KEY (`a`) -) ENGINE=InnoDB AUTO_INCREMENT=44 DEFAULT CHARSET=latin1 -INSERT INTO t1 (b,c) SELECT n,o FROM t2 WHERE o = 'false'; -SHOW CREATE TABLE t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) unsigned NOT NULL AUTO_INCREMENT, - `b` int(10) unsigned NOT NULL, - `c` enum('FALSE','TRUE') DEFAULT NULL, - PRIMARY KEY (`a`) -) ENGINE=InnoDB AUTO_INCREMENT=51 DEFAULT CHARSET=latin1 -INSERT INTO t1 (b,c) SELECT n,o FROM t2 WHERE o = 'false'; -SELECT * FROM t1; -a b c -1 1 TRUE -2 1 FALSE -3 2 TRUE -4 2 FALSE -5 3 TRUE -6 3 FALSE -7 4 TRUE -8 4 FALSE -9 5 TRUE -10 5 FALSE -13 1 TRUE -14 1 FALSE -15 2 TRUE -16 2 FALSE -17 3 TRUE -18 3 FALSE -19 4 TRUE -20 4 FALSE -21 5 TRUE -22 5 FALSE -23 1 FALSE -24 2 FALSE -25 3 FALSE -26 4 FALSE -27 5 FALSE -30 1 FALSE -31 2 FALSE -32 3 FALSE -33 4 FALSE -34 5 FALSE -37 1 FALSE -38 2 FALSE -39 3 FALSE -40 4 FALSE -41 5 FALSE -44 1 FALSE -45 2 FALSE -46 3 FALSE -47 4 FALSE -48 5 FALSE -51 1 FALSE -52 2 FALSE -53 3 FALSE -54 4 FALSE -55 5 FALSE -SHOW CREATE TABLE t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) unsigned NOT NULL AUTO_INCREMENT, - `b` int(10) unsigned NOT NULL, - `c` enum('FALSE','TRUE') DEFAULT NULL, - PRIMARY KEY (`a`) -) ENGINE=InnoDB AUTO_INCREMENT=58 DEFAULT CHARSET=latin1 -DROP TABLE t1; -DROP TABLE t2; -DROP TABLE IF EXISTS t1; -Warnings: -Note 1051 Unknown table 't1' -DROP TABLE IF EXISTS t2; -Warnings: -Note 1051 Unknown table 't2' -CREATE TABLE t1( -c1 INT(10) UNSIGNED NOT NULL AUTO_INCREMENT -PRIMARY KEY) ENGINE=InnoDB; -INSERT INTO t1 VALUES (NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL); -CREATE TABLE t2( -c1 TINYINT(3) UNSIGNED NOT NULL AUTO_INCREMENT -PRIMARY KEY) ENGINE=InnoDB; -INSERT INTO t2 SELECT c1 FROM t1; -Got one of the listed errors -INSERT INTO t2 SELECT NULL FROM t1; -Got one of the listed errors -DROP TABLE t1; -DROP TABLE t2; -CREATE TABLE t1 (c1 INT PRIMARY KEY AUTO_INCREMENT) ENGINE=InnoDB; -INSERT INTO t1 VALUES (null); -INSERT INTO t1 VALUES (null); -ALTER TABLE t1 CHANGE c1 d1 INT NOT NULL AUTO_INCREMENT; -SELECT * FROM t1; -d1 -1 -3 -SELECT * FROM t1; -d1 -1 -3 -INSERT INTO t1 VALUES(null); -Got one of the listed errors -ALTER TABLE t1 AUTO_INCREMENT = 3; -INSERT INTO t1 VALUES(null); -SELECT * FROM t1; -d1 -1 -3 -4 -DROP TABLE t1; diff --git a/storage/innodb_plugin/mysql-test/innodb-autoinc.test b/storage/innodb_plugin/mysql-test/innodb-autoinc.test deleted file mode 100644 index 61c42f45733..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-autoinc.test +++ /dev/null @@ -1,500 +0,0 @@ --- source include/have_innodb.inc -# embedded server ignores 'delayed', so skip this --- source include/not_embedded.inc - ---disable_warnings -drop table if exists t1; ---enable_warnings - -# -# Bug #34335 -# -CREATE TABLE t1 (c1 BIGINT PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (9223372036854775807, null); --- error ER_DUP_ENTRY,1062 -INSERT INTO t1 (c2) VALUES ('innodb'); -SELECT * FROM t1; -DROP TABLE t1; -# -## Test AUTOINC overflow -## - -# TINYINT -CREATE TABLE t1 (c1 TINYINT PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (127, null); --- error ER_DUP_ENTRY,1062 -INSERT INTO t1 (c2) VALUES ('innodb'); -SELECT * FROM t1; -DROP TABLE t1; - -CREATE TABLE t1 (c1 TINYINT UNSIGNED PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (255, null); --- error ER_DUP_ENTRY,1062 -INSERT INTO t1 (c2) VALUES ('innodb'); -SELECT * FROM t1; -DROP TABLE t1; -# -# SMALLINT -# -CREATE TABLE t1 (c1 SMALLINT PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (32767, null); --- error ER_DUP_ENTRY,1062 -INSERT INTO t1 (c2) VALUES ('innodb'); -SELECT * FROM t1; -DROP TABLE t1; - -CREATE TABLE t1 (c1 SMALLINT UNSIGNED PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (65535, null); --- error ER_DUP_ENTRY,1062 -INSERT INTO t1 (c2) VALUES ('innodb'); -SELECT * FROM t1; -DROP TABLE t1; -# -# MEDIUMINT -# -CREATE TABLE t1 (c1 MEDIUMINT PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (8388607, null); --- error ER_DUP_ENTRY,1062 -INSERT INTO t1 (c2) VALUES ('innodb'); -SELECT * FROM t1; -DROP TABLE t1; - -CREATE TABLE t1 (c1 MEDIUMINT UNSIGNED PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (16777215, null); --- error ER_DUP_ENTRY,1062 -INSERT INTO t1 (c2) VALUES ('innodb'); -SELECT * FROM t1; -DROP TABLE t1; -# -# INT -# -CREATE TABLE t1 (c1 INT PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (2147483647, null); --- error ER_DUP_ENTRY,1062 -INSERT INTO t1 (c2) VALUES ('innodb'); -SELECT * FROM t1; -DROP TABLE t1; - -CREATE TABLE t1 (c1 INT UNSIGNED PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (4294967295, null); --- error ER_DUP_ENTRY,1062 -INSERT INTO t1 (c2) VALUES ('innodb'); -SELECT * FROM t1; -DROP TABLE t1; -# -# BIGINT -# -CREATE TABLE t1 (c1 BIGINT PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (9223372036854775807, null); --- error ER_DUP_ENTRY,1062 -INSERT INTO t1 (c2) VALUES ('innodb'); -SELECT * FROM t1; -DROP TABLE t1; - -CREATE TABLE t1 (c1 BIGINT UNSIGNED PRIMARY KEY AUTO_INCREMENT, c2 VARCHAR(10)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (18446744073709551615, null); --- error ER_AUTOINC_READ_FAILED,1467 -INSERT INTO t1 (c2) VALUES ('innodb'); -SELECT * FROM t1; -DROP TABLE t1; - -# -# Bug 37531 -# After truncate, auto_increment behaves incorrectly for InnoDB -# -CREATE TABLE t1(c1 INT PRIMARY KEY AUTO_INCREMENT) ENGINE=InnoDB; -INSERT INTO t1 VALUES (1), (2), (3); -INSERT INTO t1 VALUES (NULL), (NULL), (NULL); -SELECT c1 FROM t1; -SHOW CREATE TABLE t1; -TRUNCATE TABLE t1; -SHOW CREATE TABLE t1; -INSERT INTO t1 VALUES (1), (2), (3); -INSERT INTO t1 VALUES (NULL), (NULL), (NULL); -SELECT c1 FROM t1; -SHOW CREATE TABLE t1; -DROP TABLE t1; - -# -# Deleting all records should not reset the AUTOINC counter. -# -CREATE TABLE t1(c1 INT PRIMARY KEY AUTO_INCREMENT) ENGINE=InnoDB; -INSERT INTO t1 VALUES (1), (2), (3); -INSERT INTO t1 VALUES (NULL), (NULL), (NULL); -SELECT c1 FROM t1; -SHOW CREATE TABLE t1; -DELETE FROM t1; -SHOW CREATE TABLE t1; -INSERT INTO t1 VALUES (1), (2), (3); -INSERT INTO t1 VALUES (NULL), (NULL), (NULL); -SELECT c1 FROM t1; -SHOW CREATE TABLE t1; -DROP TABLE t1; - -# -# Bug 38839 -# Reset the last value generated at end of statement -# -DROP TABLE IF EXISTS t1; -CREATE TABLE t1 (c1 INT AUTO_INCREMENT, c2 INT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (NULL, 1); -DELETE FROM t1 WHERE c1 = 1; -INSERT INTO t1 VALUES (2,1); -INSERT INTO t1 VALUES (NULL,8); -SELECT * FROM t1; -DROP TABLE t1; -# Bug 38839 -- same as above but for multi value insert -DROP TABLE IF EXISTS t1; -CREATE TABLE t1 (c1 INT AUTO_INCREMENT, c2 INT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (NULL, 1); -DELETE FROM t1 WHERE c1 = 1; -INSERT INTO t1 VALUES (2,1), (NULL, 8); -INSERT INTO t1 VALUES (NULL,9); -SELECT * FROM t1; -DROP TABLE t1; - -# -# Test changes to AUTOINC next value calculation -SET @@SESSION.AUTO_INCREMENT_INCREMENT=100, @@SESSION.AUTO_INCREMENT_OFFSET=10; -SHOW VARIABLES LIKE "%auto_inc%"; -DROP TABLE IF EXISTS t1; -CREATE TABLE t1 (c1 INT AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (NULL),(5),(NULL); -INSERT INTO t1 VALUES (250),(NULL); -SELECT * FROM t1; -INSERT INTO t1 VALUES (1000); -SET @@INSERT_ID=400; -INSERT INTO t1 VALUES(NULL),(NULL); -SELECT * FROM t1; -DROP TABLE t1; - -# Test with SIGNED INT column, by inserting a 0 for the first column value -# 0 is treated in the same was NULL. -# Reset the AUTOINC session variables -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -DROP TABLE IF EXISTS t1; -CREATE TABLE t1 (c1 INT AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES(0); -SELECT * FROM t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=100, @@SESSION.AUTO_INCREMENT_OFFSET=10; -INSERT INTO t1 VALUES (-1), (NULL),(2),(NULL); -INSERT INTO t1 VALUES (250),(NULL); -SELECT * FROM t1; -SET @@INSERT_ID=400; -# Duplicate error expected here for autoinc_lock_mode != TRADITIONAL --- error ER_DUP_ENTRY,1062 -INSERT INTO t1 VALUES(NULL),(NULL); -SELECT * FROM t1; -DROP TABLE t1; - -# Test with SIGNED INT column -# Reset the AUTOINC session variables -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -DROP TABLE IF EXISTS t1; -CREATE TABLE t1 (c1 INT AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES(-1); -SELECT * FROM t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=100, @@SESSION.AUTO_INCREMENT_OFFSET=10; -SHOW VARIABLES LIKE "%auto_inc%"; -INSERT INTO t1 VALUES (-2), (NULL),(2),(NULL); -INSERT INTO t1 VALUES (250),(NULL); -SELECT * FROM t1; -INSERT INTO t1 VALUES (1000); -SET @@INSERT_ID=400; -INSERT INTO t1 VALUES(NULL),(NULL); -SELECT * FROM t1; -DROP TABLE t1; - -# Test with UNSIGNED INT column, single insert -# The sign in the value is ignored and a new column value is generated -# Reset the AUTOINC session variables -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -DROP TABLE IF EXISTS t1; -CREATE TABLE t1 (c1 INT UNSIGNED AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES(-1); -SELECT * FROM t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=100, @@SESSION.AUTO_INCREMENT_OFFSET=10; -SHOW VARIABLES LIKE "%auto_inc%"; -INSERT INTO t1 VALUES (-2); -INSERT INTO t1 VALUES (NULL); -INSERT INTO t1 VALUES (2); -INSERT INTO t1 VALUES (NULL); -INSERT INTO t1 VALUES (250); -INSERT INTO t1 VALUES (NULL); -SELECT * FROM t1; -INSERT INTO t1 VALUES (1000); -SET @@INSERT_ID=400; -INSERT INTO t1 VALUES(NULL); -INSERT INTO t1 VALUES(NULL); -SELECT * FROM t1; -DROP TABLE t1; - -# Test with UNSIGNED INT column, multi-value inserts -# The sign in the value is ignored and a new column value is generated -# Reset the AUTOINC session variables -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -DROP TABLE IF EXISTS t1; -CREATE TABLE t1 (c1 INT UNSIGNED AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES(-1); -SELECT * FROM t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=100, @@SESSION.AUTO_INCREMENT_OFFSET=10; -SHOW VARIABLES LIKE "%auto_inc%"; -INSERT INTO t1 VALUES (-2),(NULL),(2),(NULL); -INSERT INTO t1 VALUES (250),(NULL); -SELECT * FROM t1; -INSERT INTO t1 VALUES (1000); -SET @@INSERT_ID=400; -# Duplicate error expected here for autoinc_lock_mode != TRADITIONAL --- error ER_DUP_ENTRY,1062 -INSERT INTO t1 VALUES(NULL),(NULL); -SELECT * FROM t1; -DROP TABLE t1; - -# -# Check for overflow handling when increment is > 1 -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -DROP TABLE IF EXISTS t1; -CREATE TABLE t1 (c1 BIGINT AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -# TODO: Fix the autoinc init code -# We have to do this because of a bug in the AUTOINC init code. -INSERT INTO t1 VALUES(NULL); -INSERT INTO t1 VALUES (9223372036854775794); #-- 2^63 - 14 -SELECT * FROM t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=2, @@SESSION.AUTO_INCREMENT_OFFSET=10; -SHOW VARIABLES LIKE "%auto_inc%"; -# This should just fit -INSERT INTO t1 VALUES (NULL),(NULL),(NULL),(NULL),(NULL),(NULL); -SELECT * FROM t1; -DROP TABLE t1; - -# -# Check for overflow handling when increment and offser are > 1 -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -DROP TABLE IF EXISTS t1; -CREATE TABLE t1 (c1 BIGINT UNSIGNED AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -# TODO: Fix the autoinc init code -# We have to do this because of a bug in the AUTOINC init code. -INSERT INTO t1 VALUES(NULL); -INSERT INTO t1 VALUES (18446744073709551603); #-- 2^64 - 13 -SELECT * FROM t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=2, @@SESSION.AUTO_INCREMENT_OFFSET=10; -SHOW VARIABLES LIKE "%auto_inc%"; -# This should fail because of overflow but it doesn't, it seems to be -# a MySQL server bug. It wraps around to 0 for the last value. -# See MySQL Bug# 39828 -# -# Instead of wrapping around, it asserts when MySQL is compiled --with-debug -# (see sql/handler.cc:handler::update_auto_increment()). Don't test for -# overflow until Bug #39828 is fixed. -# -# Since this asserts when compiled --with-debug, we can't properly test this -# until Bug #39828 is fixed. For now, this test is meaningless. -#if Bug #39828 is fixed -#INSERT INTO t1 VALUES (NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL); -#else -INSERT INTO t1 VALUES (NULL),(NULL),(NULL),(NULL),(NULL),(NULL); -#endif -SELECT * FROM t1; -DROP TABLE t1; - -# -# Check for overflow handling when increment and offset are odd numbers -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -DROP TABLE IF EXISTS t1; -CREATE TABLE t1 (c1 BIGINT UNSIGNED AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -# TODO: Fix the autoinc init code -# We have to do this because of a bug in the AUTOINC init code. -INSERT INTO t1 VALUES(NULL); -INSERT INTO t1 VALUES (18446744073709551603); #-- 2^64 - 13 -SELECT * FROM t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=5, @@SESSION.AUTO_INCREMENT_OFFSET=7; -SHOW VARIABLES LIKE "%auto_inc%"; -# This should fail because of overflow but it doesn't. It fails with -# a duplicate entry message because of a MySQL server bug, it wraps -# around. See MySQL Bug# 39828, once MySQL fix the bug we can replace -# the ER_DUP_ENTRY, 1062 below with the appropriate error message -# -# Since this asserts when compiled --with-debug, we can't properly test this -# until Bug #39828 is fixed. For now, this test is meaningless. -#if Bug #39828 is fixed -# Still need to fix this error code, error should mention overflow -#-- error ER_DUP_ENTRY,1062 -#INSERT INTO t1 VALUES (NULL),(NULL), (NULL); -#else -INSERT INTO t1 VALUES (NULL),(NULL); -#endif -SELECT * FROM t1; -DROP TABLE t1; - -# Check for overflow handling when increment and offset are odd numbers -# and check for large -ve numbers -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -DROP TABLE IF EXISTS t1; -CREATE TABLE t1 (c1 BIGINT AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -# TODO: Fix the autoinc init code -# We have to do this because of a bug in the AUTOINC init code. -INSERT INTO t1 VALUES(NULL); -INSERT INTO t1 VALUES(-9223372036854775806); #-- -2^63 + 2 -INSERT INTO t1 VALUES(-9223372036854775807); #-- -2^63 + 1 -INSERT INTO t1 VALUES(-9223372036854775808); #-- -2^63 -SELECT * FROM t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=3, @@SESSION.AUTO_INCREMENT_OFFSET=3; -SHOW VARIABLES LIKE "%auto_inc%"; -INSERT INTO t1 VALUES (NULL),(NULL), (NULL); -SELECT * FROM t1; -DROP TABLE t1; -# -# Check for overflow handling when increment and offset are very -# large numbers 2^60 -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -DROP TABLE IF EXISTS t1; -CREATE TABLE t1 (c1 BIGINT UNSIGNED AUTO_INCREMENT, PRIMARY KEY(c1)) ENGINE=InnoDB; -# TODO: Fix the autoinc init code -# We have to do this because of a bug in the AUTOINC init code. -INSERT INTO t1 VALUES(NULL); -INSERT INTO t1 VALUES (18446744073709551610); #-- 2^64 - 2 -SELECT * FROM t1; -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1152921504606846976, @@SESSION.AUTO_INCREMENT_OFFSET=1152921504606846976; -SHOW VARIABLES LIKE "%auto_inc%"; -# This should fail because of overflow but it doesn't. It wraps around -# and the autoinc values look bogus too. -# See MySQL Bug# 39828, once MySQL fix the bug we can enable the error -# code expected test. -# -- error ER_AUTOINC_READ_FAILED,1467 -# -# Since this asserts when compiled --with-debug, we can't properly test this -# until Bug #39828 is fixed. For now, this test is meaningless. -#if Bug #39828 is fixed -#-- error ER_AUTOINC_READ_FAILED,1467 -#INSERT INTO t1 VALUES (NULL),(NULL); -#else -INSERT INTO t1 VALUES (NULL); -#endif -SELECT * FROM t1; -DROP TABLE t1; - -# -# Check for floating point autoinc column handling -# -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=1; -SET @@INSERT_ID=1; -SHOW VARIABLES LIKE "%auto_inc%"; -CREATE TABLE t1 (c1 DOUBLE NOT NULL AUTO_INCREMENT, c2 INT, PRIMARY KEY (c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES(NULL, 1); -INSERT INTO t1 VALUES(NULL, 2); -SELECT * FROM t1; -ALTER TABLE t1 CHANGE c1 c1 SERIAL; -SELECT * FROM t1; -INSERT INTO t1 VALUES(NULL, 3); -INSERT INTO t1 VALUES(NULL, 4); -SELECT * FROM t1; -DROP TABLE IF EXISTS t1; -CREATE TABLE t1 (c1 FLOAT NOT NULL AUTO_INCREMENT, c2 INT, PRIMARY KEY (c1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES(NULL, 1); -INSERT INTO t1 VALUES(NULL, 2); -SELECT * FROM t1; -ALTER TABLE t1 CHANGE c1 c1 SERIAL; -SELECT * FROM t1; -INSERT INTO t1 VALUES(NULL, 3); -INSERT INTO t1 VALUES(NULL, 4); -SELECT * FROM t1; -DROP TABLE t1; - -# -# Bug# 42714: AUTOINC column calculated next value not greater than highest -# value stored in table. -# -SET @@SESSION.AUTO_INCREMENT_INCREMENT=1, @@SESSION.AUTO_INCREMENT_OFFSET=5; -DROP TABLE IF EXISTS t1; -DROP TABLE IF EXISTS t2; -CREATE TABLE t1 ( - a INT(11) UNSIGNED NOT NULL AUTO_INCREMENT, - b INT(10) UNSIGNED NOT NULL, - c ENUM('FALSE','TRUE') DEFAULT NULL, - PRIMARY KEY (a)) ENGINE = InnoDB; -CREATE TABLE t2 ( - m INT(11) UNSIGNED NOT NULL AUTO_INCREMENT, - n INT(10) UNSIGNED NOT NULL, - o enum('FALSE','TRUE') DEFAULT NULL, - PRIMARY KEY (m)) ENGINE = InnoDB; -INSERT INTO t2 (n,o) VALUES - (1 , 'true'), (1 , 'false'), (2 , 'true'), (2 , 'false'), (3 , 'true'), - (3 , 'false'), (4 , 'true'), (4 , 'false'), (5 , 'true'), (5 , 'false'); -SHOW CREATE TABLE t2; -INSERT INTO t1 (b,c) SELECT n,o FROM t2 ; -SHOW CREATE TABLE t1; -INSERT INTO t1 (b,c) SELECT n,o FROM t2 ; -SELECT * FROM t1; -SHOW CREATE TABLE t1; -INSERT INTO t1 (b,c) SELECT n,o FROM t2 WHERE o = 'false'; -SELECT * FROM t1; -SHOW CREATE TABLE t1; -INSERT INTO t1 (b,c) SELECT n,o FROM t2 WHERE o = 'false'; -SELECT * FROM t1; -SHOW CREATE TABLE t1; -INSERT INTO t1 (b,c) SELECT n,o FROM t2 WHERE o = 'false'; -SHOW CREATE TABLE t1; -INSERT INTO t1 (b,c) SELECT n,o FROM t2 WHERE o = 'false'; -SHOW CREATE TABLE t1; -INSERT INTO t1 (b,c) SELECT n,o FROM t2 WHERE o = 'false'; -SELECT * FROM t1; -SHOW CREATE TABLE t1; -DROP TABLE t1; -DROP TABLE t2; -# -# 43203: Overflow from auto incrementing causes server segv -# - -DROP TABLE IF EXISTS t1; -DROP TABLE IF EXISTS t2; -CREATE TABLE t1( - c1 INT(10) UNSIGNED NOT NULL AUTO_INCREMENT - PRIMARY KEY) ENGINE=InnoDB; -INSERT INTO t1 VALUES (NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL),(NULL); -CREATE TABLE t2( - c1 TINYINT(3) UNSIGNED NOT NULL AUTO_INCREMENT - PRIMARY KEY) ENGINE=InnoDB; --- error ER_DUP_ENTRY,1062 -INSERT INTO t2 SELECT c1 FROM t1; --- error ER_DUP_ENTRY,1467 -INSERT INTO t2 SELECT NULL FROM t1; -DROP TABLE t1; -DROP TABLE t2; -# -# 44030: Error: (1500) Couldn't read the MAX(ID) autoinc value from -# the index (PRIMARY) -# This test requires a restart of the server -CREATE TABLE t1 (c1 INT PRIMARY KEY AUTO_INCREMENT) ENGINE=InnoDB; -INSERT INTO t1 VALUES (null); -INSERT INTO t1 VALUES (null); -ALTER TABLE t1 CHANGE c1 d1 INT NOT NULL AUTO_INCREMENT; -SELECT * FROM t1; -# Restart the server --- source include/restart_mysqld.inc -# The MySQL and InnoDB data dictionaries should now be out of sync. -# The select should print message to the error log -SELECT * FROM t1; --- error ER_AUTOINC_READ_FAILED,1467 -INSERT INTO t1 VALUES(null); -ALTER TABLE t1 AUTO_INCREMENT = 3; -INSERT INTO t1 VALUES(null); -SELECT * FROM t1; -DROP TABLE t1; diff --git a/storage/innodb_plugin/mysql-test/innodb-consistent-master.opt b/storage/innodb_plugin/mysql-test/innodb-consistent-master.opt deleted file mode 100644 index 8cca44767da..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-consistent-master.opt +++ /dev/null @@ -1 +0,0 @@ ---innodb_lock_wait_timeout=2
diff --git a/storage/innodb_plugin/mysql-test/innodb-consistent.result b/storage/innodb_plugin/mysql-test/innodb-consistent.result deleted file mode 100644 index 9115791b99c..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-consistent.result +++ /dev/null @@ -1,35 +0,0 @@ -drop table if exists t1; -set session transaction isolation level read committed; -create table t1(a int not null) engine=innodb DEFAULT CHARSET=latin1; -create table t2 like t1; -insert into t2 values (1),(2),(3),(4),(5),(6),(7); -set autocommit=0; -begin; -replace into t1 select * from t2; -set session transaction isolation level read committed; -set autocommit=0; -delete from t2 where a=5; -commit; -delete from t2; -commit; -commit; -begin; -insert into t1 select * from t2; -set session transaction isolation level read committed; -set autocommit=0; -delete from t2 where a=5; -commit; -delete from t2; -commit; -commit; -select * from t1; -a -1 -2 -3 -4 -5 -6 -7 -drop table t1; -drop table t2; diff --git a/storage/innodb_plugin/mysql-test/innodb-consistent.test b/storage/innodb_plugin/mysql-test/innodb-consistent.test deleted file mode 100644 index 791600fc8a7..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-consistent.test +++ /dev/null @@ -1,58 +0,0 @@ --- source include/not_embedded.inc
--- source include/have_innodb.inc
-
---disable_warnings
-drop table if exists t1;
---enable_warnings
-
-# REPLACE INTO ... SELECT and INSERT INTO ... SELECT should do
-# a consistent read of the source table.
-
-connect (a,localhost,root,,);
-connect (b,localhost,root,,);
-connection a;
-set session transaction isolation level read committed;
-create table t1(a int not null) engine=innodb DEFAULT CHARSET=latin1;
-create table t2 like t1;
-insert into t2 values (1),(2),(3),(4),(5),(6),(7);
-set autocommit=0;
-
-# REPLACE INTO ... SELECT case
-begin;
-# this should not result in any locks on t2.
-replace into t1 select * from t2;
-
-connection b;
-set session transaction isolation level read committed;
-set autocommit=0;
-# should not cuase a lock wait.
-delete from t2 where a=5;
-commit;
-delete from t2;
-commit;
-connection a;
-commit;
-
-# INSERT INTO ... SELECT case
-begin;
-# this should not result in any locks on t2.
-insert into t1 select * from t2;
-
-connection b;
-set session transaction isolation level read committed;
-set autocommit=0;
-# should not cuase a lock wait.
-delete from t2 where a=5;
-commit;
-delete from t2;
-commit;
-connection a;
-commit;
-
-select * from t1;
-drop table t1;
-drop table t2;
-
-connection default;
-disconnect a;
-disconnect b;
diff --git a/storage/innodb_plugin/mysql-test/innodb-index.inc b/storage/innodb_plugin/mysql-test/innodb-index.inc deleted file mode 100644 index 37de3162abe..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-index.inc +++ /dev/null @@ -1,26 +0,0 @@ ---eval create table t1(a int not null, b int, c char(10), d varchar(20), primary key (a)) engine = innodb default charset=$charset -insert into t1 values (1,1,'ab','ab'),(2,2,'ac','ac'),(3,2,'ad','ad'),(4,4,'afe','afe'); -commit; ---error ER_DUP_ENTRY -alter table t1 add unique index (b); -insert into t1 values(8,9,'fff','fff'); -select * from t1; -show create table t1; -alter table t1 add index (b); -insert into t1 values(10,10,'kkk','iii'); -select * from t1; -select * from t1 force index(b) order by b; -explain select * from t1 force index(b) order by b; -show create table t1; -alter table t1 add unique index (c), add index (d); -insert into t1 values(11,11,'aaa','mmm'); -select * from t1; -select * from t1 force index(b) order by b; -select * from t1 force index(c) order by c; -select * from t1 force index(d) order by d; -explain select * from t1 force index(b) order by b; -explain select * from t1 force index(c) order by c; -explain select * from t1 force index(d) order by d; -show create table t1; -check table t1; -drop table t1; diff --git a/storage/innodb_plugin/mysql-test/innodb-index.result b/storage/innodb_plugin/mysql-test/innodb-index.result deleted file mode 100644 index a7d66b15300..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-index.result +++ /dev/null @@ -1,1170 +0,0 @@ -create table t1(a int not null, b int, c char(10) not null, d varchar(20)) engine = innodb; -insert into t1 values (5,5,'oo','oo'),(4,4,'tr','tr'),(3,4,'ad','ad'),(2,3,'ak','ak'); -commit; -alter table t1 add index b (b), add index b (b); -ERROR 42000: Duplicate key name 'b' -alter table t1 add index (b,b); -ERROR 42S21: Duplicate column name 'b' -alter table t1 add index d2 (d); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) NOT NULL, - `d` varchar(20) DEFAULT NULL, - KEY `d2` (`d`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -explain select * from t1 force index(d2) order by d; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL d2 23 NULL 4 -select * from t1 force index (d2) order by d; -a b c d -3 4 ad ad -2 3 ak ak -5 5 oo oo -4 4 tr tr -alter table t1 add unique index (b); -ERROR 23000: Duplicate entry '4' for key 'b' -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) NOT NULL, - `d` varchar(20) DEFAULT NULL, - KEY `d2` (`d`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -alter table t1 add index (b); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) NOT NULL, - `d` varchar(20) DEFAULT NULL, - KEY `d2` (`d`), - KEY `b` (`b`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -CREATE TABLE `t1#1`(a INT PRIMARY KEY) ENGINE=InnoDB; -alter table t1 add unique index (c), add index (d); -ERROR HY000: Table 'test.t1#1' already exists -rename table `t1#1` to `t1#2`; -alter table t1 add unique index (c), add index (d); -ERROR HY000: Table 'test.t1#2' already exists -drop table `t1#2`; -alter table t1 add unique index (c), add index (d); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) NOT NULL, - `d` varchar(20) DEFAULT NULL, - UNIQUE KEY `c` (`c`), - KEY `d2` (`d`), - KEY `b` (`b`), - KEY `d` (`d`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -explain select * from t1 force index(c) order by c; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL c 10 NULL 4 -alter table t1 add primary key (a), drop index c; -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) NOT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`), - KEY `d2` (`d`), - KEY `b` (`b`), - KEY `d` (`d`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -alter table t1 add primary key (c); -ERROR 42000: Multiple primary key defined -alter table t1 drop primary key, add primary key (b); -ERROR 23000: Duplicate entry '4' for key 'PRIMARY' -create unique index c on t1 (c); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) NOT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`), - UNIQUE KEY `c` (`c`), - KEY `d2` (`d`), - KEY `b` (`b`), - KEY `d` (`d`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -explain select * from t1 force index(c) order by c; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL c 10 NULL 4 -select * from t1 force index(c) order by c; -a b c d -3 4 ad ad -2 3 ak ak -5 5 oo oo -4 4 tr tr -alter table t1 drop index b, add index (b); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) NOT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`), - UNIQUE KEY `c` (`c`), - KEY `d2` (`d`), - KEY `d` (`d`), - KEY `b` (`b`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -insert into t1 values(6,1,'ggg','ggg'); -select * from t1; -a b c d -2 3 ak ak -3 4 ad ad -4 4 tr tr -5 5 oo oo -6 1 ggg ggg -select * from t1 force index(b) order by b; -a b c d -6 1 ggg ggg -2 3 ak ak -3 4 ad ad -4 4 tr tr -5 5 oo oo -select * from t1 force index(c) order by c; -a b c d -3 4 ad ad -2 3 ak ak -6 1 ggg ggg -5 5 oo oo -4 4 tr tr -select * from t1 force index(d) order by d; -a b c d -3 4 ad ad -2 3 ak ak -6 1 ggg ggg -5 5 oo oo -4 4 tr tr -explain select * from t1 force index(b) order by b; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL b 5 NULL 5 -explain select * from t1 force index(c) order by c; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL c 10 NULL 5 -explain select * from t1 force index(d) order by d; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL d 23 NULL 5 -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) NOT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`), - UNIQUE KEY `c` (`c`), - KEY `d2` (`d`), - KEY `d` (`d`), - KEY `b` (`b`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t1; -create table t1(a int not null, b int, c char(10), d varchar(20), primary key (a)) engine = innodb; -insert into t1 values (1,1,'ab','ab'),(2,2,'ac','ac'),(3,3,'ad','ad'),(4,4,'afe','afe'); -commit; -alter table t1 add index (c(2)); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`), - KEY `c` (`c`(2)) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -alter table t1 add unique index (d(10)); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`), - UNIQUE KEY `d` (`d`(10)), - KEY `c` (`c`(2)) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -insert into t1 values(5,1,'ggg','ggg'); -select * from t1; -a b c d -1 1 ab ab -2 2 ac ac -3 3 ad ad -4 4 afe afe -5 1 ggg ggg -select * from t1 force index(c) order by c; -a b c d -1 1 ab ab -2 2 ac ac -3 3 ad ad -4 4 afe afe -5 1 ggg ggg -select * from t1 force index(d) order by d; -a b c d -1 1 ab ab -2 2 ac ac -3 3 ad ad -4 4 afe afe -5 1 ggg ggg -explain select * from t1 order by b; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ALL NULL NULL NULL NULL 5 Using filesort -explain select * from t1 force index(c) order by c; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ALL NULL NULL NULL NULL 5 Using filesort -explain select * from t1 force index(d) order by d; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ALL NULL NULL NULL NULL 5 Using filesort -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`), - UNIQUE KEY `d` (`d`(10)), - KEY `c` (`c`(2)) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -alter table t1 drop index d; -insert into t1 values(8,9,'fff','fff'); -select * from t1; -a b c d -1 1 ab ab -2 2 ac ac -3 3 ad ad -4 4 afe afe -5 1 ggg ggg -8 9 fff fff -select * from t1 force index(c) order by c; -a b c d -1 1 ab ab -2 2 ac ac -3 3 ad ad -4 4 afe afe -8 9 fff fff -5 1 ggg ggg -explain select * from t1 order by b; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ALL NULL NULL NULL NULL 6 Using filesort -explain select * from t1 force index(c) order by c; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ALL NULL NULL NULL NULL 6 Using filesort -explain select * from t1 order by d; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ALL NULL NULL NULL NULL 6 Using filesort -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`), - KEY `c` (`c`(2)) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t1; -create table t1(a int not null, b int, c char(10), d varchar(20), primary key (a)) engine = innodb; -insert into t1 values (1,1,'ab','ab'),(2,2,'ac','ac'),(3,2,'ad','ad'),(4,4,'afe','afe'); -commit; -alter table t1 add unique index (b,c); -insert into t1 values(8,9,'fff','fff'); -select * from t1; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -select * from t1 force index(b) order by b; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -explain select * from t1 force index(b) order by b; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL b 16 NULL 5 -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`), - UNIQUE KEY `b` (`b`,`c`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -alter table t1 add index (b,c); -insert into t1 values(11,11,'kkk','kkk'); -select * from t1; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -11 11 kkk kkk -select * from t1 force index(b) order by b; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -11 11 kkk kkk -explain select * from t1 force index(b) order by b; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL b 16 NULL 6 -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`), - UNIQUE KEY `b` (`b`,`c`), - KEY `b_2` (`b`,`c`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -alter table t1 add unique index (c,d); -insert into t1 values(13,13,'yyy','aaa'); -select * from t1; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -11 11 kkk kkk -13 13 yyy aaa -select * from t1 force index(b) order by b; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -11 11 kkk kkk -13 13 yyy aaa -select * from t1 force index(c) order by c; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -11 11 kkk kkk -13 13 yyy aaa -explain select * from t1 force index(b) order by b; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL b 16 NULL 7 -explain select * from t1 force index(c) order by c; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL c 34 NULL 7 -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`), - UNIQUE KEY `b` (`b`,`c`), - UNIQUE KEY `c` (`c`,`d`), - KEY `b_2` (`b`,`c`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t1; -create table t1(a int not null, b int not null, c int, primary key (a), key (b)) engine = innodb; -create table t3(a int not null, c int not null, d int, primary key (a), key (c)) engine = innodb; -create table t4(a int not null, d int not null, e int, primary key (a), key (d)) engine = innodb; -create table t2(a int not null, b int not null, c int not null, d int not null, e int, -foreign key (b) references t1(b) on delete cascade, -foreign key (c) references t3(c), foreign key (d) references t4(d)) -engine = innodb; -alter table t1 drop index b; -ERROR HY000: Cannot drop index 'b': needed in a foreign key constraint -alter table t3 drop index c; -ERROR HY000: Cannot drop index 'c': needed in a foreign key constraint -alter table t4 drop index d; -ERROR HY000: Cannot drop index 'd': needed in a foreign key constraint -alter table t2 drop index b; -ERROR HY000: Cannot drop index 'b': needed in a foreign key constraint -alter table t2 drop index b, drop index c, drop index d; -ERROR HY000: Cannot drop index 'b': needed in a foreign key constraint -create unique index dc on t2 (d,c); -create index dc on t1 (b,c); -alter table t2 add primary key (a); -insert into t1 values (1,1,1); -insert into t3 values (1,1,1); -insert into t4 values (1,1,1); -insert into t2 values (1,1,1,1,1); -commit; -alter table t4 add constraint dc foreign key (a) references t1(a); -show create table t4; -Table Create Table -t4 CREATE TABLE `t4` ( - `a` int(11) NOT NULL, - `d` int(11) NOT NULL, - `e` int(11) DEFAULT NULL, - PRIMARY KEY (`a`), - KEY `d` (`d`), - CONSTRAINT `dc` FOREIGN KEY (`a`) REFERENCES `t1` (`a`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -alter table t3 add constraint dc foreign key (a) references t1(a); -ERROR HY000: Can't create table '#sql-temporary' (errno: 121) -show create table t3; -Table Create Table -t3 CREATE TABLE `t3` ( - `a` int(11) NOT NULL, - `c` int(11) NOT NULL, - `d` int(11) DEFAULT NULL, - PRIMARY KEY (`a`), - KEY `c` (`c`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -alter table t2 drop index b, add index (b); -show create table t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `a` int(11) NOT NULL, - `b` int(11) NOT NULL, - `c` int(11) NOT NULL, - `d` int(11) NOT NULL, - `e` int(11) DEFAULT NULL, - PRIMARY KEY (`a`), - UNIQUE KEY `dc` (`d`,`c`), - KEY `c` (`c`), - KEY `b` (`b`), - CONSTRAINT `t2_ibfk_1` FOREIGN KEY (`b`) REFERENCES `t1` (`b`) ON DELETE CASCADE, - CONSTRAINT `t2_ibfk_2` FOREIGN KEY (`c`) REFERENCES `t3` (`c`), - CONSTRAINT `t2_ibfk_3` FOREIGN KEY (`d`) REFERENCES `t4` (`d`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -delete from t1; -ERROR 23000: Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t4`, CONSTRAINT `dc` FOREIGN KEY (`a`) REFERENCES `t1` (`a`)) -drop index dc on t4; -ERROR 42000: Can't DROP 'dc'; check that column/key exists -alter table t3 drop foreign key dc; -ERROR HY000: Error on rename of './test/t3' to '#sql2-temporary' (errno: 152) -alter table t4 drop foreign key dc; -select * from t2; -a b c d e -1 1 1 1 1 -delete from t1; -select * from t2; -a b c d e -drop table t2,t4,t3,t1; -create table t1(a int not null, b int, c char(10), d varchar(20), primary key (a)) engine = innodb default charset=utf8; -insert into t1 values (1,1,'ab','ab'),(2,2,'ac','ac'),(3,2,'ad','ad'),(4,4,'afe','afe'); -commit; -alter table t1 add unique index (b); -ERROR 23000: Duplicate entry '2' for key 'b' -insert into t1 values(8,9,'fff','fff'); -select * from t1; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`) -) ENGINE=InnoDB DEFAULT CHARSET=utf8 -alter table t1 add index (b); -insert into t1 values(10,10,'kkk','iii'); -select * from t1; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -10 10 kkk iii -select * from t1 force index(b) order by b; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -10 10 kkk iii -explain select * from t1 force index(b) order by b; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL b 5 NULL 6 -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`), - KEY `b` (`b`) -) ENGINE=InnoDB DEFAULT CHARSET=utf8 -alter table t1 add unique index (c), add index (d); -insert into t1 values(11,11,'aaa','mmm'); -select * from t1; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -10 10 kkk iii -11 11 aaa mmm -select * from t1 force index(b) order by b; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -10 10 kkk iii -11 11 aaa mmm -select * from t1 force index(c) order by c; -a b c d -11 11 aaa mmm -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -10 10 kkk iii -select * from t1 force index(d) order by d; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -10 10 kkk iii -11 11 aaa mmm -explain select * from t1 force index(b) order by b; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL b 5 NULL 7 -explain select * from t1 force index(c) order by c; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL c 31 NULL 7 -explain select * from t1 force index(d) order by d; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL d 63 NULL 7 -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`), - UNIQUE KEY `c` (`c`), - KEY `b` (`b`), - KEY `d` (`d`) -) ENGINE=InnoDB DEFAULT CHARSET=utf8 -check table t1; -Table Op Msg_type Msg_text -test.t1 check status OK -drop table t1; -create table t1(a int not null, b int) engine = innodb; -insert into t1 values (1,1),(1,1),(1,1),(1,1); -alter table t1 add unique index (a); -ERROR 23000: Duplicate entry '1' for key 'a' -alter table t1 add unique index (b); -ERROR 23000: Duplicate entry '1' for key 'b' -alter table t1 add unique index (a), add unique index(b); -ERROR 23000: Duplicate entry '1' for key 'a' -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t1; -create table t1(a int not null, c int not null,b int, primary key(a), unique key(c), key(b)) engine = innodb; -alter table t1 drop index c, drop index b; -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `c` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - PRIMARY KEY (`a`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t1; -create table t1(a int not null, b int, primary key(a)) engine = innodb; -alter table t1 add index (b); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - PRIMARY KEY (`a`), - KEY `b` (`b`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t1; -create table t1(a int not null, b int, c char(10), d varchar(20), primary key (a)) engine = innodb; -insert into t1 values (1,1,'ab','ab'),(2,2,'ac','ac'),(3,3,'ac','ac'),(4,4,'afe','afe'),(5,4,'affe','affe'); -alter table t1 add unique index (b), add unique index (c), add unique index (d); -ERROR 23000: Duplicate entry '4' for key 'b' -alter table t1 add unique index (c), add unique index (b), add index (d); -ERROR 23000: Duplicate entry 'ac' for key 'c' -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t1; -create table t1(a int not null, b int not null, c int, primary key (a), key(c)) engine=innodb; -insert into t1 values (5,1,5),(4,2,4),(3,3,3),(2,4,2),(1,5,1); -alter table t1 add unique index (b); -insert into t1 values (10,20,20),(11,19,19),(12,18,18),(13,17,17); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) NOT NULL, - `c` int(11) DEFAULT NULL, - PRIMARY KEY (`a`), - UNIQUE KEY `b` (`b`), - KEY `c` (`c`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -check table t1; -Table Op Msg_type Msg_text -test.t1 check status OK -explain select * from t1 force index(c) order by c; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL c 5 NULL 9 -explain select * from t1 order by a; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL PRIMARY 4 NULL 9 -explain select * from t1 force index(b) order by b; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL b 4 NULL 9 -select * from t1 order by a; -a b c -1 5 1 -2 4 2 -3 3 3 -4 2 4 -5 1 5 -10 20 20 -11 19 19 -12 18 18 -13 17 17 -select * from t1 force index(b) order by b; -a b c -5 1 5 -4 2 4 -3 3 3 -2 4 2 -1 5 1 -13 17 17 -12 18 18 -11 19 19 -10 20 20 -select * from t1 force index(c) order by c; -a b c -1 5 1 -2 4 2 -3 3 3 -4 2 4 -5 1 5 -13 17 17 -12 18 18 -11 19 19 -10 20 20 -drop table t1; -create table t1(a int not null, b int not null) engine=innodb; -insert into t1 values (1,1); -alter table t1 add primary key(b); -insert into t1 values (2,2); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) NOT NULL, - PRIMARY KEY (`b`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -check table t1; -Table Op Msg_type Msg_text -test.t1 check status OK -select * from t1; -a b -1 1 -2 2 -explain select * from t1; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ALL NULL NULL NULL NULL 2 -explain select * from t1 order by a; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ALL NULL NULL NULL NULL 2 Using filesort -explain select * from t1 order by b; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL PRIMARY 4 NULL 2 -checksum table t1; -Table Checksum -test.t1 582702641 -drop table t1; -create table t1(a int not null) engine=innodb; -insert into t1 values (1); -alter table t1 add primary key(a); -insert into t1 values (2); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - PRIMARY KEY (`a`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -check table t1; -Table Op Msg_type Msg_text -test.t1 check status OK -commit; -select * from t1; -a -1 -2 -explain select * from t1; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL PRIMARY 4 NULL 2 Using index -explain select * from t1 order by a; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL PRIMARY 4 NULL 2 Using index -drop table t1; -create table t2(d varchar(17) primary key) engine=innodb default charset=utf8; -create table t3(a int primary key) engine=innodb; -insert into t3 values(22),(44),(33),(55),(66); -insert into t2 values ('jejdkrun87'),('adfd72nh9k'), -('adfdpplkeock'),('adfdijnmnb78k'),('adfdijn0loKNHJik'); -create table t1(a int, b blob, c text, d text not null) -engine=innodb default charset = utf8; -insert into t1 -select a,left(repeat(d,100*a),65535),repeat(d,20*a),d from t2,t3; -drop table t2, t3; -select count(*) from t1 where a=44; -count(*) -5 -select a, -length(b),b=left(repeat(d,100*a),65535),length(c),c=repeat(d,20*a),d from t1; -a length(b) b=left(repeat(d,100*a),65535) length(c) c=repeat(d,20*a) d -22 22000 1 4400 1 adfd72nh9k -22 35200 1 7040 1 adfdijn0loKNHJik -22 28600 1 5720 1 adfdijnmnb78k -22 26400 1 5280 1 adfdpplkeock -22 22000 1 4400 1 jejdkrun87 -33 33000 1 6600 1 adfd72nh9k -33 52800 1 10560 1 adfdijn0loKNHJik -33 42900 1 8580 1 adfdijnmnb78k -33 39600 1 7920 1 adfdpplkeock -33 33000 1 6600 1 jejdkrun87 -44 44000 1 8800 1 adfd72nh9k -44 65535 1 14080 1 adfdijn0loKNHJik -44 57200 1 11440 1 adfdijnmnb78k -44 52800 1 10560 1 adfdpplkeock -44 44000 1 8800 1 jejdkrun87 -55 55000 1 11000 1 adfd72nh9k -55 65535 1 17600 1 adfdijn0loKNHJik -55 65535 1 14300 1 adfdijnmnb78k -55 65535 1 13200 1 adfdpplkeock -55 55000 1 11000 1 jejdkrun87 -66 65535 1 13200 1 adfd72nh9k -66 65535 1 21120 1 adfdijn0loKNHJik -66 65535 1 17160 1 adfdijnmnb78k -66 65535 1 15840 1 adfdpplkeock -66 65535 1 13200 1 jejdkrun87 -alter table t1 add primary key (a), add key (b(20)); -ERROR 23000: Duplicate entry '22' for key 'PRIMARY' -delete from t1 where a%2; -check table t1; -Table Op Msg_type Msg_text -test.t1 check status OK -alter table t1 add primary key (a,b(255),c(255)), add key (b(767)); -select count(*) from t1 where a=44; -count(*) -5 -select a, -length(b),b=left(repeat(d,100*a),65535),length(c),c=repeat(d,20*a),d from t1; -a length(b) b=left(repeat(d,100*a),65535) length(c) c=repeat(d,20*a) d -22 22000 1 4400 1 adfd72nh9k -22 35200 1 7040 1 adfdijn0loKNHJik -22 28600 1 5720 1 adfdijnmnb78k -22 26400 1 5280 1 adfdpplkeock -22 22000 1 4400 1 jejdkrun87 -44 44000 1 8800 1 adfd72nh9k -44 65535 1 14080 1 adfdijn0loKNHJik -44 57200 1 11440 1 adfdijnmnb78k -44 52800 1 10560 1 adfdpplkeock -44 44000 1 8800 1 jejdkrun87 -66 65535 1 13200 1 adfd72nh9k -66 65535 1 21120 1 adfdijn0loKNHJik -66 65535 1 17160 1 adfdijnmnb78k -66 65535 1 15840 1 adfdpplkeock -66 65535 1 13200 1 jejdkrun87 -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL DEFAULT '0', - `b` blob NOT NULL, - `c` text NOT NULL, - `d` text NOT NULL, - PRIMARY KEY (`a`,`b`(255),`c`(255)), - KEY `b` (`b`(767)) -) ENGINE=InnoDB DEFAULT CHARSET=utf8 -check table t1; -Table Op Msg_type Msg_text -test.t1 check status OK -explain select * from t1 where b like 'adfd%'; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ALL b NULL NULL NULL 15 Using where -create table t2(a int, b varchar(255), primary key(a,b)) engine=innodb; -insert into t2 select a,left(b,255) from t1; -drop table t1; -rename table t2 to t1; -set innodb_lock_wait_timeout=1; -begin; -select a from t1 limit 1 for update; -a -22 -set innodb_lock_wait_timeout=1; -create index t1ba on t1 (b,a); -ERROR HY000: Lock wait timeout exceeded; try restarting transaction -commit; -begin; -select a from t1 limit 1 lock in share mode; -a -22 -create index t1ba on t1 (b,a); -drop index t1ba on t1; -ERROR HY000: Lock wait timeout exceeded; try restarting transaction -commit; -explain select a from t1 order by b; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL t1ba 261 NULL 15 Using index -select a,sleep(2+a/100) from t1 order by b limit 3; -select sleep(1); -sleep(1) -0 -drop index t1ba on t1; -a sleep(2+a/100) -22 0 -44 0 -66 0 -explain select a from t1 order by b; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL PRIMARY 261 NULL 15 Using index; Using filesort -select a from t1 order by b limit 3; -a -22 -66 -44 -commit; -drop table t1; -set global innodb_file_per_table=on; -set global innodb_file_format='Barracuda'; -create table t1(a blob,b blob,c blob,d blob,e blob,f blob,g blob,h blob, -i blob,j blob,k blob,l blob,m blob,n blob,o blob,p blob, -q blob,r blob,s blob,t blob,u blob) -engine=innodb row_format=dynamic; -create index t1a on t1 (a(1)); -create index t1b on t1 (b(1)); -create index t1c on t1 (c(1)); -create index t1d on t1 (d(1)); -create index t1e on t1 (e(1)); -create index t1f on t1 (f(1)); -create index t1g on t1 (g(1)); -create index t1h on t1 (h(1)); -create index t1i on t1 (i(1)); -create index t1j on t1 (j(1)); -create index t1k on t1 (k(1)); -create index t1l on t1 (l(1)); -create index t1m on t1 (m(1)); -create index t1n on t1 (n(1)); -create index t1o on t1 (o(1)); -create index t1p on t1 (p(1)); -create index t1q on t1 (q(1)); -create index t1r on t1 (r(1)); -create index t1s on t1 (s(1)); -create index t1t on t1 (t(1)); -create index t1u on t1 (u(1)); -ERROR HY000: Too big row -create index t1ut on t1 (u(1), t(1)); -ERROR HY000: Too big row -create index t1st on t1 (s(1), t(1)); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` blob, - `b` blob, - `c` blob, - `d` blob, - `e` blob, - `f` blob, - `g` blob, - `h` blob, - `i` blob, - `j` blob, - `k` blob, - `l` blob, - `m` blob, - `n` blob, - `o` blob, - `p` blob, - `q` blob, - `r` blob, - `s` blob, - `t` blob, - `u` blob, - KEY `t1a` (`a`(1)), - KEY `t1b` (`b`(1)), - KEY `t1c` (`c`(1)), - KEY `t1d` (`d`(1)), - KEY `t1e` (`e`(1)), - KEY `t1f` (`f`(1)), - KEY `t1g` (`g`(1)), - KEY `t1h` (`h`(1)), - KEY `t1i` (`i`(1)), - KEY `t1j` (`j`(1)), - KEY `t1k` (`k`(1)), - KEY `t1l` (`l`(1)), - KEY `t1m` (`m`(1)), - KEY `t1n` (`n`(1)), - KEY `t1o` (`o`(1)), - KEY `t1p` (`p`(1)), - KEY `t1q` (`q`(1)), - KEY `t1r` (`r`(1)), - KEY `t1s` (`s`(1)), - KEY `t1t` (`t`(1)), - KEY `t1st` (`s`(1),`t`(1)) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 ROW_FORMAT=DYNAMIC -create index t1u on t1 (u(1)); -ERROR HY000: Too big row -alter table t1 row_format=compact; -create index t1u on t1 (u(1)); -drop table t1; -set global innodb_file_per_table=0; -set global innodb_file_format=Antelope; -SET @OLD_UNIQUE_CHECKS=@@UNIQUE_CHECKS, UNIQUE_CHECKS=0; -SET @OLD_FOREIGN_KEY_CHECKS=@@FOREIGN_KEY_CHECKS, FOREIGN_KEY_CHECKS=0; -CREATE TABLE t1( -c1 BIGINT(12) NOT NULL, -PRIMARY KEY (c1) -) ENGINE=InnoDB DEFAULT CHARSET=latin1; -CREATE TABLE t2( -c1 BIGINT(16) NOT NULL, -c2 BIGINT(12) NOT NULL, -c3 BIGINT(12) NOT NULL, -PRIMARY KEY (c1) -) ENGINE=InnoDB DEFAULT CHARSET=latin1; -ALTER TABLE t2 ADD CONSTRAINT fk_t2_ca -FOREIGN KEY (c3) REFERENCES t1(c1); -SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS; -SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS; -SHOW CREATE TABLE t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `c1` bigint(16) NOT NULL, - `c2` bigint(12) NOT NULL, - `c3` bigint(12) NOT NULL, - PRIMARY KEY (`c1`), - KEY `fk_t2_ca` (`c3`), - CONSTRAINT `fk_t2_ca` FOREIGN KEY (`c3`) REFERENCES `t1` (`c1`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -CREATE INDEX i_t2_c3_c2 ON t2(c3, c2); -SHOW CREATE TABLE t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `c1` bigint(16) NOT NULL, - `c2` bigint(12) NOT NULL, - `c3` bigint(12) NOT NULL, - PRIMARY KEY (`c1`), - KEY `i_t2_c3_c2` (`c3`,`c2`), - CONSTRAINT `fk_t2_ca` FOREIGN KEY (`c3`) REFERENCES `t1` (`c1`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS; -SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS; -INSERT INTO t2 VALUES(0,0,0); -ERROR 23000: Cannot add or update a child row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `fk_t2_ca` FOREIGN KEY (`c3`) REFERENCES `t1` (`c1`)) -INSERT INTO t1 VALUES(0); -INSERT INTO t2 VALUES(0,0,0); -DROP TABLE t2; -CREATE TABLE t2( -c1 BIGINT(16) NOT NULL, -c2 BIGINT(12) NOT NULL, -c3 BIGINT(12) NOT NULL, -PRIMARY KEY (c1,c2,c3) -) ENGINE=InnoDB DEFAULT CHARSET=latin1; -ALTER TABLE t2 ADD CONSTRAINT fk_t2_ca -FOREIGN KEY (c3) REFERENCES t1(c1); -SHOW CREATE TABLE t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `c1` bigint(16) NOT NULL, - `c2` bigint(12) NOT NULL, - `c3` bigint(12) NOT NULL, - PRIMARY KEY (`c1`,`c2`,`c3`), - KEY `fk_t2_ca` (`c3`), - CONSTRAINT `fk_t2_ca` FOREIGN KEY (`c3`) REFERENCES `t1` (`c1`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -CREATE INDEX i_t2_c3_c2 ON t2(c3, c2); -SHOW CREATE TABLE t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `c1` bigint(16) NOT NULL, - `c2` bigint(12) NOT NULL, - `c3` bigint(12) NOT NULL, - PRIMARY KEY (`c1`,`c2`,`c3`), - KEY `i_t2_c3_c2` (`c3`,`c2`), - CONSTRAINT `fk_t2_ca` FOREIGN KEY (`c3`) REFERENCES `t1` (`c1`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -INSERT INTO t2 VALUES(0,0,1); -ERROR 23000: Cannot add or update a child row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `fk_t2_ca` FOREIGN KEY (`c3`) REFERENCES `t1` (`c1`)) -INSERT INTO t2 VALUES(0,0,0); -DELETE FROM t1; -ERROR 23000: Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `fk_t2_ca` FOREIGN KEY (`c3`) REFERENCES `t1` (`c1`)) -DELETE FROM t2; -DROP TABLE t2; -DROP TABLE t1; -CREATE TABLE t1( -c1 BIGINT(12) NOT NULL, -c2 INT(4) NOT NULL, -PRIMARY KEY (c2,c1) -) ENGINE=InnoDB DEFAULT CHARSET=latin1; -CREATE TABLE t2( -c1 BIGINT(16) NOT NULL, -c2 BIGINT(12) NOT NULL, -c3 BIGINT(12) NOT NULL, -PRIMARY KEY (c1) -) ENGINE=InnoDB DEFAULT CHARSET=latin1; -ALTER TABLE t2 ADD CONSTRAINT fk_t2_ca -FOREIGN KEY (c3,c2) REFERENCES t1(c1,c1); -ERROR HY000: Can't create table '#sql-temporary' (errno: 150) -ALTER TABLE t2 ADD CONSTRAINT fk_t2_ca -FOREIGN KEY (c3,c2) REFERENCES t1(c1,c2); -ERROR HY000: Can't create table '#sql-temporary' (errno: 150) -ALTER TABLE t2 ADD CONSTRAINT fk_t2_ca -FOREIGN KEY (c3,c2) REFERENCES t1(c2,c1); -ERROR HY000: Can't create table '#sql-temporary' (errno: 150) -ALTER TABLE t1 MODIFY COLUMN c2 BIGINT(12) NOT NULL; -ALTER TABLE t2 ADD CONSTRAINT fk_t2_ca -FOREIGN KEY (c3,c2) REFERENCES t1(c1,c2); -ERROR HY000: Can't create table '#sql-temporary' (errno: 150) -ALTER TABLE t2 ADD CONSTRAINT fk_t2_ca -FOREIGN KEY (c3,c2) REFERENCES t1(c2,c1); -SHOW CREATE TABLE t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `c1` bigint(12) NOT NULL, - `c2` bigint(12) NOT NULL, - PRIMARY KEY (`c2`,`c1`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -SHOW CREATE TABLE t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `c1` bigint(16) NOT NULL, - `c2` bigint(12) NOT NULL, - `c3` bigint(12) NOT NULL, - PRIMARY KEY (`c1`), - KEY `fk_t2_ca` (`c3`,`c2`), - CONSTRAINT `fk_t2_ca` FOREIGN KEY (`c3`, `c2`) REFERENCES `t1` (`c2`, `c1`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -CREATE INDEX i_t2_c2_c1 ON t2(c2, c1); -SHOW CREATE TABLE t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `c1` bigint(16) NOT NULL, - `c2` bigint(12) NOT NULL, - `c3` bigint(12) NOT NULL, - PRIMARY KEY (`c1`), - KEY `fk_t2_ca` (`c3`,`c2`), - KEY `i_t2_c2_c1` (`c2`,`c1`), - CONSTRAINT `fk_t2_ca` FOREIGN KEY (`c3`, `c2`) REFERENCES `t1` (`c2`, `c1`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -CREATE INDEX i_t2_c3_c1_c2 ON t2(c3, c1, c2); -SHOW CREATE TABLE t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `c1` bigint(16) NOT NULL, - `c2` bigint(12) NOT NULL, - `c3` bigint(12) NOT NULL, - PRIMARY KEY (`c1`), - KEY `fk_t2_ca` (`c3`,`c2`), - KEY `i_t2_c2_c1` (`c2`,`c1`), - KEY `i_t2_c3_c1_c2` (`c3`,`c1`,`c2`), - CONSTRAINT `fk_t2_ca` FOREIGN KEY (`c3`, `c2`) REFERENCES `t1` (`c2`, `c1`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -CREATE INDEX i_t2_c3_c2 ON t2(c3, c2); -SHOW CREATE TABLE t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `c1` bigint(16) NOT NULL, - `c2` bigint(12) NOT NULL, - `c3` bigint(12) NOT NULL, - PRIMARY KEY (`c1`), - KEY `i_t2_c2_c1` (`c2`,`c1`), - KEY `i_t2_c3_c1_c2` (`c3`,`c1`,`c2`), - KEY `i_t2_c3_c2` (`c3`,`c2`), - CONSTRAINT `fk_t2_ca` FOREIGN KEY (`c3`, `c2`) REFERENCES `t1` (`c2`, `c1`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -DROP TABLE t2; -DROP TABLE t1; -CREATE TABLE t1 (a INT, b CHAR(1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (3,'a'),(3,'b'),(1,'c'),(0,'d'),(1,'e'); -BEGIN; -SELECT * FROM t1; -a b -3 a -3 b -1 c -0 d -1 e -CREATE INDEX t1a ON t1(a); -SELECT * FROM t1; -a b -3 a -3 b -1 c -0 d -1 e -SELECT * FROM t1 FORCE INDEX(t1a) ORDER BY a; -ERROR HY000: Table definition has changed, please retry transaction -SELECT * FROM t1; -a b -3 a -3 b -1 c -0 d -1 e -COMMIT; -SELECT * FROM t1 FORCE INDEX(t1a) ORDER BY a; -a b -0 d -1 c -1 e -3 a -3 b -DROP TABLE t1; diff --git a/storage/innodb_plugin/mysql-test/innodb-index.test b/storage/innodb_plugin/mysql-test/innodb-index.test deleted file mode 100644 index 42888ff3686..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-index.test +++ /dev/null @@ -1,534 +0,0 @@ --- source include/have_innodb.inc - -create table t1(a int not null, b int, c char(10) not null, d varchar(20)) engine = innodb; -insert into t1 values (5,5,'oo','oo'),(4,4,'tr','tr'),(3,4,'ad','ad'),(2,3,'ak','ak'); -commit; ---error ER_DUP_KEYNAME -alter table t1 add index b (b), add index b (b); ---error ER_DUP_FIELDNAME -alter table t1 add index (b,b); -alter table t1 add index d2 (d); -show create table t1; -explain select * from t1 force index(d2) order by d; -select * from t1 force index (d2) order by d; ---error ER_DUP_ENTRY -alter table t1 add unique index (b); -show create table t1; -alter table t1 add index (b); -show create table t1; - -# Check how existing tables interfere with temporary tables. -CREATE TABLE `t1#1`(a INT PRIMARY KEY) ENGINE=InnoDB; - ---error 156 -alter table t1 add unique index (c), add index (d); -rename table `t1#1` to `t1#2`; ---error 156 -alter table t1 add unique index (c), add index (d); -drop table `t1#2`; - -alter table t1 add unique index (c), add index (d); -show create table t1; -explain select * from t1 force index(c) order by c; -alter table t1 add primary key (a), drop index c; -show create table t1; ---error ER_MULTIPLE_PRI_KEY -alter table t1 add primary key (c); ---error ER_DUP_ENTRY -alter table t1 drop primary key, add primary key (b); -create unique index c on t1 (c); -show create table t1; -explain select * from t1 force index(c) order by c; -select * from t1 force index(c) order by c; -alter table t1 drop index b, add index (b); -show create table t1; -insert into t1 values(6,1,'ggg','ggg'); -select * from t1; -select * from t1 force index(b) order by b; -select * from t1 force index(c) order by c; -select * from t1 force index(d) order by d; -explain select * from t1 force index(b) order by b; -explain select * from t1 force index(c) order by c; -explain select * from t1 force index(d) order by d; -show create table t1; -drop table t1; - -create table t1(a int not null, b int, c char(10), d varchar(20), primary key (a)) engine = innodb; -insert into t1 values (1,1,'ab','ab'),(2,2,'ac','ac'),(3,3,'ad','ad'),(4,4,'afe','afe'); -commit; -alter table t1 add index (c(2)); -show create table t1; -alter table t1 add unique index (d(10)); -show create table t1; -insert into t1 values(5,1,'ggg','ggg'); -select * from t1; -select * from t1 force index(c) order by c; -select * from t1 force index(d) order by d; -explain select * from t1 order by b; -explain select * from t1 force index(c) order by c; -explain select * from t1 force index(d) order by d; -show create table t1; -alter table t1 drop index d; -insert into t1 values(8,9,'fff','fff'); -select * from t1; -select * from t1 force index(c) order by c; -explain select * from t1 order by b; -explain select * from t1 force index(c) order by c; -explain select * from t1 order by d; -show create table t1; -drop table t1; - -create table t1(a int not null, b int, c char(10), d varchar(20), primary key (a)) engine = innodb; -insert into t1 values (1,1,'ab','ab'),(2,2,'ac','ac'),(3,2,'ad','ad'),(4,4,'afe','afe'); -commit; -alter table t1 add unique index (b,c); -insert into t1 values(8,9,'fff','fff'); -select * from t1; -select * from t1 force index(b) order by b; -explain select * from t1 force index(b) order by b; -show create table t1; -alter table t1 add index (b,c); -insert into t1 values(11,11,'kkk','kkk'); -select * from t1; -select * from t1 force index(b) order by b; -explain select * from t1 force index(b) order by b; -show create table t1; -alter table t1 add unique index (c,d); -insert into t1 values(13,13,'yyy','aaa'); -select * from t1; -select * from t1 force index(b) order by b; -select * from t1 force index(c) order by c; -explain select * from t1 force index(b) order by b; -explain select * from t1 force index(c) order by c; -show create table t1; -drop table t1; - -create table t1(a int not null, b int not null, c int, primary key (a), key (b)) engine = innodb; -create table t3(a int not null, c int not null, d int, primary key (a), key (c)) engine = innodb; -create table t4(a int not null, d int not null, e int, primary key (a), key (d)) engine = innodb; -create table t2(a int not null, b int not null, c int not null, d int not null, e int, -foreign key (b) references t1(b) on delete cascade, -foreign key (c) references t3(c), foreign key (d) references t4(d)) -engine = innodb; ---error ER_DROP_INDEX_FK -alter table t1 drop index b; ---error ER_DROP_INDEX_FK -alter table t3 drop index c; ---error ER_DROP_INDEX_FK -alter table t4 drop index d; ---error ER_DROP_INDEX_FK -alter table t2 drop index b; ---error ER_DROP_INDEX_FK -alter table t2 drop index b, drop index c, drop index d; -# Apparently, the following makes mysql_alter_table() drop index d. -create unique index dc on t2 (d,c); -create index dc on t1 (b,c); -# This should preserve the foreign key constraints. -alter table t2 add primary key (a); -insert into t1 values (1,1,1); -insert into t3 values (1,1,1); -insert into t4 values (1,1,1); -insert into t2 values (1,1,1,1,1); -commit; -alter table t4 add constraint dc foreign key (a) references t1(a); -show create table t4; ---replace_regex /'test\.#sql-[0-9a-f_]*'/'#sql-temporary'/ -# a foreign key 'test/dc' already exists ---error ER_CANT_CREATE_TABLE -alter table t3 add constraint dc foreign key (a) references t1(a); -show create table t3; -alter table t2 drop index b, add index (b); -show create table t2; ---error ER_ROW_IS_REFERENCED_2 -delete from t1; ---error ER_CANT_DROP_FIELD_OR_KEY -drop index dc on t4; -# there is no foreign key dc on t3 ---replace_regex /'\.\/test\/#sql2-[0-9a-f-]*'/'#sql2-temporary'/ ---error ER_ERROR_ON_RENAME -alter table t3 drop foreign key dc; -alter table t4 drop foreign key dc; -select * from t2; -delete from t1; -select * from t2; - -drop table t2,t4,t3,t1; - --- let charset = utf8 --- source include/innodb-index.inc - -create table t1(a int not null, b int) engine = innodb; -insert into t1 values (1,1),(1,1),(1,1),(1,1); ---error ER_DUP_ENTRY -alter table t1 add unique index (a); ---error ER_DUP_ENTRY -alter table t1 add unique index (b); ---error ER_DUP_ENTRY -alter table t1 add unique index (a), add unique index(b); -show create table t1; -drop table t1; - -create table t1(a int not null, c int not null,b int, primary key(a), unique key(c), key(b)) engine = innodb; -alter table t1 drop index c, drop index b; -show create table t1; -drop table t1; - -create table t1(a int not null, b int, primary key(a)) engine = innodb; -alter table t1 add index (b); -show create table t1; -drop table t1; - -create table t1(a int not null, b int, c char(10), d varchar(20), primary key (a)) engine = innodb; -insert into t1 values (1,1,'ab','ab'),(2,2,'ac','ac'),(3,3,'ac','ac'),(4,4,'afe','afe'),(5,4,'affe','affe'); ---error ER_DUP_ENTRY -alter table t1 add unique index (b), add unique index (c), add unique index (d); ---error ER_DUP_ENTRY -alter table t1 add unique index (c), add unique index (b), add index (d); -show create table t1; -drop table t1; - -create table t1(a int not null, b int not null, c int, primary key (a), key(c)) engine=innodb; -insert into t1 values (5,1,5),(4,2,4),(3,3,3),(2,4,2),(1,5,1); -alter table t1 add unique index (b); -insert into t1 values (10,20,20),(11,19,19),(12,18,18),(13,17,17); -show create table t1; -check table t1; -explain select * from t1 force index(c) order by c; -explain select * from t1 order by a; -explain select * from t1 force index(b) order by b; -select * from t1 order by a; -select * from t1 force index(b) order by b; -select * from t1 force index(c) order by c; -drop table t1; - -create table t1(a int not null, b int not null) engine=innodb; -insert into t1 values (1,1); -alter table t1 add primary key(b); -insert into t1 values (2,2); -show create table t1; -check table t1; -select * from t1; -explain select * from t1; -explain select * from t1 order by a; -explain select * from t1 order by b; -checksum table t1; -drop table t1; - -create table t1(a int not null) engine=innodb; -insert into t1 values (1); -alter table t1 add primary key(a); -insert into t1 values (2); -show create table t1; -check table t1; -commit; -select * from t1; -explain select * from t1; -explain select * from t1 order by a; -drop table t1; - -create table t2(d varchar(17) primary key) engine=innodb default charset=utf8; -create table t3(a int primary key) engine=innodb; - -insert into t3 values(22),(44),(33),(55),(66); - -insert into t2 values ('jejdkrun87'),('adfd72nh9k'), -('adfdpplkeock'),('adfdijnmnb78k'),('adfdijn0loKNHJik'); - -create table t1(a int, b blob, c text, d text not null) -engine=innodb default charset = utf8; - -# r2667 The following test is disabled because MySQL behavior changed. -# r2667 The test was added with this comment: -# r2667 -# r2667 ------------------------------------------------------------------------ -# r2667 r1699 | marko | 2007-08-10 19:53:19 +0300 (Fri, 10 Aug 2007) | 5 lines -# r2667 -# r2667 branches/zip: Add changes that accidentally omitted from r1698: -# r2667 -# r2667 innodb-index.test, innodb-index.result: Add a test for creating -# r2667 a PRIMARY KEY on a column that contains a NULL value. -# r2667 ------------------------------------------------------------------------ -# r2667 -# r2667 but in BZR-r2667: -# r2667 http://bazaar.launchpad.net/~mysql/mysql-server/mysql-5.1/revision/davi%40mysql.com-20080617141221-8yre8ys9j4uw3xx5?start_revid=joerg%40mysql.com-20080630105418-7qoe5ehomgrcdb89 -# r2667 MySQL changed the behavior to do full table copy when creating PRIMARY INDEX -# r2667 on a non-NULL column instead of calling ::add_index() which would fail (and -# r2667 this is what we were testing here). Before r2667 the code execution path was -# r2667 like this (when adding PRIMARY INDEX on a non-NULL column with ALTER TABLE): -# r2667 -# r2667 mysql_alter_table() -# r2667 compare_tables() // would return ALTER_TABLE_INDEX_CHANGED -# r2667 ::add_index() // would fail with "primary index cannot contain NULL" -# r2667 -# r2667 after r2667 the code execution path is the following: -# r2667 -# r2667 mysql_alter_table() -# r2667 compare_tables() // returns ALTER_TABLE_DATA_CHANGED -# r2667 full copy is done, without calling ::add_index() -# r2667 -# r2667 To enable, remove "# r2667: " below. -# r2667 -# r2667: insert into t1 values (null,null,null,'null'); -insert into t1 -select a,left(repeat(d,100*a),65535),repeat(d,20*a),d from t2,t3; -drop table t2, t3; -select count(*) from t1 where a=44; -select a, -length(b),b=left(repeat(d,100*a),65535),length(c),c=repeat(d,20*a),d from t1; -# r2667: --error ER_PRIMARY_CANT_HAVE_NULL -# r2667: alter table t1 add primary key (a), add key (b(20)); -# r2667: delete from t1 where d='null'; ---error ER_DUP_ENTRY -alter table t1 add primary key (a), add key (b(20)); -delete from t1 where a%2; -check table t1; -alter table t1 add primary key (a,b(255),c(255)), add key (b(767)); -select count(*) from t1 where a=44; -select a, -length(b),b=left(repeat(d,100*a),65535),length(c),c=repeat(d,20*a),d from t1; -show create table t1; -check table t1; -explain select * from t1 where b like 'adfd%'; - -# -# Test locking -# - -create table t2(a int, b varchar(255), primary key(a,b)) engine=innodb; -insert into t2 select a,left(b,255) from t1; -drop table t1; -rename table t2 to t1; - -connect (a,localhost,root,,); -connect (b,localhost,root,,); -connection a; -set innodb_lock_wait_timeout=1; -begin; -# Obtain an IX lock on the table -select a from t1 limit 1 for update; -connection b; -set innodb_lock_wait_timeout=1; -# This would require an S lock on the table, conflicting with the IX lock. ---error ER_LOCK_WAIT_TIMEOUT -create index t1ba on t1 (b,a); -connection a; -commit; -begin; -# Obtain an IS lock on the table -select a from t1 limit 1 lock in share mode; -connection b; -# This will require an S lock on the table. No conflict with the IS lock. -create index t1ba on t1 (b,a); -# This would require an X lock on the table, conflicting with the IS lock. ---error ER_LOCK_WAIT_TIMEOUT -drop index t1ba on t1; -connection a; -commit; -explain select a from t1 order by b; ---send -select a,sleep(2+a/100) from t1 order by b limit 3; - -# The following DROP INDEX will succeed, altough the SELECT above has -# opened a read view. However, during the execution of the SELECT, -# MySQL should hold a table lock that should block the execution -# of the DROP INDEX below. - -connection b; -select sleep(1); -drop index t1ba on t1; - -# After the index was dropped, subsequent SELECTs will use the same -# read view, but they should not be accessing the dropped index any more. - -connection a; -reap; -explain select a from t1 order by b; -select a from t1 order by b limit 3; -commit; - -connection default; -disconnect a; -disconnect b; - -drop table t1; - -let $per_table=`select @@innodb_file_per_table`; -let $format=`select @@innodb_file_format`; -set global innodb_file_per_table=on; -set global innodb_file_format='Barracuda'; -# Test creating a table that could lead to undo log overflow. -# In the undo log, we write a 768-byte prefix (REC_MAX_INDEX_COL_LEN) -# of each externally stored column that appears as a column prefix in an index. -# For this test case, it would suffice to write 1 byte, though. -create table t1(a blob,b blob,c blob,d blob,e blob,f blob,g blob,h blob, - i blob,j blob,k blob,l blob,m blob,n blob,o blob,p blob, - q blob,r blob,s blob,t blob,u blob) - engine=innodb row_format=dynamic; -create index t1a on t1 (a(1)); -create index t1b on t1 (b(1)); -create index t1c on t1 (c(1)); -create index t1d on t1 (d(1)); -create index t1e on t1 (e(1)); -create index t1f on t1 (f(1)); -create index t1g on t1 (g(1)); -create index t1h on t1 (h(1)); -create index t1i on t1 (i(1)); -create index t1j on t1 (j(1)); -create index t1k on t1 (k(1)); -create index t1l on t1 (l(1)); -create index t1m on t1 (m(1)); -create index t1n on t1 (n(1)); -create index t1o on t1 (o(1)); -create index t1p on t1 (p(1)); -create index t1q on t1 (q(1)); -create index t1r on t1 (r(1)); -create index t1s on t1 (s(1)); -create index t1t on t1 (t(1)); ---error 139 -create index t1u on t1 (u(1)); ---error 139 -create index t1ut on t1 (u(1), t(1)); -create index t1st on t1 (s(1), t(1)); -show create table t1; ---error 139 -create index t1u on t1 (u(1)); -alter table t1 row_format=compact; -create index t1u on t1 (u(1)); - -drop table t1; -eval set global innodb_file_per_table=$per_table; -eval set global innodb_file_format=$format; - -# -# Test to check whether CREATE INDEX handles implicit foreign key -# constraint modifications (Issue #70, Bug #38786) -# -SET @OLD_UNIQUE_CHECKS=@@UNIQUE_CHECKS, UNIQUE_CHECKS=0; -SET @OLD_FOREIGN_KEY_CHECKS=@@FOREIGN_KEY_CHECKS, FOREIGN_KEY_CHECKS=0; - -CREATE TABLE t1( - c1 BIGINT(12) NOT NULL, - PRIMARY KEY (c1) -) ENGINE=InnoDB DEFAULT CHARSET=latin1; - -CREATE TABLE t2( - c1 BIGINT(16) NOT NULL, - c2 BIGINT(12) NOT NULL, - c3 BIGINT(12) NOT NULL, - PRIMARY KEY (c1) -) ENGINE=InnoDB DEFAULT CHARSET=latin1; - -ALTER TABLE t2 ADD CONSTRAINT fk_t2_ca - FOREIGN KEY (c3) REFERENCES t1(c1); - -SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS; -SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS; - -SHOW CREATE TABLE t2; - -CREATE INDEX i_t2_c3_c2 ON t2(c3, c2); - -SHOW CREATE TABLE t2; - -SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS; -SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS; - ---error ER_NO_REFERENCED_ROW_2 -INSERT INTO t2 VALUES(0,0,0); -INSERT INTO t1 VALUES(0); -INSERT INTO t2 VALUES(0,0,0); - -DROP TABLE t2; - -CREATE TABLE t2( - c1 BIGINT(16) NOT NULL, - c2 BIGINT(12) NOT NULL, - c3 BIGINT(12) NOT NULL, - PRIMARY KEY (c1,c2,c3) -) ENGINE=InnoDB DEFAULT CHARSET=latin1; - -ALTER TABLE t2 ADD CONSTRAINT fk_t2_ca - FOREIGN KEY (c3) REFERENCES t1(c1); - -SHOW CREATE TABLE t2; - -CREATE INDEX i_t2_c3_c2 ON t2(c3, c2); - -SHOW CREATE TABLE t2; ---error ER_NO_REFERENCED_ROW_2 -INSERT INTO t2 VALUES(0,0,1); -INSERT INTO t2 VALUES(0,0,0); ---error ER_ROW_IS_REFERENCED_2 -DELETE FROM t1; -DELETE FROM t2; - -DROP TABLE t2; -DROP TABLE t1; - -CREATE TABLE t1( - c1 BIGINT(12) NOT NULL, - c2 INT(4) NOT NULL, - PRIMARY KEY (c2,c1) -) ENGINE=InnoDB DEFAULT CHARSET=latin1; - -CREATE TABLE t2( - c1 BIGINT(16) NOT NULL, - c2 BIGINT(12) NOT NULL, - c3 BIGINT(12) NOT NULL, - PRIMARY KEY (c1) -) ENGINE=InnoDB DEFAULT CHARSET=latin1; - ---replace_regex /'test\.#sql-[0-9_a-f-]*'/'#sql-temporary'/ ---error ER_CANT_CREATE_TABLE -ALTER TABLE t2 ADD CONSTRAINT fk_t2_ca - FOREIGN KEY (c3,c2) REFERENCES t1(c1,c1); ---replace_regex /'test\.#sql-[0-9_a-f-]*'/'#sql-temporary'/ ---error ER_CANT_CREATE_TABLE -ALTER TABLE t2 ADD CONSTRAINT fk_t2_ca - FOREIGN KEY (c3,c2) REFERENCES t1(c1,c2); ---replace_regex /'test\.#sql-[0-9_a-f-]*'/'#sql-temporary'/ ---error ER_CANT_CREATE_TABLE -ALTER TABLE t2 ADD CONSTRAINT fk_t2_ca - FOREIGN KEY (c3,c2) REFERENCES t1(c2,c1); -ALTER TABLE t1 MODIFY COLUMN c2 BIGINT(12) NOT NULL; ---replace_regex /'test\.#sql-[0-9_a-f-]*'/'#sql-temporary'/ ---error ER_CANT_CREATE_TABLE -ALTER TABLE t2 ADD CONSTRAINT fk_t2_ca - FOREIGN KEY (c3,c2) REFERENCES t1(c1,c2); - -ALTER TABLE t2 ADD CONSTRAINT fk_t2_ca - FOREIGN KEY (c3,c2) REFERENCES t1(c2,c1); -SHOW CREATE TABLE t1; -SHOW CREATE TABLE t2; -CREATE INDEX i_t2_c2_c1 ON t2(c2, c1); -SHOW CREATE TABLE t2; -CREATE INDEX i_t2_c3_c1_c2 ON t2(c3, c1, c2); -SHOW CREATE TABLE t2; -CREATE INDEX i_t2_c3_c2 ON t2(c3, c2); -SHOW CREATE TABLE t2; - -DROP TABLE t2; -DROP TABLE t1; - -connect (a,localhost,root,,); -connect (b,localhost,root,,); -connection a; -CREATE TABLE t1 (a INT, b CHAR(1)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (3,'a'),(3,'b'),(1,'c'),(0,'d'),(1,'e'); -connection b; -BEGIN; -SELECT * FROM t1; -connection a; -CREATE INDEX t1a ON t1(a); -connection b; -SELECT * FROM t1; ---error ER_TABLE_DEF_CHANGED -SELECT * FROM t1 FORCE INDEX(t1a) ORDER BY a; -SELECT * FROM t1; -COMMIT; -SELECT * FROM t1 FORCE INDEX(t1a) ORDER BY a; -connection default; -disconnect a; -disconnect b; - -DROP TABLE t1; diff --git a/storage/innodb_plugin/mysql-test/innodb-index_ucs2.result b/storage/innodb_plugin/mysql-test/innodb-index_ucs2.result deleted file mode 100644 index c8a1e8c7da1..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-index_ucs2.result +++ /dev/null @@ -1,116 +0,0 @@ -create table t1(a int not null, b int, c char(10), d varchar(20), primary key (a)) engine = innodb default charset=ucs2; -insert into t1 values (1,1,'ab','ab'),(2,2,'ac','ac'),(3,2,'ad','ad'),(4,4,'afe','afe'); -commit; -alter table t1 add unique index (b); -ERROR 23000: Duplicate entry '2' for key 'b' -insert into t1 values(8,9,'fff','fff'); -select * from t1; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`) -) ENGINE=InnoDB DEFAULT CHARSET=ucs2 -alter table t1 add index (b); -insert into t1 values(10,10,'kkk','iii'); -select * from t1; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -10 10 kkk iii -select * from t1 force index(b) order by b; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -10 10 kkk iii -explain select * from t1 force index(b) order by b; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL b 5 NULL 6 -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`), - KEY `b` (`b`) -) ENGINE=InnoDB DEFAULT CHARSET=ucs2 -alter table t1 add unique index (c), add index (d); -insert into t1 values(11,11,'aaa','mmm'); -select * from t1; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -10 10 kkk iii -11 11 aaa mmm -select * from t1 force index(b) order by b; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -10 10 kkk iii -11 11 aaa mmm -select * from t1 force index(c) order by c; -a b c d -11 11 aaa mmm -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -10 10 kkk iii -select * from t1 force index(d) order by d; -a b c d -1 1 ab ab -2 2 ac ac -3 2 ad ad -4 4 afe afe -8 9 fff fff -10 10 kkk iii -11 11 aaa mmm -explain select * from t1 force index(b) order by b; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL b 5 NULL 7 -explain select * from t1 force index(c) order by c; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL c 21 NULL 7 -explain select * from t1 force index(d) order by d; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL d 43 NULL 7 -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `d` varchar(20) DEFAULT NULL, - PRIMARY KEY (`a`), - UNIQUE KEY `c` (`c`), - KEY `b` (`b`), - KEY `d` (`d`) -) ENGINE=InnoDB DEFAULT CHARSET=ucs2 -check table t1; -Table Op Msg_type Msg_text -test.t1 check status OK -drop table t1; diff --git a/storage/innodb_plugin/mysql-test/innodb-index_ucs2.test b/storage/innodb_plugin/mysql-test/innodb-index_ucs2.test deleted file mode 100644 index fff9a4da1a8..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-index_ucs2.test +++ /dev/null @@ -1,5 +0,0 @@ --- source include/have_innodb.inc --- source include/have_ucs2.inc - --- let charset = ucs2 --- source include/innodb-index.inc diff --git a/storage/innodb_plugin/mysql-test/innodb-lock.result b/storage/innodb_plugin/mysql-test/innodb-lock.result deleted file mode 100644 index 4ace4065c34..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-lock.result +++ /dev/null @@ -1,57 +0,0 @@ -set global innodb_table_locks=1; -select @@innodb_table_locks; -@@innodb_table_locks -1 -drop table if exists t1; -set @@innodb_table_locks=1; -create table t1 (id integer, x integer) engine=INNODB; -insert into t1 values(0, 0); -set autocommit=0; -SELECT * from t1 where id = 0 FOR UPDATE; -id x -0 0 -set autocommit=0; -lock table t1 write; -update t1 set x=1 where id = 0; -select * from t1; -id x -0 1 -commit; -update t1 set x=2 where id = 0; -commit; -unlock tables; -select * from t1; -id x -0 2 -commit; -drop table t1; -set @@innodb_table_locks=0; -create table t1 (id integer primary key, x integer) engine=INNODB; -insert into t1 values(0, 0),(1,1),(2,2); -commit; -SELECT * from t1 where id = 0 FOR UPDATE; -id x -0 0 -set autocommit=0; -set @@innodb_table_locks=0; -lock table t1 write; -update t1 set x=10 where id = 2; -SELECT * from t1 where id = 2; -id x -2 2 -UPDATE t1 set x=3 where id = 2; -commit; -SELECT * from t1; -id x -0 0 -1 1 -2 3 -commit; -unlock tables; -commit; -select * from t1; -id x -0 0 -1 1 -2 10 -drop table t1; diff --git a/storage/innodb_plugin/mysql-test/innodb-lock.test b/storage/innodb_plugin/mysql-test/innodb-lock.test deleted file mode 100644 index eacf7e562be..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-lock.test +++ /dev/null @@ -1,102 +0,0 @@ --- source include/have_innodb.inc - -# -# Check and select innodb lock type -# - -set global innodb_table_locks=1; - -select @@innodb_table_locks; - -# -# Testing of explicit table locks with enforced table locks -# - -connect (con1,localhost,root,,); -connect (con2,localhost,root,,); - ---disable_warnings -drop table if exists t1; ---enable_warnings - -# -# Testing of explicit table locks with enforced table locks -# - -set @@innodb_table_locks=1; - -connection con1; -create table t1 (id integer, x integer) engine=INNODB; -insert into t1 values(0, 0); -set autocommit=0; -SELECT * from t1 where id = 0 FOR UPDATE; - -connection con2; -set autocommit=0; - -# The following statement should hang because con1 is locking the page ---send -lock table t1 write; ---sleep 2 - -connection con1; -update t1 set x=1 where id = 0; -select * from t1; -commit; - -connection con2; -reap; -update t1 set x=2 where id = 0; -commit; -unlock tables; - -connection con1; -select * from t1; -commit; - -drop table t1; - -# -# Try with old lock method (where LOCK TABLE is ignored by InnoDB) -# - -set @@innodb_table_locks=0; - -create table t1 (id integer primary key, x integer) engine=INNODB; -insert into t1 values(0, 0),(1,1),(2,2); -commit; -SELECT * from t1 where id = 0 FOR UPDATE; - -connection con2; -set autocommit=0; -set @@innodb_table_locks=0; - -# The following statement should work becase innodb doesn't check table locks -lock table t1 write; - -connection con1; - -# This will be locked by MySQL ---send -update t1 set x=10 where id = 2; ---sleep 2 - -connection con2; - -# Note that we will get a deadlock if we try to select any rows marked -# for update by con1 ! - -SELECT * from t1 where id = 2; -UPDATE t1 set x=3 where id = 2; -commit; -SELECT * from t1; -commit; -unlock tables; - -connection con1; -reap; -commit; -select * from t1; -drop table t1; - -# End of 4.1 tests diff --git a/storage/innodb_plugin/mysql-test/innodb-master.opt b/storage/innodb_plugin/mysql-test/innodb-master.opt deleted file mode 100644 index 4901efb416c..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-master.opt +++ /dev/null @@ -1 +0,0 @@ ---binlog_cache_size=32768 --innodb_lock_wait_timeout=1 diff --git a/storage/innodb_plugin/mysql-test/innodb-replace.result b/storage/innodb_plugin/mysql-test/innodb-replace.result deleted file mode 100644 index c926bb89a2e..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-replace.result +++ /dev/null @@ -1,13 +0,0 @@ -drop table if exists t1; -create table t1 (c1 char(5) unique not null, c2 int, stamp timestamp) engine=innodb; -select * from t1; -c1 c2 stamp -replace delayed into t1 (c1, c2) values ( "text1","11"); -ERROR HY000: DELAYED option not supported for table 't1' -select * from t1; -c1 c2 stamp -replace delayed into t1 (c1, c2) values ( "text1","12"); -ERROR HY000: DELAYED option not supported for table 't1' -select * from t1; -c1 c2 stamp -drop table t1; diff --git a/storage/innodb_plugin/mysql-test/innodb-replace.test b/storage/innodb_plugin/mysql-test/innodb-replace.test deleted file mode 100644 index 8c3aacde5e8..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-replace.test +++ /dev/null @@ -1,22 +0,0 @@ --- source include/have_innodb.inc -# embedded server ignores 'delayed', so skip this --- source include/not_embedded.inc - ---disable_warnings -drop table if exists t1; ---enable_warnings - -# -# Bug #1078 -# -create table t1 (c1 char(5) unique not null, c2 int, stamp timestamp) engine=innodb; -select * from t1; ---error ER_DELAYED_NOT_SUPPORTED -replace delayed into t1 (c1, c2) values ( "text1","11"); -select * from t1; ---error ER_DELAYED_NOT_SUPPORTED -replace delayed into t1 (c1, c2) values ( "text1","12"); -select * from t1; -drop table t1; - -# End of 4.1 tests diff --git a/storage/innodb_plugin/mysql-test/innodb-semi-consistent-master.opt b/storage/innodb_plugin/mysql-test/innodb-semi-consistent-master.opt deleted file mode 100644 index e76299453d3..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-semi-consistent-master.opt +++ /dev/null @@ -1 +0,0 @@ ---innodb_lock_wait_timeout=2 diff --git a/storage/innodb_plugin/mysql-test/innodb-semi-consistent.result b/storage/innodb_plugin/mysql-test/innodb-semi-consistent.result deleted file mode 100644 index ca0e362ef80..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-semi-consistent.result +++ /dev/null @@ -1,47 +0,0 @@ -drop table if exists t1; -set binlog_format=mixed; -set session transaction isolation level repeatable read; -create table t1(a int not null) engine=innodb DEFAULT CHARSET=latin1; -insert into t1 values (1),(2),(3),(4),(5),(6),(7); -set autocommit=0; -select * from t1 where a=3 lock in share mode; -a -3 -set binlog_format=mixed; -set session transaction isolation level repeatable read; -set autocommit=0; -update t1 set a=10 where a=5; -ERROR HY000: Lock wait timeout exceeded; try restarting transaction -commit; -set session transaction isolation level read committed; -update t1 set a=10 where a=5; -select * from t1 where a=2 for update; -ERROR HY000: Lock wait timeout exceeded; try restarting transaction -select * from t1 where a=2 limit 1 for update; -a -2 -update t1 set a=11 where a=6; -update t1 set a=12 where a=2; -ERROR HY000: Lock wait timeout exceeded; try restarting transaction -update t1 set a=13 where a=1; -ERROR HY000: Lock wait timeout exceeded; try restarting transaction -commit; -update t1 set a=14 where a=1; -commit; -select * from t1; -a -14 -2 -3 -4 -10 -11 -7 -drop table t1; -create table t1 (a int, b int) engine=myisam; -create table t2 (c int, d int, key (c)) engine=innodb; -insert into t1 values (1,1); -insert into t2 values (1,2); -set session transaction isolation level read committed; -delete from t1 using t1 join t2 on t1.a = t2.c where t2.d in (1); -drop table t1, t2; diff --git a/storage/innodb_plugin/mysql-test/innodb-semi-consistent.test b/storage/innodb_plugin/mysql-test/innodb-semi-consistent.test deleted file mode 100644 index 61ad7815ca9..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-semi-consistent.test +++ /dev/null @@ -1,68 +0,0 @@ --- source include/not_embedded.inc --- source include/have_innodb.inc - ---disable_warnings -drop table if exists t1; ---enable_warnings - -# basic tests of semi-consistent reads - -connect (a,localhost,root,,); -connect (b,localhost,root,,); -connection a; -set binlog_format=mixed; -set session transaction isolation level repeatable read; -create table t1(a int not null) engine=innodb DEFAULT CHARSET=latin1; -insert into t1 values (1),(2),(3),(4),(5),(6),(7); -set autocommit=0; -# this should lock the entire table -select * from t1 where a=3 lock in share mode; -connection b; -set binlog_format=mixed; -set session transaction isolation level repeatable read; -set autocommit=0; --- error ER_LOCK_WAIT_TIMEOUT -update t1 set a=10 where a=5; -connection a; -commit; -connection b; -# perform a semi-consisent read (and unlock non-matching rows) -set session transaction isolation level read committed; -update t1 set a=10 where a=5; -connection a; --- error ER_LOCK_WAIT_TIMEOUT -select * from t1 where a=2 for update; -# this should lock the records (1),(2) -select * from t1 where a=2 limit 1 for update; -connection b; -# semi-consistent read will skip non-matching locked rows a=1, a=2 -update t1 set a=11 where a=6; --- error ER_LOCK_WAIT_TIMEOUT -update t1 set a=12 where a=2; --- error ER_LOCK_WAIT_TIMEOUT -update t1 set a=13 where a=1; -connection a; -commit; -connection b; -update t1 set a=14 where a=1; -commit; -connection a; -select * from t1; -drop table t1; - -connection default; -disconnect a; -disconnect b; - -# Bug 39320 -create table t1 (a int, b int) engine=myisam; -create table t2 (c int, d int, key (c)) engine=innodb; -insert into t1 values (1,1); -insert into t2 values (1,2); -connect (a,localhost,root,,); -connection a; -set session transaction isolation level read committed; -delete from t1 using t1 join t2 on t1.a = t2.c where t2.d in (1); -connection default; -disconnect a; -drop table t1, t2; diff --git a/storage/innodb_plugin/mysql-test/innodb-timeout.result b/storage/innodb_plugin/mysql-test/innodb-timeout.result deleted file mode 100644 index be9a688cd72..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-timeout.result +++ /dev/null @@ -1,38 +0,0 @@ -set global innodb_lock_wait_timeout=42; -select @@innodb_lock_wait_timeout; -@@innodb_lock_wait_timeout -42 -set innodb_lock_wait_timeout=1; -select @@innodb_lock_wait_timeout; -@@innodb_lock_wait_timeout -1 -select @@innodb_lock_wait_timeout; -@@innodb_lock_wait_timeout -42 -set global innodb_lock_wait_timeout=347; -select @@innodb_lock_wait_timeout; -@@innodb_lock_wait_timeout -42 -set innodb_lock_wait_timeout=1; -select @@innodb_lock_wait_timeout; -@@innodb_lock_wait_timeout -1 -select @@innodb_lock_wait_timeout; -@@innodb_lock_wait_timeout -347 -create table t1(a int primary key)engine=innodb; -begin; -insert into t1 values(1),(2),(3); -select * from t1 for update; -commit; -a -1 -2 -3 -begin; -insert into t1 values(4); -select * from t1 for update; -commit; -ERROR HY000: Lock wait timeout exceeded; try restarting transaction -drop table t1; -set global innodb_lock_wait_timeout=50; diff --git a/storage/innodb_plugin/mysql-test/innodb-timeout.test b/storage/innodb_plugin/mysql-test/innodb-timeout.test deleted file mode 100644 index f23fe3cff2d..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-timeout.test +++ /dev/null @@ -1,64 +0,0 @@ --- source include/have_innodb.inc - -let $timeout=`select @@innodb_lock_wait_timeout`; -set global innodb_lock_wait_timeout=42; - -connect (a,localhost,root,,); -connect (b,localhost,root,,); - -connection a; -select @@innodb_lock_wait_timeout; -set innodb_lock_wait_timeout=1; -select @@innodb_lock_wait_timeout; - -connection b; -select @@innodb_lock_wait_timeout; -set global innodb_lock_wait_timeout=347; -select @@innodb_lock_wait_timeout; -set innodb_lock_wait_timeout=1; -select @@innodb_lock_wait_timeout; - -connect (c,localhost,root,,); -connection c; -select @@innodb_lock_wait_timeout; -connection default; -disconnect c; - -connection a; -create table t1(a int primary key)engine=innodb; -begin; -insert into t1 values(1),(2),(3); - -connection b; ---send -select * from t1 for update; - -connection a; -commit; - -connection b; -reap; - -connection a; -begin; -insert into t1 values(4); - -connection b; ---send -select * from t1 for update; - -connection a; -sleep 2; -commit; - -connection b; ---error ER_LOCK_WAIT_TIMEOUT -reap; -drop table t1; - -connection default; - -disconnect a; -disconnect b; - -eval set global innodb_lock_wait_timeout=$timeout; diff --git a/storage/innodb_plugin/mysql-test/innodb-use-sys-malloc-master.opt b/storage/innodb_plugin/mysql-test/innodb-use-sys-malloc-master.opt deleted file mode 100644 index 889834add01..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-use-sys-malloc-master.opt +++ /dev/null @@ -1,2 +0,0 @@ ---innodb-use-sys-malloc=true ---innodb-use-sys-malloc=true diff --git a/storage/innodb_plugin/mysql-test/innodb-use-sys-malloc.result b/storage/innodb_plugin/mysql-test/innodb-use-sys-malloc.result deleted file mode 100644 index 2ec4c7c8130..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-use-sys-malloc.result +++ /dev/null @@ -1,48 +0,0 @@ -SELECT @@GLOBAL.innodb_use_sys_malloc; -@@GLOBAL.innodb_use_sys_malloc -1 -1 Expected -SET @@GLOBAL.innodb_use_sys_malloc=0; -ERROR HY000: Variable 'innodb_use_sys_malloc' is a read only variable -Expected error 'Read only variable' -SELECT @@GLOBAL.innodb_use_sys_malloc; -@@GLOBAL.innodb_use_sys_malloc -1 -1 Expected -drop table if exists t1; -create table t1(a int not null) engine=innodb DEFAULT CHARSET=latin1; -insert into t1 values (1),(2),(3),(4),(5),(6),(7); -select * from t1; -a -1 -2 -3 -4 -5 -6 -7 -drop table t1; -SELECT @@GLOBAL.innodb_use_sys_malloc; -@@GLOBAL.innodb_use_sys_malloc -1 -1 Expected -SET @@GLOBAL.innodb_use_sys_malloc=0; -ERROR HY000: Variable 'innodb_use_sys_malloc' is a read only variable -Expected error 'Read only variable' -SELECT @@GLOBAL.innodb_use_sys_malloc; -@@GLOBAL.innodb_use_sys_malloc -1 -1 Expected -drop table if exists t1; -create table t1(a int not null) engine=innodb DEFAULT CHARSET=latin1; -insert into t1 values (1),(2),(3),(4),(5),(6),(7); -select * from t1; -a -1 -2 -3 -4 -5 -6 -7 -drop table t1; diff --git a/storage/innodb_plugin/mysql-test/innodb-use-sys-malloc.test b/storage/innodb_plugin/mysql-test/innodb-use-sys-malloc.test deleted file mode 100644 index 325dd19d086..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-use-sys-malloc.test +++ /dev/null @@ -1,48 +0,0 @@ ---source include/have_innodb.inc - -#display current value of innodb_use_sys_malloc -SELECT @@GLOBAL.innodb_use_sys_malloc; ---echo 1 Expected - -#try changing it. Should fail. ---error ER_INCORRECT_GLOBAL_LOCAL_VAR -SET @@GLOBAL.innodb_use_sys_malloc=0; ---echo Expected error 'Read only variable' - -SELECT @@GLOBAL.innodb_use_sys_malloc; ---echo 1 Expected - - -#do some stuff to see if it works. ---disable_warnings -drop table if exists t1; ---enable_warnings - -create table t1(a int not null) engine=innodb DEFAULT CHARSET=latin1; -insert into t1 values (1),(2),(3),(4),(5),(6),(7); -select * from t1; -drop table t1; ---source include/have_innodb.inc - -#display current value of innodb_use_sys_malloc -SELECT @@GLOBAL.innodb_use_sys_malloc; ---echo 1 Expected - -#try changing it. Should fail. ---error ER_INCORRECT_GLOBAL_LOCAL_VAR -SET @@GLOBAL.innodb_use_sys_malloc=0; ---echo Expected error 'Read only variable' - -SELECT @@GLOBAL.innodb_use_sys_malloc; ---echo 1 Expected - - -#do some stuff to see if it works. ---disable_warnings -drop table if exists t1; ---enable_warnings - -create table t1(a int not null) engine=innodb DEFAULT CHARSET=latin1; -insert into t1 values (1),(2),(3),(4),(5),(6),(7); -select * from t1; -drop table t1; diff --git a/storage/innodb_plugin/mysql-test/innodb-zip.result b/storage/innodb_plugin/mysql-test/innodb-zip.result deleted file mode 100644 index b26c4112826..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-zip.result +++ /dev/null @@ -1,421 +0,0 @@ -set global innodb_file_per_table=off; -set global innodb_file_format=`0`; -create table t0(a int primary key) engine=innodb row_format=compressed; -Warnings: -Warning 1478 InnoDB: ROW_FORMAT=COMPRESSED requires innodb_file_per_table. -Warning 1478 InnoDB: assuming ROW_FORMAT=COMPACT. -create table t00(a int primary key) engine=innodb -key_block_size=4 row_format=compressed; -Warnings: -Warning 1478 InnoDB: KEY_BLOCK_SIZE requires innodb_file_per_table. -Warning 1478 InnoDB: KEY_BLOCK_SIZE requires innodb_file_format > Antelope. -Warning 1478 InnoDB: ignoring KEY_BLOCK_SIZE=4. -Warning 1478 InnoDB: ROW_FORMAT=COMPRESSED requires innodb_file_per_table. -Warning 1478 InnoDB: assuming ROW_FORMAT=COMPACT. -create table t1(a int primary key) engine=innodb row_format=dynamic; -Warnings: -Warning 1478 InnoDB: ROW_FORMAT=DYNAMIC requires innodb_file_per_table. -Warning 1478 InnoDB: assuming ROW_FORMAT=COMPACT. -create table t2(a int primary key) engine=innodb row_format=redundant; -create table t3(a int primary key) engine=innodb row_format=compact; -create table t4(a int primary key) engine=innodb key_block_size=9; -Warnings: -Warning 1478 InnoDB: KEY_BLOCK_SIZE requires innodb_file_per_table. -Warning 1478 InnoDB: KEY_BLOCK_SIZE requires innodb_file_format > Antelope. -Warning 1478 InnoDB: ignoring KEY_BLOCK_SIZE=9. -create table t5(a int primary key) engine=innodb -key_block_size=1 row_format=redundant; -Warnings: -Warning 1478 InnoDB: KEY_BLOCK_SIZE requires innodb_file_per_table. -Warning 1478 InnoDB: KEY_BLOCK_SIZE requires innodb_file_format > Antelope. -Warning 1478 InnoDB: ignoring KEY_BLOCK_SIZE=1. -set global innodb_file_per_table=on; -create table t6(a int primary key) engine=innodb -key_block_size=1 row_format=redundant; -Warnings: -Warning 1478 InnoDB: KEY_BLOCK_SIZE requires innodb_file_format > Antelope. -Warning 1478 InnoDB: ignoring KEY_BLOCK_SIZE=1. -set global innodb_file_format=`1`; -create table t7(a int primary key) engine=innodb -key_block_size=1 row_format=redundant; -Warnings: -Warning 1478 InnoDB: ignoring KEY_BLOCK_SIZE=1 unless ROW_FORMAT=COMPRESSED. -create table t8(a int primary key) engine=innodb -key_block_size=1 row_format=fixed; -Warnings: -Warning 1478 InnoDB: ignoring KEY_BLOCK_SIZE=1 unless ROW_FORMAT=COMPRESSED. -Warning 1478 InnoDB: assuming ROW_FORMAT=COMPACT. -create table t9(a int primary key) engine=innodb -key_block_size=1 row_format=compact; -Warnings: -Warning 1478 InnoDB: ignoring KEY_BLOCK_SIZE=1 unless ROW_FORMAT=COMPRESSED. -create table t10(a int primary key) engine=innodb -key_block_size=1 row_format=dynamic; -Warnings: -Warning 1478 InnoDB: ignoring KEY_BLOCK_SIZE=1 unless ROW_FORMAT=COMPRESSED. -create table t11(a int primary key) engine=innodb -key_block_size=1 row_format=compressed; -create table t12(a int primary key) engine=innodb -key_block_size=1; -create table t13(a int primary key) engine=innodb -row_format=compressed; -create table t14(a int primary key) engine=innodb key_block_size=9; -Warnings: -Warning 1478 InnoDB: ignoring KEY_BLOCK_SIZE=9. -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -table_schema table_name row_format -test t0 Compact -test t00 Compact -test t1 Compact -test t10 Dynamic -test t11 Compressed -test t12 Compressed -test t13 Compressed -test t14 Compact -test t2 Redundant -test t3 Compact -test t4 Compact -test t5 Redundant -test t6 Redundant -test t7 Redundant -test t8 Compact -test t9 Compact -drop table t0,t00,t2,t3,t4,t5,t6,t7,t8,t9,t10,t11,t12,t13,t14; -alter table t1 key_block_size=0; -Warnings: -Warning 1478 InnoDB: ignoring KEY_BLOCK_SIZE=0. -alter table t1 row_format=dynamic; -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -table_schema table_name row_format -test t1 Dynamic -alter table t1 row_format=compact; -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -table_schema table_name row_format -test t1 Compact -alter table t1 row_format=redundant; -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -table_schema table_name row_format -test t1 Redundant -drop table t1; -create table t1(a int not null, b text, index(b(10))) engine=innodb -key_block_size=1; -create table t2(b text)engine=innodb; -insert into t2 values(concat('1abcdefghijklmnopqrstuvwxyz', repeat('A',5000))); -insert into t1 select 1, b from t2; -commit; -begin; -update t1 set b=repeat('B',100); -select a,left(b,40) from t1 natural join t2; -a left(b,40) -1 1abcdefghijklmnopqrstuvwxyzAAAAAAAAAAAAA -rollback; -select a,left(b,40) from t1 natural join t2; -a left(b,40) -1 1abcdefghijklmnopqrstuvwxyzAAAAAAAAAAAAA -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -table_schema table_name row_format -test t1 Compressed -test t2 Compact -drop table t1,t2; -SET SESSION innodb_strict_mode = off; -CREATE TABLE t1( -c TEXT NOT NULL, d TEXT NOT NULL, -PRIMARY KEY (c(767),d(767))) -ENGINE=InnoDB ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=1 CHARSET=ASCII; -ERROR 42000: Row size too large. The maximum row size for the used table type, not counting BLOBs, is 8126. You have to change some columns to TEXT or BLOBs -CREATE TABLE t1( -c TEXT NOT NULL, d TEXT NOT NULL, -PRIMARY KEY (c(767),d(767))) -ENGINE=InnoDB ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=2 CHARSET=ASCII; -ERROR 42000: Row size too large. The maximum row size for the used table type, not counting BLOBs, is 8126. You have to change some columns to TEXT or BLOBs -CREATE TABLE t1( -c TEXT NOT NULL, d TEXT NOT NULL, -PRIMARY KEY (c(767),d(767))) -ENGINE=InnoDB ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=4 CHARSET=ASCII; -drop table t1; -CREATE TABLE t1(c TEXT, PRIMARY KEY (c(440))) -ENGINE=InnoDB ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=1 CHARSET=ASCII; -ERROR 42000: Row size too large. The maximum row size for the used table type, not counting BLOBs, is 8126. You have to change some columns to TEXT or BLOBs -CREATE TABLE t1(c TEXT, PRIMARY KEY (c(438))) -ENGINE=InnoDB ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=1 CHARSET=ASCII; -INSERT INTO t1 VALUES(REPEAT('A',512)),(REPEAT('B',512)); -DROP TABLE t1; -create table t1( c1 int not null, c2 blob, c3 blob, c4 blob, -primary key(c1, c2(22), c3(22))) -engine = innodb row_format = dynamic; -begin; -insert into t1 values(1, repeat('A', 20000), repeat('B', 20000), -repeat('C', 20000)); -update t1 set c3 = repeat('D', 20000) where c1 = 1; -commit; -select count(*) from t1 where c2 = repeat('A', 20000); -count(*) -1 -select count(*) from t1 where c3 = repeat('D', 20000); -count(*) -1 -select count(*) from t1 where c4 = repeat('C', 20000); -count(*) -1 -update t1 set c3 = repeat('E', 20000) where c1 = 1; -drop table t1; -set global innodb_file_format=`0`; -select @@innodb_file_format; -@@innodb_file_format -Antelope -set global innodb_file_format=`1`; -select @@innodb_file_format; -@@innodb_file_format -Barracuda -set global innodb_file_format=`2`; -ERROR HY000: Incorrect arguments to SET -set global innodb_file_format=`-1`; -ERROR HY000: Incorrect arguments to SET -set global innodb_file_format=`Antelope`; -set global innodb_file_format=`Barracuda`; -set global innodb_file_format=`Cheetah`; -ERROR HY000: Incorrect arguments to SET -set global innodb_file_format=`abc`; -ERROR HY000: Incorrect arguments to SET -set global innodb_file_format=`1a`; -ERROR HY000: Incorrect arguments to SET -set global innodb_file_format=``; -ERROR HY000: Incorrect arguments to SET -set global innodb_file_per_table = on; -set global innodb_file_format = `1`; -set innodb_strict_mode = off; -create table t1 (id int primary key) engine = innodb key_block_size = 0; -Warnings: -Warning 1478 InnoDB: ignoring KEY_BLOCK_SIZE=0. -drop table t1; -set innodb_strict_mode = on; -create table t1 (id int primary key) engine = innodb key_block_size = 0; -ERROR HY000: Can't create table 'test.t1' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: invalid KEY_BLOCK_SIZE = 0. Valid values are [1, 2, 4, 8, 16] -Error 1005 Can't create table 'test.t1' (errno: 1478) -create table t2 (id int primary key) engine = innodb key_block_size = 9; -ERROR HY000: Can't create table 'test.t2' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: invalid KEY_BLOCK_SIZE = 9. Valid values are [1, 2, 4, 8, 16] -Error 1005 Can't create table 'test.t2' (errno: 1478) -create table t3 (id int primary key) engine = innodb key_block_size = 1; -create table t4 (id int primary key) engine = innodb key_block_size = 2; -create table t5 (id int primary key) engine = innodb key_block_size = 4; -create table t6 (id int primary key) engine = innodb key_block_size = 8; -create table t7 (id int primary key) engine = innodb key_block_size = 16; -create table t8 (id int primary key) engine = innodb row_format = compressed; -create table t9 (id int primary key) engine = innodb row_format = dynamic; -create table t10(id int primary key) engine = innodb row_format = compact; -create table t11(id int primary key) engine = innodb row_format = redundant; -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -table_schema table_name row_format -test t10 Compact -test t11 Redundant -test t3 Compressed -test t4 Compressed -test t5 Compressed -test t6 Compressed -test t7 Compressed -test t8 Compressed -test t9 Dynamic -drop table t3, t4, t5, t6, t7, t8, t9, t10, t11; -create table t1 (id int primary key) engine = innodb -key_block_size = 8 row_format = compressed; -create table t2 (id int primary key) engine = innodb -key_block_size = 8 row_format = redundant; -ERROR HY000: Can't create table 'test.t2' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: cannot specify ROW_FORMAT = REDUNDANT with KEY_BLOCK_SIZE. -Error 1005 Can't create table 'test.t2' (errno: 1478) -create table t3 (id int primary key) engine = innodb -key_block_size = 8 row_format = compact; -ERROR HY000: Can't create table 'test.t3' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: cannot specify ROW_FORMAT = COMPACT with KEY_BLOCK_SIZE. -Error 1005 Can't create table 'test.t3' (errno: 1478) -create table t4 (id int primary key) engine = innodb -key_block_size = 8 row_format = dynamic; -ERROR HY000: Can't create table 'test.t4' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: cannot specify ROW_FORMAT = DYNAMIC with KEY_BLOCK_SIZE. -Error 1005 Can't create table 'test.t4' (errno: 1478) -create table t5 (id int primary key) engine = innodb -key_block_size = 8 row_format = default; -ERROR HY000: Can't create table 'test.t5' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: cannot specify ROW_FORMAT = COMPACT with KEY_BLOCK_SIZE. -Error 1005 Can't create table 'test.t5' (errno: 1478) -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -table_schema table_name row_format -test t1 Compressed -drop table t1; -create table t1 (id int primary key) engine = innodb -key_block_size = 9 row_format = redundant; -ERROR HY000: Can't create table 'test.t1' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: invalid KEY_BLOCK_SIZE = 9. Valid values are [1, 2, 4, 8, 16] -Error 1478 InnoDB: cannot specify ROW_FORMAT = REDUNDANT with KEY_BLOCK_SIZE. -Error 1005 Can't create table 'test.t1' (errno: 1478) -create table t2 (id int primary key) engine = innodb -key_block_size = 9 row_format = compact; -ERROR HY000: Can't create table 'test.t2' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: invalid KEY_BLOCK_SIZE = 9. Valid values are [1, 2, 4, 8, 16] -Error 1478 InnoDB: cannot specify ROW_FORMAT = COMPACT with KEY_BLOCK_SIZE. -Error 1005 Can't create table 'test.t2' (errno: 1478) -create table t2 (id int primary key) engine = innodb -key_block_size = 9 row_format = dynamic; -ERROR HY000: Can't create table 'test.t2' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: invalid KEY_BLOCK_SIZE = 9. Valid values are [1, 2, 4, 8, 16] -Error 1478 InnoDB: cannot specify ROW_FORMAT = DYNAMIC with KEY_BLOCK_SIZE. -Error 1005 Can't create table 'test.t2' (errno: 1478) -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -table_schema table_name row_format -set global innodb_file_per_table = off; -create table t1 (id int primary key) engine = innodb key_block_size = 1; -ERROR HY000: Can't create table 'test.t1' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: KEY_BLOCK_SIZE requires innodb_file_per_table. -Error 1005 Can't create table 'test.t1' (errno: 1478) -create table t2 (id int primary key) engine = innodb key_block_size = 2; -ERROR HY000: Can't create table 'test.t2' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: KEY_BLOCK_SIZE requires innodb_file_per_table. -Error 1005 Can't create table 'test.t2' (errno: 1478) -create table t3 (id int primary key) engine = innodb key_block_size = 4; -ERROR HY000: Can't create table 'test.t3' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: KEY_BLOCK_SIZE requires innodb_file_per_table. -Error 1005 Can't create table 'test.t3' (errno: 1478) -create table t4 (id int primary key) engine = innodb key_block_size = 8; -ERROR HY000: Can't create table 'test.t4' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: KEY_BLOCK_SIZE requires innodb_file_per_table. -Error 1005 Can't create table 'test.t4' (errno: 1478) -create table t5 (id int primary key) engine = innodb key_block_size = 16; -ERROR HY000: Can't create table 'test.t5' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: KEY_BLOCK_SIZE requires innodb_file_per_table. -Error 1005 Can't create table 'test.t5' (errno: 1478) -create table t6 (id int primary key) engine = innodb row_format = compressed; -ERROR HY000: Can't create table 'test.t6' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: ROW_FORMAT=COMPRESSED requires innodb_file_per_table. -Error 1005 Can't create table 'test.t6' (errno: 1478) -create table t7 (id int primary key) engine = innodb row_format = dynamic; -ERROR HY000: Can't create table 'test.t7' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: ROW_FORMAT=DYNAMIC requires innodb_file_per_table. -Error 1005 Can't create table 'test.t7' (errno: 1478) -create table t8 (id int primary key) engine = innodb row_format = compact; -create table t9 (id int primary key) engine = innodb row_format = redundant; -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -table_schema table_name row_format -test t8 Compact -test t9 Redundant -drop table t8, t9; -set global innodb_file_per_table = on; -set global innodb_file_format = `0`; -create table t1 (id int primary key) engine = innodb key_block_size = 1; -ERROR HY000: Can't create table 'test.t1' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: KEY_BLOCK_SIZE requires innodb_file_format > Antelope. -Error 1005 Can't create table 'test.t1' (errno: 1478) -create table t2 (id int primary key) engine = innodb key_block_size = 2; -ERROR HY000: Can't create table 'test.t2' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: KEY_BLOCK_SIZE requires innodb_file_format > Antelope. -Error 1005 Can't create table 'test.t2' (errno: 1478) -create table t3 (id int primary key) engine = innodb key_block_size = 4; -ERROR HY000: Can't create table 'test.t3' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: KEY_BLOCK_SIZE requires innodb_file_format > Antelope. -Error 1005 Can't create table 'test.t3' (errno: 1478) -create table t4 (id int primary key) engine = innodb key_block_size = 8; -ERROR HY000: Can't create table 'test.t4' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: KEY_BLOCK_SIZE requires innodb_file_format > Antelope. -Error 1005 Can't create table 'test.t4' (errno: 1478) -create table t5 (id int primary key) engine = innodb key_block_size = 16; -ERROR HY000: Can't create table 'test.t5' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: KEY_BLOCK_SIZE requires innodb_file_format > Antelope. -Error 1005 Can't create table 'test.t5' (errno: 1478) -create table t6 (id int primary key) engine = innodb row_format = compressed; -ERROR HY000: Can't create table 'test.t6' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: ROW_FORMAT=COMPRESSED requires innodb_file_format > Antelope. -Error 1005 Can't create table 'test.t6' (errno: 1478) -create table t7 (id int primary key) engine = innodb row_format = dynamic; -ERROR HY000: Can't create table 'test.t7' (errno: 1478) -show errors; -Level Code Message -Error 1478 InnoDB: ROW_FORMAT=DYNAMIC requires innodb_file_format > Antelope. -Error 1005 Can't create table 'test.t7' (errno: 1478) -create table t8 (id int primary key) engine = innodb row_format = compact; -create table t9 (id int primary key) engine = innodb row_format = redundant; -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -table_schema table_name row_format -test t8 Compact -test t9 Redundant -drop table t8, t9; -set global innodb_file_per_table=0; -set global innodb_file_format=Antelope; -set global innodb_file_per_table=on; -set global innodb_file_format=`Barracuda`; -set global innodb_file_format_check=`Antelope`; -create table normal_table ( -c1 int -) engine = innodb; -select @@innodb_file_format_check; -@@innodb_file_format_check -Antelope -create table zip_table ( -c1 int -) engine = innodb key_block_size = 8; -select @@innodb_file_format_check; -@@innodb_file_format_check -Barracuda -set global innodb_file_format_check=`Antelope`; -select @@innodb_file_format_check; -@@innodb_file_format_check -Antelope -show table status; -select @@innodb_file_format_check; -@@innodb_file_format_check -Barracuda -drop table normal_table, zip_table; diff --git a/storage/innodb_plugin/mysql-test/innodb-zip.test b/storage/innodb_plugin/mysql-test/innodb-zip.test deleted file mode 100644 index 5bcd0e3c824..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb-zip.test +++ /dev/null @@ -1,343 +0,0 @@ --- source include/have_innodb.inc - -let $per_table=`select @@innodb_file_per_table`; -let $format=`select @@innodb_file_format`; -let $innodb_file_format_check_orig=`select @@innodb_file_format_check`; -set global innodb_file_per_table=off; -set global innodb_file_format=`0`; - -create table t0(a int primary key) engine=innodb row_format=compressed; -create table t00(a int primary key) engine=innodb -key_block_size=4 row_format=compressed; -create table t1(a int primary key) engine=innodb row_format=dynamic; -create table t2(a int primary key) engine=innodb row_format=redundant; -create table t3(a int primary key) engine=innodb row_format=compact; -create table t4(a int primary key) engine=innodb key_block_size=9; -create table t5(a int primary key) engine=innodb -key_block_size=1 row_format=redundant; - -set global innodb_file_per_table=on; -create table t6(a int primary key) engine=innodb -key_block_size=1 row_format=redundant; -set global innodb_file_format=`1`; -create table t7(a int primary key) engine=innodb -key_block_size=1 row_format=redundant; -create table t8(a int primary key) engine=innodb -key_block_size=1 row_format=fixed; -create table t9(a int primary key) engine=innodb -key_block_size=1 row_format=compact; -create table t10(a int primary key) engine=innodb -key_block_size=1 row_format=dynamic; -create table t11(a int primary key) engine=innodb -key_block_size=1 row_format=compressed; -create table t12(a int primary key) engine=innodb -key_block_size=1; -create table t13(a int primary key) engine=innodb -row_format=compressed; -create table t14(a int primary key) engine=innodb key_block_size=9; - -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; - -drop table t0,t00,t2,t3,t4,t5,t6,t7,t8,t9,t10,t11,t12,t13,t14; -alter table t1 key_block_size=0; -alter table t1 row_format=dynamic; -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -alter table t1 row_format=compact; -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -alter table t1 row_format=redundant; -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -drop table t1; - -create table t1(a int not null, b text, index(b(10))) engine=innodb -key_block_size=1; - -create table t2(b text)engine=innodb; -insert into t2 values(concat('1abcdefghijklmnopqrstuvwxyz', repeat('A',5000))); - -insert into t1 select 1, b from t2; -commit; - -connect (a,localhost,root,,); -connect (b,localhost,root,,); - -connection a; -begin; -update t1 set b=repeat('B',100); - -connection b; -select a,left(b,40) from t1 natural join t2; - -connection a; -rollback; - -connection b; -select a,left(b,40) from t1 natural join t2; - -connection default; -disconnect a; -disconnect b; - -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -drop table t1,t2; - -# The following should fail even in non-strict mode. -SET SESSION innodb_strict_mode = off; ---error ER_TOO_BIG_ROWSIZE -CREATE TABLE t1( - c TEXT NOT NULL, d TEXT NOT NULL, - PRIMARY KEY (c(767),d(767))) -ENGINE=InnoDB ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=1 CHARSET=ASCII; ---error ER_TOO_BIG_ROWSIZE -CREATE TABLE t1( - c TEXT NOT NULL, d TEXT NOT NULL, - PRIMARY KEY (c(767),d(767))) -ENGINE=InnoDB ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=2 CHARSET=ASCII; -CREATE TABLE t1( - c TEXT NOT NULL, d TEXT NOT NULL, - PRIMARY KEY (c(767),d(767))) -ENGINE=InnoDB ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=4 CHARSET=ASCII; -drop table t1; ---error ER_TOO_BIG_ROWSIZE -CREATE TABLE t1(c TEXT, PRIMARY KEY (c(440))) -ENGINE=InnoDB ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=1 CHARSET=ASCII; -CREATE TABLE t1(c TEXT, PRIMARY KEY (c(438))) -ENGINE=InnoDB ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=1 CHARSET=ASCII; -INSERT INTO t1 VALUES(REPEAT('A',512)),(REPEAT('B',512)); -DROP TABLE t1; - -# -# Test blob column inheritance (mantis issue#36) -# - -create table t1( c1 int not null, c2 blob, c3 blob, c4 blob, - primary key(c1, c2(22), c3(22))) - engine = innodb row_format = dynamic; -begin; -insert into t1 values(1, repeat('A', 20000), repeat('B', 20000), - repeat('C', 20000)); - -update t1 set c3 = repeat('D', 20000) where c1 = 1; -commit; - -# one blob column which is unchanged in update and part of PK -# one blob column which is changed and part of of PK -# one blob column which is not part of PK and is unchanged -select count(*) from t1 where c2 = repeat('A', 20000); -select count(*) from t1 where c3 = repeat('D', 20000); -select count(*) from t1 where c4 = repeat('C', 20000); - -update t1 set c3 = repeat('E', 20000) where c1 = 1; -drop table t1; - -# -# -# Test innodb_file_format -# -set global innodb_file_format=`0`; -select @@innodb_file_format; -set global innodb_file_format=`1`; -select @@innodb_file_format; --- error ER_WRONG_ARGUMENTS -set global innodb_file_format=`2`; --- error ER_WRONG_ARGUMENTS -set global innodb_file_format=`-1`; -set global innodb_file_format=`Antelope`; -set global innodb_file_format=`Barracuda`; --- error ER_WRONG_ARGUMENTS -set global innodb_file_format=`Cheetah`; --- error ER_WRONG_ARGUMENTS -set global innodb_file_format=`abc`; --- error ER_WRONG_ARGUMENTS -set global innodb_file_format=`1a`; --- error ER_WRONG_ARGUMENTS -set global innodb_file_format=``; - -#test strict mode. -# this does not work anymore, has been removed from mysqltest -# -- enable_errors -set global innodb_file_per_table = on; -set global innodb_file_format = `1`; - -set innodb_strict_mode = off; -create table t1 (id int primary key) engine = innodb key_block_size = 0; -drop table t1; - -#set strict_mode -set innodb_strict_mode = on; - -#Test different values of KEY_BLOCK_SIZE - ---error ER_CANT_CREATE_TABLE -create table t1 (id int primary key) engine = innodb key_block_size = 0; -show errors; - ---error ER_CANT_CREATE_TABLE -create table t2 (id int primary key) engine = innodb key_block_size = 9; -show errors; - - -create table t3 (id int primary key) engine = innodb key_block_size = 1; -create table t4 (id int primary key) engine = innodb key_block_size = 2; -create table t5 (id int primary key) engine = innodb key_block_size = 4; -create table t6 (id int primary key) engine = innodb key_block_size = 8; -create table t7 (id int primary key) engine = innodb key_block_size = 16; - -#check various ROW_FORMAT values. -create table t8 (id int primary key) engine = innodb row_format = compressed; -create table t9 (id int primary key) engine = innodb row_format = dynamic; -create table t10(id int primary key) engine = innodb row_format = compact; -create table t11(id int primary key) engine = innodb row_format = redundant; - -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -drop table t3, t4, t5, t6, t7, t8, t9, t10, t11; - -#test different values of ROW_FORMAT with KEY_BLOCK_SIZE -create table t1 (id int primary key) engine = innodb -key_block_size = 8 row_format = compressed; - ---error ER_CANT_CREATE_TABLE -create table t2 (id int primary key) engine = innodb -key_block_size = 8 row_format = redundant; -show errors; - ---error ER_CANT_CREATE_TABLE -create table t3 (id int primary key) engine = innodb -key_block_size = 8 row_format = compact; -show errors; - ---error ER_CANT_CREATE_TABLE -create table t4 (id int primary key) engine = innodb -key_block_size = 8 row_format = dynamic; -show errors; - ---error ER_CANT_CREATE_TABLE -create table t5 (id int primary key) engine = innodb -key_block_size = 8 row_format = default; -show errors; - -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -drop table t1; - -#test multiple errors ---error ER_CANT_CREATE_TABLE -create table t1 (id int primary key) engine = innodb -key_block_size = 9 row_format = redundant; -show errors; - ---error ER_CANT_CREATE_TABLE -create table t2 (id int primary key) engine = innodb -key_block_size = 9 row_format = compact; -show errors; - ---error ER_CANT_CREATE_TABLE -create table t2 (id int primary key) engine = innodb -key_block_size = 9 row_format = dynamic; -show errors; - -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; - -#test valid values with innodb_file_per_table unset -set global innodb_file_per_table = off; - ---error ER_CANT_CREATE_TABLE -create table t1 (id int primary key) engine = innodb key_block_size = 1; -show errors; ---error ER_CANT_CREATE_TABLE -create table t2 (id int primary key) engine = innodb key_block_size = 2; -show errors; ---error ER_CANT_CREATE_TABLE -create table t3 (id int primary key) engine = innodb key_block_size = 4; -show errors; ---error ER_CANT_CREATE_TABLE -create table t4 (id int primary key) engine = innodb key_block_size = 8; -show errors; ---error ER_CANT_CREATE_TABLE -create table t5 (id int primary key) engine = innodb key_block_size = 16; -show errors; ---error ER_CANT_CREATE_TABLE -create table t6 (id int primary key) engine = innodb row_format = compressed; -show errors; ---error ER_CANT_CREATE_TABLE -create table t7 (id int primary key) engine = innodb row_format = dynamic; -show errors; -create table t8 (id int primary key) engine = innodb row_format = compact; -create table t9 (id int primary key) engine = innodb row_format = redundant; - -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -drop table t8, t9; - -#test valid values with innodb_file_format unset -set global innodb_file_per_table = on; -set global innodb_file_format = `0`; - ---error ER_CANT_CREATE_TABLE -create table t1 (id int primary key) engine = innodb key_block_size = 1; -show errors; ---error ER_CANT_CREATE_TABLE -create table t2 (id int primary key) engine = innodb key_block_size = 2; -show errors; ---error ER_CANT_CREATE_TABLE -create table t3 (id int primary key) engine = innodb key_block_size = 4; -show errors; ---error ER_CANT_CREATE_TABLE -create table t4 (id int primary key) engine = innodb key_block_size = 8; -show errors; ---error ER_CANT_CREATE_TABLE -create table t5 (id int primary key) engine = innodb key_block_size = 16; -show errors; ---error ER_CANT_CREATE_TABLE -create table t6 (id int primary key) engine = innodb row_format = compressed; -show errors; ---error ER_CANT_CREATE_TABLE -create table t7 (id int primary key) engine = innodb row_format = dynamic; -show errors; -create table t8 (id int primary key) engine = innodb row_format = compact; -create table t9 (id int primary key) engine = innodb row_format = redundant; - -SELECT table_schema, table_name, row_format -FROM information_schema.tables WHERE engine='innodb'; -drop table t8, t9; - -eval set global innodb_file_per_table=$per_table; -eval set global innodb_file_format=$format; -# -# Testing of tablespace tagging -# --- disable_info -set global innodb_file_per_table=on; -set global innodb_file_format=`Barracuda`; -set global innodb_file_format_check=`Antelope`; -create table normal_table ( - c1 int -) engine = innodb; -select @@innodb_file_format_check; -create table zip_table ( - c1 int -) engine = innodb key_block_size = 8; -select @@innodb_file_format_check; -set global innodb_file_format_check=`Antelope`; -select @@innodb_file_format_check; --- disable_result_log -show table status; --- enable_result_log -select @@innodb_file_format_check; -drop table normal_table, zip_table; --- disable_result_log - -# -# restore environment to the state it was before this test execution -# - --- disable_query_log -eval set global innodb_file_format=$format; -eval set global innodb_file_per_table=$per_table; -eval set global innodb_file_format_check=$innodb_file_format_check_orig; diff --git a/storage/innodb_plugin/mysql-test/innodb.result b/storage/innodb_plugin/mysql-test/innodb.result deleted file mode 100644 index bdae7633fd1..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb.result +++ /dev/null @@ -1,3310 +0,0 @@ -drop table if exists t1,t2,t3,t4; -drop database if exists mysqltest; -create table t1 (id int unsigned not null auto_increment, code tinyint unsigned not null, name char(20) not null, primary key (id), key (code), unique (name)) engine=innodb; -insert into t1 (code, name) values (1, 'Tim'), (1, 'Monty'), (2, 'David'), (2, 'Erik'), (3, 'Sasha'), (3, 'Jeremy'), (4, 'Matt'); -select id, code, name from t1 order by id; -id code name -1 1 Tim -2 1 Monty -3 2 David -4 2 Erik -5 3 Sasha -6 3 Jeremy -7 4 Matt -update ignore t1 set id = 8, name = 'Sinisa' where id < 3; -select id, code, name from t1 order by id; -id code name -2 1 Monty -3 2 David -4 2 Erik -5 3 Sasha -6 3 Jeremy -7 4 Matt -8 1 Sinisa -update ignore t1 set id = id + 10, name = 'Ralph' where id < 4; -select id, code, name from t1 order by id; -id code name -3 2 David -4 2 Erik -5 3 Sasha -6 3 Jeremy -7 4 Matt -8 1 Sinisa -12 1 Ralph -drop table t1; -CREATE TABLE t1 ( -id int(11) NOT NULL auto_increment, -parent_id int(11) DEFAULT '0' NOT NULL, -level tinyint(4) DEFAULT '0' NOT NULL, -PRIMARY KEY (id), -KEY parent_id (parent_id), -KEY level (level) -) engine=innodb; -INSERT INTO t1 VALUES (1,0,0),(3,1,1),(4,1,1),(8,2,2),(9,2,2),(17,3,2),(22,4,2),(24,4,2),(28,5,2),(29,5,2),(30,5,2),(31,6,2),(32,6,2),(33,6,2),(203,7,2),(202,7,2),(20,3,2),(157,0,0),(193,5,2),(40,7,2),(2,1,1),(15,2,2),(6,1,1),(34,6,2),(35,6,2),(16,3,2),(7,1,1),(36,7,2),(18,3,2),(26,5,2),(27,5,2),(183,4,2),(38,7,2),(25,5,2),(37,7,2),(21,4,2),(19,3,2),(5,1,1),(179,5,2); -update t1 set parent_id=parent_id+100; -select * from t1 where parent_id=102; -id parent_id level -8 102 2 -9 102 2 -15 102 2 -update t1 set id=id+1000; -update t1 set id=1024 where id=1009; -Got one of the listed errors -select * from t1; -id parent_id level -1001 100 0 -1002 101 1 -1003 101 1 -1004 101 1 -1005 101 1 -1006 101 1 -1007 101 1 -1008 102 2 -1009 102 2 -1015 102 2 -1016 103 2 -1017 103 2 -1018 103 2 -1019 103 2 -1020 103 2 -1021 104 2 -1022 104 2 -1024 104 2 -1025 105 2 -1026 105 2 -1027 105 2 -1028 105 2 -1029 105 2 -1030 105 2 -1031 106 2 -1032 106 2 -1033 106 2 -1034 106 2 -1035 106 2 -1036 107 2 -1037 107 2 -1038 107 2 -1040 107 2 -1157 100 0 -1179 105 2 -1183 104 2 -1193 105 2 -1202 107 2 -1203 107 2 -update ignore t1 set id=id+1; -select * from t1; -id parent_id level -1001 100 0 -1002 101 1 -1003 101 1 -1004 101 1 -1005 101 1 -1006 101 1 -1007 101 1 -1008 102 2 -1010 102 2 -1015 102 2 -1016 103 2 -1017 103 2 -1018 103 2 -1019 103 2 -1020 103 2 -1021 104 2 -1023 104 2 -1024 104 2 -1025 105 2 -1026 105 2 -1027 105 2 -1028 105 2 -1029 105 2 -1030 105 2 -1031 106 2 -1032 106 2 -1033 106 2 -1034 106 2 -1035 106 2 -1036 107 2 -1037 107 2 -1039 107 2 -1041 107 2 -1158 100 0 -1180 105 2 -1184 104 2 -1194 105 2 -1202 107 2 -1204 107 2 -update ignore t1 set id=1023 where id=1010; -select * from t1 where parent_id=102; -id parent_id level -1008 102 2 -1010 102 2 -1015 102 2 -explain select level from t1 where level=1; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref level level 1 const # Using index -explain select level,id from t1 where level=1; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref level level 1 const # Using index -explain select level,id,parent_id from t1 where level=1; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref level level 1 const # -select level,id from t1 where level=1; -level id -1 1002 -1 1003 -1 1004 -1 1005 -1 1006 -1 1007 -select level,id,parent_id from t1 where level=1; -level id parent_id -1 1002 101 -1 1003 101 -1 1004 101 -1 1005 101 -1 1006 101 -1 1007 101 -optimize table t1; -Table Op Msg_type Msg_text -test.t1 optimize note Table does not support optimize, doing recreate + analyze instead -test.t1 optimize status OK -show keys from t1; -Table Non_unique Key_name Seq_in_index Column_name Collation Cardinality Sub_part Packed Null Index_type Comment -t1 0 PRIMARY 1 id A # NULL NULL BTREE -t1 1 parent_id 1 parent_id A # NULL NULL BTREE -t1 1 level 1 level A # NULL NULL BTREE -drop table t1; -CREATE TABLE t1 ( -gesuchnr int(11) DEFAULT '0' NOT NULL, -benutzer_id int(11) DEFAULT '0' NOT NULL, -PRIMARY KEY (gesuchnr,benutzer_id) -) engine=innodb; -replace into t1 (gesuchnr,benutzer_id) values (2,1); -replace into t1 (gesuchnr,benutzer_id) values (1,1); -replace into t1 (gesuchnr,benutzer_id) values (1,1); -select * from t1; -gesuchnr benutzer_id -1 1 -2 1 -drop table t1; -create table t1 (a int) engine=innodb; -insert into t1 values (1), (2); -optimize table t1; -Table Op Msg_type Msg_text -test.t1 optimize note Table does not support optimize, doing recreate + analyze instead -test.t1 optimize status OK -delete from t1 where a = 1; -select * from t1; -a -2 -check table t1; -Table Op Msg_type Msg_text -test.t1 check status OK -drop table t1; -create table t1 (a int,b varchar(20)) engine=innodb; -insert into t1 values (1,""), (2,"testing"); -delete from t1 where a = 1; -select * from t1; -a b -2 testing -create index skr on t1 (a); -insert into t1 values (3,""), (4,"testing"); -analyze table t1; -Table Op Msg_type Msg_text -test.t1 analyze status OK -show keys from t1; -Table Non_unique Key_name Seq_in_index Column_name Collation Cardinality Sub_part Packed Null Index_type Comment -t1 1 skr 1 a A # NULL NULL YES BTREE -drop table t1; -create table t1 (a int,b varchar(20),key(a)) engine=innodb; -insert into t1 values (1,""), (2,"testing"); -select * from t1 where a = 1; -a b -1 -drop table t1; -create table t1 (n int not null primary key) engine=innodb; -set autocommit=0; -insert into t1 values (4); -rollback; -select n, "after rollback" from t1; -n after rollback -insert into t1 values (4); -commit; -select n, "after commit" from t1; -n after commit -4 after commit -commit; -insert into t1 values (5); -insert into t1 values (4); -ERROR 23000: Duplicate entry '4' for key 'PRIMARY' -commit; -select n, "after commit" from t1; -n after commit -4 after commit -5 after commit -set autocommit=1; -insert into t1 values (6); -insert into t1 values (4); -ERROR 23000: Duplicate entry '4' for key 'PRIMARY' -select n from t1; -n -4 -5 -6 -set autocommit=0; -begin; -savepoint `my_savepoint`; -insert into t1 values (7); -savepoint `savept2`; -insert into t1 values (3); -select n from t1; -n -3 -4 -5 -6 -7 -savepoint savept3; -rollback to savepoint savept2; -rollback to savepoint savept3; -ERROR 42000: SAVEPOINT savept3 does not exist -rollback to savepoint savept2; -release savepoint `my_savepoint`; -select n from t1; -n -4 -5 -6 -7 -rollback to savepoint `my_savepoint`; -ERROR 42000: SAVEPOINT my_savepoint does not exist -rollback to savepoint savept2; -ERROR 42000: SAVEPOINT savept2 does not exist -insert into t1 values (8); -savepoint sv; -commit; -savepoint sv; -set autocommit=1; -rollback; -drop table t1; -create table t1 (n int not null primary key) engine=innodb; -start transaction; -insert into t1 values (4); -flush tables with read lock; -commit; -unlock tables; -commit; -select * from t1; -n -4 -drop table t1; -create table t1 ( id int NOT NULL PRIMARY KEY, nom varchar(64)) engine=innodb; -begin; -insert into t1 values(1,'hamdouni'); -select id as afterbegin_id,nom as afterbegin_nom from t1; -afterbegin_id afterbegin_nom -1 hamdouni -rollback; -select id as afterrollback_id,nom as afterrollback_nom from t1; -afterrollback_id afterrollback_nom -set autocommit=0; -insert into t1 values(2,'mysql'); -select id as afterautocommit0_id,nom as afterautocommit0_nom from t1; -afterautocommit0_id afterautocommit0_nom -2 mysql -rollback; -select id as afterrollback_id,nom as afterrollback_nom from t1; -afterrollback_id afterrollback_nom -set autocommit=1; -drop table t1; -CREATE TABLE t1 (id char(8) not null primary key, val int not null) engine=innodb; -insert into t1 values ('pippo', 12); -insert into t1 values ('pippo', 12); -ERROR 23000: Duplicate entry 'pippo' for key 'PRIMARY' -delete from t1; -delete from t1 where id = 'pippo'; -select * from t1; -id val -insert into t1 values ('pippo', 12); -set autocommit=0; -delete from t1; -rollback; -select * from t1; -id val -pippo 12 -delete from t1; -commit; -select * from t1; -id val -drop table t1; -create table t1 (a integer) engine=innodb; -start transaction; -rename table t1 to t2; -create table t1 (b integer) engine=innodb; -insert into t1 values (1); -rollback; -drop table t1; -rename table t2 to t1; -drop table t1; -set autocommit=1; -CREATE TABLE t1 (ID INTEGER NOT NULL PRIMARY KEY, NAME VARCHAR(64)) ENGINE=innodb; -INSERT INTO t1 VALUES (1, 'Jochen'); -select * from t1; -ID NAME -1 Jochen -drop table t1; -CREATE TABLE t1 ( _userid VARCHAR(60) NOT NULL PRIMARY KEY) ENGINE=innodb; -set autocommit=0; -INSERT INTO t1 SET _userid='marc@anyware.co.uk'; -COMMIT; -SELECT * FROM t1; -_userid -marc@anyware.co.uk -SELECT _userid FROM t1 WHERE _userid='marc@anyware.co.uk'; -_userid -marc@anyware.co.uk -drop table t1; -set autocommit=1; -CREATE TABLE t1 ( -user_id int(10) DEFAULT '0' NOT NULL, -name varchar(100), -phone varchar(100), -ref_email varchar(100) DEFAULT '' NOT NULL, -detail varchar(200), -PRIMARY KEY (user_id,ref_email) -)engine=innodb; -INSERT INTO t1 VALUES (10292,'sanjeev','29153373','sansh777@hotmail.com','xxx'),(10292,'shirish','2333604','shirish@yahoo.com','ddsds'),(10292,'sonali','323232','sonali@bolly.com','filmstar'); -select * from t1 where user_id=10292; -user_id name phone ref_email detail -10292 sanjeev 29153373 sansh777@hotmail.com xxx -10292 shirish 2333604 shirish@yahoo.com ddsds -10292 sonali 323232 sonali@bolly.com filmstar -INSERT INTO t1 VALUES (10291,'sanjeev','29153373','sansh777@hotmail.com','xxx'),(10293,'shirish','2333604','shirish@yahoo.com','ddsds'); -select * from t1 where user_id=10292; -user_id name phone ref_email detail -10292 sanjeev 29153373 sansh777@hotmail.com xxx -10292 shirish 2333604 shirish@yahoo.com ddsds -10292 sonali 323232 sonali@bolly.com filmstar -select * from t1 where user_id>=10292; -user_id name phone ref_email detail -10292 sanjeev 29153373 sansh777@hotmail.com xxx -10292 shirish 2333604 shirish@yahoo.com ddsds -10292 sonali 323232 sonali@bolly.com filmstar -10293 shirish 2333604 shirish@yahoo.com ddsds -select * from t1 where user_id>10292; -user_id name phone ref_email detail -10293 shirish 2333604 shirish@yahoo.com ddsds -select * from t1 where user_id<10292; -user_id name phone ref_email detail -10291 sanjeev 29153373 sansh777@hotmail.com xxx -drop table t1; -CREATE TABLE t1 (a int not null, b int not null,c int not null, -key(a),primary key(a,b), unique(c),key(a),unique(b)); -show index from t1; -Table Non_unique Key_name Seq_in_index Column_name Collation Cardinality Sub_part Packed Null Index_type Comment -t1 0 PRIMARY 1 a A # NULL NULL BTREE -t1 0 PRIMARY 2 b A # NULL NULL BTREE -t1 0 c 1 c A # NULL NULL BTREE -t1 0 b 1 b A # NULL NULL BTREE -t1 1 a 1 a A # NULL NULL BTREE -t1 1 a_2 1 a A # NULL NULL BTREE -drop table t1; -create table t1 (col1 int not null, col2 char(4) not null, primary key(col1)); -alter table t1 engine=innodb; -insert into t1 values ('1','1'),('5','2'),('2','3'),('3','4'),('4','4'); -select * from t1; -col1 col2 -1 1 -2 3 -3 4 -4 4 -5 2 -update t1 set col2='7' where col1='4'; -select * from t1; -col1 col2 -1 1 -2 3 -3 4 -4 7 -5 2 -alter table t1 add co3 int not null; -select * from t1; -col1 col2 co3 -1 1 0 -2 3 0 -3 4 0 -4 7 0 -5 2 0 -update t1 set col2='9' where col1='2'; -select * from t1; -col1 col2 co3 -1 1 0 -2 9 0 -3 4 0 -4 7 0 -5 2 0 -drop table t1; -create table t1 (a int not null , b int, primary key (a)) engine = innodb; -create table t2 (a int not null , b int, primary key (a)) engine = myisam; -insert into t1 VALUES (1,3) , (2,3), (3,3); -select * from t1; -a b -1 3 -2 3 -3 3 -insert into t2 select * from t1; -select * from t2; -a b -1 3 -2 3 -3 3 -delete from t1 where b = 3; -select * from t1; -a b -insert into t1 select * from t2; -select * from t1; -a b -1 3 -2 3 -3 3 -select * from t2; -a b -1 3 -2 3 -3 3 -drop table t1,t2; -CREATE TABLE t1 ( -user_name varchar(12), -password text, -subscribed char(1), -user_id int(11) DEFAULT '0' NOT NULL, -quota bigint(20), -weight double, -access_date date, -access_time time, -approved datetime, -dummy_primary_key int(11) NOT NULL auto_increment, -PRIMARY KEY (dummy_primary_key) -) ENGINE=innodb; -INSERT INTO t1 VALUES ('user_0','somepassword','N',0,0,0,'2000-09-07','23:06:59','2000-09-07 23:06:59',1); -INSERT INTO t1 VALUES ('user_1','somepassword','Y',1,1,1,'2000-09-07','23:06:59','2000-09-07 23:06:59',2); -INSERT INTO t1 VALUES ('user_2','somepassword','N',2,2,1.4142135623731,'2000-09-07','23:06:59','2000-09-07 23:06:59',3); -INSERT INTO t1 VALUES ('user_3','somepassword','Y',3,3,1.7320508075689,'2000-09-07','23:06:59','2000-09-07 23:06:59',4); -INSERT INTO t1 VALUES ('user_4','somepassword','N',4,4,2,'2000-09-07','23:06:59','2000-09-07 23:06:59',5); -select user_name, password , subscribed, user_id, quota, weight, access_date, access_time, approved, dummy_primary_key from t1 order by user_name; -user_name password subscribed user_id quota weight access_date access_time approved dummy_primary_key -user_0 somepassword N 0 0 0 2000-09-07 23:06:59 2000-09-07 23:06:59 1 -user_1 somepassword Y 1 1 1 2000-09-07 23:06:59 2000-09-07 23:06:59 2 -user_2 somepassword N 2 2 1.4142135623731 2000-09-07 23:06:59 2000-09-07 23:06:59 3 -user_3 somepassword Y 3 3 1.7320508075689 2000-09-07 23:06:59 2000-09-07 23:06:59 4 -user_4 somepassword N 4 4 2 2000-09-07 23:06:59 2000-09-07 23:06:59 5 -drop table t1; -CREATE TABLE t1 ( -id int(11) NOT NULL auto_increment, -parent_id int(11) DEFAULT '0' NOT NULL, -level tinyint(4) DEFAULT '0' NOT NULL, -KEY (id), -KEY parent_id (parent_id), -KEY level (level) -) engine=innodb; -INSERT INTO t1 VALUES (1,0,0),(3,1,1),(4,1,1),(8,2,2),(9,2,2),(17,3,2),(22,4,2),(24,4,2),(28,5,2),(29,5,2),(30,5,2),(31,6,2),(32,6,2),(33,6,2),(203,7,2),(202,7,2),(20,3,2),(157,0,0),(193,5,2),(40,7,2),(2,1,1),(15,2,2),(6,1,1),(34,6,2),(35,6,2),(16,3,2),(7,1,1),(36,7,2),(18,3,2),(26,5,2),(27,5,2),(183,4,2),(38,7,2),(25,5,2),(37,7,2),(21,4,2),(19,3,2),(5,1,1); -INSERT INTO t1 values (179,5,2); -update t1 set parent_id=parent_id+100; -select * from t1 where parent_id=102; -id parent_id level -8 102 2 -9 102 2 -15 102 2 -update t1 set id=id+1000; -update t1 set id=1024 where id=1009; -select * from t1; -id parent_id level -1001 100 0 -1003 101 1 -1004 101 1 -1008 102 2 -1024 102 2 -1017 103 2 -1022 104 2 -1024 104 2 -1028 105 2 -1029 105 2 -1030 105 2 -1031 106 2 -1032 106 2 -1033 106 2 -1203 107 2 -1202 107 2 -1020 103 2 -1157 100 0 -1193 105 2 -1040 107 2 -1002 101 1 -1015 102 2 -1006 101 1 -1034 106 2 -1035 106 2 -1016 103 2 -1007 101 1 -1036 107 2 -1018 103 2 -1026 105 2 -1027 105 2 -1183 104 2 -1038 107 2 -1025 105 2 -1037 107 2 -1021 104 2 -1019 103 2 -1005 101 1 -1179 105 2 -update ignore t1 set id=id+1; -select * from t1; -id parent_id level -1002 100 0 -1004 101 1 -1005 101 1 -1009 102 2 -1025 102 2 -1018 103 2 -1023 104 2 -1025 104 2 -1029 105 2 -1030 105 2 -1031 105 2 -1032 106 2 -1033 106 2 -1034 106 2 -1204 107 2 -1203 107 2 -1021 103 2 -1158 100 0 -1194 105 2 -1041 107 2 -1003 101 1 -1016 102 2 -1007 101 1 -1035 106 2 -1036 106 2 -1017 103 2 -1008 101 1 -1037 107 2 -1019 103 2 -1027 105 2 -1028 105 2 -1184 104 2 -1039 107 2 -1026 105 2 -1038 107 2 -1022 104 2 -1020 103 2 -1006 101 1 -1180 105 2 -update ignore t1 set id=1023 where id=1010; -select * from t1 where parent_id=102; -id parent_id level -1009 102 2 -1025 102 2 -1016 102 2 -explain select level from t1 where level=1; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref level level 1 const # Using index -select level,id from t1 where level=1; -level id -1 1004 -1 1005 -1 1003 -1 1007 -1 1008 -1 1006 -select level,id,parent_id from t1 where level=1; -level id parent_id -1 1004 101 -1 1005 101 -1 1003 101 -1 1007 101 -1 1008 101 -1 1006 101 -select level,id from t1 where level=1 order by id; -level id -1 1003 -1 1004 -1 1005 -1 1006 -1 1007 -1 1008 -delete from t1 where level=1; -select * from t1; -id parent_id level -1002 100 0 -1009 102 2 -1025 102 2 -1018 103 2 -1023 104 2 -1025 104 2 -1029 105 2 -1030 105 2 -1031 105 2 -1032 106 2 -1033 106 2 -1034 106 2 -1204 107 2 -1203 107 2 -1021 103 2 -1158 100 0 -1194 105 2 -1041 107 2 -1016 102 2 -1035 106 2 -1036 106 2 -1017 103 2 -1037 107 2 -1019 103 2 -1027 105 2 -1028 105 2 -1184 104 2 -1039 107 2 -1026 105 2 -1038 107 2 -1022 104 2 -1020 103 2 -1180 105 2 -drop table t1; -CREATE TABLE t1 ( -sca_code char(6) NOT NULL, -cat_code char(6) NOT NULL, -sca_desc varchar(50), -lan_code char(2) NOT NULL, -sca_pic varchar(100), -sca_sdesc varchar(50), -sca_sch_desc varchar(16), -PRIMARY KEY (sca_code, cat_code, lan_code), -INDEX sca_pic (sca_pic) -) engine = innodb ; -INSERT INTO t1 ( sca_code, cat_code, sca_desc, lan_code, sca_pic, sca_sdesc, sca_sch_desc) VALUES ( 'PD', 'J', 'PENDANT', 'EN', NULL, NULL, 'PENDANT'),( 'RI', 'J', 'RING', 'EN', NULL, NULL, 'RING'),( 'QQ', 'N', 'RING', 'EN', 'not null', NULL, 'RING'); -select count(*) from t1 where sca_code = 'PD'; -count(*) -1 -select count(*) from t1 where sca_code <= 'PD'; -count(*) -1 -select count(*) from t1 where sca_pic is null; -count(*) -2 -alter table t1 drop index sca_pic, add index sca_pic (cat_code, sca_pic); -select count(*) from t1 where sca_code='PD' and sca_pic is null; -count(*) -1 -select count(*) from t1 where cat_code='E'; -count(*) -0 -alter table t1 drop index sca_pic, add index (sca_pic, cat_code); -select count(*) from t1 where sca_code='PD' and sca_pic is null; -count(*) -1 -select count(*) from t1 where sca_pic >= 'n'; -count(*) -1 -select sca_pic from t1 where sca_pic is null; -sca_pic -NULL -NULL -update t1 set sca_pic="test" where sca_pic is null; -delete from t1 where sca_code='pd'; -drop table t1; -set @a:=now(); -CREATE TABLE t1 (a int not null, b timestamp not null, primary key (a)) engine=innodb; -insert into t1 (a) values(1),(2),(3); -select t1.a from t1 natural join t1 as t2 where t1.b >= @a order by t1.a; -a -1 -2 -3 -select a from t1 natural join t1 as t2 where b >= @a order by a; -a -1 -2 -3 -update t1 set a=5 where a=1; -select a from t1; -a -2 -3 -5 -drop table t1; -create table t1 (a varchar(100) not null, primary key(a), b int not null) engine=innodb; -insert into t1 values("hello",1),("world",2); -select * from t1 order by b desc; -a b -world 2 -hello 1 -optimize table t1; -Table Op Msg_type Msg_text -test.t1 optimize note Table does not support optimize, doing recreate + analyze instead -test.t1 optimize status OK -show keys from t1; -Table Non_unique Key_name Seq_in_index Column_name Collation Cardinality Sub_part Packed Null Index_type Comment -t1 0 PRIMARY 1 a A # NULL NULL BTREE -drop table t1; -create table t1 (i int, j int ) ENGINE=innodb; -insert into t1 values (1,2); -select * from t1 where i=1 and j=2; -i j -1 2 -create index ax1 on t1 (i,j); -select * from t1 where i=1 and j=2; -i j -1 2 -drop table t1; -CREATE TABLE t1 ( -a int3 unsigned NOT NULL, -b int1 unsigned NOT NULL, -UNIQUE (a, b) -) ENGINE = innodb; -INSERT INTO t1 VALUES (1, 1); -SELECT MIN(B),MAX(b) FROM t1 WHERE t1.a = 1; -MIN(B) MAX(b) -1 1 -drop table t1; -CREATE TABLE t1 (a int unsigned NOT NULL) engine=innodb; -INSERT INTO t1 VALUES (1); -SELECT * FROM t1; -a -1 -DROP TABLE t1; -create table t1 (a int primary key,b int, c int, d int, e int, f int, g int, h int, i int, j int, k int, l int, m int, n int, o int, p int, q int, r int, s int, t int, u int, v int, w int, x int, y int, z int, a1 int, a2 int, a3 int, a4 int, a5 int, a6 int, a7 int, a8 int, a9 int, b1 int, b2 int, b3 int, b4 int, b5 int, b6 int) engine = innodb; -insert into t1 values (1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1); -explain select * from t1 where a > 0 and a < 50; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 range PRIMARY PRIMARY 4 NULL # Using where -drop table t1; -create table t1 (id int NOT NULL,id2 int NOT NULL,id3 int NOT NULL,dummy1 char(30),primary key (id,id2),index index_id3 (id3)) engine=innodb; -insert into t1 values (0,0,0,'ABCDEFGHIJ'),(2,2,2,'BCDEFGHIJK'),(1,1,1,'CDEFGHIJKL'); -LOCK TABLES t1 WRITE; -insert into t1 values (99,1,2,'D'),(1,1,2,'D'); -ERROR 23000: Duplicate entry '1-1' for key 'PRIMARY' -select id from t1; -id -0 -1 -2 -select id from t1; -id -0 -1 -2 -UNLOCK TABLES; -DROP TABLE t1; -create table t1 (id int NOT NULL,id2 int NOT NULL,id3 int NOT NULL,dummy1 char(30),primary key (id,id2),index index_id3 (id3)) engine=innodb; -insert into t1 values (0,0,0,'ABCDEFGHIJ'),(2,2,2,'BCDEFGHIJK'),(1,1,1,'CDEFGHIJKL'); -LOCK TABLES t1 WRITE; -begin; -insert into t1 values (99,1,2,'D'),(1,1,2,'D'); -ERROR 23000: Duplicate entry '1-1' for key 'PRIMARY' -select id from t1; -id -0 -1 -2 -insert ignore into t1 values (100,1,2,'D'),(1,1,99,'D'); -commit; -select id,id3 from t1; -id id3 -0 0 -1 1 -2 2 -100 2 -UNLOCK TABLES; -DROP TABLE t1; -create table t1 (a char(20), unique (a(5))) engine=innodb; -drop table t1; -create table t1 (a char(20), index (a(5))) engine=innodb; -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `a` char(20) DEFAULT NULL, - KEY `a` (`a`(5)) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t1; -create temporary table t1 (a int not null auto_increment, primary key(a)) engine=innodb; -insert into t1 values (NULL),(NULL),(NULL); -delete from t1 where a=3; -insert into t1 values (NULL); -select * from t1; -a -1 -2 -4 -alter table t1 add b int; -select * from t1; -a b -1 NULL -2 NULL -4 NULL -drop table t1; -create table t1 -( -id int auto_increment primary key, -name varchar(32) not null, -value text not null, -uid int not null, -unique key(name,uid) -) engine=innodb; -insert into t1 values (1,'one','one value',101), -(2,'two','two value',102),(3,'three','three value',103); -set insert_id=5; -replace into t1 (value,name,uid) values ('other value','two',102); -delete from t1 where uid=102; -set insert_id=5; -replace into t1 (value,name,uid) values ('other value','two',102); -set insert_id=6; -replace into t1 (value,name,uid) values ('other value','two',102); -select * from t1; -id name value uid -1 one one value 101 -3 three three value 103 -6 two other value 102 -drop table t1; -create database mysqltest; -create table mysqltest.t1 (a int not null) engine= innodb; -insert into mysqltest.t1 values(1); -create table mysqltest.t2 (a int not null) engine= myisam; -insert into mysqltest.t2 values(1); -create table mysqltest.t3 (a int not null) engine= heap; -insert into mysqltest.t3 values(1); -commit; -drop database mysqltest; -show tables from mysqltest; -ERROR 42000: Unknown database 'mysqltest' -set autocommit=0; -create table t1 (a int not null) engine= innodb; -insert into t1 values(1),(2); -truncate table t1; -commit; -truncate table t1; -truncate table t1; -select * from t1; -a -insert into t1 values(1),(2); -delete from t1; -select * from t1; -a -commit; -drop table t1; -set autocommit=1; -create table t1 (a int not null) engine= innodb; -insert into t1 values(1),(2); -truncate table t1; -insert into t1 values(1),(2); -select * from t1; -a -1 -2 -truncate table t1; -insert into t1 values(1),(2); -delete from t1; -select * from t1; -a -drop table t1; -create table t1 (a int not null, b int not null, c int not null, primary key (a),key(b)) engine=innodb; -insert into t1 values (3,3,3),(1,1,1),(2,2,2),(4,4,4); -explain select * from t1 order by a; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL PRIMARY 4 NULL # -explain select * from t1 order by b; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ALL NULL NULL NULL NULL # Using filesort -explain select * from t1 order by c; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ALL NULL NULL NULL NULL # Using filesort -explain select a from t1 order by a; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL PRIMARY 4 NULL # Using index -explain select b from t1 order by b; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL b 4 NULL # Using index -explain select a,b from t1 order by b; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL b 4 NULL # Using index -explain select a,b from t1; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index NULL b 4 NULL # Using index -explain select a,b,c from t1; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ALL NULL NULL NULL NULL # -drop table t1; -create table t1 (t int not null default 1, key (t)) engine=innodb; -desc t1; -Field Type Null Key Default Extra -t int(11) NO MUL 1 -drop table t1; -CREATE TABLE t1 ( -number bigint(20) NOT NULL default '0', -cname char(15) NOT NULL default '', -carrier_id smallint(6) NOT NULL default '0', -privacy tinyint(4) NOT NULL default '0', -last_mod_date timestamp NOT NULL, -last_mod_id smallint(6) NOT NULL default '0', -last_app_date timestamp NOT NULL, -last_app_id smallint(6) default '-1', -version smallint(6) NOT NULL default '0', -assigned_scps int(11) default '0', -status tinyint(4) default '0' -) ENGINE=InnoDB; -INSERT INTO t1 VALUES (4077711111,'SeanWheeler',90,2,20020111112846,500,00000000000000,-1,2,3,1); -INSERT INTO t1 VALUES (9197722223,'berry',90,3,20020111112809,500,20020102114532,501,4,10,0); -INSERT INTO t1 VALUES (650,'San Francisco',0,0,20011227111336,342,00000000000000,-1,1,24,1); -INSERT INTO t1 VALUES (302467,'Sue\'s Subshop',90,3,20020109113241,500,20020102115111,501,7,24,0); -INSERT INTO t1 VALUES (6014911113,'SudzCarwash',520,1,20020102115234,500,20020102115259,501,33,32768,0); -INSERT INTO t1 VALUES (333,'tubs',99,2,20020109113440,501,20020109113440,500,3,10,0); -CREATE TABLE t2 ( -number bigint(20) NOT NULL default '0', -cname char(15) NOT NULL default '', -carrier_id smallint(6) NOT NULL default '0', -privacy tinyint(4) NOT NULL default '0', -last_mod_date timestamp NOT NULL, -last_mod_id smallint(6) NOT NULL default '0', -last_app_date timestamp NOT NULL, -last_app_id smallint(6) default '-1', -version smallint(6) NOT NULL default '0', -assigned_scps int(11) default '0', -status tinyint(4) default '0' -) ENGINE=InnoDB; -INSERT INTO t2 VALUES (4077711111,'SeanWheeler',0,2,20020111112853,500,00000000000000,-1,2,3,1); -INSERT INTO t2 VALUES (9197722223,'berry',90,3,20020111112818,500,20020102114532,501,4,10,0); -INSERT INTO t2 VALUES (650,'San Francisco',90,0,20020109113158,342,00000000000000,-1,1,24,1); -INSERT INTO t2 VALUES (333,'tubs',99,2,20020109113453,501,20020109113453,500,3,10,0); -select * from t1; -number cname carrier_id privacy last_mod_date last_mod_id last_app_date last_app_id version assigned_scps status -4077711111 SeanWheeler 90 2 2002-01-11 11:28:46 500 0000-00-00 00:00:00 -1 2 3 1 -9197722223 berry 90 3 2002-01-11 11:28:09 500 2002-01-02 11:45:32 501 4 10 0 -650 San Francisco 0 0 2001-12-27 11:13:36 342 0000-00-00 00:00:00 -1 1 24 1 -302467 Sue's Subshop 90 3 2002-01-09 11:32:41 500 2002-01-02 11:51:11 501 7 24 0 -6014911113 SudzCarwash 520 1 2002-01-02 11:52:34 500 2002-01-02 11:52:59 501 33 32768 0 -333 tubs 99 2 2002-01-09 11:34:40 501 2002-01-09 11:34:40 500 3 10 0 -select * from t2; -number cname carrier_id privacy last_mod_date last_mod_id last_app_date last_app_id version assigned_scps status -4077711111 SeanWheeler 0 2 2002-01-11 11:28:53 500 0000-00-00 00:00:00 -1 2 3 1 -9197722223 berry 90 3 2002-01-11 11:28:18 500 2002-01-02 11:45:32 501 4 10 0 -650 San Francisco 90 0 2002-01-09 11:31:58 342 0000-00-00 00:00:00 -1 1 24 1 -333 tubs 99 2 2002-01-09 11:34:53 501 2002-01-09 11:34:53 500 3 10 0 -delete t1, t2 from t1 left join t2 on t1.number=t2.number where (t1.carrier_id=90 and t1.number=t2.number) or (t2.carrier_id=90 and t1.number=t2.number) or (t1.carrier_id=90 and t2.number is null); -select * from t1; -number cname carrier_id privacy last_mod_date last_mod_id last_app_date last_app_id version assigned_scps status -6014911113 SudzCarwash 520 1 2002-01-02 11:52:34 500 2002-01-02 11:52:59 501 33 32768 0 -333 tubs 99 2 2002-01-09 11:34:40 501 2002-01-09 11:34:40 500 3 10 0 -select * from t2; -number cname carrier_id privacy last_mod_date last_mod_id last_app_date last_app_id version assigned_scps status -333 tubs 99 2 2002-01-09 11:34:53 501 2002-01-09 11:34:53 500 3 10 0 -select * from t2; -number cname carrier_id privacy last_mod_date last_mod_id last_app_date last_app_id version assigned_scps status -333 tubs 99 2 2002-01-09 11:34:53 501 2002-01-09 11:34:53 500 3 10 0 -drop table t1,t2; -create table t1 (id int unsigned not null auto_increment, code tinyint unsigned not null, name char(20) not null, primary key (id), key (code), unique (name)) engine=innodb; -BEGIN; -SET SESSION TRANSACTION ISOLATION LEVEL SERIALIZABLE; -SELECT @@tx_isolation,@@global.tx_isolation; -@@tx_isolation @@global.tx_isolation -SERIALIZABLE REPEATABLE-READ -insert into t1 (code, name) values (1, 'Tim'), (1, 'Monty'), (2, 'David'); -select id, code, name from t1 order by id; -id code name -1 1 Tim -2 1 Monty -3 2 David -COMMIT; -BEGIN; -SET SESSION TRANSACTION ISOLATION LEVEL REPEATABLE READ; -insert into t1 (code, name) values (2, 'Erik'), (3, 'Sasha'); -select id, code, name from t1 order by id; -id code name -1 1 Tim -2 1 Monty -3 2 David -4 2 Erik -5 3 Sasha -COMMIT; -SET binlog_format='MIXED'; -BEGIN; -SET SESSION TRANSACTION ISOLATION LEVEL READ UNCOMMITTED; -insert into t1 (code, name) values (3, 'Jeremy'), (4, 'Matt'); -select id, code, name from t1 order by id; -id code name -1 1 Tim -2 1 Monty -3 2 David -4 2 Erik -5 3 Sasha -6 3 Jeremy -7 4 Matt -COMMIT; -DROP TABLE t1; -create table t1 (n int(10), d int(10)) engine=innodb; -create table t2 (n int(10), d int(10)) engine=innodb; -insert into t1 values(1,1),(1,2); -insert into t2 values(1,10),(2,20); -UPDATE t1,t2 SET t1.d=t2.d,t2.d=30 WHERE t1.n=t2.n; -select * from t1; -n d -1 10 -1 10 -select * from t2; -n d -1 30 -2 20 -drop table t1,t2; -drop table if exists t1, t2; -CREATE TABLE t1 (a int, PRIMARY KEY (a)); -CREATE TABLE t2 (a int, PRIMARY KEY (a)) ENGINE=InnoDB; -create trigger trg_del_t2 after delete on t2 for each row -insert into t1 values (1); -insert into t1 values (1); -insert into t2 values (1),(2); -delete t2 from t2; -ERROR 23000: Duplicate entry '1' for key 'PRIMARY' -select count(*) from t2 /* must be 2 as restored after rollback caused by the error */; -count(*) -2 -drop table t1, t2; -drop table if exists t1, t2; -CREATE TABLE t1 (a int, PRIMARY KEY (a)); -CREATE TABLE t2 (a int, PRIMARY KEY (a)) ENGINE=InnoDB; -create trigger trg_del_t2 after delete on t2 for each row -insert into t1 values (1); -insert into t1 values (1); -insert into t2 values (1),(2); -delete t2 from t2; -ERROR 23000: Duplicate entry '1' for key 'PRIMARY' -select count(*) from t2 /* must be 2 as restored after rollback caused by the error */; -count(*) -2 -drop table t1, t2; -create table t1 (a int, b int) engine=innodb; -insert into t1 values(20,null); -select t2.b, ifnull(t2.b,"this is null") from t1 as t2 left join t1 as t3 on -t2.b=t3.a; -b ifnull(t2.b,"this is null") -NULL this is null -select t2.b, ifnull(t2.b,"this is null") from t1 as t2 left join t1 as t3 on -t2.b=t3.a order by 1; -b ifnull(t2.b,"this is null") -NULL this is null -insert into t1 values(10,null); -select t2.b, ifnull(t2.b,"this is null") from t1 as t2 left join t1 as t3 on -t2.b=t3.a order by 1; -b ifnull(t2.b,"this is null") -NULL this is null -NULL this is null -drop table t1; -create table t1 (a varchar(10) not null) engine=myisam; -create table t2 (b varchar(10) not null unique) engine=innodb; -select t1.a from t1,t2 where t1.a=t2.b; -a -drop table t1,t2; -create table t1 (a int not null, b int, primary key (a)) engine = innodb; -create table t2 (a int not null, b int, primary key (a)) engine = innodb; -insert into t1 values (10, 20); -insert into t2 values (10, 20); -update t1, t2 set t1.b = 150, t2.b = t1.b where t2.a = t1.a and t1.a = 10; -drop table t1,t2; -CREATE TABLE t1 (id INT NOT NULL, PRIMARY KEY (id)) ENGINE=INNODB; -CREATE TABLE t2 (id INT PRIMARY KEY, t1_id INT, INDEX par_ind (t1_id), FOREIGN KEY (t1_id) REFERENCES t1(id) ON DELETE CASCADE ) ENGINE=INNODB; -insert into t1 set id=1; -insert into t2 set id=1, t1_id=1; -delete t1,t2 from t1,t2 where t1.id=t2.t1_id; -select * from t1; -id -select * from t2; -id t1_id -drop table t2,t1; -CREATE TABLE t1(id INT NOT NULL, PRIMARY KEY (id)) ENGINE=INNODB; -CREATE TABLE t2(id INT PRIMARY KEY, t1_id INT, INDEX par_ind (t1_id) ) ENGINE=INNODB; -INSERT INTO t1 VALUES(1); -INSERT INTO t2 VALUES(1, 1); -SELECT * from t1; -id -1 -UPDATE t1,t2 SET t1.id=t1.id+1, t2.t1_id=t1.id+1; -SELECT * from t1; -id -2 -UPDATE t1,t2 SET t1.id=t1.id+1 where t1.id!=t2.id; -SELECT * from t1; -id -3 -DROP TABLE t1,t2; -set autocommit=0; -CREATE TABLE t1 (id CHAR(15) NOT NULL, value CHAR(40) NOT NULL, PRIMARY KEY(id)) ENGINE=InnoDB; -CREATE TABLE t2 (id CHAR(15) NOT NULL, value CHAR(40) NOT NULL, PRIMARY KEY(id)) ENGINE=InnoDB; -CREATE TABLE t3 (id1 CHAR(15) NOT NULL, id2 CHAR(15) NOT NULL, PRIMARY KEY(id1, id2)) ENGINE=InnoDB; -INSERT INTO t3 VALUES("my-test-1", "my-test-2"); -COMMIT; -INSERT INTO t1 VALUES("this-key", "will disappear"); -INSERT INTO t2 VALUES("this-key", "will also disappear"); -DELETE FROM t3 WHERE id1="my-test-1"; -SELECT * FROM t1; -id value -this-key will disappear -SELECT * FROM t2; -id value -this-key will also disappear -SELECT * FROM t3; -id1 id2 -ROLLBACK; -SELECT * FROM t1; -id value -SELECT * FROM t2; -id value -SELECT * FROM t3; -id1 id2 -my-test-1 my-test-2 -SELECT * FROM t3 WHERE id1="my-test-1" LOCK IN SHARE MODE; -id1 id2 -my-test-1 my-test-2 -COMMIT; -set autocommit=1; -DROP TABLE t1,t2,t3; -CREATE TABLE t1 (a int not null primary key, b int not null, unique (b)) engine=innodb; -INSERT INTO t1 values (1,1),(2,2),(3,3),(4,4),(5,5),(6,6),(7,7),(8,8),(9,9); -UPDATE t1 set a=a+100 where b between 2 and 3 and a < 1000; -SELECT * from t1; -a b -1 1 -102 2 -103 3 -4 4 -5 5 -6 6 -7 7 -8 8 -9 9 -drop table t1; -CREATE TABLE t1 (a int not null primary key, b int not null, key (b)) engine=innodb; -CREATE TABLE t2 (a int not null primary key, b int not null, key (b)) engine=innodb; -INSERT INTO t1 values (1,1),(2,2),(3,3),(4,4),(5,5),(6,6),(7,7),(8,8),(9,9),(10,10),(11,11),(12,12); -INSERT INTO t2 values (1,1),(2,2),(3,3),(4,4),(5,5),(6,6),(7,7),(8,8),(9,9); -update t1,t2 set t1.a=t1.a+100; -select * from t1; -a b -101 1 -102 2 -103 3 -104 4 -105 5 -106 6 -107 7 -108 8 -109 9 -110 10 -111 11 -112 12 -update t1,t2 set t1.a=t1.a+100 where t1.a=101; -select * from t1; -a b -201 1 -102 2 -103 3 -104 4 -105 5 -106 6 -107 7 -108 8 -109 9 -110 10 -111 11 -112 12 -update t1,t2 set t1.b=t1.b+10 where t1.b=2; -select * from t1; -a b -201 1 -103 3 -104 4 -105 5 -106 6 -107 7 -108 8 -109 9 -110 10 -111 11 -102 12 -112 12 -update t1,t2 set t1.b=t1.b+2,t2.b=t1.b+10 where t1.b between 3 and 5 and t1.a=t2.a+100; -select * from t1; -a b -201 1 -103 5 -104 6 -106 6 -105 7 -107 7 -108 8 -109 9 -110 10 -111 11 -102 12 -112 12 -select * from t2; -a b -1 1 -2 2 -6 6 -7 7 -8 8 -9 9 -3 13 -4 14 -5 15 -drop table t1,t2; -CREATE TABLE t2 ( NEXT_T BIGINT NOT NULL PRIMARY KEY) ENGINE=MyISAM; -CREATE TABLE t1 ( B_ID INTEGER NOT NULL PRIMARY KEY) ENGINE=InnoDB; -SET AUTOCOMMIT=0; -INSERT INTO t1 ( B_ID ) VALUES ( 1 ); -INSERT INTO t2 ( NEXT_T ) VALUES ( 1 ); -ROLLBACK; -Warnings: -Warning 1196 Some non-transactional changed tables couldn't be rolled back -SELECT * FROM t1; -B_ID -drop table t1,t2; -create table t1 ( pk int primary key, parent int not null, child int not null, index (parent) ) engine = innodb; -insert into t1 values (1,0,4), (2,1,3), (3,2,1), (4,1,2); -select distinct parent,child from t1 order by parent; -parent child -0 4 -1 2 -1 3 -2 1 -drop table t1; -create table t1 (a int not null auto_increment primary key, b int, c int, key(c)) engine=innodb; -create table t2 (a int not null auto_increment primary key, b int); -insert into t1 (b) values (null),(null),(null),(null),(null),(null),(null); -insert into t2 (a) select b from t1; -insert into t1 (b) select b from t2; -insert into t2 (a) select b from t1; -insert into t1 (a) select b from t2; -insert into t2 (a) select b from t1; -insert into t1 (a) select b from t2; -insert into t2 (a) select b from t1; -insert into t1 (a) select b from t2; -insert into t2 (a) select b from t1; -insert into t1 (a) select b from t2; -select count(*) from t1; -count(*) -623 -explain select * from t1 where c between 1 and 2500; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 range c c 5 NULL # Using where -update t1 set c=a; -explain select * from t1 where c between 1 and 2500; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ALL c NULL NULL NULL # Using where -drop table t1,t2; -create table t1 (id int primary key auto_increment, fk int, index index_fk (fk)) engine=innodb; -insert into t1 (id) values (null),(null),(null),(null),(null); -update t1 set fk=69 where fk is null order by id limit 1; -SELECT * from t1; -id fk -2 NULL -3 NULL -4 NULL -5 NULL -1 69 -drop table t1; -create table t1 (a int not null, b int not null, key (a)); -insert into t1 values (1,1),(1,2),(1,3),(3,1),(3,2),(3,3),(3,1),(3,2),(3,3),(2,1),(2,2),(2,3); -SET @tmp=0; -update t1 set b=(@tmp:=@tmp+1) order by a; -update t1 set b=99 where a=1 order by b asc limit 1; -update t1 set b=100 where a=1 order by b desc limit 2; -update t1 set a=a+10+b where a=1 order by b; -select * from t1 order by a,b; -a b -2 4 -2 5 -2 6 -3 7 -3 8 -3 9 -3 10 -3 11 -3 12 -13 2 -111 100 -111 100 -drop table t1; -create table t1 ( c char(8) not null ) engine=innodb; -insert into t1 values ('0'),('1'),('2'),('3'),('4'),('5'),('6'),('7'),('8'),('9'); -insert into t1 values ('A'),('B'),('C'),('D'),('E'),('F'); -alter table t1 add b char(8) not null; -alter table t1 add a char(8) not null; -alter table t1 add primary key (a,b,c); -update t1 set a=c, b=c; -create table t2 (c char(8) not null, b char(8) not null, a char(8) not null, primary key(a,b,c)) engine=innodb; -insert into t2 select * from t1; -delete t1,t2 from t2,t1 where t1.a<'B' and t2.b=t1.b; -drop table t1,t2; -SET AUTOCOMMIT=1; -create table t1 (a integer auto_increment primary key) engine=innodb; -insert into t1 (a) values (NULL),(NULL); -truncate table t1; -insert into t1 (a) values (NULL),(NULL); -SELECT * from t1; -a -1 -2 -drop table t1; -CREATE TABLE t1 (`id 1` INT NOT NULL, PRIMARY KEY (`id 1`)) ENGINE=INNODB; -CREATE TABLE t2 (id INT PRIMARY KEY, t1_id INT, INDEX par_ind (t1_id), FOREIGN KEY (`t1_id`) REFERENCES `t1`(`id 1`) ON DELETE CASCADE ) ENGINE=INNODB; -drop table t2,t1; -create table `t1` (`id` int( 11 ) not null ,primary key ( `id` )) engine = innodb; -insert into `t1`values ( 1 ) ; -create table `t2` (`id` int( 11 ) not null default '0',unique key `id` ( `id` ) ,constraint `t1_id_fk` foreign key ( `id` ) references `t1` (`id` )) engine = innodb; -insert into `t2`values ( 1 ) ; -create table `t3` (`id` int( 11 ) not null default '0',key `id` ( `id` ) ,constraint `t2_id_fk` foreign key ( `id` ) references `t2` (`id` )) engine = innodb; -insert into `t3`values ( 1 ) ; -delete t3,t2,t1 from t1,t2,t3 where t1.id =1 and t2.id = t1.id and t3.id = t2.id; -ERROR 23000: Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `t1_id_fk` FOREIGN KEY (`id`) REFERENCES `t1` (`id`)) -update t1,t2,t3 set t3.id=5, t2.id=6, t1.id=7 where t1.id =1 and t2.id = t1.id and t3.id = t2.id; -ERROR 23000: Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `t1_id_fk` FOREIGN KEY (`id`) REFERENCES `t1` (`id`)) -update t3 set t3.id=7 where t1.id =1 and t2.id = t1.id and t3.id = t2.id; -ERROR 42S22: Unknown column 't1.id' in 'where clause' -drop table t3,t2,t1; -create table t1( -id int primary key, -pid int, -index(pid), -foreign key(pid) references t1(id) on delete cascade) engine=innodb; -insert into t1 values(0,0),(1,0),(2,1),(3,2),(4,3),(5,4),(6,5),(7,6), -(8,7),(9,8),(10,9),(11,10),(12,11),(13,12),(14,13),(15,14); -delete from t1 where id=0; -ERROR 23000: Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t1`, CONSTRAINT `t1_ibfk_1` FOREIGN KEY (`pid`) REFERENCES `t1` (`id`) ON DELETE CASCADE) -delete from t1 where id=15; -delete from t1 where id=0; -drop table t1; -CREATE TABLE t1 (col1 int(1))ENGINE=InnoDB; -CREATE TABLE t2 (col1 int(1),stamp TIMESTAMP,INDEX stamp_idx -(stamp))ENGINE=InnoDB; -insert into t1 values (1),(2),(3); -insert into t2 values (1, 20020204130000),(2, 20020204130000),(4,20020204310000 ),(5,20020204230000); -Warnings: -Warning 1265 Data truncated for column 'stamp' at row 3 -SELECT col1 FROM t1 UNION SELECT col1 FROM t2 WHERE stamp < -'20020204120000' GROUP BY col1; -col1 -1 -2 -3 -4 -drop table t1,t2; -CREATE TABLE t1 ( -`id` int(10) unsigned NOT NULL auto_increment, -`id_object` int(10) unsigned default '0', -`id_version` int(10) unsigned NOT NULL default '1', -`label` varchar(100) NOT NULL default '', -`description` text, -PRIMARY KEY (`id`), -KEY `id_object` (`id_object`), -KEY `id_version` (`id_version`) -) ENGINE=InnoDB; -INSERT INTO t1 VALUES("6", "3382", "9", "Test", NULL), ("7", "102", "5", "Le Pekin (Test)", NULL),("584", "1794", "4", "Test de resto", NULL),("837", "1822", "6", "Test 3", NULL),("1119", "3524", "1", "Societe Test", NULL),("1122", "3525", "1", "Fournisseur Test", NULL); -CREATE TABLE t2 ( -`id` int(10) unsigned NOT NULL auto_increment, -`id_version` int(10) unsigned NOT NULL default '1', -PRIMARY KEY (`id`), -KEY `id_version` (`id_version`) -) ENGINE=InnoDB; -INSERT INTO t2 VALUES("3524", "1"),("3525", "1"),("1794", "4"),("102", "5"),("1822", "6"),("3382", "9"); -SELECT t2.id, t1.`label` FROM t2 INNER JOIN -(SELECT t1.id_object as id_object FROM t1 WHERE t1.`label` LIKE '%test%') AS lbl -ON (t2.id = lbl.id_object) INNER JOIN t1 ON (t2.id = t1.id_object); -id label -3382 Test -102 Le Pekin (Test) -1794 Test de resto -1822 Test 3 -3524 Societe Test -3525 Fournisseur Test -drop table t1,t2; -create table t1 (a int, b varchar(200), c text not null) checksum=1 engine=myisam; -create table t2 (a int, b varchar(200), c text not null) checksum=0 engine=innodb; -create table t3 (a int, b varchar(200), c text not null) checksum=1 engine=innodb; -insert t1 values (1, "aaa", "bbb"), (NULL, "", "ccccc"), (0, NULL, ""); -insert t2 select * from t1; -insert t3 select * from t1; -checksum table t1, t2, t3, t4 quick; -Table Checksum -test.t1 2948697075 -test.t2 NULL -test.t3 NULL -test.t4 NULL -Warnings: -Error 1146 Table 'test.t4' doesn't exist -checksum table t1, t2, t3, t4; -Table Checksum -test.t1 2948697075 -test.t2 2948697075 -test.t3 2948697075 -test.t4 NULL -Warnings: -Error 1146 Table 'test.t4' doesn't exist -checksum table t1, t2, t3, t4 extended; -Table Checksum -test.t1 2948697075 -test.t2 2948697075 -test.t3 2948697075 -test.t4 NULL -Warnings: -Error 1146 Table 'test.t4' doesn't exist -drop table t1,t2,t3; -create table t1 (id int, name char(10) not null, name2 char(10) not null) engine=innodb; -insert into t1 values(1,'first','fff'),(2,'second','sss'),(3,'third','ttt'); -select trim(name2) from t1 union all select trim(name) from t1 union all select trim(id) from t1; -trim(name2) -fff -sss -ttt -first -second -third -1 -2 -3 -drop table t1; -create table t1 (a int) engine=innodb; -create table t2 like t1; -drop table t1,t2; -create table t1 (id int(11) not null, id2 int(11) not null, unique (id,id2)) engine=innodb; -create table t2 (id int(11) not null, constraint t1_id_fk foreign key ( id ) references t1 (id)) engine = innodb; -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `id` int(11) NOT NULL, - `id2` int(11) NOT NULL, - UNIQUE KEY `id` (`id`,`id2`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -show create table t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `id` int(11) NOT NULL, - KEY `t1_id_fk` (`id`), - CONSTRAINT `t1_id_fk` FOREIGN KEY (`id`) REFERENCES `t1` (`id`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -create index id on t2 (id); -show create table t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `id` int(11) NOT NULL, - KEY `id` (`id`), - CONSTRAINT `t1_id_fk` FOREIGN KEY (`id`) REFERENCES `t1` (`id`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -create index id2 on t2 (id); -show create table t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `id` int(11) NOT NULL, - KEY `id` (`id`), - KEY `id2` (`id`), - CONSTRAINT `t1_id_fk` FOREIGN KEY (`id`) REFERENCES `t1` (`id`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop index id2 on t2; -drop index id on t2; -ERROR HY000: Cannot drop index 'id': needed in a foreign key constraint -show create table t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `id` int(11) NOT NULL, - KEY `id` (`id`), - CONSTRAINT `t1_id_fk` FOREIGN KEY (`id`) REFERENCES `t1` (`id`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t2; -create table t2 (id int(11) not null, id2 int(11) not null, constraint t1_id_fk foreign key (id,id2) references t1 (id,id2)) engine = innodb; -show create table t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `id` int(11) NOT NULL, - `id2` int(11) NOT NULL, - KEY `t1_id_fk` (`id`,`id2`), - CONSTRAINT `t1_id_fk` FOREIGN KEY (`id`, `id2`) REFERENCES `t1` (`id`, `id2`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -create unique index id on t2 (id,id2); -show create table t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `id` int(11) NOT NULL, - `id2` int(11) NOT NULL, - UNIQUE KEY `id` (`id`,`id2`), - CONSTRAINT `t1_id_fk` FOREIGN KEY (`id`, `id2`) REFERENCES `t1` (`id`, `id2`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t2; -create table t2 (id int(11) not null, id2 int(11) not null, unique (id,id2),constraint t1_id_fk foreign key (id2,id) references t1 (id,id2)) engine = innodb; -show create table t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `id` int(11) NOT NULL, - `id2` int(11) NOT NULL, - UNIQUE KEY `id` (`id`,`id2`), - KEY `t1_id_fk` (`id2`,`id`), - CONSTRAINT `t1_id_fk` FOREIGN KEY (`id2`, `id`) REFERENCES `t1` (`id`, `id2`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t2; -create table t2 (id int(11) not null, id2 int(11) not null, unique (id,id2), constraint t1_id_fk foreign key (id) references t1 (id)) engine = innodb; -show create table t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `id` int(11) NOT NULL, - `id2` int(11) NOT NULL, - UNIQUE KEY `id` (`id`,`id2`), - CONSTRAINT `t1_id_fk` FOREIGN KEY (`id`) REFERENCES `t1` (`id`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t2; -create table t2 (id int(11) not null, id2 int(11) not null, unique (id,id2),constraint t1_id_fk foreign key (id2,id) references t1 (id,id2)) engine = innodb; -show create table t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `id` int(11) NOT NULL, - `id2` int(11) NOT NULL, - UNIQUE KEY `id` (`id`,`id2`), - KEY `t1_id_fk` (`id2`,`id`), - CONSTRAINT `t1_id_fk` FOREIGN KEY (`id2`, `id`) REFERENCES `t1` (`id`, `id2`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t2; -create table t2 (id int(11) not null auto_increment, id2 int(11) not null, constraint t1_id_fk foreign key (id) references t1 (id), primary key (id), index (id,id2)) engine = innodb; -show create table t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `id` int(11) NOT NULL AUTO_INCREMENT, - `id2` int(11) NOT NULL, - PRIMARY KEY (`id`), - KEY `id` (`id`,`id2`), - CONSTRAINT `t1_id_fk` FOREIGN KEY (`id`) REFERENCES `t1` (`id`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t2; -create table t2 (id int(11) not null auto_increment, id2 int(11) not null, constraint t1_id_fk foreign key (id) references t1 (id)) engine= innodb; -show create table t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `id` int(11) NOT NULL AUTO_INCREMENT, - `id2` int(11) NOT NULL, - KEY `t1_id_fk` (`id`), - CONSTRAINT `t1_id_fk` FOREIGN KEY (`id`) REFERENCES `t1` (`id`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -alter table t2 add index id_test (id), add index id_test2 (id,id2); -show create table t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `id` int(11) NOT NULL AUTO_INCREMENT, - `id2` int(11) NOT NULL, - KEY `id_test` (`id`), - KEY `id_test2` (`id`,`id2`), - CONSTRAINT `t1_id_fk` FOREIGN KEY (`id`) REFERENCES `t1` (`id`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t2; -create table t2 (id int(11) not null, id2 int(11) not null, constraint t1_id_fk foreign key (id2,id) references t1 (id)) engine = innodb; -ERROR 42000: Incorrect foreign key definition for 't1_id_fk': Key reference and table reference don't match -create table t2 (a int auto_increment primary key, b int, index(b), foreign key (b) references t1(id), unique(b)) engine=innodb; -show create table t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `a` int(11) NOT NULL AUTO_INCREMENT, - `b` int(11) DEFAULT NULL, - PRIMARY KEY (`a`), - UNIQUE KEY `b_2` (`b`), - KEY `b` (`b`), - CONSTRAINT `t2_ibfk_1` FOREIGN KEY (`b`) REFERENCES `t1` (`id`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t2; -create table t2 (a int auto_increment primary key, b int, foreign key (b) references t1(id), foreign key (b) references t1(id), unique(b)) engine=innodb; -show create table t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `a` int(11) NOT NULL AUTO_INCREMENT, - `b` int(11) DEFAULT NULL, - PRIMARY KEY (`a`), - UNIQUE KEY `b` (`b`), - CONSTRAINT `t2_ibfk_1` FOREIGN KEY (`b`) REFERENCES `t1` (`id`), - CONSTRAINT `t2_ibfk_2` FOREIGN KEY (`b`) REFERENCES `t1` (`id`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t2, t1; -create table t1 (c char(10), index (c,c)) engine=innodb; -ERROR 42S21: Duplicate column name 'c' -create table t1 (c1 char(10), c2 char(10), index (c1,c2,c1)) engine=innodb; -ERROR 42S21: Duplicate column name 'c1' -create table t1 (c1 char(10), c2 char(10), index (c1,c1,c2)) engine=innodb; -ERROR 42S21: Duplicate column name 'c1' -create table t1 (c1 char(10), c2 char(10), index (c2,c1,c1)) engine=innodb; -ERROR 42S21: Duplicate column name 'c1' -create table t1 (c1 char(10), c2 char(10)) engine=innodb; -alter table t1 add key (c1,c1); -ERROR 42S21: Duplicate column name 'c1' -alter table t1 add key (c2,c1,c1); -ERROR 42S21: Duplicate column name 'c1' -alter table t1 add key (c1,c2,c1); -ERROR 42S21: Duplicate column name 'c1' -alter table t1 add key (c1,c1,c2); -ERROR 42S21: Duplicate column name 'c1' -drop table t1; -create table t1(a int(1) , b int(1)) engine=innodb; -insert into t1 values ('1111', '3333'); -select distinct concat(a, b) from t1; -concat(a, b) -11113333 -drop table t1; -CREATE TABLE t1 ( a char(10) ) ENGINE=InnoDB; -SELECT a FROM t1 WHERE MATCH (a) AGAINST ('test' IN BOOLEAN MODE); -ERROR HY000: The used table type doesn't support FULLTEXT indexes -DROP TABLE t1; -CREATE TABLE t1 (a_id tinyint(4) NOT NULL default '0', PRIMARY KEY (a_id)) ENGINE=InnoDB DEFAULT CHARSET=latin1; -INSERT INTO t1 VALUES (1),(2),(3); -CREATE TABLE t2 (b_id tinyint(4) NOT NULL default '0',b_a tinyint(4) NOT NULL default '0', PRIMARY KEY (b_id), KEY (b_a), -CONSTRAINT fk_b_a FOREIGN KEY (b_a) REFERENCES t1 (a_id) ON DELETE CASCADE ON UPDATE NO ACTION) ENGINE=InnoDB DEFAULT CHARSET=latin1; -INSERT INTO t2 VALUES (1,1),(2,1),(3,1),(4,2),(5,2); -SELECT * FROM (SELECT t1.*,GROUP_CONCAT(t2.b_id SEPARATOR ',') as b_list FROM (t1 LEFT JOIN (t2) on t1.a_id = t2.b_a) GROUP BY t1.a_id ) AS xyz; -a_id b_list -1 1,2,3 -2 4,5 -3 NULL -DROP TABLE t2; -DROP TABLE t1; -create temporary table t1 (a int) engine=innodb; -insert into t1 values (4711); -truncate t1; -insert into t1 values (42); -select * from t1; -a -42 -drop table t1; -create table t1 (a int) engine=innodb; -insert into t1 values (4711); -truncate t1; -insert into t1 values (42); -select * from t1; -a -42 -drop table t1; -create table t1 (a int not null, b int not null, c blob not null, d int not null, e int, primary key (a,b,c(255),d)) engine=innodb; -insert into t1 values (2,2,"b",2,2),(1,1,"a",1,1),(3,3,"ab",3,3); -select * from t1 order by a,b,c,d; -a b c d e -1 1 a 1 1 -2 2 b 2 2 -3 3 ab 3 3 -explain select * from t1 order by a,b,c,d; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ALL NULL NULL NULL NULL 3 Using filesort -drop table t1; -create table t1 (a char(1), b char(1), key(a, b)) engine=innodb; -insert into t1 values ('8', '6'), ('4', '7'); -select min(a) from t1; -min(a) -4 -select min(b) from t1 where a='8'; -min(b) -6 -drop table t1; -create table t1 (x bigint unsigned not null primary key) engine=innodb; -insert into t1(x) values (0xfffffffffffffff0),(0xfffffffffffffff1); -select * from t1; -x -18446744073709551600 -18446744073709551601 -select count(*) from t1 where x>0; -count(*) -2 -select count(*) from t1 where x=0; -count(*) -0 -select count(*) from t1 where x<0; -count(*) -0 -select count(*) from t1 where x < -16; -count(*) -0 -select count(*) from t1 where x = -16; -count(*) -0 -explain select count(*) from t1 where x > -16; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 index PRIMARY PRIMARY 8 NULL 2 Using where; Using index -select count(*) from t1 where x > -16; -count(*) -2 -select * from t1 where x > -16; -x -18446744073709551600 -18446744073709551601 -select count(*) from t1 where x = 18446744073709551601; -count(*) -1 -drop table t1; -SELECT variable_value FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_buffer_pool_pages_total'; -variable_value -8191 -SELECT variable_value FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_page_size'; -variable_value -16384 -SELECT variable_value - @innodb_rows_deleted_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_rows_deleted'; -variable_value - @innodb_rows_deleted_orig -71 -SELECT variable_value - @innodb_rows_inserted_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_rows_inserted'; -variable_value - @innodb_rows_inserted_orig -1084 -SELECT variable_value - @innodb_rows_updated_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_rows_updated'; -variable_value - @innodb_rows_updated_orig -885 -SELECT variable_value - @innodb_row_lock_waits_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_row_lock_waits'; -variable_value - @innodb_row_lock_waits_orig -0 -SELECT variable_value - @innodb_row_lock_current_waits_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_row_lock_current_waits'; -variable_value - @innodb_row_lock_current_waits_orig -0 -SELECT variable_value - @innodb_row_lock_time_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_row_lock_time'; -variable_value - @innodb_row_lock_time_orig -0 -SELECT variable_value - @innodb_row_lock_time_max_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_row_lock_time_max'; -variable_value - @innodb_row_lock_time_max_orig -0 -SELECT variable_value - @innodb_row_lock_time_avg_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_row_lock_time_avg'; -variable_value - @innodb_row_lock_time_avg_orig -0 -SET @innodb_sync_spin_loops_orig = @@innodb_sync_spin_loops; -show variables like "innodb_sync_spin_loops"; -Variable_name Value -innodb_sync_spin_loops 30 -set global innodb_sync_spin_loops=1000; -show variables like "innodb_sync_spin_loops"; -Variable_name Value -innodb_sync_spin_loops 1000 -set global innodb_sync_spin_loops=0; -show variables like "innodb_sync_spin_loops"; -Variable_name Value -innodb_sync_spin_loops 0 -set global innodb_sync_spin_loops=20; -show variables like "innodb_sync_spin_loops"; -Variable_name Value -innodb_sync_spin_loops 20 -set global innodb_sync_spin_loops=@innodb_sync_spin_loops_orig; -show variables like "innodb_thread_concurrency"; -Variable_name Value -innodb_thread_concurrency 0 -set global innodb_thread_concurrency=1001; -Warnings: -Warning 1292 Truncated incorrect thread_concurrency value: '1001' -show variables like "innodb_thread_concurrency"; -Variable_name Value -innodb_thread_concurrency 1000 -set global innodb_thread_concurrency=0; -show variables like "innodb_thread_concurrency"; -Variable_name Value -innodb_thread_concurrency 0 -set global innodb_thread_concurrency=16; -show variables like "innodb_thread_concurrency"; -Variable_name Value -innodb_thread_concurrency 16 -show variables like "innodb_concurrency_tickets"; -Variable_name Value -innodb_concurrency_tickets 500 -set global innodb_concurrency_tickets=1000; -show variables like "innodb_concurrency_tickets"; -Variable_name Value -innodb_concurrency_tickets 1000 -set global innodb_concurrency_tickets=0; -Warnings: -Warning 1292 Truncated incorrect concurrency_tickets value: '0' -show variables like "innodb_concurrency_tickets"; -Variable_name Value -innodb_concurrency_tickets 1 -set global innodb_concurrency_tickets=500; -show variables like "innodb_concurrency_tickets"; -Variable_name Value -innodb_concurrency_tickets 500 -show variables like "innodb_thread_sleep_delay"; -Variable_name Value -innodb_thread_sleep_delay 10000 -set global innodb_thread_sleep_delay=100000; -show variables like "innodb_thread_sleep_delay"; -Variable_name Value -innodb_thread_sleep_delay 100000 -set global innodb_thread_sleep_delay=0; -show variables like "innodb_thread_sleep_delay"; -Variable_name Value -innodb_thread_sleep_delay 0 -set global innodb_thread_sleep_delay=10000; -show variables like "innodb_thread_sleep_delay"; -Variable_name Value -innodb_thread_sleep_delay 10000 -set storage_engine=INNODB; -drop table if exists t1,t2,t3; ---- Testing varchar --- ---- Testing varchar --- -create table t1 (v varchar(10), c char(10), t text); -insert into t1 values('+ ', '+ ', '+ '); -set @a=repeat(' ',20); -insert into t1 values (concat('+',@a),concat('+',@a),concat('+',@a)); -Warnings: -Note 1265 Data truncated for column 'v' at row 1 -select concat('*',v,'*',c,'*',t,'*') from t1; -concat('*',v,'*',c,'*',t,'*') -*+ *+*+ * -*+ *+*+ * -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `v` varchar(10) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `t` text -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -create table t2 like t1; -show create table t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `v` varchar(10) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `t` text -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -create table t3 select * from t1; -show create table t3; -Table Create Table -t3 CREATE TABLE `t3` ( - `v` varchar(10) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `t` text -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -alter table t1 modify c varchar(10); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `v` varchar(10) DEFAULT NULL, - `c` varchar(10) DEFAULT NULL, - `t` text -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -alter table t1 modify v char(10); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `v` char(10) DEFAULT NULL, - `c` varchar(10) DEFAULT NULL, - `t` text -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -alter table t1 modify t varchar(10); -Warnings: -Note 1265 Data truncated for column 't' at row 2 -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `v` char(10) DEFAULT NULL, - `c` varchar(10) DEFAULT NULL, - `t` varchar(10) DEFAULT NULL -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -select concat('*',v,'*',c,'*',t,'*') from t1; -concat('*',v,'*',c,'*',t,'*') -*+*+*+ * -*+*+*+ * -drop table t1,t2,t3; -create table t1 (v varchar(10), c char(10), t text, key(v), key(c), key(t(10))); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `v` varchar(10) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `t` text, - KEY `v` (`v`), - KEY `c` (`c`), - KEY `t` (`t`(10)) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -select count(*) from t1; -count(*) -270 -insert into t1 values(concat('a',char(1)),concat('a',char(1)),concat('a',char(1))); -select count(*) from t1 where v='a'; -count(*) -10 -select count(*) from t1 where c='a'; -count(*) -10 -select count(*) from t1 where t='a'; -count(*) -10 -select count(*) from t1 where v='a '; -count(*) -10 -select count(*) from t1 where c='a '; -count(*) -10 -select count(*) from t1 where t='a '; -count(*) -10 -select count(*) from t1 where v between 'a' and 'a '; -count(*) -10 -select count(*) from t1 where v between 'a' and 'a ' and v between 'a ' and 'b\n'; -count(*) -10 -select count(*) from t1 where v like 'a%'; -count(*) -11 -select count(*) from t1 where c like 'a%'; -count(*) -11 -select count(*) from t1 where t like 'a%'; -count(*) -11 -select count(*) from t1 where v like 'a %'; -count(*) -9 -explain select count(*) from t1 where v='a '; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref v v 13 const # Using where; Using index -explain select count(*) from t1 where c='a '; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref c c 11 const # Using where; Using index -explain select count(*) from t1 where t='a '; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref t t 13 const # Using where -explain select count(*) from t1 where v like 'a%'; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 range v v 13 NULL # Using where; Using index -explain select count(*) from t1 where v between 'a' and 'a '; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref v v 13 const # Using where; Using index -explain select count(*) from t1 where v between 'a' and 'a ' and v between 'a ' and 'b\n'; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref v v 13 const # Using where; Using index -alter table t1 add unique(v); -ERROR 23000: Duplicate entry 'v' for key 'v_2' -alter table t1 add key(v); -select concat('*',v,'*',c,'*',t,'*') as qq from t1 where v='a'; -qq -*a*a*a* -*a *a*a * -*a *a*a * -*a *a*a * -*a *a*a * -*a *a*a * -*a *a*a * -*a *a*a * -*a *a*a * -*a *a*a * -explain select * from t1 where v='a'; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref v,v_2 # 13 const # Using where -select v,count(*) from t1 group by v limit 10; -v count(*) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -select v,count(t) from t1 group by v limit 10; -v count(t) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -select v,count(c) from t1 group by v limit 10; -v count(c) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -select sql_big_result v,count(t) from t1 group by v limit 10; -v count(t) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -select sql_big_result v,count(c) from t1 group by v limit 10; -v count(c) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -select c,count(*) from t1 group by c limit 10; -c count(*) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -select c,count(t) from t1 group by c limit 10; -c count(t) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -select sql_big_result c,count(t) from t1 group by c limit 10; -c count(t) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -select t,count(*) from t1 group by t limit 10; -t count(*) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -select t,count(t) from t1 group by t limit 10; -t count(t) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -select sql_big_result t,count(t) from t1 group by t limit 10; -t count(t) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -alter table t1 modify v varchar(300), drop key v, drop key v_2, add key v (v); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `v` varchar(300) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `t` text, - KEY `c` (`c`), - KEY `t` (`t`(10)), - KEY `v` (`v`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -select count(*) from t1 where v='a'; -count(*) -10 -select count(*) from t1 where v='a '; -count(*) -10 -select count(*) from t1 where v between 'a' and 'a '; -count(*) -10 -select count(*) from t1 where v between 'a' and 'a ' and v between 'a ' and 'b\n'; -count(*) -10 -select count(*) from t1 where v like 'a%'; -count(*) -11 -select count(*) from t1 where v like 'a %'; -count(*) -9 -explain select count(*) from t1 where v='a '; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref v v 303 const # Using where; Using index -explain select count(*) from t1 where v like 'a%'; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 range v v 303 NULL # Using where; Using index -explain select count(*) from t1 where v between 'a' and 'a '; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref v v 303 const # Using where; Using index -explain select count(*) from t1 where v between 'a' and 'a ' and v between 'a ' and 'b\n'; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref v v 303 const # Using where; Using index -explain select * from t1 where v='a'; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref v v 303 const # Using where -select v,count(*) from t1 group by v limit 10; -v count(*) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -select v,count(t) from t1 group by v limit 10; -v count(t) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -select sql_big_result v,count(t) from t1 group by v limit 10; -v count(t) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -alter table t1 drop key v, add key v (v(30)); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `v` varchar(300) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `t` text, - KEY `c` (`c`), - KEY `t` (`t`(10)), - KEY `v` (`v`(30)) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -select count(*) from t1 where v='a'; -count(*) -10 -select count(*) from t1 where v='a '; -count(*) -10 -select count(*) from t1 where v between 'a' and 'a '; -count(*) -10 -select count(*) from t1 where v between 'a' and 'a ' and v between 'a ' and 'b\n'; -count(*) -10 -select count(*) from t1 where v like 'a%'; -count(*) -11 -select count(*) from t1 where v like 'a %'; -count(*) -9 -explain select count(*) from t1 where v='a '; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref v v 33 const # Using where -explain select count(*) from t1 where v like 'a%'; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 range v v 33 NULL # Using where -explain select count(*) from t1 where v between 'a' and 'a '; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref v v 33 const # Using where -explain select count(*) from t1 where v between 'a' and 'a ' and v between 'a ' and 'b\n'; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref v v 33 const # Using where -explain select * from t1 where v='a'; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref v v 33 const # Using where -select v,count(*) from t1 group by v limit 10; -v count(*) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -select v,count(t) from t1 group by v limit 10; -v count(t) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -select sql_big_result v,count(t) from t1 group by v limit 10; -v count(t) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -alter table t1 modify v varchar(600), drop key v, add key v (v); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `v` varchar(600) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `t` text, - KEY `c` (`c`), - KEY `t` (`t`(10)), - KEY `v` (`v`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -select v,count(*) from t1 group by v limit 10; -v count(*) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -select v,count(t) from t1 group by v limit 10; -v count(t) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -select sql_big_result v,count(t) from t1 group by v limit 10; -v count(t) -a 1 -a 10 -b 10 -c 10 -d 10 -e 10 -f 10 -g 10 -h 10 -i 10 -drop table t1; -create table t1 (a char(10), unique (a)); -insert into t1 values ('a '); -insert into t1 values ('a '); -ERROR 23000: Duplicate entry 'a' for key 'a' -alter table t1 modify a varchar(10); -insert into t1 values ('a '),('a '),('a '),('a '); -ERROR 23000: Duplicate entry 'a ' for key 'a' -insert into t1 values ('a '); -ERROR 23000: Duplicate entry 'a ' for key 'a' -insert into t1 values ('a '); -ERROR 23000: Duplicate entry 'a ' for key 'a' -insert into t1 values ('a '); -ERROR 23000: Duplicate entry 'a ' for key 'a' -update t1 set a='a ' where a like 'a%'; -select concat(a,'.') from t1; -concat(a,'.') -a . -update t1 set a='abc ' where a like 'a '; -select concat(a,'.') from t1; -concat(a,'.') -a . -update t1 set a='a ' where a like 'a %'; -select concat(a,'.') from t1; -concat(a,'.') -a . -update t1 set a='a ' where a like 'a '; -select concat(a,'.') from t1; -concat(a,'.') -a . -drop table t1; -create table t1 (v varchar(10), c char(10), t text, key(v(5)), key(c(5)), key(t(5))); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `v` varchar(10) DEFAULT NULL, - `c` char(10) DEFAULT NULL, - `t` text, - KEY `v` (`v`(5)), - KEY `c` (`c`(5)), - KEY `t` (`t`(5)) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t1; -create table t1 (v char(10) character set utf8); -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `v` char(10) CHARACTER SET utf8 DEFAULT NULL -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t1; -create table t1 (v varchar(10), c char(10)) row_format=fixed; -Warnings: -Warning 1478 InnoDB: assuming ROW_FORMAT=COMPACT. -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `v` varchar(10) DEFAULT NULL, - `c` char(10) DEFAULT NULL -) ENGINE=InnoDB DEFAULT CHARSET=latin1 ROW_FORMAT=FIXED -insert into t1 values('a','a'),('a ','a '); -select concat('*',v,'*',c,'*') from t1; -concat('*',v,'*',c,'*') -*a*a* -*a *a* -drop table t1; -create table t1 (v varchar(65530), key(v(10))); -insert into t1 values(repeat('a',65530)); -select length(v) from t1 where v=repeat('a',65530); -length(v) -65530 -drop table t1; -create table t1(a int, b varchar(12), key ba(b, a)); -insert into t1 values (1, 'A'), (20, NULL); -explain select * from t1 where a=20 and b is null; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref ba ba 20 const,const 1 Using where; Using index -select * from t1 where a=20 and b is null; -a b -20 NULL -drop table t1; -create table t1 (v varchar(65530), key(v)); -Warnings: -Warning 1071 Specified key was too long; max key length is 767 bytes -drop table t1; -create table t1 (v varchar(65536)); -Warnings: -Note 1246 Converting column 'v' from VARCHAR to TEXT -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `v` mediumtext -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t1; -create table t1 (v varchar(65530) character set utf8); -Warnings: -Note 1246 Converting column 'v' from VARCHAR to TEXT -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `v` mediumtext CHARACTER SET utf8 -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t1; -set storage_engine=MyISAM; -create table t1 (v varchar(16384)) engine=innodb; -drop table t1; -create table t1 (a char(1), b char(1), key(a, b)) engine=innodb; -insert into t1 values ('8', '6'), ('4', '7'); -select min(a) from t1; -min(a) -4 -select min(b) from t1 where a='8'; -min(b) -6 -drop table t1; -CREATE TABLE t1 ( `a` int(11) NOT NULL auto_increment, `b` int(11) default NULL,PRIMARY KEY (`a`),UNIQUE KEY `b` (`b`)) ENGINE=innodb; -insert into t1 (b) values (1); -replace into t1 (b) values (2), (1), (3); -select * from t1; -a b -3 1 -2 2 -4 3 -truncate table t1; -insert into t1 (b) values (1); -replace into t1 (b) values (2); -replace into t1 (b) values (1); -replace into t1 (b) values (3); -select * from t1; -a b -3 1 -2 2 -4 3 -drop table t1; -create table t1 (rowid int not null auto_increment, val int not null,primary -key (rowid), unique(val)) engine=innodb; -replace into t1 (val) values ('1'),('2'); -replace into t1 (val) values ('1'),('2'); -insert into t1 (val) values ('1'),('2'); -ERROR 23000: Duplicate entry '1' for key 'val' -select * from t1; -rowid val -3 1 -4 2 -drop table t1; -create table t1 (a int not null auto_increment primary key, val int) engine=InnoDB; -insert into t1 (val) values (1); -update t1 set a=2 where a=1; -insert into t1 (val) values (1); -ERROR 23000: Duplicate entry '2' for key 'PRIMARY' -select * from t1; -a val -2 1 -drop table t1; -CREATE TABLE t1 (GRADE DECIMAL(4) NOT NULL, PRIMARY KEY (GRADE)) ENGINE=INNODB; -INSERT INTO t1 (GRADE) VALUES (151),(252),(343); -SELECT GRADE FROM t1 WHERE GRADE > 160 AND GRADE < 300; -GRADE -252 -SELECT GRADE FROM t1 WHERE GRADE= 151; -GRADE -151 -DROP TABLE t1; -create table t1 (f1 varchar(10), f2 varchar(10), primary key (f1,f2)) engine=innodb; -create table t2 (f3 varchar(10), f4 varchar(10), key (f4)) engine=innodb; -insert into t2 values ('aa','cc'); -insert into t1 values ('aa','bb'),('aa','cc'); -delete t1 from t1,t2 where f1=f3 and f4='cc'; -select * from t1; -f1 f2 -drop table t1,t2; -CREATE TABLE t1 ( -id INTEGER NOT NULL AUTO_INCREMENT, PRIMARY KEY (id) -) ENGINE=InnoDB; -CREATE TABLE t2 ( -id INTEGER NOT NULL, -FOREIGN KEY (id) REFERENCES t1 (id) -) ENGINE=InnoDB; -INSERT INTO t1 (id) VALUES (NULL); -SELECT * FROM t1; -id -1 -TRUNCATE t1; -INSERT INTO t1 (id) VALUES (NULL); -SELECT * FROM t1; -id -1 -DELETE FROM t1; -TRUNCATE t1; -INSERT INTO t1 (id) VALUES (NULL); -SELECT * FROM t1; -id -1 -DROP TABLE t2, t1; -CREATE TABLE t1 -( -id INT PRIMARY KEY -) ENGINE=InnoDB; -CREATE TEMPORARY TABLE t2 -( -id INT NOT NULL PRIMARY KEY, -b INT, -FOREIGN KEY (b) REFERENCES test.t1(id) -) ENGINE=InnoDB; -Got one of the listed errors -DROP TABLE t1; -create table t1 (col1 varchar(2000), index (col1(767))) -character set = latin1 engine = innodb; -create table t2 (col1 char(255), index (col1)) -character set = latin1 engine = innodb; -create table t3 (col1 binary(255), index (col1)) -character set = latin1 engine = innodb; -create table t4 (col1 varchar(767), index (col1)) -character set = latin1 engine = innodb; -create table t5 (col1 varchar(767) primary key) -character set = latin1 engine = innodb; -create table t6 (col1 varbinary(767) primary key) -character set = latin1 engine = innodb; -create table t7 (col1 text, index(col1(767))) -character set = latin1 engine = innodb; -create table t8 (col1 blob, index(col1(767))) -character set = latin1 engine = innodb; -create table t9 (col1 varchar(512), col2 varchar(512), index(col1, col2)) -character set = latin1 engine = innodb; -show create table t9; -Table Create Table -t9 CREATE TABLE `t9` ( - `col1` varchar(512) DEFAULT NULL, - `col2` varchar(512) DEFAULT NULL, - KEY `col1` (`col1`,`col2`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t1, t2, t3, t4, t5, t6, t7, t8, t9; -create table t1 (col1 varchar(768), index(col1)) -character set = latin1 engine = innodb; -Warnings: -Warning 1071 Specified key was too long; max key length is 767 bytes -create table t2 (col1 varbinary(768), index(col1)) -character set = latin1 engine = innodb; -Warnings: -Warning 1071 Specified key was too long; max key length is 767 bytes -create table t3 (col1 text, index(col1(768))) -character set = latin1 engine = innodb; -Warnings: -Warning 1071 Specified key was too long; max key length is 767 bytes -create table t4 (col1 blob, index(col1(768))) -character set = latin1 engine = innodb; -Warnings: -Warning 1071 Specified key was too long; max key length is 767 bytes -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `col1` varchar(768) DEFAULT NULL, - KEY `col1` (`col1`(767)) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t1, t2, t3, t4; -create table t1 (col1 varchar(768) primary key) -character set = latin1 engine = innodb; -ERROR 42000: Specified key was too long; max key length is 767 bytes -create table t2 (col1 varbinary(768) primary key) -character set = latin1 engine = innodb; -ERROR 42000: Specified key was too long; max key length is 767 bytes -create table t3 (col1 text, primary key(col1(768))) -character set = latin1 engine = innodb; -ERROR 42000: Specified key was too long; max key length is 767 bytes -create table t4 (col1 blob, primary key(col1(768))) -character set = latin1 engine = innodb; -ERROR 42000: Specified key was too long; max key length is 767 bytes -CREATE TABLE t1 -( -id INT PRIMARY KEY -) ENGINE=InnoDB; -CREATE TABLE t2 -( -v INT, -CONSTRAINT c1 FOREIGN KEY (v) REFERENCES t1(id) -) ENGINE=InnoDB; -INSERT INTO t2 VALUES(2); -ERROR 23000: Cannot add or update a child row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `c1` FOREIGN KEY (`v`) REFERENCES `t1` (`id`)) -INSERT INTO t1 VALUES(1); -INSERT INTO t2 VALUES(1); -DELETE FROM t1 WHERE id = 1; -ERROR 23000: Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `c1` FOREIGN KEY (`v`) REFERENCES `t1` (`id`)) -DROP TABLE t1; -ERROR 23000: Cannot delete or update a parent row: a foreign key constraint fails -SET FOREIGN_KEY_CHECKS=0; -DROP TABLE t1; -SET FOREIGN_KEY_CHECKS=1; -INSERT INTO t2 VALUES(3); -ERROR 23000: Cannot add or update a child row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `c1` FOREIGN KEY (`v`) REFERENCES `t1` (`id`)) -DROP TABLE t2; -create table t1(a int not null) engine=innodb DEFAULT CHARSET=latin1; -insert into t1 values (1),(2); -set autocommit=0; -checksum table t1; -Table Checksum -test.t1 1531596814 -insert into t1 values(3); -checksum table t1; -Table Checksum -test.t1 1531596814 -commit; -checksum table t1; -Table Checksum -test.t1 2050879373 -commit; -drop table t1; -create table t1(a int not null) engine=innodb DEFAULT CHARSET=latin1; -insert into t1 values (1),(2); -set autocommit=1; -checksum table t1; -Table Checksum -test.t1 1531596814 -set autocommit=1; -insert into t1 values(3); -checksum table t1; -Table Checksum -test.t1 2050879373 -drop table t1; -set foreign_key_checks=0; -create table t2 (a int primary key, b int, foreign key (b) references t1(a)) engine = innodb; -create table t1(a char(10) primary key, b varchar(20)) engine = innodb; -ERROR HY000: Can't create table 'test.t1' (errno: 150) -set foreign_key_checks=1; -drop table t2; -set foreign_key_checks=0; -create table t1(a varchar(10) primary key) engine = innodb DEFAULT CHARSET=latin1; -create table t2 (a varchar(10), foreign key (a) references t1(a)) engine = innodb DEFAULT CHARSET=utf8; -ERROR HY000: Can't create table 'test.t2' (errno: 150) -set foreign_key_checks=1; -drop table t1; -set foreign_key_checks=0; -create table t2 (a varchar(10), foreign key (a) references t1(a)) engine = innodb; -create table t1(a varchar(10) primary key) engine = innodb; -alter table t1 modify column a int; -Got one of the listed errors -set foreign_key_checks=1; -drop table t2,t1; -set foreign_key_checks=0; -create table t2 (a varchar(10), foreign key (a) references t1(a)) engine = innodb DEFAULT CHARSET=latin1; -create table t1(a varchar(10) primary key) engine = innodb DEFAULT CHARSET=latin1; -alter table t1 convert to character set utf8; -set foreign_key_checks=1; -drop table t2,t1; -set foreign_key_checks=0; -create table t2 (a varchar(10), foreign key (a) references t1(a)) engine = innodb DEFAULT CHARSET=latin1; -create table t3(a varchar(10) primary key) engine = innodb DEFAULT CHARSET=utf8; -rename table t3 to t1; -ERROR HY000: Error on rename of './test/t3' to './test/t1' (errno: 150) -set foreign_key_checks=1; -drop table t2,t3; -create table t1(a int primary key) row_format=redundant engine=innodb; -create table t2(a int primary key,constraint foreign key(a)references t1(a)) row_format=compact engine=innodb; -create table t3(a int primary key) row_format=compact engine=innodb; -create table t4(a int primary key,constraint foreign key(a)references t3(a)) row_format=redundant engine=innodb; -insert into t1 values(1); -insert into t3 values(1); -insert into t2 values(2); -ERROR 23000: Cannot add or update a child row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `t2_ibfk_1` FOREIGN KEY (`a`) REFERENCES `t1` (`a`)) -insert into t4 values(2); -ERROR 23000: Cannot add or update a child row: a foreign key constraint fails (`test`.`t4`, CONSTRAINT `t4_ibfk_1` FOREIGN KEY (`a`) REFERENCES `t3` (`a`)) -insert into t2 values(1); -insert into t4 values(1); -update t1 set a=2; -ERROR 23000: Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `t2_ibfk_1` FOREIGN KEY (`a`) REFERENCES `t1` (`a`)) -update t2 set a=2; -ERROR 23000: Cannot add or update a child row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `t2_ibfk_1` FOREIGN KEY (`a`) REFERENCES `t1` (`a`)) -update t3 set a=2; -ERROR 23000: Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t4`, CONSTRAINT `t4_ibfk_1` FOREIGN KEY (`a`) REFERENCES `t3` (`a`)) -update t4 set a=2; -ERROR 23000: Cannot add or update a child row: a foreign key constraint fails (`test`.`t4`, CONSTRAINT `t4_ibfk_1` FOREIGN KEY (`a`) REFERENCES `t3` (`a`)) -truncate t1; -ERROR 23000: Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `t2_ibfk_1` FOREIGN KEY (`a`) REFERENCES `t1` (`a`)) -truncate t3; -ERROR 23000: Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t4`, CONSTRAINT `t4_ibfk_1` FOREIGN KEY (`a`) REFERENCES `t3` (`a`)) -truncate t2; -truncate t4; -truncate t1; -truncate t3; -drop table t4,t3,t2,t1; -create table t1 (a varchar(255) character set utf8, -b varchar(255) character set utf8, -c varchar(255) character set utf8, -d varchar(255) character set utf8, -key (a,b,c,d)) engine=innodb; -drop table t1; -create table t1 (a varchar(255) character set utf8, -b varchar(255) character set utf8, -c varchar(255) character set utf8, -d varchar(255) character set utf8, -e varchar(255) character set utf8, -key (a,b,c,d,e)) engine=innodb; -ERROR 42000: Specified key was too long; max key length is 3072 bytes -create table t1 (s1 varbinary(2),primary key (s1)) engine=innodb; -create table t2 (s1 binary(2),primary key (s1)) engine=innodb; -create table t3 (s1 varchar(2) binary,primary key (s1)) engine=innodb; -create table t4 (s1 char(2) binary,primary key (s1)) engine=innodb; -insert into t1 values (0x41),(0x4120),(0x4100); -insert into t2 values (0x41),(0x4120),(0x4100); -ERROR 23000: Duplicate entry 'A' for key 'PRIMARY' -insert into t2 values (0x41),(0x4120); -insert into t3 values (0x41),(0x4120),(0x4100); -ERROR 23000: Duplicate entry 'A ' for key 'PRIMARY' -insert into t3 values (0x41),(0x4100); -insert into t4 values (0x41),(0x4120),(0x4100); -ERROR 23000: Duplicate entry 'A' for key 'PRIMARY' -insert into t4 values (0x41),(0x4100); -select hex(s1) from t1; -hex(s1) -41 -4100 -4120 -select hex(s1) from t2; -hex(s1) -4100 -4120 -select hex(s1) from t3; -hex(s1) -4100 -41 -select hex(s1) from t4; -hex(s1) -4100 -41 -drop table t1,t2,t3,t4; -create table t1 (a int primary key,s1 varbinary(3) not null unique) engine=innodb; -create table t2 (s1 binary(2) not null, constraint c foreign key(s1) references t1(s1) on update cascade) engine=innodb; -insert into t1 values(1,0x4100),(2,0x41),(3,0x4120),(4,0x42); -insert into t2 values(0x42); -ERROR 23000: Cannot add or update a child row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `c` FOREIGN KEY (`s1`) REFERENCES `t1` (`s1`) ON UPDATE CASCADE) -insert into t2 values(0x41); -select hex(s1) from t2; -hex(s1) -4100 -update t1 set s1=0x123456 where a=2; -select hex(s1) from t2; -hex(s1) -4100 -update t1 set s1=0x12 where a=1; -ERROR 23000: Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `c` FOREIGN KEY (`s1`) REFERENCES `t1` (`s1`) ON UPDATE CASCADE) -update t1 set s1=0x12345678 where a=1; -ERROR 23000: Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `c` FOREIGN KEY (`s1`) REFERENCES `t1` (`s1`) ON UPDATE CASCADE) -update t1 set s1=0x123457 where a=1; -ERROR 23000: Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `c` FOREIGN KEY (`s1`) REFERENCES `t1` (`s1`) ON UPDATE CASCADE) -update t1 set s1=0x1220 where a=1; -select hex(s1) from t2; -hex(s1) -1220 -update t1 set s1=0x1200 where a=1; -select hex(s1) from t2; -hex(s1) -1200 -update t1 set s1=0x4200 where a=1; -select hex(s1) from t2; -hex(s1) -4200 -delete from t1 where a=1; -ERROR 23000: Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `c` FOREIGN KEY (`s1`) REFERENCES `t1` (`s1`) ON UPDATE CASCADE) -delete from t1 where a=2; -update t2 set s1=0x4120; -delete from t1; -ERROR 23000: Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `c` FOREIGN KEY (`s1`) REFERENCES `t1` (`s1`) ON UPDATE CASCADE) -delete from t1 where a!=3; -select a,hex(s1) from t1; -a hex(s1) -3 4120 -select hex(s1) from t2; -hex(s1) -4120 -drop table t2,t1; -create table t1 (a int primary key,s1 varchar(2) binary not null unique) engine=innodb; -create table t2 (s1 char(2) binary not null, constraint c foreign key(s1) references t1(s1) on update cascade) engine=innodb; -insert into t1 values(1,0x4100),(2,0x41); -insert into t2 values(0x41); -select hex(s1) from t2; -hex(s1) -41 -update t1 set s1=0x1234 where a=1; -select hex(s1) from t2; -hex(s1) -41 -update t1 set s1=0x12 where a=2; -select hex(s1) from t2; -hex(s1) -12 -delete from t1 where a=1; -delete from t1 where a=2; -ERROR 23000: Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t2`, CONSTRAINT `c` FOREIGN KEY (`s1`) REFERENCES `t1` (`s1`) ON UPDATE CASCADE) -select a,hex(s1) from t1; -a hex(s1) -2 12 -select hex(s1) from t2; -hex(s1) -12 -drop table t2,t1; -CREATE TABLE t1(a INT, PRIMARY KEY(a)) ENGINE=InnoDB; -CREATE TABLE t2(a INT) ENGINE=InnoDB; -ALTER TABLE t2 ADD FOREIGN KEY (a) REFERENCES t1(a); -ALTER TABLE t2 DROP FOREIGN KEY t2_ibfk_1; -ALTER TABLE t2 ADD CONSTRAINT t2_ibfk_0 FOREIGN KEY (a) REFERENCES t1(a); -ALTER TABLE t2 DROP FOREIGN KEY t2_ibfk_0; -SHOW CREATE TABLE t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `a` int(11) DEFAULT NULL, - KEY `t2_ibfk_0` (`a`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -DROP TABLE t2,t1; -create table t1(a int not null, b int, c int, d int, primary key(a)) engine=innodb; -insert into t1(a) values (1),(2),(3); -commit; -set autocommit = 0; -update t1 set b = 5 where a = 2; -create trigger t1t before insert on t1 for each row begin set NEW.b = NEW.a * 10 + 5, NEW.c = NEW.a / 10; end | -set autocommit = 0; -insert into t1(a) values (10),(20),(30),(40),(50),(60),(70),(80),(90),(100), -(11),(21),(31),(41),(51),(61),(71),(81),(91),(101), -(12),(22),(32),(42),(52),(62),(72),(82),(92),(102), -(13),(23),(33),(43),(53),(63),(73),(83),(93),(103), -(14),(24),(34),(44),(54),(64),(74),(84),(94),(104); -commit; -commit; -drop trigger t1t; -drop table t1; -create table t1(a int not null, b int, c int, d int, primary key(a)) engine=innodb; -create table t2(a int not null, b int, c int, d int, primary key(a)) engine=innodb; -create table t3(a int not null, b int, c int, d int, primary key(a)) engine=innodb; -create table t4(a int not null, b int, c int, d int, primary key(a)) engine=innodb; -create table t5(a int not null, b int, c int, d int, primary key(a)) engine=innodb; -insert into t1(a) values (1),(2),(3); -insert into t2(a) values (1),(2),(3); -insert into t3(a) values (1),(2),(3); -insert into t4(a) values (1),(2),(3); -insert into t3(a) values (5),(7),(8); -insert into t4(a) values (5),(7),(8); -insert into t5(a) values (1),(2),(3),(4),(5),(6),(7),(8),(9),(10),(11),(12); -create trigger t1t before insert on t1 for each row begin -INSERT INTO t2 SET a = NEW.a; -end | -create trigger t2t before insert on t2 for each row begin -DELETE FROM t3 WHERE a = NEW.a; -end | -create trigger t3t before delete on t3 for each row begin -UPDATE t4 SET b = b + 1 WHERE a = OLD.a; -end | -create trigger t4t before update on t4 for each row begin -UPDATE t5 SET b = b + 1 where a = NEW.a; -end | -commit; -set autocommit = 0; -update t1 set b = b + 5 where a = 1; -update t2 set b = b + 5 where a = 1; -update t3 set b = b + 5 where a = 1; -update t4 set b = b + 5 where a = 1; -insert into t5(a) values(20); -set autocommit = 0; -insert into t1(a) values(7); -insert into t2(a) values(8); -delete from t2 where a = 3; -update t4 set b = b + 1 where a = 3; -commit; -drop trigger t1t; -drop trigger t2t; -drop trigger t3t; -drop trigger t4t; -drop table t1, t2, t3, t4, t5; -CREATE TABLE t1 ( -field1 varchar(8) NOT NULL DEFAULT '', -field2 varchar(8) NOT NULL DEFAULT '', -PRIMARY KEY (field1, field2) -) ENGINE=InnoDB; -CREATE TABLE t2 ( -field1 varchar(8) NOT NULL DEFAULT '' PRIMARY KEY, -FOREIGN KEY (field1) REFERENCES t1 (field1) -ON DELETE CASCADE ON UPDATE CASCADE -) ENGINE=InnoDB; -INSERT INTO t1 VALUES ('old', 'somevalu'); -INSERT INTO t1 VALUES ('other', 'anyvalue'); -INSERT INTO t2 VALUES ('old'); -INSERT INTO t2 VALUES ('other'); -UPDATE t1 SET field1 = 'other' WHERE field2 = 'somevalu'; -ERROR 23000: Upholding foreign key constraints for table 't1', entry 'other-somevalu', key 1 would lead to a duplicate entry -DROP TABLE t2; -DROP TABLE t1; -create table t1 ( -c1 bigint not null, -c2 bigint not null, -primary key (c1), -unique key (c2) -) engine=innodb; -create table t2 ( -c1 bigint not null, -primary key (c1) -) engine=innodb; -alter table t1 add constraint c2_fk foreign key (c2) -references t2(c1) on delete cascade; -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `c1` bigint(20) NOT NULL, - `c2` bigint(20) NOT NULL, - PRIMARY KEY (`c1`), - UNIQUE KEY `c2` (`c2`), - CONSTRAINT `c2_fk` FOREIGN KEY (`c2`) REFERENCES `t2` (`c1`) ON DELETE CASCADE -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -alter table t1 drop foreign key c2_fk; -show create table t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `c1` bigint(20) NOT NULL, - `c2` bigint(20) NOT NULL, - PRIMARY KEY (`c1`), - UNIQUE KEY `c2` (`c2`) -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -drop table t1, t2; -create table t1(a date) engine=innodb; -create table t2(a date, key(a)) engine=innodb; -insert into t1 values('2005-10-01'); -insert into t2 values('2005-10-01'); -select * from t1, t2 -where t2.a between t1.a - interval 2 day and t1.a + interval 2 day; -a a -2005-10-01 2005-10-01 -drop table t1, t2; -create table t1 (id int not null, f_id int not null, f int not null, -primary key(f_id, id)) engine=innodb; -create table t2 (id int not null,s_id int not null,s varchar(200), -primary key(id)) engine=innodb; -INSERT INTO t1 VALUES (8, 1, 3); -INSERT INTO t1 VALUES (1, 2, 1); -INSERT INTO t2 VALUES (1, 0, ''); -INSERT INTO t2 VALUES (8, 1, ''); -commit; -DELETE ml.* FROM t1 AS ml LEFT JOIN t2 AS mm ON (mm.id=ml.id) -WHERE mm.id IS NULL; -select ml.* from t1 as ml left join t2 as mm on (mm.id=ml.id) -where mm.id is null lock in share mode; -id f_id f -drop table t1,t2; -create table t1(a int not null, b int, primary key(a)) engine=innodb; -insert into t1 values(1,1),(2,2),(3,1),(4,2),(5,1),(6,2),(7,3); -commit; -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; -update t1 set b = 5 where b = 1; -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; -select * from t1 where a = 7 and b = 3 for update; -a b -7 3 -commit; -commit; -drop table t1; -create table t1(a int not null, b int, primary key(a)) engine=innodb; -insert into t1 values(1,1),(2,2),(3,1),(4,2),(5,1),(6,2); -commit; -set autocommit = 0; -select * from t1 lock in share mode; -a b -1 1 -2 2 -3 1 -4 2 -5 1 -6 2 -update t1 set b = 5 where b = 1; -set autocommit = 0; -select * from t1 where a = 2 and b = 2 for update; -ERROR HY000: Lock wait timeout exceeded; try restarting transaction -commit; -commit; -drop table t1; -create table t1(a int not null, b int, primary key(a)) engine=innodb; -insert into t1 values (1,2),(5,3),(4,2); -create table t2(d int not null, e int, primary key(d)) engine=innodb; -insert into t2 values (8,6),(12,1),(3,1); -commit; -set autocommit = 0; -select * from t2 for update; -d e -3 1 -8 6 -12 1 -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; -insert into t1 select * from t2; -update t1 set b = (select e from t2 where a = d); -create table t3(d int not null, e int, primary key(d)) engine=innodb -select * from t2; -commit; -commit; -drop table t1, t2, t3; -create table t1(a int not null, b int, primary key(a)) engine=innodb; -insert into t1 values (1,2),(5,3),(4,2); -create table t2(a int not null, b int, primary key(a)) engine=innodb; -insert into t2 values (8,6),(12,1),(3,1); -create table t3(d int not null, b int, primary key(d)) engine=innodb; -insert into t3 values (8,6),(12,1),(3,1); -create table t5(a int not null, b int, primary key(a)) engine=innodb; -insert into t5 values (1,2),(5,3),(4,2); -create table t6(d int not null, e int, primary key(d)) engine=innodb; -insert into t6 values (8,6),(12,1),(3,1); -create table t8(a int not null, b int, primary key(a)) engine=innodb; -insert into t8 values (1,2),(5,3),(4,2); -create table t9(d int not null, e int, primary key(d)) engine=innodb; -insert into t9 values (8,6),(12,1),(3,1); -commit; -set autocommit = 0; -select * from t2 for update; -a b -3 1 -8 6 -12 1 -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL SERIALIZABLE; -insert into t1 select * from t2; -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL SERIALIZABLE; -update t3 set b = (select b from t2 where a = d); -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL SERIALIZABLE; -create table t4(a int not null, b int, primary key(a)) engine=innodb select * from t2; -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; -insert into t5 (select * from t2 lock in share mode); -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; -update t6 set e = (select b from t2 where a = d lock in share mode); -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; -create table t7(a int not null, b int, primary key(a)) engine=innodb select * from t2 lock in share mode; -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; -insert into t8 (select * from t2 for update); -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; -update t9 set e = (select b from t2 where a = d for update); -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; -create table t10(a int not null, b int, primary key(a)) engine=innodb select * from t2 for update; -ERROR HY000: Lock wait timeout exceeded; try restarting transaction -ERROR HY000: Lock wait timeout exceeded; try restarting transaction -ERROR HY000: Lock wait timeout exceeded; try restarting transaction -ERROR HY000: Lock wait timeout exceeded; try restarting transaction -ERROR HY000: Lock wait timeout exceeded; try restarting transaction -ERROR HY000: Lock wait timeout exceeded; try restarting transaction -ERROR HY000: Lock wait timeout exceeded; try restarting transaction -ERROR HY000: Lock wait timeout exceeded; try restarting transaction -ERROR HY000: Lock wait timeout exceeded; try restarting transaction -commit; -drop table t1, t2, t3, t5, t6, t8, t9; -CREATE TABLE t1 (DB_ROW_ID int) engine=innodb; -ERROR HY000: Can't create table 'test.t1' (errno: -1) -CREATE TABLE t1 ( -a BIGINT(20) NOT NULL, -PRIMARY KEY (a) -) ENGINE=INNODB DEFAULT CHARSET=UTF8; -CREATE TABLE t2 ( -a BIGINT(20) NOT NULL, -b VARCHAR(128) NOT NULL, -c TEXT NOT NULL, -PRIMARY KEY (a,b), -KEY idx_t2_b_c (b,c(200)), -CONSTRAINT t_fk FOREIGN KEY (a) REFERENCES t1 (a) -ON DELETE CASCADE -) ENGINE=INNODB DEFAULT CHARSET=UTF8; -INSERT INTO t1 VALUES (1); -INSERT INTO t2 VALUES (1, 'bar', 'vbar'); -INSERT INTO t2 VALUES (1, 'BAR2', 'VBAR'); -INSERT INTO t2 VALUES (1, 'bar_bar', 'bibi'); -INSERT INTO t2 VALUES (1, 'customer_over', '1'); -SELECT * FROM t2 WHERE b = 'customer_over'; -a b c -1 customer_over 1 -SELECT * FROM t2 WHERE BINARY b = 'customer_over'; -a b c -1 customer_over 1 -SELECT DISTINCT p0.a FROM t2 p0 WHERE p0.b = 'customer_over'; -a -1 -/* Bang: Empty result set, above was expected: */ -SELECT DISTINCT p0.a FROM t2 p0 WHERE BINARY p0.b = 'customer_over'; -a -1 -SELECT p0.a FROM t2 p0 WHERE BINARY p0.b = 'customer_over'; -a -1 -drop table t2, t1; -CREATE TABLE t1 ( a int ) ENGINE=innodb; -BEGIN; -INSERT INTO t1 VALUES (1); -OPTIMIZE TABLE t1; -Table Op Msg_type Msg_text -test.t1 optimize note Table does not support optimize, doing recreate + analyze instead -test.t1 optimize status OK -DROP TABLE t1; -CREATE TABLE t1 (id int PRIMARY KEY, f int NOT NULL, INDEX(f)) ENGINE=InnoDB; -CREATE TABLE t2 (id int PRIMARY KEY, f INT NOT NULL, -CONSTRAINT t2_t1 FOREIGN KEY (id) REFERENCES t1 (id) -ON DELETE CASCADE ON UPDATE CASCADE) ENGINE=InnoDB; -ALTER TABLE t2 ADD FOREIGN KEY (f) REFERENCES t1 (f) ON -DELETE CASCADE ON UPDATE CASCADE; -SHOW CREATE TABLE t2; -Table Create Table -t2 CREATE TABLE `t2` ( - `id` int(11) NOT NULL, - `f` int(11) NOT NULL, - PRIMARY KEY (`id`), - KEY `f` (`f`), - CONSTRAINT `t2_ibfk_1` FOREIGN KEY (`f`) REFERENCES `t1` (`f`) ON DELETE CASCADE ON UPDATE CASCADE, - CONSTRAINT `t2_t1` FOREIGN KEY (`id`) REFERENCES `t1` (`id`) ON DELETE CASCADE ON UPDATE CASCADE -) ENGINE=InnoDB DEFAULT CHARSET=latin1 -DROP TABLE t2, t1; -CREATE TABLE t1 (a INT, INDEX(a)) ENGINE=InnoDB; -CREATE TABLE t2 (a INT, INDEX(a)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (1); -INSERT INTO t2 VALUES (1); -ALTER TABLE t2 ADD FOREIGN KEY (a) REFERENCES t1 (a) ON DELETE SET NULL; -ALTER TABLE t2 MODIFY a INT NOT NULL; -ERROR HY000: Error on rename of '#sql-temporary' to './test/t2' (errno: 150) -DELETE FROM t1; -DROP TABLE t2,t1; -CREATE TABLE t1 (a VARCHAR(5) COLLATE utf8_unicode_ci PRIMARY KEY) -ENGINE=InnoDB; -INSERT INTO t1 VALUES (0xEFBCA4EFBCA4EFBCA4); -DELETE FROM t1; -INSERT INTO t1 VALUES ('DDD'); -SELECT * FROM t1; -a -DDD -DROP TABLE t1; -CREATE TABLE t1 (id int PRIMARY KEY AUTO_INCREMENT) ENGINE=InnoDB -AUTO_INCREMENT=42; -INSERT INTO t1 VALUES (0),(347),(0); -SELECT * FROM t1; -id -42 -347 -348 -SHOW CREATE TABLE t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `id` int(11) NOT NULL AUTO_INCREMENT, - PRIMARY KEY (`id`) -) ENGINE=InnoDB AUTO_INCREMENT=349 DEFAULT CHARSET=latin1 -CREATE TABLE t2 (id int PRIMARY KEY) ENGINE=InnoDB; -INSERT INTO t2 VALUES(42),(347),(348); -ALTER TABLE t1 ADD CONSTRAINT t1_t2 FOREIGN KEY (id) REFERENCES t2(id); -SHOW CREATE TABLE t1; -Table Create Table -t1 CREATE TABLE `t1` ( - `id` int(11) NOT NULL AUTO_INCREMENT, - PRIMARY KEY (`id`), - CONSTRAINT `t1_t2` FOREIGN KEY (`id`) REFERENCES `t2` (`id`) -) ENGINE=InnoDB AUTO_INCREMENT=349 DEFAULT CHARSET=latin1 -DROP TABLE t1,t2; -set innodb_strict_mode=on; -CREATE TABLE t1 ( -c01 CHAR(255), c02 CHAR(255), c03 CHAR(255), c04 CHAR(255), -c05 CHAR(255), c06 CHAR(255), c07 CHAR(255), c08 CHAR(255), -c09 CHAR(255), c10 CHAR(255), c11 CHAR(255), c12 CHAR(255), -c13 CHAR(255), c14 CHAR(255), c15 CHAR(255), c16 CHAR(255), -c17 CHAR(255), c18 CHAR(255), c19 CHAR(255), c20 CHAR(255), -c21 CHAR(255), c22 CHAR(255), c23 CHAR(255), c24 CHAR(255), -c25 CHAR(255), c26 CHAR(255), c27 CHAR(255), c28 CHAR(255), -c29 CHAR(255), c30 CHAR(255), c31 CHAR(255), c32 CHAR(255) -) ENGINE = InnoDB; -ERROR 42000: Row size too large. The maximum row size for the used table type, not counting BLOBs, is 8126. You have to change some columns to TEXT or BLOBs -DROP TABLE IF EXISTS t1; -Warnings: -Note 1051 Unknown table 't1' -CREATE TABLE t1( -id BIGINT(20) NOT NULL AUTO_INCREMENT PRIMARY KEY -) ENGINE=InnoDB; -INSERT INTO t1 VALUES(-10); -SELECT * FROM t1; -id --10 -INSERT INTO t1 VALUES(NULL); -SELECT * FROM t1; -id --10 -1 -DROP TABLE t1; -SET binlog_format='MIXED'; -SET TX_ISOLATION='read-committed'; -SET AUTOCOMMIT=0; -DROP TABLE IF EXISTS t1, t2; -Warnings: -Note 1051 Unknown table 't1' -Note 1051 Unknown table 't2' -CREATE TABLE t1 ( a int ) ENGINE=InnoDB; -CREATE TABLE t2 LIKE t1; -SELECT * FROM t2; -a -SET binlog_format='MIXED'; -SET TX_ISOLATION='read-committed'; -SET AUTOCOMMIT=0; -INSERT INTO t1 VALUES (1); -COMMIT; -SELECT * FROM t1 WHERE a=1; -a -1 -SET binlog_format='MIXED'; -SET TX_ISOLATION='read-committed'; -SET AUTOCOMMIT=0; -SELECT * FROM t2; -a -SET binlog_format='MIXED'; -SET TX_ISOLATION='read-committed'; -SET AUTOCOMMIT=0; -INSERT INTO t1 VALUES (2); -COMMIT; -SELECT * FROM t1 WHERE a=2; -a -2 -SELECT * FROM t1 WHERE a=2; -a -2 -DROP TABLE t1; -DROP TABLE t2; -create table t1 (i int, j int) engine=innodb; -insert into t1 (i, j) values (1, 1), (2, 2); -update t1 set j = 2; -affected rows: 1 -info: Rows matched: 2 Changed: 1 Warnings: 0 -drop table t1; -create table t1 (id int) comment='this is a comment' engine=innodb; -select table_comment, data_free > 0 as data_free_is_set -from information_schema.tables -where table_schema='test' and table_name = 't1'; -table_comment data_free_is_set -this is a comment 1 -drop table t1; -CREATE TABLE t1 ( -c1 INT(10) UNSIGNED NOT NULL AUTO_INCREMENT, -c2 VARCHAR(128) NOT NULL, -PRIMARY KEY(c1) -) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=100; -CREATE TABLE t2 ( -c1 INT(10) UNSIGNED NOT NULL AUTO_INCREMENT, -c2 INT(10) UNSIGNED DEFAULT NULL, -PRIMARY KEY(c1) -) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=200; -SELECT AUTO_INCREMENT FROM INFORMATION_SCHEMA.TABLES WHERE table_name = 't2'; -AUTO_INCREMENT -200 -ALTER TABLE t2 ADD CONSTRAINT t1_t2_1 FOREIGN KEY(c1) REFERENCES t1(c1); -SELECT AUTO_INCREMENT FROM INFORMATION_SCHEMA.TABLES WHERE table_name = 't2'; -AUTO_INCREMENT -200 -DROP TABLE t2; -DROP TABLE t1; -CREATE TABLE t1 (c1 int default NULL, -c2 int default NULL -) ENGINE=InnoDB DEFAULT CHARSET=latin1; -TRUNCATE TABLE t1; -affected rows: 0 -INSERT INTO t1 VALUES (1, 1), (2, 2), (3, 3), (4, 4), (5, 5); -affected rows: 5 -info: Records: 5 Duplicates: 0 Warnings: 0 -TRUNCATE TABLE t1; -affected rows: 0 -DROP TABLE t1; -Variable_name Value -Handler_update 0 -Variable_name Value -Handler_delete 0 -Variable_name Value -Handler_update 1 -Variable_name Value -Handler_delete 1 diff --git a/storage/innodb_plugin/mysql-test/innodb.test b/storage/innodb_plugin/mysql-test/innodb.test deleted file mode 100644 index f46a3a70b56..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb.test +++ /dev/null @@ -1,2569 +0,0 @@ -####################################################################### -# # -# Please, DO NOT TOUCH this file as well as the innodb.result file. # -# These files are to be modified ONLY BY INNOBASE guys. # -# # -# Use innodb_mysql.[test|result] files instead. # -# # -# If nevertheless you need to make some changes here, please, forward # -# your commit message # -# To: innodb_dev_ww@oracle.com # -# Cc: dev-innodb@mysql.com # -# (otherwise your changes may be erased). # -# # -####################################################################### - --- source include/have_innodb.inc - -# Save the original values of some variables in order to be able to -# estimate how much they have changed during the tests. Previously this -# test assumed that e.g. rows_deleted is 0 here and after deleting 23 -# rows it expected that rows_deleted will be 23. Now we do not make -# assumptions about the values of the variables at the beginning, e.g. -# rows_deleted should be 23 + "rows_deleted before the test". This allows -# the test to be run multiple times without restarting the mysqld server. -# See Bug#43309 Test main.innodb can't be run twice --- disable_query_log -SET @innodb_thread_concurrency_orig = @@innodb_thread_concurrency; - -SET @innodb_rows_deleted_orig = (SELECT variable_value FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_rows_deleted'); -SET @innodb_rows_inserted_orig = (SELECT variable_value FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_rows_inserted'); -SET @innodb_rows_updated_orig = (SELECT variable_value FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_rows_updated'); -SET @innodb_row_lock_waits_orig = (SELECT variable_value FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_row_lock_waits'); -SET @innodb_row_lock_current_waits_orig = (SELECT variable_value FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_row_lock_current_waits'); -SET @innodb_row_lock_time_orig = (SELECT variable_value FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_row_lock_time'); -SET @innodb_row_lock_time_max_orig = (SELECT variable_value FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_row_lock_time_max'); -SET @innodb_row_lock_time_avg_orig = (SELECT variable_value FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_row_lock_time_avg'); --- enable_query_log - ---disable_warnings -drop table if exists t1,t2,t3,t4; -drop database if exists mysqltest; ---enable_warnings - -# -# Small basic test with ignore -# - -create table t1 (id int unsigned not null auto_increment, code tinyint unsigned not null, name char(20) not null, primary key (id), key (code), unique (name)) engine=innodb; - -insert into t1 (code, name) values (1, 'Tim'), (1, 'Monty'), (2, 'David'), (2, 'Erik'), (3, 'Sasha'), (3, 'Jeremy'), (4, 'Matt'); -select id, code, name from t1 order by id; - -update ignore t1 set id = 8, name = 'Sinisa' where id < 3; -select id, code, name from t1 order by id; -update ignore t1 set id = id + 10, name = 'Ralph' where id < 4; -select id, code, name from t1 order by id; - -drop table t1; - -# -# A bit bigger test -# The 'replace_column' statements are needed because the cardinality calculated -# by innodb is not always the same between runs -# - -CREATE TABLE t1 ( - id int(11) NOT NULL auto_increment, - parent_id int(11) DEFAULT '0' NOT NULL, - level tinyint(4) DEFAULT '0' NOT NULL, - PRIMARY KEY (id), - KEY parent_id (parent_id), - KEY level (level) -) engine=innodb; -INSERT INTO t1 VALUES (1,0,0),(3,1,1),(4,1,1),(8,2,2),(9,2,2),(17,3,2),(22,4,2),(24,4,2),(28,5,2),(29,5,2),(30,5,2),(31,6,2),(32,6,2),(33,6,2),(203,7,2),(202,7,2),(20,3,2),(157,0,0),(193,5,2),(40,7,2),(2,1,1),(15,2,2),(6,1,1),(34,6,2),(35,6,2),(16,3,2),(7,1,1),(36,7,2),(18,3,2),(26,5,2),(27,5,2),(183,4,2),(38,7,2),(25,5,2),(37,7,2),(21,4,2),(19,3,2),(5,1,1),(179,5,2); -update t1 set parent_id=parent_id+100; -select * from t1 where parent_id=102; -update t1 set id=id+1000; --- error ER_DUP_ENTRY,1022 -update t1 set id=1024 where id=1009; -select * from t1; -update ignore t1 set id=id+1; # This will change all rows -select * from t1; -update ignore t1 set id=1023 where id=1010; -select * from t1 where parent_id=102; ---replace_column 9 # -explain select level from t1 where level=1; ---replace_column 9 # -explain select level,id from t1 where level=1; ---replace_column 9 # -explain select level,id,parent_id from t1 where level=1; -select level,id from t1 where level=1; -select level,id,parent_id from t1 where level=1; -optimize table t1; ---replace_column 7 # -show keys from t1; -drop table t1; - -# -# Test replace -# - -CREATE TABLE t1 ( - gesuchnr int(11) DEFAULT '0' NOT NULL, - benutzer_id int(11) DEFAULT '0' NOT NULL, - PRIMARY KEY (gesuchnr,benutzer_id) -) engine=innodb; - -replace into t1 (gesuchnr,benutzer_id) values (2,1); -replace into t1 (gesuchnr,benutzer_id) values (1,1); -replace into t1 (gesuchnr,benutzer_id) values (1,1); -select * from t1; -drop table t1; - -# -# test delete using hidden_primary_key -# - -create table t1 (a int) engine=innodb; -insert into t1 values (1), (2); -optimize table t1; -delete from t1 where a = 1; -select * from t1; -check table t1; -drop table t1; - -create table t1 (a int,b varchar(20)) engine=innodb; -insert into t1 values (1,""), (2,"testing"); -delete from t1 where a = 1; -select * from t1; -create index skr on t1 (a); -insert into t1 values (3,""), (4,"testing"); -analyze table t1; ---replace_column 7 # -show keys from t1; -drop table t1; - - -# Test of reading on secondary key with may be null - -create table t1 (a int,b varchar(20),key(a)) engine=innodb; -insert into t1 values (1,""), (2,"testing"); -select * from t1 where a = 1; -drop table t1; - -# -# Test rollback -# - -create table t1 (n int not null primary key) engine=innodb; -set autocommit=0; -insert into t1 values (4); -rollback; -select n, "after rollback" from t1; -insert into t1 values (4); -commit; -select n, "after commit" from t1; -commit; -insert into t1 values (5); --- error ER_DUP_ENTRY -insert into t1 values (4); -commit; -select n, "after commit" from t1; -set autocommit=1; -insert into t1 values (6); --- error ER_DUP_ENTRY -insert into t1 values (4); -select n from t1; -set autocommit=0; -# -# savepoints -# -begin; -savepoint `my_savepoint`; -insert into t1 values (7); -savepoint `savept2`; -insert into t1 values (3); -select n from t1; -savepoint savept3; -rollback to savepoint savept2; ---error 1305 -rollback to savepoint savept3; -rollback to savepoint savept2; -release savepoint `my_savepoint`; -select n from t1; --- error 1305 -rollback to savepoint `my_savepoint`; ---error 1305 -rollback to savepoint savept2; -insert into t1 values (8); -savepoint sv; -commit; -savepoint sv; -set autocommit=1; -# nop -rollback; -drop table t1; - -# -# Test for commit and FLUSH TABLES WITH READ LOCK -# - -create table t1 (n int not null primary key) engine=innodb; -start transaction; -insert into t1 values (4); -flush tables with read lock; -# -# Current code can't handle a read lock in middle of transaction -#--error 1223; -commit; -unlock tables; -commit; -select * from t1; -drop table t1; - -# -# Testing transactions -# - -create table t1 ( id int NOT NULL PRIMARY KEY, nom varchar(64)) engine=innodb; -begin; -insert into t1 values(1,'hamdouni'); -select id as afterbegin_id,nom as afterbegin_nom from t1; -rollback; -select id as afterrollback_id,nom as afterrollback_nom from t1; -set autocommit=0; -insert into t1 values(2,'mysql'); -select id as afterautocommit0_id,nom as afterautocommit0_nom from t1; -rollback; -select id as afterrollback_id,nom as afterrollback_nom from t1; -set autocommit=1; -drop table t1; - -# -# Simple not autocommit test -# - -CREATE TABLE t1 (id char(8) not null primary key, val int not null) engine=innodb; -insert into t1 values ('pippo', 12); --- error ER_DUP_ENTRY -insert into t1 values ('pippo', 12); # Gives error -delete from t1; -delete from t1 where id = 'pippo'; -select * from t1; - -insert into t1 values ('pippo', 12); -set autocommit=0; -delete from t1; -rollback; -select * from t1; -delete from t1; -commit; -select * from t1; -drop table t1; - -# -# Test of active transactions -# - -create table t1 (a integer) engine=innodb; -start transaction; -rename table t1 to t2; -create table t1 (b integer) engine=innodb; -insert into t1 values (1); -rollback; -drop table t1; -rename table t2 to t1; -drop table t1; -set autocommit=1; - -# -# The following simple tests failed at some point -# - -CREATE TABLE t1 (ID INTEGER NOT NULL PRIMARY KEY, NAME VARCHAR(64)) ENGINE=innodb; -INSERT INTO t1 VALUES (1, 'Jochen'); -select * from t1; -drop table t1; - -CREATE TABLE t1 ( _userid VARCHAR(60) NOT NULL PRIMARY KEY) ENGINE=innodb; -set autocommit=0; -INSERT INTO t1 SET _userid='marc@anyware.co.uk'; -COMMIT; -SELECT * FROM t1; -SELECT _userid FROM t1 WHERE _userid='marc@anyware.co.uk'; -drop table t1; -set autocommit=1; - -# -# Test when reading on part of unique key -# -CREATE TABLE t1 ( - user_id int(10) DEFAULT '0' NOT NULL, - name varchar(100), - phone varchar(100), - ref_email varchar(100) DEFAULT '' NOT NULL, - detail varchar(200), - PRIMARY KEY (user_id,ref_email) -)engine=innodb; - -INSERT INTO t1 VALUES (10292,'sanjeev','29153373','sansh777@hotmail.com','xxx'),(10292,'shirish','2333604','shirish@yahoo.com','ddsds'),(10292,'sonali','323232','sonali@bolly.com','filmstar'); -select * from t1 where user_id=10292; -INSERT INTO t1 VALUES (10291,'sanjeev','29153373','sansh777@hotmail.com','xxx'),(10293,'shirish','2333604','shirish@yahoo.com','ddsds'); -select * from t1 where user_id=10292; -select * from t1 where user_id>=10292; -select * from t1 where user_id>10292; -select * from t1 where user_id<10292; -drop table t1; - -# -# Test that keys are created in right order -# - -CREATE TABLE t1 (a int not null, b int not null,c int not null, -key(a),primary key(a,b), unique(c),key(a),unique(b)); ---replace_column 7 # -show index from t1; -drop table t1; - -# -# Test of ALTER TABLE and innodb tables -# - -create table t1 (col1 int not null, col2 char(4) not null, primary key(col1)); -alter table t1 engine=innodb; -insert into t1 values ('1','1'),('5','2'),('2','3'),('3','4'),('4','4'); -select * from t1; -update t1 set col2='7' where col1='4'; -select * from t1; -alter table t1 add co3 int not null; -select * from t1; -update t1 set col2='9' where col1='2'; -select * from t1; -drop table t1; - -# -# INSERT INTO innodb tables -# - -create table t1 (a int not null , b int, primary key (a)) engine = innodb; -create table t2 (a int not null , b int, primary key (a)) engine = myisam; -insert into t1 VALUES (1,3) , (2,3), (3,3); -select * from t1; -insert into t2 select * from t1; -select * from t2; -delete from t1 where b = 3; -select * from t1; -insert into t1 select * from t2; -select * from t1; -select * from t2; -drop table t1,t2; - -# -# ORDER BY on not primary key -# - -CREATE TABLE t1 ( - user_name varchar(12), - password text, - subscribed char(1), - user_id int(11) DEFAULT '0' NOT NULL, - quota bigint(20), - weight double, - access_date date, - access_time time, - approved datetime, - dummy_primary_key int(11) NOT NULL auto_increment, - PRIMARY KEY (dummy_primary_key) -) ENGINE=innodb; -INSERT INTO t1 VALUES ('user_0','somepassword','N',0,0,0,'2000-09-07','23:06:59','2000-09-07 23:06:59',1); -INSERT INTO t1 VALUES ('user_1','somepassword','Y',1,1,1,'2000-09-07','23:06:59','2000-09-07 23:06:59',2); -INSERT INTO t1 VALUES ('user_2','somepassword','N',2,2,1.4142135623731,'2000-09-07','23:06:59','2000-09-07 23:06:59',3); -INSERT INTO t1 VALUES ('user_3','somepassword','Y',3,3,1.7320508075689,'2000-09-07','23:06:59','2000-09-07 23:06:59',4); -INSERT INTO t1 VALUES ('user_4','somepassword','N',4,4,2,'2000-09-07','23:06:59','2000-09-07 23:06:59',5); -select user_name, password , subscribed, user_id, quota, weight, access_date, access_time, approved, dummy_primary_key from t1 order by user_name; -drop table t1; - -# -# Testing of tables without primary keys -# - -CREATE TABLE t1 ( - id int(11) NOT NULL auto_increment, - parent_id int(11) DEFAULT '0' NOT NULL, - level tinyint(4) DEFAULT '0' NOT NULL, - KEY (id), - KEY parent_id (parent_id), - KEY level (level) -) engine=innodb; -INSERT INTO t1 VALUES (1,0,0),(3,1,1),(4,1,1),(8,2,2),(9,2,2),(17,3,2),(22,4,2),(24,4,2),(28,5,2),(29,5,2),(30,5,2),(31,6,2),(32,6,2),(33,6,2),(203,7,2),(202,7,2),(20,3,2),(157,0,0),(193,5,2),(40,7,2),(2,1,1),(15,2,2),(6,1,1),(34,6,2),(35,6,2),(16,3,2),(7,1,1),(36,7,2),(18,3,2),(26,5,2),(27,5,2),(183,4,2),(38,7,2),(25,5,2),(37,7,2),(21,4,2),(19,3,2),(5,1,1); -INSERT INTO t1 values (179,5,2); -update t1 set parent_id=parent_id+100; -select * from t1 where parent_id=102; -update t1 set id=id+1000; -update t1 set id=1024 where id=1009; -select * from t1; -update ignore t1 set id=id+1; # This will change all rows -select * from t1; -update ignore t1 set id=1023 where id=1010; -select * from t1 where parent_id=102; ---replace_column 9 # -explain select level from t1 where level=1; -select level,id from t1 where level=1; -select level,id,parent_id from t1 where level=1; -select level,id from t1 where level=1 order by id; -delete from t1 where level=1; -select * from t1; -drop table t1; - -# -# Test of index only reads -# -CREATE TABLE t1 ( - sca_code char(6) NOT NULL, - cat_code char(6) NOT NULL, - sca_desc varchar(50), - lan_code char(2) NOT NULL, - sca_pic varchar(100), - sca_sdesc varchar(50), - sca_sch_desc varchar(16), - PRIMARY KEY (sca_code, cat_code, lan_code), - INDEX sca_pic (sca_pic) -) engine = innodb ; - -INSERT INTO t1 ( sca_code, cat_code, sca_desc, lan_code, sca_pic, sca_sdesc, sca_sch_desc) VALUES ( 'PD', 'J', 'PENDANT', 'EN', NULL, NULL, 'PENDANT'),( 'RI', 'J', 'RING', 'EN', NULL, NULL, 'RING'),( 'QQ', 'N', 'RING', 'EN', 'not null', NULL, 'RING'); -select count(*) from t1 where sca_code = 'PD'; -select count(*) from t1 where sca_code <= 'PD'; -select count(*) from t1 where sca_pic is null; -alter table t1 drop index sca_pic, add index sca_pic (cat_code, sca_pic); -select count(*) from t1 where sca_code='PD' and sca_pic is null; -select count(*) from t1 where cat_code='E'; - -alter table t1 drop index sca_pic, add index (sca_pic, cat_code); -select count(*) from t1 where sca_code='PD' and sca_pic is null; -select count(*) from t1 where sca_pic >= 'n'; -select sca_pic from t1 where sca_pic is null; -update t1 set sca_pic="test" where sca_pic is null; -delete from t1 where sca_code='pd'; -drop table t1; - -# -# Test of opening table twice and timestamps -# -set @a:=now(); -CREATE TABLE t1 (a int not null, b timestamp not null, primary key (a)) engine=innodb; -insert into t1 (a) values(1),(2),(3); -select t1.a from t1 natural join t1 as t2 where t1.b >= @a order by t1.a; -select a from t1 natural join t1 as t2 where b >= @a order by a; -update t1 set a=5 where a=1; -select a from t1; -drop table t1; - -# -# Test with variable length primary key -# -create table t1 (a varchar(100) not null, primary key(a), b int not null) engine=innodb; -insert into t1 values("hello",1),("world",2); -select * from t1 order by b desc; -optimize table t1; ---replace_column 7 # -show keys from t1; -drop table t1; - -# -# Test of create index with NULL columns -# -create table t1 (i int, j int ) ENGINE=innodb; -insert into t1 values (1,2); -select * from t1 where i=1 and j=2; -create index ax1 on t1 (i,j); -select * from t1 where i=1 and j=2; -drop table t1; - -# -# Test min-max optimization -# - -CREATE TABLE t1 ( - a int3 unsigned NOT NULL, - b int1 unsigned NOT NULL, - UNIQUE (a, b) -) ENGINE = innodb; - -INSERT INTO t1 VALUES (1, 1); -SELECT MIN(B),MAX(b) FROM t1 WHERE t1.a = 1; -drop table t1; - -# -# Test INSERT DELAYED -# - -CREATE TABLE t1 (a int unsigned NOT NULL) engine=innodb; -# Can't test this in 3.23 -# INSERT DELAYED INTO t1 VALUES (1); -INSERT INTO t1 VALUES (1); -SELECT * FROM t1; -DROP TABLE t1; - - -# -# Crash when using many tables (Test case by Jeremy D Zawodny) -# - -create table t1 (a int primary key,b int, c int, d int, e int, f int, g int, h int, i int, j int, k int, l int, m int, n int, o int, p int, q int, r int, s int, t int, u int, v int, w int, x int, y int, z int, a1 int, a2 int, a3 int, a4 int, a5 int, a6 int, a7 int, a8 int, a9 int, b1 int, b2 int, b3 int, b4 int, b5 int, b6 int) engine = innodb; -insert into t1 values (1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1); ---replace_column 9 # -explain select * from t1 where a > 0 and a < 50; -drop table t1; - -# -# Test lock tables -# - -create table t1 (id int NOT NULL,id2 int NOT NULL,id3 int NOT NULL,dummy1 char(30),primary key (id,id2),index index_id3 (id3)) engine=innodb; -insert into t1 values (0,0,0,'ABCDEFGHIJ'),(2,2,2,'BCDEFGHIJK'),(1,1,1,'CDEFGHIJKL'); -LOCK TABLES t1 WRITE; ---error ER_DUP_ENTRY -insert into t1 values (99,1,2,'D'),(1,1,2,'D'); -select id from t1; -select id from t1; -UNLOCK TABLES; -DROP TABLE t1; - -create table t1 (id int NOT NULL,id2 int NOT NULL,id3 int NOT NULL,dummy1 char(30),primary key (id,id2),index index_id3 (id3)) engine=innodb; -insert into t1 values (0,0,0,'ABCDEFGHIJ'),(2,2,2,'BCDEFGHIJK'),(1,1,1,'CDEFGHIJKL'); -LOCK TABLES t1 WRITE; -begin; ---error ER_DUP_ENTRY -insert into t1 values (99,1,2,'D'),(1,1,2,'D'); -select id from t1; -insert ignore into t1 values (100,1,2,'D'),(1,1,99,'D'); -commit; -select id,id3 from t1; -UNLOCK TABLES; -DROP TABLE t1; - -# -# Test prefix key -# -create table t1 (a char(20), unique (a(5))) engine=innodb; -drop table t1; -create table t1 (a char(20), index (a(5))) engine=innodb; -show create table t1; -drop table t1; - -# -# Test using temporary table and auto_increment -# - -create temporary table t1 (a int not null auto_increment, primary key(a)) engine=innodb; -insert into t1 values (NULL),(NULL),(NULL); -delete from t1 where a=3; -insert into t1 values (NULL); -select * from t1; -alter table t1 add b int; -select * from t1; -drop table t1; - -#Slashdot bug -create table t1 - ( - id int auto_increment primary key, - name varchar(32) not null, - value text not null, - uid int not null, - unique key(name,uid) - ) engine=innodb; -insert into t1 values (1,'one','one value',101), - (2,'two','two value',102),(3,'three','three value',103); -set insert_id=5; -replace into t1 (value,name,uid) values ('other value','two',102); -delete from t1 where uid=102; -set insert_id=5; -replace into t1 (value,name,uid) values ('other value','two',102); -set insert_id=6; -replace into t1 (value,name,uid) values ('other value','two',102); -select * from t1; -drop table t1; - -# -# Test DROP DATABASE -# - -create database mysqltest; -create table mysqltest.t1 (a int not null) engine= innodb; -insert into mysqltest.t1 values(1); -create table mysqltest.t2 (a int not null) engine= myisam; -insert into mysqltest.t2 values(1); -create table mysqltest.t3 (a int not null) engine= heap; -insert into mysqltest.t3 values(1); -commit; -drop database mysqltest; -# Don't check error message ---error 1049 -show tables from mysqltest; - -# -# Test truncate table with and without auto_commit -# - -set autocommit=0; -create table t1 (a int not null) engine= innodb; -insert into t1 values(1),(2); -truncate table t1; -commit; -truncate table t1; -truncate table t1; -select * from t1; -insert into t1 values(1),(2); -delete from t1; -select * from t1; -commit; -drop table t1; -set autocommit=1; - -create table t1 (a int not null) engine= innodb; -insert into t1 values(1),(2); -truncate table t1; -insert into t1 values(1),(2); -select * from t1; -truncate table t1; -insert into t1 values(1),(2); -delete from t1; -select * from t1; -drop table t1; - -# -# Test of how ORDER BY works when doing it on the whole table -# - -create table t1 (a int not null, b int not null, c int not null, primary key (a),key(b)) engine=innodb; -insert into t1 values (3,3,3),(1,1,1),(2,2,2),(4,4,4); ---replace_column 9 # -explain select * from t1 order by a; ---replace_column 9 # -explain select * from t1 order by b; ---replace_column 9 # -explain select * from t1 order by c; ---replace_column 9 # -explain select a from t1 order by a; ---replace_column 9 # -explain select b from t1 order by b; ---replace_column 9 # -explain select a,b from t1 order by b; ---replace_column 9 # -explain select a,b from t1; ---replace_column 9 # -explain select a,b,c from t1; -drop table t1; - -# -# Check describe -# - -create table t1 (t int not null default 1, key (t)) engine=innodb; -desc t1; -drop table t1; - -# -# Test of multi-table-delete -# - -CREATE TABLE t1 ( - number bigint(20) NOT NULL default '0', - cname char(15) NOT NULL default '', - carrier_id smallint(6) NOT NULL default '0', - privacy tinyint(4) NOT NULL default '0', - last_mod_date timestamp NOT NULL, - last_mod_id smallint(6) NOT NULL default '0', - last_app_date timestamp NOT NULL, - last_app_id smallint(6) default '-1', - version smallint(6) NOT NULL default '0', - assigned_scps int(11) default '0', - status tinyint(4) default '0' -) ENGINE=InnoDB; -INSERT INTO t1 VALUES (4077711111,'SeanWheeler',90,2,20020111112846,500,00000000000000,-1,2,3,1); -INSERT INTO t1 VALUES (9197722223,'berry',90,3,20020111112809,500,20020102114532,501,4,10,0); -INSERT INTO t1 VALUES (650,'San Francisco',0,0,20011227111336,342,00000000000000,-1,1,24,1); -INSERT INTO t1 VALUES (302467,'Sue\'s Subshop',90,3,20020109113241,500,20020102115111,501,7,24,0); -INSERT INTO t1 VALUES (6014911113,'SudzCarwash',520,1,20020102115234,500,20020102115259,501,33,32768,0); -INSERT INTO t1 VALUES (333,'tubs',99,2,20020109113440,501,20020109113440,500,3,10,0); -CREATE TABLE t2 ( - number bigint(20) NOT NULL default '0', - cname char(15) NOT NULL default '', - carrier_id smallint(6) NOT NULL default '0', - privacy tinyint(4) NOT NULL default '0', - last_mod_date timestamp NOT NULL, - last_mod_id smallint(6) NOT NULL default '0', - last_app_date timestamp NOT NULL, - last_app_id smallint(6) default '-1', - version smallint(6) NOT NULL default '0', - assigned_scps int(11) default '0', - status tinyint(4) default '0' -) ENGINE=InnoDB; -INSERT INTO t2 VALUES (4077711111,'SeanWheeler',0,2,20020111112853,500,00000000000000,-1,2,3,1); -INSERT INTO t2 VALUES (9197722223,'berry',90,3,20020111112818,500,20020102114532,501,4,10,0); -INSERT INTO t2 VALUES (650,'San Francisco',90,0,20020109113158,342,00000000000000,-1,1,24,1); -INSERT INTO t2 VALUES (333,'tubs',99,2,20020109113453,501,20020109113453,500,3,10,0); -select * from t1; -select * from t2; -delete t1, t2 from t1 left join t2 on t1.number=t2.number where (t1.carrier_id=90 and t1.number=t2.number) or (t2.carrier_id=90 and t1.number=t2.number) or (t1.carrier_id=90 and t2.number is null); -select * from t1; -select * from t2; -select * from t2; -drop table t1,t2; - -# -# A simple test with some isolation levels -# TODO: Make this into a test using replication to really test how -# this works. -# - -create table t1 (id int unsigned not null auto_increment, code tinyint unsigned not null, name char(20) not null, primary key (id), key (code), unique (name)) engine=innodb; - -BEGIN; -SET SESSION TRANSACTION ISOLATION LEVEL SERIALIZABLE; -SELECT @@tx_isolation,@@global.tx_isolation; -insert into t1 (code, name) values (1, 'Tim'), (1, 'Monty'), (2, 'David'); -select id, code, name from t1 order by id; -COMMIT; - -BEGIN; -SET SESSION TRANSACTION ISOLATION LEVEL REPEATABLE READ; -insert into t1 (code, name) values (2, 'Erik'), (3, 'Sasha'); -select id, code, name from t1 order by id; -COMMIT; - -SET binlog_format='MIXED'; -BEGIN; -SET SESSION TRANSACTION ISOLATION LEVEL READ UNCOMMITTED; -insert into t1 (code, name) values (3, 'Jeremy'), (4, 'Matt'); -select id, code, name from t1 order by id; -COMMIT; -DROP TABLE t1; - -# -# Test of multi-table-update -# -create table t1 (n int(10), d int(10)) engine=innodb; -create table t2 (n int(10), d int(10)) engine=innodb; -insert into t1 values(1,1),(1,2); -insert into t2 values(1,10),(2,20); -UPDATE t1,t2 SET t1.d=t2.d,t2.d=30 WHERE t1.n=t2.n; -select * from t1; -select * from t2; -drop table t1,t2; - -# -# Bug #29136 erred multi-delete on trans table does not rollback -# - -# prepare ---disable_warnings -drop table if exists t1, t2; ---enable_warnings -CREATE TABLE t1 (a int, PRIMARY KEY (a)); -CREATE TABLE t2 (a int, PRIMARY KEY (a)) ENGINE=InnoDB; -create trigger trg_del_t2 after delete on t2 for each row - insert into t1 values (1); -insert into t1 values (1); -insert into t2 values (1),(2); - - -# exec cases A, B - see multi_update.test - -# A. send_error() w/o send_eof() branch - ---error ER_DUP_ENTRY -delete t2 from t2; - -# check - -select count(*) from t2 /* must be 2 as restored after rollback caused by the error */; - -# cleanup bug#29136 - -drop table t1, t2; - - -# -# Bug #29136 erred multi-delete on trans table does not rollback -# - -# prepare ---disable_warnings -drop table if exists t1, t2; ---enable_warnings -CREATE TABLE t1 (a int, PRIMARY KEY (a)); -CREATE TABLE t2 (a int, PRIMARY KEY (a)) ENGINE=InnoDB; -create trigger trg_del_t2 after delete on t2 for each row - insert into t1 values (1); -insert into t1 values (1); -insert into t2 values (1),(2); - - -# exec cases A, B - see multi_update.test - -# A. send_error() w/o send_eof() branch - ---error ER_DUP_ENTRY -delete t2 from t2; - -# check - -select count(*) from t2 /* must be 2 as restored after rollback caused by the error */; - -# cleanup bug#29136 - -drop table t1, t2; - - -# -# Testing of IFNULL -# -create table t1 (a int, b int) engine=innodb; -insert into t1 values(20,null); -select t2.b, ifnull(t2.b,"this is null") from t1 as t2 left join t1 as t3 on -t2.b=t3.a; -select t2.b, ifnull(t2.b,"this is null") from t1 as t2 left join t1 as t3 on -t2.b=t3.a order by 1; -insert into t1 values(10,null); -select t2.b, ifnull(t2.b,"this is null") from t1 as t2 left join t1 as t3 on -t2.b=t3.a order by 1; -drop table t1; - -# -# Test of read_through not existing const_table -# - -create table t1 (a varchar(10) not null) engine=myisam; -create table t2 (b varchar(10) not null unique) engine=innodb; -select t1.a from t1,t2 where t1.a=t2.b; -drop table t1,t2; -create table t1 (a int not null, b int, primary key (a)) engine = innodb; -create table t2 (a int not null, b int, primary key (a)) engine = innodb; -insert into t1 values (10, 20); -insert into t2 values (10, 20); -update t1, t2 set t1.b = 150, t2.b = t1.b where t2.a = t1.a and t1.a = 10; -drop table t1,t2; - -# -# Test of multi-table-delete with foreign key constraints -# - -CREATE TABLE t1 (id INT NOT NULL, PRIMARY KEY (id)) ENGINE=INNODB; -CREATE TABLE t2 (id INT PRIMARY KEY, t1_id INT, INDEX par_ind (t1_id), FOREIGN KEY (t1_id) REFERENCES t1(id) ON DELETE CASCADE ) ENGINE=INNODB; -insert into t1 set id=1; -insert into t2 set id=1, t1_id=1; -delete t1,t2 from t1,t2 where t1.id=t2.t1_id; -select * from t1; -select * from t2; -drop table t2,t1; -CREATE TABLE t1(id INT NOT NULL, PRIMARY KEY (id)) ENGINE=INNODB; -CREATE TABLE t2(id INT PRIMARY KEY, t1_id INT, INDEX par_ind (t1_id) ) ENGINE=INNODB; -INSERT INTO t1 VALUES(1); -INSERT INTO t2 VALUES(1, 1); -SELECT * from t1; -UPDATE t1,t2 SET t1.id=t1.id+1, t2.t1_id=t1.id+1; -SELECT * from t1; -UPDATE t1,t2 SET t1.id=t1.id+1 where t1.id!=t2.id; -SELECT * from t1; -DROP TABLE t1,t2; - -# -# Test of range_optimizer -# - -set autocommit=0; - -CREATE TABLE t1 (id CHAR(15) NOT NULL, value CHAR(40) NOT NULL, PRIMARY KEY(id)) ENGINE=InnoDB; - -CREATE TABLE t2 (id CHAR(15) NOT NULL, value CHAR(40) NOT NULL, PRIMARY KEY(id)) ENGINE=InnoDB; - -CREATE TABLE t3 (id1 CHAR(15) NOT NULL, id2 CHAR(15) NOT NULL, PRIMARY KEY(id1, id2)) ENGINE=InnoDB; - -INSERT INTO t3 VALUES("my-test-1", "my-test-2"); -COMMIT; - -INSERT INTO t1 VALUES("this-key", "will disappear"); -INSERT INTO t2 VALUES("this-key", "will also disappear"); -DELETE FROM t3 WHERE id1="my-test-1"; - -SELECT * FROM t1; -SELECT * FROM t2; -SELECT * FROM t3; -ROLLBACK; - -SELECT * FROM t1; -SELECT * FROM t2; -SELECT * FROM t3; -SELECT * FROM t3 WHERE id1="my-test-1" LOCK IN SHARE MODE; -COMMIT; -set autocommit=1; -DROP TABLE t1,t2,t3; - -# -# Check update with conflicting key -# - -CREATE TABLE t1 (a int not null primary key, b int not null, unique (b)) engine=innodb; -INSERT INTO t1 values (1,1),(2,2),(3,3),(4,4),(5,5),(6,6),(7,7),(8,8),(9,9); -# We need the a < 1000 test here to quard against the halloween problems -UPDATE t1 set a=a+100 where b between 2 and 3 and a < 1000; -SELECT * from t1; -drop table t1; - -# -# Test multi update with different join methods -# - -CREATE TABLE t1 (a int not null primary key, b int not null, key (b)) engine=innodb; -CREATE TABLE t2 (a int not null primary key, b int not null, key (b)) engine=innodb; -INSERT INTO t1 values (1,1),(2,2),(3,3),(4,4),(5,5),(6,6),(7,7),(8,8),(9,9),(10,10),(11,11),(12,12); -INSERT INTO t2 values (1,1),(2,2),(3,3),(4,4),(5,5),(6,6),(7,7),(8,8),(9,9); - -# Full join, without key -update t1,t2 set t1.a=t1.a+100; -select * from t1; - -# unique key -update t1,t2 set t1.a=t1.a+100 where t1.a=101; -select * from t1; - -# ref key -update t1,t2 set t1.b=t1.b+10 where t1.b=2; -select * from t1; - -# Range key (in t1) -update t1,t2 set t1.b=t1.b+2,t2.b=t1.b+10 where t1.b between 3 and 5 and t1.a=t2.a+100; -select * from t1; -select * from t2; - -drop table t1,t2; -CREATE TABLE t2 ( NEXT_T BIGINT NOT NULL PRIMARY KEY) ENGINE=MyISAM; -CREATE TABLE t1 ( B_ID INTEGER NOT NULL PRIMARY KEY) ENGINE=InnoDB; -SET AUTOCOMMIT=0; -INSERT INTO t1 ( B_ID ) VALUES ( 1 ); -INSERT INTO t2 ( NEXT_T ) VALUES ( 1 ); -ROLLBACK; -SELECT * FROM t1; -drop table t1,t2; -create table t1 ( pk int primary key, parent int not null, child int not null, index (parent) ) engine = innodb; -insert into t1 values (1,0,4), (2,1,3), (3,2,1), (4,1,2); -select distinct parent,child from t1 order by parent; -drop table t1; - -# -# Test that MySQL priorities clustered indexes -# -create table t1 (a int not null auto_increment primary key, b int, c int, key(c)) engine=innodb; -create table t2 (a int not null auto_increment primary key, b int); -insert into t1 (b) values (null),(null),(null),(null),(null),(null),(null); -insert into t2 (a) select b from t1; -insert into t1 (b) select b from t2; -insert into t2 (a) select b from t1; -insert into t1 (a) select b from t2; -insert into t2 (a) select b from t1; -insert into t1 (a) select b from t2; -insert into t2 (a) select b from t1; -insert into t1 (a) select b from t2; -insert into t2 (a) select b from t1; -insert into t1 (a) select b from t2; -select count(*) from t1; ---replace_column 9 # -explain select * from t1 where c between 1 and 2500; -update t1 set c=a; ---replace_column 9 # -explain select * from t1 where c between 1 and 2500; -drop table t1,t2; - -# -# Test of UPDATE ... ORDER BY -# - -create table t1 (id int primary key auto_increment, fk int, index index_fk (fk)) engine=innodb; - -insert into t1 (id) values (null),(null),(null),(null),(null); -update t1 set fk=69 where fk is null order by id limit 1; -SELECT * from t1; -drop table t1; - -create table t1 (a int not null, b int not null, key (a)); -insert into t1 values (1,1),(1,2),(1,3),(3,1),(3,2),(3,3),(3,1),(3,2),(3,3),(2,1),(2,2),(2,3); -SET @tmp=0; -update t1 set b=(@tmp:=@tmp+1) order by a; -update t1 set b=99 where a=1 order by b asc limit 1; -update t1 set b=100 where a=1 order by b desc limit 2; -update t1 set a=a+10+b where a=1 order by b; -select * from t1 order by a,b; -drop table t1; - -# -# Test of multi-table-updates (bug #1980). -# - -create table t1 ( c char(8) not null ) engine=innodb; -insert into t1 values ('0'),('1'),('2'),('3'),('4'),('5'),('6'),('7'),('8'),('9'); -insert into t1 values ('A'),('B'),('C'),('D'),('E'),('F'); - -alter table t1 add b char(8) not null; -alter table t1 add a char(8) not null; -alter table t1 add primary key (a,b,c); -update t1 set a=c, b=c; - -create table t2 (c char(8) not null, b char(8) not null, a char(8) not null, primary key(a,b,c)) engine=innodb; -insert into t2 select * from t1; - -delete t1,t2 from t2,t1 where t1.a<'B' and t2.b=t1.b; -drop table t1,t2; - -# -# test autoincrement with TRUNCATE -# - -SET AUTOCOMMIT=1; -create table t1 (a integer auto_increment primary key) engine=innodb; -insert into t1 (a) values (NULL),(NULL); -truncate table t1; -insert into t1 (a) values (NULL),(NULL); -SELECT * from t1; -drop table t1; - -# -# Test dictionary handling with spaceand quoting -# - -CREATE TABLE t1 (`id 1` INT NOT NULL, PRIMARY KEY (`id 1`)) ENGINE=INNODB; -CREATE TABLE t2 (id INT PRIMARY KEY, t1_id INT, INDEX par_ind (t1_id), FOREIGN KEY (`t1_id`) REFERENCES `t1`(`id 1`) ON DELETE CASCADE ) ENGINE=INNODB; -#show create table t2; -drop table t2,t1; - -# -# Test of multi updated and foreign keys -# - -create table `t1` (`id` int( 11 ) not null ,primary key ( `id` )) engine = innodb; -insert into `t1`values ( 1 ) ; -create table `t2` (`id` int( 11 ) not null default '0',unique key `id` ( `id` ) ,constraint `t1_id_fk` foreign key ( `id` ) references `t1` (`id` )) engine = innodb; -insert into `t2`values ( 1 ) ; -create table `t3` (`id` int( 11 ) not null default '0',key `id` ( `id` ) ,constraint `t2_id_fk` foreign key ( `id` ) references `t2` (`id` )) engine = innodb; -insert into `t3`values ( 1 ) ; ---error 1451 -delete t3,t2,t1 from t1,t2,t3 where t1.id =1 and t2.id = t1.id and t3.id = t2.id; ---error 1451 -update t1,t2,t3 set t3.id=5, t2.id=6, t1.id=7 where t1.id =1 and t2.id = t1.id and t3.id = t2.id; ---error 1054 -update t3 set t3.id=7 where t1.id =1 and t2.id = t1.id and t3.id = t2.id; -drop table t3,t2,t1; - -# -# test for recursion depth limit -# -create table t1( - id int primary key, - pid int, - index(pid), - foreign key(pid) references t1(id) on delete cascade) engine=innodb; -insert into t1 values(0,0),(1,0),(2,1),(3,2),(4,3),(5,4),(6,5),(7,6), - (8,7),(9,8),(10,9),(11,10),(12,11),(13,12),(14,13),(15,14); --- error 1451 -delete from t1 where id=0; -delete from t1 where id=15; -delete from t1 where id=0; - -drop table t1; - -# -# Test timestamps -# - -CREATE TABLE t1 (col1 int(1))ENGINE=InnoDB; -CREATE TABLE t2 (col1 int(1),stamp TIMESTAMP,INDEX stamp_idx -(stamp))ENGINE=InnoDB; -insert into t1 values (1),(2),(3); -# Note that timestamp 3 is wrong -insert into t2 values (1, 20020204130000),(2, 20020204130000),(4,20020204310000 ),(5,20020204230000); -SELECT col1 FROM t1 UNION SELECT col1 FROM t2 WHERE stamp < -'20020204120000' GROUP BY col1; -drop table t1,t2; - -# -# Test by Francois MASUREL -# - -CREATE TABLE t1 ( - `id` int(10) unsigned NOT NULL auto_increment, - `id_object` int(10) unsigned default '0', - `id_version` int(10) unsigned NOT NULL default '1', - `label` varchar(100) NOT NULL default '', - `description` text, - PRIMARY KEY (`id`), - KEY `id_object` (`id_object`), - KEY `id_version` (`id_version`) -) ENGINE=InnoDB; - -INSERT INTO t1 VALUES("6", "3382", "9", "Test", NULL), ("7", "102", "5", "Le Pekin (Test)", NULL),("584", "1794", "4", "Test de resto", NULL),("837", "1822", "6", "Test 3", NULL),("1119", "3524", "1", "Societe Test", NULL),("1122", "3525", "1", "Fournisseur Test", NULL); - -CREATE TABLE t2 ( - `id` int(10) unsigned NOT NULL auto_increment, - `id_version` int(10) unsigned NOT NULL default '1', - PRIMARY KEY (`id`), - KEY `id_version` (`id_version`) -) ENGINE=InnoDB; - -INSERT INTO t2 VALUES("3524", "1"),("3525", "1"),("1794", "4"),("102", "5"),("1822", "6"),("3382", "9"); - -SELECT t2.id, t1.`label` FROM t2 INNER JOIN -(SELECT t1.id_object as id_object FROM t1 WHERE t1.`label` LIKE '%test%') AS lbl -ON (t2.id = lbl.id_object) INNER JOIN t1 ON (t2.id = t1.id_object); -drop table t1,t2; - -create table t1 (a int, b varchar(200), c text not null) checksum=1 engine=myisam; -create table t2 (a int, b varchar(200), c text not null) checksum=0 engine=innodb; -create table t3 (a int, b varchar(200), c text not null) checksum=1 engine=innodb; -insert t1 values (1, "aaa", "bbb"), (NULL, "", "ccccc"), (0, NULL, ""); -insert t2 select * from t1; -insert t3 select * from t1; -checksum table t1, t2, t3, t4 quick; -checksum table t1, t2, t3, t4; -checksum table t1, t2, t3, t4 extended; -#show table status; -drop table t1,t2,t3; - -# -# Test problem with refering to different fields in same table in UNION -# (Bug #2552) -# -create table t1 (id int, name char(10) not null, name2 char(10) not null) engine=innodb; -insert into t1 values(1,'first','fff'),(2,'second','sss'),(3,'third','ttt'); -select trim(name2) from t1 union all select trim(name) from t1 union all select trim(id) from t1; -drop table t1; - -# -# Bug2160 -# -create table t1 (a int) engine=innodb; -create table t2 like t1; -drop table t1,t2; - -# -# Test of automaticly created foreign keys -# - -create table t1 (id int(11) not null, id2 int(11) not null, unique (id,id2)) engine=innodb; -create table t2 (id int(11) not null, constraint t1_id_fk foreign key ( id ) references t1 (id)) engine = innodb; -show create table t1; -show create table t2; -create index id on t2 (id); -show create table t2; -create index id2 on t2 (id); -show create table t2; -drop index id2 on t2; ---error ER_DROP_INDEX_FK -drop index id on t2; -show create table t2; -drop table t2; - -create table t2 (id int(11) not null, id2 int(11) not null, constraint t1_id_fk foreign key (id,id2) references t1 (id,id2)) engine = innodb; -show create table t2; -create unique index id on t2 (id,id2); -show create table t2; -drop table t2; - -# Check foreign key columns created in different order than key columns -create table t2 (id int(11) not null, id2 int(11) not null, unique (id,id2),constraint t1_id_fk foreign key (id2,id) references t1 (id,id2)) engine = innodb; -show create table t2; -drop table t2; - -create table t2 (id int(11) not null, id2 int(11) not null, unique (id,id2), constraint t1_id_fk foreign key (id) references t1 (id)) engine = innodb; -show create table t2; -drop table t2; - -create table t2 (id int(11) not null, id2 int(11) not null, unique (id,id2),constraint t1_id_fk foreign key (id2,id) references t1 (id,id2)) engine = innodb; -show create table t2; -drop table t2; - -create table t2 (id int(11) not null auto_increment, id2 int(11) not null, constraint t1_id_fk foreign key (id) references t1 (id), primary key (id), index (id,id2)) engine = innodb; -show create table t2; -drop table t2; - -create table t2 (id int(11) not null auto_increment, id2 int(11) not null, constraint t1_id_fk foreign key (id) references t1 (id)) engine= innodb; -show create table t2; -alter table t2 add index id_test (id), add index id_test2 (id,id2); -show create table t2; -drop table t2; - -# Test error handling - -# Embedded server doesn't chdir to data directory ---replace_result $MYSQLTEST_VARDIR . master-data/ '' ---error ER_WRONG_FK_DEF -create table t2 (id int(11) not null, id2 int(11) not null, constraint t1_id_fk foreign key (id2,id) references t1 (id)) engine = innodb; - -# bug#3749 - -create table t2 (a int auto_increment primary key, b int, index(b), foreign key (b) references t1(id), unique(b)) engine=innodb; -show create table t2; -drop table t2; -create table t2 (a int auto_increment primary key, b int, foreign key (b) references t1(id), foreign key (b) references t1(id), unique(b)) engine=innodb; -show create table t2; -drop table t2, t1; - - -# -# Bug #6126: Duplicate columns in keys gives misleading error message -# ---error 1060 -create table t1 (c char(10), index (c,c)) engine=innodb; ---error 1060 -create table t1 (c1 char(10), c2 char(10), index (c1,c2,c1)) engine=innodb; ---error 1060 -create table t1 (c1 char(10), c2 char(10), index (c1,c1,c2)) engine=innodb; ---error 1060 -create table t1 (c1 char(10), c2 char(10), index (c2,c1,c1)) engine=innodb; -create table t1 (c1 char(10), c2 char(10)) engine=innodb; ---error 1060 -alter table t1 add key (c1,c1); ---error 1060 -alter table t1 add key (c2,c1,c1); ---error 1060 -alter table t1 add key (c1,c2,c1); ---error 1060 -alter table t1 add key (c1,c1,c2); -drop table t1; - -# -# Bug #4082: integer truncation -# - -create table t1(a int(1) , b int(1)) engine=innodb; -insert into t1 values ('1111', '3333'); -select distinct concat(a, b) from t1; -drop table t1; - -# -# BUG#7709 test case - Boolean fulltext query against unsupported -# engines does not fail -# - -CREATE TABLE t1 ( a char(10) ) ENGINE=InnoDB; ---error 1214 -SELECT a FROM t1 WHERE MATCH (a) AGAINST ('test' IN BOOLEAN MODE); -DROP TABLE t1; - -# -# check null values #1 -# - ---disable_warnings -CREATE TABLE t1 (a_id tinyint(4) NOT NULL default '0', PRIMARY KEY (a_id)) ENGINE=InnoDB DEFAULT CHARSET=latin1; -INSERT INTO t1 VALUES (1),(2),(3); -CREATE TABLE t2 (b_id tinyint(4) NOT NULL default '0',b_a tinyint(4) NOT NULL default '0', PRIMARY KEY (b_id), KEY (b_a), - CONSTRAINT fk_b_a FOREIGN KEY (b_a) REFERENCES t1 (a_id) ON DELETE CASCADE ON UPDATE NO ACTION) ENGINE=InnoDB DEFAULT CHARSET=latin1; ---enable_warnings -INSERT INTO t2 VALUES (1,1),(2,1),(3,1),(4,2),(5,2); -SELECT * FROM (SELECT t1.*,GROUP_CONCAT(t2.b_id SEPARATOR ',') as b_list FROM (t1 LEFT JOIN (t2) on t1.a_id = t2.b_a) GROUP BY t1.a_id ) AS xyz; -DROP TABLE t2; -DROP TABLE t1; - -# -# Bug#11816 - Truncate table doesn't work with temporary innodb tables -# This is not an innodb bug, but we test it using innodb. -# -create temporary table t1 (a int) engine=innodb; -insert into t1 values (4711); -truncate t1; -insert into t1 values (42); -select * from t1; -drop table t1; -# Show that it works with permanent tables too. -create table t1 (a int) engine=innodb; -insert into t1 values (4711); -truncate t1; -insert into t1 values (42); -select * from t1; -drop table t1; - -# -# Bug #13025 Server crash during filesort -# - -create table t1 (a int not null, b int not null, c blob not null, d int not null, e int, primary key (a,b,c(255),d)) engine=innodb; -insert into t1 values (2,2,"b",2,2),(1,1,"a",1,1),(3,3,"ab",3,3); -select * from t1 order by a,b,c,d; -explain select * from t1 order by a,b,c,d; -drop table t1; - -# -# BUG#11039,#13218 Wrong key length in min() -# - -create table t1 (a char(1), b char(1), key(a, b)) engine=innodb; -insert into t1 values ('8', '6'), ('4', '7'); -select min(a) from t1; -select min(b) from t1 where a='8'; -drop table t1; - -# End of 4.1 tests - -# -# range optimizer problem -# - -create table t1 (x bigint unsigned not null primary key) engine=innodb; -insert into t1(x) values (0xfffffffffffffff0),(0xfffffffffffffff1); -select * from t1; -select count(*) from t1 where x>0; -select count(*) from t1 where x=0; -select count(*) from t1 where x<0; -select count(*) from t1 where x < -16; -select count(*) from t1 where x = -16; -explain select count(*) from t1 where x > -16; -select count(*) from t1 where x > -16; -select * from t1 where x > -16; -select count(*) from t1 where x = 18446744073709551601; -drop table t1; - - -# Test for testable InnoDB status variables. This test -# uses previous ones(pages_created, rows_deleted, ...). ---replace_result 8192 8191 -SELECT variable_value FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_buffer_pool_pages_total'; -SELECT variable_value FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_page_size'; -SELECT variable_value - @innodb_rows_deleted_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_rows_deleted'; -SELECT variable_value - @innodb_rows_inserted_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_rows_inserted'; -SELECT variable_value - @innodb_rows_updated_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_rows_updated'; - -# Test for row locks InnoDB status variables. -SELECT variable_value - @innodb_row_lock_waits_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_row_lock_waits'; -SELECT variable_value - @innodb_row_lock_current_waits_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_row_lock_current_waits'; -SELECT variable_value - @innodb_row_lock_time_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_row_lock_time'; -SELECT variable_value - @innodb_row_lock_time_max_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_row_lock_time_max'; -SELECT variable_value - @innodb_row_lock_time_avg_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_row_lock_time_avg'; - -# Test for innodb_sync_spin_loops variable -SET @innodb_sync_spin_loops_orig = @@innodb_sync_spin_loops; -show variables like "innodb_sync_spin_loops"; -set global innodb_sync_spin_loops=1000; -show variables like "innodb_sync_spin_loops"; -set global innodb_sync_spin_loops=0; -show variables like "innodb_sync_spin_loops"; -set global innodb_sync_spin_loops=20; -show variables like "innodb_sync_spin_loops"; -set global innodb_sync_spin_loops=@innodb_sync_spin_loops_orig; - -# Test for innodb_thread_concurrency variable -show variables like "innodb_thread_concurrency"; -set global innodb_thread_concurrency=1001; -show variables like "innodb_thread_concurrency"; -set global innodb_thread_concurrency=0; -show variables like "innodb_thread_concurrency"; -set global innodb_thread_concurrency=16; -show variables like "innodb_thread_concurrency"; - -# Test for innodb_concurrency_tickets variable -show variables like "innodb_concurrency_tickets"; -set global innodb_concurrency_tickets=1000; -show variables like "innodb_concurrency_tickets"; -set global innodb_concurrency_tickets=0; -show variables like "innodb_concurrency_tickets"; -set global innodb_concurrency_tickets=500; -show variables like "innodb_concurrency_tickets"; - -# Test for innodb_thread_sleep_delay variable -show variables like "innodb_thread_sleep_delay"; -set global innodb_thread_sleep_delay=100000; -show variables like "innodb_thread_sleep_delay"; -set global innodb_thread_sleep_delay=0; -show variables like "innodb_thread_sleep_delay"; -set global innodb_thread_sleep_delay=10000; -show variables like "innodb_thread_sleep_delay"; - -# -# Test varchar -# - -let $default=`select @@storage_engine`; -set storage_engine=INNODB; -source include/varchar.inc; - -# -# Some errors/warnings on create -# - -# Embedded server doesn't chdir to data directory ---replace_result $MYSQLTEST_VARDIR . master-data/ '' -create table t1 (v varchar(65530), key(v)); -drop table t1; -create table t1 (v varchar(65536)); -show create table t1; -drop table t1; -create table t1 (v varchar(65530) character set utf8); -show create table t1; -drop table t1; - -eval set storage_engine=$default; - -# InnoDB specific varchar tests -create table t1 (v varchar(16384)) engine=innodb; -drop table t1; - -# -# BUG#11039 Wrong key length in min() -# - -create table t1 (a char(1), b char(1), key(a, b)) engine=innodb; -insert into t1 values ('8', '6'), ('4', '7'); -select min(a) from t1; -select min(b) from t1 where a='8'; -drop table t1; - -# -# Bug #11080 & #11005 Multi-row REPLACE fails on a duplicate key error -# - -CREATE TABLE t1 ( `a` int(11) NOT NULL auto_increment, `b` int(11) default NULL,PRIMARY KEY (`a`),UNIQUE KEY `b` (`b`)) ENGINE=innodb; -insert into t1 (b) values (1); -replace into t1 (b) values (2), (1), (3); -select * from t1; -truncate table t1; -insert into t1 (b) values (1); -replace into t1 (b) values (2); -replace into t1 (b) values (1); -replace into t1 (b) values (3); -select * from t1; -drop table t1; - -create table t1 (rowid int not null auto_increment, val int not null,primary -key (rowid), unique(val)) engine=innodb; -replace into t1 (val) values ('1'),('2'); -replace into t1 (val) values ('1'),('2'); ---error ER_DUP_ENTRY -insert into t1 (val) values ('1'),('2'); -select * from t1; -drop table t1; - -# -# Test that update does not change internal auto-increment value -# - -create table t1 (a int not null auto_increment primary key, val int) engine=InnoDB; -insert into t1 (val) values (1); -update t1 set a=2 where a=1; -# We should get the following error because InnoDB does not update the counter ---error ER_DUP_ENTRY -insert into t1 (val) values (1); -select * from t1; -drop table t1; -# -# Bug #10465 -# - ---disable_warnings -CREATE TABLE t1 (GRADE DECIMAL(4) NOT NULL, PRIMARY KEY (GRADE)) ENGINE=INNODB; ---enable_warnings -INSERT INTO t1 (GRADE) VALUES (151),(252),(343); -SELECT GRADE FROM t1 WHERE GRADE > 160 AND GRADE < 300; -SELECT GRADE FROM t1 WHERE GRADE= 151; -DROP TABLE t1; - -# -# Bug #12340 multitable delete deletes only one record -# -create table t1 (f1 varchar(10), f2 varchar(10), primary key (f1,f2)) engine=innodb; -create table t2 (f3 varchar(10), f4 varchar(10), key (f4)) engine=innodb; -insert into t2 values ('aa','cc'); -insert into t1 values ('aa','bb'),('aa','cc'); -delete t1 from t1,t2 where f1=f3 and f4='cc'; -select * from t1; -drop table t1,t2; - -# -# Test that the slow TRUNCATE implementation resets autoincrement columns -# (bug #11946) -# - -CREATE TABLE t1 ( -id INTEGER NOT NULL AUTO_INCREMENT, PRIMARY KEY (id) -) ENGINE=InnoDB; - -CREATE TABLE t2 ( -id INTEGER NOT NULL, -FOREIGN KEY (id) REFERENCES t1 (id) -) ENGINE=InnoDB; - -INSERT INTO t1 (id) VALUES (NULL); -SELECT * FROM t1; -TRUNCATE t1; -INSERT INTO t1 (id) VALUES (NULL); -SELECT * FROM t1; - -# continued from above; test that doing a slow TRUNCATE on a table with 0 -# rows resets autoincrement columns -DELETE FROM t1; -TRUNCATE t1; -INSERT INTO t1 (id) VALUES (NULL); -SELECT * FROM t1; -DROP TABLE t2, t1; - -# Test that foreign keys in temporary tables are not accepted (bug #12084) -CREATE TABLE t1 -( - id INT PRIMARY KEY -) ENGINE=InnoDB; - ---error 1005,1005 -CREATE TEMPORARY TABLE t2 -( - id INT NOT NULL PRIMARY KEY, - b INT, - FOREIGN KEY (b) REFERENCES test.t1(id) -) ENGINE=InnoDB; -DROP TABLE t1; - -# -# Test that index column max sizes are honored (bug #13315) -# - -# prefix index -create table t1 (col1 varchar(2000), index (col1(767))) - character set = latin1 engine = innodb; - -# normal indexes -create table t2 (col1 char(255), index (col1)) - character set = latin1 engine = innodb; -create table t3 (col1 binary(255), index (col1)) - character set = latin1 engine = innodb; -create table t4 (col1 varchar(767), index (col1)) - character set = latin1 engine = innodb; -create table t5 (col1 varchar(767) primary key) - character set = latin1 engine = innodb; -create table t6 (col1 varbinary(767) primary key) - character set = latin1 engine = innodb; -create table t7 (col1 text, index(col1(767))) - character set = latin1 engine = innodb; -create table t8 (col1 blob, index(col1(767))) - character set = latin1 engine = innodb; - -# multi-column indexes are allowed to be longer -create table t9 (col1 varchar(512), col2 varchar(512), index(col1, col2)) - character set = latin1 engine = innodb; - -show create table t9; - -drop table t1, t2, t3, t4, t5, t6, t7, t8, t9; - -# these should have their index length trimmed -create table t1 (col1 varchar(768), index(col1)) - character set = latin1 engine = innodb; -create table t2 (col1 varbinary(768), index(col1)) - character set = latin1 engine = innodb; -create table t3 (col1 text, index(col1(768))) - character set = latin1 engine = innodb; -create table t4 (col1 blob, index(col1(768))) - character set = latin1 engine = innodb; - -show create table t1; - -drop table t1, t2, t3, t4; - -# these should be refused ---error 1071 -create table t1 (col1 varchar(768) primary key) - character set = latin1 engine = innodb; ---error 1071 -create table t2 (col1 varbinary(768) primary key) - character set = latin1 engine = innodb; ---error 1071 -create table t3 (col1 text, primary key(col1(768))) - character set = latin1 engine = innodb; ---error 1071 -create table t4 (col1 blob, primary key(col1(768))) - character set = latin1 engine = innodb; - -# -# Test improved foreign key error messages (bug #3443) -# - -CREATE TABLE t1 -( - id INT PRIMARY KEY -) ENGINE=InnoDB; - -CREATE TABLE t2 -( - v INT, - CONSTRAINT c1 FOREIGN KEY (v) REFERENCES t1(id) -) ENGINE=InnoDB; - ---error 1452 -INSERT INTO t2 VALUES(2); - -INSERT INTO t1 VALUES(1); -INSERT INTO t2 VALUES(1); - ---error 1451 -DELETE FROM t1 WHERE id = 1; - ---error 1217 -DROP TABLE t1; - -SET FOREIGN_KEY_CHECKS=0; -DROP TABLE t1; -SET FOREIGN_KEY_CHECKS=1; - ---error 1452 -INSERT INTO t2 VALUES(3); - -DROP TABLE t2; -# -# Test that checksum table uses a consistent read Bug #12669 -# -connect (a,localhost,root,,); -connect (b,localhost,root,,); -connection a; -create table t1(a int not null) engine=innodb DEFAULT CHARSET=latin1; -insert into t1 values (1),(2); -set autocommit=0; -checksum table t1; -connection b; -insert into t1 values(3); -connection a; -# -# Here checksum should not see insert -# -checksum table t1; -connection a; -commit; -checksum table t1; -commit; -drop table t1; -# -# autocommit = 1 -# -connection a; -create table t1(a int not null) engine=innodb DEFAULT CHARSET=latin1; -insert into t1 values (1),(2); -set autocommit=1; -checksum table t1; -connection b; -set autocommit=1; -insert into t1 values(3); -connection a; -# -# Here checksum sees insert -# -checksum table t1; -drop table t1; - -connection default; -disconnect a; -disconnect b; - -# tests for bugs #9802 and #13778 - -# test that FKs between invalid types are not accepted - -set foreign_key_checks=0; -create table t2 (a int primary key, b int, foreign key (b) references t1(a)) engine = innodb; -# Embedded server doesn't chdir to data directory ---replace_result $MYSQLTEST_VARDIR . master-data/ '' --- error 1005 -create table t1(a char(10) primary key, b varchar(20)) engine = innodb; -set foreign_key_checks=1; -drop table t2; - -# test that FKs between different charsets are not accepted in CREATE even -# when f_k_c is 0 - -set foreign_key_checks=0; -create table t1(a varchar(10) primary key) engine = innodb DEFAULT CHARSET=latin1; -# Embedded server doesn't chdir to data directory ---replace_result $MYSQLTEST_VARDIR . master-data/ '' --- error 1005 -create table t2 (a varchar(10), foreign key (a) references t1(a)) engine = innodb DEFAULT CHARSET=utf8; -set foreign_key_checks=1; -drop table t1; - -# test that invalid datatype conversions with ALTER are not allowed - -set foreign_key_checks=0; -create table t2 (a varchar(10), foreign key (a) references t1(a)) engine = innodb; -create table t1(a varchar(10) primary key) engine = innodb; --- error 1025,1025 -alter table t1 modify column a int; -set foreign_key_checks=1; -drop table t2,t1; - -# test that charset conversions with ALTER are allowed when f_k_c is 0 - -set foreign_key_checks=0; -create table t2 (a varchar(10), foreign key (a) references t1(a)) engine = innodb DEFAULT CHARSET=latin1; -create table t1(a varchar(10) primary key) engine = innodb DEFAULT CHARSET=latin1; -alter table t1 convert to character set utf8; -set foreign_key_checks=1; -drop table t2,t1; - -# test that RENAME does not allow invalid charsets when f_k_c is 0 - -set foreign_key_checks=0; -create table t2 (a varchar(10), foreign key (a) references t1(a)) engine = innodb DEFAULT CHARSET=latin1; -create table t3(a varchar(10) primary key) engine = innodb DEFAULT CHARSET=utf8; -# Embedded server doesn't chdir to data directory ---replace_result $MYSQLTEST_VARDIR . master-data/ '' --- error 1025 -rename table t3 to t1; -set foreign_key_checks=1; -drop table t2,t3; - -# test that foreign key errors are reported correctly (Bug #15550) - -create table t1(a int primary key) row_format=redundant engine=innodb; -create table t2(a int primary key,constraint foreign key(a)references t1(a)) row_format=compact engine=innodb; -create table t3(a int primary key) row_format=compact engine=innodb; -create table t4(a int primary key,constraint foreign key(a)references t3(a)) row_format=redundant engine=innodb; - -insert into t1 values(1); -insert into t3 values(1); --- error 1452 -insert into t2 values(2); --- error 1452 -insert into t4 values(2); -insert into t2 values(1); -insert into t4 values(1); --- error 1451 -update t1 set a=2; --- error 1452 -update t2 set a=2; --- error 1451 -update t3 set a=2; --- error 1452 -update t4 set a=2; --- error 1451 -truncate t1; --- error 1451 -truncate t3; -truncate t2; -truncate t4; -truncate t1; -truncate t3; - -drop table t4,t3,t2,t1; - - -# -# Test that we can create a large (>1K) key -# -create table t1 (a varchar(255) character set utf8, - b varchar(255) character set utf8, - c varchar(255) character set utf8, - d varchar(255) character set utf8, - key (a,b,c,d)) engine=innodb; -drop table t1; ---error ER_TOO_LONG_KEY -create table t1 (a varchar(255) character set utf8, - b varchar(255) character set utf8, - c varchar(255) character set utf8, - d varchar(255) character set utf8, - e varchar(255) character set utf8, - key (a,b,c,d,e)) engine=innodb; - - -# test the padding of BINARY types and collations (Bug #14189) - -create table t1 (s1 varbinary(2),primary key (s1)) engine=innodb; -create table t2 (s1 binary(2),primary key (s1)) engine=innodb; -create table t3 (s1 varchar(2) binary,primary key (s1)) engine=innodb; -create table t4 (s1 char(2) binary,primary key (s1)) engine=innodb; - -insert into t1 values (0x41),(0x4120),(0x4100); --- error ER_DUP_ENTRY -insert into t2 values (0x41),(0x4120),(0x4100); -insert into t2 values (0x41),(0x4120); --- error ER_DUP_ENTRY -insert into t3 values (0x41),(0x4120),(0x4100); -insert into t3 values (0x41),(0x4100); --- error ER_DUP_ENTRY -insert into t4 values (0x41),(0x4120),(0x4100); -insert into t4 values (0x41),(0x4100); -select hex(s1) from t1; -select hex(s1) from t2; -select hex(s1) from t3; -select hex(s1) from t4; -drop table t1,t2,t3,t4; - -create table t1 (a int primary key,s1 varbinary(3) not null unique) engine=innodb; -create table t2 (s1 binary(2) not null, constraint c foreign key(s1) references t1(s1) on update cascade) engine=innodb; - -insert into t1 values(1,0x4100),(2,0x41),(3,0x4120),(4,0x42); --- error 1452 -insert into t2 values(0x42); -insert into t2 values(0x41); -select hex(s1) from t2; -update t1 set s1=0x123456 where a=2; -select hex(s1) from t2; --- error 1451 -update t1 set s1=0x12 where a=1; --- error 1451 -update t1 set s1=0x12345678 where a=1; --- error 1451 -update t1 set s1=0x123457 where a=1; -update t1 set s1=0x1220 where a=1; -select hex(s1) from t2; -update t1 set s1=0x1200 where a=1; -select hex(s1) from t2; -update t1 set s1=0x4200 where a=1; -select hex(s1) from t2; --- error 1451 -delete from t1 where a=1; -delete from t1 where a=2; -update t2 set s1=0x4120; --- error 1451 -delete from t1; -delete from t1 where a!=3; -select a,hex(s1) from t1; -select hex(s1) from t2; - -drop table t2,t1; - -create table t1 (a int primary key,s1 varchar(2) binary not null unique) engine=innodb; -create table t2 (s1 char(2) binary not null, constraint c foreign key(s1) references t1(s1) on update cascade) engine=innodb; - -insert into t1 values(1,0x4100),(2,0x41); -insert into t2 values(0x41); -select hex(s1) from t2; -update t1 set s1=0x1234 where a=1; -select hex(s1) from t2; -update t1 set s1=0x12 where a=2; -select hex(s1) from t2; -delete from t1 where a=1; --- error 1451 -delete from t1 where a=2; -select a,hex(s1) from t1; -select hex(s1) from t2; - -drop table t2,t1; -# Ensure that <tablename>_ibfk_0 is not mistreated as a -# generated foreign key identifier. (Bug #16387) - -CREATE TABLE t1(a INT, PRIMARY KEY(a)) ENGINE=InnoDB; -CREATE TABLE t2(a INT) ENGINE=InnoDB; -ALTER TABLE t2 ADD FOREIGN KEY (a) REFERENCES t1(a); -ALTER TABLE t2 DROP FOREIGN KEY t2_ibfk_1; -ALTER TABLE t2 ADD CONSTRAINT t2_ibfk_0 FOREIGN KEY (a) REFERENCES t1(a); -ALTER TABLE t2 DROP FOREIGN KEY t2_ibfk_0; -SHOW CREATE TABLE t2; -DROP TABLE t2,t1; - -# -# Test case for bug #16229: MySQL/InnoDB uses full explicit table locks in trigger processing -# - -connect (a,localhost,root,,); -connect (b,localhost,root,,); -connection a; -create table t1(a int not null, b int, c int, d int, primary key(a)) engine=innodb; -insert into t1(a) values (1),(2),(3); -commit; -connection b; -set autocommit = 0; -update t1 set b = 5 where a = 2; -connection a; -delimiter |; -create trigger t1t before insert on t1 for each row begin set NEW.b = NEW.a * 10 + 5, NEW.c = NEW.a / 10; end | -delimiter ;| -set autocommit = 0; -connection a; -insert into t1(a) values (10),(20),(30),(40),(50),(60),(70),(80),(90),(100), -(11),(21),(31),(41),(51),(61),(71),(81),(91),(101), -(12),(22),(32),(42),(52),(62),(72),(82),(92),(102), -(13),(23),(33),(43),(53),(63),(73),(83),(93),(103), -(14),(24),(34),(44),(54),(64),(74),(84),(94),(104); -connection b; -commit; -connection a; -commit; -drop trigger t1t; -drop table t1; -disconnect a; -disconnect b; -# -# Another trigger test -# -connect (a,localhost,root,,); -connect (b,localhost,root,,); -connection a; -create table t1(a int not null, b int, c int, d int, primary key(a)) engine=innodb; -create table t2(a int not null, b int, c int, d int, primary key(a)) engine=innodb; -create table t3(a int not null, b int, c int, d int, primary key(a)) engine=innodb; -create table t4(a int not null, b int, c int, d int, primary key(a)) engine=innodb; -create table t5(a int not null, b int, c int, d int, primary key(a)) engine=innodb; -insert into t1(a) values (1),(2),(3); -insert into t2(a) values (1),(2),(3); -insert into t3(a) values (1),(2),(3); -insert into t4(a) values (1),(2),(3); -insert into t3(a) values (5),(7),(8); -insert into t4(a) values (5),(7),(8); -insert into t5(a) values (1),(2),(3),(4),(5),(6),(7),(8),(9),(10),(11),(12); - -delimiter |; -create trigger t1t before insert on t1 for each row begin - INSERT INTO t2 SET a = NEW.a; -end | - -create trigger t2t before insert on t2 for each row begin - DELETE FROM t3 WHERE a = NEW.a; -end | - -create trigger t3t before delete on t3 for each row begin - UPDATE t4 SET b = b + 1 WHERE a = OLD.a; -end | - -create trigger t4t before update on t4 for each row begin - UPDATE t5 SET b = b + 1 where a = NEW.a; -end | -delimiter ;| -commit; -set autocommit = 0; -update t1 set b = b + 5 where a = 1; -update t2 set b = b + 5 where a = 1; -update t3 set b = b + 5 where a = 1; -update t4 set b = b + 5 where a = 1; -insert into t5(a) values(20); -connection b; -set autocommit = 0; -insert into t1(a) values(7); -insert into t2(a) values(8); -delete from t2 where a = 3; -update t4 set b = b + 1 where a = 3; -commit; -drop trigger t1t; -drop trigger t2t; -drop trigger t3t; -drop trigger t4t; -drop table t1, t2, t3, t4, t5; -connection default; -disconnect a; -disconnect b; - -# -# Test that cascading updates leading to duplicate keys give the correct -# error message (bug #9680) -# - -CREATE TABLE t1 ( - field1 varchar(8) NOT NULL DEFAULT '', - field2 varchar(8) NOT NULL DEFAULT '', - PRIMARY KEY (field1, field2) -) ENGINE=InnoDB; - -CREATE TABLE t2 ( - field1 varchar(8) NOT NULL DEFAULT '' PRIMARY KEY, - FOREIGN KEY (field1) REFERENCES t1 (field1) - ON DELETE CASCADE ON UPDATE CASCADE -) ENGINE=InnoDB; - -INSERT INTO t1 VALUES ('old', 'somevalu'); -INSERT INTO t1 VALUES ('other', 'anyvalue'); - -INSERT INTO t2 VALUES ('old'); -INSERT INTO t2 VALUES ('other'); - ---error ER_FOREIGN_DUPLICATE_KEY -UPDATE t1 SET field1 = 'other' WHERE field2 = 'somevalu'; - -DROP TABLE t2; -DROP TABLE t1; - -# -# Bug#18477 - MySQL/InnoDB Ignoring Foreign Keys in ALTER TABLE -# -create table t1 ( - c1 bigint not null, - c2 bigint not null, - primary key (c1), - unique key (c2) -) engine=innodb; -# -create table t2 ( - c1 bigint not null, - primary key (c1) -) engine=innodb; -# -alter table t1 add constraint c2_fk foreign key (c2) - references t2(c1) on delete cascade; -show create table t1; -# -alter table t1 drop foreign key c2_fk; -show create table t1; -# -drop table t1, t2; - -# -# Bug #14360: problem with intervals -# - -create table t1(a date) engine=innodb; -create table t2(a date, key(a)) engine=innodb; -insert into t1 values('2005-10-01'); -insert into t2 values('2005-10-01'); -select * from t1, t2 - where t2.a between t1.a - interval 2 day and t1.a + interval 2 day; -drop table t1, t2; - -create table t1 (id int not null, f_id int not null, f int not null, -primary key(f_id, id)) engine=innodb; -create table t2 (id int not null,s_id int not null,s varchar(200), -primary key(id)) engine=innodb; -INSERT INTO t1 VALUES (8, 1, 3); -INSERT INTO t1 VALUES (1, 2, 1); -INSERT INTO t2 VALUES (1, 0, ''); -INSERT INTO t2 VALUES (8, 1, ''); -commit; -DELETE ml.* FROM t1 AS ml LEFT JOIN t2 AS mm ON (mm.id=ml.id) -WHERE mm.id IS NULL; -select ml.* from t1 as ml left join t2 as mm on (mm.id=ml.id) -where mm.id is null lock in share mode; -drop table t1,t2; - -# -# Test case where X-locks on unused rows should be released in a -# update (because READ COMMITTED isolation level) -# - -connect (a,localhost,root,,); -connect (b,localhost,root,,); -connection a; -create table t1(a int not null, b int, primary key(a)) engine=innodb; -insert into t1 values(1,1),(2,2),(3,1),(4,2),(5,1),(6,2),(7,3); -commit; -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; -update t1 set b = 5 where b = 1; -connection b; -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; -# -# X-lock to record (7,3) should be released in a update -# -select * from t1 where a = 7 and b = 3 for update; -connection a; -commit; -connection b; -commit; -drop table t1; -connection default; -disconnect a; -disconnect b; - -# -# Test case where no locks should be released (because we are not -# using READ COMMITTED isolation level) -# - -connect (a,localhost,root,,); -connect (b,localhost,root,,); -connection a; -create table t1(a int not null, b int, primary key(a)) engine=innodb; -insert into t1 values(1,1),(2,2),(3,1),(4,2),(5,1),(6,2); -commit; -set autocommit = 0; -select * from t1 lock in share mode; -update t1 set b = 5 where b = 1; -connection b; -set autocommit = 0; -# -# S-lock to records (2,2),(4,2), and (6,2) should not be released in a update -# ---error 1205 -select * from t1 where a = 2 and b = 2 for update; -# -# X-lock to record (1,1),(3,1),(5,1) should not be released in a update -# ---error 1205 -connection a; -commit; -connection b; -commit; -connection default; -disconnect a; -disconnect b; -drop table t1; - -# -# Consistent read should be used in following selects -# -# 1) INSERT INTO ... SELECT -# 2) UPDATE ... = ( SELECT ...) -# 3) CREATE ... SELECT - -connect (a,localhost,root,,); -connect (b,localhost,root,,); -connection a; -create table t1(a int not null, b int, primary key(a)) engine=innodb; -insert into t1 values (1,2),(5,3),(4,2); -create table t2(d int not null, e int, primary key(d)) engine=innodb; -insert into t2 values (8,6),(12,1),(3,1); -commit; -set autocommit = 0; -select * from t2 for update; -connection b; -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; -insert into t1 select * from t2; -update t1 set b = (select e from t2 where a = d); -create table t3(d int not null, e int, primary key(d)) engine=innodb -select * from t2; -commit; -connection a; -commit; -connection default; -disconnect a; -disconnect b; -drop table t1, t2, t3; - -# -# Consistent read should not be used if -# -# (a) isolation level is serializable OR -# (b) select ... lock in share mode OR -# (c) select ... for update -# -# in following queries: -# -# 1) INSERT INTO ... SELECT -# 2) UPDATE ... = ( SELECT ...) -# 3) CREATE ... SELECT - -connect (a,localhost,root,,); -connect (b,localhost,root,,); -connect (c,localhost,root,,); -connect (d,localhost,root,,); -connect (e,localhost,root,,); -connect (f,localhost,root,,); -connect (g,localhost,root,,); -connect (h,localhost,root,,); -connect (i,localhost,root,,); -connect (j,localhost,root,,); -connection a; -create table t1(a int not null, b int, primary key(a)) engine=innodb; -insert into t1 values (1,2),(5,3),(4,2); -create table t2(a int not null, b int, primary key(a)) engine=innodb; -insert into t2 values (8,6),(12,1),(3,1); -create table t3(d int not null, b int, primary key(d)) engine=innodb; -insert into t3 values (8,6),(12,1),(3,1); -create table t5(a int not null, b int, primary key(a)) engine=innodb; -insert into t5 values (1,2),(5,3),(4,2); -create table t6(d int not null, e int, primary key(d)) engine=innodb; -insert into t6 values (8,6),(12,1),(3,1); -create table t8(a int not null, b int, primary key(a)) engine=innodb; -insert into t8 values (1,2),(5,3),(4,2); -create table t9(d int not null, e int, primary key(d)) engine=innodb; -insert into t9 values (8,6),(12,1),(3,1); -commit; -set autocommit = 0; -select * from t2 for update; -connection b; -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL SERIALIZABLE; ---send -insert into t1 select * from t2; -connection c; -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL SERIALIZABLE; ---send -update t3 set b = (select b from t2 where a = d); -connection d; -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL SERIALIZABLE; ---send -create table t4(a int not null, b int, primary key(a)) engine=innodb select * from t2; -connection e; -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; ---send -insert into t5 (select * from t2 lock in share mode); -connection f; -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; ---send -update t6 set e = (select b from t2 where a = d lock in share mode); -connection g; -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; ---send -create table t7(a int not null, b int, primary key(a)) engine=innodb select * from t2 lock in share mode; -connection h; -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; ---send -insert into t8 (select * from t2 for update); -connection i; -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; ---send -update t9 set e = (select b from t2 where a = d for update); -connection j; -SET binlog_format='MIXED'; -set autocommit = 0; -SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED; ---send -create table t10(a int not null, b int, primary key(a)) engine=innodb select * from t2 for update; - -connection b; ---error 1205 -reap; - -connection c; ---error 1205 -reap; - -connection d; ---error 1205 -reap; - -connection e; ---error 1205 -reap; - -connection f; ---error 1205 -reap; - -connection g; ---error 1205 -reap; - -connection h; ---error 1205 -reap; - -connection i; ---error 1205 -reap; - -connection j; ---error 1205 -reap; - -connection a; -commit; - -connection default; -disconnect a; -disconnect b; -disconnect c; -disconnect d; -disconnect e; -disconnect f; -disconnect g; -disconnect h; -disconnect i; -disconnect j; -drop table t1, t2, t3, t5, t6, t8, t9; - -# bug 18934, "InnoDB crashes when table uses column names like DB_ROW_ID" ---error 1005 -CREATE TABLE t1 (DB_ROW_ID int) engine=innodb; - -# -# Bug #17152: Wrong result with BINARY comparison on aliased column -# - -CREATE TABLE t1 ( - a BIGINT(20) NOT NULL, - PRIMARY KEY (a) - ) ENGINE=INNODB DEFAULT CHARSET=UTF8; - -CREATE TABLE t2 ( - a BIGINT(20) NOT NULL, - b VARCHAR(128) NOT NULL, - c TEXT NOT NULL, - PRIMARY KEY (a,b), - KEY idx_t2_b_c (b,c(200)), - CONSTRAINT t_fk FOREIGN KEY (a) REFERENCES t1 (a) - ON DELETE CASCADE - ) ENGINE=INNODB DEFAULT CHARSET=UTF8; - -INSERT INTO t1 VALUES (1); -INSERT INTO t2 VALUES (1, 'bar', 'vbar'); -INSERT INTO t2 VALUES (1, 'BAR2', 'VBAR'); -INSERT INTO t2 VALUES (1, 'bar_bar', 'bibi'); -INSERT INTO t2 VALUES (1, 'customer_over', '1'); - -SELECT * FROM t2 WHERE b = 'customer_over'; -SELECT * FROM t2 WHERE BINARY b = 'customer_over'; -SELECT DISTINCT p0.a FROM t2 p0 WHERE p0.b = 'customer_over'; -/* Bang: Empty result set, above was expected: */ -SELECT DISTINCT p0.a FROM t2 p0 WHERE BINARY p0.b = 'customer_over'; -SELECT p0.a FROM t2 p0 WHERE BINARY p0.b = 'customer_over'; - -drop table t2, t1; - -# -# Test optimize on table with open transaction -# - -CREATE TABLE t1 ( a int ) ENGINE=innodb; -BEGIN; -INSERT INTO t1 VALUES (1); -OPTIMIZE TABLE t1; -DROP TABLE t1; - -# -# Bug #24741 (existing cascade clauses disappear when adding foreign keys) -# - -CREATE TABLE t1 (id int PRIMARY KEY, f int NOT NULL, INDEX(f)) ENGINE=InnoDB; - -CREATE TABLE t2 (id int PRIMARY KEY, f INT NOT NULL, - CONSTRAINT t2_t1 FOREIGN KEY (id) REFERENCES t1 (id) - ON DELETE CASCADE ON UPDATE CASCADE) ENGINE=InnoDB; - -ALTER TABLE t2 ADD FOREIGN KEY (f) REFERENCES t1 (f) ON -DELETE CASCADE ON UPDATE CASCADE; - -SHOW CREATE TABLE t2; -DROP TABLE t2, t1; - -# -# Bug #25927: Prevent ALTER TABLE ... MODIFY ... NOT NULL on columns -# for which there is a foreign key constraint ON ... SET NULL. -# - -CREATE TABLE t1 (a INT, INDEX(a)) ENGINE=InnoDB; -CREATE TABLE t2 (a INT, INDEX(a)) ENGINE=InnoDB; -INSERT INTO t1 VALUES (1); -INSERT INTO t2 VALUES (1); -ALTER TABLE t2 ADD FOREIGN KEY (a) REFERENCES t1 (a) ON DELETE SET NULL; -# mysqltest first does replace_regex, then replace_result ---replace_regex /'[^']*test\/#sql-[0-9a-f_]*'/'#sql-temporary'/ -# Embedded server doesn't chdir to data directory ---replace_result $MYSQLTEST_VARDIR . master-data/ '' ---error 1025 -ALTER TABLE t2 MODIFY a INT NOT NULL; -DELETE FROM t1; -DROP TABLE t2,t1; - -# -# Bug #26835: table corruption after delete+insert -# - -CREATE TABLE t1 (a VARCHAR(5) COLLATE utf8_unicode_ci PRIMARY KEY) -ENGINE=InnoDB; -INSERT INTO t1 VALUES (0xEFBCA4EFBCA4EFBCA4); -DELETE FROM t1; -INSERT INTO t1 VALUES ('DDD'); -SELECT * FROM t1; -DROP TABLE t1; - -# -# Bug #23313 (AUTO_INCREMENT=# not reported back for InnoDB tables) -# Bug #21404 (AUTO_INCREMENT value reset when Adding FKEY (or ALTER?)) -# - -CREATE TABLE t1 (id int PRIMARY KEY AUTO_INCREMENT) ENGINE=InnoDB -AUTO_INCREMENT=42; - -INSERT INTO t1 VALUES (0),(347),(0); -SELECT * FROM t1; - -SHOW CREATE TABLE t1; - -CREATE TABLE t2 (id int PRIMARY KEY) ENGINE=InnoDB; -INSERT INTO t2 VALUES(42),(347),(348); -ALTER TABLE t1 ADD CONSTRAINT t1_t2 FOREIGN KEY (id) REFERENCES t2(id); -SHOW CREATE TABLE t1; - -DROP TABLE t1,t2; - -# -# Bug #21101 (Prints wrong error message if max row size is too large) -# -set innodb_strict_mode=on; ---error 1118 -CREATE TABLE t1 ( - c01 CHAR(255), c02 CHAR(255), c03 CHAR(255), c04 CHAR(255), - c05 CHAR(255), c06 CHAR(255), c07 CHAR(255), c08 CHAR(255), - c09 CHAR(255), c10 CHAR(255), c11 CHAR(255), c12 CHAR(255), - c13 CHAR(255), c14 CHAR(255), c15 CHAR(255), c16 CHAR(255), - c17 CHAR(255), c18 CHAR(255), c19 CHAR(255), c20 CHAR(255), - c21 CHAR(255), c22 CHAR(255), c23 CHAR(255), c24 CHAR(255), - c25 CHAR(255), c26 CHAR(255), c27 CHAR(255), c28 CHAR(255), - c29 CHAR(255), c30 CHAR(255), c31 CHAR(255), c32 CHAR(255) - ) ENGINE = InnoDB; - -# -# Bug #31860 InnoDB assumes AUTOINC values can only be positive. -# -DROP TABLE IF EXISTS t1; -CREATE TABLE t1( - id BIGINT(20) NOT NULL AUTO_INCREMENT PRIMARY KEY - ) ENGINE=InnoDB; -INSERT INTO t1 VALUES(-10); -SELECT * FROM t1; -# -# NOTE: The server really needs to be restarted at this point -# for the test to be useful. -# -# Without the fix InnoDB would trip over an assertion here. -INSERT INTO t1 VALUES(NULL); -# The next value should be 1 and not -9 or a -ve number -SELECT * FROM t1; -DROP TABLE t1; - -# -# Bug #21409 Incorrect result returned when in READ-COMMITTED with -# query_cache ON -# -CONNECT (c1,localhost,root,,); -CONNECT (c2,localhost,root,,); -CONNECTION c1; -SET binlog_format='MIXED'; -SET TX_ISOLATION='read-committed'; -SET AUTOCOMMIT=0; -DROP TABLE IF EXISTS t1, t2; -CREATE TABLE t1 ( a int ) ENGINE=InnoDB; -CREATE TABLE t2 LIKE t1; -SELECT * FROM t2; -CONNECTION c2; -SET binlog_format='MIXED'; -SET TX_ISOLATION='read-committed'; -SET AUTOCOMMIT=0; -INSERT INTO t1 VALUES (1); -COMMIT; -CONNECTION c1; -SELECT * FROM t1 WHERE a=1; -DISCONNECT c1; -DISCONNECT c2; -CONNECT (c1,localhost,root,,); -CONNECT (c2,localhost,root,,); -CONNECTION c1; -SET binlog_format='MIXED'; -SET TX_ISOLATION='read-committed'; -SET AUTOCOMMIT=0; -SELECT * FROM t2; -CONNECTION c2; -SET binlog_format='MIXED'; -SET TX_ISOLATION='read-committed'; -SET AUTOCOMMIT=0; -INSERT INTO t1 VALUES (2); -COMMIT; -CONNECTION c1; -# The result set below should be the same for both selects -SELECT * FROM t1 WHERE a=2; -SELECT * FROM t1 WHERE a=2; -DROP TABLE t1; -DROP TABLE t2; -DISCONNECT c1; -DISCONNECT c2; -CONNECTION default; - -# -# Bug #29157 UPDATE, changed rows incorrect -# -create table t1 (i int, j int) engine=innodb; -insert into t1 (i, j) values (1, 1), (2, 2); ---enable_info -update t1 set j = 2; ---disable_info -drop table t1; - -# -# Bug #32440 InnoDB free space info does not appear in SHOW TABLE STATUS or -# I_S -# -create table t1 (id int) comment='this is a comment' engine=innodb; -select table_comment, data_free > 0 as data_free_is_set - from information_schema.tables - where table_schema='test' and table_name = 't1'; -drop table t1; - -# -# Bug 34920 test -# -CONNECTION default; -CREATE TABLE t1 ( - c1 INT(10) UNSIGNED NOT NULL AUTO_INCREMENT, - c2 VARCHAR(128) NOT NULL, - PRIMARY KEY(c1) -) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=100; - -CREATE TABLE t2 ( - c1 INT(10) UNSIGNED NOT NULL AUTO_INCREMENT, - c2 INT(10) UNSIGNED DEFAULT NULL, - PRIMARY KEY(c1) -) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=200; - -SELECT AUTO_INCREMENT FROM INFORMATION_SCHEMA.TABLES WHERE table_name = 't2'; -ALTER TABLE t2 ADD CONSTRAINT t1_t2_1 FOREIGN KEY(c1) REFERENCES t1(c1); -SELECT AUTO_INCREMENT FROM INFORMATION_SCHEMA.TABLES WHERE table_name = 't2'; -DROP TABLE t2; -DROP TABLE t1; -# End 34920 test -# -# Bug #29507 TRUNCATE shows to many rows effected -# -CONNECTION default; -CREATE TABLE t1 (c1 int default NULL, - c2 int default NULL -) ENGINE=InnoDB DEFAULT CHARSET=latin1; - ---enable_info -TRUNCATE TABLE t1; - -INSERT INTO t1 VALUES (1, 1), (2, 2), (3, 3), (4, 4), (5, 5); -TRUNCATE TABLE t1; - ---disable_info -DROP TABLE t1; -# -# Bug#35537 Innodb doesn't increment handler_update and handler_delete. -# --- disable_query_log --- disable_result_log - -CONNECT (c1,localhost,root,,); - -DROP TABLE IF EXISTS bug35537; -CREATE TABLE bug35537 ( - c1 int -) ENGINE=InnoDB; - -INSERT INTO bug35537 VALUES (1); - --- enable_result_log - -SHOW SESSION STATUS LIKE 'Handler_update%'; -SHOW SESSION STATUS LIKE 'Handler_delete%'; - -UPDATE bug35537 SET c1 = 2 WHERE c1 = 1; -DELETE FROM bug35537 WHERE c1 = 2; - -SHOW SESSION STATUS LIKE 'Handler_update%'; -SHOW SESSION STATUS LIKE 'Handler_delete%'; - -DROP TABLE bug35537; - -DISCONNECT c1; -CONNECTION default; - -SET GLOBAL innodb_thread_concurrency = @innodb_thread_concurrency_orig; - --- enable_query_log - -####################################################################### -# # -# Please, DO NOT TOUCH this file as well as the innodb.result file. # -# These files are to be modified ONLY BY INNOBASE guys. # -# # -# Use innodb_mysql.[test|result] files instead. # -# # -# If nevertheless you need to make some changes here, please, forward # -# your commit message # -# To: innodb_dev_ww@oracle.com # -# Cc: dev-innodb@mysql.com # -# (otherwise your changes may be erased). # -# # -####################################################################### diff --git a/storage/innodb_plugin/mysql-test/innodb_bug21704.result b/storage/innodb_plugin/mysql-test/innodb_bug21704.result deleted file mode 100644 index b8e0b15d50d..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug21704.result +++ /dev/null @@ -1,55 +0,0 @@ -# -# Bug#21704: Renaming column does not update FK definition. -# - -# Test that it's not possible to rename columns participating in a -# foreign key (either in the referencing or referenced table). - -DROP TABLE IF EXISTS t1; -DROP TABLE IF EXISTS t2; -DROP TABLE IF EXISTS t3; -CREATE TABLE t1 (a INT PRIMARY KEY, b INT) ROW_FORMAT=COMPACT ENGINE=INNODB; -CREATE TABLE t2 (a INT PRIMARY KEY, b INT, -CONSTRAINT fk1 FOREIGN KEY (a) REFERENCES t1(a)) -ROW_FORMAT=COMPACT ENGINE=INNODB; -CREATE TABLE t3 (a INT PRIMARY KEY, b INT, KEY(b), C INT, -CONSTRAINT fk2 FOREIGN KEY (b) REFERENCES t3 (a)) -ROW_FORMAT=COMPACT ENGINE=INNODB; -INSERT INTO t1 VALUES (1,1),(2,2),(3,3); -INSERT INTO t2 VALUES (1,1),(2,2),(3,3); -INSERT INTO t3 VALUES (1,1,1),(2,2,2),(3,3,3); - -# Test renaming the column in the referenced table. - -ALTER TABLE t1 CHANGE a c INT; -ERROR HY000: Error on rename of '#sql-temporary' to './test/t1' (errno: 150) -# Ensure that online column rename works. -ALTER TABLE t1 CHANGE b c INT; -affected rows: 0 -info: Records: 0 Duplicates: 0 Warnings: 0 - -# Test renaming the column in the referencing table - -ALTER TABLE t2 CHANGE a c INT; -ERROR HY000: Error on rename of '#sql-temporary' to './test/t2' (errno: 150) -# Ensure that online column rename works. -ALTER TABLE t2 CHANGE b c INT; -affected rows: 0 -info: Records: 0 Duplicates: 0 Warnings: 0 - -# Test with self-referential constraints - -ALTER TABLE t3 CHANGE a d INT; -ERROR HY000: Error on rename of '#sql-temporary' to './test/t3' (errno: 150) -ALTER TABLE t3 CHANGE b d INT; -ERROR HY000: Error on rename of '#sql-temporary' to './test/t3' (errno: 150) -# Ensure that online column rename works. -ALTER TABLE t3 CHANGE c d INT; -affected rows: 0 -info: Records: 0 Duplicates: 0 Warnings: 0 - -# Cleanup. - -DROP TABLE t3; -DROP TABLE t2; -DROP TABLE t1; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug21704.test b/storage/innodb_plugin/mysql-test/innodb_bug21704.test deleted file mode 100644 index c649b61034c..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug21704.test +++ /dev/null @@ -1,96 +0,0 @@ --- source include/have_innodb.inc - ---echo # ---echo # Bug#21704: Renaming column does not update FK definition. ---echo # - ---echo ---echo # Test that it's not possible to rename columns participating in a ---echo # foreign key (either in the referencing or referenced table). ---echo - ---disable_warnings -DROP TABLE IF EXISTS t1; -DROP TABLE IF EXISTS t2; -DROP TABLE IF EXISTS t3; ---enable_warnings - -CREATE TABLE t1 (a INT PRIMARY KEY, b INT) ROW_FORMAT=COMPACT ENGINE=INNODB; - -CREATE TABLE t2 (a INT PRIMARY KEY, b INT, - CONSTRAINT fk1 FOREIGN KEY (a) REFERENCES t1(a)) -ROW_FORMAT=COMPACT ENGINE=INNODB; - -CREATE TABLE t3 (a INT PRIMARY KEY, b INT, KEY(b), C INT, - CONSTRAINT fk2 FOREIGN KEY (b) REFERENCES t3 (a)) -ROW_FORMAT=COMPACT ENGINE=INNODB; - -INSERT INTO t1 VALUES (1,1),(2,2),(3,3); -INSERT INTO t2 VALUES (1,1),(2,2),(3,3); -INSERT INTO t3 VALUES (1,1,1),(2,2,2),(3,3,3); - ---echo ---echo # Test renaming the column in the referenced table. ---echo - -# mysqltest first does replace_regex, then replace_result ---replace_regex /'[^']*test\/#sql-[0-9a-f_]*'/'#sql-temporary'/ -# Embedded server doesn't chdir to data directory ---replace_result $MYSQLTEST_VARDIR . mysqld.1/data/ '' ---error ER_ERROR_ON_RENAME -ALTER TABLE t1 CHANGE a c INT; - ---echo # Ensure that online column rename works. - ---enable_info -ALTER TABLE t1 CHANGE b c INT; ---disable_info - ---echo ---echo # Test renaming the column in the referencing table ---echo - -# mysqltest first does replace_regex, then replace_result ---replace_regex /'[^']*test\/#sql-[0-9a-f_]*'/'#sql-temporary'/ -# Embedded server doesn't chdir to data directory ---replace_result $MYSQLTEST_VARDIR . mysqld.1/data/ '' ---error ER_ERROR_ON_RENAME -ALTER TABLE t2 CHANGE a c INT; - ---echo # Ensure that online column rename works. - ---enable_info -ALTER TABLE t2 CHANGE b c INT; ---disable_info - ---echo ---echo # Test with self-referential constraints ---echo - -# mysqltest first does replace_regex, then replace_result ---replace_regex /'[^']*test\/#sql-[0-9a-f_]*'/'#sql-temporary'/ -# Embedded server doesn't chdir to data directory ---replace_result $MYSQLTEST_VARDIR . mysqld.1/data/ '' ---error ER_ERROR_ON_RENAME -ALTER TABLE t3 CHANGE a d INT; - -# mysqltest first does replace_regex, then replace_result ---replace_regex /'[^']*test\/#sql-[0-9a-f_]*'/'#sql-temporary'/ -# Embedded server doesn't chdir to data directory ---replace_result $MYSQLTEST_VARDIR . mysqld.1/data/ '' ---error ER_ERROR_ON_RENAME -ALTER TABLE t3 CHANGE b d INT; - ---echo # Ensure that online column rename works. - ---enable_info -ALTER TABLE t3 CHANGE c d INT; ---disable_info - ---echo ---echo # Cleanup. ---echo - -DROP TABLE t3; -DROP TABLE t2; -DROP TABLE t1; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug34053.result b/storage/innodb_plugin/mysql-test/innodb_bug34053.result deleted file mode 100644 index 195775f74c8..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug34053.result +++ /dev/null @@ -1 +0,0 @@ -SET storage_engine=InnoDB; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug34053.test b/storage/innodb_plugin/mysql-test/innodb_bug34053.test deleted file mode 100644 index b935e45c06d..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug34053.test +++ /dev/null @@ -1,50 +0,0 @@ -# -# Make sure http://bugs.mysql.com/34053 remains fixed. -# - --- source include/not_embedded.inc --- source include/have_innodb.inc - -SET storage_engine=InnoDB; - -# we do not really care about what gets printed, we are only -# interested in getting success or failure according to our -# expectations --- disable_query_log --- disable_result_log - -GRANT USAGE ON *.* TO 'shane'@'localhost' IDENTIFIED BY '12345'; -FLUSH PRIVILEGES; - --- connect (con1,localhost,shane,12345,) - --- connection con1 --- error ER_SPECIFIC_ACCESS_DENIED_ERROR -CREATE TABLE innodb_monitor (a INT) ENGINE=INNODB; --- error ER_SPECIFIC_ACCESS_DENIED_ERROR -CREATE TABLE innodb_mem_validate (a INT) ENGINE=INNODB; -CREATE TABLE innodb_monitorx (a INT) ENGINE=INNODB; -DROP TABLE innodb_monitorx; -CREATE TABLE innodb_monito (a INT) ENGINE=INNODB; -DROP TABLE innodb_monito; -CREATE TABLE xinnodb_monitor (a INT) ENGINE=INNODB; -DROP TABLE xinnodb_monitor; -CREATE TABLE nnodb_monitor (a INT) ENGINE=INNODB; -DROP TABLE nnodb_monitor; - --- connection default -CREATE TABLE innodb_monitor (a INT) ENGINE=INNODB; -CREATE TABLE innodb_mem_validate (a INT) ENGINE=INNODB; - --- connection con1 --- error ER_SPECIFIC_ACCESS_DENIED_ERROR -DROP TABLE innodb_monitor; --- error ER_SPECIFIC_ACCESS_DENIED_ERROR -DROP TABLE innodb_mem_validate; - --- connection default -DROP TABLE innodb_monitor; -DROP TABLE innodb_mem_validate; -DROP USER 'shane'@'localhost'; - --- disconnect con1 diff --git a/storage/innodb_plugin/mysql-test/innodb_bug34300.result b/storage/innodb_plugin/mysql-test/innodb_bug34300.result deleted file mode 100644 index ae9fee81ad7..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug34300.result +++ /dev/null @@ -1,4 +0,0 @@ -f4 f8 -xxx zzz -f4 f8 -xxx zzz diff --git a/storage/innodb_plugin/mysql-test/innodb_bug34300.test b/storage/innodb_plugin/mysql-test/innodb_bug34300.test deleted file mode 100644 index 68c385fd72a..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug34300.test +++ /dev/null @@ -1,34 +0,0 @@ -# -# Bug#34300 Tinyblob & tinytext fields currupted after export/import and alter in 5.1 -# http://bugs.mysql.com/34300 -# - --- source include/have_innodb.inc - --- disable_query_log --- disable_result_log - -# set packet size and reconnect -let $max_packet=`select @@global.max_allowed_packet`; -SET @@global.max_allowed_packet=16777216; ---connect (newconn, localhost, root,,) - -DROP TABLE IF EXISTS bug34300; -CREATE TABLE bug34300 ( - f4 TINYTEXT, - f6 MEDIUMTEXT, - f8 TINYBLOB -) ENGINE=InnoDB; - -INSERT INTO bug34300 VALUES ('xxx', repeat('a', 8459264), 'zzz'); - --- enable_result_log - -SELECT f4, f8 FROM bug34300; - -ALTER TABLE bug34300 ADD COLUMN (f10 INT); - -SELECT f4, f8 FROM bug34300; - -DROP TABLE bug34300; -EVAL SET @@global.max_allowed_packet=$max_packet; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug35220.result b/storage/innodb_plugin/mysql-test/innodb_bug35220.result deleted file mode 100644 index 195775f74c8..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug35220.result +++ /dev/null @@ -1 +0,0 @@ -SET storage_engine=InnoDB; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug35220.test b/storage/innodb_plugin/mysql-test/innodb_bug35220.test deleted file mode 100644 index 26f7d6b1ddd..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug35220.test +++ /dev/null @@ -1,16 +0,0 @@ -# -# Bug#35220 ALTER TABLE too picky on reserved word "foreign" -# http://bugs.mysql.com/35220 -# - --- source include/have_innodb.inc - -SET storage_engine=InnoDB; - -# we care only that the following SQL commands do not produce errors --- disable_query_log --- disable_result_log - -CREATE TABLE bug35220 (foreign_col INT, dummy_cant_delete_all_columns INT); -ALTER TABLE bug35220 DROP foreign_col; -DROP TABLE bug35220; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug36169.result b/storage/innodb_plugin/mysql-test/innodb_bug36169.result deleted file mode 100644 index aa80e4d7aa4..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug36169.result +++ /dev/null @@ -1,2 +0,0 @@ -SET GLOBAL innodb_file_format='Barracuda'; -SET GLOBAL innodb_file_per_table=ON; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug36169.test b/storage/innodb_plugin/mysql-test/innodb_bug36169.test deleted file mode 100644 index 5bf55193b5c..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug36169.test +++ /dev/null @@ -1,1159 +0,0 @@ -# -# Bug#36169 create innodb compressed table with too large row size crashed -# http://bugs.mysql.com/36169 -# - --- source include/have_innodb.inc - -let $file_format=`select @@innodb_file_format`; -let $file_per_table=`select @@innodb_file_per_table`; -SET GLOBAL innodb_file_format='Barracuda'; -SET GLOBAL innodb_file_per_table=ON; - -# -# The following is copied from http://bugs.mysql.com/36169 -# (http://bugs.mysql.com/file.php?id=9121) -# Probably it can be simplified but that is not obvious. -# - -# we care only that the following SQL commands do produce errors -# as expected and do not crash the server --- disable_query_log --- disable_result_log - -# Generating 10 tables -# Creating a table with 94 columns and 24 indexes -DROP TABLE IF EXISTS `table0`; ---error ER_TOO_BIG_ROWSIZE -CREATE TABLE IF NOT EXISTS `table0` -(`col0` BOOL, -`col1` BOOL, -`col2` TINYINT, -`col3` DATE, -`col4` TIME, -`col5` SET ('test1','test2','test3'), -`col6` TIME, -`col7` TEXT, -`col8` DECIMAL, -`col9` SET ('test1','test2','test3'), -`col10` FLOAT, -`col11` DOUBLE PRECISION, -`col12` ENUM ('test1','test2','test3'), -`col13` TINYBLOB, -`col14` YEAR, -`col15` SET ('test1','test2','test3'), -`col16` NUMERIC, -`col17` NUMERIC, -`col18` BLOB, -`col19` DATETIME, -`col20` DOUBLE PRECISION, -`col21` DECIMAL, -`col22` DATETIME, -`col23` NUMERIC, -`col24` NUMERIC, -`col25` LONGTEXT, -`col26` TINYBLOB, -`col27` TIME, -`col28` TINYBLOB, -`col29` ENUM ('test1','test2','test3'), -`col30` SMALLINT, -`col31` REAL, -`col32` FLOAT, -`col33` CHAR (175), -`col34` TINYTEXT, -`col35` TINYTEXT, -`col36` TINYBLOB, -`col37` TINYBLOB, -`col38` TINYTEXT, -`col39` MEDIUMBLOB, -`col40` TIMESTAMP, -`col41` DOUBLE, -`col42` SMALLINT, -`col43` LONGBLOB, -`col44` VARCHAR (80), -`col45` MEDIUMTEXT, -`col46` NUMERIC, -`col47` BIGINT, -`col48` DATE, -`col49` TINYBLOB, -`col50` DATE, -`col51` BOOL, -`col52` MEDIUMINT, -`col53` FLOAT, -`col54` TINYBLOB, -`col55` LONGTEXT, -`col56` SMALLINT, -`col57` ENUM ('test1','test2','test3'), -`col58` DATETIME, -`col59` MEDIUMTEXT, -`col60` VARCHAR (232), -`col61` NUMERIC, -`col62` YEAR, -`col63` SMALLINT, -`col64` TIMESTAMP, -`col65` BLOB, -`col66` LONGBLOB, -`col67` INT, -`col68` LONGTEXT, -`col69` ENUM ('test1','test2','test3'), -`col70` INT, -`col71` TIME, -`col72` TIMESTAMP, -`col73` TIMESTAMP, -`col74` VARCHAR (170), -`col75` SET ('test1','test2','test3'), -`col76` TINYBLOB, -`col77` BIGINT, -`col78` NUMERIC, -`col79` DATETIME, -`col80` YEAR, -`col81` NUMERIC, -`col82` LONGBLOB, -`col83` TEXT, -`col84` CHAR (83), -`col85` DECIMAL, -`col86` FLOAT, -`col87` INT, -`col88` VARCHAR (145), -`col89` DATE, -`col90` DECIMAL, -`col91` DECIMAL, -`col92` MEDIUMBLOB, -`col93` TIME, -KEY `idx0` (`col69`,`col90`,`col8`), -KEY `idx1` (`col60`), -KEY `idx2` (`col60`,`col70`,`col74`), -KEY `idx3` (`col22`,`col32`,`col72`,`col30`), -KEY `idx4` (`col29`), -KEY `idx5` (`col19`,`col45`(143)), -KEY `idx6` (`col46`,`col48`,`col5`,`col39`(118)), -KEY `idx7` (`col48`,`col61`), -KEY `idx8` (`col93`), -KEY `idx9` (`col31`), -KEY `idx10` (`col30`,`col21`), -KEY `idx11` (`col67`), -KEY `idx12` (`col44`,`col6`,`col8`,`col38`(226)), -KEY `idx13` (`col71`,`col41`,`col15`,`col49`(88)), -KEY `idx14` (`col78`), -KEY `idx15` (`col63`,`col67`,`col64`), -KEY `idx16` (`col17`,`col86`), -KEY `idx17` (`col77`,`col56`,`col10`,`col55`(24)), -KEY `idx18` (`col62`), -KEY `idx19` (`col31`,`col57`,`col56`,`col53`), -KEY `idx20` (`col46`), -KEY `idx21` (`col83`(54)), -KEY `idx22` (`col51`,`col7`(120)), -KEY `idx23` (`col7`(163),`col31`,`col71`,`col14`) -)engine=innodb ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=1; - -# Creating a table with 10 columns and 32 indexes -DROP TABLE IF EXISTS `table1`; ---error ER_TOO_BIG_ROWSIZE -CREATE TABLE IF NOT EXISTS `table1` -(`col0` CHAR (113), -`col1` FLOAT, -`col2` BIGINT, -`col3` DECIMAL, -`col4` BLOB, -`col5` LONGTEXT, -`col6` SET ('test1','test2','test3'), -`col7` BIGINT, -`col8` BIGINT, -`col9` TINYBLOB, -KEY `idx0` (`col5`(101),`col7`,`col8`), -KEY `idx1` (`col8`), -KEY `idx2` (`col4`(177),`col9`(126),`col6`,`col3`), -KEY `idx3` (`col5`(160)), -KEY `idx4` (`col9`(242)), -KEY `idx5` (`col4`(139),`col2`,`col3`), -KEY `idx6` (`col7`), -KEY `idx7` (`col6`,`col2`,`col0`,`col3`), -KEY `idx8` (`col9`(66)), -KEY `idx9` (`col5`(253)), -KEY `idx10` (`col1`,`col7`,`col2`), -KEY `idx11` (`col9`(242),`col0`,`col8`,`col5`(163)), -KEY `idx12` (`col8`), -KEY `idx13` (`col0`,`col9`(37)), -KEY `idx14` (`col0`), -KEY `idx15` (`col5`(111)), -KEY `idx16` (`col8`,`col0`,`col5`(13)), -KEY `idx17` (`col4`(139)), -KEY `idx18` (`col5`(189),`col2`,`col3`,`col9`(136)), -KEY `idx19` (`col0`,`col3`,`col1`,`col8`), -KEY `idx20` (`col8`), -KEY `idx21` (`col0`,`col7`,`col9`(227),`col3`), -KEY `idx22` (`col0`), -KEY `idx23` (`col2`), -KEY `idx24` (`col3`), -KEY `idx25` (`col2`,`col3`), -KEY `idx26` (`col0`), -KEY `idx27` (`col5`(254)), -KEY `idx28` (`col3`), -KEY `idx29` (`col3`), -KEY `idx30` (`col7`,`col3`,`col0`,`col4`(220)), -KEY `idx31` (`col4`(1),`col0`) -)engine=innodb ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=1; - -# Creating a table with 141 columns and 18 indexes -DROP TABLE IF EXISTS `table2`; ---error ER_TOO_BIG_ROWSIZE -CREATE TABLE IF NOT EXISTS `table2` -(`col0` BOOL, -`col1` MEDIUMINT, -`col2` VARCHAR (209), -`col3` MEDIUMBLOB, -`col4` CHAR (13), -`col5` DOUBLE, -`col6` TINYTEXT, -`col7` REAL, -`col8` SMALLINT, -`col9` BLOB, -`col10` TINYINT, -`col11` DECIMAL, -`col12` BLOB, -`col13` DECIMAL, -`col14` LONGBLOB, -`col15` SMALLINT, -`col16` LONGBLOB, -`col17` TINYTEXT, -`col18` FLOAT, -`col19` CHAR (78), -`col20` MEDIUMTEXT, -`col21` SET ('test1','test2','test3'), -`col22` MEDIUMINT, -`col23` INT, -`col24` MEDIUMBLOB, -`col25` ENUM ('test1','test2','test3'), -`col26` TINYBLOB, -`col27` VARCHAR (116), -`col28` TIMESTAMP, -`col29` BLOB, -`col30` SMALLINT, -`col31` DOUBLE PRECISION, -`col32` DECIMAL, -`col33` DECIMAL, -`col34` TEXT, -`col35` MEDIUMINT, -`col36` MEDIUMINT, -`col37` BIGINT, -`col38` VARCHAR (253), -`col39` TINYBLOB, -`col40` MEDIUMBLOB, -`col41` BIGINT, -`col42` DOUBLE, -`col43` TEXT, -`col44` BLOB, -`col45` TIME, -`col46` MEDIUMINT, -`col47` DOUBLE PRECISION, -`col48` SET ('test1','test2','test3'), -`col49` DOUBLE PRECISION, -`col50` VARCHAR (97), -`col51` TEXT, -`col52` NUMERIC, -`col53` ENUM ('test1','test2','test3'), -`col54` MEDIUMTEXT, -`col55` MEDIUMINT, -`col56` DATETIME, -`col57` DATETIME, -`col58` MEDIUMTEXT, -`col59` CHAR (244), -`col60` LONGBLOB, -`col61` MEDIUMBLOB, -`col62` DOUBLE, -`col63` SMALLINT, -`col64` BOOL, -`col65` SMALLINT, -`col66` VARCHAR (212), -`col67` TIME, -`col68` REAL, -`col69` BOOL, -`col70` BIGINT, -`col71` DATE, -`col72` TINYINT, -`col73` ENUM ('test1','test2','test3'), -`col74` DATE, -`col75` TIME, -`col76` DATETIME, -`col77` BOOL, -`col78` TINYTEXT, -`col79` MEDIUMINT, -`col80` NUMERIC, -`col81` LONGTEXT, -`col82` SET ('test1','test2','test3'), -`col83` DOUBLE PRECISION, -`col84` NUMERIC, -`col85` VARCHAR (184), -`col86` DOUBLE PRECISION, -`col87` MEDIUMTEXT, -`col88` MEDIUMBLOB, -`col89` BOOL, -`col90` SMALLINT, -`col91` TINYINT, -`col92` ENUM ('test1','test2','test3'), -`col93` BOOL, -`col94` TIMESTAMP, -`col95` BOOL, -`col96` MEDIUMTEXT, -`col97` DECIMAL, -`col98` BOOL, -`col99` DECIMAL, -`col100` MEDIUMINT, -`col101` DOUBLE PRECISION, -`col102` TINYINT, -`col103` BOOL, -`col104` MEDIUMINT, -`col105` DECIMAL, -`col106` NUMERIC, -`col107` TIMESTAMP, -`col108` MEDIUMBLOB, -`col109` TINYBLOB, -`col110` SET ('test1','test2','test3'), -`col111` YEAR, -`col112` TIMESTAMP, -`col113` CHAR (201), -`col114` BOOL, -`col115` TINYINT, -`col116` DOUBLE, -`col117` TINYINT, -`col118` TIMESTAMP, -`col119` SET ('test1','test2','test3'), -`col120` SMALLINT, -`col121` TINYBLOB, -`col122` TIMESTAMP, -`col123` BLOB, -`col124` DATE, -`col125` SMALLINT, -`col126` ENUM ('test1','test2','test3'), -`col127` MEDIUMBLOB, -`col128` DOUBLE PRECISION, -`col129` REAL, -`col130` VARCHAR (159), -`col131` MEDIUMBLOB, -`col132` BIGINT, -`col133` INT, -`col134` SET ('test1','test2','test3'), -`col135` CHAR (198), -`col136` SET ('test1','test2','test3'), -`col137` MEDIUMTEXT, -`col138` SMALLINT, -`col139` BLOB, -`col140` LONGBLOB, -KEY `idx0` (`col14`(139),`col24`(208),`col38`,`col35`), -KEY `idx1` (`col48`,`col118`,`col29`(131),`col100`), -KEY `idx2` (`col86`,`col67`,`col43`(175)), -KEY `idx3` (`col19`), -KEY `idx4` (`col40`(220),`col67`), -KEY `idx5` (`col99`,`col56`), -KEY `idx6` (`col68`,`col28`,`col137`(157)), -KEY `idx7` (`col51`(160),`col99`,`col45`,`col39`(9)), -KEY `idx8` (`col15`,`col52`,`col90`,`col94`), -KEY `idx9` (`col24`(3),`col139`(248),`col108`(118),`col41`), -KEY `idx10` (`col36`,`col92`,`col114`), -KEY `idx11` (`col115`,`col9`(116)), -KEY `idx12` (`col130`,`col93`,`col134`), -KEY `idx13` (`col123`(65)), -KEY `idx14` (`col44`(90),`col86`,`col119`), -KEY `idx15` (`col69`), -KEY `idx16` (`col132`,`col81`(118),`col18`), -KEY `idx17` (`col24`(250),`col7`,`col92`,`col45`) -)engine=innodb ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=1; - -# Creating a table with 199 columns and 1 indexes -DROP TABLE IF EXISTS `table3`; ---error ER_TOO_BIG_ROWSIZE -CREATE TABLE IF NOT EXISTS `table3` -(`col0` SMALLINT, -`col1` SET ('test1','test2','test3'), -`col2` TINYTEXT, -`col3` DOUBLE, -`col4` NUMERIC, -`col5` DATE, -`col6` BIGINT, -`col7` DOUBLE, -`col8` TEXT, -`col9` INT, -`col10` REAL, -`col11` TINYINT, -`col12` NUMERIC, -`col13` NUMERIC, -`col14` TIME, -`col15` DOUBLE, -`col16` REAL, -`col17` MEDIUMBLOB, -`col18` YEAR, -`col19` TINYTEXT, -`col20` YEAR, -`col21` CHAR (250), -`col22` TINYINT, -`col23` TINYINT, -`col24` SMALLINT, -`col25` DATETIME, -`col26` MEDIUMINT, -`col27` LONGBLOB, -`col28` VARCHAR (106), -`col29` FLOAT, -`col30` MEDIUMTEXT, -`col31` TINYBLOB, -`col32` BIGINT, -`col33` YEAR, -`col34` REAL, -`col35` MEDIUMBLOB, -`col36` LONGTEXT, -`col37` LONGBLOB, -`col38` BIGINT, -`col39` FLOAT, -`col40` TIME, -`col41` DATETIME, -`col42` BOOL, -`col43` BIGINT, -`col44` SMALLINT, -`col45` TIME, -`col46` DOUBLE PRECISION, -`col47` TIME, -`col48` TINYTEXT, -`col49` DOUBLE PRECISION, -`col50` BIGINT, -`col51` NUMERIC, -`col52` TINYBLOB, -`col53` DATE, -`col54` DECIMAL, -`col55` SMALLINT, -`col56` TINYTEXT, -`col57` ENUM ('test1','test2','test3'), -`col58` YEAR, -`col59` TIME, -`col60` TINYINT, -`col61` DECIMAL, -`col62` DOUBLE, -`col63` DATE, -`col64` LONGTEXT, -`col65` DOUBLE, -`col66` VARCHAR (88), -`col67` MEDIUMTEXT, -`col68` DATE, -`col69` MEDIUMINT, -`col70` DECIMAL, -`col71` MEDIUMTEXT, -`col72` LONGTEXT, -`col73` REAL, -`col74` DOUBLE, -`col75` TIME, -`col76` DATE, -`col77` DECIMAL, -`col78` MEDIUMBLOB, -`col79` NUMERIC, -`col80` BIGINT, -`col81` YEAR, -`col82` SMALLINT, -`col83` MEDIUMINT, -`col84` TINYINT, -`col85` MEDIUMBLOB, -`col86` TIME, -`col87` MEDIUMBLOB, -`col88` LONGTEXT, -`col89` BOOL, -`col90` BLOB, -`col91` LONGBLOB, -`col92` YEAR, -`col93` BLOB, -`col94` INT, -`col95` TINYTEXT, -`col96` TINYINT, -`col97` DECIMAL, -`col98` ENUM ('test1','test2','test3'), -`col99` MEDIUMINT, -`col100` TINYINT, -`col101` MEDIUMBLOB, -`col102` TINYINT, -`col103` SET ('test1','test2','test3'), -`col104` TIMESTAMP, -`col105` TEXT, -`col106` DATETIME, -`col107` MEDIUMTEXT, -`col108` CHAR (220), -`col109` TIME, -`col110` VARCHAR (131), -`col111` DECIMAL, -`col112` FLOAT, -`col113` SMALLINT, -`col114` BIGINT, -`col115` LONGBLOB, -`col116` SET ('test1','test2','test3'), -`col117` ENUM ('test1','test2','test3'), -`col118` BLOB, -`col119` MEDIUMTEXT, -`col120` SET ('test1','test2','test3'), -`col121` DATETIME, -`col122` FLOAT, -`col123` VARCHAR (242), -`col124` YEAR, -`col125` MEDIUMBLOB, -`col126` TIME, -`col127` BOOL, -`col128` TINYBLOB, -`col129` DOUBLE, -`col130` TINYINT, -`col131` BIGINT, -`col132` SMALLINT, -`col133` INT, -`col134` DOUBLE PRECISION, -`col135` MEDIUMBLOB, -`col136` SET ('test1','test2','test3'), -`col137` TINYTEXT, -`col138` DOUBLE PRECISION, -`col139` NUMERIC, -`col140` BLOB, -`col141` SET ('test1','test2','test3'), -`col142` INT, -`col143` VARCHAR (26), -`col144` BLOB, -`col145` REAL, -`col146` SET ('test1','test2','test3'), -`col147` LONGBLOB, -`col148` TEXT, -`col149` BLOB, -`col150` CHAR (189), -`col151` LONGTEXT, -`col152` INT, -`col153` FLOAT, -`col154` LONGTEXT, -`col155` DATE, -`col156` LONGBLOB, -`col157` TINYBLOB, -`col158` REAL, -`col159` DATE, -`col160` TIME, -`col161` YEAR, -`col162` DOUBLE, -`col163` VARCHAR (90), -`col164` FLOAT, -`col165` NUMERIC, -`col166` ENUM ('test1','test2','test3'), -`col167` DOUBLE PRECISION, -`col168` DOUBLE PRECISION, -`col169` TINYBLOB, -`col170` TIME, -`col171` SMALLINT, -`col172` TINYTEXT, -`col173` SMALLINT, -`col174` DOUBLE, -`col175` VARCHAR (14), -`col176` VARCHAR (90), -`col177` REAL, -`col178` MEDIUMINT, -`col179` TINYBLOB, -`col180` FLOAT, -`col181` TIMESTAMP, -`col182` REAL, -`col183` DOUBLE PRECISION, -`col184` BIGINT, -`col185` INT, -`col186` MEDIUMTEXT, -`col187` TIME, -`col188` FLOAT, -`col189` TIME, -`col190` INT, -`col191` FLOAT, -`col192` MEDIUMINT, -`col193` TINYINT, -`col194` MEDIUMTEXT, -`col195` DATE, -`col196` TIME, -`col197` YEAR, -`col198` CHAR (206), -KEY `idx0` (`col39`,`col23`) -)engine=innodb ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=1; - -# Creating a table with 133 columns and 16 indexes -DROP TABLE IF EXISTS `table4`; ---error ER_TOO_BIG_ROWSIZE -CREATE TABLE IF NOT EXISTS `table4` -(`col0` VARCHAR (60), -`col1` NUMERIC, -`col2` LONGTEXT, -`col3` MEDIUMTEXT, -`col4` LONGTEXT, -`col5` LONGBLOB, -`col6` LONGBLOB, -`col7` DATETIME, -`col8` TINYTEXT, -`col9` BLOB, -`col10` BOOL, -`col11` BIGINT, -`col12` TEXT, -`col13` VARCHAR (213), -`col14` TINYBLOB, -`col15` BOOL, -`col16` MEDIUMTEXT, -`col17` DOUBLE, -`col18` TEXT, -`col19` BLOB, -`col20` SET ('test1','test2','test3'), -`col21` TINYINT, -`col22` DATETIME, -`col23` TINYINT, -`col24` ENUM ('test1','test2','test3'), -`col25` REAL, -`col26` BOOL, -`col27` FLOAT, -`col28` LONGBLOB, -`col29` DATETIME, -`col30` FLOAT, -`col31` SET ('test1','test2','test3'), -`col32` LONGBLOB, -`col33` NUMERIC, -`col34` YEAR, -`col35` VARCHAR (146), -`col36` BIGINT, -`col37` DATETIME, -`col38` DATE, -`col39` SET ('test1','test2','test3'), -`col40` CHAR (112), -`col41` FLOAT, -`col42` YEAR, -`col43` TIME, -`col44` DOUBLE, -`col45` NUMERIC, -`col46` FLOAT, -`col47` DECIMAL, -`col48` BIGINT, -`col49` DECIMAL, -`col50` YEAR, -`col51` MEDIUMTEXT, -`col52` LONGBLOB, -`col53` SET ('test1','test2','test3'), -`col54` BLOB, -`col55` FLOAT, -`col56` REAL, -`col57` REAL, -`col58` TEXT, -`col59` MEDIUMBLOB, -`col60` INT, -`col61` INT, -`col62` DATE, -`col63` TEXT, -`col64` DATE, -`col65` ENUM ('test1','test2','test3'), -`col66` DOUBLE PRECISION, -`col67` TINYTEXT, -`col68` TINYBLOB, -`col69` FLOAT, -`col70` BLOB, -`col71` DATETIME, -`col72` DOUBLE, -`col73` LONGTEXT, -`col74` TIME, -`col75` DATETIME, -`col76` VARCHAR (122), -`col77` MEDIUMTEXT, -`col78` MEDIUMTEXT, -`col79` BOOL, -`col80` LONGTEXT, -`col81` TINYTEXT, -`col82` NUMERIC, -`col83` DOUBLE PRECISION, -`col84` DATE, -`col85` YEAR, -`col86` BLOB, -`col87` TINYTEXT, -`col88` DOUBLE PRECISION, -`col89` MEDIUMINT, -`col90` MEDIUMTEXT, -`col91` NUMERIC, -`col92` DATETIME, -`col93` NUMERIC, -`col94` SET ('test1','test2','test3'), -`col95` TINYTEXT, -`col96` SET ('test1','test2','test3'), -`col97` YEAR, -`col98` MEDIUMINT, -`col99` TEXT, -`col100` TEXT, -`col101` TIME, -`col102` VARCHAR (225), -`col103` TINYTEXT, -`col104` TEXT, -`col105` MEDIUMTEXT, -`col106` TINYINT, -`col107` TEXT, -`col108` LONGBLOB, -`col109` LONGTEXT, -`col110` TINYTEXT, -`col111` CHAR (56), -`col112` YEAR, -`col113` ENUM ('test1','test2','test3'), -`col114` TINYBLOB, -`col115` DATETIME, -`col116` DATE, -`col117` TIME, -`col118` MEDIUMTEXT, -`col119` DOUBLE PRECISION, -`col120` FLOAT, -`col121` TIMESTAMP, -`col122` MEDIUMINT, -`col123` YEAR, -`col124` DATE, -`col125` TEXT, -`col126` FLOAT, -`col127` TINYTEXT, -`col128` BOOL, -`col129` NUMERIC, -`col130` TIMESTAMP, -`col131` INT, -`col132` MEDIUMBLOB, -KEY `idx0` (`col130`), -KEY `idx1` (`col30`,`col55`,`col19`(31)), -KEY `idx2` (`col104`(186)), -KEY `idx3` (`col131`), -KEY `idx4` (`col64`,`col93`,`col2`(11)), -KEY `idx5` (`col34`,`col121`,`col22`), -KEY `idx6` (`col33`,`col55`,`col83`), -KEY `idx7` (`col17`,`col87`(245),`col99`(17)), -KEY `idx8` (`col65`,`col120`), -KEY `idx9` (`col82`), -KEY `idx10` (`col9`(72)), -KEY `idx11` (`col88`), -KEY `idx12` (`col128`,`col9`(200),`col71`,`col66`), -KEY `idx13` (`col77`(126)), -KEY `idx14` (`col105`(26),`col13`,`col117`), -KEY `idx15` (`col4`(246),`col130`,`col115`,`col3`(141)) -)engine=innodb ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=1; - -# Creating a table with 176 columns and 13 indexes -DROP TABLE IF EXISTS `table5`; ---error ER_TOO_BIG_ROWSIZE -CREATE TABLE IF NOT EXISTS `table5` -(`col0` MEDIUMTEXT, -`col1` VARCHAR (90), -`col2` TINYTEXT, -`col3` TIME, -`col4` BOOL, -`col5` TINYTEXT, -`col6` BOOL, -`col7` TIMESTAMP, -`col8` TINYBLOB, -`col9` TINYINT, -`col10` YEAR, -`col11` SET ('test1','test2','test3'), -`col12` TEXT, -`col13` CHAR (248), -`col14` BIGINT, -`col15` TEXT, -`col16` TINYINT, -`col17` NUMERIC, -`col18` SET ('test1','test2','test3'), -`col19` LONGBLOB, -`col20` FLOAT, -`col21` INT, -`col22` TEXT, -`col23` BOOL, -`col24` DECIMAL, -`col25` DOUBLE PRECISION, -`col26` FLOAT, -`col27` TINYBLOB, -`col28` NUMERIC, -`col29` MEDIUMBLOB, -`col30` DATE, -`col31` LONGTEXT, -`col32` DATE, -`col33` FLOAT, -`col34` BIGINT, -`col35` TINYTEXT, -`col36` MEDIUMTEXT, -`col37` TIME, -`col38` INT, -`col39` TINYINT, -`col40` SET ('test1','test2','test3'), -`col41` CHAR (130), -`col42` SMALLINT, -`col43` INT, -`col44` MEDIUMTEXT, -`col45` VARCHAR (126), -`col46` INT, -`col47` DOUBLE PRECISION, -`col48` BIGINT, -`col49` MEDIUMTEXT, -`col50` TINYBLOB, -`col51` MEDIUMINT, -`col52` TEXT, -`col53` VARCHAR (208), -`col54` VARCHAR (207), -`col55` NUMERIC, -`col56` DATETIME, -`col57` ENUM ('test1','test2','test3'), -`col58` NUMERIC, -`col59` TINYBLOB, -`col60` VARCHAR (73), -`col61` MEDIUMTEXT, -`col62` TINYBLOB, -`col63` DATETIME, -`col64` NUMERIC, -`col65` MEDIUMINT, -`col66` DATETIME, -`col67` NUMERIC, -`col68` TINYINT, -`col69` VARCHAR (58), -`col70` DECIMAL, -`col71` MEDIUMTEXT, -`col72` DATE, -`col73` TIME, -`col74` DOUBLE PRECISION, -`col75` DECIMAL, -`col76` MEDIUMBLOB, -`col77` REAL, -`col78` YEAR, -`col79` YEAR, -`col80` LONGBLOB, -`col81` BLOB, -`col82` BIGINT, -`col83` ENUM ('test1','test2','test3'), -`col84` NUMERIC, -`col85` SET ('test1','test2','test3'), -`col86` MEDIUMTEXT, -`col87` LONGBLOB, -`col88` TIME, -`col89` ENUM ('test1','test2','test3'), -`col90` DECIMAL, -`col91` FLOAT, -`col92` DATETIME, -`col93` TINYTEXT, -`col94` TIMESTAMP, -`col95` TIMESTAMP, -`col96` TEXT, -`col97` REAL, -`col98` VARCHAR (198), -`col99` TIME, -`col100` TINYINT, -`col101` BIGINT, -`col102` LONGBLOB, -`col103` LONGBLOB, -`col104` MEDIUMINT, -`col105` MEDIUMTEXT, -`col106` TIMESTAMP, -`col107` SMALLINT, -`col108` NUMERIC, -`col109` DECIMAL, -`col110` FLOAT, -`col111` DECIMAL, -`col112` REAL, -`col113` TINYTEXT, -`col114` FLOAT, -`col115` VARCHAR (7), -`col116` LONGTEXT, -`col117` DATE, -`col118` BIGINT, -`col119` TEXT, -`col120` BIGINT, -`col121` BLOB, -`col122` CHAR (110), -`col123` NUMERIC, -`col124` MEDIUMBLOB, -`col125` NUMERIC, -`col126` NUMERIC, -`col127` BOOL, -`col128` TIME, -`col129` TINYBLOB, -`col130` TINYBLOB, -`col131` DATE, -`col132` INT, -`col133` VARCHAR (123), -`col134` CHAR (238), -`col135` VARCHAR (225), -`col136` LONGTEXT, -`col137` LONGBLOB, -`col138` REAL, -`col139` TINYBLOB, -`col140` DATETIME, -`col141` TINYTEXT, -`col142` LONGBLOB, -`col143` BIGINT, -`col144` VARCHAR (236), -`col145` TEXT, -`col146` YEAR, -`col147` DECIMAL, -`col148` TEXT, -`col149` MEDIUMBLOB, -`col150` TINYINT, -`col151` BOOL, -`col152` VARCHAR (72), -`col153` INT, -`col154` VARCHAR (165), -`col155` TINYINT, -`col156` MEDIUMTEXT, -`col157` DOUBLE PRECISION, -`col158` TIME, -`col159` MEDIUMBLOB, -`col160` LONGBLOB, -`col161` DATETIME, -`col162` DOUBLE PRECISION, -`col163` BLOB, -`col164` ENUM ('test1','test2','test3'), -`col165` TIMESTAMP, -`col166` DATE, -`col167` TINYBLOB, -`col168` TINYBLOB, -`col169` LONGBLOB, -`col170` DATETIME, -`col171` BIGINT, -`col172` VARCHAR (30), -`col173` LONGTEXT, -`col174` TIME, -`col175` FLOAT, -KEY `idx0` (`col16`,`col156`(139),`col97`,`col120`), -KEY `idx1` (`col24`,`col0`(108)), -KEY `idx2` (`col117`,`col173`(34),`col132`,`col82`), -KEY `idx3` (`col2`(86)), -KEY `idx4` (`col2`(43)), -KEY `idx5` (`col83`,`col35`(87),`col111`), -KEY `idx6` (`col6`,`col134`,`col92`), -KEY `idx7` (`col56`), -KEY `idx8` (`col30`,`col53`,`col129`(66)), -KEY `idx9` (`col53`,`col113`(211),`col32`,`col15`(75)), -KEY `idx10` (`col34`), -KEY `idx11` (`col126`), -KEY `idx12` (`col24`) -)engine=innodb ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=1; - -# Creating a table with 179 columns and 46 indexes -DROP TABLE IF EXISTS `table6`; --- error ER_TOO_BIG_ROWSIZE ---error ER_TOO_BIG_ROWSIZE -CREATE TABLE IF NOT EXISTS `table6` -(`col0` ENUM ('test1','test2','test3'), -`col1` MEDIUMBLOB, -`col2` MEDIUMBLOB, -`col3` DATETIME, -`col4` DATE, -`col5` YEAR, -`col6` REAL, -`col7` NUMERIC, -`col8` MEDIUMBLOB, -`col9` TEXT, -`col10` TIMESTAMP, -`col11` DOUBLE, -`col12` DOUBLE, -`col13` SMALLINT, -`col14` TIMESTAMP, -`col15` DECIMAL, -`col16` DATE, -`col17` TEXT, -`col18` LONGBLOB, -`col19` BIGINT, -`col20` FLOAT, -`col21` DATETIME, -`col22` TINYINT, -`col23` MEDIUMBLOB, -`col24` SET ('test1','test2','test3'), -`col25` TIME, -`col26` TEXT, -`col27` LONGTEXT, -`col28` BIGINT, -`col29` REAL, -`col30` YEAR, -`col31` MEDIUMBLOB, -`col32` MEDIUMINT, -`col33` FLOAT, -`col34` TEXT, -`col35` DATE, -`col36` TIMESTAMP, -`col37` REAL, -`col38` BLOB, -`col39` BLOB, -`col40` BLOB, -`col41` TINYBLOB, -`col42` INT, -`col43` TINYINT, -`col44` REAL, -`col45` BIGINT, -`col46` TIMESTAMP, -`col47` BLOB, -`col48` ENUM ('test1','test2','test3'), -`col49` BOOL, -`col50` CHAR (109), -`col51` DOUBLE, -`col52` DOUBLE PRECISION, -`col53` ENUM ('test1','test2','test3'), -`col54` FLOAT, -`col55` DOUBLE PRECISION, -`col56` CHAR (166), -`col57` TEXT, -`col58` TIME, -`col59` DECIMAL, -`col60` TEXT, -`col61` ENUM ('test1','test2','test3'), -`col62` LONGTEXT, -`col63` YEAR, -`col64` DOUBLE, -`col65` CHAR (87), -`col66` DATE, -`col67` BOOL, -`col68` MEDIUMBLOB, -`col69` DATETIME, -`col70` DECIMAL, -`col71` TIME, -`col72` REAL, -`col73` LONGTEXT, -`col74` BLOB, -`col75` REAL, -`col76` INT, -`col77` INT, -`col78` FLOAT, -`col79` DOUBLE, -`col80` MEDIUMINT, -`col81` ENUM ('test1','test2','test3'), -`col82` VARCHAR (221), -`col83` BIGINT, -`col84` TINYINT, -`col85` BIGINT, -`col86` FLOAT, -`col87` MEDIUMBLOB, -`col88` CHAR (126), -`col89` MEDIUMBLOB, -`col90` DATETIME, -`col91` TINYINT, -`col92` DOUBLE, -`col93` NUMERIC, -`col94` DATE, -`col95` BLOB, -`col96` DATETIME, -`col97` TIME, -`col98` LONGBLOB, -`col99` INT, -`col100` SET ('test1','test2','test3'), -`col101` TINYBLOB, -`col102` INT, -`col103` MEDIUMBLOB, -`col104` MEDIUMTEXT, -`col105` FLOAT, -`col106` TINYBLOB, -`col107` VARCHAR (26), -`col108` TINYINT, -`col109` TIME, -`col110` TINYBLOB, -`col111` LONGBLOB, -`col112` TINYTEXT, -`col113` FLOAT, -`col114` TINYINT, -`col115` NUMERIC, -`col116` TIME, -`col117` SET ('test1','test2','test3'), -`col118` DATE, -`col119` SMALLINT, -`col120` BLOB, -`col121` TINYTEXT, -`col122` REAL, -`col123` YEAR, -`col124` REAL, -`col125` BOOL, -`col126` BLOB, -`col127` REAL, -`col128` MEDIUMBLOB, -`col129` TIMESTAMP, -`col130` LONGBLOB, -`col131` MEDIUMBLOB, -`col132` YEAR, -`col133` YEAR, -`col134` INT, -`col135` MEDIUMINT, -`col136` MEDIUMINT, -`col137` TINYTEXT, -`col138` TINYBLOB, -`col139` BLOB, -`col140` SET ('test1','test2','test3'), -`col141` ENUM ('test1','test2','test3'), -`col142` ENUM ('test1','test2','test3'), -`col143` TINYTEXT, -`col144` DATETIME, -`col145` TEXT, -`col146` DOUBLE PRECISION, -`col147` DECIMAL, -`col148` MEDIUMTEXT, -`col149` TINYTEXT, -`col150` SET ('test1','test2','test3'), -`col151` MEDIUMTEXT, -`col152` CHAR (126), -`col153` DOUBLE, -`col154` CHAR (243), -`col155` SET ('test1','test2','test3'), -`col156` SET ('test1','test2','test3'), -`col157` DATETIME, -`col158` DOUBLE, -`col159` NUMERIC, -`col160` DECIMAL, -`col161` FLOAT, -`col162` LONGBLOB, -`col163` LONGTEXT, -`col164` INT, -`col165` TIME, -`col166` CHAR (27), -`col167` VARCHAR (63), -`col168` TEXT, -`col169` TINYBLOB, -`col170` TINYBLOB, -`col171` ENUM ('test1','test2','test3'), -`col172` INT, -`col173` TIME, -`col174` DECIMAL, -`col175` DOUBLE, -`col176` MEDIUMBLOB, -`col177` LONGBLOB, -`col178` CHAR (43), -KEY `idx0` (`col131`(219)), -KEY `idx1` (`col67`,`col122`,`col59`,`col87`(33)), -KEY `idx2` (`col83`,`col42`,`col57`(152)), -KEY `idx3` (`col106`(124)), -KEY `idx4` (`col173`,`col80`,`col165`,`col89`(78)), -KEY `idx5` (`col174`,`col145`(108),`col23`(228),`col141`), -KEY `idx6` (`col157`,`col140`), -KEY `idx7` (`col130`(188),`col15`), -KEY `idx8` (`col52`), -KEY `idx9` (`col144`), -KEY `idx10` (`col155`), -KEY `idx11` (`col62`(230),`col1`(109)), -KEY `idx12` (`col151`(24),`col95`(85)), -KEY `idx13` (`col114`), -KEY `idx14` (`col42`,`col98`(56),`col146`), -KEY `idx15` (`col147`,`col39`(254),`col35`), -KEY `idx16` (`col79`), -KEY `idx17` (`col65`), -KEY `idx18` (`col149`(165),`col168`(119),`col32`,`col117`), -KEY `idx19` (`col64`), -KEY `idx20` (`col93`), -KEY `idx21` (`col64`,`col113`,`col104`(182)), -KEY `idx22` (`col52`,`col111`(189)), -KEY `idx23` (`col45`), -KEY `idx24` (`col154`,`col107`,`col110`(159)), -KEY `idx25` (`col149`(1),`col87`(131)), -KEY `idx26` (`col58`,`col115`,`col63`), -KEY `idx27` (`col95`(9),`col0`,`col87`(113)), -KEY `idx28` (`col92`,`col130`(1)), -KEY `idx29` (`col151`(129),`col137`(254),`col13`), -KEY `idx30` (`col49`), -KEY `idx31` (`col28`), -KEY `idx32` (`col83`,`col146`), -KEY `idx33` (`col155`,`col90`,`col17`(245)), -KEY `idx34` (`col174`,`col169`(44),`col107`), -KEY `idx35` (`col113`), -KEY `idx36` (`col52`), -KEY `idx37` (`col16`,`col120`(190)), -KEY `idx38` (`col28`), -KEY `idx39` (`col131`(165)), -KEY `idx40` (`col135`,`col26`(86)), -KEY `idx41` (`col69`,`col94`), -KEY `idx42` (`col105`,`col151`(38),`col97`), -KEY `idx43` (`col88`), -KEY `idx44` (`col176`(100),`col42`,`col73`(189),`col94`), -KEY `idx45` (`col2`(27),`col27`(116)) -)engine=innodb ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=1; - -DROP TABLE IF EXISTS table0; -DROP TABLE IF EXISTS table1; -DROP TABLE IF EXISTS table2; -DROP TABLE IF EXISTS table3; -DROP TABLE IF EXISTS table4; -DROP TABLE IF EXISTS table5; -DROP TABLE IF EXISTS table6; - -EVAL SET GLOBAL innodb_file_format=$file_format; -EVAL SET GLOBAL innodb_file_per_table=$file_per_table; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug36172.result b/storage/innodb_plugin/mysql-test/innodb_bug36172.result deleted file mode 100644 index 195775f74c8..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug36172.result +++ /dev/null @@ -1 +0,0 @@ -SET storage_engine=InnoDB; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug36172.test b/storage/innodb_plugin/mysql-test/innodb_bug36172.test deleted file mode 100644 index c6c4e6fae47..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug36172.test +++ /dev/null @@ -1,32 +0,0 @@ -# -# Test case for bug 36172 -# - --- source include/not_embedded.inc --- source include/have_innodb.inc - -SET storage_engine=InnoDB; - -# we do not really care about what gets printed, we are only -# interested in getting success or failure according to our -# expectations - --- disable_query_log --- disable_result_log - -let $file_format=`select @@innodb_file_format`; -let $file_format_check=`select @@innodb_file_format_check`; -let $file_per_table=`select @@innodb_file_per_table`; -SET GLOBAL innodb_file_format='Barracuda'; -SET GLOBAL innodb_file_per_table=on; - -DROP TABLE IF EXISTS `table0`; -CREATE TABLE `table0` ( `col0` tinyint(1) DEFAULT NULL, `col1` tinyint(1) DEFAULT NULL, `col2` tinyint(4) DEFAULT NULL, `col3` date DEFAULT NULL, `col4` time DEFAULT NULL, `col5` set('test1','test2','test3') DEFAULT NULL, `col6` time DEFAULT NULL, `col7` text, `col8` decimal(10,0) DEFAULT NULL, `col9` set('test1','test2','test3') DEFAULT NULL, `col10` float DEFAULT NULL, `col11` double DEFAULT NULL, `col12` enum('test1','test2','test3') DEFAULT NULL, `col13` tinyblob, `col14` year(4) DEFAULT NULL, `col15` set('test1','test2','test3') DEFAULT NULL, `col16` decimal(10,0) DEFAULT NULL, `col17` decimal(10,0) DEFAULT NULL, `col18` blob, `col19` datetime DEFAULT NULL, `col20` double DEFAULT NULL, `col21` decimal(10,0) DEFAULT NULL, `col22` datetime DEFAULT NULL, `col23` decimal(10,0) DEFAULT NULL, `col24` decimal(10,0) DEFAULT NULL, `col25` longtext, `col26` tinyblob, `col27` time DEFAULT NULL, `col28` tinyblob, `col29` enum('test1','test2','test3') DEFAULT NULL, `col30` smallint(6) DEFAULT NULL, `col31` double DEFAULT NULL, `col32` float DEFAULT NULL, `col33` char(175) DEFAULT NULL, `col34` tinytext, `col35` tinytext, `col36` tinyblob, `col37` tinyblob, `col38` tinytext, `col39` mediumblob, `col40` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, `col41` double DEFAULT NULL, `col42` smallint(6) DEFAULT NULL, `col43` longblob, `col44` varchar(80) DEFAULT NULL, `col45` mediumtext, `col46` decimal(10,0) DEFAULT NULL, `col47` bigint(20) DEFAULT NULL, `col48` date DEFAULT NULL, `col49` tinyblob, `col50` date DEFAULT NULL, `col51` tinyint(1) DEFAULT NULL, `col52` mediumint(9) DEFAULT NULL, `col53` float DEFAULT NULL, `col54` tinyblob, `col55` longtext, `col56` smallint(6) DEFAULT NULL, `col57` enum('test1','test2','test3') DEFAULT NULL, `col58` datetime DEFAULT NULL, `col59` mediumtext, `col60` varchar(232) DEFAULT NULL, `col61` decimal(10,0) DEFAULT NULL, `col62` year(4) DEFAULT NULL, `col63` smallint(6) DEFAULT NULL, `col64` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00', `col65` blob, `col66` longblob, `col67` int(11) DEFAULT NULL, `col68` longtext, `col69` enum('test1','test2','test3') DEFAULT NULL, `col70` int(11) DEFAULT NULL, `col71` time DEFAULT NULL, `col72` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00', `col73` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00', `col74` varchar(170) DEFAULT NULL, `col75` set('test1','test2','test3') DEFAULT NULL, `col76` tinyblob, `col77` bigint(20) DEFAULT NULL, `col78` decimal(10,0) DEFAULT NULL, `col79` datetime DEFAULT NULL, `col80` year(4) DEFAULT NULL, `col81` decimal(10,0) DEFAULT NULL, `col82` longblob, `col83` text, `col84` char(83) DEFAULT NULL, `col85` decimal(10,0) DEFAULT NULL, `col86` float DEFAULT NULL, `col87` int(11) DEFAULT NULL, `col88` varchar(145) DEFAULT NULL, `col89` date DEFAULT NULL, `col90` decimal(10,0) DEFAULT NULL, `col91` decimal(10,0) DEFAULT NULL, `col92` mediumblob, `col93` time DEFAULT NULL, KEY `idx0` (`col69`,`col90`,`col8`), KEY `idx1` (`col60`), KEY `idx2` (`col60`,`col70`,`col74`), KEY `idx3` (`col22`,`col32`,`col72`,`col30`), KEY `idx4` (`col29`), KEY `idx5` (`col19`,`col45`(143)), KEY `idx6` (`col46`,`col48`,`col5`,`col39`(118)), KEY `idx7` (`col48`,`col61`), KEY `idx8` (`col93`), KEY `idx9` (`col31`), KEY `idx10` (`col30`,`col21`), KEY `idx11` (`col67`), KEY `idx12` (`col44`,`col6`,`col8`,`col38`(226)), KEY `idx13` (`col71`,`col41`,`col15`,`col49`(88)), KEY `idx14` (`col78`), KEY `idx15` (`col63`,`col67`,`col64`), KEY `idx16` (`col17`,`col86`), KEY `idx17` (`col77`,`col56`,`col10`,`col55`(24)), KEY `idx18` (`col62`), KEY `idx19` (`col31`,`col57`,`col56`,`col53`), KEY `idx20` (`col46`), KEY `idx21` (`col83`(54)), KEY `idx22` (`col51`,`col7`(120)), KEY `idx23` (`col7`(163),`col31`,`col71`,`col14`) ) ENGINE=InnoDB DEFAULT CHARSET=latin1 ROW_FORMAT=COMPRESSED KEY_BLOCK_SIZE=2; -insert ignore into `table0` set `col23` = 7887371.5084383683, `col24` = 4293854615.6906948000, `col25` = 'vitalist', `col26` = 'widespread', `col27` = '3570490', `col28` = 'habitual', `col30` = -5471, `col31` = 4286985783.6771750000, `col32` = 6354540.9826654866, `col33` = 'defoliation', `col34` = 'logarithms', `col35` = 'tegument\'s', `col36` = 'scouting\'s', `col37` = 'intermittency', `col38` = 'elongates', `col39` = 'prophecies', `col40` = '20560103035939', `col41` = 4292809130.0544143000, `col42` = 22057, `col43` = 'Hess\'s', `col44` = 'bandstand', `col45` = 'phenylketonuria', `col46` = 6338767.4018677324, `col47` = 5310247, `col48` = '12592418', `col49` = 'churchman\'s', `col50` = '32226125', `col51` = -58, `col52` = -6207968, `col53` = 1244839.3255104220, `col54` = 'robotized', `col55` = 'monotonous', `col56` = -26909, `col58` = '20720107023550', `col59` = 'suggestiveness\'s', `col60` = 'gemology', `col61` = 4287800670.2229986000, `col62` = '1944', `col63` = -16827, `col64` = '20700107212324', `col65` = 'Nicolais', `col66` = 'apteryx', `col67` = 6935317, `col68` = 'stroganoff', `col70` = 3316430, `col71` = '3277608', `col72` = '19300511045918', `col73` = '20421201003327', `col74` = 'attenuant', `col75` = '15173', `col76` = 'upstroke\'s', `col77` = 8118987, `col78` = 6791516.2735374002, `col79` = '20780701144624', `col80` = '2134', `col81` = 4290682351.3127537000, `col82` = 'unexplainably', `col83` = 'Storm', `col84` = 'Greyso\'s', `col85` = 4289119212.4306774000, `col86` = 7617575.8796655172, `col87` = -6325335, `col88` = 'fondue\'s', `col89` = '40608940', `col90` = 1659421.8093508712, `col91` = 8346904.6584368423, `col92` = 'reloads', `col93` = '5188366'; -CHECK TABLE table0 EXTENDED; -INSERT IGNORE INTO `table0` SET `col19` = '19940127002709', `col20` = 2383927.9055146948, `col21` = 4293243420.5621204000, `col22` = '20511211123705', `col23` = 4289899778.6573381000, `col24` = 4293449279.0540481000, `col25` = 'emphysemic', `col26` = 'dentally', `col27` = '2347406', `col28` = 'eruct', `col30` = 1222, `col31` = 4294372994.9941406000, `col32` = 4291385574.1173744000, `col33` = 'borrowing\'s', `col34` = 'septics', `col35` = 'ratter\'s', `col36` = 'Kaye', `col37` = 'Florentia', `col38` = 'allium', `col39` = 'barkeep', `col40` = '19510407003441', `col41` = 4293559200.4215522000, `col42` = 22482, `col43` = 'decussate', `col44` = 'Brom\'s', `col45` = 'violated', `col46` = 4925506.4635456400, `col47` = 930549, `col48` = '51296066', `col49` = 'voluminously', `col50` = '29306676', `col51` = -88, `col52` = -2153690, `col53` = 4290250202.1464887000, `col54` = 'expropriation', `col55` = 'Aberdeen\'s', `col56` = 20343, `col58` = '19640415171532', `col59` = 'extern', `col60` = 'Ubana', `col61` = 4290487961.8539081000, `col62` = '2147', `col63` = -24271, `col64` = '20750801194548', `col65` = 'Cunaxa\'s', `col66` = 'pasticcio', `col67` = 2795817, `col68` = 'Indore\'s', `col70` = 6864127, `col71` = '1817832', `col72` = '20540506114211', `col73` = '20040101012300', `col74` = 'rationalized', `col75` = '45522', `col76` = 'indene', `col77` = -6964559, `col78` = 4247535.5266884370, `col79` = '20720416124357', `col80` = '2143', `col81` = 4292060102.4466386000, `col82` = 'striving', `col83` = 'boneblack\'s', `col84` = 'redolent', `col85` = 6489697.9009369183, `col86` = 4287473465.9731131000, `col87` = 7726015, `col88` = 'perplexed', `col89` = '17153791', `col90` = 5478587.1108127078, `col91` = 4287091404.7004304000, `col92` = 'Boulez\'s', `col93` = '2931278'; -CHECK TABLE table0 EXTENDED; -DROP TABLE table0; -EVAL SET GLOBAL innodb_file_format=$file_format; -EVAL SET GLOBAL innodb_file_format_check=$file_format_check; -EVAL SET GLOBAL innodb_file_per_table=$file_per_table; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug40360.result b/storage/innodb_plugin/mysql-test/innodb_bug40360.result deleted file mode 100644 index ef4cf463903..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug40360.result +++ /dev/null @@ -1,4 +0,0 @@ -SET TX_ISOLATION='READ-COMMITTED'; -CREATE TABLE bug40360 (a INT) engine=innodb; -INSERT INTO bug40360 VALUES (1); -DROP TABLE bug40360; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug40360.test b/storage/innodb_plugin/mysql-test/innodb_bug40360.test deleted file mode 100644 index e88837aab4f..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug40360.test +++ /dev/null @@ -1,16 +0,0 @@ -# -# Make sure http://bugs.mysql.com/40360 remains fixed. -# - --- source include/not_embedded.inc --- source include/have_innodb.inc - -SET TX_ISOLATION='READ-COMMITTED'; - -# This is the default since MySQL 5.1.29 SET BINLOG_FORMAT='STATEMENT'; - -CREATE TABLE bug40360 (a INT) engine=innodb; - -INSERT INTO bug40360 VALUES (1); - -DROP TABLE bug40360; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug40565.result b/storage/innodb_plugin/mysql-test/innodb_bug40565.result deleted file mode 100644 index 21e923d9336..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug40565.result +++ /dev/null @@ -1,9 +0,0 @@ -create table bug40565(value decimal(4,2)) engine=innodb; -insert into bug40565 values (1), (null); -update bug40565 set value=NULL; -affected rows: 1 -info: Rows matched: 2 Changed: 1 Warnings: 0 -update bug40565 set value=NULL; -affected rows: 0 -info: Rows matched: 2 Changed: 0 Warnings: 0 -drop table bug40565; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug40565.test b/storage/innodb_plugin/mysql-test/innodb_bug40565.test deleted file mode 100644 index d7aa0fd514a..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug40565.test +++ /dev/null @@ -1,10 +0,0 @@ -# Bug #40565 Update Query Results in "1 Row Affected" But Should Be "Zero Rows" --- source include/have_innodb.inc - -create table bug40565(value decimal(4,2)) engine=innodb; -insert into bug40565 values (1), (null); ---enable_info -update bug40565 set value=NULL; -update bug40565 set value=NULL; ---disable_info -drop table bug40565; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug41904.result b/storage/innodb_plugin/mysql-test/innodb_bug41904.result deleted file mode 100644 index 6070d32d181..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug41904.result +++ /dev/null @@ -1,4 +0,0 @@ -CREATE TABLE bug41904 (id INT PRIMARY KEY, uniquecol CHAR(15)) ENGINE=InnoDB; -INSERT INTO bug41904 VALUES (1,NULL), (2,NULL); -CREATE UNIQUE INDEX ui ON bug41904 (uniquecol); -DROP TABLE bug41904; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug41904.test b/storage/innodb_plugin/mysql-test/innodb_bug41904.test deleted file mode 100644 index 365c5229adc..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug41904.test +++ /dev/null @@ -1,14 +0,0 @@ -# -# Make sure http://bugs.mysql.com/41904 remains fixed. -# - --- source include/not_embedded.inc --- source include/have_innodb.inc - -CREATE TABLE bug41904 (id INT PRIMARY KEY, uniquecol CHAR(15)) ENGINE=InnoDB; - -INSERT INTO bug41904 VALUES (1,NULL), (2,NULL); - -CREATE UNIQUE INDEX ui ON bug41904 (uniquecol); - -DROP TABLE bug41904; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug42101-nonzero-master.opt b/storage/innodb_plugin/mysql-test/innodb_bug42101-nonzero-master.opt deleted file mode 100644 index d71dbe17d5b..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug42101-nonzero-master.opt +++ /dev/null @@ -1 +0,0 @@ ---innodb_commit_concurrency=1 diff --git a/storage/innodb_plugin/mysql-test/innodb_bug42101-nonzero.result b/storage/innodb_plugin/mysql-test/innodb_bug42101-nonzero.result deleted file mode 100644 index 277dfffdd35..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug42101-nonzero.result +++ /dev/null @@ -1,26 +0,0 @@ -set global innodb_commit_concurrency=0; -ERROR HY000: Incorrect arguments to SET -select @@innodb_commit_concurrency; -@@innodb_commit_concurrency -1 -set global innodb_commit_concurrency=1; -select @@innodb_commit_concurrency; -@@innodb_commit_concurrency -1 -set global innodb_commit_concurrency=42; -select @@innodb_commit_concurrency; -@@innodb_commit_concurrency -42 -set global innodb_commit_concurrency=DEFAULT; -select @@innodb_commit_concurrency; -@@innodb_commit_concurrency -1 -set global innodb_commit_concurrency=0; -ERROR HY000: Incorrect arguments to SET -select @@innodb_commit_concurrency; -@@innodb_commit_concurrency -1 -set global innodb_commit_concurrency=1; -select @@innodb_commit_concurrency; -@@innodb_commit_concurrency -1 diff --git a/storage/innodb_plugin/mysql-test/innodb_bug42101-nonzero.test b/storage/innodb_plugin/mysql-test/innodb_bug42101-nonzero.test deleted file mode 100644 index 685fdf20489..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug42101-nonzero.test +++ /dev/null @@ -1,21 +0,0 @@ -# -# Bug#42101 Race condition in innodb_commit_concurrency -# http://bugs.mysql.com/42101 -# - --- source include/have_innodb.inc - ---error ER_WRONG_ARGUMENTS -set global innodb_commit_concurrency=0; -select @@innodb_commit_concurrency; -set global innodb_commit_concurrency=1; -select @@innodb_commit_concurrency; -set global innodb_commit_concurrency=42; -select @@innodb_commit_concurrency; -set global innodb_commit_concurrency=DEFAULT; -select @@innodb_commit_concurrency; ---error ER_WRONG_ARGUMENTS -set global innodb_commit_concurrency=0; -select @@innodb_commit_concurrency; -set global innodb_commit_concurrency=1; -select @@innodb_commit_concurrency; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug42101.result b/storage/innodb_plugin/mysql-test/innodb_bug42101.result deleted file mode 100644 index 805097ffe9d..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug42101.result +++ /dev/null @@ -1,22 +0,0 @@ -set global innodb_commit_concurrency=0; -select @@innodb_commit_concurrency; -@@innodb_commit_concurrency -0 -set global innodb_commit_concurrency=1; -ERROR HY000: Incorrect arguments to SET -select @@innodb_commit_concurrency; -@@innodb_commit_concurrency -0 -set global innodb_commit_concurrency=42; -ERROR HY000: Incorrect arguments to SET -select @@innodb_commit_concurrency; -@@innodb_commit_concurrency -0 -set global innodb_commit_concurrency=0; -select @@innodb_commit_concurrency; -@@innodb_commit_concurrency -0 -set global innodb_commit_concurrency=DEFAULT; -select @@innodb_commit_concurrency; -@@innodb_commit_concurrency -0 diff --git a/storage/innodb_plugin/mysql-test/innodb_bug42101.test b/storage/innodb_plugin/mysql-test/innodb_bug42101.test deleted file mode 100644 index b6536490d48..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug42101.test +++ /dev/null @@ -1,19 +0,0 @@ -# -# Bug#42101 Race condition in innodb_commit_concurrency -# http://bugs.mysql.com/42101 -# - --- source include/have_innodb.inc - -set global innodb_commit_concurrency=0; -select @@innodb_commit_concurrency; ---error ER_WRONG_ARGUMENTS -set global innodb_commit_concurrency=1; -select @@innodb_commit_concurrency; ---error ER_WRONG_ARGUMENTS -set global innodb_commit_concurrency=42; -select @@innodb_commit_concurrency; -set global innodb_commit_concurrency=0; -select @@innodb_commit_concurrency; -set global innodb_commit_concurrency=DEFAULT; -select @@innodb_commit_concurrency; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug44032.result b/storage/innodb_plugin/mysql-test/innodb_bug44032.result deleted file mode 100644 index da2a000b06e..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug44032.result +++ /dev/null @@ -1,7 +0,0 @@ -CREATE TABLE bug44032(c CHAR(3) CHARACTER SET UTF8) ROW_FORMAT=REDUNDANT -ENGINE=InnoDB; -INSERT INTO bug44032 VALUES('abc'),(0xEFBCA4EFBCA4EFBCA4); -UPDATE bug44032 SET c='DDD' WHERE c=0xEFBCA4EFBCA4EFBCA4; -UPDATE bug44032 SET c=NULL WHERE c='DDD'; -UPDATE bug44032 SET c='DDD' WHERE c IS NULL; -DROP TABLE bug44032; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug44032.test b/storage/innodb_plugin/mysql-test/innodb_bug44032.test deleted file mode 100644 index a963cb8b68f..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug44032.test +++ /dev/null @@ -1,13 +0,0 @@ -# Bug44032 no update-in-place of UTF-8 columns in ROW_FORMAT=REDUNDANT -# (btr_cur_update_in_place not invoked when updating from/to NULL; -# the update is performed by delete and insert instead) - --- source include/have_innodb.inc - -CREATE TABLE bug44032(c CHAR(3) CHARACTER SET UTF8) ROW_FORMAT=REDUNDANT -ENGINE=InnoDB; -INSERT INTO bug44032 VALUES('abc'),(0xEFBCA4EFBCA4EFBCA4); -UPDATE bug44032 SET c='DDD' WHERE c=0xEFBCA4EFBCA4EFBCA4; -UPDATE bug44032 SET c=NULL WHERE c='DDD'; -UPDATE bug44032 SET c='DDD' WHERE c IS NULL; -DROP TABLE bug44032; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug44369.result b/storage/innodb_plugin/mysql-test/innodb_bug44369.result deleted file mode 100644 index e4b84ecac19..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug44369.result +++ /dev/null @@ -1,14 +0,0 @@ -create table bug44369 (DB_ROW_ID int) engine=innodb; -ERROR HY000: Can't create table 'test.bug44369' (errno: -1) -create table bug44369 (db_row_id int) engine=innodb; -ERROR HY000: Can't create table 'test.bug44369' (errno: -1) -show errors; -Level Code Message -Error 1005 Error creating table 'test/bug44369' with column name 'db_row_id'. 'db_row_id' is a reserved name. Please try to re-create the table with a different column name. -Error 1005 Can't create table 'test.bug44369' (errno: -1) -create table bug44369 (db_TRX_Id int) engine=innodb; -ERROR HY000: Can't create table 'test.bug44369' (errno: -1) -show errors; -Level Code Message -Error 1005 Error creating table 'test/bug44369' with column name 'db_TRX_Id'. 'db_TRX_Id' is a reserved name. Please try to re-create the table with a different column name. -Error 1005 Can't create table 'test.bug44369' (errno: -1) diff --git a/storage/innodb_plugin/mysql-test/innodb_bug44369.test b/storage/innodb_plugin/mysql-test/innodb_bug44369.test deleted file mode 100644 index 495059eb5e6..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug44369.test +++ /dev/null @@ -1,21 +0,0 @@ -# This is the test for bug 44369. We should -# block table creation with columns match -# some innodb internal reserved key words, -# both case sensitively and insensitely. - ---source include/have_innodb.inc - -# This create table operation should fail. ---error ER_CANT_CREATE_TABLE -create table bug44369 (DB_ROW_ID int) engine=innodb; - -# This create should fail as well ---error ER_CANT_CREATE_TABLE -create table bug44369 (db_row_id int) engine=innodb; - -show errors; - ---error ER_CANT_CREATE_TABLE -create table bug44369 (db_TRX_Id int) engine=innodb; - -show errors; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug44571.result b/storage/innodb_plugin/mysql-test/innodb_bug44571.result deleted file mode 100644 index 36374edcb3e..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug44571.result +++ /dev/null @@ -1,9 +0,0 @@ -CREATE TABLE bug44571 (foo INT) ENGINE=InnoDB; -ALTER TABLE bug44571 CHANGE foo bar INT; -ALTER TABLE bug44571 ADD INDEX bug44571b (foo); -ERROR 42000: Key column 'foo' doesn't exist in table -ALTER TABLE bug44571 ADD INDEX bug44571b (bar); -ERROR HY000: Incorrect key file for table 'bug44571'; try to repair it -CREATE INDEX bug44571b ON bug44571 (bar); -ERROR HY000: Incorrect key file for table 'bug44571'; try to repair it -DROP TABLE bug44571; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug44571.test b/storage/innodb_plugin/mysql-test/innodb_bug44571.test deleted file mode 100644 index 685463ceff9..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug44571.test +++ /dev/null @@ -1,17 +0,0 @@ -# -# Bug#44571 InnoDB Plugin crashes on ADD INDEX -# http://bugs.mysql.com/44571 -# --- source include/have_innodb.inc - -CREATE TABLE bug44571 (foo INT) ENGINE=InnoDB; -ALTER TABLE bug44571 CHANGE foo bar INT; --- error ER_KEY_COLUMN_DOES_NOT_EXITS -ALTER TABLE bug44571 ADD INDEX bug44571b (foo); -# The following will fail, because the CHANGE foo bar was -# not communicated to InnoDB. ---error ER_NOT_KEYFILE -ALTER TABLE bug44571 ADD INDEX bug44571b (bar); ---error ER_NOT_KEYFILE -CREATE INDEX bug44571b ON bug44571 (bar); -DROP TABLE bug44571; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug45357.result b/storage/innodb_plugin/mysql-test/innodb_bug45357.result deleted file mode 100644 index 7adeff2062f..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug45357.result +++ /dev/null @@ -1,7 +0,0 @@ -set session transaction isolation level read committed; -create table bug45357(a int, b int,key(b))engine=innodb; -insert into bug45357 values (25170,6122); -update bug45357 set a=1 where b=30131; -delete from bug45357 where b < 20996; -delete from bug45357 where b < 7001; -drop table bug45357; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug45357.test b/storage/innodb_plugin/mysql-test/innodb_bug45357.test deleted file mode 100644 index 81727f352dd..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug45357.test +++ /dev/null @@ -1,10 +0,0 @@ --- source include/have_innodb.inc - -set session transaction isolation level read committed; - -create table bug45357(a int, b int,key(b))engine=innodb; -insert into bug45357 values (25170,6122); -update bug45357 set a=1 where b=30131; -delete from bug45357 where b < 20996; -delete from bug45357 where b < 7001; -drop table bug45357; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug46000.result b/storage/innodb_plugin/mysql-test/innodb_bug46000.result deleted file mode 100644 index ccff888a48d..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug46000.result +++ /dev/null @@ -1,17 +0,0 @@ -create table bug46000(`id` int,key `GEN_CLUST_INDEX`(`id`))engine=innodb; -ERROR HY000: Can't create table 'test.bug46000' (errno: -1) -create table bug46000(`id` int, key `GEN_clust_INDEX`(`id`))engine=innodb; -ERROR HY000: Can't create table 'test.bug46000' (errno: -1) -show errors; -Level Code Message -Error 1005 Cannot Create Index with name 'GEN_CLUST_INDEX'. The name is reserved for the system default primary index. -Error 1005 Can't create table 'test.bug46000' (errno: -1) -create table bug46000(id int) engine=innodb; -create index GEN_CLUST_INDEX on bug46000(id); -ERROR HY000: Can't create table '#sql-temporary' (errno: -1) -show errors; -Level Code Message -Error 1005 Cannot Create Index with name 'GEN_CLUST_INDEX'. The name is reserved for the system default primary index. -Error 1005 Can't create table '#sql-temporary' (errno: -1) -create index idx on bug46000(id); -drop table bug46000; diff --git a/storage/innodb_plugin/mysql-test/innodb_bug46000.test b/storage/innodb_plugin/mysql-test/innodb_bug46000.test deleted file mode 100644 index 80c18c58ef0..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_bug46000.test +++ /dev/null @@ -1,34 +0,0 @@ -# This is the test for bug 46000. We shall -# block any index creation with the name of -# "GEN_CLUST_INDEX", which is the reserved -# name for innodb default primary index. - ---source include/have_innodb.inc - -# This 'create table' operation should fail because of -# using the reserve name as its index name. ---error ER_CANT_CREATE_TABLE -create table bug46000(`id` int,key `GEN_CLUST_INDEX`(`id`))engine=innodb; - -# Mixed upper/lower case of the reserved key words ---error ER_CANT_CREATE_TABLE -create table bug46000(`id` int, key `GEN_clust_INDEX`(`id`))engine=innodb; - -show errors; - -create table bug46000(id int) engine=innodb; - -# This 'create index' operation should fail. ---replace_regex /'[^']*test.#sql-[0-9a-f_]*'/'#sql-temporary'/ ---error ER_CANT_CREATE_TABLE -create index GEN_CLUST_INDEX on bug46000(id); - ---replace_regex /'[^']*test.#sql-[0-9a-f_]*'/'#sql-temporary'/ -show errors; - -# This 'create index' operation should succeed, no -# temp table left from last failed create index -# operation. -create index idx on bug46000(id); - -drop table bug46000; diff --git a/storage/innodb_plugin/mysql-test/innodb_file_format.result b/storage/innodb_plugin/mysql-test/innodb_file_format.result deleted file mode 100644 index 8e9a317308b..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_file_format.result +++ /dev/null @@ -1,45 +0,0 @@ -select @@innodb_file_format; -@@innodb_file_format -Antelope -select @@innodb_file_format_check; -@@innodb_file_format_check -Antelope -set global innodb_file_format=antelope; -set global innodb_file_format=barracuda; -set global innodb_file_format=cheetah; -ERROR HY000: Incorrect arguments to SET -select @@innodb_file_format; -@@innodb_file_format -Barracuda -set global innodb_file_format=default; -select @@innodb_file_format; -@@innodb_file_format -Antelope -set global innodb_file_format=on; -ERROR HY000: Incorrect arguments to SET -set global innodb_file_format=off; -ERROR HY000: Incorrect arguments to SET -select @@innodb_file_format; -@@innodb_file_format -Antelope -set global innodb_file_format_check=antelope; -set global innodb_file_format_check=barracuda; -set global innodb_file_format_check=cheetah; -ERROR HY000: Incorrect arguments to SET -select @@innodb_file_format_check; -@@innodb_file_format_check -Barracuda -set global innodb_file_format_check=default; -Warnings: -Warning 1210 Ignoring SET innodb_file_format=on -select @@innodb_file_format_check; -@@innodb_file_format_check -Barracuda -set global innodb_file_format=on; -ERROR HY000: Incorrect arguments to SET -set global innodb_file_format=off; -ERROR HY000: Incorrect arguments to SET -select @@innodb_file_format_check; -@@innodb_file_format_check -Barracuda -set global innodb_file_format_check=antelope; diff --git a/storage/innodb_plugin/mysql-test/innodb_file_format.test b/storage/innodb_plugin/mysql-test/innodb_file_format.test deleted file mode 100644 index d63c9b0228f..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_file_format.test +++ /dev/null @@ -1,29 +0,0 @@ --- source include/have_innodb.inc - -select @@innodb_file_format; -select @@innodb_file_format_check; -set global innodb_file_format=antelope; -set global innodb_file_format=barracuda; ---error ER_WRONG_ARGUMENTS -set global innodb_file_format=cheetah; -select @@innodb_file_format; -set global innodb_file_format=default; -select @@innodb_file_format; ---error ER_WRONG_ARGUMENTS -set global innodb_file_format=on; ---error ER_WRONG_ARGUMENTS -set global innodb_file_format=off; -select @@innodb_file_format; -set global innodb_file_format_check=antelope; -set global innodb_file_format_check=barracuda; ---error ER_WRONG_ARGUMENTS -set global innodb_file_format_check=cheetah; -select @@innodb_file_format_check; -set global innodb_file_format_check=default; -select @@innodb_file_format_check; ---error ER_WRONG_ARGUMENTS -set global innodb_file_format=on; ---error ER_WRONG_ARGUMENTS -set global innodb_file_format=off; -select @@innodb_file_format_check; -set global innodb_file_format_check=antelope; diff --git a/storage/innodb_plugin/mysql-test/innodb_information_schema.result b/storage/innodb_plugin/mysql-test/innodb_information_schema.result deleted file mode 100644 index 396cae579ce..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_information_schema.result +++ /dev/null @@ -1,23 +0,0 @@ -lock_mode lock_type lock_table lock_index lock_rec lock_data -X RECORD `test`.```t'\"_str` `PRIMARY` 2 '1', 'abc', '''abc', 'abc''', 'a''bc', 'a''bc''', '''abc''''' -X RECORD `test`.```t'\"_str` `PRIMARY` 2 '1', 'abc', '''abc', 'abc''', 'a''bc', 'a''bc''', '''abc''''' -X RECORD `test`.```t'\"_str` `PRIMARY` 3 '2', 'abc', '"abc', 'abc"', 'a"bc', 'a"bc"', '"abc""' -X RECORD `test`.```t'\"_str` `PRIMARY` 3 '2', 'abc', '"abc', 'abc"', 'a"bc', 'a"bc"', '"abc""' -X RECORD `test`.```t'\"_str` `PRIMARY` 4 '3', 'abc', '\\abc', 'abc\\', 'a\\bc', 'a\\bc\\', '\\abc\\\\' -X RECORD `test`.```t'\"_str` `PRIMARY` 4 '3', 'abc', '\\abc', 'abc\\', 'a\\bc', 'a\\bc\\', '\\abc\\\\' -X RECORD `test`.```t'\"_str` `PRIMARY` 5 '4', 'abc', '\0abc', 'abc\0', 'a\0bc', 'a\0bc\0', 'a\0bc\0\0' -X RECORD `test`.```t'\"_str` `PRIMARY` 5 '4', 'abc', '\0abc', 'abc\0', 'a\0bc', 'a\0bc\0', 'a\0bc\0\0' -X RECORD `test`.`t_min` `PRIMARY` 2 -128, 0, -32768, 0, -8388608, 0, -2147483648, 0, -9223372036854775808, 0 -X RECORD `test`.`t_min` `PRIMARY` 2 -128, 0, -32768, 0, -8388608, 0, -2147483648, 0, -9223372036854775808, 0 -X RECORD `test`.`t_max` `PRIMARY` 2 127, 255, 32767, 65535, 8388607, 16777215, 2147483647, 4294967295, 9223372036854775807, 18446744073709551615 -X RECORD `test`.`t_max` `PRIMARY` 2 127, 255, 32767, 65535, 8388607, 16777215, 2147483647, 4294967295, 9223372036854775807, 18446744073709551615 -X RECORD `test`.```t'\"_str` `PRIMARY` 1 supremum pseudo-record -X RECORD `test`.```t'\"_str` `PRIMARY` 1 supremum pseudo-record -lock_table COUNT(*) -`test`.`t_max` 2 -`test`.`t_min` 2 -`test`.```t'\"_str` 10 -lock_table COUNT(*) -"test"."t_max" 2 -"test"."t_min" 2 -"test"."`t'\""_str" 10 diff --git a/storage/innodb_plugin/mysql-test/innodb_information_schema.test b/storage/innodb_plugin/mysql-test/innodb_information_schema.test deleted file mode 100644 index eaed653854a..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_information_schema.test +++ /dev/null @@ -1,145 +0,0 @@ -# -# Test that user data is correctly "visualized" in -# INFORMATION_SCHEMA.innodb_locks.lock_data -# - --- source include/have_innodb.inc - --- disable_query_log --- disable_result_log - -SET storage_engine=InnoDB; - --- disable_warnings -DROP TABLE IF EXISTS t_min, t_max; --- enable_warnings - -let $table_def = -( - c01 TINYINT, - c02 TINYINT UNSIGNED, - c03 SMALLINT, - c04 SMALLINT UNSIGNED, - c05 MEDIUMINT, - c06 MEDIUMINT UNSIGNED, - c07 INT, - c08 INT UNSIGNED, - c09 BIGINT, - c10 BIGINT UNSIGNED, - PRIMARY KEY(c01, c02, c03, c04, c05, c06, c07, c08, c09, c10) -); - --- eval CREATE TABLE t_min $table_def; -INSERT INTO t_min VALUES -(-128, 0, - -32768, 0, - -8388608, 0, - -2147483648, 0, - -9223372036854775808, 0); - --- eval CREATE TABLE t_max $table_def; -INSERT INTO t_max VALUES -(127, 255, - 32767, 65535, - 8388607, 16777215, - 2147483647, 4294967295, - 9223372036854775807, 18446744073709551615); - -CREATE TABLE ```t'\"_str` ( - c1 VARCHAR(32), - c2 VARCHAR(32), - c3 VARCHAR(32), - c4 VARCHAR(32), - c5 VARCHAR(32), - c6 VARCHAR(32), - c7 VARCHAR(32), - PRIMARY KEY(c1, c2, c3, c4, c5, c6, c7) -); -INSERT INTO ```t'\"_str` VALUES -('1', 'abc', '''abc', 'abc''', 'a''bc', 'a''bc''', '''abc'''''); -INSERT INTO ```t'\"_str` VALUES -('2', 'abc', '"abc', 'abc"', 'a"bc', 'a"bc"', '"abc""'); -INSERT INTO ```t'\"_str` VALUES -('3', 'abc', '\\abc', 'abc\\', 'a\\bc', 'a\\bc\\', '\\abc\\\\'); -INSERT INTO ```t'\"_str` VALUES -('4', 'abc', 0x00616263, 0x61626300, 0x61006263, 0x6100626300, 0x610062630000); - --- connect (con_lock,localhost,root,,) --- connect (con_min_trylock,localhost,root,,) --- connect (con_max_trylock,localhost,root,,) --- connect (con_str_insert_supremum,localhost,root,,) --- connect (con_str_lock_row1,localhost,root,,) --- connect (con_str_lock_row2,localhost,root,,) --- connect (con_str_lock_row3,localhost,root,,) --- connect (con_str_lock_row4,localhost,root,,) --- connect (con_verify_innodb_locks,localhost,root,,) - --- connection con_lock -SET autocommit=0; -SELECT * FROM t_min FOR UPDATE; -SELECT * FROM t_max FOR UPDATE; -SELECT * FROM ```t'\"_str` FOR UPDATE; - --- connection con_min_trylock --- send -SELECT * FROM t_min FOR UPDATE; - --- connection con_max_trylock --- send -SELECT * FROM t_max FOR UPDATE; - --- connection con_str_insert_supremum --- send -INSERT INTO ```t'\"_str` VALUES -('z', 'z', 'z', 'z', 'z', 'z', 'z'); - --- connection con_str_lock_row1 --- send -SELECT * FROM ```t'\"_str` WHERE c1 = '1' FOR UPDATE; - --- connection con_str_lock_row2 --- send -SELECT * FROM ```t'\"_str` WHERE c1 = '2' FOR UPDATE; - --- connection con_str_lock_row3 --- send -SELECT * FROM ```t'\"_str` WHERE c1 = '3' FOR UPDATE; - --- connection con_str_lock_row4 --- send -SELECT * FROM ```t'\"_str` WHERE c1 = '4' FOR UPDATE; - -# Give time to the above 2 queries to execute before continuing. -# Without this sleep it sometimes happens that the SELECT from innodb_locks -# executes before some of them, resulting in less than expected number -# of rows being selected from innodb_locks. --- sleep 0.1 - --- enable_result_log --- connection con_verify_innodb_locks -SELECT lock_mode, lock_type, lock_table, lock_index, lock_rec, lock_data -FROM INFORMATION_SCHEMA.INNODB_LOCKS ORDER BY lock_data; - -SELECT lock_table,COUNT(*) FROM INFORMATION_SCHEMA.INNODB_LOCKS -GROUP BY lock_table; - -set @save_sql_mode = @@sql_mode; -SET SQL_MODE='ANSI_QUOTES'; -SELECT lock_table,COUNT(*) FROM INFORMATION_SCHEMA.INNODB_LOCKS -GROUP BY lock_table; -SET @@sql_mode=@save_sql_mode; --- disable_result_log - --- connection default - --- disconnect con_lock --- disconnect con_min_trylock --- disconnect con_max_trylock --- disconnect con_str_insert_supremum --- disconnect con_str_lock_row1 --- disconnect con_str_lock_row2 --- disconnect con_str_lock_row3 --- disconnect con_str_lock_row4 --- disconnect con_verify_innodb_locks - -DROP TABLE t_min, t_max, ```t'\"_str`; diff --git a/storage/innodb_plugin/mysql-test/innodb_trx_weight.inc b/storage/innodb_plugin/mysql-test/innodb_trx_weight.inc deleted file mode 100644 index 56d3d47da36..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_trx_weight.inc +++ /dev/null @@ -1,51 +0,0 @@ --- connect (con1,localhost,root,,) --- connect (con2,localhost,root,,) - --- connection con1 -SET autocommit=0; -SELECT * FROM t1 FOR UPDATE; --- if ($con1_extra_sql_present) { - -- eval $con1_extra_sql --- } - --- connection con2 -SET autocommit=0; -SELECT * FROM t2 FOR UPDATE; --- if ($con2_extra_sql_present) { - -- eval $con2_extra_sql --- } - --- if ($con1_should_be_rolledback) { - -- connection con1 - -- send - INSERT INTO t2 VALUES (0); - - -- connection con2 - INSERT INTO t1 VALUES (0); - ROLLBACK; - - -- connection con1 - -- error ER_LOCK_DEADLOCK - -- reap --- } -# else --- if (!$con1_should_be_rolledback) { - -- connection con2 - -- send - INSERT INTO t1 VALUES (0); - - -- connection con1 - INSERT INTO t2 VALUES (0); - ROLLBACK; - - -- connection con2 - -- error ER_LOCK_DEADLOCK - -- reap --- } - --- connection default - -DELETE FROM t5_nontrans; - --- disconnect con1 --- disconnect con2 diff --git a/storage/innodb_plugin/mysql-test/innodb_trx_weight.result b/storage/innodb_plugin/mysql-test/innodb_trx_weight.result deleted file mode 100644 index 195775f74c8..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_trx_weight.result +++ /dev/null @@ -1 +0,0 @@ -SET storage_engine=InnoDB; diff --git a/storage/innodb_plugin/mysql-test/innodb_trx_weight.test b/storage/innodb_plugin/mysql-test/innodb_trx_weight.test deleted file mode 100644 index b72eaad345f..00000000000 --- a/storage/innodb_plugin/mysql-test/innodb_trx_weight.test +++ /dev/null @@ -1,108 +0,0 @@ -# -# Ensure that the number of locks (SELECT FOR UPDATE for example) is -# added to the number of altered rows when choosing the smallest -# transaction to kill as a victim when a deadlock is detected. -# Also transactions what had edited non-transactional tables should -# be heavier than ones that had not. -# - --- source include/have_innodb.inc - -SET storage_engine=InnoDB; - -# we do not really care about what gets printed, we are only -# interested in getting the deadlock resolved according to our -# expectations --- disable_query_log --- disable_result_log - -# we want to use "-- eval statement1; statement2" which does not work with -# prepared statements. Because this test should not behave differently with -# or without prepared statements we disable them so the test does not fail -# if someone runs ./mysql-test-run.pl --ps-protocol --- disable_ps_protocol - --- disable_warnings -DROP TABLE IF EXISTS t1, t2, t3, t4, t5_nontrans; --- enable_warnings - -# we will create a simple deadlock with t1, t2 and two connections -CREATE TABLE t1 (a INT); -CREATE TABLE t2 (a INT); - -# auxiliary table with a bulk of rows which will be locked by a -# transaction to increase its weight -CREATE TABLE t3 (a INT); - -# auxiliary empty table which will be inserted by a -# transaction to increase its weight -CREATE TABLE t4 (a INT); - -# auxiliary non-transactional table which will be edited by a -# transaction to tremendously increase its weight -CREATE TABLE t5_nontrans (a INT) ENGINE=MyISAM; - -INSERT INTO t1 VALUES (1); -INSERT INTO t2 VALUES (1); -# insert a lot of rows in t3 -INSERT INTO t3 VALUES (1); -INSERT INTO t3 SELECT * FROM t3; -INSERT INTO t3 SELECT * FROM t3; -INSERT INTO t3 SELECT * FROM t3; -INSERT INTO t3 SELECT * FROM t3; -INSERT INTO t3 SELECT * FROM t3; -INSERT INTO t3 SELECT * FROM t3; -INSERT INTO t3 SELECT * FROM t3; -INSERT INTO t3 SELECT * FROM t3; -INSERT INTO t3 SELECT * FROM t3; -INSERT INTO t3 SELECT * FROM t3; -INSERT INTO t3 SELECT * FROM t3; - -# test locking weight - --- let $con1_extra_sql = --- let $con1_extra_sql_present = 0 --- let $con2_extra_sql = SELECT * FROM t3 FOR UPDATE --- let $con2_extra_sql_present = 1 --- let $con1_should_be_rolledback = 1 --- source include/innodb_trx_weight.inc - --- let $con1_extra_sql = INSERT INTO t4 VALUES (1), (1) --- let $con1_extra_sql_present = 1 --- let $con2_extra_sql = SELECT * FROM t3 FOR UPDATE --- let $con2_extra_sql_present = 1 --- let $con1_should_be_rolledback = 1 --- source include/innodb_trx_weight.inc - --- let $con1_extra_sql = INSERT INTO t4 VALUES (1), (1), (1), (1), (1), (1) --- let $con1_extra_sql_present = 1 --- let $con2_extra_sql = SELECT * FROM t3 FOR UPDATE --- let $con2_extra_sql_present = 1 --- let $con1_should_be_rolledback = 0 --- source include/innodb_trx_weight.inc - -# test weight when non-transactional tables are edited - --- let $con1_extra_sql = INSERT INTO t4 VALUES (1), (1), (1) --- let $con1_extra_sql_present = 1 --- let $con2_extra_sql = --- let $con2_extra_sql_present = 0 --- let $con1_should_be_rolledback = 0 --- source include/innodb_trx_weight.inc - --- let $con1_extra_sql = INSERT INTO t4 VALUES (1), (1), (1) --- let $con1_extra_sql_present = 1 --- let $con2_extra_sql = INSERT INTO t5_nontrans VALUES (1) --- let $con2_extra_sql_present = 1 --- let $con1_should_be_rolledback = 1 --- source include/innodb_trx_weight.inc - --- let $con1_extra_sql = INSERT INTO t4 VALUES (1), (1), (1) --- let $con1_extra_sql = $con1_extra_sql; INSERT INTO t5_nontrans VALUES (1) --- let $con1_extra_sql_present = 1 --- let $con2_extra_sql = INSERT INTO t5_nontrans VALUES (1) --- let $con2_extra_sql_present = 1 --- let $con1_should_be_rolledback = 0 --- source include/innodb_trx_weight.inc - -DROP TABLE t1, t2, t3, t4, t5_nontrans; diff --git a/storage/innodb_plugin/mysql-test/patches/innodb-index.diff b/storage/innodb_plugin/mysql-test/patches/innodb-index.diff deleted file mode 100644 index 0b008c96f25..00000000000 --- a/storage/innodb_plugin/mysql-test/patches/innodb-index.diff +++ /dev/null @@ -1,62 +0,0 @@ -This part of the innodb-index test causes mysqld to print some warnings -and subsequently the whole mysql-test suite to fail. - -A permanent solution is probably to remove the printouts from the source -code or to somehow tell the mysql-test suite that warnings are expected. -Currently we simply do not execute the problematic tests. Please -coordinate a permanent solution with Marko, who added those tests. - -This cannot be proposed to MySQL because it touches files that are not -in the MySQL source repository. - -Index: storage/innobase/mysql-test/innodb-index.result -=================================================================== ---- storage/innobase/mysql-test/innodb-index.result (revision 2870) -+++ storage/innobase/mysql-test/innodb-index.result (working copy) -@@ -43,19 +43,12 @@ t1 CREATE TABLE `t1` ( - `b` int(11) DEFAULT NULL, - `c` char(10) NOT NULL, - `d` varchar(20) DEFAULT NULL, - KEY `d2` (`d`), - KEY `b` (`b`) - ) ENGINE=InnoDB DEFAULT CHARSET=latin1 --CREATE TABLE `t1#1`(a INT PRIMARY KEY) ENGINE=InnoDB; --alter table t1 add unique index (c), add index (d); --ERROR HY000: Table 'test.t1#1' already exists --rename table `t1#1` to `t1#2`; --alter table t1 add unique index (c), add index (d); --ERROR HY000: Table 'test.t1#2' already exists --drop table `t1#2`; - alter table t1 add unique index (c), add index (d); - show create table t1; - Table Create Table - t1 CREATE TABLE `t1` ( - `a` int(11) NOT NULL, - `b` int(11) DEFAULT NULL, -Index: storage/innobase/mysql-test/innodb-index.test -=================================================================== ---- storage/innobase/mysql-test/innodb-index.test (revision 2870) -+++ storage/innobase/mysql-test/innodb-index.test (working copy) -@@ -14,22 +14,12 @@ select * from t1 force index (d2) order - --error ER_DUP_ENTRY - alter table t1 add unique index (b); - show create table t1; - alter table t1 add index (b); - show create table t1; - --# Check how existing tables interfere with temporary tables. --CREATE TABLE `t1#1`(a INT PRIMARY KEY) ENGINE=InnoDB; -- ----error 156 --alter table t1 add unique index (c), add index (d); --rename table `t1#1` to `t1#2`; ----error 156 --alter table t1 add unique index (c), add index (d); --drop table `t1#2`; -- - alter table t1 add unique index (c), add index (d); - show create table t1; - explain select * from t1 force index(c) order by c; - alter table t1 add primary key (a), drop index c; - show create table t1; - --error ER_MULTIPLE_PRI_KEY diff --git a/storage/innodb_plugin/os/os0file.c b/storage/innodb_plugin/os/os0file.c index 37edad442db..b244e3974b3 100644 --- a/storage/innodb_plugin/os/os0file.c +++ b/storage/innodb_plugin/os/os0file.c @@ -1,23 +1,6 @@ -/***************************************************************************** - -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. - -This program is free software; you can redistribute it and/or modify it under -the terms of the GNU General Public License as published by the Free Software -Foundation; version 2 of the License. - -This program is distributed in the hope that it will be useful, but WITHOUT -ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS -FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. - -You should have received a copy of the GNU General Public License along with -this program; if not, write to the Free Software Foundation, Inc., 59 Temple -Place, Suite 330, Boston, MA 02111-1307 USA - -*****************************************************************************/ /*********************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. Copyright (c) 2009, Percona Inc. Portions of this file contain modifications contributed and copyrighted @@ -806,7 +789,15 @@ next_file: #ifdef HAVE_READDIR_R ret = readdir_r(dir, (struct dirent*)dirent_buf, &ent); - if (ret != 0) { + if (ret != 0 +#ifdef UNIV_AIX + /* On AIX, only if we got non-NULL 'ent' (result) value and + a non-zero 'ret' (return) value, it indicates a failed + readdir_r() call. An NULL 'ent' with an non-zero 'ret' + would indicate the "end of the directory" is reached. */ + && ent != NULL +#endif + ) { fprintf(stderr, "InnoDB: cannot read directory %s, error %lu\n", dirname, (ulong)ret); @@ -3923,6 +3914,9 @@ os_aio_simulated_handle( ulint n; ulint i; + /* Fix compiler warning */ + *consecutive_ios = NULL; + segment = os_aio_get_array_and_local_segment(&array, global_segment); restart: diff --git a/storage/innodb_plugin/page/page0page.c b/storage/innodb_plugin/page/page0page.c index ab2ba60570e..10008f9ac25 100644 --- a/storage/innodb_plugin/page/page0page.c +++ b/storage/innodb_plugin/page/page0page.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1994, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1994, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -658,6 +658,14 @@ page_copy_rec_list_end( index, mtr); } + /* Update PAGE_MAX_TRX_ID on the uncompressed page. + Modifications will be redo logged and copied to the compressed + page in page_zip_compress() or page_zip_reorganize() below. */ + if (dict_index_is_sec_or_ibuf(index) && page_is_leaf(page)) { + page_update_max_trx_id(new_block, NULL, + page_get_max_trx_id(page), mtr); + } + if (UNIV_LIKELY_NULL(new_page_zip)) { mtr_set_log_mode(mtr, log_mode); @@ -696,15 +704,10 @@ page_copy_rec_list_end( } } - /* Update the lock table, MAX_TRX_ID, and possible hash index */ + /* Update the lock table and possible hash index */ lock_move_rec_list_end(new_block, block, rec); - if (dict_index_is_sec_or_ibuf(index) && page_is_leaf(page)) { - page_update_max_trx_id(new_block, new_page_zip, - page_get_max_trx_id(page), mtr); - } - btr_search_move_or_delete_hash_entries(new_block, block, index); return(ret); @@ -772,6 +775,16 @@ page_copy_rec_list_start( mem_heap_free(heap); } + /* Update PAGE_MAX_TRX_ID on the uncompressed page. + Modifications will be redo logged and copied to the compressed + page in page_zip_compress() or page_zip_reorganize() below. */ + if (dict_index_is_sec_or_ibuf(index) + && page_is_leaf(page_align(rec))) { + page_update_max_trx_id(new_block, NULL, + page_get_max_trx_id(page_align(rec)), + mtr); + } + if (UNIV_LIKELY_NULL(new_page_zip)) { mtr_set_log_mode(mtr, log_mode); @@ -809,14 +822,7 @@ page_copy_rec_list_start( } } - /* Update MAX_TRX_ID, the lock table, and possible hash index */ - - if (dict_index_is_sec_or_ibuf(index) - && page_is_leaf(page_align(rec))) { - page_update_max_trx_id(new_block, new_page_zip, - page_get_max_trx_id(page_align(rec)), - mtr); - } + /* Update the lock table and possible hash index */ lock_move_rec_list_start(new_block, block, rec, ret); @@ -2408,8 +2414,13 @@ page_validate( } offs = page_offset(rec_get_start(rec, offsets)); + i = rec_offs_size(offsets); + if (UNIV_UNLIKELY(offs + i >= UNIV_PAGE_SIZE)) { + fputs("InnoDB: record offset out of bounds\n", stderr); + goto func_exit; + } - for (i = rec_offs_size(offsets); i--; ) { + while (i--) { if (UNIV_UNLIKELY(buf[offs + i])) { /* No other record may overlap this */ @@ -2517,8 +2528,13 @@ n_owned_zero: count++; offs = page_offset(rec_get_start(rec, offsets)); + i = rec_offs_size(offsets); + if (UNIV_UNLIKELY(offs + i >= UNIV_PAGE_SIZE)) { + fputs("InnoDB: record offset out of bounds\n", stderr); + goto func_exit; + } - for (i = rec_offs_size(offsets); i--; ) { + while (i--) { if (UNIV_UNLIKELY(buf[offs + i])) { fputs("InnoDB: Record overlaps another" diff --git a/storage/innodb_plugin/plug.in.disabled b/storage/innodb_plugin/plug.in.disabled index 4ebde50cb35..e638332d74a 100644 --- a/storage/innodb_plugin/plug.in.disabled +++ b/storage/innodb_plugin/plug.in.disabled @@ -1,5 +1,5 @@ # -# Copyright (c) 2006, 2009, Innobase Oy. All Rights Reserved. +# Copyright (c) 2006, 2010, Innobase Oy. All Rights Reserved. # # This program is free software; you can redistribute it and/or modify it under # the terms of the GNU General Public License as published by the Free Software @@ -15,7 +15,7 @@ # MYSQL_STORAGE_ENGINE(innodb_plugin,, [InnoDB Storage Engine], - [Transactional Tables using InnoDB],) + [Transactional Tables using InnoDB], [max,max-no-ndb]) MYSQL_PLUGIN_DIRECTORY(innodb_plugin, [storage/innodb_plugin]) MYSQL_PLUGIN_DYNAMIC(innodb_plugin, [ha_innodb_plugin.la]) MYSQL_PLUGIN_ACTIONS(innodb_plugin, [ diff --git a/storage/innodb_plugin/rem/rem0rec.c b/storage/innodb_plugin/rem/rem0rec.c index 1c8b3fd8c1e..37ba8ca2ffe 100644 --- a/storage/innodb_plugin/rem/rem0rec.c +++ b/storage/innodb_plugin/rem/rem0rec.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1994, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1994, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -212,6 +212,13 @@ rec_get_n_extern_new( const dict_col_t* col = dict_field_get_col(field); len = *lens--; + /* If the maximum length of the field is up + to 255 bytes, the actual length is always + stored in one byte. If the maximum length is + more than 255 bytes, the actual length is + stored in one byte for 0..127. The length + will be encoded in two bytes when it is 128 or + more, or when the field is stored externally. */ if (UNIV_UNLIKELY(col->len > 255) || UNIV_UNLIKELY(col->mtype == DATA_BLOB)) { if (len & 0x80) { @@ -294,6 +301,13 @@ rec_init_offsets_comp_ordinary( const dict_col_t* col = dict_field_get_col(field); len = *lens--; + /* If the maximum length of the field is up + to 255 bytes, the actual length is always + stored in one byte. If the maximum length is + more than 255 bytes, the actual length is + stored in one byte for 0..127. The length + will be encoded in two bytes when it is 128 or + more, or when the field is stored externally. */ if (UNIV_UNLIKELY(col->len > 255) || UNIV_UNLIKELY(col->mtype == DATA_BLOB)) { @@ -425,6 +439,15 @@ rec_init_offsets( const dict_col_t* col = dict_field_get_col(field); len = *lens--; + /* If the maximum length of the field + is up to 255 bytes, the actual length + is always stored in one byte. If the + maximum length is more than 255 bytes, + the actual length is stored in one + byte for 0..127. The length will be + encoded in two bytes when it is 128 or + more, or when the field is stored + externally. */ if (UNIV_UNLIKELY(col->len > 255) || UNIV_UNLIKELY(col->mtype == DATA_BLOB)) { @@ -647,6 +670,13 @@ rec_get_offsets_reverse( const dict_col_t* col = dict_field_get_col(field); len = *lens++; + /* If the maximum length of the field is up + to 255 bytes, the actual length is always + stored in one byte. If the maximum length is + more than 255 bytes, the actual length is + stored in one byte for 0..127. The length + will be encoded in two bytes when it is 128 or + more, or when the field is stored externally. */ if (UNIV_UNLIKELY(col->len > 255) || UNIV_UNLIKELY(col->mtype == DATA_BLOB)) { if (len & 0x80) { @@ -695,19 +725,9 @@ rec_get_nth_field_offs_old( ulint os; ulint next_os; - ut_ad(rec && len); - ut_ad(n < rec_get_n_fields_old(rec)); - - if (UNIV_UNLIKELY(n > REC_MAX_N_FIELDS)) { - fprintf(stderr, "Error: trying to access field %lu in rec\n", - (ulong) n); - ut_error; - } - - if (UNIV_UNLIKELY(rec == NULL)) { - fputs("Error: rec is NULL pointer\n", stderr); - ut_error; - } + ut_ad(len); + ut_a(rec); + ut_a(n < rec_get_n_fields_old(rec)); if (rec_get_1byte_offs_flag(rec)) { os = rec_1_get_field_start_offs(rec, n); @@ -791,12 +811,20 @@ rec_get_converted_size_comp_prefix( ut_ad(len <= col->len || col->mtype == DATA_BLOB); + /* If the maximum length of a variable-length field + is up to 255 bytes, the actual length is always stored + in one byte. If the maximum length is more than 255 + bytes, the actual length is stored in one byte for + 0..127. The length will be encoded in two bytes when + it is 128 or more, or when the field is stored externally. */ + if (field->fixed_len) { ut_ad(len == field->fixed_len); /* dict_index_add_col() should guarantee this */ ut_ad(!field->prefix_len || field->fixed_len == field->prefix_len); } else if (dfield_is_ext(&fields[i])) { + ut_ad(col->len >= 256 || col->mtype == DATA_BLOB); extra_size += 2; } else if (len < 128 || (col->len < 256 && col->mtype != DATA_BLOB)) { @@ -1096,6 +1124,8 @@ rec_convert_dtuple_to_rec_comp( /* Store the data and the offsets */ for (i = 0, field = fields; i < n_fields; i++, field++) { + const dict_field_t* ifield; + type = dfield_get_type(field); len = dfield_get_len(field); @@ -1130,12 +1160,20 @@ rec_convert_dtuple_to_rec_comp( /* only nullable fields can be null */ ut_ad(!dfield_is_null(field)); - fixed_len = dict_index_get_nth_field(index, i)->fixed_len; - + ifield = dict_index_get_nth_field(index, i); + fixed_len = ifield->fixed_len; + /* If the maximum length of a variable-length field + is up to 255 bytes, the actual length is always stored + in one byte. If the maximum length is more than 255 + bytes, the actual length is stored in one byte for + 0..127. The length will be encoded in two bytes when + it is 128 or more, or when the field is stored externally. */ if (fixed_len) { ut_ad(len == fixed_len); ut_ad(!dfield_is_ext(field)); } else if (dfield_is_ext(field)) { + ut_ad(ifield->col->len >= 256 + || ifield->col->mtype == DATA_BLOB); ut_ad(len <= REC_MAX_INDEX_COL_LEN + BTR_EXTERN_FIELD_REF_SIZE); *lens-- = (byte) (len >> 8) | 0xc0; @@ -1225,11 +1263,20 @@ rec_convert_dtuple_to_rec( mem_heap_t* heap = NULL; ulint offsets_[REC_OFFS_NORMAL_SIZE]; const ulint* offsets; + ulint i; rec_offs_init(offsets_); offsets = rec_get_offsets(rec, index, offsets_, ULINT_UNDEFINED, &heap); ut_ad(rec_validate(rec, offsets)); + ut_ad(dtuple_get_n_fields(dtuple) + == rec_offs_n_fields(offsets)); + + for (i = 0; i < rec_offs_n_fields(offsets); i++) { + ut_ad(!dfield_is_ext(dtuple_get_nth_field(dtuple, i)) + == !rec_offs_nth_extern(offsets, i)); + } + if (UNIV_LIKELY_NULL(heap)) { mem_heap_free(heap); } @@ -1412,6 +1459,13 @@ rec_copy_prefix_to_buf( prefix_len += field->fixed_len; } else { ulint len = *lens--; + /* If the maximum length of the column is up + to 255 bytes, the actual length is always + stored in one byte. If the maximum length is + more than 255 bytes, the actual length is + stored in one byte for 0..127. The length + will be encoded in two bytes when it is 128 or + more, or when the column is stored externally. */ if (col->len > 255 || col->mtype == DATA_BLOB) { if (len & 0x80) { /* 1exxxxxx */ diff --git a/storage/innodb_plugin/row/row0ins.c b/storage/innodb_plugin/row/row0ins.c index fe51fce82c4..230dc45dadc 100644 --- a/storage/innodb_plugin/row/row0ins.c +++ b/storage/innodb_plugin/row/row0ins.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -1991,7 +1991,7 @@ row_ins_index_entry_low( btr_cur_search_to_nth_level(index, 0, entry, PAGE_CUR_LE, mode | BTR_INSERT | ignore_sec_unique, - &cursor, 0, &mtr); + &cursor, 0, __FILE__, __LINE__, &mtr); if (cursor.flag == BTR_CUR_INSERT_TO_IBUF) { /* The insertion was made to the insert buffer already during @@ -2049,7 +2049,8 @@ row_ins_index_entry_low( btr_cur_search_to_nth_level(index, 0, entry, PAGE_CUR_LE, mode | BTR_INSERT, - &cursor, 0, &mtr); + &cursor, 0, + __FILE__, __LINE__, &mtr); } } @@ -2104,7 +2105,8 @@ function_exit: mtr_start(&mtr); btr_cur_search_to_nth_level(index, 0, entry, PAGE_CUR_LE, - BTR_MODIFY_TREE, &cursor, 0, &mtr); + BTR_MODIFY_TREE, &cursor, 0, + __FILE__, __LINE__, &mtr); rec = btr_cur_get_rec(&cursor); offsets = rec_get_offsets(rec, index, NULL, ULINT_UNDEFINED, &heap); diff --git a/storage/innodb_plugin/row/row0merge.c b/storage/innodb_plugin/row/row0merge.c index 25f041c0885..d61d626f92e 100644 --- a/storage/innodb_plugin/row/row0merge.c +++ b/storage/innodb_plugin/row/row0merge.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 2005, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 2005, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -424,14 +424,13 @@ row_merge_dup_report( row_merge_dup_t* dup, /*!< in/out: for reporting duplicates */ const dfield_t* entry) /*!< in: duplicate index entry */ { - mrec_buf_t buf; + mrec_buf_t* buf; const dtuple_t* tuple; dtuple_t tuple_store; const rec_t* rec; const dict_index_t* index = dup->index; ulint n_fields= dict_index_get_n_fields(index); - mem_heap_t* heap = NULL; - ulint offsets_[REC_OFFS_NORMAL_SIZE]; + mem_heap_t* heap; ulint* offsets; ulint n_ext; @@ -441,22 +440,22 @@ row_merge_dup_report( return; } - rec_offs_init(offsets_); - /* Convert the tuple to a record and then to MySQL format. */ + heap = mem_heap_create((1 + REC_OFFS_HEADER_SIZE + n_fields) + * sizeof *offsets + + sizeof *buf); + + buf = mem_heap_alloc(heap, sizeof *buf); tuple = dtuple_from_fields(&tuple_store, entry, n_fields); n_ext = dict_index_is_clust(index) ? dtuple_get_n_ext(tuple) : 0; - rec = rec_convert_dtuple_to_rec(buf, index, tuple, n_ext); - offsets = rec_get_offsets(rec, index, offsets_, ULINT_UNDEFINED, - &heap); + rec = rec_convert_dtuple_to_rec(*buf, index, tuple, n_ext); + offsets = rec_get_offsets(rec, index, NULL, ULINT_UNDEFINED, &heap); innobase_rec_to_mysql(dup->table, rec, index, offsets); - if (UNIV_LIKELY_NULL(heap)) { - mem_heap_free(heap); - } + mem_heap_free(heap); } /*************************************************************//** @@ -627,22 +626,26 @@ row_merge_buf_write( } /******************************************************//** -Create a memory heap and allocate space for row_merge_rec_offsets(). +Create a memory heap and allocate space for row_merge_rec_offsets() +and mrec_buf_t[3]. @return memory heap */ static mem_heap_t* row_merge_heap_create( /*==================*/ const dict_index_t* index, /*!< in: record descriptor */ + mrec_buf_t** buf, /*!< out: 3 buffers */ ulint** offsets1, /*!< out: offsets */ ulint** offsets2) /*!< out: offsets */ { ulint i = 1 + REC_OFFS_HEADER_SIZE + dict_index_get_n_fields(index); - mem_heap_t* heap = mem_heap_create(2 * i * sizeof *offsets1); + mem_heap_t* heap = mem_heap_create(2 * i * sizeof **offsets1 + + 3 * sizeof **buf); - *offsets1 = mem_heap_alloc(heap, i * sizeof *offsets1); - *offsets2 = mem_heap_alloc(heap, i * sizeof *offsets2); + *buf = mem_heap_alloc(heap, 3 * sizeof **buf); + *offsets1 = mem_heap_alloc(heap, i * sizeof **offsets1); + *offsets2 = mem_heap_alloc(heap, i * sizeof **offsets2); (*offsets1)[0] = (*offsets2)[0] = i; (*offsets1)[1] = (*offsets2)[1] = dict_index_get_n_fields(index); @@ -1394,7 +1397,8 @@ row_merge_blocks( { mem_heap_t* heap; /*!< memory heap for offsets0, offsets1 */ - mrec_buf_t buf[3]; /*!< buffer for handling split mrec in block[] */ + mrec_buf_t* buf; /*!< buffer for handling + split mrec in block[] */ const byte* b0; /*!< pointer to block[0] */ const byte* b1; /*!< pointer to block[1] */ byte* b2; /*!< pointer to block[2] */ @@ -1414,7 +1418,7 @@ row_merge_blocks( } #endif /* UNIV_DEBUG */ - heap = row_merge_heap_create(index, &offsets0, &offsets1); + heap = row_merge_heap_create(index, &buf, &offsets0, &offsets1); /* Write a record and read the next record. Split the output file in two halves, which can be merged on the following pass. */ @@ -1500,7 +1504,7 @@ row_merge_blocks_copy( { mem_heap_t* heap; /*!< memory heap for offsets0, offsets1 */ - mrec_buf_t buf[3]; /*!< buffer for handling + mrec_buf_t* buf; /*!< buffer for handling split mrec in block[] */ const byte* b0; /*!< pointer to block[0] */ byte* b2; /*!< pointer to block[2] */ @@ -1518,7 +1522,7 @@ row_merge_blocks_copy( } #endif /* UNIV_DEBUG */ - heap = row_merge_heap_create(index, &offsets0, &offsets1); + heap = row_merge_heap_create(index, &buf, &offsets0, &offsets1); /* Write a record and read the next record. Split the output file in two halves, which can be merged on the following pass. */ @@ -1760,7 +1764,6 @@ row_merge_insert_index_tuples( int fd, /*!< in: file descriptor */ row_merge_block_t* block) /*!< in/out: file buffer */ { - mrec_buf_t buf; const byte* b; que_thr_t* thr; ins_node_t* node; @@ -1779,7 +1782,7 @@ row_merge_insert_index_tuples( trx->op_info = "inserting index entries"; - graph_heap = mem_heap_create(500); + graph_heap = mem_heap_create(500 + sizeof(mrec_buf_t)); node = ins_node_create(INS_DIRECT, table, graph_heap); thr = pars_complete_graph_for_exec(node, trx, graph_heap); @@ -1801,12 +1804,14 @@ row_merge_insert_index_tuples( if (!row_merge_read(fd, foffs, block)) { error = DB_CORRUPTION; } else { + mrec_buf_t* buf = mem_heap_alloc(graph_heap, sizeof *buf); + for (;;) { const mrec_t* mrec; dtuple_t* dtuple; ulint n_ext; - b = row_merge_read_rec(block, &buf, b, index, + b = row_merge_read_rec(block, buf, b, index, fd, &foffs, &mrec, offsets); if (UNIV_UNLIKELY(!b)) { /* End of list, or I/O error */ @@ -1977,14 +1982,12 @@ row_merge_drop_index( /* Drop the field definitions of the index. */ "DELETE FROM SYS_FIELDS WHERE INDEX_ID = :indexid;\n" /* Drop the index definition and the B-tree. */ - "DELETE FROM SYS_INDEXES WHERE ID = :indexid\n" - " AND TABLE_ID = :tableid;\n" + "DELETE FROM SYS_INDEXES WHERE ID = :indexid;\n" "END;\n"; ut_ad(index && table && trx); pars_info_add_dulint_literal(info, "indexid", index->id); - pars_info_add_dulint_literal(info, "tableid", table->id); trx_start_if_not_started(trx); trx->op_info = "dropping index"; @@ -2033,47 +2036,79 @@ row_merge_drop_temp_indexes(void) /*=============================*/ { trx_t* trx; - ulint err; - - /* We use the private SQL parser of Innobase to generate the - query graphs needed in deleting the dictionary data from system - tables in Innobase. Deleting a row from SYS_INDEXES table also - frees the file segments of the B-tree associated with the index. */ - static const char drop_temp_indexes[] = - "PROCEDURE DROP_TEMP_INDEXES_PROC () IS\n" - "indexid CHAR;\n" - "DECLARE CURSOR c IS SELECT ID FROM SYS_INDEXES\n" - "WHERE SUBSTR(NAME,0,1)='" TEMP_INDEX_PREFIX_STR "';\n" - "BEGIN\n" - "\tOPEN c;\n" - "\tWHILE 1=1 LOOP\n" - "\t\tFETCH c INTO indexid;\n" - "\t\tIF (SQL % NOTFOUND) THEN\n" - "\t\t\tEXIT;\n" - "\t\tEND IF;\n" - "\t\tDELETE FROM SYS_FIELDS WHERE INDEX_ID = indexid;\n" - "\t\tDELETE FROM SYS_INDEXES WHERE ID = indexid;\n" - "\tEND LOOP;\n" - "\tCLOSE c;\n" - "\tCOMMIT WORK;\n" - "END;\n"; + btr_pcur_t pcur; + mtr_t mtr; + /* Load the table definitions that contain partially defined + indexes, so that the data dictionary information can be checked + when accessing the tablename.ibd files. */ trx = trx_allocate_for_background(); trx->op_info = "dropping partially created indexes"; row_mysql_lock_data_dictionary(trx); - /* Incomplete transactions may be holding some locks on the - data dictionary tables. However, they should never have been - able to lock the records corresponding to the partially - created indexes that we are attempting to delete, because the - table was locked when the indexes were being created. We will - drop the partially created indexes before the rollback of - incomplete transactions is initiated. Thus, this should not - interfere with the incomplete transactions. */ - trx->isolation_level = TRX_ISO_READ_UNCOMMITTED; - err = que_eval_sql(NULL, drop_temp_indexes, FALSE, trx); - ut_a(err == DB_SUCCESS); + mtr_start(&mtr); + + btr_pcur_open_at_index_side( + TRUE, + dict_table_get_first_index(dict_sys->sys_indexes), + BTR_SEARCH_LEAF, &pcur, TRUE, &mtr); + + for (;;) { + const rec_t* rec; + const byte* field; + ulint len; + dulint table_id; + dict_table_t* table; + btr_pcur_move_to_next_user_rec(&pcur, &mtr); + + if (!btr_pcur_is_on_user_rec(&pcur)) { + break; + } + + rec = btr_pcur_get_rec(&pcur); + field = rec_get_nth_field_old(rec, DICT_SYS_INDEXES_NAME_FIELD, + &len); + if (len == UNIV_SQL_NULL || len == 0 + || (char) *field != TEMP_INDEX_PREFIX) { + continue; + } + + /* This is a temporary index. */ + + field = rec_get_nth_field_old(rec, 0/*TABLE_ID*/, &len); + if (len != 8) { + /* Corrupted TABLE_ID */ + continue; + } + + table_id = mach_read_from_8(field); + + btr_pcur_store_position(&pcur, &mtr); + btr_pcur_commit_specify_mtr(&pcur, &mtr); + + table = dict_load_table_on_id(table_id); + + if (table) { + dict_index_t* index; + + for (index = dict_table_get_first_index(table); + index; index = dict_table_get_next_index(index)) { + + if (*index->name == TEMP_INDEX_PREFIX) { + row_merge_drop_index(index, table, trx); + trx_commit_for_mysql(trx); + } + } + } + + mtr_start(&mtr); + btr_pcur_restore_position(BTR_SEARCH_LEAF, + &pcur, &mtr); + } + + btr_pcur_close(&pcur); + mtr_commit(&mtr); row_mysql_unlock_data_dictionary(trx); trx_free_for_background(trx); } diff --git a/storage/innodb_plugin/row/row0mysql.c b/storage/innodb_plugin/row/row0mysql.c index 181c39de881..24abf8067f2 100644 --- a/storage/innodb_plugin/row/row0mysql.c +++ b/storage/innodb_plugin/row/row0mysql.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 2000, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 2000, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -485,7 +485,7 @@ next_column: /****************************************************************//** Handles user errors and lock waits detected by the database engine. @return TRUE if it was a lock wait and we should continue running the -query thread */ +query thread and in that case the thr is ALREADY in the running state. */ UNIV_INTERN ibool row_mysql_handle_errors( @@ -1458,7 +1458,7 @@ row_unlock_for_mysql( if (UNIV_UNLIKELY (!srv_locks_unsafe_for_binlog - && trx->isolation_level != TRX_ISO_READ_COMMITTED)) { + && trx->isolation_level > TRX_ISO_READ_COMMITTED)) { fprintf(stderr, "InnoDB: Error: calling row_unlock_for_mysql though\n" @@ -3255,19 +3255,13 @@ check_next_foreign: "END;\n" , FALSE, trx); - if (err != DB_SUCCESS) { - ut_a(err == DB_OUT_OF_FILE_SPACE); - - err = DB_MUST_GET_MORE_FILE_SPACE; - - row_mysql_handle_errors(&err, trx, NULL, NULL); - - ut_error; - } else { - ibool is_path; + switch (err) { + ibool is_temp; const char* name_or_path; mem_heap_t* heap; + case DB_SUCCESS: + heap = mem_heap_create(200); /* Clone the name, in case it has been allocated @@ -3277,12 +3271,13 @@ check_next_foreign: space_id = table->space; if (table->dir_path_of_temp_table != NULL) { - is_path = TRUE; name_or_path = mem_heap_strdup( heap, table->dir_path_of_temp_table); + is_temp = TRUE; } else { - is_path = FALSE; name_or_path = name; + is_temp = (table->flags >> DICT_TF2_SHIFT) + & DICT_TF2_TEMPORARY; } dict_table_remove_from_cache(table); @@ -3302,8 +3297,8 @@ check_next_foreign: if (err == DB_SUCCESS && space_id > 0) { if (!fil_space_for_table_exists_in_mem(space_id, name_or_path, - is_path, - FALSE, TRUE)) { + is_temp, FALSE, + !is_temp)) { err = DB_SUCCESS; fprintf(stderr, @@ -3332,7 +3327,27 @@ check_next_foreign: } mem_heap_free(heap); + break; + + case DB_TOO_MANY_CONCURRENT_TRXS: + /* Cannot even find a free slot for the + the undo log. We can directly exit here + and return the DB_TOO_MANY_CONCURRENT_TRXS + error. */ + break; + + case DB_OUT_OF_FILE_SPACE: + err = DB_MUST_GET_MORE_FILE_SPACE; + + row_mysql_handle_errors(&err, trx, NULL, NULL); + + /* Fall through to raise error */ + + default: + /* No other possible error returns */ + ut_error; } + funct_exit: if (locked_dictionary) { @@ -3348,6 +3363,90 @@ funct_exit: return((int) err); } +/*********************************************************************//** +Drop all temporary tables during crash recovery. */ +UNIV_INTERN +void +row_mysql_drop_temp_tables(void) +/*============================*/ +{ + trx_t* trx; + btr_pcur_t pcur; + mtr_t mtr; + mem_heap_t* heap; + + trx = trx_allocate_for_background(); + trx->op_info = "dropping temporary tables"; + row_mysql_lock_data_dictionary(trx); + + heap = mem_heap_create(200); + + mtr_start(&mtr); + + btr_pcur_open_at_index_side( + TRUE, + dict_table_get_first_index(dict_sys->sys_tables), + BTR_SEARCH_LEAF, &pcur, TRUE, &mtr); + + for (;;) { + const rec_t* rec; + const byte* field; + ulint len; + const char* table_name; + dict_table_t* table; + + btr_pcur_move_to_next_user_rec(&pcur, &mtr); + + if (!btr_pcur_is_on_user_rec(&pcur)) { + break; + } + + rec = btr_pcur_get_rec(&pcur); + field = rec_get_nth_field_old(rec, 4/*N_COLS*/, &len); + if (len != 4 || !(mach_read_from_4(field) & 0x80000000UL)) { + continue; + } + + /* Because this is not a ROW_FORMAT=REDUNDANT table, + the is_temp flag is valid. Examine it. */ + + field = rec_get_nth_field_old(rec, 7/*MIX_LEN*/, &len); + if (len != 4 + || !(mach_read_from_4(field) & DICT_TF2_TEMPORARY)) { + continue; + } + + /* This is a temporary table. */ + field = rec_get_nth_field_old(rec, 0/*NAME*/, &len); + if (len == UNIV_SQL_NULL || len == 0) { + /* Corrupted SYS_TABLES.NAME */ + continue; + } + + table_name = mem_heap_strdupl(heap, (const char*) field, len); + + btr_pcur_store_position(&pcur, &mtr); + btr_pcur_commit_specify_mtr(&pcur, &mtr); + + table = dict_load_table(table_name); + + if (table) { + row_drop_table_for_mysql(table_name, trx, FALSE); + trx_commit_for_mysql(trx); + } + + mtr_start(&mtr); + btr_pcur_restore_position(BTR_SEARCH_LEAF, + &pcur, &mtr); + } + + btr_pcur_close(&pcur); + mtr_commit(&mtr); + mem_heap_free(heap); + row_mysql_unlock_data_dictionary(trx); + trx_free_for_background(trx); +} + /*******************************************************************//** Drop all foreign keys in a database, see Bug#18942. Called at the end of row_drop_database_for_mysql(). @@ -3899,14 +3998,15 @@ Checks that the index contains entries in an ascending order, unique constraint is not broken, and calculates the number of index entries in the read view of the current transaction. @return TRUE if ok */ -static +UNIV_INTERN ibool -row_scan_and_check_index( -/*=====================*/ - row_prebuilt_t* prebuilt, /*!< in: prebuilt struct in MySQL */ - dict_index_t* index, /*!< in: index */ - ulint* n_rows) /*!< out: number of entries seen in the - current consistent read */ +row_check_index_for_mysql( +/*======================*/ + row_prebuilt_t* prebuilt, /*!< in: prebuilt struct + in MySQL handle */ + const dict_index_t* index, /*!< in: index */ + ulint* n_rows) /*!< out: number of entries + seen in the consistent read */ { dtuple_t* prev_entry = NULL; ulint matched_fields; @@ -3927,31 +4027,9 @@ row_scan_and_check_index( *n_rows = 0; - if (!row_merge_is_index_usable(prebuilt->trx, index)) { - /* A newly created index may lack some delete-marked - records that may exist in the read view of - prebuilt->trx. Thus, such indexes must not be - accessed by consistent read. */ - return(is_ok); - } - buf = mem_alloc(UNIV_PAGE_SIZE); heap = mem_heap_create(100); - /* Make a dummy template in prebuilt, which we will use - in scanning the index entries */ - - prebuilt->index = index; - /* row_merge_is_index_usable() was already checked above. */ - prebuilt->index_usable = TRUE; - prebuilt->sql_stat_start = TRUE; - prebuilt->template_type = ROW_MYSQL_DUMMY_TEMPLATE; - prebuilt->n_template = 0; - prebuilt->need_to_access_clustered = FALSE; - - dtuple_set_n_fields(prebuilt->search_tuple, 0); - - prebuilt->select_lock_type = LOCK_NONE; cnt = 1000; ret = row_search_for_mysql(buf, PAGE_CUR_G, prebuilt, 0, 0); @@ -4070,119 +4148,6 @@ not_ok: } /*********************************************************************//** -Checks a table for corruption. -@return DB_ERROR or DB_SUCCESS */ -UNIV_INTERN -ulint -row_check_table_for_mysql( -/*======================*/ - row_prebuilt_t* prebuilt) /*!< in: prebuilt struct in MySQL - handle */ -{ - dict_table_t* table = prebuilt->table; - dict_index_t* index; - ulint n_rows; - ulint n_rows_in_table = ULINT_UNDEFINED; - ulint ret = DB_SUCCESS; - ulint old_isolation_level; - - if (table->ibd_file_missing) { - ut_print_timestamp(stderr); - fprintf(stderr, " InnoDB: Error:\n" - "InnoDB: MySQL is trying to use a table handle" - " but the .ibd file for\n" - "InnoDB: table %s does not exist.\n" - "InnoDB: Have you deleted the .ibd file" - " from the database directory under\n" - "InnoDB: the MySQL datadir, or have you" - " used DISCARD TABLESPACE?\n" - "InnoDB: Look from\n" - "InnoDB: " REFMAN "innodb-troubleshooting.html\n" - "InnoDB: how you can resolve the problem.\n", - table->name); - return(DB_ERROR); - } - - prebuilt->trx->op_info = "checking table"; - - old_isolation_level = prebuilt->trx->isolation_level; - - /* We must run the index record counts at an isolation level - >= READ COMMITTED, because a dirty read can see a wrong number - of records in some index; to play safe, we use always - REPEATABLE READ here */ - - prebuilt->trx->isolation_level = TRX_ISO_REPEATABLE_READ; - - /* Enlarge the fatal lock wait timeout during CHECK TABLE. */ - mutex_enter(&kernel_mutex); - srv_fatal_semaphore_wait_threshold += 7200; /* 2 hours */ - mutex_exit(&kernel_mutex); - - index = dict_table_get_first_index(table); - - while (index != NULL) { - /* fputs("Validating index ", stderr); - ut_print_name(stderr, trx, FALSE, index->name); - putc('\n', stderr); */ - - if (!btr_validate_index(index, prebuilt->trx)) { - ret = DB_ERROR; - } else { - if (!row_scan_and_check_index(prebuilt,index, &n_rows)){ - ret = DB_ERROR; - } - - if (trx_is_interrupted(prebuilt->trx)) { - ret = DB_INTERRUPTED; - break; - } - - /* fprintf(stderr, "%lu entries in index %s\n", n_rows, - index->name); */ - - if (index == dict_table_get_first_index(table)) { - n_rows_in_table = n_rows; - } else if (n_rows != n_rows_in_table) { - - ret = DB_ERROR; - - fputs("Error: ", stderr); - dict_index_name_print(stderr, - prebuilt->trx, index); - fprintf(stderr, - " contains %lu entries," - " should be %lu\n", - (ulong) n_rows, - (ulong) n_rows_in_table); - } - } - - index = dict_table_get_next_index(index); - } - - /* Restore the original isolation level */ - prebuilt->trx->isolation_level = old_isolation_level; - - /* We validate also the whole adaptive hash index for all tables - at every CHECK TABLE */ - - if (!btr_search_validate()) { - - ret = DB_ERROR; - } - - /* Restore the fatal lock wait timeout after CHECK TABLE. */ - mutex_enter(&kernel_mutex); - srv_fatal_semaphore_wait_threshold -= 7200; /* 2 hours */ - mutex_exit(&kernel_mutex); - - prebuilt->trx->op_info = ""; - - return(ret); -} - -/*********************************************************************//** Determines if a table is a magic monitor table. @return TRUE if monitor table */ UNIV_INTERN diff --git a/storage/innodb_plugin/row/row0row.c b/storage/innodb_plugin/row/row0row.c index 128ac3ba3e8..cb7dfa2b7c9 100644 --- a/storage/innodb_plugin/row/row0row.c +++ b/storage/innodb_plugin/row/row0row.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -915,6 +915,10 @@ row_raw_format( ret = row_raw_format_int(data, data_len, prtype, buf, buf_size, &format_in_hex); + if (format_in_hex) { + + goto format_in_hex; + } break; case DATA_CHAR: case DATA_VARCHAR: @@ -923,14 +927,15 @@ row_raw_format( ret = row_raw_format_str(data, data_len, prtype, buf, buf_size, &format_in_hex); + if (format_in_hex) { + + goto format_in_hex; + } + break; /* XXX support more data types */ default: - - format_in_hex = TRUE; - } - - if (format_in_hex) { + format_in_hex: if (UNIV_LIKELY(buf_size > 2)) { diff --git a/storage/innodb_plugin/row/row0sel.c b/storage/innodb_plugin/row/row0sel.c index 3ef9726588e..d0702a0cd2f 100644 --- a/storage/innodb_plugin/row/row0sel.c +++ b/storage/innodb_plugin/row/row0sel.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1997, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1997, 2010, Innobase Oy. All Rights Reserved. Copyright (c) 2008, Google Inc. Portions of this file contain modifications contributed and copyrighted by @@ -132,7 +132,8 @@ index record. NOTE: the comparison is NOT done as a binary comparison, but character fields are compared with collation! @return TRUE if the secondary record is equal to the corresponding -fields in the clustered record, when compared with collation */ +fields in the clustered record, when compared with collation; +FALSE if not equal or if the clustered record has been marked for deletion */ static ibool row_sel_sec_rec_is_for_clust_rec( @@ -431,10 +432,6 @@ row_sel_fetch_columns( data = rec_get_nth_field(rec, offsets, field_no, &len); - if (len == UNIV_SQL_NULL) { - len = UNIV_SQL_NULL; - } - needs_copy = column->copy_val; } @@ -855,7 +852,7 @@ row_sel_get_clust_rec( trx = thr_get_trx(thr); if (srv_locks_unsafe_for_binlog - || trx->isolation_level == TRX_ISO_READ_COMMITTED) { + || trx->isolation_level <= TRX_ISO_READ_COMMITTED) { lock_type = LOCK_REC_NOT_GAP; } else { lock_type = LOCK_ORDINARY; @@ -1468,7 +1465,7 @@ rec_loop: if (srv_locks_unsafe_for_binlog || trx->isolation_level - == TRX_ISO_READ_COMMITTED) { + <= TRX_ISO_READ_COMMITTED) { if (page_rec_is_supremum(next_rec)) { @@ -1525,7 +1522,7 @@ skip_lock: trx = thr_get_trx(thr); if (srv_locks_unsafe_for_binlog - || trx->isolation_level == TRX_ISO_READ_COMMITTED) { + || trx->isolation_level <= TRX_ISO_READ_COMMITTED) { if (page_rec_is_supremum(rec)) { @@ -2170,36 +2167,6 @@ row_fetch_print( return((void*)42); } -/****************************************************************//** -Callback function for fetch that stores an unsigned 4 byte integer to the -location pointed. The column's type must be DATA_INT, DATA_UNSIGNED, length -= 4. -@return always returns NULL */ -UNIV_INTERN -void* -row_fetch_store_uint4( -/*==================*/ - void* row, /*!< in: sel_node_t* */ - void* user_arg) /*!< in: data pointer */ -{ - sel_node_t* node = row; - ib_uint32_t* val = user_arg; - ulint tmp; - - dfield_t* dfield = que_node_get_val(node->select_list); - const dtype_t* type = dfield_get_type(dfield); - ulint len = dfield_get_len(dfield); - - ut_a(dtype_get_mtype(type) == DATA_INT); - ut_a(dtype_get_prtype(type) & DATA_UNSIGNED); - ut_a(len == 4); - - tmp = mach_read_from_4(dfield_get_data(dfield)); - *val = (ib_uint32_t) tmp; - - return(NULL); -} - /***********************************************************//** Prints a row in a select result. @return query thread to run next or NULL */ @@ -2981,6 +2948,7 @@ row_sel_get_clust_rec_for_mysql( if (clust_rec && (old_vers + || trx->isolation_level <= TRX_ISO_READ_UNCOMMITTED || rec_get_deleted_flag(rec, dict_table_is_comp( sec_index->table))) && !row_sel_sec_rec_is_for_clust_rec( @@ -3202,14 +3170,17 @@ row_sel_try_search_shortcut_for_mysql( ut_ad(dict_index_is_clust(index)); ut_ad(!prebuilt->templ_contains_blob); +#ifndef UNIV_SEARCH_DEBUG btr_pcur_open_with_no_init(index, search_tuple, PAGE_CUR_GE, BTR_SEARCH_LEAF, pcur, -#ifndef UNIV_SEARCH_DEBUG RW_S_LATCH, -#else + mtr); +#else /* UNIV_SEARCH_DEBUG */ + btr_pcur_open_with_no_init(index, search_tuple, PAGE_CUR_GE, + BTR_SEARCH_LEAF, pcur, 0, -#endif mtr); +#endif /* UNIV_SEARCH_DEBUG */ rec = btr_pcur_get_rec(pcur); if (!page_rec_is_user_rec(rec)) { @@ -3694,7 +3665,7 @@ shortcut_fails_too_big_rec: && !page_rec_is_supremum(rec) && set_also_gap_locks && !(srv_locks_unsafe_for_binlog - || trx->isolation_level == TRX_ISO_READ_COMMITTED) + || trx->isolation_level <= TRX_ISO_READ_COMMITTED) && prebuilt->select_lock_type != LOCK_NONE) { /* Try to place a gap lock on the next index record @@ -3790,7 +3761,7 @@ rec_loop: if (set_also_gap_locks && !(srv_locks_unsafe_for_binlog - || trx->isolation_level == TRX_ISO_READ_COMMITTED) + || trx->isolation_level <= TRX_ISO_READ_COMMITTED) && prebuilt->select_lock_type != LOCK_NONE) { /* Try to place a lock on the index record */ @@ -3924,7 +3895,7 @@ wrong_offs: if (set_also_gap_locks && !(srv_locks_unsafe_for_binlog || trx->isolation_level - == TRX_ISO_READ_COMMITTED) + <= TRX_ISO_READ_COMMITTED) && prebuilt->select_lock_type != LOCK_NONE) { /* Try to place a gap lock on the index @@ -3960,7 +3931,7 @@ wrong_offs: if (set_also_gap_locks && !(srv_locks_unsafe_for_binlog || trx->isolation_level - == TRX_ISO_READ_COMMITTED) + <= TRX_ISO_READ_COMMITTED) && prebuilt->select_lock_type != LOCK_NONE) { /* Try to place a gap lock on the index @@ -4008,7 +3979,7 @@ wrong_offs: if (!set_also_gap_locks || srv_locks_unsafe_for_binlog - || trx->isolation_level == TRX_ISO_READ_COMMITTED + || trx->isolation_level <= TRX_ISO_READ_COMMITTED || (unique_search && !UNIV_UNLIKELY(rec_get_deleted_flag(rec, comp)))) { @@ -4047,7 +4018,7 @@ no_gap_lock: const rec_t* old_vers; case DB_SUCCESS: if (srv_locks_unsafe_for_binlog - || trx->isolation_level == TRX_ISO_READ_COMMITTED) { + || trx->isolation_level <= TRX_ISO_READ_COMMITTED) { /* Note that a record of prebuilt->index was locked. */ prebuilt->new_rec_locks = 1; @@ -4056,6 +4027,7 @@ no_gap_lock: case DB_LOCK_WAIT: if (UNIV_LIKELY(prebuilt->row_read_type != ROW_READ_TRY_SEMI_CONSISTENT) + || unique_search || index != clust_index) { goto lock_wait_or_error; @@ -4179,7 +4151,7 @@ no_gap_lock: /* The record is delete-marked: we can skip it */ if ((srv_locks_unsafe_for_binlog - || trx->isolation_level == TRX_ISO_READ_COMMITTED) + || trx->isolation_level <= TRX_ISO_READ_COMMITTED) && prebuilt->select_lock_type != LOCK_NONE && !did_semi_consistent_read) { @@ -4246,7 +4218,7 @@ requires_clust_rec: } if ((srv_locks_unsafe_for_binlog - || trx->isolation_level == TRX_ISO_READ_COMMITTED) + || trx->isolation_level <= TRX_ISO_READ_COMMITTED) && prebuilt->select_lock_type != LOCK_NONE) { /* Note that both the secondary index record and the clustered index record were locked. */ @@ -4259,7 +4231,7 @@ requires_clust_rec: /* The record is delete marked: we can skip it */ if ((srv_locks_unsafe_for_binlog - || trx->isolation_level == TRX_ISO_READ_COMMITTED) + || trx->isolation_level <= TRX_ISO_READ_COMMITTED) && prebuilt->select_lock_type != LOCK_NONE) { /* No need to keep a lock on a delete-marked @@ -4470,7 +4442,7 @@ lock_wait_or_error: moves_up, &mtr); if ((srv_locks_unsafe_for_binlog - || trx->isolation_level == TRX_ISO_READ_COMMITTED) + || trx->isolation_level <= TRX_ISO_READ_COMMITTED) && !same_user_rec) { /* Since we were not able to restore the cursor @@ -4616,6 +4588,7 @@ row_search_autoinc_read_column( dict_index_t* index, /*!< in: index to read from */ const rec_t* rec, /*!< in: current rec */ ulint col_no, /*!< in: column number */ + ulint mtype, /*!< in: column main type */ ibool unsigned_type) /*!< in: signed or unsigned flag */ { ulint len; @@ -4632,10 +4605,26 @@ row_search_autoinc_read_column( data = rec_get_nth_field(rec, offsets, col_no, &len); ut_a(len != UNIV_SQL_NULL); - ut_a(len <= sizeof value); - /* we assume AUTOINC value cannot be negative */ - value = mach_read_int_type(data, len, unsigned_type); + switch (mtype) { + case DATA_INT: + ut_a(len <= sizeof value); + value = mach_read_int_type(data, len, unsigned_type); + break; + + case DATA_FLOAT: + ut_a(len == sizeof(float)); + value = (ib_uint64_t) mach_float_read(data); + break; + + case DATA_DOUBLE: + ut_a(len == sizeof(double)); + value = (ib_uint64_t) mach_double_read(data); + break; + + default: + ut_error; + } if (UNIV_LIKELY_NULL(heap)) { mem_heap_free(heap); @@ -4721,7 +4710,8 @@ row_search_max_autoinc( dfield->col->prtype & DATA_UNSIGNED); *value = row_search_autoinc_read_column( - index, rec, i, unsigned_type); + index, rec, i, + dfield->col->mtype, unsigned_type); } } diff --git a/storage/innodb_plugin/row/row0umod.c b/storage/innodb_plugin/row/row0umod.c index 6be475d8c78..e7245dbee41 100644 --- a/storage/innodb_plugin/row/row0umod.c +++ b/storage/innodb_plugin/row/row0umod.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1997, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1997, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -144,13 +144,17 @@ row_undo_mod_clust_low( /***********************************************************//** Removes a clustered index record after undo if possible. +This is attempted when the record was inserted by updating a +delete-marked record and there no longer exist transactions +that would see the delete-marked record. In other words, we +roll back the insert by purging the record. @return DB_SUCCESS, DB_FAIL, or error code: we may run out of file space */ static ulint row_undo_mod_remove_clust_low( /*==========================*/ undo_node_t* node, /*!< in: row undo node */ - que_thr_t* thr __attribute__((unused)), /*!< in: query thread */ + que_thr_t* thr, /*!< in: query thread */ mtr_t* mtr, /*!< in: mtr */ ulint mode) /*!< in: BTR_MODIFY_LEAF or BTR_MODIFY_TREE */ { @@ -159,6 +163,7 @@ row_undo_mod_remove_clust_low( ulint err; ibool success; + ut_ad(node->rec_type == TRX_UNDO_UPD_DEL_REC); pcur = &(node->pcur); btr_cur = btr_pcur_get_btr_cur(pcur); @@ -190,11 +195,13 @@ row_undo_mod_remove_clust_low( } else { ut_ad(mode == BTR_MODIFY_TREE); - /* Note that since this operation is analogous to purge, - we can free also inherited externally stored fields: - hence the RB_NONE in the call below */ + /* This operation is analogous to purge, we can free also + inherited externally stored fields */ - btr_cur_pessimistic_delete(&err, FALSE, btr_cur, RB_NONE, mtr); + btr_cur_pessimistic_delete(&err, FALSE, btr_cur, + thr_is_recv(thr) + ? RB_RECOVERY_PURGE_REC + : RB_NONE, mtr); /* The delete operation may fail if we have little file space left: TODO: easiest to crash the database @@ -370,10 +377,11 @@ row_undo_mod_del_mark_or_remove_sec_low( } else { ut_ad(mode == BTR_MODIFY_TREE); - /* No need to distinguish RB_RECOVERY here, because we - are deleting a secondary index record: the distinction - between RB_NORMAL and RB_RECOVERY only matters when - deleting a record that contains externally stored + /* No need to distinguish RB_RECOVERY_PURGE here, + because we are deleting a secondary index record: + the distinction between RB_NORMAL and + RB_RECOVERY_PURGE only matters when deleting a + record that contains externally stored columns. */ ut_ad(!dict_index_is_clust(index)); btr_cur_pessimistic_delete(&err, FALSE, btr_cur, @@ -438,7 +446,7 @@ row_undo_mod_del_unmark_sec_and_undo_update( BTR_MODIFY_TREE */ que_thr_t* thr, /*!< in: query thread */ dict_index_t* index, /*!< in: index */ - dtuple_t* entry) /*!< in: index entry */ + const dtuple_t* entry) /*!< in: index entry */ { mem_heap_t* heap; btr_pcur_t pcur; @@ -533,6 +541,7 @@ row_undo_mod_upd_del_sec( dict_index_t* index; ulint err = DB_SUCCESS; + ut_ad(node->rec_type == TRX_UNDO_UPD_DEL_REC); heap = mem_heap_create(1024); while (node->index != NULL) { @@ -550,7 +559,7 @@ row_undo_mod_upd_del_sec( does not exist. However, this situation may only occur during the rollback of incomplete transactions. */ - ut_a(trx_is_recv(thr_get_trx(thr))); + ut_a(thr_is_recv(thr)); } else { err = row_undo_mod_del_mark_or_remove_sec( node, thr, index, entry); diff --git a/storage/innodb_plugin/row/row0upd.c b/storage/innodb_plugin/row/row0upd.c index 58dfd43ead9..95d1d00aeef 100644 --- a/storage/innodb_plugin/row/row0upd.c +++ b/storage/innodb_plugin/row/row0upd.c @@ -1344,9 +1344,6 @@ row_upd_copy_columns( data = rec_get_nth_field(rec, offsets, column->field_nos[SYM_CLUST_FIELD_NO], &len); - if (len == UNIV_SQL_NULL) { - len = UNIV_SQL_NULL; - } eval_node_copy_and_alloc_val(column, data, len); column = UT_LIST_GET_NEXT(col_var_list, column); diff --git a/storage/innodb_plugin/srv/srv0srv.c b/storage/innodb_plugin/srv/srv0srv.c index 639da1ed2f3..63c355cea32 100644 --- a/storage/innodb_plugin/srv/srv0srv.c +++ b/storage/innodb_plugin/srv/srv0srv.c @@ -1,7 +1,8 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. Copyright (c) 2008, 2009 Google Inc. +Copyright (c) 2009, Percona Inc. Portions of this file contain modifications contributed and copyrighted by Google, Inc. Those modifications are gratefully acknowledged and are described @@ -9,6 +10,13 @@ briefly in the InnoDB documentation. The contributions by Google are incorporated with their permission, and subject to the conditions contained in the file COPYING.Google. +Portions of this file contain modifications contributed and copyrighted +by Percona Inc.. Those modifications are +gratefully acknowledged and are described briefly in the InnoDB +documentation. The contributions by Percona Inc. are incorporated with +their permission, and subject to the conditions contained in the file +COPYING.Percona. + This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; version 2 of the License. @@ -22,32 +30,6 @@ this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA *****************************************************************************/ -/*********************************************************************** - -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. -Copyright (c) 2009, Percona Inc. - -Portions of this file contain modifications contributed and copyrighted -by Percona Inc.. Those modifications are -gratefully acknowledged and are described briefly in the InnoDB -documentation. The contributions by Percona Inc. are incorporated with -their permission, and subject to the conditions contained in the file -COPYING.Percona. - -This program is free software; you can redistribute it and/or modify it -under the terms of the GNU General Public License as published by the -Free Software Foundation; version 2 of the License. - -This program is distributed in the hope that it will be useful, but -WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General -Public License for more details. - -You should have received a copy of the GNU General Public License along -with this program; if not, write to the Free Software Foundation, Inc., -59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -***********************************************************************/ /**************************************************//** @file srv/srv0srv.c @@ -119,7 +101,8 @@ UNIV_INTERN ulint srv_fatal_semaphore_wait_threshold = 600; in microseconds, in order to reduce the lagging of the purge thread. */ UNIV_INTERN ulint srv_dml_needed_delay = 0; -UNIV_INTERN ibool srv_lock_timeout_and_monitor_active = FALSE; +UNIV_INTERN ibool srv_lock_timeout_active = FALSE; +UNIV_INTERN ibool srv_monitor_active = FALSE; UNIV_INTERN ibool srv_error_monitor_active = FALSE; UNIV_INTERN const char* srv_main_thread_op_info = ""; @@ -188,7 +171,17 @@ UNIV_INTERN ulong srv_flush_log_at_trx_commit = 1; the checkpoints. */ UNIV_INTERN char srv_adaptive_flushing = TRUE; -/* The sort order table of the MySQL latin1_swedish_ci character set +/** Maximum number of times allowed to conditionally acquire +mutex before switching to blocking wait on the mutex */ +#define MAX_MUTEX_NOWAIT 20 + +/** Check whether the number of failed nonblocking mutex +acquisition attempts exceeds maximum allowed value. If so, +srv_printf_innodb_monitor() will request mutex acquisition +with mutex_enter(), which will wait until it gets the mutex. */ +#define MUTEX_NOWAIT(mutex_skipped) ((mutex_skipped) < MAX_MUTEX_NOWAIT) + +/** The sort order table of the MySQL latin1_swedish_ci character set collation */ UNIV_INTERN const byte* srv_latin1_ordering; @@ -1616,8 +1609,9 @@ srv_suspend_mysql_thread( innodb_lock_wait_timeout, because trx->mysql_thd == NULL. */ lock_wait_timeout = thd_lock_wait_timeout(trx->mysql_thd); - if (lock_wait_timeout < 100000000 - && wait_time > (double) lock_wait_timeout) { + if (trx_is_interrupted(trx) + || (lock_wait_timeout < 100000000 + && wait_time > (double) lock_wait_timeout)) { trx->error_state = DB_LOCK_WAIT_TIMEOUT; } @@ -1683,12 +1677,15 @@ srv_refresh_innodb_monitor_stats(void) } /******************************************************************//** -Outputs to a file the output of the InnoDB Monitor. */ +Outputs to a file the output of the InnoDB Monitor. +@return FALSE if not all information printed +due to failure to obtain necessary mutex */ UNIV_INTERN -void +ibool srv_printf_innodb_monitor( /*======================*/ FILE* file, /*!< in: output stream */ + ibool nowait, /*!< in: whether to wait for kernel mutex */ ulint* trx_start, /*!< out: file position of the start of the list of active transactions */ ulint* trx_end) /*!< out: file position of the end of @@ -1697,6 +1694,7 @@ srv_printf_innodb_monitor( double time_elapsed; time_t current_time; ulint n_reserved; + ibool ret; mutex_enter(&srv_innodb_monitor_mutex); @@ -1720,9 +1718,9 @@ srv_printf_innodb_monitor( "Per second averages calculated from the last %lu seconds\n", (ulong)time_elapsed); - fputs("----------\n" - "BACKGROUND THREAD\n" - "----------\n", file); + fputs("-----------------\n" + "BACKGROUND THREAD\n" + "-----------------\n", file); srv_print_master_thread_info(file); fputs("----------\n" @@ -1746,24 +1744,31 @@ srv_printf_innodb_monitor( mutex_exit(&dict_foreign_err_mutex); - lock_print_info_summary(file); - if (trx_start) { - long t = ftell(file); - if (t < 0) { - *trx_start = ULINT_UNDEFINED; - } else { - *trx_start = (ulint) t; + /* Only if lock_print_info_summary proceeds correctly, + before we call the lock_print_info_all_transactions + to print all the lock information. */ + ret = lock_print_info_summary(file, nowait); + + if (ret) { + if (trx_start) { + long t = ftell(file); + if (t < 0) { + *trx_start = ULINT_UNDEFINED; + } else { + *trx_start = (ulint) t; + } } - } - lock_print_info_all_transactions(file); - if (trx_end) { - long t = ftell(file); - if (t < 0) { - *trx_end = ULINT_UNDEFINED; - } else { - *trx_end = (ulint) t; + lock_print_info_all_transactions(file); + if (trx_end) { + long t = ftell(file); + if (t < 0) { + *trx_end = ULINT_UNDEFINED; + } else { + *trx_end = (ulint) t; + } } } + fputs("--------\n" "FILE I/O\n" "--------\n", file); @@ -1861,6 +1866,8 @@ srv_printf_innodb_monitor( "============================\n", file); mutex_exit(&srv_innodb_monitor_mutex); fflush(file); + + return(ret); } /******************************************************************//** @@ -1948,26 +1955,23 @@ srv_export_innodb_status(void) } /*********************************************************************//** -A thread which wakes up threads whose lock wait may have lasted too long. -This also prints the info output by various InnoDB monitors. +A thread which prints the info output by various InnoDB monitors. @return a dummy parameter */ UNIV_INTERN os_thread_ret_t -srv_lock_timeout_and_monitor_thread( -/*================================*/ +srv_monitor_thread( +/*===============*/ void* arg __attribute__((unused))) /*!< in: a dummy parameter required by os_thread_create */ { - srv_slot_t* slot; double time_elapsed; time_t current_time; time_t last_table_monitor_time; time_t last_tablespace_monitor_time; time_t last_monitor_time; - ibool some_waits; - double wait_time; - ulint i; + ulint mutex_skipped; + ibool last_srv_print_monitor; #ifdef UNIV_DEBUG_THREAD_CREATION fprintf(stderr, "Lock timeout thread starts, id %lu\n", @@ -1978,13 +1982,15 @@ srv_lock_timeout_and_monitor_thread( last_table_monitor_time = time(NULL); last_tablespace_monitor_time = time(NULL); last_monitor_time = time(NULL); + mutex_skipped = 0; + last_srv_print_monitor = srv_print_innodb_monitor; loop: - srv_lock_timeout_and_monitor_active = TRUE; + srv_monitor_active = TRUE; - /* When someone is waiting for a lock, we wake up every second - and check if a timeout has passed for a lock wait */ + /* Wake up every 5 seconds to see if we need to print + monitor information. */ - os_thread_sleep(1000000); + os_thread_sleep(5000000); current_time = time(NULL); @@ -1994,14 +2000,40 @@ loop: last_monitor_time = time(NULL); if (srv_print_innodb_monitor) { - srv_printf_innodb_monitor(stderr, NULL, NULL); + /* Reset mutex_skipped counter everytime + srv_print_innodb_monitor changes. This is to + ensure we will not be blocked by kernel_mutex + for short duration information printing, + such as requested by sync_array_print_long_waits() */ + if (!last_srv_print_monitor) { + mutex_skipped = 0; + last_srv_print_monitor = TRUE; + } + + if (!srv_printf_innodb_monitor(stderr, + MUTEX_NOWAIT(mutex_skipped), + NULL, NULL)) { + mutex_skipped++; + } else { + /* Reset the counter */ + mutex_skipped = 0; + } + } else { + last_srv_print_monitor = FALSE; } + if (srv_innodb_status) { mutex_enter(&srv_monitor_file_mutex); rewind(srv_monitor_file); - srv_printf_innodb_monitor(srv_monitor_file, NULL, - NULL); + if (!srv_printf_innodb_monitor(srv_monitor_file, + MUTEX_NOWAIT(mutex_skipped), + NULL, NULL)) { + mutex_skipped++; + } else { + mutex_skipped = 0; + } + os_file_set_eof(srv_monitor_file); mutex_exit(&srv_monitor_file_mutex); } @@ -2054,6 +2086,56 @@ loop: } } + if (srv_shutdown_state >= SRV_SHUTDOWN_CLEANUP) { + goto exit_func; + } + + if (srv_print_innodb_monitor + || srv_print_innodb_lock_monitor + || srv_print_innodb_tablespace_monitor + || srv_print_innodb_table_monitor) { + goto loop; + } + + srv_monitor_active = FALSE; + + goto loop; + +exit_func: + srv_monitor_active = FALSE; + + /* We count the number of threads in os_thread_exit(). A created + thread should always use that to exit and not use return() to exit. */ + + os_thread_exit(NULL); + + OS_THREAD_DUMMY_RETURN; +} + +/*********************************************************************//** +A thread which wakes up threads whose lock wait may have lasted too long. +@return a dummy parameter */ +UNIV_INTERN +os_thread_ret_t +srv_lock_timeout_thread( +/*====================*/ + void* arg __attribute__((unused))) + /* in: a dummy parameter required by + os_thread_create */ +{ + srv_slot_t* slot; + ibool some_waits; + double wait_time; + ulint i; + +loop: + /* When someone is waiting for a lock, we wake up every second + and check if a timeout has passed for a lock wait */ + + os_thread_sleep(1000000); + + srv_lock_timeout_active = TRUE; + mutex_enter(&kernel_mutex); some_waits = FALSE; @@ -2077,9 +2159,10 @@ loop: lock_wait_timeout = thd_lock_wait_timeout( trx->mysql_thd); - if (lock_wait_timeout < 100000000 - && (wait_time > (double) lock_wait_timeout - || wait_time < 0)) { + if (trx_is_interrupted(trx) + || (lock_wait_timeout < 100000000 + && (wait_time > (double) lock_wait_timeout + || wait_time < 0))) { /* Timeout exceeded or a wrap-around in system time counter: cancel the lock request queued @@ -2104,17 +2187,11 @@ loop: goto exit_func; } - if (some_waits || srv_print_innodb_monitor - || srv_print_innodb_lock_monitor - || srv_print_innodb_tablespace_monitor - || srv_print_innodb_table_monitor) { + if (some_waits) { goto loop; } - /* No one was waiting for a lock and no monitor was active: - suspend this thread */ - - srv_lock_timeout_and_monitor_active = FALSE; + srv_lock_timeout_active = FALSE; #if 0 /* The following synchronisation is disabled, since @@ -2124,7 +2201,7 @@ loop: goto loop; exit_func: - srv_lock_timeout_and_monitor_active = FALSE; + srv_lock_timeout_active = FALSE; /* We count the number of threads in os_thread_exit(). A created thread should always use that to exit and not use return() to exit. */ @@ -2449,7 +2526,10 @@ loop: BUF_FLUSH_LIST, n_flush, IB_ULONGLONG_MAX); - skip_sleep = TRUE; + + if (n_flush == PCT_IO(100)) { + skip_sleep = TRUE; + } } } diff --git a/storage/innodb_plugin/srv/srv0start.c b/storage/innodb_plugin/srv/srv0start.c index d5f6120ca31..e517b9a86b0 100644 --- a/storage/innodb_plugin/srv/srv0start.c +++ b/storage/innodb_plugin/srv/srv0start.c @@ -1,7 +1,8 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. Copyright (c) 2008, Google Inc. +Copyright (c) 2009, Percona Inc. Portions of this file contain modifications contributed and copyrighted by Google, Inc. Those modifications are gratefully acknowledged and are described @@ -9,6 +10,13 @@ briefly in the InnoDB documentation. The contributions by Google are incorporated with their permission, and subject to the conditions contained in the file COPYING.Google. +Portions of this file contain modifications contributed and copyrighted +by Percona Inc.. Those modifications are +gratefully acknowledged and are described briefly in the InnoDB +documentation. The contributions by Percona Inc. are incorporated with +their permission, and subject to the conditions contained in the file +COPYING.Percona. + This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; version 2 of the License. @@ -22,32 +30,6 @@ this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA *****************************************************************************/ -/*********************************************************************** - -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. -Copyright (c) 2009, Percona Inc. - -Portions of this file contain modifications contributed and copyrighted -by Percona Inc.. Those modifications are -gratefully acknowledged and are described briefly in the InnoDB -documentation. The contributions by Percona Inc. are incorporated with -their permission, and subject to the conditions contained in the file -COPYING.Percona. - -This program is free software; you can redistribute it and/or modify it -under the terms of the GNU General Public License as published by the -Free Software Foundation; version 2 of the License. - -This program is distributed in the hope that it will be useful, but -WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General -Public License for more details. - -You should have received a copy of the GNU General Public License along -with this program; if not, write to the Free Software Foundation, Inc., -59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -***********************************************************************/ /********************************************************************//** @file srv/srv0start.c @@ -105,6 +87,7 @@ Created 2/16/1996 Heikki Tuuri # include "btr0pcur.h" # include "thr0loc.h" # include "os0sync.h" /* for INNODB_RW_LOCKS_USE_ATOMICS */ +# include "zlib.h" /* for ZLIB_VERSION */ /** Log sequence number immediately after startup */ UNIV_INTERN ib_uint64_t srv_start_lsn; @@ -143,9 +126,9 @@ static mutex_t ios_mutex; static ulint ios; /** io_handler_thread parameters for thread identification */ -static ulint n[SRV_MAX_N_IO_THREADS + 5]; +static ulint n[SRV_MAX_N_IO_THREADS + 6]; /** io_handler_thread identifiers */ -static os_thread_id_t thread_ids[SRV_MAX_N_IO_THREADS + 5]; +static os_thread_id_t thread_ids[SRV_MAX_N_IO_THREADS + 6]; /** We use this mutex to test the return value of pthread_mutex_trylock on successful locking. HP-UX does NOT return 0, though Linux et al do. */ @@ -1074,7 +1057,11 @@ innobase_start_or_create_for_mysql(void) #ifdef UNIV_IBUF_DEBUG fprintf(stderr, "InnoDB: !!!!!!!! UNIV_IBUF_DEBUG switched on !!!!!!!!!\n" - "InnoDB: Crash recovery will fail with UNIV_IBUF_DEBUG\n"); +# ifdef UNIV_IBUF_COUNT_DEBUG + "InnoDB: !!!!!!!! UNIV_IBUF_COUNT_DEBUG switched on !!!!!!!!!\n" + "InnoDB: Crash recovery will fail with UNIV_IBUF_COUNT_DEBUG\n" +# endif + ); #endif #ifdef UNIV_SYNC_DEBUG @@ -1101,7 +1088,15 @@ innobase_start_or_create_for_mysql(void) "InnoDB: The InnoDB memory heap is disabled\n"); } - fprintf(stderr, "InnoDB: %s\n", IB_ATOMICS_STARTUP_MSG); + fputs("InnoDB: " IB_ATOMICS_STARTUP_MSG + "\nInnoDB: Compressed tables use zlib " ZLIB_VERSION +#ifdef UNIV_ZIP_DEBUG + " with validation" +#endif /* UNIV_ZIP_DEBUG */ +#ifdef UNIV_ZIP_COPY + " and extra copying" +#endif /* UNIV_ZIP_COPY */ + "\n" , stderr); /* Since InnoDB does not currently clean up all its internal data structures in MySQL Embedded Server Library server_end(), we @@ -1575,6 +1570,14 @@ innobase_start_or_create_for_mysql(void) dict_boot(); trx_sys_init_at_db_start(); + /* Initialize the fsp free limit global variable in the log + system */ + fsp_header_get_free_limit(); + + /* recv_recovery_from_checkpoint_finish needs trx lists which + are initialized in trx_sys_init_at_db_start(). */ + + recv_recovery_from_checkpoint_finish(); if (srv_force_recovery < SRV_FORCE_NO_IBUF_MERGE) { /* The following call is necessary for the insert buffer to work with multiple tablespaces. We must @@ -1590,26 +1593,14 @@ innobase_start_or_create_for_mysql(void) every table in the InnoDB data dictionary that has an .ibd file. - We also determine the maximum tablespace id used. - - TODO: We may have incomplete transactions in the - data dictionary tables. Does that harm the scanning of - the data dictionary below? */ + We also determine the maximum tablespace id used. */ dict_check_tablespaces_and_store_max_id( recv_needed_recovery); } srv_startup_is_before_trx_rollback_phase = FALSE; - - /* Initialize the fsp free limit global variable in the log - system */ - fsp_header_get_free_limit(); - - /* recv_recovery_from_checkpoint_finish needs trx lists which - are initialized in trx_sys_init_at_db_start(). */ - - recv_recovery_from_checkpoint_finish(); + recv_recovery_rollback_active(); /* It is possible that file_format tag has never been set. In this case we initialize it to minimum @@ -1658,15 +1649,18 @@ innobase_start_or_create_for_mysql(void) /* fprintf(stderr, "Max allowed record size %lu\n", page_get_free_space_of_empty() / 2); */ - /* Create the thread which watches the timeouts for lock waits - and prints InnoDB monitor info */ - - os_thread_create(&srv_lock_timeout_and_monitor_thread, NULL, + /* Create the thread which watches the timeouts for lock waits */ + os_thread_create(&srv_lock_timeout_thread, NULL, thread_ids + 2 + SRV_MAX_N_IO_THREADS); /* Create the thread which warns of long semaphore waits */ os_thread_create(&srv_error_monitor_thread, NULL, thread_ids + 3 + SRV_MAX_N_IO_THREADS); + + /* Create the thread which prints InnoDB monitor info */ + os_thread_create(&srv_monitor_thread, NULL, + thread_ids + 4 + SRV_MAX_N_IO_THREADS); + srv_is_being_started = FALSE; if (trx_doublewrite == NULL) { diff --git a/storage/innodb_plugin/sync/sync0sync.c b/storage/innodb_plugin/sync/sync0sync.c index 569fc6328c4..2be9d667705 100644 --- a/storage/innodb_plugin/sync/sync0sync.c +++ b/storage/innodb_plugin/sync/sync0sync.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1995, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1995, 2010, Innobase Oy. All Rights Reserved. Copyright (c) 2008, Google Inc. Portions of this file contain modifications contributed and copyrighted by @@ -315,6 +315,15 @@ mutex_free( ut_a(mutex_get_lock_word(mutex) == 0); ut_a(mutex_get_waiters(mutex) == 0); +#ifdef UNIV_MEM_DEBUG + if (mutex == &mem_hash_mutex) { + ut_ad(UT_LIST_GET_LEN(mutex_list) == 1); + ut_ad(UT_LIST_GET_FIRST(mutex_list) == &mem_hash_mutex); + UT_LIST_REMOVE(list, mutex_list, mutex); + goto func_exit; + } +#endif /* UNIV_MEM_DEBUG */ + if (mutex != &mutex_list_mutex #ifdef UNIV_SYNC_DEBUG && mutex != &sync_thread_mutex @@ -336,7 +345,9 @@ mutex_free( } os_event_free(mutex->event); - +#ifdef UNIV_MEM_DEBUG +func_exit: +#endif /* UNIV_MEM_DEBUG */ #if !defined(HAVE_ATOMIC_BUILTINS) os_fast_mutex_free(&(mutex->os_fast_mutex)); #endif @@ -947,12 +958,62 @@ sync_thread_levels_contain( } /******************************************************************//** +Checks if the level array for the current thread contains a +mutex or rw-latch at the specified level. +@return a matching latch, or NULL if not found */ +UNIV_INTERN +void* +sync_thread_levels_contains( +/*========================*/ + ulint level) /*!< in: latching order level + (SYNC_DICT, ...)*/ +{ + sync_level_t* arr; + sync_thread_t* thread_slot; + sync_level_t* slot; + ulint i; + + if (!sync_order_checks_on) { + + return(NULL); + } + + mutex_enter(&sync_thread_mutex); + + thread_slot = sync_thread_level_arrays_find_slot(); + + if (thread_slot == NULL) { + + mutex_exit(&sync_thread_mutex); + + return(NULL); + } + + arr = thread_slot->levels; + + for (i = 0; i < SYNC_THREAD_N_LEVELS; i++) { + + slot = sync_thread_levels_get_nth(arr, i); + + if (slot->latch != NULL && slot->level == level) { + + mutex_exit(&sync_thread_mutex); + return(slot->latch); + } + } + + mutex_exit(&sync_thread_mutex); + + return(NULL); +} + +/******************************************************************//** Checks that the level array for the current thread is empty. -@return TRUE if empty except the exceptions specified below */ +@return a latch, or NULL if empty except the exceptions specified below */ UNIV_INTERN -ibool -sync_thread_levels_empty_gen( -/*=========================*/ +void* +sync_thread_levels_nonempty_gen( +/*============================*/ ibool dict_mutex_allowed) /*!< in: TRUE if dictionary mutex is allowed to be owned by the thread, also purge_is_running mutex is @@ -965,7 +1026,7 @@ sync_thread_levels_empty_gen( if (!sync_order_checks_on) { - return(TRUE); + return(NULL); } mutex_enter(&sync_thread_mutex); @@ -976,7 +1037,7 @@ sync_thread_levels_empty_gen( mutex_exit(&sync_thread_mutex); - return(TRUE); + return(NULL); } arr = thread_slot->levels; @@ -993,13 +1054,13 @@ sync_thread_levels_empty_gen( mutex_exit(&sync_thread_mutex); ut_error; - return(FALSE); + return(slot->latch); } } mutex_exit(&sync_thread_mutex); - return(TRUE); + return(NULL); } /******************************************************************//** @@ -1370,6 +1431,12 @@ sync_close(void) mutex = UT_LIST_GET_FIRST(mutex_list); while (mutex) { +#ifdef UNIV_MEM_DEBUG + if (mutex == &mem_hash_mutex) { + mutex = UT_LIST_GET_NEXT(list, mutex); + continue; + } +#endif /* UNIV_MEM_DEBUG */ mutex_free(mutex); mutex = UT_LIST_GET_FIRST(mutex_list); } diff --git a/storage/innodb_plugin/trx/trx0i_s.c b/storage/innodb_plugin/trx/trx0i_s.c index 1b20eaabf42..c160eb2942a 100644 --- a/storage/innodb_plugin/trx/trx0i_s.c +++ b/storage/innodb_plugin/trx/trx0i_s.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 2007, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 2007, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -28,11 +28,18 @@ table cache" for later retrieval. Created July 17, 2007 Vasil Dimov *******************************************************/ +/* Found during the build of 5.5.3 on Linux 2.4 and early 2.6 kernels: + The includes "univ.i" -> "my_global.h" cause a different path + to be taken further down with pthread functions and types, + so they must come first. + From the symptoms, this is related to bug#46587 in the MySQL bug DB. +*/ +#include "univ.i" + #include <mysql/plugin.h> #include "mysql_addons.h" -#include "univ.i" #include "buf0buf.h" #include "dict0dict.h" #include "ha0storage.h" diff --git a/storage/innodb_plugin/trx/trx0rec.c b/storage/innodb_plugin/trx/trx0rec.c index 5097cf18dcd..f50e10ed756 100644 --- a/storage/innodb_plugin/trx/trx0rec.c +++ b/storage/innodb_plugin/trx/trx0rec.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -350,8 +350,13 @@ trx_undo_rec_get_col_val( ut_ad(*orig_len >= BTR_EXTERN_FIELD_REF_SIZE); ut_ad(*len > *orig_len); - ut_ad(*len >= REC_MAX_INDEX_COL_LEN + /* @see dtuple_convert_big_rec() */ + ut_ad(*len >= BTR_EXTERN_FIELD_REF_SIZE * 2); + /* we do not have access to index->table here + ut_ad(dict_table_get_format(index->table) >= DICT_TF_FORMAT_ZIP + || *len >= REC_MAX_INDEX_COL_LEN + BTR_EXTERN_FIELD_REF_SIZE); + */ *len += UNIV_EXTERN_STORAGE_FIELD; break; @@ -977,6 +982,7 @@ trx_undo_update_rec_get_update( fprintf(stderr, "\n" "InnoDB: n_fields = %lu, i = %lu, ptr %p\n", (ulong) n_fields, (ulong) i, ptr); + *upd = NULL; return(NULL); } @@ -1074,11 +1080,15 @@ trx_undo_rec_get_partial_row( /* If the prefix of this column is indexed, ensure that enough prefix is stored in the undo log record. */ - ut_a(ignore_prefix - || !col->ord_part - || dfield_get_len(dfield) - >= REC_MAX_INDEX_COL_LEN - + BTR_EXTERN_FIELD_REF_SIZE); + if (!ignore_prefix && col->ord_part) { + ut_a(dfield_get_len(dfield) + >= 2 * BTR_EXTERN_FIELD_REF_SIZE); + ut_a(dict_table_get_format(index->table) + >= DICT_TF_FORMAT_ZIP + || dfield_get_len(dfield) + >= REC_MAX_INDEX_COL_LEN + + BTR_EXTERN_FIELD_REF_SIZE); + } } } diff --git a/storage/innodb_plugin/trx/trx0rseg.c b/storage/innodb_plugin/trx/trx0rseg.c index 8d754788e2a..36dea9b2a95 100644 --- a/storage/innodb_plugin/trx/trx0rseg.c +++ b/storage/innodb_plugin/trx/trx0rseg.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -286,39 +286,3 @@ trx_rseg_list_and_array_init( } } } - -/****************************************************************//** -Creates a new rollback segment to the database. -@return the created segment object, NULL if fail */ -UNIV_INTERN -trx_rseg_t* -trx_rseg_create( -/*============*/ - ulint space, /*!< in: space id */ - ulint max_size, /*!< in: max size in pages */ - ulint* id, /*!< out: rseg id */ - mtr_t* mtr) /*!< in: mtr */ -{ - ulint flags; - ulint zip_size; - ulint page_no; - trx_rseg_t* rseg; - - mtr_x_lock(fil_space_get_latch(space, &flags), mtr); - zip_size = dict_table_flags_to_zip_size(flags); - mutex_enter(&kernel_mutex); - - page_no = trx_rseg_header_create(space, zip_size, max_size, id, mtr); - - if (page_no == FIL_NULL) { - - mutex_exit(&kernel_mutex); - return(NULL); - } - - rseg = trx_rseg_mem_create(*id, space, zip_size, page_no, mtr); - - mutex_exit(&kernel_mutex); - - return(rseg); -} diff --git a/storage/innodb_plugin/trx/trx0sys.c b/storage/innodb_plugin/trx/trx0sys.c index 79e5af1c677..410c55f132d 100644 --- a/storage/innodb_plugin/trx/trx0sys.c +++ b/storage/innodb_plugin/trx/trx0sys.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -584,8 +584,8 @@ trx_sys_doublewrite_init_or_restore_pages( " recover the database" " with the my.cnf\n" "InnoDB: option:\n" - "InnoDB: set-variable=" - "innodb_force_recovery=6\n"); + "InnoDB:" + " innodb_force_recovery=6\n"); exit(1); } @@ -1535,6 +1535,7 @@ trx_sys_file_format_id_to_name( #endif /* !UNIV_HOTBACKUP */ +#ifndef UNIV_HOTBACKUP /********************************************************************* Shutdown/Close the transaction system. */ UNIV_INTERN @@ -1611,3 +1612,4 @@ trx_sys_close(void) trx_sys = NULL; mutex_exit(&kernel_mutex); } +#endif /* !UNIV_HOTBACKUP */ diff --git a/storage/innodb_plugin/trx/trx0trx.c b/storage/innodb_plugin/trx/trx0trx.c index 0951b98b79f..6ef7e62e6ae 100644 --- a/storage/innodb_plugin/trx/trx0trx.c +++ b/storage/innodb_plugin/trx/trx0trx.c @@ -1,6 +1,6 @@ /***************************************************************************** -Copyright (c) 1996, 2009, Innobase Oy. All Rights Reserved. +Copyright (c) 1996, 2010, Innobase Oy. All Rights Reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software @@ -425,6 +425,7 @@ trx_lists_init_at_db_start(void) trx_undo_t* undo; trx_t* trx; + ut_ad(mutex_own(&kernel_mutex)); UT_LIST_INIT(trx_sys->trx_list); /* Look from the rollback segments if there exist undo logs for @@ -842,7 +843,7 @@ trx_commit_off_kernel( recovery i.e.: back ground rollback thread is still active then there is a chance that the rollback thread may see this trx as COMMITTED_IN_MEMORY and goes adhead to clean it - up calling trx_cleanup_at_db_startup(). This can happen + up calling trx_cleanup_at_db_startup(). This can happen in the case we are committing a trx here that is left in PREPARED state during the crash. Note that commit of the rollback of a PREPARED trx happens in the recovery thread diff --git a/storage/innodb_plugin/ut/ut0rbt.c b/storage/innodb_plugin/ut/ut0rbt.c new file mode 100644 index 00000000000..3d7bc91e714 --- /dev/null +++ b/storage/innodb_plugin/ut/ut0rbt.c @@ -0,0 +1,1249 @@ +/***************************************************************************** + +Copyright (c) 2006, 2009, Innobase Oy. All Rights Reserved. + +This program is free software; you can redistribute it and/or modify it under +the terms of the GNU General Public License as published by the Free Software +Foundation; version 2 of the License. + +This program is distributed in the hope that it will be useful, but WITHOUT +ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS +FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. + +You should have received a copy of the GNU General Public License along with +this program; if not, write to the Free Software Foundation, Inc., 59 Temple +Place, Suite 330, Boston, MA 02111-1307 USA + +*****************************************************************************/ + +/*******************************************************************//** +@file ut/ut0rbt.c +Red-Black tree implementation + +Created 2007-03-20 Sunny Bains +***********************************************************************/ + +#include "ut0rbt.h" + +/************************************************************************ +Definition of a red-black tree +============================== + +A red-black tree is a binary search tree which has the following +red-black properties: + + 1. Every node is either red or black. + 2. Every leaf (NULL - in our case tree->nil) is black. + 3. If a node is red, then both its children are black. + 4. Every simple path from a node to a descendant leaf contains the + same number of black nodes. + + from (3) above, the implication is that on any path from the root + to a leaf, red nodes must not be adjacent. + + However, any number of black nodes may appear in a sequence. */ + +#if defined(IB_RBT_TESTING) +#warning "Testing enabled!" +#endif + +#define ROOT(t) (t->root->left) +#define SIZEOF_NODE(t) ((sizeof(ib_rbt_node_t) + t->sizeof_value) - 1) + +/****************************************************************//** +Print out the sub-tree recursively. */ +static +void +rbt_print_subtree( +/*==============*/ + const ib_rbt_t* tree, /*!< in: tree to traverse */ + const ib_rbt_node_t* node, /*!< in: node to print */ + ib_rbt_print_node print) /*!< in: print key function */ +{ + /* FIXME: Doesn't do anything yet */ + if (node != tree->nil) { + print(node); + rbt_print_subtree(tree, node->left, print); + rbt_print_subtree(tree, node->right, print); + } +} + +/****************************************************************//** +Verify that the keys are in order. +@return TRUE of OK. FALSE if not ordered */ +static +ibool +rbt_check_ordering( +/*===============*/ + const ib_rbt_t* tree) /*!< in: tree to verfify */ +{ + const ib_rbt_node_t* node; + const ib_rbt_node_t* prev = NULL; + + /* Iterate over all the nodes, comparing each node with the prev */ + for (node = rbt_first(tree); node; node = rbt_next(tree, prev)) { + + if (prev && tree->compare(prev->value, node->value) >= 0) { + return(FALSE); + } + + prev = node; + } + + return(TRUE); +} + +/****************************************************************//** +Check that every path from the root to the leaves has the same count. +Count is expressed in the number of black nodes. +@return 0 on failure else black height of the subtree */ +static +ibool +rbt_count_black_nodes( +/*==================*/ + const ib_rbt_t* tree, /*!< in: tree to verify */ + const ib_rbt_node_t* node) /*!< in: start of sub-tree */ +{ + ulint result; + + if (node != tree->nil) { + ulint left_height = rbt_count_black_nodes(tree, node->left); + + ulint right_height = rbt_count_black_nodes(tree, node->right); + + if (left_height == 0 + || right_height == 0 + || left_height != right_height) { + + result = 0; + } else if (node->color == IB_RBT_RED) { + + /* Case 3 */ + if (node->left->color != IB_RBT_BLACK + || node->right->color != IB_RBT_BLACK) { + + result = 0; + } else { + result = left_height; + } + /* Check if it's anything other than RED or BLACK. */ + } else if (node->color != IB_RBT_BLACK) { + + result = 0; + } else { + + result = right_height + 1; + } + } else { + result = 1; + } + + return(result); +} + +/****************************************************************//** +Turn the node's right child's left sub-tree into node's right sub-tree. +This will also make node's right child it's parent. */ +static +void +rbt_rotate_left( +/*============*/ + const ib_rbt_node_t* nil, /*!< in: nil node of the tree */ + ib_rbt_node_t* node) /*!< in: node to rotate */ +{ + ib_rbt_node_t* right = node->right; + + node->right = right->left; + + if (right->left != nil) { + right->left->parent = node; + } + + /* Right's new parent was node's parent. */ + right->parent = node->parent; + + /* Since root's parent is tree->nil and root->parent->left points + back to root, we can avoid the check. */ + if (node == node->parent->left) { + /* Node was on the left of its parent. */ + node->parent->left = right; + } else { + /* Node must have been on the right. */ + node->parent->right = right; + } + + /* Finally, put node on right's left. */ + right->left = node; + node->parent = right; +} + +/****************************************************************//** +Turn the node's left child's right sub-tree into node's left sub-tree. +This also make node's left child it's parent. */ +static +void +rbt_rotate_right( +/*=============*/ + const ib_rbt_node_t* nil, /*!< in: nil node of tree */ + ib_rbt_node_t* node) /*!< in: node to rotate */ +{ + ib_rbt_node_t* left = node->left; + + node->left = left->right; + + if (left->right != nil) { + left->right->parent = node; + } + + /* Left's new parent was node's parent. */ + left->parent = node->parent; + + /* Since root's parent is tree->nil and root->parent->left points + back to root, we can avoid the check. */ + if (node == node->parent->right) { + /* Node was on the left of its parent. */ + node->parent->right = left; + } else { + /* Node must have been on the left. */ + node->parent->left = left; + } + + /* Finally, put node on left's right. */ + left->right = node; + node->parent = left; +} + +/****************************************************************//** +Append a node to the tree. +@return inserted node */ +static +ib_rbt_node_t* +rbt_tree_add_child( +/*===============*/ + const ib_rbt_t* tree, /*!< in: rbt tree */ + ib_rbt_bound_t* parent, /*!< in: node's parent */ + ib_rbt_node_t* node) /*!< in: node to add */ +{ + /* Cast away the const. */ + ib_rbt_node_t* last = (ib_rbt_node_t*) parent->last; + + if (last == tree->root || parent->result < 0) { + last->left = node; + } else { + /* FIXME: We don't handle duplicates (yet)! */ + ut_a(parent->result != 0); + + last->right = node; + } + + node->parent = last; + + return(node); +} + +/****************************************************************//** +Generic binary tree insert +@return inserted node */ +static +ib_rbt_node_t* +rbt_tree_insert( +/*============*/ + ib_rbt_t* tree, /*!< in: rb tree */ + const void* key, /*!< in: key for ordering */ + ib_rbt_node_t* node) /*!< in: node hold the insert value */ +{ + ib_rbt_bound_t parent; + ib_rbt_node_t* current = ROOT(tree); + + parent.result = 0; + parent.last = tree->root; + + /* Regular binary search. */ + while (current != tree->nil) { + + parent.last = current; + parent.result = tree->compare(key, current->value); + + if (parent.result < 0) { + current = current->left; + } else { + current = current->right; + } + } + + ut_a(current == tree->nil); + + rbt_tree_add_child(tree, &parent, node); + + return(node); +} + +/****************************************************************//** +Balance a tree after inserting a node. */ +static +void +rbt_balance_tree( +/*=============*/ + const ib_rbt_t* tree, /*!< in: tree to balance */ + ib_rbt_node_t* node) /*!< in: node that was inserted */ +{ + const ib_rbt_node_t* nil = tree->nil; + ib_rbt_node_t* parent = node->parent; + + /* Restore the red-black property. */ + node->color = IB_RBT_RED; + + while (node != ROOT(tree) && parent->color == IB_RBT_RED) { + ib_rbt_node_t* grand_parent = parent->parent; + + if (parent == grand_parent->left) { + ib_rbt_node_t* uncle = grand_parent->right; + + if (uncle->color == IB_RBT_RED) { + + /* Case 1 - change the colors. */ + uncle->color = IB_RBT_BLACK; + parent->color = IB_RBT_BLACK; + grand_parent->color = IB_RBT_RED; + + /* Move node up the tree. */ + node = grand_parent; + + } else { + + if (node == parent->right) { + /* Right is a black node and node is + to the right, case 2 - move node + up and rotate. */ + node = parent; + rbt_rotate_left(nil, node); + } + + grand_parent = node->parent->parent; + + /* Case 3. */ + node->parent->color = IB_RBT_BLACK; + grand_parent->color = IB_RBT_RED; + + rbt_rotate_right(nil, grand_parent); + } + + } else { + ib_rbt_node_t* uncle = grand_parent->left; + + if (uncle->color == IB_RBT_RED) { + + /* Case 1 - change the colors. */ + uncle->color = IB_RBT_BLACK; + parent->color = IB_RBT_BLACK; + grand_parent->color = IB_RBT_RED; + + /* Move node up the tree. */ + node = grand_parent; + + } else { + + if (node == parent->left) { + /* Left is a black node and node is to + the right, case 2 - move node up and + rotate. */ + node = parent; + rbt_rotate_right(nil, node); + } + + grand_parent = node->parent->parent; + + /* Case 3. */ + node->parent->color = IB_RBT_BLACK; + grand_parent->color = IB_RBT_RED; + + rbt_rotate_left(nil, grand_parent); + } + } + + parent = node->parent; + } + + /* Color the root black. */ + ROOT(tree)->color = IB_RBT_BLACK; +} + +/****************************************************************//** +Find the given node's successor. +@return successor node or NULL if no successor */ +static +ib_rbt_node_t* +rbt_find_successor( +/*===============*/ + const ib_rbt_t* tree, /*!< in: rb tree */ + const ib_rbt_node_t* current)/*!< in: this is declared const + because it can be called via + rbt_next() */ +{ + const ib_rbt_node_t* nil = tree->nil; + ib_rbt_node_t* next = current->right; + + /* Is there a sub-tree to the right that we can follow. */ + if (next != nil) { + + /* Follow the left most links of the current right child. */ + while (next->left != nil) { + next = next->left; + } + + } else { /* We will have to go up the tree to find the successor. */ + ib_rbt_node_t* parent = current->parent; + + /* Cast away the const. */ + next = (ib_rbt_node_t*) current; + + while (parent != tree->root && next == parent->right) { + next = parent; + parent = next->parent; + } + + next = (parent == tree->root) ? NULL : parent; + } + + return(next); +} + +/****************************************************************//** +Find the given node's precedecessor. +@return predecessor node or NULL if no predecesor */ +static +ib_rbt_node_t* +rbt_find_predecessor( +/*=================*/ + const ib_rbt_t* tree, /*!< in: rb tree */ + const ib_rbt_node_t* current) /*!< in: this is declared const + because it can be called via + rbt_prev() */ +{ + const ib_rbt_node_t* nil = tree->nil; + ib_rbt_node_t* prev = current->left; + + /* Is there a sub-tree to the left that we can follow. */ + if (prev != nil) { + + /* Follow the right most links of the current left child. */ + while (prev->right != nil) { + prev = prev->right; + } + + } else { /* We will have to go up the tree to find the precedecessor. */ + ib_rbt_node_t* parent = current->parent; + + /* Cast away the const. */ + prev = (ib_rbt_node_t*)current; + + while (parent != tree->root && prev == parent->left) { + prev = parent; + parent = prev->parent; + } + + prev = (parent == tree->root) ? NULL : parent; + } + + return(prev); +} + +/****************************************************************//** +Replace node with child. After applying transformations eject becomes +an orphan. */ +static +void +rbt_eject_node( +/*===========*/ + ib_rbt_node_t* eject, /*!< in: node to eject */ + ib_rbt_node_t* node) /*!< in: node to replace with */ +{ + /* Update the to be ejected node's parent's child pointers. */ + if (eject->parent->left == eject) { + eject->parent->left = node; + } else if (eject->parent->right == eject) { + eject->parent->right = node; + } else { + ut_a(0); + } + /* eject is now an orphan but otherwise its pointers + and color are left intact. */ + + node->parent = eject->parent; +} + +/****************************************************************//** +Replace a node with another node. */ +static +void +rbt_replace_node( +/*=============*/ + ib_rbt_node_t* replace, /*!< in: node to replace */ + ib_rbt_node_t* node) /*!< in: node to replace with */ +{ + ib_rbt_color_t color = node->color; + + /* Update the node pointers. */ + node->left = replace->left; + node->right = replace->right; + + /* Update the child node pointers. */ + node->left->parent = node; + node->right->parent = node; + + /* Make the parent of replace point to node. */ + rbt_eject_node(replace, node); + + /* Swap the colors. */ + node->color = replace->color; + replace->color = color; +} + +/****************************************************************//** +Detach node from the tree replacing it with one of it's children. +@return the child node that now occupies the position of the detached node */ +static +ib_rbt_node_t* +rbt_detach_node( +/*============*/ + const ib_rbt_t* tree, /*!< in: rb tree */ + ib_rbt_node_t* node) /*!< in: node to detach */ +{ + ib_rbt_node_t* child; + const ib_rbt_node_t* nil = tree->nil; + + if (node->left != nil && node->right != nil) { + /* Case where the node to be deleted has two children. */ + ib_rbt_node_t* successor = rbt_find_successor(tree, node); + + ut_a(successor != nil); + ut_a(successor->parent != nil); + ut_a(successor->left == nil); + + child = successor->right; + + /* Remove the successor node and replace with its child. */ + rbt_eject_node(successor, child); + + /* Replace the node to delete with its successor node. */ + rbt_replace_node(node, successor); + } else { + ut_a(node->left == nil || node->right == nil); + + child = (node->left != nil) ? node->left : node->right; + + /* Replace the node to delete with one of it's children. */ + rbt_eject_node(node, child); + } + + /* Reset the node links. */ + node->parent = node->right = node->left = tree->nil; + + return(child); +} + +/****************************************************************//** +Rebalance the right sub-tree after deletion. +@return node to rebalance if more rebalancing required else NULL */ +static +ib_rbt_node_t* +rbt_balance_right( +/*==============*/ + const ib_rbt_node_t* nil, /*!< in: rb tree nil node */ + ib_rbt_node_t* parent, /*!< in: parent node */ + ib_rbt_node_t* sibling)/*!< in: sibling node */ +{ + ib_rbt_node_t* node = NULL; + + ut_a(sibling != nil); + + /* Case 3. */ + if (sibling->color == IB_RBT_RED) { + + parent->color = IB_RBT_RED; + sibling->color = IB_RBT_BLACK; + + rbt_rotate_left(nil, parent); + + sibling = parent->right; + + ut_a(sibling != nil); + } + + /* Since this will violate case 3 because of the change above. */ + if (sibling->left->color == IB_RBT_BLACK + && sibling->right->color == IB_RBT_BLACK) { + + node = parent; /* Parent needs to be rebalanced too. */ + sibling->color = IB_RBT_RED; + + } else { + if (sibling->right->color == IB_RBT_BLACK) { + + ut_a(sibling->left->color == IB_RBT_RED); + + sibling->color = IB_RBT_RED; + sibling->left->color = IB_RBT_BLACK; + + rbt_rotate_right(nil, sibling); + + sibling = parent->right; + ut_a(sibling != nil); + } + + sibling->color = parent->color; + sibling->right->color = IB_RBT_BLACK; + + parent->color = IB_RBT_BLACK; + + rbt_rotate_left(nil, parent); + } + + return(node); +} + +/****************************************************************//** +Rebalance the left sub-tree after deletion. +@return node to rebalance if more rebalancing required else NULL */ +static +ib_rbt_node_t* +rbt_balance_left( +/*=============*/ + const ib_rbt_node_t* nil, /*!< in: rb tree nil node */ + ib_rbt_node_t* parent, /*!< in: parent node */ + ib_rbt_node_t* sibling)/*!< in: sibling node */ +{ + ib_rbt_node_t* node = NULL; + + ut_a(sibling != nil); + + /* Case 3. */ + if (sibling->color == IB_RBT_RED) { + + parent->color = IB_RBT_RED; + sibling->color = IB_RBT_BLACK; + + rbt_rotate_right(nil, parent); + sibling = parent->left; + + ut_a(sibling != nil); + } + + /* Since this will violate case 3 because of the change above. */ + if (sibling->right->color == IB_RBT_BLACK + && sibling->left->color == IB_RBT_BLACK) { + + node = parent; /* Parent needs to be rebalanced too. */ + sibling->color = IB_RBT_RED; + + } else { + if (sibling->left->color == IB_RBT_BLACK) { + + ut_a(sibling->right->color == IB_RBT_RED); + + sibling->color = IB_RBT_RED; + sibling->right->color = IB_RBT_BLACK; + + rbt_rotate_left(nil, sibling); + + sibling = parent->left; + + ut_a(sibling != nil); + } + + sibling->color = parent->color; + sibling->left->color = IB_RBT_BLACK; + + parent->color = IB_RBT_BLACK; + + rbt_rotate_right(nil, parent); + } + + return(node); +} + +/****************************************************************//** +Delete the node and rebalance the tree if necessary */ +static +void +rbt_remove_node_and_rebalance( +/*==========================*/ + ib_rbt_t* tree, /*!< in: rb tree */ + ib_rbt_node_t* node) /*!< in: node to remove */ +{ + /* Detach node and get the node that will be used + as rebalance start. */ + ib_rbt_node_t* child = rbt_detach_node(tree, node); + + if (node->color == IB_RBT_BLACK) { + ib_rbt_node_t* last = child; + + ROOT(tree)->color = IB_RBT_RED; + + while (child && child->color == IB_RBT_BLACK) { + ib_rbt_node_t* parent = child->parent; + + /* Did the deletion cause an imbalance in the + parents left sub-tree. */ + if (parent->left == child) { + + child = rbt_balance_right( + tree->nil, parent, parent->right); + + } else if (parent->right == child) { + + child = rbt_balance_left( + tree->nil, parent, parent->left); + + } else { + ut_error; + } + + if (child) { + last = child; + } + } + + ut_a(last); + + last->color = IB_RBT_BLACK; + ROOT(tree)->color = IB_RBT_BLACK; + } + + /* Note that we have removed a node from the tree. */ + --tree->n_nodes; +} + +/****************************************************************//** +Recursively free the nodes. */ +static +void +rbt_free_node( +/*==========*/ + ib_rbt_node_t* node, /*!< in: node to free */ + ib_rbt_node_t* nil) /*!< in: rb tree nil node */ +{ + if (node != nil) { + rbt_free_node(node->left, nil); + rbt_free_node(node->right, nil); + + ut_free(node); + } +} + +/****************************************************************//** +Free all the nodes and free the tree. */ +UNIV_INTERN +void +rbt_free( +/*=====*/ + ib_rbt_t* tree) /*!< in: rb tree to free */ +{ + rbt_free_node(tree->root, tree->nil); + ut_free(tree->nil); + ut_free(tree); +} + +/****************************************************************//** +Create an instance of a red black tree. +@return an empty rb tree */ +UNIV_INTERN +ib_rbt_t* +rbt_create( +/*=======*/ + size_t sizeof_value, /*!< in: sizeof data item */ + ib_rbt_compare compare) /*!< in: fn to compare items */ +{ + ib_rbt_t* tree; + ib_rbt_node_t* node; + + tree = (ib_rbt_t*) ut_malloc(sizeof(*tree)); + memset(tree, 0, sizeof(*tree)); + + tree->sizeof_value = sizeof_value; + + /* Create the sentinel (NIL) node. */ + node = tree->nil = (ib_rbt_node_t*) ut_malloc(sizeof(*node)); + memset(node, 0, sizeof(*node)); + + node->color = IB_RBT_BLACK; + node->parent = node->left = node->right = node; + + /* Create the "fake" root, the real root node will be the + left child of this node. */ + node = tree->root = (ib_rbt_node_t*) ut_malloc(sizeof(*node)); + memset(node, 0, sizeof(*node)); + + node->color = IB_RBT_BLACK; + node->parent = node->left = node->right = tree->nil; + + tree->compare = compare; + + return(tree); +} + +/****************************************************************//** +Generic insert of a value in the rb tree. +@return inserted node */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_insert( +/*=======*/ + ib_rbt_t* tree, /*!< in: rb tree */ + const void* key, /*!< in: key for ordering */ + const void* value) /*!< in: value of key, this value + is copied to the node */ +{ + ib_rbt_node_t* node; + + /* Create the node that will hold the value data. */ + node = (ib_rbt_node_t*) ut_malloc(SIZEOF_NODE(tree)); + + memcpy(node->value, value, tree->sizeof_value); + node->parent = node->left = node->right = tree->nil; + + /* Insert in the tree in the usual way. */ + rbt_tree_insert(tree, key, node); + rbt_balance_tree(tree, node); + + ++tree->n_nodes; + + return(node); +} + +/****************************************************************//** +Add a new node to the tree, useful for data that is pre-sorted. +@return appended node */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_add_node( +/*=========*/ + ib_rbt_t* tree, /*!< in: rb tree */ + ib_rbt_bound_t* parent, /*!< in: bounds */ + const void* value) /*!< in: this value is copied + to the node */ +{ + ib_rbt_node_t* node; + + /* Create the node that will hold the value data */ + node = (ib_rbt_node_t*) ut_malloc(SIZEOF_NODE(tree)); + + memcpy(node->value, value, tree->sizeof_value); + node->parent = node->left = node->right = tree->nil; + + /* If tree is empty */ + if (parent->last == NULL) { + parent->last = tree->root; + } + + /* Append the node, the hope here is that the caller knows + what s/he is doing. */ + rbt_tree_add_child(tree, parent, node); + rbt_balance_tree(tree, node); + + ++tree->n_nodes; + +#if defined(IB_RBT_TESTING) + ut_a(rbt_validate(tree)); +#endif + return(node); +} + +/****************************************************************//** +Find a matching node in the rb tree. +@return NULL if not found else the node where key was found */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_lookup( +/*=======*/ + const ib_rbt_t* tree, /*!< in: rb tree */ + const void* key) /*!< in: key to use for search */ +{ + const ib_rbt_node_t* current = ROOT(tree); + + /* Regular binary search. */ + while (current != tree->nil) { + int result = tree->compare(key, current->value); + + if (result < 0) { + current = current->left; + } else if (result > 0) { + current = current->right; + } else { + break; + } + } + + return(current != tree->nil ? current : NULL); +} + +/****************************************************************//** +Delete a node from the red black tree, identified by key. +@return TRUE if success FALSE if not found */ +UNIV_INTERN +ibool +rbt_delete( +/*=======*/ + ib_rbt_t* tree, /*!< in: rb tree */ + const void* key) /*!< in: key to delete */ +{ + ibool deleted = FALSE; + ib_rbt_node_t* node = (ib_rbt_node_t*) rbt_lookup(tree, key); + + if (node) { + rbt_remove_node_and_rebalance(tree, node); + + ut_free(node); + deleted = TRUE; + } + + return(deleted); +} + +/****************************************************************//** +Remove a node from the rb tree, the node is not free'd, that is the +callers responsibility. +@return deleted node but without the const */ +UNIV_INTERN +ib_rbt_node_t* +rbt_remove_node( +/*============*/ + ib_rbt_t* tree, /*!< in: rb tree */ + const ib_rbt_node_t* const_node) /*!< in: node to delete, this + is a fudge and declared const + because the caller can access + only const nodes */ +{ + /* Cast away the const. */ + rbt_remove_node_and_rebalance(tree, (ib_rbt_node_t*) const_node); + + /* This is to make it easier to do something like this: + ut_free(rbt_remove_node(node)); + */ + + return((ib_rbt_node_t*) const_node); +} + +/****************************************************************//** +Find the node that has the lowest key that is >= key. +@return node satisfying the lower bound constraint or NULL */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_lower_bound( +/*============*/ + const ib_rbt_t* tree, /*!< in: rb tree */ + const void* key) /*!< in: key to search */ +{ + ib_rbt_node_t* lb_node = NULL; + ib_rbt_node_t* current = ROOT(tree); + + while (current != tree->nil) { + int result = tree->compare(key, current->value); + + if (result > 0) { + + current = current->right; + + } else if (result < 0) { + + lb_node = current; + current = current->left; + + } else { + lb_node = current; + break; + } + } + + return(lb_node); +} + +/****************************************************************//** +Find the node that has the greatest key that is <= key. +@return node satisfying the upper bound constraint or NULL */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_upper_bound( +/*============*/ + const ib_rbt_t* tree, /*!< in: rb tree */ + const void* key) /*!< in: key to search */ +{ + ib_rbt_node_t* ub_node = NULL; + ib_rbt_node_t* current = ROOT(tree); + + while (current != tree->nil) { + int result = tree->compare(key, current->value); + + if (result > 0) { + + ub_node = current; + current = current->right; + + } else if (result < 0) { + + current = current->left; + + } else { + ub_node = current; + break; + } + } + + return(ub_node); +} + +/****************************************************************//** +Find the node that has the greatest key that is <= key. +@return value of result */ +UNIV_INTERN +int +rbt_search( +/*=======*/ + const ib_rbt_t* tree, /*!< in: rb tree */ + ib_rbt_bound_t* parent, /*!< in: search bounds */ + const void* key) /*!< in: key to search */ +{ + ib_rbt_node_t* current = ROOT(tree); + + /* Every thing is greater than the NULL root. */ + parent->result = 1; + parent->last = NULL; + + while (current != tree->nil) { + + parent->last = current; + parent->result = tree->compare(key, current->value); + + if (parent->result > 0) { + current = current->right; + } else if (parent->result < 0) { + current = current->left; + } else { + break; + } + } + + return(parent->result); +} + +/****************************************************************//** +Find the node that has the greatest key that is <= key. But use the +supplied comparison function. +@return value of result */ +UNIV_INTERN +int +rbt_search_cmp( +/*===========*/ + const ib_rbt_t* tree, /*!< in: rb tree */ + ib_rbt_bound_t* parent, /*!< in: search bounds */ + const void* key, /*!< in: key to search */ + ib_rbt_compare compare) /*!< in: fn to compare items */ +{ + ib_rbt_node_t* current = ROOT(tree); + + /* Every thing is greater than the NULL root. */ + parent->result = 1; + parent->last = NULL; + + while (current != tree->nil) { + + parent->last = current; + parent->result = compare(key, current->value); + + if (parent->result > 0) { + current = current->right; + } else if (parent->result < 0) { + current = current->left; + } else { + break; + } + } + + return(parent->result); +} + +/****************************************************************//** +Get the leftmost node. +Return the left most node in the tree. */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_first( +/*======*/ + const ib_rbt_t* tree) /* in: rb tree */ +{ + ib_rbt_node_t* first = NULL; + ib_rbt_node_t* current = ROOT(tree); + + while (current != tree->nil) { + first = current; + current = current->left; + } + + return(first); +} + +/****************************************************************//** +Return the right most node in the tree. +@return the rightmost node or NULL */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_last( +/*=====*/ + const ib_rbt_t* tree) /*!< in: rb tree */ +{ + ib_rbt_node_t* last = NULL; + ib_rbt_node_t* current = ROOT(tree); + + while (current != tree->nil) { + last = current; + current = current->right; + } + + return(last); +} + +/****************************************************************//** +Return the next node. +@return node next from current */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_next( +/*=====*/ + const ib_rbt_t* tree, /*!< in: rb tree */ + const ib_rbt_node_t* current)/*!< in: current node */ +{ + return(current ? rbt_find_successor(tree, current) : NULL); +} + +/****************************************************************//** +Return the previous node. +@return node prev from current */ +UNIV_INTERN +const ib_rbt_node_t* +rbt_prev( +/*=====*/ + const ib_rbt_t* tree, /*!< in: rb tree */ + const ib_rbt_node_t* current)/*!< in: current node */ +{ + return(current ? rbt_find_predecessor(tree, current) : NULL); +} + +/****************************************************************//** +Reset the tree. Delete all the nodes. */ +UNIV_INTERN +void +rbt_clear( +/*======*/ + ib_rbt_t* tree) /*!< in: rb tree */ +{ + rbt_free_node(ROOT(tree), tree->nil); + + tree->n_nodes = 0; + tree->root->left = tree->root->right = tree->nil; +} + +/****************************************************************//** +Merge the node from dst into src. Return the number of nodes merged. +@return no. of recs merged */ +UNIV_INTERN +ulint +rbt_merge_uniq( +/*===========*/ + ib_rbt_t* dst, /*!< in: dst rb tree */ + const ib_rbt_t* src) /*!< in: src rb tree */ +{ + ib_rbt_bound_t parent; + ulint n_merged = 0; + const ib_rbt_node_t* src_node = rbt_first(src); + + if (rbt_empty(src) || dst == src) { + return(0); + } + + for (/* No op */; src_node; src_node = rbt_next(src, src_node)) { + + if (rbt_search(dst, &parent, src_node->value) != 0) { + rbt_add_node(dst, &parent, src_node->value); + ++n_merged; + } + } + + return(n_merged); +} + +/****************************************************************//** +Merge the node from dst into src. Return the number of nodes merged. +Delete the nodes from src after copying node to dst. As a side effect +the duplicates will be left untouched in the src. +@return no. of recs merged */ +UNIV_INTERN +ulint +rbt_merge_uniq_destructive( +/*=======================*/ + ib_rbt_t* dst, /*!< in: dst rb tree */ + ib_rbt_t* src) /*!< in: src rb tree */ +{ + ib_rbt_bound_t parent; + ib_rbt_node_t* src_node; + ulint old_size = rbt_size(dst); + + if (rbt_empty(src) || dst == src) { + return(0); + } + + for (src_node = (ib_rbt_node_t*) rbt_first(src); src_node; /* */) { + ib_rbt_node_t* prev = src_node; + + src_node = (ib_rbt_node_t*)rbt_next(src, prev); + + /* Skip duplicates. */ + if (rbt_search(dst, &parent, prev->value) != 0) { + + /* Remove and reset the node but preserve + the node (data) value. */ + rbt_remove_node_and_rebalance(src, prev); + + /* The nil should be taken from the dst tree. */ + prev->parent = prev->left = prev->right = dst->nil; + rbt_tree_add_child(dst, &parent, prev); + rbt_balance_tree(dst, prev); + + ++dst->n_nodes; + } + } + +#if defined(IB_RBT_TESTING) + ut_a(rbt_validate(dst)); + ut_a(rbt_validate(src)); +#endif + return(rbt_size(dst) - old_size); +} + +/****************************************************************//** +Check that every path from the root to the leaves has the same count and +the tree nodes are in order. +@return TRUE if OK FALSE otherwise */ +UNIV_INTERN +ibool +rbt_validate( +/*=========*/ + const ib_rbt_t* tree) /*!< in: RB tree to validate */ +{ + if (rbt_count_black_nodes(tree, ROOT(tree)) > 0) { + return(rbt_check_ordering(tree)); + } + + return(FALSE); +} + +/****************************************************************//** +Iterate over the tree in depth first order. */ +UNIV_INTERN +void +rbt_print( +/*======*/ + const ib_rbt_t* tree, /*!< in: tree to traverse */ + ib_rbt_print_node print) /*!< in: print function */ +{ + rbt_print_subtree(tree, ROOT(tree), print); +} |