diff --git a/Core/EVIL.Grammar/AST/Statements/ExpressionStatement.cs b/Core/EVIL.Grammar/AST/Statements/ExpressionStatement.cs
index 7b9ec9ba..052ae037 100644
--- a/Core/EVIL.Grammar/AST/Statements/ExpressionStatement.cs
+++ b/Core/EVIL.Grammar/AST/Statements/ExpressionStatement.cs
@@ -9,6 +9,8 @@ public sealed class ExpressionStatement : Statement
public ExpressionStatement(Expression expression)
{
Expression = expression;
+ Reparent(Expression);
+
Line = expression.Line;
}
}
diff --git a/FrontEnd/EVIL.evil/EVIL.evil.csproj b/FrontEnd/EVIL.evil/EVIL.evil.csproj
index 29d4b47e..8353d6a8 100644
--- a/FrontEnd/EVIL.evil/EVIL.evil.csproj
+++ b/FrontEnd/EVIL.evil/EVIL.evil.csproj
@@ -4,7 +4,7 @@
net7.0
enable
evil
- 1.6.0
+ 1.7.0
diff --git a/FrontEnd/EVIL.evil/EvmFrontEnd.cs b/FrontEnd/EVIL.evil/EvmFrontEnd.cs
index 47bc9c2a..b4eedc86 100644
--- a/FrontEnd/EVIL.evil/EvmFrontEnd.cs
+++ b/FrontEnd/EVIL.evil/EvmFrontEnd.cs
@@ -30,12 +30,14 @@ public partial class EvmFrontEnd
{ "h|help", "display this message and quit.", (h) => _displayHelpAndQuit = h != null },
{ "v|version", "display compiler and VM version information.", (v) => _displayVersionAndQuit = v != null },
{ "I|include-dir=", "add include directory to the list of search paths.", (I) => _includeHandler.AddIncludeSearchPath(I) },
- { "g|gen-docs", "generate documentation for all detected native modules.", (g) => _generateModuleDocsAndQuit = g != null }
+ { "g|gen-docs", "generate documentation for all detected native modules.", (g) => _generateModuleDocsAndQuit = g != null },
+ { "d|disasm", "disassemble the compiled script.", (d) => _disassembleCompiledScript = d != null }
};
private static bool _displayHelpAndQuit;
private static bool _displayVersionAndQuit;
- private static bool _generateModuleDocsAndQuit;
+ private static bool _generateModuleDocsAndQuit;
+ private static bool _disassembleCompiledScript;
public async Task Run(string[] args)
{
@@ -122,6 +124,16 @@ public async Task Run(string[] args)
Terminate(msg, exitCode: ExitCode.CompilerError);
}
+ if (_disassembleCompiledScript)
+ {
+ Console.WriteLine($"Disassembly of '{scriptPath}'\n-------------------");
+
+ foreach (var chunk in script.Chunks)
+ {
+ Disassembler.Disassemble(chunk, Console.Out);
+ }
+ }
+
if (!script.TryFindChunkByName("main", out var mainChunk))
{
Terminate(
diff --git a/VirtualMachine/Ceres/Ceres.csproj b/VirtualMachine/Ceres/Ceres.csproj
index 2e193d58..e0945ff6 100644
--- a/VirtualMachine/Ceres/Ceres.csproj
+++ b/VirtualMachine/Ceres/Ceres.csproj
@@ -5,7 +5,7 @@
enable
11.0
- 1.3.0
+ 1.3.1
Ceres
Ceres
diff --git a/VirtualMachine/Ceres/TranslationEngine/Compiler.Expression.Assignment.cs b/VirtualMachine/Ceres/TranslationEngine/Compiler.Expression.Assignment.cs
index b6a3c177..181bb96e 100644
--- a/VirtualMachine/Ceres/TranslationEngine/Compiler.Expression.Assignment.cs
+++ b/VirtualMachine/Ceres/TranslationEngine/Compiler.Expression.Assignment.cs
@@ -2,6 +2,7 @@
using Ceres.TranslationEngine.Diagnostics;
using EVIL.Grammar;
using EVIL.Grammar.AST.Expressions;
+using EVIL.Grammar.AST.Statements;
namespace Ceres.TranslationEngine
{
@@ -22,6 +23,7 @@ public override void Visit(AssignmentExpression assignmentExpression)
Chunk.CodeGenerator.Emit(OpCode.LDNIL);
Chunk.CodeGenerator.Emit(OpCode.CNE);
Chunk.CodeGenerator.Emit(OpCode.TJMP, valueNotNilLabel);
+ Chunk.CodeGenerator.Emit(OpCode.POP);
Visit(assignmentExpression.Right);
Chunk.CodeGenerator.Emit(OpCode.DUP);
EmitVarSet(symRef.Identifier);
@@ -29,7 +31,7 @@ public override void Visit(AssignmentExpression assignmentExpression)
return;
}
-
+
if (assignmentExpression.OperationType != AssignmentOperationType.Direct)
{
EmitVarGet(symRef.Identifier);
@@ -77,6 +79,7 @@ public override void Visit(AssignmentExpression assignmentExpression)
Chunk.CodeGenerator.Emit(OpCode.LDNIL);
Chunk.CodeGenerator.Emit(OpCode.CNE);
Chunk.CodeGenerator.Emit(OpCode.TJMP, valueNotNilLabel);
+ Chunk.CodeGenerator.Emit(OpCode.POP);
Visit(assignmentExpression.Right);
Chunk.CodeGenerator.Emit(OpCode.DUP);
Visit(ie.Indexable);
@@ -86,7 +89,7 @@ public override void Visit(AssignmentExpression assignmentExpression)
return;
}
-
+
if (assignmentExpression.OperationType != AssignmentOperationType.Direct)
{
Visit(ie);
diff --git a/VirtualMachine/Tests/Ceres.LanguageTests/tests/004_assignment_operators.vil b/VirtualMachine/Tests/Ceres.LanguageTests/tests/004_assignment_operators.vil
index 43e1c0c1..e71dcf5d 100644
--- a/VirtualMachine/Tests/Ceres.LanguageTests/tests/004_assignment_operators.vil
+++ b/VirtualMachine/Tests/Ceres.LanguageTests/tests/004_assignment_operators.vil
@@ -194,10 +194,10 @@ fn coalescing_assignment_table_entry() {
#[test]
fn chained_coalescing_assignment_table_entry_when_first_is_nil() {
val t = { };
- val a = "";
+ val a = "string";
rw val b = nil;
- t.entry ??= b ??= a;
+ t.entry ??= (b ??= a);
assert.equal(b, a);
assert.equal(t.entry, a);