Patchwork tree-ssa-strlen vs. zero-length strings

login
register
mail settings
Submitter Jakub Jelinek
Date Oct. 27, 2011, 7:37 a.m.
Message ID <20111027073742.GI1052@tyan-ft48-01.lab.bos.redhat.com>
Download mbox | patch
Permalink /patch/122077/
State New
Headers show

Comments

Jakub Jelinek - Oct. 27, 2011, 7:37 a.m.
On Wed, Oct 26, 2011 at 10:22:21PM -0700, Ian Lance Taylor wrote:
> I don't think it is possible to trigger this using C because I don't
> think it is possible to have a zero-length STRING_CST in C.

Ugh.

I think the following should work, after all it will be tiny more efficient,
I chose to use c_strlen just to avoid some code duplication.
c_strlen will return even variable lengths etc. and we are only interested
in constant string lengths, etc.  If c_strlen is only called in places which
expect zero-terminated strings, it will be fine.

2011-10-27  Jakub Jelinek  <jakub@redhat.com>

	* tree-ssa-strlen.c: Include expr.h.
	(get_stridx): Don't use c_strlen, instead use string_constant
	and compute string length from it.
	* Makefile.in (tree-ssa-strlen.o): Depend on $(EXPR_H).


	Jakub
Ian Taylor - Oct. 27, 2011, 4:10 p.m.
Jakub Jelinek <jakub@redhat.com> writes:

> On Wed, Oct 26, 2011 at 10:22:21PM -0700, Ian Lance Taylor wrote:
>> I don't think it is possible to trigger this using C because I don't
>> think it is possible to have a zero-length STRING_CST in C.
>
> Ugh.
>
> I think the following should work, after all it will be tiny more efficient,
> I chose to use c_strlen just to avoid some code duplication.
> c_strlen will return even variable lengths etc. and we are only interested
> in constant string lengths, etc.  If c_strlen is only called in places which
> expect zero-terminated strings, it will be fine.
>
> 2011-10-27  Jakub Jelinek  <jakub@redhat.com>
>
> 	* tree-ssa-strlen.c: Include expr.h.
> 	(get_stridx): Don't use c_strlen, instead use string_constant
> 	and compute string length from it.
> 	* Makefile.in (tree-ssa-strlen.o): Depend on $(EXPR_H).

Looks good to me.

Thanks.

Ian

Patch

--- gcc/tree-ssa-strlen.c.jj	2011-10-26 14:19:11.000000000 +0200
+++ gcc/tree-ssa-strlen.c	2011-10-27 08:55:39.000000000 +0200
@@ -28,6 +28,7 @@  along with GCC; see the file COPYING3.  
 #include "tree-ssa-propagate.h"
 #include "gimple-pretty-print.h"
 #include "params.h"
+#include "expr.h"
 
 /* A vector indexed by SSA_NAME_VERSION.  0 means unknown, positive value
    is an index into strinfo vector, negative value stands for
@@ -176,7 +177,7 @@  get_addr_stridx (tree exp)
 static int
 get_stridx (tree exp)
 {
-  tree l;
+  tree s, o;
 
   if (TREE_CODE (exp) == SSA_NAME)
     return VEC_index (int, ssa_ver_to_stridx, SSA_NAME_VERSION (exp));
@@ -188,14 +189,17 @@  get_stridx (tree exp)
 	return idx;
     }
 
-  l = c_strlen (exp, 0);
-  if (l != NULL_TREE
-      && host_integerp (l, 1))
-    {
-      unsigned HOST_WIDE_INT len = tree_low_cst (l, 1);
-      if (len == (unsigned int) len
-	  && (int) len >= 0)
-	return ~(int) len;
+  s = string_constant (exp, &o);
+  if (s != NULL_TREE
+      && (o == NULL_TREE || host_integerp (o, 0))
+      && TREE_STRING_LENGTH (s) > 0)
+    {
+      HOST_WIDE_INT offset = o ? tree_low_cst (o, 0) : 0;
+      const char *p = TREE_STRING_POINTER (s);
+      int max = TREE_STRING_LENGTH (s) - 1;
+
+      if (p[max] == '\0' && offset >= 0 && offset <= max)
+	return ~(int) strlen (p + offset);
     }
   return 0;
 }
--- gcc/Makefile.in.jj	2011-10-26 14:19:11.000000000 +0200
+++ gcc/Makefile.in	2011-10-27 08:54:10.000000000 +0200
@@ -3173,7 +3173,7 @@  tree-ssa-ccp.o : tree-ssa-ccp.c $(TREE_F
    $(DBGCNT_H) tree-pretty-print.h gimple-pretty-print.h gimple-fold.h
 tree-ssa-strlen.o : tree-ssa-strlen.c $(CONFIG_H) $(SYSTEM_H) coretypes.h \
    $(TREE_FLOW_H) $(TREE_PASS_H) domwalk.h alloc-pool.h tree-ssa-propagate.h \
-   gimple-pretty-print.h $(PARAMS_H)
+   gimple-pretty-print.h $(PARAMS_H) $(EXPR_H)
 tree-sra.o : tree-sra.c $(CONFIG_H) $(SYSTEM_H) coretypes.h alloc-pool.h \
    $(TM_H) $(TREE_H) $(GIMPLE_H) $(CGRAPH_H) $(TREE_FLOW_H) \
    $(IPA_PROP_H) $(DIAGNOSTIC_H) statistics.h $(TREE_DUMP_H) $(TIMEVAR_H) \