I am writing a small program to check the endianness using Go:
var i int = 0x0100
ptr := unsafe.Pointer(&i)
if 0x01 == *(*byte)(ptr) {
fmt.Println("Big Endian")
} else if 0x00 == *(*byte)(ptr) {
fmt.Println("Little Endian")
} else {
// ...
}
I import "unsafe"
package to convert *int
to *byte
.
But as mentioned in https://golang.org/pkg/unsafe/:
Package unsafe contains operations that step around the type safety of Go programs.
Packages that import unsafe may be non-portable and are not protected by the Go 1 compatibility guidelines.
Is there a better way to determine endianness, or do I have to use unsafe package?
What you want to do is architecture-specific, and Go doesn't do a whole lot to help you determine your host's byte order as far as I can tell. Your solution using unsafe pointers is probably the best you can do.
If you know the byte order you want to speak in and encode/decode accordingly, you can use the encoding/binary
package for that: https://godoc.org/encoding/binary#ByteOrder
If you truly need to rely on host byte order, you might be banging your head on a design anti-pattern that you should try to avoid if possible: https://commandcenter.blogspot.com/2012/04/byte-order-fallacy.html
Also here's a spirited discussion on golang-nuts about this very topic, with opinions expressed on both sides of the debate: https://groups.google.com/forum/#!topic/golang-nuts/3GEzwKfRRQw
That email thread has a suggestion by Russ Cox to just statically define the desired byte order (or the host byte order) using build constraints:
For months now our code has had:
var hbo = binary.LittleEndian // hack - we want host byte order!
so we can use encoding.Binary to read things.
Put that in a file named byteorder_amd64.go and it stops being a hack. It need not be in the standard library.
Hope that helps...