This commit is contained in:
nub31
2026-03-01 18:14:54 +01:00
parent 5f4a4172bf
commit 2b7eb56895
9 changed files with 192 additions and 138 deletions

View File

@@ -86,17 +86,7 @@ public class Parser
throw BasicError("Invalid modifier for function", modifier.Value);
var name = ExpectIdent();
var parameters = new List<NodeDefinitionFunc.Param>();
ExpectSymbol(Symbol.OpenParen);
while (!TryExpectSymbol(Symbol.CloseParen))
{
var paramStartIndex = index;
var parameterName = ExpectIdent();
ExpectSymbol(Symbol.Colon);
var parameterType = ParseType();
parameters.Add(new NodeDefinitionFunc.Param(TokensFrom(paramStartIndex), parameterName, parameterType));
}
var parameters = ParseFuncParameters();
NodeType? returnType = null;
if (TryExpectSymbol(Symbol.Colon))
@@ -132,6 +122,7 @@ public class Parser
var fieldName = ExpectIdent();
ExpectSymbol(Symbol.Colon);
var fieldType = ParseType();
TryExpectSymbol(Symbol.Comma);
fields.Add(new NodeDefinitionStruct.Field(TokensFrom(fieldStartIndex), fieldName, fieldType));
}
@@ -154,8 +145,13 @@ public class Parser
{
var variantsStartIndex = index;
var variantName = ExpectIdent();
ExpectSymbol(Symbol.Colon);
var variantType = ParseType();
NodeType? variantType = null;
if (TryExpectSymbol(Symbol.Colon))
variantType = ParseType();
TryExpectSymbol(Symbol.Comma);
variants.Add(new NodeDefinitionEnum.Variant(TokensFrom(variantsStartIndex), variantName, variantType));
}
@@ -180,6 +176,35 @@ public class Parser
throw BasicError("Not a valid definition", Peek());
}
private List<NodeDefinitionFunc.Param> ParseFuncParameters()
{
var parameters = new List<NodeDefinitionFunc.Param>();
ExpectSymbol(Symbol.OpenParen);
while (true)
{
if (TryExpectSymbol(Symbol.CloseParen))
break;
var startIndex = index;
var name = ExpectIdent();
ExpectSymbol(Symbol.Colon);
var type = ParseType();
parameters.Add(new NodeDefinitionFunc.Param(TokensFrom(startIndex), name, type));
if (!TryExpectSymbol(Symbol.Comma))
{
ExpectSymbol(Symbol.CloseParen);
break;
}
}
return parameters;
}
private NodeStatement ParseStatement()
{
var startIndex = index;
@@ -251,10 +276,10 @@ public class Parser
while (!TryExpectSymbol(Symbol.CloseCurly))
{
var caseStartIndex = index;
var type = ExpectIdent();
var variableName = ExpectIdent();
var variant = ExpectIdent();
TryExpectIdent(out var variableName);
var body = ParseStatement();
cases.Add(new NodeStatementMatch.Case(TokensFrom(caseStartIndex), type, variableName, body));
cases.Add(new NodeStatementMatch.Case(TokensFrom(caseStartIndex), variant, variableName, body));
}
return new NodeStatementMatch(TokensFrom(startIndex), target, cases);
@@ -350,7 +375,7 @@ public class Parser
initializers.Add(new NodeExpressionStructLiteral.Initializer(TokensFrom(initializerStartIndex), fieldName, fieldValue));
}
expr = new NodeExpressionStructLiteral(TokensFrom(startIndex), null, initializers);
expr = new NodeExpressionStructLiteral(TokensFrom(startIndex), initializers);
}
else if (TryExpectSymbol(Symbol.Bang))
{
@@ -380,30 +405,11 @@ public class Parser
expr = new NodeExpressionIdent(TokensFrom(startIndex), sections);
}
else if (TryExpectKeyword(Keyword.Struct))
{
var type = ParseType();
var initializers = new List<NodeExpressionStructLiteral.Initializer>();
ExpectSymbol(Symbol.OpenCurly);
while (!TryExpectSymbol(Symbol.CloseCurly))
{
var initializerStartIndex = startIndex;
var fieldName = ExpectIdent();
ExpectSymbol(Symbol.Equal);
var fieldValue = ParseExpression();
initializers.Add(new NodeExpressionStructLiteral.Initializer(TokensFrom(initializerStartIndex), fieldName, fieldValue));
}
expr = new NodeExpressionStructLiteral(TokensFrom(startIndex), type, initializers);
}
else if (TryExpectKeyword(Keyword.Enum))
else if (TryExpectKeyword(Keyword.New))
{
var type = ParseType();
var value = ParseExpression();
expr = new NodeExpressionEnumLiteral(TokensFrom(startIndex), type, value);
return new NodeExpressionNewNamedType(TokensFrom(startIndex), type, value);
}
else
{
@@ -769,10 +775,10 @@ public class NodeDefinitionEnum(List<Token> tokens, bool exported, TokenIdent na
public TokenIdent Name { get; } = name;
public List<Variant> Variants { get; } = variants;
public class Variant(List<Token> tokens, TokenIdent name, NodeType type) : Node(tokens)
public class Variant(List<Token> tokens, TokenIdent name, NodeType? type) : Node(tokens)
{
public TokenIdent Name { get; } = name;
public NodeType Type { get; } = type;
public NodeType? Type { get; } = type;
}
}
@@ -838,10 +844,10 @@ public class NodeStatementMatch(List<Token> tokens, NodeExpression target, List<
public NodeExpression Target { get; } = target;
public List<Case> Cases { get; } = cases;
public class Case(List<Token> tokens, TokenIdent type, TokenIdent variableName, NodeStatement body) : Node(tokens)
public class Case(List<Token> tokens, TokenIdent type, TokenIdent? variableName, NodeStatement body) : Node(tokens)
{
public TokenIdent Variant { get; } = type;
public TokenIdent VariableName { get; } = variableName;
public TokenIdent? VariableName { get; } = variableName;
public NodeStatement Body { get; } = body;
}
}
@@ -863,9 +869,14 @@ public class NodeExpressionBoolLiteral(List<Token> tokens, TokenBoolLiteral valu
public TokenBoolLiteral Value { get; } = value;
}
public class NodeExpressionStructLiteral(List<Token> tokens, NodeType? type, List<NodeExpressionStructLiteral.Initializer> initializers) : NodeExpression(tokens)
public class NodeExpressionNewNamedType(List<Token> tokens, NodeType type, NodeExpression value) : NodeExpression(tokens)
{
public NodeType Type { get; } = type;
public NodeExpression Value { get; } = value;
}
public class NodeExpressionStructLiteral(List<Token> tokens, List<NodeExpressionStructLiteral.Initializer> initializers) : NodeExpression(tokens)
{
public NodeType? Type { get; } = type;
public List<Initializer> Initializers { get; } = initializers;
public class Initializer(List<Token> tokens, TokenIdent name, NodeExpression value) : Node(tokens)
@@ -875,12 +886,6 @@ public class NodeExpressionStructLiteral(List<Token> tokens, NodeType? type, Lis
}
}
public class NodeExpressionEnumLiteral(List<Token> tokens, NodeType type, NodeExpression value) : NodeExpression(tokens)
{
public NodeType Type { get; } = type;
public NodeExpression Value { get; } = value;
}
public class NodeExpressionMemberAccess(List<Token> tokens, NodeExpression target, TokenIdent name) : NodeExpression(tokens)
{
public NodeExpression Target { get; } = target;