Compiler
- Moved configuration sub-system to its own class `CompilerConfiguration` - `getConfig()` and `setConfig()` are now templatised to generate, at compile-time, type-specific versions which will fetch and convert using the requested type - Added some more default configuration parameters for DGen DGen - Implemented configuration checking for `genTabs()` and `emitEntryPoint()` (both which have the default config value of `true`) - Added commented-out testing code (see issue #88)
This commit is contained in:
parent
a772b55966
commit
a987f114ac
|
@ -10,6 +10,7 @@ import compiler.codegen.instruction : Instruction;
|
|||
import std.range : walkLength;
|
||||
import gogga;
|
||||
import std.conv : to;
|
||||
import compiler.compiler : CompilerConfiguration;
|
||||
|
||||
/**
|
||||
* TODO: Perhaps have an interface that can emit(Context/Parent, Statement)
|
||||
|
@ -21,6 +22,7 @@ public abstract class CodeEmitter
|
|||
{
|
||||
protected TypeChecker typeChecker;
|
||||
protected File file;
|
||||
protected CompilerConfiguration config;
|
||||
|
||||
/**
|
||||
* The selected queue is the queue to be used
|
||||
|
@ -125,7 +127,7 @@ public abstract class CodeEmitter
|
|||
return functionBodyInstrs.keys();
|
||||
}
|
||||
|
||||
this(TypeChecker typeChecker, File file)
|
||||
this(TypeChecker typeChecker, File file, CompilerConfiguration config)
|
||||
{
|
||||
this.typeChecker = typeChecker;
|
||||
|
||||
|
@ -138,6 +140,7 @@ public abstract class CodeEmitter
|
|||
gprintln("CodeEmitter: Got number of function defs: "~to!(string)(functionBodyInstrs));
|
||||
|
||||
this.file = file;
|
||||
this.config = config;
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -18,6 +18,7 @@ import compiler.symbols.data : SymbolType, Variable, Function, VariableParameter
|
|||
import compiler.symbols.check : getCharacter;
|
||||
import misc.utils : Stack;
|
||||
import compiler.symbols.typing.core : Type, Primitive, Integer, Void, Pointer;
|
||||
import compiler.compiler : CompilerConfiguration;
|
||||
|
||||
public final class DCodeEmitter : CodeEmitter
|
||||
{
|
||||
|
@ -27,9 +28,9 @@ public final class DCodeEmitter : CodeEmitter
|
|||
private bool varDecWantsConsumeVarAss = false;
|
||||
|
||||
|
||||
this(TypeChecker typeChecker, File file)
|
||||
this(TypeChecker typeChecker, File file, CompilerConfiguration config)
|
||||
{
|
||||
super(typeChecker, file);
|
||||
super(typeChecker, file, config);
|
||||
}
|
||||
|
||||
private ulong transformDepth = 0;
|
||||
|
@ -37,10 +38,16 @@ public final class DCodeEmitter : CodeEmitter
|
|||
private string genTabs(ulong count)
|
||||
{
|
||||
string tabStr;
|
||||
for(ulong i = 0; i < count; i++)
|
||||
|
||||
/* Only generate tabs if enabled in compiler config */
|
||||
if(config.getConfig!(bool)("dgen:pretty_code"))
|
||||
{
|
||||
tabStr~="\t";
|
||||
for(ulong i = 0; i < count; i++)
|
||||
{
|
||||
tabStr~="\t";
|
||||
}
|
||||
}
|
||||
|
||||
return tabStr;
|
||||
}
|
||||
|
||||
|
@ -515,8 +522,13 @@ public final class DCodeEmitter : CodeEmitter
|
|||
emitFunctionPrototypes();
|
||||
emitFunctionDefinitions();
|
||||
|
||||
//TODO: Emit main (entry point)
|
||||
emitEntryPoint();
|
||||
|
||||
// If enabled (default: yes) then emit entry point (TODO: change later)
|
||||
if(config.getConfig!(bool)("dgen_emit_entrypoint_test"))
|
||||
{
|
||||
//TODO: Emit main (entry point)
|
||||
emitEntryPoint();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -13,6 +13,30 @@ import core.stdc.stdlib;
|
|||
import compiler.codegen.emit.core;
|
||||
import compiler.codegen.emit.dgen;
|
||||
|
||||
public class CompilerConfiguration
|
||||
{
|
||||
private string[string] config;
|
||||
|
||||
public void setConfig(VType)(string key, VType value)
|
||||
{
|
||||
config[key] = to!(string)(value);
|
||||
}
|
||||
|
||||
public VType getConfig(VType)(string key)
|
||||
{
|
||||
import std.algorithm : canFind;
|
||||
if(canFind(config.keys(), key))
|
||||
{
|
||||
return to!(VType)(config[key]);
|
||||
}
|
||||
else
|
||||
{
|
||||
// TODO: Change to a TError
|
||||
// throw new Exception("Key not found");
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public class Compiler
|
||||
{
|
||||
|
@ -32,33 +56,23 @@ public class Compiler
|
|||
private CodeEmitter emitter;
|
||||
private File emitOutFile;
|
||||
|
||||
private string[string] config;
|
||||
/* The configuration */
|
||||
private CompilerConfiguration config;
|
||||
|
||||
/* TODO: Make the default config */
|
||||
private void defaultConfig()
|
||||
{
|
||||
/* Enable Behaviour-C fixes */
|
||||
setConfig("behavec:preinline_args", "true");
|
||||
config.setConfig("behavec:preinline_args", true);
|
||||
|
||||
/* Enable pretty code generation for DGen */
|
||||
config.setConfig("dgen:pretty_code", true);
|
||||
|
||||
/* Enable entry point test generation for DGen */
|
||||
config.setConfig("dgen_emit_entrypoint_test", true);
|
||||
}
|
||||
|
||||
public void setConfig(string key, string value)
|
||||
{
|
||||
config[key] = value;
|
||||
}
|
||||
|
||||
public string getConfig(string key)
|
||||
{
|
||||
import std.algorithm : canFind;
|
||||
if(canFind(config.keys(), key))
|
||||
{
|
||||
return config[key];
|
||||
}
|
||||
else
|
||||
{
|
||||
// TODO: Change to a TError
|
||||
throw new Exception("Key not found");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Create a new compiler instance to compile the given
|
||||
|
@ -71,6 +85,8 @@ public class Compiler
|
|||
this.inputSource = sourceCode;
|
||||
this.emitOutFile = emitOutFile;
|
||||
|
||||
this.config = new CompilerConfiguration();
|
||||
|
||||
/* Enable the default config */
|
||||
defaultConfig();
|
||||
}
|
||||
|
@ -100,7 +116,7 @@ public class Compiler
|
|||
this.typeChecker.beginCheck();
|
||||
|
||||
/* Perform code emitting */
|
||||
this.emitter = new DCodeEmitter(typeChecker, emitOutFile);
|
||||
this.emitter = new DCodeEmitter(typeChecker, emitOutFile, config);
|
||||
emitter.emit(); // Emit the code
|
||||
emitOutFile.close(); // Flush (perform the write() syscall)
|
||||
emitter.finalize(); // Call CC on the file containing generated C code
|
||||
|
@ -147,4 +163,24 @@ void beginCompilation(string[] sourceFiles)
|
|||
/* Perform the compilation */
|
||||
compiler.compile();
|
||||
}
|
||||
}
|
||||
|
||||
unittest
|
||||
{
|
||||
// TODO: Add tests here for our `simple_<x>.t` tests or put them in DGen, I think here is better
|
||||
// FIXME: Crashes and I think because too fast or actually bad state? Maybe something is not being
|
||||
// cleared, I believe this may be what is happening
|
||||
// ... see issue #88
|
||||
// string[] testFiles = ["source/tlang/testing/simple_functions.t",
|
||||
// "source/tlang/testing/simple_while.t",
|
||||
// "source/tlang/testing/simple_for_loops.t",
|
||||
// "source/tlang/testing/simple_cast.t",
|
||||
// "source/tlang/testing/simple_conditionals.t",
|
||||
// "source/tlang/testing/nested_conditionals.t",
|
||||
// "source/tlang/testing/simple_discard.t"
|
||||
// ];
|
||||
// foreach(string testFile; testFiles)
|
||||
// {
|
||||
// beginCompilation([testFile]);
|
||||
// }
|
||||
}
|
Loading…
Reference in New Issue