Am Montag, dem 18.12.2023 um 20:14 +0100 schrieb Jakub Jelinek:
> Hi!
> 
> The following patch changes -Walloc-size warning to no longer warn
> about int *p = calloc (1, sizeof (int));, because as discussed earlier,
> the size is IMNSHO sufficient in that case, for alloc_size with 2
> arguments warns if the product of the 2 arguments is insufficiently small.
> 
> Also, it warns also for explicit casts of malloc/calloc etc. calls
> rather than just implicit, so not just
>   int *p = malloc (1);
> but also
>   int *p = (int *) malloc (1);
> 
> It also fixes some ICEs where the code didn't verify the alloc_size
> arguments properly (Walloc-size-5.c testcase ICEs with vanilla trunk).
> 
> And lastly, it introduces a coding style warning, -Wcalloc-transposed-args
> to warn for calloc (sizeof (struct S), 1) and similar calls (regardless
> of what they are cast to, warning whenever first argument is sizeof and
> the second is not).

I would generally see function arguments that are swapped relative
to the documented ABI as more than a coding style issue even inĀ 
cases where it can be expected to make no difference.

> 
> Ok for trunk if this passes bootstrap/regtest?

I wonder whether we could turn on -Walloc-size for -Wall with this change?


Martin


> 
> If yes, I'd implement it for C++ next.
> If not, we should at least fix the ICEs.
> 
> 2023-12-18  Jakub Jelinek  <ja...@redhat.com>
> 
> gcc/
>       * doc/invoke.texi (-Walloc-size): Add to the list of
>       warning options, remove unnecessary line-break.
>       (-Wcalloc-transposed-args): Document new warning.
> gcc/c-family/
>       * c.opt (Wcalloc-transposed-args): New warning.
>       * c-common.h (warn_for_calloc, warn_for_alloc_size): Declare.
>       * c-warn.cc (warn_for_calloc, warn_for_alloc_size): New functions.
> gcc/c/
>       * c-parser.cc (c_parser_postfix_expression_after_primary): Grow
>       sizeof_arg and sizeof_arg_loc arrays to 6 elements.  Call
>       warn_for_calloc if warn_calloc_transposed_args for functions with
>       alloc_size type attribute with 2 arguments.
>       (c_parser_expr_list): Use 6 instead of 3.
>       * c-typeck.cc (build_c_cast): Call warn_for_alloc_size for casts
>       of calls to functions with alloc_size type attribute.
>       (convert_for_assignment): Likewise.
> gcc/testsuite/
>       * gcc.dg/Walloc-size-4.c: New test.
>       * gcc.dg/Walloc-size-5.c: New test.
>       * gcc.dg/Wcalloc-transposed-args-1.c: New test.
> 
> --- gcc/doc/invoke.texi.jj    2023-12-18 09:39:49.411355496 +0100
> +++ gcc/doc/invoke.texi       2023-12-18 19:59:37.139525128 +0100
> @@ -328,7 +328,7 @@ Objective-C and Objective-C++ Dialects}.
>  -pedantic-errors -fpermissive
>  -w  -Wextra  -Wall  -Wabi=@var{n}
>  -Waddress  -Wno-address-of-packed-member  -Waggregate-return
> --Walloc-size-larger-than=@var{byte-size}  -Walloc-zero
> +-Walloc-size  -Walloc-size-larger-than=@var{byte-size}  -Walloc-zero
>  -Walloca  -Walloca-larger-than=@var{byte-size}
>  -Wno-aggressive-loop-optimizations
>  -Warith-conversion
> @@ -344,6 +344,7 @@ Objective-C and Objective-C++ Dialects}.
>  -Wc++20-compat
>  -Wno-c++11-extensions  -Wno-c++14-extensions -Wno-c++17-extensions
>  -Wno-c++20-extensions  -Wno-c++23-extensions
> +-Wcalloc-transposed-args
>  -Wcast-align  -Wcast-align=strict  -Wcast-function-type  -Wcast-qual
>  -Wchar-subscripts
>  -Wclobbered  -Wcomment
> @@ -8260,8 +8261,7 @@ Warn about calls to allocation functions
>  @code{alloc_size} that specify insufficient size for the target type of
>  the pointer the result is assigned to, including those to the built-in
>  forms of the functions @code{aligned_alloc}, @code{alloca},
> -@code{calloc},
> -@code{malloc}, and @code{realloc}.
> +@code{calloc}, @code{malloc}, and @code{realloc}.
>  
>  @opindex Wno-alloc-zero
>  @opindex Walloc-zero
> @@ -8274,6 +8274,21 @@ when called with a zero size differs amo
>  of @code{realloc} has been deprecated) relying on it may result in subtle
>  portability bugs and should be avoided.
>  
> +@opindex Wcalloc-transposed-args
> +@opindex Wno-calloc-transposed-args
> +@item -Wcalloc-transposed-args
> +Warn about calls to allocation functions decorated with attribute
> +@code{alloc_size} with two arguments, which use @code{sizeof} operator
> +as the earlier size argument and don't use it as the later size argument.
> +This is a coding style warning.  The first argument to @code{calloc} is
> +documented to be number of elements in array, while the second argument
> +is size of each element, so @code{calloc (@var{n}, sizeof (int))} is 
> preferred
> +over @code{calloc (sizeof (int), @var{n})}.  If @code{sizeof} in the earlier
> +argument and not the latter is intentional, the warning can be suppressed
> +by using @code{calloc (sizeof (struct @var{S}) + 0, n)} or
> +@code{calloc (1 * sizeof (struct @var{S}), 4)} or using @code{sizeof} in the
> +later argument as well.
> +
>  @opindex Walloc-size-larger-than=
>  @opindex Wno-alloc-size-larger-than
>  @item -Walloc-size-larger-than=@var{byte-size}
> --- gcc/c-family/c.opt.jj     2023-12-14 07:49:52.951583511 +0100
> +++ gcc/c-family/c.opt        2023-12-18 13:57:11.834184689 +0100
> @@ -502,6 +502,10 @@ Wc++26-extensions
>  C++ ObjC++ Var(warn_cxx26_extensions) Warning Init(1)
>  Warn about C++26 constructs in code compiled with an older standard.
>  
> +Wcalloc-transposed-args
> +C ObjC C++ ObjC++ Var(warn_calloc_transposed_args) Warning LangEnabledBy(C 
> ObjC C++ ObjC++,Wextra)
> +Warn about suspicious calls to calloc-like functions where sizeof expression 
> is the earlier size argument and not the latter.
> +
>  Wcast-function-type
>  C ObjC C++ ObjC++ Var(warn_cast_function_type) Warning EnabledBy(Wextra)
>  Warn about casts between incompatible function types.
> --- gcc/c-family/c-common.h.jj        2023-12-14 07:49:52.915584002 +0100
> +++ gcc/c-family/c-common.h   2023-12-18 16:26:40.420196735 +0100
> @@ -1599,6 +1599,9 @@ extern void warn_about_parentheses (loca
>  extern void warn_for_unused_label (tree label);
>  extern void warn_for_div_by_zero (location_t, tree divisor);
>  extern void warn_for_memset (location_t, tree, tree, int);
> +extern void warn_for_calloc (location_t *, tree, vec<tree, va_gc> *,
> +                          tree *, tree);
> +extern void warn_for_alloc_size (location_t, tree, tree, tree);
>  extern void warn_for_sign_compare (location_t,
>                                  tree orig_op0, tree orig_op1,
>                                  tree op0, tree op1,
> --- gcc/c-family/c-warn.cc.jj 2023-12-14 07:49:52.951583511 +0100
> +++ gcc/c-family/c-warn.cc    2023-12-18 19:30:47.285607029 +0100
> @@ -2263,6 +2263,76 @@ warn_for_memset (location_t loc, tree ar
>      }
>  }
>  
> +/* Warn for calloc (sizeof (X), n).  */
> +
> +void
> +warn_for_calloc (location_t *sizeof_arg_loc, tree callee,
> +              vec<tree, va_gc> *params, tree *sizeof_arg, tree attr)
> +{
> +  if (!TREE_VALUE (attr) || !TREE_CHAIN (TREE_VALUE (attr)))
> +    return;
> +
> +  int arg1 = TREE_INT_CST_LOW (TREE_VALUE (TREE_VALUE (attr))) - 1;
> +  int arg2
> +    = TREE_INT_CST_LOW (TREE_VALUE (TREE_CHAIN (TREE_VALUE (attr)))) - 1;
> +  if (arg1 < 0
> +      || (unsigned) arg1 >= vec_safe_length (params)
> +      || arg1 >= 6
> +      || arg2 < 0
> +      || (unsigned) arg2 >= vec_safe_length (params)
> +      || arg2 >= 6
> +      || arg1 >= arg2)
> +    return;
> +
> +  if (sizeof_arg[arg1] == NULL_TREE || sizeof_arg[arg2] != NULL_TREE)
> +    return;
> +
> +  if (warning_at (sizeof_arg_loc[arg1], OPT_Wcalloc_transposed_args,
> +               "%qD sizes specified with %<sizeof%> in the earlier "
> +               "argument and not in the later argument", callee))
> +    inform (sizeof_arg_loc[arg1], "earlier argument should specify number "
> +         "of elements, later size of each element");
> +}
> +
> +/* Warn for allocator calls where the constant allocated size is smaller
> +   than sizeof (TYPE).  */
> +
> +void
> +warn_for_alloc_size (location_t loc, tree type, tree call, tree alloc_size)
> +{
> +  if (!TREE_VALUE (alloc_size))
> +    return;
> +
> +  tree arg1 = TREE_VALUE (TREE_VALUE (alloc_size));
> +  int idx1 = TREE_INT_CST_LOW (arg1) - 1;
> +  if (idx1 < 0 || idx1 >= call_expr_nargs (call))
> +    return;
> +  arg1 = CALL_EXPR_ARG (call, idx1);
> +  if (TREE_CODE (arg1) != INTEGER_CST)
> +    return;
> +  if (TREE_CHAIN (TREE_VALUE (alloc_size)))
> +    {
> +      tree arg2 = TREE_VALUE (TREE_CHAIN (TREE_VALUE (alloc_size)));
> +      int idx2 = TREE_INT_CST_LOW (arg2) - 1;
> +      if (idx2 < 0 || idx2 >= call_expr_nargs (call))
> +     return;
> +      arg2 = CALL_EXPR_ARG (call, idx2);
> +      if (TREE_CODE (arg2) != INTEGER_CST)
> +     return;
> +      arg1 = int_const_binop (MULT_EXPR, fold_convert (sizetype, arg1),
> +                           fold_convert (sizetype, arg2));
> +      if (TREE_CODE (arg1) != INTEGER_CST)
> +     return;
> +    }
> +  if (!VOID_TYPE_P (type)
> +      && TYPE_SIZE_UNIT (type)
> +      && TREE_CODE (TYPE_SIZE_UNIT (type)) == INTEGER_CST
> +      && tree_int_cst_lt (arg1, TYPE_SIZE_UNIT (type)))
> +    warning_at (loc, OPT_Walloc_size,
> +             "allocation of insufficient size %qE for type %qT with "
> +             "size %qE", arg1, type, TYPE_SIZE_UNIT (type));
> +}
> +
>  /* Subroutine of build_binary_op. Give warnings for comparisons
>     between signed and unsigned quantities that may fail. Do the
>     checking based on the original operand trees ORIG_OP0 and ORIG_OP1,
> --- gcc/c/c-parser.cc.jj      2023-12-14 07:49:52.969583266 +0100
> +++ gcc/c/c-parser.cc 2023-12-18 19:24:01.508298779 +0100
> @@ -12478,8 +12478,8 @@ c_parser_postfix_expression_after_primar
>  {
>    struct c_expr orig_expr;
>    tree ident, idx;
> -  location_t sizeof_arg_loc[3], comp_loc;
> -  tree sizeof_arg[3];
> +  location_t sizeof_arg_loc[6], comp_loc;
> +  tree sizeof_arg[6];
>    unsigned int literal_zero_mask;
>    unsigned int i;
>    vec<tree, va_gc> *exprlist;
> @@ -12512,7 +12512,7 @@ c_parser_postfix_expression_after_primar
>         {
>           matching_parens parens;
>           parens.consume_open (parser);
> -         for (i = 0; i < 3; i++)
> +         for (i = 0; i < 6; i++)
>             {
>               sizeof_arg[i] = NULL_TREE;
>               sizeof_arg_loc[i] = UNKNOWN_LOCATION;
> @@ -12577,6 +12577,13 @@ c_parser_postfix_expression_after_primar
>                                     "not permitted in intervening code");
>                 parser->omp_for_parse_state->fail = true;
>               }
> +           if (warn_calloc_transposed_args)
> +             if (tree attr = lookup_attribute ("alloc_size",
> +                                               TYPE_ATTRIBUTES
> +                                                 (TREE_TYPE (expr.value))))
> +               if (TREE_VALUE (attr) && TREE_CHAIN (TREE_VALUE (attr)))
> +                 warn_for_calloc (sizeof_arg_loc, expr.value, exprlist,
> +                                  sizeof_arg, attr);
>           }
>  
>         start = expr.get_start ();
> @@ -12861,7 +12868,7 @@ c_parser_expr_list (c_parser *parser, bo
>       vec_safe_push (orig_types, expr.original_type);
>        if (locations)
>       locations->safe_push (expr.get_location ());
> -      if (++idx < 3
> +      if (++idx < 6
>         && sizeof_arg != NULL
>         && (expr.original_code == SIZEOF_EXPR
>             || expr.original_code == PAREN_SIZEOF_EXPR))
> --- gcc/c/c-typeck.cc.jj      2023-12-14 07:49:52.990582980 +0100
> +++ gcc/c/c-typeck.cc 2023-12-18 19:01:40.013746860 +0100
> @@ -6054,6 +6054,19 @@ build_c_cast (location_t loc, tree type,
>                           c_addr_space_name (as_to),
>                           c_addr_space_name (as_from));
>           }
> +
> +       /* Warn of new allocations that are not big enough for the target
> +          type.  */
> +       if (warn_alloc_size && TREE_CODE (value) == CALL_EXPR)
> +         if (tree fndecl = get_callee_fndecl (value))
> +           if (DECL_IS_MALLOC (fndecl))
> +             {
> +               tree attrs = TYPE_ATTRIBUTES (TREE_TYPE (fndecl));
> +               tree alloc_size = lookup_attribute ("alloc_size", attrs);
> +               if (alloc_size)
> +                 warn_for_alloc_size (loc, TREE_TYPE (type), value,
> +                                      alloc_size);
> +             }
>       }
>  
>        /* Warn about possible alignment problems.  */
> @@ -7277,32 +7290,15 @@ convert_for_assignment (location_t locat
>  
>        /* Warn of new allocations that are not big enough for the target
>        type.  */
> -      tree fndecl;
> -      if (warn_alloc_size
> -       && TREE_CODE (rhs) == CALL_EXPR
> -       && (fndecl = get_callee_fndecl (rhs)) != NULL_TREE
> -       && DECL_IS_MALLOC (fndecl))
> -     {
> -       tree fntype = TREE_TYPE (fndecl);
> -       tree fntypeattrs = TYPE_ATTRIBUTES (fntype);
> -       tree alloc_size = lookup_attribute ("alloc_size", fntypeattrs);
> -       if (alloc_size)
> +      if (warn_alloc_size && TREE_CODE (rhs) == CALL_EXPR)
> +     if (tree fndecl = get_callee_fndecl (rhs))
> +       if (DECL_IS_MALLOC (fndecl))
>           {
> -           tree args = TREE_VALUE (alloc_size);
> -           int idx = TREE_INT_CST_LOW (TREE_VALUE (args)) - 1;
> -           /* For calloc only use the second argument.  */
> -           if (TREE_CHAIN (args))
> -             idx = TREE_INT_CST_LOW (TREE_VALUE (TREE_CHAIN (args))) - 1;
> -           tree arg = CALL_EXPR_ARG (rhs, idx);
> -           if (TREE_CODE (arg) == INTEGER_CST
> -               && !VOID_TYPE_P (ttl) && TYPE_SIZE_UNIT (ttl)
> -               && INTEGER_CST == TREE_CODE (TYPE_SIZE_UNIT (ttl))
> -               && tree_int_cst_lt (arg, TYPE_SIZE_UNIT (ttl)))
> -              warning_at (location, OPT_Walloc_size, "allocation of "
> -                          "insufficient size %qE for type %qT with "
> -                          "size %qE", arg, ttl, TYPE_SIZE_UNIT (ttl));
> +           tree attrs = TYPE_ATTRIBUTES (TREE_TYPE (fndecl));
> +           tree alloc_size = lookup_attribute ("alloc_size", attrs);
> +           if (alloc_size)
> +             warn_for_alloc_size (location, ttl, rhs, alloc_size);
>           }
> -     }
>  
>        /* See if the pointers point to incompatible address spaces.  */
>        asl = TYPE_ADDR_SPACE (ttl);
> --- gcc/testsuite/gcc.dg/Walloc-size-4.c.jj   2023-12-18 19:06:41.069528176 
> +0100
> +++ gcc/testsuite/gcc.dg/Walloc-size-4.c      2023-12-18 19:34:06.964824180 
> +0100
> @@ -0,0 +1,54 @@
> +/* Tests the warnings for insufficient allocation size.  */
> +/* { dg-do compile } */
> +/* { dg-options "-Walloc-size -Wno-calloc-transposed-args" } */
> +
> +struct S { int x[10]; };
> +void bar (struct S *);
> +typedef __SIZE_TYPE__ size_t;
> +void *myfree (void *, int, int);
> +void *mymalloc (int, int, size_t) __attribute__((malloc, malloc (myfree), 
> alloc_size (3)));
> +void *mycalloc (int, int, size_t, size_t) __attribute__((malloc, malloc 
> (myfree), alloc_size (3, 4)));
> +
> +void
> +foo (void)
> +{
> +  struct S *p = (struct S *) __builtin_malloc (sizeof *p);
> +  __builtin_free (p);
> +  p = (struct S *) __builtin_malloc (sizeof p);              /* { dg-warning 
> "allocation of insufficient size" } */
> +  __builtin_free (p);
> +  p = (struct S *) __builtin_alloca (sizeof p);              /* { dg-warning 
> "allocation of insufficient size" } */
> +  bar (p);
> +  p = (struct S *) __builtin_calloc (1, sizeof p);   /* { dg-warning 
> "allocation of insufficient size" } */
> +  __builtin_free (p);
> +  bar ((struct S *) __builtin_malloc (4));           /* { dg-warning 
> "allocation of insufficient size" } */
> +  __builtin_free (p);
> +  p = (struct S *) __builtin_calloc (sizeof *p, 1);
> +  __builtin_free (p);
> +  p = __builtin_calloc (sizeof *p, 1);
> +  __builtin_free (p);
> +}
> +
> +void
> +baz (void)
> +{
> +  struct S *p = (struct S *) mymalloc (42, 42, sizeof *p);
> +  myfree (p, 42, 42);
> +  p = (struct S *) mymalloc (42, 42, sizeof p);              /* { dg-warning 
> "allocation of insufficient size" } */
> +  myfree (p, 42, 42);
> +  p = (struct S *) mycalloc (42, 42, 1, sizeof p);   /* { dg-warning 
> "allocation of insufficient size" } */
> +  myfree (p, 42, 42);
> +  bar ((struct S *) mymalloc (42, 42, 4));           /* { dg-warning 
> "allocation of insufficient size" } */
> +  myfree (p, 42, 42);
> +  p = (struct S *) mycalloc (42, 42, sizeof *p, 1);
> +  myfree (p, 42, 42);
> +  p = mycalloc (42, 42, sizeof *p, 1);
> +  myfree (p, 42, 42);
> +  p = mymalloc (42, 42, sizeof *p);
> +  myfree (p, 42, 42);
> +  p = mymalloc (42, 42, sizeof p);                   /* { dg-warning 
> "allocation of insufficient size" } */
> +  myfree (p, 42, 42);
> +  p = mycalloc (42, 42, 1, sizeof p);                        /* { dg-warning 
> "allocation of insufficient size" } */
> +  myfree (p, 42, 42);
> +  bar (mymalloc (42, 42, 4));                                /* { dg-warning 
> "allocation of insufficient size" } */
> +  myfree (p, 42, 42);
> +}
> --- gcc/testsuite/gcc.dg/Walloc-size-5.c.jj   2023-12-18 19:18:13.451180896 
> +0100
> +++ gcc/testsuite/gcc.dg/Walloc-size-5.c      2023-12-18 19:19:25.244173868 
> +0100
> @@ -0,0 +1,20 @@
> +/* { dg-do compile } */
> +/* { dg-options "-Walloc-size -std=gnu11" } */
> +
> +struct S { int x[10]; };
> +void myfree ();
> +void *mymalloc () __attribute__((malloc, alloc_size (16)));
> +void *mycalloc () __attribute__((malloc, alloc_size (16, 17)));
> +
> +void
> +foo (void)
> +{
> +  struct S *p = mymalloc (1);
> +  myfree (p);
> +  p = mycalloc (1, 1);
> +  myfree (p);
> +  p = (struct S *) mymalloc (1);
> +  myfree (p);
> +  p = (struct S *) mycalloc (1, 1);
> +  myfree (p);
> +}
> --- gcc/testsuite/gcc.dg/Wcalloc-transposed-args-1.c.jj       2023-12-18 
> 19:39:42.930196797 +0100
> +++ gcc/testsuite/gcc.dg/Wcalloc-transposed-args-1.c  2023-12-18 
> 19:52:03.273855456 +0100
> @@ -0,0 +1,54 @@
> +/* { dg-do compile } */
> +/* { dg-options "-Wcalloc-transposed-args" } */
> +
> +typedef __SIZE_TYPE__ size_t;
> +void free (void *);
> +void *calloc (size_t, size_t);
> +void *myfree (void *, int, int);
> +void *mycalloc (int, int, size_t, size_t) __attribute__((malloc, malloc 
> (myfree), alloc_size (3, 4)));
> +
> +void
> +foo (int n)
> +{
> +  void *p;
> +  p = __builtin_calloc (1, sizeof (int));
> +  __builtin_free (p);
> +  p = __builtin_calloc (n, sizeof (int));
> +  __builtin_free (p);
> +  p = __builtin_calloc (sizeof (int), 1);            /* { dg-warning 
> "'__builtin_calloc' sizes specified with 'sizeof' in the earlier argument and 
> not in the later argument" } */
> +  __builtin_free (p);                                        /* { dg-message 
> "earlier argument should specify number of elements, later size of each 
> element" "" { target *-*-* } .-1 } */
> +  p = __builtin_calloc (sizeof (int), n);            /* { dg-warning 
> "'__builtin_calloc' sizes specified with 'sizeof' in the earlier argument and 
> not in the later argument" } */
> +  __builtin_free (p);                                        /* { dg-message 
> "earlier argument should specify number of elements, later size of each 
> element" "" { target *-*-* } .-1 } */
> +  p = __builtin_calloc ((sizeof (int)), 1);          /* { dg-warning 
> "'__builtin_calloc' sizes specified with 'sizeof' in the earlier argument and 
> not in the later argument" } */
> +  __builtin_free (p);                                        /* { dg-message 
> "earlier argument should specify number of elements, later size of each 
> element" "" { target *-*-* } .-1 } */
> +  p = __builtin_calloc (sizeof (int) + 0, 1);
> +  __builtin_free (p);
> +  p = __builtin_calloc (sizeof (int), sizeof (char));
> +  __builtin_free (p);
> +  p = __builtin_calloc (1 * sizeof (int), 1);
> +  __builtin_free (p);
> +  p = calloc (1, sizeof (int));
> +  free (p);
> +  p = calloc (n, sizeof (int));
> +  free (p);
> +  p = calloc (sizeof (int), 1);                              /* { dg-warning 
> "'calloc' sizes specified with 'sizeof' in the earlier argument and not in 
> the later argument" } */
> +  free (p);                                          /* { dg-message 
> "earlier argument should specify number of elements, later size of each 
> element" "" { target *-*-* } .-1 } */
> +  p = calloc (sizeof (int), n);                              /* { dg-warning 
> "'calloc' sizes specified with 'sizeof' in the earlier argument and not in 
> the later argument" } */
> +  free (p);                                          /* { dg-message 
> "earlier argument should specify number of elements, later size of each 
> element" "" { target *-*-* } .-1 } */
> +  p = calloc (sizeof (int), sizeof (char));
> +  free (p);
> +  p = calloc (1 * sizeof (int), 1);
> +  free (p);
> +  p = mycalloc (42, 42, 1, sizeof (int));
> +  myfree (p, 42, 42);
> +  p = mycalloc (42, 42, n, sizeof (int));
> +  myfree (p, 42, 42);
> +  p = mycalloc (42, 42, sizeof (int), 1);            /* { dg-warning 
> "'mycalloc' sizes specified with 'sizeof' in the earlier argument and not in 
> the later argument" } */
> +  myfree (p, 42, 42);                                        /* { dg-message 
> "earlier argument should specify number of elements, later size of each 
> element" "" { target *-*-* } .-1 } */
> +  p = mycalloc (42, 42, sizeof (int), n);            /* { dg-warning 
> "'mycalloc' sizes specified with 'sizeof' in the earlier argument and not in 
> the later argument" } */
> +  myfree (p, 42, 42);                                        /* { dg-message 
> "earlier argument should specify number of elements, later size of each 
> element" "" { target *-*-* } .-1 } */
> +  p = mycalloc (42, 42, sizeof (int), sizeof (char));
> +  myfree (p, 42, 42);
> +  p = mycalloc (42, 42, 1 * sizeof (int), 1);
> +  myfree (p, 42, 42);
> +}
> 
>       Jakub
> 

Reply via email to