[MDEV-27562] MSAN use-of-uninitialized-value errors in cmp_buffer_with_ref upon multi-table update Created: 2022-01-21  Updated: 2023-11-28

Status: Open
Project: MariaDB Server
Component/s: Server
Affects Version/s: 10.5, 10.6, 10.7, 10.8, 10.10, 10.11, 11.0, 11.1, 11.2
Fix Version/s: 10.5, 10.6, 10.11, 11.0, 11.1, 11.2

Type: Bug Priority: Major
Reporter: Elena Stepanova Assignee: Oleksandr Byelkin
Resolution: Unresolved Votes: 0
Labels: None


 Description   

--source include/have_innodb.inc
 
CREATE TABLE t1 (id INT PRIMARY KEY, a VARCHAR(256)) ENGINE=InnoDB;
INSERT INTO t1 VALUES (1,'foo'),(2,'bar');
 
CREATE TABLE t2 (x INT) ENGINE=InnoDB;
INSERT INTO t2 VALUES (1);
 
UPDATE t1, t2 SET id = 4 WHERE a IN (SELECT 'baz' UNION SELECT 'qux');
 
# Cleanup
DROP TABLE t1, t2;

10.5 e8e755ea6cb

Uninitialized bytes in MemcmpInterceptorCommon at offset 6 inside [0x715000092f38, 259)
==72856==WARNING: MemorySanitizer: use-of-uninitialized-value
    #0 0x56542020c6fe in bcmp (/home/jenkins/10.5/sql/mariadbd+0x7196fe)
    #1 0x56542094e20c in cmp_buffer_with_ref(THD*, TABLE*, st_table_ref*) /home/jenkins/10.5/sql/sql_select.cc:24581:10
    #2 0x56542094e20c in join_read_key2(THD*, st_join_table*, TABLE*, st_table_ref*) /home/jenkins/10.5/sql/sql_select.cc:21577:7
    #3 0x565420e9ee27 in Expression_cache_tmptable::check_value(Item**) /home/jenkins/10.5/sql/sql_expression_cache.cc:221:15
    #4 0x56542144e414 in Item_cache_wrapper::check_cache() /home/jenkins/10.5/sql/item.cc:8783:22
    #5 0x56542144eced in Item_cache_wrapper::val_int() /home/jenkins/10.5/sql/item.cc:8846:22
    #6 0x56542094c27b in evaluate_join_record(JOIN*, st_join_table*, int) /home/jenkins/10.5/sql/sql_select.cc:21011:25
    #7 0x56542094a516 in sub_select(JOIN*, st_join_table*, bool) /home/jenkins/10.5/sql/sql_select.cc:20952:9
    #8 0x56542094cd31 in evaluate_join_record(JOIN*, st_join_table*, int) /home/jenkins/10.5/sql/sql_select.cc:21143:11
    #9 0x56542094a436 in sub_select(JOIN*, st_join_table*, bool) /home/jenkins/10.5/sql/sql_select.cc:20913:9
    #10 0x5654208c260a in do_select(JOIN*, Procedure*) /home/jenkins/10.5/sql/sql_select.cc:20445:14
    #11 0x5654208c260a in JOIN::exec_inner() /home/jenkins/10.5/sql/sql_select.cc:4538:50
    #12 0x5654208be50c in JOIN::exec() /home/jenkins/10.5/sql/sql_select.cc:4318:3
    #13 0x565420828c93 in mysql_select(THD*, TABLE_LIST*, List<Item>&, Item*, unsigned int, st_order*, st_order*, Item*, st_order*, unsigned long long, select_result*, st_select_lex_unit*, st_select_lex*) /home/jenkins/10.5/sql/sql_select.cc:4795:9
    #14 0x565420b8011e in mysql_multi_update(THD*, TABLE_LIST*, List<Item>*, List<Item>*, Item*, unsigned long long, enum_duplicates, bool, st_select_lex_unit*, st_select_lex*, multi_update**) /home/jenkins/10.5/sql/sql_update.cc:1961:8
    #15 0x565420754216 in mysql_execute_command(THD*) /home/jenkins/10.5/sql/sql_parse.cc:4548:12
    #16 0x56542071f938 in mysql_parse(THD*, char*, unsigned int, Parser_state*, bool, bool) /home/jenkins/10.5/sql/sql_parse.cc:8100:18
    #17 0x565420712bfc in dispatch_command(enum_server_command, THD*, char*, unsigned int, bool, bool) /home/jenkins/10.5/sql/sql_parse.cc:1891:7
    #18 0x5654207218ac in do_command(THD*) /home/jenkins/10.5/sql/sql_parse.cc:1370:17
    #19 0x565420d158d9 in do_handle_one_connection(CONNECT*, bool) /home/jenkins/10.5/sql/sql_connect.cc:1418:11
    #20 0x565420d14ff5 in handle_one_connection /home/jenkins/10.5/sql/sql_connect.cc:1312:5
    #21 0x5654221168ea in pfs_spawn_thread /home/jenkins/10.5/storage/perfschema/pfs.cc:2201:3
    #22 0x7f9f983b6608 in start_thread /build/glibc-eX1tMB/glibc-2.31/nptl/pthread_create.c:477:8
    #23 0x7f9f980bb292 in clone /build/glibc-eX1tMB/glibc-2.31/misc/../sysdeps/unix/sysv/linux/x86_64/clone.S:95
 
  Uninitialized value was stored to memory at
    #0 0x565420202119 in __msan_memcpy (/home/jenkins/10.5/sql/mariadbd+0x70f119)
    #1 0x56542094e555 in cmp_buffer_with_ref(THD*, TABLE*, st_table_ref*) /home/jenkins/10.5/sql/sql_select.cc:24573:7
    #2 0x56542094e555 in join_read_key2(THD*, st_join_table*, TABLE*, st_table_ref*) /home/jenkins/10.5/sql/sql_select.cc:21577:7
 
  Uninitialized value was stored to memory at
    #0 0x565420202119 in __msan_memcpy (/home/jenkins/10.5/sql/mariadbd+0x70f119)
    #1 0x56542132f473 in field_conv_memcpy(Field*, Field*) /home/jenkins/10.5/sql/field_conv.cc:832:5
    #2 0x56542132f473 in field_conv(Field*, Field*) /home/jenkins/10.5/sql/field_conv.cc:862:10
 
  Memory was marked as uninitialized
    #0 0x5654202089ae in __msan_allocated_memory (/home/jenkins/10.5/sql/mariadbd+0x7159ae)
    #1 0x565422aec348 in row_sel_field_store_in_mysql_format_func(unsigned char*, mysql_row_templ_t const*, dict_index_t const*, unsigned long, unsigned char const*, unsigned long) /home/jenkins/10.5/storage/innobase/row/row0sel.cc:2755:2
 
SUMMARY: MemorySanitizer: use-of-uninitialized-value (/home/jenkins/10.5/sql/mariadbd+0x7196fe) in bcmp

Not reproducible with Valgrind.
Earlier versions may well be affected, but MSAN works meaningfully only with 10.5+, hence the choice of the "affects versions" values.



 Comments   
Comment by Marko Mäkelä [ 2022-01-21 ]

It is great to see MemorySanitizer being used.

For the reports to be even more useful, I think that it may be necessary to tweak the origin tracking so that instead of reporting the latest place where the uninitialized data was copied (in this case with memcpy()), the report would identify the original source of the uninitialized data.

In the MSAN_OPTIONS=help=1 output, I see a few options related to origin tracking. In our top-level CMakeLists.txt we have the following:

OPTION(WITH_MSAN "Enable memory sanitizer" OFF)
IF (WITH_MSAN)
  MY_CHECK_AND_SET_COMPILER_FLAG("-fsanitize=memory -fsanitize-memory-track-origins -U_FORTIFY_SOURCE" DEBUG RELWITHDEBINFO)
ENDIF()

Without deep origin tracking, it is hard to debug things even in rr replay, because you would have to set watchpoints to trace the MSAN shadow bytes for each edge in the assignment graph. The MSAN shadow byte addresses are included in the output of the internal function __msan_print_shadow(buffer,length). A number of potentially useful functions are defined in /usr/lib/llvm-*/lib/clang/*/include/sanitizer/msan_interface.h. We are only invoking some via include/my_valgrind.h, mostly by InnoDB and by Field_varstring::mark_unused_memory_as_defined() that is potentially hiding errors.

Comment by Elena Stepanova [ 2022-03-06 ]

As discussed elsewhere, all settings are already there, but apparently the origin tracking is done on the "best effort" basis. In some cases, we see the output like

Uninitialized value was created by an allocation of 'wc' in the stack frame of function '_Z8find_setPK10st_typelibPKcmPK15charset_info_stPPcPjPb'
    #0 0x55a9196ab820 in find_set(st_typelib const*, char const*, unsigned long, charset_info_st const*, char**, unsigned int*, bool*) /server/sql/strfunc.cc:52

(that's from a different occasion, unrelated to this report!)

but more often it's absent.

Generated at Thu Feb 08 09:53:51 UTC 2024 using Jira 8.20.16#820016-sha1:9d11dbea5f4be3d4cc21f03a88dd11d8c8687422.