changeset 725:84291c0a9e13

Added member callLevel to class Macro.
author Aziz K?ksal <aziz.koeksal@gmail.com>
date Sat, 02 Feb 2008 14:24:29 +0100
parents 0b8a6e876b6d
children 7917811f8116
files trunk/src/dil/doc/Macro.d
diffstat 1 files changed, 17 insertions(+), 4 deletions(-) [+]
line wrap: on
line diff
--- a/trunk/src/dil/doc/Macro.d	Sat Feb 02 12:39:37 2008 +0100
+++ b/trunk/src/dil/doc/Macro.d	Sat Feb 02 14:24:29 2008 +0100
@@ -12,6 +12,7 @@
 {
   string name; /// The name of the macro.
   string text; /// Substitution text.
+  uint callLevel;  /// Recursive call level.
   this (string name, string text)
   {
     this.name = name;
@@ -130,7 +131,7 @@
   return begin[0 .. end - begin];
 }
 
-char[] expandMacros(MacroTable table, char[] text)
+char[] expandMacros(MacroTable table, char[] text, char[][] args = null)
 {
   char[] result;
   char* p = text.ptr;
@@ -153,7 +154,7 @@
         // Create macro name.
         auto macroName = makeString(idBegin, p);
         // Get arguments.
-        auto args = scanArguments(p, textEnd);
+        auto macroArgs = scanArguments(p, textEnd);
         // TODO: still expand macro if no closing bracket was found?
         if (p == textEnd)
           break; // No closing bracket found.
@@ -163,7 +164,17 @@
 
         auto macro_ = table.search(macroName);
         if (macro_)
-          result ~= expandArguments(macro_.text, args);
+        { // Ignore recursive macro if:
+          if (macro_.callLevel != 0 &&
+               (macroArgs.length == 0 || // Macro has no arguments.
+                args.length && args[0] == macroArgs[0]) // arg0 == macroArg0.
+             )
+            continue;
+          macro_.callLevel++;
+          auto expandedText = expandArguments(macro_.text, macroArgs);
+          result ~= expandMacros(table, expandedText, macroArgs);
+          macro_.callLevel--;
+        }
         continue;
       }
     }
@@ -177,6 +188,8 @@
 /// Scans until the closing ')' is found.
 /// Returns [$0, $1, $2 ...].
 char[][] scanArguments(ref char* p, char* textEnd)
+out(args) { assert(args.length != 1); }
+body
 {
   // D specs: "The argument text can contain nested parentheses,
   //           "" or '' strings, comments, or tags."
@@ -279,7 +292,7 @@
 
       if (*p == '+')
       { // $+ = $2 to $n
-        if (args.length > 1)
+        if (args.length > 2)
           result ~= makeString(args[2].ptr, args[0].ptr + args[0].length);
       }
       else