From 35e6ada72631379053fbf620e79ddaeafc9659e9 Mon Sep 17 00:00:00 2001 From: Stephan Bergmann Date: Mon, 14 Oct 2019 15:54:03 +0200 Subject: Fix misuse of OStringLiteral ...(which got introduced with 9b5dad13b56bdde7c40970351af3da3a2c3c9350 "loplugin:stringadd look for unnecessary temporaries", and had reportedly broken CppunitTest_sc_ucalc on tml's Windows build by hitting the "strlen( str ) == N - 1" assert at include/rtl/string.hxx:1867), by introducing rtl::OStringView (and rtl::OUStringView, for consistency). Change-Id: I766b600274302ded66a6bffc91be189b20ed1ac3 Reviewed-on: https://gerrit.libreoffice.org/80778 Tested-by: Jenkins Reviewed-by: Stephan Bergmann --- include/rtl/stringconcat.hxx | 55 ++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 55 insertions(+) (limited to 'include/rtl') diff --git a/include/rtl/stringconcat.hxx b/include/rtl/stringconcat.hxx index 3fd8b6720851..c075a29d9c80 100644 --- a/include/rtl/stringconcat.hxx +++ b/include/rtl/stringconcat.hxx @@ -480,6 +480,61 @@ struct ToStringHelper< OUStringNumber< T > > static const bool allowOUStringConcat = true; }; +// Abstractions over null-terminated char and sal_Unicode strings that sometimes are needed in +// concatenations of multiple such raw strings, as in +// +// char const * s1, s2; +// OString s = OStringView(s1) + s2; +// +// (Providing specializations of ToStringHelper and +// ToStringHelper would look dubious, as it would give meaning to expressions +// like +// +// std::string_view(s1) + s2 +// +// that do not involve any user-defined types.) + +class OStringView { +public: + explicit OStringView(char const * s): view_(s) {} + + std::size_t length() const { return view_.length(); } + + char const * data() const { return view_.data(); } + +private: + std::string_view view_; +}; + +template<> +struct ToStringHelper< OStringView > + { + static std::size_t length( const OStringView& v ) { return v.length(); } + static char* addData( char* buffer, const OStringView& v ) SAL_RETURNS_NONNULL { return addDataHelper( buffer, v.data(), v.length() ); } + static const bool allowOStringConcat = true; + static const bool allowOUStringConcat = false; + }; + +class OUStringView { +public: + explicit OUStringView(sal_Unicode const * s): view_(s) {} + + std::size_t length() const { return view_.length(); } + + sal_Unicode const * data() const { return view_.data(); } + +private: + std::u16string_view view_; +}; + +template<> +struct ToStringHelper< OUStringView > + { + static std::size_t length( const OUStringView& v ) { return v.length(); } + static sal_Unicode* addData( sal_Unicode* buffer, const OUStringView& v ) SAL_RETURNS_NONNULL { return addDataHelper( buffer, v.data(), v.length() ); } + static const bool allowOStringConcat = false; + static const bool allowOUStringConcat = true; + }; } // namespace -- cgit