[Bug c++/86480] [8/9 Regression] error: parameter packs not expanded with '...' in a recursive variadic lambda

2018-07-14 Thread jason at gcc dot gnu.org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86480

Jason Merrill  changed:

   What|Removed |Added

 CC||jason at gcc dot gnu.org

--- Comment #4 from Jason Merrill  ---
Created attachment 44395
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=44395=edit
patch

The find_parameter_packs_r hunk fixes this bug; the cp_walk_subtrees hunk fixes
a bug also found by my testcase, but is incomplete.

[Bug tree-optimization/86274] [7 Regression] SEGFAULT when logging std::to_string(NAN)

2018-07-14 Thread msebor at gcc dot gnu.org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86274

Martin Sebor  changed:

   What|Removed |Added

Summary|[7/8 Regression] SEGFAULT   |[7 Regression] SEGFAULT
   |when logging|when logging
   |std::to_string(NAN) |std::to_string(NAN)

--- Comment #20 from Martin Sebor  ---
Backported to GCC 8 in r262661.

[Bug tree-optimization/86274] [7/8 Regression] SEGFAULT when logging std::to_string(NAN)

2018-07-14 Thread msebor at gcc dot gnu.org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86274

--- Comment #19 from Martin Sebor  ---
Author: msebor
Date: Sat Jul 14 21:32:10 2018
New Revision: 262661

URL: https://gcc.gnu.org/viewcvs?rev=262661=gcc=rev
Log:
PR tree-optimization/86274 - SEGFAULT when logging std::to_string(NAN)

gcc/ChangeLog:

PR tree-optimization/86274
* gimple-ssa-sprintf.c (fmtresult::type_max_digits): Verify
precondition.
(format_floating): Correct handling of infinities and NaNs.

gcc/testsuite/ChangeLog:

PR tree-optimization/86274
* gcc.dg/tree-ssa/builtin-sprintf-9.c: New test.
* gcc.dg/tree-ssa/builtin-sprintf-warn-1.c: Adjust.
* gcc.dg/tree-ssa/builtin-sprintf-warn-10.c: Same.
* gcc.dg/tree-ssa/builtin-sprintf-warn-15.c: Same.
* gcc.dg/tree-ssa/builtin-sprintf-warn-7.c: Same.
* gcc.dg/tree-ssa/builtin-sprintf.c: Same.
* gcc.dg/tree-ssa/pr83198.c: Same.


Added:
branches/gcc-8-branch/gcc/testsuite/gcc.dg/torture/builtin-sprintf.c
branches/gcc-8-branch/gcc/testsuite/gcc.dg/tree-ssa/builtin-sprintf-9.c
Modified:
branches/gcc-8-branch/gcc/ChangeLog
branches/gcc-8-branch/gcc/gimple-ssa-sprintf.c
branches/gcc-8-branch/gcc/testsuite/ChangeLog
   
branches/gcc-8-branch/gcc/testsuite/gcc.dg/tree-ssa/builtin-sprintf-warn-1.c
   
branches/gcc-8-branch/gcc/testsuite/gcc.dg/tree-ssa/builtin-sprintf-warn-10.c
   
branches/gcc-8-branch/gcc/testsuite/gcc.dg/tree-ssa/builtin-sprintf-warn-15.c
   
branches/gcc-8-branch/gcc/testsuite/gcc.dg/tree-ssa/builtin-sprintf-warn-7.c
branches/gcc-8-branch/gcc/testsuite/gcc.dg/tree-ssa/builtin-sprintf.c
branches/gcc-8-branch/gcc/testsuite/gcc.dg/tree-ssa/pr83198.c

[Bug c++/86524] New: std::less with pointer arguments not usable in static_assert in constexpr function

2018-07-14 Thread david at doublewise dot net
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86524

Bug ID: 86524
   Summary: std::less with pointer arguments not usable in
static_assert in constexpr function
   Product: gcc
   Version: 8.1.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c++
  Assignee: unassigned at gcc dot gnu.org
  Reporter: david at doublewise dot net
  Target Milestone: ---

This code worked in gcc 7.3, but no longer works as of 8.1 or trunk.


#include 

void f1() {
constexpr int x = 0;
static_assert(!( < ));
static_assert(!std::less<>{}(, ));
}

constexpr void f2() {
constexpr int x = 0;
static_assert(!( < ));
static_assert(!std::less<>{}(, ));
}


In this example, the function f1 compiles fine, but f2 gives:

> g++ -std=c++17

: In function 'constexpr void f2()':

:12:19: error: non-constant condition for static assertion

 static_assert(!std::less<>{}(, ));

   ^~

Compiler returned: 1


The same problem occurs if using `std::less` instead of
`std::less<>`.

[Bug tree-optimization/86259] [8/9 Regression] min(4, strlen(s)) optimized to strlen(s) with -flto

2018-07-14 Thread msebor at gcc dot gnu.org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86259

--- Comment #30 from Martin Sebor  ---
(In reply to Bernd Edlinger from comment #28)
> 
> Can someone explain why the example in comment #21 works when
> pointer arithmentic instead of integer arithmetic is used?

Because the optimization (making use of the size of the referenced array)
doesn't apply in the pointer case.  In the integer case, ccp simplifies the
strlen argument to a COMPONENT_REF:

  Visiting statement:
  _2 = sp_ip_9 + 4;
  which is likely CONSTANT
  Match-and-simplified sp_ip_9 + 4 to bp.0_1
  Lattice value changed to CONSTANT bp.0_1.  Adding SSA edges to worklist.
  marking stmt to be not simulated again

  Visiting statement:
  _3 = (const char *) _2;
  which is likely CONSTANT
  Match-and-simplified (const char *) _2 to 
  Lattice value changed to CONSTANT   Adding SSA edges to worklist.
  marking stmt to be not simulated again

The COMPONENT_REF fully describes the structure of an access to a member and so
lends itself to interesting analysis which then opens up opportunities for both
optimization and bug detection (e.g., buffer overflow).

In the pointer case ccp replaces the argument with with a MEM_REF:

  Visiting statement:
  _1 = sp_ip_7 + 4;
  which is likely CONSTANT
  Lattice value changed to CONSTANT [(void *) + 4B].  Adding SSA edges to
worklist.
  marking stmt to be not simulated again

A ME_REF is a concise but low-level way of referencing memory via a base
address an an offset.  It doesn't include reliable information about the
structure of the referenced memory.  It's easier to do some basic things with
but much harder to use for interesting, higher level analysis.  By folding
expressions into MEM_REF early on, GCC effectively disables subsequent
optimizations that are designed to do interesting things at a higher level.

[Bug tree-optimization/86259] [8/9 Regression] min(4, strlen(s)) optimized to strlen(s) with -flto

2018-07-14 Thread msebor at gcc dot gnu.org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86259

--- Comment #29 from Martin Sebor  ---
(In reply to rguent...@suse.de from comment #25)
> 
> Istr the proposal suggests a -fno-provenance option. How would we handle
> these cases with that?

The proposal is still being discussed and it's not clear how it will evolve or
if the option will survive.  I'm not sure if the handling of these cases would
be consistent under the option.  I imagine some would be expected to work as if
whole objects were just arrays of bytes once provenance were not considered
after some non-trivial pointer expression were involved, while others would
still be undefined because of the array rule which is unrelated to provenance
(e.g., indexing past the end of an array).  I haven't absorbed the proposals
enough yet to say for sure where the line is, and even the authors are still
forming their opinion on some of these cases.

(In reply to Bernd Edlinger from comment #26)
> Hmmm, does this imply that
> the "container_of" macro in linux/include/kernel.h will be broken:

The macro is broken today because it relies on undefined behavior: advancing a
pointer from one subobject to another.  The latest revision of the proposal
discusses some ideas that might make this and other similar examples work
(e.g., a "function" such as a built-in that would make the compiler either lose
the provenance of a pointer or assign it a different provenance without
changing its value).  Some people have suggested that casts might make it work.

This isn't new.  Just like it's not valid to take a pointer to one array and
advance it to the next and dereference it, it's not valid to take a pointer to
a struct member, advance it to point to another member, and then derefernce it.
 Given the following definition, the call f(2) is undefined and GCC eliminates
the test on that basis.  The same rule applies to struct members.

  char a[2][2];

  void f (int i)
  {
char c = a[1][0];
char *p = [0][i];
*p = 1; // can only change the array a[0], not a[1]
if (c != a[1][0])   // folded to false because a[0][i] is only defined when
i is zero
  __builtin_abort ();
  }

To make it "work" this way you need to convince the compiler the
two-dimensional 2 X 2 matrix is really a one dimensional 4-element array.  The
following works with GCC but it's still undefined so I wouldn't recommend
relying on it.  I imagine making the pointer volatile would always work (but
it's still undefined).

void g (int i)
{
  char (*p)[4] = a;   // -Wincompatible-pointer-types here

  char c = (*p)[2];
  char *q = &(*p)[i];
  *q = 1;
  if (c != (*p)[2])   // not folded
__builtin_abort ();
}

[Bug debug/86523] [9 Regression] ICE in gen_member_die, at dwarf2out.c:24933 starting from r262560

2018-07-14 Thread marxin at gcc dot gnu.org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86523

--- Comment #1 from Martin Liška  ---
One more test-case with a bit different BT:

$  cat ice.ii
namespace {
class a typedef b;
class a {};
} // namespace
class c {
  struct C {
b d;
  };
  C e() const;
};
c::C c::e() const {
  C g;
  struct h {
C g;
h(C *) {}
  } f();
}

$ g++ ice.ii -O2 -flto=8 -g -shared
ice.ii: In member function ‘c::C c::e() const’:
ice.ii:17:1: warning: no return statement in function returning non-void
[-Wreturn-type]
 }
 ^

lto1: internal compiler error: in dwarf2out_finish, at dwarf2out.c:31107
0x5c87cd dwarf2out_finish
/home/marxin/Programming/gcc/gcc/dwarf2out.c:31107
Please submit a full bug report,
with preprocessed source if appropriate.
Please include the complete backtrace with any bug report.
See  for instructions.
make: *** [/tmp/cc5TI8Oi.mk:2: /tmp/ccQqbTv7.ltrans0.ltrans.o] Error 1
lto-wrapper: fatal error: make returned 2 exit status
compilation terminated.
/usr/bin/ld: error: lto-wrapper failed
collect2: error: ld returned 1 exit status

[Bug debug/86523] New: [9 Regression] ICE in gen_member_die, at dwarf2out.c:24933 starting from r262560

2018-07-14 Thread marxin at gcc dot gnu.org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86523

Bug ID: 86523
   Summary: [9 Regression] ICE in gen_member_die, at
dwarf2out.c:24933 starting from r262560
   Product: gcc
   Version: 9.0
Status: UNCONFIRMED
  Keywords: ice-on-valid-code
  Severity: normal
  Priority: P3
 Component: debug
  Assignee: unassigned at gcc dot gnu.org
  Reporter: marxin at gcc dot gnu.org
CC: hubicka at gcc dot gnu.org
  Target Milestone: ---

Following ICEs:

$ cat ice.ii
class a typedef b;
class a {};
class c {
  struct C {
b d;
  };
  C e() const;
};
c::C c::e() const {
  C g;
  struct h {
C g;
h(C *) {}
  } f();
}

$ g++ ice.ii -O2 -flto=8 -g  -shared
ice.ii: In member function ‘c::C c::e() const’:
ice.ii:15:1: warning: no return statement in function returning non-void
[-Wreturn-type]
 }
 ^
lto1: internal compiler error: in gen_member_die, at dwarf2out.c:24933
0x5c62e3 gen_member_die
/home/marxin/Programming/gcc/gcc/dwarf2out.c:24933
0x5c62e3 gen_struct_or_union_type_die
/home/marxin/Programming/gcc/gcc/dwarf2out.c:25128
0x85c5af gen_tagged_type_die
/home/marxin/Programming/gcc/gcc/dwarf2out.c:25329
0x87633f gen_typedef_die
/home/marxin/Programming/gcc/gcc/dwarf2out.c:25243
0x85a2fa gen_decl_die
/home/marxin/Programming/gcc/gcc/dwarf2out.c:26229
0x85ceac gen_type_die_with_usage
/home/marxin/Programming/gcc/gcc/dwarf2out.c:25394
0x85db06 gen_type_die
/home/marxin/Programming/gcc/gcc/dwarf2out.c:25578
0x85a5e2 gen_decl_die
/home/marxin/Programming/gcc/gcc/dwarf2out.c:26297
0x85c0d2 gen_member_die
/home/marxin/Programming/gcc/gcc/dwarf2out.c:25032
0x85c0d2 gen_struct_or_union_type_die
/home/marxin/Programming/gcc/gcc/dwarf2out.c:25128
0x85c5af gen_tagged_type_die
/home/marxin/Programming/gcc/gcc/dwarf2out.c:25329
0x85d427 gen_type_die_with_usage
/home/marxin/Programming/gcc/gcc/dwarf2out.c:25524
0x85db06 gen_type_die
/home/marxin/Programming/gcc/gcc/dwarf2out.c:25578
0x85a5e2 gen_decl_die
/home/marxin/Programming/gcc/gcc/dwarf2out.c:26297
0x85c0d2 gen_member_die
/home/marxin/Programming/gcc/gcc/dwarf2out.c:25032
0x85c0d2 gen_struct_or_union_type_die
/home/marxin/Programming/gcc/gcc/dwarf2out.c:25128
0x85c5af gen_tagged_type_die
/home/marxin/Programming/gcc/gcc/dwarf2out.c:25329
0x85d427 gen_type_die_with_usage
/home/marxin/Programming/gcc/gcc/dwarf2out.c:25524
0x85db06 gen_type_die
/home/marxin/Programming/gcc/gcc/dwarf2out.c:25578
0x85e4b4 modified_type_die
/home/marxin/Programming/gcc/gcc/dwarf2out.c:13395

[Bug c++/86522] gcc-7.3.0 on x86-only fails to compile mariadb/mysql: error: unsupported size for integer register

2018-07-14 Thread valko at linux dot karinthy.hu
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86522

--- Comment #3 from valko at linux dot karinthy.hu ---
Created attachment 44394
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=44394=edit
sql_prepare.ii.gz

[Bug c++/86522] gcc-7.3.0 on x86-only fails to compile mariadb/mysql: error: unsupported size for integer register

2018-07-14 Thread valko at linux dot karinthy.hu
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86522

--- Comment #2 from valko at linux dot karinthy.hu ---
Created attachment 44393
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=44393=edit
gcc compilation output (including -v)

[Bug c++/86522] New: gcc-7.3.0 on x86-only fails to compile mariadb/mysql: error: unsupported size for integer register

2018-07-14 Thread valko at linux dot karinthy.hu
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86522

Bug ID: 86522
   Summary: gcc-7.3.0 on x86-only fails to compile mariadb/mysql:
error: unsupported size for integer register
   Product: gcc
   Version: 7.3.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c++
  Assignee: unassigned at gcc dot gnu.org
  Reporter: valko at linux dot karinthy.hu
  Target Milestone: ---

After switching to gcc-7.3.0, my Gentoo build system is no longer able to
compile mariadb and mysql packages on x86 platform.
Using the previous compiler version (6.4.0) in the same environment works.
Different versions of mariadb (10.0.35, 10.1.31, 10.2.15) or mysql (5.6.39) all
produce the same error message (the source file/function/line number is
different, but the error message is the same).
Using no optimization flag (removing -O2) works, using different levels of
optimization (-O1 or -O3) fails.

The problem only manifests itself on x86, a very similar amd64 build
environment works perfectly.

I reproduced the failure with a vanilla 7.3.0 to exclude the effects of
Gentoo-specific gcc patches.

[Bug c++/86522] gcc-7.3.0 on x86-only fails to compile mariadb/mysql: error: unsupported size for integer register

2018-07-14 Thread valko at linux dot karinthy.hu
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86522

--- Comment #1 from valko at linux dot karinthy.hu ---
Created attachment 44392
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=44392=edit
gcc command line failing

[Bug tree-optimization/86259] [8/9 Regression] min(4, strlen(s)) optimized to strlen(s) with -flto

2018-07-14 Thread bernd.edlinger at hotmail dot de
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86259

--- Comment #28 from Bernd Edlinger  ---
(In reply to Davin McCall from comment #27)
> Again, there was no pointer arithmetic (other than the line containing
> 'strlen', but that particular case the pointer has the address of the union
> object, which has been cast to (char *), and the '+ 4' should be valid then,
> surely, by 6.3.2.7 paragraph 7 (ignoring that it requires 'successive
> increments' rather than arbitrary addition, or is that supposed to be
> significant?).

Can someone explain why the example in comment #21 works when
pointer arithmentic instead of integer arithmetic is used?

char *sp_ip = (char *)bp - offsetof(struct S,b);
strcpy(u.xx, "abcdefghijk");
size_t len = strlen((char *)(union U*)sp_ip + 4);
puts(len == 7 ? "YES" : "NO");

prints "YES"

[Bug c++/86515] std::initializer_list constructor is not a constant expression

2018-07-14 Thread redi at gcc dot gnu.org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86515

Jonathan Wakely  changed:

   What|Removed |Added

   Keywords||rejects-valid
 Status|UNCONFIRMED |NEW
   Last reconfirmed||2018-07-14
 Ever confirmed|0   |1

[Bug libstdc++/86513] ostringstream default constructor missing from libstdc++

2018-07-14 Thread redi at gcc dot gnu.org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86513

Jonathan Wakely  changed:

   What|Removed |Added

 Status|UNCONFIRMED |WAITING
   Last reconfirmed||2018-07-14
 Ever confirmed|0   |1

--- Comment #1 from Jonathan Wakely  ---
Have you done a clean build?

Those symbols were added last week, but if you are doing an incremental build
in an existing build tree you need to do 'make clean' in the libstdc++-v3 build
directory and then build again.

If you're using the subversion trunk you need to be prepared to do such things.

[Bug c++/86521] New: GCC 8 selects incorrect overload of ref-qualified conversion operator template

2018-07-14 Thread yannick.lepennec+gcc at live dot fr
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86521

Bug ID: 86521
   Summary: GCC 8 selects incorrect overload of ref-qualified
conversion operator template
   Product: gcc
   Version: 8.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c++
  Assignee: unassigned at gcc dot gnu.org
  Reporter: yannick.lepennec+gcc at live dot fr
  Target Milestone: ---

Please consider the following code, built with `g++ -std=c++17 -Wall -Wextra
-pedantic`.
It used to be accepted by GCC 7.3, but this is no longer the case since GCC 8.
Godbolt for convenience: https://godbolt.org/g/oXFQex

It was broken since r258755, which makes this code ICE instead. The ICE itself
was fixed in r259123, but said fix now makes GCC reject it with the below
error.
This is still the case on today's r262658. As far as I can tell, GCC seems to
be incorrectly selecting the `const&` overload instead of the `&&` one.

#include 

template
struct require_cast {
T val;

template
explicit operator U () && {
return std::move(val);
}

template
explicit operator U const& () const& {
return val;
}
};

struct base {
base() = default;
base(base&&) = default;
base& operator=(base&&) = default;

base(base const&) = delete;
base& operator=(base const&) = delete;
};

struct derived : base {};

int main() {
require_cast d;
(void)static_cast(std::move(d));
(void)static_cast(std::move(d));
}


repro.c++: In function ‘int main()’:
repro.c++:34:41: error: use of deleted function ‘base::base(const base&)’
 (void)static_cast(std::move(d));
 ^
repro.c++:23:5: note: declared here
 base(base const&) = delete;
 ^~~~
repro.c++:35:44: error: use of deleted function ‘derived::derived(const
derived&)’
 (void)static_cast(std::move(d));
^
repro.c++:27:8: note: ‘derived::derived(const derived&)’ is implicitly deleted
because the default definition would be ill-formed:
 struct derived : base {};
^~~
repro.c++:27:8: error: use of deleted function ‘base::base(const base&)’
repro.c++:23:5: note: declared here
 base(base const&) = delete;
 ^~~~

[Bug lto/86517] relocation R_X86_64_32 against `.rodata.str1.1' can not be used when making a shared object with LTO

2018-07-14 Thread hjl.tools at gmail dot com
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86517

--- Comment #3 from H.J. Lu  ---
(In reply to Jan Hubicka from comment #2)
> I think the problem here is that you can compile PIE and PIC object into pie
> binary

He used

gcc -pie -O2 -pthread -ldl -lxml2 1.o 2.o x.a -rdynamic -flto=9 -shared
^
-shared overrides -pie.  He was building a shared object, not a PIE.

[Bug tree-optimization/86259] [8/9 Regression] min(4, strlen(s)) optimized to strlen(s) with -flto

2018-07-14 Thread davmac at davmac dot org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86259

--- Comment #27 from Davin McCall  ---
(In reply to Martin Sebor from comment #24)
> The code in example #21 has the same bug:
> [...]

... due to provenance, you are claiming, if I understand correctly. But I don't
see anything in the current language standard that allows or even supports this
reasoning (perhaps I'm missing it). For the other examples you can say that the
result of the pointer arithmetic is not defined (because it is not specified by
6.5.6). But for this case, the pointer was cast to an integer type before any
arithmetic was performed.

> The strlen call is undefined because (char*)sp_ip is known to point just
> past the last element of u.s.b.

It actually points at the first element of u.s.b - we start with ,
subtract the offset of that element from the container object (the offset will
be 4), then add 4. I don't think this by itself invalidates what you have said,
though.

>  It wouldn't matter if there happened to be
> a valid string at that address -- there isn't in this case because what's
> there is a char[4] with no terminating NUL.

That is true only if "address" means something more than "pointer value". I can
assert that ((char *)sp_ip + 4) and (u.xx + 4) are equal before the strlen, and
the compiler optimises away the assert. Furthermore, there is definitely a
valid string at u.xx + 4 and therefore at ((char *)) + 4. The provenance
rules you're suggesting lead to the conclusion that I can check (via an '=='
comparison) if a pointer refers to a particular object, and find that it does,
but then invoke undefined behaviour when dereferencing it [*]. While there may
be changes in the committee pipeline that would make this the case, in the
language as defined now I don't see how this interpretation can be justified.

[*] or if such a pointer comparison would also be undefined, i could anyway
cast both pointers to an integer type and compare them then.

>  The pointer wasn't derived from
> that address.  The pointer was derived from u.s.b and points to u.s.b +
> sizeof u.s.b, and there can never be anything valid beyond the end of an
> object.

(It points at u.s.b, actually).

> 
> [...]  Just like it's not valid to increment a pointer from
> a[0][1] to a[1][0] and dereference the latter in 'char a[2][2]; it's not
> valid to increment a pointer to one struct member to point to another and
> dereference it.

Again, there was no pointer arithmetic (other than the line containing
'strlen', but that particular case the pointer has the address of the union
object, which has been cast to (char *), and the '+ 4' should be valid then,
surely, by 6.3.2.7 paragraph 7 (ignoring that it requires 'successive
increments' rather than arbitrary addition, or is that supposed to be
significant?).

I believe I understand the point of the provenance rules, but I do not think it
is right to implement provenance as transferring to integers, on-by-default, in
a compiler for the current language specification.

[Bug tree-optimization/86259] [8/9 Regression] min(4, strlen(s)) optimized to strlen(s) with -flto

2018-07-14 Thread bernd.edlinger at hotmail dot de
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86259

Bernd Edlinger  changed:

   What|Removed |Added

 CC||bernd.edlinger at hotmail dot 
de

--- Comment #26 from Bernd Edlinger  ---
Hmmm, does this imply that
the "container_of" macro in linux/include/kernel.h will be broken:

/**
 * container_of - cast a member of a structure out to the containing structure
 * @ptr:the pointer to the member.
 * @type:   the type of the container struct this is embedded in.
 * @member: the name of the member within the struct.
 *
 */
#define container_of(ptr, type, member) ({  \
void *__mptr = (void *)(ptr);   \
BUILD_BUG_ON_MSG(!__same_type(*(ptr), ((type *)0)->member) &&   \
 !__same_type(*(ptr), void),\
 "pointer type mismatch in container_of()");\
((type *)(__mptr - offsetof(type, member))); })


Or is the arithmetic on void * exempt from this undefined behavior?

[Bug lto/86517] relocation R_X86_64_32 against `.rodata.str1.1' can not be used when making a shared object with LTO

2018-07-14 Thread hubicka at ucw dot cz
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86517

--- Comment #2 from Jan Hubicka  ---
> https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86517
> 
> H.J. Lu  changed:
> 
>What|Removed |Added
> 
>  Status|UNCONFIRMED |RESOLVED
>  CC||hjl.tools at gmail dot com
>  Resolution|--- |INVALID
> 
> --- Comment #1 from H.J. Lu  ---
> I(In reply to Martin Liška from comment #0)
> 
> > 
> > $ gcc -flto -c -fPIE -O2 1.i 2.i && gcc -fPIC -c -O2 lib.i -flto && ar rv
> > x.a lib.o && gcc -pie -O2 -pthread -ldl -lxml2 1.o 2.o x.a -rdynamic -flto=9
> > -shared
> > r - lib.o
> 
> I don't believe you can build a shared object with -fPIE and linker tells
> you to recompile with -fPIC.

I think the problem here is that you can compile PIE and PIC object into pie
binary
at least on x86-64, but the way we merge options in lto-wrapper, we disable
both PIE and
PIC at LTO linktime.
I think we ought to consider PIE as lower variant of PIC and resolve such funny
combination as -fPIE.

Honza

[Bug tree-optimization/86259] [8/9 Regression] min(4, strlen(s)) optimized to strlen(s) with -flto

2018-07-14 Thread rguenther at suse dot de
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86259

--- Comment #25 from rguenther at suse dot de  ---
On July 14, 2018 2:26:06 AM GMT+02:00, "msebor at gcc dot gnu.org"
 wrote:
>https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86259
>
>--- Comment #24 from Martin Sebor  ---
>The code in example #21 has the same bug:
>
>union U u;
>u.s = (struct S){0, 0, 0};
>
>char *bp = u.s.b;   // <<< bp points to u.s.b
>
> uintptr_t sp_ip = (uintptr_t)bp - offsetof(struct S,b);   // sp_ip has
>u.s.b's provenance
>
>strcpy(u.xx, "abcdefghijk");
> size_t len = strlen((char *)(union U *)sp_ip + 4);   // still the same
>provenance
>
>puts(len == 7 ? "YES" : "NO");
>
>The strlen call is undefined because (char*)sp_ip is known to point
>just past
>the last element of u.s.b.  It wouldn't matter if there happened to be
>a valid
>string at that address -- there isn't in this case because what's there
>is a
>char[4] with no terminating NUL.  The pointer wasn't derived from that
>address.
>The pointer was derived from u.s.b and points to u.s.b + sizeof u.s.b,
>and
>there can never be anything valid beyond the end of an object. 
>
>Compile the test case with -fdump-tree-fre1=/dev/stdout to see what GCC
>sees:
>
>  bp.0_1 = (long unsigned int) 
>  sp_ip_9 = bp.0_1 + 18446744073709551612;
>  MEM[(char * {ref-all})] = MEM[(char * {ref-all})"abcdefghijk"];
>  _4 = __builtin_strlen ();
>
>The rule to keep in mind is that pointer arithmetic is only valid
>within the
>boundaries of the smallest subobject it points to.  This applies to
>structs as
>much as arrays.  Just like it's not valid to increment a pointer from
>a[0][1]
>to a[1][0] and dereference the latter in 'char a[2][2]; it's not valid
>to
>increment a pointer to one struct member to point to another and
>dereference
>it.

Istr the proposal suggests a -fno-provenance option. How would we handle these
cases with that?

[Bug lto/86490] lto1: fatal error: multiple prevailing defs

2018-07-14 Thread zenith432 at users dot sourceforge.net
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86490

--- Comment #14 from zenith432 at users dot sourceforge.net ---
(In reply to H.J. Lu from comment #13)
> 
> But the symbol in question won't be USED by lto1 at all.

Ok.  I didn't completely check the logic for resolutions in ld.bfd so didn't
understand that it *knows* the symbol won't be used.

If ld knows a symbol in the IR won't be used and wants to trick lto1 into
discarding the symbol - it can do so by setting the resolution to
LDPR_PREEMPTED_REG.  lto1 has no way of verifying whether the symbol is defined
outside the IR or not - so will simply respond to this resolution by discarding
the symbol.

There is an example of this in gold in
Pluginobj::get_symbol_resolution_info

>  if (static_cast(nsyms) > this->symbols_.size())
>{
>  // We never decided to include this object. We mark all symbols as
>  // preempted.
>  gold_assert(this->symbols_.size() == 0);
>  for (int i = 0; i < nsyms; i++)
>syms[i].resolution = LDPR_PREEMPTED_REG;
>  return version > 2 ? LDPS_NO_SYMS : LDPS_OK;
>}

I did not completely follow the gold code as to why it may decide not to
include the object, but if gold decides not to include the object after it's
been claimed - this is how it gets all its symbols to be discarded by lto1.

Note that there are cases of multiple defs in the IR of an unused symbol where
the linker still has to stop with an error.  For example - if the duplicate def
is a regular kind (non-common, non-weak) and the obj files all appear on the
command-line (not archive) - this is a duplicate symbol error even if the
symbol is unreferenced.  The linker can either print the error itself - or
leave multiple prevailing defs for lto1 to print the error :)