Bug 1424103 - constexpr-ify mozilla::Span. r?hsivonen draft
authorMasatoshi Kimura <VYV03354@nifty.ne.jp>
Fri, 08 Dec 2017 23:20:56 +0900
changeset 710479 673ad7ef611b793fa355b81b635ec1b9e97da7c7
parent 710478 1d9b3217821f037ddc072c9259f9dfc0ec6bffc4
child 710867 b31b2098efaaaec7e8b618255a8a666f8fad8b6a
push id92827
push userVYV03354@nifty.ne.jp
push dateSun, 10 Dec 2017 12:52:36 +0000
reviewershsivonen
bugs1424103
milestone59.0a1
Bug 1424103 - constexpr-ify mozilla::Span. r?hsivonen MozReview-Commit-ID: 4e98Aer9V1k
mfbt/Span.h
--- a/mfbt/Span.h
+++ b/mfbt/Span.h
@@ -31,21 +31,29 @@
 #include <algorithm>
 #include <array>
 #include <cstring>
 #include <iterator>
 
 // Classifications for reasons why constexpr was removed in C++14 to C++11
 // conversion. Once we upgrade compilers, we can try defining each of these
 // to constexpr to restore a category of constexprs at a time.
+#if !defined(__clang__) && defined(__GNUC__) && __cpp_constexpr < 201304
 #define MOZ_SPAN_ASSERTION_CONSTEXPR
 #define MOZ_SPAN_GCC_CONSTEXPR
 #define MOZ_SPAN_EXPLICITLY_DEFAULTED_CONSTEXPR
 #define MOZ_SPAN_CONSTEXPR_NOT_JUST_RETURN
 #define MOZ_SPAN_NON_CONST_CONSTEXPR
+#else
+#define MOZ_SPAN_ASSERTION_CONSTEXPR constexpr
+#define MOZ_SPAN_GCC_CONSTEXPR constexpr
+#define MOZ_SPAN_EXPLICITLY_DEFAULTED_CONSTEXPR constexpr
+#define MOZ_SPAN_CONSTEXPR_NOT_JUST_RETURN constexpr
+#define MOZ_SPAN_NON_CONST_CONSTEXPR constexpr
+#endif
 
 #ifdef _MSC_VER
 #pragma warning(push)
 
 // turn off some warnings that are noisy about our MOZ_RELEASE_ASSERT statements
 #pragma warning(disable : 4127) // conditional expression is constant
 
 // blanket turn off warnings from CppCoreCheck for now
@@ -186,44 +194,44 @@ public:
   operator=(const span_iterator<Span, IsConst>&) = default;
 
   MOZ_SPAN_GCC_CONSTEXPR reference operator*() const
   {
     MOZ_RELEASE_ASSERT(span_);
     return (*span_)[index_];
   }
 
-  MOZ_SPAN_GCC_CONSTEXPR pointer operator->() const
+  constexpr pointer operator->() const
   {
     MOZ_RELEASE_ASSERT(span_);
     return &((*span_)[index_]);
   }
 
   MOZ_SPAN_NON_CONST_CONSTEXPR span_iterator& operator++()
   {
     MOZ_RELEASE_ASSERT(span_ && index_ >= 0 && index_ < span_->Length());
     ++index_;
     return *this;
   }
 
-  MOZ_SPAN_NON_CONST_CONSTEXPR span_iterator operator++(int)
+  constexpr span_iterator operator++(int)
   {
     auto ret = *this;
     ++(*this);
     return ret;
   }
 
   MOZ_SPAN_NON_CONST_CONSTEXPR span_iterator& operator--()
   {
     MOZ_RELEASE_ASSERT(span_ && index_ > 0 && index_ <= span_->Length());
     --index_;
     return *this;
   }
 
-  MOZ_SPAN_NON_CONST_CONSTEXPR span_iterator operator--(int)
+  constexpr span_iterator operator--(int)
   {
     auto ret = *this;
     --(*this);
     return ret;
   }
 
   MOZ_SPAN_CONSTEXPR_NOT_JUST_RETURN span_iterator
   operator+(difference_type n) const
@@ -235,24 +243,24 @@ public:
   MOZ_SPAN_GCC_CONSTEXPR span_iterator& operator+=(difference_type n)
   {
     MOZ_RELEASE_ASSERT(span_ && (index_ + n) >= 0 &&
                        (index_ + n) <= span_->Length());
     index_ += n;
     return *this;
   }
 
-  MOZ_SPAN_CONSTEXPR_NOT_JUST_RETURN span_iterator
+  constexpr span_iterator
   operator-(difference_type n) const
   {
     auto ret = *this;
     return ret -= n;
   }
 
-  MOZ_SPAN_NON_CONST_CONSTEXPR span_iterator& operator-=(difference_type n)
+  constexpr span_iterator& operator-=(difference_type n)
 
   {
     return *this += -n;
   }
 
   MOZ_SPAN_GCC_CONSTEXPR difference_type
   operator-(const span_iterator& rhs) const
   {
@@ -279,29 +287,29 @@ public:
 
   MOZ_SPAN_GCC_CONSTEXPR friend bool operator<(const span_iterator& lhs,
                                                const span_iterator& rhs)
   {
     MOZ_RELEASE_ASSERT(lhs.span_ == rhs.span_);
     return lhs.index_ < rhs.index_;
   }
 
-  MOZ_SPAN_GCC_CONSTEXPR friend bool operator<=(const span_iterator& lhs,
+  constexpr friend bool operator<=(const span_iterator& lhs,
                                                 const span_iterator& rhs)
   {
     return !(rhs < lhs);
   }
 
-  MOZ_SPAN_GCC_CONSTEXPR friend bool operator>(const span_iterator& lhs,
+  constexpr friend bool operator>(const span_iterator& lhs,
                                                const span_iterator& rhs)
   {
     return rhs < lhs;
   }
 
-  MOZ_SPAN_GCC_CONSTEXPR friend bool operator>=(const span_iterator& lhs,
+  constexpr friend bool operator>=(const span_iterator& lhs,
                                                 const span_iterator& rhs)
   {
     return !(rhs > lhs);
   }
 
   void swap(span_iterator& rhs)
   {
     std::swap(index_, rhs.index_);
@@ -643,105 +651,105 @@ public:
   MOZ_SPAN_EXPLICITLY_DEFAULTED_CONSTEXPR Span& operator=(Span&& other)
     = default;
 
   // [Span.sub], Span subviews
   /**
    * Subspan with first N elements with compile-time N.
    */
   template<size_t Count>
-  MOZ_SPAN_GCC_CONSTEXPR Span<element_type, Count> First() const
+  constexpr Span<element_type, Count> First() const
   {
     MOZ_RELEASE_ASSERT(Count <= size());
     return { data(), Count };
   }
 
   /**
    * Subspan with last N elements with compile-time N.
    */
   template<size_t Count>
-  MOZ_SPAN_GCC_CONSTEXPR Span<element_type, Count> Last() const
+  constexpr Span<element_type, Count> Last() const
   {
     const size_t len = size();
     MOZ_RELEASE_ASSERT(Count <= len);
     return { data() + (len - Count), Count };
   }
 
   /**
    * Subspan with compile-time start index and length.
    */
   template<size_t Offset, size_t Count = dynamic_extent>
-  MOZ_SPAN_GCC_CONSTEXPR Span<element_type, Count> Subspan() const
+  constexpr Span<element_type, Count> Subspan() const
   {
     const size_t len = size();
     MOZ_RELEASE_ASSERT(Offset <= len &&
       (Count == dynamic_extent || (Offset + Count <= len)));
     return { data() + Offset,
              Count == dynamic_extent ? len - Offset : Count };
   }
 
   /**
    * Subspan with first N elements with run-time N.
    */
-  MOZ_SPAN_GCC_CONSTEXPR Span<element_type, dynamic_extent> First(
+  constexpr Span<element_type, dynamic_extent> First(
     index_type aCount) const
   {
     MOZ_RELEASE_ASSERT(aCount <= size());
     return { data(), aCount };
   }
 
   /**
    * Subspan with last N elements with run-time N.
    */
-  MOZ_SPAN_GCC_CONSTEXPR Span<element_type, dynamic_extent> Last(
+  constexpr Span<element_type, dynamic_extent> Last(
     index_type aCount) const
   {
     const size_t len = size();
     MOZ_RELEASE_ASSERT(aCount <= len);
     return { data() + (len - aCount), aCount };
   }
 
   /**
    * Subspan with run-time start index and length.
    */
-  MOZ_SPAN_GCC_CONSTEXPR Span<element_type, dynamic_extent> Subspan(
+  constexpr Span<element_type, dynamic_extent> Subspan(
     index_type aStart,
     index_type aLength = dynamic_extent) const
   {
     const size_t len = size();
     MOZ_RELEASE_ASSERT(aStart <= len &&
                        (aLength == dynamic_extent ||
                         (aStart + aLength <= len)));
     return { data() + aStart,
              aLength == dynamic_extent ? len - aStart : aLength };
   }
 
   /**
    * Subspan with run-time start index. (Rust's &foo[start..])
    */
-  MOZ_SPAN_GCC_CONSTEXPR Span<element_type, dynamic_extent> From(
+  constexpr Span<element_type, dynamic_extent> From(
     index_type aStart) const
   {
     return Subspan(aStart);
   }
 
   /**
    * Subspan with run-time exclusive end index. (Rust's &foo[..end])
    */
-  MOZ_SPAN_GCC_CONSTEXPR Span<element_type, dynamic_extent> To(
+  constexpr Span<element_type, dynamic_extent> To(
     index_type aEnd) const
   {
     return Subspan(0, aEnd);
   }
 
   /**
    * Subspan with run-time start index and exclusive end index.
    * (Rust's &foo[start..end])
    */
-  MOZ_SPAN_GCC_CONSTEXPR Span<element_type, dynamic_extent> FromTo(
+  constexpr Span<element_type, dynamic_extent> FromTo(
     index_type aStart,
     index_type aEnd) const
   {
     MOZ_RELEASE_ASSERT(aStart <= aEnd);
     return Subspan(aStart, aEnd - aStart);
   }
 
   // [Span.obs], Span observers
@@ -775,17 +783,17 @@ public:
 
   /**
    * Checks if the the length of the span is zero (standard-libray duck
    * typing version).
    */
   constexpr bool empty() const { return size() == 0; }
 
   // [Span.elem], Span element access
-  MOZ_SPAN_GCC_CONSTEXPR reference operator[](index_type idx) const
+  constexpr reference operator[](index_type idx) const
   {
     MOZ_RELEASE_ASSERT(idx < storage_.size());
     return data()[idx];
   }
 
   /**
    * Access element of span by index (standard-library duck typing version).
    */