summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--myisam/mi_packrec.c36
-rw-r--r--mysql-test/r/myisampack.result22
-rw-r--r--mysql-test/t/myisampack.test25
3 files changed, 56 insertions, 27 deletions
diff --git a/myisam/mi_packrec.c b/myisam/mi_packrec.c
index df9a4d18a6c..68911d7f129 100644
--- a/myisam/mi_packrec.c
+++ b/myisam/mi_packrec.c
@@ -208,10 +208,17 @@ my_bool _mi_read_pack_info(MI_INFO *info, pbool fix_keys)
This segment will be reallocated after construction of the tables.
*/
length=(uint) (elements*2+trees*(1 << myisam_quick_table_bits));
+ /*
+ To keep some algorithms simpler, we accept that they access
+ bytes beyond the end of the input data. This can affect up to
+ one byte less than the "word size" size used in this file,
+ which is BITS_SAVED / 8. To avoid accessing non-allocated
+ data, we add (BITS_SAVED / 8) - 1 bytes to the buffer size.
+ */
if (!(share->decode_tables=(uint16*)
my_malloc((length + OFFSET_TABLE_SIZE) * sizeof(uint16) +
- (uint) (share->pack.header_length - sizeof(header)),
- MYF(MY_WME | MY_ZEROFILL))))
+ (uint) (share->pack.header_length - sizeof(header) +
+ (BITS_SAVED / 8) - 1), MYF(MY_WME | MY_ZEROFILL))))
goto err1;
tmp_buff=share->decode_tables+length;
disk_cache=(byte*) (tmp_buff+OFFSET_TABLE_SIZE);
@@ -1430,31 +1437,6 @@ static void fill_buffer(MI_BIT_BUFF *bit_buff)
bit_buff->current_byte=0;
return;
}
- else
- {
- uint len= 0;
- uint i= 0;
- /*
- Check if the remaining buffer/record to read is less than the word size.
- If so read byte by byte
-
- Note: if this branch becomes a bottleneck it can be removed, assuming
- that the second memory segment allocates 7 extra bytes (see
- _mi_read_pack_info()).
- */
- len= bit_buff->end - bit_buff->pos;
- if (len < (BITS_SAVED / 8))
- {
- bit_buff->current_byte= 0;
- for (i=0 ; i < len ; i++)
- {
- bit_buff->current_byte+= (((uint) ((uchar) bit_buff->pos[len - i - 1]))
- << (8 * i));
- }
- bit_buff->pos= bit_buff->end;
- return;
- }
- }
#if BITS_SAVED == 64
bit_buff->current_byte= ((((uint) ((uchar) bit_buff->pos[7]))) +
diff --git a/mysql-test/r/myisampack.result b/mysql-test/r/myisampack.result
index b4b200549a5..736a550e32b 100644
--- a/mysql-test/r/myisampack.result
+++ b/mysql-test/r/myisampack.result
@@ -38,3 +38,25 @@ SELECT COUNT(*) FROM t1;
COUNT(*)
1024
DROP TABLE t1;
+#
+# Bug #43973 - backup_myisam.test fails on 6.0-bugteam
+#
+CREATE DATABASE mysql_db1;
+CREATE TABLE mysql_db1.t1 (c1 VARCHAR(5), c2 int);
+CREATE INDEX i1 ON mysql_db1.t1 (c1, c2);
+INSERT INTO mysql_db1.t1 VALUES ('A',1);
+INSERT INTO mysql_db1.t1 SELECT * FROM mysql_db1.t1;
+INSERT INTO mysql_db1.t1 SELECT * FROM mysql_db1.t1;
+INSERT INTO mysql_db1.t1 SELECT * FROM mysql_db1.t1;
+INSERT INTO mysql_db1.t1 SELECT * FROM mysql_db1.t1;
+INSERT INTO mysql_db1.t1 SELECT * FROM mysql_db1.t1;
+INSERT INTO mysql_db1.t1 SELECT * FROM mysql_db1.t1;
+INSERT INTO mysql_db1.t1 SELECT * FROM mysql_db1.t1;
+FLUSH TABLE mysql_db1.t1;
+# Compress the table using MYISAMPACK tool
+# Run MYISAMCHK tool on the compressed table
+SELECT COUNT(*) FROM mysql_db1.t1 WHERE c2 < 5;
+COUNT(*)
+128
+DROP TABLE mysql_db1.t1;
+DROP DATABASE mysql_db1;
diff --git a/mysql-test/t/myisampack.test b/mysql-test/t/myisampack.test
index ace7afce88a..ce27071bcf8 100644
--- a/mysql-test/t/myisampack.test
+++ b/mysql-test/t/myisampack.test
@@ -50,3 +50,28 @@ FLUSH TABLE t1;
--exec $MYISAMPACK $MYSQLTEST_VARDIR/master-data/test/t1
SELECT COUNT(*) FROM t1;
DROP TABLE t1;
+
+--echo #
+--echo # Bug #43973 - backup_myisam.test fails on 6.0-bugteam
+--echo #
+CREATE DATABASE mysql_db1;
+CREATE TABLE mysql_db1.t1 (c1 VARCHAR(5), c2 int);
+CREATE INDEX i1 ON mysql_db1.t1 (c1, c2);
+INSERT INTO mysql_db1.t1 VALUES ('A',1);
+INSERT INTO mysql_db1.t1 SELECT * FROM mysql_db1.t1;
+INSERT INTO mysql_db1.t1 SELECT * FROM mysql_db1.t1;
+INSERT INTO mysql_db1.t1 SELECT * FROM mysql_db1.t1;
+INSERT INTO mysql_db1.t1 SELECT * FROM mysql_db1.t1;
+INSERT INTO mysql_db1.t1 SELECT * FROM mysql_db1.t1;
+INSERT INTO mysql_db1.t1 SELECT * FROM mysql_db1.t1;
+INSERT INTO mysql_db1.t1 SELECT * FROM mysql_db1.t1;
+FLUSH TABLE mysql_db1.t1;
+#
+--echo # Compress the table using MYISAMPACK tool
+--exec $MYISAMPACK -s $MYSQLTEST_VARDIR/master-data/mysql_db1/t1
+--echo # Run MYISAMCHK tool on the compressed table
+--exec $MYISAMCHK -srq $MYSQLTEST_VARDIR/master-data/mysql_db1/t1
+SELECT COUNT(*) FROM mysql_db1.t1 WHERE c2 < 5;
+#
+DROP TABLE mysql_db1.t1;
+DROP DATABASE mysql_db1;