nutils.pas 4.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156
  1. {
  2. $Id$
  3. Copyright (c) 1998-2002 by Florian Klaempfl
  4. Type checking and register allocation for inline nodes
  5. This program is free software; you can redistribute it and/or modify
  6. it under the terms of the GNU General Public License as published by
  7. the Free Software Foundation; either version 2 of the License, or
  8. (at your option) any later version.
  9. This program is distributed in the hope that it will be useful,
  10. but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. GNU General Public License for more details.
  13. You should have received a copy of the GNU General Public License
  14. along with this program; if not, write to the Free Software
  15. Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  16. ****************************************************************************
  17. }
  18. unit nutils;
  19. {$i fpcdefs.inc}
  20. interface
  21. uses
  22. node;
  23. type
  24. { resulttype of functions that process on all nodes in a (sub)tree }
  25. foreachnoderesult = (
  26. { false, continue recursion }
  27. fen_false,
  28. { false, stop recursion }
  29. fen_norecurse_false,
  30. { true, continue recursion }
  31. fen_true,
  32. { true, stop recursion }
  33. fen_norecurse_true
  34. );
  35. foreachnodefunction = function(var n: tnode): foreachnoderesult of object;
  36. staticforeachnodefunction = function(var n: tnode): foreachnoderesult;
  37. function foreachnode(var n: tnode; f: foreachnodefunction): boolean;
  38. function foreachnodestatic(var n: tnode; f: staticforeachnodefunction): boolean;
  39. implementation
  40. uses nflw,nset,ncal;
  41. function foreachnode(var n: tnode; f: foreachnodefunction): boolean;
  42. begin
  43. result := false;
  44. if not assigned(n) then
  45. exit;
  46. case f(n) of
  47. fen_norecurse_false:
  48. exit;
  49. fen_norecurse_true:
  50. begin
  51. result := true;
  52. exit;
  53. end;
  54. fen_true:
  55. result := true;
  56. { result is already false
  57. fen_false:
  58. result := false; }
  59. end;
  60. case n.nodetype of
  61. calln:
  62. result := foreachnode(tcallnode(n).methodpointer,f) or result;
  63. procinlinen:
  64. result := foreachnode(tprocinlinenode(n).inlinetree,f) or result;
  65. ifn, whilerepeatn, forn:
  66. begin
  67. { not in one statement, won't work because of b- }
  68. result := foreachnode(tloopnode(n).t1,f) or result;
  69. result := foreachnode(tloopnode(n).t2,f) or result;
  70. end;
  71. raisen:
  72. result := foreachnode(traisenode(n).frametree,f) or result;
  73. casen:
  74. result := foreachnode(tcasenode(n). elseblock,f) or result;
  75. end;
  76. if n.inheritsfrom(tbinarynode) then
  77. begin
  78. result := foreachnode(tbinarynode(n).right,f) or result;
  79. result := foreachnode(tbinarynode(n).left,f) or result;
  80. end
  81. else if n.inheritsfrom(tunarynode) then
  82. result := foreachnode(tunarynode(n).left,f) or result;
  83. end;
  84. function foreachnodestatic(var n: tnode; f: staticforeachnodefunction): boolean;
  85. begin
  86. result := false;
  87. if not assigned(n) then
  88. exit;
  89. case f(n) of
  90. fen_norecurse_false:
  91. exit;
  92. fen_norecurse_true:
  93. begin
  94. result := true;
  95. exit;
  96. end;
  97. fen_true:
  98. result := true;
  99. { result is already false
  100. fen_false:
  101. result := false; }
  102. end;
  103. case n.nodetype of
  104. calln:
  105. result := foreachnodestatic(tcallnode(n).methodpointer,f) or result;
  106. procinlinen:
  107. result := foreachnodestatic(tprocinlinenode(n).inlinetree,f) or result;
  108. ifn, whilerepeatn, forn:
  109. begin
  110. { not in one statement, won't work because of b- }
  111. result := foreachnodestatic(tloopnode(n).t1,f) or result;
  112. result := foreachnodestatic(tloopnode(n).t2,f) or result;
  113. end;
  114. raisen:
  115. result := foreachnodestatic(traisenode(n).frametree,f) or result;
  116. casen:
  117. result := foreachnodestatic(tcasenode(n). elseblock,f) or result;
  118. end;
  119. if n.inheritsfrom(tbinarynode) then
  120. begin
  121. result := foreachnodestatic(tbinarynode(n).right,f) or result;
  122. result := foreachnodestatic(tbinarynode(n).left,f) or result;
  123. end
  124. else if n.inheritsfrom(tunarynode) then
  125. result := foreachnodestatic(tunarynode(n).left,f) or result;
  126. end;
  127. end.
  128. {
  129. $Log$
  130. Revision 1.1 2003-04-23 12:35:34 florian
  131. * fixed several issues with powerpc
  132. + applied a patch from Jonas for nested function calls (PowerPC only)
  133. * ...
  134. }