Rockbox open source high quality audio player as a Music Player Daemon
mpris rockbox mpd libadwaita audio rust zig deno
2
fork

Configure Feed

Select the types of activity you want to include in your feed.

Skip libc-shadowing wrappers in codeclib.c under CODECS_STATIC

Native crash inside rb_subscribe_status — addr2line + objdump traced
it back to: String::clone() → memcpy at 0xc780e8 → SEGV reading 0xe0.
But 0xc780e8 turned out to be inside codec_malloc's region — the linker
had resolved memcpy to codeclib.c's wrapper instead of libc's.

codeclib.c provides wrappers for memcpy/memset/memmove/memcmp/strcpy/
strcat/strcmp/memchr/qsort that delegate to ci->memcpy etc. — codec_api
function pointers normally set up when codecs are dlopen'd as separate
shared libs without their own libc. With -Wl,-z,muldefs (which we need
for the ogg duplicate-symbol problem across vorbis/opus/speex/tremor),
the linker picked codeclib's wrappers over libc's. Calling them with
ci == NULL (firmware not booted yet) → null deref.

Gate all the libc-shadowing wrappers in codeclib.c behind
#ifndef CODECS_STATIC so static-link builds use libc directly. The
codec implementations (which were calling memcpy etc.) get the libc
versions transparently — no codec source changes needed.

After the fix, `nm -D librockbox_expo.so | grep memcpy` shows the
expected `U memcpy@LIBC` (resolved by Android's dynamic linker at
runtime) instead of pointing at codec_malloc's region.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>

+10
+10
lib/rbcodec/codecs/lib/codeclib.c
··· 106 106 return(ci->strlen(s)); 107 107 } 108 108 109 + /* These wrappers exist because Rockbox codecs are normally dlopen'd as 110 + * separate shared libs without their own libc — they get function 111 + * pointers to libc primitives via the codec_api `ci` struct. For the 112 + * Android cdylib build (CODECS_STATIC), all codecs are statically linked 113 + * into one binary that already has libc — these wrappers would shadow 114 + * libc's memcpy/memset/etc. and the Rust allocator, kernel, etc. would 115 + * end up calling them with `ci == NULL`, causing immediate segfaults. 116 + * Skip them in static-link mode and let the codecs use libc directly. */ 117 + #ifndef CODECS_STATIC 109 118 char *strcpy(char *dest, const char *src) 110 119 { 111 120 return(ci->strcpy(dest,src)); ··· 151 160 { 152 161 ci->qsort(base,nmemb,size,compar); 153 162 } 163 + #endif /* !CODECS_STATIC */ 154 164 155 165 /* From ffmpeg - libavutil/common.h */ 156 166 const uint8_t bs_log2_tab[256] ICONST_ATTR = {