1
2
3
4
5
6
7 package json
8
9 import (
10 "bytes"
11 "cmp"
12 "encoding"
13 "encoding/base32"
14 "encoding/base64"
15 "encoding/hex"
16 "errors"
17 "fmt"
18 "math"
19 "reflect"
20 "slices"
21 "strconv"
22 "strings"
23 "sync"
24
25 "encoding/json/internal"
26 "encoding/json/internal/jsonflags"
27 "encoding/json/internal/jsonopts"
28 "encoding/json/internal/jsonwire"
29 "encoding/json/jsontext"
30 )
31
32
33
34
35 const optimizeCommon = true
36
37 var (
38
39 anyType = reflect.TypeFor[any]()
40 boolType = reflect.TypeFor[bool]()
41 stringType = reflect.TypeFor[string]()
42 float64Type = reflect.TypeFor[float64]()
43 mapStringAnyType = reflect.TypeFor[map[string]any]()
44 sliceAnyType = reflect.TypeFor[[]any]()
45
46 bytesType = reflect.TypeFor[[]byte]()
47 emptyStructType = reflect.TypeFor[struct{}]()
48 )
49
50 const startDetectingCyclesAfter = 1000
51
52 type seenPointers = map[any]struct{}
53
54 type typedPointer struct {
55 typ reflect.Type
56 ptr any
57 len int
58 }
59
60
61
62 func visitPointer(m *seenPointers, v reflect.Value) error {
63 p := typedPointer{v.Type(), v.UnsafePointer(), sliceLen(v)}
64 if _, ok := (*m)[p]; ok {
65 return internal.ErrCycle
66 }
67 if *m == nil {
68 *m = make(seenPointers)
69 }
70 (*m)[p] = struct{}{}
71 return nil
72 }
73 func leavePointer(m *seenPointers, v reflect.Value) {
74 p := typedPointer{v.Type(), v.UnsafePointer(), sliceLen(v)}
75 delete(*m, p)
76 }
77
78 func sliceLen(v reflect.Value) int {
79 if v.Kind() == reflect.Slice {
80 return v.Len()
81 }
82 return 0
83 }
84
85 func len64[Bytes ~[]byte | ~string](in Bytes) int64 {
86 return int64(len(in))
87 }
88
89 func makeDefaultArshaler(t reflect.Type) *arshaler {
90 switch t.Kind() {
91 case reflect.Bool:
92 return makeBoolArshaler(t)
93 case reflect.String:
94 return makeStringArshaler(t)
95 case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
96 return makeIntArshaler(t)
97 case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
98 return makeUintArshaler(t)
99 case reflect.Float32, reflect.Float64:
100 return makeFloatArshaler(t)
101 case reflect.Map:
102 return makeMapArshaler(t)
103 case reflect.Struct:
104 return makeStructArshaler(t)
105 case reflect.Slice:
106 fncs := makeSliceArshaler(t)
107 if t.Elem().Kind() == reflect.Uint8 {
108 return makeBytesArshaler(t, fncs)
109 }
110 return fncs
111 case reflect.Array:
112 fncs := makeArrayArshaler(t)
113 if t.Elem().Kind() == reflect.Uint8 {
114 return makeBytesArshaler(t, fncs)
115 }
116 return fncs
117 case reflect.Pointer:
118 return makePointerArshaler(t)
119 case reflect.Interface:
120 return makeInterfaceArshaler(t)
121 default:
122 return makeInvalidArshaler(t)
123 }
124 }
125
126 func makeBoolArshaler(t reflect.Type) *arshaler {
127 var fncs arshaler
128 fncs.marshal = func(enc *jsontext.Encoder, va addressableValue, mo *jsonopts.Struct) error {
129 xe := export.Encoder(enc)
130 if mo.Format != "" && mo.FormatDepth == xe.Tokens.Depth() {
131 return newInvalidFormatError(enc, t, mo)
132 }
133
134
135 if optimizeCommon && !mo.Flags.Get(jsonflags.AnyWhitespace|jsonflags.StringifyBoolsAndStrings) && !xe.Tokens.Last.NeedObjectName() {
136 xe.Buf = strconv.AppendBool(xe.Tokens.MayAppendDelim(xe.Buf, 't'), va.Bool())
137 xe.Tokens.Last.Increment()
138 if xe.NeedFlush() {
139 return xe.Flush()
140 }
141 return nil
142 }
143
144 if mo.Flags.Get(jsonflags.StringifyBoolsAndStrings) {
145 if va.Bool() {
146 return enc.WriteToken(jsontext.String("true"))
147 } else {
148 return enc.WriteToken(jsontext.String("false"))
149 }
150 }
151 return enc.WriteToken(jsontext.Bool(va.Bool()))
152 }
153 fncs.unmarshal = func(dec *jsontext.Decoder, va addressableValue, uo *jsonopts.Struct) error {
154 xd := export.Decoder(dec)
155 if uo.Format != "" && uo.FormatDepth == xd.Tokens.Depth() {
156 return newInvalidFormatError(dec, t, uo)
157 }
158 tok, err := dec.ReadToken()
159 if err != nil {
160 return err
161 }
162 k := tok.Kind()
163 switch k {
164 case 'n':
165 if !uo.Flags.Get(jsonflags.MergeWithLegacySemantics) {
166 va.SetBool(false)
167 }
168 return nil
169 case 't', 'f':
170 if !uo.Flags.Get(jsonflags.StringifyBoolsAndStrings) {
171 va.SetBool(tok.Bool())
172 return nil
173 }
174 case '"':
175 if uo.Flags.Get(jsonflags.StringifyBoolsAndStrings) {
176 switch tok.String() {
177 case "true":
178 va.SetBool(true)
179 case "false":
180 va.SetBool(false)
181 default:
182 if uo.Flags.Get(jsonflags.StringifyWithLegacySemantics) && tok.String() == "null" {
183 if !uo.Flags.Get(jsonflags.MergeWithLegacySemantics) {
184 va.SetBool(false)
185 }
186 return nil
187 }
188 return newUnmarshalErrorAfterWithValue(dec, t, strconv.ErrSyntax)
189 }
190 return nil
191 }
192 }
193 return newUnmarshalErrorAfterWithSkipping(dec, uo, t, nil)
194 }
195 return &fncs
196 }
197
198 func makeStringArshaler(t reflect.Type) *arshaler {
199 var fncs arshaler
200 fncs.marshal = func(enc *jsontext.Encoder, va addressableValue, mo *jsonopts.Struct) error {
201 xe := export.Encoder(enc)
202 if mo.Format != "" && mo.FormatDepth == xe.Tokens.Depth() {
203 return newInvalidFormatError(enc, t, mo)
204 }
205
206
207 s := va.String()
208 if optimizeCommon && !mo.Flags.Get(jsonflags.AnyWhitespace|jsonflags.StringifyBoolsAndStrings) && !xe.Tokens.Last.NeedObjectName() {
209 b := xe.Buf
210 b = xe.Tokens.MayAppendDelim(b, '"')
211 b, err := jsonwire.AppendQuote(b, s, &mo.Flags)
212 if err == nil {
213 xe.Buf = b
214 xe.Tokens.Last.Increment()
215 if xe.NeedFlush() {
216 return xe.Flush()
217 }
218 return nil
219 }
220
221
222 }
223
224 if mo.Flags.Get(jsonflags.StringifyBoolsAndStrings) {
225 b, err := jsonwire.AppendQuote(nil, s, &mo.Flags)
226 if err != nil {
227 return newMarshalErrorBefore(enc, t, &jsontext.SyntacticError{Err: err})
228 }
229 q, err := jsontext.AppendQuote(nil, b)
230 if err != nil {
231 panic("BUG: second AppendQuote should never fail: " + err.Error())
232 }
233 return enc.WriteValue(q)
234 }
235 return enc.WriteToken(jsontext.String(s))
236 }
237 fncs.unmarshal = func(dec *jsontext.Decoder, va addressableValue, uo *jsonopts.Struct) error {
238 xd := export.Decoder(dec)
239 if uo.Format != "" && uo.FormatDepth == xd.Tokens.Depth() {
240 return newInvalidFormatError(dec, t, uo)
241 }
242 var flags jsonwire.ValueFlags
243 val, err := xd.ReadValue(&flags)
244 if err != nil {
245 return err
246 }
247 k := val.Kind()
248 switch k {
249 case 'n':
250 if !uo.Flags.Get(jsonflags.MergeWithLegacySemantics) {
251 va.SetString("")
252 }
253 return nil
254 case '"':
255 val = jsonwire.UnquoteMayCopy(val, flags.IsVerbatim())
256 if uo.Flags.Get(jsonflags.StringifyBoolsAndStrings) {
257 val, err = jsontext.AppendUnquote(nil, val)
258 if err != nil {
259 return newUnmarshalErrorAfter(dec, t, err)
260 }
261 if uo.Flags.Get(jsonflags.StringifyWithLegacySemantics) && string(val) == "null" {
262 if !uo.Flags.Get(jsonflags.MergeWithLegacySemantics) {
263 va.SetString("")
264 }
265 return nil
266 }
267 }
268 if xd.StringCache == nil {
269 xd.StringCache = new(stringCache)
270 }
271 str := makeString(xd.StringCache, val)
272 va.SetString(str)
273 return nil
274 }
275 return newUnmarshalErrorAfter(dec, t, nil)
276 }
277 return &fncs
278 }
279
280 var (
281 appendEncodeBase16 = hex.AppendEncode
282 appendEncodeBase32 = base32.StdEncoding.AppendEncode
283 appendEncodeBase32Hex = base32.HexEncoding.AppendEncode
284 appendEncodeBase64 = base64.StdEncoding.AppendEncode
285 appendEncodeBase64URL = base64.URLEncoding.AppendEncode
286 encodedLenBase16 = hex.EncodedLen
287 encodedLenBase32 = base32.StdEncoding.EncodedLen
288 encodedLenBase32Hex = base32.HexEncoding.EncodedLen
289 encodedLenBase64 = base64.StdEncoding.EncodedLen
290 encodedLenBase64URL = base64.URLEncoding.EncodedLen
291 appendDecodeBase16 = hex.AppendDecode
292 appendDecodeBase32 = base32.StdEncoding.AppendDecode
293 appendDecodeBase32Hex = base32.HexEncoding.AppendDecode
294 appendDecodeBase64 = base64.StdEncoding.AppendDecode
295 appendDecodeBase64URL = base64.URLEncoding.AppendDecode
296 )
297
298 func makeBytesArshaler(t reflect.Type, fncs *arshaler) *arshaler {
299
300
301
302
303
304
305 marshalArray := fncs.marshal
306 isNamedByte := t.Elem().PkgPath() != ""
307 hasMarshaler := implementsAny(t.Elem(), allMarshalerTypes...)
308 fncs.marshal = func(enc *jsontext.Encoder, va addressableValue, mo *jsonopts.Struct) error {
309 if !mo.Flags.Get(jsonflags.FormatBytesWithLegacySemantics) && isNamedByte {
310 return marshalArray(enc, va, mo)
311 }
312 xe := export.Encoder(enc)
313 appendEncode := appendEncodeBase64
314 if mo.Format != "" && mo.FormatDepth == xe.Tokens.Depth() {
315 switch mo.Format {
316 case "base64":
317 appendEncode = appendEncodeBase64
318 case "base64url":
319 appendEncode = appendEncodeBase64URL
320 case "base32":
321 appendEncode = appendEncodeBase32
322 case "base32hex":
323 appendEncode = appendEncodeBase32Hex
324 case "base16", "hex":
325 appendEncode = appendEncodeBase16
326 case "array":
327 mo.Format = ""
328 return marshalArray(enc, va, mo)
329 default:
330 return newInvalidFormatError(enc, t, mo)
331 }
332 } else if mo.Flags.Get(jsonflags.FormatByteArrayAsArray) && va.Kind() == reflect.Array {
333 return marshalArray(enc, va, mo)
334 } else if mo.Flags.Get(jsonflags.FormatBytesWithLegacySemantics) && hasMarshaler {
335 return marshalArray(enc, va, mo)
336 }
337 if mo.Flags.Get(jsonflags.FormatNilSliceAsNull) && va.Kind() == reflect.Slice && va.IsNil() {
338
339 return enc.WriteToken(jsontext.Null)
340 }
341 return xe.AppendRaw('"', true, func(b []byte) ([]byte, error) {
342 return appendEncode(b, va.Bytes()), nil
343 })
344 }
345 unmarshalArray := fncs.unmarshal
346 fncs.unmarshal = func(dec *jsontext.Decoder, va addressableValue, uo *jsonopts.Struct) error {
347 if !uo.Flags.Get(jsonflags.FormatBytesWithLegacySemantics) && isNamedByte {
348 return unmarshalArray(dec, va, uo)
349 }
350 xd := export.Decoder(dec)
351 appendDecode, encodedLen := appendDecodeBase64, encodedLenBase64
352 if uo.Format != "" && uo.FormatDepth == xd.Tokens.Depth() {
353 switch uo.Format {
354 case "base64":
355 appendDecode, encodedLen = appendDecodeBase64, encodedLenBase64
356 case "base64url":
357 appendDecode, encodedLen = appendDecodeBase64URL, encodedLenBase64URL
358 case "base32":
359 appendDecode, encodedLen = appendDecodeBase32, encodedLenBase32
360 case "base32hex":
361 appendDecode, encodedLen = appendDecodeBase32Hex, encodedLenBase32Hex
362 case "base16", "hex":
363 appendDecode, encodedLen = appendDecodeBase16, encodedLenBase16
364 case "array":
365 uo.Format = ""
366 return unmarshalArray(dec, va, uo)
367 default:
368 return newInvalidFormatError(dec, t, uo)
369 }
370 } else if uo.Flags.Get(jsonflags.FormatByteArrayAsArray) && va.Kind() == reflect.Array {
371 return unmarshalArray(dec, va, uo)
372 } else if uo.Flags.Get(jsonflags.FormatBytesWithLegacySemantics) && dec.PeekKind() == '[' {
373 return unmarshalArray(dec, va, uo)
374 }
375 var flags jsonwire.ValueFlags
376 val, err := xd.ReadValue(&flags)
377 if err != nil {
378 return err
379 }
380 k := val.Kind()
381 switch k {
382 case 'n':
383 if !uo.Flags.Get(jsonflags.MergeWithLegacySemantics) || va.Kind() != reflect.Array {
384 va.SetZero()
385 }
386 return nil
387 case '"':
388
389
390
391
392
393
394
395 val = jsonwire.UnquoteMayCopy(val, flags.IsVerbatim())
396 b, err := appendDecode(va.Bytes()[:0], val)
397 if err != nil {
398 return newUnmarshalErrorAfter(dec, t, err)
399 }
400 if len(val) != encodedLen(len(b)) && !uo.Flags.Get(jsonflags.ParseBytesWithLooseRFC4648) {
401
402
403
404
405 i := bytes.IndexAny(val, "\r\n")
406 err := fmt.Errorf("illegal character %s at offset %d", jsonwire.QuoteRune(val[i:]), i)
407 return newUnmarshalErrorAfter(dec, t, err)
408 }
409
410 if va.Kind() == reflect.Array {
411 dst := va.Bytes()
412 clear(dst[copy(dst, b):])
413 if len(b) != len(dst) && !uo.Flags.Get(jsonflags.UnmarshalArrayFromAnyLength) {
414 err := fmt.Errorf("decoded length of %d mismatches array length of %d", len(b), len(dst))
415 return newUnmarshalErrorAfter(dec, t, err)
416 }
417 } else {
418 if b == nil {
419 b = []byte{}
420 }
421 va.SetBytes(b)
422 }
423 return nil
424 }
425 return newUnmarshalErrorAfter(dec, t, nil)
426 }
427 return fncs
428 }
429
430 func makeIntArshaler(t reflect.Type) *arshaler {
431 var fncs arshaler
432 bits := t.Bits()
433 fncs.marshal = func(enc *jsontext.Encoder, va addressableValue, mo *jsonopts.Struct) error {
434 xe := export.Encoder(enc)
435 if mo.Format != "" && mo.FormatDepth == xe.Tokens.Depth() {
436 return newInvalidFormatError(enc, t, mo)
437 }
438
439
440 if optimizeCommon && !mo.Flags.Get(jsonflags.AnyWhitespace|jsonflags.StringifyNumbers) && !xe.Tokens.Last.NeedObjectName() {
441 xe.Buf = strconv.AppendInt(xe.Tokens.MayAppendDelim(xe.Buf, '0'), va.Int(), 10)
442 xe.Tokens.Last.Increment()
443 if xe.NeedFlush() {
444 return xe.Flush()
445 }
446 return nil
447 }
448
449 k := stringOrNumberKind(xe.Tokens.Last.NeedObjectName() || mo.Flags.Get(jsonflags.StringifyNumbers))
450 return xe.AppendRaw(k, true, func(b []byte) ([]byte, error) {
451 return strconv.AppendInt(b, va.Int(), 10), nil
452 })
453 }
454 fncs.unmarshal = func(dec *jsontext.Decoder, va addressableValue, uo *jsonopts.Struct) error {
455 xd := export.Decoder(dec)
456 if uo.Format != "" && uo.FormatDepth == xd.Tokens.Depth() {
457 return newInvalidFormatError(dec, t, uo)
458 }
459 stringify := xd.Tokens.Last.NeedObjectName() || uo.Flags.Get(jsonflags.StringifyNumbers)
460 var flags jsonwire.ValueFlags
461 val, err := xd.ReadValue(&flags)
462 if err != nil {
463 return err
464 }
465 k := val.Kind()
466 switch k {
467 case 'n':
468 if !uo.Flags.Get(jsonflags.MergeWithLegacySemantics) {
469 va.SetInt(0)
470 }
471 return nil
472 case '"':
473 if !stringify {
474 break
475 }
476 val = jsonwire.UnquoteMayCopy(val, flags.IsVerbatim())
477 if uo.Flags.Get(jsonflags.StringifyWithLegacySemantics) && string(val) == "null" {
478 if !uo.Flags.Get(jsonflags.MergeWithLegacySemantics) {
479 va.SetInt(0)
480 }
481 return nil
482 }
483 fallthrough
484 case '0':
485 if stringify && k == '0' {
486 break
487 }
488 var negOffset int
489 neg := len(val) > 0 && val[0] == '-'
490 if neg {
491 negOffset = 1
492 }
493 n, ok := jsonwire.ParseUint(val[negOffset:])
494 maxInt := uint64(1) << (bits - 1)
495 overflow := (neg && n > maxInt) || (!neg && n > maxInt-1)
496 if !ok {
497 if n != math.MaxUint64 {
498 return newUnmarshalErrorAfterWithValue(dec, t, strconv.ErrSyntax)
499 }
500 overflow = true
501 }
502 if overflow {
503 return newUnmarshalErrorAfterWithValue(dec, t, strconv.ErrRange)
504 }
505 if neg {
506 va.SetInt(int64(-n))
507 } else {
508 va.SetInt(int64(+n))
509 }
510 return nil
511 }
512 return newUnmarshalErrorAfter(dec, t, nil)
513 }
514 return &fncs
515 }
516
517 func makeUintArshaler(t reflect.Type) *arshaler {
518 var fncs arshaler
519 bits := t.Bits()
520 fncs.marshal = func(enc *jsontext.Encoder, va addressableValue, mo *jsonopts.Struct) error {
521 xe := export.Encoder(enc)
522 if mo.Format != "" && mo.FormatDepth == xe.Tokens.Depth() {
523 return newInvalidFormatError(enc, t, mo)
524 }
525
526
527 if optimizeCommon && !mo.Flags.Get(jsonflags.AnyWhitespace|jsonflags.StringifyNumbers) && !xe.Tokens.Last.NeedObjectName() {
528 xe.Buf = strconv.AppendUint(xe.Tokens.MayAppendDelim(xe.Buf, '0'), va.Uint(), 10)
529 xe.Tokens.Last.Increment()
530 if xe.NeedFlush() {
531 return xe.Flush()
532 }
533 return nil
534 }
535
536 k := stringOrNumberKind(xe.Tokens.Last.NeedObjectName() || mo.Flags.Get(jsonflags.StringifyNumbers))
537 return xe.AppendRaw(k, true, func(b []byte) ([]byte, error) {
538 return strconv.AppendUint(b, va.Uint(), 10), nil
539 })
540 }
541 fncs.unmarshal = func(dec *jsontext.Decoder, va addressableValue, uo *jsonopts.Struct) error {
542 xd := export.Decoder(dec)
543 if uo.Format != "" && uo.FormatDepth == xd.Tokens.Depth() {
544 return newInvalidFormatError(dec, t, uo)
545 }
546 stringify := xd.Tokens.Last.NeedObjectName() || uo.Flags.Get(jsonflags.StringifyNumbers)
547 var flags jsonwire.ValueFlags
548 val, err := xd.ReadValue(&flags)
549 if err != nil {
550 return err
551 }
552 k := val.Kind()
553 switch k {
554 case 'n':
555 if !uo.Flags.Get(jsonflags.MergeWithLegacySemantics) {
556 va.SetUint(0)
557 }
558 return nil
559 case '"':
560 if !stringify {
561 break
562 }
563 val = jsonwire.UnquoteMayCopy(val, flags.IsVerbatim())
564 if uo.Flags.Get(jsonflags.StringifyWithLegacySemantics) && string(val) == "null" {
565 if !uo.Flags.Get(jsonflags.MergeWithLegacySemantics) {
566 va.SetUint(0)
567 }
568 return nil
569 }
570 fallthrough
571 case '0':
572 if stringify && k == '0' {
573 break
574 }
575 n, ok := jsonwire.ParseUint(val)
576 maxUint := uint64(1) << bits
577 overflow := n > maxUint-1
578 if !ok {
579 if n != math.MaxUint64 {
580 return newUnmarshalErrorAfterWithValue(dec, t, strconv.ErrSyntax)
581 }
582 overflow = true
583 }
584 if overflow {
585 return newUnmarshalErrorAfterWithValue(dec, t, strconv.ErrRange)
586 }
587 va.SetUint(n)
588 return nil
589 }
590 return newUnmarshalErrorAfter(dec, t, nil)
591 }
592 return &fncs
593 }
594
595 func makeFloatArshaler(t reflect.Type) *arshaler {
596 var fncs arshaler
597 bits := t.Bits()
598 fncs.marshal = func(enc *jsontext.Encoder, va addressableValue, mo *jsonopts.Struct) error {
599 xe := export.Encoder(enc)
600 var allowNonFinite bool
601 if mo.Format != "" && mo.FormatDepth == xe.Tokens.Depth() {
602 if mo.Format == "nonfinite" {
603 allowNonFinite = true
604 } else {
605 return newInvalidFormatError(enc, t, mo)
606 }
607 }
608
609 fv := va.Float()
610 if math.IsNaN(fv) || math.IsInf(fv, 0) {
611 if !allowNonFinite {
612 err := fmt.Errorf("unsupported value: %v", fv)
613 return newMarshalErrorBefore(enc, t, err)
614 }
615 return enc.WriteToken(jsontext.Float(fv))
616 }
617
618
619 if optimizeCommon && !mo.Flags.Get(jsonflags.AnyWhitespace|jsonflags.StringifyNumbers) && !xe.Tokens.Last.NeedObjectName() {
620 xe.Buf = jsonwire.AppendFloat(xe.Tokens.MayAppendDelim(xe.Buf, '0'), fv, bits)
621 xe.Tokens.Last.Increment()
622 if xe.NeedFlush() {
623 return xe.Flush()
624 }
625 return nil
626 }
627
628 k := stringOrNumberKind(xe.Tokens.Last.NeedObjectName() || mo.Flags.Get(jsonflags.StringifyNumbers))
629 return xe.AppendRaw(k, true, func(b []byte) ([]byte, error) {
630 return jsonwire.AppendFloat(b, va.Float(), bits), nil
631 })
632 }
633 fncs.unmarshal = func(dec *jsontext.Decoder, va addressableValue, uo *jsonopts.Struct) error {
634 xd := export.Decoder(dec)
635 var allowNonFinite bool
636 if uo.Format != "" && uo.FormatDepth == xd.Tokens.Depth() {
637 if uo.Format == "nonfinite" {
638 allowNonFinite = true
639 } else {
640 return newInvalidFormatError(dec, t, uo)
641 }
642 }
643 stringify := xd.Tokens.Last.NeedObjectName() || uo.Flags.Get(jsonflags.StringifyNumbers)
644 var flags jsonwire.ValueFlags
645 val, err := xd.ReadValue(&flags)
646 if err != nil {
647 return err
648 }
649 k := val.Kind()
650 switch k {
651 case 'n':
652 if !uo.Flags.Get(jsonflags.MergeWithLegacySemantics) {
653 va.SetFloat(0)
654 }
655 return nil
656 case '"':
657 val = jsonwire.UnquoteMayCopy(val, flags.IsVerbatim())
658 if allowNonFinite {
659 switch string(val) {
660 case "NaN":
661 va.SetFloat(math.NaN())
662 return nil
663 case "Infinity":
664 va.SetFloat(math.Inf(+1))
665 return nil
666 case "-Infinity":
667 va.SetFloat(math.Inf(-1))
668 return nil
669 }
670 }
671 if !stringify {
672 break
673 }
674 if uo.Flags.Get(jsonflags.StringifyWithLegacySemantics) && string(val) == "null" {
675 if !uo.Flags.Get(jsonflags.MergeWithLegacySemantics) {
676 va.SetFloat(0)
677 }
678 return nil
679 }
680 if n, err := jsonwire.ConsumeNumber(val); n != len(val) || err != nil {
681 return newUnmarshalErrorAfterWithValue(dec, t, strconv.ErrSyntax)
682 }
683 fallthrough
684 case '0':
685 if stringify && k == '0' {
686 break
687 }
688 fv, ok := jsonwire.ParseFloat(val, bits)
689 va.SetFloat(fv)
690 if !ok {
691 return newUnmarshalErrorAfterWithValue(dec, t, strconv.ErrRange)
692 }
693 return nil
694 }
695 return newUnmarshalErrorAfter(dec, t, nil)
696 }
697 return &fncs
698 }
699
700 func makeMapArshaler(t reflect.Type) *arshaler {
701
702
703
704
705
706
707
708 var fncs arshaler
709 var (
710 once sync.Once
711 keyFncs *arshaler
712 valFncs *arshaler
713 )
714 init := func() {
715 keyFncs = lookupArshaler(t.Key())
716 valFncs = lookupArshaler(t.Elem())
717 }
718 nillableLegacyKey := t.Key().Kind() == reflect.Pointer &&
719 implementsAny(t.Key(), textMarshalerType, textAppenderType)
720 fncs.marshal = func(enc *jsontext.Encoder, va addressableValue, mo *jsonopts.Struct) error {
721
722 xe := export.Encoder(enc)
723 if xe.Tokens.Depth() > startDetectingCyclesAfter {
724 if err := visitPointer(&xe.SeenPointers, va.Value); err != nil {
725 return newMarshalErrorBefore(enc, t, err)
726 }
727 defer leavePointer(&xe.SeenPointers, va.Value)
728 }
729
730 emitNull := mo.Flags.Get(jsonflags.FormatNilMapAsNull)
731 if mo.Format != "" && mo.FormatDepth == xe.Tokens.Depth() {
732 switch mo.Format {
733 case "emitnull":
734 emitNull = true
735 mo.Format = ""
736 case "emitempty":
737 emitNull = false
738 mo.Format = ""
739 default:
740 return newInvalidFormatError(enc, t, mo)
741 }
742 }
743
744
745 n := va.Len()
746 if n == 0 {
747 if emitNull && va.IsNil() {
748 return enc.WriteToken(jsontext.Null)
749 }
750
751 if optimizeCommon && !mo.Flags.Get(jsonflags.AnyWhitespace) && !xe.Tokens.Last.NeedObjectName() {
752 xe.Buf = append(xe.Tokens.MayAppendDelim(xe.Buf, '{'), "{}"...)
753 xe.Tokens.Last.Increment()
754 if xe.NeedFlush() {
755 return xe.Flush()
756 }
757 return nil
758 }
759 }
760
761 once.Do(init)
762 if err := enc.WriteToken(jsontext.BeginObject); err != nil {
763 return err
764 }
765 if n > 0 {
766 nonDefaultKey := keyFncs.nonDefault
767 marshalKey := keyFncs.marshal
768 marshalVal := valFncs.marshal
769 if mo.Marshalers != nil {
770 var ok bool
771 marshalKey, ok = mo.Marshalers.(*Marshalers).lookup(marshalKey, t.Key())
772 marshalVal, _ = mo.Marshalers.(*Marshalers).lookup(marshalVal, t.Elem())
773 nonDefaultKey = nonDefaultKey || ok
774 }
775 k := newAddressableValue(t.Key())
776 v := newAddressableValue(t.Elem())
777
778
779
780
781 if !nonDefaultKey && mapKeyWithUniqueRepresentation(k.Kind(), mo.Flags.Get(jsonflags.AllowInvalidUTF8)) {
782 xe.Tokens.Last.DisableNamespace()
783 }
784
785 switch {
786 case !mo.Flags.Get(jsonflags.Deterministic) || n <= 1:
787 for iter := va.Value.MapRange(); iter.Next(); {
788 k.SetIterKey(iter)
789 err := marshalKey(enc, k, mo)
790 if err != nil {
791 if mo.Flags.Get(jsonflags.CallMethodsWithLegacySemantics) &&
792 errors.Is(err, jsontext.ErrNonStringName) && nillableLegacyKey && k.IsNil() {
793 err = enc.WriteToken(jsontext.String(""))
794 }
795 if err != nil {
796 if serr, ok := err.(*jsontext.SyntacticError); ok && serr.Err == jsontext.ErrNonStringName {
797 err = newMarshalErrorBefore(enc, k.Type(), err)
798 }
799 return err
800 }
801 }
802 v.SetIterValue(iter)
803 if err := marshalVal(enc, v, mo); err != nil {
804 return err
805 }
806 }
807 case !nonDefaultKey && t.Key().Kind() == reflect.String:
808 names := getStrings(n)
809 for i, iter := 0, va.Value.MapRange(); i < n && iter.Next(); i++ {
810 k.SetIterKey(iter)
811 (*names)[i] = k.String()
812 }
813 names.Sort()
814 for _, name := range *names {
815 if err := enc.WriteToken(jsontext.String(name)); err != nil {
816 return err
817 }
818
819 k.SetString(name)
820 v.Set(va.MapIndex(k.Value))
821 if err := marshalVal(enc, v, mo); err != nil {
822 return err
823 }
824 }
825 putStrings(names)
826 default:
827 type member struct {
828 name string
829 key addressableValue
830 val addressableValue
831 }
832 members := make([]member, n)
833 keys := reflect.MakeSlice(reflect.SliceOf(t.Key()), n, n)
834 vals := reflect.MakeSlice(reflect.SliceOf(t.Elem()), n, n)
835 for i, iter := 0, va.Value.MapRange(); i < n && iter.Next(); i++ {
836
837 k := addressableValue{keys.Index(i), true}
838 k.SetIterKey(iter)
839 v := addressableValue{vals.Index(i), true}
840 v.SetIterValue(iter)
841 err := marshalKey(enc, k, mo)
842 if err != nil {
843 if mo.Flags.Get(jsonflags.CallMethodsWithLegacySemantics) &&
844 errors.Is(err, jsontext.ErrNonStringName) && nillableLegacyKey && k.IsNil() {
845 err = enc.WriteToken(jsontext.String(""))
846 }
847 if err != nil {
848 if serr, ok := err.(*jsontext.SyntacticError); ok && serr.Err == jsontext.ErrNonStringName {
849 err = newMarshalErrorBefore(enc, k.Type(), err)
850 }
851 return err
852 }
853 }
854 name := xe.UnwriteOnlyObjectMemberName()
855 members[i] = member{name, k, v}
856 }
857
858
859
860 slices.SortFunc(members, func(x, y member) int {
861 return strings.Compare(x.name, y.name)
862 })
863 for _, member := range members {
864 if err := enc.WriteToken(jsontext.String(member.name)); err != nil {
865 return err
866 }
867 if err := marshalVal(enc, member.val, mo); err != nil {
868 return err
869 }
870 }
871 }
872 }
873 if err := enc.WriteToken(jsontext.EndObject); err != nil {
874 return err
875 }
876 return nil
877 }
878 fncs.unmarshal = func(dec *jsontext.Decoder, va addressableValue, uo *jsonopts.Struct) error {
879 xd := export.Decoder(dec)
880 if uo.Format != "" && uo.FormatDepth == xd.Tokens.Depth() {
881 switch uo.Format {
882 case "emitnull", "emitempty":
883 uo.Format = ""
884 default:
885 return newInvalidFormatError(dec, t, uo)
886 }
887 }
888 tok, err := dec.ReadToken()
889 if err != nil {
890 return err
891 }
892 k := tok.Kind()
893 switch k {
894 case 'n':
895 va.SetZero()
896 return nil
897 case '{':
898 once.Do(init)
899 if va.IsNil() {
900 va.Set(reflect.MakeMap(t))
901 }
902
903 nonDefaultKey := keyFncs.nonDefault
904 unmarshalKey := keyFncs.unmarshal
905 unmarshalVal := valFncs.unmarshal
906 if uo.Unmarshalers != nil {
907 var ok bool
908 unmarshalKey, ok = uo.Unmarshalers.(*Unmarshalers).lookup(unmarshalKey, t.Key())
909 unmarshalVal, _ = uo.Unmarshalers.(*Unmarshalers).lookup(unmarshalVal, t.Elem())
910 nonDefaultKey = nonDefaultKey || ok
911 }
912 k := newAddressableValue(t.Key())
913 v := newAddressableValue(t.Elem())
914
915
916
917
918
919
920
921 if !nonDefaultKey && mapKeyWithUniqueRepresentation(k.Kind(), uo.Flags.Get(jsonflags.AllowInvalidUTF8)) {
922 xd.Tokens.Last.DisableNamespace()
923 }
924
925
926
927
928
929 var seen reflect.Value
930 if !uo.Flags.Get(jsonflags.AllowDuplicateNames) && va.Len() > 0 {
931 seen = reflect.MakeMap(reflect.MapOf(k.Type(), emptyStructType))
932 }
933
934 var errUnmarshal error
935 for dec.PeekKind() != '}' {
936
937 k.SetZero()
938 err := unmarshalKey(dec, k, uo)
939 if err != nil {
940 if isFatalError(err, uo.Flags) {
941 return err
942 }
943 if err := dec.SkipValue(); err != nil {
944 return err
945 }
946 errUnmarshal = cmp.Or(errUnmarshal, err)
947 continue
948 }
949 if k.Kind() == reflect.Interface && !k.IsNil() && !k.Elem().Type().Comparable() {
950 err := newUnmarshalErrorAfter(dec, t, fmt.Errorf("invalid incomparable key type %v", k.Elem().Type()))
951 if !uo.Flags.Get(jsonflags.ReportErrorsWithLegacySemantics) {
952 return err
953 }
954 if err2 := dec.SkipValue(); err2 != nil {
955 return err2
956 }
957 errUnmarshal = cmp.Or(errUnmarshal, err)
958 continue
959 }
960
961
962 if v2 := va.MapIndex(k.Value); v2.IsValid() {
963 if !uo.Flags.Get(jsonflags.AllowDuplicateNames) && (!seen.IsValid() || seen.MapIndex(k.Value).IsValid()) {
964
965 name := xd.PreviousTokenOrValue()
966 return newDuplicateNameError(dec.StackPointer(), nil, dec.InputOffset()-len64(name))
967 }
968 if !uo.Flags.Get(jsonflags.MergeWithLegacySemantics) {
969 v.Set(v2)
970 } else {
971 v.SetZero()
972 }
973 } else {
974 v.SetZero()
975 }
976
977
978 err = unmarshalVal(dec, v, uo)
979 va.SetMapIndex(k.Value, v.Value)
980 if seen.IsValid() {
981 seen.SetMapIndex(k.Value, reflect.Zero(emptyStructType))
982 }
983 if err != nil {
984 if isFatalError(err, uo.Flags) {
985 return err
986 }
987 errUnmarshal = cmp.Or(errUnmarshal, err)
988 }
989 }
990 if _, err := dec.ReadToken(); err != nil {
991 return err
992 }
993 return errUnmarshal
994 }
995 return newUnmarshalErrorAfterWithSkipping(dec, uo, t, nil)
996 }
997 return &fncs
998 }
999
1000
1001
1002
1003
1004 func mapKeyWithUniqueRepresentation(k reflect.Kind, allowInvalidUTF8 bool) bool {
1005 switch k {
1006 case reflect.Bool,
1007 reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64,
1008 reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
1009 return true
1010 case reflect.String:
1011
1012
1013 return !allowInvalidUTF8
1014 default:
1015
1016
1017 return false
1018 }
1019 }
1020
1021 var errNilField = errors.New("cannot set embedded pointer to unexported struct type")
1022
1023 func makeStructArshaler(t reflect.Type) *arshaler {
1024
1025
1026
1027
1028 var fncs arshaler
1029 var (
1030 once sync.Once
1031 fields structFields
1032 errInit *SemanticError
1033 )
1034 init := func() {
1035 fields, errInit = makeStructFields(t)
1036 }
1037 fncs.marshal = func(enc *jsontext.Encoder, va addressableValue, mo *jsonopts.Struct) error {
1038 xe := export.Encoder(enc)
1039 if mo.Format != "" && mo.FormatDepth == xe.Tokens.Depth() {
1040 return newInvalidFormatError(enc, t, mo)
1041 }
1042 once.Do(init)
1043 if errInit != nil && !mo.Flags.Get(jsonflags.ReportErrorsWithLegacySemantics) {
1044 return newMarshalErrorBefore(enc, errInit.GoType, errInit.Err)
1045 }
1046 if err := enc.WriteToken(jsontext.BeginObject); err != nil {
1047 return err
1048 }
1049 var seenIdxs uintSet
1050 prevIdx := -1
1051 xe.Tokens.Last.DisableNamespace()
1052 for i := range fields.flattened {
1053 f := &fields.flattened[i]
1054 v := addressableValue{va.Field(f.index0), va.forcedAddr}
1055 if len(f.index) > 0 {
1056 v = v.fieldByIndex(f.index, false)
1057 if !v.IsValid() {
1058 continue
1059 }
1060 }
1061
1062
1063
1064 if (f.omitzero || mo.Flags.Get(jsonflags.OmitZeroStructFields)) &&
1065 ((f.isZero == nil && v.IsZero()) || (f.isZero != nil && f.isZero(v))) {
1066 continue
1067 }
1068
1069
1070 if f.omitempty && mo.Flags.Get(jsonflags.OmitEmptyWithLegacySemantics) && isLegacyEmpty(v) {
1071 continue
1072 }
1073
1074 marshal := f.fncs.marshal
1075 nonDefault := f.fncs.nonDefault
1076 if mo.Marshalers != nil {
1077 var ok bool
1078 marshal, ok = mo.Marshalers.(*Marshalers).lookup(marshal, f.typ)
1079 nonDefault = nonDefault || ok
1080 }
1081
1082
1083
1084
1085 if f.omitempty && !mo.Flags.Get(jsonflags.OmitEmptyWithLegacySemantics) &&
1086 !nonDefault && f.isEmpty != nil && f.isEmpty(v) {
1087 continue
1088 }
1089
1090
1091
1092
1093
1094
1095
1096
1097
1098
1099
1100 if optimizeCommon {
1101
1102 b := xe.Buf
1103 if xe.Tokens.Last.Length() > 0 {
1104 b = append(b, ',')
1105 if mo.Flags.Get(jsonflags.SpaceAfterComma) {
1106 b = append(b, ' ')
1107 }
1108 }
1109 if mo.Flags.Get(jsonflags.Multiline) {
1110 b = xe.AppendIndent(b, xe.Tokens.NeedIndent('"'))
1111 }
1112
1113
1114 n0 := len(b)
1115 if !f.nameNeedEscape {
1116 b = append(b, f.quotedName...)
1117 } else {
1118 b, _ = jsonwire.AppendQuote(b, f.name, &mo.Flags)
1119 }
1120 xe.Buf = b
1121 xe.Names.ReplaceLastQuotedOffset(n0)
1122 xe.Tokens.Last.Increment()
1123 } else {
1124 if err := enc.WriteToken(jsontext.String(f.name)); err != nil {
1125 return err
1126 }
1127 }
1128
1129
1130 flagsOriginal := mo.Flags
1131 if f.string {
1132 if !mo.Flags.Get(jsonflags.StringifyWithLegacySemantics) {
1133 mo.Flags.Set(jsonflags.StringifyNumbers | 1)
1134 } else if canLegacyStringify(f.typ) {
1135 mo.Flags.Set(jsonflags.StringifyNumbers | jsonflags.StringifyBoolsAndStrings | 1)
1136 }
1137 }
1138 if f.format != "" {
1139 mo.FormatDepth = xe.Tokens.Depth()
1140 mo.Format = f.format
1141 }
1142 err := marshal(enc, v, mo)
1143 mo.Flags = flagsOriginal
1144 mo.Format = ""
1145 if err != nil {
1146 return err
1147 }
1148
1149
1150 if f.omitempty && !mo.Flags.Get(jsonflags.OmitEmptyWithLegacySemantics) {
1151 var prevName *string
1152 if prevIdx >= 0 {
1153 prevName = &fields.flattened[prevIdx].name
1154 }
1155 if xe.UnwriteEmptyObjectMember(prevName) {
1156 continue
1157 }
1158 }
1159
1160
1161
1162
1163 if !mo.Flags.Get(jsonflags.AllowDuplicateNames) && fields.inlinedFallback != nil {
1164 seenIdxs.insert(uint(f.id))
1165 }
1166 prevIdx = f.id
1167 }
1168 if fields.inlinedFallback != nil && !(mo.Flags.Get(jsonflags.DiscardUnknownMembers) && fields.inlinedFallback.unknown) {
1169 var insertUnquotedName func([]byte) bool
1170 if !mo.Flags.Get(jsonflags.AllowDuplicateNames) {
1171 insertUnquotedName = func(name []byte) bool {
1172
1173
1174 if foldedFields := fields.lookupByFoldedName(name); len(foldedFields) > 0 {
1175 if f := fields.byActualName[string(name)]; f != nil {
1176 return seenIdxs.insert(uint(f.id))
1177 }
1178 for _, f := range foldedFields {
1179 if f.matchFoldedName(name, &mo.Flags) {
1180 return seenIdxs.insert(uint(f.id))
1181 }
1182 }
1183 }
1184
1185
1186
1187 return xe.Namespaces.Last().InsertUnquoted(name)
1188 }
1189 }
1190 if err := marshalInlinedFallbackAll(enc, va, mo, fields.inlinedFallback, insertUnquotedName); err != nil {
1191 return err
1192 }
1193 }
1194 if err := enc.WriteToken(jsontext.EndObject); err != nil {
1195 return err
1196 }
1197 return nil
1198 }
1199 fncs.unmarshal = func(dec *jsontext.Decoder, va addressableValue, uo *jsonopts.Struct) error {
1200 xd := export.Decoder(dec)
1201 if uo.Format != "" && uo.FormatDepth == xd.Tokens.Depth() {
1202 return newInvalidFormatError(dec, t, uo)
1203 }
1204 tok, err := dec.ReadToken()
1205 if err != nil {
1206 return err
1207 }
1208 k := tok.Kind()
1209 switch k {
1210 case 'n':
1211 if !uo.Flags.Get(jsonflags.MergeWithLegacySemantics) {
1212 va.SetZero()
1213 }
1214 return nil
1215 case '{':
1216 once.Do(init)
1217 if errInit != nil && !uo.Flags.Get(jsonflags.ReportErrorsWithLegacySemantics) {
1218 return newUnmarshalErrorAfter(dec, errInit.GoType, errInit.Err)
1219 }
1220 var seenIdxs uintSet
1221 xd.Tokens.Last.DisableNamespace()
1222 var errUnmarshal error
1223 for dec.PeekKind() != '}' {
1224
1225 var flags jsonwire.ValueFlags
1226 val, err := xd.ReadValue(&flags)
1227 if err != nil {
1228 return err
1229 }
1230 name := jsonwire.UnquoteMayCopy(val, flags.IsVerbatim())
1231 f := fields.byActualName[string(name)]
1232 if f == nil {
1233 for _, f2 := range fields.lookupByFoldedName(name) {
1234 if f2.matchFoldedName(name, &uo.Flags) {
1235 f = f2
1236 break
1237 }
1238 }
1239 if f == nil {
1240 if uo.Flags.Get(jsonflags.RejectUnknownMembers) && (fields.inlinedFallback == nil || fields.inlinedFallback.unknown) {
1241 err := newUnmarshalErrorAfter(dec, t, ErrUnknownName)
1242 if !uo.Flags.Get(jsonflags.ReportErrorsWithLegacySemantics) {
1243 return err
1244 }
1245 errUnmarshal = cmp.Or(errUnmarshal, err)
1246 }
1247 if !uo.Flags.Get(jsonflags.AllowDuplicateNames) && !xd.Namespaces.Last().InsertUnquoted(name) {
1248
1249 return newDuplicateNameError(dec.StackPointer(), nil, dec.InputOffset()-len64(val))
1250 }
1251
1252 if fields.inlinedFallback == nil {
1253
1254 if err := dec.SkipValue(); err != nil {
1255 return err
1256 }
1257 } else {
1258
1259 if err := unmarshalInlinedFallbackNext(dec, va, uo, fields.inlinedFallback, val, name); err != nil {
1260 if isFatalError(err, uo.Flags) {
1261 return err
1262 }
1263 errUnmarshal = cmp.Or(errUnmarshal, err)
1264 }
1265 }
1266 continue
1267 }
1268 }
1269 if !uo.Flags.Get(jsonflags.AllowDuplicateNames) && !seenIdxs.insert(uint(f.id)) {
1270
1271 return newDuplicateNameError(dec.StackPointer(), nil, dec.InputOffset()-len64(val))
1272 }
1273
1274
1275 unmarshal := f.fncs.unmarshal
1276 if uo.Unmarshalers != nil {
1277 unmarshal, _ = uo.Unmarshalers.(*Unmarshalers).lookup(unmarshal, f.typ)
1278 }
1279 flagsOriginal := uo.Flags
1280 if f.string {
1281 if !uo.Flags.Get(jsonflags.StringifyWithLegacySemantics) {
1282 uo.Flags.Set(jsonflags.StringifyNumbers | 1)
1283 } else if canLegacyStringify(f.typ) {
1284 uo.Flags.Set(jsonflags.StringifyNumbers | jsonflags.StringifyBoolsAndStrings | 1)
1285 }
1286 }
1287 if f.format != "" {
1288 uo.FormatDepth = xd.Tokens.Depth()
1289 uo.Format = f.format
1290 }
1291 v := addressableValue{va.Field(f.index0), va.forcedAddr}
1292 if len(f.index) > 0 {
1293 v = v.fieldByIndex(f.index, true)
1294 if !v.IsValid() {
1295 err := newUnmarshalErrorBefore(dec, t, errNilField)
1296 if !uo.Flags.Get(jsonflags.ReportErrorsWithLegacySemantics) {
1297 return err
1298 }
1299 errUnmarshal = cmp.Or(errUnmarshal, err)
1300 unmarshal = func(dec *jsontext.Decoder, _ addressableValue, _ *jsonopts.Struct) error {
1301 return dec.SkipValue()
1302 }
1303 }
1304 }
1305 err = unmarshal(dec, v, uo)
1306 uo.Flags = flagsOriginal
1307 uo.Format = ""
1308 if err != nil {
1309 if isFatalError(err, uo.Flags) {
1310 return err
1311 }
1312 errUnmarshal = cmp.Or(errUnmarshal, err)
1313 }
1314 }
1315 if _, err := dec.ReadToken(); err != nil {
1316 return err
1317 }
1318 return errUnmarshal
1319 }
1320 return newUnmarshalErrorAfterWithSkipping(dec, uo, t, nil)
1321 }
1322 return &fncs
1323 }
1324
1325 func (va addressableValue) fieldByIndex(index []int, mayAlloc bool) addressableValue {
1326 for _, i := range index {
1327 va = va.indirect(mayAlloc)
1328 if !va.IsValid() {
1329 return va
1330 }
1331 va = addressableValue{va.Field(i), va.forcedAddr}
1332 }
1333 return va
1334 }
1335
1336 func (va addressableValue) indirect(mayAlloc bool) addressableValue {
1337 if va.Kind() == reflect.Pointer {
1338 if va.IsNil() {
1339 if !mayAlloc || !va.CanSet() {
1340 return addressableValue{}
1341 }
1342 va.Set(reflect.New(va.Type().Elem()))
1343 }
1344 va = addressableValue{va.Elem(), false}
1345 }
1346 return va
1347 }
1348
1349
1350 func isLegacyEmpty(v addressableValue) bool {
1351
1352 switch v.Kind() {
1353 case reflect.Bool:
1354 return v.Bool() == false
1355 case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
1356 return v.Int() == 0
1357 case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
1358 return v.Uint() == 0
1359 case reflect.Float32, reflect.Float64:
1360 return v.Float() == 0
1361 case reflect.String, reflect.Map, reflect.Slice, reflect.Array:
1362 return v.Len() == 0
1363 case reflect.Pointer, reflect.Interface:
1364 return v.IsNil()
1365 }
1366 return false
1367 }
1368
1369
1370
1371
1372
1373 func canLegacyStringify(t reflect.Type) bool {
1374
1375 if t.Name() == "" && t.Kind() == reflect.Ptr {
1376 t = t.Elem()
1377 }
1378 switch t.Kind() {
1379 case reflect.Bool, reflect.String,
1380 reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64,
1381 reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr,
1382 reflect.Float32, reflect.Float64:
1383 return true
1384 }
1385 return false
1386 }
1387
1388 func makeSliceArshaler(t reflect.Type) *arshaler {
1389 var fncs arshaler
1390 var (
1391 once sync.Once
1392 valFncs *arshaler
1393 )
1394 init := func() {
1395 valFncs = lookupArshaler(t.Elem())
1396 }
1397 fncs.marshal = func(enc *jsontext.Encoder, va addressableValue, mo *jsonopts.Struct) error {
1398
1399 xe := export.Encoder(enc)
1400 if xe.Tokens.Depth() > startDetectingCyclesAfter {
1401 if err := visitPointer(&xe.SeenPointers, va.Value); err != nil {
1402 return newMarshalErrorBefore(enc, t, err)
1403 }
1404 defer leavePointer(&xe.SeenPointers, va.Value)
1405 }
1406
1407 emitNull := mo.Flags.Get(jsonflags.FormatNilSliceAsNull)
1408 if mo.Format != "" && mo.FormatDepth == xe.Tokens.Depth() {
1409 switch mo.Format {
1410 case "emitnull":
1411 emitNull = true
1412 mo.Format = ""
1413 case "emitempty":
1414 emitNull = false
1415 mo.Format = ""
1416 default:
1417 return newInvalidFormatError(enc, t, mo)
1418 }
1419 }
1420
1421
1422 n := va.Len()
1423 if n == 0 {
1424 if emitNull && va.IsNil() {
1425 return enc.WriteToken(jsontext.Null)
1426 }
1427
1428 if optimizeCommon && !mo.Flags.Get(jsonflags.AnyWhitespace) && !xe.Tokens.Last.NeedObjectName() {
1429 xe.Buf = append(xe.Tokens.MayAppendDelim(xe.Buf, '['), "[]"...)
1430 xe.Tokens.Last.Increment()
1431 if xe.NeedFlush() {
1432 return xe.Flush()
1433 }
1434 return nil
1435 }
1436 }
1437
1438 once.Do(init)
1439 if err := enc.WriteToken(jsontext.BeginArray); err != nil {
1440 return err
1441 }
1442 marshal := valFncs.marshal
1443 if mo.Marshalers != nil {
1444 marshal, _ = mo.Marshalers.(*Marshalers).lookup(marshal, t.Elem())
1445 }
1446 for i := range n {
1447 v := addressableValue{va.Index(i), false}
1448 if err := marshal(enc, v, mo); err != nil {
1449 return err
1450 }
1451 }
1452 if err := enc.WriteToken(jsontext.EndArray); err != nil {
1453 return err
1454 }
1455 return nil
1456 }
1457 emptySlice := reflect.MakeSlice(t, 0, 0)
1458 fncs.unmarshal = func(dec *jsontext.Decoder, va addressableValue, uo *jsonopts.Struct) error {
1459 xd := export.Decoder(dec)
1460 if uo.Format != "" && uo.FormatDepth == xd.Tokens.Depth() {
1461 switch uo.Format {
1462 case "emitnull", "emitempty":
1463 uo.Format = ""
1464 default:
1465 return newInvalidFormatError(dec, t, uo)
1466 }
1467 }
1468
1469 tok, err := dec.ReadToken()
1470 if err != nil {
1471 return err
1472 }
1473 k := tok.Kind()
1474 switch k {
1475 case 'n':
1476 va.SetZero()
1477 return nil
1478 case '[':
1479 once.Do(init)
1480 unmarshal := valFncs.unmarshal
1481 if uo.Unmarshalers != nil {
1482 unmarshal, _ = uo.Unmarshalers.(*Unmarshalers).lookup(unmarshal, t.Elem())
1483 }
1484 mustZero := true
1485 cap := va.Cap()
1486 if cap > 0 {
1487 va.SetLen(cap)
1488 }
1489 var i int
1490 var errUnmarshal error
1491 for dec.PeekKind() != ']' {
1492 if i == cap {
1493 va.Value.Grow(1)
1494 cap = va.Cap()
1495 va.SetLen(cap)
1496 mustZero = false
1497 }
1498 v := addressableValue{va.Index(i), false}
1499 i++
1500 if mustZero && !uo.Flags.Get(jsonflags.MergeWithLegacySemantics) {
1501 v.SetZero()
1502 }
1503 if err := unmarshal(dec, v, uo); err != nil {
1504 if isFatalError(err, uo.Flags) {
1505 va.SetLen(i)
1506 return err
1507 }
1508 errUnmarshal = cmp.Or(errUnmarshal, err)
1509 }
1510 }
1511 if i == 0 {
1512 va.Set(emptySlice)
1513 } else {
1514 va.SetLen(i)
1515 }
1516 if _, err := dec.ReadToken(); err != nil {
1517 return err
1518 }
1519 return errUnmarshal
1520 }
1521 return newUnmarshalErrorAfterWithSkipping(dec, uo, t, nil)
1522 }
1523 return &fncs
1524 }
1525
1526 var errArrayUnderflow = errors.New("too few array elements")
1527 var errArrayOverflow = errors.New("too many array elements")
1528
1529 func makeArrayArshaler(t reflect.Type) *arshaler {
1530 var fncs arshaler
1531 var (
1532 once sync.Once
1533 valFncs *arshaler
1534 )
1535 init := func() {
1536 valFncs = lookupArshaler(t.Elem())
1537 }
1538 n := t.Len()
1539 fncs.marshal = func(enc *jsontext.Encoder, va addressableValue, mo *jsonopts.Struct) error {
1540 xe := export.Encoder(enc)
1541 if mo.Format != "" && mo.FormatDepth == xe.Tokens.Depth() {
1542 return newInvalidFormatError(enc, t, mo)
1543 }
1544 once.Do(init)
1545 if err := enc.WriteToken(jsontext.BeginArray); err != nil {
1546 return err
1547 }
1548 marshal := valFncs.marshal
1549 if mo.Marshalers != nil {
1550 marshal, _ = mo.Marshalers.(*Marshalers).lookup(marshal, t.Elem())
1551 }
1552 for i := range n {
1553 v := addressableValue{va.Index(i), va.forcedAddr}
1554 if err := marshal(enc, v, mo); err != nil {
1555 return err
1556 }
1557 }
1558 if err := enc.WriteToken(jsontext.EndArray); err != nil {
1559 return err
1560 }
1561 return nil
1562 }
1563 fncs.unmarshal = func(dec *jsontext.Decoder, va addressableValue, uo *jsonopts.Struct) error {
1564 xd := export.Decoder(dec)
1565 if uo.Format != "" && uo.FormatDepth == xd.Tokens.Depth() {
1566 return newInvalidFormatError(dec, t, uo)
1567 }
1568 tok, err := dec.ReadToken()
1569 if err != nil {
1570 return err
1571 }
1572 k := tok.Kind()
1573 switch k {
1574 case 'n':
1575 if !uo.Flags.Get(jsonflags.MergeWithLegacySemantics) {
1576 va.SetZero()
1577 }
1578 return nil
1579 case '[':
1580 once.Do(init)
1581 unmarshal := valFncs.unmarshal
1582 if uo.Unmarshalers != nil {
1583 unmarshal, _ = uo.Unmarshalers.(*Unmarshalers).lookup(unmarshal, t.Elem())
1584 }
1585 var i int
1586 var errUnmarshal error
1587 for dec.PeekKind() != ']' {
1588 if i >= n {
1589 if err := dec.SkipValue(); err != nil {
1590 return err
1591 }
1592 err = errArrayOverflow
1593 continue
1594 }
1595 v := addressableValue{va.Index(i), va.forcedAddr}
1596 if !uo.Flags.Get(jsonflags.MergeWithLegacySemantics) {
1597 v.SetZero()
1598 }
1599 if err := unmarshal(dec, v, uo); err != nil {
1600 if isFatalError(err, uo.Flags) {
1601 return err
1602 }
1603 errUnmarshal = cmp.Or(errUnmarshal, err)
1604 }
1605 i++
1606 }
1607 for ; i < n; i++ {
1608 va.Index(i).SetZero()
1609 err = errArrayUnderflow
1610 }
1611 if _, err := dec.ReadToken(); err != nil {
1612 return err
1613 }
1614 if err != nil && !uo.Flags.Get(jsonflags.UnmarshalArrayFromAnyLength) {
1615 return newUnmarshalErrorAfter(dec, t, err)
1616 }
1617 return errUnmarshal
1618 }
1619 return newUnmarshalErrorAfterWithSkipping(dec, uo, t, nil)
1620 }
1621 return &fncs
1622 }
1623
1624 func makePointerArshaler(t reflect.Type) *arshaler {
1625 var fncs arshaler
1626 var (
1627 once sync.Once
1628 valFncs *arshaler
1629 )
1630 init := func() {
1631 valFncs = lookupArshaler(t.Elem())
1632 }
1633 fncs.marshal = func(enc *jsontext.Encoder, va addressableValue, mo *jsonopts.Struct) error {
1634
1635 xe := export.Encoder(enc)
1636 if xe.Tokens.Depth() > startDetectingCyclesAfter {
1637 if err := visitPointer(&xe.SeenPointers, va.Value); err != nil {
1638 return newMarshalErrorBefore(enc, t, err)
1639 }
1640 defer leavePointer(&xe.SeenPointers, va.Value)
1641 }
1642
1643
1644 if va.IsNil() {
1645 return enc.WriteToken(jsontext.Null)
1646 }
1647 once.Do(init)
1648 marshal := valFncs.marshal
1649 if mo.Marshalers != nil {
1650 marshal, _ = mo.Marshalers.(*Marshalers).lookup(marshal, t.Elem())
1651 }
1652 v := addressableValue{va.Elem(), false}
1653 return marshal(enc, v, mo)
1654 }
1655 fncs.unmarshal = func(dec *jsontext.Decoder, va addressableValue, uo *jsonopts.Struct) error {
1656
1657 if dec.PeekKind() == 'n' {
1658 if _, err := dec.ReadToken(); err != nil {
1659 return err
1660 }
1661 va.SetZero()
1662 return nil
1663 }
1664 once.Do(init)
1665 unmarshal := valFncs.unmarshal
1666 if uo.Unmarshalers != nil {
1667 unmarshal, _ = uo.Unmarshalers.(*Unmarshalers).lookup(unmarshal, t.Elem())
1668 }
1669 if va.IsNil() {
1670 va.Set(reflect.New(t.Elem()))
1671 }
1672 v := addressableValue{va.Elem(), false}
1673 if err := unmarshal(dec, v, uo); err != nil {
1674 return err
1675 }
1676 if uo.Flags.Get(jsonflags.StringifyWithLegacySemantics) &&
1677 uo.Flags.Get(jsonflags.StringifyNumbers|jsonflags.StringifyBoolsAndStrings) {
1678
1679
1680
1681
1682
1683
1684 if string(export.Decoder(dec).PreviousTokenOrValue()) == `"null"` {
1685 va.SetZero()
1686 }
1687 }
1688 return nil
1689 }
1690 return &fncs
1691 }
1692
1693 func makeInterfaceArshaler(t reflect.Type) *arshaler {
1694
1695
1696
1697
1698 var fncs arshaler
1699 var whichMarshaler reflect.Type
1700 for _, iface := range allMarshalerTypes {
1701 if t.Implements(iface) {
1702 whichMarshaler = t
1703 break
1704 }
1705 }
1706 fncs.marshal = func(enc *jsontext.Encoder, va addressableValue, mo *jsonopts.Struct) error {
1707 xe := export.Encoder(enc)
1708 if mo.Format != "" && mo.FormatDepth == xe.Tokens.Depth() {
1709 return newInvalidFormatError(enc, t, mo)
1710 }
1711 if va.IsNil() {
1712 return enc.WriteToken(jsontext.Null)
1713 } else if mo.Flags.Get(jsonflags.CallMethodsWithLegacySemantics) && whichMarshaler != nil {
1714
1715
1716
1717 if va.Elem().Kind() == reflect.Pointer && va.Elem().IsNil() {
1718 v2 := newAddressableValue(whichMarshaler)
1719 switch whichMarshaler {
1720 case jsonMarshalerToType:
1721 v2.Set(reflect.ValueOf(struct{ MarshalerTo }{va.Elem().Interface().(MarshalerTo)}))
1722 case jsonMarshalerType:
1723 v2.Set(reflect.ValueOf(struct{ Marshaler }{va.Elem().Interface().(Marshaler)}))
1724 case textAppenderType:
1725 v2.Set(reflect.ValueOf(struct{ encoding.TextAppender }{va.Elem().Interface().(encoding.TextAppender)}))
1726 case textMarshalerType:
1727 v2.Set(reflect.ValueOf(struct{ encoding.TextMarshaler }{va.Elem().Interface().(encoding.TextMarshaler)}))
1728 }
1729 va = v2
1730 }
1731 }
1732 v := newAddressableValue(va.Elem().Type())
1733 v.Set(va.Elem())
1734 marshal := lookupArshaler(v.Type()).marshal
1735 if mo.Marshalers != nil {
1736 marshal, _ = mo.Marshalers.(*Marshalers).lookup(marshal, v.Type())
1737 }
1738
1739 if optimizeCommon &&
1740 t == anyType && !mo.Flags.Get(jsonflags.StringifyNumbers|jsonflags.StringifyBoolsAndStrings) && mo.Format == "" &&
1741 (mo.Marshalers == nil || !mo.Marshalers.(*Marshalers).fromAny) {
1742 return marshalValueAny(enc, va.Elem().Interface(), mo)
1743 }
1744 return marshal(enc, v, mo)
1745 }
1746 fncs.unmarshal = func(dec *jsontext.Decoder, va addressableValue, uo *jsonopts.Struct) error {
1747 xd := export.Decoder(dec)
1748 if uo.Format != "" && uo.FormatDepth == xd.Tokens.Depth() {
1749 return newInvalidFormatError(dec, t, uo)
1750 }
1751 if uo.Flags.Get(jsonflags.MergeWithLegacySemantics) && !va.IsNil() {
1752
1753
1754
1755
1756
1757 e := va.Elem()
1758 if e.Kind() == reflect.Pointer && !e.IsNil() {
1759 if dec.PeekKind() == 'n' && e.Elem().Kind() == reflect.Pointer {
1760 if _, err := dec.ReadToken(); err != nil {
1761 return err
1762 }
1763 va.Elem().Elem().SetZero()
1764 return nil
1765 }
1766 } else {
1767 va.SetZero()
1768 }
1769 }
1770 if dec.PeekKind() == 'n' {
1771 if _, err := dec.ReadToken(); err != nil {
1772 return err
1773 }
1774 va.SetZero()
1775 return nil
1776 }
1777 var v addressableValue
1778 if va.IsNil() {
1779
1780
1781
1782
1783
1784 if optimizeCommon &&
1785 t == anyType && !uo.Flags.Get(jsonflags.AllowDuplicateNames) && uo.Format == "" &&
1786 (uo.Unmarshalers == nil || !uo.Unmarshalers.(*Unmarshalers).fromAny) {
1787 v, err := unmarshalValueAny(dec, uo)
1788
1789
1790 if v != nil {
1791 va.Set(reflect.ValueOf(v))
1792 }
1793 return err
1794 }
1795
1796 k := dec.PeekKind()
1797 if !isAnyType(t) {
1798 return newUnmarshalErrorBeforeWithSkipping(dec, uo, t, internal.ErrNilInterface)
1799 }
1800 switch k {
1801 case 'f', 't':
1802 v = newAddressableValue(boolType)
1803 case '"':
1804 v = newAddressableValue(stringType)
1805 case '0':
1806 if uo.Flags.Get(jsonflags.UnmarshalAnyWithRawNumber) {
1807 v = addressableValue{reflect.ValueOf(internal.NewRawNumber()).Elem(), true}
1808 } else {
1809 v = newAddressableValue(float64Type)
1810 }
1811 case '{':
1812 v = newAddressableValue(mapStringAnyType)
1813 case '[':
1814 v = newAddressableValue(sliceAnyType)
1815 default:
1816
1817
1818
1819
1820 _, err := dec.ReadValue()
1821 return err
1822 }
1823 } else {
1824
1825
1826
1827 v = newAddressableValue(va.Elem().Type())
1828 v.Set(va.Elem())
1829 }
1830 unmarshal := lookupArshaler(v.Type()).unmarshal
1831 if uo.Unmarshalers != nil {
1832 unmarshal, _ = uo.Unmarshalers.(*Unmarshalers).lookup(unmarshal, v.Type())
1833 }
1834 err := unmarshal(dec, v, uo)
1835 va.Set(v.Value)
1836 return err
1837 }
1838 return &fncs
1839 }
1840
1841
1842 func isAnyType(t reflect.Type) bool {
1843
1844
1845
1846
1847 return t == anyType || anyType.Implements(t)
1848 }
1849
1850 func makeInvalidArshaler(t reflect.Type) *arshaler {
1851 var fncs arshaler
1852 fncs.marshal = func(enc *jsontext.Encoder, va addressableValue, mo *jsonopts.Struct) error {
1853 return newMarshalErrorBefore(enc, t, nil)
1854 }
1855 fncs.unmarshal = func(dec *jsontext.Decoder, va addressableValue, uo *jsonopts.Struct) error {
1856 return newUnmarshalErrorBefore(dec, t, nil)
1857 }
1858 return &fncs
1859 }
1860
1861 func stringOrNumberKind(isString bool) jsontext.Kind {
1862 if isString {
1863 return '"'
1864 } else {
1865 return '0'
1866 }
1867 }
1868
1869 type uintSet64 uint64
1870
1871 func (s uintSet64) has(i uint) bool { return s&(1<<i) > 0 }
1872 func (s *uintSet64) set(i uint) { *s |= 1 << i }
1873
1874
1875
1876 type uintSet struct {
1877 lo uintSet64
1878 hi []uintSet64
1879 }
1880
1881
1882 func (s *uintSet) has(i uint) bool {
1883 if i < 64 {
1884 return s.lo.has(i)
1885 } else {
1886 i -= 64
1887 iHi, iLo := int(i/64), i%64
1888 return iHi < len(s.hi) && s.hi[iHi].has(iLo)
1889 }
1890 }
1891
1892
1893 func (s *uintSet) insert(i uint) bool {
1894
1895 if i < 64 {
1896 has := s.lo.has(i)
1897 s.lo.set(i)
1898 return !has
1899 } else {
1900 i -= 64
1901 iHi, iLo := int(i/64), i%64
1902 if iHi >= len(s.hi) {
1903 s.hi = append(s.hi, make([]uintSet64, iHi+1-len(s.hi))...)
1904 s.hi = s.hi[:cap(s.hi)]
1905 }
1906 has := s.hi[iHi].has(iLo)
1907 s.hi[iHi].set(iLo)
1908 return !has
1909 }
1910 }
1911
View as plain text