I think you need to check if inhdr.Data is aligned with 8 bytes as well.

On Sunday, February 26, 2017 at 2:54:00 PM UTC-8, Bill Katz wrote:
>
> Hi,
>
> We'd like to do a zero-copy conversion of []byte to []uint64 where the 
> underlying memory for the byte slice is properly aligned for N uint64 
> values.  After looking at (6) in the unsafe package documentation 
> <https://golang.org/pkg/unsafe/#Pointer>, I'm wondering if the code below 
> is valid because I only use reflect.SliceHeader as pointers, and it seems 
> to fit pattern 6.
>
> https://play.golang.org/p/FxxKIK08pX
>
> package main
>
> import (
> "fmt"
> "reflect"
> "unsafe"
> )
>
> func byteToUint64(b []byte) (out []uint64, err error) {
> inhdr := *(*reflect.SliceHeader)(unsafe.Pointer(&b))
> if inhdr.Len % 8 != 0 {
> err = fmt.Errorf("cannot convert non-aligned []byte length (%d) to 
> []uint64", inhdr.Len)
> return
> }
> if inhdr.Cap % 8 != 0 {
> err = fmt.Errorf("cannot convert non-aligned []byte capacity (%d) to 
> []uint64", inhdr.Cap)
> return
> }
> outhdr := *(*reflect.SliceHeader)(unsafe.Pointer(&out))
> outhdr.Len = inhdr.Len / 8
> outhdr.Cap = inhdr.Cap / 8
> outhdr.Data = inhdr.Data
> out = *(*[]uint64)(unsafe.Pointer(&outhdr))
> return
> }
>
> func main() {
> b := make([]byte, 24)
> u, err := byteToUint64(b)
> if err != nil {
> fmt.Println(err)
> } else {
> fmt.Printf("b: %v\n", b)
> fmt.Printf("u: %v\n", u)
> fmt.Printf("len(u) = %d, cap(u) = %d\n", len(u), cap(u))
> u[0] = 15
> fmt.Printf("Set u[0] to 15\n")
> fmt.Printf("b: %v\n", b)
> fmt.Printf("u: %v\n", u)
> u[2] = 255
> fmt.Printf("Set u[2] to 255\n")
> fmt.Printf("b: %v\n", b)
> fmt.Printf("u: %v\n", u)
> }
> }
>
> Outputs:
>
> b: [0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0]
> u: [0 0 0]
> len(u) = 3, cap(u) = 3
> Set u[0] to 15
> b: [15 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0]
> u: [15 0 0]
> Set u[2] to 255
> b: [15 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 255 0 0 0 0 0 0 0]
> u: [15 0 255]
>
>
>

-- 
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.
For more options, visit https://groups.google.com/d/optout.

Reply via email to