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

Commit 2e17f15

Browse files
sjoelundOpenModelica-Hudson
authored andcommitted
Handle range special case for reductions
This resolves ticket:4474
1 parent 5ee6abb commit 2e17f15

File tree

2 files changed

+59
-33
lines changed

2 files changed

+59
-33
lines changed

Compiler/Template/CodegenCFunctions.tpl

Lines changed: 58 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -6467,18 +6467,37 @@ template daeExpReduction(Exp exp, Context context, Text &preExp,
64676467
let loopHeadIter = (iterators |> iter as REDUCTIONITER(__) =>
64686468
let identType = expTypeFromExpModelica(iter.exp)
64696469
let arrayType = expTypeFromExpArray(iter.exp)
6470-
let loopVar = '<%iter.id%>_loopVar'
6470+
let iteratorName = contextIteratorName(iter.id, context)
6471+
let loopVar = match iter.exp case RANGE(__) then iteratorName else '<%iter.id%>_loopVar'
6472+
let stepVar = match iter.exp case RANGE(__) then tempDecl(identType,&tmpVarDecls)
6473+
let stopVar = match iter.exp case RANGE(__) then tempDecl(identType,&tmpVarDecls)
64716474
let &guardExpPre = buffer ""
64726475
let &tmpVarDecls += (match identType
64736476
case "modelica_metatype" then 'modelica_metatype <%loopVar%> = 0;<%\n%>'
6474-
else '<%arrayType%> <%loopVar%>;<%\n%>')
6475-
let firstIndex = match identType case "modelica_metatype" then (if isMetaArray(iter.exp) then tempDecl("int",&tmpVarDecls) else "") else tempDecl("int",&tmpVarDecls)
6476-
let rangeExp = daeExp(iter.exp,context,&rangeExpPre,&tmpVarDecls, &auxFunction)
6477+
else (match iter.exp case RANGE(__) then "" else '<%arrayType%> <%loopVar%>;<%\n%>'))
6478+
let firstIndex = match iter.exp case RANGE(__) then tempDecl(identType,&tmpVarDecls) else (match identType case "modelica_metatype" then (if isMetaArray(iter.exp) then tempDecl("int",&tmpVarDecls) else "") else tempDecl("int",&tmpVarDecls))
6479+
let rangeExpStep = (match iter.exp case RANGE(step=NONE()) then "1 /* Range step-value */" case RANGE(step=SOME(step)) then '<%daeExp(step,context,&rangeExpPre,&tmpVarDecls, &auxFunction)%> /* Range step-value */' else "")
6480+
let rangeExpStop = (match iter.exp case RANGE(__) then '<%daeExp(stop,context,&rangeExpPre,&tmpVarDecls, &auxFunction)%> /* Range stop-value */' else "")
6481+
let rangeExp = (match iter.exp case RANGE(__) then '<%daeExp(start,context,&rangeExpPre,&tmpVarDecls, &auxFunction)%> /* Range start-value */' else daeExp(iter.exp,context,&rangeExpPre,&tmpVarDecls, &auxFunction))
6482+
let &rangeExpPre += if rangeExpStep then '<%stepVar%> = <%rangeExpStep%>;<%\n%>'
6483+
let &rangeExpPre += if rangeExpStop then '<%stopVar%> = <%rangeExpStop%>;<%\n%>'
64776484
let &rangeExpPre += '<%loopVar%> = <%rangeExp%>;<%\n%>'
6478-
let &rangeExpPre += if firstIndex then '<%firstIndex%> = 1;<%\n%>'
6485+
let &rangeExpPre += if rangeExpStop then
6486+
<<
6487+
if (<%stepVar%> == 0) {
6488+
FILE_INFO info = omc_dummyFileInfo;
6489+
omc_assert(threadData, info, "Range with a step of zero.");
6490+
}<%\n%>
6491+
>>
6492+
let &tmpVarDecls += match iter.exp case RANGE(__) then 'modelica_integer <%iter.id%>_length;<%\n%>'
6493+
let &rangeExpPre += match iter.exp case RANGE(__) then '<%firstIndex%> = <%iteratorName%> /* Remember the range start-value */;<%\n%>' else (if firstIndex then '<%firstIndex%> = 1;<%\n%>')
64796494
let guardCond = (match iter.guardExp case SOME(grd) then daeExp(grd, context, &guardExpPre, &tmpVarDecls, &auxFunction) else "")
6480-
let iteratorName = contextIteratorName(iter.id, context)
6495+
let &rangeExpPre += match iter.exp case RANGE(__) then '<%iteratorName%> = (<%rangeExp%>)-<%stepVar%>;<%\n%>' /* We pre-increment the counter, so subtract the step for the first variable for ranges */
64816496
let &tmpVarDecls += '<%identType%> <%iteratorName%>;<%\n%>'
6497+
let &rangeExpPre += if rangeExpStop then
6498+
<<
6499+
<%iter.id%>_length = ((<%stopVar%>-<%firstIndex%>)/<%stepVar%>)+1;
6500+
>>
64826501
let guardExp =
64836502
<<
64846503
<%&guardExpPre%>
@@ -6525,34 +6544,46 @@ template daeExpReduction(Exp exp, Context context, Text &preExp,
65256544
)
65266545
)
65276546
else
6528-
let addr = match iter.ty
6529-
case T_ARRAY(ty=T_COMPLEX(complexClassType = record_state)) then
6530-
let rec_name = '<%underscorePath(ClassInf.getStateName(record_state))%>'
6531-
'*((<%rec_name%>*)generic_array_element_addr1(&<%loopVar%>, sizeof(<%rec_name%>), <%firstIndex%>++))'
6532-
else
6533-
'*(<%arrayType%>_element_addr1(&<%loopVar%>, 1, <%firstIndex%>++))'
6534-
(if stringEq(guardCond,"") then
6535-
<<
6536-
if(<%firstIndex%> <= size_of_dimension_base_array(<%loopVar%>, 1)) {
6537-
<%iteratorName%> = <%addr%>;
6538-
<%endLoop%>--;
6539-
}
6540-
>>
6541-
else
6542-
<<
6543-
while(<%firstIndex%> <= size_of_dimension_base_array(<%loopVar%>, 1)) {
6544-
<%iteratorName%> = <%addr%>;
6545-
<%guardExp%>
6546-
}
6547-
>>)))
6547+
( /* Not metatype */
6548+
match iter.exp
6549+
case RANGE(__) then
6550+
<<
6551+
<%if stringEq(guardCond,"") then "if" else "while"%> (<%stepVar%> > 0 ? <%iteratorName%>+<%stepVar%> <= <%stopVar%> : <%iteratorName%>+<%stepVar%> >= <%stopVar%>) {
6552+
<%iteratorName%> += <%stepVar%>;
6553+
<%if stringEq(guardCond,"") then '<%endLoop%>--;' else guardExp%>
6554+
}
6555+
>>
6556+
else /* Not a range; allocate a big array... */
6557+
let addr = match iter.ty
6558+
case T_ARRAY(ty=T_COMPLEX(complexClassType = record_state)) then
6559+
let rec_name = '<%underscorePath(ClassInf.getStateName(record_state))%>'
6560+
'*((<%rec_name%>*)generic_array_element_addr1(&<%loopVar%>, sizeof(<%rec_name%>), <%firstIndex%>++))'
6561+
else
6562+
'*(<%arrayType%>_element_addr1(&<%loopVar%>, 1, <%firstIndex%>++))'
6563+
(if stringEq(guardCond,"") then
6564+
<<
6565+
if(<%firstIndex%> <= size_of_dimension_base_array(<%loopVar%>, 1)) {
6566+
<%iteratorName%> = <%addr%>;
6567+
<%endLoop%>--;
6568+
}
6569+
>>
6570+
else
6571+
<<
6572+
while(<%firstIndex%> <= size_of_dimension_base_array(<%loopVar%>, 1)) {
6573+
<%iteratorName%> = <%addr%>;
6574+
<%guardExp%>
6575+
}
6576+
>>
6577+
)))
6578+
)
65486579
let firstValue = (match ri.path
65496580
case IDENT(name="array") then
65506581
let length = tempDecl("int",&tmpVarDecls)
65516582
let &rangeExpPre += '<%length%> = 0;<%\n%>'
65526583
let _ = (iterators |> iter as REDUCTIONITER(__) =>
65536584
let loopVar = '<%iter.id%>_loopVar'
65546585
let identType = expTypeFromExpModelica(iter.exp)
6555-
let &rangeExpPre += '<%length%> = modelica_integer_max(<%length%>,<%match identType case "modelica_metatype" then (if isMetaArray(iter.exp) then 'arrayLength(<%loopVar%>)' else 'listLength(<%loopVar%>)') else 'size_of_dimension_base_array(<%loopVar%>, 1)'%>);<%\n%>'
6586+
let &rangeExpPre += '<%length%> = modelica_integer_max(<%length%>,<%match identType case "modelica_metatype" then (if isMetaArray(iter.exp) then 'arrayLength(<%loopVar%>)' else 'listLength(<%loopVar%>)') else match iter.exp case RANGE(__) then '<%iter.id%>_length' else 'size_of_dimension_base_array(<%loopVar%>, 1)'%>);<%\n%>'
65566587
"")
65576588
<<
65586589
<%arrIndex%> = 1;

Compiler/Util/ExpandableArray.mo

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -231,12 +231,7 @@ algorithm
231231
elseif capacity == 1 then
232232
listT := {Util.getOption(data[1])};
233233
else
234-
listT := {};
235-
for i in capacity:-1:1 loop
236-
if isSome(data[i]) then
237-
listT := Util.getOption(data[i])::listT;
238-
end if;
239-
end for;
234+
listT := list(Util.getOption(data[i]) for i guard isSome(data[i]) in 1:capacity);
240235
end if;
241236
end toList;
242237

0 commit comments

Comments
 (0)