[MDEV-18780] Assertion `col->prtype == prtype' failed in innobase_rename_or_enlarge_column_try upon CHANGE COLUMN Created: 2019-03-01  Updated: 2023-11-28

Status: Confirmed
Project: MariaDB Server
Component/s: Data Definition - Alter Table, Storage Engine - InnoDB
Affects Version/s: 10.5.3, 10.4, 10.5, 10.6, 10.7, 10.8, 10.9, 10.10, 10.11, 11.0
Fix Version/s: 10.4, 10.5, 10.6, 10.11

Type: Bug Priority: Major
Reporter: Elena Stepanova Assignee: Oleksandr Byelkin
Resolution: Unresolved Votes: 0
Labels: None

Issue Links:
Relates
relates to MDEV-15563 Instant failure-free data type conver... Closed

 Description   

--source include/have_innodb.inc
 
CREATE TABLE t1 (pk INT PRIMARY KEY) ENGINE=InnoDB ROW_FORMAT=REDUNDANT;
ALTER TABLE t1 DROP PRIMARY KEY;
ALTER TABLE t1 ADD d INT;
ALTER TABLE t1 CHANGE pk f INT;
 
# Cleanup
DROP TABLE t1;

10.4 5a087444

mysqld: /data/src/10.4/storage/innobase/handler/handler0alter.cc:9087: bool innobase_rename_or_enlarge_column_try(const dict_table_t*, trx_t*, const char*, ulint, const Field&, bool): Assertion `col->prtype == prtype' failed.
190301 12:39:06 [ERROR] mysqld got signal 6 ;
 
#7  0x00007f2ce5087ee2 in __assert_fail () from /lib/x86_64-linux-gnu/libc.so.6
#8  0x0000557bd691ef7a in innobase_rename_or_enlarge_column_try (user_table=0x7f2c8c048328, trx=0x7f2cdac5b268, table_name=0x7f2c8c1a2485 "t1", pos=0, f=..., is_v=false) at /data/src/10.4/storage/innobase/handler/handler0alter.cc:9087
#9  0x0000557bd691f34a in innobase_rename_or_enlarge_columns_try (ha_alter_info=0x7f2cda370900, ctx=0x7f2c8c016b00, altered_table=0x7f2c8c0667f0, table=0x7f2c8c150840, trx=0x7f2cdac5b268, table_name=0x7f2c8c1a2485 "t1") at /data/src/10.4/storage/innobase/handler/handler0alter.cc:9158
#10 0x0000557bd693030f in commit_try_norebuild (ha_alter_info=0x7f2cda370900, ctx=0x7f2c8c016b00, altered_table=0x7f2c8c0667f0, old_table=0x7f2c8c150840, trx=0x7f2cdac5b268, table_name=0x7f2c8c1a2485 "t1") at /data/src/10.4/storage/innobase/handler/handler0alter.cc:10140
#11 0x0000557bd69222b0 in ha_innobase::commit_inplace_alter_table (this=0x7f2c8c051548, altered_table=0x7f2c8c0667f0, ha_alter_info=0x7f2cda370900, commit=true) at /data/src/10.4/storage/innobase/handler/handler0alter.cc:10824
#12 0x0000557bd659ecd4 in handler::ha_commit_inplace_alter_table (this=0x7f2c8c051548, altered_table=0x7f2c8c0667f0, ha_alter_info=0x7f2cda370900, commit=true) at /data/src/10.4/sql/handler.cc:4677
#13 0x0000557bd6335491 in mysql_inplace_alter_table (thd=0x7f2c8c000b00, table_list=0x7f2c8c015590, table=0x7f2c8c150840, altered_table=0x7f2c8c0667f0, ha_alter_info=0x7f2cda370900, inplace_supported=HA_ALTER_INPLACE_INSTANT, target_mdl_request=0x7f2cda370b30, alter_ctx=0x7f2cda3710e0) at /data/src/10.4/sql/sql_table.cc:7695
#14 0x0000557bd633bb05 in mysql_alter_table (thd=0x7f2c8c000b00, new_db=0x7f2c8c005290, new_name=0x7f2c8c005690, create_info=0x7f2cda371cd0, table_list=0x7f2c8c015590, alter_info=0x7f2cda371c10, order_num=0, order=0x0, ignore=false) at /data/src/10.4/sql/sql_table.cc:9922
#15 0x0000557bd63c9f44 in Sql_cmd_alter_table::execute (this=0x7f2c8c015d68, thd=0x7f2c8c000b00) at /data/src/10.4/sql/sql_alter.cc:499
#16 0x0000557bd625b2e4 in mysql_execute_command (thd=0x7f2c8c000b00) at /data/src/10.4/sql/sql_parse.cc:6346
#17 0x0000557bd626048c in mysql_parse (thd=0x7f2c8c000b00, rawbuf=0x7f2c8c0154a8 "ALTER TABLE t1 CHANGE pk f INT", length=30, parser_state=0x7f2cda373180, is_com_multi=false, is_next_command=false) at /data/src/10.4/sql/sql_parse.cc:8157
#18 0x0000557bd624bb7a in dispatch_command (command=COM_QUERY, thd=0x7f2c8c000b00, packet=0x7f2c8c139ff1 "ALTER TABLE t1 CHANGE pk f INT", packet_length=30, is_com_multi=false, is_next_command=false) at /data/src/10.4/sql/sql_parse.cc:1829
#19 0x0000557bd624a34e in do_command (thd=0x7f2c8c000b00) at /data/src/10.4/sql/sql_parse.cc:1358
#20 0x0000557bd63c3e59 in do_handle_one_connection (connect=0x557bda235de0) at /data/src/10.4/sql/sql_connect.cc:1399
#21 0x0000557bd63c3bca in handle_one_connection (arg=0x557bda235de0) at /data/src/10.4/sql/sql_connect.cc:1302
#22 0x0000557bd68bab51 in pfs_spawn_thread (arg=0x557bda27bc50) at /data/src/10.4/storage/perfschema/pfs.cc:1862
#23 0x00007f2ce6d5e494 in start_thread (arg=0x7f2cda374700) at pthread_create.c:333
#24 0x00007f2ce514493f in clone () from /lib/x86_64-linux-gnu/libc.so.6

Not reproducible on 10.3.
No obvious effect on a non-debug build.



 Comments   
Comment by Marko Mäkelä [ 2019-03-04 ]

Here is how I would extend the existing tests with this test case:

diff --git a/mysql-test/suite/innodb/t/instant_alter.test b/mysql-test/suite/innodb/t/instant_alter.test
index b6be9137532..6cccd2f91af 100644
--- a/mysql-test/suite/innodb/t/instant_alter.test
+++ b/mysql-test/suite/innodb/t/instant_alter.test
@@ -745,6 +745,16 @@ INSERT INTO t1 VALUES(2,'bah',3);
 SELECT * FROM t1;
 DROP TABLE t1;
 
+# MDEV-18780 Assertion col->prtype == prtype failed on ALTER TABLE
+eval CREATE TABLE t1 (pk INT PRIMARY KEY) $engine;
+INSERT INTO t1 VALUES(0);
+--enable_info
+ALTER TABLE t1 DROP PRIMARY KEY;
+ALTER TABLE t1 ADD d INT;
+ALTER TABLE t1 CHANGE pk f INT;
+--disable_info
+DROP TABLE t1;
+
 dec $format;
 }
 disconnect analyze;

The problem only occurs for ROW_FORMAT=REDUNDANT, possibly because MDEV-15563 allows instantaneous removal of NOT NULL attribute from the columns of such tables. If the redundant NOT NULL is added to the last (column-renaming) ALTER TABLE statement, then the test will pass.

The SQL layer seems to set wrong metadata for the column. We have !(prtype & DATA_NOT_NULL) even though the column is part of the PRIMARY KEY, and therefore NOT NULL is implied. Both f.maybe_null() nor f.real_maybe_null() hold, even though they should not.

Also, ha_alter_info->handler_flags has 3 flags set, instead of the expected 1:

ha_alter_info->handler_flags =
  HA_INPLACE_ADD_UNIQUE_INDEX_NO_WRITE |
  ALTER_COLUMN_NULLABLE
  ALTER_COLUMN_NAME;

Why would it claim to add an index and not drop any index? Given that ha_alter_info->index_add_count=0, no flag for creating an index should be set.

Comment by Elena Stepanova [ 2019-09-17 ]

The assertion has changed, now it is this (with the same original test case):

10.4 c793f078

mysqld: /data/src/10.4/storage/innobase/handler/handler0alter.cc:9142: bool innobase_rename_or_enlarge_column_try(ha_innobase_inplace_ctx*, trx_t*, const char*, ulint, const Field&, bool): Assertion `!((col->prtype ^ prtype) & ~(16384U|32768U))' failed.
190917 17:51:52 [ERROR] mysqld got signal 6 ;
 
#7  0x00007f7cae63af12 in __GI___assert_fail (assertion=0x562a58ee2e68 "!((col->prtype ^ prtype) & ~(16384U|32768U))", file=0x562a58edd798 "/data/src/10.4/storage/innobase/handler/handler0alter.cc", line=9142, function=0x562a58ee79a0 <innobase_rename_or_enlarge_column_try(ha_innobase_inplace_ctx*, trx_t*, char const*, unsigned long, Field const&, bool)::__PRETTY_FUNCTION__> "bool innobase_rename_or_enlarge_column_try(ha_innobase_inplace_ctx*, trx_t*, const char*, ulint, const Field&, bool)") at assert.c:101
#8  0x0000562a585b0fed in innobase_rename_or_enlarge_column_try (ctx=0x7f7c5c014788, trx=0x7f7ca84a5268, table_name=0x7f7c5c14be6d "t1", pos=0, f=..., is_v=false) at /data/src/10.4/storage/innobase/handler/handler0alter.cc:9142
#9  0x0000562a585b1455 in innobase_rename_or_enlarge_columns_try (ha_alter_info=0x7f7ca8207790, ctx=0x7f7c5c014788, altered_table=0x7f7ca8207820, table=0x7f7c5c14f520, trx=0x7f7ca84a5268, table_name=0x7f7c5c14be6d "t1") at /data/src/10.4/storage/innobase/handler/handler0alter.cc:9211
#10 0x0000562a585c7ece in commit_try_norebuild (ha_alter_info=0x7f7ca8207790, ctx=0x7f7c5c014788, altered_table=0x7f7ca8207820, old_table=0x7f7c5c14f520, trx=0x7f7ca84a5268, table_name=0x7f7c5c14be6d "t1") at /data/src/10.4/storage/innobase/handler/handler0alter.cc:10159
#11 0x0000562a585b5552 in ha_innobase::commit_inplace_alter_table (this=0x7f7c5c150388, altered_table=0x7f7ca8207820, ha_alter_info=0x7f7ca8207790, commit=true) at /data/src/10.4/storage/innobase/handler/handler0alter.cc:10921
#12 0x0000562a5831b479 in handler::ha_commit_inplace_alter_table (this=0x7f7c5c150388, altered_table=0x7f7ca8207820, ha_alter_info=0x7f7ca8207790, commit=true) at /data/src/10.4/sql/handler.cc:4567
#13 0x0000562a58098e55 in mysql_inplace_alter_table (thd=0x7f7c5c000b00, table_list=0x7f7c5c013200, table=0x7f7c5c14f520, altered_table=0x7f7ca8207820, ha_alter_info=0x7f7ca8207790, inplace_supported=HA_ALTER_INPLACE_INSTANT, target_mdl_request=0x7f7ca82085f0, alter_ctx=0x7f7ca8209120) at /data/src/10.4/sql/sql_table.cc:7766
#14 0x0000562a5809f9f1 in mysql_alter_table (thd=0x7f7c5c000b00, new_db=0x7f7c5c0052b8, new_name=0x7f7c5c0056c0, create_info=0x7f7ca8209d10, table_list=0x7f7c5c013200, alter_info=0x7f7ca8209c50, order_num=0, order=0x0, ignore=false) at /data/src/10.4/sql/sql_table.cc:10086
#15 0x0000562a58137f59 in Sql_cmd_alter_table::execute (this=0x7f7c5c0139e0, thd=0x7f7c5c000b00) at /data/src/10.4/sql/sql_alter.cc:508
#16 0x0000562a57fb5a49 in mysql_execute_command (thd=0x7f7c5c000b00) at /data/src/10.4/sql/sql_parse.cc:6098
#17 0x0000562a57fbb192 in mysql_parse (thd=0x7f7c5c000b00, rawbuf=0x7f7c5c013118 "ALTER TABLE t1 CHANGE pk f INT", length=30, parser_state=0x7f7ca820b170, is_com_multi=false, is_next_command=false) at /data/src/10.4/sql/sql_parse.cc:7908
#18 0x0000562a57fa6192 in dispatch_command (command=COM_QUERY, thd=0x7f7c5c000b00, packet=0x7f7c5c19dba1 "ALTER TABLE t1 CHANGE pk f INT", packet_length=30, is_com_multi=false, is_next_command=false) at /data/src/10.4/sql/sql_parse.cc:1842
#19 0x0000562a57fa47dc in do_command (thd=0x7f7c5c000b00) at /data/src/10.4/sql/sql_parse.cc:1359
#20 0x0000562a5812e71b in do_handle_one_connection (connect=0x562a5b327880) at /data/src/10.4/sql/sql_connect.cc:1412
#21 0x0000562a5812e46a in handle_one_connection (arg=0x562a5b327880) at /data/src/10.4/sql/sql_connect.cc:1316
#22 0x0000562a58b66003 in pfs_spawn_thread (arg=0x562a5b2a61f0) at /data/src/10.4/storage/perfschema/pfs.cc:1862
#23 0x00007f7cb01af4a4 in start_thread (arg=0x7f7ca820c700) at pthread_create.c:456
#24 0x00007f7cae6f7d0f in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:97

Here is an even simpler test case which produces the same:

--source include/have_innodb.inc
 
CREATE TABLE t1 (a INT NOT NULL) ENGINE=InnoDB ROW_FORMAT=REDUNDANT;
ALTER TABLE t1 CHANGE a f INT;
 
# Cleanup
DROP TABLE t1;

Comment by Roel Van de Paar [ 2020-04-22 ]

Also on 10.5.3 (dbg, not opt)

10.5.3 98003440c2f8d20164a191ced1b7d92b283bb68f

mysqld: /test/10.5_dbg/storage/innobase/handler/handler0alter.cc:9115: bool innobase_rename_or_enlarge_column_try(ha_innobase_inplace_ctx*, trx_t*, const char*, ulint, const Field&, bool): Assertion `!((col->prtype ^ prtype) & ~(16384U|32768U))' failed.

Generated at Thu Feb 08 08:46:40 UTC 2024 using Jira 8.20.16#820016-sha1:9d11dbea5f4be3d4cc21f03a88dd11d8c8687422.