Loading myisam/myisampack.c +30 −8 Original line number Diff line number Diff line Loading @@ -111,6 +111,8 @@ typedef struct st_isam_mrg { uint ref_length; uint max_blob_length; my_off_t records; /* true if at least one source file has at least one disabled index */ my_bool src_file_has_indexes_disabled; } PACK_MRG_INFO; Loading Loading @@ -413,9 +415,16 @@ static bool open_isam_files(PACK_MRG_INFO *mrg,char **names,uint count) mrg->current=0; mrg->file=(MI_INFO**) my_malloc(sizeof(MI_INFO*)*count,MYF(MY_FAE)); mrg->free_file=1; mrg->src_file_has_indexes_disabled= 0; for (i=0; i < count ; i++) { if (!(mrg->file[i]=open_isam_file(names[i],O_RDONLY))) if ((mrg->file[i]=open_isam_file(names[i],O_RDONLY))) { mrg->src_file_has_indexes_disabled |= (mrg->file[i]->s->state.key_map != (1ULL << mrg->file[i]->s->base.keys) - 1); } else goto error; } /* Check that files are identical */ Loading Loading @@ -2040,12 +2049,21 @@ static int save_state(MI_INFO *isam_file,PACK_MRG_INFO *mrg,my_off_t new_length, share->state.dellink= HA_OFFSET_ERROR; share->state.split=(ha_rows) mrg->records; share->state.version=(ulong) time((time_t*) 0); share->state.key_map=0; if (share->state.key_map != (1ULL << share->base.keys) - 1) { /* Don't save key_file_length here, keep key_file_length of original file so "myisamchk -rq" can use this value (this is necessary because index size cannot be easily calculated for fulltext keys) Some indexes are disabled, cannot use current key_file_length value as an estimate of upper bound of index file size. Use packed data file size instead. */ share->state.state.key_file_length= new_length; } /* If there are no disabled indexes, keep key_file_length value from original file so "myisamchk -rq" can use this value (this is necessary because index size cannot be easily calculated for fulltext keys) */ share->state.key_map=0; for (key=0 ; key < share->base.keys ; key++) share->state.key_root[key]= HA_OFFSET_ERROR; for (key=0 ; key < share->state.header.max_block_size ; key++) Loading @@ -2054,8 +2072,7 @@ static int save_state(MI_INFO *isam_file,PACK_MRG_INFO *mrg,my_off_t new_length, share->changed=1; /* Force write of header */ share->state.open_count=0; share->global_changed=0; VOID(my_chsize(share->kfile, share->state.state.key_file_length, 0, MYF(0))); VOID(my_chsize(share->kfile, share->base.keystart, 0, MYF(0))); if (share->base.keys) isamchk_neaded=1; DBUG_RETURN(mi_state_info_write(share->kfile,&share->state,1+2)); Loading @@ -2078,7 +2095,12 @@ static int save_state_mrg(File file,PACK_MRG_INFO *mrg,my_off_t new_length, state.state.del=0; state.state.empty=0; state.state.records=state.split=(ha_rows) mrg->records; state.state.key_file_length=isam_file->s->base.keystart; /* See comment above in save_state about key_file_length handling. */ if (mrg->src_file_has_indexes_disabled) { isam_file->s->state.state.key_file_length= max(isam_file->s->state.state.key_file_length, new_length); } state.dellink= HA_OFFSET_ERROR; state.version=(ulong) time((time_t*) 0); state.key_map=0; Loading mysql-test/r/rpl_commit_after_flush.result 0 → 100644 +13 −0 Original line number Diff line number Diff line slave stop; drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9; reset master; reset slave; drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9; slave start; create table t1 (a int) type=innodb; begin; insert into t1 values(1); flush tables with read lock; commit; unlock tables; drop table t1; mysql-test/t/rpl_commit_after_flush.test 0 → 100644 +17 −0 Original line number Diff line number Diff line source include/master-slave.inc; source include/have_innodb.inc; create table t1 (a int) type=innodb; begin; insert into t1 values(1); flush tables with read lock; commit; save_master_pos; connection slave; sync_with_master; # cleanup connection master; unlock tables; drop table t1; save_master_pos; connection slave; sync_with_master; sql/lock.cc +8 −2 Original line number Diff line number Diff line Loading @@ -751,9 +751,15 @@ bool wait_if_global_read_lock(THD *thd, bool abort_on_refresh, bool is_not_commi { if (thd->global_read_lock) // This thread had the read locks { if (is_not_commit) my_error(ER_CANT_UPDATE_WITH_READLOCK,MYF(0)); (void) pthread_mutex_unlock(&LOCK_open); DBUG_RETURN(1); /* We allow FLUSHer to COMMIT; we assume FLUSHer knows what it does. This allowance is needed to not break existing versions of innobackup which do a BEGIN; INSERT; FLUSH TABLES WITH READ LOCK; COMMIT. */ DBUG_RETURN(is_not_commit); } old_message=thd->enter_cond(&COND_refresh, &LOCK_open, "Waiting for release of readlock"); Loading Loading
myisam/myisampack.c +30 −8 Original line number Diff line number Diff line Loading @@ -111,6 +111,8 @@ typedef struct st_isam_mrg { uint ref_length; uint max_blob_length; my_off_t records; /* true if at least one source file has at least one disabled index */ my_bool src_file_has_indexes_disabled; } PACK_MRG_INFO; Loading Loading @@ -413,9 +415,16 @@ static bool open_isam_files(PACK_MRG_INFO *mrg,char **names,uint count) mrg->current=0; mrg->file=(MI_INFO**) my_malloc(sizeof(MI_INFO*)*count,MYF(MY_FAE)); mrg->free_file=1; mrg->src_file_has_indexes_disabled= 0; for (i=0; i < count ; i++) { if (!(mrg->file[i]=open_isam_file(names[i],O_RDONLY))) if ((mrg->file[i]=open_isam_file(names[i],O_RDONLY))) { mrg->src_file_has_indexes_disabled |= (mrg->file[i]->s->state.key_map != (1ULL << mrg->file[i]->s->base.keys) - 1); } else goto error; } /* Check that files are identical */ Loading Loading @@ -2040,12 +2049,21 @@ static int save_state(MI_INFO *isam_file,PACK_MRG_INFO *mrg,my_off_t new_length, share->state.dellink= HA_OFFSET_ERROR; share->state.split=(ha_rows) mrg->records; share->state.version=(ulong) time((time_t*) 0); share->state.key_map=0; if (share->state.key_map != (1ULL << share->base.keys) - 1) { /* Don't save key_file_length here, keep key_file_length of original file so "myisamchk -rq" can use this value (this is necessary because index size cannot be easily calculated for fulltext keys) Some indexes are disabled, cannot use current key_file_length value as an estimate of upper bound of index file size. Use packed data file size instead. */ share->state.state.key_file_length= new_length; } /* If there are no disabled indexes, keep key_file_length value from original file so "myisamchk -rq" can use this value (this is necessary because index size cannot be easily calculated for fulltext keys) */ share->state.key_map=0; for (key=0 ; key < share->base.keys ; key++) share->state.key_root[key]= HA_OFFSET_ERROR; for (key=0 ; key < share->state.header.max_block_size ; key++) Loading @@ -2054,8 +2072,7 @@ static int save_state(MI_INFO *isam_file,PACK_MRG_INFO *mrg,my_off_t new_length, share->changed=1; /* Force write of header */ share->state.open_count=0; share->global_changed=0; VOID(my_chsize(share->kfile, share->state.state.key_file_length, 0, MYF(0))); VOID(my_chsize(share->kfile, share->base.keystart, 0, MYF(0))); if (share->base.keys) isamchk_neaded=1; DBUG_RETURN(mi_state_info_write(share->kfile,&share->state,1+2)); Loading @@ -2078,7 +2095,12 @@ static int save_state_mrg(File file,PACK_MRG_INFO *mrg,my_off_t new_length, state.state.del=0; state.state.empty=0; state.state.records=state.split=(ha_rows) mrg->records; state.state.key_file_length=isam_file->s->base.keystart; /* See comment above in save_state about key_file_length handling. */ if (mrg->src_file_has_indexes_disabled) { isam_file->s->state.state.key_file_length= max(isam_file->s->state.state.key_file_length, new_length); } state.dellink= HA_OFFSET_ERROR; state.version=(ulong) time((time_t*) 0); state.key_map=0; Loading
mysql-test/r/rpl_commit_after_flush.result 0 → 100644 +13 −0 Original line number Diff line number Diff line slave stop; drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9; reset master; reset slave; drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9; slave start; create table t1 (a int) type=innodb; begin; insert into t1 values(1); flush tables with read lock; commit; unlock tables; drop table t1;
mysql-test/t/rpl_commit_after_flush.test 0 → 100644 +17 −0 Original line number Diff line number Diff line source include/master-slave.inc; source include/have_innodb.inc; create table t1 (a int) type=innodb; begin; insert into t1 values(1); flush tables with read lock; commit; save_master_pos; connection slave; sync_with_master; # cleanup connection master; unlock tables; drop table t1; save_master_pos; connection slave; sync_with_master;
sql/lock.cc +8 −2 Original line number Diff line number Diff line Loading @@ -751,9 +751,15 @@ bool wait_if_global_read_lock(THD *thd, bool abort_on_refresh, bool is_not_commi { if (thd->global_read_lock) // This thread had the read locks { if (is_not_commit) my_error(ER_CANT_UPDATE_WITH_READLOCK,MYF(0)); (void) pthread_mutex_unlock(&LOCK_open); DBUG_RETURN(1); /* We allow FLUSHer to COMMIT; we assume FLUSHer knows what it does. This allowance is needed to not break existing versions of innobackup which do a BEGIN; INSERT; FLUSH TABLES WITH READ LOCK; COMMIT. */ DBUG_RETURN(is_not_commit); } old_message=thd->enter_cond(&COND_refresh, &LOCK_open, "Waiting for release of readlock"); Loading