I'm not sure how enthusiastic I am about replacing my downstream Clang -fsanitize=local-init option with the upstream -ftrivial-auto-var-init=zero -enable-trivial-auto-var-init-zero-knowing-it-will-be-removed-from-clang. Yes, that's literally what you need to pass to enable this.
Conversation
Replying to
Yeah that’s the compromise approach which allowed it to go in at all… wants to get rid of it as well 🙂
IMO we need to show perf of 0 versus pattern can’t be bridged, so 0 is there to stay.
1
1
I'm not using zero for performance. I explain the choice in github.com/GrapheneOS/har as "Zero-based filling has the least chance of uncovering latent bugs, but also the best chance of mitigating vulnerabilities.". Uncovering bugs also isn't necessarily good for this use case.
1
I understand, but the discussion was around performance. If we want to keep zero, performance is how it’ll happen.
Or, empirical data that zero is better.
1
Isn't using it for hardening software in production a valid use case? I would be using zero filling even if the CPU performed worst for zero filling. Using a different value gets complicated because it ideally creates pointers to protected memory and far away from anything valid.
1
on 64-bit platforms, repeated 0xAA have that property.
However, repeated 0xAA is a pretty large size index, zero isn't.
But! In a context like a kernel zero is often a valid pointer sentinel...
So what the "right" choice is was pretty hard to agree, and all that was left was perf
1
It has that property for 64-bit pointers, but not 32-bit pointers. In a 32-bit process on a 64-bit OS, the entire 32-bit address space is usually accessible. As another common example, the standard Android Runtime uses 32-bit pointers for the managed heaps to reduce memory usage.
1
Zero is also simply by far the most conservative and safest value. It's typically what the software is already depending on, since memory starts off zeroed and often stays zeroed or ends up that way. It's the least likely to be a change from how it already was before doing it.
1
It's by far the worst option for uncovering bugs, but by far safest option for hardening. It's the only value that I feel comfortable using in production. I'd rather leave the data uninitialized than using any other value. I'd be scared of making more vulnerabilities exploitable.
1
It would be difficult to find a real case -ftrivial-auto-var-init=zero made incorrect software less safe, while it makes lots of incorrect software safer from exploitation or other failures. Neither Clang or GCC support hard errors on all uninit use and it's not socially viable.
2
If there was a -Wuninitialized=strict, at least there would be a viable alternative for people who care about performance. Clang's own codebase completely depends on -ftrivial-auto-var-init=zero -fwrapv -fno-strict-aliasing whether or not they're passed as switches to build it...

