On Wed, Dec 07, 2016 at 08:24:33PM -0700, Martin Sebor wrote: > @@ -8622,15 +8635,17 @@ rewrite_call_expr (location_t loc, tree exp, int > skip, tree fndecl, int n, ...) > } > > /* Validate a single argument ARG against a tree code CODE representing > - a type. */ > + a type. When NONNULL is true consider a pointer argument valid only > + if it's non-null. Return true when argument is valid. */ > > static bool > -validate_arg (const_tree arg, enum tree_code code) > +validate_arg (const_tree arg, enum tree_code code, bool nonnull /*= false*/) > { > if (!arg) > return false; > else if (code == POINTER_TYPE) > - return POINTER_TYPE_P (TREE_TYPE (arg)); > + return POINTER_TYPE_P (TREE_TYPE (arg)) > + && (!nonnull || !integer_zerop (arg)); > else if (code == INTEGER_TYPE) > return INTEGRAL_TYPE_P (TREE_TYPE (arg)); > return code == TREE_CODE (TREE_TYPE (arg));
This is badly formatted, it would need to be return (POINTER_TYPE_P (TREE_TYPE (arg)) && (!nonnull || !integer_zerop (arg))); but more importantly, we have 45 validate_arg calls that really don't care about the nonnull stuff and a single one that cares. I think it would be better to revert the validate_arg changes and do: case POINTER_TYPE: /* The actual argument must be nonnull when either the whole called function has been declared nonnull, or when the formal argument corresponding to the actual argument has been. */ if (argmap) nonnull = bitmap_empty_p (argmap) || bitmap_bit_p (argmap, argno); arg = next_const_call_expr_arg (&iter); if (!validate_arg (arg, code) || (nonnull && !integer_zerop (arg))) goto end; break; default: /* If no parameters remain or the parameter's code does not match the specified code, return false. Otherwise continue checking any remaining arguments. */ arg = next_const_call_expr_arg (&iter); if (!validate_arg (arg, code, nonnull)) goto end; break; Jakub