Skip to content

Commit 2bab289

Browse files
authored
Cherry pick fixes for 1.25.2 (#14235)
* Avoid dangerous Element->getModel()->isConnector() (#14180) - Fix missing checks for if an elements model exists before trying to use it by adding `Element::isConnector` and using that instead of `Element->getModel()->isConnector()`. * Fix URL for OMSimulator documentation in OMEdit (#14175) * Fix copyClass (#14222) - Rewrite `AbsynUtil.pathStripSamePrefix` to return an option, to be able to handle the case where the whole path is a prefix. - Fix NFApi.updateMovedPath/Cref to skip prefixing the path when the whole qualified path is a prefix.
1 parent bd9cab7 commit 2bab289

File tree

11 files changed

+77
-34
lines changed

11 files changed

+77
-34
lines changed

OMCompiler/Compiler/FrontEnd/AbsynUtil.mo

Lines changed: 14 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1539,19 +1539,28 @@ public function pathStripSamePrefix
15391539
"strips the same prefix paths and returns the stripped path. e.g pathStripSamePrefix(P.M.A, P.M.B) => A"
15401540
input Absyn.Path inPath1;
15411541
input Absyn.Path inPath2;
1542-
output Absyn.Path outPath = inPath1;
1542+
output Option<Absyn.Path> outPath;
15431543
protected
1544-
Absyn.Path path2 = inPath2;
1544+
Absyn.Path path1 = inPath1, path2 = inPath2;
15451545
algorithm
1546-
while pathFirstIdent(outPath) == pathFirstIdent(path2) loop
1547-
outPath := pathRest(outPath);
1546+
while pathFirstIdent(path1) == pathFirstIdent(path2) loop
1547+
if pathIsIdent(path1) then
1548+
// The whole first path is a prefix of the second.
1549+
outPath := NONE();
1550+
return;
1551+
end if;
1552+
1553+
path1 := pathRest(path1);
15481554

15491555
if pathIsIdent(path2) then
1550-
return;
1556+
// The whole second path is a prefix of the first.
1557+
break;
15511558
end if;
15521559

15531560
path2 := pathRest(path2);
15541561
end while;
1562+
1563+
outPath := SOME(path1);
15551564
end pathStripSamePrefix;
15561565

15571566
public function pathPrefix

OMCompiler/Compiler/Script/Interactive.mo

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5451,7 +5451,7 @@ algorithm
54515451
modification := InteractiveUtil.makeModifierFromArgs(bindingExp, modifier, info);
54525452
(io, redecl, attr) := getDefaultPrefixes(program, typeName);
54535453

5454-
ty_path := AbsynUtil.pathStripSamePrefix(typeName, classPath);
5454+
SOME(ty_path) := AbsynUtil.pathStripSamePrefix(typeName, classPath);
54555455

54565456
if AbsynUtil.pathContains(classPath, AbsynUtil.pathFirstIdent(ty_path)) then
54575457
// Keep the full type name if the first identifier of the stripped name

OMCompiler/Compiler/Script/NFApi.mo

Lines changed: 18 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -2724,6 +2724,7 @@ function updateMovedPath
27242724
input MoveEnv env;
27252725
protected
27262726
Absyn.Path qualified_path;
2727+
Option<Absyn.Path> opt_path;
27272728
algorithm
27282729
// Try to look up the qualified path needed to be able to find the name in
27292730
// this scope even if the root class that contains the scope is moved elsewhere.
@@ -2742,10 +2743,16 @@ algorithm
27422743
if AbsynUtil.pathIsQual(qualified_path) then
27432744
// If the path is qualified it needs to be joined with the original path,
27442745
// but we remove any part of the path that's the same as the destination.
2745-
qualified_path := AbsynUtil.pathStripSamePrefix(qualified_path, env.destinationPath);
2746+
opt_path := AbsynUtil.pathStripSamePrefix(qualified_path, env.destinationPath);
27462747

2747-
if AbsynUtil.pathIsQual(qualified_path) then
2748-
path := AbsynUtil.joinPaths(AbsynUtil.pathPrefix(qualified_path), path);
2748+
if isSome(opt_path) then
2749+
SOME(qualified_path) := opt_path;
2750+
2751+
if AbsynUtil.pathIsQual(qualified_path) then
2752+
path := AbsynUtil.joinPaths(AbsynUtil.pathPrefix(qualified_path), path);
2753+
end if;
2754+
else
2755+
fail();
27492756
end if;
27502757
elseif AbsynUtil.pathFirstIdent(qualified_path) == AbsynUtil.pathFirstIdent(env.destinationPath) then
27512758
// Special case, the path refers to the destination package, e.g. moving path A.B.C into A.
@@ -2834,6 +2841,7 @@ function updateMovedCref
28342841
input MoveEnv env;
28352842
protected
28362843
Absyn.Path qualified_path;
2844+
Option<Absyn.Path> opt_path;
28372845
algorithm
28382846
if AbsynUtil.crefIsFullyQualified(cref) or AbsynUtil.crefIsWild(cref) then
28392847
return;
@@ -2856,10 +2864,14 @@ algorithm
28562864
if AbsynUtil.pathIsQual(qualified_path) then
28572865
// If the path is qualified it needs to be joined with the original cref,
28582866
// but we remove any part of the path that's the same as the destination.
2859-
qualified_path := AbsynUtil.pathStripSamePrefix(qualified_path, env.destinationPath);
2867+
opt_path := AbsynUtil.pathStripSamePrefix(qualified_path, env.destinationPath);
2868+
2869+
if isSome(opt_path) then
2870+
SOME(qualified_path) := opt_path;
28602871

2861-
if AbsynUtil.pathIsQual(qualified_path) then
2862-
cref := AbsynUtil.joinCrefs(AbsynUtil.pathToCref(AbsynUtil.pathPrefix(qualified_path)), cref);
2872+
if AbsynUtil.pathIsQual(qualified_path) then
2873+
cref := AbsynUtil.joinCrefs(AbsynUtil.pathToCref(AbsynUtil.pathPrefix(qualified_path)), cref);
2874+
end if;
28632875
end if;
28642876
elseif AbsynUtil.pathFirstIdent(qualified_path) == AbsynUtil.pathFirstIdent(env.destinationPath) then
28652877
// Special case, the cref refers to the destination package, e.g. moving path A.B.C into A.

OMEdit/OMEditLIB/Annotations/LineAnnotation.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1411,7 +1411,7 @@ void LineAnnotation::handleCollidingConnections()
14111411
QList<QGraphicsItem*> items = collidingItems(Qt::IntersectsItemShape);
14121412
for (int i = 0; i < items.size(); ++i) {
14131413
if (Element *pElement = dynamic_cast<Element*>(items.at(i))) {
1414-
if ((pElement->getModel() && pElement->getModel()->isConnector())
1414+
if (pElement->isConnector()
14151415
|| (pElement->getLibraryTreeItem() && (pElement->getLibraryTreeItem()->getOMSConnector() || pElement->getLibraryTreeItem()->getOMSBusConnector()
14161416
|| pElement->getLibraryTreeItem()->getOMSTLMBusConnector()))) {
14171417
mCollidingConnectorElements.append(pElement);

OMEdit/OMEditLIB/Element/Element.cpp

Lines changed: 17 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -401,7 +401,7 @@ QRectF Element::boundingRect() const
401401
} else if (isPort()) {
402402
ExtentAnnotation extent;
403403
if (mpModelComponent) {
404-
if (mpModelComponent->getModel()->isConnector() && (mpGraphicsView->isDiagramView()) && canUseDiagramAnnotation()) {
404+
if (mpModelComponent->isConnector() && (mpGraphicsView->isDiagramView()) && canUseDiagramAnnotation()) {
405405
mpModelComponent->getAnnotation()->getPlacementAnnotation().getTransformation().getExtent();
406406
} else {
407407
mpModelComponent->getAnnotation()->getPlacementAnnotation().getIconTransformation().getExtent();
@@ -557,7 +557,7 @@ ModelInstance::CoordinateSystem Element::getCoordinateSystem() const
557557
{
558558
ModelInstance::CoordinateSystem coordinateSystem;
559559
if (mpModelComponent && mpModel) {
560-
if (mpModelComponent->getModel()->isConnector() && (mpGraphicsView->isDiagramView()) && canUseDiagramAnnotation()) {
560+
if (mpModelComponent->isConnector() && (mpGraphicsView->isDiagramView()) && canUseDiagramAnnotation()) {
561561
coordinateSystem = mpModel->getAnnotation()->getDiagramAnnotation()->mMergedCoordinateSystem;
562562
} else {
563563
coordinateSystem = mpModel->getAnnotation()->getIconAnnotation()->mMergedCoordinateSystem;
@@ -626,7 +626,7 @@ QString Element::getPlacementAnnotation(bool ModelicaSyntax)
626626
placementAnnotationString.append(QString("visible=%1,").arg(mTransformation.getVisible().toQString()));
627627
}
628628
}
629-
if ((mpLibraryTreeItem && mpLibraryTreeItem->isConnector()) || (mpModelComponent && mpModelComponent->getModel()->isConnector())) {
629+
if ((mpLibraryTreeItem && mpLibraryTreeItem->isConnector()) || (mpModelComponent && mpModelComponent->isConnector())) {
630630
if (mpGraphicsView->isIconView()) {
631631
// first get the component from diagram view and get the transformations
632632
Element *pElement = mpGraphicsView->getModelWidget()->getDiagramGraphicsView()->getElementObject(getName());
@@ -692,7 +692,7 @@ QString Element::getOMCPlacementAnnotation(QPointF position)
692692
if (mTransformation.isValid()) {
693693
placementAnnotationString.append(mTransformation.getVisible() ? "true" : "false");
694694
}
695-
if ((mpLibraryTreeItem && mpLibraryTreeItem->isConnector()) || (mpModelComponent && mpModelComponent->getModel()->isConnector())) {
695+
if ((mpLibraryTreeItem && mpLibraryTreeItem->isConnector()) || (mpModelComponent && mpModelComponent->isConnector())) {
696696
if (mpGraphicsView->isIconView()) {
697697
// first get the component from diagram view and get the transformations
698698
Element *pElement;
@@ -746,6 +746,16 @@ QString Element::getTransformationExtent()
746746
return transformationExtent;
747747
}
748748

749+
/*!
750+
* \brief Element::isConnector
751+
* Returns true if the Element class is connector.
752+
* \return
753+
*/
754+
bool Element::isConnector() const
755+
{
756+
return mpModel && mpModel->isConnector();
757+
}
758+
749759
/*!
750760
* \brief Element::isExpandableConnector
751761
* Returns true if the Element class is expandable connector.
@@ -891,7 +901,7 @@ void Element::createClassElements()
891901
foreach (auto pElement, elements) {
892902
if (pElement->isComponent()) {
893903
auto pComponent = dynamic_cast<ModelInstance::Component*>(pElement);
894-
if (pComponent->isPublic() && pComponent->getModel() && pComponent->getModel()->isConnector()) {
904+
if (pComponent->isPublic() && pComponent->isConnector()) {
895905
mElementsList.append(new Element(pComponent, this, getRootParentElement()));
896906
}
897907
}
@@ -1617,11 +1627,11 @@ void Element::createClassShapes()
16171627
// Always use the IconMap here. Only IconMap makes sense for drawing icons of Element.
16181628
if (!(pExtendModel && !pExtendModel->getIconDiagramMapPrimitivesVisible(true))) {
16191629
/* issue #12074
1620-
* Use mpModelComponent->getModel()->isConnector() here instead of mpModel->isConnector()
1630+
* Use mpModelComponent->isConnector() here instead of mpModel->isConnector()
16211631
* So when called for extends we use the top level element restriction.
16221632
* We use the same mpModelComponent for top level and extends elements. See Element constructor above for extends element type.
16231633
*/
1624-
if (mpModelComponent && mpModelComponent->getModel()->isConnector() && mpGraphicsView->isDiagramView() && canUseDiagramAnnotation()) {
1634+
if (mpModelComponent && mpModelComponent->isConnector() && mpGraphicsView->isDiagramView() && canUseDiagramAnnotation()) {
16251635
shapes = mpModel->getAnnotation()->getDiagramAnnotation()->getGraphics();
16261636
} else {
16271637
shapes = mpModel->getAnnotation()->getIconAnnotation()->getGraphics();

OMEdit/OMEditLIB/Element/Element.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -159,6 +159,7 @@ class Element : public QObject, public QGraphicsItem
159159
QString getOMCPlacementAnnotation(QPointF position);
160160
QString getTransformationOrigin();
161161
QString getTransformationExtent();
162+
bool isConnector() const;
162163
bool isExpandableConnector() const;
163164
bool isArray() const;
164165
QStringList getAbsynArrayIndexes() const;

OMEdit/OMEditLIB/MainWindow.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3073,7 +3073,7 @@ void MainWindow::openModelicaDocumentation()
30733073
*/
30743074
void MainWindow::openOMSimulatorUsersGuide()
30753075
{
3076-
QUrl OMSimulatorUsersGuideUrl("https://openmodelica.org/doc/OMSimulator/master/html/");
3076+
QUrl OMSimulatorUsersGuideUrl("https://openmodelica.org/doc/OMSimulator/master/OMSimulator/UsersGuide/html/");
30773077
QDesktopServices::openUrl(OMSimulatorUsersGuideUrl);
30783078
}
30793079

OMEdit/OMEditLIB/Modeling/Commands.cpp

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -234,7 +234,7 @@ void UpdateComponentTransformationsCommand::redoInternal()
234234
{
235235
ModelWidget *pModelWidget = mpComponent->getGraphicsView()->getModelWidget();
236236
if (mMoveConnectorsTogether && pModelWidget->getLibraryTreeItem()->isModelica()
237-
&& (mpComponent->getModel() && mpComponent->getModel()->isConnector())) {
237+
&& mpComponent->isConnector()) {
238238
GraphicsView *pGraphicsView;
239239
if (mpComponent->getGraphicsView()->isIconView()) {
240240
pGraphicsView = pModelWidget->getDiagramGraphicsView();
@@ -274,8 +274,7 @@ void UpdateComponentTransformationsCommand::redoInternal()
274274
void UpdateComponentTransformationsCommand::undo()
275275
{
276276
ModelWidget *pModelWidget = mpComponent->getGraphicsView()->getModelWidget();
277-
if (mMoveConnectorsTogether && pModelWidget->getLibraryTreeItem()->isModelica()
278-
&& (mpComponent->getModel() && mpComponent->getModel()->isConnector())) {
277+
if (mMoveConnectorsTogether && pModelWidget->getLibraryTreeItem()->isModelica() && mpComponent->isConnector()) {
279278
GraphicsView *pGraphicsView;
280279
if (mpComponent->getGraphicsView()->isIconView()) {
281280
pGraphicsView = pModelWidget->getDiagramGraphicsView();

OMEdit/OMEditLIB/Modeling/Model.cpp

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1514,7 +1514,7 @@ namespace ModelInstance
15141514
if (connector.size() == 1) return true;
15151515

15161516
auto elem = model.lookupElement(connector.first().getName(false));
1517-
return elem && elem->getModel() && elem->getModel()->isConnector();
1517+
return elem && elem->isConnector();
15181518
}
15191519

15201520
bool isCompatibleConnectorDirection(const Element &lhs, bool lhsOutside, const Element &rhs, bool rhsOutside)
@@ -2069,6 +2069,16 @@ namespace ModelInstance
20692069
return mpPrefixes ? mpPrefixes.get()->isRedeclare() : false;
20702070
}
20712071

2072+
bool Element::isConnector() const
2073+
{
2074+
return mpModel && mpModel->isConnector();
2075+
}
2076+
2077+
bool Element::isExpandableConnector() const
2078+
{
2079+
return mpModel && mpModel->isExpandableConnector();
2080+
}
2081+
20722082
QString Element::getConnector() const
20732083
{
20742084
return mpPrefixes ? mpPrefixes.get()->getConnector() : "";

OMEdit/OMEditLIB/Modeling/Model.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -694,6 +694,8 @@ namespace ModelInstance
694694
bool isOuter() const;
695695
Replaceable *getReplaceable() const;
696696
bool isRedeclare() const;
697+
bool isConnector() const;
698+
bool isExpandableConnector() const;
697699
QString getConnector() const;
698700
QString getVariability() const;
699701
QString getDirectionPrefix() const;

0 commit comments

Comments
 (0)