grammar,compiler: Add Support For Fixed-Width Integers
Distinguishing between signed and unsigned fixed-width integer types must still be done. Signed-off-by: Will Hawkins <hawkinsw@obs.cr>
This commit is contained in:
@@ -101,9 +101,41 @@ extension P4IntValue: CompilableExpression {
|
||||
node: SwiftTreeSitter.Node, withContext context: CompilerContext
|
||||
) -> Result<EvaluatableExpression?> {
|
||||
let node = node.child(at: 0)!
|
||||
#SkipUnlessNodeType<SwiftTreeSitter.Node>(node: node, type: "integer")
|
||||
if let parsed_int = Int(node.text!) {
|
||||
return .Ok(P4Value(P4IntValue(withValue: parsed_int)))
|
||||
|
||||
#SkipUnlessNodesTypes<SwiftTreeSitter.Node>(
|
||||
node: node, types: ["integer", "integer_elaborated"])
|
||||
|
||||
var bit_width: BitWidth = BitWidth.Infinite
|
||||
let value_source: String
|
||||
if node.nodeType == "integer_elaborated" {
|
||||
let re = /([0-9]+)([ws])([\-0-9]+)/
|
||||
let integer_components = node.text!.matches(of: re)
|
||||
|
||||
if integer_components.isEmpty || integer_components.count > 1 {
|
||||
return .Error(
|
||||
ErrorWithLocation(
|
||||
sourceLocation: node.toSourceLocation(),
|
||||
withError: "Failed to parse elaborated integer: \(node.text!)"))
|
||||
}
|
||||
|
||||
let width_source = "\(integer_components[0].1)"
|
||||
guard let width = Int(width_source) else {
|
||||
return .Error(
|
||||
ErrorWithLocation(
|
||||
sourceLocation: node.toSourceLocation(),
|
||||
withError: "Failed to parse width from elaborated integer: \(width_source)"))
|
||||
}
|
||||
|
||||
/// TODO: Handle signed vs. unsigned.
|
||||
|
||||
bit_width = BitWidth.Width(width)
|
||||
value_source = "\(integer_components[0].3)"
|
||||
} else {
|
||||
value_source = node.text!
|
||||
}
|
||||
|
||||
if let parsed_int = Int(value_source) {
|
||||
return .Ok(P4Value(P4IntValue(withValue: parsed_int, andWidth: bit_width)))
|
||||
} else {
|
||||
return .Error(
|
||||
ErrorWithLocation(
|
||||
|
||||
@@ -34,7 +34,42 @@ extension P4Int: CompilableType {
|
||||
public static func CompileType(
|
||||
type: SwiftTreeSitter.Node, withContext: CompilerContext
|
||||
) -> Common.Result<(any Common.P4Type)?> {
|
||||
return type.text == "int" ? .Ok(P4Int()) : .Ok(.none)
|
||||
|
||||
// Drill down, as appropriate.
|
||||
let base_type_node = type.child(at: 0)!
|
||||
#SkipUnlessNodeType<SwiftTreeSitter.Node>(
|
||||
node: base_type_node, type: "baseType")
|
||||
|
||||
let type_node = base_type_node.child(at: 0)!
|
||||
#SkipUnlessNodeType<SwiftTreeSitter.Node>(
|
||||
node: type_node, type: "int_type")
|
||||
|
||||
var walker = Walker(node: type_node)
|
||||
|
||||
var int_node: Node? = .none
|
||||
|
||||
#MustOr(
|
||||
result: int_node, thing: walker.getNext(),
|
||||
or: Result<P4Type?>.Error(
|
||||
ErrorWithLocation(
|
||||
sourceLocation: type_node.toSourceLocation(),
|
||||
withError: "Missing elements in int type declaration")))
|
||||
|
||||
// Move passed the keyword.
|
||||
walker.next()
|
||||
|
||||
if let bit_width_node = walker.getNext() {
|
||||
guard let bit_width = Int(bit_width_node.child(at: 1)!.text!),
|
||||
bit_width != 0
|
||||
else {
|
||||
return .Error(
|
||||
ErrorWithLocation(
|
||||
sourceLocation: bit_width_node.toSourceLocation(),
|
||||
withError: "Could not parse \(bit_width_node.text!) into integer"))
|
||||
}
|
||||
return .Ok(P4Int(BitWidth.Width(bit_width)))
|
||||
}
|
||||
return .Ok(P4Int())
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user