Linux GNU 11.4.0 Code Coverage Report


Directory: ./
Coverage: low: ≥ 0% medium: ≥ 75.0% high: ≥ 90.0%
Coverage Exec / Excl / Total
Lines: 76.8% 86 / 0 / 112
Functions: -% 0 / 1 / 1
Branches: 64.5% 71 / 0 / 110

OMCompiler/Compiler/NFFrontEnd/NFAttributes.mo
Line Branch Exec Source
1 /*
2 * This file is part of OpenModelica.
3 *
4 * Copyright (c) 1998-2026, Open Source Modelica Consortium (OSMC),
5 * c/o Linköpings universitet, Department of Computer and Information Science,
6 * SE-58183 Linköping, Sweden.
7 *
8 * All rights reserved.
9 *
10 * THIS PROGRAM IS PROVIDED UNDER THE TERMS OF AGPL VERSION 3 LICENSE OR
11 * THIS OSMC PUBLIC LICENSE (OSMC-PL) VERSION 1.8.
12 * ANY USE, REPRODUCTION OR DISTRIBUTION OF THIS PROGRAM CONSTITUTES
13 * RECIPIENT'S ACCEPTANCE OF THE OSMC PUBLIC LICENSE OR THE GNU AGPL
14 * VERSION 3, ACCORDING TO RECIPIENTS CHOICE.
15 *
16 * The OpenModelica software and the OSMC (Open Source Modelica Consortium)
17 * Public License (OSMC-PL) are obtained from OSMC, either from the above
18 * address, from the URLs:
19 * http://www.openmodelica.org or
20 * https://github.com/OpenModelica/ or
21 * http://www.ida.liu.se/projects/OpenModelica,
22 * and in the OpenModelica distribution.
23 *
24 * GNU AGPL version 3 is obtained from:
25 * https://www.gnu.org/licenses/licenses.html#GPL
26 *
27 * This program is distributed WITHOUT ANY WARRANTY; without
28 * even the implied warranty of MERCHANTABILITY or FITNESS
29 * FOR A PARTICULAR PURPOSE, EXCEPT AS EXPRESSLY SET FORTH
30 * IN THE BY RECIPIENT SELECTED SUBSIDIARY LICENSE CONDITIONS OF OSMC-PL.
31 *
32 * See the full OSMC Public License conditions for more details.
33 *
34 */
35
36 encapsulated uniontype NFAttributes
37
38 import InstContext = NFInstContext;
39 import NFInstNode.InstNode;
40 import NFPrefixes.*;
41 import SCode;
42 import Restriction = NFRestriction;
43
44 protected
45 import Absyn;
46 import Class = NFClass;
47 import DAE;
48 import IOStream;
49 import Prefixes = NFPrefixes;
50 import SCodeUtil;
51
52 import Attributes = NFAttributes;
53
54 public
55 constant Attributes DEFAULT_ATTR =
56 ATTRIBUTES(
57 ConnectorType.NON_CONNECTOR,
58 Parallelism.NON_PARALLEL,
59 Variability.CONTINUOUS,
60 Direction.NONE,
61 InnerOuter.NOT_INNER_OUTER,
62 false,
63 false,
64 Replaceable.NOT_REPLACEABLE(),
65 false
66 );
67
68 constant Attributes INPUT_ATTR =
69 ATTRIBUTES(
70 ConnectorType.NON_CONNECTOR,
71 Parallelism.NON_PARALLEL,
72 Variability.CONTINUOUS,
73 Direction.INPUT,
74 InnerOuter.NOT_INNER_OUTER,
75 false,
76 false,
77 Replaceable.NOT_REPLACEABLE(),
78 false
79 );
80
81 constant Attributes OUTPUT_ATTR =
82 ATTRIBUTES(
83 ConnectorType.NON_CONNECTOR,
84 Parallelism.NON_PARALLEL,
85 Variability.CONTINUOUS,
86 Direction.OUTPUT,
87 InnerOuter.NOT_INNER_OUTER,
88 false,
89 false,
90 Replaceable.NOT_REPLACEABLE(),
91 false
92 );
93
94 constant Attributes CONSTANT_ATTR =
95 ATTRIBUTES(
96 ConnectorType.NON_CONNECTOR,
97 Parallelism.NON_PARALLEL,
98 Variability.CONSTANT,
99 Direction.NONE,
100 InnerOuter.NOT_INNER_OUTER,
101 false,
102 false,
103 Replaceable.NOT_REPLACEABLE(),
104 false
105 );
106
107 constant Attributes IMPL_DISCRETE_ATTR =
108 ATTRIBUTES(
109 ConnectorType.NON_CONNECTOR,
110 Parallelism.NON_PARALLEL,
111 Variability.IMPLICITLY_DISCRETE,
112 Direction.NONE,
113 InnerOuter.NOT_INNER_OUTER,
114 false,
115 false,
116 Replaceable.NOT_REPLACEABLE(),
117 false
118 );
119
120 constant Attributes AUGMENTED_ATTR =
121 ATTRIBUTES(
122 ConnectorType.AUGMENTED,
123 Parallelism.NON_PARALLEL,
124 Variability.CONTINUOUS,
125 Direction.NONE,
126 InnerOuter.NOT_INNER_OUTER,
127 false,
128 false,
129 Replaceable.NOT_REPLACEABLE(),
130 false
131 );
132
133
134 record ATTRIBUTES
135 ConnectorType.Type connectorType;
136 Parallelism parallelism;
137 Variability variability;
138 Direction direction;
139 InnerOuter innerOuter;
140 Boolean isFinal;
141 Boolean isRedeclare;
142 Replaceable isReplaceable;
143 Boolean isResizable;
144 end ATTRIBUTES;
145
146 function fromSCode
147 input SCode.Attributes compAttr;
148 input SCode.Prefixes compPrefs;
149 output Attributes attributes;
150 protected
151 ConnectorType.Type cty;
152 Parallelism par;
153 Variability var;
154 Direction dir;
155 InnerOuter io;
156 Boolean fin, redecl;
157 Replaceable repl;
158 algorithm
159 attributes := match (compAttr, compPrefs)
160 case (SCode.Attributes.ATTR(
161 connectorType = SCode.ConnectorType.POTENTIAL(),
162 parallelism = SCode.Parallelism.NON_PARALLEL(),
163 variability = SCode.Variability.VAR(),
164 direction = Absyn.Direction.BIDIR()),
165 SCode.Prefixes.PREFIXES(
166 redeclarePrefix = SCode.Redeclare.NOT_REDECLARE(),
167 finalPrefix = SCode.Final.NOT_FINAL(),
168 innerOuter = Absyn.InnerOuter.NOT_INNER_OUTER(),
169 replaceablePrefix = SCode.Replaceable.NOT_REPLACEABLE()))
170 then DEFAULT_ATTR;
171
172 else
173 algorithm
174 347352 cty := ConnectorType.fromSCode(compAttr.connectorType);
175 347352 par := Prefixes.parallelismFromSCode(compAttr.parallelism);
176 347352 var := Prefixes.variabilityFromSCode(compAttr.variability);
177 347352 dir := Prefixes.directionFromSCode(compAttr.direction);
178 347352 io := Prefixes.innerOuterFromSCode(compPrefs.innerOuter);
179 347352 fin := SCodeUtil.finalBool(compPrefs.finalPrefix);
180 347352 redecl := SCodeUtil.redeclareBool(compPrefs.redeclarePrefix);
181 repl := Replaceable.NOT_REPLACEABLE();
182
4/4
✓ Branch 0 taken 341792 times.
✓ Branch 1 taken 5560 times.
✓ Branch 2 taken 332670 times.
✓ Branch 3 taken 14682 times.
1021814 then
183 Attributes.ATTRIBUTES(cty, par, var, dir, io, fin, redecl, repl, false);
184 end match;
185 end fromSCode;
186
187 function fromDerivedSCode
188 input SCode.Attributes scodeAttr;
189 output Attributes attributes;
190 protected
191 ConnectorType.Type cty;
192 Variability var;
193 Direction dir;
194 algorithm
195 attributes := match scodeAttr
196 case SCode.Attributes.ATTR(
197 connectorType = SCode.ConnectorType.POTENTIAL(),
198 variability = SCode.Variability.VAR(),
199 direction = Absyn.Direction.BIDIR())
200 then DEFAULT_ATTR;
201
202 else
203 algorithm
204 1104 cty := ConnectorType.fromSCode(scodeAttr.connectorType);
205 1104 var := Prefixes.variabilityFromSCode(scodeAttr.variability);
206 1104 dir := Prefixes.directionFromSCode(scodeAttr.direction);
207 1104 then
208 ATTRIBUTES(cty, Parallelism.NON_PARALLEL,
209 var, dir, InnerOuter.NOT_INNER_OUTER, false, false, Replaceable.NOT_REPLACEABLE(), false);
210
211 end match;
212 end fromDerivedSCode;
213
214 function mergeComponentAttributes
215 input Attributes outerAttr;
216 input Attributes innerAttr;
217 input InstNode node;
218 input Restriction parentRestriction;
219 output Attributes attr;
220 protected
221 ConnectorType.Type cty;
222 Parallelism par;
223 Variability var;
224 Direction dir;
225 Boolean fin, redecl, resize;
226 Replaceable repl;
227 algorithm
228
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 956641 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
956641 if referenceEq(outerAttr, DEFAULT_ATTR) and innerAttr.connectorType == 0 then
229 attr := innerAttr;
230 elseif referenceEq(innerAttr, DEFAULT_ATTR) then
231 609087 cty := ConnectorType.merge(outerAttr.connectorType, innerAttr.connectorType, node);
232 609087 attr := Attributes.ATTRIBUTES(cty, outerAttr.parallelism,
233 outerAttr.variability, outerAttr.direction, innerAttr.innerOuter, outerAttr.isFinal,
234 innerAttr.isRedeclare, innerAttr.isReplaceable, innerAttr.isResizable);
235 else
236 347554 cty := ConnectorType.merge(outerAttr.connectorType, innerAttr.connectorType, node);
237 347554 par := Prefixes.mergeParallelism(outerAttr.parallelism, innerAttr.parallelism, node);
238 347554 var := Prefixes.variabilityMin(outerAttr.variability, innerAttr.variability);
239
240
2/2
✓ Branch 1 taken 70149 times.
✓ Branch 2 taken 277405 times.
347554 if Restriction.isFunction(parentRestriction) then
241 70149 dir := innerAttr.direction;
242 else
243 277405 dir := Prefixes.mergeDirection(outerAttr.direction, innerAttr.direction, node);
244 end if;
245
246
4/4
✓ Branch 0 taken 344810 times.
✓ Branch 1 taken 2743 times.
✓ Branch 2 taken 330392 times.
✓ Branch 3 taken 14418 times.
347553 fin := outerAttr.isFinal or innerAttr.isFinal;
247 347553 redecl := innerAttr.isRedeclare;
248 347553 repl := innerAttr.isReplaceable;
249 347553 resize := innerAttr.isResizable;
250
5/6
✓ Branch 0 taken 347553 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 341993 times.
✓ Branch 3 taken 5560 times.
✓ Branch 4 taken 330392 times.
✓ Branch 5 taken 17161 times.
1367491 attr := Attributes.ATTRIBUTES(cty, par, var, dir, innerAttr.innerOuter, fin, redecl, repl, resize);
251 end if;
252 end mergeComponentAttributes;
253
254 function mergeDerivedAttributes
255 input Attributes outerAttr;
256 input Attributes innerAttr;
257 input InstNode node;
258 output Attributes attr;
259 protected
260 ConnectorType.Type cty;
261 Parallelism par;
262 Variability var;
263 Direction dir;
264 InnerOuter io;
265 Boolean fin, redecl, resize;
266 Replaceable repl;
267 algorithm
268
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 693489 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
693489 if referenceEq(innerAttr, DEFAULT_ATTR) and outerAttr.connectorType == 0 then
269 attr := outerAttr;
270 elseif referenceEq(outerAttr, DEFAULT_ATTR) and innerAttr.connectorType == 0 then
271 attr := innerAttr;
272 else
273
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 70366 times.
70366 Attributes.ATTRIBUTES(cty, par, var, dir, io, fin, redecl, repl, resize) := outerAttr;
274 70366 cty := ConnectorType.merge(cty, innerAttr.connectorType, node, isClass = true);
275 70366 var := Prefixes.variabilityMin(var, innerAttr.variability);
276 70366 dir := Prefixes.mergeDirection(dir, innerAttr.direction, node, allowSame = true);
277
3/6
✓ Branch 0 taken 70365 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 70365 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 70365 times.
✗ Branch 5 not taken.
281460 attr := Attributes.ATTRIBUTES(cty, par, var, dir, innerAttr.innerOuter, fin, redecl, repl, resize);
278 end if;
279 end mergeDerivedAttributes;
280
281 function mergeRedeclaredComponentAttributes
282 input Attributes origAttr;
283 input Attributes redeclAttr;
284 input InstNode node;
285 output Attributes attr;
286 protected
287 ConnectorType.Type cty, rcty, cty_fs, rcty_fs;
288 Parallelism par, rpar;
289 Variability var, rvar;
290 Direction dir, rdir;
291 InnerOuter io, rio;
292 Boolean fin, redecl, resize;
293 Replaceable repl;
294 algorithm
295
1/2
✓ Branch 0 taken 5561 times.
✗ Branch 1 not taken.
5561 if referenceEq(origAttr, DEFAULT_ATTR) then
296 attr := redeclAttr;
297 elseif referenceEq(redeclAttr, DEFAULT_ATTR) then
298 attr := origAttr;
299 else
300
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 5561 times.
5561 Attributes.ATTRIBUTES(cty, par, var, dir, io, _, _, _, _) := origAttr;
301
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 5561 times.
5561 Attributes.ATTRIBUTES(rcty, rpar, rvar, rdir, rio, fin, redecl, repl, resize) := redeclAttr;
302
303 // If no prefix is given for one of these attributes in the redeclaration,
304 // then the one from the original declaration is used. The redeclare is not
305 // allowed to change an existing prefix on the original declaration, except
306 // for the variability which can be lowered (e.g. parameter -> constant) and
307 // final which is always taken from the redeclare (since redeclaring a final
308 // element isn't allowed).
309
310 5561 rcty_fs := intBitAnd(rcty, ConnectorType.FLOW_STREAM_MASK);
311 5561 cty_fs := intBitAnd(cty, ConnectorType.FLOW_STREAM_MASK);
312
2/2
✓ Branch 0 taken 967 times.
✓ Branch 1 taken 4594 times.
5561 if rcty_fs > 0 then
313
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 967 times.
967 if cty_fs > 0 and rcty_fs <> cty_fs then
314 ✗ printRedeclarePrefixError(node, ConnectorType.toString(rcty), ConnectorType.toString(cty));
315 end if;
316 end if;
317
318 5561 cty := intBitOr(rcty, cty_fs);
319
320
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 5561 times.
5561 if rpar <> Parallelism.NON_PARALLEL then
321 ✗ if par <> Parallelism.NON_PARALLEL and par <> rpar then
322 ✗ printRedeclarePrefixError(node, Prefixes.parallelismString(rpar), Prefixes.parallelismString(par));
323 end if;
324
325 par := rpar;
326 end if;
327
328
2/2
✓ Branch 0 taken 481 times.
✓ Branch 1 taken 5080 times.
5561 if rvar <> Variability.CONTINUOUS then
329
2/2
✓ Branch 0 taken 1 time.
✓ Branch 1 taken 480 times.
481 if rvar > var then
330 1 printRedeclarePrefixError(node, Prefixes.variabilityString(rvar), Prefixes.variabilityString(var));
331 end if;
332
333 var := rvar;
334 end if;
335
336
2/2
✓ Branch 0 taken 650 times.
✓ Branch 1 taken 4910 times.
5560 if rdir <> Direction.NONE then
337
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 650 times.
650 if dir <> Direction.NONE and rdir <> dir then
338 ✗ printRedeclarePrefixError(node, Prefixes.directionString(rdir), Prefixes.directionString(dir));
339 end if;
340
341 dir := rdir;
342 end if;
343
344
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 5560 times.
5560 if rio <> InnerOuter.NOT_INNER_OUTER then
345 ✗ if io <> InnerOuter.NOT_INNER_OUTER and rio <> io then
346 ✗ printRedeclarePrefixError(node, Prefixes.innerOuterString(rio), Prefixes.innerOuterString(io));
347 end if;
348
349 io := rio;
350 end if;
351
352
5/6
✓ Branch 0 taken 5560 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 1 time.
✓ Branch 3 taken 5559 times.
✓ Branch 4 taken 4964 times.
✓ Branch 5 taken 596 times.
16085 attr := Attributes.ATTRIBUTES(cty, par, var, dir, io, fin, redecl, repl, resize);
353 end if;
354 end mergeRedeclaredComponentAttributes;
355
356 function mergeRedeclaredClassPrefixes
357 input Class.Prefixes origPrefs;
358 input Class.Prefixes redeclPrefs;
359 input InstNode node;
360 output Class.Prefixes prefs;
361 protected
362 SCode.Encapsulated enc;
363 SCode.Partial par;
364 SCode.Final fin;
365 Absyn.InnerOuter io, rio;
366 SCode.Replaceable repl;
367 algorithm
368
1/2
✓ Branch 0 taken 6439 times.
✗ Branch 1 not taken.
6439 if referenceEq(origPrefs, NFClass.DEFAULT_PREFIXES) then
369 prefs := redeclPrefs;
370 else
371
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6439 times.
6439 Class.Prefixes.PREFIXES(innerOuter = io) := origPrefs;
372
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6439 times.
6439 Class.Prefixes.PREFIXES(enc, par, fin, rio, repl) := redeclPrefs;
373
374 io := match (io, rio)
375 case (Absyn.InnerOuter.NOT_INNER_OUTER(), _) then rio;
376 case (_, Absyn.InnerOuter.NOT_INNER_OUTER()) then io;
377 case (Absyn.InnerOuter.INNER(), Absyn.InnerOuter.INNER()) then io;
378 case (Absyn.InnerOuter.OUTER(), Absyn.InnerOuter.OUTER()) then io;
379 case (Absyn.InnerOuter.INNER_OUTER(), Absyn.InnerOuter.INNER_OUTER()) then io;
380 else
381 algorithm
382 ✗ printRedeclarePrefixError(node,
383 Prefixes.innerOuterString(Prefixes.innerOuterFromSCode(rio)),
384 Prefixes.innerOuterString(Prefixes.innerOuterFromSCode(io)));
385 ✗ then
386 fail();
387 end match;
388
389 6439 prefs := Class.Prefixes.PREFIXES(enc, par, fin, io, repl);
390 end if;
391 end mergeRedeclaredClassPrefixes;
392
393 function printRedeclarePrefixError
394 input InstNode node;
395 input String prefix1;
396 input String prefix2;
397 algorithm
398 2 Error.addSourceMessageAndFail(Error.REDECLARE_MISMATCHED_PREFIX,
399 {prefix1, InstNode.name(node), prefix2}, InstNode.info(node));
400 end printRedeclarePrefixError;
401
402 function checkDeclaredComponentAttributes
403 input output Attributes attr;
404 input Restriction parentRestriction;
405 input InstNode component;
406 algorithm
407 () := match parentRestriction
408 case Restriction.CONNECTOR()
409 algorithm
410 // Components of a connector may not have prefixes 'inner' or 'outer'.
411 46250 assertNotInnerOuter(attr.innerOuter, component, parentRestriction);
412
413
2/2
✓ Branch 0 taken 202 times.
✓ Branch 1 taken 46048 times.
46250 if parentRestriction.isExpandable then
414 // Components of an expandable connector may not have the prefix 'flow'.
415 202 assertNotFlowStream(attr.connectorType, component, parentRestriction);
416
417 // Mark components in expandable connectors as potentially present.
418 202 attr.connectorType := intBitOr(attr.connectorType, ConnectorType.POTENTIALLY_PRESENT);
419 end if;
420 then
421 ();
422
423 case Restriction.RECORD()
424 algorithm
425 // Elements of a record may not have prefixes 'input', 'output', 'inner', 'outer', 'stream', or 'flow'.
426 551956 assertNotInputOutput(attr.direction, component, parentRestriction);
427 551956 assertNotInnerOuter(attr.innerOuter, component, parentRestriction);
428 551956 assertNotFlowStream(attr.connectorType, component, parentRestriction);
429 then
430 ();
431
432 else ();
433 end match;
434 end checkDeclaredComponentAttributes;
435
436 function invalidComponentPrefixError
437 input String prefix;
438 input InstNode node;
439 input Restriction restriction;
440 algorithm
441 ✗ Error.addSourceMessage(Error.INVALID_COMPONENT_PREFIX,
442 {prefix, InstNode.name(node), Restriction.toString(restriction)}, InstNode.info(node));
443 end invalidComponentPrefixError;
444
445 function assertNotInputOutput
446 input Direction dir;
447 input InstNode node;
448 input Restriction restriction;
449 algorithm
450
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 551956 times.
551956 if dir <> Direction.NONE then
451 ✗ invalidComponentPrefixError(Prefixes.directionString(dir), node, restriction);
452 ✗ fail();
453 end if;
454 end assertNotInputOutput;
455
456 function assertNotInnerOuter
457 input InnerOuter io;
458 input InstNode node;
459 input Restriction restriction;
460 algorithm
461
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 598206 times.
598206 if io <> InnerOuter.NOT_INNER_OUTER then
462 ✗ invalidComponentPrefixError(Prefixes.innerOuterString(io), node, restriction);
463 ✗ fail();
464 end if;
465 end assertNotInnerOuter;
466
467 function assertNotFlowStream
468 input ConnectorType.Type cty;
469 input InstNode node;
470 input Restriction restriction;
471 algorithm
472
1/2
✗ Branch 1 not taken.
✓ Branch 2 taken 552158 times.
552158 if ConnectorType.isFlowOrStream(cty) then
473 ✗ invalidComponentPrefixError(ConnectorType.toString(cty), node, restriction);
474 ✗ fail();
475 end if;
476 end assertNotFlowStream;
477
478 function updateComponentConnectorType
479 input output Attributes attributes;
480 input Restriction restriction;
481 input InstContext.Type context;
482 input InstNode component;
483 protected
484 ConnectorType.Type cty = attributes.connectorType;
485 algorithm
486
2/2
✓ Branch 1 taken 77858 times.
✓ Branch 2 taken 878539 times.
956397 if ConnectorType.isConnectorType(cty) then
487
2/2
✓ Branch 1 taken 23914 times.
✓ Branch 2 taken 53944 times.
77858 if Restriction.isConnector(restriction) then
488
4/6
✓ Branch 0 taken 3 times.
✓ Branch 1 taken 23911 times.
✓ Branch 3 taken 3 times.
✗ Branch 4 not taken.
✗ Branch 7 not taken.
✓ Branch 8 taken 3 times.
23914 if attributes.variability < Variability.DISCRETE and not InstContext.inRelaxed(context) and
489 not Class.isBuiltin(InstNode.getClass(component)) then
490 ✗ Error.addSourceMessage(Error.INVALID_CONNECTOR_VARIABILITY,
491 {Prefixes.variabilityString(attributes.variability), InstNode.name(component)}, InstNode.info(component));
492 ✗ fail();
493 end if;
494
495
2/2
✓ Branch 1 taken 41 times.
✓ Branch 2 taken 23873 times.
23914 if Restriction.isExpandableConnector(restriction) then
496 41 cty := ConnectorType.setPresent(cty);
497 else
498 23873 cty := intBitAnd(cty, intBitNot(ConnectorType.EXPANDABLE));
499 end if;
500 else
501 // The connector type might have the connector or expandable bits set
502 // because of a parent node, but they should be unset if the component
503 // itself isn't a connector.
504 53944 cty := intBitAnd(cty,
505 intBitNot(intBitOr(ConnectorType.CONNECTOR, ConnectorType.EXPANDABLE)));
506 end if;
507
508 // Connector elements that are not flow/stream are potentials.
509
2/2
✓ Branch 1 taken 56994 times.
✓ Branch 2 taken 20864 times.
77858 if not ConnectorType.isFlowOrStream(cty) then
510 56994 cty := ConnectorType.setPotential(cty);
511 end if;
512
513
2/2
✓ Branch 0 taken 77857 times.
✓ Branch 1 taken 1 time.
77858 if cty <> attributes.connectorType then
514 77857 attributes.connectorType := cty;
515 end if;
516 elseif ConnectorType.isFlowOrStream(cty) and not InstContext.inRedeclared(context) then
517 // The Modelica specification forbids using stream outside connector
518 // declarations, but has no such restriction for flow. To compromise we
519 // print a warning for both flow and stream.
520 ✗ Error.addStrictMessage(Error.CONNECTOR_PREFIX_OUTSIDE_CONNECTOR,
521 {ConnectorType.toString(cty)}, InstNode.info(component));
522
523 // Remove the erroneous flow/stream prefix and keep going.
524 ✗ attributes.connectorType := ConnectorType.unsetFlowStream(cty);
525 end if;
526 end updateComponentConnectorType;
527
528 function updateClassConnectorType
529 input Restriction res;
530 input output Attributes attrs;
531 algorithm
532
2/2
✓ Branch 1 taken 42 times.
✓ Branch 2 taken 860747 times.
860789 if Restriction.isExpandableConnector(res) then
533 42 attrs.connectorType := ConnectorType.setExpandable(attrs.connectorType);
534 elseif Restriction.isConnector(res) then
535 24926 attrs.connectorType := ConnectorType.setConnector(attrs.connectorType);
536 end if;
537 end updateClassConnectorType;
538
539 function updateVariability
540 "Updates the variability based on the type of the attributes' owner (e.g.
541 Integer is implicitly discrete)."
542 input output Attributes attr;
543 input Class cls;
544 input InstNode clsNode;
545 input InstNode compNode;
546 input InstContext.Type context;
547 protected
548 Variability var = attr.variability;
549 algorithm
550
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 956397 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
956397 if referenceEq(attr, DEFAULT_ATTR) and InstNode.isDiscreteClass(clsNode) then
551 attr := NFAttributes.IMPL_DISCRETE_ATTR;
552 elseif var == Variability.CONTINUOUS and InstNode.isDiscreteClass(clsNode) then
553 19164 attr.variability := Variability.IMPLICITLY_DISCRETE;
554 elseif var < Variability.CONTINUOUS and InstContext.inFunction(context) and
555 attr.direction <> Direction.NONE and
556 SCodeUtil.isEmptyMod(InstNode.getAnnotation("__OpenModelica_functionVariability", compNode)) then
557 // Variability prefixes on function parameters has no semantic meaning,
558 // remove them so we don't have to worry about accidentally evaluating
559 // e.g. an input declared as constant/parameter.
560 7557 attr.variability := Variability.CONTINUOUS;
561 elseif var == Variability.PARAMETER and not Flags.isSet(Flags.NF_SCALARIZE)
562 and Util.getOptionOrDefault(SCodeUtil.lookupBooleanAnnotationMod(InstNode.getAnnotation("__OpenModelica_resizable", compNode)), false) then
563 3 attr.variability := Variability.NON_STRUCTURAL_PARAMETER;
564 attr.isResizable := true;
565 end if;
566 end updateVariability;
567
568 function setConnectorType
569 input ConnectorType.Type cty;
570 input output Attributes attr;
571 algorithm
572 ✗ attr.connectorType := cty;
573 end setConnectorType;
574
575 function setVariability
576 input Variability var;
577 input output Attributes attr;
578 algorithm
579 ✗ attr.variability := var;
580 end setVariability;
581
582 function setDirection
583 input Direction dir;
584 input output Attributes attr;
585 algorithm
586 ✗ attr.direction := dir;
587 end setDirection;
588
589 function setInnerOuter
590 input InnerOuter io;
591 input output Attributes attr;
592 algorithm
593 ✗ attr.innerOuter := io;
594 end setInnerOuter;
595
596 function setFinal
597 input Boolean fin;
598 input output Attributes attr;
599 algorithm
600 ✗ attr.isFinal := fin;
601 end setFinal;
602
603 function setRedeclare
604 input Boolean redecl;
605 input output Attributes attr;
606 algorithm
607 ✗ attr.isRedeclare := redecl;
608 end setRedeclare;
609
610 function setReplaceable
611 input Replaceable repl;
612 input output Attributes attr;
613 algorithm
614 ✗ attr.isReplaceable := repl;
615 end setReplaceable;
616
617 function toDAE
618 input Attributes ina;
619 input Visibility vis;
620 output DAE.Attributes outa;
621 algorithm
622 95638 outa := DAE.ATTR(
623 ConnectorType.toDAE(ina.connectorType),
624 parallelismToSCode(ina.parallelism),
625 variabilityToSCode(ina.variability),
626 directionToAbsyn(ina.direction),
627 innerOuterToAbsyn(ina.innerOuter),
628 visibilityToSCode(vis)
629 );
630 end toDAE;
631
632 function toString
633 input Attributes attr;
634 input Type ty;
635 output String str;
636 algorithm
637
3/4
✓ Branch 0 taken 1110 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 1118 times.
✗ Branch 3 not taken.
3346 str := (if attr.isRedeclare then "redeclare " else "") +
638 (if attr.isFinal then "final " else "") +
639 Prefixes.unparseInnerOuter(attr.innerOuter) +
640 Prefixes.unparseReplaceable(attr.isReplaceable) +
641 Prefixes.unparseParallelism(attr.parallelism) +
642 ConnectorType.unparse(attr.connectorType) +
643 Prefixes.unparseVariability(attr.variability, ty) +
644 Prefixes.unparseDirection(attr.direction);
645 end toString;
646
647 function toFlatStream
648 input Attributes attr;
649 input Type ty;
650 input output IOStream.IOStream s;
651 input Boolean isTopLevel = true;
652 algorithm
653 955 s := IOStream.append(s, Prefixes.unparseVariability(attr.variability, ty));
654
655
2/2
✓ Branch 0 taken 788 times.
✓ Branch 1 taken 167 times.
955 if isTopLevel then
656 167 s := IOStream.append(s, Prefixes.unparseDirection(attr.direction));
657 end if;
658 end toFlatStream;
659
660 annotation(__OpenModelica_Interface="nf_frontend");
661 end NFAttributes;
662
663