Skip to content
This repository was archived by the owner on May 18, 2019. It is now read-only.

Commit 0dbd1e9

Browse files
kbalzereitOpenModelica-Hudson
authored andcommitted
added improved symbolical inline solver
- symbolic inline integration is working by replacing the der operator with the difference quotient(forward/backward) - solver supports explicit and implicit order 1 integration methods enabled by compiler flag --symSolver=(impEuler|expEuler) - added solver methods to the runtime -s symSolver|symSolverSsc without and with step size control
1 parent 69c53b3 commit 0dbd1e9

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

41 files changed

+1307
-621
lines changed

Compiler/BackEnd/BackendDAE.mo

Lines changed: 11 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -111,7 +111,6 @@ uniontype Shared "Data shared for all equation-systems"
111111
Variables externalObjects "External object variables";
112112
Variables aliasVars "Data originating from removed simple equations needed to build
113113
variables' lookup table (in C output).
114-
115114
In that way, double buffering of variables in pre()-buffer, extrapolation
116115
buffer and results caching, etc., is avoided, but in C-code output all the
117116
data about variables' names, comments, units, etc. is preserved as well as
@@ -132,6 +131,13 @@ uniontype Shared "Data shared for all equation-systems"
132131
end SHARED;
133132
end Shared;
134133

134+
uniontype InlineData
135+
record INLINE_DATA
136+
EqSystems inlineSystems;
137+
Variables knownVariables;
138+
end INLINE_DATA;
139+
end InlineData;
140+
135141
uniontype BasePartition
136142
record BASE_PARTITION
137143
.DAE.ClockKind clock;
@@ -170,6 +176,7 @@ uniontype BackendDAEType "BackendDAEType to indicate different types of BackendD
170176
record ARRAYSYSTEM "Type for multi dim equation arrays BackendDAE.DAE" end ARRAYSYSTEM;
171177
record PARAMETERSYSTEM "Type for parameter system BackendDAE.DAE" end PARAMETERSYSTEM;
172178
record INITIALSYSTEM "Type for initial system BackendDAE.DAE" end INITIALSYSTEM;
179+
record INLINESYSTEM "Type for inline system BackendDAE.DAE" end INLINESYSTEM;
173180
end BackendDAEType;
174181

175182
//
@@ -262,9 +269,8 @@ uniontype VarKind "variable kind"
262269
record OPT_LOOP_INPUT
263270
.DAE.ComponentRef replaceExp;
264271
end OPT_LOOP_INPUT;
265-
record ALG_STATE "algebraic state"
266-
VarKind oldKind;
267-
end ALG_STATE;
272+
record ALG_STATE end ALG_STATE; // algebraic state used by inline solver
273+
record ALG_STATE_OLD end ALG_STATE_OLD; // algebraic state old value used by inline solver
268274
record DAE_RESIDUAL_VAR end DAE_RESIDUAL_VAR; // variable kind used for DAEmode
269275
end VarKind;
270276

@@ -715,7 +721,7 @@ public constant String functionDerivativeNamePrefix = "$funDER";
715721

716722
public constant String optimizationMayerTermName = "$OMC$objectMayerTerm";
717723
public constant String optimizationLagrangeTermName = "$OMC$objectLagrangeTerm";
718-
public constant String symEulerDT = "__OMC_DT";
724+
public constant String symSolverDT = "__OMC_DT";
719725

720726
type FullJacobian = Option<list<tuple<Integer, Integer, Equation>>>;
721727

Compiler/BackEnd/BackendDAECreate.mo

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -158,7 +158,8 @@ algorithm
158158
extObjCls,
159159
BackendDAE.SIMULATION(),
160160
symjacs,inExtraInfo,
161-
BackendDAEUtil.emptyPartitionsInfo()));
161+
BackendDAEUtil.emptyPartitionsInfo()
162+
));
162163
BackendDAEUtil.checkBackendDAEWithErrorMsg(outBackendDAE);
163164
varSize := BackendVariable.varsSize(vars_1);
164165
eqnSize := BackendDAEUtil.equationSize(eqnarr);

Compiler/BackEnd/BackendDAEOptimize.mo

Lines changed: 0 additions & 138 deletions
Original file line numberDiff line numberDiff line change
@@ -5171,144 +5171,6 @@ algorithm
51715171

51725172
end simplifyLoops_SplitFactors;
51735173

5174-
5175-
// =============================================================================
5176-
// section for symEuler
5177-
//
5178-
// replace der(x) with difference quotient
5179-
// --> implicit euler
5180-
//
5181-
// after removeSimpliEquation
5182-
// before tearing
5183-
// ToDo: not add to initial equation
5184-
// author: Vitalij Ruge
5185-
// =============================================================================
5186-
5187-
public function symEuler
5188-
input BackendDAE.BackendDAE inDAE;
5189-
output BackendDAE.BackendDAE outDAE;
5190-
algorithm
5191-
outDAE := if Flags.getConfigBool(Flags.SYM_EULER) then symEulerWork(inDAE, true) else inDAE;
5192-
end symEuler;
5193-
5194-
protected function symEulerWork
5195-
input BackendDAE.BackendDAE inDAE;
5196-
input Boolean b " true => add, false => remove euler equation";
5197-
output BackendDAE.BackendDAE outDAE;
5198-
protected
5199-
list<BackendDAE.EqSystem> osystlst = {};
5200-
BackendDAE.EqSystem syst_;
5201-
BackendDAE.Shared shared;
5202-
BackendDAE.Var tmpv;
5203-
DAE.ComponentRef cref;
5204-
algorithm
5205-
// make dt
5206-
cref := ComponentReference.makeCrefIdent(BackendDAE.symEulerDT, DAE.T_REAL_DEFAULT, {});
5207-
tmpv := BackendVariable.makeVar(cref);
5208-
//tmpv := BackendVariable.setVarKind(tmpv, BackendDAE.PARAM());
5209-
tmpv := BackendVariable.setBindExp(tmpv, SOME(DAE.RCONST(0.0)));
5210-
shared := BackendVariable.addGlobalKnownVarDAE(tmpv, inDAE.shared);
5211-
5212-
for syst in inDAE.eqs loop
5213-
(syst_, shared) := symEulerUpdateSyst(syst, b, shared);
5214-
osystlst := syst_ :: osystlst;
5215-
end for;
5216-
5217-
outDAE := BackendDAE.DAE(osystlst, shared);
5218-
//BackendDump.bltdump("BackendDAEOptimize.removeSymEulerEquation", outDAE);
5219-
end symEulerWork;
5220-
5221-
protected function symEulerUpdateSyst
5222-
input BackendDAE.EqSystem iSyst;
5223-
input Boolean b;
5224-
input BackendDAE.Shared shared;
5225-
output BackendDAE.EqSystem oSyst;
5226-
output BackendDAE.Shared oShared = shared;
5227-
protected
5228-
array<Option<BackendDAE.Equation>> equOptArr;
5229-
Option<BackendDAE.Equation> oeqn;
5230-
BackendDAE.Equation eqn;
5231-
BackendDAE.Variables vars;
5232-
BackendDAE.EquationArray eqns;
5233-
Integer n;
5234-
list<DAE.ComponentRef> crlst;
5235-
5236-
algorithm
5237-
oSyst := match iSyst
5238-
local
5239-
BackendDAE.EqSystem syst;
5240-
case syst as BackendDAE.EQSYSTEM(orderedVars=vars, orderedEqs=eqns)
5241-
algorithm
5242-
BackendDAE.EQUATION_ARRAY(equOptArr=equOptArr) := eqns;
5243-
n := arrayLength(equOptArr);
5244-
crlst := {};
5245-
for i in 1:n loop
5246-
oeqn := arrayGet(equOptArr, i);
5247-
if isSome(oeqn) then
5248-
SOME(eqn) := oeqn;
5249-
(eqn, (_,crlst)) := BackendEquation.traverseExpsOfEquation(eqn, symEulerUpdateEqn, (b,crlst));
5250-
arrayUpdate(equOptArr, i, SOME(eqn));
5251-
end if;
5252-
end for;
5253-
// states -> vars
5254-
vars := symEulerState(vars, crlst, b);
5255-
syst.orderedVars := vars;
5256-
syst.orderedEqs := eqns;
5257-
then BackendDAEUtil.clearEqSyst(syst);
5258-
end match;
5259-
end symEulerUpdateSyst;
5260-
5261-
protected function symEulerState
5262-
input BackendDAE.Variables vars;
5263-
input list<DAE.ComponentRef> crlst;
5264-
input Boolean b;
5265-
output BackendDAE.Variables ovars = vars;
5266-
5267-
protected
5268-
Integer idx;
5269-
BackendDAE.VarKind kind, oldKind;
5270-
algorithm
5271-
for cref in crlst loop
5272-
(_, idx) := BackendVariable.getVar2(cref, ovars);
5273-
oldKind := BackendVariable.getVarKindForVar(idx,ovars);
5274-
if b then
5275-
kind := BackendDAE.ALG_STATE(oldKind);
5276-
else
5277-
BackendDAE.ALG_STATE(kind) := oldKind;
5278-
end if;
5279-
ovars := BackendVariable.setVarKindForVar(idx, kind, ovars);
5280-
end for;
5281-
end symEulerState;
5282-
5283-
protected function symEulerUpdateEqn
5284-
input DAE.Exp inExp;
5285-
input tuple<Boolean, list<DAE.ComponentRef>> inTpl;
5286-
output DAE.Exp outExp;
5287-
output tuple<Boolean, list<DAE.ComponentRef>> outTpl;
5288-
algorithm
5289-
(outExp, outTpl) := Expression.traverseExpBottomUp(inExp, symEulerUpdateDer, inTpl);
5290-
end symEulerUpdateEqn;
5291-
5292-
protected function symEulerUpdateDer
5293-
input DAE.Exp inExp;
5294-
input tuple<Boolean, list<DAE.ComponentRef>> inTpl;
5295-
output DAE.Exp outExp;
5296-
output tuple<Boolean, list<DAE.ComponentRef>> outTpl;
5297-
algorithm
5298-
(outExp, outTpl) := match (inTpl, inExp)
5299-
local DAE.Exp exp; DAE.Type tp; list<DAE.ComponentRef> cr_lst; DAE.ComponentRef cr;
5300-
5301-
case ((true,cr_lst), DAE.CALL(path=Absyn.IDENT(name="der"), expLst={exp as DAE.CREF(ty=tp, componentRef = cr)}))
5302-
then (Expression.makePureBuiltinCall("$_DF$DER", {exp}, tp), (true,List.unionElt(cr,cr_lst)));
5303-
5304-
case ((false,cr_lst), DAE.CALL(path=Absyn.IDENT(name="$_DF$DER"), expLst={exp as DAE.CREF(ty=tp, componentRef = cr)}))
5305-
then (Expression.makePureBuiltinCall("der", {exp}, tp),(false, List.unionElt(cr,cr_lst)));
5306-
5307-
else (inExp, inTpl);
5308-
end match;
5309-
end symEulerUpdateDer;
5310-
5311-
53125174
// =============================================================================
53135175
// section for introduceDerAlias
53145176
//

Compiler/BackEnd/BackendDAEUtil.mo

Lines changed: 26 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -104,6 +104,7 @@ import ResolveLoops;
104104
import SCode;
105105
import Sorting;
106106
import StateMachineFeatures;
107+
import SymbolicImplicitSolver;
107108
import SymbolicJacobian;
108109
import SynchronousFeatures;
109110
import System;
@@ -486,6 +487,15 @@ algorithm
486487
outSystem := BackendDAE.EQSYSTEM(vars, eqns, m, mt, matching, inSystem.stateSets, inSystem.partitionKind, removedEqs);
487488
end copyEqSystem;
488489

490+
public function copyEqSystems
491+
input BackendDAE.EqSystems inSystems;
492+
output BackendDAE.EqSystems outSystems = {};
493+
algorithm
494+
for e in inSystems loop
495+
outSystems := copyEqSystem(e) :: outSystems;
496+
end for;
497+
end copyEqSystems;
498+
489499
public function mergeEqSystems
490500
input BackendDAE.EqSystem System1;
491501
input output BackendDAE.EqSystem System2;
@@ -1305,7 +1315,7 @@ protected
13051315
BackendDAE.Variables v;
13061316
algorithm
13071317
BackendDAE.EQSYSTEM(orderedVars = v,m=SOME(m)) := syst;
1308-
if Flags.getConfigBool(Flags.SYM_EULER) then
1318+
if (Flags.getConfigEnum(Flags.SYM_SOLVER) > 0) then
13091319
(_,statevarindx_lst) := BackendVariable.getAllAlgStateVarIndexFromVariables(v);
13101320
else
13111321
(_,statevarindx_lst) := BackendVariable.getAllStateVarIndexFromVariables(v);
@@ -1675,7 +1685,11 @@ algorithm
16751685
case syst as BackendDAE.EQSYSTEM( orderedEqs=ordererdEqs, orderedVars=v,
16761686
matching=BackendDAE.MATCHING(ass1=ass1, ass2=ass2) )
16771687
algorithm
1678-
(_, statevarindx_lst) := BackendVariable.getAllStateVarIndexFromVariables(v);
1688+
if (Flags.getConfigEnum(Flags.SYM_SOLVER) > 0) then
1689+
(_,statevarindx_lst) := BackendVariable.getAllAlgStateVarIndexFromVariables(v);
1690+
else
1691+
(_,statevarindx_lst) := BackendVariable.getAllStateVarIndexFromVariables(v);
1692+
end if;
16791693
indx_lst_v := BackendVariable.getVarIndexFromVariables(iVars, v);
16801694

16811695
indx_lst_v := listAppend(indx_lst_v, statevarindx_lst) "overestimate";
@@ -2981,6 +2995,9 @@ algorithm
29812995
case (BackendDAE.VAR(varKind = BackendDAE.VARIABLE())::rest,i::irest,_,_)
29822996
guard not AvlSetInt.hasKey(vars, i)
29832997
then incidenceRowExp1(rest,irest,AvlSetInt.add(vars, i),diffindex);
2998+
case (BackendDAE.VAR(varKind = BackendDAE.ALG_STATE())::rest,i::irest,_,_)
2999+
guard not AvlSetInt.hasKey(vars, i)
3000+
then incidenceRowExp1(rest,irest,AvlSetInt.add(vars, i),diffindex);
29843001
case (BackendDAE.VAR(varKind = BackendDAE.DISCRETE())::rest,i::irest,_,_)
29853002
guard not AvlSetInt.hasKey(vars, i)
29863003
then incidenceRowExp1(rest,irest,AvlSetInt.add(vars, i),diffindex);
@@ -6770,6 +6787,7 @@ public function getSolvedSystem "Run the equation system pipeline."
67706787
input Option<list<String>> strPostOptModules = NONE();
67716788
output BackendDAE.BackendDAE outSimDAE;
67726789
output BackendDAE.BackendDAE outInitDAE;
6790+
output Option<BackendDAE.InlineData > outInlineData;
67736791
output Boolean outUseHomotopy "true if homotopy(...) is used during initialization";
67746792
output Option<BackendDAE.BackendDAE> outInitDAE_lambda0;
67756793
output list<BackendDAE.Equation> outRemovedInitialEquationLst;
@@ -6781,6 +6799,7 @@ protected
67816799
list<tuple<BackendDAEFunc.optimizationModule, String>> postOptModules;
67826800
tuple<BackendDAEFunc.StructurallySingularSystemHandlerFunc, String, BackendDAEFunc.stateDeselectionFunc, String> daeHandler;
67836801
tuple<BackendDAEFunc.matchingAlgorithmFunc, String> matchingAlgorithm;
6802+
BackendDAE.InlineData inlineData;
67846803
algorithm
67856804
preOptModules := getPreOptModules(strPreOptModules);
67866805
postOptModules := getPostOptModules(strPostOptModules);
@@ -6833,6 +6852,9 @@ algorithm
68336852
simDAE := BackendDAEOptimize.addInitialStmtsToAlgorithms(simDAE);
68346853
simDAE := Initialization.removeInitializationStuff(simDAE);
68356854

6855+
// generate inline solver
6856+
outInlineData := SymbolicImplicitSolver.symSolver(simDAE);
6857+
68366858
// post-optimization phase
68376859
outSimDAE := postOptimizeDAE(simDAE, postOptModules, matchingAlgorithm, daeHandler);
68386860

@@ -7398,7 +7420,6 @@ protected function allPostOptimizationModules
73987420
(BackendDAEOptimize.inlineFunctionInLoops, "forceInlineFunctionInLoops"), // before simplifyComplexFunction
73997421
(BackendDAEOptimize.simplifyComplexFunction, "simplifyComplexFunction"),
74007422
(ExpressionSolve.solveSimpleEquations, "solveSimpleEquations"),
7401-
(BackendDAEOptimize.symEuler, "symEuler"),
74027423
(ResolveLoops.reshuffling_post, "reshufflePost"),
74037424
(DynamicOptimization.reduceDynamicOptimization, "reduceDynamicOptimization"), // before tearing
74047425
(Tearing.tearingSystem, "tearingSystem"),
@@ -7573,10 +7594,6 @@ algorithm
75737594
enabledModules := deprecatedDebugFlag(Flags.ADD_SCALED_VARS, enabledModules, "addScaledVars_states", "postOptModules+");
75747595
enabledModules := deprecatedDebugFlag(Flags.ADD_SCALED_VARS_INPUT, enabledModules, "addScaledVars_inputs", "postOptModules+");
75757596

7576-
if Flags.getConfigBool(Flags.SYM_EULER) then
7577-
enabledModules := "symEuler"::enabledModules;
7578-
end if;
7579-
75807597
if Flags.getConfigInt(Flags.SIMPLIFY_LOOPS) > 0 then
75817598
enabledModules := "simplifyLoops"::enabledModules;
75827599
end if;
@@ -8346,7 +8363,8 @@ algorithm
83468363
backendDAEType,
83478364
{},
83488365
ei,
8349-
emptyPartitionsInfo());
8366+
emptyPartitionsInfo()
8367+
);
83508368
end createEmptyShared;
83518369

83528370
public function emptyPartitionsInfo

Compiler/BackEnd/BackendDump.mo

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -253,6 +253,9 @@ end printClassAttributes;
253253

254254
public function printShared "This function dumps the BackendDAE.Shared representation to stdout."
255255
input BackendDAE.Shared inShared;
256+
protected
257+
BackendDAE.EqSystems eqS;
258+
BackendDAE.InlineData inlineData;
256259
algorithm
257260
print("\nBackendDAEType: ");
258261
printBackendDAEType(inShared.backendDAEType);
@@ -279,6 +282,7 @@ algorithm
279282
if Flags.isSet(Flags.DUMP_FUNCTIONS) then
280283
DAEDump.dumpFunctionTree(inShared.functionTree, "Functions");
281284
end if;
285+
282286
end printShared;
283287

284288
public function printBasePartitions
@@ -351,6 +355,7 @@ algorithm
351355
case (BackendDAE.ARRAYSYSTEM()) then "multidim equation arrays";
352356
case (BackendDAE.PARAMETERSYSTEM()) then "parameter system";
353357
case (BackendDAE.INITIALSYSTEM()) then "initialization";
358+
case (BackendDAE.INLINESYSTEM()) then "inline system";
354359
end match;
355360
end printBackendDAEType2String;
356361

@@ -2406,6 +2411,7 @@ algorithm
24062411
case BackendDAE.OPT_TGRID() then "OPT_TGRID";
24072412
case BackendDAE.OPT_LOOP_INPUT() then "OPT_LOOP_INPUT";
24082413
case BackendDAE.ALG_STATE() then "ALG_STATE";
2414+
case BackendDAE.ALG_STATE_OLD() then "ALG_STATE_OLD";
24092415
end match;
24102416
end kindString;
24112417

Compiler/BackEnd/BackendEquation.mo

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -649,7 +649,7 @@ algorithm
649649
end traverseExpsOfEquationListList_WithStop;
650650

651651
public function traverseExpsOfEquation<T> "author: Frenkel TUD 2010-11
652-
Traverses all expressions of a equation.
652+
Traverses all expressions of an equation.
653653
It is possible to change the equation."
654654
input BackendDAE.Equation inEquation;
655655
input FuncExpType inFunc;

Compiler/BackEnd/BackendVariable.mo

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1184,6 +1184,17 @@ algorithm
11841184
end match;
11851185
end isRealOptimizeDerInput;
11861186

1187+
public function isAlgebraicOldState
1188+
"Return true if variable is old algebraic variable for inline integration."
1189+
input BackendDAE.Var inVar;
1190+
output Boolean outBoolean;
1191+
algorithm
1192+
outBoolean := match (inVar)
1193+
case (BackendDAE.VAR(varKind = BackendDAE.ALG_STATE_OLD())) then true;
1194+
else false;
1195+
end match;
1196+
end isAlgebraicOldState;
1197+
11871198
public function hasMayerTermAnno
11881199
"author: Vitalij Ruge
11891200
Return true if variable has isMayer=true annotation"

Compiler/BackEnd/Differentiate.mo

Lines changed: 0 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1651,14 +1651,6 @@ algorithm
16511651
then
16521652
(exp_1, inFuncs);
16531653

1654-
/*der(x)/dt*/
1655-
case ("$_DF$DER",_)
1656-
equation
1657-
(exp_1,_) = differentiateExp(exp, inDiffwrtCref, inInputData,inDiffType,inFuncs, maxIter, expStack);
1658-
exp_2 = Expression.crefExp(ComponentReference.makeCrefIdent(BackendDAE.symEulerDT, DAE.T_REAL_DEFAULT, {}));
1659-
then
1660-
(Expression.expDiv(exp_1,exp_2), inFuncs);
1661-
16621654
end match;
16631655
end differentiateCallExp1Arg;
16641656

0 commit comments

Comments
 (0)