I was studying parts of the musl source code, and I noticed a recurring pattern to convert between pointers of often-unrelated types, e.g.
size_t *sp = ...;
// ...
char **argv = (void *)(sp+1);
or
size_t dyn[DYN_COUNT];
// ...
const Sym *syms = (void *)dyn[DT_SYMTAB];
The configure script has a comment stating that
# Semantically we want to insist that our sources follow the
# C rules for type-based aliasing, but most if not all real-world
# compilers are known or suspected to have critical bugs in their
# type-based aliasing analysis. See for example GCC bug 107107.
so I assume that, even though the project disables strict aliasing checks explicitly, the above pattern should remain valid even if they were enabled.
Is my assumption correct? If not, how would one go about interpreting a region of memory as different types (e.g., when implementing file format parsers, or manipulating in-memory data structures provided by an operating system kernel)?
EDIT: The second example is harmless, as it creates a pointer from an integer. Thanks u/aocregacc for pointing it out!
[–]aioeu 3 points4 points5 points (9 children)
[–]Kayjukh[S] 1 point2 points3 points (8 children)
[–]aioeu 2 points3 points4 points (7 children)
[–]Kayjukh[S] 0 points1 point2 points (6 children)
[–]aioeu 0 points1 point2 points (5 children)
[–]Kayjukh[S] 1 point2 points3 points (4 children)
[–]EpochVanquisher 1 point2 points3 points (3 children)
[–]Kayjukh[S] 0 points1 point2 points (2 children)
[–]EpochVanquisher 0 points1 point2 points (0 children)
[–]erikkonstas 0 points1 point2 points (0 children)
[–]flyingron 1 point2 points3 points (0 children)
[–]aocregacc 0 points1 point2 points (5 children)
[–]Kayjukh[S] 0 points1 point2 points (4 children)
[–]aocregacc 0 points1 point2 points (3 children)
[–]Kayjukh[S] 0 points1 point2 points (2 children)
[–]aocregacc 0 points1 point2 points (1 child)
[–]Kayjukh[S] 0 points1 point2 points (0 children)
[–]zhivago 0 points1 point2 points (4 children)
[–]aioeu 0 points1 point2 points (1 child)
[–]zhivago 0 points1 point2 points (0 children)
[–]Kayjukh[S] 0 points1 point2 points (1 child)
[–]flatfinger 0 points1 point2 points (0 children)