Trait -> Interface
This commit is contained in:
@@ -24,7 +24,6 @@ public partial class QBEGenerator
|
|||||||
LiteralNode literal => EmitLiteral(literal),
|
LiteralNode literal => EmitLiteral(literal),
|
||||||
UnaryExpressionNode unaryExpression => EmitUnaryExpression(unaryExpression),
|
UnaryExpressionNode unaryExpression => EmitUnaryExpression(unaryExpression),
|
||||||
StructFieldAccessNode structFieldAccess => EmitStructFieldAccess(structFieldAccess),
|
StructFieldAccessNode structFieldAccess => EmitStructFieldAccess(structFieldAccess),
|
||||||
InterfaceFuncAccessNode traitFuncAccess => EmitTraitFuncAccess(traitFuncAccess),
|
|
||||||
ArrayIndexAccessNode arrayIndex => EmitArrayIndexAccess(arrayIndex),
|
ArrayIndexAccessNode arrayIndex => EmitArrayIndexAccess(arrayIndex),
|
||||||
_ => throw new ArgumentOutOfRangeException(nameof(expression))
|
_ => throw new ArgumentOutOfRangeException(nameof(expression))
|
||||||
};
|
};
|
||||||
@@ -414,11 +413,6 @@ public partial class QBEGenerator
|
|||||||
return new Val(output, structFieldAccess.Type, ValKind.Pointer);
|
return new Val(output, structFieldAccess.Type, ValKind.Pointer);
|
||||||
}
|
}
|
||||||
|
|
||||||
private Val EmitTraitFuncAccess(InterfaceFuncAccessNode interfaceFuncAccess)
|
|
||||||
{
|
|
||||||
throw new NotImplementedException();
|
|
||||||
}
|
|
||||||
|
|
||||||
private Val EmitFuncCall(FuncCallNode funcCall)
|
private Val EmitFuncCall(FuncCallNode funcCall)
|
||||||
{
|
{
|
||||||
var expression = EmitExpression(funcCall.Expression);
|
var expression = EmitExpression(funcCall.Expression);
|
||||||
|
|||||||
@@ -55,12 +55,6 @@ public partial class QBEGenerator
|
|||||||
_writer.NewLine();
|
_writer.NewLine();
|
||||||
}
|
}
|
||||||
|
|
||||||
foreach (var trait in _definitionTable.GetTraits())
|
|
||||||
{
|
|
||||||
EmitTraitVTable(trait);
|
|
||||||
_writer.NewLine();
|
|
||||||
}
|
|
||||||
|
|
||||||
foreach (var funcDef in _syntaxTree.Definitions.OfType<LocalFuncNode>())
|
foreach (var funcDef in _syntaxTree.Definitions.OfType<LocalFuncNode>())
|
||||||
{
|
{
|
||||||
EmitFuncDefinition(LocalFuncName(funcDef), funcDef.Signature.Parameters, funcDef.Signature.ReturnType, funcDef.Body);
|
EmitFuncDefinition(LocalFuncName(funcDef), funcDef.Signature.Parameters, funcDef.Signature.ReturnType, funcDef.Body);
|
||||||
@@ -411,18 +405,6 @@ public partial class QBEGenerator
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void EmitTraitVTable(TraitNode traitDef)
|
|
||||||
{
|
|
||||||
_writer.WriteLine($"type {CustomTypeName(traitDef.Name)} = {{");
|
|
||||||
|
|
||||||
foreach (var func in traitDef.Functions)
|
|
||||||
{
|
|
||||||
_writer.Indented($"l, # func {func.Name}({string.Join(", ", func.Signature.Parameters.Select(x => $"{x.Name}: {x.Type}"))}): {func.Signature.ReturnType}");
|
|
||||||
}
|
|
||||||
|
|
||||||
_writer.WriteLine("}");
|
|
||||||
}
|
|
||||||
|
|
||||||
private void EmitBlock(BlockNode block, Scope? scope = null)
|
private void EmitBlock(BlockNode block, Scope? scope = null)
|
||||||
{
|
{
|
||||||
_scopes.Push(scope ?? Scope.SubScope());
|
_scopes.Push(scope ?? Scope.SubScope());
|
||||||
|
|||||||
@@ -37,8 +37,8 @@ public sealed class TypedDefinitionTable
|
|||||||
return _definitions.OfType<StructNode>();
|
return _definitions.OfType<StructNode>();
|
||||||
}
|
}
|
||||||
|
|
||||||
public IEnumerable<TraitNode> GetTraits()
|
public IEnumerable<InterfaceNode> GetInterfaces()
|
||||||
{
|
{
|
||||||
return _definitions.OfType<TraitNode>();
|
return _definitions.OfType<InterfaceNode>();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -38,14 +38,14 @@ public class DefinitionTable
|
|||||||
return structNode.Fields.Where(x => x.Name == field);
|
return structNode.Fields.Where(x => x.Name == field);
|
||||||
}
|
}
|
||||||
|
|
||||||
public IEnumerable<InterfaceSyntax> LookupTrait(CustomTypeNode type)
|
public IEnumerable<InterfaceSyntax> LookupInterface(CustomTypeNode type)
|
||||||
{
|
{
|
||||||
return _definitions
|
return _definitions
|
||||||
.OfType<InterfaceSyntax>()
|
.OfType<InterfaceSyntax>()
|
||||||
.Where(x => x.Name == type.Name);
|
.Where(x => x.Name == type.Name);
|
||||||
}
|
}
|
||||||
|
|
||||||
public IEnumerable<InterfaceFuncSyntax> LookupTraitFunc(InterfaceSyntax @interface, string name)
|
public IEnumerable<InterfaceFuncSyntax> LookupInterfaceFunc(InterfaceSyntax @interface, string name)
|
||||||
{
|
{
|
||||||
return @interface.Functions.Where(x => x.Name == name);
|
return @interface.Functions.Where(x => x.Name == name);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -14,6 +14,6 @@ public record StructFieldNode(int Index, string Name, TypeNode Type, Optional<Ex
|
|||||||
|
|
||||||
public record StructNode(string Name, IReadOnlyList<StructFieldNode> Fields) : DefinitionNode;
|
public record StructNode(string Name, IReadOnlyList<StructFieldNode> Fields) : DefinitionNode;
|
||||||
|
|
||||||
public record TraitFuncNode(string Name, FuncSignatureNode Signature) : Node;
|
public record InterfacenFuncNode(string Name, FuncSignatureNode Signature) : Node;
|
||||||
|
|
||||||
public record TraitNode(string Name, IReadOnlyList<TraitFuncNode> Functions) : DefinitionNode;
|
public record InterfaceNode(string Name, IReadOnlyList<InterfacenFuncNode> Functions) : DefinitionNode;
|
||||||
@@ -217,7 +217,7 @@ public class CustomTypeNode(string name) : NubComplexTypeNode
|
|||||||
return CustomTypeKind.Struct;
|
return CustomTypeKind.Struct;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (definitionTable.GetTraits().Any(x => x.Name == Name))
|
if (definitionTable.GetInterfaces().Any(x => x.Name == Name))
|
||||||
{
|
{
|
||||||
return CustomTypeKind.Interface;
|
return CustomTypeKind.Interface;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -52,23 +52,23 @@ public sealed class TypeChecker
|
|||||||
return node switch
|
return node switch
|
||||||
{
|
{
|
||||||
ExternFuncSyntax definition => CheckExternFuncDefinition(definition),
|
ExternFuncSyntax definition => CheckExternFuncDefinition(definition),
|
||||||
InterfaceSyntax definition => CheckTraitDefinition(definition),
|
InterfaceSyntax definition => CheckInterfaceDefinition(definition),
|
||||||
LocalFuncSyntax definition => CheckLocalFuncDefinition(definition),
|
LocalFuncSyntax definition => CheckLocalFuncDefinition(definition),
|
||||||
StructSyntax definition => CheckStruct(definition),
|
StructSyntax definition => CheckStruct(definition),
|
||||||
_ => throw new ArgumentOutOfRangeException(nameof(node))
|
_ => throw new ArgumentOutOfRangeException(nameof(node))
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
private TraitNode CheckTraitDefinition(InterfaceSyntax node)
|
private InterfaceNode CheckInterfaceDefinition(InterfaceSyntax node)
|
||||||
{
|
{
|
||||||
var functions = new List<TraitFuncNode>();
|
var functions = new List<InterfacenFuncNode>();
|
||||||
|
|
||||||
foreach (var function in node.Functions)
|
foreach (var function in node.Functions)
|
||||||
{
|
{
|
||||||
functions.Add(new TraitFuncNode(function.Name, CheckFuncSignature(function.Signature)));
|
functions.Add(new InterfacenFuncNode(function.Name, CheckFuncSignature(function.Signature)));
|
||||||
}
|
}
|
||||||
|
|
||||||
return new TraitNode(node.Name, functions);
|
return new InterfaceNode(node.Name, functions);
|
||||||
}
|
}
|
||||||
|
|
||||||
private StructNode CheckStruct(StructSyntax node)
|
private StructNode CheckStruct(StructSyntax node)
|
||||||
@@ -362,28 +362,28 @@ public sealed class TypeChecker
|
|||||||
|
|
||||||
if (boundExpression.Type is CustomTypeNode customType)
|
if (boundExpression.Type is CustomTypeNode customType)
|
||||||
{
|
{
|
||||||
var traits = _definitionTable.LookupTrait(customType).ToArray();
|
var interfaces = _definitionTable.LookupInterface(customType).ToArray();
|
||||||
if (traits.Length > 0)
|
if (interfaces.Length > 0)
|
||||||
{
|
{
|
||||||
if (traits.Length > 1)
|
if (interfaces.Length > 1)
|
||||||
{
|
{
|
||||||
throw new CheckException(Diagnostic.Error($"Trait {customType} has multiple definitions").Build());
|
throw new CheckException(Diagnostic.Error($"Interface {customType} has multiple definitions").Build());
|
||||||
}
|
}
|
||||||
|
|
||||||
var trait = traits[0];
|
var @interface = interfaces[0];
|
||||||
|
|
||||||
var traitFuncs = _definitionTable.LookupTraitFunc(trait, expression.Member).ToArray();
|
var interfaceFuncs = _definitionTable.LookupInterfaceFunc(@interface, expression.Member).ToArray();
|
||||||
if (traits.Length > 0)
|
if (interfaces.Length > 0)
|
||||||
{
|
{
|
||||||
if (traits.Length > 1)
|
if (interfaces.Length > 1)
|
||||||
{
|
{
|
||||||
throw new CheckException(Diagnostic.Error($"Trait {customType} has multiple functions with the name {expression.Member}").Build());
|
throw new CheckException(Diagnostic.Error($"Interface {customType} has multiple functions with the name {expression.Member}").Build());
|
||||||
}
|
}
|
||||||
|
|
||||||
var traitFunc = traitFuncs[0];
|
var interfaceFunc = interfaceFuncs[0];
|
||||||
|
|
||||||
var returnType = CheckType(traitFunc.Signature.ReturnType);
|
var returnType = CheckType(interfaceFunc.Signature.ReturnType);
|
||||||
var parameterTypes = traitFunc.Signature.Parameters.Select(p => CheckType(p.Type)).ToList();
|
var parameterTypes = interfaceFunc.Signature.Parameters.Select(p => CheckType(p.Type)).ToList();
|
||||||
var type = new FuncTypeNode(parameterTypes, returnType);
|
var type = new FuncTypeNode(parameterTypes, returnType);
|
||||||
return new InterfaceFuncAccessNode(type, customType, boundExpression, expression.Member);
|
return new InterfaceFuncAccessNode(type, customType, boundExpression, expression.Member);
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user