Commit Graph

199187 Commits

Author SHA1 Message Date
a89e734fcb ColumnStore 6.4.10-1 2025-01-29 10:44:18 +01:00
d0c2a007ee C/C 3.3.14 2025-01-29 10:44:18 +01:00
17e31abd8b compilation failure on CentOS 7 2025-01-29 10:44:02 +01:00
38d3b6027b MDEV-35943 ASAN errors in Query_arena::free_items / fill_schema_table_from_frm
shouldn't try to close the table if open failed.

followup for deb20fb751
2025-01-29 10:43:34 +01:00
03d2328785 MDEV-35944 DELETE fails to notice transaction abort, violating ACID
Process errors of read_record().

Also, add an assert that Marko requested
2025-01-29 10:43:29 +01:00
d5e7bce14b MDEV-35966 galera.galera_as_master crashes in debug builds
innobase_commit(): When Galera is used with SET SQL_LOG_BIN=OFF,
some debug assertions that had been added in
commit ddd7d5d8e3 (MDEV-24035)
would fail. Let us relax those assertions for Galera transactions,
to allow an implicit commit after an internally executed XA PREPARE.

Note that trx_undo_report_row_operation() only allows undo log records
to be added to ACTIVE transactions (not after XA PREPARE). Hence, this
relaxation should be safe with respect to writes.
2025-01-29 10:42:57 +01:00
3cfffb4de6 MDEV-35962 CREATE INDEX fails to heal a FOREIGN KEY constraint
commit_cache_norebuild(): Replace any newly added indexes in
the attached foreign key constraints.
2025-01-29 09:04:50 +02:00
831f5bc66f MDEV-33978 P_S.THREADS is not showing all server threads
page_encrypt_thread_key: The key for fil_crypt_thread().

All other InnoDB threads should already have been registered for
performance_schema ever since
commit a2f510fccf
2025-01-27 12:08:30 +02:00
d77b9a4925 MDEV-34355: rpl.rpl_semi_sync_no_missed_ack_after_add_slave ‘server_3 should have sent…’
MDEV-35477 incorrectly reverted the original test fix of MDEV-34355,
thinking it superseded that fix. It is still needed though. Pasting
the content of the original patch’s commit message, as it is still
relevant (and the method to reproduce the test failure still works).

“””
The problem is that the test could query the status variable
Rpl_semi_sync_slave_send_ack before the slave actually updated it.
This would result in an immediate --die assertion killing the rest
of the test. The bottom of this commit message has a small patch
that can be applied to reproduce the test failure.

This patch fixes the test failure by waiting for the variable to be
updated before querying its value.

diff --git a/sql/semisync_slave.cc b/sql/semisync_slave.cc
index 9ddd4c5c8d7..60538079fce 100644
--- a/sql/semisync_slave.cc
+++ b/sql/semisync_slave.cc
@@ -303,7 +303,10 @@ int Repl_semi_sync_slave::slave_reply(Master_info *mi)
     reply_res= DBUG_EVALUATE_IF("semislave_failed_net_flush", 1,
                                 net_flush(net));
     if (!reply_res)
+    {
+      sleep(1);
       rpl_semi_sync_slave_send_ack++;
+    }
   }
   DBUG_RETURN(reply_res);
 }
“””
2025-01-25 11:05:32 -07:00
72e1cc8f52 MDEV-35806: Error in read_log_event() corrupts relay log writer, crashes server
In Log_event::read_log_event(), don't use IO_CACHE::error of the relay log's
IO_CACHE to signal an error back to the caller. When reading the active
relay log, this flag is also being used by the IO thread, and setting it can
randomly cause the IO thread to wrongly detect IO error on writing and
permanently disable the relay log.

This was seen sporadically in test case rpl.rpl_from_mysql80. The read
error set by the SQL thread in the IO_CACHE would be interpreted as a
write error by the IO thread, which would cause it to throw a fatal
error and close the relay log. And this would later cause CHANGE
MASTER to try to purge a closed relay log, resulting in nullptr crash.

SQL thread is not able to parse an event read from the relay log. This
can happen like here when replicating unknown events from a MySQL master,
potentially also for other reasons.

Also fix a mistake in my_b_flush_io_cache() introduced back in 2001
(fa09f2cd7e) where my_b_flush_io_cache() could wrongly return an error set
in IO_CACHE::error, even if the flush operation itself succeeded.

Also fix another sporadic failure in rpl.rpl_from_mysql80 where the outout
of MASTER_POS_WAIT() depended on timing of SQL and IO thread.

Reviewed-by: Monty <monty@mariadb.org>
Reviewed-by: Andrei Elkin <andrei.elkin@mariadb.com>
Signed-off-by: Kristian Nielsen <knielsen@knielsen-hq.org>
2025-01-24 09:15:20 +00:00
2543be6942 MDEV-35854: Clarify row_rename_table_for_mysql()
enum rename_fk: Replaces the "bool use_fk" parameter of
row_rename_table_for_mysql() and innobase_rename_table():

RENAME_IGNORE_FK: Replaces use_fk=false when the operation cannot
involve any FOREIGN KEY constraints, that is, it is a partitioned
table or an internal table for FULLTEXT INDEX.

RENAME_REBUILD: Replaces use_fk=false when the table may contain
FOREIGN KEY constraints, which must not be modified in the data
dictionary tables SYS_FOREIGN and SYS_FOREIGN_COLS.

RENAME_ALTER_COPY: Replaces use_fk=true. This is only specified
in ha_innobase::rename_table(), which may be invoked as part of
ALTER TABLE…ALGORITHM=COPY, but also during RENAME TABLE.

An alternative value RENAME_FK could be useful to specify in
ha_innobase::rename_table() when it is executed as part of
CREATE OR REPLACE TABLE, which currently is not an atomic operation.

Reviewed by: Debarun Banerjee
2025-01-23 14:38:35 +02:00
d4da659b43 MDEV-35854: Simplify dict_get_referenced_table()
innodb_convert_name(): Convert a schema or table name to
my_charset_filename compatible format.

dict_table_lookup(): Replaces dict_get_referenced_table().
Make the callers responsible for invoking innodb_convert_name().

innobase_casedn_str(): Remove. Let us invoke my_casedn_str() directly.

dict_table_rename_in_cache(): Do not duplicate a call to
dict_mem_foreign_table_name_lookup_set().

innobase_convert_to_filename_charset(): Defined static in the only
compilation unit that needs it.

dict_scan_id(): Remove the constant parameters
table_id=FALSE, accept_also_dot=TRUE. Invoke strconvert() directly.

innobase_convert_from_id(): Remove; only called from dict_scan_id().

innobase_convert_from_table_id(): Remove (dead code).

table_name_t::dblen(), table_name_t::basename(): In non-debug builds,
tolerate names that may miss a '/' separator.

Reviewed by: Debarun Banerjee
2025-01-23 14:38:08 +02:00
fa74c1a40f Non partitioned table could be marked as partitioned in ddl.log
partion_engine_name was not reset when looping over tables in
mysql_rm_table_no_locks.

This could cause maria_backup to think that at normal droped
table was partitioned.

This issue was discovered in 11.8 as part of atomic created and replace
and only the fix was backported.
2025-01-21 19:21:06 +02:00
c05e7c4e0e MDEV-35708 lock_rec_get_prev() returns only the first record lock
It's supposed that the function gets the previous lock set on a record.
But if there are several locks set on a record, it will return only the
first one. Continue locks list iteration till the certain lock even if
the certain bit in lock bitmap is set.
2025-01-20 12:03:50 +03:00
98dbe3bfaf Merge 10.5 into 10.6 2025-01-20 09:57:37 +02:00
8d6c9ef001 MDEV-34925 Fix segv on thd in spider recovery.
Create temporary thd whenever needed in spider xa commit / recovery.
This prevents crash during recovery.
2025-01-20 10:50:45 +11:00
cbb24d9aa5 MDEV-35646: Limit pseudo_thread_id to UINT32_MAX
Although the `my_thread_id` type is 64 bits, binlog format specs
limits it to 32 bits in practice. (See also: MDEV-35706)

The writable SQL variable `pseudo_thread_id` didn’t realize this though
and had a range of `ULONGLONG_MAX` (at least `UINT64_MAX` in C/C++).
It consequentially accepted larger values silently, but only the lower
32 bits of whom gets binlogged; this could lead to inconsistency.

Reviewed-by: Brandon Nesterenko <brandon.nesterenko@mariadb.com>
2025-01-18 17:27:54 -07:00
782c4b94f0 MDEV-25654 only force HA_KEY_ALG_HASH for fast alter partition
not for any ALTER TABLE without ALTER_CHANGE_COLUMN.

This fixes galera_sr.MDEV-28971 test

followup for 0dcd30197a
2025-01-18 15:11:12 +01:00
b1f57a98a8 cleanup: Alter_table_ctx::Alter_table_ctx() 2025-01-18 15:07:53 +01:00
b87c1b06dc MDEV-29968 update test results
followup for 350cc77fee
2025-01-18 08:10:49 +01:00
a69da0c31e MDEV-19761 Before Trigger not processed for Not Null Columns if no explicit value and no DEFAULT
it's incorrect to zero out table->triggers->extra_null_bitmap
before a statement, because if insert uses an explicit field list
and omits a field that has no default value, the field should
get NULL implicitly. So extra_null_bitmap should have 1s for all
fields that have no defaults

* create extra_null_bitmap_init and initialize it as above
* copy extra_null_bitmap_init to extra_null_bitmap for inserts
* still zero out extra_null_bitmap for updates/deletes where
  all fields definitely have a value
* make not_null_fields_have_null_values() to send
  ER_NO_DEFAULT_FOR_FIELD for fields with no default and no value,
  otherwise creation of a trigger with an empty body would change the
  error message
2025-01-17 23:42:56 +01:00
350cc77fee MDEV-29968 Functions in default values in tables with some character sets break SHOW CREATE (and mysqldump)
Item:print_for_table_def() uses QT_TO_SYSTEM_CHARSET to print
the DEFAULT expression into FRM file during CREATE TABLE.
Therefore, the expression is encoded in utf8 in FRM.

get_field_default_value() erroneously used field->charset() to
print the DEFAULT expression at SHOW CREATE TABLE time.

Fixing get_field_default_value() to use &my_charset_utf8mb4_general_ci instead.
This makes DEFAULT work in the way way with:

- virtual column expressions:

    if (field->vcol_info)
    {
      StringBuffer<MAX_FIELD_WIDTH> str(&my_charset_utf8mb4_general_ci);
      field->vcol_info->print(&str);

- check constraint expressions:

    if (field->check_constraint)
    {
      StringBuffer<MAX_FIELD_WIDTH> str(&my_charset_utf8mb4_general_ci);
      field->check_constraint->print(&str);

Additional cleanup:
Fixing system_charset_info to &my_charset_utf8mb4_general_ci in a few
places to make non-BMP characters work in DEFAULT, virtual column,
check constraint expressions.
2025-01-17 15:39:55 +04:00
f521b8ac21 MDEV-35723: applying non-zero offset to null pointer in INSERT
row_mysql_read_blob_ref(): Correctly handle what Field_blob::store()
generates for length=0.
2025-01-17 12:34:03 +02:00
c69fb1a627 MDEV-35864 UBSAN: "applying zero offset to null pointer" when using a Field_set with empty values
The val_buffer variable can come to Field_set::val_str()
with the Ptr member equal to nullptr. This caused UBSAN errors
"applying zero offset to null pointer" in my_strnncollsp_simple()
and other strnncollsp() virtual implementations. Fixing the code to
make sure its Ptr is not equal to nullptr.
2025-01-17 14:05:48 +04:00
df602ff7fa Fix main.stack on Windows
A part of the test, that tests that a frame of recursive SP takes the
same amount of stack, relies on the fact that 3 calls to that
SP are executed in the same OS thread. This is not guaranteed with
threadpool(not with Windows native threadpool, anyway)

Fix the test to execute SP calls in the same thread, as semicolon-separated
batched command.
2025-01-16 23:04:59 +01:00
86b257f870 MDEV-35632 HandlerSocket uses deprecated C++98 auto_ptr
Change uses of auto_ptr to unique_ptr
2025-01-16 11:43:27 -05:00
a6ab0e6c0b MDEV-34898 Doublewrite recovery of innodb_checksum_algorithm=full_crc32 encrypted pages does not work
- Use file_key_management encryption plugin instead of
example_key_management_plugin for the encryption.doublewrite_debug
test case
2025-01-16 18:14:49 +05:30
78157c4765 MDEV-35840 Eliminate -warray-bounds triggered by TABLE_SHARE::db_type()
The warnings are triggered with -O3
2025-01-16 10:48:11 +11:00
0abef37ccd Minor lock_sys cleanup
Let us make some member functions of lock_sys_t non-static
to avoid some shuffling of function parameter registers.

lock_cancel_waiting_and_release(): Declare static, because there
are no external callers.

Reviewed by: Debarun Banerjee
2025-01-15 16:55:29 +02:00
b82abc7163 MDEV-35701 trx_t::autoinc_locks causes unnecessary dynamic memory allocation
trx_t::autoinc_locks: Use small_vector<lock_t*,4> in order to avoid any
dynamic memory allocation in the most common case (a statement is
holding AUTO_INCREMENT locks on at most 4 tables or partitions).

lock_cancel_waiting_and_release(): Instead of removing elements from
the middle, simply assign nullptr, like lock_table_remove_autoinc_lock().

The added test innodb.auto_increment_lock_mode covers the dynamic memory
allocation as well as nondeterministically (occasionally) covers
the out-of-order lock release in lock_table_remove_autoinc_lock().

Reviewed by: Debarun Banerjee
2025-01-15 16:55:01 +02:00
a5174aaffb MDEV-35828: Assertion fails in alloc_root() when memory causes it to call itself
(Variant 2: use stack for buffers)
my_malloc_size_cb_func() has a call to thd->alloc() to produce an error message.
thd->alloc() calls alloc_root(), so one can end up with this stack trace:

  alloc_root()
  THD::alloc()
  my_malloc_size_cb_func()
  my_malloc()
  alloc_root()

where alloc_root() calls itself. This is a problem, as alloc_root() is not
reenterable.

Fixed this by switching my_malloc_size_cb_func() to use space on the stack
instead.
2025-01-15 12:34:25 +02:00
0fa1a7cc6a MDEV-28130 MariaDB SEGV issue at tree_search_next
In case of error last_pos points to null_element and there is no any
other children. tree_search_next() walks the children from last_pos
until the leaves (null_element) ignoring the case the topmost parent
in search state is the leaf itself.
2025-01-14 18:56:14 +03:00
ab90eaad79 MDEV-22695 Server crashes in heap_rnext upon DELETE from a HEAP table
Quick read record uses different handler (H1) for finding records. It
cannot use ha_delete_row() handler (H2) as it is different search
mode: inited == INDEX for H1, inited == RND for H2. So, read handler
H1 uses index while write handler H2 uses random access.

For going next record in H1 there is info->last_pos optimization for
stepping index via tree_search_next(). This optimization can work with
deleted rows only if delete is conducted in the same handler, there
is:

67      int hp_rb_delete_key(HP_INFO *info, register HP_KEYDEF *keyinfo,
68                         const uchar *record, uchar *recpos, int flag)
69      {
...
74        if (flag)
75          info->last_pos= NULL; /* For heap_rnext/heap_rprev */

But this cannot work for different handler. So, last_pos in H1 after
delete in H2 contains stale info->parents array and last_pos points
into that parents. In the specific test case last_pos' parent is
already freed node and tree_search_next() steps into it.

The fix invalidates local savings of info->parents and info->last_pos
based on key_version. Record deletion increments share->key_version in
H2, so in H1 we know the tree might be changed.

Another good measure would be to use H1 for delete. But this is bigger
refactoring than just bug fixing.
2025-01-14 18:56:13 +03:00
4a58d1085d MDEV-35612 EXCHANGE PARTITION does not work for tables with unique blobs
mysql_compare_tables() failed because of no long hash index generated
fields in prepared tmp_create_info. In comparison we should skip these
fields in the original table by:

  1. skipping INVISIBLE_SYSTEM fields;

  2. getting key_info from table->s instead of table as TABLE_SHARE
     contains unwrapped key_info.
2025-01-14 18:56:13 +03:00
78c192644c MDEV-35343 unexpected replace behaviour when long unique index on
system versioned table

For versioned table REPLACE first tries to insert a row, if it gets
duplicate key error and optimization is possible it does UPDATE +
INSERT history. If optimization is not possible it goes normal branch
for UPDATE to history and repeats the cycle of INSERT.

The failure was in normal branch when we tried UPDATE to history but
such history already exists from previous cycles. There is no such
failures in optimized branch because vers_insert_history_row() already
ignores duplicates.

The fix ignores duplicate errors for UPDATE to history and does DELETE
instead.
2025-01-14 18:56:13 +03:00
e1e1e50bba MDEV-35343 DML debug logging
Usage:

mtr --mysqld=--debug=d,dml,query:i:o,/tmp/dml.log

Example output:

T@6    : dispatch_command: query: insert into t1 values ('a')
T@6    : handler::ha_write_row: exit: INSERT: t1(a) = 0
T@6    : dispatch_command: query: alter ignore table t1 add unique index (data)
T@6    : handler::ha_write_row: exit: INSERT: t1(a) = 0
T@6    : dispatch_command: query: alter ignore table t1 add unique index (data)
T@6    : handler::ha_write_row: exit: INSERT: t1(a) = 0

T@6    : dispatch_command: query: replace into t1 values ('b'), ('c'), ('a'), ('b')
T@6    : handler::ha_write_row: exit: INSERT: t1(b) = 0
T@6    : handler::ha_write_row: exit: INSERT: t1(c) = 0
T@6    : handler::ha_write_row: exit: INSERT: t1(a) = 121
T@6    : write_record: exit: DELETE: t1(a) = 0
T@6    : handler::ha_write_row: exit: INSERT: t1(a) = 0
T@6    : handler::ha_write_row: exit: INSERT: t1(b) = 121
T@6    : write_record: exit: DELETE: t1(b) = 0
T@6    : handler::ha_write_row: exit: INSERT: t1(b) = 0
2025-01-14 18:56:13 +03:00
e760a6dc1c MDEV-35343 ha_heap: recover the cursor after failed ha_update_row 2025-01-14 18:56:13 +03:00
0dcd30197a MDEV-25654 Unexpected ER_CRASHED_ON_USAGE and Assertion
`limit >= trx_id' failed in purge_node_t::skip

For fast alter partition ALTER lost hash fields in frm field
count. mysql_prepare_create_table() did not call add_hash_field()
because the logic of ALTER-ing field types implies automatic
promotion/demotion to/from hash index. So we don't pass hash algorithm
to mysql_prepare_create_table() and let it decide itself, but it
cannot decide it correctly for fast alter partition.

So now mysql_prepare_alter_table() is a bit more sophisticated on what
to pass in the algorithm. If not changed any fields it will force
mysql_prepare_create_table() to re-add hash fields by setting
HA_KEY_ALG_HASH.

The problem with the original logic is mysql_prepare_alter_table()
does not care 100% about hash property so the decision is blurred
between mysql_prepare_alter_table() and mysql_prepare_create_table().
2025-01-14 18:56:13 +03:00
0cf2176b79 MDEV-34033 Exchange partition with virtual columns fails
MDEV-28127 did is_equal() which compared vcol expressions
literally. But another table vcol expression is not equal because of
different table name.

We implement another comparison method is_identical() which respects
different table name in vcol comparison. If any field item points to
table_A and compared field item points to table_B, such items are
treated as equal in (table_A, table_B) comparison. This is done by
cloning table_B expression and renaming any table_B entries to table_A
in it.
2025-01-14 18:56:13 +03:00
92383f8db1 MDEV-26891 Segfault in Field::register_field_in_read_map upon INSERT
DELAYED with virtual columns

Segfault was cause by two different copies of same Field instance in
prepared delayed insert. One was made by
Delayed_insert::get_local_table() (see make_new_field()). That copy
went through parse_vcol_defs() and received new vcol_info->expr.

Another one was made by copy_keys_from_share() by this code:

        /*
          We are using only a prefix of the column as a key:
          Create a new field for the key part that matches the index
        */
        field= key_part->field=field->make_new_field(root, outparam, 0);
        field->field_length= key_part->length;

So, key_part and table got different objects of same field and the
crash was because key_part->field->vcol_info->expr is NULL.

The fix does update_keypart_vcol_info() to update vcol_info->expr in
key_part->field.

Cleanup: memdup_vcol() is static inline instead of macro + check OOM.
2025-01-14 18:56:13 +03:00
d8adc52863 MDEV-22441 SCOPE_VALUE macro for temporary values
- Needless engaged_ removed;
  - SCOPE_VALUE, SCOPE_SET, SCOPE_CLEAR macros for neater declaration;
  - IF_CLASS / IF_NOT_CLASS SFINAE checkers to pass arg by value or
    reference;
  - inline keyword;
  - couple of refactorings of temporary free_list.
2025-01-14 18:56:13 +03:00
52dd489515 MDEV-22441 implement a generic way to change a value of a variable in a scope
Example:
{
  auto _= make_scope_value(var, tmp_value);
}

make_scope_value(): a function which returns RAII object which temporary
changes a value of a variable

detail::Scope_value: actual implementation of such RAII class.
It shouldn't be used directly! That's why it's inside a namespace detail.
2025-01-14 18:54:43 +03:00
b337e14440 WITHOUT_ABI_CHECK
ABI check takes several seconds on compilation. It is not needed in
repetitive build during the development process.
2025-01-14 18:54:43 +03:00
200c235244 MDEV-35429 my_snprintf fixes for 10.5+
* Innobase `os0file.cc`: use `PRIu64` over `llu`
  * These came after I prepared #3485.
* MyISAM `mi_check.c`: in impossible block length warning
  * I missed this one in #3485 (and #3360 too?).
2025-01-14 17:57:51 +11:00
6868d965db MDEV-34825 FreeBSD fails to build under clang natively (postfix)
The fix in MDEV-34825/#3484/dff354e7df2f originally just took the FreeBSD carried
patch of inline ASM as it didn't have the __ppc_get_timebase function.

What clang does have is the __builtin_ppc_get_timebase, which was
replaced in the same commit, which was the fix taken from Alpine.

To reduce complexity - we only need one working function rather
than an equivalent asm implementation.

Noted by Marko, thanks!
2025-01-14 17:20:50 +11:00
d1f2ceee1b MDEV-33064: Sync trx->wsrep state from THD on trx start
Replace trx->wsrep= 0 with an assert in trx_rollback_for_mysql()

Signed-off-by: Julius Goryavsky <julius.goryavsky@mariadb.com>
2025-01-14 02:17:22 +01:00
901c6c7ab6 MDEV-33064: Sync trx->wsrep state from THD on trx start
InnoDB transactions may be reused after committed:
- when taken from the transaction pool
- during a DDL operation execution

In this case wsrep flag on trx object is cleared, which may cause wrong
execution logic afterwards (wsrep-related hooks are not run).

Make trx->wsrep flag initialize from THD object only once on InnoDB transaction
start and don't change it throughout the transaction's lifetime.
The flag is reset at commit time as before.

Unconditionally set wsrep=OFF for THD objects that represent InnoDB background
threads.

Make Wsrep_schema::store_view() operate in its own transaction.

Fix streaming replication transactions' fragments rollback to not switch
THD->wsrep value during transaction's execution
(use THD->wsrep_ignore_table as a workaround).

Signed-off-by: Julius Goryavsky <julius.goryavsky@mariadb.com>
2025-01-14 02:17:22 +01:00
4b0ac5a12b MDEV-35838 libressl support differences in CRYPTO_set_mem_functions
Based on FreeBSD patch.

The FreeBSD inclusion of check_openssl_compatibility prevented
any use of the crypto callbacks and as such the later differences
where ignored.

The later differences in coc_malloc didn't propegate to the other
callback functions of CRYPTO_set_mem_functions where a reduced
argument list also applied.

Looking where[2] libressl added the functions it was of the
same prototype 10 years ago so omitting any version check.

[1] a34cf9c2db/databases/mariadb106-server/files/patch-mysys__ssl_openssl.c
[2] 5ebad8acea (diff-7f393e5489e6c5780773408f11ca27d9b3bb8f55b174631a1e9467a1dd3010b9R22)
2025-01-14 12:13:22 +11:00
d8c841d0d4 MDEV-35096: History is stored in different partitions on different nodes when using SYSTEM VERSION
Row-injection updates don’t correctly set the historical partition
for tables with system versioning and system_time partitions. This
results in inconsistencies between the master and slave when
replicating transactions that target such tables (i.e. the primary
server would correctly distribute archived rows amongst its
partitions, whereas the replica would have all archived rows in a
single partition). The function
partition_info::vers_set_hist_part(THD*) is used to set the
partition; however, its initial check for
vers_require_hist_part(THD*) returns false, bypassing the rest of
the function (which sets up the partition to use). This is because
the actual check uses the LEX sql_command (via
LEX::vers_history_generating()) to determine if the command is valid
to generate history. Row injections don’t have sql_commands though.

This patch provides a fix which extends the check in
vers_history_generating() to additionally allow row injections to be
history generating (via the function LEX::is_stmt_row_injection()).

Special thanks to Jan Lindstrom <jan.lindstrom@galeracluster.com>
for his work in reproducing the bug, and providing an initial test
case.

Reviewed By
============
Kristian Nielsen <knielsen@knielsen-hq.org>
Aleksey Midenkov <midenok@mariadb.com>
2025-01-13 15:59:07 -07:00
133e26fd7d MDEV-34924 : gtid_slave_pos table neven been deleted on non replica nodes (wsrep_gtid_mode = 1)
Problem was caused by MDEV-31413 commit 277968aa where
mysql.gtid_slave_pos table was replicated by Galera.
However, as not all nodes in Galera cluster are replica
nodes, rows were not deleted from table.

In this fix this is corrected so that mysql.gtid_slave_pos
table is not replicated by Galera. Instead when Galera
node receives GTID event and wsrep_gtid_mode=1, this event
is stored to mysql.gtid_slave_pos table.

Added test case galera_2primary_replica for 2 async
primaries replicating to galera cluster.

Added test case galera_circular_replication where
async primary replicates to galera cluster and
one of the galera cluster nodes is master
to async replica.

Modified test case galera_restart_replica to monitor
gtid positions and rows in mysql.gtid_pos_table.
2025-01-13 19:14:26 +01:00