1377
1378
FLAGSTR(thd->options, OPTION_NOT_AUTOCOMMIT),
1378
1379
FLAGSTR(thd->options, OPTION_BEGIN)));
1380
thd->binlog_flush_pending_rows_event(TRUE);
1383
1382
NULL denotes ROLLBACK with nothing to replicate: i.e., rollback of
1384
1383
only transactional tables. If the transaction contain changes to
1467
1468
static int binlog_commit(handlerton *hton, THD *thd, bool all)
1469
1471
DBUG_ENTER("binlog_commit");
1470
1472
binlog_trx_data *const trx_data=
1471
1473
(binlog_trx_data*) thd_get_ha_data(thd, binlog_hton);
1481
Decision table for committing a transaction. The top part, the
1482
*conditions* represent different cases that can occur, and hte
1483
bottom part, the *actions*, represent what should be done in that
1486
Real transaction 'all' was true
1488
Statement in cache There were at least one statement in the
1491
In transaction We are inside a transaction
1493
Stmt modified non-trans The statement being committed modified a
1494
non-transactional table
1496
All modified non-trans Some statement before this one in the
1497
transaction modified a non-transactional
1501
============================= = = = = = = = = = = = = = = = =
1502
Real transaction N N N N N N N N N N N N N N N N
1503
Statement in cache N N N N N N N N Y Y Y Y Y Y Y Y
1504
In transaction N N N N Y Y Y Y N N N N Y Y Y Y
1505
Stmt modified non-trans N N Y Y N N Y Y N N Y Y N N Y Y
1506
All modified non-trans N Y N Y N Y N Y N Y N Y N Y N Y
1508
Action: (C)ommit/(A)ccumulate C C - C A C - C - - - - A A - A
1509
============================= = = = = = = = = = = = = = = = =
1512
============================= = = = = = = = = = = = = = = = =
1513
Real transaction Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y Y
1514
Statement in cache N N N N N N N N Y Y Y Y Y Y Y Y
1515
In transaction N N N N Y Y Y Y N N N N Y Y Y Y
1516
Stmt modified non-trans N N Y Y N N Y Y N N Y Y N N Y Y
1517
All modified non-trans N Y N Y N Y N Y N Y N Y N Y N Y
1519
(C)ommit/(A)ccumulate/(-) - - - - C C - C - - - - C C - C
1520
============================= = = = = = = = = = = = = = = = =
1522
In other words, we commit the transaction if and only if both of
1523
the following are true:
1524
- We are not in a transaction and committing a statement
1526
- We are in a transaction and one (or more) of the following are
1529
- A full transaction is committed
1533
- A non-transactional statement is committed and there is
1483
We commit the transaction if:
1485
- We are not in a transaction and committing a statement, or
1487
- We are in a transaction and a full transaction is committed
1536
1489
Otherwise, we accumulate the statement
1544
1497
YESNO(in_transaction),
1545
1498
YESNO(thd->transaction.all.modified_non_trans_table),
1546
1499
YESNO(thd->transaction.stmt.modified_non_trans_table)));
1547
if (in_transaction &&
1549
(!trx_data->at_least_one_stmt &&
1550
thd->transaction.stmt.modified_non_trans_table)) ||
1551
!in_transaction && !all)
1500
if (!in_transaction || all)
1553
1502
Query_log_event qev(thd, STRING_WITH_LEN("COMMIT"), TRUE, FALSE);
1554
1503
qev.error_code= 0; // see comment in MYSQL_LOG::write(THD, IO_CACHE)
1555
int error= binlog_end_trans(thd, trx_data, &qev, all);
1504
error= binlog_end_trans(thd, trx_data, &qev, all);
1510
trx_data->before_stmt_pos = MY_OFF_T_UNDEF; // part of the stmt commit
2960
2917
DBUG_ASSERT(!strcmp(rli->linfo.log_file_name,rli->event_relay_log_name));
2962
2919
pthread_mutex_lock(&LOCK_index);
2963
pthread_mutex_lock(&rli->log_space_lock);
2964
rli->relay_log.purge_logs(rli->group_relay_log_name, included,
2965
0, 0, &rli->log_space_total);
2966
// Tell the I/O thread to take the relay_log_space_limit into account
2967
rli->ignore_log_space_limit= 0;
2968
pthread_mutex_unlock(&rli->log_space_lock);
2920
to_purge_if_included= my_strdup(rli->group_relay_log_name, MYF(0));
2971
Ok to broadcast after the critical region as there is no risk of
2972
the mutex being destroyed by this thread later - this helps save
2975
pthread_cond_broadcast(&rli->log_space_cond);
2978
2923
Read the next log file name from the index file and pass it back to
2980
If included is true, we want the first relay log;
2981
otherwise we want the one after event_relay_log_name.
2983
if ((included && (error=find_log_pos(&rli->linfo, NullS, 0))) ||
2985
((error=find_log_pos(&rli->linfo, rli->event_relay_log_name, 0)) ||
2986
(error=find_next_log(&rli->linfo, 0)))))
2926
if((error=find_log_pos(&rli->linfo, rli->event_relay_log_name, 0)) ||
2927
(error=find_next_log(&rli->linfo, 0)))
2989
2930
sql_print_error("next log error: %d offset: %s log: %s included: %d",
2991
2932
llstr(rli->linfo.index_file_offset,buff),
2992
rli->group_relay_log_name,
2933
rli->event_relay_log_name,
3017
2958
/* Store where we are in the new file for the execution thread */
3018
2959
flush_relay_log_info(rli);
2961
DBUG_EXECUTE_IF("crash_before_purge_logs", abort(););
2963
pthread_mutex_lock(&rli->log_space_lock);
2964
rli->relay_log.purge_logs(to_purge_if_included, included,
2965
0, 0, &rli->log_space_total);
2966
// Tell the I/O thread to take the relay_log_space_limit into account
2967
rli->ignore_log_space_limit= 0;
2968
pthread_mutex_unlock(&rli->log_space_lock);
2971
Ok to broadcast after the critical region as there is no risk of
2972
the mutex being destroyed by this thread later - this helps save
2975
pthread_cond_broadcast(&rli->log_space_cond);
2978
* Need to update the log pos because purge logs has been called
2979
* after fetching initially the log pos at the begining of the method.
2981
if((error=find_log_pos(&rli->linfo, rli->event_relay_log_name, 0)))
2984
sql_print_error("next log error: %d offset: %s log: %s included: %d",
2986
llstr(rli->linfo.index_file_offset,buff),
2987
rli->group_relay_log_name,
2992
/* If included was passed, rli->linfo should be the first entry. */
2993
DBUG_ASSERT(!included || rli->linfo.index_file_start_offset == 0);
2996
my_free(to_purge_if_included, MYF(0));
3021
2997
pthread_mutex_unlock(&LOCK_index);
3022
2998
DBUG_RETURN(error);
3078
3053
if (need_mutex)
3079
3054
pthread_mutex_lock(&LOCK_index);
3080
if ((error=find_log_pos(&log_info, to_log, 0 /*no mutex*/)))
3055
if ((error=find_log_pos(&log_info, to_log, 0 /*no mutex*/)))
3057
sql_print_error("MYSQL_LOG::purge_logs was called with file %s not "
3058
"listed in the index.", to_log);
3063
For crash recovery reasons the index needs to be updated before
3064
any files are deleted. Move files to be deleted into a temp file
3065
to be processed after the index is updated.
3067
if (!my_b_inited(&purge_temp))
3069
if ((error=open_cached_file(&purge_temp, mysql_tmpdir, TEMP_PREFIX,
3070
DISK_BUFFER_SIZE, MYF(MY_WME))))
3072
sql_print_error("MYSQL_LOG::purge_logs failed to open purge_temp");
3078
if ((error=reinit_io_cache(&purge_temp, WRITE_CACHE, 0, 0, 1)))
3080
sql_print_error("MYSQL_LOG::purge_logs failed to reinit purge_temp "
3084
3087
File name exists in index file; delete until we find this file
3089
3092
while ((strcmp(to_log,log_info.log_file_name) || (exit_loop=included)) &&
3090
3093
!log_in_use(log_info.log_file_name))
3095
if ((error=my_b_write(&purge_temp, (const uchar*)log_info.log_file_name,
3096
strlen(log_info.log_file_name))) ||
3097
(error=my_b_write(&purge_temp, (const uchar*)"\n", 1)))
3099
sql_print_error("MYSQL_LOG::purge_logs failed to copy %s to purge_temp",
3100
log_info.log_file_name);
3104
if (find_next_log(&log_info, 0) || exit_loop)
3108
/* We know how many files to delete. Update index file. */
3109
if ((error=update_log_index(&log_info, need_update_threads)))
3111
sql_print_error("MSYQL_LOG::purge_logs failed to update the index file");
3115
DBUG_EXECUTE_IF("crash_after_update_index", abort(););
3117
/* Switch purge_temp for read. */
3118
if ((error=reinit_io_cache(&purge_temp, READ_CACHE, 0, 0, 0)))
3120
sql_print_error("MSYQL_LOG::purge_logs failed to reinit purge_temp "
3125
/* Read each entry from purge_temp and delete the file. */
3130
if ((length=my_b_gets(&purge_temp, log_info.log_file_name,
3133
if (purge_temp.error)
3135
error= purge_temp.error;
3136
sql_print_error("MSYQL_LOG::purge_logs error %d reading from "
3137
"purge_temp", error);
3145
/* Get rid of the trailing '\n' */
3146
log_info.log_file_name[length-1]= 0;
3148
ha_binlog_index_purge_file(current_thd, log_info.log_file_name);
3093
3151
if (!my_stat(log_info.log_file_name, &s, MYF(0)))
3193
ha_binlog_index_purge_file(current_thd, log_info.log_file_name);
3195
if (find_next_log(&log_info, 0) || exit_loop)
3200
If we get killed -9 here, the sysadmin would have to edit
3201
the log index file after restart - otherwise, this should be safe
3203
error= update_log_index(&log_info, need_update_threads);
3253
close_cached_file(&purge_temp);
3209
3254
if (need_mutex)
3210
3255
pthread_mutex_unlock(&LOCK_index);
3211
3256
DBUG_RETURN(error);
3218
3263
@param thd Thread pointer
3219
@param before_date Delete all log files before given date.
3264
@param purge_time Delete all log files before given date.
3222
3267
If any of the logs before the deleted one is in use,
3240
3286
DBUG_ENTER("purge_logs_before_date");
3242
3288
pthread_mutex_lock(&LOCK_index);
3245
Delete until we find curren file
3246
or a file that is used or a file
3247
that is older than purge_time.
3249
3291
if ((error=find_log_pos(&log_info, NullS, 0 /*no mutex*/)))
3298
if (stat_area.st_mtime >= purge_time)
3340
if (stat_area.st_mtime < purge_time)
3342
log_info.log_file_name,
3343
sizeof(log_info.log_file_name));
3300
if (my_delete(log_info.log_file_name, MYF(0)))
3302
if (my_errno == ENOENT)
3304
/* It's not fatal even if we can't delete a log file */
3307
push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_WARN,
3308
ER_LOG_PURGE_NO_FILE, ER(ER_LOG_PURGE_NO_FILE),
3309
log_info.log_file_name);
3311
sql_print_information("Failed to delete file '%s'",
3312
log_info.log_file_name);
3319
push_warning_printf(thd, MYSQL_ERROR::WARN_LEVEL_ERROR,
3320
ER_BINLOG_PURGE_FATAL_ERR,
3321
"a problem with deleting %s; "
3322
"consider examining correspondence "
3323
"of your binlog index file "
3324
"to the actual binlog files",
3325
log_info.log_file_name);
3329
sql_print_information("Failed to delete log file '%s'",
3330
log_info.log_file_name);
3332
error= LOG_INFO_FATAL;
3336
ha_binlog_index_purge_file(current_thd, log_info.log_file_name);
3338
3347
if (find_next_log(&log_info, 0))
3343
If we get killed -9 here, the sysadmin would have to edit
3344
the log index file after restart - otherwise, this should be safe
3346
error= update_log_index(&log_info, 1);
3351
error= (to_log[0] ? purge_logs(to_log, 1, 0, 1, (ulonglong *) 0) : 0);
3349
3354
pthread_mutex_unlock(&LOCK_index);