From 6d1081cda278f57349fc239db77ccbc84e50d8f1 Mon Sep 17 00:00:00 2001 From: unknown Date: Tue, 3 Jun 2003 23:13:06 +0200 Subject: [PATCH] One-line fix for bug 576 (DBUG_ASSERT failure when using CHANGE MASTER TO RELAY_LOG_POS=4). Plus a changeset which I had committed but forgot to push (and this changeset is lost on another computer, so I recreate it here). This changeset is "user-friendly SHOW BINLOG EVENTS and CHANGE MASTER TO when log positions < 4 are used. sql/slave.cc: fix for bug 576 (DBUG_ASSERT failure when using CHANGE MASTER TO RELAY_LOG_POS=4). sql/sql_repl.cc: User-friendly SHOW BINLOG EVENTS: SHOW BINLOG EVENTS FROM 0: currently one gets MASTER> show binlog events from 0; ERROR 1220: Error when executing command SHOW BINLOG EVENTS: Invalid log position so we silently convert <4 to 4. sql/sql_yacc.yy: User-friendly CHANGE MASTER TO: presently when one does CHANGE MASTER TO MASTER_LOG_POS=0 he gets 030425 10:12:41 Slave I/O thread: connected to master 'root@localhost:3306', r eplication started in log 'gbichot-bin.013' at position 151 030425 10:12:41 Error reading packet from server: Client requested master to st art replication from impossible position (server_errno=1236) 030425 10:12:41 Got fatal error 1236: 'Client requested master to start replica tion from impossible position' from master when reading data from binary log 030425 10:12:41 Slave I/O thread exiting, read up to log 'gbichot-bin.013', pos ition 151 while she/he probably just wanted to start at the beginning of the binlog, which is 4. So we silently convert <4 to 4 in sql_yacc.yy (i.e. in the slave code; fortunately all versions have the same BIN_LOG_HEADER_SIZE=4 and we should not change this). See comments for an explaination of why we have to do this in sql_yacc.yy, not in sql_repl.cc. Same thing for CHANGE MASTER TO RELAY_LOG_POS. sql/unireg.h: warning comment --- sql/slave.cc | 2 +- sql/sql_repl.cc | 8 +------- sql/sql_yacc.yy | 14 ++++++++++++++ sql/unireg.h | 8 ++++++-- 4 files changed, 22 insertions(+), 10 deletions(-) diff --git a/sql/slave.cc b/sql/slave.cc index ec1041894bd..c2762dbd6f4 100644 --- a/sql/slave.cc +++ b/sql/slave.cc @@ -269,7 +269,7 @@ int init_relay_log_pos(RELAY_LOG_INFO* rli,const char* log, goto err; rli->cur_log = &rli->cache_buf; } - if (pos > BIN_LOG_HEADER_SIZE) + if (pos >= BIN_LOG_HEADER_SIZE) my_b_seek(rli->cur_log,(off_t)pos); err: diff --git a/sql/sql_repl.cc b/sql/sql_repl.cc index 283dd20a56c..ca993c053a1 100644 --- a/sql/sql_repl.cc +++ b/sql/sql_repl.cc @@ -961,7 +961,7 @@ int show_binlog_events(THD* thd) { LEX_MASTER_INFO *lex_mi = &thd->lex.mi; ha_rows event_count, limit_start, limit_end; - my_off_t pos = lex_mi->pos; + my_off_t pos = max(BIN_LOG_HEADER_SIZE, lex_mi->pos); // user-friendly char search_file_name[FN_REFLEN], *name; const char *log_file_name = lex_mi->log_file_name; pthread_mutex_t *log_lock = mysql_bin_log.get_log_lock(); @@ -989,12 +989,6 @@ int show_binlog_events(THD* thd) if ((file=open_binlog(&log, linfo.log_file_name, &errmsg)) < 0) goto err; - if (pos < 4) - { - errmsg = "Invalid log position"; - goto err; - } - pthread_mutex_lock(log_lock); my_b_seek(&log, pos); diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index c79750c8014..b0c81d6f6b0 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -706,6 +706,18 @@ master_def: MASTER_LOG_POS_SYM EQ ulonglong_num { Lex->mi.pos = $3; + /* + If the user specified a value < BIN_LOG_HEADER_SIZE, adjust it + instead of causing subsequent errors. + We need to do it in this file, because only there we know that + MASTER_LOG_POS has been explicitely specified. On the contrary + in change_master() (sql_repl.cc) we cannot distinguish between 0 + (MASTER_LOG_POS explicitely specified as 0) and 0 (unspecified), + whereas we want to distinguish (specified 0 means "read the binlog + from 0" (4 in fact), unspecified means "don't change the position + (keep the preceding value)"). + */ + Lex->mi.pos = max(BIN_LOG_HEADER_SIZE, Lex->mi.pos); } | MASTER_CONNECT_RETRY_SYM EQ ULONG_NUM @@ -721,6 +733,8 @@ master_def: RELAY_LOG_POS_SYM EQ ULONG_NUM { Lex->mi.relay_log_pos = $3; + /* Adjust if < BIN_LOG_HEADER_SIZE (same comment as Lex->mi.pos) */ + Lex->mi.relay_log_pos = max(BIN_LOG_HEADER_SIZE, Lex->mi.relay_log_pos); }; diff --git a/sql/unireg.h b/sql/unireg.h index f69d67455dd..f2cace51fa7 100644 --- a/sql/unireg.h +++ b/sql/unireg.h @@ -130,9 +130,13 @@ bfill((A)->null_flags,(A)->null_bytes,255);\ */ #define MIN_TURBOBM_PATTERN_LEN 3 -/* Defines for binary logging */ +/* + Defines for binary logging. + Do not decrease the value of BIN_LOG_HEADER_SIZE. + Do not even increase it before checking code. +*/ -#define BIN_LOG_HEADER_SIZE 4 +#define BIN_LOG_HEADER_SIZE 4 /* Include prototypes for unireg */