Skip to content

Commit 033f547

Browse files
authored
Improve mergeComponents (#10128)
- Implement merging of variable bindings. - Replace names in modifiers too. Fixes #10126
1 parent 3002440 commit 033f547

File tree

2 files changed

+64
-10
lines changed

2 files changed

+64
-10
lines changed

OMCompiler/Compiler/NFFrontEnd/NFInstUtil.mo

Lines changed: 62 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -332,6 +332,7 @@ public
332332
algorithm
333333
// Merge components.
334334
(elems, name_map) := mergeScalars3(cdef.elementLst);
335+
elems := list(mergeScalarsElement(e, name_map) for e in elems);
335336
cdef.elementLst := elems;
336337
// Replace references to merged components with their new names.
337338
cdef.normalEquationLst := mergeScalarsEql(cdef.normalEquationLst, name_map);
@@ -546,10 +547,6 @@ public
546547
has_submods := not listEmpty(mod.subModLst);
547548

548549
if has_binding then
549-
if stringEmpty(name) then
550-
strl := Dump.printExpStr(Util.getOption(mod.binding)) :: strl;
551-
end if;
552-
553550
strl := "=" :: strl;
554551
end if;
555552

@@ -677,7 +674,7 @@ public
677674
case SCode.Mod.MOD()
678675
algorithm
679676
if isSome(mod.binding) then
680-
names := AbsynUtil.stringListPathReversed(name) :: names;
677+
names := makeModPath(name) :: names;
681678
end if;
682679

683680
for m in mod.subModLst loop
@@ -690,6 +687,18 @@ public
690687
end match;
691688
end getModNames;
692689

690+
function makeModPath
691+
input list<String> name;
692+
output Absyn.Path path;
693+
algorithm
694+
if listEmpty(name) then
695+
// Use $ to indicate an empty path since paths can't be empty.
696+
path := Absyn.Path.IDENT("$");
697+
else
698+
path := AbsynUtil.stringListPathReversed(name);
699+
end if;
700+
end makeModPath;
701+
693702
function mergeMods2
694703
"Helper function to mergeMods, replaces bindings in the given modifier with
695704
the merged bindings."
@@ -706,7 +715,7 @@ public
706715
// If the modifier has a binding expression, look up the new binding
707716
// in the map and replace it.
708717
if isSome(mod.binding) then
709-
new_binding := UnorderedMap.getOrFail(AbsynUtil.stringListPathReversed(name), bindingMap);
718+
new_binding := UnorderedMap.getOrFail(makeModPath(name), bindingMap);
710719
mod.binding := SOME(new_binding);
711720
end if;
712721

@@ -761,7 +770,9 @@ public
761770
algorithm
762771
outMod := match name
763772
case Absyn.Path.IDENT()
764-
then SCodeUtil.lookupModInMod(name.name, mod);
773+
// $ means an empty path, return the given modifier in that case.
774+
// Otherwise look the name up in the modifier.
775+
then if name.name == "$" then mod else SCodeUtil.lookupModInMod(name.name, mod);
765776

766777
case Absyn.Path.QUALIFIED()
767778
algorithm
@@ -771,6 +782,27 @@ public
771782
end match;
772783
end lookupMod;
773784

785+
function mergeScalarsElement
786+
input output SCode.Element element;
787+
input UnorderedMap<String, Absyn.ComponentRef> nameMap;
788+
algorithm
789+
() := match element
790+
case SCode.Element.EXTENDS()
791+
algorithm
792+
element.modifications := mergeScalarsMod(element.modifications, nameMap);
793+
then
794+
();
795+
796+
case SCode.Element.COMPONENT()
797+
algorithm
798+
element.modifications := mergeScalarsMod(element.modifications, nameMap);
799+
then
800+
();
801+
802+
else ();
803+
end match;
804+
end mergeScalarsElement;
805+
774806
function mergeScalarsEql
775807
"Updates the names of merged components in a list of equations."
776808
input output list<SCode.Equation> eql;
@@ -798,6 +830,29 @@ public
798830
end match;
799831
end mergeScalarsEq;
800832

833+
function mergeScalarsMod
834+
input output SCode.Mod mod;
835+
input UnorderedMap<String, Absyn.ComponentRef> nameMap;
836+
algorithm
837+
() := match mod
838+
case SCode.Mod.MOD()
839+
algorithm
840+
mod.binding := Util.applyOption(mod.binding, function mergeScalarsExps(nameMap = nameMap));
841+
mod.subModLst := list(mergeScalarsSubMod(m, nameMap) for m in mod.subModLst);
842+
then
843+
();
844+
845+
else ();
846+
end match;
847+
end mergeScalarsMod;
848+
849+
function mergeScalarsSubMod
850+
input output SCode.SubMod mod;
851+
input UnorderedMap<String, Absyn.ComponentRef> nameMap;
852+
algorithm
853+
mod.mod := mergeScalarsMod(mod.mod, nameMap);
854+
end mergeScalarsSubMod;
855+
801856
function mergeScalarsExps
802857
"Updates the names of merged components in an expression."
803858
input output Absyn.Exp exp;

testsuite/flattening/modelica/scodeinst/MergeComponents8.mo

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -24,12 +24,11 @@ end MergeComponents8;
2424

2525
// Result:
2626
// class MergeComponents8
27-
// parameter Real n1 = 1.0;
28-
// parameter Real n2 = 2.0;
2927
// Real[2] $A1.x;
3028
// Real[2] $A1.y;
3129
// Real[2] $A1.u;
32-
// parameter Real[2] $A1.p = {n1, n2};
30+
// parameter Real[2] $A1.p = {$Real2[1], $Real2[2]};
31+
// parameter Real[2] $Real2 = {1.0, 2.0};
3332
// equation
3433
// for $i1 in 1:2 loop
3534
// der($A1[$i1].x) = (-$A1[$i1].p * $A1[$i1].x) + $A1[$i1].u;

0 commit comments

Comments
 (0)