Live data from Hacker News

GCC always assumes aligned pointer accesses (2020)

trust-in-soft.com

51–60 of 128 posts

Re: GCC always assumes aligned pointer accesses (2020)

#51

Machine language architecture is flawed. The assumption of alignment is in the machine language. Compilers can only use the instructions that are there. They have a difficult choice: close their eyes and generate aligned-pointer moves, or use a sequence of tests and partial move instructions that is orders of magnitude less efficient. We've needed machine instructions to load or move memory efficiently regardless of…

In retrospect, too many crazy software dances are due to miserliness on the part of hardware designs. Saving a couple bits in the address lines and not needing to straddle cache lines? We're far past the point where that's a considerable cost, as all modern ISA implementations now attest.

Re: GCC always assumes aligned pointer accesses (2020)

#52
post #22
post #15

Earlier quoted context omitted.

Both gcc and clang will optimize a memcpy to an unaligned load/store where possible.

If the compiler is so smart, I guess it could insert a memcpy when needed? The standard, you may say.. I would argue it's the standard need to be changed. The modern reading of the standard is not useful as a low-level language and is unsafe as a high-level language.

Right, I agree that it would be nice to have some way to request unaligned load/store to be permitted, alike -fwrapv for signed int wrapping. But nevertheless the UB behavior is a reasonable option that's beneficial for other things.

Re: GCC always assumes aligned pointer accesses (2020)

#53
post #17
post #2

The arguments in this blogpost are fundamentally flawed. The fact that they opened a bug based on them but got shut down should have raised all red flags. When compiling and running a C program, the only thing that matters is "what the C abstract machine does". Programs that exhibit UB in the abstract machine are allowed to do "anything". Trying to scope that down using arguments of the form "but what the hardware do…

And one of the anythings permitted would be to behave in a documented manner characteristic of the target environment. The program is after all almost certainly being built to run on an actual machine; if you know what that actual machine does, it would sometimes be useful to be able to take advantage of that. We might not be able to demand this on the basis that the standard requires it, but as a quality of implemen…

The problem is that what the machine does isn't necessarily consistent. If you're using old-as-the-green-hills integer instructions then yes, the CPU supports unaligned access. If you want to benefit from the speedup afforded by the latest vector instructions, now it suddenly it doesn't.

Also, to be fair, GCC does appear to back off the optimisations when dealing with, for example, a struct with the packed attribute.

Re: GCC always assumes aligned pointer accesses (2020)

#54
post #19

Earlier quoted context omitted.

It dates to the first standardization of C in 1989. The "C as portable assembly" view ended when ANSI C got standardized, and K&R's 2nd edition was published.

I would argue it's the modern understanding of C standard is flawed. Back in 89, many of those unspecified behavior were understood as implementation/hardware dependent, not undefined. Aliasing was the norm, `restrict` was actually a keyword. Modern C is neither safe nor low-level.

I haven't gotten to use C in industry, but I was taught that undefined behavior just means that it is defined by the running system and not the compiler. Is that not the general understanding? Maybe I was just taught that way because it was old timers teaching it.

Re: GCC always assumes aligned pointer accesses (2020)

#55
post #12
post #2

The arguments in this blogpost are fundamentally flawed. The fact that they opened a bug based on them but got shut down should have raised all red flags. When compiling and running a C program, the only thing that matters is "what the C abstract machine does". Programs that exhibit UB in the abstract machine are allowed to do "anything". Trying to scope that down using arguments of the form "but what the hardware do…

That's what the author meant when he said "The shift of the C language from “portable assembly” to “high-level programming language without the safety of high-level programming languages”" Back in the 1980s, C was expected to do what hardware does. There was no "the C abstract machine". The abstract machine idea was introduced much later. > The arguments in this blogpost are fundamentally flawed. The "fundamentally f…

This turns out to be contentious. There are two histories of the C language and which one you get told is true depends on who you ask.

1/ a way to emit specific assembly with a compiler dealing with register allocation and instruction selection

2/ an abstract machine specification that permits optimisations and also happens to lower well defined code to some architectures

My working theory is that the language standardisation effort invented the latter. So when people say C was always like this, they mean since ansi c89, and there was no language before that. And when people say C used to be typed/convenient assembly language, they're referring to the language that was called C that existed in reality prior to that standards document.

The WG14 mailing list was insistent (in correspondence to me) that C was always like this, some of whom were presumably around at the time. A partial counterargument is the semi-infamous message from Dennis Richie copied in various places, e.g. https://www.lysator.liu.se/c/dmr-on-noalias.html

An out of context quote from that email to encourage people to read said context and ideally reply here with more information on this historical assessment

"The fundamental problem is that it is not possible to write real programs using the X3J11 definition of C. The committee has created an unreal language that no one can or will actually use."

Regards

Re: GCC always assumes aligned pointer accesses (2020)

#56
post #39
post #19

Earlier quoted context omitted.

I would argue it's the modern understanding of C standard is flawed. Back in 89, many of those unspecified behavior were understood as implementation/hardware dependent, not undefined. Aliasing was the norm, `restrict` was actually a keyword. Modern C is neither safe nor low-level.

> Back in 89 […] `restrict` was actually a keyword. Was it? I thought it’s more recent. https://en.wikipedia.org/wiki/Restrict seems to agree ( “In the C programming language, restrict is a keyword, introduced by the C99 standard,[1] that can be used in pointer declarations” ), as does https://en.cppreference.com/w/c/language/restrict ( “restrict type qualifier (since C99)” ) Was there an older usage?

I've used several pre-C99 embedded compilers that supported restrict. IIRC, probably of mid 90s vintage.

Re: GCC always assumes aligned pointer accesses (2020)

#57
post #44
post #12

Earlier quoted context omitted.

That's what the author meant when he said "The shift of the C language from “portable assembly” to “high-level programming language without the safety of high-level programming languages”" Back in the 1980s, C was expected to do what hardware does. There was no "the C abstract machine". The abstract machine idea was introduced much later. > The arguments in this blogpost are fundamentally flawed. The "fundamentally f…

How does C do what hardware does and store things in registers when it can?

Two ways. One is the platform ABI sometimes says specific arguments are passed in specific registers. The second is (essentially) assigning local variables offsets on a machine stack where some offsets are stored in registers.

Re: GCC always assumes aligned pointer accesses (2020)

#58
post #23
post #2

The arguments in this blogpost are fundamentally flawed. The fact that they opened a bug based on them but got shut down should have raised all red flags. When compiling and running a C program, the only thing that matters is "what the C abstract machine does". Programs that exhibit UB in the abstract machine are allowed to do "anything". Trying to scope that down using arguments of the form "but what the hardware do…

Honestly, I think you are both incorrect. C has always had a concept of implementation defined behavior, and unaligned memory accesses used to be defined to work correctly on x86. Intel added instructions that can’t handle unaligned access, so they broke that contract. I’d argue that it is an instruction set architecture bug. Alternatively, Intel could argue that compilers shouldn’t emit vector instructions unless th…

Loads of architectures can't do misaligned memory access. Even x86 has problems when variables span cache lines. The compiler usually deals with this for the programmer, e.g. by rounding the address down then doing multiple operations and splicing the result together.

Re: GCC always assumes aligned pointer accesses (2020)

#59
post #19

Earlier quoted context omitted.

I would argue it's the modern understanding of C standard is flawed. Back in 89, many of those unspecified behavior were understood as implementation/hardware dependent, not undefined. Aliasing was the norm, `restrict` was actually a keyword. Modern C is neither safe nor low-level.

I haven't gotten to use C in industry, but I was taught that undefined behavior just means that it is defined by the running system and not the compiler. Is that not the general understanding? Maybe I was just taught that way because it was old timers teaching it.

No. See this for details on how UB is handled by compilers:

http://blog.llvm.org/2011/05/what-every-c-programmer-should-...

The TL;DR is that compilers compile code based on assumptions that UB won't be invoked. This sometimes produces extremely surprising results which have nothing to do with the hardware/OS.

Re: GCC always assumes aligned pointer accesses (2020)

#60
post #19

Earlier quoted context omitted.

I would argue it's the modern understanding of C standard is flawed. Back in 89, many of those unspecified behavior were understood as implementation/hardware dependent, not undefined. Aliasing was the norm, `restrict` was actually a keyword. Modern C is neither safe nor low-level.

I haven't gotten to use C in industry, but I was taught that undefined behavior just means that it is defined by the running system and not the compiler. Is that not the general understanding? Maybe I was just taught that way because it was old timers teaching it.

That’s indeed incorrect. Undefined behavior anywhere means that the entirety of your program is undefined and may do anything.
Post reply on HN