diff --git a/float32_unsupported_test.go b/float32_unsupported_test.go new file mode 100644 index 00000000..c7bfe929 --- /dev/null +++ b/float32_unsupported_test.go @@ -0,0 +1,97 @@ +package json_test + +import ( + stdjson "encoding/json" + "math" + "testing" + + json "github.com/goccy/go-json" +) + +// nonFiniteFloat32 shapes exercises every float32 opcode family (bare, pointer, +// struct head/field/end, omitempty, string tag, slice, map) with a non-finite value. +func nonFiniteFloat32Shapes(f float32) map[string]interface{} { + p := f + return map[string]interface{}{ + "bare": f, + "ptr": &p, + "structHead": struct{ A float32 }{f}, + "structPtr": struct{ A *float32 }{&p}, + "structField": struct { + X int + A float32 + }{1, f}, + "omitempty": struct { + A float32 `json:",omitempty"` + }{f}, + "string": struct { + A float32 `json:",string"` + }{f}, + "slice": []float32{f}, + "map": map[string]float32{"k": f}, + } +} + +// float32 Inf/NaN must return *UnsupportedValueError and emit no output, matching +// encoding/json and the existing float64 behaviour, across all four VM variants. +func TestMarshalFloat32NonFinite(t *testing.T) { + marshalers := []struct { + name string + fn func(interface{}) ([]byte, error) + }{ + {"plain", func(v interface{}) ([]byte, error) { return json.Marshal(v) }}, + {"indent", func(v interface{}) ([]byte, error) { return json.MarshalIndent(v, "", "\t") }}, + {"color", func(v interface{}) ([]byte, error) { + return json.MarshalWithOption(v, json.Colorize(json.DefaultColorScheme)) + }}, + {"colorIndent", func(v interface{}) ([]byte, error) { + return json.MarshalIndentWithOption(v, "", "\t", json.Colorize(json.DefaultColorScheme)) + }}, + } + values := map[string]float32{ + "+Inf": float32(math.Inf(1)), + "-Inf": float32(math.Inf(-1)), + "NaN": float32(math.NaN()), + } + for vname, f := range values { + for sname, shape := range nonFiniteFloat32Shapes(f) { + std, stdErr := stdjson.Marshal(shape) + for _, m := range marshalers { + got, err := m.fn(shape) + t.Logf("%s/%s/%s: goccy=(%q,%v) stdlib=(%q,%v)", vname, sname, m.name, got, err, std, stdErr) + if err == nil { + t.Errorf("%s/%s/%s: expected error, got output %q", vname, sname, m.name, got) + continue + } + if _, ok := err.(*json.UnsupportedValueError); !ok { + t.Errorf("%s/%s/%s: got %T, want *UnsupportedValueError", vname, sname, m.name, err) + } + if len(got) != 0 { + t.Errorf("%s/%s/%s: expected no output on error, got %q", vname, sname, m.name, got) + } + } + } + } +} + +// Finite float32 must still marshal byte-identically to encoding/json (no over-fix). +func TestMarshalFloat32FiniteUnchanged(t *testing.T) { + values := []float32{0, 1.5, -1.5, 1e30, math.MaxFloat32, math.SmallestNonzeroFloat32} + for _, f := range values { + for sname, shape := range nonFiniteFloat32Shapes(f) { + std, stdErr := stdjson.Marshal(shape) + if stdErr != nil { + t.Fatalf("stdlib failed on finite %v/%s: %v", f, sname, stdErr) + } + got, err := json.Marshal(shape) + t.Logf("finite %v/%s: goccy=%q stdlib=%q", f, sname, got, std) + if err != nil { + t.Errorf("finite %v/%s: unexpected error %v", f, sname, err) + continue + } + if string(got) != string(std) { + t.Errorf("finite %v/%s: goccy=%q stdlib=%q", f, sname, got, std) + } + } + } +} diff --git a/internal/cmd/generator/vm.go.tmpl b/internal/cmd/generator/vm.go.tmpl index 645d20f9..7fdcde4a 100644 --- a/internal/cmd/generator/vm.go.tmpl +++ b/internal/cmd/generator/vm.go.tmpl @@ -79,7 +79,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b store(ctxptr, code.Idx, p) fallthrough case encoder.OpFloat32: - b = appendFloat32(ctx, b, ptrToFloat32(load(ctxptr, code.Idx))) + v := ptrToFloat32(load(ctxptr, code.Idx)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next case encoder.OpFloat64Ptr: @@ -1152,7 +1156,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendStructHead(ctx, b) } b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p+uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next case encoder.OpStructPtrHeadOmitEmptyFloat32: @@ -1185,6 +1193,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b code = code.NextField } else { b = appendStructKey(ctx, code, b) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next @@ -1216,7 +1227,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b } b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p+uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) code = code.Next @@ -1251,6 +1266,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b } else { b = appendStructKey(ctx, code, b) b = append(b, '"') + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) @@ -1286,7 +1304,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p == 0 { b = appendNull(ctx, b) } else { - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) } b = appendComma(ctx, b) code = code.Next @@ -1318,7 +1340,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b } if p != 0 { b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) } code = code.Next @@ -1353,7 +1379,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendNull(ctx, b) } else { b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') } b = appendComma(ctx, b) @@ -1387,7 +1417,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) } @@ -3437,7 +3471,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b case encoder.OpStructFieldFloat32: p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p+uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next case encoder.OpStructFieldOmitEmptyFloat32: @@ -3445,6 +3483,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b v := ptrToFloat32(p + uintptr(code.Offset)) if v != 0 { b = appendStructKey(ctx, code, b) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) } @@ -3453,7 +3494,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p+uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) code = code.Next @@ -3463,6 +3508,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if v != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) @@ -3475,7 +3523,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p == 0 { b = appendNull(ctx, b) } else { - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) } b = appendComma(ctx, b) code = code.Next @@ -3484,7 +3536,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p = ptrToNPtr(p+uintptr(code.Offset), code.PtrNum) if p != 0 { b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) } code = code.Next @@ -3496,7 +3552,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendNull(ctx, b) } else { b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') } b = appendComma(ctx, b) @@ -3507,7 +3567,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) } @@ -4334,7 +4398,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b case encoder.OpStructEndFloat32: p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p+uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendStructEnd(ctx, code, b) code = code.Next case encoder.OpStructEndOmitEmptyFloat32: @@ -4342,6 +4410,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b v := ptrToFloat32(p + uintptr(code.Offset)) if v != 0 { b = appendStructKey(ctx, code, b) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = appendStructEnd(ctx, code, b) } else { @@ -4352,7 +4423,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p+uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendStructEnd(ctx, code, b) code = code.Next @@ -4362,6 +4437,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if v != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendStructEnd(ctx, code, b) @@ -4376,7 +4454,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p == 0 { b = appendNull(ctx, b) } else { - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) } b = appendStructEnd(ctx, code, b) code = code.Next @@ -4385,7 +4467,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p = ptrToNPtr(p+uintptr(code.Offset), code.PtrNum) if p != 0 { b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendStructEnd(ctx, code, b) } else { b = appendStructEndSkipLast(ctx, code, b) @@ -4399,7 +4485,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendNull(ctx, b) } else { b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') } b = appendStructEnd(ctx, code, b) @@ -4410,7 +4500,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendStructEnd(ctx, code, b) } else { diff --git a/internal/encoder/vm/vm.go b/internal/encoder/vm/vm.go index 645d20f9..06e646b9 100644 --- a/internal/encoder/vm/vm.go +++ b/internal/encoder/vm/vm.go @@ -79,7 +79,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b store(ctxptr, code.Idx, p) fallthrough case encoder.OpFloat32: - b = appendFloat32(ctx, b, ptrToFloat32(load(ctxptr, code.Idx))) + v := ptrToFloat32(load(ctxptr, code.Idx)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next case encoder.OpFloat64Ptr: @@ -1152,7 +1156,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendStructHead(ctx, b) } b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next case encoder.OpStructPtrHeadOmitEmptyFloat32: @@ -1185,6 +1193,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b code = code.NextField } else { b = appendStructKey(ctx, code, b) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next @@ -1216,7 +1227,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b } b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) code = code.Next @@ -1251,6 +1266,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b } else { b = appendStructKey(ctx, code, b) b = append(b, '"') + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) @@ -1286,7 +1304,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p == 0 { b = appendNull(ctx, b) } else { - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) } b = appendComma(ctx, b) code = code.Next @@ -1318,7 +1340,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b } if p != 0 { b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) } code = code.Next @@ -1353,7 +1379,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendNull(ctx, b) } else { b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') } b = appendComma(ctx, b) @@ -1387,7 +1417,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) } @@ -3437,7 +3471,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b case encoder.OpStructFieldFloat32: p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next case encoder.OpStructFieldOmitEmptyFloat32: @@ -3445,6 +3483,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b v := ptrToFloat32(p + uintptr(code.Offset)) if v != 0 { b = appendStructKey(ctx, code, b) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) } @@ -3453,7 +3494,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) code = code.Next @@ -3463,6 +3508,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if v != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) @@ -3475,7 +3523,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p == 0 { b = appendNull(ctx, b) } else { - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) } b = appendComma(ctx, b) code = code.Next @@ -3484,7 +3536,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p = ptrToNPtr(p+uintptr(code.Offset), code.PtrNum) if p != 0 { b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) } code = code.Next @@ -3496,7 +3552,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendNull(ctx, b) } else { b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') } b = appendComma(ctx, b) @@ -3507,7 +3567,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) } @@ -4334,7 +4398,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b case encoder.OpStructEndFloat32: p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendStructEnd(ctx, code, b) code = code.Next case encoder.OpStructEndOmitEmptyFloat32: @@ -4342,6 +4410,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b v := ptrToFloat32(p + uintptr(code.Offset)) if v != 0 { b = appendStructKey(ctx, code, b) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = appendStructEnd(ctx, code, b) } else { @@ -4352,7 +4423,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendStructEnd(ctx, code, b) code = code.Next @@ -4362,6 +4437,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if v != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendStructEnd(ctx, code, b) @@ -4376,7 +4454,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p == 0 { b = appendNull(ctx, b) } else { - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) } b = appendStructEnd(ctx, code, b) code = code.Next @@ -4385,7 +4467,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p = ptrToNPtr(p+uintptr(code.Offset), code.PtrNum) if p != 0 { b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendStructEnd(ctx, code, b) } else { b = appendStructEndSkipLast(ctx, code, b) @@ -4399,7 +4485,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendNull(ctx, b) } else { b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') } b = appendStructEnd(ctx, code, b) @@ -4410,7 +4500,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendStructEnd(ctx, code, b) } else { diff --git a/internal/encoder/vm_color/vm.go b/internal/encoder/vm_color/vm.go index a63e83e5..cc25e9a4 100644 --- a/internal/encoder/vm_color/vm.go +++ b/internal/encoder/vm_color/vm.go @@ -79,7 +79,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b store(ctxptr, code.Idx, p) fallthrough case encoder.OpFloat32: - b = appendFloat32(ctx, b, ptrToFloat32(load(ctxptr, code.Idx))) + v := ptrToFloat32(load(ctxptr, code.Idx)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next case encoder.OpFloat64Ptr: @@ -1152,7 +1156,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendStructHead(ctx, b) } b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next case encoder.OpStructPtrHeadOmitEmptyFloat32: @@ -1185,6 +1193,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b code = code.NextField } else { b = appendStructKey(ctx, code, b) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next @@ -1216,7 +1227,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b } b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) code = code.Next @@ -1251,6 +1266,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b } else { b = appendStructKey(ctx, code, b) b = append(b, '"') + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) @@ -1286,7 +1304,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p == 0 { b = appendNull(ctx, b) } else { - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) } b = appendComma(ctx, b) code = code.Next @@ -1318,7 +1340,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b } if p != 0 { b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) } code = code.Next @@ -1353,7 +1379,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendNull(ctx, b) } else { b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') } b = appendComma(ctx, b) @@ -1387,7 +1417,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) } @@ -3437,7 +3471,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b case encoder.OpStructFieldFloat32: p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next case encoder.OpStructFieldOmitEmptyFloat32: @@ -3445,6 +3483,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b v := ptrToFloat32(p + uintptr(code.Offset)) if v != 0 { b = appendStructKey(ctx, code, b) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) } @@ -3453,7 +3494,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) code = code.Next @@ -3463,6 +3508,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if v != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) @@ -3475,7 +3523,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p == 0 { b = appendNull(ctx, b) } else { - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) } b = appendComma(ctx, b) code = code.Next @@ -3484,7 +3536,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p = ptrToNPtr(p+uintptr(code.Offset), code.PtrNum) if p != 0 { b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) } code = code.Next @@ -3496,7 +3552,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendNull(ctx, b) } else { b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') } b = appendComma(ctx, b) @@ -3507,7 +3567,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) } @@ -4334,7 +4398,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b case encoder.OpStructEndFloat32: p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendStructEnd(ctx, code, b) code = code.Next case encoder.OpStructEndOmitEmptyFloat32: @@ -4342,6 +4410,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b v := ptrToFloat32(p + uintptr(code.Offset)) if v != 0 { b = appendStructKey(ctx, code, b) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = appendStructEnd(ctx, code, b) } else { @@ -4352,7 +4423,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendStructEnd(ctx, code, b) code = code.Next @@ -4362,6 +4437,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if v != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendStructEnd(ctx, code, b) @@ -4376,7 +4454,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p == 0 { b = appendNull(ctx, b) } else { - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) } b = appendStructEnd(ctx, code, b) code = code.Next @@ -4385,7 +4467,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p = ptrToNPtr(p+uintptr(code.Offset), code.PtrNum) if p != 0 { b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendStructEnd(ctx, code, b) } else { b = appendStructEndSkipLast(ctx, code, b) @@ -4399,7 +4485,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendNull(ctx, b) } else { b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') } b = appendStructEnd(ctx, code, b) @@ -4410,7 +4500,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendStructEnd(ctx, code, b) } else { diff --git a/internal/encoder/vm_color_indent/vm.go b/internal/encoder/vm_color_indent/vm.go index 3b4e22e5..2cbd7387 100644 --- a/internal/encoder/vm_color_indent/vm.go +++ b/internal/encoder/vm_color_indent/vm.go @@ -79,7 +79,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b store(ctxptr, code.Idx, p) fallthrough case encoder.OpFloat32: - b = appendFloat32(ctx, b, ptrToFloat32(load(ctxptr, code.Idx))) + v := ptrToFloat32(load(ctxptr, code.Idx)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next case encoder.OpFloat64Ptr: @@ -1152,7 +1156,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendStructHead(ctx, b) } b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next case encoder.OpStructPtrHeadOmitEmptyFloat32: @@ -1185,6 +1193,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b code = code.NextField } else { b = appendStructKey(ctx, code, b) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next @@ -1216,7 +1227,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b } b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) code = code.Next @@ -1251,6 +1266,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b } else { b = appendStructKey(ctx, code, b) b = append(b, '"') + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) @@ -1286,7 +1304,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p == 0 { b = appendNull(ctx, b) } else { - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) } b = appendComma(ctx, b) code = code.Next @@ -1318,7 +1340,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b } if p != 0 { b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) } code = code.Next @@ -1353,7 +1379,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendNull(ctx, b) } else { b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') } b = appendComma(ctx, b) @@ -1387,7 +1417,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) } @@ -3437,7 +3471,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b case encoder.OpStructFieldFloat32: p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next case encoder.OpStructFieldOmitEmptyFloat32: @@ -3445,6 +3483,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b v := ptrToFloat32(p + uintptr(code.Offset)) if v != 0 { b = appendStructKey(ctx, code, b) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) } @@ -3453,7 +3494,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) code = code.Next @@ -3463,6 +3508,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if v != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) @@ -3475,7 +3523,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p == 0 { b = appendNull(ctx, b) } else { - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) } b = appendComma(ctx, b) code = code.Next @@ -3484,7 +3536,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p = ptrToNPtr(p+uintptr(code.Offset), code.PtrNum) if p != 0 { b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) } code = code.Next @@ -3496,7 +3552,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendNull(ctx, b) } else { b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') } b = appendComma(ctx, b) @@ -3507,7 +3567,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) } @@ -4334,7 +4398,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b case encoder.OpStructEndFloat32: p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendStructEnd(ctx, code, b) code = code.Next case encoder.OpStructEndOmitEmptyFloat32: @@ -4342,6 +4410,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b v := ptrToFloat32(p + uintptr(code.Offset)) if v != 0 { b = appendStructKey(ctx, code, b) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = appendStructEnd(ctx, code, b) } else { @@ -4352,7 +4423,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendStructEnd(ctx, code, b) code = code.Next @@ -4362,6 +4437,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if v != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendStructEnd(ctx, code, b) @@ -4376,7 +4454,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p == 0 { b = appendNull(ctx, b) } else { - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) } b = appendStructEnd(ctx, code, b) code = code.Next @@ -4385,7 +4467,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p = ptrToNPtr(p+uintptr(code.Offset), code.PtrNum) if p != 0 { b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendStructEnd(ctx, code, b) } else { b = appendStructEndSkipLast(ctx, code, b) @@ -4399,7 +4485,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendNull(ctx, b) } else { b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') } b = appendStructEnd(ctx, code, b) @@ -4410,7 +4500,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendStructEnd(ctx, code, b) } else { diff --git a/internal/encoder/vm_indent/vm.go b/internal/encoder/vm_indent/vm.go index 836c5c8a..daf0ffc8 100644 --- a/internal/encoder/vm_indent/vm.go +++ b/internal/encoder/vm_indent/vm.go @@ -79,7 +79,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b store(ctxptr, code.Idx, p) fallthrough case encoder.OpFloat32: - b = appendFloat32(ctx, b, ptrToFloat32(load(ctxptr, code.Idx))) + v := ptrToFloat32(load(ctxptr, code.Idx)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next case encoder.OpFloat64Ptr: @@ -1152,7 +1156,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendStructHead(ctx, b) } b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next case encoder.OpStructPtrHeadOmitEmptyFloat32: @@ -1185,6 +1193,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b code = code.NextField } else { b = appendStructKey(ctx, code, b) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next @@ -1216,7 +1227,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b } b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) code = code.Next @@ -1251,6 +1266,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b } else { b = appendStructKey(ctx, code, b) b = append(b, '"') + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) @@ -1286,7 +1304,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p == 0 { b = appendNull(ctx, b) } else { - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) } b = appendComma(ctx, b) code = code.Next @@ -1318,7 +1340,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b } if p != 0 { b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) } code = code.Next @@ -1353,7 +1379,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendNull(ctx, b) } else { b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') } b = appendComma(ctx, b) @@ -1387,7 +1417,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) } @@ -3437,7 +3471,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b case encoder.OpStructFieldFloat32: p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) code = code.Next case encoder.OpStructFieldOmitEmptyFloat32: @@ -3445,6 +3483,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b v := ptrToFloat32(p + uintptr(code.Offset)) if v != 0 { b = appendStructKey(ctx, code, b) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) } @@ -3453,7 +3494,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) code = code.Next @@ -3463,6 +3508,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if v != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) @@ -3475,7 +3523,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p == 0 { b = appendNull(ctx, b) } else { - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) } b = appendComma(ctx, b) code = code.Next @@ -3484,7 +3536,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p = ptrToNPtr(p+uintptr(code.Offset), code.PtrNum) if p != 0 { b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendComma(ctx, b) } code = code.Next @@ -3496,7 +3552,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendNull(ctx, b) } else { b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') } b = appendComma(ctx, b) @@ -3507,7 +3567,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendComma(ctx, b) } @@ -4334,7 +4398,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b case encoder.OpStructEndFloat32: p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendStructEnd(ctx, code, b) code = code.Next case encoder.OpStructEndOmitEmptyFloat32: @@ -4342,6 +4410,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b v := ptrToFloat32(p + uintptr(code.Offset)) if v != 0 { b = appendStructKey(ctx, code, b) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = appendStructEnd(ctx, code, b) } else { @@ -4352,7 +4423,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p := load(ctxptr, code.Idx) b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p+uintptr(code.Offset))) + v := ptrToFloat32(p + uintptr(code.Offset)) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendStructEnd(ctx, code, b) code = code.Next @@ -4362,6 +4437,9 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if v != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendStructEnd(ctx, code, b) @@ -4376,7 +4454,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p == 0 { b = appendNull(ctx, b) } else { - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) } b = appendStructEnd(ctx, code, b) code = code.Next @@ -4385,7 +4467,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b p = ptrToNPtr(p+uintptr(code.Offset), code.PtrNum) if p != 0 { b = appendStructKey(ctx, code, b) - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = appendStructEnd(ctx, code, b) } else { b = appendStructEndSkipLast(ctx, code, b) @@ -4399,7 +4485,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b b = appendNull(ctx, b) } else { b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') } b = appendStructEnd(ctx, code, b) @@ -4410,7 +4500,11 @@ func Run(ctx *encoder.RuntimeContext, b []byte, codeSet *encoder.OpcodeSet) ([]b if p != 0 { b = appendStructKey(ctx, code, b) b = append(b, '"') - b = appendFloat32(ctx, b, ptrToFloat32(p)) + v := ptrToFloat32(p) + if math.IsInf(float64(v), 0) || math.IsNaN(float64(v)) { + return nil, errUnsupportedFloat(float64(v)) + } + b = appendFloat32(ctx, b, v) b = append(b, '"') b = appendStructEnd(ctx, code, b) } else {