Skip to content

Commit

Permalink
Its all coming together
Browse files Browse the repository at this point in the history
  • Loading branch information
HeronErin committed Apr 26, 2024
1 parent bdfb0bd commit e5da519
Show file tree
Hide file tree
Showing 3 changed files with 144 additions and 30 deletions.
19 changes: 11 additions & 8 deletions source/main.d
Original file line number Diff line number Diff line change
Expand Up @@ -10,12 +10,15 @@ import std.stdio;
void main()
{
size_t index = 0;
auto newScope = parseMultilineScope(FUNCTION_SCOPE_PARSE, "
int x = 5;
int y = x++ - 5;
if (x > y){
writeln(`hello world`);
}
".tokenizeText, index, nullable!ScopeData(null));
newScope.writeln;
auto newScope = parseMultilineScope(GLOBAL_SCOPE_PARSE, "
import std.stdio : writeln, write;
import std.math;
public static int main(){
int x = 5;
int y = x++ - 5;
if (x > y)
writeln(`hello world`);
}".tokenizeText, index, nullable!ScopeData(null));
newScope.tree();
}
40 changes: 32 additions & 8 deletions source/parsing/treegen/astTypes.d
Original file line number Diff line number Diff line change
Expand Up @@ -107,12 +107,19 @@ enum OperationVariety
EqualTo,
NotEqualTo
}

import parsing.treegen.scopeParser : ScopeData;

struct ConditionNodeData
{
dchar[][] precedingKeywords;
bool isScope;
AstNode condition;
ScopeData conditionScope;
union
{
ScopeData conditionScope;
AstNode conditionResultNode;
}
}

struct SingleArgumentOperationNodeData
Expand Down Expand Up @@ -209,17 +216,20 @@ class AstNode
import std.stdio;
import std.conv;

if (tabCount != -1)
{
foreach (i; 0 .. tabCount)
write("| ");
write("");
}
alias printTabs() = {
if (tabCount != -1)
{
foreach (i; 0 .. tabCount)
write("| ");
write("");
}
};
printTabs();

switch (action)
{
case AstAction.Call:
writeln(callNodeData.func.to!string ~ ":");
writeln("Call " ~ callNodeData.func.to!string ~ ":");
callNodeData.args.tree(tabCount + 1);
break;
case AstAction.DoubleArgumentOperation:
Expand Down Expand Up @@ -254,6 +264,20 @@ class AstNode
writeln(": ");
assignVariableNodeData.value.tree(tabCount + 1);
break;
case AstAction.IfStatement:
write(action);
writeln(" hasScope = " ~ conditionNodeData.isScope.to!string ~ " keywords = " ~ conditionNodeData
.precedingKeywords.to!string);
conditionNodeData.condition.tree(tabCount + 1);
if (conditionNodeData.isScope){
import parsing.treegen.scopeParser : tree;
conditionNodeData.conditionScope.tree(tabCount + 1);
}else{
conditionNodeData.conditionResultNode.tree(tabCount + 1);
}
// printTabs();
break;

default:
writeln(this.to!string);
break;
Expand Down
115 changes: 101 additions & 14 deletions source/parsing/treegen/scopeParser.d
Original file line number Diff line number Diff line change
Expand Up @@ -21,8 +21,8 @@ struct DeclaredFunction
{
dchar[][] precedingKeywords;
dchar[][] suffixKeywords;
NameUnit returnType;
NameUnit name;
NameUnit returnType;
// TODO: Args
ScopeData functionScope;
}
Expand All @@ -45,8 +45,10 @@ class ScopeData
DeclaredVariable[] declaredVariables;
Array!AstNode instructions;

void toString(scope void delegate(const(char)[]) sink) const {
void toString(scope void delegate(const(char)[]) sink) const
{
import std.conv;

sink("ScopeData{isPartialModule = ");
sink(isPartialModule.to!string);
sink(", moduleName = ");
Expand Down Expand Up @@ -220,7 +222,8 @@ LineVarietyTestResult parseLine(const(VarietyTestPair[]) scopeParseMethod, Token
.name,
parseMultilineScope(
FUNCTION_SCOPE_PARSE,
lineVariety.tokenMatches[FUNCTION_SCOPE].assertAs(TokenGrepMethod.Glob).tokens,
lineVariety.tokenMatches[FUNCTION_SCOPE].assertAs(TokenGrepMethod.Glob)
.tokens,
temp,
nullable!ScopeData(parent)
)
Expand All @@ -229,9 +232,11 @@ LineVarietyTestResult parseLine(const(VarietyTestPair[]) scopeParseMethod, Token
// assert(0);
break;
case LineVariety.IfStatementWithScope:
case LineVariety.IfStatementWithoutScope:
size_t endingIndex = index + lineVariety.length;
scope (exit) index = endingIndex;

scope (exit)
index = endingIndex;

size_t temp;

auto conditionNodes = expressionNodeFromTokens(
Expand All @@ -240,22 +245,40 @@ LineVarietyTestResult parseLine(const(VarietyTestPair[]) scopeParseMethod, Token
if (conditionNodes.length != 1)
throw new SyntaxError(
"Expression node tree could not be parsed properly (Not reducable into single node within if statement condition)");

ConditionNodeData conditionNodeData;
conditionNodeData.precedingKeywords = keywords;
conditionNodeData.condition = conditionNodes[0];
conditionNodeData.conditionScope
= parseMultilineScope(
if (lineVariety.lineVariety == LineVariety.IfStatementWithScope)
{
conditionNodeData.isScope = true;
conditionNodeData.conditionScope
= parseMultilineScope(
FUNCTION_SCOPE_PARSE,
lineVariety.tokenMatches[1].assertAs(TokenGrepMethod.Glob).tokens,
temp,
nullable!ScopeData(parent)
lineVariety.tokenMatches[1].assertAs(TokenGrepMethod.Glob)
.tokens,
temp,
nullable!ScopeData(parent)
);
}
else
{
conditionNodeData.isScope = false;
auto conditionLineNode = expressionNodeFromTokens(
lineVariety.tokenMatches[1].assertAs(TokenGrepMethod.Glob).tokens
);
if (conditionLineNode.length != 1)
throw new SyntaxError(
"Expression node tree could not be parsed properly (if without scope)");
conditionNodeData.conditionResultNode = conditionLineNode[0];

}
AstNode node = new AstNode();
node.action = AstAction.IfStatement;
node.conditionNodeData = conditionNodeData;
parent.instructions ~= node;
break;

case LineVariety.SimpleExpression:
size_t expression_end = tokens.findNearestSemiColon(index);
if (expression_end == -1)
Expand Down Expand Up @@ -294,6 +317,69 @@ ScopeData parseMultilineScope(const(VarietyTestPair[]) scopeParseMethod, Token[]
return scopeData;
}

void tree(ScopeData scopeData) => tree(scopeData, 0);
void tree(ScopeData scopeData, size_t tabCount)
{
import std.conv;

alias printTabs() = {
foreach (_; 0 .. tabCount)
write("| ");
};
alias printTabsV() = { printTabs(); write(""); };

printTabsV();
write("Scope: ");
write("isPartialModule = ");
writeln(scopeData.isPartialModule);
tabCount++;

printTabs();
write("Variables: ");
foreach (var; scopeData.declaredVariables)
{
write(var.name.to!string ~ " as " ~ var.type.to!string);
write(", ");
}
write("\n");
printTabs();
write("Imports: ");
foreach (imported; scopeData.imports)
{
write(imported.nameUnit);
write(": (");
foreach (selection; imported.importSelection)
{
selection.write;
write(", ");
}
write("), ");
}
write("\n");
printTabs();
writeln("Functions: ");
tabCount++;
foreach (func; scopeData.declaredFunctions)
{
printTabs();
write(func.precedingKeywords);
write(" ");
write(func.returnType);
write(" ");
write(func.name);
write("\n");
func.functionScope.tree(tabCount);
}
tabCount--;
printTabs();
writeln("AST nodes("~scopeData.instructions.length.to!string~"):");
foreach (AstNode node; scopeData.instructions)
{
node.tree(tabCount);
}

}

unittest
{
import parsing.tokenizer.make_tokens;
Expand Down Expand Up @@ -328,7 +414,7 @@ unittest
["float".makeUnicodeString]))
]
);

assert(newScope.instructions[0].action == AstAction.AssignVariable);
assert(newScope.instructions[1].action == AstAction.AssignVariable);
assert(newScope.instructions[2].action == AstAction.AssignVariable);
Expand Down Expand Up @@ -362,12 +448,13 @@ unittest
"floaty".makeUnicodeString
]);
}

unittest
{
import parsing.tokenizer.make_tokens;

size_t index;
auto t = "let x = 4/*asdadasd*/;".tokenizeText;
auto r = getLineVarietyTestResult(FUNCTION_SCOPE_PARSE, t, index);
assert(r.lineVariety == LineVariety.DeclarationAndAssignment);
}
}

0 comments on commit e5da519

Please sign in to comment.