Commit 48083d73 authored by unknown's avatar unknown

After-merge fixes for problems seen in buildbot after merging MySQL-5.1.35.

 - Version number.
 - Valgrind false alarms in libz.
 - New variant of suppression for Valgrind warning in dlclose().
 - Fix double free() in plugin init error case.

configure.in:
  Fix version number. We should reset the maria variant back to `1' when the MySQL version
  number increases.
include/my_sys.h:
  Fix false alarms in Valgrind for zlib.
  
  Apply same fix as for archive storage handler also to the cases of compression in the
  client protocol, and to the compression SQL function.
mysql-test/valgrind.supp:
  A new variant of the dlclose() suppression is needed now.
mysys/my_compress.c:
  Fix false alarms in Valgrind for zlib.
  
  Apply same fix as for archive storage handler also to the cases of compression in the
  client protocol, and to the compression SQL function.
sql/handler.cc:
  Fix a double free() in error case for plugin initialisation.
sql/item_strfunc.cc:
  Fix false alarms in Valgrind for zlib.
  
  Apply same fix as for archive storage handler also to the cases of compression in the
  client protocol, and to the compression SQL function.
parent ae134314
...@@ -9,8 +9,11 @@ AC_CANONICAL_SYSTEM ...@@ -9,8 +9,11 @@ AC_CANONICAL_SYSTEM
# remember to also update version.c in ndb # remember to also update version.c in ndb
# #
# When changing major version number please also check switch statement # When changing major version number please also check switch statement
# in mysqlbinlog::check_master_version(). # in mysqlbinlog.cc / check_master_version().
AM_INIT_AUTOMAKE(mysql, 5.1.35-maria-beta2) #
# When merging new MySQL releases, update the version number to match the
# MySQL version number, but reset the maria subrelease (-beta1).
AM_INIT_AUTOMAKE(mysql, 5.1.35-maria-beta1)
AM_CONFIG_HEADER([include/config.h:config.h.in]) AM_CONFIG_HEADER([include/config.h:config.h.in])
PROTOCOL_VERSION=10 PROTOCOL_VERSION=10
......
...@@ -879,6 +879,10 @@ extern my_bool my_compress(uchar *, size_t *, size_t *); ...@@ -879,6 +879,10 @@ extern my_bool my_compress(uchar *, size_t *, size_t *);
extern my_bool my_uncompress(uchar *, size_t , size_t *); extern my_bool my_uncompress(uchar *, size_t , size_t *);
extern uchar *my_compress_alloc(const uchar *packet, size_t *len, extern uchar *my_compress_alloc(const uchar *packet, size_t *len,
size_t *complen); size_t *complen);
extern void *my_az_allocator(void *dummy, unsigned int items, unsigned int size);
extern void my_az_free(void *dummy, void *address);
extern int my_compress_buffer(uchar *dest, size_t *destLen,
const uchar *source, size_t sourceLen);
extern int packfrm(uchar *, size_t, uchar **, size_t *); extern int packfrm(uchar *, size_t, uchar **, size_t *);
extern int unpackfrm(uchar **, size_t *, const uchar *); extern int unpackfrm(uchar **, size_t *, const uchar *);
......
...@@ -400,6 +400,20 @@ ...@@ -400,6 +400,20 @@
fun:_Z13plugin_dl_delPK19st_mysql_lex_string fun:_Z13plugin_dl_delPK19st_mysql_lex_string
} }
{
dlclose memory loss from plugin variant 3
Memcheck:Leak
fun:malloc
fun:_dl_scope_free
fun:_dl_close_worker
fun:_dl_close
fun:_dl_catch_error
fun:_dlerror_run
fun:dlclose
fun:_Z15free_plugin_memP12st_plugin_dl
fun:_Z13plugin_dl_delPK19st_mysql_lex_string
}
{ {
dlopen / ptread_cancel_init memory loss on Suse Linux 10.3 32/64 bit dlopen / ptread_cancel_init memory loss on Suse Linux 10.3 32/64 bit
Memcheck:Leak Memcheck:Leak
......
...@@ -57,19 +57,85 @@ my_bool my_compress(uchar *packet, size_t *len, size_t *complen) ...@@ -57,19 +57,85 @@ my_bool my_compress(uchar *packet, size_t *len, size_t *complen)
} }
/*
Valgrind normally gives false alarms for zlib operations, in the form of
"conditional jump depends on uninitialised values" etc. The reason is
explained in the zlib FAQ (http://www.zlib.net/zlib_faq.html#faq36):
"That is intentional for performance reasons, and the output of deflate
is not affected."
Also discussed on a blog
(http://www.sirena.org.uk/log/2006/02/19/zlib-generating-valgrind-warnings/):
"...loop unrolling in the zlib library causes the mentioned
“Conditional jump or move depends on uninitialised value(s)”
warnings. These are safe since the results of the comparison are
subsequently ignored..."
"the results of the calculations are discarded by bounds checking done
after the loop exits"
Fix by initializing the memory allocated by zlib when running under Valgrind.
This fix is safe, since such memory is only used internally by zlib, so we
will not hide any bugs in mysql this way.
*/
void *my_az_allocator(void *dummy, unsigned int items, unsigned int size)
{
return my_malloc((size_t)items*(size_t)size, IF_VALGRIND(MY_ZEROFILL, MYF(0)));
}
void my_az_free(void *dummy, void *address)
{
my_free(address, MYF(MY_ALLOW_ZERO_PTR));
}
/*
This works like zlib compress(), but using custom memory allocators to work
better with my_malloc leak detection and Valgrind.
*/
int my_compress_buffer(uchar *dest, size_t *destLen,
const uchar *source, size_t sourceLen)
{
z_stream stream;
int err;
stream.next_in = (Bytef*)source;
stream.avail_in = (uInt)sourceLen;
stream.next_out = (Bytef*)dest;
stream.avail_out = (uInt)*destLen;
if ((size_t)stream.avail_out != *destLen)
return Z_BUF_ERROR;
stream.zalloc = (alloc_func)my_az_allocator;
stream.zfree = (free_func)my_az_free;
stream.opaque = (voidpf)0;
err = deflateInit(&stream, Z_DEFAULT_COMPRESSION);
if (err != Z_OK) return err;
err = deflate(&stream, Z_FINISH);
if (err != Z_STREAM_END) {
deflateEnd(&stream);
return err == Z_OK ? Z_BUF_ERROR : err;
}
*destLen = stream.total_out;
err = deflateEnd(&stream);
return err;
}
uchar *my_compress_alloc(const uchar *packet, size_t *len, size_t *complen) uchar *my_compress_alloc(const uchar *packet, size_t *len, size_t *complen)
{ {
uchar *compbuf; uchar *compbuf;
uLongf tmp_complen;
int res; int res;
*complen= *len * 120 / 100 + 12; *complen= *len * 120 / 100 + 12;
if (!(compbuf= (uchar *) my_malloc(*complen, MYF(MY_WME)))) if (!(compbuf= (uchar *) my_malloc(*complen, MYF(MY_WME))))
return 0; /* Not enough memory */ return 0; /* Not enough memory */
tmp_complen= (uLongf) *complen; res= my_compress_buffer(compbuf, complen, packet, *len);
res= compress((Bytef*) compbuf, &tmp_complen, (Bytef*) packet, (uLong) *len);
*complen= tmp_complen;
if (res != Z_OK) if (res != Z_OK)
{ {
......
...@@ -432,9 +432,6 @@ int ha_initialize_handlerton(st_plugin_int *plugin) ...@@ -432,9 +432,6 @@ int ha_initialize_handlerton(st_plugin_int *plugin)
{ {
sql_print_error("Plugin '%s' init function returned error.", sql_print_error("Plugin '%s' init function returned error.",
plugin->name.str); plugin->name.str);
/* Free data, so that we don't refer to it in ha_finalize_handlerton */
my_free(hton, MYF(0));
plugin->data= 0;
goto err; goto err;
} }
......
...@@ -3243,7 +3243,7 @@ longlong Item_func_crc32::val_int() ...@@ -3243,7 +3243,7 @@ longlong Item_func_crc32::val_int()
String *Item_func_compress::val_str(String *str) String *Item_func_compress::val_str(String *str)
{ {
int err= Z_OK, code; int err= Z_OK, code;
ulong new_size; size_t new_size;
String *res; String *res;
Byte *body; Byte *body;
char *tmp, *last_char; char *tmp, *last_char;
...@@ -3279,8 +3279,8 @@ String *Item_func_compress::val_str(String *str) ...@@ -3279,8 +3279,8 @@ String *Item_func_compress::val_str(String *str)
body= ((Byte*)buffer.ptr()) + 4; body= ((Byte*)buffer.ptr()) + 4;
// As far as we have checked res->is_empty() we can use ptr() // As far as we have checked res->is_empty() we can use ptr()
if ((err= compress(body, &new_size, if ((err= my_compress_buffer(body, &new_size, (const uchar *)res->ptr(),
(const Bytef*)res->ptr(), res->length())) != Z_OK) res->length())) != Z_OK)
{ {
code= err==Z_MEM_ERROR ? ER_ZLIB_Z_MEM_ERROR : ER_ZLIB_Z_BUF_ERROR; code= err==Z_MEM_ERROR ? ER_ZLIB_Z_MEM_ERROR : ER_ZLIB_Z_BUF_ERROR;
push_warning(current_thd,MYSQL_ERROR::WARN_LEVEL_ERROR,code,ER(code)); push_warning(current_thd,MYSQL_ERROR::WARN_LEVEL_ERROR,code,ER(code));
......
...@@ -16,6 +16,8 @@ ...@@ -16,6 +16,8 @@
#include <stdio.h> #include <stdio.h>
#include <string.h> #include <string.h>
#include "my_sys.h"
static int const gz_magic[2] = {0x1f, 0x8b}; /* gzip magic header */ static int const gz_magic[2] = {0x1f, 0x8b}; /* gzip magic header */
static int const az_magic[3] = {0xfe, 0x03, 0x01}; /* az magic header */ static int const az_magic[3] = {0xfe, 0x03, 0x01}; /* az magic header */
...@@ -37,40 +39,6 @@ void putLong(File file, uLong x); ...@@ -37,40 +39,6 @@ void putLong(File file, uLong x);
uLong getLong(azio_stream *s); uLong getLong(azio_stream *s);
void read_header(azio_stream *s, unsigned char *buffer); void read_header(azio_stream *s, unsigned char *buffer);
/*
Valgrind normally gives false alarms for zlib operations, in the form of
"conditional jump depends on uninitialised values" etc. The reason is
explained in the zlib FAQ (http://www.zlib.net/zlib_faq.html#faq36):
"That is intentional for performance reasons, and the output of deflate
is not affected."
Also discussed on a blog
(http://www.sirena.org.uk/log/2006/02/19/zlib-generating-valgrind-warnings/):
"...loop unrolling in the zlib library causes the mentioned
“Conditional jump or move depends on uninitialised value(s)”
warnings. These are safe since the results of the comparison are
subsequently ignored..."
"the results of the calculations are discarded by bounds checking done
after the loop exits"
Fix by initializing the memory allocated by zlib when running under Valgrind.
This fix is safe, since such memory is only used internally by zlib, so we
will not hide any bugs in mysql this way.
*/
static void *az_allocator(void *dummy, uInt items, uInt size)
{
return my_malloc((size_t)items*(size_t)size, IF_VALGRIND(MY_ZEROFILL, MYF(0)));
}
static void az_free(void *dummy, void *address)
{
my_free(address, MYF(MY_ALLOW_ZERO_PTR));
}
/* =========================================================================== /* ===========================================================================
Opens a gzip (.gz) file for reading or writing. The mode parameter Opens a gzip (.gz) file for reading or writing. The mode parameter
is as in fopen ("rb" or "wb"). The file is given either by file descriptor is as in fopen ("rb" or "wb"). The file is given either by file descriptor
...@@ -86,8 +54,8 @@ int az_open (azio_stream *s, const char *path, int Flags, File fd) ...@@ -86,8 +54,8 @@ int az_open (azio_stream *s, const char *path, int Flags, File fd)
int level = Z_DEFAULT_COMPRESSION; /* compression level */ int level = Z_DEFAULT_COMPRESSION; /* compression level */
int strategy = Z_DEFAULT_STRATEGY; /* compression strategy */ int strategy = Z_DEFAULT_STRATEGY; /* compression strategy */
s->stream.zalloc = az_allocator; s->stream.zalloc = my_az_allocator;
s->stream.zfree = az_free; s->stream.zfree = my_az_free;
s->stream.opaque = (voidpf)0; s->stream.opaque = (voidpf)0;
memset(s->inbuf, 0, AZ_BUFSIZE_READ); memset(s->inbuf, 0, AZ_BUFSIZE_READ);
memset(s->outbuf, 0, AZ_BUFSIZE_WRITE); memset(s->outbuf, 0, AZ_BUFSIZE_WRITE);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment