summaryrefslogtreecommitdiff
path: root/source/fud_string.cpp
diff options
context:
space:
mode:
authorDominick Allen <djallen@librehumanitas.org>2024-10-15 20:56:26 -0500
committerDominick Allen <djallen@librehumanitas.org>2024-10-15 20:56:26 -0500
commitf3ac764684c64fbdd2094853a80b23e570cd5d9c (patch)
tree3b7f64480a1247455d28e23b6bb5ff63303c9170 /source/fud_string.cpp
parent71976e927cca43b970cb659c03fd6908c352ea3d (diff)
Conver to using static constructors for string, sqlite, files.
Diffstat (limited to 'source/fud_string.cpp')
-rw-r--r--source/fud_string.cpp113
1 files changed, 80 insertions, 33 deletions
diff --git a/source/fud_string.cpp b/source/fud_string.cpp
index 3a9aca0..82a9fe5 100644
--- a/source/fud_string.cpp
+++ b/source/fud_string.cpp
@@ -46,30 +46,37 @@ ssize_t cStringLength(const char* str, size_t maxLength)
return size;
}
-// NOLINTBEGIN(cppcoreguidelines-pro-type-reinterpret-cast)
-String::String(const utf8* cString) : String(reinterpret_cast<const char*>(cString))
-{
-}
-// NOLINTEND(cppcoreguidelines-pro-type-reinterpret-cast)
-
-String::String(const char* cString)
+StringResult String::makeFromCString(const char* cString)
{
auto lenResult = cStringLength(cString);
if (lenResult < 0 || lenResult >= SSIZE_MAX) {
- m_length = 1;
- m_capacity = 0;
- } else if (static_cast<size_t>(lenResult) < SSO_BUF_SIZE) {
- m_length = static_cast<size_t>(lenResult);
- fudAssert(copyMem(m_buffer.data(), m_buffer.size(), cString, m_length) == FudStatus::Success);
- fudAssert(nullTerminate() == FudStatus::Success);
- } else {
- m_length = static_cast<size_t>(lenResult);
- m_capacity = m_length + 1;
- m_data = static_cast<utf8*>(fudAlloc(m_capacity));
- fudAssert(m_data != nullptr);
- fudAssert(copyMem(m_data, m_capacity, cString, m_length) == FudStatus::Success);
- fudAssert(nullTerminate() == FudStatus::Success);
+ return StringResult::error(FudStatus::InvalidInput);
+ }
+
+ String output{};
+ auto* data = output.m_buffer.data();
+ output.m_length = static_cast<size_t>(lenResult);
+ if (output.m_length >= output.m_capacity) {
+ output.m_capacity = output.m_length + 1;
+ data = static_cast<utf8*>(fudAlloc(output.m_capacity));
+ if (data == nullptr) {
+ return StringResult::error(FudStatus::AllocFailure);
+ }
+ output.m_data = data;
}
+ auto copyStatus = copyMem(data, output.m_capacity, cString, output.m_length);
+ fudAssert(copyStatus == FudStatus::Success);
+ auto terminateStatus = output.nullTerminate();
+ fudAssert(terminateStatus == FudStatus::Success);
+
+ return StringResult::okay(std::move(output));
+}
+
+StringResult String::makeFromUtf8(const utf8* utf8String)
+{
+ // NOLINTBEGIN(cppcoreguidelines-pro-type-reinterpret-cast)
+ return makeFromCString(reinterpret_cast<const char*>(utf8String));
+ // NOLINTEND(cppcoreguidelines-pro-type-reinterpret-cast)
}
String::String(const String& rhs) : m_length{rhs.m_length}, m_capacity{rhs.m_capacity}
@@ -364,7 +371,7 @@ FudStatus String::append(StringView source)
return FudStatus::OperationInvalid;
}
const size_t newSize = newLength + 1; // cppcheck-suppress knownConditionTrueFalse
- if (newSize < newLength) { // cppcheck-suppress knownConditionTrueFalse
+ if (newSize < newLength) { // cppcheck-suppress knownConditionTrueFalse
return FudStatus::OperationInvalid;
}
if (newSize >= m_capacity) {
@@ -386,22 +393,60 @@ FudStatus String::append(StringView source)
return status;
}
-String String::catenate(const char* rhs) const
+StringResult String::catenate(const char* rhs) const
{
- String rhsString{rhs};
- return catenate(rhsString);
-}
+ if (!valid()) {
+ return StringResult::error(FudStatus::InvalidInput);
+ }
+
+ auto lenResult = cStringLength(rhs);
+ if (lenResult < 0 || lenResult >= SSIZE_MAX) {
+ return StringResult::error(FudStatus::InvalidInput);
+ }
+ size_t rhsLength = static_cast<size_t>(lenResult);
-String String::catenate(const String& rhs) const
-{
String output{};
- output.m_length = 1;
- output.m_capacity = 0;
+ if (SIZE_MAX - m_length < rhsLength)
+ {
+ return StringResult::error(FudStatus::Failure);
+ }
+
+ output.m_length = m_length + rhsLength;
+ auto* destPtr = output.m_buffer.data();
+ if (output.m_length >= output.m_capacity) {
+ output.m_capacity = output.m_length + 1;
+ destPtr = static_cast<utf8*>(fudAlloc(output.m_capacity));
+ if (destPtr == nullptr) {
+ return StringResult::error(FudStatus::AllocFailure);
+ }
+ output.m_data = destPtr;
+ }
+
+ auto status = copyMem(destPtr, m_capacity, data(), length());
+ fudAssert(status == FudStatus::Success);
+
+ status = copyMem(destPtr + length(), output.m_capacity - length(), rhs, rhsLength);
+ fudAssert(status == FudStatus::Success);
+
+ auto terminateStatus = output.nullTerminate();
+ fudAssert(terminateStatus == FudStatus::Success);
+
+ return StringResult::okay(std::move(output));
+}
+
+StringResult String::catenate(const String& rhs) const
+{
if (!valid() || !rhs.valid()) {
- return output;
+ return StringResult::error(FudStatus::InvalidInput);
}
+ if (SIZE_MAX - m_length < rhs.length())
+ {
+ return StringResult::error(FudStatus::Failure);
+ }
+
+ String output{};
output.m_length = m_length + rhs.length();
output.m_capacity = output.m_length + 1;
if (output.m_capacity < SSO_BUF_SIZE) {
@@ -414,12 +459,14 @@ String String::catenate(const String& rhs) const
auto* destPtr = output.data();
auto status = copyMem(destPtr, m_capacity, data(), length());
fudAssert(status == FudStatus::Success);
+
status = copyMem(destPtr + length(), output.m_capacity - length(), rhs.data(), rhs.length());
fudAssert(status == FudStatus::Success);
- static_cast<void>(status);
- fudAssert(output.nullTerminate() == FudStatus::Success);
- return output;
+ auto terminateStatus = output.nullTerminate();
+ fudAssert(terminateStatus == FudStatus::Success);
+
+ return StringResult::okay(std::move(output));
}
bool String::compare(const String& rhs) const