From ec33f404bb16564a9aea3044cd8504d6885165b0 Mon Sep 17 00:00:00 2001 From: Abseil Team Date: Thu, 3 Mar 2022 06:35:20 -0800 Subject: Export of internal Abseil changes -- f2ffea8ae1c1b152b63bf561375cfb6eb6b9dbe5 by Derek Mauro : Internal change PiperOrigin-RevId: 432180490 Change-Id: I5e318e1d06fe26eee08920fe39f8a6285eb8e217 -- e5d0de4b3293833eab3f77252a091ac4ed74b210 by Derek Mauro : absl::optional - Add a workaround for an internal compiler error in GCC5 though GCC10 PiperOrigin-RevId: 432047437 Change-Id: I524a9098dadc116d8a423dd66f7ec5ee894f2874 GitOrigin-RevId: f2ffea8ae1c1b152b63bf561375cfb6eb6b9dbe5 --- absl/types/optional.h | 31 +++++++++++++++++-------------- absl/types/optional_test.cc | 26 ++++++++++++++++++++++++++ 2 files changed, 43 insertions(+), 14 deletions(-) (limited to 'absl/types') diff --git a/absl/types/optional.h b/absl/types/optional.h index 61540cfd..134b2aff 100644 --- a/absl/types/optional.h +++ b/absl/types/optional.h @@ -282,15 +282,16 @@ class optional : private optional_internal::optional_data, optional& operator=(optional&& src) = default; // Value assignment operators - template < - typename U = T, - typename = typename std::enable_if, typename std::decay::type>>, - absl::negation< - absl::conjunction, - std::is_same::type>>>, - std::is_constructible, std::is_assignable>::value>::type> + template , typename std::decay::type> >, + absl::negation, + std::is_same::type> > >, + std::is_constructible, + std::is_assignable >::value>::type> optional& operator=(U&& v) { this->assign(std::forward(v)); return *this; @@ -298,13 +299,14 @@ class optional : private optional_internal::optional_data, template < typename U, + int&..., // Workaround an internal compiler error in GCC 5 to 10. typename = typename std::enable_if>, + absl::negation >, std::is_constructible, std::is_assignable, absl::negation< optional_internal:: is_constructible_convertible_assignable_from_optional< - T, U>>>::value>::type> + T, U> > >::value>::type> optional& operator=(const optional& rhs) { if (rhs) { this->assign(*rhs); @@ -315,13 +317,14 @@ class optional : private optional_internal::optional_data, } template >, std::is_constructible, - std::is_assignable, + absl::negation >, + std::is_constructible, std::is_assignable, absl::negation< optional_internal:: is_constructible_convertible_assignable_from_optional< - T, U>>>::value>::type> + T, U> > >::value>::type> optional& operator=(optional&& rhs) { if (rhs) { this->assign(std::move(*rhs)); diff --git a/absl/types/optional_test.cc b/absl/types/optional_test.cc index 7ef142cb..1846e695 100644 --- a/absl/types/optional_test.cc +++ b/absl/types/optional_test.cc @@ -27,6 +27,32 @@ #include "absl/meta/type_traits.h" #include "absl/strings/string_view.h" +// The following types help test an internal compiler error in GCC5 though +// GCC10. The case OptionalTest.InternalCompilerErrorInGcc5ToGcc10 crashes the +// compiler without a workaround. This test case should remain at the beginning +// of the file as the internal compiler error is sensitive to other constructs +// in this file. +template +using GccIceHelper1 = T; +template +struct GccIceHelper2 {}; +template +class GccIce { + template &, U>> + GccIce& operator=(GccIceHelper2 const&) {} +}; + +TEST(OptionalTest, InternalCompilerErrorInGcc5ToGcc10) { + GccIce instantiate_ice_with_same_type_as_optional; + static_cast(instantiate_ice_with_same_type_as_optional); + absl::optional val1; + absl::optional val2; + val1 = val2; +} + struct Hashable {}; namespace std { -- cgit v1.2.3