List:Internals« Previous MessageNext Message »
From:Mats Kindahl Date:April 21 2005 5:34am
Subject:bk commit into 5.1 tree (mats:1.1803)
View as plain text  
Below is the list of changes that have just been committed into a local
5.1 repository of mats. When mats does a push these changes will
be propagated to the main repository and, within 24 hours after the
push, to the public repository.
For information on how to access the public repository
see http://dev.mysql.com/doc/mysql/en/installing-source-tree.html

ChangeSet
  1.1803 05/04/21 07:34:06 mats@stripped +2 -0
  Merge mysql.com:/home/bk/w1012-bis-mysql-5.1
  into mysql.com:/home/bk/w1012-mysql-5.1

  sql/log_event.h
    1.110 05/04/21 07:34:04 mats@stripped +0 -0
    Auto merged

  sql/log_event.cc
    1.172 05/04/21 07:34:04 mats@stripped +0 -0
    Auto merged

# This is a BitKeeper patch.  What follows are the unified diffs for the
# set of deltas contained in the patch.  The rest of the patch, the part
# that BitKeeper cares about, is below these diffs.
# User:	mats
# Host:	romeo.kindahl.net
# Root:	/home/bk/w1012-mysql-5.1/RESYNC

--- 1.171/sql/log_event.cc	2005-04-15 11:35:38 +02:00
+++ 1.172/sql/log_event.cc	2005-04-21 07:34:04 +02:00
@@ -4742,7 +4742,7 @@
     m_rows_buf(my_malloc(1024 * sizeof(*m_rows_buf), MYF(MY_WME))),
     m_rows_cur(m_rows_buf),
     m_rows_end(m_rows_buf + 1024),
-    m_rows_flags(0)
+    m_flags(0)
 {
 }
 #endif
@@ -4766,8 +4766,8 @@
   m_table_id = uint4korr(post_begin + RW_MAPID_OFFSET);
   DBUG_PRINT("info",("m_table_id=%d", m_table_id));
 
-  m_rows_flags = uint2korr(post_begin + RW_FLAGS_OFFSET);
-  DBUG_PRINT("info",("m_rows_flags=%d", m_rows_flags));
+  m_flags = uint2korr(post_begin + RW_FLAGS_OFFSET);
+  DBUG_PRINT("info",("m_flags=%d", m_flags));
   
   byte const* const var_begin = post_begin + ROWS_HEADER_LEN;
 
@@ -4930,18 +4930,48 @@
   }
   do_after_row_operations(table);
 
-  if (m_rows_flags & TRANS_END_F) {
-    // This is the end of a statement, so close (and unlock) the tables we
-    // opened when processing the Table_map_log_event starting the statement.
+  if (m_flags & TRANS_END_F) {
+    // This is the end of a statement or transaction, so close (and unlock)
+    // the tables we opened when processing the Table_map_log_event starting
+    // the statement.
 
     // !!! This will clear *all* mappings, not only those that are open for
-    // !!! the thread. There is not good handle for on-close actions for
+    // !!! the table. There is not good handle for on-close actions for
     // !!! tables.  
     rli->m_table_map.clear_tables();
+
+    DBUG_PRINT("info", ("thd->locked_tables=%p, thd->lock=%p",   
+			thd->locked_tables, thd->lock));
+
+    ha_commit(thd);
     close_thread_tables(thd);
   }
     
-  DBUG_RETURN(error || Log_event::exec_event(rli));
+  /*
+    This is copied from the Log_event::exec_event(). We step the relay log
+    positions ourself, since the generic version does not behave the way we
+    want.
+   */
+  DBUG_PRINT("info", ("TRANS_END_F is %s", 
+		      (m_flags & TRANS_END_F) ? "set" : "clear"));
+  DBUG_PRINT("info", ("OPTION_BEGIN is %s", 
+		      (thd->options & OPTION_BEGIN) ? "set" : "clear"));
+  if ((thd->options & OPTION_BEGIN) 
+      || !(m_flags & TRANS_END_F))
+  {
+    DBUG_PRINT("info", ("calling inc_event_relay_log_pos()"));
+    rli->inc_event_relay_log_pos();
+  }
+  else
+  {
+    DBUG_PRINT("info", ("calling inc_group_relay_log_pos() "
+			"and flush_relay_log_info()"));
+    rli->inc_group_relay_log_pos(0);
+    flush_relay_log_info(rli);
+    rli->last_master_timestamp= when;
+  }
+
+  DBUG_RETURN(error);
 }
 #endif // HAVE_REPLICATION
 #endif // MYSQL_CLIENT
@@ -4954,7 +4984,7 @@
   DBUG_PRINT("info", ("writing MAPID %d (4 bytes)", m_table_id));
   int4store(buf + RW_MAPID_OFFSET, m_table_id);
   DBUG_PRINT("info", ("writing FLAGS %d (2 bytes)", m_table_id));
-  int2store(buf + RW_FLAGS_OFFSET, m_rows_flags);
+  int2store(buf + RW_FLAGS_OFFSET, m_flags);
   bool result = my_b_safe_write(file, buf, ROWS_HEADER_LEN);
   DBUG_RETURN(result);
 }
@@ -4996,7 +5026,7 @@
  */
 #ifndef MYSQL_CLIENT
 Table_map_log_event::
-Table_map_log_event(THD* thd, TABLE* tbl, ulong tid)
+Table_map_log_event(THD* thd, TABLE* tbl, ulong tid, uint16 flags)
   : Log_event(thd, 0, tbl->file->has_transactions()), 
     m_table(tbl),
     m_dbnam(tbl->s->db), 
@@ -5005,7 +5035,8 @@
     m_tbllen(strlen(m_tblnam)),
     m_colcnt(tbl->s->fields), m_coltype(0),
     m_memory(0),
-    m_table_id(tid)
+    m_table_id(tid),
+    m_flags(flags)
 {
   DBUG_ENTER("Table_map_log_event::Table_map_log_event(THD*,...)");
 
@@ -5055,6 +5086,9 @@
 
   m_table_id = uint4korr(post_start + TM_MAPID_OFFSET);
 
+  m_flags = uint2korr(post_start + TM_FLAGS_OFFSET);
+  DBUG_PRINT("info",("m_flags=%d", m_flags));
+  
   /* Read the variable part of the event */
   const char* const vpart = post_start + TABLE_MAP_HEADER_LEN;
 
@@ -5107,6 +5141,65 @@
 
 #ifndef MYSQL_CLIENT
 #ifdef HAVE_REPLICATION
+/*
+  Find a table based on database name and table name. 
+
+  DESCRIPTION
+
+    Currently, only the first table of the 'table_list' is located. If the
+    table is found in the list of open tables for the thread, the 'table'
+    field of 'table_list' is filled in.
+
+  PARAMETERS
+
+    thd        Thread structure
+    table_list List of tables to locate in the thd->open_tables list.
+    count      Pointer to count variable that will be set to the number of
+               tables found.  If the pointer is NULL, nothing will be stored.
+
+  RETURN VALUE
+
+    The number of tables found.
+
+  TO DO
+
+    Replace the list of table searches with a hash based on the combined
+    database and table name.  The handler_tables_hash is inappropriate since
+    it hashes on the table alias.  At the same time, the function can be
+    extended to handle a full list of table names, in the same spirit as
+    open_tables() and lock_tables().
+*/
+static unsigned int
+find_tables(THD* thd, TABLE_LIST* table_list, unsigned int *count)
+{
+  DBUG_ENTER("find_tables(THD*, TABLE_LIST*, unsigned int*)");
+
+  unsigned int result = 0;
+
+  DBUG_PRINT("enter", ("table_list->db='%s', table_list->table_name='%s'", 
+		       table_list->db, table_list->table_name))
+
+  for (TABLE* table= thd->open_tables; table ; table= table->next) 
+  {
+    DBUG_PRINT("info", ("Looking at %p [ db='%s', table_name='%s' ]", 
+			table, table->s->db, table->s->table_name))
+    if (strcmp(table->s->db, table_list->db) == 0 
+	&& strcmp(table->s->table_name, table_list->table_name) == 0)
+    {
+      // Copy the table pointer into the table list.
+      table_list->table = table;
+      result = 1;
+      break;
+    }
+  }
+
+  if (count)
+    *count = result;
+
+  DBUG_PRINT("return", ("result=%d", result));
+  DBUG_RETURN(result);
+}
+
 int Table_map_log_event::
 exec_event(st_relay_log_info* rli)
 {
@@ -5119,17 +5212,47 @@
   thd->query_id = next_query_id();
   pthread_mutex_unlock(&LOCK_thread_count);
 
-  // Open and lock the table
+  /*
+    Open the table if it is not already open and lock it afterwards.
+  */
   TABLE_LIST table_list;
   memset(&table_list, 0, sizeof(table_list));
   table_list.db = const_cast<char*>(m_dbnam);
   table_list.alias = table_list.table_name = const_cast<char*>(m_tblnam);
-  if (open_ltable(thd, &table_list, TL_WRITE) == NULL)
-    DBUG_RETURN(1);		// Failed to open and lock table
+  table_list.lock_type = TL_WRITE;
+  table_list.next_global = table_list.next_local = 0;
+
+  unsigned int count = 1;
+  TABLE_LIST* tables = &table_list;
+  if (find_tables(thd, &table_list, NULL) == 0) 
+  {
+    open_tables(thd, &tables, &count);
+  } 
+  lock_tables(thd, &table_list, count);
+  DBUG_PRINT("info", ("thd->locked_tables=%p, thd->lock=%p",   
+		      thd->locked_tables, thd->lock));
+
+  /*
+    Now we have opened and locked the table. Now we can change the state of
+    the instance and update the values.
+  */
   m_table = table_list.table;
 
   int error = rli->m_table_map.set_table(m_table_id, m_table);
-  DBUG_RETURN(error || Log_event::exec_event(rli));
+
+  /* 
+     We explicitly do not call Log_event::exec_event() here since we do not
+     want the relay log position to be flushed to disk. The flushing will be
+     done by the last Rows_log_event that either ends a statement (outside a
+     transaction) or a transaction.
+
+     A table map event can *never* end a transaction or a statement, so we
+     just step the relay log position.
+   */
+
+  rli->inc_event_relay_log_pos();
+
+  DBUG_RETURN(error);
 }
 #endif // HAVE_REPLICATION
 #endif // !MYSQL_CLIENT
@@ -5141,7 +5264,10 @@
   DBUG_ENTER("Table_map_log_event::write_data_header(IO_CACHE*)");
 
   byte buf[TABLE_MAP_HEADER_LEN];
+  DBUG_PRINT("info", ("writing MAPID %d (4 bytes)", m_table_id));
   int4store(buf + TM_MAPID_OFFSET, m_table_id);
+  DBUG_PRINT("info", ("writing FLAGS %d (2 bytes)", m_table_id));
+  int2store(buf + TM_FLAGS_OFFSET, m_flags);
 
   DBUG_RETURN(my_b_safe_write(file, buf, TABLE_MAP_HEADER_LEN));
 }
@@ -5344,11 +5470,6 @@
   {
     DBUG_PRINT("info", ("Fetching row by scanning table"));
 
-#if 0    // Save the position
-    table->file->position(record_buf);
-    byte* const last_rowid = table->file->ref;
-#endif
-
     // Continue until we find the right record or have made a full loop
     do
     {
@@ -5365,13 +5486,6 @@
 	  return error;
 	}
       }    
-
-#if 0
-      // Check if we've scanned the entire table.
-      table->file->position(record_buf);
-      if (table->file->cmp_ref(last_rowid, table->file->ref) == 0)
-	return HA_ERR_END_OF_FILE;
-#endif
     }
     while (record_compare(table, table->record[0], record_buf) != 0);
   }
@@ -5496,14 +5610,14 @@
  
   if (int error = find_and_fetch_row(table, m_key, m_search_record))
   {
-    DBUG_PRINT("return", ("error = %d", error));
+    DBUG_PRINT("return", ("error=%d", error));
     DBUG_RETURN(error);
   }
     
   // Now we should have the right row to delete
   int const error = table->file->ha_delete_row(m_search_record);
 
-  DBUG_PRINT("return", ("error = %d", error));
+  DBUG_PRINT("return", ("error=%d", error));
   DBUG_RETURN(error);
 }
 #endif // !defined(MYSQL_CLIENT) && defined(HAVE_REPLICATION)
@@ -5625,7 +5739,7 @@
 
   if (int error = find_and_fetch_row(table, m_key, m_search_record))
   {
-    DBUG_PRINT("return", ("error = %d", error));
+    DBUG_PRINT("return", ("error=%d", error));
     DBUG_RETURN(error);
   }
     
@@ -5633,7 +5747,7 @@
   int const error = table->file->ha_update_row(table->record[0], 
 					       table->record[1]);
 
-  DBUG_PRINT("return", ("error = %d", error));
+  DBUG_PRINT("return", ("error=%d", error));
   DBUG_RETURN(error);
 }
 #endif // !defined(MYSQL_CLIENT) && defined(HAVE_REPLICATION)

--- 1.109/sql/log_event.h	2005-04-15 11:35:38 +02:00
+++ 1.110/sql/log_event.h	2005-04-21 07:34:04 +02:00
@@ -204,7 +204,7 @@
 #define DELETE_FILE_HEADER_LEN 4
 #define FORMAT_DESCRIPTION_HEADER_LEN (START_V3_HEADER_LEN+1+LOG_EVENT_TYPES)
 #define ROWS_HEADER_LEN        6
-#define TABLE_MAP_HEADER_LEN   4
+#define TABLE_MAP_HEADER_LEN   6
 #define EXECUTE_LOAD_QUERY_EXTRA_HEADER_LEN (4 + 4 + 4 + 1)
 #define EXECUTE_LOAD_QUERY_HEADER_LEN  (QUERY_HEADER_LEN + EXECUTE_LOAD_QUERY_EXTRA_HEADER_LEN)
 
@@ -299,6 +299,7 @@
 
 /* TM = "Table Map" */
 #define TM_MAPID_OFFSET    0
+#define TM_FLAGS_OFFSET    4
 
 /* RW = "RoWs" */
 #define RW_MAPID_OFFSET    0
@@ -1623,8 +1624,21 @@
     TYPE_CODE = TABLE_MAP_EVENT
   };
 
+  enum enum_flags {
+    NO_FLAGS = 0U,
+    TRANS_BEG_F = (1 << 0)	// First event of a transaction
+  };
+
+  void set_flag(enum_flags flag) { 
+    m_flags |= flag; 
+  }
+
+  void clear_flag(enum_flags flag) { 
+    m_flags &= ~flag; 
+  }
+
 #ifndef MYSQL_CLIENT
-  Table_map_log_event(THD *thd, TABLE* tbl, ulong tid);
+  Table_map_log_event(THD *thd, TABLE* tbl, ulong tid, uint16 flags);
 #endif
   Table_map_log_event(const char* buf, uint event_len, 
                       const Format_description_log_event *description_event);
@@ -1663,6 +1677,7 @@
 
   gptr           m_memory;
   ulong          m_table_id;
+  uint16         m_flags;
 
   size_t         m_data_size;
   ulong          m_thread_id;
@@ -1698,18 +1713,18 @@
 {
 public:
   enum enum_flags {
-    STMT_END_F  = (1 << 0),	// Last event of a statement
-    TRANS_END_F = (1 << 1)	// Last event of a transaction
+    NO_FLAGS = 0U,
+    TRANS_END_F = (1U << 0)	// Last event of a transaction
   };
 
   virtual ~Rows_log_event();
 
-  void set_flags(enum_flags flags) { 
-    m_rows_flags |= flags; 
+  void set_flag(enum_flags flags) { 
+    m_flags |= flags; 
   }
 
-  void clear_flags(enum_flags flags) { 
-    m_rows_flags &= ~flags; 
+  void clear_flag(enum_flags flags) { 
+    m_flags &= ~flags; 
   }
 
 #ifndef MYSQL_CLIENT
@@ -1772,7 +1787,7 @@
   byte* m_rows_cur;		// One-after the end of the data
   byte* m_rows_end;		// One-after the end of the allocated space
 
-  uint16 m_rows_flags;		// Flags for row-level events
+  uint16 m_flags;		// Flags for row-level events
 
 private:
 #ifndef MYSQL_CLIENT
Thread
bk commit into 5.1 tree (mats:1.1803)Mats Kindahl21 Apr