decoder_compat.go 5.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201
  1. //go:build (!amd64 && !arm64) || go1.25 || !go1.17 || (arm64 && !go1.20)
  2. // +build !amd64,!arm64 go1.25 !go1.17 arm64,!go1.20
  3. /*
  4. * Copyright 2023 ByteDance Inc.
  5. *
  6. * Licensed under the Apache License, Version 2.0 (the "License");
  7. * you may not use this file except in compliance with the License.
  8. * You may obtain a copy of the License at
  9. *
  10. * http://www.apache.org/licenses/LICENSE-2.0
  11. *
  12. * Unless required by applicable law or agreed to in writing, software
  13. * distributed under the License is distributed on an "AS IS" BASIS,
  14. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  15. * See the License for the specific language governing permissions and
  16. * limitations under the License.
  17. */
  18. package decoder
  19. import (
  20. "bytes"
  21. "encoding/json"
  22. "io"
  23. "reflect"
  24. "unsafe"
  25. "github.com/bytedance/sonic/internal/decoder/consts"
  26. "github.com/bytedance/sonic/internal/native/types"
  27. "github.com/bytedance/sonic/option"
  28. "github.com/bytedance/sonic/internal/compat"
  29. )
  30. func init() {
  31. compat.Warn("sonic/decoder")
  32. }
  33. const (
  34. _F_use_int64 = consts.F_use_int64
  35. _F_disable_urc = consts.F_disable_unknown
  36. _F_disable_unknown = consts.F_disable_unknown
  37. _F_copy_string = consts.F_copy_string
  38. _F_use_number = consts.F_use_number
  39. _F_validate_string = consts.F_validate_string
  40. _F_allow_control = consts.F_allow_control
  41. _F_no_validate_json = consts.F_no_validate_json
  42. _F_case_sensitive = consts.F_case_sensitive
  43. )
  44. type Options uint64
  45. const (
  46. OptionUseInt64 Options = 1 << _F_use_int64
  47. OptionUseNumber Options = 1 << _F_use_number
  48. OptionUseUnicodeErrors Options = 1 << _F_disable_urc
  49. OptionDisableUnknown Options = 1 << _F_disable_unknown
  50. OptionCopyString Options = 1 << _F_copy_string
  51. OptionValidateString Options = 1 << _F_validate_string
  52. OptionNoValidateJSON Options = 1 << _F_no_validate_json
  53. OptionCaseSensitive Options = 1 << _F_case_sensitive
  54. )
  55. func (self *Decoder) SetOptions(opts Options) {
  56. if (opts & OptionUseNumber != 0) && (opts & OptionUseInt64 != 0) {
  57. panic("can't set OptionUseInt64 and OptionUseNumber both!")
  58. }
  59. self.f = uint64(opts)
  60. }
  61. // Decoder is the decoder context object
  62. type Decoder struct {
  63. i int
  64. f uint64
  65. s string
  66. }
  67. // NewDecoder creates a new decoder instance.
  68. func NewDecoder(s string) *Decoder {
  69. return &Decoder{s: s}
  70. }
  71. // Pos returns the current decoding position.
  72. func (self *Decoder) Pos() int {
  73. return self.i
  74. }
  75. func (self *Decoder) Reset(s string) {
  76. self.s = s
  77. self.i = 0
  78. // self.f = 0
  79. }
  80. // NOTE: api fallback do nothing
  81. func (self *Decoder) CheckTrailings() error {
  82. pos := self.i
  83. buf := self.s
  84. /* skip all the trailing spaces */
  85. if pos != len(buf) {
  86. for pos < len(buf) && (types.SPACE_MASK & (1 << buf[pos])) != 0 {
  87. pos++
  88. }
  89. }
  90. /* then it must be at EOF */
  91. if pos == len(buf) {
  92. return nil
  93. }
  94. /* junk after JSON value */
  95. return nil
  96. }
  97. // Decode parses the JSON-encoded data from current position and stores the result
  98. // in the value pointed to by val.
  99. func (self *Decoder) Decode(val interface{}) error {
  100. r := bytes.NewBufferString(self.s)
  101. dec := json.NewDecoder(r)
  102. if (self.f & uint64(OptionUseNumber)) != 0 {
  103. dec.UseNumber()
  104. }
  105. if (self.f & uint64(OptionDisableUnknown)) != 0 {
  106. dec.DisallowUnknownFields()
  107. }
  108. return dec.Decode(val)
  109. }
  110. // UseInt64 indicates the Decoder to unmarshal an integer into an interface{} as an
  111. // int64 instead of as a float64.
  112. func (self *Decoder) UseInt64() {
  113. self.f |= 1 << _F_use_int64
  114. self.f &^= 1 << _F_use_number
  115. }
  116. // UseNumber indicates the Decoder to unmarshal a number into an interface{} as a
  117. // json.Number instead of as a float64.
  118. func (self *Decoder) UseNumber() {
  119. self.f &^= 1 << _F_use_int64
  120. self.f |= 1 << _F_use_number
  121. }
  122. // UseUnicodeErrors indicates the Decoder to return an error when encounter invalid
  123. // UTF-8 escape sequences.
  124. func (self *Decoder) UseUnicodeErrors() {
  125. self.f |= 1 << _F_disable_urc
  126. }
  127. // DisallowUnknownFields indicates the Decoder to return an error when the destination
  128. // is a struct and the input contains object keys which do not match any
  129. // non-ignored, exported fields in the destination.
  130. func (self *Decoder) DisallowUnknownFields() {
  131. self.f |= 1 << _F_disable_unknown
  132. }
  133. // CopyString indicates the Decoder to decode string values by copying instead of referring.
  134. func (self *Decoder) CopyString() {
  135. self.f |= 1 << _F_copy_string
  136. }
  137. // ValidateString causes the Decoder to validate string values when decoding string value
  138. // in JSON. Validation is that, returning error when unescaped control chars(0x00-0x1f) or
  139. // invalid UTF-8 chars in the string value of JSON.
  140. func (self *Decoder) ValidateString() {
  141. self.f |= 1 << _F_validate_string
  142. }
  143. // Pretouch compiles vt ahead-of-time to avoid JIT compilation on-the-fly, in
  144. // order to reduce the first-hit latency.
  145. //
  146. // Opts are the compile options, for example, "option.WithCompileRecursiveDepth" is
  147. // a compile option to set the depth of recursive compile for the nested struct type.
  148. func Pretouch(vt reflect.Type, opts ...option.CompileOption) error {
  149. return nil
  150. }
  151. type StreamDecoder = json.Decoder
  152. // NewStreamDecoder adapts to encoding/json.NewDecoder API.
  153. //
  154. // NewStreamDecoder returns a new decoder that reads from r.
  155. func NewStreamDecoder(r io.Reader) *StreamDecoder {
  156. return json.NewDecoder(r)
  157. }
  158. // SyntaxError represents json syntax error
  159. type SyntaxError json.SyntaxError
  160. // Description
  161. func (s SyntaxError) Description() string {
  162. return (*json.SyntaxError)(unsafe.Pointer(&s)).Error()
  163. }
  164. // Error
  165. func (s SyntaxError) Error() string {
  166. return (*json.SyntaxError)(unsafe.Pointer(&s)).Error()
  167. }
  168. // MismatchTypeError represents mismatching between json and object
  169. type MismatchTypeError json.UnmarshalTypeError