#At file:///Users/kaa/src/bzr/bugteam/bug44796/my50-bug44796/ based on revid:matthias.leich@stripped
2748 Alexey Kopytov 2009-05-20
Bug #44796: valgrind: too many my_longlong10_to_str_8bit
warnings after uncompressed_length
UNCOMPRESSED_LENGTH() did not validate its argument. In
particular, if the argument length was less than 4 bytes,
an uninitialized memory value was returned as a result.
Since the result of COMPRESS() is either an empty string or
a 4-byte length prefix followed by compressed data, the bug was
fixed by ensuring that the argument of UNCOMPRESSED_LENGTH() is
either an empty string or contains at least 5 bytes (as done in
UNCOMPRESS()). This is the best we can do to validate input
without decompressing.
modified:
mysql-test/r/func_compress.result
mysql-test/t/func_compress.test
sql/item_strfunc.cc
per-file messages:
mysql-test/r/func_compress.result
Added a test case for bug #44796.
mysql-test/t/func_compress.test
Added a test case for bug #44796.
sql/item_strfunc.cc
Make sure that the argument of UNCOMPRESSED_LENGTH() contains
at least 5 bytes (as done in UNCOMPRESS()).
=== modified file 'mysql-test/r/func_compress.result'
--- a/mysql-test/r/func_compress.result 2006-10-13 14:09:22 +0000
+++ b/mysql-test/r/func_compress.result 2009-05-20 08:30:06 +0000
@@ -116,4 +116,19 @@ Warnings:
Error 1259 ZLIB: Input data corrupted
Error 1259 ZLIB: Input data corrupted
drop table t1;
+CREATE TABLE t1 (c1 INT);
+INSERT INTO t1 VALUES (1), (1111), (11111);
+SELECT UNCOMPRESS(c1), UNCOMPRESSED_LENGTH(c1) FROM t1;
+UNCOMPRESS(c1) UNCOMPRESSED_LENGTH(c1)
+NULL NULL
+NULL NULL
+NULL 825307441
+Warnings:
+Error 1259 ZLIB: Input data corrupted
+Error 1259 ZLIB: Input data corrupted
+Error 1259 ZLIB: Input data corrupted
+Error 1259 ZLIB: Input data corrupted
+Error 1256 Uncompressed data size too large; the maximum size is 104857600 (probably, length of uncompressed data was corrupted)
+EXPLAIN EXTENDED SELECT * FROM (SELECT UNCOMPRESSED_LENGTH(c1) FROM t1) AS s;
+DROP TABLE t1;
End of 5.0 tests
=== modified file 'mysql-test/t/func_compress.test'
--- a/mysql-test/t/func_compress.test 2006-10-13 14:09:22 +0000
+++ b/mysql-test/t/func_compress.test 2009-05-20 08:30:06 +0000
@@ -82,4 +82,21 @@ select *, uncompress(a) from t1;
select *, uncompress(a), uncompress(a) is null from t1;
drop table t1;
+#
+# Bug #44796: valgrind: too many my_longlong10_to_str_8bit warnings after
+# uncompressed_length
+#
+
+CREATE TABLE t1 (c1 INT);
+INSERT INTO t1 VALUES (1), (1111), (11111);
+
+SELECT UNCOMPRESS(c1), UNCOMPRESSED_LENGTH(c1) FROM t1;
+
+# We do not need the results, just make sure there are no valgrind errors
+--disable_result_log
+EXPLAIN EXTENDED SELECT * FROM (SELECT UNCOMPRESSED_LENGTH(c1) FROM t1) AS s;
+--enable_result_log
+
+DROP TABLE t1;
+
--echo End of 5.0 tests
=== modified file 'sql/item_strfunc.cc'
--- a/sql/item_strfunc.cc 2009-05-12 08:18:27 +0000
+++ b/sql/item_strfunc.cc 2009-05-20 08:30:06 +0000
@@ -3108,7 +3108,21 @@ longlong Item_func_uncompressed_length::
if (res->is_empty()) return 0;
/*
- res->ptr() using is safe because we have tested that string is not empty,
+ If length is <= 4 bytes, data is corrupt. This is the best we can do
+ to detect garbage input without decompressing it.
+ */
+ if (res->length() <= 4)
+ {
+ push_warning_printf(current_thd, MYSQL_ERROR::WARN_LEVEL_ERROR,
+ ER_ZLIB_Z_DATA_ERROR,
+ ER(ER_ZLIB_Z_DATA_ERROR));
+ null_value= 1;
+ return 0;
+ }
+
+ /*
+ res->ptr() using is safe because we have tested that string is at least
+ 5 bytes long.
res->c_ptr() is not used because:
- we do not need \0 terminated string to get first 4 bytes
- c_ptr() tests simbol after string end (uninitialiozed memory) which
| Thread |
|---|
| • bzr commit into mysql-5.0-bugteam branch (Alexey.Kopytov:2748)Bug#44796 | Alexey Kopytov | 20 May |