Skip to content

Commit

Permalink
Separate compilation: Adding API call to get dependencies of the pack…
Browse files Browse the repository at this point in the history
…ages (transitive closure of imports is too general; causing hundreds of packages to be recompiled on small edits)

git-svn-id: https://openmodelica.org/svn/OpenModelica/trunk@16533 f25d12d1-65f4-0310-ae8a-bbce733d8d8e
  • Loading branch information
sjoelund committed Jul 1, 2013
1 parent a3ac10e commit 4272192
Show file tree
Hide file tree
Showing 6 changed files with 191 additions and 114 deletions.
93 changes: 0 additions & 93 deletions Compiler/FrontEnd/Dump.mo
Original file line number Diff line number Diff line change
Expand Up @@ -46,8 +46,6 @@ encapsulated package Dump

// public imports
public import Absyn;
public import Interactive;

public type Ident = String;

// protected imports
Expand Down Expand Up @@ -609,97 +607,6 @@ algorithm
end match;
end unparseRestrictionStr;

public function printIstmtStr
"function: printIstmtStr
Prints an interactive statement to a string."
input Interactive.Statements inStatements;
output String strIstmt;
algorithm
strIstmt := matchcontinue (inStatements)
local
Absyn.AlgorithmItem alg;
Absyn.Exp expr;
list<Interactive.Statement> l;
Boolean sc;
String str;

case (Interactive.ISTMTS(interactiveStmtLst = {Interactive.IALG(algItem = alg)}))
equation
str = unparseAlgorithmStr(0, alg);
then
str;

case (Interactive.ISTMTS(interactiveStmtLst = {Interactive.IEXP(exp = expr)}))
equation
str = printExpStr(expr);
then
str;

case (Interactive.ISTMTS(interactiveStmtLst = (Interactive.IALG(algItem = alg) :: l),semicolon = sc))
equation
str = unparseAlgorithmStr(0, alg);
str = str +& "; " +& printIstmtStr(Interactive.ISTMTS(l,sc));
then
str;

case (Interactive.ISTMTS(interactiveStmtLst = (Interactive.IEXP(exp = expr) :: l),semicolon = sc))
equation
str = printExpStr(expr);
str = str +& "; " +& printIstmtStr(Interactive.ISTMTS(l,sc));
then
str;
case (_) then "unknown";
end matchcontinue;
end printIstmtStr;

public function dumpIstmt
"function: dumpIstmt
Dumps an interactive statement to the Print buffer."
input Interactive.Statements inStatements;
algorithm
_ := matchcontinue (inStatements)
local
Absyn.AlgorithmItem alg;
Absyn.Exp expr;
list<Interactive.Statement> l;
Boolean sc;

case (Interactive.ISTMTS(interactiveStmtLst = {Interactive.IALG(algItem = alg)}))
equation
Print.printBuf("IALG(");
printAlgorithmitem(alg);
Print.printBuf(")\n");
then
();

case (Interactive.ISTMTS(interactiveStmtLst = {Interactive.IEXP(exp = expr)}))
equation
Print.printBuf("IEXP(");
printExp(expr);
Print.printBuf(")\n");
then
();

case (Interactive.ISTMTS(interactiveStmtLst = (Interactive.IALG(algItem = alg) :: l),semicolon = sc))
equation
Print.printBuf("IALG(");
printAlgorithmitem(alg);
Print.printBuf(",");
dumpIstmt(Interactive.ISTMTS(l,sc));
then
();
case (Interactive.ISTMTS(interactiveStmtLst = (Interactive.IEXP(exp = expr) :: l),semicolon = sc))
equation
Print.printBuf("IEXP(");
printExp(expr);
Print.printBuf(",");
dumpIstmt(Interactive.ISTMTS(l,sc));
then
();
case (_) then ();
end matchcontinue;
end dumpIstmt;

public function printInfo
"function: printInfo
author: adrpo, 2006-02-05
Expand Down
7 changes: 7 additions & 0 deletions Compiler/FrontEnd/ModelicaBuiltin.mo
Original file line number Diff line number Diff line change
Expand Up @@ -1005,6 +1005,13 @@ annotation(Documentation(info="<html><p>Under construction.</p>
</html>"),preferredView="text");
end generateSeparateCode;

function generateSeparateCodeDependencies
output String [:,:] dependencies;
external "builtin";
annotation(Documentation(info="<html><p>Under construction.</p>
</html>"),preferredView="text");
end generateSeparateCodeDependencies;

function getLinker
output String linker;
external "builtin";
Expand Down
17 changes: 5 additions & 12 deletions Compiler/Main/Main.mo
Original file line number Diff line number Diff line change
Expand Up @@ -232,10 +232,7 @@ algorithm
case (SOME(stmts), NONE(), _, _)
equation
(result, st) = Interactive.evaluate(stmts, inSymbolTable, false);
Debug.fprint(Flags.DUMP, "\n--------------- Parsed expression ---------------\n");
Debug.fcall(Flags.DUMP, Dump.dumpIstmt, stmts);
then
(result, st);
then (result, st);

// Add a class or function to the interactive symbol table.
case (NONE(), SOME(prog), _, Interactive.SYMBOLTABLE(ast = ast, lstVarVal = vars))
Expand All @@ -247,8 +244,7 @@ algorithm
Debug.fcall(Flags.DUMP, Dump.dump, prog);
result = makeClassDefResult(prog) "Return vector of toplevel classnames.";
st = Interactive.setSymbolTableAST(inSymbolTable, prog);
then
(result, st);
then (result, st);

// A parser error occured in parseCommand, display the error message. This
// is handled here instead of in parseCommand, since parseCommand does not
Expand All @@ -259,24 +255,21 @@ algorithm
result = Print.getString();
result = stringAppend(result, "Syntax Error\n");
result = stringAppend(result, Error.printMessagesStr());
then
(result, inSymbolTable);
then (result, inSymbolTable);

// A non-parser error occured, display the error message.
case (_, _, _, _)
equation
true = Util.isSome(inStatements) or Util.isSome(inProgram);
result = Error.printMessagesStr();
then
(result, inSymbolTable);
then (result, inSymbolTable);

else
equation
true = Util.isSome(inStatements) or Util.isSome(inProgram);
_ = setStackOverflowSignal(false);
Error.addMessage(Error.STACK_OVERFLOW, {inCommand});
then
("", inSymbolTable);
then ("", inSymbolTable);

end matchcontinue;
end handleCommand2;
Expand Down
109 changes: 108 additions & 1 deletion Compiler/Script/CevalScript.mo
Original file line number Diff line number Diff line change
Expand Up @@ -86,6 +86,7 @@ protected import ExpressionSimplify;
protected import ExpressionDump;
protected import Flags;
protected import Global;
protected import Graph;
protected import Inst;
protected import InnerOuter;
protected import List;
Expand Down Expand Up @@ -897,7 +898,7 @@ algorithm
Absyn.ComponentRef crefCName;
list<tuple<String,Values.Value>> resultValues;
list<Real> realVals;
list<tuple<String,list<String>>> deps;
list<tuple<String,list<String>>> deps,depstransitive,depstransposed;
Absyn.CodeNode codeNode;
list<Values.Value> cvars,vals2;
list<Absyn.Path> paths;
Expand Down Expand Up @@ -1909,6 +1910,26 @@ algorithm
then
(cache,Values.BOOL(false),st);

case (cache,env,"generateSeparateCodeDependencies",{},(st as Interactive.SYMBOLTABLE(ast = p)),_)
equation
sp = SCodeUtil.translateAbsyn2SCode2(p,false);
names = List.map(sp,SCode.getElementName);
deps = Graph.buildGraph(names,buildDependencyGraph,sp);
depstransitive = Graph.buildGraph(names,buildTransitiveDependencyGraph,deps);
depstransitive = List.sort(depstransitive, compareNumberOfDependencies);
print("Total number of modules: " +& intString(listLength(depstransitive)) +& "\n");
str = stringDelimitList(List.map(depstransitive, transitiveDependencyString), "\n");
print(str +& "\n");
depstransposed = Graph.transposeGraph(Graph.emptyGraph(names),deps,stringEq);
depstransposed = Graph.buildGraph(names,buildTransitiveDependencyGraph,depstransposed);
depstransposed = List.sort(depstransposed, compareNumberOfDependencies);
// str = stringDelimitList(List.map(depstransposed, dependencyString), "\n");
print("(Transposed) Total number of modules: " +& intString(listLength(depstransposed)) +& "\n");
str = stringDelimitList(List.map(depstransposed, transitiveDependencyString), "\n");
print(str +& "\n");
// v = ValuesUtil.makeArray(List.map(files, ValuesUtil.makeString));
then (cache,Values.META_FAIL(),st);

case (cache,env,"generateSeparateCode",{Values.ARRAY(valueLst={})},(st as Interactive.SYMBOLTABLE(ast = p)),_)
equation
sp = SCodeUtil.translateAbsyn2SCode(p);
Expand Down Expand Up @@ -6910,4 +6931,90 @@ algorithm
Values.CODE(Absyn.C_TYPENAME(Absyn.IDENT(str))) := val;
end getTypeNameIdent;

protected function buildDependencyGraph
input String name;
input SCode.Program sp;
output list<String> edges;
algorithm
edges := match (name,sp)
local
list<SCode.Element> elts;
case (_,_)
equation
SCode.CLASS(classDef=SCode.PARTS(elementLst=elts)) = List.getMemberOnTrue(name, sp, SCode.isClassNamed);
(_,_,_,elts,_) = SCode.partitionElements(elts);
then List.map(elts, importDepenency);
end match;
end buildDependencyGraph;

protected function buildTransitiveDependencyGraph
input String name;
input list<tuple<String,list<String>>> oldgraph;
output list<String> edges;
algorithm
edges := matchcontinue (name,oldgraph)
local
String str;
case (_,_) then Graph.allReachableNodes(({name},{}),oldgraph,stringEq);
else
equation
str = "CevalScript.buildTransitiveDependencyGraph failed: " +& name;
Error.addMessage(Error.INTERNAL_ERROR, {str});
then fail();
end matchcontinue;
end buildTransitiveDependencyGraph;

protected function importDepenency
input SCode.Element simp;
output String name;
algorithm
name := match simp
local
Absyn.Import imp;
Absyn.Info info;
String str;
case SCode.IMPORT(imp=Absyn.NAMED_IMPORT(path=Absyn.IDENT(name))) then name;
case SCode.IMPORT(imp=Absyn.QUAL_IMPORT(path=Absyn.IDENT(name))) then name;
case SCode.IMPORT(imp=Absyn.UNQUAL_IMPORT(path=Absyn.IDENT(name))) then name;
case SCode.IMPORT(imp=Absyn.GROUP_IMPORT(prefix=Absyn.IDENT(name))) then name;
case SCode.IMPORT(imp=imp,info=info)
equation
str = "CevalScript.importDepenency could not handle:" +& Dump.unparseImportStr(imp);
Error.addSourceMessage(Error.INTERNAL_ERROR,{str},info);
then fail();
end match;
end importDepenency;

protected function compareNumberOfDependencies
input tuple<String,list<String>> node1;
input tuple<String,list<String>> node2;
output Boolean cmp;
protected
list<String> deps1,deps2;
algorithm
(_,deps1) := node1;
(_,deps2) := node2;
cmp := listLength(deps1) >= listLength(deps2);
end compareNumberOfDependencies;

protected function dependencyString
input tuple<String,list<String>> deps;
output String str;
protected
list<String> strs;
algorithm
(str,strs) := deps;
str := str +& " (" +& intString(listLength(strs)) +& "): " +& stringDelimitList(strs, ",");
end dependencyString;

protected function transitiveDependencyString
input tuple<String,list<String>> deps;
output String str;
protected
list<String> strs;
algorithm
(_,strs) := deps;
str := intString(listLength(strs)) +& ": " +& stringDelimitList(strs, ",");
end transitiveDependencyString;

end CevalScript;
43 changes: 42 additions & 1 deletion Compiler/Script/Interactive.mo
Original file line number Diff line number Diff line change
Expand Up @@ -343,7 +343,7 @@ algorithm
case (_, _)
equation
true = Flags.isSet(Flags.SHOW_STATEMENT);
print("Evaluating: " +& Dump.printIstmtStr(ISTMTS({s}, semicolon)) +& "\n");
print("Evaluating: " +& printIstmtStr(ISTMTS({s}, semicolon)) +& "\n");
then
();

Expand Down Expand Up @@ -19372,4 +19372,45 @@ algorithm
end match;
end getBaseClassNameFromExtends;

protected function printIstmtStr "Prints an interactive statement to a string."
input Statements inStatements;
output String strIstmt;
algorithm
strIstmt := matchcontinue (inStatements)
local
Absyn.AlgorithmItem alg;
Absyn.Exp expr;
list<Statement> l;
Boolean sc;
String str;

case (ISTMTS(interactiveStmtLst = {IALG(algItem = alg)}))
equation
str = Dump.unparseAlgorithmStr(0, alg);
then
str;

case (ISTMTS(interactiveStmtLst = {IEXP(exp = expr)}))
equation
str = Dump.printExpStr(expr);
then
str;

case (ISTMTS(interactiveStmtLst = (IALG(algItem = alg) :: l),semicolon = sc))
equation
str = Dump.unparseAlgorithmStr(0, alg);
str = str +& "; " +& printIstmtStr(ISTMTS(l,sc));
then
str;

case (ISTMTS(interactiveStmtLst = (IEXP(exp = expr) :: l),semicolon = sc))
equation
str = Dump.printExpStr(expr);
str = str +& "; " +& printIstmtStr(ISTMTS(l,sc));
then
str;
else "unknown";
end matchcontinue;
end printIstmtStr;

end Interactive;

0 comments on commit 4272192

Please sign in to comment.