From a2c6059905bb9cb719e58f11f31d52102f2ad49a Mon Sep 17 00:00:00 2001 From: Ole Erik Peistorpet Date: Sun, 26 May 2024 19:30:00 +0200 Subject: [PATCH] Guiding the compiler: when to inline inside append, emplace_back --- auxi/core_util.h | 15 ++++++++++++ dynarray.h | 62 ++++++++++++++++++++++++++---------------------- 2 files changed, 49 insertions(+), 28 deletions(-) diff --git a/auxi/core_util.h b/auxi/core_util.h index cdbdc5d6..e592f193 100644 --- a/auxi/core_util.h +++ b/auxi/core_util.h @@ -28,6 +28,21 @@ #endif +#ifndef OEL_HAS_LIKELY + #if (__cplusplus >= 202001 and (!defined __clang__ or __clang_major__ >= 12)) or (defined _MSC_VER and _MSC_VER >= 1929) + #define OEL_HAS_LIKELY 1 + #else + #define OEL_HAS_LIKELY 0 + #endif +#endif + +#if OEL_HAS_LIKELY + #define OEL_UNLIKELY [[unlikely]] +#else + #define OEL_UNLIKELY +#endif + + #ifdef __GNUC__ #define OEL_ALWAYS_INLINE __attribute__((always_inline)) #else diff --git a/dynarray.h b/dynarray.h index 1838cb7e..56c9dfdb 100644 --- a/dynarray.h +++ b/dynarray.h @@ -401,19 +401,9 @@ class dynarray (void) _debugSizeUpdater{_m}; } -#ifdef _MSC_VER - __declspec(noinline) // to get the compiler to inline calling function -#endif - void _growBy(size_type const count) - { - auto const s = size(); - _realloc(_calcCapAdd(count, s), s); - } - - void _growByOne() - { - _realloc(_calcCapAddOne(), size()); - } + // These are not defined inline as a compiler hint + void _growBy(size_type const); + void _growByOne(); template< typename UninitFiller > @@ -522,7 +512,7 @@ class dynarray template< typename InputIter > InputIter _doAppend(InputIter src, size_type const count) { - if (_spareCapacity() < count) + if (_spareCapacity() < count) OEL_UNLIKELY _growBy(count); if constexpr (can_memmove_with) @@ -681,6 +671,23 @@ typename dynarray::iterator return _detail::MakeDynarrIter(_m, pPos); } + +template< typename T, typename Alloc > +#if defined _MSC_VER and !OEL_HAS_LIKELY + __declspec(noinline) // to get the compiler to inline calling function +#endif +void dynarray::_growBy(size_type const count) +{ + auto const s = size(); + _realloc(_calcCapAdd(count, s), s); +} + +template< typename T, typename Alloc > +void dynarray::_growByOne() +{ + _realloc(_calcCapAddOne(), size()); +} + template< typename T, typename Alloc > template< typename... Args > inline T & dynarray::emplace_back(Args &&... args) & @@ -695,6 +702,19 @@ inline T & dynarray::emplace_back(Args &&... args) & return *(_m.end++); } +template< typename T, typename Alloc > +inline void dynarray::append(size_type count, const T & val) +{ + if (_spareCapacity() < count) OEL_UNLIKELY + _growBy(count); + + auto const pos = _m.end; + _uninitFill::template call< forward_t >(pos, pos + count, _m, val); + + _debugSizeUpdater guard{_m}; + _m.end += count; +} + template< typename T, typename Alloc > dynarray::dynarray(dynarray && other, Alloc a) @@ -805,20 +825,6 @@ void dynarray::shrink_to_fit() } -template< typename T, typename Alloc > -inline void dynarray::append(size_type count, const T & val) -{ - if (_spareCapacity() < count) - _growBy(count); - - auto const pos = _m.end; - _uninitFill::template call< forward_t >(pos, pos + count, _m, val); - - _debugSizeUpdater guard{_m}; - _m.end += count; -} - - template< typename T, typename Alloc > inline void dynarray::pop_back() noexcept {