From 62d54389c847f71c55f93c711d7969a89e1d4cfe Mon Sep 17 00:00:00 2001 From: florian Date: Mon, 7 May 2007 19:14:21 +0000 Subject: [PATCH] + life dfa for if, label and goto git-svn-id: trunk@7297 - --- compiler/optdfa.pas | 88 +++++++++++++++++++++++++++++-------------- compiler/optutils.pas | 35 +++++++++++++++-- 2 files changed, 92 insertions(+), 31 deletions(-) diff --git a/compiler/optdfa.pas b/compiler/optdfa.pas index 2c94ec9f67..a20f6e0396 100644 --- a/compiler/optdfa.pas +++ b/compiler/optdfa.pas @@ -20,7 +20,7 @@ **************************************************************************** } -{ $define DEBUG_DFA} +{$define DEBUG_DFA} { this unit implements routines to perform dfa } unit optdfa; @@ -154,7 +154,6 @@ unit optdfa; var l : TDFASet; begin - n.allocoptinfo; if assigned(n.successor) then begin { @@ -187,6 +186,9 @@ unit optdfa; if node=nil then exit; + { ensure we've already optinfo set } + node.allocoptinfo; + if nf_processing in node.flags then exit; include(node.flags,nf_processing); @@ -202,7 +204,6 @@ unit optdfa; calclife(node); if lnf_testatbegin in twhilerepeatnode(node).loopflags then begin - { first, do things as usual, get life information from the successor } node.allocoptinfo; if not(assigned(node.optinfo^.def)) and not(assigned(node.optinfo^.use)) then @@ -228,40 +229,71 @@ unit optdfa; CreateInfo(twhilerepeatnode(node).right); end; end; + assignn: + begin + if not(assigned(node.optinfo^.def)) and + not(assigned(node.optinfo^.use)) then + begin + dfainfo.use:=@node.optinfo^.use; + dfainfo.def:=@node.optinfo^.def; + dfainfo.map:=map; + foreachnodestatic(pm_postprocess,node,@AddDefUse,@dfainfo); + end; + calclife(node); + end; statementn: begin - { actually an expression doing something? } - case tstatementnode(node).statement.nodetype of - assignn: - begin - node.allocoptinfo; - if not(assigned(node.optinfo^.def)) and - not(assigned(node.optinfo^.use)) then - begin - dfainfo.use:=@node.optinfo^.use; - dfainfo.def:=@node.optinfo^.def; - dfainfo.map:=map; - foreachnodestatic(pm_postprocess,tstatementnode(node).left,@AddDefUse,@dfainfo); - end; - calclife(node); - end; - else - begin - { nested statement } - CreateInfo(tstatementnode(node).statement); - { inherit info } - node.allocoptinfo; - node.optinfo^.life:=tstatementnode(node).statement.optinfo^.life; - end; - end; + { nested statement } + CreateInfo(tstatementnode(node).statement); + { inherit info } + node.optinfo^.life:=tstatementnode(node).statement.optinfo^.life; end; blockn: begin CreateInfo(tblocknode(node).statements); - node.allocoptinfo; if assigned(tblocknode(node).statements) then node.optinfo^.life:=tblocknode(node).statements.optinfo^.life; end; + ifn: + begin + { get information from cond. expression } + if not(assigned(node.optinfo^.def)) and + not(assigned(node.optinfo^.use)) then + begin + dfainfo.use:=@node.optinfo^.use; + dfainfo.def:=@node.optinfo^.def; + dfainfo.map:=map; + foreachnodestatic(pm_postprocess,tifnode(node).left,@AddDefUse,@dfainfo); + end; + { create life info for left and right node } + CreateInfo(tifnode(node).right); + CreateInfo(tifnode(node).t1); + + { ensure that we don't remove life info } + l:=node.optinfo^.life; + + { get life info from then branch } + if assigned(tifnode(node).right) then + DFASetIncludeSet(l,tifnode(node).right.optinfo^.life); + { get life info from else branch } + if assigned(tifnode(node).t1) then + DFASetIncludeSet(l,tifnode(node).t1.optinfo^.life) + else + if assigned(node.successor) then + DFASetIncludeSet(l,node.successor.optinfo^.life); + { add use info from cond. expression } + DFASetIncludeSet(l,tifnode(node).optinfo^.use); + { finally, update the life info of the node } + UpdateLifeInfo(node,l); + end; + goton: + begin + calclife(node); + end; + labeln: + begin + calclife(node); + end; else internalerror(2007050502); end; diff --git a/compiler/optutils.pas b/compiler/optutils.pas index 6f3d1e4b57..0838cbb1f5 100644 --- a/compiler/optutils.pas +++ b/compiler/optutils.pas @@ -210,6 +210,36 @@ unit optutils; Breakstack.Delete(Breakstack.Count-1); Continuestack.Delete(Continuestack.Count-1); end; + ifn: + begin + result:=p; + DoSet(tifnode(p).right,succ); + DoSet(tifnode(p).t1,succ); + p.successor:=succ; + end; + labeln: + begin + result:=p; + if assigned(tlabelnode(p).left) then + begin + DoSet(tlabelnode(p).left,succ); + p.successor:=tlabelnode(p).left; + end + else + p.successor:=succ; + end; + assignn: + begin + result:=p; + p.successor:=succ; + end; + goton: + begin + result:=p; + if not(assigned(tgotonode(p).labelnode)) then + internalerror(2007050701); + p.successor:=tgotonode(p).labelnode; + end; { exit is actually a jump to some final. code exitn: begin @@ -217,12 +247,11 @@ unit optutils; p.successor:=nil; end; } - ifn, + inlinen, + calln, exitn, withn, casen, - labeln, - goton, tryexceptn, raisen, tryfinallyn,