Skip to content

Commit

Permalink
Fixes StrCat() performance regression when not using libc++
Browse files Browse the repository at this point in the history
65d7b6d changed StrCat() to not use an intermediate buffer when the
result fits in the SSO buffer, but only libc++ has an SSO buffer large
enough for this optimization to work.

PiperOrigin-RevId: 564447163
Change-Id: I0c7fa4afed3369b36e13e7d1691eb7f933ea0091
  • Loading branch information
derekmauro authored and copybara-github committed Sep 11, 2023
1 parent 317085a commit f3eae68
Showing 1 changed file with 20 additions and 3 deletions.
23 changes: 20 additions & 3 deletions absl/strings/str_cat.h
Original file line number Diff line number Diff line change
Expand Up @@ -498,11 +498,28 @@ inline std::string SingleArgStrCat(unsigned long long x) {
inline std::string SingleArgStrCat(float x) { return FloatToString(x); }
inline std::string SingleArgStrCat(double x) { return FloatToString(x); }


template <typename T, typename = std::enable_if_t<std::is_arithmetic<T>{} &&
!std::is_same<T, char>{}>>
// As of September 2023, the SingleArgStrCat() optimization is only enabled for
// libc++. The reasons for this are:
// 1) The SSO size for libc++ is 23, while libstdc++ and MSSTL have an SSO size
// of 15. Since IntegerToString unconditionally resizes the string to 22 bytes,
// this causes both libstdc++ and MSSTL to allocate.
// 2) strings_internal::STLStringResizeUninitialized() only has an
// implementation that avoids initialization when using libc++. This isn't as
// relevant as (1), and the cost should be benchmarked if (1) ever changes on
// libstc++ or MSSTL.
#ifdef _LIBCPP_VERSION
#define ABSL_INTERNAL_STRCAT_ENABLE_FAST_CASE true
#else
#define ABSL_INTERNAL_STRCAT_ENABLE_FAST_CASE false
#endif

template <typename T, typename = std::enable_if_t<
ABSL_INTERNAL_STRCAT_ENABLE_FAST_CASE &&
std::is_arithmetic<T>{} && !std::is_same<T, char>{}>>
using EnableIfFastCase = T;

#undef ABSL_INTERNAL_STRCAT_ENABLE_FAST_CASE

} // namespace strings_internal

ABSL_MUST_USE_RESULT inline std::string StrCat() { return std::string(); }
Expand Down

0 comments on commit f3eae68

Please sign in to comment.