]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
vec: Fix bootstrap on i686-linux, 32-bit darwin and AIX
authorJakub Jelinek <jakub@redhat.com>
Fri, 14 Aug 2020 07:29:47 +0000 (09:29 +0200)
committerJakub Jelinek <jakub@redhat.com>
Fri, 14 Aug 2020 07:29:47 +0000 (09:29 +0200)
As mentioned earlier, embedded_size is broken on vecs of long long, double
etc. on some platforms, which breaks bootstrap.
E.g. on i686-linux, the problem is mostly with older GCC versions being used
as stage1 compiler (GCC 4.8 to 7.* in particular), because alignas (long long)
makes U 64-bit aligned, while when long long m_vecdata[1]; is in vec, it is
only 32-bit aligned.  We've tried various ways and the following one seems
to work, use the old way (offsetof (vec, m_vecdata)) for non-class types
as well as standard layout class types, i.e. whenever offsetof is guaranteed
to work, and for others use the new day (in that case we don't run into
problems with long long or other scalar types and for the structure layout
there is just a struct with a given alignment.

2020-08-14  Jakub Jelinek  <jakub@redhat.com>
    Jonathan Wakely  <jwakely@redhat.com>

* system.h: Include type_traits.
* vec.h (vec<T, A, vl_embed>::embedded_size): Use offsetof and asserts
on vec_stdlayout, which is conditionally a vec (for standard layout T)
and otherwise vec_embedded.

Co-Authored-By: Jonathan Wakely <jwakely@redhat.com>
gcc/system.h
gcc/vec.h

index a241e1355c40120478a0403f153c6e59561bf28c..3c543a005d856997ae5792133b3e89db2cded92b 100644 (file)
@@ -235,6 +235,7 @@ extern int errno;
 # include <cstring>
 # include <new>
 # include <utility>
+# include <type_traits>
 #endif
 
 /* Some of glibc's string inlines cause warnings.  Plus we'd rather
index db48e979d77843ef98607ed97603b385ad59b1d0..6ede62791b0aee653052bb3958fc4543ccf06bc8 100644 (file)
--- a/gcc/vec.h
+++ b/gcc/vec.h
@@ -1283,9 +1283,11 @@ vec<T, A, vl_embed>::embedded_size (unsigned alloc)
 {
   struct alignas (T) U { char data[sizeof (T)]; };
   typedef vec<U, A, vl_embed> vec_embedded;
-  static_assert (sizeof (vec_embedded) == sizeof(vec), "");
-  static_assert (alignof (vec_embedded) == alignof(vec), "");
-  return offsetof (vec_embedded, m_vecdata) + alloc * sizeof (T);
+  typedef typename std::conditional<std::is_standard_layout<T>::value,
+                                   vec, vec_embedded>::type vec_stdlayout;
+  static_assert (sizeof (vec_stdlayout) == sizeof (vec), "");
+  static_assert (alignof (vec_stdlayout) == alignof (vec), "");
+  return offsetof (vec_stdlayout, m_vecdata) + alloc * sizeof (T);
 }