From c33d3170f809470b7a743c42e2337172872488a3 Mon Sep 17 00:00:00 2001 From: Sebastian Holmqvist Date: Mon, 17 May 2021 16:22:58 +0200 Subject: [PATCH] fix(parser): add support for scientific notation integers Try and parse as floats and then convert to int64. Ensure large numbers can be represented. --- pkg/dbc/parser.go | 13 ++++- testdata/dbc/example/example.dbc | 1 + testdata/dbc/example/example.dbc.golden | 77 ++++++++++++++----------- 3 files changed, 55 insertions(+), 36 deletions(-) diff --git a/pkg/dbc/parser.go b/pkg/dbc/parser.go index 3ab4f8d..026fb9f 100644 --- a/pkg/dbc/parser.go +++ b/pkg/dbc/parser.go @@ -3,6 +3,7 @@ package dbc import ( "bytes" "fmt" + "math" "strconv" "strings" "text/scanner" @@ -315,13 +316,19 @@ func (p *Parser) int() int64 { isNegative = true } tok := p.nextToken() - if tok.typ != scanner.Int { - p.failf(tok.pos, "expected int") + if tok.typ != scanner.Int && tok.typ != scanner.Float { + p.failf(tok.pos, "expected int or float") } - i, err := strconv.ParseInt(tok.txt, 10, 64) + f, err := strconv.ParseFloat(tok.txt, 64) if err != nil { p.failf(tok.pos, "invalid int") } + i := int64(f) + if f > math.MaxInt64 { + i = math.MaxInt64 + } else if f < math.MinInt64 { + i = math.MinInt64 + } if isNegative { i *= -1 } diff --git a/testdata/dbc/example/example.dbc b/testdata/dbc/example/example.dbc index 7ea4f35..0a2c628 100644 --- a/testdata/dbc/example/example.dbc +++ b/testdata/dbc/example/example.dbc @@ -53,6 +53,7 @@ BA_DEF_ BO_ "GenMsgSendType" ENUM "None","Cyclic","OnEvent"; BA_DEF_ BO_ "GenMsgCycleTime" INT 0 0; BA_DEF_ SG_ "FieldType" STRING ; BA_DEF_ SG_ "GenSigStartValue" INT 0 10000; +BA_DEF_ SG_ "SPN" INT -3.4E+038 3.4E+038; BA_DEF_DEF_ "BusType" "CAN"; BA_DEF_DEF_ "FieldType" ""; BA_DEF_DEF_ "GenMsgCycleTime" 0; diff --git a/testdata/dbc/example/example.dbc.golden b/testdata/dbc/example/example.dbc.golden index e6e18d9..2fecb58 100644 --- a/testdata/dbc/example/example.dbc.golden +++ b/testdata/dbc/example/example.dbc.golden @@ -1,4 +1,4 @@ -([]dbc.Def) (len=43) { +([]dbc.Def) (len=44) { (*dbc.VersionDef)({ Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:1:1, Version: (string) "" @@ -616,36 +616,47 @@ MaximumFloat: (float64) 0, EnumValues: ([]string) }), - (*dbc.AttributeDefaultValueDef)({ + (*dbc.AttributeDef)({ Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:56:1, + ObjectType: (dbc.ObjectType) (len=3) "SG_", + Name: (dbc.Identifier) (len=3) "SPN", + Type: (dbc.AttributeValueType) (len=3) "INT", + MinimumInt: (int64) -9223372036854775807, + MaximumInt: (int64) 9223372036854775807, + MinimumFloat: (float64) 0, + MaximumFloat: (float64) 0, + EnumValues: ([]string) + }), + (*dbc.AttributeDefaultValueDef)({ + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:57:1, AttributeName: (dbc.Identifier) (len=7) "BusType", DefaultIntValue: (int64) 0, DefaultFloatValue: (float64) 0, DefaultStringValue: (string) (len=3) "CAN" }), (*dbc.AttributeDefaultValueDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:57:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:58:1, AttributeName: (dbc.Identifier) (len=9) "FieldType", DefaultIntValue: (int64) 0, DefaultFloatValue: (float64) 0, DefaultStringValue: (string) "" }), (*dbc.AttributeDefaultValueDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:58:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:59:1, AttributeName: (dbc.Identifier) (len=15) "GenMsgCycleTime", DefaultIntValue: (int64) 0, DefaultFloatValue: (float64) 0, DefaultStringValue: (string) "" }), (*dbc.AttributeDefaultValueDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:59:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:60:1, AttributeName: (dbc.Identifier) (len=16) "GenSigStartValue", DefaultIntValue: (int64) 0, DefaultFloatValue: (float64) 0, DefaultStringValue: (string) "" }), (*dbc.AttributeValueForObjectDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:61:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:62:1, AttributeName: (dbc.Identifier) (len=14) "GenMsgSendType", ObjectType: (dbc.ObjectType) (len=3) "BO_", MessageID: (dbc.MessageID) 1, @@ -657,7 +668,7 @@ StringValue: (string) (len=4) "None" }), (*dbc.AttributeValueForObjectDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:62:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:63:1, AttributeName: (dbc.Identifier) (len=14) "GenMsgSendType", ObjectType: (dbc.ObjectType) (len=3) "BO_", MessageID: (dbc.MessageID) 100, @@ -669,7 +680,7 @@ StringValue: (string) (len=6) "Cyclic" }), (*dbc.AttributeValueForObjectDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:63:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:64:1, AttributeName: (dbc.Identifier) (len=15) "GenMsgCycleTime", ObjectType: (dbc.ObjectType) (len=3) "BO_", MessageID: (dbc.MessageID) 100, @@ -681,7 +692,7 @@ StringValue: (string) "" }), (*dbc.AttributeValueForObjectDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:64:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:65:1, AttributeName: (dbc.Identifier) (len=14) "GenMsgSendType", ObjectType: (dbc.ObjectType) (len=3) "BO_", MessageID: (dbc.MessageID) 101, @@ -693,7 +704,7 @@ StringValue: (string) (len=6) "Cyclic" }), (*dbc.AttributeValueForObjectDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:65:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:66:1, AttributeName: (dbc.Identifier) (len=15) "GenMsgCycleTime", ObjectType: (dbc.ObjectType) (len=3) "BO_", MessageID: (dbc.MessageID) 101, @@ -705,7 +716,7 @@ StringValue: (string) "" }), (*dbc.AttributeValueForObjectDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:66:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:67:1, AttributeName: (dbc.Identifier) (len=14) "GenMsgSendType", ObjectType: (dbc.ObjectType) (len=3) "BO_", MessageID: (dbc.MessageID) 200, @@ -717,7 +728,7 @@ StringValue: (string) (len=6) "Cyclic" }), (*dbc.AttributeValueForObjectDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:67:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:68:1, AttributeName: (dbc.Identifier) (len=15) "GenMsgCycleTime", ObjectType: (dbc.ObjectType) (len=3) "BO_", MessageID: (dbc.MessageID) 200, @@ -729,7 +740,7 @@ StringValue: (string) "" }), (*dbc.AttributeValueForObjectDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:68:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:69:1, AttributeName: (dbc.Identifier) (len=14) "GenMsgSendType", ObjectType: (dbc.ObjectType) (len=3) "BO_", MessageID: (dbc.MessageID) 400, @@ -741,7 +752,7 @@ StringValue: (string) (len=6) "Cyclic" }), (*dbc.AttributeValueForObjectDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:69:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:70:1, AttributeName: (dbc.Identifier) (len=15) "GenMsgCycleTime", ObjectType: (dbc.ObjectType) (len=3) "BO_", MessageID: (dbc.MessageID) 400, @@ -753,7 +764,7 @@ StringValue: (string) "" }), (*dbc.AttributeValueForObjectDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:70:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:71:1, AttributeName: (dbc.Identifier) (len=14) "GenMsgSendType", ObjectType: (dbc.ObjectType) (len=3) "BO_", MessageID: (dbc.MessageID) 500, @@ -765,7 +776,7 @@ StringValue: (string) (len=7) "OnEvent" }), (*dbc.AttributeValueForObjectDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:71:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:72:1, AttributeName: (dbc.Identifier) (len=9) "FieldType", ObjectType: (dbc.ObjectType) (len=3) "SG_", MessageID: (dbc.MessageID) 100, @@ -777,7 +788,7 @@ StringValue: (string) (len=7) "Command" }), (*dbc.AttributeValueForObjectDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:72:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:73:1, AttributeName: (dbc.Identifier) (len=9) "FieldType", ObjectType: (dbc.ObjectType) (len=3) "SG_", MessageID: (dbc.MessageID) 500, @@ -789,7 +800,7 @@ StringValue: (string) (len=8) "TestEnum" }), (*dbc.AttributeValueForObjectDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:73:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:74:1, AttributeName: (dbc.Identifier) (len=16) "GenSigStartValue", ObjectType: (dbc.ObjectType) (len=3) "SG_", MessageID: (dbc.MessageID) 500, @@ -801,91 +812,91 @@ StringValue: (string) "" }), (*dbc.ValueDescriptionsDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:75:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:76:1, ObjectType: (dbc.ObjectType) (len=3) "SG_", MessageID: (dbc.MessageID) 100, SignalName: (dbc.Identifier) (len=7) "Command", EnvironmentVariableName: (dbc.Identifier) "", ValueDescriptions: ([]dbc.ValueDescriptionDef) (len=3) { (dbc.ValueDescriptionDef) { - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:75:18, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:76:18, Value: (float64) 2, Description: (string) (len=6) "Reboot" }, (dbc.ValueDescriptionDef) { - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:75:29, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:76:29, Value: (float64) 1, Description: (string) (len=4) "Sync" }, (dbc.ValueDescriptionDef) { - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:75:38, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:76:38, Value: (float64) 0, Description: (string) (len=4) "None" } } }), (*dbc.ValueDescriptionsDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:76:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:77:1, ObjectType: (dbc.ObjectType) (len=3) "SG_", MessageID: (dbc.MessageID) 500, SignalName: (dbc.Identifier) (len=8) "TestEnum", EnvironmentVariableName: (dbc.Identifier) "", ValueDescriptions: ([]dbc.ValueDescriptionDef) (len=2) { (dbc.ValueDescriptionDef) { - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:76:19, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:77:19, Value: (float64) 2, Description: (string) (len=3) "Two" }, (dbc.ValueDescriptionDef) { - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:76:27, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:77:27, Value: (float64) 1, Description: (string) (len=3) "One" } } }), (*dbc.ValueDescriptionsDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:77:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:78:1, ObjectType: (dbc.ObjectType) (len=3) "SG_", MessageID: (dbc.MessageID) 500, SignalName: (dbc.Identifier) (len=14) "TestScaledEnum", EnvironmentVariableName: (dbc.Identifier) "", ValueDescriptions: ([]dbc.ValueDescriptionDef) (len=4) { (dbc.ValueDescriptionDef) { - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:77:25, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:78:25, Value: (float64) 3, Description: (string) (len=3) "Six" }, (dbc.ValueDescriptionDef) { - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:77:33, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:78:33, Value: (float64) 2, Description: (string) (len=4) "Four" }, (dbc.ValueDescriptionDef) { - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:77:42, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:78:42, Value: (float64) 1, Description: (string) (len=3) "Two" }, (dbc.ValueDescriptionDef) { - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:77:50, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:78:50, Value: (float64) 0, Description: (string) (len=4) "Zero" } } }), (*dbc.ValueDescriptionsDef)({ - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:78:1, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:79:1, ObjectType: (dbc.ObjectType) (len=3) "SG_", MessageID: (dbc.MessageID) 500, SignalName: (dbc.Identifier) (len=12) "TestBoolEnum", EnvironmentVariableName: (dbc.Identifier) "", ValueDescriptions: ([]dbc.ValueDescriptionDef) (len=2) { (dbc.ValueDescriptionDef) { - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:78:23, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:79:23, Value: (float64) 1, Description: (string) (len=3) "One" }, (dbc.ValueDescriptionDef) { - Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:78:31, + Pos: (scanner.Position) ../../testdata/dbc/example/example.dbc:79:31, Value: (float64) 0, Description: (string) (len=4) "Zero" }