mirror of https://github.com/goccy/go-json.git
Merge pull request #59 from goccy/feature/refactor-ptr
Refactor cast manipulation from uintptr
This commit is contained in:
commit
71f8fc352b
450
encode_vm.go
450
encode_vm.go
|
@ -35,6 +35,20 @@ func errUnsupportedValue(code *opcode, ptr uintptr) *UnsupportedValueError {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func errUnsupportedFloat(v float64) *UnsupportedValueError {
|
||||||
|
return &UnsupportedValueError{
|
||||||
|
Value: reflect.ValueOf(v),
|
||||||
|
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func errMarshaler(code *opcode, err error) *MarshalerError {
|
||||||
|
return &MarshalerError{
|
||||||
|
Type: rtype2type(code.typ),
|
||||||
|
Err: err,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
recursiveLevel := 0
|
recursiveLevel := 0
|
||||||
seenPtr := map[uintptr]struct{}{}
|
seenPtr := map[uintptr]struct{}{}
|
||||||
|
@ -140,10 +154,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
case opFloat64:
|
case opFloat64:
|
||||||
v := e.ptrToFloat64(load(ctxptr, code.idx))
|
v := e.ptrToFloat64(load(ctxptr, code.idx))
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeFloat64(v)
|
e.encodeFloat64(v)
|
||||||
e.encodeByte(',')
|
e.encodeByte(',')
|
||||||
|
@ -151,10 +162,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
case opFloat64Indent:
|
case opFloat64Indent:
|
||||||
v := e.ptrToFloat64(load(ctxptr, code.idx))
|
v := e.ptrToFloat64(load(ctxptr, code.idx))
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeFloat64(v)
|
e.encodeFloat64(v)
|
||||||
e.encodeBytes([]byte{',', '\n'})
|
e.encodeBytes([]byte{',', '\n'})
|
||||||
|
@ -177,8 +185,8 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
code = code.next
|
code = code.next
|
||||||
case opBytes:
|
case opBytes:
|
||||||
ptr := load(ctxptr, code.idx)
|
ptr := load(ctxptr, code.idx)
|
||||||
header := *(**sliceHeader)(unsafe.Pointer(&ptr))
|
slice := e.ptrToSlice(ptr)
|
||||||
if ptr == 0 || uintptr(header.data) == 0 {
|
if ptr == 0 || uintptr(slice.data) == 0 {
|
||||||
e.encodeNull()
|
e.encodeNull()
|
||||||
} else {
|
} else {
|
||||||
e.encodeByteSlice(e.ptrToBytes(ptr))
|
e.encodeByteSlice(e.ptrToBytes(ptr))
|
||||||
|
@ -187,8 +195,8 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
code = code.next
|
code = code.next
|
||||||
case opBytesIndent:
|
case opBytesIndent:
|
||||||
ptr := load(ctxptr, code.idx)
|
ptr := load(ctxptr, code.idx)
|
||||||
header := (*sliceHeader)(unsafe.Pointer(&ptr))
|
slice := e.ptrToSlice(ptr)
|
||||||
if ptr == 0 || uintptr(header.data) == 0 {
|
if ptr == 0 || uintptr(slice.data) == 0 {
|
||||||
e.encodeNull()
|
e.encodeNull()
|
||||||
} else {
|
} else {
|
||||||
e.encodeByteSlice(e.ptrToBytes(ptr))
|
e.encodeByteSlice(e.ptrToBytes(ptr))
|
||||||
|
@ -203,17 +211,11 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
code = code.next
|
code = code.next
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&ptr)),
|
|
||||||
}))
|
|
||||||
if _, exists := seenPtr[ptr]; exists {
|
if _, exists := seenPtr[ptr]; exists {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedValue(code, ptr)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: fmt.Sprintf("encountered a cycle via %s", code.typ),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
seenPtr[ptr] = struct{}{}
|
seenPtr[ptr] = struct{}{}
|
||||||
|
v := e.ptrToInterface(code, ptr)
|
||||||
rv := reflect.ValueOf(v)
|
rv := reflect.ValueOf(v)
|
||||||
if rv.IsNil() {
|
if rv.IsNil() {
|
||||||
e.encodeNull()
|
e.encodeNull()
|
||||||
|
@ -285,17 +287,11 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
code = code.next
|
code = code.next
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&ptr)),
|
|
||||||
}))
|
|
||||||
if _, exists := seenPtr[ptr]; exists {
|
if _, exists := seenPtr[ptr]; exists {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedValue(code, ptr)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: fmt.Sprintf("encountered a cycle via %s", code.typ),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
seenPtr[ptr] = struct{}{}
|
seenPtr[ptr] = struct{}{}
|
||||||
|
v := e.ptrToInterface(code, ptr)
|
||||||
rv := reflect.ValueOf(v)
|
rv := reflect.ValueOf(v)
|
||||||
if rv.IsNil() {
|
if rv.IsNil() {
|
||||||
e.encodeNull()
|
e.encodeNull()
|
||||||
|
@ -368,16 +364,10 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
code = code.next
|
code = code.next
|
||||||
case opMarshalJSON:
|
case opMarshalJSON:
|
||||||
ptr := load(ctxptr, code.idx)
|
ptr := load(ctxptr, code.idx)
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
v := e.ptrToInterface(code, ptr)
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&ptr)),
|
|
||||||
}))
|
|
||||||
b, err := v.(Marshaler).MarshalJSON()
|
b, err := v.(Marshaler).MarshalJSON()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
if len(b) == 0 {
|
if len(b) == 0 {
|
||||||
return errUnexpectedEndOfJSON(
|
return errUnexpectedEndOfJSON(
|
||||||
|
@ -386,35 +376,18 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
var buf bytes.Buffer
|
var buf bytes.Buffer
|
||||||
if e.enabledIndent {
|
|
||||||
if err := encodeWithIndent(
|
|
||||||
&buf,
|
|
||||||
b,
|
|
||||||
string(e.prefix)+string(bytes.Repeat(e.indentStr, code.indent)),
|
|
||||||
string(e.indentStr),
|
|
||||||
); err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if err := compact(&buf, b, e.enabledHTMLEscape); err != nil {
|
if err := compact(&buf, b, e.enabledHTMLEscape); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
}
|
|
||||||
e.encodeBytes(buf.Bytes())
|
e.encodeBytes(buf.Bytes())
|
||||||
e.encodeByte(',')
|
e.encodeByte(',')
|
||||||
code = code.next
|
code = code.next
|
||||||
case opMarshalJSONIndent:
|
case opMarshalJSONIndent:
|
||||||
ptr := load(ctxptr, code.idx)
|
ptr := load(ctxptr, code.idx)
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
v := e.ptrToInterface(code, ptr)
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&ptr)),
|
|
||||||
}))
|
|
||||||
b, err := v.(Marshaler).MarshalJSON()
|
b, err := v.(Marshaler).MarshalJSON()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
if len(b) == 0 {
|
if len(b) == 0 {
|
||||||
return errUnexpectedEndOfJSON(
|
return errUnexpectedEndOfJSON(
|
||||||
|
@ -423,7 +396,6 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
var buf bytes.Buffer
|
var buf bytes.Buffer
|
||||||
if e.enabledIndent {
|
|
||||||
if err := encodeWithIndent(
|
if err := encodeWithIndent(
|
||||||
&buf,
|
&buf,
|
||||||
b,
|
b,
|
||||||
|
@ -432,24 +404,18 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
); err != nil {
|
); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
} else {
|
|
||||||
if err := compact(&buf, b, e.enabledHTMLEscape); err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
}
|
|
||||||
e.encodeBytes(buf.Bytes())
|
e.encodeBytes(buf.Bytes())
|
||||||
e.encodeBytes([]byte{',', '\n'})
|
e.encodeBytes([]byte{',', '\n'})
|
||||||
code = code.next
|
code = code.next
|
||||||
case opMarshalText:
|
case opMarshalText:
|
||||||
ptr := load(ctxptr, code.idx)
|
ptr := load(ctxptr, code.idx)
|
||||||
isPtr := code.typ.Kind() == reflect.Ptr
|
isPtr := code.typ.Kind() == reflect.Ptr
|
||||||
p := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
p := e.ptrToUnsafePtr(ptr)
|
||||||
if p == nil {
|
if p == nil {
|
||||||
e.encodeNull()
|
e.encodeNull()
|
||||||
e.encodeByte(',')
|
e.encodeByte(',')
|
||||||
} else if isPtr && *(*unsafe.Pointer)(p) == nil {
|
} else if isPtr && *(*unsafe.Pointer)(p) == nil {
|
||||||
e.encodeBytes([]byte{'"', '"'})
|
e.encodeBytes([]byte{'"', '"', ','})
|
||||||
e.encodeByte(',')
|
|
||||||
} else {
|
} else {
|
||||||
if isPtr && code.typ.Elem().Implements(marshalTextType) {
|
if isPtr && code.typ.Elem().Implements(marshalTextType) {
|
||||||
p = *(*unsafe.Pointer)(p)
|
p = *(*unsafe.Pointer)(p)
|
||||||
|
@ -460,10 +426,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
}))
|
}))
|
||||||
bytes, err := v.(encoding.TextMarshaler).MarshalText()
|
bytes, err := v.(encoding.TextMarshaler).MarshalText()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
||||||
e.encodeByte(',')
|
e.encodeByte(',')
|
||||||
|
@ -472,13 +435,12 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
case opMarshalTextIndent:
|
case opMarshalTextIndent:
|
||||||
ptr := load(ctxptr, code.idx)
|
ptr := load(ctxptr, code.idx)
|
||||||
isPtr := code.typ.Kind() == reflect.Ptr
|
isPtr := code.typ.Kind() == reflect.Ptr
|
||||||
p := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
p := e.ptrToUnsafePtr(ptr)
|
||||||
if p == nil {
|
if p == nil {
|
||||||
e.encodeNull()
|
e.encodeNull()
|
||||||
e.encodeBytes([]byte{',', '\n'})
|
e.encodeBytes([]byte{',', '\n'})
|
||||||
} else if isPtr && *(*unsafe.Pointer)(p) == nil {
|
} else if isPtr && *(*unsafe.Pointer)(p) == nil {
|
||||||
e.encodeBytes([]byte{'"', '"'})
|
e.encodeBytes([]byte{'"', '"', ',', '\n'})
|
||||||
e.encodeBytes([]byte{',', '\n'})
|
|
||||||
} else {
|
} else {
|
||||||
if isPtr && code.typ.Elem().Implements(marshalTextType) {
|
if isPtr && code.typ.Elem().Implements(marshalTextType) {
|
||||||
p = *(*unsafe.Pointer)(p)
|
p = *(*unsafe.Pointer)(p)
|
||||||
|
@ -489,10 +451,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
}))
|
}))
|
||||||
bytes, err := v.(encoding.TextMarshaler).MarshalText()
|
bytes, err := v.(encoding.TextMarshaler).MarshalText()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
||||||
e.encodeBytes([]byte{',', '\n'})
|
e.encodeBytes([]byte{',', '\n'})
|
||||||
|
@ -500,19 +459,19 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
code = code.next
|
code = code.next
|
||||||
case opSliceHead:
|
case opSliceHead:
|
||||||
p := load(ctxptr, code.idx)
|
p := load(ctxptr, code.idx)
|
||||||
header := *(**sliceHeader)(unsafe.Pointer(&p))
|
slice := e.ptrToSlice(p)
|
||||||
if p == 0 || uintptr(header.data) == 0 {
|
if p == 0 || uintptr(slice.data) == 0 {
|
||||||
e.encodeNull()
|
e.encodeNull()
|
||||||
e.encodeByte(',')
|
e.encodeByte(',')
|
||||||
code = code.end.next
|
code = code.end.next
|
||||||
} else {
|
} else {
|
||||||
store(ctxptr, code.elemIdx, 0)
|
store(ctxptr, code.elemIdx, 0)
|
||||||
store(ctxptr, code.length, uintptr(header.len))
|
store(ctxptr, code.length, uintptr(slice.len))
|
||||||
store(ctxptr, code.idx, uintptr(header.data))
|
store(ctxptr, code.idx, uintptr(slice.data))
|
||||||
if header.len > 0 {
|
if slice.len > 0 {
|
||||||
e.encodeByte('[')
|
e.encodeByte('[')
|
||||||
code = code.next
|
code = code.next
|
||||||
store(ctxptr, code.idx, uintptr(header.data))
|
store(ctxptr, code.idx, uintptr(slice.data))
|
||||||
} else {
|
} else {
|
||||||
e.encodeBytes([]byte{'[', ']', ','})
|
e.encodeBytes([]byte{'[', ']', ','})
|
||||||
code = code.end.next
|
code = code.end.next
|
||||||
|
@ -542,15 +501,15 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
e.encodeBytes([]byte{',', '\n'})
|
e.encodeBytes([]byte{',', '\n'})
|
||||||
code = code.end.next
|
code = code.end.next
|
||||||
} else {
|
} else {
|
||||||
header := *(**sliceHeader)(unsafe.Pointer(&p))
|
slice := e.ptrToSlice(p)
|
||||||
store(ctxptr, code.elemIdx, 0)
|
store(ctxptr, code.elemIdx, 0)
|
||||||
store(ctxptr, code.length, uintptr(header.len))
|
store(ctxptr, code.length, uintptr(slice.len))
|
||||||
store(ctxptr, code.idx, uintptr(header.data))
|
store(ctxptr, code.idx, uintptr(slice.data))
|
||||||
if header.len > 0 {
|
if slice.len > 0 {
|
||||||
e.encodeBytes([]byte{'[', '\n'})
|
e.encodeBytes([]byte{'[', '\n'})
|
||||||
e.encodeIndent(code.indent + 1)
|
e.encodeIndent(code.indent + 1)
|
||||||
code = code.next
|
code = code.next
|
||||||
store(ctxptr, code.idx, uintptr(header.data))
|
store(ctxptr, code.idx, uintptr(slice.data))
|
||||||
} else {
|
} else {
|
||||||
e.encodeIndent(code.indent)
|
e.encodeIndent(code.indent)
|
||||||
e.encodeBytes([]byte{'[', ']', '\n'})
|
e.encodeBytes([]byte{'[', ']', '\n'})
|
||||||
|
@ -565,15 +524,15 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
e.encodeBytes([]byte{',', '\n'})
|
e.encodeBytes([]byte{',', '\n'})
|
||||||
code = code.end.next
|
code = code.end.next
|
||||||
} else {
|
} else {
|
||||||
header := *(**sliceHeader)(unsafe.Pointer(&p))
|
slice := e.ptrToSlice(p)
|
||||||
store(ctxptr, code.elemIdx, 0)
|
store(ctxptr, code.elemIdx, 0)
|
||||||
store(ctxptr, code.length, uintptr(header.len))
|
store(ctxptr, code.length, uintptr(slice.len))
|
||||||
store(ctxptr, code.idx, uintptr(header.data))
|
store(ctxptr, code.idx, uintptr(slice.data))
|
||||||
if header.len > 0 {
|
if slice.len > 0 {
|
||||||
e.encodeBytes([]byte{'[', '\n'})
|
e.encodeBytes([]byte{'[', '\n'})
|
||||||
e.encodeIndent(code.indent + 1)
|
e.encodeIndent(code.indent + 1)
|
||||||
code = code.next
|
code = code.next
|
||||||
store(ctxptr, code.idx, uintptr(header.data))
|
store(ctxptr, code.idx, uintptr(slice.data))
|
||||||
} else {
|
} else {
|
||||||
e.encodeIndent(code.indent)
|
e.encodeIndent(code.indent)
|
||||||
e.encodeBytes([]byte{'[', ']', ',', '\n'})
|
e.encodeBytes([]byte{'[', ']', ',', '\n'})
|
||||||
|
@ -690,7 +649,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
e.encodeByte(',')
|
e.encodeByte(',')
|
||||||
code = code.end.next
|
code = code.end.next
|
||||||
} else {
|
} else {
|
||||||
uptr := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
uptr := e.ptrToUnsafePtr(ptr)
|
||||||
mlen := maplen(uptr)
|
mlen := maplen(uptr)
|
||||||
if mlen > 0 {
|
if mlen > 0 {
|
||||||
e.encodeByte('{')
|
e.encodeByte('{')
|
||||||
|
@ -722,8 +681,8 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
code = code.end.next
|
code = code.end.next
|
||||||
} else {
|
} else {
|
||||||
// load pointer
|
// load pointer
|
||||||
ptr = uintptr(**(**unsafe.Pointer)(unsafe.Pointer(&ptr)))
|
ptr = e.ptrToPtr(ptr)
|
||||||
uptr := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
uptr := e.ptrToUnsafePtr(ptr)
|
||||||
if ptr == 0 {
|
if ptr == 0 {
|
||||||
e.encodeNull()
|
e.encodeNull()
|
||||||
e.encodeByte(',')
|
e.encodeByte(',')
|
||||||
|
@ -760,7 +719,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
if e.unorderedMap {
|
if e.unorderedMap {
|
||||||
if idx < length {
|
if idx < length {
|
||||||
ptr := load(ctxptr, code.mapIter)
|
ptr := load(ctxptr, code.mapIter)
|
||||||
iter := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
iter := e.ptrToUnsafePtr(ptr)
|
||||||
store(ctxptr, code.elemIdx, idx)
|
store(ctxptr, code.elemIdx, idx)
|
||||||
key := mapiterkey(iter)
|
key := mapiterkey(iter)
|
||||||
store(ctxptr, code.next.idx, uintptr(key))
|
store(ctxptr, code.next.idx, uintptr(key))
|
||||||
|
@ -777,7 +736,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
*posPtr = append(*posPtr, len(e.buf))
|
*posPtr = append(*posPtr, len(e.buf))
|
||||||
if idx < length {
|
if idx < length {
|
||||||
ptr := load(ctxptr, code.mapIter)
|
ptr := load(ctxptr, code.mapIter)
|
||||||
iter := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
iter := e.ptrToUnsafePtr(ptr)
|
||||||
store(ctxptr, code.elemIdx, idx)
|
store(ctxptr, code.elemIdx, idx)
|
||||||
key := mapiterkey(iter)
|
key := mapiterkey(iter)
|
||||||
store(ctxptr, code.next.idx, uintptr(key))
|
store(ctxptr, code.next.idx, uintptr(key))
|
||||||
|
@ -796,7 +755,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
*posPtr = append(*posPtr, len(e.buf))
|
*posPtr = append(*posPtr, len(e.buf))
|
||||||
}
|
}
|
||||||
ptr := load(ctxptr, code.mapIter)
|
ptr := load(ctxptr, code.mapIter)
|
||||||
iter := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
iter := e.ptrToUnsafePtr(ptr)
|
||||||
value := mapitervalue(iter)
|
value := mapitervalue(iter)
|
||||||
store(ctxptr, code.next.idx, uintptr(value))
|
store(ctxptr, code.next.idx, uintptr(value))
|
||||||
mapiternext(iter)
|
mapiternext(iter)
|
||||||
|
@ -810,7 +769,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
}
|
}
|
||||||
kvs := make([]mapKV, 0, length)
|
kvs := make([]mapKV, 0, length)
|
||||||
ptr := load(ctxptr, code.mapPos)
|
ptr := load(ctxptr, code.mapPos)
|
||||||
posPtr := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
posPtr := e.ptrToUnsafePtr(ptr)
|
||||||
pos := *(*[]int)(posPtr)
|
pos := *(*[]int)(posPtr)
|
||||||
for i := 0; i < length; i++ {
|
for i := 0; i < length; i++ {
|
||||||
startKey := pos[i*2]
|
startKey := pos[i*2]
|
||||||
|
@ -849,7 +808,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
e.encodeBytes([]byte{',', '\n'})
|
e.encodeBytes([]byte{',', '\n'})
|
||||||
code = code.end.next
|
code = code.end.next
|
||||||
} else {
|
} else {
|
||||||
uptr := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
uptr := e.ptrToUnsafePtr(ptr)
|
||||||
mlen := maplen(uptr)
|
mlen := maplen(uptr)
|
||||||
if mlen > 0 {
|
if mlen > 0 {
|
||||||
e.encodeBytes([]byte{'{', '\n'})
|
e.encodeBytes([]byte{'{', '\n'})
|
||||||
|
@ -886,8 +845,8 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
code = code.end.next
|
code = code.end.next
|
||||||
} else {
|
} else {
|
||||||
// load pointer
|
// load pointer
|
||||||
ptr = uintptr(**(**unsafe.Pointer)(unsafe.Pointer(&ptr)))
|
ptr = e.ptrToPtr(ptr)
|
||||||
uptr := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
uptr := e.ptrToUnsafePtr(ptr)
|
||||||
if uintptr(uptr) == 0 {
|
if uintptr(uptr) == 0 {
|
||||||
e.encodeIndent(code.indent)
|
e.encodeIndent(code.indent)
|
||||||
e.encodeNull()
|
e.encodeNull()
|
||||||
|
@ -932,7 +891,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
e.encodeIndent(code.indent)
|
e.encodeIndent(code.indent)
|
||||||
store(ctxptr, code.elemIdx, idx)
|
store(ctxptr, code.elemIdx, idx)
|
||||||
ptr := load(ctxptr, code.mapIter)
|
ptr := load(ctxptr, code.mapIter)
|
||||||
iter := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
iter := e.ptrToUnsafePtr(ptr)
|
||||||
key := mapiterkey(iter)
|
key := mapiterkey(iter)
|
||||||
store(ctxptr, code.next.idx, uintptr(key))
|
store(ctxptr, code.next.idx, uintptr(key))
|
||||||
code = code.next
|
code = code.next
|
||||||
|
@ -949,7 +908,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
*posPtr = append(*posPtr, len(e.buf))
|
*posPtr = append(*posPtr, len(e.buf))
|
||||||
if idx < length {
|
if idx < length {
|
||||||
ptr := load(ctxptr, code.mapIter)
|
ptr := load(ctxptr, code.mapIter)
|
||||||
iter := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
iter := e.ptrToUnsafePtr(ptr)
|
||||||
store(ctxptr, code.elemIdx, idx)
|
store(ctxptr, code.elemIdx, idx)
|
||||||
key := mapiterkey(iter)
|
key := mapiterkey(iter)
|
||||||
store(ctxptr, code.next.idx, uintptr(key))
|
store(ctxptr, code.next.idx, uintptr(key))
|
||||||
|
@ -967,7 +926,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
*posPtr = append(*posPtr, len(e.buf))
|
*posPtr = append(*posPtr, len(e.buf))
|
||||||
}
|
}
|
||||||
ptr := load(ctxptr, code.mapIter)
|
ptr := load(ctxptr, code.mapIter)
|
||||||
iter := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
iter := e.ptrToUnsafePtr(ptr)
|
||||||
value := mapitervalue(iter)
|
value := mapitervalue(iter)
|
||||||
store(ctxptr, code.next.idx, uintptr(value))
|
store(ctxptr, code.next.idx, uintptr(value))
|
||||||
mapiternext(iter)
|
mapiternext(iter)
|
||||||
|
@ -1072,7 +1031,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
// restore ctxptr
|
// restore ctxptr
|
||||||
offset := load(ctxptr, code.idx)
|
offset := load(ctxptr, code.idx)
|
||||||
ptr := load(ctxptr, code.elemIdx)
|
ptr := load(ctxptr, code.elemIdx)
|
||||||
code = (*opcode)(*(*unsafe.Pointer)(unsafe.Pointer(&ptr)))
|
code = (*opcode)(e.ptrToUnsafePtr(ptr))
|
||||||
ctxptr = ctx.ptr() + offset
|
ctxptr = ctx.ptr() + offset
|
||||||
ptrOffset = offset
|
ptrOffset = offset
|
||||||
case opStructFieldPtrHead:
|
case opStructFieldPtrHead:
|
||||||
|
@ -1574,10 +1533,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
} else {
|
} else {
|
||||||
v := e.ptrToFloat64(ptr + code.offset)
|
v := e.ptrToFloat64(ptr + code.offset)
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeByte('{')
|
e.encodeByte('{')
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
|
@ -1595,10 +1551,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
} else {
|
} else {
|
||||||
v := e.ptrToFloat64(ptr + code.offset)
|
v := e.ptrToFloat64(ptr + code.offset)
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
e.encodeFloat64(v)
|
e.encodeFloat64(v)
|
||||||
|
@ -1827,10 +1780,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
e.encodeByte('{')
|
e.encodeByte('{')
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
ptr += code.offset
|
ptr += code.offset
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
v := e.ptrToInterface(code, ptr)
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&ptr)),
|
|
||||||
}))
|
|
||||||
rv := reflect.ValueOf(v)
|
rv := reflect.ValueOf(v)
|
||||||
if rv.Type().Kind() == reflect.Interface && rv.IsNil() {
|
if rv.Type().Kind() == reflect.Interface && rv.IsNil() {
|
||||||
e.encodeNull()
|
e.encodeNull()
|
||||||
|
@ -1839,10 +1789,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
}
|
}
|
||||||
b, err := rv.Interface().(Marshaler).MarshalJSON()
|
b, err := rv.Interface().(Marshaler).MarshalJSON()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
if len(b) == 0 {
|
if len(b) == 0 {
|
||||||
return errUnexpectedEndOfJSON(
|
return errUnexpectedEndOfJSON(
|
||||||
|
@ -1868,10 +1815,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
} else {
|
} else {
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
ptr += code.offset
|
ptr += code.offset
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
v := e.ptrToInterface(code, ptr)
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&ptr)),
|
|
||||||
}))
|
|
||||||
rv := reflect.ValueOf(v)
|
rv := reflect.ValueOf(v)
|
||||||
if rv.Type().Kind() == reflect.Interface && rv.IsNil() {
|
if rv.Type().Kind() == reflect.Interface && rv.IsNil() {
|
||||||
e.encodeNull()
|
e.encodeNull()
|
||||||
|
@ -1880,10 +1824,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
}
|
}
|
||||||
b, err := rv.Interface().(Marshaler).MarshalJSON()
|
b, err := rv.Interface().(Marshaler).MarshalJSON()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
if len(b) == 0 {
|
if len(b) == 0 {
|
||||||
return errUnexpectedEndOfJSON(
|
return errUnexpectedEndOfJSON(
|
||||||
|
@ -1919,10 +1860,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
e.encodeByte('{')
|
e.encodeByte('{')
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
ptr += code.offset
|
ptr += code.offset
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
v := e.ptrToInterface(code, ptr)
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&ptr)),
|
|
||||||
}))
|
|
||||||
rv := reflect.ValueOf(v)
|
rv := reflect.ValueOf(v)
|
||||||
if rv.Type().Kind() == reflect.Interface && rv.IsNil() {
|
if rv.Type().Kind() == reflect.Interface && rv.IsNil() {
|
||||||
e.encodeNull()
|
e.encodeNull()
|
||||||
|
@ -1932,10 +1870,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
}
|
}
|
||||||
bytes, err := rv.Interface().(encoding.TextMarshaler).MarshalText()
|
bytes, err := rv.Interface().(encoding.TextMarshaler).MarshalText()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
||||||
e.encodeByte(',')
|
e.encodeByte(',')
|
||||||
|
@ -1951,10 +1886,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
} else {
|
} else {
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
ptr += code.offset
|
ptr += code.offset
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
v := e.ptrToInterface(code, ptr)
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&ptr)),
|
|
||||||
}))
|
|
||||||
rv := reflect.ValueOf(v)
|
rv := reflect.ValueOf(v)
|
||||||
if rv.Type().Kind() == reflect.Interface && rv.IsNil() {
|
if rv.Type().Kind() == reflect.Interface && rv.IsNil() {
|
||||||
e.encodeNull()
|
e.encodeNull()
|
||||||
|
@ -1964,10 +1896,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
}
|
}
|
||||||
bytes, err := rv.Interface().(encoding.TextMarshaler).MarshalText()
|
bytes, err := rv.Interface().(encoding.TextMarshaler).MarshalText()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
||||||
e.encodeByte(',')
|
e.encodeByte(',')
|
||||||
|
@ -2235,10 +2164,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
} else {
|
} else {
|
||||||
v := e.ptrToFloat64(ptr)
|
v := e.ptrToFloat64(ptr)
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeIndent(code.indent)
|
e.encodeIndent(code.indent)
|
||||||
e.encodeBytes([]byte{'{', '\n'})
|
e.encodeBytes([]byte{'{', '\n'})
|
||||||
|
@ -2869,10 +2795,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
code = code.nextField
|
code = code.nextField
|
||||||
} else {
|
} else {
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
e.encodeFloat64(v)
|
e.encodeFloat64(v)
|
||||||
|
@ -2896,10 +2819,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
code = code.nextField
|
code = code.nextField
|
||||||
} else {
|
} else {
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
e.encodeFloat64(v)
|
e.encodeFloat64(v)
|
||||||
|
@ -3057,7 +2977,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
} else {
|
} else {
|
||||||
e.encodeByte('{')
|
e.encodeByte('{')
|
||||||
ptr += code.offset
|
ptr += code.offset
|
||||||
p := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
p := e.ptrToUnsafePtr(ptr)
|
||||||
isPtr := code.typ.Kind() == reflect.Ptr
|
isPtr := code.typ.Kind() == reflect.Ptr
|
||||||
if p == nil || (!isPtr && *(*unsafe.Pointer)(p) == nil) {
|
if p == nil || (!isPtr && *(*unsafe.Pointer)(p) == nil) {
|
||||||
code = code.nextField
|
code = code.nextField
|
||||||
|
@ -3102,7 +3022,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
code = code.end.next
|
code = code.end.next
|
||||||
} else {
|
} else {
|
||||||
ptr += code.offset
|
ptr += code.offset
|
||||||
p := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
p := e.ptrToUnsafePtr(ptr)
|
||||||
isPtr := code.typ.Kind() == reflect.Ptr
|
isPtr := code.typ.Kind() == reflect.Ptr
|
||||||
if p == nil || (!isPtr && *(*unsafe.Pointer)(p) == nil) {
|
if p == nil || (!isPtr && *(*unsafe.Pointer)(p) == nil) {
|
||||||
code = code.nextField
|
code = code.nextField
|
||||||
|
@ -3150,7 +3070,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
} else {
|
} else {
|
||||||
e.encodeByte('{')
|
e.encodeByte('{')
|
||||||
ptr += code.offset
|
ptr += code.offset
|
||||||
p := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
p := e.ptrToUnsafePtr(ptr)
|
||||||
isPtr := code.typ.Kind() == reflect.Ptr
|
isPtr := code.typ.Kind() == reflect.Ptr
|
||||||
if p == nil || (!isPtr && *(*unsafe.Pointer)(p) == nil) {
|
if p == nil || (!isPtr && *(*unsafe.Pointer)(p) == nil) {
|
||||||
code = code.nextField
|
code = code.nextField
|
||||||
|
@ -3181,7 +3101,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
code = code.end.next
|
code = code.end.next
|
||||||
} else {
|
} else {
|
||||||
ptr += code.offset
|
ptr += code.offset
|
||||||
p := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
p := e.ptrToUnsafePtr(ptr)
|
||||||
isPtr := code.typ.Kind() == reflect.Ptr
|
isPtr := code.typ.Kind() == reflect.Ptr
|
||||||
if p == nil || (!isPtr && *(*unsafe.Pointer)(p) == nil) {
|
if p == nil || (!isPtr && *(*unsafe.Pointer)(p) == nil) {
|
||||||
code = code.nextField
|
code = code.nextField
|
||||||
|
@ -3556,10 +3476,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
code = code.nextField
|
code = code.nextField
|
||||||
} else {
|
} else {
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeIndent(code.indent + 1)
|
e.encodeIndent(code.indent + 1)
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
|
@ -4091,10 +4008,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
e.encodeByte('{')
|
e.encodeByte('{')
|
||||||
v := e.ptrToFloat64(ptr + code.offset)
|
v := e.ptrToFloat64(ptr + code.offset)
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
e.encodeString(fmt.Sprint(v))
|
e.encodeString(fmt.Sprint(v))
|
||||||
|
@ -4114,10 +4028,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
} else {
|
} else {
|
||||||
v := e.ptrToFloat64(ptr + code.offset)
|
v := e.ptrToFloat64(ptr + code.offset)
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
e.encodeString(fmt.Sprint(v))
|
e.encodeString(fmt.Sprint(v))
|
||||||
|
@ -4253,7 +4164,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
} else {
|
} else {
|
||||||
e.encodeByte('{')
|
e.encodeByte('{')
|
||||||
ptr += code.offset
|
ptr += code.offset
|
||||||
p := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
p := e.ptrToUnsafePtr(ptr)
|
||||||
isPtr := code.typ.Kind() == reflect.Ptr
|
isPtr := code.typ.Kind() == reflect.Ptr
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{typ: code.typ, ptr: p}))
|
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{typ: code.typ, ptr: p}))
|
||||||
b, err := v.(Marshaler).MarshalJSON()
|
b, err := v.(Marshaler).MarshalJSON()
|
||||||
|
@ -4296,7 +4207,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
code = code.end.next
|
code = code.end.next
|
||||||
} else {
|
} else {
|
||||||
ptr += code.offset
|
ptr += code.offset
|
||||||
p := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
p := e.ptrToUnsafePtr(ptr)
|
||||||
isPtr := code.typ.Kind() == reflect.Ptr
|
isPtr := code.typ.Kind() == reflect.Ptr
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{typ: code.typ, ptr: p}))
|
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{typ: code.typ, ptr: p}))
|
||||||
b, err := v.(Marshaler).MarshalJSON()
|
b, err := v.(Marshaler).MarshalJSON()
|
||||||
|
@ -4343,7 +4254,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
} else {
|
} else {
|
||||||
e.encodeByte('{')
|
e.encodeByte('{')
|
||||||
ptr += code.offset
|
ptr += code.offset
|
||||||
p := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
p := e.ptrToUnsafePtr(ptr)
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{typ: code.typ, ptr: p}))
|
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{typ: code.typ, ptr: p}))
|
||||||
bytes, err := v.(encoding.TextMarshaler).MarshalText()
|
bytes, err := v.(encoding.TextMarshaler).MarshalText()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -4369,14 +4280,11 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
code = code.end.next
|
code = code.end.next
|
||||||
} else {
|
} else {
|
||||||
ptr += code.offset
|
ptr += code.offset
|
||||||
p := *(*unsafe.Pointer)(unsafe.Pointer(&ptr))
|
p := e.ptrToUnsafePtr(ptr)
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{typ: code.typ, ptr: p}))
|
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{typ: code.typ, ptr: p}))
|
||||||
bytes, err := v.(encoding.TextMarshaler).MarshalText()
|
bytes, err := v.(encoding.TextMarshaler).MarshalText()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
||||||
|
@ -4664,10 +4572,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
e.encodeBytes([]byte{'{', '\n'})
|
e.encodeBytes([]byte{'{', '\n'})
|
||||||
v := e.ptrToFloat64(ptr + code.offset)
|
v := e.ptrToFloat64(ptr + code.offset)
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeIndent(code.indent + 1)
|
e.encodeIndent(code.indent + 1)
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
|
@ -4961,10 +4866,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
}
|
}
|
||||||
v := e.ptrToFloat64(p)
|
v := e.ptrToFloat64(p)
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeFloat64(v)
|
e.encodeFloat64(v)
|
||||||
e.encodeByte(',')
|
e.encodeByte(',')
|
||||||
|
@ -4974,10 +4876,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
v := e.ptrToFloat64(ptr + code.offset)
|
v := e.ptrToFloat64(ptr + code.offset)
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeFloat64(v)
|
e.encodeFloat64(v)
|
||||||
e.encodeByte(',')
|
e.encodeByte(',')
|
||||||
|
@ -5026,16 +4925,10 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
ptr := load(ctxptr, code.headIdx)
|
ptr := load(ctxptr, code.headIdx)
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
p := ptr + code.offset
|
p := ptr + code.offset
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
v := e.ptrToInterface(code, p)
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&p)),
|
|
||||||
}))
|
|
||||||
b, err := v.(Marshaler).MarshalJSON()
|
b, err := v.(Marshaler).MarshalJSON()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
var buf bytes.Buffer
|
var buf bytes.Buffer
|
||||||
if err := compact(&buf, b, e.enabledHTMLEscape); err != nil {
|
if err := compact(&buf, b, e.enabledHTMLEscape); err != nil {
|
||||||
|
@ -5048,16 +4941,10 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
ptr := load(ctxptr, code.headIdx)
|
ptr := load(ctxptr, code.headIdx)
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
p := ptr + code.offset
|
p := ptr + code.offset
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
v := e.ptrToInterface(code, p)
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&p)),
|
|
||||||
}))
|
|
||||||
bytes, err := v.(encoding.TextMarshaler).MarshalText()
|
bytes, err := v.(encoding.TextMarshaler).MarshalText()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
||||||
e.encodeByte(',')
|
e.encodeByte(',')
|
||||||
|
@ -5195,10 +5082,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
ptr := load(ctxptr, code.headIdx)
|
ptr := load(ctxptr, code.headIdx)
|
||||||
v := e.ptrToFloat64(ptr + code.offset)
|
v := e.ptrToFloat64(ptr + code.offset)
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeFloat64(v)
|
e.encodeFloat64(v)
|
||||||
e.encodeBytes([]byte{',', '\n'})
|
e.encodeBytes([]byte{',', '\n'})
|
||||||
|
@ -5236,16 +5120,10 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
e.encodeByte(' ')
|
e.encodeByte(' ')
|
||||||
ptr := load(ctxptr, code.headIdx)
|
ptr := load(ctxptr, code.headIdx)
|
||||||
p := ptr + code.offset
|
p := ptr + code.offset
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
v := e.ptrToInterface(code, p)
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&p)),
|
|
||||||
}))
|
|
||||||
b, err := v.(Marshaler).MarshalJSON()
|
b, err := v.(Marshaler).MarshalJSON()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
var buf bytes.Buffer
|
var buf bytes.Buffer
|
||||||
if err := compact(&buf, b, e.enabledHTMLEscape); err != nil {
|
if err := compact(&buf, b, e.enabledHTMLEscape); err != nil {
|
||||||
|
@ -5260,8 +5138,8 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
e.encodeByte(' ')
|
e.encodeByte(' ')
|
||||||
ptr := load(ctxptr, code.headIdx)
|
ptr := load(ctxptr, code.headIdx)
|
||||||
p := ptr + code.offset
|
p := ptr + code.offset
|
||||||
header := *(**sliceHeader)(unsafe.Pointer(&p))
|
array := e.ptrToSlice(p)
|
||||||
if p == 0 || uintptr(header.data) == 0 {
|
if p == 0 || uintptr(array.data) == 0 {
|
||||||
e.encodeNull()
|
e.encodeNull()
|
||||||
e.encodeBytes([]byte{',', '\n'})
|
e.encodeBytes([]byte{',', '\n'})
|
||||||
code = code.nextField
|
code = code.nextField
|
||||||
|
@ -5274,8 +5152,8 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
e.encodeByte(' ')
|
e.encodeByte(' ')
|
||||||
ptr := load(ctxptr, code.headIdx)
|
ptr := load(ctxptr, code.headIdx)
|
||||||
p := ptr + code.offset
|
p := ptr + code.offset
|
||||||
header := *(**sliceHeader)(unsafe.Pointer(&p))
|
slice := e.ptrToSlice(p)
|
||||||
if p == 0 || uintptr(header.data) == 0 {
|
if p == 0 || uintptr(slice.data) == 0 {
|
||||||
e.encodeNull()
|
e.encodeNull()
|
||||||
e.encodeBytes([]byte{',', '\n'})
|
e.encodeBytes([]byte{',', '\n'})
|
||||||
code = code.nextField
|
code = code.nextField
|
||||||
|
@ -5292,8 +5170,8 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
e.encodeNull()
|
e.encodeNull()
|
||||||
code = code.nextField
|
code = code.nextField
|
||||||
} else {
|
} else {
|
||||||
p = uintptr(**(**unsafe.Pointer)(unsafe.Pointer(&p)))
|
p = e.ptrToPtr(p)
|
||||||
mlen := maplen(*(*unsafe.Pointer)(unsafe.Pointer(&p)))
|
mlen := maplen(e.ptrToUnsafePtr(p))
|
||||||
if mlen == 0 {
|
if mlen == 0 {
|
||||||
e.encodeBytes([]byte{'{', '}', ',', '\n'})
|
e.encodeBytes([]byte{'{', '}', ',', '\n'})
|
||||||
mapCode := code.next
|
mapCode := code.next
|
||||||
|
@ -5312,8 +5190,8 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
e.encodeNull()
|
e.encodeNull()
|
||||||
code = code.nextField
|
code = code.nextField
|
||||||
} else {
|
} else {
|
||||||
p = uintptr(**(**unsafe.Pointer)(unsafe.Pointer(&p)))
|
p = e.ptrToPtr(p)
|
||||||
mlen := maplen(*(*unsafe.Pointer)(unsafe.Pointer(&p)))
|
mlen := maplen(e.ptrToUnsafePtr(p))
|
||||||
if mlen == 0 {
|
if mlen == 0 {
|
||||||
e.encodeBytes([]byte{'{', '}', ',', '\n'})
|
e.encodeBytes([]byte{'{', '}', ',', '\n'})
|
||||||
code = code.nextField
|
code = code.nextField
|
||||||
|
@ -5455,10 +5333,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
v := e.ptrToFloat64(ptr + code.offset)
|
v := e.ptrToFloat64(ptr + code.offset)
|
||||||
if v != 0 {
|
if v != 0 {
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
e.encodeFloat64(v)
|
e.encodeFloat64(v)
|
||||||
|
@ -5495,17 +5370,11 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
case opStructFieldOmitEmptyMarshalJSON:
|
case opStructFieldOmitEmptyMarshalJSON:
|
||||||
ptr := load(ctxptr, code.headIdx)
|
ptr := load(ctxptr, code.headIdx)
|
||||||
p := ptr + code.offset
|
p := ptr + code.offset
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
v := e.ptrToInterface(code, p)
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&p)),
|
|
||||||
}))
|
|
||||||
if v != nil {
|
if v != nil {
|
||||||
b, err := v.(Marshaler).MarshalJSON()
|
b, err := v.(Marshaler).MarshalJSON()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
var buf bytes.Buffer
|
var buf bytes.Buffer
|
||||||
if err := compact(&buf, b, e.enabledHTMLEscape); err != nil {
|
if err := compact(&buf, b, e.enabledHTMLEscape); err != nil {
|
||||||
|
@ -5518,21 +5387,11 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
case opStructFieldOmitEmptyMarshalText:
|
case opStructFieldOmitEmptyMarshalText:
|
||||||
ptr := load(ctxptr, code.headIdx)
|
ptr := load(ctxptr, code.headIdx)
|
||||||
p := ptr + code.offset
|
p := ptr + code.offset
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
v := e.ptrToInterface(code, p)
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&p)),
|
|
||||||
}))
|
|
||||||
if v != nil {
|
if v != nil {
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&p)),
|
|
||||||
}))
|
|
||||||
bytes, err := v.(encoding.TextMarshaler).MarshalText()
|
bytes, err := v.(encoding.TextMarshaler).MarshalText()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
||||||
e.encodeByte(',')
|
e.encodeByte(',')
|
||||||
|
@ -5541,8 +5400,8 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
case opStructFieldOmitEmptyArray:
|
case opStructFieldOmitEmptyArray:
|
||||||
ptr := load(ctxptr, code.headIdx)
|
ptr := load(ctxptr, code.headIdx)
|
||||||
p := ptr + code.offset
|
p := ptr + code.offset
|
||||||
header := *(**sliceHeader)(unsafe.Pointer(&p))
|
array := e.ptrToSlice(p)
|
||||||
if p == 0 || uintptr(header.data) == 0 {
|
if p == 0 || uintptr(array.data) == 0 {
|
||||||
code = code.nextField
|
code = code.nextField
|
||||||
} else {
|
} else {
|
||||||
code = code.next
|
code = code.next
|
||||||
|
@ -5550,8 +5409,8 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
case opStructFieldOmitEmptySlice:
|
case opStructFieldOmitEmptySlice:
|
||||||
ptr := load(ctxptr, code.headIdx)
|
ptr := load(ctxptr, code.headIdx)
|
||||||
p := ptr + code.offset
|
p := ptr + code.offset
|
||||||
header := *(**sliceHeader)(unsafe.Pointer(&p))
|
slice := e.ptrToSlice(p)
|
||||||
if p == 0 || uintptr(header.data) == 0 {
|
if p == 0 || uintptr(slice.data) == 0 {
|
||||||
code = code.nextField
|
code = code.nextField
|
||||||
} else {
|
} else {
|
||||||
code = code.next
|
code = code.next
|
||||||
|
@ -5720,10 +5579,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
v := e.ptrToFloat64(ptr + code.offset)
|
v := e.ptrToFloat64(ptr + code.offset)
|
||||||
if v != 0 {
|
if v != 0 {
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeIndent(code.indent)
|
e.encodeIndent(code.indent)
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
|
@ -5771,8 +5627,8 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
case opStructFieldOmitEmptyArrayIndent:
|
case opStructFieldOmitEmptyArrayIndent:
|
||||||
ptr := load(ctxptr, code.headIdx)
|
ptr := load(ctxptr, code.headIdx)
|
||||||
p := ptr + code.offset
|
p := ptr + code.offset
|
||||||
header := *(**sliceHeader)(unsafe.Pointer(&p))
|
array := e.ptrToSlice(p)
|
||||||
if p == 0 || uintptr(header.data) == 0 {
|
if p == 0 || uintptr(array.data) == 0 {
|
||||||
code = code.nextField
|
code = code.nextField
|
||||||
} else {
|
} else {
|
||||||
e.encodeIndent(code.indent)
|
e.encodeIndent(code.indent)
|
||||||
|
@ -5783,8 +5639,8 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
case opStructFieldOmitEmptySliceIndent:
|
case opStructFieldOmitEmptySliceIndent:
|
||||||
ptr := load(ctxptr, code.headIdx)
|
ptr := load(ctxptr, code.headIdx)
|
||||||
p := ptr + code.offset
|
p := ptr + code.offset
|
||||||
header := *(**sliceHeader)(unsafe.Pointer(&p))
|
slice := e.ptrToSlice(p)
|
||||||
if p == 0 || uintptr(header.data) == 0 {
|
if p == 0 || uintptr(slice.data) == 0 {
|
||||||
code = code.nextField
|
code = code.nextField
|
||||||
} else {
|
} else {
|
||||||
e.encodeIndent(code.indent)
|
e.encodeIndent(code.indent)
|
||||||
|
@ -5919,10 +5775,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
ptr := load(ctxptr, code.headIdx)
|
ptr := load(ctxptr, code.headIdx)
|
||||||
v := e.ptrToFloat64(ptr + code.offset)
|
v := e.ptrToFloat64(ptr + code.offset)
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
e.encodeString(fmt.Sprint(v))
|
e.encodeString(fmt.Sprint(v))
|
||||||
|
@ -5952,16 +5805,10 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
case opStructFieldStringTagMarshalJSON:
|
case opStructFieldStringTagMarshalJSON:
|
||||||
ptr := load(ctxptr, code.headIdx)
|
ptr := load(ctxptr, code.headIdx)
|
||||||
p := ptr + code.offset
|
p := ptr + code.offset
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
v := e.ptrToInterface(code, p)
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&p)),
|
|
||||||
}))
|
|
||||||
b, err := v.(Marshaler).MarshalJSON()
|
b, err := v.(Marshaler).MarshalJSON()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
var buf bytes.Buffer
|
var buf bytes.Buffer
|
||||||
if err := compact(&buf, b, e.enabledHTMLEscape); err != nil {
|
if err := compact(&buf, b, e.enabledHTMLEscape); err != nil {
|
||||||
|
@ -5973,16 +5820,10 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
case opStructFieldStringTagMarshalText:
|
case opStructFieldStringTagMarshalText:
|
||||||
ptr := load(ctxptr, code.headIdx)
|
ptr := load(ctxptr, code.headIdx)
|
||||||
p := ptr + code.offset
|
p := ptr + code.offset
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
v := e.ptrToInterface(code, p)
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&p)),
|
|
||||||
}))
|
|
||||||
bytes, err := v.(encoding.TextMarshaler).MarshalText()
|
bytes, err := v.(encoding.TextMarshaler).MarshalText()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
||||||
e.encodeByte(',')
|
e.encodeByte(',')
|
||||||
|
@ -6087,10 +5928,7 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
ptr := load(ctxptr, code.headIdx)
|
ptr := load(ctxptr, code.headIdx)
|
||||||
v := e.ptrToFloat64(ptr + code.offset)
|
v := e.ptrToFloat64(ptr + code.offset)
|
||||||
if math.IsInf(v, 0) || math.IsNaN(v) {
|
if math.IsInf(v, 0) || math.IsNaN(v) {
|
||||||
return &UnsupportedValueError{
|
return errUnsupportedFloat(v)
|
||||||
Value: reflect.ValueOf(v),
|
|
||||||
Str: strconv.FormatFloat(v, 'g', -1, 64),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeIndent(code.indent)
|
e.encodeIndent(code.indent)
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
|
@ -6137,16 +5975,10 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
e.encodeByte(' ')
|
e.encodeByte(' ')
|
||||||
p := ptr + code.offset
|
p := ptr + code.offset
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
v := e.ptrToInterface(code, p)
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&p)),
|
|
||||||
}))
|
|
||||||
b, err := v.(Marshaler).MarshalJSON()
|
b, err := v.(Marshaler).MarshalJSON()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
var buf bytes.Buffer
|
var buf bytes.Buffer
|
||||||
if err := compact(&buf, b, e.enabledHTMLEscape); err != nil {
|
if err := compact(&buf, b, e.enabledHTMLEscape); err != nil {
|
||||||
|
@ -6161,16 +5993,10 @@ func (e *Encoder) run(ctx *encodeRuntimeContext, code *opcode) error {
|
||||||
e.encodeKey(code)
|
e.encodeKey(code)
|
||||||
e.encodeByte(' ')
|
e.encodeByte(' ')
|
||||||
p := ptr + code.offset
|
p := ptr + code.offset
|
||||||
v := *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
v := e.ptrToInterface(code, p)
|
||||||
typ: code.typ,
|
|
||||||
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&p)),
|
|
||||||
}))
|
|
||||||
bytes, err := v.(encoding.TextMarshaler).MarshalText()
|
bytes, err := v.(encoding.TextMarshaler).MarshalText()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &MarshalerError{
|
return errMarshaler(code, err)
|
||||||
Type: rtype2type(code.typ),
|
|
||||||
Err: err,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
e.encodeString(*(*string)(unsafe.Pointer(&bytes)))
|
||||||
e.encodeBytes([]byte{',', '\n'})
|
e.encodeBytes([]byte{',', '\n'})
|
||||||
|
@ -6205,7 +6031,6 @@ END:
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (e *Encoder) ptrToPtr(p uintptr) uintptr { return **(**uintptr)(unsafe.Pointer(&p)) }
|
|
||||||
func (e *Encoder) ptrToInt(p uintptr) int { return **(**int)(unsafe.Pointer(&p)) }
|
func (e *Encoder) ptrToInt(p uintptr) int { return **(**int)(unsafe.Pointer(&p)) }
|
||||||
func (e *Encoder) ptrToInt8(p uintptr) int8 { return **(**int8)(unsafe.Pointer(&p)) }
|
func (e *Encoder) ptrToInt8(p uintptr) int8 { return **(**int8)(unsafe.Pointer(&p)) }
|
||||||
func (e *Encoder) ptrToInt16(p uintptr) int16 { return **(**int16)(unsafe.Pointer(&p)) }
|
func (e *Encoder) ptrToInt16(p uintptr) int16 { return **(**int16)(unsafe.Pointer(&p)) }
|
||||||
|
@ -6222,3 +6047,16 @@ func (e *Encoder) ptrToBool(p uintptr) bool { return **(**bool)(unsafe.Poi
|
||||||
func (e *Encoder) ptrToByte(p uintptr) byte { return **(**byte)(unsafe.Pointer(&p)) }
|
func (e *Encoder) ptrToByte(p uintptr) byte { return **(**byte)(unsafe.Pointer(&p)) }
|
||||||
func (e *Encoder) ptrToBytes(p uintptr) []byte { return **(**[]byte)(unsafe.Pointer(&p)) }
|
func (e *Encoder) ptrToBytes(p uintptr) []byte { return **(**[]byte)(unsafe.Pointer(&p)) }
|
||||||
func (e *Encoder) ptrToString(p uintptr) string { return **(**string)(unsafe.Pointer(&p)) }
|
func (e *Encoder) ptrToString(p uintptr) string { return **(**string)(unsafe.Pointer(&p)) }
|
||||||
|
func (e *Encoder) ptrToSlice(p uintptr) *sliceHeader { return *(**sliceHeader)(unsafe.Pointer(&p)) }
|
||||||
|
func (e *Encoder) ptrToPtr(p uintptr) uintptr {
|
||||||
|
return uintptr(**(**unsafe.Pointer)(unsafe.Pointer(&p)))
|
||||||
|
}
|
||||||
|
func (e *Encoder) ptrToUnsafePtr(p uintptr) unsafe.Pointer {
|
||||||
|
return *(*unsafe.Pointer)(unsafe.Pointer(&p))
|
||||||
|
}
|
||||||
|
func (e *Encoder) ptrToInterface(code *opcode, p uintptr) interface{} {
|
||||||
|
return *(*interface{})(unsafe.Pointer(&interfaceHeader{
|
||||||
|
typ: code.typ,
|
||||||
|
ptr: *(*unsafe.Pointer)(unsafe.Pointer(&p)),
|
||||||
|
}))
|
||||||
|
}
|
||||||
|
|
Loading…
Reference in New Issue