Uploaded image for project: 'MariaDB Server'
  1. MariaDB Server
  2. MDEV-15527

page_compressed compressed page partially during import tablespace

Details

    • 10.3.6-1

    Description

      The CREATE TABLE attribute page_compressed that was introduced in MariaDB 10.1.3 has no effect when innodb_doublewrite=0. This is because the actual compression only takes place within the doublewrite buffer code path.

      The purpose of the doublewrite buffer is to guarantee crash-safety in the event that InnoDB is killed in the middle of a page write. Because it could become a performance bottleneck for write-heavy workloads, some users may choose to set innodb_doublewrite=0 and take the risk that crash recovery may fail. (The page should be referred to by the redo log, and a log checkpoint should not be made while a page write is still in progress, so the page corruption should be detected at InnoDB startup.)

      Attachments

        Issue Links

          Activity

            To repeat this, run:

            ./mtr --mysqld=--skip-innodb-doublewrite encryption.innodb-discard-import
            

            And observe the test failure:

            CURRENT_TEST: encryption.innodb-discard-import
            --- /mariadb/10.2/mysql-test/suite/encryption/r/innodb-discard-import.result	2017-05-10 14:14:26.228207275 +0300
            +++ /mariadb/10.2/mysql-test/suite/encryption/r/innodb-discard-import.reject	2018-03-09 14:32:57.500763121 +0200
            @@ -129,6 +129,6 @@
             # t3 yes on expecting NOT FOUND
             NOT FOUND /tmpres/ in t3.ibd
             # t4 yes on expecting NOT FOUND
            -NOT FOUND /mysql/ in t4.ibd
            +FOUND 484 /mysql/ in t4.ibd
             DROP PROCEDURE innodb_insert_proc;
             DROP TABLE t1,t2,t3,t4;
             
            mysqltest: Result content mismatch
            

            MDEV-15529 will disable this part of the test.

            marko Marko Mäkelä added a comment - To repeat this, run: ./mtr --mysqld=--skip-innodb-doublewrite encryption.innodb-discard-import And observe the test failure: CURRENT_TEST: encryption.innodb-discard-import --- /mariadb/10.2/mysql-test/suite/encryption/r/innodb-discard-import.result 2017-05-10 14:14:26.228207275 +0300 +++ /mariadb/10.2/mysql-test/suite/encryption/r/innodb-discard-import.reject 2018-03-09 14:32:57.500763121 +0200 @@ -129,6 +129,6 @@ # t3 yes on expecting NOT FOUND NOT FOUND /tmpres/ in t3.ibd # t4 yes on expecting NOT FOUND -NOT FOUND /mysql/ in t4.ibd +FOUND 484 /mysql/ in t4.ibd DROP PROCEDURE innodb_insert_proc; DROP TABLE t1,t2,t3,t4;   mysqltest: Result content mismatch MDEV-15529 will disable this part of the test.

            --source include/have_innodb.inc
             
            let $innodb_compression_algo = `SELECT @@innodb_compression_algorithm`;
            SET GLOBAL innodb_compression_algorithm = 1;
            --let $MYSQLD_DATADIR = `SELECT @@datadir`
             
            create table t1(c1 bigint not null, b char(200))  engine=innodb page_compressed=1;
            show create table t1;
             
            delimiter //;
            create procedure innodb_insert_proc (repeat_count int)
            begin
              declare current_num int;
              set current_num = 0;
              while current_num < repeat_count do
                insert into t1 values(current_num, repeat('maria', 30));
               set current_num = current_num + 1;
              end while;
            end//
            delimiter ;//
            commit;
             
            set autocommit=0;
            call innodb_insert_proc(2000);
            commit;
            set autocommit=1;
             
            SELECT COUNT(*) from t1;
            -- let SEARCH_PATTERN=maria
            -- let SEARCH_FILE=$MYSQLD_DATADIR/test/t1.ibd
            --source include/search_pattern_in_file.inc
             
            FLUSH TABLES t1 FOR EXPORT;
             
            let MYSQLD_DATADIR=`select @@datadir`;
            perl;
            do "$ENV{MTR_SUITE_DIR}/include/innodb-util.pl";
            ib_backup_tablespaces("test", "t1");
            EOF
            UNLOCK TABLES;
            SELECT SPACE FROM INFORMATION_SCHEMA.innodb_sys_tables where name = "test/t1";
            drop table t1;
             
            create table t1(c1 bigint not null, b char(200))  engine=innodb page_compressed=1;
            ALTER TABLE t1 DISCARD TABLESPACE;
            --list_files $MYSQLD_DATADIR/test
             
             
            perl;
            do "$ENV{MTR_SUITE_DIR}/include/innodb-util.pl";
            ib_discard_tablespaces("test", "t1");
            ib_restore_tablespaces("test", "t1");
            EOF
            --list_files $MYSQLD_DATADIR/test
             
            SELECT SPACE FROM INFORMATION_SCHEMA.innodb_sys_tables where name ="test/t1";
            ALTER TABLE t1 IMPORT TABLESPACE;
            SELECT COUNT(*) from t1;
            SHOW CREATE TABLE t1;
            -- let SEARCH_PATTERN=maria
            -- let SEARCH_FILE=$MYSQLD_DATADIR/test/t1.ibd
            --source include/search_pattern_in_file.inc
            drop procedure innodb_insert_proc;
            drop table t1;
            

            The above test case can able to repeat the scenario.

            String value("maria") found only in root page of clustered index. (3rd page)

             err = btr_root_adjust_on_import(index); 

            The above function call is omitted then t1.ibd doesn't contain maria. Need to check.

            thiru Thirunarayanan Balathandayuthapani added a comment - --source include/have_innodb.inc   let $innodb_compression_algo = `SELECT @@innodb_compression_algorithm`; SET GLOBAL innodb_compression_algorithm = 1; --let $MYSQLD_DATADIR = `SELECT @@datadir`   create table t1(c1 bigint not null, b char(200)) engine=innodb page_compressed=1; show create table t1;   delimiter //; create procedure innodb_insert_proc (repeat_count int) begin declare current_num int; set current_num = 0; while current_num < repeat_count do insert into t1 values(current_num, repeat('maria', 30)); set current_num = current_num + 1; end while; end// delimiter ;// commit;   set autocommit=0; call innodb_insert_proc(2000); commit; set autocommit=1;   SELECT COUNT(*) from t1; -- let SEARCH_PATTERN=maria -- let SEARCH_FILE=$MYSQLD_DATADIR/test/t1.ibd --source include/search_pattern_in_file.inc   FLUSH TABLES t1 FOR EXPORT;   let MYSQLD_DATADIR=`select @@datadir`; perl; do "$ENV{MTR_SUITE_DIR}/include/innodb-util.pl"; ib_backup_tablespaces("test", "t1"); EOF UNLOCK TABLES; SELECT SPACE FROM INFORMATION_SCHEMA.innodb_sys_tables where name = "test/t1"; drop table t1;   create table t1(c1 bigint not null, b char(200)) engine=innodb page_compressed=1; ALTER TABLE t1 DISCARD TABLESPACE; --list_files $MYSQLD_DATADIR/test     perl; do "$ENV{MTR_SUITE_DIR}/include/innodb-util.pl"; ib_discard_tablespaces("test", "t1"); ib_restore_tablespaces("test", "t1"); EOF --list_files $MYSQLD_DATADIR/test   SELECT SPACE FROM INFORMATION_SCHEMA.innodb_sys_tables where name ="test/t1"; ALTER TABLE t1 IMPORT TABLESPACE; SELECT COUNT(*) from t1; SHOW CREATE TABLE t1; -- let SEARCH_PATTERN=maria -- let SEARCH_FILE=$MYSQLD_DATADIR/test/t1.ibd --source include/search_pattern_in_file.inc drop procedure innodb_insert_proc; drop table t1; The above test case can able to repeat the scenario. String value("maria") found only in root page of clustered index. (3rd page) err = btr_root_adjust_on_import(index); The above function call is omitted then t1.ibd doesn't contain maria. Need to check.

            Commit a6ea7b353b5143f5a61fd37c246c49072ba8c421 looks OK to push (with minor changes), but I do not think that it qualifies as a full fix. We should punch holes to the page_compressed files even if the doublewrite buffer is disabled.

            marko Marko Mäkelä added a comment - Commit a6ea7b353b5143f5a61fd37c246c49072ba8c421 looks OK to push (with minor changes), but I do not think that it qualifies as a full fix. We should punch holes to the page_compressed  files even if the doublewrite buffer is disabled.

            Commit a6ea7b353b5143f5a61fd37c246c49072ba8c421 has been pushed as a workaround of MDEV-15527.

            commit e27535093d1670fde6034c92366e8128b683b903
            Author: Thirunarayanan Balathandayuthapani <thiru@mariadb.com>
            Date:   Mon Mar 26 15:48:27 2018 +0530
                - Follow-up fix to MDEV-15229
            

            It only writes zero in remaining uncompressed size of the page with zero.

            thiru Thirunarayanan Balathandayuthapani added a comment - Commit a6ea7b353b5143f5a61fd37c246c49072ba8c421 has been pushed as a workaround of MDEV-15527 . commit e27535093d1670fde6034c92366e8128b683b903 Author: Thirunarayanan Balathandayuthapani <thiru@mariadb.com> Date: Mon Mar 26 15:48:27 2018 +0530 - Follow-up fix to MDEV-15229 It only writes zero in remaining uncompressed size of the page with zero.

            I posted some comments for the 10.2-based patch. I think that we will also need a 10.5-based version, because the I/O code is quite different there.

            marko Marko Mäkelä added a comment - I posted some comments for the 10.2-based patch. I think that we will also need a 10.5-based version, because the I/O code is quite different there.

            People

              thiru Thirunarayanan Balathandayuthapani
              marko Marko Mäkelä
              Votes:
              2 Vote for this issue
              Watchers:
              6 Start watching this issue

              Dates

                Created:
                Updated:
                Resolved:

                Git Integration

                  Error rendering 'com.xiplink.jira.git.jira_git_plugin:git-issue-webpanel'. Please contact your Jira administrators.