1
0
mirror of https://github.com/json-iterator/go.git synced 2024-11-27 08:30:57 +02:00

#135 fix leading zero

This commit is contained in:
Tao Wen 2017-07-18 11:23:29 +08:00
parent c966eaa031
commit 18d6ae2668
3 changed files with 97 additions and 1 deletions

View File

@ -78,6 +78,35 @@ func (iter *Iterator) readPositiveFloat32() (ret float32) {
value := uint64(0)
c := byte(' ')
i := iter.head
// first char
if i == iter.tail {
return iter.readFloat32SlowPath()
}
c = iter.buf[i]
i++
ind := floatDigits[c]
switch ind {
case invalidCharForNumber:
return iter.readFloat32SlowPath()
case endOfNumber:
iter.ReportError("readFloat32", "empty number")
return
case dotInNumber:
iter.ReportError("readFloat32", "leading dot is invalid")
return
case 0:
if i == iter.tail {
return iter.readFloat32SlowPath()
}
c = iter.buf[i]
switch c {
case '0', '1', '2', '3', '4', '5', '6', '7', '8', '9':
iter.ReportError("readFloat32", "leading zero is invalid")
return
}
}
value = uint64(ind)
// chars before dot
non_decimal_loop:
for ; i < iter.tail; i++ {
c = iter.buf[i]
@ -96,6 +125,7 @@ non_decimal_loop:
}
value = (value << 3) + (value << 1) + uint64(ind) // value = value * 10 + ind;
}
// chars after dot
if c == '.' {
i++
decimalPlaces := 0
@ -189,6 +219,35 @@ func (iter *Iterator) readPositiveFloat64() (ret float64) {
value := uint64(0)
c := byte(' ')
i := iter.head
// first char
if i == iter.tail {
return iter.readFloat64SlowPath()
}
c = iter.buf[i]
i++
ind := floatDigits[c]
switch ind {
case invalidCharForNumber:
return iter.readFloat64SlowPath()
case endOfNumber:
iter.ReportError("readFloat64", "empty number")
return
case dotInNumber:
iter.ReportError("readFloat64", "leading dot is invalid")
return
case 0:
if i == iter.tail {
return iter.readFloat64SlowPath()
}
c = iter.buf[i]
switch c {
case '0', '1', '2', '3', '4', '5', '6', '7', '8', '9':
iter.ReportError("readFloat64", "leading zero is invalid")
return
}
}
value = uint64(ind)
// chars before dot
non_decimal_loop:
for ; i < iter.tail; i++ {
c = iter.buf[i]
@ -207,6 +266,7 @@ non_decimal_loop:
}
value = (value << 3) + (value << 1) + uint64(ind) // value = value * 10 + ind;
}
// chars after dot
if c == '.' {
i++
decimalPlaces := 0

View File

@ -77,7 +77,10 @@ func (iter *Iterator) Skip() {
iter.skipThreeBytes('r', 'u', 'e') // true
case 'f':
iter.skipFourBytes('a', 'l', 's', 'e') // false
case '-', '0', '1', '2', '3', '4', '5', '6', '7', '8', '9':
case '0':
iter.unreadByte()
iter.ReadFloat32()
case '-', '1', '2', '3', '4', '5', '6', '7', '8', '9':
iter.skipNumber()
case '[':
iter.skipArray()

View File

@ -4,6 +4,7 @@ import (
"github.com/stretchr/testify/require"
"testing"
"encoding/json"
"io"
)
func Test_missing_object_end(t *testing.T) {
@ -77,4 +78,36 @@ func Test_double_negative(t *testing.T) {
should.NotNil(UnmarshalFromString(`--2`, &vFloat32))
var vInt int
should.NotNil(UnmarshalFromString(`--2`, &vInt))
iter := ParseString(ConfigDefault, `--2`)
iter.Skip()
should.NotEqual(io.EOF, iter.Error)
should.NotNil(iter.Error)
}
func Test_leading_zero(t *testing.T) {
should := require.New(t)
var v interface{}
should.NotNil(json.Unmarshal([]byte(`01`), &v))
var vFloat64 float64
should.NotNil(UnmarshalFromString(`01`, &vFloat64))
var vFloat32 float32
should.NotNil(UnmarshalFromString(`01`, &vFloat32))
var vInt int
should.NotNil(UnmarshalFromString(`01`, &vInt))
iter := ParseString(ConfigDefault, `01,`)
iter.Skip()
should.NotEqual(io.EOF, iter.Error)
should.NotNil(iter.Error)
}
func Test_empty_as_number(t *testing.T) {
should := require.New(t)
iter := ParseString(ConfigDefault, `,`)
iter.ReadFloat64()
should.NotEqual(io.EOF, iter.Error)
should.NotNil(iter.Error)
iter = ParseString(ConfigDefault, `,`)
iter.ReadFloat32()
should.NotEqual(io.EOF, iter.Error)
should.NotNil(iter.Error)
}