Commit 1392eba6 authored by Michael Widenius's avatar Michael Widenius

Merged InnoDB plugin from MySQL 5.1.54 -> MySQL 5.1.55 into xtradb

mysql-test/r/innodb-zip.result:
  File has been moved to suite/innodb_plugin
mysql-test/t/innodb-zip.test:
  File has been moved to suite/innodb_plugin
parent b35743f9
This diff is collapsed.
This diff is collapsed.
...@@ -134,7 +134,7 @@ Table Create Table ...@@ -134,7 +134,7 @@ Table Create Table
t1 CREATE TABLE `t1` ( t1 CREATE TABLE `t1` (
`c1` int(11) NOT NULL AUTO_INCREMENT, `c1` int(11) NOT NULL AUTO_INCREMENT,
PRIMARY KEY (`c1`) PRIMARY KEY (`c1`)
) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=latin1 ) ENGINE=InnoDB AUTO_INCREMENT=102 DEFAULT CHARSET=latin1
DROP TABLE t1; DROP TABLE t1;
CREATE TABLE t1 CREATE TABLE t1
(a INT NULL AUTO_INCREMENT, (a INT NULL AUTO_INCREMENT,
...@@ -440,7 +440,7 @@ Table Create Table ...@@ -440,7 +440,7 @@ Table Create Table
t1 CREATE TABLE `t1` ( t1 CREATE TABLE `t1` (
`c1` int(11) NOT NULL AUTO_INCREMENT, `c1` int(11) NOT NULL AUTO_INCREMENT,
PRIMARY KEY (`c1`) PRIMARY KEY (`c1`)
) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=latin1 ) ENGINE=InnoDB AUTO_INCREMENT=102 DEFAULT CHARSET=latin1
/*!50100 PARTITION BY HASH (c1) /*!50100 PARTITION BY HASH (c1)
PARTITIONS 2 */ PARTITIONS 2 */
DROP TABLE t1; DROP TABLE t1;
......
This diff is collapsed.
2011-01-06 The InnoDB Team
* row/row0merge.c:
Fix Bug#59312 Examine MAX_FULL_NAME_LEN in InnoDB to address
possible insufficient name buffer
2011-01-06 The InnoDB Team
* dict/dict0dict.c, handler/ha_innodb.cc, handler/i_s.cc,
include/univ.i:
Fix Bug#58643 InnoDB: too long table name
2011-01-06 The InnoDB Team
* handler/i_s.cc, include/trx0i_s.h, trx/trx0i_s.c:
Fix Bug#55397 cannot select from innodb_trx when trx_query contains
blobs that aren't strings
2011-01-04 The InnoDB Team
* dict/dict0dict.c:
Fix Bug#59197 double quote in field comment prevents foreign
key constraint creation
2010-12-21 The InnoDB Team
* include/btr0cur.h, include/row0upd.h, btr/btr0cur.c,
row/row0umod.c, row/row0upd.c:
Fix Bug#55284 Double free of off-page columns due to lock wait
while updating PRIMARY KEY
2010-12-21 The InnoDB Team
* include/data0data.h, include/data0data.ic, include/row0upd.h,
btr/btr0cur.c, row/row0purge.c, row/row0umod.c, row/row0upd.c,
innodb.result, innodb.test:
Fix Bug#58912 InnoDB unnecessarily avoids update-in-place
on column prefix indexes
2010-12-09 The InnoDB Team
* buf/buf0lru.c:
Fix Bug#57600 output of I/O sum[%lu] can go negative
2010-11-11 The InnoDB Team 2010-11-11 The InnoDB Team
* thr/thr0loc.c, trx/trx0i_s.c: * thr/thr0loc.c, trx/trx0i_s.c:
Fix Bug#57802 Empty ASSERTION parameter passed to the HASH_SEARCH macro Fix Bug#57802 Empty ASSERTION parameter passed to the HASH_SEARCH macro
......
...@@ -675,7 +675,7 @@ btr_page_get_father_node_ptr_func( ...@@ -675,7 +675,7 @@ btr_page_get_father_node_ptr_func(
" to fix the\n" " to fix the\n"
"InnoDB: corruption. If the crash happens at " "InnoDB: corruption. If the crash happens at "
"the database startup, see\n" "the database startup, see\n"
"InnoDB: " REFMAN "forcing-recovery.html about\n" "InnoDB: " REFMAN "forcing-innodb-recovery.html about\n"
"InnoDB: forcing recovery. " "InnoDB: forcing recovery. "
"Then dump + drop + reimport.\n", stderr); "Then dump + drop + reimport.\n", stderr);
......
...@@ -1933,7 +1933,8 @@ btr_cur_update_in_place( ...@@ -1933,7 +1933,8 @@ btr_cur_update_in_place(
NOT call it if index is secondary */ NOT call it if index is secondary */
if (!dict_index_is_clust(index) if (!dict_index_is_clust(index)
|| row_upd_changes_ord_field_binary(NULL, index, update)) { || row_upd_changes_ord_field_binary(NULL, NULL,
index, update)) {
/* Remove possible hash index pointer to this record */ /* Remove possible hash index pointer to this record */
btr_search_update_hash_on_delete(cursor); btr_search_update_hash_on_delete(cursor);
...@@ -2685,27 +2686,24 @@ ulint ...@@ -2685,27 +2686,24 @@ ulint
btr_cur_del_mark_set_clust_rec( btr_cur_del_mark_set_clust_rec(
/*===========================*/ /*===========================*/
ulint flags, /*!< in: undo logging and locking flags */ ulint flags, /*!< in: undo logging and locking flags */
btr_cur_t* cursor, /*!< in: cursor */ buf_block_t* block, /*!< in/out: buffer block of the record */
rec_t* rec, /*!< in/out: record */
dict_index_t* index, /*!< in: clustered index of the record */
const ulint* offsets,/*!< in: rec_get_offsets(rec) */
ibool val, /*!< in: value to set */ ibool val, /*!< in: value to set */
que_thr_t* thr, /*!< in: query thread */ que_thr_t* thr, /*!< in: query thread */
mtr_t* mtr) /*!< in: mtr */ mtr_t* mtr) /*!< in: mtr */
{ {
dict_index_t* index;
buf_block_t* block;
roll_ptr_t roll_ptr; roll_ptr_t roll_ptr;
ulint err; ulint err;
rec_t* rec;
page_zip_des_t* page_zip; page_zip_des_t* page_zip;
trx_t* trx; trx_t* trx;
mem_heap_t* heap = NULL;
ulint offsets_[REC_OFFS_NORMAL_SIZE];
ulint* offsets = offsets_;
rec_offs_init(offsets_);
rec = btr_cur_get_rec(cursor); ut_ad(dict_index_is_clust(index));
index = cursor->index; ut_ad(rec_offs_validate(rec, index, offsets));
ut_ad(!!page_rec_is_comp(rec) == dict_table_is_comp(index->table)); ut_ad(!!page_rec_is_comp(rec) == dict_table_is_comp(index->table));
offsets = rec_get_offsets(rec, index, offsets, ULINT_UNDEFINED, &heap); ut_ad(buf_block_get_frame(block) == page_align(rec));
ut_ad(page_is_leaf(page_align(rec)));
#ifdef UNIV_DEBUG #ifdef UNIV_DEBUG
if (btr_cur_print_record_ops && thr) { if (btr_cur_print_record_ops && thr) {
...@@ -2717,13 +2715,12 @@ btr_cur_del_mark_set_clust_rec( ...@@ -2717,13 +2715,12 @@ btr_cur_del_mark_set_clust_rec(
ut_ad(dict_index_is_clust(index)); ut_ad(dict_index_is_clust(index));
ut_ad(!rec_get_deleted_flag(rec, rec_offs_comp(offsets))); ut_ad(!rec_get_deleted_flag(rec, rec_offs_comp(offsets)));
err = lock_clust_rec_modify_check_and_lock(flags, err = lock_clust_rec_modify_check_and_lock(flags, block,
btr_cur_get_block(cursor),
rec, index, offsets, thr); rec, index, offsets, thr);
if (err != DB_SUCCESS) { if (err != DB_SUCCESS) {
goto func_exit; return(err);
} }
err = trx_undo_report_row_operation(flags, TRX_UNDO_MODIFY_OP, thr, err = trx_undo_report_row_operation(flags, TRX_UNDO_MODIFY_OP, thr,
...@@ -2731,11 +2728,9 @@ btr_cur_del_mark_set_clust_rec( ...@@ -2731,11 +2728,9 @@ btr_cur_del_mark_set_clust_rec(
&roll_ptr); &roll_ptr);
if (err != DB_SUCCESS) { if (err != DB_SUCCESS) {
goto func_exit; return(err);
} }
block = btr_cur_get_block(cursor);
if (block->is_hashed) { if (block->is_hashed) {
rw_lock_x_lock(&btr_search_latch); rw_lock_x_lock(&btr_search_latch);
} }
...@@ -2758,10 +2753,6 @@ btr_cur_del_mark_set_clust_rec( ...@@ -2758,10 +2753,6 @@ btr_cur_del_mark_set_clust_rec(
btr_cur_del_mark_set_clust_rec_log(flags, rec, index, val, trx, btr_cur_del_mark_set_clust_rec_log(flags, rec, index, val, trx,
roll_ptr, mtr); roll_ptr, mtr);
func_exit:
if (UNIV_LIKELY_NULL(heap)) {
mem_heap_free(heap);
}
return(err); return(err);
} }
...@@ -3856,107 +3847,35 @@ btr_cur_set_ownership_of_extern_field( ...@@ -3856,107 +3847,35 @@ btr_cur_set_ownership_of_extern_field(
} }
/*******************************************************************//** /*******************************************************************//**
Marks not updated extern fields as not-owned by this record. The ownership Marks non-updated off-page fields as disowned by this record. The ownership
is transferred to the updated record which is inserted elsewhere in the must be transferred to the updated record which is inserted elsewhere in the
index tree. In purge only the owner of externally stored field is allowed index tree. In purge only the owner of externally stored field is allowed
to free the field. to free the field. */
@return TRUE if BLOB ownership was transferred */
UNIV_INTERN UNIV_INTERN
ibool void
btr_cur_mark_extern_inherited_fields( btr_cur_disown_inherited_fields(
/*=================================*/ /*============================*/
page_zip_des_t* page_zip,/*!< in/out: compressed page whose uncompressed page_zip_des_t* page_zip,/*!< in/out: compressed page whose uncompressed
part will be updated, or NULL */ part will be updated, or NULL */
rec_t* rec, /*!< in/out: record in a clustered index */ rec_t* rec, /*!< in/out: record in a clustered index */
dict_index_t* index, /*!< in: index of the page */ dict_index_t* index, /*!< in: index of the page */
const ulint* offsets,/*!< in: array returned by rec_get_offsets() */ const ulint* offsets,/*!< in: array returned by rec_get_offsets() */
const upd_t* update, /*!< in: update vector */ const upd_t* update, /*!< in: update vector */
mtr_t* mtr) /*!< in: mtr, or NULL if not logged */ mtr_t* mtr) /*!< in/out: mini-transaction */
{ {
ulint n;
ulint j;
ulint i; ulint i;
ibool change_ownership = FALSE;
ut_ad(rec_offs_validate(rec, NULL, offsets)); ut_ad(rec_offs_validate(rec, index, offsets));
ut_ad(!rec_offs_comp(offsets) || !rec_get_node_ptr_flag(rec)); ut_ad(!rec_offs_comp(offsets) || !rec_get_node_ptr_flag(rec));
ut_ad(rec_offs_any_extern(offsets));
ut_ad(mtr);
if (!rec_offs_any_extern(offsets)) { for (i = 0; i < rec_offs_n_fields(offsets); i++) {
if (rec_offs_nth_extern(offsets, i)
return(FALSE); && !upd_get_field_by_field_no(update, i)) {
}
n = rec_offs_n_fields(offsets);
for (i = 0; i < n; i++) {
if (rec_offs_nth_extern(offsets, i)) {
/* Check it is not in updated fields */
if (update) {
for (j = 0; j < upd_get_n_fields(update);
j++) {
if (upd_get_nth_field(update, j)
->field_no == i) {
goto updated;
}
}
}
btr_cur_set_ownership_of_extern_field( btr_cur_set_ownership_of_extern_field(
page_zip, rec, index, offsets, i, FALSE, mtr); page_zip, rec, index, offsets, i, FALSE, mtr);
change_ownership = TRUE;
updated:
;
}
}
return(change_ownership);
}
/*******************************************************************//**
The complement of the previous function: in an update entry may inherit
some externally stored fields from a record. We must mark them as inherited
in entry, so that they are not freed in a rollback. */
UNIV_INTERN
void
btr_cur_mark_dtuple_inherited_extern(
/*=================================*/
dtuple_t* entry, /*!< in/out: updated entry to be
inserted to clustered index */
const upd_t* update) /*!< in: update vector */
{
ulint i;
for (i = 0; i < dtuple_get_n_fields(entry); i++) {
dfield_t* dfield = dtuple_get_nth_field(entry, i);
byte* data;
ulint len;
ulint j;
if (!dfield_is_ext(dfield)) {
continue;
}
/* Check if it is in updated fields */
for (j = 0; j < upd_get_n_fields(update); j++) {
if (upd_get_nth_field(update, j)->field_no == i) {
goto is_updated;
}
} }
data = dfield_get_data(dfield);
len = dfield_get_len(dfield);
data[len - BTR_EXTERN_FIELD_REF_SIZE + BTR_EXTERN_LEN]
|= BTR_EXTERN_INHERITED_FLAG;
is_updated:
;
} }
} }
...@@ -3995,29 +3914,6 @@ btr_cur_unmark_extern_fields( ...@@ -3995,29 +3914,6 @@ btr_cur_unmark_extern_fields(
} }
} }
/*******************************************************************//**
Marks all extern fields in a dtuple as owned by the record. */
UNIV_INTERN
void
btr_cur_unmark_dtuple_extern_fields(
/*================================*/
dtuple_t* entry) /*!< in/out: clustered index entry */
{
ulint i;
for (i = 0; i < dtuple_get_n_fields(entry); i++) {
dfield_t* dfield = dtuple_get_nth_field(entry, i);
if (dfield_is_ext(dfield)) {
byte* data = dfield_get_data(dfield);
ulint len = dfield_get_len(dfield);
data[len - BTR_EXTERN_FIELD_REF_SIZE + BTR_EXTERN_LEN]
&= ~BTR_EXTERN_OWNER_FLAG;
}
}
}
/*******************************************************************//** /*******************************************************************//**
Flags the data tuple fields that are marked as extern storage in the Flags the data tuple fields that are marked as extern storage in the
update vector. We use this function to remember which fields we must update vector. We use this function to remember which fields we must
......
...@@ -457,7 +457,7 @@ buf_page_is_corrupted( ...@@ -457,7 +457,7 @@ buf_page_is_corrupted(
"you may have copied the InnoDB\n" "you may have copied the InnoDB\n"
"InnoDB: tablespace but not the InnoDB " "InnoDB: tablespace but not the InnoDB "
"log files. See\n" "log files. See\n"
"InnoDB: " REFMAN "forcing-recovery.html\n" "InnoDB: " REFMAN "forcing-innodb-recovery.html\n"
"InnoDB: for more information.\n", "InnoDB: for more information.\n",
(ulong) mach_read_from_4(read_buf (ulong) mach_read_from_4(read_buf
+ FIL_PAGE_OFFSET), + FIL_PAGE_OFFSET),
...@@ -3999,7 +3999,7 @@ buf_page_io_complete( ...@@ -3999,7 +3999,7 @@ buf_page_io_complete(
"InnoDB: TABLE to scan your" "InnoDB: TABLE to scan your"
" table for corruption.\n" " table for corruption.\n"
"InnoDB: See also " "InnoDB: See also "
REFMAN "forcing-recovery.html\n" REFMAN "forcing-innodb-recovery.html\n"
"InnoDB: about forcing recovery.\n", stderr); "InnoDB: about forcing recovery.\n", stderr);
if (srv_pass_corrupt_table && !trx_sys_sys_space(bpage->space) if (srv_pass_corrupt_table && !trx_sys_sys_space(bpage->space)
......
...@@ -2093,6 +2093,7 @@ buf_LRU_stat_update(void) ...@@ -2093,6 +2093,7 @@ buf_LRU_stat_update(void)
/*=====================*/ /*=====================*/
{ {
buf_LRU_stat_t* item; buf_LRU_stat_t* item;
buf_LRU_stat_t cur_stat;
/* If we haven't started eviction yet then don't update stats. */ /* If we haven't started eviction yet then don't update stats. */
if (buf_pool->freed_page_clock == 0) { if (buf_pool->freed_page_clock == 0) {
...@@ -2107,12 +2108,19 @@ buf_LRU_stat_update(void) ...@@ -2107,12 +2108,19 @@ buf_LRU_stat_update(void)
buf_LRU_stat_arr_ind++; buf_LRU_stat_arr_ind++;
buf_LRU_stat_arr_ind %= BUF_LRU_STAT_N_INTERVAL; buf_LRU_stat_arr_ind %= BUF_LRU_STAT_N_INTERVAL;
/* Add the current value and subtract the obsolete entry. */ /* Add the current value and subtract the obsolete entry.
buf_LRU_stat_sum.io += buf_LRU_stat_cur.io - item->io; Since buf_LRU_stat_cur is not protected by any mutex,
buf_LRU_stat_sum.unzip += buf_LRU_stat_cur.unzip - item->unzip; it can be changing between adding to buf_LRU_stat_sum
and copying to item. Assign it to local variables to make
sure the same value assign to the buf_LRU_stat_sum
and item */
cur_stat = buf_LRU_stat_cur;
buf_LRU_stat_sum.io += cur_stat.io - item->io;
buf_LRU_stat_sum.unzip += cur_stat.unzip - item->unzip;
/* Put current entry in the array. */ /* Put current entry in the array. */
memcpy(item, &buf_LRU_stat_cur, sizeof *item); memcpy(item, &cur_stat, sizeof *item);
//buf_pool_mutex_exit(); //buf_pool_mutex_exit();
mutex_exit(&buf_pool_mutex); mutex_exit(&buf_pool_mutex);
......
...@@ -937,7 +937,7 @@ dict_table_rename_in_cache( ...@@ -937,7 +937,7 @@ dict_table_rename_in_cache(
dict_foreign_t* foreign; dict_foreign_t* foreign;
dict_index_t* index; dict_index_t* index;
ulint fold; ulint fold;
char old_name[MAX_TABLE_NAME_LEN + 1]; char old_name[MAX_FULL_NAME_LEN + 1];
ut_ad(table); ut_ad(table);
ut_ad(mutex_own(&(dict_sys->mutex))); ut_ad(mutex_own(&(dict_sys->mutex)));
...@@ -949,7 +949,7 @@ dict_table_rename_in_cache( ...@@ -949,7 +949,7 @@ dict_table_rename_in_cache(
ut_print_timestamp(stderr); ut_print_timestamp(stderr);
fprintf(stderr, "InnoDB: too long table name: '%s', " fprintf(stderr, "InnoDB: too long table name: '%s', "
"max length is %d\n", table->name, "max length is %d\n", table->name,
MAX_TABLE_NAME_LEN); MAX_FULL_NAME_LEN);
ut_error; ut_error;
} }
...@@ -999,11 +999,11 @@ dict_table_rename_in_cache( ...@@ -999,11 +999,11 @@ dict_table_rename_in_cache(
ut_fold_string(old_name), table); ut_fold_string(old_name), table);
if (strlen(new_name) > strlen(table->name)) { if (strlen(new_name) > strlen(table->name)) {
/* We allocate MAX_TABLE_NAME_LEN+1 bytes here to avoid /* We allocate MAX_FULL_NAME_LEN + 1 bytes here to avoid
memory fragmentation, we assume a repeated calls of memory fragmentation, we assume a repeated calls of
ut_realloc() with the same size do not cause fragmentation */ ut_realloc() with the same size do not cause fragmentation */
ut_a(strlen(new_name) <= MAX_TABLE_NAME_LEN); ut_a(strlen(new_name) <= MAX_FULL_NAME_LEN);
table->name = ut_realloc(table->name, MAX_TABLE_NAME_LEN + 1); table->name = ut_realloc(table->name, MAX_FULL_NAME_LEN + 1);
} }
memcpy(table->name, new_name, strlen(new_name) + 1); memcpy(table->name, new_name, strlen(new_name) + 1);
...@@ -2756,7 +2756,7 @@ dict_scan_to( ...@@ -2756,7 +2756,7 @@ dict_scan_to(
quote = '\0'; quote = '\0';
} else if (quote) { } else if (quote) {
/* Within quotes: do nothing. */ /* Within quotes: do nothing. */
} else if (*ptr == '`' || *ptr == '"') { } else if (*ptr == '`' || *ptr == '"' || *ptr == '\'') {
/* Starting quote: remember the quote character. */ /* Starting quote: remember the quote character. */
quote = *ptr; quote = *ptr;
} else { } else {
......
...@@ -3355,7 +3355,7 @@ fseg_free_page_low( ...@@ -3355,7 +3355,7 @@ fseg_free_page_low(
"InnoDB: database!\n", (ulong) page); "InnoDB: database!\n", (ulong) page);
crash: crash:
fputs("InnoDB: Please refer to\n" fputs("InnoDB: Please refer to\n"
"InnoDB: " REFMAN "forcing-recovery.html\n" "InnoDB: " REFMAN "forcing-innodb-recovery.html\n"
"InnoDB: about forcing recovery.\n", stderr); "InnoDB: about forcing recovery.\n", stderr);
ut_error; ut_error;
} }
......
This diff is collapsed.
...@@ -1239,8 +1239,16 @@ fill_innodb_trx_from_cache( ...@@ -1239,8 +1239,16 @@ fill_innodb_trx_from_cache(
row->trx_mysql_thread_id)); row->trx_mysql_thread_id));
/* trx_query */ /* trx_query */
OK(field_store_string(fields[IDX_TRX_QUERY], if (row->trx_query) {
row->trx_query)); /* store will do appropriate character set
conversion check */
fields[IDX_TRX_QUERY]->store(
row->trx_query, strlen(row->trx_query),
row->trx_query_cs);
fields[IDX_TRX_QUERY]->set_notnull();
} else {
fields[IDX_TRX_QUERY]->set_null();
}
OK(schema_table_store_record(thd, table)); OK(schema_table_store_record(thd, table));
} }
...@@ -1443,16 +1451,7 @@ fill_innodb_locks_from_cache( ...@@ -1443,16 +1451,7 @@ fill_innodb_locks_from_cache(
for (i = 0; i < rows_num; i++) { for (i = 0; i < rows_num; i++) {
i_s_locks_row_t* row; i_s_locks_row_t* row;
char buf[MAX_FULL_NAME_LEN + 1];
/* note that the decoded database or table name is
never expected to be longer than NAME_LEN;
NAME_LEN for database name
2 for surrounding quotes around database name
NAME_LEN for table name
2 for surrounding quotes around table name
1 for the separating dot (.)
9 for the #mysql50# prefix */
char buf[2 * NAME_LEN + 14];
const char* bufend; const char* bufend;
char lock_trx_id[TRX_ID_MAX_LEN + 1]; char lock_trx_id[TRX_ID_MAX_LEN + 1];
......
...@@ -332,10 +332,14 @@ ulint ...@@ -332,10 +332,14 @@ ulint
btr_cur_del_mark_set_clust_rec( btr_cur_del_mark_set_clust_rec(
/*===========================*/ /*===========================*/
ulint flags, /*!< in: undo logging and locking flags */ ulint flags, /*!< in: undo logging and locking flags */
btr_cur_t* cursor, /*!< in: cursor */ buf_block_t* block, /*!< in/out: buffer block of the record */
rec_t* rec, /*!< in/out: record */
dict_index_t* index, /*!< in: clustered index of the record */
const ulint* offsets,/*!< in: rec_get_offsets(rec) */
ibool val, /*!< in: value to set */ ibool val, /*!< in: value to set */
que_thr_t* thr, /*!< in: query thread */ que_thr_t* thr, /*!< in: query thread */
mtr_t* mtr); /*!< in: mtr */ mtr_t* mtr) /*!< in: mtr */
__attribute__((nonnull));
/***********************************************************//** /***********************************************************//**
Sets a secondary index record delete mark to TRUE or FALSE. Sets a secondary index record delete mark to TRUE or FALSE.
@return DB_SUCCESS, DB_LOCK_WAIT, or error number */ @return DB_SUCCESS, DB_LOCK_WAIT, or error number */
...@@ -481,40 +485,22 @@ btr_estimate_number_of_different_key_vals( ...@@ -481,40 +485,22 @@ btr_estimate_number_of_different_key_vals(
/*======================================*/ /*======================================*/
dict_index_t* index); /*!< in: index */ dict_index_t* index); /*!< in: index */
/*******************************************************************//** /*******************************************************************//**
Marks not updated extern fields as not-owned by this record. The ownership Marks non-updated off-page fields as disowned by this record. The ownership
is transferred to the updated record which is inserted elsewhere in the must be transferred to the updated record which is inserted elsewhere in the
index tree. In purge only the owner of externally stored field is allowed index tree. In purge only the owner of externally stored field is allowed
to free the field. to free the field. */
@return TRUE if BLOB ownership was transferred */
UNIV_INTERN UNIV_INTERN
ibool void
btr_cur_mark_extern_inherited_fields( btr_cur_disown_inherited_fields(
/*=================================*/ /*============================*/
page_zip_des_t* page_zip,/*!< in/out: compressed page whose uncompressed page_zip_des_t* page_zip,/*!< in/out: compressed page whose uncompressed
part will be updated, or NULL */ part will be updated, or NULL */
rec_t* rec, /*!< in/out: record in a clustered index */ rec_t* rec, /*!< in/out: record in a clustered index */
dict_index_t* index, /*!< in: index of the page */ dict_index_t* index, /*!< in: index of the page */
const ulint* offsets,/*!< in: array returned by rec_get_offsets() */ const ulint* offsets,/*!< in: array returned by rec_get_offsets() */
const upd_t* update, /*!< in: update vector */ const upd_t* update, /*!< in: update vector */
mtr_t* mtr); /*!< in: mtr, or NULL if not logged */ mtr_t* mtr) /*!< in/out: mini-transaction */
/*******************************************************************//** __attribute__((nonnull(2,3,4,5,6)));
The complement of the previous function: in an update entry may inherit
some externally stored fields from a record. We must mark them as inherited
in entry, so that they are not freed in a rollback. */
UNIV_INTERN
void
btr_cur_mark_dtuple_inherited_extern(
/*=================================*/
dtuple_t* entry, /*!< in/out: updated entry to be
inserted to clustered index */
const upd_t* update); /*!< in: update vector */
/*******************************************************************//**
Marks all extern fields in a dtuple as owned by the record. */
UNIV_INTERN
void
btr_cur_unmark_dtuple_extern_fields(
/*================================*/
dtuple_t* entry); /*!< in/out: clustered index entry */
/*******************************************************************//** /*******************************************************************//**
Stores the fields in big_rec_vec to the tablespace and puts pointers to Stores the fields in big_rec_vec to the tablespace and puts pointers to
them in rec. The extern flags in rec will have to be set beforehand. them in rec. The extern flags in rec will have to be set beforehand.
......
...@@ -154,14 +154,19 @@ dfield_dup( ...@@ -154,14 +154,19 @@ dfield_dup(
dfield_t* field, /*!< in/out: data field */ dfield_t* field, /*!< in/out: data field */
mem_heap_t* heap); /*!< in: memory heap where allocated */ mem_heap_t* heap); /*!< in: memory heap where allocated */
/*********************************************************************//** /*********************************************************************//**
Tests if data length and content is equal for two dfields. Tests if two data fields are equal.
@return TRUE if equal */ If len==0, tests the data length and content for equality.
If len>0, tests the first len bytes of the content for equality.
@return TRUE if both fields are NULL or if they are equal */
UNIV_INLINE UNIV_INLINE
ibool ibool
dfield_datas_are_binary_equal( dfield_datas_are_binary_equal(
/*==========================*/ /*==========================*/
const dfield_t* field1, /*!< in: field */ const dfield_t* field1, /*!< in: field */
const dfield_t* field2);/*!< in: field */ const dfield_t* field2, /*!< in: field */
ulint len) /*!< in: maximum prefix to compare,
or 0 to compare the whole field length */
__attribute__((nonnull, warn_unused_result));
/*********************************************************************//** /*********************************************************************//**
Tests if dfield data length and content is equal to the given. Tests if dfield data length and content is equal to the given.
@return TRUE if equal */ @return TRUE if equal */
......
...@@ -229,20 +229,30 @@ dfield_dup( ...@@ -229,20 +229,30 @@ dfield_dup(
} }
/*********************************************************************//** /*********************************************************************//**
Tests if data length and content is equal for two dfields. Tests if two data fields are equal.
@return TRUE if equal */ If len==0, tests the data length and content for equality.
If len>0, tests the first len bytes of the content for equality.
@return TRUE if both fields are NULL or if they are equal */
UNIV_INLINE UNIV_INLINE
ibool ibool
dfield_datas_are_binary_equal( dfield_datas_are_binary_equal(
/*==========================*/ /*==========================*/
const dfield_t* field1, /*!< in: field */ const dfield_t* field1, /*!< in: field */
const dfield_t* field2) /*!< in: field */ const dfield_t* field2, /*!< in: field */
ulint len) /*!< in: maximum prefix to compare,
or 0 to compare the whole field length */
{ {
ulint len; ulint len2 = len;
len = field1->len; if (field1->len == UNIV_SQL_NULL || len == 0 || field1->len < len) {
len = field1->len;
}
if (field2->len == UNIV_SQL_NULL || len2 == 0 || field2->len < len2) {
len2 = field2->len;
}
return(len == field2->len return(len == len2
&& (len == UNIV_SQL_NULL && (len == UNIV_SQL_NULL
|| !memcmp(field1->data, field2->data, len))); || !memcmp(field1->data, field2->data, len)));
} }
......
...@@ -286,10 +286,13 @@ row_upd_changes_ord_field_binary( ...@@ -286,10 +286,13 @@ row_upd_changes_ord_field_binary(
row and the data values in update are not row and the data values in update are not
known when this function is called, e.g., at known when this function is called, e.g., at
compile time */ compile time */
const row_ext_t*ext, /*!< NULL, or prefixes of the externally
stored columns in the old row */
dict_index_t* index, /*!< in: index of the record */ dict_index_t* index, /*!< in: index of the record */
const upd_t* update);/*!< in: update vector for the row; NOTE: the const upd_t* update) /*!< in: update vector for the row; NOTE: the
field numbers in this MUST be clustered index field numbers in this MUST be clustered index
positions! */ positions! */
__attribute__((nonnull(3,4), warn_unused_result));
/***********************************************************//** /***********************************************************//**
Checks if an update vector changes an ordering field of an index record. Checks if an update vector changes an ordering field of an index record.
This function is fast if the update vector is short or the number of ordering This function is fast if the update vector is short or the number of ordering
...@@ -462,11 +465,16 @@ struct upd_node_struct{ ...@@ -462,11 +465,16 @@ struct upd_node_struct{
#define UPD_NODE_INSERT_CLUSTERED 3 /* clustered index record should be #define UPD_NODE_INSERT_CLUSTERED 3 /* clustered index record should be
inserted, old record is already delete inserted, old record is already delete
marked */ marked */
#define UPD_NODE_UPDATE_ALL_SEC 4 /* an ordering field of the clustered #define UPD_NODE_INSERT_BLOB 4 /* clustered index record should be
inserted, old record is already
delete-marked; non-updated BLOBs
should be inherited by the new record
and disowned by the old record */
#define UPD_NODE_UPDATE_ALL_SEC 5 /* an ordering field of the clustered
index record was changed, or this is index record was changed, or this is
a delete operation: should update a delete operation: should update
all the secondary index records */ all the secondary index records */
#define UPD_NODE_UPDATE_SOME_SEC 5 /* secondary index entries should be #define UPD_NODE_UPDATE_SOME_SEC 6 /* secondary index entries should be
looked at and updated if an ordering looked at and updated if an ordering
field changed */ field changed */
......
...@@ -110,6 +110,8 @@ struct i_s_trx_row_struct { ...@@ -110,6 +110,8 @@ struct i_s_trx_row_struct {
/*!< thd_get_thread_id() */ /*!< thd_get_thread_id() */
const char* trx_query; /*!< MySQL statement being const char* trx_query; /*!< MySQL statement being
executed in the transaction */ executed in the transaction */
struct charset_info_st* trx_query_cs; /*!< charset encode the MySQL
statement */
}; };
/** This structure represents INFORMATION_SCHEMA.innodb_lock_waits row */ /** This structure represents INFORMATION_SCHEMA.innodb_lock_waits row */
......
...@@ -46,7 +46,7 @@ Created 1/20/1994 Heikki Tuuri ...@@ -46,7 +46,7 @@ Created 1/20/1994 Heikki Tuuri
#define INNODB_VERSION_MAJOR 1 #define INNODB_VERSION_MAJOR 1
#define INNODB_VERSION_MINOR 0 #define INNODB_VERSION_MINOR 0
#define INNODB_VERSION_BUGFIX 14 #define INNODB_VERSION_BUGFIX 15
#define PERCONA_INNODB_VERSION 12.5 #define PERCONA_INNODB_VERSION 12.5
/* The following is the InnoDB version as shown in /* The following is the InnoDB version as shown in
...@@ -303,6 +303,18 @@ number does not include a terminating '\0'. InnoDB probably can handle ...@@ -303,6 +303,18 @@ number does not include a terminating '\0'. InnoDB probably can handle
longer names internally */ longer names internally */
#define MAX_TABLE_NAME_LEN 192 #define MAX_TABLE_NAME_LEN 192
/* The maximum length of a database name. Like MAX_TABLE_NAME_LEN this is
the MySQL's NAME_LEN, see check_and_convert_db_name(). */
#define MAX_DATABASE_NAME_LEN MAX_TABLE_NAME_LEN
/* MAX_FULL_NAME_LEN defines the full name path including the
database name and table name. In addition, 14 bytes is added for:
2 for surrounding quotes around table name
1 for the separating dot (.)
9 for the #mysql50# prefix */
#define MAX_FULL_NAME_LEN \
(MAX_TABLE_NAME_LEN + MAX_DATABASE_NAME_LEN + 14)
/* /*
UNIVERSAL TYPE DEFINITIONS UNIVERSAL TYPE DEFINITIONS
========================== ==========================
......
...@@ -93,6 +93,25 @@ ib_vector_get( ...@@ -93,6 +93,25 @@ ib_vector_get(
ib_vector_t* vec, /*!< in: vector */ ib_vector_t* vec, /*!< in: vector */
ulint n); /*!< in: element index to get */ ulint n); /*!< in: element index to get */
/****************************************************************//**
Get last element. The vector must not be empty.
@return last element */
UNIV_INLINE
void*
ib_vector_get_last(
/*===============*/
ib_vector_t* vec); /*!< in: vector */
/****************************************************************//**
Set the n'th element. */
UNIV_INLINE
void
ib_vector_set(
/*==========*/
ib_vector_t* vec, /*!< in/out: vector */
ulint n, /*!< in: element index to set */
void* elem); /*!< in: data element */
/****************************************************************//** /****************************************************************//**
Remove the last element from the vector. */ Remove the last element from the vector. */
UNIV_INLINE UNIV_INLINE
......
...@@ -50,6 +50,35 @@ ib_vector_get( ...@@ -50,6 +50,35 @@ ib_vector_get(
return(vec->data[n]); return(vec->data[n]);
} }
/****************************************************************//**
Get last element. The vector must not be empty.
@return last element */
UNIV_INLINE
void*
ib_vector_get_last(
/*===============*/
ib_vector_t* vec) /*!< in: vector */
{
ut_a(vec->used > 0);
return(vec->data[vec->used - 1]);
}
/****************************************************************//**
Set the n'th element. */
UNIV_INLINE
void
ib_vector_set(
/*==========*/
ib_vector_t* vec, /*!< in/out: vector */
ulint n, /*!< in: element index to set */
void* elem) /*!< in: data element */
{
ut_a(n < vec->used);
vec->data[n] = elem;
}
/****************************************************************//** /****************************************************************//**
Remove the last element from the vector. Remove the last element from the vector.
@return last vector element */ @return last vector element */
......
...@@ -3631,6 +3631,80 @@ lock_table_create( ...@@ -3631,6 +3631,80 @@ lock_table_create(
return(lock); return(lock);
} }
/*************************************************************//**
Pops autoinc lock requests from the transaction's autoinc_locks. We
handle the case where there are gaps in the array and they need to
be popped off the stack. */
UNIV_INLINE
void
lock_table_pop_autoinc_locks(
/*=========================*/
trx_t* trx) /*!< in/out: transaction that owns the AUTOINC locks */
{
ut_ad(mutex_own(&kernel_mutex));
ut_ad(!ib_vector_is_empty(trx->autoinc_locks));
/* Skip any gaps, gaps are NULL lock entries in the
trx->autoinc_locks vector. */
do {
ib_vector_pop(trx->autoinc_locks);
if (ib_vector_is_empty(trx->autoinc_locks)) {
return;
}
} while (ib_vector_get_last(trx->autoinc_locks) == NULL);
}
/*************************************************************//**
Removes an autoinc lock request from the transaction's autoinc_locks. */
UNIV_INLINE
void
lock_table_remove_autoinc_lock(
/*===========================*/
lock_t* lock, /*!< in: table lock */
trx_t* trx) /*!< in/out: transaction that owns the lock */
{
lock_t* autoinc_lock;
lint i = ib_vector_size(trx->autoinc_locks) - 1;
ut_ad(mutex_own(&kernel_mutex));
ut_ad(lock_get_mode(lock) == LOCK_AUTO_INC);
ut_ad(lock_get_type_low(lock) & LOCK_TABLE);
ut_ad(!ib_vector_is_empty(trx->autoinc_locks));
/* With stored functions and procedures the user may drop
a table within the same "statement". This special case has
to be handled by deleting only those AUTOINC locks that were
held by the table being dropped. */
autoinc_lock = ib_vector_get(trx->autoinc_locks, i);
/* This is the default fast case. */
if (autoinc_lock == lock) {
lock_table_pop_autoinc_locks(trx);
} else {
/* The last element should never be NULL */
ut_a(autoinc_lock != NULL);
/* Handle freeing the locks from within the stack. */
while (--i >= 0) {
autoinc_lock = ib_vector_get(trx->autoinc_locks, i);
if (UNIV_LIKELY(autoinc_lock == lock)) {
ib_vector_set(trx->autoinc_locks, i, NULL);
return;
}
}
/* Must find the autoinc lock. */
ut_error;
}
}
/*************************************************************//** /*************************************************************//**
Removes a table lock request from the queue and the trx list of locks; Removes a table lock request from the queue and the trx list of locks;
this is a low-level function which does NOT check if waiting requests this is a low-level function which does NOT check if waiting requests
...@@ -3670,10 +3744,8 @@ lock_table_remove_low( ...@@ -3670,10 +3744,8 @@ lock_table_remove_low(
if (!lock_get_wait(lock) if (!lock_get_wait(lock)
&& !ib_vector_is_empty(trx->autoinc_locks)) { && !ib_vector_is_empty(trx->autoinc_locks)) {
lock_t* autoinc_lock;
autoinc_lock = ib_vector_pop(trx->autoinc_locks); lock_table_remove_autoinc_lock(lock, trx);
ut_a(autoinc_lock == lock);
} }
ut_a(table->n_waiting_or_granted_auto_inc_locks > 0); ut_a(table->n_waiting_or_granted_auto_inc_locks > 0);
......
...@@ -2260,7 +2260,7 @@ recv_report_corrupt_log( ...@@ -2260,7 +2260,7 @@ recv_report_corrupt_log(
"InnoDB: far enough in recovery! Please run CHECK TABLE\n" "InnoDB: far enough in recovery! Please run CHECK TABLE\n"
"InnoDB: on your InnoDB tables to check that they are ok!\n" "InnoDB: on your InnoDB tables to check that they are ok!\n"
"InnoDB: If mysqld crashes after this recovery, look at\n" "InnoDB: If mysqld crashes after this recovery, look at\n"
"InnoDB: " REFMAN "forcing-recovery.html\n" "InnoDB: " REFMAN "forcing-innodb-recovery.html\n"
"InnoDB: about forcing recovery.\n", stderr); "InnoDB: about forcing recovery.\n", stderr);
fflush(stderr); fflush(stderr);
...@@ -2968,9 +2968,10 @@ recv_recovery_from_checkpoint_start_func( ...@@ -2968,9 +2968,10 @@ recv_recovery_from_checkpoint_start_func(
#endif /* UNIV_LOG_ARCHIVE */ #endif /* UNIV_LOG_ARCHIVE */
byte* buf; byte* buf;
byte* log_hdr_buf; byte* log_hdr_buf;
byte log_hdr_buf_base[LOG_FILE_HDR_SIZE + OS_FILE_LOG_BLOCK_SIZE]; byte *log_hdr_buf_base;
ulint err; ulint err;
log_hdr_buf_base= alloca(LOG_FILE_HDR_SIZE + OS_FILE_LOG_BLOCK_SIZE);
log_hdr_buf = ut_align(log_hdr_buf_base, OS_FILE_LOG_BLOCK_SIZE); log_hdr_buf = ut_align(log_hdr_buf_base, OS_FILE_LOG_BLOCK_SIZE);
#ifdef UNIV_LOG_ARCHIVE #ifdef UNIV_LOG_ARCHIVE
......
...@@ -140,17 +140,24 @@ MYSQL_PLUGIN_ACTIONS(xtradb, [ ...@@ -140,17 +140,24 @@ MYSQL_PLUGIN_ACTIONS(xtradb, [
) )
AC_MSG_CHECKING(whether Solaris libc atomic functions are available) AC_MSG_CHECKING(whether Solaris libc atomic functions are available)
# either define HAVE_IB_SOLARIS_ATOMICS or not # Define HAVE_IB_SOLARIS_ATOMICS if _all_ of the following
AC_CHECK_FUNCS(atomic_cas_ulong \ # functions are present.
AC_CHECK_FUNCS(atomic_add_long_nv \
atomic_cas_32 \ atomic_cas_32 \
atomic_cas_64 \ atomic_cas_64 \
atomic_add_long_nv \ atomic_cas_ulong \
atomic_swap_uchar, atomic_swap_uchar)
AC_DEFINE([HAVE_IB_SOLARIS_ATOMICS], [1], if test "${ac_cv_func_atomic_add_long_nv}" = "yes" -a \
[Define to 1 if Solaris libc atomic functions \ "${ac_cv_func_atomic_cas_32}" = "yes" -a \
are available]) "${ac_cv_func_atomic_cas_64}" = "yes" -a \
) "${ac_cv_func_atomic_cas_ulong}" = "yes" -a \
"${ac_cv_func_atomic_swap_uchar}" = "yes" ; then
AC_DEFINE([HAVE_IB_SOLARIS_ATOMICS], [1],
[Define to 1 if Solaris libc atomic functions are available]
)
fi
AC_MSG_CHECKING(whether pthread_t can be used by Solaris libc atomic functions) AC_MSG_CHECKING(whether pthread_t can be used by Solaris libc atomic functions)
# either define HAVE_IB_ATOMIC_PTHREAD_T_SOLARIS or not # either define HAVE_IB_ATOMIC_PTHREAD_T_SOLARIS or not
......
...@@ -2350,7 +2350,7 @@ row_merge_rename_tables( ...@@ -2350,7 +2350,7 @@ row_merge_rename_tables(
{ {
ulint err = DB_ERROR; ulint err = DB_ERROR;
pars_info_t* info; pars_info_t* info;
char old_name[MAX_TABLE_NAME_LEN + 1]; char old_name[MAX_FULL_NAME_LEN + 1];
ut_ad(trx->mysql_thread_id == os_thread_get_curr_id()); ut_ad(trx->mysql_thread_id == os_thread_get_curr_id());
ut_ad(old_table != new_table); ut_ad(old_table != new_table);
...@@ -2365,7 +2365,7 @@ row_merge_rename_tables( ...@@ -2365,7 +2365,7 @@ row_merge_rename_tables(
ut_print_timestamp(stderr); ut_print_timestamp(stderr);
fprintf(stderr, "InnoDB: too long table name: '%s', " fprintf(stderr, "InnoDB: too long table name: '%s', "
"max length is %d\n", old_table->name, "max length is %d\n", old_table->name,
MAX_TABLE_NAME_LEN); MAX_FULL_NAME_LEN);
ut_error; ut_error;
} }
......
...@@ -574,7 +574,7 @@ row_mysql_handle_errors( ...@@ -574,7 +574,7 @@ row_mysql_handle_errors(
"InnoDB: If the mysqld server crashes" "InnoDB: If the mysqld server crashes"
" after the startup or when\n" " after the startup or when\n"
"InnoDB: you dump the tables, look at\n" "InnoDB: you dump the tables, look at\n"
"InnoDB: " REFMAN "forcing-recovery.html" "InnoDB: " REFMAN "forcing-innodb-recovery.html"
" for help.\n", stderr); " for help.\n", stderr);
break; break;
case DB_FOREIGN_EXCEED_MAX_CASCADE: case DB_FOREIGN_EXCEED_MAX_CASCADE:
......
...@@ -413,7 +413,7 @@ row_purge_upd_exist_or_extern( ...@@ -413,7 +413,7 @@ row_purge_upd_exist_or_extern(
while (node->index != NULL) { while (node->index != NULL) {
index = node->index; index = node->index;
if (row_upd_changes_ord_field_binary(NULL, node->index, if (row_upd_changes_ord_field_binary(NULL, NULL, node->index,
node->update)) { node->update)) {
/* Build the older version of the index entry */ /* Build the older version of the index entry */
entry = row_build_index_entry(node->row, NULL, entry = row_build_index_entry(node->row, NULL,
......
...@@ -668,19 +668,18 @@ row_undo_mod_upd_exist_sec( ...@@ -668,19 +668,18 @@ row_undo_mod_upd_exist_sec(
while (node->index != NULL) { while (node->index != NULL) {
index = node->index; index = node->index;
if (row_upd_changes_ord_field_binary(node->row, node->index, if (row_upd_changes_ord_field_binary(
node->update)) { node->row, node->ext, node->index, node->update)) {
/* Build the newest version of the index entry */ /* Build the newest version of the index entry */
entry = row_build_index_entry(node->row, node->ext, entry = row_build_index_entry(node->row, node->ext,
index, heap); index, heap);
if (UNIV_UNLIKELY(!entry)) { if (UNIV_UNLIKELY(!entry)) {
/* The server must have crashed in /* The server must have crashed in
row_upd_clust_rec_by_insert(), in row_upd_clust_rec_by_insert() before
row_ins_index_entry_low() before the updated externally stored columns (BLOBs)
btr_store_big_rec_extern_fields() of the new clustered index entry were
has written the externally stored columns written. */
(BLOBs) of the new clustered index entry. */
/* The table must be in DYNAMIC or COMPRESSED /* The table must be in DYNAMIC or COMPRESSED
format. REDUNDANT and COMPACT formats format. REDUNDANT and COMPACT formats
......
This diff is collapsed.
...@@ -431,7 +431,7 @@ i_s_locks_row_validate( ...@@ -431,7 +431,7 @@ i_s_locks_row_validate(
/* record lock */ /* record lock */
ut_ad(!strcmp("RECORD", row->lock_type)); ut_ad(!strcmp("RECORD", row->lock_type));
ut_ad(row->lock_index != NULL); ut_ad(row->lock_index != NULL);
ut_ad(row->lock_data != NULL); /* row->lock_data == NULL if buf_page_try_get() == NULL */
ut_ad(row->lock_page != ULINT_UNDEFINED); ut_ad(row->lock_page != ULINT_UNDEFINED);
ut_ad(row->lock_rec != ULINT_UNDEFINED); ut_ad(row->lock_rec != ULINT_UNDEFINED);
} }
...@@ -494,7 +494,6 @@ fill_trx_row( ...@@ -494,7 +494,6 @@ fill_trx_row(
stmt = innobase_get_stmt(trx->mysql_thd, &stmt_len); stmt = innobase_get_stmt(trx->mysql_thd, &stmt_len);
if (stmt != NULL) { if (stmt != NULL) {
char query[TRX_I_S_TRX_QUERY_MAX_LEN + 1]; char query[TRX_I_S_TRX_QUERY_MAX_LEN + 1];
if (stmt_len > TRX_I_S_TRX_QUERY_MAX_LEN) { if (stmt_len > TRX_I_S_TRX_QUERY_MAX_LEN) {
...@@ -508,6 +507,8 @@ fill_trx_row( ...@@ -508,6 +507,8 @@ fill_trx_row(
cache->storage, stmt, stmt_len + 1, cache->storage, stmt, stmt_len + 1,
MAX_ALLOWED_FOR_STORAGE(cache)); MAX_ALLOWED_FOR_STORAGE(cache));
row->trx_query_cs = innobase_get_charset(trx->mysql_thd);
if (row->trx_query == NULL) { if (row->trx_query == NULL) {
return(FALSE); return(FALSE);
......
...@@ -79,7 +79,7 @@ ut_dbg_assertion_failed( ...@@ -79,7 +79,7 @@ ut_dbg_assertion_failed(
" or crashes, even\n" " or crashes, even\n"
"InnoDB: immediately after the mysqld startup, there may be\n" "InnoDB: immediately after the mysqld startup, there may be\n"
"InnoDB: corruption in the InnoDB tablespace. Please refer to\n" "InnoDB: corruption in the InnoDB tablespace. Please refer to\n"
"InnoDB: " REFMAN "forcing-recovery.html\n" "InnoDB: " REFMAN "forcing-innodb-recovery.html\n"
"InnoDB: about forcing recovery.\n", stderr); "InnoDB: about forcing recovery.\n", stderr);
#if defined(UNIV_SYNC_DEBUG) || !defined(UT_DBG_USE_ABORT) #if defined(UNIV_SYNC_DEBUG) || !defined(UT_DBG_USE_ABORT)
ut_dbg_stop_threads = TRUE; ut_dbg_stop_threads = TRUE;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment