mirror of
https://gitlab.com/freepascal.org/fpc/source.git
synced 2025-04-12 17:09:35 +02:00
* check for more controll flow statements before doing loop unrolling
git-svn-id: trunk@39083 -
This commit is contained in:
parent
308e439d5d
commit
8f472d5212
1
.gitattributes
vendored
1
.gitattributes
vendored
@ -13755,6 +13755,7 @@ tests/test/tunit1.pp svneol=native#text/plain
|
||||
tests/test/tunit2.pp svneol=native#text/plain
|
||||
tests/test/tunit3.pp svneol=native#text/plain
|
||||
tests/test/tunroll1.pp svneol=native#text/plain
|
||||
tests/test/tunroll2.pp svneol=native#text/pascal
|
||||
tests/test/tutf81.pp svneol=native#text/plain
|
||||
tests/test/tutf82.pp svneol=native#text/plain
|
||||
tests/test/tutf8cpl.pp svneol=native#text/plain
|
||||
|
@ -74,9 +74,9 @@ unit optloop;
|
||||
end;
|
||||
preplaceinfo = ^treplaceinfo;
|
||||
|
||||
function checkbreakcontinue(var n:tnode; arg: pointer): foreachnoderesult;
|
||||
function checkcontrollflowstatements(var n:tnode; arg: pointer): foreachnoderesult;
|
||||
begin
|
||||
if n.nodetype in [breakn,continuen] then
|
||||
if n.nodetype in [breakn,continuen,goton,labeln,exitn,raisen] then
|
||||
result:=fen_norecurse_true
|
||||
else
|
||||
result:=fen_false;
|
||||
@ -105,7 +105,7 @@ unit optloop;
|
||||
unrollblock : tblocknode;
|
||||
getridoffor : boolean;
|
||||
replaceinfo : treplaceinfo;
|
||||
usesbreakcontinue : boolean;
|
||||
hascontrollflowstatements : boolean;
|
||||
begin
|
||||
result:=nil;
|
||||
if (cs_opt_size in current_settings.optimizerswitches) then
|
||||
@ -129,7 +129,7 @@ unit optloop;
|
||||
else
|
||||
counts:=tordconstnode(tfornode(node).t1).value-tordconstnode(tfornode(node).right).value+1;
|
||||
|
||||
usesbreakcontinue:=foreachnodestatic(tfornode(node).t2,@checkbreakcontinue,nil);
|
||||
hascontrollflowstatements:=foreachnodestatic(tfornode(node).t2,@checkcontrollflowstatements,nil);
|
||||
|
||||
{ don't unroll more than we need,
|
||||
|
||||
@ -143,7 +143,7 @@ unit optloop;
|
||||
unrollblock:=internalstatements(unrollstatement);
|
||||
|
||||
{ can we get rid completly of the for ? }
|
||||
getridoffor:=(unrolls=counts) and not(usesbreakcontinue) and
|
||||
getridoffor:=(unrolls=counts) and not(hascontrollflowstatements) and
|
||||
{ TP/Macpas allows assignments to the for-variables, so we cannot get rid of the for }
|
||||
([m_tp7,m_mac]*current_settings.modeswitches=[]);
|
||||
|
||||
|
59
tests/test/tunroll2.pp
Normal file
59
tests/test/tunroll2.pp
Normal file
@ -0,0 +1,59 @@
|
||||
{ %OPT=-Ooloopunroll -Sg }
|
||||
{$mode objfpc}
|
||||
|
||||
uses
|
||||
sysutils;
|
||||
|
||||
var
|
||||
c,i : Integer;
|
||||
|
||||
|
||||
function f1 : Integer;
|
||||
begin
|
||||
for Result:=1 to 2 do
|
||||
if (i=1234) and (Result=2) then
|
||||
Exit;
|
||||
end;
|
||||
|
||||
|
||||
function f2 : Integer;
|
||||
begin
|
||||
for Result:=1 to 2 do
|
||||
if (i=1234) and (Result=2) then
|
||||
Break;
|
||||
end;
|
||||
|
||||
function f3 : Integer;
|
||||
label
|
||||
Stop;
|
||||
begin
|
||||
for Result:=1 to 2 do
|
||||
if (i=1234) and (Result=2) then
|
||||
Goto Stop;
|
||||
Stop:
|
||||
end;
|
||||
|
||||
function f4 : Integer;
|
||||
begin
|
||||
Result:=-1;
|
||||
for c:=1 to 2 do
|
||||
if (i=1234) and (Result=2) then
|
||||
Raise Exception.Create('Test');
|
||||
end;
|
||||
|
||||
begin
|
||||
i:=1234;
|
||||
if f1<>2 then
|
||||
halt(1);
|
||||
if f2<>2 then
|
||||
halt(1);
|
||||
if f3<>2 then
|
||||
halt(1);
|
||||
try
|
||||
f4;
|
||||
except
|
||||
if c<>2 then
|
||||
halt(1);
|
||||
end;
|
||||
writeln('ok');
|
||||
end.
|
Loading…
Reference in New Issue
Block a user