[PATCH] Make strlen range computations more conservative
Richard Biener
rguenther@suse.de
Mon Aug 20 10:24:00 GMT 2018
On Sun, 19 Aug 2018, Bernd Edlinger wrote:
> Hi,
>
>
> I rebased my range computation patch to current trunk,
> and updated it according to what was discussed here.
>
> That means get_range_strlen has already a parameter
> that is used to differentiate between ranges for warnings
> and ranges for code-gen.
>
> That is called "strict", in the 4-parameter overload
> and "fuzzy" in the internally used 7-parameter overload.
>
> So I added an "optimistic" parameter to my
> get_inner_char_array_unless_typecast helper function.
> That's it.
>
> Therefore at this time, there is only one warning regression
> in one test case and one xfailed warning test case fixed.
>
> So that is par on the warning regression side.
>
> The failed test case is gcc/testsuite/gcc.dg/pr83373.c which
> uses -fassume-zero-terminated-char-arrays, to enable the
> (unsafe) feedback from string-length information to VRP to
> suppress the warning.
>
> The 5 test cases that were designed to check the optimized
> tree dump have to use the new -fassume-zero-terminated-char-arrays
> option, but that is what we agreed upon.
>
> The patch is not dependent on any other patches.
>
>
> Bootstrapped and reg-tested on x86_64-pc-linux-gnu.
> Is it OK for trunk?
+ tree base = arg;
+ while (TREE_CODE (base) == ARRAY_REF
+ || TREE_CODE (base) == ARRAY_RANGE_REF
+ || TREE_CODE (base) == COMPONENT_REF)
+ base = TREE_OPERAND (base, 0);
+
+ /* If this looks like a type cast don't assume anything. */
+ if ((TREE_CODE (base) == MEM_REF
+ && (! integer_zerop (TREE_OPERAND (base, 1))
+ || TYPE_MAIN_VARIANT (TREE_TYPE (TREE_TYPE (TREE_OPERAND (base,
0))))
+ != TYPE_MAIN_VARIANT (TREE_TYPE (base))))
I'm not convinced you are testing anything useful here.
TREE_OPERAND (base, 1) might be a pointer which means it's type
doesn't have any semantics so you are testing the access type
against "random". If you'd restrict this to ADDR_EXPRs and
look at the objects declared type then you'd still miss
type-changes from a dynamic type that is different from what
is declared.
So my conclusion is if you really want to not want to return
arg for things that look like a type cast then you have to
unconditionally return NULL_TREE.
+ || TREE_CODE (base) == VIEW_CONVERT_EXPR
+ /* Or other stuff that would be handled by get_inner_reference. */
simply use || handled_component_p (base) for the above and the rest
to be sure to handle everything that is not stripped above.
+ || TREE_CODE (base) == BIT_FIELD_REF
+ || TREE_CODE (base) == REALPART_EXPR
+ || TREE_CODE (base) == IMAGPART_EXPR)
+ return NULL_TREE;
Btw, you are always returning the passed arg or NULL_TREE so
formulating this as a predicate function makes uses easier.
Not sure why it is called "inner" char array?
There do seem to be independently useful fixes in the patch that
I'd approve immediately.
Btw, I don't think we want sth like
flag_assume_zero_terminated_char_arrays or even make it default at
-Ofast.
Richard.
More information about the Gcc-patches
mailing list