• unknown's avatar
    BUG#31168: @@hostname does not replicate · 6aa51ac0
    unknown authored
    Problem: in mixed and statement mode, a query that refers to a
    system variable will use the slave's value when replayed on
    slave. So if the value of a system variable is inserted into a
    table, the slave will differ from the master.
    Fix: mark statements that refer to a system variable as "unsafe",
    meaning they will be replicated by row in mixed mode and produce a warning
    in statement mode. There are some exceptions: some variables are actually
    replicated. Those should *not* be marked as unsafe.
    BUG#34732: mysqlbinlog does not print default values for auto_increment variables
    Problem: mysqlbinlog does not print default values for some variables,
    including auto_increment_increment and others. So if a client executing
    the output of mysqlbinlog has different default values, replication will
    be wrong.
    Fix: Always print default values for all variables that are replicated.
    I need to fix the two bugs at the same time, because the test cases would
    fail if I only fixed one of them.
    
    
    include/m_ctype.h:
      Added definition of ILLEGAL_CHARSET_INFO_NUMBER. We just need a symbol
      for a number that will never be used by any charset. ~0U should be safe
      since charset numbers are sequential, starting from 0.
    mysql-test/include/commit.inc:
      Upated test to avoid making statements unsafe.
    mysql-test/r/commit_1innodb.result:
      Updated test needs updated result file.
    mysql-test/r/mysqlbinlog.result:
      Updated result file.
    mysql-test/r/mysqlbinlog2.result:
      Updated result file.
    mysql-test/r/user_var-binlog.result:
      Updated result file.
    mysql-test/suite/binlog/r/binlog_base64_flag.result:
      Updated result file.
    mysql-test/suite/binlog/r/binlog_stm_ctype_ucs.result:
      Updated result file.
    mysql-test/suite/binlog/r/binlog_unsafe.result:
      Modified test file needs modified result file.
    mysql-test/suite/binlog/t/binlog_base64_flag.test:
      Need to filter out pseudo_thread_id from result since it is
      nondeterministic.
    mysql-test/suite/binlog/t/binlog_unsafe.test:
      Add tests that using variables is unsafe. The 'CREATE VIEW' tests didn't
      make sense, so I removed them. SHOW WARNINGS is not necessary either,
      because we get warnings for each statement in the result file.
    mysql-test/suite/rpl/r/rpl_row_mysqlbinlog.result:
      Updated result file.
    mysql-test/suite/rpl/r/rpl_skip_error.result:
      Updated result file.
    mysql-test/suite/rpl/t/rpl_skip_error.test:
      The test used @@server_id, which is not safe to replicate, so it would
      have given a warning. The way it used @@server_id was hackish (issue a
      query on master that removes rows only on master), so I replaced it by a
      more robust way to do the same thing (connect to slave and insert the
      rows only there).
      Also clarified what the test case does.
    mysql-test/t/mysqlbinlog2.test:
      Use --short-form instead of manually filtering out nondeterministic stuff
      from mysqlbinlog (because we added the nondeterministic @@pseudo_thread_id
      to the output).
    sql/item_func.cc:
      Added method of Item_func_get_system_var that indicates whether the given
      system variable will be written to the binlog or not.
    sql/item_func.h:
      Added method of Item_func_get_system_var that indicates whether the given
      system variable will be written to the binlog or not.
    sql/log_event.cc:
       - auto_increment_offset was not written to the binlog if
      auto_increment_increment=1
       - mysqlbinlog did not output default values for some variables
      (BUG#34732). In st_print_event_info, we remember for each variable whether
      it has been printed or not. This is achieved in different ways for
      different variables:
          - For auto_increment_*, lc_time_names, charset_database_number,
            we set the default values in st_print_event_info to something
            illegal, so that it will look like they have changed the first time
            they are seen.
          - For charset, sql_mode, pseudo_thread_id, we add a flag to
            st_print_event_info which indicates whether the variable has been
            printed.
          - Since pseudo_thread_id is now printed more often, and its value is
            not guaranteed to be constant across different runs of the same
            test script, I replaced it by a constant if --short-form is used.
       - Moved st_print_event_info constructor from log_event.h to log_event.cc,
      since it now depends on ILLEGAL_CHARSET_NUMBER, which is defined in
      m_ctype.h, which is better to include from a .cc file than from a header
      file.
    sql/log_event.h:
      Added fields to st_print_event_info that indicate whether some of the
      variables have been written or not. Since the initialization of
      charset_database_number now depends on ILLEGAL_CHARSET_INFO_NUMBER, which
      is defined in a header file, which we'd better not include from this
      header file -- I moved the constructor from here to log_event.cc.
    sql/set_var.cc:
      System variables now have a flag binlog_status, which indicates if they
      are written to the binlog. If nothing is specified, all variables are
      marked as not written to the binlog (NOT_IN_BINLOG) when created. In this
      file, the variables that are written to the binlog are marked with
      SESSION_VARIABLE_IN_BINLOG.
    sql/set_var.h:
      Added flag binlog_status to class sys_var. Added a getter and a
      constructor parameter that sets it.
      Since I had to change sys_var_thd_enum constructor anyways, I simplified
      it to use default values of arguments instead of three copies of the
      constructor.
    sql/sql_yacc.yy:
      Mark statements that refer to a system variable as "unsafe",
      meaning they will be replicated by row in mixed mode. Added comment to
      explain strange piece of code just above.
    mysql-test/include/diff_tables.inc:
      New auxiliary test file that tests whether two tables (possibly one on
      master and one on slave) differ.
    mysql-test/suite/rpl/r/rpl_variables.result:
      New test case needs new result file.
    mysql-test/suite/rpl/r/rpl_variables_stm.result:
      New test file needs new result file.
    mysql-test/suite/rpl/t/rpl_variables.test:
      Test that INSERT of @@variables is replicated correctly (by switching to
      row-based mode).
    mysql-test/suite/rpl/t/rpl_variables_stm.test:
      Test that replication of @@variables which are replicated explicitly works
      as expected in statement mode (without giving warnings).
    6aa51ac0
set_var.h 40.6 KB