Skip to content

Commit 10cfd12

Browse files
committed
Working self-checking based on full re-assembly
1 parent 51e588a commit 10cfd12

14 files changed

Lines changed: 683 additions & 106 deletions

File tree

.idea/workspace.xml

Lines changed: 25 additions & 25 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.
Lines changed: 145 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,145 @@
1+
package ko.carbonel.compiler.codegen;
2+
3+
import ko.carbonel.compiler.intermediate.tinyRust.TinyRustSymbolTable;
4+
import ko.carbonel.compiler.intermediate.tinyRust.ast.expression.*;
5+
import ko.carbonel.compiler.intermediate.tinyRust.ast.statement.*;
6+
import ko.carbonel.compiler.intermediate.tinyRust.ts.ClassEntry;
7+
import ko.carbonel.compiler.intermediate.tinyRust.ts.MethodEntry;
8+
import ko.carbonel.compiler.intermediate.tinyRust.ts.VariableEntry;
9+
10+
import java.util.List;
11+
import java.util.stream.Collectors;
12+
13+
public class DeCompiler {
14+
private DeCompiler() {
15+
throw new IllegalStateException("Utility class");
16+
}
17+
18+
public static String decompile(TinyRustSymbolTable tinyRustSymbolTable) {
19+
TinyRustSymbolTable temp = new TinyRustSymbolTable();
20+
String classes = tinyRustSymbolTable.classEntries.stream()
21+
.filter(it->temp.classEntries.stream().noneMatch(primitive->primitive.name.lexeme().equals(it.name.lexeme())))
22+
.map(DeCompiler::decompileClass).collect(Collectors.joining("\n"));
23+
String main = decompileMain(tinyRustSymbolTable.main);
24+
return classes + "\n" + main;
25+
}
26+
27+
private static String decompileMain(MethodEntry main) {
28+
String out = "";
29+
out += "fn " + main.name.lexeme() + "(";
30+
out += main.parameters.stream().map(DeCompiler::decompileArgument).collect(Collectors.joining(", "));
31+
out += ")";
32+
out += decompileStatement(main.block, main.variables);
33+
return out;
34+
}
35+
36+
37+
private static String decompileMethod(MethodEntry method) {
38+
String out = "";
39+
if (method.name.lexeme().equals(MethodEntry.CONSTRUCTOR)){
40+
out += method.name.lexeme() + "(";
41+
out += method.parameters.stream().map(DeCompiler::decompileArgument).collect(Collectors.joining(", "));
42+
out += ")";
43+
}else{
44+
if (method.isStatic) out += "static ";
45+
out += "fn " + method.name.lexeme() + "(";
46+
out += method.parameters.stream().map(DeCompiler::decompileArgument).collect(Collectors.joining(", "));
47+
out += ") -> " + method.returnType.type.lexeme();
48+
}
49+
out += decompileStatement(method.block, method.variables);
50+
return out;
51+
}
52+
53+
private static String decompileStatement(BlockStatementEntry statementEntry, List<VariableEntry> vars) {
54+
String out = "";
55+
out += "{\n";
56+
out += vars.stream().map(DeCompiler::decompileVariable).collect(Collectors.joining("\n"));
57+
out += "\n";
58+
out += statementEntry.statements.stream().map(DeCompiler::decompileStatement).collect(Collectors.joining("\n"));
59+
out += "\n}";
60+
return out;
61+
}
62+
63+
private static String decompileVariable(VariableEntry variableEntry) {
64+
return (variableEntry.type.isArray ? "Array " : "") + variableEntry.type.type.lexeme()+ ": " + variableEntry.name.lexeme() + ";";
65+
}
66+
67+
private static String decompileStatement(StatementEntry statementEntry) {
68+
String out = "";
69+
if (statementEntry instanceof EmptyStatementEntry) {
70+
out += ";";
71+
} else if (statementEntry instanceof ExpressionStatementEntry exp) {
72+
out += "(" + decompileExpression(exp.expression) + ");";
73+
} else if (statementEntry instanceof BlockStatementEntry blk) {
74+
out += "{\n";
75+
out += blk.statements.stream().map(DeCompiler::decompileStatement).collect(Collectors.joining("\n"));
76+
out += "\n}";
77+
} else if (statementEntry instanceof IfStatementEntry iF) {
78+
out += "if (" + decompileExpression(iF.ifCondition) + ")\n";
79+
out += decompileStatement(iF.ifBody);
80+
if (iF.elseBody != null) {
81+
out += " else\n";
82+
out += decompileStatement(iF.elseBody);
83+
}
84+
} else if (statementEntry instanceof WhileStatementEntry whl) {
85+
out += "while (" + decompileExpression(whl.whileCondition) + ")\n";
86+
out += decompileStatement(whl.whileBody);
87+
} else if (statementEntry instanceof ReturnStatementEntry ret) {
88+
out += "return " + decompileExpression(ret.returnExpression) + ";";
89+
} else if (statementEntry instanceof AssignStatementEntry as) {
90+
out += decompileExpression(as.lhs()) + "=" + decompileExpression(as.rhs()) + ";";
91+
} else throw new RuntimeException("Unknown statement type " + statementEntry.getClass().getName());
92+
return out;
93+
}
94+
95+
private static String decompileExpression(ExpressionEntry expression) {
96+
String out = "";
97+
if (expression instanceof UnaryExpressionEntry un) {
98+
out += un.operator.lexeme() + decompileExpression(un.expression);
99+
} else if (expression instanceof LiteralExpressionEntry lit) {
100+
out += lit.literal.lexeme();
101+
} else if (expression instanceof BinaryExpressionEntry bin) {
102+
out += "(" + decompileExpression(bin.left) + " " + bin.operator.lexeme() + " " + decompileExpression(bin.right) + ")";
103+
} else if (expression instanceof MethodCallExpressionEntry call) {
104+
out += call.methodName.lexeme() + "(";
105+
out += call.arguments.stream().map(DeCompiler::decompileExpression).collect(Collectors.joining(", "));
106+
out += ")";
107+
} else if (expression instanceof NewClassExpressionEntry newExp) {
108+
out += "new " + newExp.className.lexeme() + "(";
109+
out += newExp.constructorArguments.stream().map(DeCompiler::decompileExpression).collect(Collectors.joining(", "));
110+
out += ")";
111+
} else if (expression instanceof ArrayAccessExpressionEntry array) {
112+
out += decompileExpression(array.array) + "[" + decompileExpression(array.index) + "]";
113+
} else if (expression instanceof FieldAccessEntry field) {
114+
out += field.fieldName.lexeme();
115+
} else if (expression instanceof ChainedExpressionEntry chain) {
116+
out += decompileExpression(chain.base) + "." + decompileExpression(chain.chain);
117+
} else if (expression instanceof NewArrayExpressionEntry array) {
118+
out += "new " + array.type.lexeme() + "[" + decompileExpression(array.size) + "]";
119+
} else if (expression instanceof ClassRefEntry cls) {
120+
out += cls.name.lexeme();
121+
} else throw new RuntimeException("Unknown expression type " + expression.getClass().getName());
122+
return out;
123+
}
124+
125+
private static String decompileClass(ClassEntry clazz) {
126+
String out = "class " + clazz.name.lexeme();
127+
if (clazz.superClass != null) out += " : " + clazz.superClass.type.lexeme();
128+
out += " {\n";
129+
out += clazz.fields.stream().map(DeCompiler::decompileField).collect(Collectors.joining("\n"));
130+
out += clazz.methods.stream().map(DeCompiler::decompileMethod).collect(Collectors.joining("\n"));
131+
out += "\n}\n";
132+
return out;
133+
}
134+
135+
private static String decompileField(VariableEntry variableEntry) {
136+
String out = "";
137+
if (variableEntry.isPublic) out += "pub ";
138+
out += (variableEntry.type.isArray ? "Array " : "") + variableEntry.type.type.lexeme() + ": " + variableEntry.name.lexeme();
139+
return out + ";";
140+
}
141+
142+
private static String decompileArgument(VariableEntry variableEntry) {
143+
return (variableEntry.type.isArray ? "Array " : "") + (variableEntry.type.type.lexeme() + ": " + variableEntry.name.lexeme());
144+
}
145+
}

src/main/java/ko/carbonel/compiler/generated/AttrTinyRustParser.java

Lines changed: 20 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1207,7 +1207,19 @@ private List<TinyRustLexerToken> matchToken_Stmt_star(){
12071207
private List<TinyRustLexerToken> matchToken_Stmt(){
12081208
enter("matchToken_Stmt");
12091209
List<TinyRustLexerToken> result = null;
1210-
if (peek(TinyRustTokenType.IF)){
1210+
if (peek(TinyRustTokenType.RETURN)){
1211+
st.newReturn();
1212+
TinyRustLexerToken v_1 = match(TinyRustTokenType.RETURN);
1213+
List<TinyRustLexerToken> v_2 = matchToken_Stmt_factored();
1214+
st.endReturn();
1215+
} else if (peek(TinyRustTokenType.OPN_PAREN)){
1216+
st.newExpr();
1217+
TinyRustLexerToken v_1 = match(TinyRustTokenType.OPN_PAREN);
1218+
List<TinyRustLexerToken> v_2 = matchToken_ExpOr();
1219+
TinyRustLexerToken v_3 = match(TinyRustTokenType.CLS_PAREN);
1220+
TinyRustLexerToken v_4 = match(TinyRustTokenType.SEMI_COLON);
1221+
st.endExpr();
1222+
} else if (peek(TinyRustTokenType.IF)){
12111223
st.newIf();
12121224
TinyRustLexerToken v_1 = match(TinyRustTokenType.IF);
12131225
TinyRustLexerToken v_2 = match(TinyRustTokenType.OPN_PAREN);
@@ -1217,6 +1229,9 @@ private List<TinyRustLexerToken> matchToken_Stmt(){
12171229
List<TinyRustLexerToken> v_6 = matchToken_Stmt();
12181230
List<TinyRustLexerToken> v_7 = matchToken_Stmt_factored_factored_factored();
12191231
st.ifEnd();
1232+
} else if (peek(TinyRustTokenType.SEMI_COLON)){
1233+
st.newEmpty();
1234+
TinyRustLexerToken v_1 = match(TinyRustTokenType.SEMI_COLON);
12201235
} else if (peek(TinyRustTokenType.WHILE)){
12211236
st.newWhile();
12221237
TinyRustLexerToken v_1 = match(TinyRustTokenType.WHILE);
@@ -1226,29 +1241,14 @@ private List<TinyRustLexerToken> matchToken_Stmt(){
12261241
st.whileBody();
12271242
List<TinyRustLexerToken> v_6 = matchToken_Stmt();
12281243
st.endWhile();
1229-
} else if (peek(TinyRustTokenType.RETURN)){
1230-
st.newReturn();
1231-
TinyRustLexerToken v_1 = match(TinyRustTokenType.RETURN);
1232-
List<TinyRustLexerToken> v_2 = matchToken_Stmt_factored();
1233-
st.endReturn();
1234-
} else if (peek(TinyRustTokenType.SEMI_COLON)){
1235-
st.newEmpty();
1236-
TinyRustLexerToken v_1 = match(TinyRustTokenType.SEMI_COLON);
1237-
} else if (peek(TinyRustTokenType.OPN_BRACE)){
1238-
st.newBlock();
1239-
TinyRustLexerToken v_1 = match(TinyRustTokenType.OPN_BRACE);
1240-
List<TinyRustLexerToken> v_2 = matchToken_Method_factored();
1241-
} else if (peek(TinyRustTokenType.OPN_PAREN)){
1242-
st.newExpr();
1243-
TinyRustLexerToken v_1 = match(TinyRustTokenType.OPN_PAREN);
1244-
List<TinyRustLexerToken> v_2 = matchToken_ExpOr();
1245-
TinyRustLexerToken v_3 = match(TinyRustTokenType.CLS_PAREN);
1246-
TinyRustLexerToken v_4 = match(TinyRustTokenType.SEMI_COLON);
1247-
st.endExpr();
12481244
} else if (peek(TinyRustTokenType.ATTR_ID, TinyRustTokenType.SELF)){
12491245
st.newAssign();
12501246
List<TinyRustLexerToken> v_1 = matchToken_Assign();
12511247
TinyRustLexerToken v_2 = match(TinyRustTokenType.SEMI_COLON);
1248+
} else if (peek(TinyRustTokenType.OPN_BRACE)){
1249+
st.newBlock();
1250+
TinyRustLexerToken v_1 = match(TinyRustTokenType.OPN_BRACE);
1251+
List<TinyRustLexerToken> v_2 = matchToken_Method_factored();
12521252
} else {
12531253
handleUnexpectedToken("Stmt", Set.of(TinyRustTokenType.ATTR_ID, TinyRustTokenType.IF, TinyRustTokenType.OPN_BRACE, TinyRustTokenType.OPN_PAREN, TinyRustTokenType.RETURN, TinyRustTokenType.SELF, TinyRustTokenType.SEMI_COLON, TinyRustTokenType.WHILE));
12541254
}

0 commit comments

Comments
 (0)