summaryrefslogtreecommitdiff
path: root/vendor/github.com/bytedance/sonic/internal/decoder/optdec/stringopts.go
diff options
context:
space:
mode:
Diffstat (limited to 'vendor/github.com/bytedance/sonic/internal/decoder/optdec/stringopts.go')
-rw-r--r--vendor/github.com/bytedance/sonic/internal/decoder/optdec/stringopts.go360
1 files changed, 360 insertions, 0 deletions
diff --git a/vendor/github.com/bytedance/sonic/internal/decoder/optdec/stringopts.go b/vendor/github.com/bytedance/sonic/internal/decoder/optdec/stringopts.go
new file mode 100644
index 000000000..5af8c97e2
--- /dev/null
+++ b/vendor/github.com/bytedance/sonic/internal/decoder/optdec/stringopts.go
@@ -0,0 +1,360 @@
+package optdec
+
+import (
+ "encoding/json"
+ "math"
+ "unsafe"
+
+ "github.com/bytedance/sonic/internal/rt"
+)
+
+type ptrStrDecoder struct {
+ typ *rt.GoType
+ deref decFunc
+}
+
+// Pointer Value is allocated in the Caller
+func (d *ptrStrDecoder) FromDom(vp unsafe.Pointer, node Node, ctx *context) error {
+ if node.IsNull() {
+ *(*unsafe.Pointer)(vp) = nil
+ return nil
+ }
+
+ s, ok := node.AsStrRef(ctx)
+ if !ok {
+ return error_mismatch(node, ctx, stringType)
+ }
+
+ if s == "null" {
+ *(*unsafe.Pointer)(vp) = nil
+ return nil
+ }
+
+ if *(*unsafe.Pointer)(vp) == nil {
+ *(*unsafe.Pointer)(vp) = rt.Mallocgc(d.typ.Size, d.typ, true)
+ }
+
+ return d.deref.FromDom(*(*unsafe.Pointer)(vp), node, ctx)
+}
+
+type boolStringDecoder struct {
+}
+
+func (d *boolStringDecoder) FromDom(vp unsafe.Pointer, node Node, ctx *context) error {
+ if node.IsNull() {
+ return nil
+ }
+
+ s, ok := node.AsStrRef(ctx)
+ if !ok {
+ return error_mismatch(node, ctx, stringType)
+ }
+
+ if s == "null" {
+ return nil
+ }
+
+ b, err := ParseBool(s)
+ if err != nil {
+ return error_mismatch(node, ctx, boolType)
+ }
+
+ *(*bool)(vp) = b
+ return nil
+}
+
+func parseI64(node Node, ctx *context) (int64, error, bool) {
+ if node.IsNull() {
+ return 0, nil, true
+ }
+
+ s, ok := node.AsStrRef(ctx)
+ if !ok {
+ return 0, error_mismatch(node, ctx, stringType), false
+ }
+
+ if s == "null" {
+ return 0, nil, true
+ }
+
+ ret, err := ParseI64(s)
+ return ret, err, false
+}
+
+type i8StringDecoder struct{}
+
+func (d *i8StringDecoder) FromDom(vp unsafe.Pointer, node Node, ctx *context) error {
+ ret, err, null := parseI64(node, ctx)
+ if null {
+ return nil
+ }
+
+ if err != nil {
+ return err
+ }
+
+ if ret > math.MaxInt8 || ret < math.MinInt8 {
+ return error_mismatch(node, ctx, int8Type)
+ }
+
+ *(*int8)(vp) = int8(ret)
+ return nil
+}
+
+type i16StringDecoder struct{}
+
+func (d *i16StringDecoder) FromDom(vp unsafe.Pointer, node Node, ctx *context) error {
+ ret, err, null := parseI64(node, ctx)
+ if null {
+ return nil
+ }
+
+ if err != nil {
+ return err
+ }
+
+ if ret > math.MaxInt16 || ret < math.MinInt16 {
+ return error_mismatch(node, ctx, int16Type)
+ }
+
+ *(*int16)(vp) = int16(ret)
+ return nil
+}
+
+type i32StringDecoder struct{}
+
+func (d *i32StringDecoder) FromDom(vp unsafe.Pointer, node Node, ctx *context) error {
+ ret, err, null := parseI64(node, ctx)
+ if null {
+ return nil
+ }
+
+ if err != nil {
+ return err
+ }
+
+ if ret > math.MaxInt32 || ret < math.MinInt32 {
+ return error_mismatch(node, ctx, int32Type)
+ }
+
+ *(*int32)(vp) = int32(ret)
+ return nil
+}
+
+type i64StringDecoder struct{}
+
+func (d *i64StringDecoder) FromDom(vp unsafe.Pointer, node Node, ctx *context) error {
+ ret, err, null := parseI64(node, ctx)
+ if null {
+ return nil
+ }
+
+ if err != nil {
+ return err
+ }
+
+ *(*int64)(vp) = int64(ret)
+ return nil
+}
+
+func parseU64(node Node, ctx *context) (uint64, error, bool) {
+ if node.IsNull() {
+ return 0, nil, true
+ }
+
+ s, ok := node.AsStrRef(ctx)
+ if !ok {
+ return 0, error_mismatch(node, ctx, stringType), false
+ }
+
+ if s == "null" {
+ return 0, nil, true
+ }
+
+ ret, err := ParseU64(s)
+ return ret, err, false
+}
+
+type u8StringDecoder struct{}
+
+func (d *u8StringDecoder) FromDom(vp unsafe.Pointer, node Node, ctx *context) error {
+ ret, err, null := parseU64(node, ctx)
+ if null {
+ return nil
+ }
+
+ if err != nil {
+ return err
+ }
+
+ if ret > math.MaxUint8 {
+ return error_mismatch(node, ctx, uint8Type)
+ }
+
+ *(*uint8)(vp) = uint8(ret)
+ return nil
+}
+
+type u16StringDecoder struct{}
+
+func (d *u16StringDecoder) FromDom(vp unsafe.Pointer, node Node, ctx *context) error {
+ ret, err, null := parseU64(node, ctx)
+ if null {
+ return nil
+ }
+
+ if err != nil {
+ return err
+ }
+
+ if ret > math.MaxUint16 {
+ return error_mismatch(node, ctx, uint16Type)
+ }
+
+ *(*uint16)(vp) = uint16(ret)
+ return nil
+}
+
+type u32StringDecoder struct{}
+
+func (d *u32StringDecoder) FromDom(vp unsafe.Pointer, node Node, ctx *context) error {
+ ret, err, null := parseU64(node, ctx)
+ if null {
+ return nil
+ }
+
+ if err != nil {
+ return err
+ }
+
+ if ret > math.MaxUint32 {
+ return error_mismatch(node, ctx, uint32Type)
+ }
+
+ *(*uint32)(vp) = uint32(ret)
+ return nil
+}
+
+
+type u64StringDecoder struct{}
+
+func (d *u64StringDecoder) FromDom(vp unsafe.Pointer, node Node, ctx *context) error {
+ ret, err, null := parseU64(node, ctx)
+ if null {
+ return nil
+ }
+
+ if err != nil {
+ return err
+ }
+
+ *(*uint64)(vp) = uint64(ret)
+ return nil
+}
+
+type f32StringDecoder struct{}
+
+func (d *f32StringDecoder) FromDom(vp unsafe.Pointer, node Node, ctx *context) error {
+ if node.IsNull() {
+ return nil
+ }
+
+ s, ok := node.AsStrRef(ctx)
+ if !ok {
+ return error_mismatch(node, ctx, stringType)
+ }
+
+ if s == "null" {
+ return nil
+ }
+
+ ret, err := ParseF64(s)
+ if err != nil || ret > math.MaxFloat32 || ret < -math.MaxFloat32 {
+ return error_mismatch(node, ctx, float32Type)
+ }
+
+ *(*float32)(vp) = float32(ret)
+ return nil
+}
+
+type f64StringDecoder struct{}
+
+func (d *f64StringDecoder) FromDom(vp unsafe.Pointer, node Node, ctx *context) error {
+ if node.IsNull() {
+ return nil
+ }
+
+ s, ok := node.AsStrRef(ctx)
+ if !ok {
+ return error_mismatch(node, ctx, stringType)
+ }
+
+ if s == "null" {
+ return nil
+ }
+
+ ret, err := ParseF64(s)
+ if err != nil {
+ return error_mismatch(node, ctx, float64Type)
+ }
+
+ *(*float64)(vp) = float64(ret)
+ return nil
+}
+
+/* parse string field with string options */
+type strStringDecoder struct{}
+
+func (d *strStringDecoder) FromDom(vp unsafe.Pointer, node Node, ctx *context) error {
+ if node.IsNull() {
+ return nil
+ }
+
+ s, ok := node.AsStrRef(ctx)
+ if !ok {
+ return error_mismatch(node, ctx, stringType)
+ }
+
+ if s == "null" {
+ return nil
+ }
+
+ s, err := Unquote(s)
+ if err != nil {
+ return error_mismatch(node, ctx, stringType)
+ }
+
+ *(*string)(vp) = s
+ return nil
+}
+
+type numberStringDecoder struct{}
+
+func (d *numberStringDecoder) FromDom(vp unsafe.Pointer, node Node, ctx *context) error {
+ if node.IsNull() {
+ return nil
+ }
+
+ s, ok := node.AsStrRef(ctx)
+ if !ok {
+ return error_mismatch(node, ctx, stringType)
+ }
+
+ if s == "null" {
+ return nil
+ }
+
+ num, ok := node.ParseNumber(ctx)
+ if !ok {
+ return error_mismatch(node, ctx, jsonNumberType)
+ }
+
+ end, ok := SkipNumberFast(s, 0)
+ // has error or trailing chars
+ if !ok || end != len(s) {
+ return error_mismatch(node, ctx, jsonNumberType)
+ }
+
+ *(*json.Number)(vp) = json.Number(num)
+ return nil
+}