List:Internals« Previous MessageNext Message »
From:Marc Alff Date:June 30 2006 3:48am
Subject:Re: Contribution for Bug#18161 (show create trigger / drop trigger
if exist / show trigger code)
View as plain text  
Hi All

Stewart Smith wrote:
> On Wed, 2006-06-28 at 16:39 -0700, Marc Alff wrote:
>   
>> - Run the test cases with Purify (I would, but don't have access to it).
>>     
>
> valgrind will be as-good if not better. you can
> ./mysql-test-run.pl --valgrind --valgrind-all
>
> to do that if you have valgrind installed.
>
> i recommend getting the latest from valgrind.org.
>
> it will take a long time to run the tests. perhaps only --do-test the
> appropriate ones.
>   

Thanks for the pointers, and yes, running all the tests does take a
while ... but is very instructive.

When executing the new tests cases (trigger-code, trigger-51) as part of
the whole suite,
the results comes clean.

However, when executing the tests alone, some errors are reported, which
can be also reproduced with other tests.
Below are 2 examples.

Error I : Conditional jump or move depends on uninitialised value(s)
==================================================

==25523== Conditional jump or move depends on uninitialised value(s)
==25523==    at 0x8AADD7: trx_sys_create_doublewrite_buf (trx0sys.c:197)
==25523==    by 0x8A1579: innobase_start_or_create_for_mysql
(srv0start.c:1550)
==25523==    by 0x6CBF02: innobase_init() (ha_innodb.cc:1588)
==25523==    by 0x78523F: plugin_initialize(st_plugin_int*)
(sql_plugin.cc:528)
==25523==    by 0x785717: plugin_init() (sql_plugin.cc:685)
==25523==    by 0x5E9933: init_server_components() (mysqld.cc:3190)
==25523==    by 0x5E9F61: main (mysqld.cc:3576)
InnoDB: Doublewrite buffer not found: creating new

The code affected is :

file ./storage/innobase/trx/trx0sys.c
in function trx_sys_create_doublewrite_buf()

        page = buf_page_get(TRX_SYS_SPACE, TRX_SYS_PAGE_NO, RW_X_LATCH,
&mtr);
#ifdef UNIV_SYNC_DEBUG
        buf_page_dbg_add_level(page, SYNC_NO_ORDER_CHECK);
#endif /* UNIV_SYNC_DEBUG */

        doublewrite = page + TRX_SYS_DOUBLEWRITE;

[line 197]        if (mach_read_from_4(doublewrite +
TRX_SYS_DOUBLEWRITE_MAGIC)
                                        == TRX_SYS_DOUBLEWRITE_MAGIC_N) {

Does this qualifies as a bug in InnoDB (I am assuming yes) ?
According to valgrind, the code in line 192 looks for a header which is
not initialized in the 'page',
making the test unsafe.

Error II : Syscall param pwrite64(buf) points to uninitialised byte(s)
=================================================

Below is an example with one call stack, but this error occurs a lot of
times
in different contexts.

==26750== Thread 13:
==26750== Syscall param pwrite64(buf) points to uninitialised byte(s)
==26750==    at 0x4D41D3C: (within /lib64/tls/libpthread.so)
==26750==    by 0x97FEF6: my_pwrite (my_pread.c:101)
==26750==    by 0x982E8C: flush_cached_blocks (mf_keycache.c:2280)
==26750==    by 0x9831F0: flush_key_blocks_int (mf_keycache.c:2459)
==26750==    by 0x983445: flush_key_blocks (mf_keycache.c:2555)
==26750==    by 0x8CE9AC: mi_lock_database (mi_locking.c:64)
==26750==    by 0x6C024E: ha_myisam::external_lock(THD*, int)
(ha_myisam.cc:1400)
==26750==    by 0x6BB6A9: handler::ha_external_lock(THD*, int)
(handler.cc:3373)
==26750==    by 0x5E2633: unlock_external(THD*, st_table**, unsigned)
(lock.cc:641)
==26750==    by 0x5E1C91: mysql_unlock_tables(THD*, st_mysql_lock*)
(lock.cc:271)
==26750==    by 0x65C8CE: mysql_insert(THD*, st_table_list*,
List<Item>&, List<List<Item> >&, List<Item>&,
List<Item>&,
enum_duplicates, bool) (sql_insert.cc:599)
==26750==    by 0x601F53: mysql_execute_command(THD*) (sql_parse.cc:3348)
==26750==    by 0x607E39: mysql_parse(THD*, char*, unsigned)
(sql_parse.cc:6072)
==26750==    by 0x5FE9A6: dispatch_command(enum_server_command, THD*,
char*, unsigned) (sql_parse.cc:1796)
==26750==    by 0x5FE187: do_command(THD*) (sql_parse.cc:1582)
==26750==    by 0x5FD3F3: handle_one_connection (sql_parse.cc:1222)
==26750==  Address 0xBC51D68 is 72 bytes inside a block of size 857,132
alloc'd
==26750==    at 0x4A1AAC7: malloc (in
/usr/lib64/valgrind/amd64-linux/vgpreload_memcheck.so)
==26750==    by 0x98754D: _mymalloc (safemalloc.c:138)
==26750==    by 0x99855A: my_large_malloc (my_largepage.c:65)
==26750==    by 0x980512: init_key_cache (mf_keycache.c:343)
==26750==    by 0x6B9F82: ha_init_key_cache(char const*, st_key_cache*)
(handler.cc:2509)
==26750==    by 0x5F3830: process_key_caches(int (*)(char const*,
st_key_cache*)) (set_var.cc:3824)
==26750==    by 0x5E9C0E: init_server_components() (mysqld.cc:3302)
==26750==    by 0x5E9F61: main (mysqld.cc:3576)

My question is, how should these error reported by valgrind by handled :

- is this a known false positive ?

- "ok" to ignore since the data written to disk contains optional fields,
which if not used can have a random value (but this really creates noise).

- should the code be changed to initialize unused fields with default
values ?
This would make the code more predictable and deterministic,
as well as making valgrind happy.
I have not tried in this case, just assuming a malloc with MY_ZEROFILL
in init_key_cache() should fix it.

In other words, what kind of valgrind reports are considered worth
filing a bug / a patch ?

Thanks,
Marc Alff.

Thread
Contribution for Bug#18161 (show create trigger / drop trigger ifexist / show trigger code)Marc Alff29 Jun
  • Re: Contribution for Bug#18161 (show create trigger / drop triggerif exist / show trigger code)Stewart Smith29 Jun
    • Re: Contribution for Bug#18161 (show create trigger / drop triggerif exist / show trigger code)Marc Alff30 Jun
      • Re: Contribution for Bug#18161 (show create trigger / drop triggerif exist / show trigger code)Stewart Smith30 Jun
        • Re: Contribution for Bug#18161 (show create trigger / drop triggerif exist / show trigger code)Marc Alff2 Jul