ugorji / go

idiomatic codec and rpc lib for msgpack, cbor, json, etc. msgpack.org[Go]
MIT License
1.86k stars 295 forks source link

codecgen broken for array types #214

Closed ajwerner closed 7 years ago

ajwerner commented 7 years ago
$ cat junk.go
package junk

type ArrayType [16]byte
$ codecgen -x -o gen.go -c github.com/ugorji/codec junk.go
codecgen error: error running 'go run codecgen-main-7661.generated.go': exit status 1, console: panic: 82:20: expected operand, found '%' (and 1 more errors)

goroutine 1 [running]:
junk.CodecGenTempWrite7661()
        /ssd/a/home/andrew/upcode/go/src/junk/codecgen-pkg-7661.generated.go:30 +0x41c
main.main()
        /ssd/a/home/andrew/upcode/go/src/junk/codecgen-main-7661.generated.go:6 +0x20
exit status 2

the below patch fixes it:

diff --git a/codec/gen.go b/codec/gen.go
index 7d430e5..63000be 100644
--- a/codec/gen.go
+++ b/codec/gen.go
@@ -1332,7 +1332,7 @@ func (x *genRunner) decListFallback(varname string, rtid uintptr, t reflect.Type
                return
        }
        if t.Kind() == reflect.Array && t.Elem().Kind() == reflect.Uint8 {
-               x.linef("r.DecodeBytes( ((*[%s]byte)(%s))[:], true)", t.Len(), varname)
+               x.linef("r.DecodeBytes( ((*[%d]byte)(%s))[:], true)", t.Len(), varname)
                return
        }
        type tstruc struct {

https://github.com/ugorji/go/blob/master/codec/gen.go#L1335

I would pull request but don't want to get into some legal things. Thanks!

ajwerner commented 7 years ago

Actually, there's still a problem in the generated code in encListFallback:

it generates

func (x codecSelfer7661) encArrayType(v *ArrayType, e *codec1978.Encoder) {
var h codecSelfer7661
z, r := codec1978.GenHelperEncoder(e)
_, _, _ = h, z, r
r.EncodeStringBytes(codecSelferC_RAW7661, ([16]byte(v))[:])
}

but you can't cast the pointer to ArrayType to the byte slice. Looking at the code it seems hard to tell whether the array type is a pointer here? or maybe they always are. anyway, seems to me like it should just do: (*v)[:]

ajwerner commented 7 years ago
diff --git a/codec/gen.go b/codec/gen.go
index 7d430e5..fea30ce 100644
--- a/codec/gen.go
+++ b/codec/gen.go
@@ -999,7 +999,7 @@ func (x *genRunner) encListFallback(varname string, t reflect.Type) {
                return
        }
        if t.Kind() == reflect.Array && t.Elem().Kind() == reflect.Uint8 {
-               x.linef("r.EncodeStringBytes(codecSelferC_RAW%s, ([%v]byte(%s))[:])", x.xs, t.Len(), varname)
+               x.linef("r.EncodeStringBytes(codecSelferC_RAW%s, ((*[%d]byte)(%s))[:])", x.xs, t.Len(), varname)
                return
        }
        i := x.varsfx()
@@ -1332,7 +1332,7 @@ func (x *genRunner) decListFallback(varname string, rtid uintptr, t reflect.Type
                return
        }
        if t.Kind() == reflect.Array && t.Elem().Kind() == reflect.Uint8 {
-               x.linef("r.DecodeBytes( ((*[%s]byte)(%s))[:], true)", t.Len(), varname)
+               x.linef("r.DecodeBytes( ((*[%d]byte)(%s))[:], true)", t.Len(), varname)
                return
        }
        type tstruc struct {

seems to do it

ugorji commented 7 years ago

BTW, thanks for the bug report and for looking to see where the issue was lurking. Saved me much time. Much appreciated.