tinycc-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Tinycc-devel] simple dead code detection


From: Zdenek Pavlas
Subject: [Tinycc-devel] simple dead code detection
Date: Tue, 19 Jun 2007 20:45:29 +0200
User-agent: Thunderbird 1.5.0.10 (X11/20070301)

Hi,

This is an attempt to remove (some) unnecessary jumps. Hit rates on the test source (i have used tcc itself) are quite high, but the overall savings are well below 2%, since most of the code are not jumps. The overhead to keep track of jumps and labels is relatively high, so I've better made it conditional. I have tested the i386 target and it looks ok. undo_gjmp() for arm and c67 is implemented too and should be ok, but I can't test it.

--
Zdenek Pavlas


Index: arm-gen.c
===================================================================
RCS file: /var/cvs/tinycc/arm-gen.c,v
retrieving revision 1.1.1.1
diff -u -b -B -w -p -r1.1.1.1 arm-gen.c
--- arm-gen.c   15 Jun 2007 14:29:47 -0000      1.1.1.1
+++ arm-gen.c   19 Jun 2007 17:23:58 -0000
@@ -1010,6 +1010,17 @@ int gjmp(int t)
   return r;
 }
 
+#ifdef CONFIG_TCC_DCD
+/* reclaim useless jump */
+void undo_gjmp(int *t)
+{
+    if (*t == ind - 4) {
+        *t = decbranch(*t);
+        ind -= 4;
+    }
+}
+#endif
+
 /* generate a jump to a fixed address */
 void gjmp_addr(int a)
 {
Index: c67-gen.c
===================================================================
RCS file: /var/cvs/tinycc/c67-gen.c,v
retrieving revision 1.1.1.1
diff -u -b -B -w -p -r1.1.1.1 c67-gen.c
--- c67-gen.c   15 Jun 2007 14:29:47 -0000      1.1.1.1
+++ c67-gen.c   19 Jun 2007 17:31:29 -0000
@@ -2044,6 +2044,19 @@ int gjmp(int t)
     return ind1;
 }
 
+#ifdef CONFIG_TCC_DCD
+/* reclaim useless jump */
+void undo_gjmp(int *t)
+{
+    if (*t == ind - 16) {
+        int *p = (int *)(cur_text_section->data + *t);
+        *t = (p[0] >> 7 & 0xffff) |
+             (p[1] >> 7 & 0xffff) << 16;
+        ind -= 16;
+    }
+}
+#endif
+
 /* generate a jump to a fixed address */
 void gjmp_addr(int a)
 {
Index: tcc.c
===================================================================
RCS file: /var/cvs/tinycc/tcc.c,v
retrieving revision 1.2
diff -u -b -B -w -p -r1.2 tcc.c
--- tcc.c       18 Jun 2007 12:49:34 -0000      1.2
+++ tcc.c       19 Jun 2007 17:50:05 -0000
@@ -7152,6 +7152,14 @@ static int is_label(void)
     }
 }
 
+#ifdef CONFIG_TCC_DCD
+static int dead_code;
+#define gjmp(s)      (dead_code = 1, gjmp(s))
+#define gjmp_addr(t) (dead_code = 1, gjmp_addr(t))
+#define gsym(s)      (dead_code = 0, gsym(s))
+#define ind          (dead_code = 0, ind)
+#endif
+
 static void block(int *bsym, int *csym, int *case_sym, int *def_sym, 
                   int case_reg, int is_expr)
 {
@@ -7372,6 +7380,12 @@ static void block(int *bsym, int *csym, 
         if (!case_sym)
             expect("switch");
         /* since a case is like a label, we must skip it with a jmp */
+#ifdef CONFIG_TCC_DCD
+        if (dead_code) { /* 98% */
+            b = 0;
+            undo_gjmp(case_sym); /* 15% */
+        } else
+#endif
         b = gjmp(0);
     next_case:
         next();
@@ -8215,6 +8229,10 @@ static void gen_function(Sym *sym)
     gfunc_prolog(&sym->type);
     rsym = 0;
     block(NULL, NULL, NULL, NULL, 0, 0);
+#ifdef CONFIG_TCC_DCD
+    if (dead_code) /* 34% */
+        undo_gjmp(&rsym); /* 99% */
+#endif
     gsym(rsym);
     gfunc_epilog();
     cur_text_section->data_offset = ind;
Index: i386/i386-gen.c
===================================================================
RCS file: /var/cvs/tinycc/i386/i386-gen.c,v
retrieving revision 1.1.1.1
diff -u -b -B -w -p -r1.1.1.1 i386-gen.c
--- i386/i386-gen.c     15 Jun 2007 14:29:47 -0000      1.1.1.1
+++ i386/i386-gen.c     19 Jun 2007 17:24:30 -0000
@@ -555,6 +555,17 @@ int gjmp(int t)
     return psym(0xe9, t);
 }
 
+#ifdef CONFIG_TCC_DCD
+/* reclaim useless jump */
+void undo_gjmp(int *t)
+{
+    if (*t == ind - 4) {
+        *t = *(int *)(cur_text_section->data + *t);
+        ind -= 5;
+    }
+}
+#endif
+
 /* generate a jump to a fixed address */
 void gjmp_addr(int a)
 {

reply via email to

[Prev in Thread] Current Thread [Next in Thread]