|
|
@@ -8,7 +8,7 @@ import (
|
|
|
type realDecoder struct {
|
|
|
raw []byte
|
|
|
off int
|
|
|
- stack []pushDecoder
|
|
|
+ stack []PushDecoder
|
|
|
}
|
|
|
|
|
|
func (rd *realDecoder) remaining() int {
|
|
|
@@ -17,7 +17,7 @@ func (rd *realDecoder) remaining() int {
|
|
|
|
|
|
// primitives
|
|
|
|
|
|
-func (rd *realDecoder) getInt8() (int8, error) {
|
|
|
+func (rd *realDecoder) GetInt8() (int8, error) {
|
|
|
if rd.remaining() < 1 {
|
|
|
return -1, InsufficientData
|
|
|
}
|
|
|
@@ -26,7 +26,7 @@ func (rd *realDecoder) getInt8() (int8, error) {
|
|
|
return tmp, nil
|
|
|
}
|
|
|
|
|
|
-func (rd *realDecoder) getInt16() (int16, error) {
|
|
|
+func (rd *realDecoder) GetInt16() (int16, error) {
|
|
|
if rd.remaining() < 2 {
|
|
|
return -1, InsufficientData
|
|
|
}
|
|
|
@@ -35,7 +35,7 @@ func (rd *realDecoder) getInt16() (int16, error) {
|
|
|
return tmp, nil
|
|
|
}
|
|
|
|
|
|
-func (rd *realDecoder) getInt32() (int32, error) {
|
|
|
+func (rd *realDecoder) GetInt32() (int32, error) {
|
|
|
if rd.remaining() < 4 {
|
|
|
return -1, InsufficientData
|
|
|
}
|
|
|
@@ -44,7 +44,7 @@ func (rd *realDecoder) getInt32() (int32, error) {
|
|
|
return tmp, nil
|
|
|
}
|
|
|
|
|
|
-func (rd *realDecoder) getInt64() (int64, error) {
|
|
|
+func (rd *realDecoder) GetInt64() (int64, error) {
|
|
|
if rd.remaining() < 8 {
|
|
|
return -1, InsufficientData
|
|
|
}
|
|
|
@@ -53,49 +53,7 @@ func (rd *realDecoder) getInt64() (int64, error) {
|
|
|
return tmp, nil
|
|
|
}
|
|
|
|
|
|
-// arrays
|
|
|
-
|
|
|
-func (rd *realDecoder) getInt32Array() ([]int32, error) {
|
|
|
- if rd.remaining() < 4 {
|
|
|
- return nil, InsufficientData
|
|
|
- }
|
|
|
- n := int(binary.BigEndian.Uint32(rd.raw[rd.off:]))
|
|
|
- rd.off += 4
|
|
|
-
|
|
|
- var ret []int32 = nil
|
|
|
- if rd.remaining() < 4*n {
|
|
|
- return nil, InsufficientData
|
|
|
- } else if n > 0 {
|
|
|
- ret = make([]int32, n)
|
|
|
- for i := range ret {
|
|
|
- ret[i] = int32(binary.BigEndian.Uint32(rd.raw[rd.off:]))
|
|
|
- rd.off += 4
|
|
|
- }
|
|
|
- }
|
|
|
- return ret, nil
|
|
|
-}
|
|
|
-
|
|
|
-func (rd *realDecoder) getInt64Array() ([]int64, error) {
|
|
|
- if rd.remaining() < 4 {
|
|
|
- return nil, InsufficientData
|
|
|
- }
|
|
|
- n := int(binary.BigEndian.Uint32(rd.raw[rd.off:]))
|
|
|
- rd.off += 4
|
|
|
-
|
|
|
- var ret []int64 = nil
|
|
|
- if rd.remaining() < 8*n {
|
|
|
- return nil, InsufficientData
|
|
|
- } else if n > 0 {
|
|
|
- ret = make([]int64, n)
|
|
|
- for i := range ret {
|
|
|
- ret[i] = int64(binary.BigEndian.Uint64(rd.raw[rd.off:]))
|
|
|
- rd.off += 8
|
|
|
- }
|
|
|
- }
|
|
|
- return ret, nil
|
|
|
-}
|
|
|
-
|
|
|
-func (rd *realDecoder) getArrayCount() (int, error) {
|
|
|
+func (rd *realDecoder) GetArrayLength() (int, error) {
|
|
|
if rd.remaining() < 4 {
|
|
|
return -1, InsufficientData
|
|
|
}
|
|
|
@@ -109,59 +67,99 @@ func (rd *realDecoder) getArrayCount() (int, error) {
|
|
|
return tmp, nil
|
|
|
}
|
|
|
|
|
|
-// misc
|
|
|
+// collections
|
|
|
|
|
|
-func (rd *realDecoder) getString() (string, error) {
|
|
|
- tmp, err := rd.getInt16()
|
|
|
+func (rd *realDecoder) GetBytes() ([]byte, error) {
|
|
|
+ tmp, err := rd.GetInt32()
|
|
|
|
|
|
if err != nil {
|
|
|
- return "", err
|
|
|
+ return nil, err
|
|
|
}
|
|
|
|
|
|
n := int(tmp)
|
|
|
|
|
|
switch {
|
|
|
case n < -1:
|
|
|
- return "", DecodingError
|
|
|
+ return nil, DecodingError
|
|
|
case n == -1:
|
|
|
- return "", nil
|
|
|
+ return nil, nil
|
|
|
case n == 0:
|
|
|
- return "", nil
|
|
|
+ return make([]byte, 0), nil
|
|
|
case n > rd.remaining():
|
|
|
- return "", InsufficientData
|
|
|
+ return nil, InsufficientData
|
|
|
default:
|
|
|
- tmp := string(rd.raw[rd.off : rd.off+n])
|
|
|
+ tmp := rd.raw[rd.off : rd.off+n]
|
|
|
rd.off += n
|
|
|
return tmp, nil
|
|
|
}
|
|
|
}
|
|
|
|
|
|
-func (rd *realDecoder) getBytes() ([]byte, error) {
|
|
|
- tmp, err := rd.getInt32()
|
|
|
+func (rd *realDecoder) GetString() (string, error) {
|
|
|
+ tmp, err := rd.GetInt16()
|
|
|
|
|
|
if err != nil {
|
|
|
- return nil, err
|
|
|
+ return "", err
|
|
|
}
|
|
|
|
|
|
n := int(tmp)
|
|
|
|
|
|
switch {
|
|
|
case n < -1:
|
|
|
- return nil, DecodingError
|
|
|
+ return "", DecodingError
|
|
|
case n == -1:
|
|
|
- return nil, nil
|
|
|
+ return "", nil
|
|
|
case n == 0:
|
|
|
- return make([]byte, 0), nil
|
|
|
+ return "", nil
|
|
|
case n > rd.remaining():
|
|
|
- return nil, InsufficientData
|
|
|
+ return "", InsufficientData
|
|
|
default:
|
|
|
- tmp := rd.raw[rd.off : rd.off+n]
|
|
|
+ tmp := string(rd.raw[rd.off : rd.off+n])
|
|
|
rd.off += n
|
|
|
return tmp, nil
|
|
|
}
|
|
|
}
|
|
|
|
|
|
-func (rd *realDecoder) getSubset(length int) (packetDecoder, error) {
|
|
|
+func (rd *realDecoder) GetInt32Array() ([]int32, error) {
|
|
|
+ if rd.remaining() < 4 {
|
|
|
+ return nil, InsufficientData
|
|
|
+ }
|
|
|
+ n := int(binary.BigEndian.Uint32(rd.raw[rd.off:]))
|
|
|
+ rd.off += 4
|
|
|
+
|
|
|
+ var ret []int32 = nil
|
|
|
+ if rd.remaining() < 4*n {
|
|
|
+ return nil, InsufficientData
|
|
|
+ } else if n > 0 {
|
|
|
+ ret = make([]int32, n)
|
|
|
+ for i := range ret {
|
|
|
+ ret[i] = int32(binary.BigEndian.Uint32(rd.raw[rd.off:]))
|
|
|
+ rd.off += 4
|
|
|
+ }
|
|
|
+ }
|
|
|
+ return ret, nil
|
|
|
+}
|
|
|
+
|
|
|
+func (rd *realDecoder) GetInt64Array() ([]int64, error) {
|
|
|
+ if rd.remaining() < 4 {
|
|
|
+ return nil, InsufficientData
|
|
|
+ }
|
|
|
+ n := int(binary.BigEndian.Uint32(rd.raw[rd.off:]))
|
|
|
+ rd.off += 4
|
|
|
+
|
|
|
+ var ret []int64 = nil
|
|
|
+ if rd.remaining() < 8*n {
|
|
|
+ return nil, InsufficientData
|
|
|
+ } else if n > 0 {
|
|
|
+ ret = make([]int64, n)
|
|
|
+ for i := range ret {
|
|
|
+ ret[i] = int64(binary.BigEndian.Uint64(rd.raw[rd.off:]))
|
|
|
+ rd.off += 8
|
|
|
+ }
|
|
|
+ }
|
|
|
+ return ret, nil
|
|
|
+}
|
|
|
+
|
|
|
+func (rd *realDecoder) GetSubset(length int) (PacketDecoder, error) {
|
|
|
if length > rd.remaining() {
|
|
|
return nil, InsufficientData
|
|
|
}
|
|
|
@@ -169,12 +167,12 @@ func (rd *realDecoder) getSubset(length int) (packetDecoder, error) {
|
|
|
return &realDecoder{raw: rd.raw[rd.off : rd.off+length]}, nil
|
|
|
}
|
|
|
|
|
|
-// stackable
|
|
|
+// stacks
|
|
|
|
|
|
-func (rd *realDecoder) push(in pushDecoder) error {
|
|
|
- in.saveOffset(rd.off)
|
|
|
+func (rd *realDecoder) Push(in PushDecoder) error {
|
|
|
+ in.SaveOffset(rd.off)
|
|
|
|
|
|
- reserve := in.reserveLength()
|
|
|
+ reserve := in.ReserveLength()
|
|
|
if rd.remaining() < reserve {
|
|
|
return DecodingError
|
|
|
}
|
|
|
@@ -186,18 +184,10 @@ func (rd *realDecoder) push(in pushDecoder) error {
|
|
|
return nil
|
|
|
}
|
|
|
|
|
|
-func (rd *realDecoder) pushLength32() error {
|
|
|
- return rd.push(&length32Decoder{})
|
|
|
-}
|
|
|
-
|
|
|
-func (rd *realDecoder) pushCRC32() error {
|
|
|
- return rd.push(&crc32Decoder{})
|
|
|
-}
|
|
|
-
|
|
|
-func (rd *realDecoder) pop() error {
|
|
|
+func (rd *realDecoder) Pop() error {
|
|
|
// this is go's ugly pop pattern (the inverse of append)
|
|
|
in := rd.stack[len(rd.stack)-1]
|
|
|
rd.stack = rd.stack[:len(rd.stack)-1]
|
|
|
|
|
|
- return in.check(rd.off, rd.raw)
|
|
|
+ return in.Check(rd.off, rd.raw)
|
|
|
}
|