Skip to content

Ensure string returned by dupdirname is always null-terminated

Mauricio Collares requested to merge collares/sympow:dupdirname into master

Setting SYMPOW_CACHEDIR to a non-existent directory ending with three slashes should cause it to be created if its parent directory exists. Currently, however, the code that processes the environment variable is susceptible to undefined behaviour due the output buffer not being big enough to contain a terminating NULL char. In the example AddressSanitizer run below, the calculated parent directory contains trailing junk, which makes sympow complain about it being non-existent. The topmost error refers to the code that tries to print the unterminated string returned by dupdirname.

$ SYMPOW_CACHEDIR="/tmp/nix-build-sage-tests-9.8.rc0.drv-0/sage-home/.sage/sympow///" sympow
=================================================================
==434558==ERROR: AddressSanitizer: heap-buffer-overflow on address
0x606000000057 at pc 0x7f716925eab7 bp 0x7ffe97e65960 sp
0x7ffe97e65110
READ of size 56 at 0x606000000057 thread T0
    #0 0x7f716925eab6 in printf_common(void*, char const*, __va_list_tag*) (/nix/store/sq78g74zs4sj7n1j5709g9c2pmffx1y8-gcc-11.3.0-lib/lib/libasan.so.6+0x5eab6)
    #1 0x7f716925f36e in __interceptor_vfprintf (/nix/store/sq78g74zs4sj7n1j5709g9c2pmffx1y8-gcc-11.3.0-lib/lib/libasan.so.6+0x5f36e)
    #2 0x7f716925f54e in __interceptor___fprintf_chk (/nix/store/sq78g74zs4sj7n1j5709g9c2pmffx1y8-gcc-11.3.0-lib/lib/libasan.so.6+0x5f54e)
    #3 0x42e43d in prepare_main (/nix/store/7pakvs110xypxp6zq9qs6p9788x41y3y-sympow-2.023.6/bin/.sympow-wrapped+0x42e43d)
    #4 0x402f4a in main (/nix/store/7pakvs110xypxp6zq9qs6p9788x41y3y-sympow-2.023.6/bin/.sympow-wrapped+0x402f4a)
    #5 0x7f7168e2924d in __libc_start_call_main (/nix/store/yzjgl0h6a3qh1mby405428f16xww37h0-glibc-2.35-224/lib/libc.so.6+0x2924d)
    #6 0x7f7168e29308 in __libc_start_main_impl (/nix/store/yzjgl0h6a3qh1mby405428f16xww37h0-glibc-2.35-224/lib/libc.so.6+0x29308)
    #7 0x403e84 in _start (/nix/store/7pakvs110xypxp6zq9qs6p9788x41y3y-sympow-2.023.6/bin/.sympow-wrapped+0x403e84)

0x606000000057 is located 0 bytes to the right of 55-byte region
[0x606000000020,0x606000000057)
allocated by thread T0 here:
    #0 0x7f71692b1987 in __interceptor_calloc (/nix/store/sq78g74zs4sj7n1j5709g9c2pmffx1y8-gcc-11.3.0-lib/lib/libasan.so.6+0xb1987)
    #1 0x42d8e3 in dupdirname (/nix/store/7pakvs110xypxp6zq9qs6p9788x41y3y-sympow-2.023.6/bin/.sympow-wrapped+0x42d8e3)

SUMMARY: AddressSanitizer: heap-buffer-overflow (/nix/store/sq78g74zs4sj7n1j5709g9c2pmffx1y8-gcc-11.3.0-lib/lib/libasan.so.6+0x5eab6)
in printf_common(void*, char const*, __va_list_tag*)
Shadow bytes around the buggy address:
  0x0c0c7fff7fb0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
  0x0c0c7fff7fc0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
  0x0c0c7fff7fd0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
  0x0c0c7fff7fe0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
  0x0c0c7fff7ff0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
=>0x0c0c7fff8000: fa fa fa fa 00 00 00 00 00 00[07]fa fa fa fa fa
  0x0c0c7fff8010: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
  0x0c0c7fff8020: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
  0x0c0c7fff8030: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
  0x0c0c7fff8040: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
  0x0c0c7fff8050: fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa fa
Shadow byte legend (one shadow byte represents 8 application bytes):
  Addressable:           00
  Partially addressable: 01 02 03 04 05 06 07
  Heap left redzone:       fa
  Freed heap region:       fd
  Stack left redzone:      f1
  Stack mid redzone:       f2
  Stack right redzone:     f3
  Stack after return:      f5
  Stack use after scope:   f8
  Global redzone:          f9
  Global init order:       f6
  Poisoned by user:        f7
  Container overflow:      fc
  Array cookie:            ac
  Intra object redzone:    bb
  ASan internal:           fe
  Left alloca redzone:     ca
  Right alloca redzone:    cb
  Shadow gap:              cc
==434558==ABORTING

Merge request reports