use crate::ast::*; grammar(); // Skip over comments match { r"\s*" => { }, r"//[^\n\r]*[\n\r]*" => { }, _ } pub Namespace: Namespace = { "namespace" > > > => Namespace{<>} } Extension: Extension = { "extension" "{" > > "}" => Extension{name, version: version.unwrap_or_default(), interface, interfaces, types} } Interface: Interface = { "interface" "{" "}" => Interface { name, version: v.unwrap_or_default(), events: e.unwrap_or_default(), methods: m.unwrap_or_default() } } ExtensionInterface: ExtensionInterface = { "interface" "{" "}" => ExtensionInterface { name, version, events: e.unwrap_or_default(), methods: m.unwrap_or_default() } } ImplicitInterface: ImplicitInterface = { "interface" "{" "}" => ImplicitInterface { events: e.unwrap_or_default(), methods: m.unwrap_or_default() } } Version: Version = { "version" => (<>) } Events: Vec = { "events" "{" > "}" => <> } Methods: Vec = { "methods" "{" > "}" => <> } Func: Func = { "(" > ")" " )?> => Func{<>} } Arg: Arg = { ":" => Arg{<>} } // Argument types Type: Type = { PrimType => Type::Primitive(<>), Ident => Type::Custom(<>), IntType => Type::IntType(<>), "[]" => Type::Array(Box::new(<>)), } PrimType: PrimType = { "string" => PrimType::String, "object" => PrimType::Object, "uuid" => PrimType::Uuid, "bytes" => PrimType::Bytes, "bool" => PrimType::Bool, "matrix4x4" => PrimType::Matrix4x4, "f32" => PrimType::F32, "f64" => PrimType::F64, } // These are seperate as only they can back an enum IntType: IntType = { "u8" => IntType::U8, "u16" => IntType::U16, "u32" => IntType::U32, "u64" => IntType::U64, "u128" => IntType::U128, "vu8" => IntType::VU8, "vu16" => IntType::VU16, "vu32" => IntType::VU32, "vu64" => IntType::VU64, "vu128" => IntType::VU128, "i8" => IntType::I8, "i16" => IntType::I16, "i32" => IntType::I32, "i64" => IntType::I64, "i128" => IntType::I128, "vi8" => IntType::VI8, "vi16" => IntType::VI16, "vi32" => IntType::VI32, "vi64" => IntType::VI64, "vi128" => IntType::VI128, } // Typedefs TypeDef: TypeDef = { "struct" => TypeDef{name, kind: TypeKind::Struct(s)}, "enum" "(" ")" => TypeDef{name, kind: TypeKind::Enum(Enum{fields, backing})}, // Enum => TypeDef::Enum(<>), } Struct: Struct = { "{" > "}" => Struct{<>} } StructField: StructField = { ":" => StructField{<>} } Enum: Vec = { "{" > "}" => <> } EnumField: EnumField = { )?> => EnumField{<>} } // Terminals // Num: u8 = { // r"[0-9]+" => <>.parse().unwrap() // } Num: u8 = { // TODO: This is a bit hacky, but it works for now Int => <>.try_into().unwrap(), } Int: i64 = { r"(-)?[0-9]+" => <>.parse().unwrap() } Ident: String = { r"[a-zA-Z][a-zA-Z0-9_]*" => <>.to_owned() } // Combinators List: Vec = { )*> => v }; Comma: Vec = { ",")*> => match e { None=> v, Some(e) => { let mut v = v; v.push(e); v } } };