diff --git a/src/ConstString.hpp b/src/ConstString.hpp index cf979d5..ce45b47 100644 --- a/src/ConstString.hpp +++ b/src/ConstString.hpp @@ -15,9 +15,11 @@ ConstStringCore( inline constexpr Arbutils::ConstString operator"" _const(const char* c, size_t l) { - return Arbutils::ConstString(c, l); + return Arbutils::ConstString::Literal(c, l); +} +inline constexpr Arbutils::ConstString operator"" _c(const char* c, size_t l) { + return Arbutils::ConstString::Literal(c, l); } -inline constexpr Arbutils::ConstString operator"" _c(const char* c, size_t l) { return Arbutils::ConstString(c, l); } ConstStringCore( CaseInsensitiveConstString, @@ -28,10 +30,10 @@ ConstStringCore( };); inline constexpr Arbutils::CaseInsensitiveConstString operator"" _const_nocase(const char* c, size_t l) { - return Arbutils::CaseInsensitiveConstString(c, l); + return Arbutils::CaseInsensitiveConstString::Literal(c, l); } inline constexpr Arbutils::CaseInsensitiveConstString operator"" _cnc(const char* c, size_t l) { - return Arbutils::CaseInsensitiveConstString(c, l); + return Arbutils::CaseInsensitiveConstString::Literal(c, l); } #endif // ARBUTILS_CONSTSTRING_HPP diff --git a/src/__ConstStringCore.hpp b/src/__ConstStringCore.hpp index 814fdf6..abdab50 100644 --- a/src/__ConstStringCore.hpp +++ b/src/__ConstStringCore.hpp @@ -11,7 +11,7 @@ namespace Arbutils { \ class name { \ private: \ - const char* _str; \ + char* _str; \ size_t _length; \ uint32_t _hash; \ \ @@ -19,12 +19,19 @@ \ inline static int constexpr Length(const char* str) { return *str ? 1 + Length(str + 1) : 0; } \ \ + constexpr explicit name(const char* str, size_t size, bool) \ + : _str(const_cast(str)), _length(size), _hash(Hash(str)) {} \ + \ public: \ - constexpr name() : _str(""), _length(0), _hash(Hash("")){}; \ - constexpr explicit name(const char* str) : _str(str), _length(Length(str)), _hash(Hash(str)){}; \ - STDSTRINGCONSTEXPR explicit name(const std::string& str) \ - : _str(str.c_str()), _length(str.length()), _hash(Hash(str.c_str())){}; \ - constexpr explicit name(const char* str, size_t size) : _str(str), _length(size), _hash(Hash(str)){}; \ + explicit name(const char* str, size_t size) : _str(nullptr), _length(size), _hash(Hash(str)) { \ + _str = new char[size]; \ + strcpy(_str, str); \ + } \ + name() : name("", 0){}; \ + explicit name(const char* str) : name(str, Length(str)){}; \ + explicit name(const std::string& str) : name(str.c_str(), str.size()){}; \ + \ + static constexpr inline name Literal(const char* str, size_t size) { return name(str, size, false); } \ \ [[nodiscard]] inline constexpr const char* c_str() const noexcept { return _str; } \ [[nodiscard]] inline std::string std_str() const { return std::string(_str, _length); } \ diff --git a/tests/ConstStringTests.cpp b/tests/ConstStringTests.cpp index a4a4653..7596c46 100644 --- a/tests/ConstStringTests.cpp +++ b/tests/ConstStringTests.cpp @@ -42,5 +42,23 @@ TEST_CASE("Use case insensitive const string in switch case", "[Utilities]") { } } +__attribute__((optnone)) +static Arbutils::CaseInsensitiveConstString TestCreateConstString(){ + char originalVal [6]; + originalVal[0] = 'f'; + originalVal[1] = 'o'; + originalVal[2] = 'o'; + originalVal[3] = 'b'; + originalVal[4] = 'a'; + originalVal[5] = 'r'; + return Arbutils::CaseInsensitiveConstString(originalVal); +} + +TEST_CASE("Out of scope char* doesn't lose reference", "[Utilities]") { + Arbutils::CaseInsensitiveConstString val = TestCreateConstString(); + INFO(val.c_str()); + REQUIRE(strcmp(val.c_str(), "foobar") == 0); +} + #endif \ No newline at end of file