Marshalling implemented
This commit is contained in:
parent
0603ba907c
commit
8023e70530
377
marshal.go
377
marshal.go
|
@ -6,6 +6,8 @@ import (
|
||||||
"io"
|
"io"
|
||||||
"math"
|
"math"
|
||||||
"reflect"
|
"reflect"
|
||||||
|
|
||||||
|
"gitea.olznet.de/OlzNet/slog"
|
||||||
)
|
)
|
||||||
|
|
||||||
func MarshalString(in string) (ret []byte) {
|
func MarshalString(in string) (ret []byte) {
|
||||||
|
@ -482,3 +484,378 @@ func baseTypeMarshaller(e interface{}, w io.Writer) (err error) {
|
||||||
|
|
||||||
return binary.Write(w, binary.BigEndian, sb)
|
return binary.Write(w, binary.BigEndian, sb)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func marshalBool(e bool) (ret []byte) {
|
||||||
|
ret = make([]byte, ST_ID_SIZE+1)
|
||||||
|
ret[0] = 1
|
||||||
|
if e == true {
|
||||||
|
ret[0] = 0
|
||||||
|
}
|
||||||
|
return ret
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalUint8(e uint8) (ret []byte) {
|
||||||
|
ret = make([]byte, 1)
|
||||||
|
ret[0] = byte(e)
|
||||||
|
return ret
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalUint16(e uint16) (ret []byte) {
|
||||||
|
ret = make([]byte, 2)
|
||||||
|
binary.BigEndian.PutUint16(ret, e)
|
||||||
|
return ret
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalUint32(e uint32) (ret []byte) {
|
||||||
|
ret = make([]byte, 4)
|
||||||
|
binary.BigEndian.PutUint32(ret, e)
|
||||||
|
return ret
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalUint64(e uint64) (ret []byte) {
|
||||||
|
ret = make([]byte, 8)
|
||||||
|
binary.BigEndian.PutUint64(ret, e)
|
||||||
|
return ret
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalInt8(e int8) (ret []byte) {
|
||||||
|
ret = make([]byte, 1)
|
||||||
|
ret[0] = byte(e)
|
||||||
|
return ret
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalInt16(e int16) (ret []byte) {
|
||||||
|
ret = make([]byte, 2)
|
||||||
|
binary.BigEndian.PutUint16(ret, uint16(e))
|
||||||
|
return ret
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalInt32(e int32) (ret []byte) {
|
||||||
|
ret = make([]byte, 4)
|
||||||
|
binary.BigEndian.PutUint32(ret, uint32(e))
|
||||||
|
return ret
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalInt64(e int64) (ret []byte) {
|
||||||
|
ret = make([]byte, 8)
|
||||||
|
binary.BigEndian.PutUint64(ret, uint64(e))
|
||||||
|
return ret
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalFloat32(e float32) (ret []byte) {
|
||||||
|
ret = make([]byte, 4)
|
||||||
|
binary.BigEndian.PutUint32(ret, math.Float32bits(e))
|
||||||
|
return ret
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalFloat64(e float64) (ret []byte) {
|
||||||
|
ret = make([]byte, 8)
|
||||||
|
binary.BigEndian.PutUint64(ret, math.Float64bits(e))
|
||||||
|
return ret
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalString(e string) (ret []byte) {
|
||||||
|
slen := len(e)
|
||||||
|
ret = make([]byte, slen+4)
|
||||||
|
binary.BigEndian.PutUint32(ret, uint32(slen))
|
||||||
|
copy(ret[4:], []byte(e))
|
||||||
|
return ret
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalNil(e uint16) (ret []byte) {
|
||||||
|
return marshalUint16(e)
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalPtrIfNil(e interface{}, ntype *NType) (ie interface{}, ret []byte, isNil bool) {
|
||||||
|
if ntype.Indirection == 0 {
|
||||||
|
return e, nil, false
|
||||||
|
}
|
||||||
|
|
||||||
|
nl := uint16(0)
|
||||||
|
v := reflect.ValueOf(e)
|
||||||
|
if v.Kind() == reflect.Invalid {
|
||||||
|
ret = append(ret, marshalTypeId(ST_NIL)...)
|
||||||
|
ret = append(ret, marshalNil(nl)...)
|
||||||
|
return e, ret, true
|
||||||
|
}
|
||||||
|
|
||||||
|
for i := 0; i < ntype.Indirection; i++ {
|
||||||
|
v = reflect.Indirect(v)
|
||||||
|
nl++
|
||||||
|
if v.Kind() == reflect.Invalid || (v.Kind() == reflect.Ptr && v.IsNil()) {
|
||||||
|
ret = append(ret, marshalTypeId(ST_NIL)...)
|
||||||
|
ret = append(ret, marshalNil(uint16(nl))...)
|
||||||
|
return e, ret, true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ret = append(ret, marshalTypeId(ntype.ValType)...)
|
||||||
|
return v.Interface(), ret, false
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalError(e interface{}, ntype *NType) (ret []byte, err error) {
|
||||||
|
nl := uint16(0)
|
||||||
|
v := reflect.ValueOf(e)
|
||||||
|
if v.Kind() == reflect.Invalid {
|
||||||
|
ret = append(ret, marshalTypeId(ST_NIL)...)
|
||||||
|
ret = append(ret, marshalNil(nl)...)
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
|
||||||
|
for i := 0; i < ntype.Indirection; i++ {
|
||||||
|
v = reflect.Indirect(v)
|
||||||
|
nl++
|
||||||
|
if v.Kind() == reflect.Invalid || v.IsNil() {
|
||||||
|
ret = append(ret, marshalTypeId(ST_NIL)...)
|
||||||
|
ret = append(ret, marshalNil(uint16(nl))...)
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ierr, ok := v.Interface().(error)
|
||||||
|
if !ok {
|
||||||
|
return ret, fmt.Errorf("Not an error interface '%v': %w", v.Interface(), ErrValueInvalid)
|
||||||
|
}
|
||||||
|
|
||||||
|
ret = append(ret, marshalTypeId(ST_STRING)...)
|
||||||
|
ret = append(ret, marshalString(ierr.Error())...)
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalTypeId(e uint32) (ret []byte) {
|
||||||
|
return marshalUint32(e)
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalCommon(e interface{}, ntype *NType) (ret []byte, err error) {
|
||||||
|
ctype := getTypeById(ntype.ValType)
|
||||||
|
if ctype == nil {
|
||||||
|
return ret, fmt.Errorf("ssob: Unknown common type '%d': %w", ntype.ValType, ErrTypeUnknown)
|
||||||
|
}
|
||||||
|
|
||||||
|
// pointer could be nil
|
||||||
|
e, ptrNil, isNil := marshalPtrIfNil(e, ntype)
|
||||||
|
if ptrNil != nil {
|
||||||
|
if isNil {
|
||||||
|
return ptrNil, err
|
||||||
|
}
|
||||||
|
ret = append(ret, ptrNil...)
|
||||||
|
}
|
||||||
|
|
||||||
|
switch ctype.Id {
|
||||||
|
case ST_BOOL:
|
||||||
|
if ie, ok := e.(bool); !ok {
|
||||||
|
return ret, fmt.Errorf("ssob: Invalid interface type '%v' expected 'bool': %w", e, ErrTypeInvalid)
|
||||||
|
} else {
|
||||||
|
ret = append(ret, marshalBool(ie)...)
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
case ST_UINT8:
|
||||||
|
if ie, ok := e.(uint8); !ok {
|
||||||
|
return ret, fmt.Errorf("ssob: Invalid interface type '%v' expected 'uint8': %w", e, ErrTypeInvalid)
|
||||||
|
} else {
|
||||||
|
ret = append(ret, marshalUint8(ie)...)
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
case ST_UINT16:
|
||||||
|
if ie, ok := e.(uint16); !ok {
|
||||||
|
return ret, fmt.Errorf("ssob: Invalid interface type '%v' expected 'uint16': %w", e, ErrTypeInvalid)
|
||||||
|
} else {
|
||||||
|
ret = append(ret, marshalUint16(ie)...)
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
case ST_UINT32:
|
||||||
|
if ie, ok := e.(uint32); !ok {
|
||||||
|
return ret, fmt.Errorf("ssob: Invalid interface type '%v' expected 'uint32': %w", e, ErrTypeInvalid)
|
||||||
|
} else {
|
||||||
|
ret = append(ret, marshalUint32(ie)...)
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
case ST_UINT64:
|
||||||
|
if ie, ok := e.(uint64); !ok {
|
||||||
|
return ret, fmt.Errorf("ssob: Invalid interface type '%v' expected 'uint64': %w", e, ErrTypeInvalid)
|
||||||
|
} else {
|
||||||
|
ret = append(ret, marshalUint64(ie)...)
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
case ST_INT8:
|
||||||
|
if ie, ok := e.(int8); !ok {
|
||||||
|
return ret, fmt.Errorf("ssob: Invalid interface type '%v' expected 'int8': %w", e, ErrTypeInvalid)
|
||||||
|
} else {
|
||||||
|
ret = append(ret, marshalInt8(ie)...)
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
case ST_INT16:
|
||||||
|
if ie, ok := e.(int16); !ok {
|
||||||
|
return ret, fmt.Errorf("ssob: Invalid interface type '%v' expected 'int16': %w", e, ErrTypeInvalid)
|
||||||
|
} else {
|
||||||
|
ret = append(ret, marshalInt16(ie)...)
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
case ST_INT32:
|
||||||
|
if ie, ok := e.(int32); !ok {
|
||||||
|
return ret, fmt.Errorf("ssob: Invalid interface type '%v' expected 'int32': %w", e, ErrTypeInvalid)
|
||||||
|
} else {
|
||||||
|
ret = append(ret, marshalInt32(ie)...)
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
case ST_INT64:
|
||||||
|
if ie, ok := e.(int64); !ok {
|
||||||
|
return ret, fmt.Errorf("ssob: Invalid interface type '%v' expected 'int64': %w", e, ErrTypeInvalid)
|
||||||
|
} else {
|
||||||
|
ret = append(ret, marshalInt64(ie)...)
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
case ST_FLOAT32:
|
||||||
|
if ie, ok := e.(float32); !ok {
|
||||||
|
return ret, fmt.Errorf("ssob: Invalid interface type '%v' expected 'float32': %w", e, ErrTypeInvalid)
|
||||||
|
} else {
|
||||||
|
ret = append(ret, marshalFloat32(ie)...)
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
case ST_FLOAT64:
|
||||||
|
if ie, ok := e.(float64); !ok {
|
||||||
|
return ret, fmt.Errorf("ssob: Invalid interface type '%v' expected 'float64': %w", e, ErrTypeInvalid)
|
||||||
|
} else {
|
||||||
|
ret = append(ret, marshalFloat64(ie)...)
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
case ST_STRING:
|
||||||
|
if ie, ok := e.(string); !ok {
|
||||||
|
return ret, fmt.Errorf("ssob: Invalid interface type '%v' expected 'string': %w", e, ErrTypeInvalid)
|
||||||
|
} else {
|
||||||
|
ret = append(ret, marshalString(ie)...)
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
case ST_ERROR:
|
||||||
|
return marshalError(e, ntype)
|
||||||
|
default:
|
||||||
|
return ret, fmt.Errorf("ssob: Unknown common type '%d': %w", ctype.Id, ErrTypeUnknown)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalSlice(e interface{}, ntype *NType) (ret []byte, err error) {
|
||||||
|
v := reflect.ValueOf(e)
|
||||||
|
if v.Kind() != reflect.Slice {
|
||||||
|
return ret, fmt.Errorf("ssob: Invalid value '%v': %w", v.Kind(), ErrValueInvalid)
|
||||||
|
}
|
||||||
|
|
||||||
|
stype := getTypeById(ntype.ValType)
|
||||||
|
if stype == nil {
|
||||||
|
return ret, fmt.Errorf("ssob: Unknown type '%d': %w", ntype.ValType, ErrTypeUnknown)
|
||||||
|
}
|
||||||
|
|
||||||
|
l := v.Len()
|
||||||
|
ret = append(ret, marshalUint32(uint32(l))...)
|
||||||
|
for i := 0; i < l; i++ {
|
||||||
|
tbytes, err := marshalType(v.Index(i).Interface(), stype)
|
||||||
|
if err != nil {
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
ret = append(ret, tbytes...)
|
||||||
|
}
|
||||||
|
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalArray(e interface{}, ntype *NType) (ret []byte, err error) {
|
||||||
|
v := reflect.ValueOf(e)
|
||||||
|
if v.Kind() != reflect.Array {
|
||||||
|
return ret, fmt.Errorf("ssob: Invalid value '%v': %w", v.Kind(), ErrValueInvalid)
|
||||||
|
}
|
||||||
|
|
||||||
|
stype := getTypeById(ntype.ValType)
|
||||||
|
if stype == nil {
|
||||||
|
return ret, fmt.Errorf("ssob: Unknown type '%d': %w", ntype.ValType, ErrTypeUnknown)
|
||||||
|
}
|
||||||
|
|
||||||
|
for i := 0; i < ntype.arrayLen; i++ {
|
||||||
|
tbytes, err := marshalType(v.Index(i).Interface(), stype)
|
||||||
|
if err != nil {
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
ret = append(ret, tbytes...)
|
||||||
|
}
|
||||||
|
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalStruct(e interface{}, ntype *NType) (ret []byte, err error) {
|
||||||
|
v := reflect.ValueOf(e)
|
||||||
|
if v.Kind() != reflect.Struct {
|
||||||
|
return ret, fmt.Errorf("ssob: Invalid value '%v': %w", v.Kind(), ErrValueInvalid)
|
||||||
|
}
|
||||||
|
|
||||||
|
stype := getTypeById(ntype.ValType)
|
||||||
|
if stype == nil {
|
||||||
|
return ret, fmt.Errorf("ssob: Unknown type '%d': %w", ntype.ValType, ErrTypeUnknown)
|
||||||
|
}
|
||||||
|
|
||||||
|
for i, field := range stype.structFields {
|
||||||
|
ftype := getTypeById(field.Id)
|
||||||
|
if ftype == nil {
|
||||||
|
return ret, fmt.Errorf("ssob: Unknown type '%d': %w", field.Id, ErrTypeUnknown)
|
||||||
|
}
|
||||||
|
slog.LOG_DEBUGFLN("sfield: %v", ftype)
|
||||||
|
tbytes, err := marshalType(v.Field(i).Interface(), ftype)
|
||||||
|
if err != nil {
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
ret = append(ret, tbytes...)
|
||||||
|
}
|
||||||
|
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalInterface(e interface{}, ntype *NType) (ret []byte, err error) {
|
||||||
|
stype := getTypeById(ntype.ValType)
|
||||||
|
if stype == nil {
|
||||||
|
return ret, fmt.Errorf("ssob: Unknown type '%d': %w", ntype.ValType, ErrTypeUnknown)
|
||||||
|
}
|
||||||
|
|
||||||
|
return marshalCommon(e, ntype)
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalType(e interface{}, ntype *NType) (ret []byte, err error) {
|
||||||
|
switch ntype.MainTypeId {
|
||||||
|
case ST_COMMON:
|
||||||
|
return marshalCommon(e, ntype)
|
||||||
|
case ST_SLICE:
|
||||||
|
return marshalSlice(e, ntype)
|
||||||
|
case ST_ARRAY:
|
||||||
|
return marshalArray(e, ntype)
|
||||||
|
case ST_STRUCT:
|
||||||
|
return marshalStruct(e, ntype)
|
||||||
|
case ST_INTERFACE:
|
||||||
|
return marshalInterface(e, ntype)
|
||||||
|
default:
|
||||||
|
return ret, fmt.Errorf("ssob: Unknown type '%d': %w", ntype.MainTypeId, ErrTypeUnknown)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func marshalVal(e interface{}) (ret []byte, err error) {
|
||||||
|
i, n, nl, err := indirectType(e)
|
||||||
|
if err != nil {
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
slog.LOG_DEBUGFLN("i: %v | n: %v | nl: %v | err: %v", i, n, nl, err)
|
||||||
|
|
||||||
|
// type id
|
||||||
|
bytes := marshalTypeId(n.Id)
|
||||||
|
|
||||||
|
// nil pointer
|
||||||
|
if i == nil {
|
||||||
|
bytes = append(bytes, marshalTypeId(ST_NIL)...)
|
||||||
|
bytes = append(bytes, marshalNil(nl)...)
|
||||||
|
} else {
|
||||||
|
if tbytes, err := marshalType(i, n); err != nil {
|
||||||
|
return ret, err
|
||||||
|
} else {
|
||||||
|
bytes = append(bytes, tbytes...)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ret = append(ret, marshalUint32(uint32(len(bytes)))...)
|
||||||
|
ret = append(ret, bytes...)
|
||||||
|
|
||||||
|
return ret, err
|
||||||
|
}
|
||||||
|
|
180
types.go
180
types.go
|
@ -12,6 +12,7 @@ type allocatorFunc func(vals ...interface{}) interface{}
|
||||||
type marshallerFunc func(interface{}, io.Writer) error
|
type marshallerFunc func(interface{}, io.Writer) error
|
||||||
type unmarshallerFunc func(io.Reader) (interface{}, error)
|
type unmarshallerFunc func(io.Reader) (interface{}, error)
|
||||||
|
|
||||||
|
type marshalFunc func(interface{}) ([]byte, error)
|
||||||
type nallocFunc func() interface{}
|
type nallocFunc func() interface{}
|
||||||
|
|
||||||
type RegisteredTypes struct {
|
type RegisteredTypes struct {
|
||||||
|
@ -23,16 +24,16 @@ type RegisteredTypes struct {
|
||||||
}
|
}
|
||||||
|
|
||||||
const (
|
const (
|
||||||
ST_COMMON = 0
|
ST_COMMON = 0
|
||||||
ST_SLICE = 1
|
ST_SLICE = 1
|
||||||
ST_ARRAY = 2
|
ST_ARRAY = 2
|
||||||
ST_STRUCT = 3
|
ST_STRUCT = 3
|
||||||
ST_MAP = 4
|
ST_MAP = 4
|
||||||
ST_INTERFACE = 5
|
ST_INTERFACE = 5
|
||||||
ST_STRUCT_FIELD = 6
|
|
||||||
)
|
)
|
||||||
|
|
||||||
type StructField struct {
|
type StructField struct {
|
||||||
|
Id uint32
|
||||||
Name string
|
Name string
|
||||||
Tag string
|
Tag string
|
||||||
}
|
}
|
||||||
|
@ -42,8 +43,9 @@ type NType struct {
|
||||||
Id uint32
|
Id uint32
|
||||||
Indirection int
|
Indirection int
|
||||||
MainTypeId uint32
|
MainTypeId uint32
|
||||||
ValTypes []uint32
|
ValType uint32
|
||||||
structFields []*StructField
|
structFields []*StructField
|
||||||
|
arrayLen int
|
||||||
alloc nallocFunc
|
alloc nallocFunc
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -79,6 +81,7 @@ const (
|
||||||
ST_FLOAT64 = 11
|
ST_FLOAT64 = 11
|
||||||
ST_STRING = 12
|
ST_STRING = 12
|
||||||
ST_ERROR = 13
|
ST_ERROR = 13
|
||||||
|
ST_NIL = 14
|
||||||
)
|
)
|
||||||
|
|
||||||
func init() {
|
func init() {
|
||||||
|
@ -89,96 +92,103 @@ func init() {
|
||||||
cacheTypes.nnames = make(map[string]*NType)
|
cacheTypes.nnames = make(map[string]*NType)
|
||||||
|
|
||||||
boolType := &NType{
|
boolType := &NType{
|
||||||
"bool", ST_BOOL, 0, ST_COMMON, []uint32{ST_BOOL},
|
"bool", ST_BOOL, 0, ST_COMMON, ST_BOOL, nil,
|
||||||
nil, func() interface{} { return new(bool) },
|
0, func() interface{} { return new(bool) },
|
||||||
}
|
}
|
||||||
cacheTypes.ntypes[ST_BOOL] = boolType
|
cacheTypes.ntypes[ST_BOOL] = boolType
|
||||||
cacheTypes.nnames["bool"] = boolType
|
cacheTypes.nnames["bool"] = boolType
|
||||||
|
|
||||||
uint8Type := &NType{
|
uint8Type := &NType{
|
||||||
"uint8", ST_UINT8, 0, ST_COMMON, []uint32{ST_UINT8},
|
"uint8", ST_UINT8, 0, ST_COMMON, ST_UINT8, nil,
|
||||||
nil, func() interface{} { return new(uint8) },
|
0, func() interface{} { return new(uint8) },
|
||||||
}
|
}
|
||||||
cacheTypes.ntypes[ST_UINT8] = uint8Type
|
cacheTypes.ntypes[ST_UINT8] = uint8Type
|
||||||
cacheTypes.nnames["uint8"] = uint8Type
|
cacheTypes.nnames["uint8"] = uint8Type
|
||||||
|
|
||||||
uint16Type := &NType{
|
uint16Type := &NType{
|
||||||
"uint16", ST_UINT16, 0, ST_COMMON, []uint32{ST_UINT16},
|
"uint16", ST_UINT16, 0, ST_COMMON, ST_UINT16, nil,
|
||||||
nil, func() interface{} { return new(uint16) },
|
0, func() interface{} { return new(uint16) },
|
||||||
}
|
}
|
||||||
cacheTypes.ntypes[ST_UINT16] = uint16Type
|
cacheTypes.ntypes[ST_UINT16] = uint16Type
|
||||||
cacheTypes.nnames["uint16"] = uint16Type
|
cacheTypes.nnames["uint16"] = uint16Type
|
||||||
|
|
||||||
uint32Type := &NType{
|
uint32Type := &NType{
|
||||||
"uint32", ST_UINT32, 0, ST_COMMON, []uint32{ST_UINT32},
|
"uint32", ST_UINT32, 0, ST_COMMON, ST_UINT32, nil,
|
||||||
nil, func() interface{} { return new(uint32) },
|
0, func() interface{} { return new(uint32) },
|
||||||
}
|
}
|
||||||
cacheTypes.ntypes[ST_UINT32] = uint32Type
|
cacheTypes.ntypes[ST_UINT32] = uint32Type
|
||||||
cacheTypes.nnames["uint32"] = uint32Type
|
cacheTypes.nnames["uint32"] = uint32Type
|
||||||
|
|
||||||
uint64Type := &NType{
|
uint64Type := &NType{
|
||||||
"uint64", ST_UINT64, 0, ST_COMMON, []uint32{ST_UINT64},
|
"uint64", ST_UINT64, 0, ST_COMMON, ST_UINT64, nil,
|
||||||
nil, func() interface{} { return new(uint64) },
|
0, func() interface{} { return new(uint64) },
|
||||||
}
|
}
|
||||||
cacheTypes.ntypes[ST_UINT64] = uint64Type
|
cacheTypes.ntypes[ST_UINT64] = uint64Type
|
||||||
cacheTypes.nnames["uint64"] = uint64Type
|
cacheTypes.nnames["uint64"] = uint64Type
|
||||||
|
|
||||||
int8Type := &NType{
|
int8Type := &NType{
|
||||||
"int8", ST_INT8, 0, ST_COMMON, []uint32{ST_INT8},
|
"int8", ST_INT8, 0, ST_COMMON, ST_INT8, nil,
|
||||||
nil, func() interface{} { return new(int8) },
|
0, func() interface{} { return new(int8) },
|
||||||
}
|
}
|
||||||
cacheTypes.ntypes[ST_INT8] = int8Type
|
cacheTypes.ntypes[ST_INT8] = int8Type
|
||||||
cacheTypes.nnames["int8"] = int8Type
|
cacheTypes.nnames["int8"] = int8Type
|
||||||
|
|
||||||
int16Type := &NType{
|
int16Type := &NType{
|
||||||
"int16", ST_INT16, 0, ST_COMMON, []uint32{ST_INT16},
|
"int16", ST_INT16, 0, ST_COMMON, ST_INT16, nil,
|
||||||
nil, func() interface{} { return new(int16) },
|
0, func() interface{} { return new(int16) },
|
||||||
}
|
}
|
||||||
cacheTypes.ntypes[ST_INT16] = int16Type
|
cacheTypes.ntypes[ST_INT16] = int16Type
|
||||||
cacheTypes.nnames["int16"] = int16Type
|
cacheTypes.nnames["int16"] = int16Type
|
||||||
|
|
||||||
int32Type := &NType{
|
int32Type := &NType{
|
||||||
"int32", ST_INT32, 0, ST_COMMON, []uint32{ST_INT32},
|
"int32", ST_INT32, 0, ST_COMMON, ST_INT32, nil,
|
||||||
nil, func() interface{} { return new(int32) },
|
0, func() interface{} { return new(int32) },
|
||||||
}
|
}
|
||||||
cacheTypes.ntypes[ST_INT32] = int32Type
|
cacheTypes.ntypes[ST_INT32] = int32Type
|
||||||
cacheTypes.nnames["int32"] = int32Type
|
cacheTypes.nnames["int32"] = int32Type
|
||||||
|
|
||||||
int64Type := &NType{
|
int64Type := &NType{
|
||||||
"int64", ST_INT64, 0, ST_COMMON, []uint32{ST_INT64},
|
"int64", ST_INT64, 0, ST_COMMON, ST_INT64, nil,
|
||||||
nil, func() interface{} { return new(int64) },
|
0, func() interface{} { return new(int64) },
|
||||||
}
|
}
|
||||||
cacheTypes.ntypes[ST_INT64] = int64Type
|
cacheTypes.ntypes[ST_INT64] = int64Type
|
||||||
cacheTypes.nnames["int64"] = int64Type
|
cacheTypes.nnames["int64"] = int64Type
|
||||||
|
|
||||||
float32Type := &NType{
|
float32Type := &NType{
|
||||||
"float32", ST_FLOAT32, 0, ST_COMMON, []uint32{ST_FLOAT32},
|
"float32", ST_FLOAT32, 0, ST_COMMON, ST_FLOAT32, nil,
|
||||||
nil, func() interface{} { return new(float32) },
|
0, func() interface{} { return new(float32) },
|
||||||
}
|
}
|
||||||
cacheTypes.ntypes[ST_FLOAT32] = float32Type
|
cacheTypes.ntypes[ST_FLOAT32] = float32Type
|
||||||
cacheTypes.nnames["float32"] = float32Type
|
cacheTypes.nnames["float32"] = float32Type
|
||||||
|
|
||||||
float64Type := &NType{
|
float64Type := &NType{
|
||||||
"float64", ST_FLOAT64, 0, ST_COMMON, []uint32{ST_FLOAT64},
|
"float64", ST_FLOAT64, 0, ST_COMMON, ST_FLOAT64, nil,
|
||||||
nil, func() interface{} { return new(float64) },
|
0, func() interface{} { return new(float64) },
|
||||||
}
|
}
|
||||||
cacheTypes.ntypes[ST_FLOAT64] = float64Type
|
cacheTypes.ntypes[ST_FLOAT64] = float64Type
|
||||||
cacheTypes.nnames["float64"] = float64Type
|
cacheTypes.nnames["float64"] = float64Type
|
||||||
|
|
||||||
stringType := &NType{
|
stringType := &NType{
|
||||||
"string", ST_STRING, 0, ST_COMMON, []uint32{ST_STRING},
|
"string", ST_STRING, 0, ST_COMMON, ST_STRING, nil,
|
||||||
nil, func() interface{} { return new(string) },
|
0, func() interface{} { return new(string) },
|
||||||
}
|
}
|
||||||
cacheTypes.ntypes[ST_STRING] = stringType
|
cacheTypes.ntypes[ST_STRING] = stringType
|
||||||
cacheTypes.nnames["string"] = stringType
|
cacheTypes.nnames["string"] = stringType
|
||||||
|
|
||||||
errorType := &NType{
|
errorType := &NType{
|
||||||
"error", ST_ERROR, 0, ST_COMMON, []uint32{ST_ERROR},
|
"error", ST_ERROR, 0, ST_COMMON, ST_ERROR, nil,
|
||||||
nil, func() interface{} { return new(error) },
|
0, func() interface{} { return new(error) },
|
||||||
}
|
}
|
||||||
cacheTypes.ntypes[ST_ERROR] = errorType
|
cacheTypes.ntypes[ST_ERROR] = errorType
|
||||||
cacheTypes.nnames["error"] = errorType
|
cacheTypes.nnames["error"] = errorType
|
||||||
|
|
||||||
|
nilType := &NType{
|
||||||
|
"nil", ST_NIL, 0, ST_NIL, ST_NIL, nil,
|
||||||
|
0, func() interface{} { return nil },
|
||||||
|
}
|
||||||
|
cacheTypes.ntypes[ST_NIL] = nilType
|
||||||
|
cacheTypes.nnames["nil"] = nilType
|
||||||
|
|
||||||
cacheTypes.types[ST_BOOL] = Type{
|
cacheTypes.types[ST_BOOL] = Type{
|
||||||
"bool", ST_BOOL,
|
"bool", ST_BOOL,
|
||||||
func(vals ...interface{}) interface{} { return new(bool) },
|
func(vals ...interface{}) interface{} { return new(bool) },
|
||||||
|
@ -344,7 +354,7 @@ func getTypeByName(name string) (ret *NType) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func parseType(t reflect.Type) (ret nallocFunc, mainTypeId uint32, indirection int, valTypes []uint32, base bool, sfields []*StructField, err error) {
|
func parseType(t reflect.Type) (ret nallocFunc, mainTypeId uint32, indirection int, valType uint32, base bool, sfields []*StructField, arrayLen int, err error) {
|
||||||
indirection = 0
|
indirection = 0
|
||||||
ret = func() interface{} {
|
ret = func() interface{} {
|
||||||
vret := reflect.New(t)
|
vret := reflect.New(t)
|
||||||
|
@ -361,8 +371,8 @@ func parseType(t reflect.Type) (ret nallocFunc, mainTypeId uint32, indirection i
|
||||||
return vret.Interface()
|
return vret.Interface()
|
||||||
}
|
}
|
||||||
|
|
||||||
valTypes = []uint32{}
|
|
||||||
sfields = []*StructField{}
|
sfields = []*StructField{}
|
||||||
|
arrayLen = 0
|
||||||
vret := reflect.New(t)
|
vret := reflect.New(t)
|
||||||
val := vret.Elem()
|
val := vret.Elem()
|
||||||
nval := vret
|
nval := vret
|
||||||
|
@ -385,25 +395,27 @@ func parseType(t reflect.Type) (ret nallocFunc, mainTypeId uint32, indirection i
|
||||||
typ := reflect.TypeOf(val.Interface())
|
typ := reflect.TypeOf(val.Interface())
|
||||||
slog.LOG_DEBUGFLN("typ.Kind(): %s", typ.Kind())
|
slog.LOG_DEBUGFLN("typ.Kind(): %s", typ.Kind())
|
||||||
slog.LOG_DEBUGFLN("val.Type(): %s", typ.Elem())
|
slog.LOG_DEBUGFLN("val.Type(): %s", typ.Elem())
|
||||||
|
slog.LOG_DEBUGFLN("SLICE")
|
||||||
vt, err := getTypeByNameRegister(typ.Elem().String(), typ.Elem())
|
vt, err := getTypeByNameRegister(typ.Elem().String(), typ.Elem())
|
||||||
slog.LOG_DEBUGFLN("vt: %v", vt)
|
slog.LOG_DEBUGFLN("vt: %v", vt)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return ret, mainTypeId, indirection, valTypes, base, sfields, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
return ret, mainTypeId, indirection, valType, base, sfields, arrayLen, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
||||||
}
|
}
|
||||||
valTypes = append(valTypes, vt.Id)
|
valType = vt.Id
|
||||||
base = false
|
base = false
|
||||||
mainTypeId = ST_SLICE
|
mainTypeId = ST_SLICE
|
||||||
case reflect.Array:
|
case reflect.Array:
|
||||||
typ := reflect.TypeOf(val.Interface())
|
typ := reflect.TypeOf(val.Interface())
|
||||||
|
arrayLen = val.Len()
|
||||||
slog.LOG_DEBUGFLN("typ.Kind(): %s", typ.Kind())
|
slog.LOG_DEBUGFLN("typ.Kind(): %s", typ.Kind())
|
||||||
slog.LOG_DEBUGFLN("val.Type(): %s", typ.Elem())
|
slog.LOG_DEBUGFLN("val.Type(): %s", typ.Elem())
|
||||||
|
slog.LOG_DEBUGFLN("ARRAY")
|
||||||
vt, err := getTypeByNameRegister(typ.Elem().String(), typ.Elem())
|
vt, err := getTypeByNameRegister(typ.Elem().String(), typ.Elem())
|
||||||
slog.LOG_DEBUGFLN("vt: %v", vt)
|
slog.LOG_DEBUGFLN("vt: %v", vt)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return ret, mainTypeId, indirection, valTypes, base, sfields, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
return ret, mainTypeId, indirection, valType, base, sfields, arrayLen, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
||||||
}
|
}
|
||||||
valTypes = append(valTypes, uint32(val.Len()))
|
valType = vt.Id
|
||||||
valTypes = append(valTypes, vt.Id)
|
|
||||||
base = false
|
base = false
|
||||||
mainTypeId = ST_ARRAY
|
mainTypeId = ST_ARRAY
|
||||||
case reflect.Interface:
|
case reflect.Interface:
|
||||||
|
@ -414,9 +426,9 @@ func parseType(t reflect.Type) (ret nallocFunc, mainTypeId uint32, indirection i
|
||||||
vt, err := getTypeByNameRegister(typ.Elem().String(), typ.Elem())
|
vt, err := getTypeByNameRegister(typ.Elem().String(), typ.Elem())
|
||||||
slog.LOG_DEBUGFLN("vt: %v", vt)
|
slog.LOG_DEBUGFLN("vt: %v", vt)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return ret, mainTypeId, indirection, valTypes, base, sfields, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
return ret, mainTypeId, indirection, valType, base, sfields, arrayLen, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
||||||
}
|
}
|
||||||
valTypes = append(valTypes, vt.Id)
|
valType = vt.Id
|
||||||
}
|
}
|
||||||
mainTypeId = ST_INTERFACE
|
mainTypeId = ST_INTERFACE
|
||||||
case reflect.Struct:
|
case reflect.Struct:
|
||||||
|
@ -427,9 +439,9 @@ func parseType(t reflect.Type) (ret nallocFunc, mainTypeId uint32, indirection i
|
||||||
vt, err := getTypeByNameRegister(typ.String(), typ)
|
vt, err := getTypeByNameRegister(typ.String(), typ)
|
||||||
slog.LOG_DEBUGFLN("vt: %v", vt)
|
slog.LOG_DEBUGFLN("vt: %v", vt)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return ret, mainTypeId, indirection, valTypes, base, sfields, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
return ret, mainTypeId, indirection, valType, base, sfields, arrayLen, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
||||||
}
|
}
|
||||||
valTypes = append(valTypes, vt.Id)
|
valType = vt.Id
|
||||||
} else {
|
} else {
|
||||||
sl := val.NumField()
|
sl := val.NumField()
|
||||||
for i := 0; i < sl; i++ {
|
for i := 0; i < sl; i++ {
|
||||||
|
@ -438,12 +450,12 @@ func parseType(t reflect.Type) (ret nallocFunc, mainTypeId uint32, indirection i
|
||||||
sfield := new(StructField)
|
sfield := new(StructField)
|
||||||
sfield.Name = val.Type().Field(i).Name
|
sfield.Name = val.Type().Field(i).Name
|
||||||
sfield.Tag = string(val.Type().Field(i).Tag)
|
sfield.Tag = string(val.Type().Field(i).Tag)
|
||||||
sfields = append(sfields, sfield)
|
|
||||||
vt, err := getTypeByNameRegister(val.Field(i).Type().String(), val.Field(i).Type())
|
vt, err := getTypeByNameRegister(val.Field(i).Type().String(), val.Field(i).Type())
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return ret, mainTypeId, indirection, valTypes, base, sfields, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
return ret, mainTypeId, indirection, valType, base, sfields, arrayLen, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
||||||
}
|
}
|
||||||
valTypes = append(valTypes, vt.Id)
|
sfield.Id = vt.Id
|
||||||
|
sfields = append(sfields, sfield)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
base = false
|
base = false
|
||||||
|
@ -459,25 +471,25 @@ func parseType(t reflect.Type) (ret nallocFunc, mainTypeId uint32, indirection i
|
||||||
vt, err := getTypeByNameRegister(typ.String(), typ)
|
vt, err := getTypeByNameRegister(typ.String(), typ)
|
||||||
slog.LOG_DEBUGFLN("vt: %v", vt)
|
slog.LOG_DEBUGFLN("vt: %v", vt)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return ret, mainTypeId, indirection, valTypes, base, sfields, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
return ret, mainTypeId, indirection, valType, base, sfields, arrayLen, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
||||||
}
|
}
|
||||||
valTypes = append(valTypes, vt.Id)
|
valType = vt.Id
|
||||||
} else {
|
} else {
|
||||||
// Key
|
// Key
|
||||||
vt, err := getTypeByNameRegister(typ.Key().String(), typ.Key())
|
vt, err := getTypeByNameRegister(typ.Key().String(), typ.Key())
|
||||||
slog.LOG_DEBUGFLN("vt: %v", vt)
|
slog.LOG_DEBUGFLN("vt: %v", vt)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return ret, mainTypeId, indirection, valTypes, base, sfields, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
return ret, mainTypeId, indirection, valType, base, sfields, arrayLen, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
||||||
}
|
}
|
||||||
valTypes = append(valTypes, vt.Id)
|
valType = vt.Id
|
||||||
|
|
||||||
// Val
|
// Val
|
||||||
vt, err = getTypeByNameRegister(typ.Elem().String(), typ.Elem())
|
vt, err = getTypeByNameRegister(typ.Elem().String(), typ.Elem())
|
||||||
slog.LOG_DEBUGFLN("vt: %v", vt)
|
slog.LOG_DEBUGFLN("vt: %v", vt)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return ret, mainTypeId, indirection, valTypes, base, sfields, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
return ret, mainTypeId, indirection, valType, base, sfields, arrayLen, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
||||||
}
|
}
|
||||||
valTypes = append(valTypes, vt.Id)
|
valType = vt.Id
|
||||||
base = false
|
base = false
|
||||||
}
|
}
|
||||||
mainTypeId = ST_MAP
|
mainTypeId = ST_MAP
|
||||||
|
@ -489,9 +501,9 @@ func parseType(t reflect.Type) (ret nallocFunc, mainTypeId uint32, indirection i
|
||||||
vt, err := getTypeByNameRegister(typ.Kind().String(), typ)
|
vt, err := getTypeByNameRegister(typ.Kind().String(), typ)
|
||||||
slog.LOG_DEBUGFLN("vt: %v", vt)
|
slog.LOG_DEBUGFLN("vt: %v", vt)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return ret, mainTypeId, indirection, valTypes, base, sfields, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
return ret, mainTypeId, indirection, valType, base, sfields, arrayLen, fmt.Errorf("ssob: Failed receiving type '%s': %w", typ.Elem(), err)
|
||||||
}
|
}
|
||||||
valTypes = append(valTypes, vt.Id)
|
valType = vt.Id
|
||||||
}
|
}
|
||||||
mainTypeId = ST_COMMON
|
mainTypeId = ST_COMMON
|
||||||
}
|
}
|
||||||
|
@ -499,7 +511,7 @@ func parseType(t reflect.Type) (ret nallocFunc, mainTypeId uint32, indirection i
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return ret, mainTypeId, indirection, valTypes, base, sfields, err
|
return ret, mainTypeId, indirection, valType, base, sfields, arrayLen, err
|
||||||
}
|
}
|
||||||
|
|
||||||
func getTypeByNameRegister(name string, t reflect.Type) (ret *NType, err error) {
|
func getTypeByNameRegister(name string, t reflect.Type) (ret *NType, err error) {
|
||||||
|
@ -526,7 +538,7 @@ func createType(t reflect.Type) (ret *NType, base bool, err error) {
|
||||||
ret = new(NType)
|
ret = new(NType)
|
||||||
ret.Name = t.String()
|
ret.Name = t.String()
|
||||||
slog.LOG_DEBUGFLN("t.Name(): %s", t)
|
slog.LOG_DEBUGFLN("t.Name(): %s", t)
|
||||||
ret.alloc, ret.MainTypeId, ret.Indirection, ret.ValTypes, base, ret.structFields, err = parseType(t)
|
ret.alloc, ret.MainTypeId, ret.Indirection, ret.ValType, base, ret.structFields, ret.arrayLen, err = parseType(t)
|
||||||
|
|
||||||
return ret, base, err
|
return ret, base, err
|
||||||
}
|
}
|
||||||
|
@ -547,7 +559,7 @@ func registerType(t reflect.Type) (err error) {
|
||||||
}
|
}
|
||||||
ntype.Id = cacheTypes.NextId
|
ntype.Id = cacheTypes.NextId
|
||||||
if base {
|
if base {
|
||||||
ntype.ValTypes = []uint32{ntype.Id}
|
ntype.ValType = ntype.Id
|
||||||
}
|
}
|
||||||
cacheTypes.ntypes[ntype.Id] = ntype
|
cacheTypes.ntypes[ntype.Id] = ntype
|
||||||
cacheTypes.nnames[ntype.Name] = ntype
|
cacheTypes.nnames[ntype.Name] = ntype
|
||||||
|
@ -563,7 +575,55 @@ func registerType(t reflect.Type) (err error) {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func splitType(e interface{}) (t reflect.Type, v reflect.Value, err error) {
|
||||||
|
t = reflect.TypeOf(e)
|
||||||
|
if t == nil || t.Kind() != reflect.Ptr {
|
||||||
|
return t, v, fmt.Errorf("ssob: Interface is not a valid address: %w", ErrTypeInvalid)
|
||||||
|
}
|
||||||
|
|
||||||
|
v = reflect.ValueOf(e)
|
||||||
|
if v.IsNil() {
|
||||||
|
return t, v, fmt.Errorf("ssob: Got nil: %w", ErrValueInvalid)
|
||||||
|
}
|
||||||
|
|
||||||
|
return t, v, err
|
||||||
|
}
|
||||||
|
|
||||||
|
func indirectType(e interface{}) (ret interface{}, ntype *NType, nilLevel uint16, err error) {
|
||||||
|
nilLevel = 0
|
||||||
|
|
||||||
|
t, v, err := splitType(e)
|
||||||
|
if err != nil {
|
||||||
|
return nil, nil, nilLevel, err
|
||||||
|
}
|
||||||
|
|
||||||
|
ntype, err = getTypeByNameRegister(t.Elem().String(), t.Elem())
|
||||||
|
if err != nil {
|
||||||
|
return nil, nil, nilLevel, err
|
||||||
|
}
|
||||||
|
|
||||||
|
for i := 0; i < ntype.Indirection; i++ {
|
||||||
|
v = reflect.Indirect(v)
|
||||||
|
if v.IsNil() {
|
||||||
|
nilLevel += uint16(i)
|
||||||
|
return nil, ntype, nilLevel, err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return reflect.Indirect(v).Interface(), ntype, nilLevel, err
|
||||||
|
}
|
||||||
|
|
||||||
func RegisterType(e interface{}) (err error) {
|
func RegisterType(e interface{}) (err error) {
|
||||||
t := reflect.TypeOf(e)
|
t := reflect.TypeOf(e)
|
||||||
return registerType(t)
|
if t == nil || t.Kind() != reflect.Ptr {
|
||||||
|
return fmt.Errorf("ssob: Interface is not a valid address: %w", ErrTypeInvalid)
|
||||||
|
}
|
||||||
|
|
||||||
|
if err = registerType(t.Elem()); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
b, ee := marshalVal(e)
|
||||||
|
slog.LOG_DEBUGFLN("Bytes: %v | err: %v", b, ee)
|
||||||
|
return ee
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue