Skip to content

Commit

Permalink
Improved handling of parse error & ambiguity in concrete fragments
Browse files Browse the repository at this point in the history
Closes issue #1091 and issue #1093
  • Loading branch information
PaulKlint committed Jun 21, 2017
1 parent 35bf4f0 commit 396f2c8
Show file tree
Hide file tree
Showing 6 changed files with 75 additions and 33 deletions.
70 changes: 44 additions & 26 deletions src/org/rascalmpl/library/experiments/Compiler/Compile.rsc
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ import Map;
import Set;
import Relation;
import Exception;
import experiments::Compiler::RVM::Interpreter::CompileTimeError;

import lang::rascal::\syntax::Rascal;
//import experiments::Compiler::Rascal2muRascal::ParseModule;
Expand Down Expand Up @@ -138,17 +139,26 @@ tuple[Configuration, RVMModule] compile1(str qualifiedModuleName, PathConfig pcf
return <config, rvmMod>;
}
//if(verbose) println("rascal2rvm: Compiling <moduleLoc>");
start_comp = cpuTime();
muMod = r2mu(M, config, pcfg, reloc=reloc, verbose=verbose, optimize=optimize, enableAsserts=enableAsserts);
rvmMod = mu2rvm(muMod, verbose=verbose, optimize=optimize);
comp_time = (cpuTime() - start_comp)/1000000;
if(verbose) println("Compiling <moduleLoc>: check: <check_time>, compile: <comp_time>, total: <check_time+comp_time> ms");
//if(verbose) println("compile: Writing RVMModule <rvmModuleLoc>");
writeBinaryValueFile(rvmModuleLoc, rvmMod);
return <config, rvmMod>;
try {
//if(verbose) println("rascal2rvm: Compiling <moduleLoc>");
start_comp = cpuTime();
muMod = r2mu(M, config, pcfg, reloc=reloc, verbose=verbose, optimize=optimize, enableAsserts=enableAsserts);
rvmMod = mu2rvm(muMod, verbose=verbose, optimize=optimize);
comp_time = (cpuTime() - start_comp)/1000000;
if(verbose) println("Compiling <moduleLoc>: check: <check_time>, compile: <comp_time>, total: <check_time+comp_time> ms");
//if(verbose) println("compile: Writing RVMModule <rvmModuleLoc>");
writeBinaryValueFile(rvmModuleLoc, rvmMod);
return <config, rvmMod>;
} catch e: CompileTimeError(m): {
rvmMod = errorRVMModule("<M.header.name>", {m}, moduleLoc);
try {
writeBinaryValueFile(rvmModuleLoc, rvmMod);
} catch IO(str msg): {
println("CANNOT WRITE ERROR MODULE FOR <M.header.name>: <msg>");
}
return <config, rvmMod>;
}
}

@doc{Compile a Rascal source module (given at a location) to RVM}
Expand Down Expand Up @@ -293,15 +303,14 @@ lang::rascal::\syntax::Rascal::Declaration getMain(lang::rascal::\syntax::Rascal
if(m2: (Module) `<Header h> <Toplevel* pre> <Toplevel tl_main>` := m){
return tl_main.declaration;
}
throw "getMain: cannot match toplevels";
throw InternalCompilerError("getMain: cannot match toplevels", m@\loc);
}

Module removeMain(lang::rascal::\syntax::Rascal::Module m) {
if(m2: (Module) `<Header h> <Toplevel* pre> <Toplevel mn>` := m){
return (Module) `<Header h> <Toplevel* pre>`;
}
throw "removeMain: no main found";
return m;
throw InternalCompilerError("removeMain: no main found", m@\loc);
}

Configuration noPreviousConfig = newConfiguration(pathConfig());
Expand Down Expand Up @@ -348,18 +357,27 @@ tuple[Configuration, RVMModule] compile1Incremental(str qualifiedModuleName, boo
}
rvmModuleLoc = RVMModuleWriteLoc(qualifiedModuleName, pcfg);
if(verbose) println("rascal2rvm: Compiling <moduleLoc>");
start_comp = cpuTime();
muMod = r2mu(M, config, pcfg, verbose=verbose, optimize=optimize, enableAsserts=enableAsserts); // never a reloc
rvmMod = mu2rvm(muMod, verbose=verbose, optimize=optimize);
comp_time = (cpuTime() - start_comp)/1000000;
if(verbose) println("Compiling <moduleLoc>: check: <check_time>, compile: <comp_time>, total: <check_time+comp_time> ms");
if(verbose) println("compile: Writing RVMModule <rvmModuleLoc>");
writeBinaryValueFile(rvmModuleLoc, rvmMod);

return <config, rvmMod>;
try {
if(verbose) println("rascal2rvm: Compiling <moduleLoc>");
start_comp = cpuTime();
muMod = r2mu(M, config, pcfg, verbose=verbose, optimize=optimize, enableAsserts=enableAsserts); // never a reloc
rvmMod = mu2rvm(muMod, verbose=verbose, optimize=optimize);
comp_time = (cpuTime() - start_comp)/1000000;
if(verbose) println("Compiling <moduleLoc>: check: <check_time>, compile: <comp_time>, total: <check_time+comp_time> ms");
if(verbose) println("compile: Writing RVMModule <rvmModuleLoc>");
writeBinaryValueFile(rvmModuleLoc, rvmMod);

return <config, rvmMod>;
} catch e: CompileTimeError(m): {
rvmMod = errorRVMModule("<M.header.name>", {m}, moduleLoc);
try {
writeBinaryValueFile(rvmModuleLoc, rvmMod);
} catch IO(str msg): {
println("CANNOT WRITE ERROR MODULE FOR <M.header.name>: <msg>");
}
return <config, rvmMod>;
}
}

RVMModule compileIncremental(str qualifiedModuleName, bool reuseConfig, PathConfig pcfg, bool verbose = false, bool optimize = true, bool enableAsserts=false){
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
module experiments::Compiler::Examples::Tst1

int f(int n, int m) = n * m;
import XXX;

//int fac(int n) = (n <= 1) ? 1 : n * fac(n-1);

value main() { n = f(2,3); return n; }
value main() = 42;
Original file line number Diff line number Diff line change
Expand Up @@ -329,6 +329,12 @@ ITree parseFragment1(IString name, IValue start, IConstructor tree, ISourceLocat
ISourceLocation src = vf.sourceLocation(loc, loc.getOffset() + e.getOffset(), loc.getLength(), loc.getBeginLine() + e.getBeginLine() - 1, loc.getEndLine() + e.getEndLine() - 1, loc.getBeginColumn() + e.getBeginColumn(), loc.getBeginColumn() + e.getEndColumn());
throw RascalRuntimeException.parseError(src, null);
}
catch (Ambiguous e) {
ITree tree1 = e.getTree();
throw RascalRuntimeException.ambiguity(e.getLocation(),
vf.string(SymbolAdapter.toString(TreeAdapter.getType(tree1), false)),
vf.string(TreeAdapter.yield(tree)), null);
}
}

private char[] replaceAntiQuotesByHoles(ITree lit, Map<String, ITree> antiquotes, RascalExecutionContext rex) throws IOException {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@ import String;
import lang::rascal::\syntax::Rascal;
import ParseTree;

import experiments::Compiler::RVM::Interpreter::CompileTimeError;

import experiments::Compiler::muRascal::AST;

import lang::rascal::types::AbstractName;
Expand Down Expand Up @@ -189,8 +191,12 @@ private void translateFunctionDeclaration(FunctionDeclaration fd, node body, lis

leaveFunctionScope();
leaveFunctionDeclaration();

} catch e: {
} catch e: CompileTimeError(m): {
throw e;
} catch Ambiguity(loc src, str stype, str string): {
throw CompileTimeError(error("Ambiguous code", src));
}
catch e: {
throw "EXCEPTION in translateFunctionDeclaration, compiling <fd.signature.name>: <e>";
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@ import Map;
import Set;
import ParseTree;
import util::Reflective;
import Exception;
import experiments::Compiler::RVM::Interpreter::CompileTimeError;

import lang::rascal::\syntax::Rascal;

Expand Down Expand Up @@ -588,7 +590,13 @@ public Tree parseConcrete(e: appl(Production cprod, list[Tree] cargs)){
//println("translateConcrete, fragType = <fragType>");
reifiedFragType = symbolToValue(fragType);
// TODO: getGrammar uses a global variable. Add as parameter to the call stack instead
return parseFragment(getModuleName(), getModuleTags(), reifiedFragType, e, e@\loc, getGrammar());
try {
return parseFragment(getModuleName(), getModuleTags(), reifiedFragType, e, e@\loc, getGrammar());
} catch ParseError(loc src): {
throw CompileTimeError(error("Parse error in concrete fragment or pattern", src));
} catch Ambiguity(loc src, str stype, str string): {
throw CompileTimeError(error("Ambiguity in concrete fragment or pattern (of type <stype>)", src));
}
}
public MuExp translateConcrete(e: appl(Production cprod, list[Tree] cargs)){
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import util::Reflective;
//import util::ValueUI;

import ParseTree;
import experiments::Compiler::RVM::Interpreter::CompileTimeError;

import lang::rascal::\syntax::Rascal;
import experiments::Compiler::muRascal::AST;
Expand Down Expand Up @@ -119,9 +120,12 @@ MuModule r2mu(lang::rascal::\syntax::Rascal::Module M, Configuration config, Pat
if (verbose) println("Parse error in concrete syntax <l>; returning error module");
return errorMuModule(getModuleName(), {error("Parse error in concrete syntax fragment", l)}, M@\loc);
}
catch value e: {
return errorMuModule(getModuleName(), {error("Unexpected compiler exception <e>", M@\loc)}, M@\loc);
catch CompileTimeError(Message m): {
return errorMuModule(getModuleName(), {m}, M@\loc);
}
//catch value e: {
// return errorMuModule(getModuleName(), {error("Unexpected compiler exception <e>", M@\loc)}, M@\loc);
//}
finally {
resetModuleInfo(optimize, enableAsserts);
resetScopeExtraction();
Expand Down

0 comments on commit 396f2c8

Please sign in to comment.