List:Commits« Previous MessageNext Message »
From:Sven Sandberg Date:January 8 2009 2:28pm
Subject:bzr commit into mysql-5.1 branch (sven:2711) Bug#41961
View as plain text  
#At file:///home/sven/bzr/b41961-post_header_len/5.1-rpl/ based on revid:sven@stripped

 2711 Sven Sandberg	2009-01-08
      BUG#41961: Some log_event types do not skip post-header when reading
      Problem: when the server reads a log_event from file, it should read
      the post-header lengths from the format_description_log_event. Some
      event types which currently have post-header length 0 did not do this,
      and instead had a hard-coded zero length for the post-header. That
      means the current server version will not be able to read future
      versions of these events.
      Fix: make the reader functions read the post-header.
modified:
  sql/log_event.cc
  sql/log_event.h

per-file messages:
  sql/log_event.cc
     - Made Format_description_log_event constructor initialize all
       post-header lengths explicitly, to make it easier to find them
       in the source code. After this, it is no longer necessary to pass
       the MY_ZEROFILL flag to my_malloc. I removed the flag since
       that means valgrind will give a warning if a future event type
       does not declare its length here.
     - Made INTVAR, RAND, USER_VAR, and XID events skip post_header_len
       when reading from file.
  sql/log_event.h
    Added explicit defines for the length of all event types.
=== modified file 'sql/log_event.cc'
--- a/sql/log_event.cc	2008-11-12 17:51:47 +0000
+++ b/sql/log_event.cc	2009-01-08 14:28:45 +0000
@@ -3424,7 +3424,7 @@ Format_description_log_event(uint8 binlo
     number_of_event_types= LOG_EVENT_TYPES;
     /* we'll catch my_malloc() error in is_valid() */
     post_header_len=(uint8*) my_malloc(number_of_event_types*sizeof(uint8),
-                                       MYF(MY_ZEROFILL));
+                                       MYF(0));
     /*
       This long list of assignments is not beautiful, but I see no way to
       make it nicer, as the right members are #defines, not array members, so
@@ -3432,16 +3432,35 @@ Format_description_log_event(uint8 binlo
     */
     if (post_header_len)
     {
+      /* Note: all event types must explicitly fill in their lengths here. */
       post_header_len[START_EVENT_V3-1]= START_V3_HEADER_LEN;
       post_header_len[QUERY_EVENT-1]= QUERY_HEADER_LEN;
+      post_header_len[STOP_EVENT-1]= STOP_HEADER_LEN;
       post_header_len[ROTATE_EVENT-1]= ROTATE_HEADER_LEN;
+      post_header_len[INTVAR_EVENT-1]= INTVAR_HEADER_LEN;
       post_header_len[LOAD_EVENT-1]= LOAD_HEADER_LEN;
+      post_header_len[SLAVE_EVENT-1]= SLAVE_HEADER_LEN;
       post_header_len[CREATE_FILE_EVENT-1]= CREATE_FILE_HEADER_LEN;
       post_header_len[APPEND_BLOCK_EVENT-1]= APPEND_BLOCK_HEADER_LEN;
       post_header_len[EXEC_LOAD_EVENT-1]= EXEC_LOAD_HEADER_LEN;
       post_header_len[DELETE_FILE_EVENT-1]= DELETE_FILE_HEADER_LEN;
       post_header_len[NEW_LOAD_EVENT-1]= post_header_len[LOAD_EVENT-1];
+      post_header_len[RAND_EVENT-1]= RAND_HEADER_LEN;
+      post_header_len[USER_VAR_EVENT-1]= USER_VAR_HEADER_LEN;
       post_header_len[FORMAT_DESCRIPTION_EVENT-1]= FORMAT_DESCRIPTION_HEADER_LEN;
+      post_header_len[XID_EVENT-1]= XID_HEADER_LEN;
+      post_header_len[BEGIN_LOAD_QUERY_EVENT-1]= post_header_len[APPEND_BLOCK_EVENT-1];
+      post_header_len[EXECUTE_LOAD_QUERY_EVENT-1]= EXECUTE_LOAD_QUERY_HEADER_LEN;
+      /*
+        The PRE_GA events are never be written to any binlog, but
+        their lengths are included in Format_description_log_event.
+        Hence, we need to be assign some value here, to avoid reading
+        uninitialized memory when the array is written to disk.
+      */
+      post_header_len[PRE_GA_WRITE_ROWS_EVENT-1] = 0;
+      post_header_len[PRE_GA_UPDATE_ROWS_EVENT-1] = 0;
+      post_header_len[PRE_GA_DELETE_ROWS_EVENT-1] = 0;
+
       post_header_len[TABLE_MAP_EVENT-1]=    TABLE_MAP_HEADER_LEN;
       post_header_len[WRITE_ROWS_EVENT-1]=   ROWS_HEADER_LEN;
       post_header_len[UPDATE_ROWS_EVENT-1]=  ROWS_HEADER_LEN;
@@ -3461,8 +3480,6 @@ Format_description_log_event(uint8 binlo
                       post_header_len[WRITE_ROWS_EVENT-1]=
                       post_header_len[UPDATE_ROWS_EVENT-1]=
                       post_header_len[DELETE_ROWS_EVENT-1]= 6;);
-      post_header_len[BEGIN_LOAD_QUERY_EVENT-1]= post_header_len[APPEND_BLOCK_EVENT-1];
-      post_header_len[EXECUTE_LOAD_QUERY_EVENT-1]= EXECUTE_LOAD_QUERY_HEADER_LEN;
       post_header_len[INCIDENT_EVENT-1]= INCIDENT_HEADER_LEN;
     }
     break;
@@ -4813,7 +4830,8 @@ Intvar_log_event::Intvar_log_event(const
                                    const Format_description_log_event* description_event)
   :Log_event(buf, description_event)
 {
-  buf+= description_event->common_header_len;
+  buf+= description_event->common_header_len +
+    description_event->post_header_len[INTVAR_EVENT-1];
   type= buf[I_TYPE_OFFSET];
   val= uint8korr(buf+I_VAL_OFFSET);
 }
@@ -4957,7 +4975,8 @@ Rand_log_event::Rand_log_event(const cha
                                const Format_description_log_event* description_event)
   :Log_event(buf, description_event)
 {
-  buf+= description_event->common_header_len;
+  buf+= description_event->common_header_len +
+    description_event->post_header_len[RAND_EVENT-1];
   seed1= uint8korr(buf+RAND_SEED1_OFFSET);
   seed2= uint8korr(buf+RAND_SEED2_OFFSET);
 }
@@ -5061,7 +5080,8 @@ Xid_log_event(const char* buf,
               const Format_description_log_event *description_event)
   :Log_event(buf, description_event)
 {
-  buf+= description_event->common_header_len;
+  buf+= description_event->common_header_len +
+    description_event->post_header_len[XID_EVENT-1];
   memcpy((char*) &xid, buf, sizeof(xid));
 }
 
@@ -5207,7 +5227,8 @@ User_var_log_event(const char* buf,
                    const Format_description_log_event* description_event)
   :Log_event(buf, description_event)
 {
-  buf+= description_event->common_header_len;
+  buf+= description_event->common_header_len +
+    description_event->post_header_len[XID_EVENT-1];
   name_len= uint4korr(buf);
   name= (char *) buf + UV_NAME_LEN_SIZE;
   buf+= UV_NAME_LEN_SIZE + name_len;

=== modified file 'sql/log_event.h'
--- a/sql/log_event.h	2008-09-29 05:36:42 +0000
+++ b/sql/log_event.h	2009-01-08 14:28:45 +0000
@@ -227,14 +227,20 @@ struct sql_ex_info
 #define QUERY_HEADER_MINIMAL_LEN     (4 + 4 + 1 + 2)
 // where 5.0 differs: 2 for len of N-bytes vars.
 #define QUERY_HEADER_LEN     (QUERY_HEADER_MINIMAL_LEN + 2)
+#define STOP_HEADER_LEN      0
 #define LOAD_HEADER_LEN      (4 + 4 + 4 + 1 +1 + 4)
+#define SLAVE_HEADER_LEN     0
 #define START_V3_HEADER_LEN     (2 + ST_SERVER_VER_LEN + 4)
 #define ROTATE_HEADER_LEN    8 // this is FROZEN (the Rotate post-header is frozen)
+#define INTVAR_HEADER_LEN      0
 #define CREATE_FILE_HEADER_LEN 4
 #define APPEND_BLOCK_HEADER_LEN 4
 #define EXEC_LOAD_HEADER_LEN   4
 #define DELETE_FILE_HEADER_LEN 4
+#define RAND_HEADER_LEN        0
+#define USER_VAR_HEADER_LEN    0
 #define FORMAT_DESCRIPTION_HEADER_LEN (START_V3_HEADER_LEN+1+LOG_EVENT_TYPES)
+#define XID_HEADER_LEN         0
 #define ROWS_HEADER_LEN        8
 #define TABLE_MAP_HEADER_LEN   8
 #define EXECUTE_LOAD_QUERY_EXTRA_HEADER_LEN (4 + 4 + 4 + 1)

Thread
bzr commit into mysql-5.1 branch (sven:2711) Bug#41961Sven Sandberg8 Jan