From 6d0a8bcca053f59f665132eea656fdecfd35d79e Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Henrik=20Grubbstr=C3=B6m=20=28Grubba=29?=
 <grubba@grubba.org>
Date: Sat, 1 Nov 2014 11:12:31 +0100
Subject: [PATCH] Optimizer [treeopt]: Cleaned up parser somewhat.

---
 bin/mktreeopt.pike | 126 ++++++++++++++++++++++++---------------------
 1 file changed, 67 insertions(+), 59 deletions(-)

diff --git a/bin/mktreeopt.pike b/bin/mktreeopt.pike
index 0d34ed5b27..60d1a6c853 100644
--- a/bin/mktreeopt.pike
+++ b/bin/mktreeopt.pike
@@ -463,6 +463,72 @@ string fix_extras(string s)
   return a * "";
 }
 
+void read_car_cdr(object(node) res, array(string) linepos)
+{
+  int c = data[pos];
+
+  if (c == '(') {
+    string otpos = tpos;
+    pos++;
+
+    tpos = "A"+otpos;
+
+    if (data[pos] == '$') {
+      // FIXME: Support for recurring nodes.
+      // Useful for common subexpression elimination.
+      pos++;
+      int tag = read_int();
+      string ntpos;
+      if (!(ntpos = marks[tag])) {
+	fail("%s:%d: Tag $%d used before being defined.\n",
+	     fname, line, tag);
+      } else if (ntpos == "") {
+	fail("%s:%d: Tag $%d is the root, and can't be used for "
+	     "exact matching.\n",
+	     fname, line, tag);
+      } else {
+	// FIXME: Ought to check that the tag isn't for one of our parents.
+	res->car = res->real_car = sprintf("C%sR(n)", ntpos);
+      }
+      eat_whitespace();
+    } else {
+      res->car = res->real_car = read_node(linepos);
+    }
+
+    expect(',');
+    eat_whitespace();
+
+    tpos = "D"+otpos;
+
+    if (data[pos] == '$') {
+      // FIXME: Support for recurring nodes.
+      // Useful for common subexpression elimination.
+      pos++;
+      int tag = read_int();
+      string ntpos;
+      if (!(ntpos = marks[tag])) {
+	fail("%s:%d: Tag $%d used before being defined.\n",
+	     fname, line, tag);
+      } else if (ntpos == "") {
+	fail("%s:%d: Tag $%d is the root, and can't be used for "
+	     "exact matching.\n",
+	     fname, line, tag);
+      } else {
+	// FIXME: Ought to check that the tag isn't for one of our parents.
+	res->cdr = res->real_cdr = sprintf("C%sR(n)", ntpos);
+      }
+      eat_whitespace();
+    } else {
+      res->cdr = res->real_cdr = read_node(linepos);
+    }
+
+    tpos = otpos;
+    expect(')');
+
+    eat_whitespace();
+  }
+}
+
 object(node) read_node(array(string) linepos)
 {
   object(node) res = node();
@@ -545,66 +611,8 @@ object(node) read_node(array(string) linepos)
       eat_whitespace();
       c = data[pos];
     }
-    if (c == '(') {
-      string otpos = tpos;
-      pos++;
-
-      tpos = "A"+otpos;
-
-      if (data[pos] == '$') {
-	// FIXME: Support for recurring nodes.
-	// Useful for common subexpression elimination.
-	pos++;
-	int tag = read_int();
-	string ntpos;
-	if (!(ntpos = marks[tag])) {
-	  fail("%s:%d: Tag $%d used before being defined.\n",
-	       fname, line, tag);
-	} else if (ntpos == "") {
-	  fail("%s:%d: Tag $%d is the root, and can't be used for "
-	       "exact matching.\n",
-	       fname, line, tag);
-	} else {	
-	  // FIXME: Ought to check that the tag isn't for one of our parents.
-	  res->car = res->real_car = sprintf("C%sR(n)", ntpos);
-	}
-	eat_whitespace();
-      } else {
-	res->car = res->real_car = read_node(linepos);
-      }
-
-      expect(',');
-      eat_whitespace();
 
-      tpos = "D"+otpos;
-
-      if (data[pos] == '$') {
-	// FIXME: Support for recurring nodes.
-	// Useful for common subexpression elimination.
-	pos++;
-	int tag = read_int();
-	string ntpos;
-	if (!(ntpos = marks[tag])) {
-	  fail("%s:%d: Tag $%d used before being defined.\n",
-	       fname, line, tag);
-	} else if (ntpos == "") {
-	  fail("%s:%d: Tag $%d is the root, and can't be used for "
-	       "exact matching.\n",
-	       fname, line, tag);
-	} else {	
-	  // FIXME: Ought to check that the tag isn't for one of our parents.
-	  res->cdr = res->real_cdr = sprintf("C%sR(n)", ntpos);
-	}
-	eat_whitespace();
-      } else {
-	res->cdr = res->real_cdr = read_node(linepos);
-      }
-
-      tpos = otpos;
-      expect(')');
-
-      eat_whitespace();
-    }
+    read_car_cdr(res, linepos);
 
     if ((res->token == "*") && !sizeof(res->extras) &&
 	!res->car && !res->cdr) {
-- 
GitLab