[Bug analyzer/109580] New: #pragma GCC diagnostic ignored "-Wanalyzer-fd-leak" is ineffective

2023-04-20 Thread eggert at gnu dot org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109580

Bug ID: 109580
   Summary: #pragma GCC diagnostic ignored "-Wanalyzer-fd-leak" is
ineffective
   Product: gcc
   Version: 13.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: analyzer
  Assignee: dmalcolm at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

Created attachment 54896
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=54896=edit
compressed test program illustrating false positive

This is gcc (GCC) 13.0.1 20230401 (Red Hat 13.0.1-0), and I ran into this
problem when compiling Emacs. This is a regression compared to GCC 12.

Compile the attached compressed program with:

gzip -d emacs1.i.gz
gcc -fanalyzer -O2 -S emacs1.i

GCC will generate output starting with:

In function ‘Fdaemon_initialized’:
cc1: warning: leak of file descriptor ‘dup2(nfd, 0)’ [CWE-775]
[-Wanalyzer-fd-leak]

However, the first line of emacs1.i is:

#pragma GCC diagnostic ignored "-Wanalyzer-fd-leak"

so that diagnostic should not be emitted.

[Bug analyzer/109579] New: -Wanalyzer-out-of-bounds false positive in Emacs mapping stack

2023-04-20 Thread eggert at gnu dot org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109579

Bug ID: 109579
   Summary: -Wanalyzer-out-of-bounds false positive in Emacs
mapping stack
   Product: gcc
   Version: 13.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: analyzer
  Assignee: dmalcolm at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

Created attachment 54895
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=54895=edit
compressed test program illustrating false positive

This is gcc (GCC) 13.0.1 20230401 (Red Hat 13.0.1-0) on x86-64, and I ran into
this problem when compiling Emacs. Take the attached file ccl1.i.gz and then
run:

gzip -d ccl1.i.gz
gcc -S -fanalyzer -O2 ccl1.i

The incorrect diagnostics are as follows. These diagnostics are wrong since the
two uses of "mapping_stack_pointer--" in lines 33010 and 33011 are protected
due to those lines being in the else-part of "if (mapping_stack_pointer <=
(mapping_stack + 1))", which means mapping_stack_pointer cannot possibly
underrun the buffer simply by subtracting one from it twice.

I can work around this by compiling with -Wno-analyzer-out-of-bounds but this
seems a bit drastic.

Here are the incorrect diagnostics. These diagnostics are a regression since
GCC 12.

-

ccl1.i: In function ‘ccl_driver’:
ccl1.i:33010:107: warning: buffer under-read [CWE-127]
[-Wanalyzer-out-of-bounds]
33010 |   do { mapping_stack_pointer--; (map_set_rest_length) =
mapping_stack_pointer->rest_length; (orig_op) =
mapping_stack_pointer->orig_val; } while (0);
  |
~~^
  ‘Fccl_execute_on_string’: events 1-4
|
|33434 | __attribute__((section (".subrs"))) static union Aligned_Lisp_Subr
Sccl_execute_on_string = {{{ PVEC_SUBR << PSEUDOVECTOR_AREA_BITS }, { .a5 =
Fccl_execute_on_string }, 3, 5, "ccl-execute-on-string", {0}, 0}}; Lisp_Object
Fccl_execute_on_string
|  |   
   
  
^~
|  |   
   
   |
|  |   
   
   (1)
entry to ‘Fccl_execute_on_string’
|..
|33446 |   if (! setup_ccl_program (, ccl_prog))
|  |  ~ 
|  |  |
|  |  (2) following ‘true’ branch...
|33447 | error ("Invalid CCL program");
|33448 |   CHECK_VECTOR (status);
|  |   ~
|  |   |
|  |   (3) ...to here
|  |   (4) calling ‘CHECK_VECTOR’ from ‘Fccl_execute_on_string’
|
+--> ‘CHECK_VECTOR’: events 5-6
   |
   | 5942 | CHECK_VECTOR (Lisp_Object x)
   |  | ^~~~
   |  | |
   |  | (5) entry to ‘CHECK_VECTOR’
   | 5943 | {
   | 5944 |   CHECK_TYPE (VECTORP (x), builtin_lisp_symbol (1495), x);
   |  |   ~~~
   |  |   |
   |  |   (6) calling ‘VECTORP’ from ‘CHECK_VECTOR’
   |
   +--> ‘VECTORP’: events 7-8
  |
  | 5933 | VECTORP (Lisp_Object x)
  |  | ^~~
  |  | |
  |  | (7) entry to ‘VECTORP’
  | 5934 | {
  | 5935 |   return VECTORLIKEP (x) && ! (ASIZE (x) & (
  |  |~
  |  ||
  |  |(8) inlined call to
‘ASIZE’ from ‘VECTORP’
  |
  +--> ‘ASIZE’: event 9
 |
 | 5916 |   ((0 <= size) ? (void) 0 :
__builtin_unreachable ());
 |  |  
^~~
 |  |   |
 |  |   (9) following
‘false’ branch (when ‘size >= 0’)...
 |
  <--+
 

[Bug analyzer/109577] New: -Wanalyzer-allocation-size mishandles __builtin_mul_overflow

2023-04-20 Thread eggert at gnu dot org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=109577

Bug ID: 109577
   Summary: -Wanalyzer-allocation-size mishandles
__builtin_mul_overflow
   Product: gcc
   Version: 13.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: analyzer
  Assignee: dmalcolm at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

This is (GCC) 13.0.1 20230401 (Red Hat 13.0.1-0) on x86-64.

Compile the following program with 'gcc -O2 -S -fanalyzer t.c'. GCC will
incorrectly complain "warning: allocated buffer size is not a multiple of the
pointee's size [CWE-131]". But the allocated buffer size must be a multiple of
sizeof (double), due to the checked call to __builtin_mul_overflow. As the
code's comment suggests, if the code uses plain * (integer multiply) instead
the bogus warning goes away.

I ran into this problem when compiling Emacs, which is often careful about
checking integer overflow. As a result I think I'll compile Emacs with
-Wno-analyzer-allocation-size to suppress false alarms, which would be a real
shame since this warning is useful for lower-quality code.

  #include 

  int
  main (int argc, char **argv)
  {
size_t s;
double *d;
if (__builtin_mul_overflow (argc, sizeof *d, ))
  return 1;
// No warning if the above is replaced with 's = argc * sizeof *d;'.
d = malloc (s);
if (d && s)
  {
d[0] = argc;
d[argc - 1] = argc + 1;
return d[0];
  }
return 0;
  }

[Bug c/108690] New: -Wstrict-prototypes too picky for C23

2023-02-06 Thread eggert at gnu dot org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=108690

Bug ID: 108690
   Summary: -Wstrict-prototypes too picky for C23
   Product: gcc
   Version: unknown
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

We ran into this problem in Gnulib when considering how to migrate towards C23.

With GCC 12.2.1 20221121 (Red Hat 12.2.1-4) on x86-64, compile the following
one-line program t.c with 'gcc -S -std=gnu2x -Wstrict-prototypes t.c':

int f ();

GCC complains:

t.c:1:1: warning: function declaration isn’t a prototype [-Wstrict-prototypes]
1 | int f ();
  | ^~~

This diagnostic is incorrect, because in C23 every function declaration and
definition is prototyped: 'int f ();' means the same thing as 'int f (void);'.
This incorrect warning is causing us to think we should stop using
-Wstrict-prototypes, but that would have a negative consequence in the common
case of pre-C23 builds.

In short, -Wstrict-prototypes should be a no-op in C23, since all functions are
prototyped in C23.

[Bug c/101682] gcc incorrectly rejects C2x attributes after declaration-specifiers

2021-07-30 Thread eggert at gnu dot org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=101682

Paul Eggert  changed:

   What|Removed |Added

 Status|UNCONFIRMED |RESOLVED
 Resolution|--- |INVALID

--- Comment #5 from Paul Eggert  ---
Thanks for the clarification, Joseph. I'll fix Gnulib accordingly. Marking the
bug as RESOLVED INVALID.

FWIW the comment 2 code works even with bleeding-edge clang because
__has_c_attribute (nodiscard) is still 0 in there.


PS. It is a bit annoying that one can't do this:

int f (int) [[nodiscard]];

as that would match the existing Gnulib style of putting attributes at the end
of the function declarations. I don't know whether such a thing could be added
as a GCC extension, but I suppose it's not worth the trouble since it wouldn't
be portable as per draft C2x.

[Bug c/101682] gcc incorrectly rejects C2x attributes after declaration-specifiers

2021-07-29 Thread eggert at gnu dot org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=101682

--- Comment #2 from Paul Eggert  ---
Clang's warnings are not a problem here, because in clang 12.0.0 (the current
release) __has_c_attribute(nodiscard) is false, so code like this works:

#ifndef __has_c_attribute
# define __has_c_attribute(x) 0
#endif
#if __has_c_attribute (nodiscard)
# define NODISCARD [[nodiscard]]
#else
# define NODISCARD
#endif
extern NODISCARD int f (void);
extern int NODISCARD g (void);
int NODISCARD h (void);
NODISCARD extern int i (void);
NODISCARD int j (void);

Although draft C2x recommends this sort of macro preprocessing and it works
with Clang 12.0.0, this code doesn't work with GCC 11.2.0 due to its
incompatibility with draft C2x.

This is more what the original code looked like, by the way; I removed the
macro preprocessing to simplify the original bug report.

[Bug c/101682] New: gcc incorrectly rejects C2x attributes after declaration-specifiers

2021-07-29 Thread eggert at gnu dot org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=101682

Bug ID: 101682
   Summary: gcc incorrectly rejects C2x attributes after
declaration-specifiers
   Product: gcc
   Version: 11.2.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

The grammar at the start of section 6.7 of the current C2x draft (N2596) says
that attribute specifiers may appear either before or after declaration
specifiers. Unfortunately, GCC rejects attribution specifiers after declaration
specifiers. For example, for this this source code:

extern [[nodiscard]] int f (void);
extern int [[nodiscard]] g (void);
int [[nodiscard]] h (void);
[[nodiscard]] extern int i (void);
[[nodiscard]] int j (void);

the command 'gcc -S t.c' rejects the first three lines even though they conform
to the draft standard. It allows only the last two lines. The incorrect GCC
output is:

t.c:1:1: warning: ‘nodiscard’ attribute ignored [-Wattributes]
1 | extern [[nodiscard]] int f (void);
  | ^~
t.c:1:22: error: expected identifier or ‘(’ before ‘int’
1 | extern [[nodiscard]] int f (void);
  |  ^~~
t.c:2:1: warning: ‘nodiscard’ attribute ignored [-Wattributes]
2 | extern int [[nodiscard]] g (void);
  | ^~
t.c:3:1: warning: ‘nodiscard’ attribute ignored [-Wattributes]
3 | int [[nodiscard]] h (void);
  | ^~~

This is with GCC 11.2.0, which I built myself on an RHEL 8.4 x86-64 platform.

[Bug other/100735] New: -fno-trampolines doc wrongly implies it affects C, C++ etc.

2021-05-23 Thread eggert at gnu dot org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=100735

Bug ID: 100735
   Summary: -fno-trampolines doc wrongly implies it affects C, C++
etc.
   Product: gcc
   Version: 11.1.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: other
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

Created attachment 50859
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=50859=edit
doc patch for -fno-trampolines confusion

The GCC manual's documentation of -fno-trampolines was apparently written from
an Ada point of view. However, when I read it I understandably mistook it to
say that -fno-trampolines also works for C, C++, etc. It doesn't: it is
silently ignored for these languages, and I assume for any language other than
Ada.

This confusion caused me to go in the wrong direction in a Gnulib dicussion, as
I mistakenly thought that entire C apps with nested functions could be compiled
with -fno-trampolines and then use nested C function in stack overflow handlers
where the alternate stack is allocated via malloc. I was wrong, as this won't
work on common platforms like x86-64 where malloc yields non-executable
storage.

A proposed fix for the GCC manual is attached.

[Bug target/99591] New: Improving __builtin_add_overflow performance on x86-64

2021-03-15 Thread eggert at gnu dot org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=99591

Bug ID: 99591
   Summary: Improving __builtin_add_overflow performance on x86-64
   Product: gcc
   Version: 10.2.1
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: target
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

This is with gcc (GCC) 10.2.1 20201125 (Red Hat 10.2.1-9) on x86-64. For the
function:

_Bool signed1_overflow (signed char a, signed char b)
{
  signed char r;
  return __builtin_add_overflow (a, b, );
}

gcc generates the code:

signed1_overflow:
movsbl  %sil, %esi
movsbl  %dil, %edi
addb%sil, %dil
seto%al
ret

The movsbl instructions are unnecessary and can be omitted.


For the function:

_Bool signed2_overflow (short a, short b)
{
  short r;
  return __builtin_add_overflow (a, b, );
}

gcc generates:

signed2_overflow:
movswl  %di, %edi
movswl  %si, %esi
xorl%eax, %eax
addw%si, %di
jo  .L8
.L6:
andl$1, %eax
ret
.L8:
movl$1, %eax
jmp .L6

Better would be this:

signed2_overflow:
addw%si, %di
seto%al
retq

There are similar opportunities for improvement in __builtin_sub_overflow and
__builtin_mul_overflow.

This bug report follows up on this discussion about Gnulib:

https://lists.gnu.org/r/bug-gnulib/2021-03/msg00078.html
https://lists.gnu.org/r/bug-gnulib/2021-03/msg00079.html
https://lists.gnu.org/r/bug-gnulib/2021-03/msg00080.html

[Bug c/97370] comedy of boolean errors for '!a & (b|c)'

2020-10-12 Thread eggert at gnu dot org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=97370

Paul Eggert  changed:

   What|Removed |Added

 CC||eggert at gnu dot org

--- Comment #4 from Paul Eggert  ---
(In reply to Harald van Dijk from comment #3)

> Perhaps the warning could be suppressed specifically for boolean variables,
> since those make it more likely that the (!a) & b meaning is exactly what is
> intended?

Yes, that's the idea. When a and b are booleans, !a & b has just one sensible
interpretation, and people are no more likely to get it wrong than to get -a +
b wrong. This distinguishes this case from the one discussed in PR 7543.

[Bug debug/80646] [8/9/10 Regression] wrong type info for extern inline function when compiling Emacs

2019-11-14 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=80646

Paul Eggert  changed:

   What|Removed |Added

 Status|WAITING |RESOLVED
 Resolution|--- |MOVED

--- Comment #7 from Paul Eggert  ---
(In reply to Richard Biener from comment #6)

I still see the problem on Fedora 31 x86-64, but you're right that it appears
to be a GDB bug rather than a GCC bug. I added a note to that effect to the GDB
bug report  and am
marking the GCC bug as RESOLVED MOVED (moved to GDB, that is). The bug appears
to be low priority on the GDB side, but I don't know how to fix that

[Bug target/82170] gcc optimizes int range-checking poorly on x86-64

2019-03-18 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=82170

Paul Eggert  changed:

   What|Removed |Added

Version|7.1.1   |8.3.1

--- Comment #10 from Paul Eggert  ---
I just now ran into this problem in another situation and so was reminded of
this bug report.

For what it's worth, clang does a good job of optimizing these comparisons. I
just now compiled the sample C source code attached to this bug report, and
clang version 7.0.1 (Fedora 7.0.1-4.fc29) x86-64 generates the same code for
checked_arg_portable that it does for checked_arg_GCC7, whereas GCC 8.3.1
20190223 (Red Hat 8.3.1-2) x86-64 still generates poorly-optimized code for
checked_arg_portable.

[Bug middle-end/85563] [8/9 regression] -Wmaybe-uninitialized false alarm regression with __builtin_unreachable and GCC 8

2019-02-01 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=85563

Paul Eggert  changed:

   What|Removed |Added

 CC||eggert at gnu dot org

--- Comment #8 from Paul Eggert  ---
(In reply to Jakub Jelinek from comment #7)

> Or just rewrite whatever you are doing to something that doesn't suffer from
> this.  Say:
>   (tail) = Vframe_list;
>   while ((frame1 = XCAR (tail), 1))
> {
>   body...;
>   tail = XCDR (tail);
>   if (!CONSP (tail))
> break;
> }

Unfortunately that wouldn't be right, since Vframe_list might be Qnil so the
first XCAR would be invalid.

In Emacs I worked around the problem by adding an unnecessary initialization to
the frame1 variable that GCC was complaining about; see:

https://git.savannah.gnu.org/cgit/emacs.git/commit/?id=65ac27783a959a8339c2aab0f1e54d9b508a1f1f

and look for "GCC bug 85563"; Emacs has an UNINIT macro that is used to pacify
GCC when GCC isn't smart enough to see that a variable does not need to be
initialized.

Anyway, thanks for looking into it.

[Bug c/71157] -Wnull-dereference false alarm in wrong function

2018-09-16 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=71157

--- Comment #9 from Paul Eggert  ---
(In reply to Eric Gallager from comment #8)

> Try marking it up with __attribute__((returns_nonnull)) and/or
> __attribute__((nonnull)). If the first one works, then it's a case where GCC
> should suggest it, in which case it's bug 84203.

Neither suggestion works, unfortunately. That is, I tried undoing the
abovementioned patch to etags.c that works around the problem, and then
modifying the declaration of skip_spaces this way:

static char *skip_spaces (char *) __attribute__ ((nonnull (1)));

or this way:

static char *skip_spaces (char *) __attribute__ ((returns_nonnull));

Neither modification worked: in both cases I still got the bogus warnings. This
was with gcc (Ubuntu 7.3.0-16ubuntu3) 7.3.0.

[Bug tree-optimization/81401] False positive sprintf warning at O2 (-Wformat-overflow)

2018-05-30 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=81401

Paul Eggert  changed:

   What|Removed |Added

 CC||eggert at gnu dot org

--- Comment #3 from Paul Eggert  ---
Created attachment 44216
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=44216=edit
Extract from Emacs source code illustrating the bug

I see this bug's symptoms when compiling Emacs with gcc (GCC) 8.1.1 20180502
(Red Hat 8.1.1-1) on x86-64. I narrowed it down to the attached source file
x.i. When I compile it with:

gcc -S -Wformat-overflow=1 -O2 x.i

I get the following diagnostic, which is a false alarm as the sprintf call
cannot overflow because the value is obviously in the range 0..0x3F.

x.i: In function ‘x_draw_glyphless_glyph_string_foreground’:
x.i:29:22: warning: ‘__builtin___sprintf_chk’ may write a terminating nul past
the end of the destination [-Wformat-overflow=]
   sprintf (buf, "%0*X", ch < 0x1 ? 4 : 6, ch);
  ^
x.i:9:10: note: ‘__builtin___sprintf_chk’ output between 5 and 8 bytes into a
destination of size 7
   return __builtin___sprintf_chk (s, 1,
  ^~
   __builtin_object_size (s, 1), fmt,
   ~~
   __builtin_va_arg_pack ());
   ~

[Bug middle-end/85602] -Wsizeof-pointer-memaccess for strncat with size of source

2018-05-14 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=85602

--- Comment #4 from Paul Eggert  ---
Thanks, that workaround is much better for coreutils, and I installed it here:

https://git.savannah.gnu.org/cgit/coreutils.git/commit/?id=f6cb50cc991d461f443ea3afc517c9e1e37ef496

[Bug middle-end/85602] -Wsizeof-pointer-memaccess for strncat with size of source

2018-05-14 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=85602

--- Comment #2 from Paul Eggert  ---
Thanks for looking into it. For what it's worth, the practical effect of this
new warning was that I changed that part of coreutils to not use strncat,
causing 3 lines of code to grow to 8 lines. See the end of:

https://git.savannah.gnu.org/cgit/coreutils.git/commit/?id=9781fcd532f30afe174239a22816a83c40528b27

Another part of coreutils still uses strncat (also correctly). Let's hope GCC
doesn't start warning about it too

[Bug c/85562] -Wsuggest-attribute=malloc misleads about "returning normally"

2018-05-10 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=85562

Paul Eggert  changed:

   What|Removed |Added

 CC||eggert at gnu dot org

--- Comment #2 from Paul Eggert  ---
Also please see GCC bug 85734, which is about false alarms with
-Wsuggest-attribute=malloc.

[Bug c/85734] New: --suggest-attribute=malloc misdiagnoses static functions

2018-05-10 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=85734

Bug ID: 85734
   Summary: --suggest-attribute=malloc misdiagnoses static
functions
   Product: gcc
   Version: 8.1.1
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

GCC 8's --suggest-attribute=malloc diagnoses static functions, even though the
malloc attribute is useless for static functions (after all, the compiler has
deduced the property on its own). This is leading to my having to litter code
with '__attribute__ (malloc)' declarations merely to pacify GCC. GCC should
treat the malloc attribute like other attributes (e.g., const), and should
issue the diagnostic only for non-static functions where the attribute is in
fact useful.

This bug report differs from GCC bug 85562, in that this bug is about false
alarms whereas bug 85562 is about the wording of the diagnostics.

Here is an illustration of the bug. For this program:

#include 
   void *pe (void *x) { return x; }
static void *ps (void *x) { return x; }
   void *me (size_t n) { return malloc (n); }
static void *ms (size_t n) { return malloc (n); }
int main (void) { return !pe (me (1)) + !ps (ms (2)); }

gcc (GCC) 8.1.1 20180502 (Red Hat 8.1.1-1) x86-64, with the command:

gcc -Wsuggest-attribute=malloc -Wsuggest-attribute=const -O2 -S example.c

outputs the diagnostics at the end of this bug report. GCC correctly diagnoses
'pe' amd 'me', which are extern. GCC is correctly silent for the pure function
'ps', which is static. However, GCC mistakenly diagnoses 'ms', which is also
static.

example.c: In function ‘ms’:
example.c:5:14: warning: function might be candidate for attribute ‘malloc’ if
it is known to return normally [-Wsuggest-attribute=malloc]
 static void *ms (size_t n) { return malloc (n); }
  ^~
example.c: In function ‘pe’:
example.c:2:14: warning: function might be candidate for attribute ‘const’
[-Wsuggest-attribute=const]
void *pe (void *x) { return x; }
  ^~
example.c: In function ‘me’:
example.c:4:14: warning: function might be candidate for attribute ‘malloc’ if
it is known to return normally [-Wsuggest-attribute=malloc]
void *me (size_t n) { return malloc (n); }
  ^~

[Bug middle-end/85602] New: regression with strncat and -Wall in GCC 8

2018-05-01 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=85602

Bug ID: 85602
   Summary: regression with strncat and -Wall in GCC 8
   Product: gcc
   Version: 8.0.1
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: middle-end
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

Created attachment 44051
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=44051=edit
test program illustrating the regression

I ran into some problems building GNU Coreutils with gcc (GCC) 8.0.1 20180324
(Red Hat 8.0.1-0.20) and isolated it to the attached program w.c. The command
"gcc -Wall w.c" reports:

w.c: In function ‘main’:
w.c:11:35: warning: argument to ‘sizeof’ in ‘strncat’ call is the same
expression as the source; did you mean to use the size of the destination?
[-Wsizeof-pointer-memaccess]
   strncat (buf, u.ut_user, sizeof u.ut_user);

This diagnostic is quite wrong, and propagates confusion about strncat. Unlike
strncpy, strncat does not zero-fill the destination, and it is almost always
incorrect to do as GCC suggests which is to specify the size of the destination
as the third argument.

The source code is correct as-is: it is one of the few places where strncat is
the right function to use, as strncat was designed for struct utmp and similar
data structures. GCC 7 does not warn about this usage, and GCC 8 should not
warn either.

[Bug middle-end/48968] incorrect warning about longjmp/vfork clobbering a local (-W -O2, x86-64)

2017-12-26 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=48968

--- Comment #13 from Paul Eggert  ---
(In reply to Eric Gallager from comment #12)
> (In reply to Paul Eggert from comment #11)
> > Also please see related bugs Bug 21161, Bug 54561, Bug 61118, Bug 65041, Bug
> > 83162. Perhaps they should be merged?
> 
> Sure, but into which one?

I expect that merges typically go into the lowest-numbered bug, which in this
case is 21161.

[Bug c/83257] New: ICE with flexible array member and -fchkp-narrow-to-innermost-array

2017-12-02 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=83257

Bug ID: 83257
   Summary: ICE with flexible array member and
-fchkp-narrow-to-innermost-array
   Product: gcc
   Version: 7.2.1
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

Created attachment 42778
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=42778=edit
Source file illustrating compiler bug

I ran into this while trying to compile an experimental version of GNU Emacs
with GCC 7.2.1 20170915 (Red Hat 7.2.1-2) on Fedora 27 x86-64. To reproduce,
compile the attached program v.i with:

gcc -mmpx -fcheck-pointer-bounds -fchkp-narrow-to-innermost-array -S v.i

Output is:

v.i: In function ‘main.chkp’:
v.i:14:1: internal compiler error: Segmentation fault
 }
 ^
Please submit a full bug report,
...

The problem appears to be the use of the flexible array member, in combination
with the -fchkp-narrow-to-innermost-array option.

[Bug c/83251] __builtin___bnd_narrow_ptr_bounds(x, x, ...) generates wrong code that modifies a constant

2017-12-01 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=83251

--- Comment #1 from Paul Eggert  ---
Created attachment 42774
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=42774=edit
Test case subroutines (you also need foomain.i)

[Bug c/83251] New: __builtin___bnd_narrow_ptr_bounds(x, x, ...) generates wrong code that modifies a constant

2017-12-01 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=83251

Bug ID: 83251
   Summary: __builtin___bnd_narrow_ptr_bounds(x, x, ...) generates
wrong code that modifies a constant
   Product: gcc
   Version: 7.2.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

Created attachment 42773
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=42773=edit
Test case main program (you also need foobody.i)

I ran into this problem trying to use -fcheck-pointer-bounds on GNU Emacs. I
used gcc (Ubuntu 7.2.0-8ubuntu3) 7.2.0 on x86-64 (Ubuntu 17.10); my CPU was a
Kaby Lake processor (Intel Core i3-7100U) that supports Intel MPX. To
reproduce, compile and run the attached source code as follows:

gcc -mmpx -fcheck-pointer-bounds -O2 -S foobody.i foomain.i
gcc -mmpx -fcheck-pointer-bounds -O2 foobody.s foomain.s
./a.out

a.out's output contains many incorrect lines like this:

Saw a #BR! status 1 at 0x55fae4af26da

The problem occurs because incorrect code is generated for the function
'calculate_address', whose source code looks like this:

  Lisp_Object *sym = [1213];
  char *narsym = __builtin___bnd_narrow_ptr_bounds (sym, sym,
sizeof (Lisp_Object));
  return (Lisp_Object) (narsym + sizeof *sym);

This is a pure function that merely calculates an address and returns it.
Instead, as foobody.s shows, this function's implementation also modifies
global metadata, for example:

movq8+__chkp_bounds_of_lispsym(%rip), %rax
cmpq%rdx, %rax
cmovb   %rdx, %rax
movq%rax, 8+__chkp_bounds_of_lispsym(%rip)

Here calculate_address's implementation conditionally shrinks
__chkp_bounds_of_lispsym, the bounds of the 'lispsym' array. But lispsym is a
static array and its bounds should never change. As a result of this mistaken
implementation, later valid attempts to access the lispsym array (in
'obviously_safe') fail their bounds check and this mistake in GCC causes the
program to crash even though it is a valid program.

[Bug tree-optimization/83177] ICE with -mmpx -fcheck-pointer-bounds + __builtin___bnd_narrow_ptr_bounds + _setjmp

2017-11-27 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=83177

--- Comment #1 from Paul Eggert  ---
Created attachment 42727
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=42727=edit
Compiler output generated for crash on v.i

[Bug tree-optimization/83177] New: ICE with -mmpx -fcheck-pointer-bounds + __builtin___bnd_narrow_ptr_bounds + _setjmp

2017-11-27 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=83177

Bug ID: 83177
   Summary: ICE with -mmpx -fcheck-pointer-bounds +
__builtin___bnd_narrow_ptr_bounds + _setjmp
   Product: gcc
   Version: 7.2.1
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: tree-optimization
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---
  Host: x86-64

Created attachment 42726
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=42726=edit
Preprocessed source code illustrating the bug.

I got this when compiling an experimental version of GNU Emacs. I used GCC
7.2.1 20170915 (Red Hat 7.2.1-2) on x86-74 (Fedora 27). To reproduce, compile
the attached program via:

gcc -mmpx -fcheck-pointer-bounds -S v.i

The output is:

Unable to coalesce ssa_names 253 and 236 which are marked as MUST COALESCE.
__bound_tmp.11_253(ab) and  __bound_tmp.11_236(ab)
v.i: In function ‘internal_lisp_condition_case.chkp’:
v.i:143:1: internal compiler error: SSA corruption
 internal_lisp_condition_case (Lisp_Object var, Lisp_Object bodyform,
 ^~~~
Please submit a full bug report,
with preprocessed source if appropriate.
See <http://bugzilla.redhat.com/bugzilla> for instructions.
Preprocessed source stored into /tmp/ccZ79fr1.out file, please attach this to
y\
our bugreport.

I will attach /tmp/ccZ79fr1.out.

[Bug tree-optimization/80776] -Wformat-overflow false positive for %d on integer bounded by __builtin_unreachable

2017-11-25 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=80776

--- Comment #3 from Paul Eggert  ---
(In reply to Richard Biener from comment #1)
> Possibly the walk in remove_range_assertions visits the latter before the
> former block but in principle we do have code to handle this there.

I just ran into the same problem again, with the following code derived from
GNU Emacs, and it suggests that your diagnosis is correct. Perhaps this can be
used in a test case once the bug is fixed. If I remove the "if (! (0 <= i))
__builtin_unreachable ();" the bogus warning goes away, which suggests that the
earlier test is hiding the later one somehow. This is with GCC 7.2.1 20170915
(Red Hat 7.2.1-2) on x86-64.

extern __inline __attribute__ ((__always_inline__)) __attribute__
((__gnu_inline__)) __attribute__ ((__artificial__)) int
__attribute__ ((__nothrow__ , __leaf__)) sprintf (char *__restrict __s, const
char *__restrict __fmt, ...)
{
  return __builtin___sprintf_chk (__s, 2 - 1,
  __builtin_object_size (__s, 2 > 1), __fmt, __builtin_va_arg_pack ());
}
char number[sizeof "99"];
int somerandom (void);
void
Foo (void)
{
  int i = somerandom ();
  if (! (0 <= i))
__builtin_unreachable ();
  if (! (0 <= i && i <= 99))
__builtin_unreachable ();
  sprintf (number, "%d", i);
}

$ gcc -Wformat-overflow -O2 -S v.i
v.i: In function ‘Foo’:
v.i:17:21: warning: ‘%d’ directive writing between 1 and 10 bytes into a region
of size 7 [-Wformat-overflow=]
   sprintf (number, "%d", i);
 ^~
v.i:17:20: note: directive argument in the range [0, 2147483647]
   sprintf (number, "%d", i);
^~~~
v.i:4:10: note: ‘__builtin___sprintf_chk’ output between 2 and 11 bytes into a
destination of size 7
   return __builtin___sprintf_chk (__s, 2 - 1,
  ^~~~
   __builtin_object_size (__s, 2 > 1), __fmt, __builtin_va_arg_pack ());
   

[Bug middle-end/61118] [6/7/8 Regression] Indirect call generated for pthread_cleanup_push with constant cleanup function

2017-11-25 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=61118

--- Comment #14 from Paul Eggert  ---
Also please see related reports Bug 21161, Bug 48968, Bug 54561, Bug 65041, and
Bug 83162. The last-listed one also is a regression, perhaps induced by the
fancier optimization in recent GCC versions. I suspect that the bugs should be
merged.

[Bug middle-end/48968] incorrect warning about longjmp/vfork clobbering a local (-W -O2, x86-64)

2017-11-25 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=48968

--- Comment #11 from Paul Eggert  ---
Also please see related bugs Bug 21161, Bug 54561, Bug 61118, Bug 65041, Bug
83162. Perhaps they should be merged?

[Bug middle-end/21161] "clobbered by longjmp" warning ignores the data flow

2017-11-25 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=21161

Paul Eggert  changed:

   What|Removed |Added

 CC||eggert at gnu dot org

--- Comment #5 from Paul Eggert  ---
Also please see Bug 48968, Bug 54561, Bug 61118, Bug 65041, and Bug 83162,
which all seem to be related to this one.

[Bug middle-end/65041] Improve -Wclobbered

2017-11-25 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=65041

--- Comment #4 from Paul Eggert  ---
Also please see Bug 83162, which may be related.

[Bug c/83162] New: x86-64 -Wclobbered issuing more false alarms (regression)

2017-11-25 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=83162

Bug ID: 83162
   Summary: x86-64 -Wclobbered issuing more false alarms
(regression)
   Product: gcc
   Version: 7.2.1
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

Created attachment 42717
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=42717=edit
Test case for "gcc -O2 -S -Wclobbered" on x86-64

When building GNU Emacs we're finding that -Wclobbered is now issuing so many
false alarms that I think we will turn it off in more modules. I ran into this
problem again today, and narrowed it down to the attached program simplified
from Emacs. Compile and run it with:

gcc -O2 -S -Wclobbered clobbered.c

and GCC outputs:

clobbered.c: In function ‘module_vec_set’:
clobbered.c:22:29: warning: argument ‘vec’ might be clobbered by ‘longjmp’ or
‘vfork’ [-Wclobbered]
 module_vec_set (Lisp_Object vec, long i, Lisp_Object val)
 ^~~
clobbered.c:22:54: warning: argument ‘val’ might be clobbered by ‘longjmp’ or
‘vfork’ [-Wclobbered]
 module_vec_set (Lisp_Object vec, long i, Lisp_Object val)
  ^~~

Both diagnostics are bogus, since _setjmp's caller immediately returns if
_setjmp returns nonzero.

I am using gcc (GCC) 7.2.1 20170915 (Red Hat 7.2.1-2) on x86-64. I do not
observe the problem with gcc (GCC) 4.8.5 20150623 (Red Hat 4.8.5-16), so it is
a regression.

Also see Bug 21161, Bug 48968, Bug 54561, Bug 61118, and Bug 65041. This
particular test case appears to be new though, as it is a regression.

[Bug middle-end/65041] Improve -Wclobbered

2017-11-19 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=65041

Paul Eggert  changed:

   What|Removed |Added

 CC||eggert at gnu dot org

--- Comment #3 from Paul Eggert  ---
The bug for a2 seems related to Bug 21161, for which we have several
near-replicas (Bug 48968, Bug 54561, Bug 61118).

[Bug middle-end/61118] Spurious -Wclobbered warning generated by gcc 4.9.0 for pthread_cleanup_push

2017-11-19 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=61118

Paul Eggert  changed:

   What|Removed |Added

 CC||eggert at gnu dot org

--- Comment #12 from Paul Eggert  ---
(In reply to Yuri Gribov from comment #11)
> (In reply to Tavian Barnes from comment #10)
> > > I think it is - __cancel_arg is assigned inside a while loop
> > 
> > Specifically a do { } while(0); loop, which obviously has only one 
> > iteration.
> 
> Actually I was talking about surrounding while
> ((double)future->progress/future->total < progress)...

The variables in question do not survive from one iteration to the next of the
surrounding while loop, so they cannot contribute to a setjmp/longjmp problem.
The code looks like this:

  while ((double)future->progress/future->total < progress) {
...
void (*__cancel_routine) (void *) = (cleanup_fn);
void *__cancel_arg = (>mutex);
if (__sigsetjmp (((struct __jmp_buf_tag *) (void *)
  __cancel_buf.__cancel_jmp_buf),
 0)) {
  __cancel_routine (__cancel_arg);
  ...
}
...
  }

As the addresses of the locals do not escape and they are never assigned to
after initialization and they do not survive until the next call to
__sigsetjmp, the warnings are false alarms.

Possibly GCC is hoisting the locals out of the loop, incorrectly transforming
the above code into this:

  void (*__cancel_routine) (void *);
  void *__cancel_arg;
  while ((double)future->progress/future->total < progress) {
...
__cancel_routine = (cleanup_fn);
__cancel_arg = (>mutex);
if (__sigsetjmp (((struct __jmp_buf_tag *) (void *)
  __cancel_buf.__cancel_jmp_buf),
 0)) {
  __cancel_routine (__cancel_arg);
  ...
}
...
  }

where the warning would be valid.

Also see Bug 48968 which has similar symptoms.

[Bug c/82914] 'struct __attribute__ ((aligned (N))) s' ignores 'aligned' attribute

2017-11-09 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=82914

--- Comment #4 from Paul Eggert  ---
(In reply to Richard Biener from comment #2)

> You are not using aligned on a 'struct or struct member' but on the variable
> in all but (b).

If that's the intent, then GCC is mishandling the first example I gave in
comment #0:

  struct s { char mem; };
  __attribute__ ((aligned (8))) struct s a;
  struct __attribute__ ((aligned (8))) s b;
  struct s __attribute__ ((aligned (8))) c;
  struct s d __attribute__ ((aligned (8)));

Here, GCC says the alignment of 'b' is 1, not 8. What happened to the
attribute?

Later discussion in https://bugs.gnu.org/29183 has revealed that this first
example is also relevant to Emacs, and that Emacs crashes due to problems in
this area as well.

In summary there seems to be no straightforward way in GNU C to get what Emacs
wants, which is to say, "I want V's address to be a multiple of max(8, (natural
alignment for V))." I think I'll look into fixing Emacs to use unions instead.

Could you please fix the GCC documentation to clarify what's going on here? I
don't understand it myself, so I'm afraid any doc patch that I propose wouldc
be wrong.

[Bug c/82914] 'struct __attribute__ ((aligned (N))) s' ignores 'aligned' attribute

2017-11-08 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=82914

--- Comment #1 from Paul Eggert  ---
(In reply to Paul Eggert from comment #0)

Sorry, but my example in comment #0 (although it illustrates a bug) doesn't
illustrate the bug that crashed GCC. Here's a better example:

  struct t { long mem; };
  __attribute__ ((aligned (2))) struct t a;
  struct __attribute__ ((aligned (2))) t b;
  struct t __attribute__ ((aligned (2))) c;
  struct t d __attribute__ ((aligned (2)));

This compiles into:

.comm   a,8,2
.comm   b,8,8
.comm   c,8,2
.comm   d,8,2

Here, only 'b' is aligned correctly. The variables a, c, and d have an
alignment of only 2, but they should have an alignment of 8 because
__attribute__ ((aligned (8))) is documented to never decrease the alignment of
a structure, only to increase it. The GCC 7.2 documentation

says, "When used on a struct, or struct member, the 'aligned' attribute can
only increase the alignment; in order to decrease it, the 'packed' attribute
must be specified as well."

[Bug c/82914] New: 'struct __attribute__ ((aligned (N))) s' ignores 'aligned' attribute

2017-11-08 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=82914

Bug ID: 82914
   Summary: 'struct __attribute__ ((aligned (N))) s' ignores
'aligned' attribute
   Product: gcc
   Version: 7.2.1
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

I'm reporting a GCC problem that caused Emacs to SIGSEGV as described here:

https://bugs.gnu.org/29183

I tracked the problem down to an '__attribute__ ((aligned (8)))' that GCC
silently ignored. To reproduce the problem, consider the following program:

  struct s { char mem; };
  __attribute__ ((aligned (8))) struct s a;
  struct __attribute__ ((aligned (8))) s b;
  struct s __attribute__ ((aligned (8))) c;
  struct s d __attribute__ ((aligned (8)));

Compile this with 'gcc -S' on x86-64, and you get:

.comm   a,1,8
.comm   b,1,1
.comm   c,1,8
.comm   d,1,8

Although the variables a, c, and d are properly aligned, the variable b is not:
the 'aligned' attribute is silently ignored for b.

I reproduced this problem with GCC 7.2.1 20170915 (Red Hat 7.2.1-2), running on
Fedora 26 x86-64.

[Bug target/82170] gcc optimizes int range-checking poorly on x86-64

2017-09-11 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=82170

Paul Eggert  changed:

   What|Removed |Added

  Attachment #42149|0   |1
is obsolete||

--- Comment #5 from Paul Eggert  ---
Created attachment 42153
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=42153=edit
assembly-language output for poorly-optimized code, version 2

[Bug target/82170] gcc optimizes int range-checking poorly on x86-64

2017-09-11 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=82170

Paul Eggert  changed:

   What|Removed |Added

  Attachment #42148|0   |1
is obsolete||

--- Comment #4 from Paul Eggert  ---
Created attachment 42152
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=42152=edit
source code that is poorly optimized on x86-64, version 2

[Bug target/82170] gcc optimizes int range-checking poorly on x86-64

2017-09-11 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=82170

--- Comment #3 from Paul Eggert  ---
(In reply to Marc Glisse from comment #2)
> Note that n==(int)n (gcc documents that this must work) may work with more
> gcc versions and is more readable.

Thanks, good point, I'll suggest switching to that in glibc, and will update
the attachements accordingly. Still, the point remains that the portable code
should compile to something just as efficient as 'n == (int) n', which is not
portable.

[Bug target/82170] gcc optimizes int range-checking poorly on x86-64

2017-09-10 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=82170

--- Comment #1 from Paul Eggert  ---
Created attachment 42149
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=42149=edit
assembly-language output for poorly-optimized code

[Bug target/82170] New: gcc optimizes int range-checking poorly on x86-64

2017-09-10 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=82170

Bug ID: 82170
   Summary: gcc optimizes int range-checking poorly on x86-64
   Product: gcc
   Version: 7.1.1
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: target
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

Created attachment 42148
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=42148=edit
source code that is poorly optimized on x86-64

GCC on Fedora 26 x86-64 (GCC 7.1.1 20170622 (Red Hat 7.1.1-3) generates
poorly-optimized machine instructions for C code that tests in the obvious way
whether a 'long long' fits in 'int'. If n is long long, the expression (INT_MIN
<= n && n <= INT_MAX) should generate code that is no worse than
(!__builtin_add_overflow_p (n, 0, 0)). However, with -O2 optimization before
the conditional branch, the former expression generates four instructions
containing two literal constants, whereas the latter generates just two
instructions that reference only registers.

For the code that prompted this bug report we will likely use an "#if __GNUC__
< 7" that uses __builtin_add_overflow_p for GCC 7 and later, and the portable
code otherwise. It'd be nicer, though, if we could just use the portable code. 
See:

https://sourceware.org/ml/libc-alpha/2017-09/msg00411.html

Attached are a source program inrange.c and an assembly-language file inrange.s
produced by 'gcc -O2 -S' that illustrates the problem. Akthough the two
functions checked_arg_GCC7 and checked_arg_portable should have the same
machine code, the former is more efficient than the latter.

[Bug c/81650] New: gcc -m32 mishandles -Walloc-size-larger-than=9223372036854775807

2017-08-01 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=81650

Bug ID: 81650
   Summary: gcc -m32 mishandles
-Walloc-size-larger-than=9223372036854775807
   Product: gcc
   Version: 7.1.1
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

This is following up a Gnulib bug report:

http://lists.gnu.org/archive/html/bug-gnulib/2017-07/msg00150.html

which appears to stem from a bug in GCC. To reproduce the problem, compile the
following program:

extern void *malloc (unsigned long);
int
main (void)
{
  return !malloc (5);
}

with this shell command:

gcc -m32 -Walloc-size-larger-than=9223372036854775807 -S foo.c

On Fedora 26, gcc 7.1.1 20170622 (Red Hat 7.1.1-3) outputs the following false
alarm:

foo.c: In function 'main':
foo.c:5:11: warning: argument 1 value '5' exceeds maximum object size -1
[-Walloc-size-larger-than=]
   return !malloc (5);
   ^~
foo.c:1:14: note: in a call to allocation function 'malloc' declared here
 extern void *malloc (unsigned long);
  ^~

GCC works correctly (i.e., silently) if -m32 is omitted. Evidently GCC is not
doing the right thing when the operand of -Walloc-size-larger-than is too
large: such an operand should be treated as infinity, not as -1.

[Bug c/51309] -Wstrict-overflow false alarm when overflow impossible in loop body

2017-07-25 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=51309

--- Comment #2 from Paul Eggert  ---
(In reply to Eric Gallager from comment #1)
> I can't seem to reproduce the warning

Thanks, I can no longer reproduce the warning either. I used GCC 7.1.1 20170622
(Red Hat 7.1.1-3). So it looks like the problem is fixed.

[Bug sanitizer/80659] [7/8 Regression] -fsanitize=address evokes ICE in in gimplify_switch_expr

2017-05-16 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=80659

Paul Eggert  changed:

   What|Removed |Added

 CC||eggert at gnu dot org

--- Comment #8 from Paul Eggert  ---
(In reply to jim from comment #5)

Here's a simpler test case that illustrates the same bug (GCC 7.1.0, x86-64,
compiled via "gcc -O2 -S -fsanitize=address v2.i"):

  typedef struct Lisp_Object { long i; } Lisp_Object;
  struct Lisp_String { char *data; };

  Lisp_Object
  server_accept_connection (int sa_family)
  {
switch (sa_family)
  {
  default:;
Lisp_Object x = (Lisp_Object) { (long) &(struct Lisp_String) {">"} + 4
};
return x;
  }
  }

[Bug c/80787] New: gcc -Wmaybe-uninitialized false negative when compiling Emacs

2017-05-16 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=80787

Bug ID: 80787
   Summary: gcc -Wmaybe-uninitialized false negative when
compiling Emacs
   Product: gcc
   Version: 7.1.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

I found this problem when compiling GNU Emacs with GCC 7.1.0 and with Clang
3.9.1.  GCC missed an uninitialized-variable bug that Clang correctly warned
about. To reproduce the problem with GCC 7.1.0 x86-64, compile the following
stripped-down test case:

  _Bool
  xg_update_scrollbar_pos (int a, int b)
  {
_Bool hidden;
if (a < b)
  hidden = 1;
return !hidden;
  }

using the command:

  gcc -O2 -Wall -S u.i

GCC does not warn, even though 'hidden' is a possibly-uninitialized variable.
With the same options, Clang warns about the bug.

[Bug c/80776] New: -Wformat-overflow false positive for %d on integer bounded by __builtin_unreachable

2017-05-16 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=80776

Bug ID: 80776
   Summary: -Wformat-overflow false positive for %d on integer
bounded by __builtin_unreachable
   Product: gcc
   Version: 7.1.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

I found this problem when compiling Emacs with GCC 7.1.0 on x86-64. Emacs uses
__builtin_unreachable to let the compiler know about ranges and thereby
suppress false alarms. Here is a stripped-down example of the bug:

  extern int sprintf (char *restrict, const char *restrict, ...)
__attribute__ ((__nothrow__));
  extern int foo (void);

  int
  Fgenerate_new_buffer_name (void)
  {
char number[2];
int i = foo ();
if (i < 0)
  __builtin_unreachable ();
if (i >= 2)
  __builtin_unreachable ();
return sprintf (number, "%d", i);
  }

Compile this with:

  gcc -c -Wformat-overflow -O2  t.i

The output is:

t.i: In function 'Fgenerate_new_buffer_name':
t.i:14:28: warning: '%d' directive writing between 1 and 10 bytes into a
region\
 of size 2 [-Wformat-overflow=]
   return sprintf (number, "%d", i);
^~
t.i:14:27: note: directive argument in the range [0, 2147483647]
   return sprintf (number, "%d", i);
   ^~~~

The diagnostic is incorrect, as the directive argument I is in the range [0,
1]. Changing the two ifs to read just "if (i < 0 || i >= 2)
__builtin_unreachable ();" works around this particular bug, but other variants
show similar problems.

[Bug debug/80646] [5/6/7 Regression] wrong type info for extern inline function when compiling Emacs

2017-05-08 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=80646

--- Comment #3 from Paul Eggert  ---
(In reply to Richard Biener from comment #1)

> So I start to belive this is a gdb bug.

Thanks, I filed a GDB bug report here:

https://sourceware.org/bugzilla/show_bug.cgi?id=21473

[Bug ipa/53896] nonreturning function suggested as 'pure' candidate

2017-05-05 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=53896

--- Comment #3 from Paul Eggert  ---
(In reply to Martin Liška from comment #2)
> it's still up to user to mark the function as pure.

Thanks for looking into it. We have worked around the problem in GNU Emacs by
avoiding the -Wsuggest-attribute=pure option. It might be helpful to document
this limitation of -Wsuggest-attribute=pure, and perhaps the option should even
be deprecated due to its limited utility.

[Bug debug/80646] New: [Regression] wrong type info for extern inline function when compiling Emacs

2017-05-05 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=80646

Bug ID: 80646
   Summary: [Regression] wrong type info for extern inline
function when compiling Emacs
   Product: gcc
   Version: 6.3.1
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: debug
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

Created attachment 41327
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=41327=edit
gzipped tarball of three source files illustrating the bug

GCC 6.3.1 x86-64 20161221 (Red Hat 6.3.1-1) outputs incorrect debug information
for inline functions in some cases, and this can make programs hard to debug.
The problem does not occur for GCC 4.8.5 20150623 (Red Hat 4.8.5-11), so this
appears to be a regression.

I ran into the problem while attempting to debug GNU Emacs, and constructed a
small test case to illustrate it. To reproduce it on Fedora 25 x86-64 with
6.3.1 20161221, extract the files lisp.h, t.c and u.c from the attached
tarball, and compile them by running the shell command:

gcc -g3 -O2 t.c u.c

Then use GDB as follows:

$ gdb a.out
...
(gdb) ptype make_number
type = int ()
(gdb) ptype make_natnum
type = struct {
long i;
} (long)
(gdb) ptype XIL
type = struct {
long i;
} (long)
(gdb)

The reported type of 'make_number' is incorrect: it should be the same type as
that of make_natnum and XIL, but instead is a function returning 'int'. This
incorrect type can cause GDB to print incorrect results in expressions
involving make_number. Looking at the assembly-language output, it appears that
GCC is generating the wrong debug information for this example.

[Bug c/80515] __attribute__ ((__noreturn__)) false alarm for 'main'

2017-04-25 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=80515

--- Comment #6 from Paul Eggert  ---
> main always return according to the standard

No, the C standard does not require 'main' to return. It's perfectly acceptable
for 'main' to never return, and many programs are written that way.

> what you are asking for is a non standard extension

Any program that uses '__attribute__ ((__noreturn__))' is *already* using a
nonstandard extension. It would be more useful if this nonstandard extension
worked for 'main' like it does for other functions, because many 'main'
functions in fact do not return.

[Bug c/80515] __attribute__ ((__noreturn__)) false alarm for 'main'

2017-04-25 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=80515

--- Comment #4 from Paul Eggert  ---
> main() has an implicit return 0.

That's irrelevant to the purpose of the warning. The warning is there to catch
the common typo of a function containing a return statement even though it is
declared 'noreturn'. But there is no typo here.

As it stands now, the 'main' function cannot have __attribute__
((__noreturn__)), even when 'main' is designed to never return. This
restriction makes no sense from the user's point of view.

[Bug c/80515] New: __attribute__ ((__noreturn__)) false alarm for 'main'

2017-04-25 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=80515

Bug ID: 80515
   Summary: __attribute__ ((__noreturn__)) false alarm for 'main'
   Product: gcc
   Version: 6.3.1
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

For this one-line C program:

__attribute__ ((__noreturn__)) int main (void) { for (;;); }

GCC complains:

: warning: function declared ‘noreturn’ has a ‘return’ statement

even though the 'main' function does not have a 'return' statement.

[Bug c/68971] -Woverflow false alarm in code unreachable after __builtin_mul_overflow

2017-02-15 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68971

--- Comment #12 from Paul Eggert  ---
Ah, sorry, I am using GCC 6.3.1, whereas __builtin_mul_overflow_p is a GCC
7-ism.  Somehow I got it into my head that __builtin_mul_overflow(A,B,C) should
be a constant expression if A, B, are constant expressions and C is a
(constant) null pointer, but evidently that's not the case. Since the problem
must be fixed in GCC 7 with its new __builtin_mul_overflow_p primitive, please
close this bug.

[Bug c/68971] -Woverflow false alarm in code unreachable after __builtin_mul_overflow

2017-02-15 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68971

--- Comment #10 from Paul Eggert  ---
Unfortunately, the patch for Bug#68120 does not seem to have addressed the
problem here. For example, although the following code uses the new feature
enabled by that patch:

  int f (void) {
return (__builtin_mul_overflow (0x7fff, 0x7fff, (int *) 0)
? 2
: 0x7fff * 0x7fff);
  }

I still get the following warning with GCC 6.3.1 20161221 (Red Hat 6.3.1-1)
x86-64:

t.c: In function ‘f’:
t.c:4:19: warning: integer overflow in expression [-Woverflow]
  : 0x7fff * 0x7fff);
   ^

[Bug middle-end/4210] should not warning with dead code

2017-02-15 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=4210

--- Comment #25 from Paul Eggert  ---
I'd like this bug to be changed from SUSPENDED to CONFIRMED, given that it's
continuing to be a problem (e.g., bug#79479).

Also, I'd like to suggest what I hope is a simple fix. In 2006 Joseph wrote
"skip_evaluation can't be set for if (0) because you can jump into if (0),
whereas jumps into statement expressions are not permitted". So, how about if
we merely set skip_evaluation for "if (0)" when the then-part lacks labels?
This should be an easy test, as it shouldn't require parsing the whole function
body. The test might still generate false alarms for code containing gotos, but
in practice such gotos are rare, so the proposed change should be a significant
improvement even if it's not perfect.

[Bug c/79479] -Woverflow false alarm in unreachable expression

2017-02-15 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=79479

--- Comment #14 from Paul Eggert  ---
Thanks, please feel free to mark this as a duplicate of Bug#4210. I plan to
follow up there.

[Bug c/79479] -Woverflow false alarm in unreachable expression

2017-02-14 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=79479

--- Comment #12 from Paul Eggert  ---
If the proposed change would introduce significant problems with false
positives or false negatives, then surely GCC already has these problems in
conditional expressions. These problems ought to be addressed regardless of
what GCC does with conditional statements. What false-positive and/or
false-negative problems are these? Should they have bug reports?

I'm still mystified as to why a conditional statement should generate false
positives that the equivalent conditional expression does not generate. This
makes little sense from the programmer's point of view.

[Bug c/79479] -Woverflow false alarm in unreachable expression

2017-02-13 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=79479

--- Comment #9 from Paul Eggert  ---
> 1) It's too subtle for non-expert programmers to understand.

Actually, it's typically easy for non-experts to follow this. For example,
although GCC falsely warns about this:

  /*1*/ if (0) return INT_MAX + 1; else return 0;

GCC handles this correctly:

  /*2*/ return 0 ? INT_MAX + 1 : 0;

If /*1*/ were really "too subtle" for non-experts, /*2*/ would also be "too
subtle". In practice, though, /*2*/ is working well and is not "too subtle",
and GCC should be able to make /*1*/ work as well.

> 2) It's unclear under what conditions the warning should or should not be
> issued.

As a first approximation, have GCC treat /*1*/ like it treats /*2*/.

> What if the controlling expression evaluates to zero but is not a
> constant expression?

Do what /*2*/ does.

> With or without optimization?

Again, do what /*2*/ does.

> 3) Avoiding the warning would require removing the implementation from the
> front end and adding it to the middle-end, which tends to lead to
> inconsistencies and both false positives and negatives.  (This isn't an
> argument against also handling the overflow in the middle-end, as
> -Wstrict-overflow does, but rather one against removing it from the front 
> end.)

Perhaps, given GCC's current internal structure it's nontrivial to fix GCC to
eliminate the false alarms.  However, this doesn't affect the fact that they
are false alarms, and that problems in this area are due to problems in GCC's
internal structure rather than being problems intrinsic to the analysis of C
programs.

> 4) There are a number of similar warnings that behave the same way (e.g.,
> -Wshift-negative-value, -Wshift-count-overflow and -Wshift-overflow).  GCC
> should be consistent in handling all these and so all the others would need to
> change as well.

Yes, that sounds right.

> 5) There is an easy way to rewrite the code to avoid the warning:
>
>   int too_large (long x)
>   {
>   #if INT_MAX < LONG_MAX   // or in GCC 7, INT_SIZE < LONG_SIZE
> return 32768 * 65536L < x;
>   #else
> return 0;
>   #endif
>   }

Although #if works for this particular example, it does not work with modern
programming styles that try to avoid the preprocessor for various good reasons.
Worse, #if does not work for expressions that contain constants that are not
visible to the C proprocessor. In the following example, GCC reports a false
alarm and this cannot be handled by the preprocessor because the preprocessor
cannot see the values of ELTS and MULTIPLIER. Another example: sizeof is
commonly involved in overflow checks, and the preprocessor cannot handle
sizeof.

#include 
/* Assume these are supplied by some header elsewhere, as enums.  */
enum { ELTS = 10, MULTIPLIER = 10 };
/* Return ELTS times MULTIPLIER.  If the result would overflow,
   return the closest representable value.  */
int ELTS_times_MULTIPLIER_saturated (void) {
  enum { a = ELTS, b = MULTIPLIER };
  if (b < 0) {
if (a < 0) {
  if (INT_MAX / b <= a)
return INT_MAX;
} else {
  if (b != -1 && INT_MIN / b < a)
return INT_MIN;
}
  } else if (b != 0) {
if (a < 0) {
  if (a < INT_MIN / b)
return INT_MIN;
} else {
  if (INT_MAX / b < a)
return INT_MAX;
}
  }
  return a * b;
}

[Bug c/79479] -Woverflow false alarm in unreachable expression

2017-02-13 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=79479

--- Comment #7 from Paul Eggert  ---
> the translation of a program that contains an overflowing constant expression 
> has undefined behavior

Sure, but the programs in question do not contain constant expressions in sense
of the C standard. They contain expressions that consist entirely of constants,
which is a different thing. For example, assuming 32-bit int the following
program contains the constant expression 'INT_MAX + 1' and the C standard
requires a diagnostic for the overflow: 

  #include 
  int F (void) {
if (0) {
  static int too_big = INT_MAX + 1;
  return too_big != 0;
}
return 0;
  }

In contrast, the following program is valid C code and its behavior is
well-defined because 'INT_MAX + 1' is not a constant expression (in the
C-standard sense) and it is never evaluated:

  #include 
  int G (void) {
if (0) {
  int too_big = INT_MAX + 1;
  return too_big != 0;
}
return 0;
  }

This bug report is about the latter kind of program. In practice these are
often useful programs and GCC's overflow diagnostics are false alarms.

[Bug c/79479] New: -Woverflow false alarm in unreachable expression

2017-02-12 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=79479

Bug ID: 79479
   Summary: -Woverflow false alarm in unreachable expression
   Product: gcc
   Version: 6.3.1
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

Created attachment 40722
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=40722=edit
gcc -m32 -Woverflow incorrectly complains about this

Compile the attached program with:

gcc -m32 -S too-large.c

and it responds:

too-large.c: In function ‘too_large’:
too-large.c:5:18: warning: integer overflow in expression [-Woverflow]
 return 32768 * 65536L < x;

Since the expression 32768 * 65536L cannot be executed on this platform (and
this is by design, the code tests whether the multiplication is advisable
before  trying it), the warning is a false alarm.

Bruno Haible originally reported this problem in bug-gnulib, here:

http://lists.gnu.org/archive/html/bug-gnulib/2017-02/msg00041.html

As this sort of thing is common in portable code that is checking for overflow
correctly, I suggest disabling -Woverflow tests inside unreachable expressions.

[Bug debug/78685] -Og generates too many ""s

2016-12-21 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=78685

--- Comment #5 from Paul Eggert  ---
Just to clarify: 'main' (in the sample program) is just an example. The
problems developers are seeing when debugging Emacs almost all involve
functions other than 'main'.

It should be OK for -Og to optimize significantly less than it does now, so
long as -Og remains better than -O0. As things stand, -Og is pretty much
useless for its stated purpose because GDB so often cannot display values of
locals, and I expect this partly explains why -Og is so rarely used in
practice.

In Emacs, developers use -O0 for debugging, but this can be reeeaally slow
because -O0 does not inline and Emacs relies heavily on small inlined
functions. Although Emacs works around this problem by using macros instead of
functions, such workarounds have obvious drawbacks. For Emacs, it would be nice
if -Og did not discard locals, but continued to inline.

[Bug debug/78685] New: -Og generates too many ""s

2016-12-05 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=78685

Bug ID: 78685
   Summary: -Og generates too many ""s
   Product: gcc
   Version: 6.2.1
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: debug
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---
  Host: x86-64

Created attachment 40253
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=40253=edit
preprocessed C program illustrating -Og problem

Emacs developers are having trouble using -Og to debug Emacs, and so are still
using -O0; see, for example:

http://lists.gnu.org/archive/html/emacs-devel/2016-12/msg00199.html

I reproduced the problem and came up with a small program (attached) that
illustrates it. Here's a sample transcript on Fedora 24 x86-64, which uses gcc
(GCC) 6.2.1 20160916 (Red Hat 6.2.1-2):

$ gcc -Og -g3 Ogbug.i
$ gdb a.out
GNU gdb (GDB) Fedora 7.11.1-86.fc24
...
Reading symbols from a.out...done.
(gdb) b call_debugger
Breakpoint 1 at 0x4004d6: file Ogbug.i, line 6.
(gdb) r
Starting program: /home/eggert/junk/a.out 

Breakpoint 1, call_debugger (x=3) at Ogbug.i:6
6 v = x;
(gdb) bt
#0  call_debugger (x=3) at Ogbug.i:6
#1  0x00400519 in apply_lambda (fun=1, args=2, count=)
at Ogbug.i:14
#2  0x00400547 in main (argc=, argv=)
at Ogbug.i:22


It's hard to debug a program with all those ""s getting in the
way.

[Bug c/78339] New: -fcheck-pointer-bounds breaks -fsuggest-attribute=noreturn on main 'exit'

2016-11-13 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=78339

Bug ID: 78339
   Summary: -fcheck-pointer-bounds breaks
-fsuggest-attribute=noreturn on main 'exit'
   Product: gcc
   Version: 6.2.1
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

I found this bug when trying to build Emacs with -fcheck-pointer-bounds.
Suppose the file profile.i contains:

extern _Noreturn void exit (int);
int main (void) { exit (1); }

Then when GCC 6.2.1 20160916 (Red Hat 6.2.1-2) x86-64 is invoked like this:

gcc -S -mmpx -fcheck-pointer-bounds -Wsuggest-attribute=noreturn profile.i

GCC issues the following bogus complaint:

profile.i: In function 'main.chkp':
profile.i:2:5: warning: function might be candidate for attribute 'noreturn'
[-Wsuggest-attribute=noreturn]
 int main (void) { exit (1); }
 ^~~~

The bogus complaint is not issued if the option -fcheck-pointer-bounds is
removed.

[Bug c/78081] New: -Wmaybe-initialized false-alarm regression for Emacs regex.c

2016-10-22 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=78081

Bug ID: 78081
   Summary: -Wmaybe-initialized false-alarm regression for Emacs
regex.c
   Product: gcc
   Version: 6.2.1
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

Created attachment 39869
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=39869=edit
test program illustrating -Wmaybe-uninitialized false alarm

I found this when compiling a test version of GNU Emacs with gcc (GCC) 6.2.1
20160916 (Red Hat 6.2.1-2) on x86-64. The problem does not occur with gcc (GCC)
4.8.5 20150623 (Red Hat 4.8.5-4) on x86-64 so this appears to be a regression.

The problem caused the Emacs build to fail when configured with
--enable-gcc-warnings, when compiling src/regex.c. I reduced the problem case
to a relatively small source file u2.i (attached). Compile it with the command:

gcc -S -Werror=maybe-uninitialized -O2 u2.i

GCC will complain as follows and then fail:

u2.i: In function 're_search_2':
u2.i:59:42: error: 'offset2' may be used uninitialized in this function
[-Werro\
r=maybe-uninitialized]
   if (string2) string2 = offset2 + new_base;
  ^~

This diagnostic is incorrect, as offset2 must be initialized, using the same
reasoning that offset1 must be initialized (which GCC gets right).

[Bug c/77876] New: -Wbool-operation rejects useful code involving '~'

2016-10-05 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=77876

Bug ID: 77876
   Summary: -Wbool-operation rejects useful code involving '~'
   Product: gcc
   Version: 7.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

GCC's recently-added -Wbool-operation flag rejects useful code like this:

#include 
enum { BILLION = 1000 * 1000 * 1000 };
time_t foo (time_t s, int res) { return s & ~ (res == 2 * BILLION); }

This is a simplified version of Gnulib code using '~' that runs afoul of
-Wbool-operation; see the bug report here:

http://lists.gnu.org/archive/html/bug-gnulib/2016-10/txtbxk_mHAW_p.txt

Rather than contort user code to pacify this misguided warning, I suggest
making the warning more useful. The fundamental bug here is not applying ~ to a
boolean; it's storing ~x into a boolean. More generally, the problem occurs
when converting an expression that GCC can't prove to be 0 or 1 to bool. GCC
should check for that instead. This would catch not only thinkos with ~ and ++
and --, but also similar thinkos involving other integer and floating-point
operations. And it would correctly accept the Gnulib code.

[Bug c/71157] -Wnull-dereference false alarm in wrong function

2016-07-04 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=71157

--- Comment #6 from Paul Eggert  ---
> this is because it thinks skip_space() may return NULL:

That sounds like a bug, then, as skip_spaces immediately dereferences its
argument, so it cannot possibly return NULL.

Also, skip_spaces is never passed an argument that could possibly be NULL, so
even if the function simply returns its argument the result cannot be NULL.

[Bug c/71157] -Wnull-dereference false alarm in wrong function

2016-05-19 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=71157

--- Comment #4 from Paul Eggert  ---
I worked around the GCC bug by applying the attached file etags.c.patch to GNU
Emacs. etags.c.patch replaces some weird but valid C code (add a small constant
to a pointer and test whether the resulting pointer is non-null, a test that
always yields 1) with more-normal code (add a small constant to a pointer, then
yield 1). After preprocessing, this yields the attached file e-patched.i, and
the command 'gcc -O2 -S -Wnull-dereference e-patched.i' does not issue the
bogus warnings.

[Bug c/71157] -Wnull-dereference false alarm in wrong function

2016-05-19 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=71157

--- Comment #3 from Paul Eggert  ---
Created attachment 38532
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=38532=edit
patched version of e.i that avoids GCC bug

[Bug c/71157] -Wnull-dereference false alarm in wrong function

2016-05-19 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=71157

--- Comment #2 from Paul Eggert  ---
Created attachment 38531
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=38531=edit
GNU Emacs lib-src/etags.c patch to work around GCC bug

[Bug c/71157] New: -Wnull-dereference false alarm in wrong function

2016-05-16 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=71157

Bug ID: 71157
   Summary: -Wnull-dereference false alarm in wrong function
   Product: gcc
   Version: 6.1.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

Created attachment 38504
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=38504=edit
preprocessed source code for emacs/lib-src/etags.c

I discovered this when compiling bleeding-edge GNU Emacs with GCC 6.1.0 on
x86-64. For the attached file e.i, the shell command:

gcc -O2 -S -Wnull-dereference e.i

issues the diagnostics:

e.i: In function 'Forth_words':
e.i:9690:10: warning: potential null pointer dereference [-Wnull-dereference]
   while (*cp != '\0' && !c_isspace (*cp))
  ^~~
e.i:9690:10: warning: potential null pointer dereference [-Wnull-dereference]
e.i:9690:10: warning: potential null pointer dereference [-Wnull-dereference]

I see three things wrong with these diagnostics. First, line 9690 is nowhere
near the function Forth_words. Second, I see no path to line 9690 in which its
pointer CP can possibly be null. Furthermore, CP is dereferenced only twice in
line 9690, so why are there three warnings?

[Bug c/68120] can't easily deal with integer overflow at compile time

2016-05-01 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68120

--- Comment #6 from Paul Eggert  ---
(In reply to Martin Sebor from comment #5)
> Patch posted for review:
> https://gcc.gnu.org/ml/gcc-patches/2016-05/msg00013.html

Thanks. This patch appears to address almost all the request, and it is
definitely a step forward.

Even with the change, I see no easy way in a constant expression to compute the
bottom-order bits (ignoring overflow) of a signed integer value, but I can
raise this issue as a separate enhancement request if it turns into a problem
in practice.

[Bug c++/69763] _Alignof(double) in C gives different results from alignof(double) in C++

2016-02-10 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=69763

Paul Eggert  changed:

   What|Removed |Added

 CC||eggert at gnu dot org

--- Comment #1 from Paul Eggert  ---
In bug 52023 Joseph S. Myers wrote that the C++11 alignof was left alone, so
that it is different from C11 alignof. I don't know why this was done, but it
does appear to be deliberate. See:

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=52023#c14

[Bug c/68971] -Woverflow false alarm in code unreachable after __builtin_mul_overflow

2015-12-18 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68971

--- Comment #6 from Paul Eggert  ---
(In reply to Martin Sebor from comment #5)
> This is a valid constant expression

I'm aware of the distinction between constant and other expressions. I'm trying
to give the ordinary user's viewpoint, not the viewpoint of a language
standards nerd. From the ordinary user's viewpoint GCC is busted here because
it is crying wolf. There are tons of other places where GCC could cry wolf
while following the letter of the standard, but GCC doesn't do that because in
practice crying wolf is counterproductive.

> since __builtin_mul_overflow has already computed the product it
> seems that the result should be used rather than computed again using plain
> multiplication.

It's a test program, and it's doing things twice in order to test them for
consistency. You're right, most likely this particular combination wouldn't
occur except in test programs. So it could be that the use of -Wno-overflow can
be limited to test programs, if we're lucky. Still, it'd be better if GCC were
fixed to not cry wolf in situations like these.

[Bug c/68971] -Woverflow false alarm in code unreachable after __builtin_mul_overflow

2015-12-18 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68971

--- Comment #8 from Paul Eggert  ---
(In reply to Martin Sebor from comment #7)

> Perhaps what's needed is for GCC to treat the builtins as constant
> expressions when they're invoked with them as operands.  If you agree with
> that approach, I suggest closing this bug and opening a new one with that
> request.

Yes, I already filed a bug report along these lines, as Bug#68120.

> because sophisticated warnings that try to avoid
> issuing false positives for unreachable code (e.g., -Wmaybe-uninutialized)
> depend on optimizations they tend to be inconsistent not only between
> optimization settings but also between different targets.

Yes, that issue is well known. We generally work around the problem by enabling
fancy warnings only on one platform (x86-64) with known settings, and not
bothering with other platforms. A corollary of this practice is that
warning-related GCC bugs tend not to be reported or fixed on platforms other
than x86-64.

However, this workaround does not suffice for -Woverflow because -Woverflow is
enabled by default. This raises the priority of getting -Woverflow right.

[Bug c/68120] can't easily deal with integer overflow at compile time

2015-12-18 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68120

--- Comment #2 from Paul Eggert  ---
(In reply to Paul Eggert from comment #0)
> I am working around the problem with macro definitions like this:
> 
>  # define INT_ADD_OVERFLOW(a, b) \
>(__builtin_constant_p ((a) == (b)) \
> ? _GL_INT_ADD_OVERFLOW (a, b) \
> : __builtin_add_overflow (a, b, &(__typeof__ ((a) + (b))) {0}))

Just to follow up on my own bug report, the above approach turned out not to
work, because the resulting macro expands to an expression that is not an
integer constant expression according to GCC's current rules. I eventually gave
up on this approach entirely, and INT_ADD_OVERFLOW (a, b) now expands to this:

  (0 * (0 * (b) + (a)) - (1)) < 0) ? - (~ (0 * (0 * (b) + (a)) + (0)) ==
-1) - 0 * (0 * (b) + (a)) + (1)) << (sizeof ((0 * (b) + (a)) + 0) * 8 - 2))
- 1) * 2 + 1) : (0 * (0 * (b) + (a)) + (0 < 0 ? ((b) < 0 ? (a) < 0 * (0
* (b) + (a)) - (1)) < 0) ? - (~ (0 * (0 * (b) + (a)) + (0)) == -1) - 0 * (0
* (b) + (a)) + (1)) << (sizeof ((0 * (b) + (a)) + 0) * 8 - 2)) - 1) * 2 + 1) :
(0 * (0 * (b) + (a)) + (0 - (b) : 0 * (0 * (b) + (a)) - (1)) < 0) ?
0 * (0 * (b) + (a)) + (1)) << (sizeof ((0 * (b) + (a)) + 0) * 8 - 2)) - 1)
* 2 + 1) : (0 * (0 * (b) + (a)) - (1 - (b) < (a)) : (a) < 0 ? (b) <= (a) +
(b) : (b) < 0 ? (a) <= (a) + (b) : (a) + (b) < (b))

Although this *is* an integer constant expression, it is less nice than a
simple call to __builtin_add_overflow would be, and it generates less-efficient
code in some cases when A and B are not constants.

[Bug c/68971] New: -Woverflow false alarm in code unreachable after __builtin_mul_overflow

2015-12-17 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68971

Bug ID: 68971
   Summary: -Woverflow false alarm in code unreachable after
__builtin_mul_overflow
   Product: gcc
   Version: 5.3.1
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

Compile the following code with 'gcc -O2 -S u.c' (x86-64, GCC 5.3.1 20151207
(Red Hat 5.3.1-2)):

  int
  main (void)
  {
int result;
return (__builtin_mul_overflow (0x7fff, 0x7fff, )
? 2
: result == 0x7fff * 0x7fff);
  }

GCC complains:

  u.c: In function ‘main’:
  u.c:7:29: warning: integer overflow in expression [-Woverflow]
: result == 0x7fff * 0x7fff);
 ^

But line 7 is unreachable, and GCC determined this (as can be seen in the
assembly-language output: 'main' simply returns 2 unconditionally). GCC should
not warn about integer overflows in unreachable code.

This bug appears to be independent of Bug#4210, as the problem occurs in both
if statements and if expressions.

This bug is causing problems with gnulib; see:

http://lists.gnu.org/archive/html/bug-gnulib/2015-12/msg00011.html

I guess we'll work around it in the meantime by compiling the program with
-Wno-overflow, but GCC should get fixed.

[Bug c/68971] -Woverflow false alarm in code unreachable after __builtin_mul_overflow

2015-12-17 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68971

--- Comment #4 from Paul Eggert  ---
(In reply to Martin Sebor from comment #1)
> constant expressions are evaluated during translation

This is not a constant expression. Not that that should matter. For example:

  enum { a = (1 ? 0 : 1 / 0) };
  enum { b = (1 ? 0 : 0x7fff * 0x7fff) };

Both integer constant expressions are valid C, and GCC (correctly) doesn't warn
about either of them.

> The program is incorrect and the warning helps find the bug.

No, the program has perfectly well-defined runtime behavior in GNU C because
the integer overflow is not evaluated. There is no bug here, and GCC's warning
is a false alarm.

This problem was occurring in gnulib, and we have worked around it in gnulib by
disabling -Woverflow in the affected translation unit. As a practical matter it
would be better if -Woverflow did not generate false alarms in cases like this,
as the false alarms will cause -Woverflow to be disabled in more places. Which
would be too bad, as __builtin_mul_overflow etc. are likely to be used in
programs where -Woverflow would otherwise be quite useful.

[Bug c/68193] New: _Generic -Woverflow false alarm

2015-11-02 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68193

Bug ID: 68193
   Summary: _Generic -Woverflow false alarm
   Product: gcc
   Version: 5.2.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

I ran into this problem when developing Gnulib code.  This is with GCC 5.2.0 on
x86-64.  Compile the following program t.c with 'gcc -Wall t.c':

int
main (void)
{
  int i = 0;
  int j = _Generic (i,
int: 0,
long int: (i = (long int) 9223372036854775808UL));
  return i + j;
}

GCC generates the bogus warning:

t.c: In function 'main':
t.c:7:22: warning: overflow in implicit constant conversion [-Woverflow]
   long int: (i = (long int) 9223372036854775808UL));
  ^

The warning is bogus because the corresponding expression is not evaluated, as
per the semantics of _Generic.

Add 1 to that big constant, changing it to 9223372036854775809UL, and the bogus
warning goes away.  So it's possible that there are two bugs here, one having
to do with bogus warnings in unevaluated _Generic subexpressions, the other
having to do with (unsigned long) LONG_MIN.

[Bug target/68110] __builtin_sub_overflow unsigned performance issue

2015-10-27 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68110

--- Comment #3 from Paul Eggert  ---
(In reply to Andrew Pinski from comment #2)
> So the question is does anyone use this function without "a - b" later on? 

Not that I know of. The usual pattern for callers of the Gnulib macro is to use
the macro to check whether there's overflow, and then to subtract if the result
wouldn't overflow. So you're correct that my example is a microbenchmark and is
not a good representative.

That being said, and I'm just thinking aloud here, it may be helpful for GCC to
try "a < b" as an alternative way to test for unsigned subtraction overflow, or
conversely to have GCC use __builtin_sub_overflow as an alternative way to
compute "a < b". Here's a slightly-more-realistic example:

  unsigned long
  sub1 (unsigned long a, unsigned long b)
  {
if (a < b)
  return b - a;
else
  return a - b;
  }

  unsigned long
  sub2 (unsigned long a, unsigned long b)
  {
unsigned long c;
if (__builtin_sub_overflow (a, b, ))
  return b - a;
else
  return c;
  }

On x86-64, gcc -O2 -S generates this:

  sub1:
  movq%rsi, %rdx
  movq%rdi, %rax
  subq%rdi, %rdx
  subq%rsi, %rax
  cmpq%rsi, %rdi
  cmovb   %rdx, %rax
  ret

  sub2:
  movq%rdi, %rax
  subq%rsi, %rax
  cmpq%rdi, %rax
  ja  .L13
  rep ret
  .L13:
  movq%rsi, %rax
  subq%rdi, %rax
  ret

The two functions have the same behavior. Presumably one implementation is
better than the other, and could be used for both sub1 and sub2.


[Bug c/68120] New: can't easily deal with integer overflow at compile time

2015-10-27 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68120

Bug ID: 68120
   Summary: can't easily deal with integer overflow at compile
time
   Product: gcc
   Version: unknown
Status: UNCONFIRMED
  Severity: enhancement
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

This is a followup to Bug#61129, which asked for integer-overflow-detecting
arithmetic intrinsics. We have them now (thanks!) but I'm running into some
problems using them.

The Gnulib intprops module defines macros to check for integer overflow, e.g.,
INT_ADD_OVERFLOW (a, b) returns 1 if the C expression A+B would overflow. These
macros are implemented in portable C. I'm trying to use GCC 5's new
__builtin_add_overflow etc. functions to speed up their runtime execution. This
turns out to be a pain because these macros are used in integer constant
expressions, where __builtin_add_overflow etc. cannot be used.

I am working around the problem with macro definitions like this:

 # define INT_ADD_OVERFLOW(a, b) \
   (__builtin_constant_p ((a) == (b)) \
? _GL_INT_ADD_OVERFLOW (a, b) \
: __builtin_add_overflow (a, b, &(__typeof__ ((a) + (b))) {0}))

where _GL_INT_ADD_OVERFLOW is a complex macro implemented in Standard C and is
a constant expression when its arguments are constant expressions. Although I
think this will work, it is ugly, and the macro _GL_INT_ADD_OVERFLOW is
complicated.

To simplify use of __builtin_add_overflow etc., I suggest extending these
builtins as follows.

First, allow the 3rd argument to be a null pointer constant of type
pointer-to-integer, meaning that the caller only wants to know if the overflow
occurred and does not want the low-order bits of the result. E.g.,
__builtin_add_overflow (a, b, (int *) 0) returns 1 if the mathematical value of
A + B does not fit in 'int'.  This would allow the above macro to be simplified
to:

 # define INT_ADD_OVERFLOW(a, b) \
   __builtin_add_overflow (a, b, (__typeof__ ((a) + (b)) *) 0)

Second, allow the 3rd argument to be omitted, as a shorthand for a null pointer
to the integer type of A+B. This further simplification would allow the above
macro to be simplified to:

  # define INT_ADD_OVERFLOW(a, b) __builtin_add_overflow (a, b)

Third, add a function __builtin_add_wrapv (a, b, c) that acts like
__builtin_add_overflow (a, b, c) except that it returns the value that would be
stored if C were a non-null pointer.  The 3rd argument C is optional here too,
with the same semantics as for __builtin_add_overflow.  This will let the user
get the bottom-order bits of an overflowed value in a constant expression,
something that can't be done with the current primitives.

The basic idea here is that we need intrinsics that deal with values and that
do not require non-null addresses, so that we can use these intrinsics in
constant expressions.


[Bug c/68121] New: __builtin_constant_p should not warn about integer overflow

2015-10-27 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68121

Bug ID: 68121
   Summary: __builtin_constant_p should not warn about integer
overflow
   Product: gcc
   Version: 5.2.0
Status: UNCONFIRMED
  Severity: minor
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

Compile this with "gcc -S" (x86-64):

  enum {
x = 20,
y = 20,
a = __builtin_constant_p (x + y) ? x : -1,
  };

GCC warns "integer overflow in expression [-Woverflow]" and points to the "+",
even though the "+" is not evaluated. This sort of warning should be disabled
in the argument of __builtin_constant_p, just as it's disabled in the argument
of other expressions like sizeof that do not actually evaluate their arguments.
In the above case, __builtin_constant_p should return 1 without warning about
overflow.

I ran into this problem when using a macro definition like this:

 #define INT_ADD_OVERFLOW(a, b) \
   (__builtin_constant_p ((a) + (b)) \
? _GL_INT_ADD_OVERFLOW (a, b) \
: __builtin_add_overflow (a, b, &(__typeof__ ((a) + (b))) {0}))

where _GL_INT_ADD_OVERFLOW (a, b) expands to a complicated expression that does
not overflow, and that yields 1 if A+B would overflow. GCC incorrectly warned
about (a)+(b) overflowing in the argument of __builtin_constant_p. I worked
around the bug by changing the first "+" to "==" in the macro body, but that's
kinda weird.


[Bug c/68110] New: __builtin_sub_overflow unsigned performance issue

2015-10-26 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68110

Bug ID: 68110
   Summary: __builtin_sub_overflow unsigned performance issue
   Product: gcc
   Version: 5.2.1
Status: UNCONFIRMED
  Severity: minor
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

I ran into this minor performance issue when changing Gnulib's lib/intprops.h
to use the new __builtin_sub_overflow function. I found that
__builtin_sub_overflow is less efficient than the portable C code that it
replaced, when the operands and result are unsigned, or unsigned long, or
unsigned long long. To reproduce the problem, compile and run the following
program with 'gcc -O2 -S' on x86-64:

  _Bool f1 (unsigned long long a, unsigned long long b)
  {
return a < b;
  }

  _Bool f2 (unsigned long long a, unsigned long long b)
  {
unsigned long long r;
return __builtin_sub_overflow (a, b, );
  }

Although the functions are semantically equivalent, f1 uses only 3
instructions:

f1:
cmpq%rsi, %rdi
setb%al
ret

whereas f2 uses 5 instructions:

f2:
movq%rdi, %rax
subq%rsi, %rax
cmpq%rdi, %rax
seta%al
ret

There is a similar problem for x86.


[Bug c/68046] New: -ftrapv doesn't catch leaq-based overflows on x86-64

2015-10-21 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=68046

Bug ID: 68046
   Summary: -ftrapv doesn't catch leaq-based overflows on x86-64
   Product: gcc
   Version: 5.2.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
  Target Milestone: ---

On x86-64 for this program:

long i = 0x7fffL;
int main (void)
{
  return i + 1 < i;
}

gcc -ftrapv -O2 -S generates this code:

main:
movqi(%rip), %rax
leaq1(%rax), %rdx
cmpq%rdx, %rax
setg%al
movzbl  %al, %eax
ret

which does not trap, even though the addition overflows.


[Bug sanitizer/67662] New: -fsanitize=undefined cries wolf for X - 1 + X when X is 2**30

2015-09-21 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=67662

Bug ID: 67662
   Summary: -fsanitize=undefined cries wolf for X - 1 + X when X
is 2**30
   Product: gcc
   Version: 5.2.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: sanitizer
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org
CC: dodji at gcc dot gnu.org, dvyukov at gcc dot gnu.org,
jakub at gcc dot gnu.org, kcc at gcc dot gnu.org
  Target Milestone: ---

Created attachment 36358
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=36358=edit
Test program illustrating the bug

I uncovered this bug while trying to use -fsanitize=undefined on the tzcode
source.

gcc -fsanitize=undefined (x86-64) reports an error at runtime for the
expression 'X - 1 + X' when X is 2**30, even though that expression does not
overflow. To reproduce the problem, compile and run the attached program u.c
with:

gcc -fsanitize=undefined -static-libubsan -O2 u.c
./a.out

It's a valid program that does not overflow, but the output I get is:

u.c:5:31: runtime error: signed integer overflow: 1073741824 + 1073741824
canno\
t be represented in type 'int'
u.c:5:7: runtime error: signed integer overflow: -2147483648 - 1 cannot be
repr\
esented in type 'int'

There is a similar problem with 2**62 and 'long long'.


[Bug c/28901] -Wunused-variable ignores unused const initialised variables

2015-09-18 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=28901

--- Comment #12 from Paul Eggert  ---
(In reply to Manuel López-Ibáñez from comment #11)

> Another alternative is to only warn if the variable is defined in the main
> file (MAIN_FILE_P) as opposed to an included file.

Thanks, this is a reasonable suggestion; it would fix the cry-wolf problem for
tzcode, which is what prompted me to object to the original proposal.

The alternative of littering the code with many instances of __attribute__
((unused)) (or is it __attribute ((used)? I can never remember) is less
appealing.

[Bug c/28901] -Wunused-variable ignores unused const initialised variables

2015-09-18 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=28901

Paul Eggert  changed:

   What|Removed |Added

 CC||eggert at gnu dot org

--- Comment #10 from Paul Eggert  ---
This topic came up on the libc-alpha mailing list.  The proposed change would
break compilation of tzcode, which has a private header that defines static
constants not all of which are used in every file that includes the header.

In tzcode the problem can be worked around by using a #define rather than a
static constant, but many C programmers nowadays prefer avoiding #define when
possible, and static constants let you do that in many cases. (An enum wouldn't
work for the tzcode case, as the values might be outside int range.)  Also, in
many environments macros are invisible to the debugger but static constants are
visible, so the static constants are nicer for people debugging their code.

This reminds me of when gcc -Wmissing-declarations used to diagnose every
C99-style inline function in an include file (GCC bug 63877). The warning was
put in and tested, but the tests used only old-fashioned C programming styles,
and the warning caused real problems by people using a more modern C style.

It'd be fine to add an option to enable the new warning, but please don't
enable them merely because -Wall or -Wunused-variable is specified.


[Bug c/63943] New: -Wmaybe-uninitialized pragma mishandled in inlined function

2014-11-18 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=63943

Bug ID: 63943
   Summary: -Wmaybe-uninitialized pragma mishandled in inlined
function
   Product: gcc
   Version: 4.9.2
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org

Created attachment 34031
  -- https://gcc.gnu.org/bugzilla/attachment.cgi?id=34031action=edit
Program with -Wmaybe-uninitialized problem

Compile the attached program t.c with gcc -Wmaybe-uninitialized -O2 -c t.c on
x86-64 with GCC 4.9.2, and the output will be:

t.c: In function 'main':
t.c:17:3: warning: '*((void *)v+4)' may be used uninitialized in this function
[-Wmaybe-uninitialized]
   return argc  1 ? !argv : dereference (v + 1);
   ^

'#pragma GCC diagnostic ignored -Wmaybe-uninitialized' is in effect when the
possibly-uninitialized variable is used, but this use is in a function that GCC
inlined, and GCC is incorrectly warning based on the pragma setting in the
calling function, not based on the pragma setting where the dereferencing
actually occurs.

The problem does not occur with GCC 4.8.3 so this appears to be a regression.

The problem also goes away if I add '__attribute__((noinline))' to the
'dereference' function, so this appears to be related to inlining.

I ran into this problem while thinking about enabling -Werror when compiling
glibc; my first cut at this ran into the above problem.


[Bug c/63877] New: - -Wmissing-declarations produces false alarms for C99 inline functions

2014-11-14 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=63877

Bug ID: 63877
   Summary: - -Wmissing-declarations produces false alarms for C99
inline functions
   Product: gcc
   Version: 4.9.2
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org

This is a followup to PR c/54113, which was about -Wmissing-prototypes.  This
followup bug report is the same, except it is about -Wmissing-declarations.

-Wmissing-declarations produces false alarms for C99-style
inline functions.  We can use the same example as for PR c/54113.
Suppose foo.h contains this:

  inline float square(float x) {return x*x;}
  inline float cube(float x) {return x*x*x;}

and foo.c contains this:

  #include foo.h
  extern float square(float x);
  extern float cube(float x);

Then the command:

  gcc -c -Wmissing-declarations foo.c

outputs:

  In file included from foo.c:1:0:
  foo.h:1:14: warning: no previous declaration for 'square'
[-Wmissing-declarations]
   inline float square(float x) {return x*x;}
  ^
  foo.h:2:14: warning: no previous declaration for 'cube'
[-Wmissing-declarations]
   inline float cube(float x) {return x*x*x;}
  ^

The diagnostics should not be output, as this is the normal
way to use inline functions in C.

To fix this, I suggest that the diagnostic be suppressed
for inline functions, at least for C99 mode.


[Bug c/63495] struct __attribute__ ((aligned (8))) broken on x86

2014-10-10 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=63495

--- Comment #6 from Paul Eggert eggert at gnu dot org ---
That was fast!  Thank you.


[Bug c/63495] New: struct __attribute__ ((aligned (8))) broken on x86

2014-10-09 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=63495

Bug ID: 63495
   Summary: struct __attribute__ ((aligned (8))) broken on x86
   Product: gcc
   Version: 4.9.1
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org

Compile and run the following two-line program with an x86 target:

struct __attribute__ ((aligned (8))) s { char c; };
_Static_assert (_Alignof (struct s) = 8, wrong alignment);

This should compile, but here are the symptoms I observe with GCC 4.9.1:

$ gcc -m32 t.c
t.c:2:1: error: static assertion failed: wrong alignment
 _Static_assert (_Alignof (struct s) = 8, wrong alignment);
 ^

On the buggy platform the structure's alignment is 4; it should be 8.

The program compiles fine with GCC 4.8.3, so there is a regression here.  The
program also compiles fine on x86-64.

The alignment bug breaks the trunk version of GNU Emacs when built on a 32-bit
platform; see
http://lists.gnu.org/archive/html/emacs-devel/2014-10/msg00261.html.  I'll
try to fix Emacs to work around the bug, but the GCC bug really should get
fixed.


[Bug c/61409] New: [4.9 regression] -Wmaybe-uninitialized false-positive with -O2

2014-06-04 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=61409

Bug ID: 61409
   Summary: [4.9 regression] -Wmaybe-uninitialized false-positive
with -O2
   Product: gcc
   Version: 4.9.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c
  Assignee: unassigned at gcc dot gnu.org
  Reporter: eggert at gnu dot org

Created attachment 32887
  -- https://gcc.gnu.org/bugzilla/attachment.cgi?id=32887action=edit
sample program illustrating the false positive

GCC 4.9.0 x86-64.  I do not observe the bug with GCC 4.8.2.

I discovered this bug when compiling GNU Emacs, and abstracted it into the
simplest test case I could easily generate.  When I compile the attached
program g.i with the command:

gcc -Wmaybe-uninitialized -O2 -c g.i

GCC warns:

g.i:607:21: warning: 'mw' may be used uninitialized in this function
[-Wmaybe-uninitialized]
   mw-pixel_top = rw-pixel_height;

But mw cannot possibly be uninitialized here.  Also, mw was used in the
previous line, with no warning.

The bug may be related to lines 602 and 603, which are long and which do not
mention mw, as removing these lines makes the diagnostic go away.


[Bug middle-end/61409] [4.9/4.10 regression] -Wmaybe-uninitialized false-positive with -O2

2014-06-04 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=61409

--- Comment #3 from Paul Eggert eggert at gnu dot org ---
(In reply to Manuel López-Ibáñez from comment #1)

 My guess is that what is uninitialized is rw and some optimization pass
 messed up the variable names when creating temporaries.

I'm afraid it's more serious than that, because 'rw = XWINDOW (make_window
());' always initializes 'rw'.

Thanks for simplifying the test case.

[Bug other/56955] documentation for attribute malloc contradicts itself

2014-05-22 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=56955

Paul Eggert eggert at gnu dot org changed:

   What|Removed |Added

  Attachment #32832|0   |1
is obsolete||

--- Comment #20 from Paul Eggert eggert at gnu dot org ---
Created attachment 32844
  -- https://gcc.gnu.org/bugzilla/attachment.cgi?id=32844action=edit
Revised-again doc patch for __attribute__ ((malloc))

Patch revised based on further comments on gcc-patches.


[Bug other/56955] documentation for attribute malloc contradicts itself

2014-05-21 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=56955

--- Comment #18 from Paul Eggert eggert at gnu dot org ---
(In reply to Richard Biener from comment #16)

 void foo (int *p)
 {
   int *q = realloc (p, sizeof (int));
   *q = 2;
 }
 
 may I remove the store *q = 2 as dead?

Yes, the consensus nowadays is that you can.

I'll be happy to send the proposed change to gcc-patches but would like to be
sure it's correct first.  Has this new information about realloc changed your
opinion about whether realloc can be given the malloc attribute?


[Bug other/56955] documentation for attribute malloc contradicts itself

2014-05-20 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=56955

Paul Eggert eggert at gnu dot org changed:

   What|Removed |Added

 CC||eggert at gnu dot org

--- Comment #6 from Paul Eggert eggert at gnu dot org ---
Created attachment 32831
  -- https://gcc.gnu.org/bugzilla/attachment.cgi?id=32831action=edit
Clarify documentation for __attribute__ ((malloc)).

This topic recently came up on the glibc mailing list and there's clearly a lot
of confusion about it.  See, for example,
https://sourceware.org/ml/libc-alpha/2014-05/msg00519.html.  Attaching a
proposed patch to the documentation to try to help clear this up.


[Bug other/56955] documentation for attribute malloc contradicts itself

2014-05-20 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=56955

--- Comment #8 from Paul Eggert eggert at gnu dot org ---
Comment on attachment 32831
  -- https://gcc.gnu.org/bugzilla/attachment.cgi?id=32831
Clarify documentation for __attribute__ ((malloc)).

Index: gcc/ChangeLog
===
--- gcc/ChangeLog  (revision 210629)
+++ gcc/ChangeLog  (working copy)
@@ -1,3 +1,10 @@
+2014-05-20  Paul Eggert  egg...@cs.ucla.edu
+
+  PR other/56955
+  * doc/extend.texi (Function Attributes): Fix  __attribute__ ((malloc))
+  documentation; the old documentation didn't clearly state the
+  constraints on the contents of the pointed-to storage.
+
 2014-05-19  David Wohlferd d...@limegreensocks.com
 
   * doc/extend.texi: Create Label Attributes section,
Index: gcc/doc/extend.texi
===
--- gcc/doc/extend.texi(revision 210629)
+++ gcc/doc/extend.texi(working copy)
@@ -3207,15 +3207,20 @@
 
 @item malloc
 @cindex @code{malloc} attribute
-The @code{malloc} attribute is used to tell the compiler that a function
-may be treated as if any non-@code{NULL} pointer it returns cannot
-alias any other pointer valid when the function returns and that the memory
-has undefined content.
-This often improves optimization.
-Standard functions with this property include @code{malloc} and
-@code{calloc}.  @code{realloc}-like functions do not have this
-property as the memory pointed to does not have undefined content.
+This tells the compiler that a function is @code{malloc}-like, i.e.,
+that if the function returns a non-null pointer @var{P}, then @var{P}
+cannot alias any other pointer valid when the function returns, and
+moreover the contents of any storage addressed by @var{P} cannot
+contain a pointer that aliases any other pointer valid when the
+function returns.
 
+Ussing this attribute often improves optimization.  Functions like
+@code{malloc} and @code{calloc} have this property because they return
+a pointer to uninitialized or zeroed-out storage.  However, functions
+like @code{realloc} do not have this property, as they can return a
+pointer to storage containing pointers that alias already-valid
+pointers.
+
 @item mips16/nomips16
 @cindex @code{mips16} attribute
 @cindex @code{nomips16} attribute

[Bug other/56955] documentation for attribute malloc contradicts itself

2014-05-20 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=56955

Paul Eggert eggert at gnu dot org changed:

   What|Removed |Added

  Attachment #32831|0   |1
is obsolete||

--- Comment #9 from Paul Eggert eggert at gnu dot org ---
Created attachment 32832
  -- https://gcc.gnu.org/bugzilla/attachment.cgi?id=32832action=edit
Revised documentation patch for __attribute__ ((malloc))

Thanks for the quick review.  Revised patch attached.  Sorry about the noise in
my previous reply, I hit Submit by accident.


[Bug other/56955] documentation for attribute malloc contradicts itself

2014-05-20 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=56955

--- Comment #11 from Paul Eggert eggert at gnu dot org ---
Created attachment 32834
  -- https://gcc.gnu.org/bugzilla/attachment.cgi?id=32834action=edit
Sample illustrating GCC's optimization with __attribute__ ((malloc))


[Bug other/56955] documentation for attribute malloc contradicts itself

2014-05-20 Thread eggert at gnu dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=56955

--- Comment #12 from Paul Eggert eggert at gnu dot org ---
(In reply to Rich Felker from comment #10)
 This assumption only aids
 optimization in the case where a pointer residing in the obtained memory is
 used (e.g. dereferenced or compared with another pointer) before anything is
 stored to it.

No, it also aids optimization because GCC can infer lack of aliasing elsewhere,
even if no pointer in the newly allocated memory is used-before-set.  Consider
the contrived example am.c (which I've added as an attachment to this report). 
It has two functions f and g that differ only in that f calls m which has
__attribute__ ((malloc)) whereas g calls n which does not.  With the weaker
assumption you're suggesting, GCC could not optimize away the reload from
a-next in f, because of the intervening assignment '*p = q'.

I've compiled this with both GCC 4.9.0 and Clang 3.4 on x86-64 with -O2.  Both
compile g to essentially the same 15 instructions.  Clang, which I suspect uses
the weaker assumption, compiles f to 14 instructions; GCC compiles f to 11
instructions.


  1   2   >