-
-
Notifications
You must be signed in to change notification settings - Fork 1.5k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
sizeof broken on armv7l / linux (rpi3 + raspbian) #9667
Comments
Here is the source code that needs to be fixed Line 1698 in 8d850f7
Since you have the setup to run the test and it is you who is affected by this, do you work on it to fix it? |
Actually, anybody can test this using docker (even on travis), no rpi needed (likewise ppc and anything else that qemu supports): https://ownyourbits.com/2018/06/27/running-and-building-arm-docker-containers-in-x86/ And right now, not fixing anything - just doing an inventory of things that will break on ARM for Nimbus/Status.. we'll likely be making some custom docker images with Nim on them as well, so as to ease testing |
I try to find a reliably source for correct sizes and alignments for different platforms. ARM is a very important platform and I would like to get the sizes correct. I went to https://godbolt.org/ and put this code in there: #include <string.h>
#include <stdio.h>
#include <stdint.h>
#include <stddef.h>
typedef struct {
uint8_t a; uint64_t b;
} MyStruct;
#define alignof(x) __alignof__(x)
int sizes[] = {
sizeof(uint8_t),
sizeof(uint16_t),
sizeof(uint32_t),
sizeof(uint64_t),
sizeof(float),
sizeof(double),
sizeof(long),
};
int alignments[] = {
alignof(uint8_t),
alignof(uint16_t),
alignof(uint32_t),
alignof(uint64_t),
alignof(float),
alignof(double),
alignof(long),
};
int other[] = {
alignof(MyStruct),
offsetof(MyStruct, b),
}; Then I selected the compiler to output ARM assembly, but I could not find any non self aligned values in the output. @arnetheduck can you explain this? Is raspberry pi a different ARM then what they are using on godbold.org? |
I tested this on an actual raspberry pi 3. There is no failing test. |
Perhaps there is no failing test because you were trying with a different version? Since 0.19, the test has changed substantially, but the original test in 0.19 still fails, even when compiled with a recent devel like 28b3c8d - it used to look like this: discard """
file: "tsize.nim"
output: "40 3 12 32"
"""
type
TMyRecord {.final.} = object
x, y: int
b: bool
r: float
s: string
TMyEnum = enum
tmOne, tmTwo, tmThree, tmFour
TMyArray1 = array[3, uint8]
TMyArray2 = array[1..3, int32]
TMyArray3 = array[TMyEnum, float64]
const
mysize1 = sizeof(TMyArray1)
mysize2 = sizeof(TMyArray2)
mysize3 = sizeof(TMyArray3)
write(stdout, sizeof(TMyRecord))
echo ' ', mysize1, ' ', mysize2, ' ',mysize3 and the output is what is in this bug report originally (wrong, compared to what the test says it should be). I'm not sure if the test is wrong or the code is wrong.
ARM is really a family of platforms, all with different features, sizes and ABI's. They're also called different things by different people.
see #5664 (comment) - the code has since moved to https://github.com/rust-lang/rust/tree/master/src/librustc_target/spec - there are plenty of platforms there. clang will have a similar list, as will gcc, msvc etc. In general, the difficulty lies in agreeing with the C compiler - either you have to duplicate the knowledge in nim by typing it out, or you have to fetch it from the c compiler. Like pointed out before, the key takeaway is that alignment is affected by compiler vendor (ms vs unix), compiler flags (lots), programming language (c / lowest common denominator / ffi vs optimal abi), arch/distro (android vs general linux for example), cpu (bits, mode etc), memory models and whole bunch of other things - the view that everything is aligned to its size is simplistic at best, but mostly just wrong. As an example, sometimes, c compilers choose different alignments for efficiency reasons - code size vs speed, because a larger alignment will use more memory but be more efficient overall. Here's a very common case: https://stackoverflow.com/questions/11108328/double-alignment - what the right alignment is depends. Adding |
That test is wrong. It expects
Nim support two ABI's, the C ABI and the packed ABI. Nim does not introduce a new ABI. There is no new nim specific ABI. The programmer has full control to use |
Is this documented somewhere? |
Nim generates C code. So anything that is not {.packed.} is aligned like a C struct. No special rules added by Nim. |
Nim 0.19
The text was updated successfully, but these errors were encountered: