Re: [go-nuts] linux/arm struct alignment seems wrong
On Wed, Sep 9, 2020 at 8:17 PM Ian Lance Taylor wrote: > Exact alignment/offset compatibility with the C ABI is not a goal. > Sorry. (It's actually harder than one might think to maintain that > kind of compatibility. For example, on x86, the C ABI uses one > alignment for double variables and a different alignment for double > variables that appear as a field in a struct. Unless, of course, you > use the -malign-double option. And more generally some platforms have > multiple C ABIs, including x86 if you count the MCU psABI.) > > The Go structs in the syscall package that need to match C structs are > carefully written to work correctly. > > You may find the cgo -godefs option to be helpful, as it provides Go > structs that exactly match C structs, given a particular set of > compiler options. Thanks a lot for the clarification. Assuming that IIRC, cgo -godefs acquire the alignment/offset info by invoking the C compiler, it's unfortunately not a good option for a project that aims to avoid CGo in the first place. But I now think there's a feasible solution to this problem, having not as high a cost as I feared first when reading your answer. I shall see tomorrow. Thanks again. -- You received this message because you are subscribed to the Google Groups "golang-nuts" group. To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscr...@googlegroups.com. To view this discussion on the web visit https://groups.google.com/d/msgid/golang-nuts/CAA40n-Vq1d2mFwmb4FVjuAdmCfa%3Du%2BoNBqEoGmY%2B_ba2j5WBWw%40mail.gmail.com.
Re: [go-nuts] linux/arm struct alignment seems wrong
On Wed, Sep 9, 2020 at 4:59 AM Jan Mercl <0xj...@gmail.com> wrote: > > If the intent is to have Go alignments/offsets of types compatible > with the C ABI then I think it's safe to say this is a bug. > > And the existence of the syscall package, in some cases passing > Go-defined structs to the kernel that must be binary compatible with > their C definitions, IMO suggests that the intent is indeed there. Exact alignment/offset compatibility with the C ABI is not a goal. Sorry. (It's actually harder than one might think to maintain that kind of compatibility. For example, on x86, the C ABI uses one alignment for double variables and a different alignment for double variables that appear as a field in a struct. Unless, of course, you use the -malign-double option. And more generally some platforms have multiple C ABIs, including x86 if you count the MCU psABI.) The Go structs in the syscall package that need to match C structs are carefully written to work correctly. You may find the cgo -godefs option to be helpful, as it provides Go structs that exactly match C structs, given a particular set of compiler options. Ian -- You received this message because you are subscribed to the Google Groups "golang-nuts" group. To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscr...@googlegroups.com. To view this discussion on the web visit https://groups.google.com/d/msgid/golang-nuts/CAOyqgcW%2ByA%2BzE4afZ81GJHCXm%3De9tfz-8gD99EQiEe%2Bk7xOKRw%40mail.gmail.com.
Re: [go-nuts] linux/arm struct alignment seems wrong
On Wed, Sep 9, 2020 at 1:45 PM 'Dan Kortschak' via golang-nuts wrote: > I think it comes down to these lines in src/cmd/internal/sys/arch.go > [1] > > ``` > var ArchARM = { > Name: "arm", > Family:ARM, > ByteOrder: binary.LittleEndian, > PtrSize: 4, > RegSize: 4, > MinLC: 4, > } > > var ArchARM64 = { > Name: "arm64", > Family:ARM64, > ByteOrder: binary.LittleEndian, > PtrSize: 8, > RegSize: 8, > MinLC: 4, > } > ``` > this line in src/cmd/compile/internal/gc/main.go [2] > ``` > Widthreg = thearch.LinkArch.RegSize > ``` > > and these lines in src/cmd/compile/internal/gc/align.go [3] > ``` > case TINT64, TUINT64, TFLOAT64: > w = 8 > t.Align = uint8(Widthreg) > ``` > > [1]https://golang.org/src/cmd/internal/sys/arch.go > [2]https://golang.org/src/cmd/compile/internal/gc/main.go > [3]https://golang.org/src/cmd/compile/internal/gc/align.go Thank you very much for the thorough investigation. If the intent is to have Go alignments/offsets of types compatible with the C ABI then I think it's safe to say this is a bug. And the existence of the syscall package, in some cases passing Go-defined structs to the kernel that must be binary compatible with their C definitions, IMO suggests that the intent is indeed there. -- You received this message because you are subscribed to the Google Groups "golang-nuts" group. To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscr...@googlegroups.com. To view this discussion on the web visit https://groups.google.com/d/msgid/golang-nuts/CAA40n-UFLsy0%3DSAWR3CM2YqVTWcEAgfQpkRaAn0LWkSQ%3DWeTcw%40mail.gmail.com.
Re: [go-nuts] linux/arm struct alignment seems wrong
On Wed, 2020-09-09 at 13:21 +0200, Jan Mercl wrote: > > > On Wed, Sep 9, 2020 at 1:09 PM 'Dan Kortschak' via golang-nuts < > golang-nuts@googlegroups.com> wrote: > > > What does cgo -godefs give you? On my amd64 and arm64 I get this: > > > > ``` > > ~/cznic $ cat main.go > > package main > > > > /* > > struct s { > > long long i; > > } x; > > */ > > import "C" > > > > type S struct { > > i int64 > > } > > > > type C_s C.struct_s > > > > ~/cznic $ go tool cgo -godefs main.go > > // Code generated by cmd/cgo -godefs; DO NOT EDIT. > > // cgo -godefs main.go > > > > package main > > > > type S struct { > > i int64 > > } > > > > type C_s struct { > > I int64 > > } > > ``` > > amd64 > = > > > jnml@e5-1650:~/tmp$ go version > go version go1.15.1 linux/amd64 > jnml@e5-1650:~/tmp$ cat main.go > package main > > /* > struct s { > long long i; > } x; > */ > import "C" > > type S struct { > i int64 > } > > type C_s C.struct_s > jnml@e5-1650:~/tmp$ go tool cgo -godefs main.go > // Code generated by cmd/cgo -godefs; DO NOT EDIT. > // cgo -godefs main.go > > package main > > type S struct { > i int64 > } > > type C_s struct { > I int64 > } > jnml@e5-1650:~/tmp$ > > arm > = > == > > pi@raspberrypi:~/src/tmp.tmp $ go version > go version go1.15.1 linux/arm > pi@raspberrypi:~/src/tmp.tmp $ cat main.go > package main > > /* > struct s { > long long i; > } x; > */ > import "C" > > type S struct { > i int64 > } > > type C_s C.struct_s > pi@raspberrypi:~/src/tmp.tmp $ go tool cgo -godefs main.go > // Code generated by cmd/cgo -godefs; DO NOT EDIT. > // cgo -godefs main.go > > package main > > type S struct { > i int64 > } > > type C_s struct { > I int64 > } > pi@raspberrypi:~/src/tmp.tmp $ > > No difference between the outputs AFAICT. Seems good to me. > > I think it comes down to these lines in src/cmd/internal/sys/arch.go [1] ``` var ArchARM = { Name: "arm", Family:ARM, ByteOrder: binary.LittleEndian, PtrSize: 4, RegSize: 4, MinLC: 4, } var ArchARM64 = { Name: "arm64", Family:ARM64, ByteOrder: binary.LittleEndian, PtrSize: 8, RegSize: 8, MinLC: 4, } ``` this line in src/cmd/compile/internal/gc/main.go [2] ``` Widthreg = thearch.LinkArch.RegSize ``` and these lines in src/cmd/compile/internal/gc/align.go [3] ``` case TINT64, TUINT64, TFLOAT64: w = 8 t.Align = uint8(Widthreg) ``` [1]https://golang.org/src/cmd/internal/sys/arch.go [2]https://golang.org/src/cmd/compile/internal/gc/main.go [3]https://golang.org/src/cmd/compile/internal/gc/align.go -- You received this message because you are subscribed to the Google Groups "golang-nuts" group. To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscr...@googlegroups.com. To view this discussion on the web visit https://groups.google.com/d/msgid/golang-nuts/9faee5b3868886c3c7415ecc1c2469f2e008abe2.camel%40kortschak.io.
Re: [go-nuts] linux/arm struct alignment seems wrong
On Wed, Sep 9, 2020 at 1:09 PM 'Dan Kortschak' via golang-nuts < golang-nuts@googlegroups.com> wrote: > What does cgo -godefs give you? On my amd64 and arm64 I get this: > > ``` > ~/cznic $ cat main.go > package main > > /* > struct s { > long long i; > } x; > */ > import "C" > > type S struct { > i int64 > } > > type C_s C.struct_s > > ~/cznic $ go tool cgo -godefs main.go > // Code generated by cmd/cgo -godefs; DO NOT EDIT. > // cgo -godefs main.go > > package main > > type S struct { > i int64 > } > > type C_s struct { > I int64 > } > ``` amd64 = jnml@e5-1650:~/tmp$ go version go version go1.15.1 linux/amd64 jnml@e5-1650:~/tmp$ cat main.go package main /* struct s { long long i; } x; */ import "C" type S struct { i int64 } type C_s C.struct_s jnml@e5-1650:~/tmp$ go tool cgo -godefs main.go // Code generated by cmd/cgo -godefs; DO NOT EDIT. // cgo -godefs main.go package main type S struct { i int64 } type C_s struct { I int64 } jnml@e5-1650:~/tmp$ arm === pi@raspberrypi:~/src/tmp.tmp $ go version go version go1.15.1 linux/arm pi@raspberrypi:~/src/tmp.tmp $ cat main.go package main /* struct s { long long i; } x; */ import "C" type S struct { i int64 } type C_s C.struct_s pi@raspberrypi:~/src/tmp.tmp $ go tool cgo -godefs main.go // Code generated by cmd/cgo -godefs; DO NOT EDIT. // cgo -godefs main.go package main type S struct { i int64 } type C_s struct { I int64 } pi@raspberrypi:~/src/tmp.tmp $ No difference between the outputs AFAICT. Seems good to me. -- You received this message because you are subscribed to the Google Groups "golang-nuts" group. To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscr...@googlegroups.com. To view this discussion on the web visit https://groups.google.com/d/msgid/golang-nuts/CAA40n-Xj22QAWdU-CjxibUhBEwxChm-HOORUUxbpfG2ihY0Sjg%40mail.gmail.com.
Re: [go-nuts] linux/arm struct alignment seems wrong
On Wed, 2020-09-09 at 12:50 +0200, Jan Mercl wrote: > On Wed, Sep 9, 2020 at 12:41 PM Dan Kortschak > wrote: > > > I get the following > > > > ``` > > C alignof struct s: 8 > > Go alignof struct s: 8 > > Go alignofS: 8 > > ~/cznic $ go version > > go version go1.15.1 linux/arm64 > > ~/cznic $ uname -a > > Linux bildr 4.19.0-10-arm64 #1 SMP Debian 4.19.132-1 (2020-07-24) > > aarch64 GNU/Linux > > ``` > > > > I have an arm64 linux running on my pi, maybe the armv7l behaviour > > is > > different. > > Seems to be the case as armv7l is AFAIK a 32 bit only CPU. And arm64 > is next on the list of my targets so thank you for the information. > > But the question is still the same. Is it a bug or is my assumption > about Go and C agreeing on alignments/offsets invalid? I realizethe > specs say nothing in this regard. What does cgo -godefs give you? On my amd64 and arm64 I get this: ``` ~/cznic $ cat main.go package main /* struct s { long long i; } x; */ import "C" type S struct { i int64 } type C_s C.struct_s ~/cznic $ go tool cgo -godefs main.go // Code generated by cmd/cgo -godefs; DO NOT EDIT. // cgo -godefs main.go package main type S struct { i int64 } type C_s struct { I int64 } ``` -- You received this message because you are subscribed to the Google Groups "golang-nuts" group. To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscr...@googlegroups.com. To view this discussion on the web visit https://groups.google.com/d/msgid/golang-nuts/bf4ba2bfde7a4a0c2d858e5ae1af8c118694b541.camel%40kortschak.io.
Re: [go-nuts] linux/arm struct alignment seems wrong
On Wed, Sep 9, 2020 at 12:41 PM Dan Kortschak wrote: > I get the following > > ``` > C alignof struct s: 8 > Go alignof struct s: 8 > Go alignofS: 8 > ~/cznic $ go version > go version go1.15.1 linux/arm64 > ~/cznic $ uname -a > Linux bildr 4.19.0-10-arm64 #1 SMP Debian 4.19.132-1 (2020-07-24) > aarch64 GNU/Linux > ``` > > I have an arm64 linux running on my pi, maybe the armv7l behaviour is > different. Seems to be the case as armv7l is AFAIK a 32 bit only CPU. And arm64 is next on the list of my targets so thank you for the information. But the question is still the same. Is it a bug or is my assumption about Go and C agreeing on alignments/offsets invalid? I realizethe specs say nothing in this regard. -- You received this message because you are subscribed to the Google Groups "golang-nuts" group. To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscr...@googlegroups.com. To view this discussion on the web visit https://groups.google.com/d/msgid/golang-nuts/CAA40n-XvvraqMF_5boDqFo%3DSVLdTo79bX-AJyAfQBJxVu1Tx4A%40mail.gmail.com.
Re: [go-nuts] linux/arm struct alignment seems wrong
On Wed, 2020-09-09 at 12:19 +0200, Jan Mercl wrote: > Observation: > > pi@raspberrypi:~/src/tmp.tmp $ go version > go version go1.15.1 linux/arm > pi@raspberrypi:~/src/tmp.tmp $ cat main.go > package main > > /* > > struct s { > long long i; > } x; > > size_t align() { > return _Alignof(struct s); > } > > */ > import "C" > > import ( > "fmt" > "unsafe" > ) > > type S struct { > i int64 > } > > func main() { > fmt.Printf(" C alignof struct s: %v\n", C.align()) > fmt.Printf("Go alignof struct s: %v\n", > unsafe.Alignof(C.struct_s{})) > fmt.Printf("Go alignofS: %v\n", unsafe.Alignof(S{})) > } > pi@raspberrypi:~/src/tmp.tmp $ go run main.go > C alignof struct s: 8 > Go alignof struct s: 4 > Go alignofS: 4 > pi@raspberrypi:~/src/tmp.tmp $ uname -a > Linux raspberrypi 4.19.66-v7+ #1253 SMP Thu Aug 15 11:49:46 BST 2019 > armv7l GNU/Linux > pi@raspberrypi:~/src/tmp.tmp $ > > My code relies on all the numbers being the same, ie. that Go will > report the same as C for both C.struct_s{} and S{}. > AFAICT Go and C agree on struct layout on linux/{amd64,386} perfectly > in all cases I've tested (thousands probably). > > Is this a bug or are my expectations ill founded? > > Thanks in advance for any insights. > I get the following ``` C alignof struct s: 8 Go alignof struct s: 8 Go alignofS: 8 ~/cznic $ go version go version go1.15.1 linux/arm64 ~/cznic $ uname -a Linux bildr 4.19.0-10-arm64 #1 SMP Debian 4.19.132-1 (2020-07-24) aarch64 GNU/Linux ``` I have an arm64 linux running on my pi, maybe the armv7l behaviour is different. Dan -- You received this message because you are subscribed to the Google Groups "golang-nuts" group. To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscr...@googlegroups.com. To view this discussion on the web visit https://groups.google.com/d/msgid/golang-nuts/da8da3f14f311a23ab0191d7e8ba130a068c73b8.camel%40kortschak.io.