Compare commits

...

4 Commits

Author SHA1 Message Date
doylet b39afa94ff Path seperator cleanup 2026-07-31 22:41:14 +10:00
doylet e06f9df22b Add DN_V2F32Rotate 2026-07-31 21:55:12 +10:00
doylet 10e7b4ae82 Fix tests relying on emscripten maco before it is defined 2026-07-30 15:06:58 +10:00
doylet 70aee42856 Get the bar fixes 2026-07-28 00:42:40 +10:00
10 changed files with 1322 additions and 954 deletions
+261 -266
View File
@@ -1,4 +1,4 @@
// Generated by the DN single header generator 2026-07-21 20:17:37 // Generated by the DN single header generator 2026-07-31 22:40:42
// DN: Single header generator commented out => #if defined(_CLANGD) // DN: Single header generator commented out => #if defined(_CLANGD)
// #define DN_WITH_TESTS 1 // #define DN_WITH_TESTS 1
@@ -3259,22 +3259,22 @@ DN_API void DN_Str8x1024AppendFmtV(DN_Str8x1024 *str, DN_FMT_ATTRIB char const *
DN_FmtVAppend(str->data, &str->count, sizeof(str->data), fmt, args); DN_FmtVAppend(str->data, &str->count, sizeof(str->data), fmt, args);
} }
DN_API DN_Str8x32 DN_Str8x32FromU64(DN_U64 val, char separator) DN_API DN_Str8x32 DN_Str8x32FromU64(DN_U64 val, char seperator)
{ {
DN_Str8x32 result = {}; DN_Str8x32 result = {};
DN_Str8x32 temp = DN_Str8x32FromFmt("%" PRIu64, val); DN_Str8x32 temp = DN_Str8x32FromFmt("%" PRIu64, val);
DN_USize temp_index = 0; DN_USize temp_index = 0;
// NOTE: Write the digits the first, up to [0, 2] digits that do not need a thousandth separator // NOTE: Write the digits the first, up to [0, 2] digits that do not need a thousandth seperator
DN_USize range_without_separator = temp.count % 3; DN_USize range_without_seperator = temp.count % 3;
for (; temp_index < range_without_separator; temp_index++) for (; temp_index < range_without_seperator; temp_index++)
result.data[result.count++] = temp.data[temp_index]; result.data[result.count++] = temp.data[temp_index];
// NOTE: Write the subsequent digits and every 3rd digit, add the seperator // NOTE: Write the subsequent digits and every 3rd digit, add the seperator
DN_USize digit_counter = 0; DN_USize digit_counter = 0;
for (; temp_index < temp.count; temp_index++, digit_counter++) { for (; temp_index < temp.count; temp_index++, digit_counter++) {
if (separator && temp_index && (digit_counter % 3 == 0)) if (seperator && temp_index && (digit_counter % 3 == 0))
result.data[result.count++] = separator; result.data[result.count++] = seperator;
result.data[result.count++] = temp.data[temp_index]; result.data[result.count++] = temp.data[temp_index];
} }
return result; return result;
@@ -3758,8 +3758,8 @@ DN_API DN_Str8 DN_Str8TrimByteOrderMark(DN_Str8 string)
DN_API DN_Str8 DN_Str8FileNameFromPath(DN_Str8 path) DN_API DN_Str8 DN_Str8FileNameFromPath(DN_Str8 path)
{ {
DN_Str8 separators[] = {DN_Str8Lit("/"), DN_Str8Lit("\\")}; DN_Str8 seperators[] = {DN_Str8Lit("/"), DN_Str8Lit("\\")};
DN_Str8BSplitResult split = DN_Str8BSplitLastArray(path, separators, DN_ArrayCountU(separators)); DN_Str8BSplitResult split = DN_Str8BSplitLastArray(path, seperators, DN_ArrayCountU(seperators));
DN_Str8 result = split.rhs.count ? split.rhs : split.lhs; DN_Str8 result = split.rhs.count ? split.rhs : split.lhs;
return result; return result;
} }
@@ -3787,9 +3787,9 @@ DN_API DN_Str8 DN_Str8FileExtension(DN_Str8 path)
DN_API DN_Str8 DN_Str8FileDirectoryFromPath(DN_Str8 path) DN_API DN_Str8 DN_Str8FileDirectoryFromPath(DN_Str8 path)
{ {
DN_Str8 separators[] = {DN_Str8Lit("/"), DN_Str8Lit("\\")}; DN_Str8 seperators[] = {DN_Str8Lit("/"), DN_Str8Lit("\\")};
DN_Str8BSplitResult split = DN_Str8BSplitLastArray(path, separators, DN_ArrayCountU(separators)); DN_Str8BSplitResult split = DN_Str8BSplitLastArray(path, seperators, DN_ArrayCountU(seperators));
DN_Str8 result = split.lhs; DN_Str8 result = split.rhs.count == 0 ? DN_Str8Lit(".") : split.lhs;
return result; return result;
} }
@@ -4087,7 +4087,7 @@ DN_API DN_Str8 DN_Str8LineBreakAllocator(DN_Str8 src, DN_USize desired_width, DN
continue; continue;
} }
// Check if adding this word (plus separator space) would overflow // Check if adding this word (plus seperator space) would overflow
DN_USize combined_length = curr_line_length + 1 + split.lhs.count; DN_USize combined_length = curr_line_length + 1 + split.lhs.count;
if (combined_length > desired_width) { if (combined_length > desired_width) {
// Commit current line, start new line with current word // Commit current line, start new line with current word
@@ -4455,7 +4455,7 @@ DN_API DN_Str8Slice DN_Str8SplitAllocAVX512F(DN_Arena *arena, DN_Str8 string, DN
} }
#endif // DN_STR8_AVX512F #endif // DN_STR8_AVX512F
DN_API DN_Str8 DN_Str8SliceRender(DN_Str8Slice slice, DN_Str8 separator, DN_Arena *arena) DN_API DN_Str8 DN_Str8SliceRender(DN_Str8Slice slice, DN_Str8 seperator, DN_Arena *arena)
{ {
DN_Str8 result = {}; DN_Str8 result = {};
if (!arena) if (!arena)
@@ -4464,7 +4464,7 @@ DN_API DN_Str8 DN_Str8SliceRender(DN_Str8Slice slice, DN_Str8 separator, DN_Aren
DN_USize total_size = 0; DN_USize total_size = 0;
for (DN_USize index = 0; index < slice.count; index++) { for (DN_USize index = 0; index < slice.count; index++) {
if (index) if (index)
total_size += separator.count; total_size += seperator.count;
DN_Str8 item = slice.data[index]; DN_Str8 item = slice.data[index];
total_size += item.count; total_size += item.count;
} }
@@ -4474,8 +4474,8 @@ DN_API DN_Str8 DN_Str8SliceRender(DN_Str8Slice slice, DN_Str8 separator, DN_Aren
DN_USize write_index = 0; DN_USize write_index = 0;
for (DN_USize index = 0; index < slice.count; index++) { for (DN_USize index = 0; index < slice.count; index++) {
if (index) { if (index) {
DN_Memcpy(result.data + write_index, separator.data, separator.count); DN_Memcpy(result.data + write_index, seperator.data, seperator.count);
write_index += separator.count; write_index += seperator.count;
} }
DN_Str8 item = slice.data[index]; DN_Str8 item = slice.data[index];
DN_Memcpy(result.data + write_index, item.data, item.count); DN_Memcpy(result.data + write_index, item.data, item.count);
@@ -4594,7 +4594,7 @@ DN_API bool DN_Str16Eq(DN_Str16 lhs, DN_Str16 rhs)
} }
DN_API DN_Str16 DN_Str16SliceRender(DN_Str16Slice slice, DN_Str16 separator, DN_Arena *arena) DN_API DN_Str16 DN_Str16SliceRender(DN_Str16Slice slice, DN_Str16 seperator, DN_Arena *arena)
{ {
DN_Str16 result = {}; DN_Str16 result = {};
if (!arena) if (!arena)
@@ -4603,7 +4603,7 @@ DN_API DN_Str16 DN_Str16SliceRender(DN_Str16Slice slice, DN_Str16 separator, DN_
DN_USize total_size = 0; DN_USize total_size = 0;
for (DN_USize index = 0; index < slice.count; index++) { for (DN_USize index = 0; index < slice.count; index++) {
if (index) if (index)
total_size += separator.count; total_size += seperator.count;
DN_Str16 item = slice.data[index]; DN_Str16 item = slice.data[index];
total_size += item.count; total_size += item.count;
} }
@@ -4613,8 +4613,8 @@ DN_API DN_Str16 DN_Str16SliceRender(DN_Str16Slice slice, DN_Str16 separator, DN_
DN_USize write_index = 0; DN_USize write_index = 0;
for (DN_USize index = 0; index < slice.count; index++) { for (DN_USize index = 0; index < slice.count; index++) {
if (index) { if (index) {
DN_Memcpy(result.data + write_index, separator.data, separator.count * sizeof(result.data[0])); DN_Memcpy(result.data + write_index, seperator.data, seperator.count * sizeof(result.data[0]));
write_index += separator.count; write_index += seperator.count;
} }
DN_Str16 item = slice.data[index]; DN_Str16 item = slice.data[index];
DN_Memcpy(result.data + write_index, item.data, item.count * sizeof(result.data[0])); DN_Memcpy(result.data + write_index, item.data, item.count * sizeof(result.data[0]));
@@ -4916,6 +4916,188 @@ DN_API DN_Str8 DN_Str8FromStr8BuilderDelimitArena(DN_Str8Builder const *builder,
return result; return result;
} }
DN_API bool DN_PathAddRef(DN_Path *path, DN_Str8 add, DN_Arena *arena)
{
if (!arena || !path)
return false;
if (add.count == 0)
return true;
DN_Str8 const delimiter_array[] = {
DN_Str8Lit("\\"),
DN_Str8Lit("/")};
if (path->links_size == 0)
path->has_prefix_path_seperator = (add.data[0] == '/');
for (;;) {
DN_Str8BSplitResult delimiter = DN_Str8BSplitArray(add, delimiter_array, DN_ArrayCountU(delimiter_array));
for (; delimiter.lhs.data; delimiter = DN_Str8BSplitArray(delimiter.rhs, delimiter_array, DN_ArrayCountU(delimiter_array))) {
if (delimiter.lhs.count <= 0)
continue;
DN_Str8Link *link = DN_ArenaNew(arena, DN_Str8Link, DN_ZMem_Yes);
if (!link)
return false;
link->string = delimiter.lhs;
link->prev = path->tail;
if (path->tail)
path->tail->next = link;
else
path->head = link;
path->tail = link;
path->links_size += 1;
path->string_size += delimiter.lhs.count;
}
if (!delimiter.lhs.data)
break;
}
return true;
}
DN_API bool DN_PathAdd(DN_Path *path, DN_Str8 add, DN_Arena *arena)
{
DN_Str8 copy = DN_Str8FromStr8Arena(add, arena);
bool result = copy.count ? true : DN_PathAddRef(path, copy, arena);
return result;
}
DN_API bool DN_PathAddF(DN_Path *path, DN_Arena *arena, DN_FMT_ATTRIB char const *fmt, ...)
{
va_list args;
va_start(args, fmt);
DN_Str8 add = DN_Str8FmtVArena(arena, fmt, args);
va_end(args);
bool result = DN_PathAddRef(path, add, arena);
return result;
}
DN_API bool DN_PathPop(DN_Path *path)
{
if (!path)
return false;
if (path->tail) {
DN_Assert(path->head);
path->links_size -= 1;
path->string_size -= path->tail->string.count;
path->tail = path->tail->prev;
if (path->tail)
path->tail->next = nullptr;
else
path->head = nullptr;
} else {
DN_Assert(!path->head);
}
return true;
}
DN_API DN_Str8 DN_Str8FromPath(DN_Path const *path, DN_Str8 path_seperator, DN_Allocator allocator)
{
DN_Str8 result = {};
if (!path || path->links_size <= 0)
return result;
// NOTE: Each link except the last one needs the path seperator appended to it, '/' or '\\'
DN_USize string_size = (path->has_prefix_path_seperator ? path_seperator.count : 0) + path->string_size + ((path->links_size - 1) * path_seperator.count);
result = DN_Str8AllocAllocator(string_size, DN_ZMem_No, allocator);
if (result.data) {
char *dest = result.data;
if (path->has_prefix_path_seperator) {
DN_Memcpy(dest, path_seperator.data, path_seperator.count);
dest += path_seperator.count;
}
for (DN_Str8Link *link = path->head; link; link = link->next) {
DN_Str8 string = link->string;
DN_Memcpy(dest, string.data, string.count);
dest += string.count;
if (link != path->tail) {
DN_Memcpy(dest, path_seperator.data, path_seperator.count);
dest += path_seperator.count;
}
}
}
result.data[string_size] = 0;
return result;
}
DN_API DN_Str8 DN_Str8FmtVPathArena(DN_Str8 path_seperator, DN_Arena *arena, DN_FMT_ATTRIB char const *fmt, va_list args)
{
DN_TcScratch scratch = DN_TcScratchBeginArena(&arena, 1);
DN_Str8 path = DN_Str8FmtVArena(arena, fmt, args);
DN_Path fs_path = {};
DN_PathAddRef(&fs_path, path, &scratch.arena);
DN_Allocator allocator = DN_AllocatorFromArena(arena);
DN_Str8 result = DN_Str8FromPath(&fs_path, path_seperator, allocator);
DN_TcScratchEnd(&scratch);
return result;
}
DN_API DN_Str8 DN_Str8FmtPathArena(DN_Str8 path_seperator, DN_Arena *arena, DN_FMT_ATTRIB char const *fmt, ...)
{
DN_TcScratch scratch = DN_TcScratchBeginArena(&arena, 1);
va_list args;
va_start(args, fmt);
DN_Str8 path = DN_Str8FmtVArena(arena, fmt, args);
va_end(args);
DN_Path fs_path = {};
DN_PathAddRef(&fs_path, path, &scratch.arena);
DN_Allocator allocator = DN_AllocatorFromArena(arena);
DN_Str8 result = DN_Str8FromPath(&fs_path, path_seperator, allocator);
DN_TcScratchEnd(&scratch);
return result;
}
DN_API DN_Str8 DN_Str8FmtVPathPool(DN_Str8 path_seperator, DN_Pool *pool, DN_FMT_ATTRIB char const *fmt, va_list args)
{
DN_TcScratch scratch = DN_TcScratchBeginArena(&pool->arena, 1);
DN_Str8 path = DN_Str8FmtVPool(pool, fmt, args);
DN_Path fs_path = {};
DN_PathAddRef(&fs_path, path, &scratch.arena);
DN_Allocator allocator = DN_AllocatorFromPool(pool);
DN_Str8 result = DN_Str8FromPath(&fs_path, path_seperator, allocator);
DN_TcScratchEnd(&scratch);
return result;
}
DN_API DN_Str8 DN_Str8FmtPathPool(DN_Str8 path_seperator, DN_Pool *pool, DN_FMT_ATTRIB char const *fmt, ...)
{
va_list args;
va_start(args, fmt);
DN_Str8 result = DN_Str8FmtVPathPool(path_seperator, pool, fmt, args);
va_end(args);
return result;
}
DN_API DN_Str8 DN_Str8FmtOsPathPool(DN_Pool *pool, DN_FMT_ATTRIB char const *fmt, ...)
{
va_list args;
va_start(args, fmt);
DN_Str8 result = DN_Str8FmtVPathPool(DN_OsPathSeperatorStr8, pool, fmt, args);
va_end(args);
return result;
}
DN_API DN_Str8 DN_Str8FmtOsPathArena(DN_Arena *arena, DN_FMT_ATTRIB char const *fmt, ...)
{
va_list args;
va_start(args, fmt);
DN_Str8 result = DN_Str8FmtVPathArena(DN_OsPathSeperatorStr8, arena, fmt, args);
va_end(args);
return result;
}
// NOTE: DN_UTF // NOTE: DN_UTF
DN_API int DN_UTF8Encode(DN_U8 utf8[4], DN_U32 codepoint) DN_API int DN_UTF8Encode(DN_U8 utf8[4], DN_U32 codepoint)
{ {
@@ -5775,7 +5957,7 @@ static void DN_QSortInsertion_(void *array, DN_USize array_size, DN_USize elem_s
DN_TcScratchEnd(&scratch); DN_TcScratchEnd(&scratch);
} }
DN_API void DN_QSort(void *array, DN_USize array_size, DN_USize elem_size, void *user_context, DN_QSortCompareFunc *compare) DN_API void DN_QSort_(void *array, DN_USize array_size, DN_USize elem_size, void *user_context, DN_QSortCompareFunc *compare)
{ {
if (!array || array_size <= 1 || elem_size == 0 || !compare) if (!array || array_size <= 1 || elem_size == 0 || !compare)
return; return;
@@ -5818,14 +6000,22 @@ DN_API void DN_QSort(void *array, DN_USize array_size, DN_USize elem_size, void
// Move pivot to right of partition // Move pivot to right of partition
// 4, 5, 2, 3, |6, 8, ^7* // 4, 5, 2, 3, |6, 8, ^7*
DN_QSortSwapElems_(array, elem_size, partition_index, pivot_index); DN_QSortSwapElems_(array, elem_size, partition_index, pivot_index);
DN_QSort(array_u8, partition_index, elem_size, user_context, compare); DN_QSort_(array_u8, partition_index, elem_size, user_context, compare);
// Skip the value at partion index since that is guaranteed to be sorted. // Skip the value at partion index since that is guaranteed to be sorted.
// 4, 5, 2, 3, (x), 8, 7 // 4, 5, 2, 3, (x), 8, 7
DN_USize one_after_partition_index = partition_index + 1; DN_USize one_after_partition_index = partition_index + 1;
DN_QSort(array_u8 + (one_after_partition_index * elem_size), (array_size - one_after_partition_index), elem_size, user_context, compare); DN_QSort_(array_u8 + (one_after_partition_index * elem_size), (array_size - one_after_partition_index), elem_size, user_context, compare);
} }
#if defined(__cplusplus)
template <typename T>
DN_API void DN_QSort(T *array, DN_USize array_size, void *user_context, DN_QSortCompareFunc *compare)
{
DN_QSort_(array, array_size, sizeof(T), user_context, compare);
}
#endif
DN_API bool DN_QSortCompareStr8NaturalAsc(void const* lhs, void const *rhs, void *user_context) DN_API bool DN_QSortCompareStr8NaturalAsc(void const* lhs, void const *rhs, void *user_context)
{ {
DN_Str8EqCase eq_case = *DN_Cast(DN_Str8EqCase *) user_context; DN_Str8EqCase eq_case = *DN_Cast(DN_Str8EqCase *) user_context;
@@ -5878,32 +6068,32 @@ DN_API bool DN_QSortCompareBytesGT(void const* lhs, void const *rhs, void *user_
DN_API void DN_QSortBytesLT(void *array, DN_USize array_size, DN_USize elem_size) DN_API void DN_QSortBytesLT(void *array, DN_USize array_size, DN_USize elem_size)
{ {
DN_QSort(array, array_size, elem_size, &elem_size, DN_QSortCompareBytesLT); DN_QSort_(array, array_size, elem_size, &elem_size, DN_QSortCompareBytesLT);
} }
DN_API void DN_QSortBytesGT(void *array, DN_USize array_size, DN_USize elem_size) DN_API void DN_QSortBytesGT(void *array, DN_USize array_size, DN_USize elem_size)
{ {
DN_QSort(array, array_size, elem_size, &elem_size, DN_QSortCompareBytesGT); DN_QSort_(array, array_size, elem_size, &elem_size, DN_QSortCompareBytesGT);
} }
DN_API void DN_QSortStr8NaturalAsc(DN_Str8 *array, DN_USize array_size, DN_Str8EqCase eq_case) DN_API void DN_QSortStr8NaturalAsc(DN_Str8 *array, DN_USize array_size, DN_Str8EqCase eq_case)
{ {
DN_QSort(array, array_size, sizeof(*array), /*user_context=*/ &eq_case, DN_QSortCompareStr8NaturalAsc); DN_QSort_(array, array_size, sizeof(*array), /*user_context=*/ &eq_case, DN_QSortCompareStr8NaturalAsc);
} }
DN_API void DN_QSortStr8NaturalDesc(DN_Str8 *array, DN_USize array_size, DN_Str8EqCase eq_case) DN_API void DN_QSortStr8NaturalDesc(DN_Str8 *array, DN_USize array_size, DN_Str8EqCase eq_case)
{ {
DN_QSort(array, array_size, sizeof(*array), /*user_context=*/ &eq_case, DN_QSortCompareStr8NaturalDesc); DN_QSort_(array, array_size, sizeof(*array), /*user_context=*/ &eq_case, DN_QSortCompareStr8NaturalDesc);
} }
DN_API void DN_QSortStr8LexicographicAsc(DN_Str8 *array, DN_USize array_size, DN_Str8EqCase eq_case) DN_API void DN_QSortStr8LexicographicAsc(DN_Str8 *array, DN_USize array_size, DN_Str8EqCase eq_case)
{ {
DN_QSort(array, array_size, sizeof(*array), /*user_context=*/ &eq_case, DN_QSortCompareStr8LexicographicAsc); DN_QSort_(array, array_size, sizeof(*array), /*user_context=*/ &eq_case, DN_QSortCompareStr8LexicographicAsc);
} }
DN_API void DN_QSortStr8LexicographicDesc(DN_Str8 *array, DN_USize array_size, DN_Str8EqCase eq_case) DN_API void DN_QSortStr8LexicographicDesc(DN_Str8 *array, DN_USize array_size, DN_Str8EqCase eq_case)
{ {
DN_QSort(array, array_size, sizeof(*array), /*user_context=*/ &eq_case, DN_QSortCompareStr8LexicographicDesc); DN_QSort_(array, array_size, sizeof(*array), /*user_context=*/ &eq_case, DN_QSortCompareStr8LexicographicDesc);
} }
DN_API bool DN_BSearchLessThanBytes(void const *lhs, void const *rhs, void *user_context) DN_API bool DN_BSearchLessThanBytes(void const *lhs, void const *rhs, void *user_context)
@@ -6112,7 +6302,7 @@ DN_FORCE_INLINE DN_U64 DN_Murmur3FMix64_(DN_U64 k)
return k; return k;
} }
DN_API DN_U32 DN_Murmur3HashU128FromBytesX86(void const *bytes, int len, DN_U32 seed) DN_API DN_U32 DN_Murmur3HashU32FromBytesX86(void const *bytes, int len, DN_U32 seed)
{ {
const DN_U8 *data = (const DN_U8 *)bytes; const DN_U8 *data = (const DN_U8 *)bytes;
const int nblocks = len / 4; const int nblocks = len / 4;
@@ -6127,8 +6317,7 @@ DN_API DN_U32 DN_Murmur3HashU128FromBytesX86(void const *bytes, int len, DN_U32
const DN_U32 *blocks = (const DN_U32 *)(data + nblocks * 4); const DN_U32 *blocks = (const DN_U32 *)(data + nblocks * 4);
for (int i = -nblocks; i; i++) for (int i = -nblocks; i; i++) {
{
DN_U32 k1 = DN_Murmur3GetBlock32_(blocks, i); DN_U32 k1 = DN_Murmur3GetBlock32_(blocks, i);
k1 *= c1; k1 *= c1;
@@ -6147,8 +6336,7 @@ DN_API DN_U32 DN_Murmur3HashU128FromBytesX86(void const *bytes, int len, DN_U32
DN_U32 k1 = 0; DN_U32 k1 = 0;
switch (len & 3) switch (len & 3) {
{
case 3: case 3:
k1 ^= tail[2] << 16; k1 ^= tail[2] << 16;
case 2: case 2:
@@ -6187,8 +6375,7 @@ DN_API DN_Murmur3 DN_Murmur3HashU128FromBytesX64(void const *bytes, int len, DN_
const DN_U64 *blocks = (const DN_U64 *)(data); const DN_U64 *blocks = (const DN_U64 *)(data);
for (int i = 0; i < nblocks; i++) for (int i = 0; i < nblocks; i++) {
{
DN_U64 k1 = DN_Murmur3GetBlock64_(blocks, i * 2 + 0); DN_U64 k1 = DN_Murmur3GetBlock64_(blocks, i * 2 + 0);
DN_U64 k2 = DN_Murmur3GetBlock64_(blocks, i * 2 + 1); DN_U64 k2 = DN_Murmur3GetBlock64_(blocks, i * 2 + 1);
@@ -6219,8 +6406,7 @@ DN_API DN_Murmur3 DN_Murmur3HashU128FromBytesX64(void const *bytes, int len, DN_
DN_U64 k1 = 0; DN_U64 k1 = 0;
DN_U64 k2 = 0; DN_U64 k2 = 0;
switch (len & 15) switch (len & 15) {
{
case 15: case 15:
k2 ^= ((DN_U64)tail[14]) << 48; k2 ^= ((DN_U64)tail[14]) << 48;
case 14: case 14:
@@ -6788,6 +6974,12 @@ DN_API DN_V2F32 DN_V2F32Lerp(DN_V2F32 a, DN_F32 t, DN_V2F32 b)
return result; return result;
} }
DN_API DN_V2F32 DN_V2F32Rotate(DN_V2F32 v, DN_F32 cos_a, DN_F32 sin_a)
{
DN_V2F32 result = DN_V2F32From2N(v.x * cos_a - v.y * sin_a, v.x * sin_a + v.y * cos_a);
return result;
}
DN_API bool operator!=(DN_V2F32 lhs, DN_V2F32 rhs) DN_API bool operator!=(DN_V2F32 lhs, DN_V2F32 rhs)
{ {
bool result = !(lhs == rhs); bool result = !(lhs == rhs);
@@ -7392,7 +7584,7 @@ DN_API DN_V4F32 DN_V4F32Linear01FromSrgb01(DN_V4F32 srgb01)
DN_API DN_V4F32 DN_V4F32Linear01Desaturate(DN_V4F32 linear01, DN_F32 t01) DN_API DN_V4F32 DN_V4F32Linear01Desaturate(DN_V4F32 linear01, DN_F32 t01)
{ {
DN_F32 luminance = (linear01.r * DN_V3F32_Rgb_LUMINANCE.r) + (linear01.g * DN_V3F32_Rgb_LUMINANCE.g) + (linear01.b * DN_V3F32_Rgb_LUMINANCE.b); DN_F32 luminance = (linear01.r * DN_V3F32_RGB_LUMINANCE.r) + (linear01.g * DN_V3F32_RGB_LUMINANCE.g) + (linear01.b * DN_V3F32_RGB_LUMINANCE.b);
DN_V4F32 result = linear01; DN_V4F32 result = linear01;
result.rgb = DN_V3F32Lerp(result.rgb, t01, DN_V3F32From1N(luminance)); result.rgb = DN_V3F32Lerp(result.rgb, t01, DN_V3F32From1N(luminance));
return result; return result;
@@ -11603,7 +11795,7 @@ static void DN_OS_LoggerSetFilePathNoMutex_(DN_OSLogger *logger, DN_Pool *pool,
logger->file_path = {}; logger->file_path = {};
} }
DN_OS_FileClose(&logger->file); DN_OS_FileClose(&logger->file);
logger->file_path = DN_OS_PathFmtPool(pool, "%.*s", DN_Str8PrintFmt(file_path)); logger->file_path = DN_Str8FmtOsPathPool(pool, "%.*s", DN_Str8PrintFmt(file_path));
// NOTE: Clear the sticky file error flag if it was set // NOTE: Clear the sticky file error flag if it was set
logger->flags &= ~DN_OSLoggerFlags_FileError; logger->flags &= ~DN_OSLoggerFlags_FileError;
@@ -11626,7 +11818,7 @@ static void DN_OS_DoLogFileSetupAndRotation_(DN_OSLogger *logger)
// NOTE: Set a default file path to log to if it's not been set yet // NOTE: Set a default file path to log to if it's not been set yet
if (logger->file_path.count == 0) { if (logger->file_path.count == 0) {
DN_Str8 exe_dir = DN_OS_ExeDir(&scratch.arena); DN_Str8 exe_dir = DN_OS_ExeDir(&scratch.arena);
DN_Str8 default_file_path = DN_OS_PathFmtArena(&scratch.arena, "%.*s/dn.log", DN_Str8PrintFmt(exe_dir)); DN_Str8 default_file_path = DN_Str8FmtOsPathArena(&scratch.arena, "%.*s/dn.log", DN_Str8PrintFmt(exe_dir));
DN_OS_LoggerSetFilePathNoMutex_(logger, DN_TcMainPool(), default_file_path); DN_OS_LoggerSetFilePathNoMutex_(logger, DN_TcMainPool(), default_file_path);
} }
@@ -11825,26 +12017,26 @@ DN_API DN_Arena DN_OS_ArenaFromHeapBasic(DN_U64 size, DN_MemFlags flags)
} }
// NOTE: Date // NOTE: Date
DN_API DN_Str8x32 DN_OS_DateLocalTimeStr8(DN_Date time, char date_separator, char hms_separator) DN_API DN_Str8x32 DN_OS_DateLocalTimeStr8(DN_Date time, char date_seperator, char hms_seperator)
{ {
DN_Str8x32 result = DN_Str8x32FromFmt("%hu%c%02hhu%c%02hhu %02hhu%c%02hhu%c%02hhu", DN_Str8x32 result = DN_Str8x32FromFmt("%hu%c%02hhu%c%02hhu %02hhu%c%02hhu%c%02hhu",
time.year, time.year,
date_separator, date_seperator,
time.month, time.month,
date_separator, date_seperator,
time.day, time.day,
time.hour, time.hour,
hms_separator, hms_seperator,
time.minutes, time.minutes,
hms_separator, hms_seperator,
time.seconds); time.seconds);
return result; return result;
} }
DN_API DN_Str8x32 DN_OS_DateLocalTimeStr8Now(char date_separator, char hms_separator) DN_API DN_Str8x32 DN_OS_DateLocalTimeStr8Now(char date_seperator, char hms_seperator)
{ {
DN_Date time = DN_OS_DateLocalTimeNow(); DN_Date time = DN_OS_DateLocalTimeNow();
DN_Str8x32 result = DN_OS_DateLocalTimeStr8(time, date_separator, hms_separator); DN_Str8x32 result = DN_OS_DateLocalTimeStr8(time, date_seperator, hms_seperator);
return result; return result;
} }
@@ -11855,8 +12047,8 @@ DN_API DN_Str8 DN_OS_ExeDir(DN_Arena *arena)
return result; return result;
DN_TcScratch scratch = DN_TcScratchBeginArena(&arena, 1); DN_TcScratch scratch = DN_TcScratchBeginArena(&arena, 1);
DN_Str8 exe_path = DN_OS_ExePath(&scratch.arena); DN_Str8 exe_path = DN_OS_ExePath(&scratch.arena);
DN_Str8 separators[] = {DN_Str8Lit("/"), DN_Str8Lit("\\")}; DN_Str8 seperators[] = {DN_Str8Lit("/"), DN_Str8Lit("\\")};
DN_Str8BSplitResult split = DN_Str8BSplitLastArray(exe_path, separators, DN_ArrayCountU(separators)); DN_Str8BSplitResult split = DN_Str8BSplitLastArray(exe_path, seperators, DN_ArrayCountU(seperators));
result = DN_Str8FromStr8Arena(split.lhs, arena); result = DN_Str8FromStr8Arena(split.lhs, arena);
DN_TcScratchEnd(&scratch); DN_TcScratchEnd(&scratch);
return result; return result;
@@ -12185,201 +12377,6 @@ DN_API bool DN_OS_PathIsOlderThan(DN_Str8 path, DN_Str8 check_against)
return result; return result;
} }
DN_API bool DN_OS_PathAddRef(DN_Arena *arena, DN_OSPath *fs_path, DN_Str8 path)
{
if (!arena || !fs_path || path.count == 0)
return false;
if (path.count <= 0)
return true;
DN_Str8 const delimiter_array[] = {
DN_Str8Lit("\\"),
DN_Str8Lit("/")};
if (fs_path->links_size == 0)
fs_path->has_prefix_path_separator = (path.data[0] == '/');
for (;;) {
DN_Str8BSplitResult delimiter = DN_Str8BSplitArray(path, delimiter_array, DN_ArrayCountU(delimiter_array));
for (; delimiter.lhs.data; delimiter = DN_Str8BSplitArray(delimiter.rhs, delimiter_array, DN_ArrayCountU(delimiter_array))) {
if (delimiter.lhs.count <= 0)
continue;
DN_OSPathLink *link = DN_ArenaNew(arena, DN_OSPathLink, DN_ZMem_Yes);
if (!link)
return false;
link->string = delimiter.lhs;
link->prev = fs_path->tail;
if (fs_path->tail)
fs_path->tail->next = link;
else
fs_path->head = link;
fs_path->tail = link;
fs_path->links_size += 1;
fs_path->string_size += delimiter.lhs.count;
}
if (!delimiter.lhs.data)
break;
}
return true;
}
DN_API bool DN_OS_PathAdd(DN_Arena *arena, DN_OSPath *fs_path, DN_Str8 path)
{
DN_Str8 copy = DN_Str8FromStr8Arena(path, arena);
bool result = copy.count ? true : DN_OS_PathAddRef(arena, fs_path, copy);
return result;
}
DN_API bool DN_OS_PathAddF(DN_Arena *arena, DN_OSPath *fs_path, DN_FMT_ATTRIB char const *fmt, ...)
{
va_list args;
va_start(args, fmt);
DN_Str8 path = DN_Str8FmtVArena(arena, fmt, args);
va_end(args);
bool result = DN_OS_PathAddRef(arena, fs_path, path);
return result;
}
DN_API bool DN_OS_PathPop(DN_OSPath *fs_path)
{
if (!fs_path)
return false;
if (fs_path->tail) {
DN_Assert(fs_path->head);
fs_path->links_size -= 1;
fs_path->string_size -= fs_path->tail->string.count;
fs_path->tail = fs_path->tail->prev;
if (fs_path->tail)
fs_path->tail->next = nullptr;
else
fs_path->head = nullptr;
} else {
DN_Assert(!fs_path->head);
}
return true;
}
DN_API DN_Str8 DN_OS_PathBuildWithSeparatorAllocator(DN_Allocator allocator, DN_OSPath const *fs_path, DN_Str8 path_separator)
{
DN_Str8 result = {};
if (!fs_path || fs_path->links_size <= 0)
return result;
// NOTE: Each link except the last one needs the path separator appended to it, '/' or '\\'
DN_USize string_size = (fs_path->has_prefix_path_separator ? path_separator.count : 0) + fs_path->string_size + ((fs_path->links_size - 1) * path_separator.count);
result = DN_Str8AllocAllocator(string_size, DN_ZMem_No, allocator);
if (result.data) {
char *dest = result.data;
if (fs_path->has_prefix_path_separator) {
DN_Memcpy(dest, path_separator.data, path_separator.count);
dest += path_separator.count;
}
for (DN_OSPathLink *link = fs_path->head; link; link = link->next) {
DN_Str8 string = link->string;
DN_Memcpy(dest, string.data, string.count);
dest += string.count;
if (link != fs_path->tail) {
DN_Memcpy(dest, path_separator.data, path_separator.count);
dest += path_separator.count;
}
}
}
result.data[string_size] = 0;
return result;
}
DN_API DN_Str8 DN_OS_PathToArena(DN_Arena *arena, DN_Str8 path, DN_Str8 path_separator)
{
DN_OSPath fs_path = {};
DN_OS_PathAddRef(arena, &fs_path, path);
DN_Allocator allocator = DN_AllocatorFromArena(arena);
DN_Str8 result = DN_OS_PathBuildWithSeparatorAllocator(allocator, &fs_path, path_separator);
return result;
}
DN_API DN_Str8 DN_OS_PathToPool(DN_Pool *pool, DN_Str8 path, DN_Str8 path_separator)
{
DN_TcScratch scratch = DN_TcScratchBeginArena(&pool->arena, 1);
DN_OSPath fs_path = {};
DN_OS_PathAddRef(&scratch.arena, &fs_path, path);
DN_Allocator allocator = DN_AllocatorFromPool(pool);
DN_Str8 result = DN_OS_PathBuildWithSeparatorAllocator(allocator, &fs_path, path_separator);
DN_TcScratchEnd(&scratch);
return result;
}
DN_API DN_Str8 DN_OS_PathToFmtArena(DN_Arena *arena, DN_Str8 path_separator, DN_FMT_ATTRIB char const *fmt, ...)
{
DN_TcScratch scratch = DN_TcScratchBeginArena(&arena, 1);
va_list args;
va_start(args, fmt);
DN_Str8 path = DN_Str8FmtVArena(&scratch.arena, fmt, args);
va_end(args);
DN_Str8 result = DN_OS_PathToArena(arena, path, path_separator);
DN_TcScratchEnd(&scratch);
return result;
}
DN_API DN_Str8 DN_OS_PathToFmtPool(DN_Pool *pool, DN_Str8 path_separator, DN_FMT_ATTRIB char const *fmt, ...)
{
DN_TcScratch scratch = DN_TcScratchBeginArena(&pool->arena, 1);
va_list args;
va_start(args, fmt);
DN_Str8 path = DN_Str8FmtVArena(&scratch.arena, fmt, args);
va_end(args);
DN_Str8 result = DN_OS_PathToPool(pool, path, path_separator);
DN_TcScratchEnd(&scratch);
return result;
}
DN_API DN_Str8 DN_OS_PathArena(DN_Arena *arena, DN_Str8 path)
{
DN_Str8 result = DN_OS_PathToArena(arena, path, DN_OSPathSeparatorStr8);
return result;
}
DN_API DN_Str8 DN_OS_PathPool(DN_Pool *pool, DN_Str8 path)
{
DN_Str8 result = DN_OS_PathToPool(pool, path, DN_OSPathSeparatorStr8);
return result;
}
DN_API DN_Str8 DN_OS_PathFmtArena(DN_Arena *arena, DN_FMT_ATTRIB char const *fmt, ...)
{
DN_TcScratch scratch = DN_TcScratchBeginArena(&arena, 1);
va_list args;
va_start(args, fmt);
DN_Str8 path = DN_Str8FmtVArena(&scratch.arena, fmt, args);
va_end(args);
DN_Str8 result = DN_OS_PathArena(arena, path);
DN_TcScratchEnd(&scratch);
return result;
}
DN_API DN_Str8 DN_OS_PathFmtPool(DN_Pool *pool, DN_FMT_ATTRIB char const *fmt, ...)
{
DN_TcScratch scratch = DN_TcScratchBeginArena(&pool->arena, 1);
va_list args;
va_start(args, fmt);
DN_Str8 path = DN_Str8FmtVArena(&scratch.arena, fmt, args);
va_end(args);
DN_Str8 result = DN_OS_PathPool(pool, path);
DN_TcScratchEnd(&scratch);
return result;
}
DN_API DN_OSExecArgs DN_OS_ExecArgsDefault() DN_API DN_OSExecArgs DN_OS_ExecArgsDefault()
{ {
DN_OSExecArgs result = {}; DN_OSExecArgs result = {};
@@ -14605,25 +14602,25 @@ DN_API DN_OSPosixProcSelfStatus DN_OS_PosixProcSelfStatus()
for (DN_ForItSize(line_it, DN_Str8, lines.data, lines.count)) { for (DN_ForItSize(line_it, DN_Str8, lines.data, lines.count)) {
DN_Str8 line = DN_Str8TrimWhitespaceAround(*line_it.data); DN_Str8 line = DN_Str8TrimWhitespaceAround(*line_it.data);
if (DN_Str8StartsWith(line, NAME, DN_Str8EqCase_Insensitive)) { if (DN_Str8StartsWithInsensitive(line, NAME)) {
DN_Str8 str8 = DN_Str8TrimWhitespaceAround(DN_Str8Subset(line, NAME.count, line.count)); DN_Str8 str8 = DN_Str8TrimWhitespaceAround(DN_Str8Subset(line, NAME.count, line.count));
result.name_size = DN_Min(str8.count, sizeof(result.name)); result.name_size = DN_Min(str8.count, sizeof(result.name));
DN_Memcpy(result.name, str8.data, result.name_size); DN_Memcpy(result.name, str8.data, result.name_size);
} else if (DN_Str8StartsWith(line, PID, DN_Str8EqCase_Insensitive)) { } else if (DN_Str8StartsWithInsensitive(line, PID)) {
DN_Str8 str8 = DN_Str8TrimWhitespaceAround(DN_Str8Subset(line, PID.count, line.count)); DN_Str8 str8 = DN_Str8TrimWhitespaceAround(DN_Str8Subset(line, PID.count, line.count));
DN_U64FromResult to_u64 = DN_U64FromStr8(str8); DN_U64FromResult to_u64 = DN_U64FromStr8(str8);
result.pid = to_u64.value; result.pid = to_u64.value;
DN_Assert(to_u64.success); DN_Assert(to_u64.success);
} else if (DN_Str8StartsWith(line, VM_SIZE, DN_Str8EqCase_Insensitive)) { } else if (DN_Str8StartsWithInsensitive(line, VM_SIZE)) {
DN_Str8 size_with_kb = DN_Str8TrimWhitespaceAround(DN_Str8Subset(line, VM_SIZE.count, line.count)); DN_Str8 size_with_kb = DN_Str8TrimWhitespaceAround(DN_Str8Subset(line, VM_SIZE.count, line.count));
DN_Assert(DN_Str8EndsWith(size_with_kb, DN_Str8Lit("kB"))); DN_Assert(DN_Str8EndsWithSensitive(size_with_kb, DN_Str8Lit("kB")));
DN_Str8 vm_size = DN_Str8BSplit(size_with_kb, DN_Str8Lit(" ")).lhs; DN_Str8 vm_size = DN_Str8BSplit(size_with_kb, DN_Str8Lit(" ")).lhs;
DN_U64FromResult to_u64 = DN_U64FromStr8(vm_size); DN_U64FromResult to_u64 = DN_U64FromStr8(vm_size);
result.vm_size = DN_Kilobytes(to_u64.value); result.vm_size = DN_Kilobytes(to_u64.value);
DN_Assert(to_u64.success); DN_Assert(to_u64.success);
} else if (DN_Str8StartsWith(line, VM_PEAK, DN_Str8EqCase_Insensitive)) { } else if (DN_Str8StartsWithInsensitive(line, VM_PEAK)) {
DN_Str8 size_with_kb = DN_Str8TrimWhitespaceAround(DN_Str8Subset(line, VM_PEAK.count, line.count)); DN_Str8 size_with_kb = DN_Str8TrimWhitespaceAround(DN_Str8Subset(line, VM_PEAK.count, line.count));
DN_Assert(DN_Str8EndsWith(size_with_kb, DN_Str8Lit("kB"))); DN_Assert(DN_Str8EndsWithSensitive(size_with_kb, DN_Str8Lit("kB")));
DN_Str8 vm_size = DN_Str8BSplit(size_with_kb, DN_Str8Lit(" ")).lhs; DN_Str8 vm_size = DN_Str8BSplit(size_with_kb, DN_Str8Lit(" ")).lhs;
DN_U64FromResult to_u64 = DN_U64FromStr8(vm_size); DN_U64FromResult to_u64 = DN_U64FromStr8(vm_size);
result.vm_peak = DN_Kilobytes(to_u64.value); result.vm_peak = DN_Kilobytes(to_u64.value);
@@ -14637,8 +14634,6 @@ DN_API DN_OSPosixProcSelfStatus DN_OS_PosixProcSelfStatus()
} }
#elif defined(DN_PLATFORM_WIN32) #elif defined(DN_PLATFORM_WIN32)
// DN: Single header generator commented out => #include "OS/dn_os_w32.cpp" // DN: Single header generator commented out => #include "OS/dn_os_w32.cpp"
#define DN_OS_W32_CPP
// DN: Single header generator commented out => #if defined(_CLANGD) // DN: Single header generator commented out => #if defined(_CLANGD)
// #define DN_WITH_OS 1 // #define DN_WITH_OS 1
// #include "../dn.h" // #include "../dn.h"
@@ -15288,9 +15283,9 @@ DN_API bool DN_OS_PathIterateDir(DN_Str8 path, DN_OSDirIterator *it)
// add those characters in this branch, so overwrite the null // add those characters in this branch, so overwrite the null
// character, add the glob and re-null terminate the buffer. // character, add the glob and re-null terminate the buffer.
if (needs_asterisks) if (needs_asterisks)
adjusted_path = DN_OS_PathFmtArena(&scratch.arena, "%.*s*", DN_Str8PrintFmt(path)); adjusted_path = DN_Str8FmtOsPathArena(&scratch.arena, "%.*s*", DN_Str8PrintFmt(path));
else else
adjusted_path = DN_OS_PathFmtArena(&scratch.arena, "%.*s/*", DN_Str8PrintFmt(path)); adjusted_path = DN_Str8FmtOsPathArena(&scratch.arena, "%.*s/*", DN_Str8PrintFmt(path));
} }
path16 = DN_OS_W32Str8ToStr16(&scratch.arena, adjusted_path); path16 = DN_OS_W32Str8ToStr16(&scratch.arena, adjusted_path);
@@ -17483,17 +17478,17 @@ DN_NETRequestHandle DN_NET_EmcDoHTTP(DN_NETCore *net, DN_Str8 url, DN_Str8 metho
// NOTE: Setup the HTTP request via Emscripten // NOTE: Setup the HTTP request via Emscripten
emscripten_fetch_attr_t fetch_attribs = {}; emscripten_fetch_attr_t fetch_attribs = {};
{ {
DN_Assert(req->args.payload.data[req->args.payload.size] == 0); DN_Assert(req->args.payload.data[req->args.payload.count] == 0);
DN_Assert(req->url.data[req->url.size] == 0); DN_Assert(req->url.data[req->url.count] == 0);
// NOTE: Setup request for emscripten // NOTE: Setup request for emscripten
emscripten_fetch_attr_init(&fetch_attribs); emscripten_fetch_attr_init(&fetch_attribs);
fetch_attribs.requestData = req->args.payload.data; fetch_attribs.requestData = req->args.payload.data;
fetch_attribs.requestDataSize = req->args.payload.size; fetch_attribs.requestDataSize = req->args.payload.count;
DN_Assert(req->method.size < DN_ArrayCountU(fetch_attribs.requestMethod)); DN_Assert(req->method.count < DN_ArrayCountU(fetch_attribs.requestMethod));
DN_Memcpy(fetch_attribs.requestMethod, req->method.data, req->method.size); DN_Memcpy(fetch_attribs.requestMethod, req->method.data, req->method.count);
fetch_attribs.requestMethod[req->method.size] = 0; fetch_attribs.requestMethod[req->method.count] = 0;
// NOTE: Assign HTTP headers // NOTE: Assign HTTP headers
if (req->args.headers_size) { if (req->args.headers_size) {
@@ -17507,9 +17502,9 @@ DN_NETRequestHandle DN_NET_EmcDoHTTP(DN_NETCore *net, DN_Str8 url, DN_Str8 metho
// NOTE: Handle basic auth // NOTE: Handle basic auth
if (req->args.flags & DN_NETDoHTTPFlags_BasicAuth) { if (req->args.flags & DN_NETDoHTTPFlags_BasicAuth) {
if (req->args.username.size && req->args.password.size) { if (req->args.username.count && req->args.password.count) {
DN_Assert(req->args.username.data[req->args.username.size] == 0); DN_Assert(req->args.username.data[req->args.username.count] == 0);
DN_Assert(req->args.password.data[req->args.password.size] == 0); DN_Assert(req->args.password.data[req->args.password.count] == 0);
fetch_attribs.withCredentials = true; fetch_attribs.withCredentials = true;
fetch_attribs.userName = req->args.username.data; fetch_attribs.userName = req->args.username.data;
fetch_attribs.password = req->args.password.data; fetch_attribs.password = req->args.password.data;
@@ -17579,7 +17574,7 @@ void DN_NET_EmcDoWSSend(DN_NETRequestHandle handle, DN_Str8 data, DN_NETWSSend s
} break; } break;
case DN_NETWSSend_Binary: { case DN_NETWSSend_Binary: {
result = emscripten_websocket_send_binary(emc_request->socket, data.data, data.size); result = emscripten_websocket_send_binary(emc_request->socket, data.data, data.count);
} break; } break;
case DN_NETWSSend_Close: { case DN_NETWSSend_Close: {
+54 -55
View File
@@ -1,4 +1,4 @@
// Generated by the DN single header generator 2026-07-21 20:17:37 // Generated by the DN single header generator 2026-07-31 22:40:42
#if !defined(DN_H) #if !defined(DN_H)
#define DN_H #define DN_H
@@ -302,6 +302,7 @@
// NOTE: Platform identification // NOTE: Platform identification
#if !defined(DN_PLATFORM_EMSCRIPTEN) && \ #if !defined(DN_PLATFORM_EMSCRIPTEN) && \
!defined(DN_PLATFORM_POSIX) && \ !defined(DN_PLATFORM_POSIX) && \
!defined(DN_PLATFORM_ARM64) && \
!defined(DN_PLATFORM_WIN32) !defined(DN_PLATFORM_WIN32)
#if defined(__aarch64__) || defined(_M_ARM64) #if defined(__aarch64__) || defined(_M_ARM64)
#define DN_PLATFORM_ARM64 #define DN_PLATFORM_ARM64
@@ -1504,6 +1505,25 @@ enum DN_Str8BuilderAdd
DN_Str8BuilderAdd_Prepend, DN_Str8BuilderAdd_Prepend,
}; };
#if !defined(DN_OsPathSeperator)
#if defined(DN_PLATFORM_WIN32)
#define DN_OsPathSeperator "\\"
#else
#define DN_OsPathSeperator "/"
#endif
#define DN_OsPathSeperatorStr8 DN_Str8Lit(DN_OsPathSeperator)
#endif
typedef struct DN_Path DN_Path;
struct DN_Path
{
bool has_prefix_path_seperator;
DN_Str8Link *head;
DN_Str8Link *tail;
DN_USize string_size;
DN_U16 links_size;
};
typedef DN_U32 DN_AgeUnit; typedef DN_U32 DN_AgeUnit;
enum DN_AgeUnit_ enum DN_AgeUnit_
{ {
@@ -4227,7 +4247,6 @@ enum DN_OSFileRotateFlags_
DN_OSFileRotateFlags_KeepBaseFile = 1 << 0, DN_OSFileRotateFlags_KeepBaseFile = 1 << 0,
}; };
enum DN_OSPathInfoType enum DN_OSPathInfoType
{ {
DN_OSPathInfoType_Unknown, DN_OSPathInfoType_Unknown,
@@ -4286,34 +4305,6 @@ enum DN_OSFileAccess_
DN_OSFileAccess_All = DN_OSFileAccess_ReadWrite | DN_OSFileAccess_Execute | DN_OSFileAccess_AppendOnly, DN_OSFileAccess_All = DN_OSFileAccess_ReadWrite | DN_OSFileAccess_Execute | DN_OSFileAccess_AppendOnly,
}; };
// NOTE: DN_OSPath
#if !defined(DN_OSPathSeparator)
#if defined(DN_PLATFORM_WIN32)
#define DN_OSPathSeparator "\\"
#else
#define DN_OSPathSeparator "/"
#endif
#define DN_OSPathSeparatorStr8 DN_Str8Lit(DN_OSPathSeparator)
#endif
typedef struct DN_OSPathLink DN_OSPathLink;
struct DN_OSPathLink
{
DN_Str8 string;
DN_OSPathLink *next;
DN_OSPathLink *prev;
};
typedef struct DN_OSPath DN_OSPath;
struct DN_OSPath
{
bool has_prefix_path_separator;
DN_OSPathLink *head;
DN_OSPathLink *tail;
DN_USize string_size;
DN_U16 links_size;
};
typedef DN_U32 DN_OSExecFlags; typedef DN_U32 DN_OSExecFlags;
enum DN_OSExecFlags_ enum DN_OSExecFlags_
{ {
@@ -5028,7 +5019,7 @@ DN_API void DN_Str8x512AppendFmtV
DN_API void DN_Str8x1024AppendFmt (DN_Str8x1024 *str, DN_FMT_ATTRIB char const *fmt, ...); DN_API void DN_Str8x1024AppendFmt (DN_Str8x1024 *str, DN_FMT_ATTRIB char const *fmt, ...);
DN_API void DN_Str8x1024AppendFmtV (DN_Str8x1024 *str, DN_FMT_ATTRIB char const *fmt, va_list args); DN_API void DN_Str8x1024AppendFmtV (DN_Str8x1024 *str, DN_FMT_ATTRIB char const *fmt, va_list args);
DN_API DN_Str8x32 DN_Str8x32FromU64 (DN_U64 val, char separator); DN_API DN_Str8x32 DN_Str8x32FromU64 (DN_U64 val, char seperator);
DN_API bool DN_Str8Is (DN_Str8 string, DN_Str8IsFlags flags); DN_API bool DN_Str8Is (DN_Str8 string, DN_Str8IsFlags flags);
DN_API char * DN_Str8End (DN_Str8 string); DN_API char * DN_Str8End (DN_Str8 string);
DN_API DN_Str8 DN_Str8Subset (DN_Str8 string, DN_USize offset, DN_USize count); DN_API DN_Str8 DN_Str8Subset (DN_Str8 string, DN_USize offset, DN_USize count);
@@ -5104,13 +5095,13 @@ DN_API DN_USize DN_Str8SplitAVX512F
DN_API DN_Str8Slice DN_Str8SplitAllocAVX512F (DN_Arena *arena, DN_Str8 string, DN_Str8 delimiter, DN_Str8SplitFlags flags); DN_API DN_Str8Slice DN_Str8SplitAllocAVX512F (DN_Arena *arena, DN_Str8 string, DN_Str8 delimiter, DN_Str8SplitFlags flags);
#endif #endif
DN_API DN_Str8 DN_Str8SliceRender (DN_Str8Slice array, DN_Str8 separator, DN_Arena *arena); DN_API DN_Str8 DN_Str8SliceRender (DN_Str8Slice array, DN_Str8 seperator, DN_Arena *arena);
DN_API DN_Str8 DN_Str8RenderSpaceSep (DN_Str8Slice array, DN_Arena *arena); DN_API DN_Str8 DN_Str8RenderSpaceSep (DN_Str8Slice array, DN_Arena *arena);
DN_API int DN_Str8CompareNatural (DN_Str8 lhs, DN_Str8 rhs, DN_Str8EqCase eq_case); DN_API int DN_Str8CompareNatural (DN_Str8 lhs, DN_Str8 rhs, DN_Str8EqCase eq_case);
DN_API int DN_Str8CompareLexicographic (DN_Str8 lhs, DN_Str8 rhs, DN_Str8EqCase eq_case); DN_API int DN_Str8CompareLexicographic (DN_Str8 lhs, DN_Str8 rhs, DN_Str8EqCase eq_case);
DN_API bool DN_Str16Eq (DN_Str16 lhs, DN_Str16 rhs); DN_API bool DN_Str16Eq (DN_Str16 lhs, DN_Str16 rhs);
DN_API DN_Str16 DN_Str16SliceRender (DN_Str16Slice array, DN_Str16 separator, DN_Arena *arena); DN_API DN_Str16 DN_Str16SliceRender (DN_Str16Slice array, DN_Str16 seperator, DN_Arena *arena);
DN_API DN_Str16 DN_Str16RenderSpaceSep (DN_Str16Slice array, DN_Arena *arena); DN_API DN_Str16 DN_Str16RenderSpaceSep (DN_Str16Slice array, DN_Arena *arena);
DN_API DN_Str8Builder DN_Str8BuilderFromArena (DN_Arena *arena); DN_API DN_Str8Builder DN_Str8BuilderFromArena (DN_Arena *arena);
@@ -5146,6 +5137,18 @@ DN_API DN_Str8 DN_Str8FromStr8BuilderArena
DN_API DN_Str8 DN_Str8FromStr8BuilderDelimitAllocator (DN_Str8Builder const *builder, DN_Str8 delimiter, DN_Allocator allocator); DN_API DN_Str8 DN_Str8FromStr8BuilderDelimitAllocator (DN_Str8Builder const *builder, DN_Str8 delimiter, DN_Allocator allocator);
DN_API DN_Str8 DN_Str8FromStr8BuilderDelimitArena (DN_Str8Builder const *builder, DN_Str8 delimiter, DN_Arena *arena); DN_API DN_Str8 DN_Str8FromStr8BuilderDelimitArena (DN_Str8Builder const *builder, DN_Str8 delimiter, DN_Arena *arena);
DN_API bool DN_PathAddRef (DN_Path *path, DN_Str8 add, DN_Arena *arena);
DN_API bool DN_PathAdd (DN_Path *path, DN_Str8 add, DN_Arena *arena);
DN_API bool DN_PathAddF (DN_Path *path, DN_FMT_ATTRIB char const *fmt, ...);
DN_API bool DN_PathPop (DN_Path *path);
DN_API DN_Str8 DN_Str8FromPath (DN_Path const *path, DN_Str8 path_seperator, DN_Allocator allocator);
DN_API DN_Str8 DN_Str8FmtPathVArena (DN_Str8 path_seperator, DN_Arena *arena, char const *fmt, va_list args);
DN_API DN_Str8 DN_Str8FmtPathArena (DN_Str8 path_seperator, DN_Arena *arena, DN_FMT_ATTRIB char const *fmt, ...);
DN_API DN_Str8 DN_Str8FmtPathVPool (DN_Str8 path_seperator, DN_Pool *pool, char const *fmt, va_list args);
DN_API DN_Str8 DN_Str8FmtPathPool (DN_Str8 path_seperator, DN_Pool *pool, DN_FMT_ATTRIB char const *fmt, ...);
DN_API DN_Str8 DN_Str8FmtOsPathArena (DN_Arena *arena, DN_FMT_ATTRIB char const *fmt, ...);
DN_API DN_Str8 DN_Str8FmtOsPathPool (DN_Pool *pool, DN_FMT_ATTRIB char const *fmt, ...);
DN_API int DN_UTF8Encode (DN_U8 utf8[4], DN_U32 codepoint); DN_API int DN_UTF8Encode (DN_U8 utf8[4], DN_U32 codepoint);
DN_API int DN_UTF16Encode (DN_U16 utf16[2], DN_U32 codepoint); DN_API int DN_UTF16Encode (DN_U16 utf16[2], DN_U32 codepoint);
DN_API DN_UTF8DecodeResult DN_UTF8Decode (DN_Str8 stream); DN_API DN_UTF8DecodeResult DN_UTF8Decode (DN_Str8 stream);
@@ -5249,7 +5252,14 @@ DN_API void DN_ProfilerFmtToStdout
DN_API DN_F64 DN_ProfilerSecFromTsc (DN_Profiler *profiler, DN_U64 duration_tsc); DN_API DN_F64 DN_ProfilerSecFromTsc (DN_Profiler *profiler, DN_U64 duration_tsc);
DN_API DN_F64 DN_ProfilerMsFromTsc (DN_Profiler *profiler, DN_U64 duration_tsc); DN_API DN_F64 DN_ProfilerMsFromTsc (DN_Profiler *profiler, DN_U64 duration_tsc);
DN_API void DN_QSort (void *array, DN_USize array_size, DN_USize elem_size, void *user_context, DN_QSortCompareFunc *compare); DN_API void DN_QSort_ (void *array, DN_USize array_size, DN_USize elem_size, void *user_context, DN_QSortCompareFunc *compare);
#if defined(__cplusplus)
template <typename T> void DN_QSortT (T *array, DN_USize array_size, void *user_context, DN_QSortCompareFunc *compare);
#define DN_QSort(array, array_size, user_context, compare) DN_QSortT(array, array_size, user_context, compare)
#else
#define DN_QSort(array, array_size, user_context, compare) DN_QSort_(array, array_size, sizeof(*array), user_context, compare)
#endif
DN_API bool DN_QSortCompareStr8NaturalAsc (void const* lhs, void const *rhs, void *user_context); DN_API bool DN_QSortCompareStr8NaturalAsc (void const* lhs, void const *rhs, void *user_context);
DN_API bool DN_QSortCompareStr8NaturalDesc (void const* lhs, void const *rhs, void *user_context); DN_API bool DN_QSortCompareStr8NaturalDesc (void const* lhs, void const *rhs, void *user_context);
DN_API bool DN_QSortCompareStr8LexicographicAsc (void const* lhs, void const *rhs, void *user_context); DN_API bool DN_QSortCompareStr8LexicographicAsc (void const* lhs, void const *rhs, void *user_context);
@@ -5429,10 +5439,16 @@ DN_API DN_V2U16& operator/=
DN_API DN_V2U16& operator-= (DN_V2U16& lhs, DN_V2U16 rhs); DN_API DN_V2U16& operator-= (DN_V2U16& lhs, DN_V2U16 rhs);
DN_API DN_V2U16& operator+= (DN_V2U16& lhs, DN_V2U16 rhs); DN_API DN_V2U16& operator+= (DN_V2U16& lhs, DN_V2U16 rhs);
// NOTE: DN_V2F32
// API
// DN_V2F32Rotate
// Rotate a vector using the precomputed cosine and sine value of the angle (e.g.
// `cos_a => cos(your_angle * 2.f * DN_PiF32)` and `sin_a => sinf(your_angle * 2.f * DN_PiF32)`)
#define DN_V2U32Zero DN_Literal(DN_V2U32){{(DN_U32)(0), (DN_U32)(0)}} #define DN_V2U32Zero DN_Literal(DN_V2U32){{(DN_U32)(0), (DN_U32)(0)}}
#define DN_V2U32One DN_Literal(DN_V2U32){{(DN_U32)(1), (DN_U32)(1)}} #define DN_V2U32One DN_Literal(DN_V2U32){{(DN_U32)(1), (DN_U32)(1)}}
#define DN_V2U32From1N(x) DN_Literal(DN_V2U32){{(DN_U32)(x), (DN_U32)(x)}} #define DN_V2U32From1N(x) DN_Literal(DN_V2U32){{(DN_U32)(x), (DN_U32)(x)}}
#define DN_V2U32From2N(x, y) DN_Literal(DN_V2U32){{(DN_U32)(x), (DN_U32)(y)}} #define DN_V2U32From2N(x, y) DN_Literal(DN_V2U32){{(DN_U32)(x), (DN_U32)(y)}}
#define DN_V2U32FromV2(v2) DN_Literal(DN_V2U32){{(DN_U32)(v2.x), (DN_U32)(v2.y)}}
#define DN_V2F32Zero DN_Literal(DN_V2F32){{(DN_F32)(0), (DN_F32)(0)}} #define DN_V2F32Zero DN_Literal(DN_V2F32){{(DN_F32)(0), (DN_F32)(0)}}
#define DN_V2F32One DN_Literal(DN_V2F32){{(DN_F32)(1), (DN_F32)(1)}} #define DN_V2F32One DN_Literal(DN_V2F32){{(DN_F32)(1), (DN_F32)(1)}}
@@ -5441,6 +5457,7 @@ DN_API DN_V2U16& operator+=
#define DN_V2F32FromV2(xy) DN_Literal(DN_V2F32){{(DN_F32)(xy).x, (DN_F32)(xy).y}} #define DN_V2F32FromV2(xy) DN_Literal(DN_V2F32){{(DN_F32)(xy).x, (DN_F32)(xy).y}}
DN_API DN_V2F32 DN_V2F32Lerp (DN_V2F32 a, DN_F32 t, DN_V2F32 b); DN_API DN_V2F32 DN_V2F32Lerp (DN_V2F32 a, DN_F32 t, DN_V2F32 b);
DN_API DN_V2F32 DN_V2F32Rotate (DN_V2F32 v, DN_F32 cos_a, DN_F32 sin_a);
DN_API bool operator!= (DN_V2F32 lhs, DN_V2F32 rhs); DN_API bool operator!= (DN_V2F32 lhs, DN_V2F32 rhs);
DN_API bool operator== (DN_V2F32 lhs, DN_V2F32 rhs); DN_API bool operator== (DN_V2F32 lhs, DN_V2F32 rhs);
@@ -5510,7 +5527,7 @@ DN_API DN_F32 DN_V2F32Area
// NOTE: Grayscale co-efficients from: // NOTE: Grayscale co-efficients from:
// https://github.com/EpicGames/UnrealEngine/blob/260bb2e1c5610b31c63a36206eedd289409c5f11/Engine/Source/Runtime/Core/Private/Math/Color.cpp#L304 // https://github.com/EpicGames/UnrealEngine/blob/260bb2e1c5610b31c63a36206eedd289409c5f11/Engine/Source/Runtime/Core/Private/Math/Color.cpp#L304
DN_V3F32 static const DN_V3F32_Rgb_LUMINANCE = DN_V3F32From3N(0.3f, 0.59f, 0.11f); DN_V3F32 static const DN_V3F32_RGB_LUMINANCE = DN_V3F32From3N(0.3f, 0.59f, 0.11f);
DN_API bool operator== (DN_V3F32 lhs, DN_V3F32 rhs); DN_API bool operator== (DN_V3F32 lhs, DN_V3F32 rhs);
DN_API bool operator!= (DN_V3F32 lhs, DN_V3F32 rhs); DN_API bool operator!= (DN_V3F32 lhs, DN_V3F32 rhs);
@@ -6526,8 +6543,8 @@ DN_API void * DN_OS_MemAlloc (D
DN_API void DN_OS_MemDealloc (void *ptr); DN_API void DN_OS_MemDealloc (void *ptr);
DN_API DN_Date DN_OS_DateLocalTimeNow (); DN_API DN_Date DN_OS_DateLocalTimeNow ();
DN_API DN_Str8x32 DN_OS_DateLocalTimeStr8Now (char date_separator = '-', char hms_separator = ':'); DN_API DN_Str8x32 DN_OS_DateLocalTimeStr8Now (char date_seperator = '-', char hms_seperator = ':');
DN_API DN_Str8x32 DN_OS_DateLocalTimeStr8 (DN_Date time, char date_separator = '-', char hms_separator = ':'); DN_API DN_Str8x32 DN_OS_DateLocalTimeStr8 (DN_Date time, char date_seperator = '-', char hms_seperator = ':');
DN_API DN_U64 DN_OS_DateUnixTimeNs (); DN_API DN_U64 DN_OS_DateUnixTimeNs ();
#define DN_OS_DateUnixTimeUs() (DN_OS_DateUnixTimeNs() / 1000) #define DN_OS_DateUnixTimeUs() (DN_OS_DateUnixTimeNs() / 1000)
#define DN_OS_DateUnixTimeMs() (DN_OS_DateUnixTimeNs() / (1000 * 1000)) #define DN_OS_DateUnixTimeMs() (DN_OS_DateUnixTimeNs() / (1000 * 1000))
@@ -6626,24 +6643,6 @@ DN_API bool DN_OS_PathIsDir (D
DN_API bool DN_OS_PathMakeDir (DN_Str8 path); DN_API bool DN_OS_PathMakeDir (DN_Str8 path);
DN_API bool DN_OS_PathIterateDir (DN_Str8 path, DN_OSDirIterator *it); DN_API bool DN_OS_PathIterateDir (DN_Str8 path, DN_OSDirIterator *it);
DN_API bool DN_OS_PathAddRef (DN_Arena *arena, DN_OSPath *fs_path, DN_Str8 path);
DN_API bool DN_OS_PathAdd (DN_Arena *arena, DN_OSPath *fs_path, DN_Str8 path);
DN_API bool DN_OS_PathAddF (DN_Arena *arena, DN_OSPath *fs_path, DN_FMT_ATTRIB char const *fmt, ...);
DN_API bool DN_OS_PathPop (DN_OSPath *fs_path);
DN_API DN_Str8 DN_OS_PathBuildWithSeparatorAllocator (DN_Allocator allocator, DN_OSPath const *fs_path, DN_Str8 path_separator);
DN_API DN_Str8 DN_OS_PathToArena (DN_Arena *arena, DN_Str8 path, DN_Str8 path_separtor);
DN_API DN_Str8 DN_OS_PathToPool (DN_Pool *pool, DN_Str8 path, DN_Str8 path_separtor);
DN_API DN_Str8 DN_OS_PathToFmtArena (DN_Arena *arena, DN_Str8 path_separator, DN_FMT_ATTRIB char const *fmt, ...);
DN_API DN_Str8 DN_OS_PathToFmtPool (DN_Pool *pool, DN_Str8 path_separator, DN_FMT_ATTRIB char const *fmt, ...);
DN_API DN_Str8 DN_OS_PathArena (DN_Arena *arena, DN_Str8 path);
DN_API DN_Str8 DN_OS_PathPool (DN_Pool *pool, DN_Str8 path);
DN_API DN_Str8 DN_OS_PathFmtArena (DN_Arena *arena, DN_FMT_ATTRIB char const *fmt, ...);
DN_API DN_Str8 DN_OS_PathFmtPool (DN_Pool *pool, DN_FMT_ATTRIB char const *fmt, ...);
#define DN_OS_PathBuildFwdSlash(allocator, fs_path) DN_OS_PathBuildWithSeparatorAllocator(allocator, fs_path, DN_Str8Lit("/"))
#define DN_OS_PathBuildBackSlash(allocator, fs_path) DN_OS_PathBuildWithSeparatorAllocator(allocator, fs_path, DN_Str8Lit("\\"))
#define DN_OS_PathBuild(allocator, fs_path) DN_OS_PathBuildWithSeparatorAllocator(allocator, fs_path, DN_OSPathSeparatorStr8)
DN_API void DN_OS_Exit (int32_t exit_code); DN_API void DN_OS_Exit (int32_t exit_code);
DN_API DN_OSExecArgs DN_OS_ExecArgsDefault (); DN_API DN_OSExecArgs DN_OS_ExecArgsDefault ();
DN_API DN_OSExecResult DN_OS_ExecPump (DN_OSExecAsyncHandle handle, char *stdout_buffer, size_t *stdout_size, char *stderr_buffer, size_t *stderr_size, DN_U32 timeout_ms, DN_ErrSink *err); DN_API DN_OSExecResult DN_OS_ExecPump (DN_OSExecAsyncHandle handle, char *stdout_buffer, size_t *stdout_size, char *stderr_buffer, size_t *stderr_size, DN_U32 timeout_ms, DN_ErrSink *err);
+6 -6
View File
@@ -1414,25 +1414,25 @@ DN_API DN_OSPosixProcSelfStatus DN_OS_PosixProcSelfStatus()
for (DN_ForItSize(line_it, DN_Str8, lines.data, lines.count)) { for (DN_ForItSize(line_it, DN_Str8, lines.data, lines.count)) {
DN_Str8 line = DN_Str8TrimWhitespaceAround(*line_it.data); DN_Str8 line = DN_Str8TrimWhitespaceAround(*line_it.data);
if (DN_Str8StartsWith(line, NAME, DN_Str8EqCase_Insensitive)) { if (DN_Str8StartsWithInsensitive(line, NAME)) {
DN_Str8 str8 = DN_Str8TrimWhitespaceAround(DN_Str8Subset(line, NAME.count, line.count)); DN_Str8 str8 = DN_Str8TrimWhitespaceAround(DN_Str8Subset(line, NAME.count, line.count));
result.name_size = DN_Min(str8.count, sizeof(result.name)); result.name_size = DN_Min(str8.count, sizeof(result.name));
DN_Memcpy(result.name, str8.data, result.name_size); DN_Memcpy(result.name, str8.data, result.name_size);
} else if (DN_Str8StartsWith(line, PID, DN_Str8EqCase_Insensitive)) { } else if (DN_Str8StartsWithInsensitive(line, PID)) {
DN_Str8 str8 = DN_Str8TrimWhitespaceAround(DN_Str8Subset(line, PID.count, line.count)); DN_Str8 str8 = DN_Str8TrimWhitespaceAround(DN_Str8Subset(line, PID.count, line.count));
DN_U64FromResult to_u64 = DN_U64FromStr8(str8); DN_U64FromResult to_u64 = DN_U64FromStr8(str8);
result.pid = to_u64.value; result.pid = to_u64.value;
DN_Assert(to_u64.success); DN_Assert(to_u64.success);
} else if (DN_Str8StartsWith(line, VM_SIZE, DN_Str8EqCase_Insensitive)) { } else if (DN_Str8StartsWithInsensitive(line, VM_SIZE)) {
DN_Str8 size_with_kb = DN_Str8TrimWhitespaceAround(DN_Str8Subset(line, VM_SIZE.count, line.count)); DN_Str8 size_with_kb = DN_Str8TrimWhitespaceAround(DN_Str8Subset(line, VM_SIZE.count, line.count));
DN_Assert(DN_Str8EndsWith(size_with_kb, DN_Str8Lit("kB"))); DN_Assert(DN_Str8EndsWithSensitive(size_with_kb, DN_Str8Lit("kB")));
DN_Str8 vm_size = DN_Str8BSplit(size_with_kb, DN_Str8Lit(" ")).lhs; DN_Str8 vm_size = DN_Str8BSplit(size_with_kb, DN_Str8Lit(" ")).lhs;
DN_U64FromResult to_u64 = DN_U64FromStr8(vm_size); DN_U64FromResult to_u64 = DN_U64FromStr8(vm_size);
result.vm_size = DN_Kilobytes(to_u64.value); result.vm_size = DN_Kilobytes(to_u64.value);
DN_Assert(to_u64.success); DN_Assert(to_u64.success);
} else if (DN_Str8StartsWith(line, VM_PEAK, DN_Str8EqCase_Insensitive)) { } else if (DN_Str8StartsWithInsensitive(line, VM_PEAK)) {
DN_Str8 size_with_kb = DN_Str8TrimWhitespaceAround(DN_Str8Subset(line, VM_PEAK.count, line.count)); DN_Str8 size_with_kb = DN_Str8TrimWhitespaceAround(DN_Str8Subset(line, VM_PEAK.count, line.count));
DN_Assert(DN_Str8EndsWith(size_with_kb, DN_Str8Lit("kB"))); DN_Assert(DN_Str8EndsWithSensitive(size_with_kb, DN_Str8Lit("kB")));
DN_Str8 vm_size = DN_Str8BSplit(size_with_kb, DN_Str8Lit(" ")).lhs; DN_Str8 vm_size = DN_Str8BSplit(size_with_kb, DN_Str8Lit(" ")).lhs;
DN_U64FromResult to_u64 = DN_U64FromStr8(vm_size); DN_U64FromResult to_u64 = DN_U64FromStr8(vm_size);
result.vm_peak = DN_Kilobytes(to_u64.value); result.vm_peak = DN_Kilobytes(to_u64.value);
+2 -4
View File
@@ -1,5 +1,3 @@
#define DN_OS_W32_CPP
#if defined(_CLANGD) #if defined(_CLANGD)
#define DN_WITH_OS 1 #define DN_WITH_OS 1
#include "../dn.h" #include "../dn.h"
@@ -649,9 +647,9 @@ DN_API bool DN_OS_PathIterateDir(DN_Str8 path, DN_OSDirIterator *it)
// add those characters in this branch, so overwrite the null // add those characters in this branch, so overwrite the null
// character, add the glob and re-null terminate the buffer. // character, add the glob and re-null terminate the buffer.
if (needs_asterisks) if (needs_asterisks)
adjusted_path = DN_OS_PathFmtArena(&scratch.arena, "%.*s*", DN_Str8PrintFmt(path)); adjusted_path = DN_Str8FmtOsPathArena(&scratch.arena, "%.*s*", DN_Str8PrintFmt(path));
else else
adjusted_path = DN_OS_PathFmtArena(&scratch.arena, "%.*s/*", DN_Str8PrintFmt(path)); adjusted_path = DN_Str8FmtOsPathArena(&scratch.arena, "%.*s/*", DN_Str8PrintFmt(path));
} }
path16 = DN_OS_W32Str8ToStr16(&scratch.arena, adjusted_path); path16 = DN_OS_W32Str8ToStr16(&scratch.arena, adjusted_path);
+252 -255
View File
@@ -3257,22 +3257,22 @@ DN_API void DN_Str8x1024AppendFmtV(DN_Str8x1024 *str, DN_FMT_ATTRIB char const *
DN_FmtVAppend(str->data, &str->count, sizeof(str->data), fmt, args); DN_FmtVAppend(str->data, &str->count, sizeof(str->data), fmt, args);
} }
DN_API DN_Str8x32 DN_Str8x32FromU64(DN_U64 val, char separator) DN_API DN_Str8x32 DN_Str8x32FromU64(DN_U64 val, char seperator)
{ {
DN_Str8x32 result = {}; DN_Str8x32 result = {};
DN_Str8x32 temp = DN_Str8x32FromFmt("%" PRIu64, val); DN_Str8x32 temp = DN_Str8x32FromFmt("%" PRIu64, val);
DN_USize temp_index = 0; DN_USize temp_index = 0;
// NOTE: Write the digits the first, up to [0, 2] digits that do not need a thousandth separator // NOTE: Write the digits the first, up to [0, 2] digits that do not need a thousandth seperator
DN_USize range_without_separator = temp.count % 3; DN_USize range_without_seperator = temp.count % 3;
for (; temp_index < range_without_separator; temp_index++) for (; temp_index < range_without_seperator; temp_index++)
result.data[result.count++] = temp.data[temp_index]; result.data[result.count++] = temp.data[temp_index];
// NOTE: Write the subsequent digits and every 3rd digit, add the seperator // NOTE: Write the subsequent digits and every 3rd digit, add the seperator
DN_USize digit_counter = 0; DN_USize digit_counter = 0;
for (; temp_index < temp.count; temp_index++, digit_counter++) { for (; temp_index < temp.count; temp_index++, digit_counter++) {
if (separator && temp_index && (digit_counter % 3 == 0)) if (seperator && temp_index && (digit_counter % 3 == 0))
result.data[result.count++] = separator; result.data[result.count++] = seperator;
result.data[result.count++] = temp.data[temp_index]; result.data[result.count++] = temp.data[temp_index];
} }
return result; return result;
@@ -3756,8 +3756,8 @@ DN_API DN_Str8 DN_Str8TrimByteOrderMark(DN_Str8 string)
DN_API DN_Str8 DN_Str8FileNameFromPath(DN_Str8 path) DN_API DN_Str8 DN_Str8FileNameFromPath(DN_Str8 path)
{ {
DN_Str8 separators[] = {DN_Str8Lit("/"), DN_Str8Lit("\\")}; DN_Str8 seperators[] = {DN_Str8Lit("/"), DN_Str8Lit("\\")};
DN_Str8BSplitResult split = DN_Str8BSplitLastArray(path, separators, DN_ArrayCountU(separators)); DN_Str8BSplitResult split = DN_Str8BSplitLastArray(path, seperators, DN_ArrayCountU(seperators));
DN_Str8 result = split.rhs.count ? split.rhs : split.lhs; DN_Str8 result = split.rhs.count ? split.rhs : split.lhs;
return result; return result;
} }
@@ -3785,9 +3785,9 @@ DN_API DN_Str8 DN_Str8FileExtension(DN_Str8 path)
DN_API DN_Str8 DN_Str8FileDirectoryFromPath(DN_Str8 path) DN_API DN_Str8 DN_Str8FileDirectoryFromPath(DN_Str8 path)
{ {
DN_Str8 separators[] = {DN_Str8Lit("/"), DN_Str8Lit("\\")}; DN_Str8 seperators[] = {DN_Str8Lit("/"), DN_Str8Lit("\\")};
DN_Str8BSplitResult split = DN_Str8BSplitLastArray(path, separators, DN_ArrayCountU(separators)); DN_Str8BSplitResult split = DN_Str8BSplitLastArray(path, seperators, DN_ArrayCountU(seperators));
DN_Str8 result = split.lhs; DN_Str8 result = split.rhs.count == 0 ? DN_Str8Lit(".") : split.lhs;
return result; return result;
} }
@@ -4085,7 +4085,7 @@ DN_API DN_Str8 DN_Str8LineBreakAllocator(DN_Str8 src, DN_USize desired_width, DN
continue; continue;
} }
// Check if adding this word (plus separator space) would overflow // Check if adding this word (plus seperator space) would overflow
DN_USize combined_length = curr_line_length + 1 + split.lhs.count; DN_USize combined_length = curr_line_length + 1 + split.lhs.count;
if (combined_length > desired_width) { if (combined_length > desired_width) {
// Commit current line, start new line with current word // Commit current line, start new line with current word
@@ -4453,7 +4453,7 @@ DN_API DN_Str8Slice DN_Str8SplitAllocAVX512F(DN_Arena *arena, DN_Str8 string, DN
} }
#endif // DN_STR8_AVX512F #endif // DN_STR8_AVX512F
DN_API DN_Str8 DN_Str8SliceRender(DN_Str8Slice slice, DN_Str8 separator, DN_Arena *arena) DN_API DN_Str8 DN_Str8SliceRender(DN_Str8Slice slice, DN_Str8 seperator, DN_Arena *arena)
{ {
DN_Str8 result = {}; DN_Str8 result = {};
if (!arena) if (!arena)
@@ -4462,7 +4462,7 @@ DN_API DN_Str8 DN_Str8SliceRender(DN_Str8Slice slice, DN_Str8 separator, DN_Aren
DN_USize total_size = 0; DN_USize total_size = 0;
for (DN_USize index = 0; index < slice.count; index++) { for (DN_USize index = 0; index < slice.count; index++) {
if (index) if (index)
total_size += separator.count; total_size += seperator.count;
DN_Str8 item = slice.data[index]; DN_Str8 item = slice.data[index];
total_size += item.count; total_size += item.count;
} }
@@ -4472,8 +4472,8 @@ DN_API DN_Str8 DN_Str8SliceRender(DN_Str8Slice slice, DN_Str8 separator, DN_Aren
DN_USize write_index = 0; DN_USize write_index = 0;
for (DN_USize index = 0; index < slice.count; index++) { for (DN_USize index = 0; index < slice.count; index++) {
if (index) { if (index) {
DN_Memcpy(result.data + write_index, separator.data, separator.count); DN_Memcpy(result.data + write_index, seperator.data, seperator.count);
write_index += separator.count; write_index += seperator.count;
} }
DN_Str8 item = slice.data[index]; DN_Str8 item = slice.data[index];
DN_Memcpy(result.data + write_index, item.data, item.count); DN_Memcpy(result.data + write_index, item.data, item.count);
@@ -4592,7 +4592,7 @@ DN_API bool DN_Str16Eq(DN_Str16 lhs, DN_Str16 rhs)
} }
DN_API DN_Str16 DN_Str16SliceRender(DN_Str16Slice slice, DN_Str16 separator, DN_Arena *arena) DN_API DN_Str16 DN_Str16SliceRender(DN_Str16Slice slice, DN_Str16 seperator, DN_Arena *arena)
{ {
DN_Str16 result = {}; DN_Str16 result = {};
if (!arena) if (!arena)
@@ -4601,7 +4601,7 @@ DN_API DN_Str16 DN_Str16SliceRender(DN_Str16Slice slice, DN_Str16 separator, DN_
DN_USize total_size = 0; DN_USize total_size = 0;
for (DN_USize index = 0; index < slice.count; index++) { for (DN_USize index = 0; index < slice.count; index++) {
if (index) if (index)
total_size += separator.count; total_size += seperator.count;
DN_Str16 item = slice.data[index]; DN_Str16 item = slice.data[index];
total_size += item.count; total_size += item.count;
} }
@@ -4611,8 +4611,8 @@ DN_API DN_Str16 DN_Str16SliceRender(DN_Str16Slice slice, DN_Str16 separator, DN_
DN_USize write_index = 0; DN_USize write_index = 0;
for (DN_USize index = 0; index < slice.count; index++) { for (DN_USize index = 0; index < slice.count; index++) {
if (index) { if (index) {
DN_Memcpy(result.data + write_index, separator.data, separator.count * sizeof(result.data[0])); DN_Memcpy(result.data + write_index, seperator.data, seperator.count * sizeof(result.data[0]));
write_index += separator.count; write_index += seperator.count;
} }
DN_Str16 item = slice.data[index]; DN_Str16 item = slice.data[index];
DN_Memcpy(result.data + write_index, item.data, item.count * sizeof(result.data[0])); DN_Memcpy(result.data + write_index, item.data, item.count * sizeof(result.data[0]));
@@ -4914,6 +4914,188 @@ DN_API DN_Str8 DN_Str8FromStr8BuilderDelimitArena(DN_Str8Builder const *builder,
return result; return result;
} }
DN_API bool DN_PathAddRef(DN_Path *path, DN_Str8 add, DN_Arena *arena)
{
if (!arena || !path)
return false;
if (add.count == 0)
return true;
DN_Str8 const delimiter_array[] = {
DN_Str8Lit("\\"),
DN_Str8Lit("/")};
if (path->links_size == 0)
path->has_prefix_path_seperator = (add.data[0] == '/');
for (;;) {
DN_Str8BSplitResult delimiter = DN_Str8BSplitArray(add, delimiter_array, DN_ArrayCountU(delimiter_array));
for (; delimiter.lhs.data; delimiter = DN_Str8BSplitArray(delimiter.rhs, delimiter_array, DN_ArrayCountU(delimiter_array))) {
if (delimiter.lhs.count <= 0)
continue;
DN_Str8Link *link = DN_ArenaNew(arena, DN_Str8Link, DN_ZMem_Yes);
if (!link)
return false;
link->string = delimiter.lhs;
link->prev = path->tail;
if (path->tail)
path->tail->next = link;
else
path->head = link;
path->tail = link;
path->links_size += 1;
path->string_size += delimiter.lhs.count;
}
if (!delimiter.lhs.data)
break;
}
return true;
}
DN_API bool DN_PathAdd(DN_Path *path, DN_Str8 add, DN_Arena *arena)
{
DN_Str8 copy = DN_Str8FromStr8Arena(add, arena);
bool result = copy.count ? true : DN_PathAddRef(path, copy, arena);
return result;
}
DN_API bool DN_PathAddF(DN_Path *path, DN_Arena *arena, DN_FMT_ATTRIB char const *fmt, ...)
{
va_list args;
va_start(args, fmt);
DN_Str8 add = DN_Str8FmtVArena(arena, fmt, args);
va_end(args);
bool result = DN_PathAddRef(path, add, arena);
return result;
}
DN_API bool DN_PathPop(DN_Path *path)
{
if (!path)
return false;
if (path->tail) {
DN_Assert(path->head);
path->links_size -= 1;
path->string_size -= path->tail->string.count;
path->tail = path->tail->prev;
if (path->tail)
path->tail->next = nullptr;
else
path->head = nullptr;
} else {
DN_Assert(!path->head);
}
return true;
}
DN_API DN_Str8 DN_Str8FromPath(DN_Path const *path, DN_Str8 path_seperator, DN_Allocator allocator)
{
DN_Str8 result = {};
if (!path || path->links_size <= 0)
return result;
// NOTE: Each link except the last one needs the path seperator appended to it, '/' or '\\'
DN_USize string_size = (path->has_prefix_path_seperator ? path_seperator.count : 0) + path->string_size + ((path->links_size - 1) * path_seperator.count);
result = DN_Str8AllocAllocator(string_size, DN_ZMem_No, allocator);
if (result.data) {
char *dest = result.data;
if (path->has_prefix_path_seperator) {
DN_Memcpy(dest, path_seperator.data, path_seperator.count);
dest += path_seperator.count;
}
for (DN_Str8Link *link = path->head; link; link = link->next) {
DN_Str8 string = link->string;
DN_Memcpy(dest, string.data, string.count);
dest += string.count;
if (link != path->tail) {
DN_Memcpy(dest, path_seperator.data, path_seperator.count);
dest += path_seperator.count;
}
}
}
result.data[string_size] = 0;
return result;
}
DN_API DN_Str8 DN_Str8FmtVPathArena(DN_Str8 path_seperator, DN_Arena *arena, DN_FMT_ATTRIB char const *fmt, va_list args)
{
DN_TcScratch scratch = DN_TcScratchBeginArena(&arena, 1);
DN_Str8 path = DN_Str8FmtVArena(arena, fmt, args);
DN_Path fs_path = {};
DN_PathAddRef(&fs_path, path, &scratch.arena);
DN_Allocator allocator = DN_AllocatorFromArena(arena);
DN_Str8 result = DN_Str8FromPath(&fs_path, path_seperator, allocator);
DN_TcScratchEnd(&scratch);
return result;
}
DN_API DN_Str8 DN_Str8FmtPathArena(DN_Str8 path_seperator, DN_Arena *arena, DN_FMT_ATTRIB char const *fmt, ...)
{
DN_TcScratch scratch = DN_TcScratchBeginArena(&arena, 1);
va_list args;
va_start(args, fmt);
DN_Str8 path = DN_Str8FmtVArena(arena, fmt, args);
va_end(args);
DN_Path fs_path = {};
DN_PathAddRef(&fs_path, path, &scratch.arena);
DN_Allocator allocator = DN_AllocatorFromArena(arena);
DN_Str8 result = DN_Str8FromPath(&fs_path, path_seperator, allocator);
DN_TcScratchEnd(&scratch);
return result;
}
DN_API DN_Str8 DN_Str8FmtVPathPool(DN_Str8 path_seperator, DN_Pool *pool, DN_FMT_ATTRIB char const *fmt, va_list args)
{
DN_TcScratch scratch = DN_TcScratchBeginArena(&pool->arena, 1);
DN_Str8 path = DN_Str8FmtVPool(pool, fmt, args);
DN_Path fs_path = {};
DN_PathAddRef(&fs_path, path, &scratch.arena);
DN_Allocator allocator = DN_AllocatorFromPool(pool);
DN_Str8 result = DN_Str8FromPath(&fs_path, path_seperator, allocator);
DN_TcScratchEnd(&scratch);
return result;
}
DN_API DN_Str8 DN_Str8FmtPathPool(DN_Str8 path_seperator, DN_Pool *pool, DN_FMT_ATTRIB char const *fmt, ...)
{
va_list args;
va_start(args, fmt);
DN_Str8 result = DN_Str8FmtVPathPool(path_seperator, pool, fmt, args);
va_end(args);
return result;
}
DN_API DN_Str8 DN_Str8FmtOsPathPool(DN_Pool *pool, DN_FMT_ATTRIB char const *fmt, ...)
{
va_list args;
va_start(args, fmt);
DN_Str8 result = DN_Str8FmtVPathPool(DN_OsPathSeperatorStr8, pool, fmt, args);
va_end(args);
return result;
}
DN_API DN_Str8 DN_Str8FmtOsPathArena(DN_Arena *arena, DN_FMT_ATTRIB char const *fmt, ...)
{
va_list args;
va_start(args, fmt);
DN_Str8 result = DN_Str8FmtVPathArena(DN_OsPathSeperatorStr8, arena, fmt, args);
va_end(args);
return result;
}
// NOTE: DN_UTF // NOTE: DN_UTF
DN_API int DN_UTF8Encode(DN_U8 utf8[4], DN_U32 codepoint) DN_API int DN_UTF8Encode(DN_U8 utf8[4], DN_U32 codepoint)
{ {
@@ -5773,7 +5955,7 @@ static void DN_QSortInsertion_(void *array, DN_USize array_size, DN_USize elem_s
DN_TcScratchEnd(&scratch); DN_TcScratchEnd(&scratch);
} }
DN_API void DN_QSort(void *array, DN_USize array_size, DN_USize elem_size, void *user_context, DN_QSortCompareFunc *compare) DN_API void DN_QSort_(void *array, DN_USize array_size, DN_USize elem_size, void *user_context, DN_QSortCompareFunc *compare)
{ {
if (!array || array_size <= 1 || elem_size == 0 || !compare) if (!array || array_size <= 1 || elem_size == 0 || !compare)
return; return;
@@ -5816,14 +5998,22 @@ DN_API void DN_QSort(void *array, DN_USize array_size, DN_USize elem_size, void
// Move pivot to right of partition // Move pivot to right of partition
// 4, 5, 2, 3, |6, 8, ^7* // 4, 5, 2, 3, |6, 8, ^7*
DN_QSortSwapElems_(array, elem_size, partition_index, pivot_index); DN_QSortSwapElems_(array, elem_size, partition_index, pivot_index);
DN_QSort(array_u8, partition_index, elem_size, user_context, compare); DN_QSort_(array_u8, partition_index, elem_size, user_context, compare);
// Skip the value at partion index since that is guaranteed to be sorted. // Skip the value at partion index since that is guaranteed to be sorted.
// 4, 5, 2, 3, (x), 8, 7 // 4, 5, 2, 3, (x), 8, 7
DN_USize one_after_partition_index = partition_index + 1; DN_USize one_after_partition_index = partition_index + 1;
DN_QSort(array_u8 + (one_after_partition_index * elem_size), (array_size - one_after_partition_index), elem_size, user_context, compare); DN_QSort_(array_u8 + (one_after_partition_index * elem_size), (array_size - one_after_partition_index), elem_size, user_context, compare);
} }
#if defined(__cplusplus)
template <typename T>
DN_API void DN_QSort(T *array, DN_USize array_size, void *user_context, DN_QSortCompareFunc *compare)
{
DN_QSort_(array, array_size, sizeof(T), user_context, compare);
}
#endif
DN_API bool DN_QSortCompareStr8NaturalAsc(void const* lhs, void const *rhs, void *user_context) DN_API bool DN_QSortCompareStr8NaturalAsc(void const* lhs, void const *rhs, void *user_context)
{ {
DN_Str8EqCase eq_case = *DN_Cast(DN_Str8EqCase *) user_context; DN_Str8EqCase eq_case = *DN_Cast(DN_Str8EqCase *) user_context;
@@ -5876,32 +6066,32 @@ DN_API bool DN_QSortCompareBytesGT(void const* lhs, void const *rhs, void *user_
DN_API void DN_QSortBytesLT(void *array, DN_USize array_size, DN_USize elem_size) DN_API void DN_QSortBytesLT(void *array, DN_USize array_size, DN_USize elem_size)
{ {
DN_QSort(array, array_size, elem_size, &elem_size, DN_QSortCompareBytesLT); DN_QSort_(array, array_size, elem_size, &elem_size, DN_QSortCompareBytesLT);
} }
DN_API void DN_QSortBytesGT(void *array, DN_USize array_size, DN_USize elem_size) DN_API void DN_QSortBytesGT(void *array, DN_USize array_size, DN_USize elem_size)
{ {
DN_QSort(array, array_size, elem_size, &elem_size, DN_QSortCompareBytesGT); DN_QSort_(array, array_size, elem_size, &elem_size, DN_QSortCompareBytesGT);
} }
DN_API void DN_QSortStr8NaturalAsc(DN_Str8 *array, DN_USize array_size, DN_Str8EqCase eq_case) DN_API void DN_QSortStr8NaturalAsc(DN_Str8 *array, DN_USize array_size, DN_Str8EqCase eq_case)
{ {
DN_QSort(array, array_size, sizeof(*array), /*user_context=*/ &eq_case, DN_QSortCompareStr8NaturalAsc); DN_QSort_(array, array_size, sizeof(*array), /*user_context=*/ &eq_case, DN_QSortCompareStr8NaturalAsc);
} }
DN_API void DN_QSortStr8NaturalDesc(DN_Str8 *array, DN_USize array_size, DN_Str8EqCase eq_case) DN_API void DN_QSortStr8NaturalDesc(DN_Str8 *array, DN_USize array_size, DN_Str8EqCase eq_case)
{ {
DN_QSort(array, array_size, sizeof(*array), /*user_context=*/ &eq_case, DN_QSortCompareStr8NaturalDesc); DN_QSort_(array, array_size, sizeof(*array), /*user_context=*/ &eq_case, DN_QSortCompareStr8NaturalDesc);
} }
DN_API void DN_QSortStr8LexicographicAsc(DN_Str8 *array, DN_USize array_size, DN_Str8EqCase eq_case) DN_API void DN_QSortStr8LexicographicAsc(DN_Str8 *array, DN_USize array_size, DN_Str8EqCase eq_case)
{ {
DN_QSort(array, array_size, sizeof(*array), /*user_context=*/ &eq_case, DN_QSortCompareStr8LexicographicAsc); DN_QSort_(array, array_size, sizeof(*array), /*user_context=*/ &eq_case, DN_QSortCompareStr8LexicographicAsc);
} }
DN_API void DN_QSortStr8LexicographicDesc(DN_Str8 *array, DN_USize array_size, DN_Str8EqCase eq_case) DN_API void DN_QSortStr8LexicographicDesc(DN_Str8 *array, DN_USize array_size, DN_Str8EqCase eq_case)
{ {
DN_QSort(array, array_size, sizeof(*array), /*user_context=*/ &eq_case, DN_QSortCompareStr8LexicographicDesc); DN_QSort_(array, array_size, sizeof(*array), /*user_context=*/ &eq_case, DN_QSortCompareStr8LexicographicDesc);
} }
DN_API bool DN_BSearchLessThanBytes(void const *lhs, void const *rhs, void *user_context) DN_API bool DN_BSearchLessThanBytes(void const *lhs, void const *rhs, void *user_context)
@@ -6110,7 +6300,7 @@ DN_FORCE_INLINE DN_U64 DN_Murmur3FMix64_(DN_U64 k)
return k; return k;
} }
DN_API DN_U32 DN_Murmur3HashU128FromBytesX86(void const *bytes, int len, DN_U32 seed) DN_API DN_U32 DN_Murmur3HashU32FromBytesX86(void const *bytes, int len, DN_U32 seed)
{ {
const DN_U8 *data = (const DN_U8 *)bytes; const DN_U8 *data = (const DN_U8 *)bytes;
const int nblocks = len / 4; const int nblocks = len / 4;
@@ -6125,8 +6315,7 @@ DN_API DN_U32 DN_Murmur3HashU128FromBytesX86(void const *bytes, int len, DN_U32
const DN_U32 *blocks = (const DN_U32 *)(data + nblocks * 4); const DN_U32 *blocks = (const DN_U32 *)(data + nblocks * 4);
for (int i = -nblocks; i; i++) for (int i = -nblocks; i; i++) {
{
DN_U32 k1 = DN_Murmur3GetBlock32_(blocks, i); DN_U32 k1 = DN_Murmur3GetBlock32_(blocks, i);
k1 *= c1; k1 *= c1;
@@ -6145,8 +6334,7 @@ DN_API DN_U32 DN_Murmur3HashU128FromBytesX86(void const *bytes, int len, DN_U32
DN_U32 k1 = 0; DN_U32 k1 = 0;
switch (len & 3) switch (len & 3) {
{
case 3: case 3:
k1 ^= tail[2] << 16; k1 ^= tail[2] << 16;
case 2: case 2:
@@ -6185,8 +6373,7 @@ DN_API DN_Murmur3 DN_Murmur3HashU128FromBytesX64(void const *bytes, int len, DN_
const DN_U64 *blocks = (const DN_U64 *)(data); const DN_U64 *blocks = (const DN_U64 *)(data);
for (int i = 0; i < nblocks; i++) for (int i = 0; i < nblocks; i++) {
{
DN_U64 k1 = DN_Murmur3GetBlock64_(blocks, i * 2 + 0); DN_U64 k1 = DN_Murmur3GetBlock64_(blocks, i * 2 + 0);
DN_U64 k2 = DN_Murmur3GetBlock64_(blocks, i * 2 + 1); DN_U64 k2 = DN_Murmur3GetBlock64_(blocks, i * 2 + 1);
@@ -6217,8 +6404,7 @@ DN_API DN_Murmur3 DN_Murmur3HashU128FromBytesX64(void const *bytes, int len, DN_
DN_U64 k1 = 0; DN_U64 k1 = 0;
DN_U64 k2 = 0; DN_U64 k2 = 0;
switch (len & 15) switch (len & 15) {
{
case 15: case 15:
k2 ^= ((DN_U64)tail[14]) << 48; k2 ^= ((DN_U64)tail[14]) << 48;
case 14: case 14:
@@ -6786,6 +6972,12 @@ DN_API DN_V2F32 DN_V2F32Lerp(DN_V2F32 a, DN_F32 t, DN_V2F32 b)
return result; return result;
} }
DN_API DN_V2F32 DN_V2F32Rotate(DN_V2F32 v, DN_F32 cos_a, DN_F32 sin_a)
{
DN_V2F32 result = DN_V2F32From2N(v.x * cos_a - v.y * sin_a, v.x * sin_a + v.y * cos_a);
return result;
}
DN_API bool operator!=(DN_V2F32 lhs, DN_V2F32 rhs) DN_API bool operator!=(DN_V2F32 lhs, DN_V2F32 rhs)
{ {
bool result = !(lhs == rhs); bool result = !(lhs == rhs);
@@ -7390,7 +7582,7 @@ DN_API DN_V4F32 DN_V4F32Linear01FromSrgb01(DN_V4F32 srgb01)
DN_API DN_V4F32 DN_V4F32Linear01Desaturate(DN_V4F32 linear01, DN_F32 t01) DN_API DN_V4F32 DN_V4F32Linear01Desaturate(DN_V4F32 linear01, DN_F32 t01)
{ {
DN_F32 luminance = (linear01.r * DN_V3F32_Rgb_LUMINANCE.r) + (linear01.g * DN_V3F32_Rgb_LUMINANCE.g) + (linear01.b * DN_V3F32_Rgb_LUMINANCE.b); DN_F32 luminance = (linear01.r * DN_V3F32_RGB_LUMINANCE.r) + (linear01.g * DN_V3F32_RGB_LUMINANCE.g) + (linear01.b * DN_V3F32_RGB_LUMINANCE.b);
DN_V4F32 result = linear01; DN_V4F32 result = linear01;
result.rgb = DN_V3F32Lerp(result.rgb, t01, DN_V3F32From1N(luminance)); result.rgb = DN_V3F32Lerp(result.rgb, t01, DN_V3F32From1N(luminance));
return result; return result;
@@ -11601,7 +11793,7 @@ static void DN_OS_LoggerSetFilePathNoMutex_(DN_OSLogger *logger, DN_Pool *pool,
logger->file_path = {}; logger->file_path = {};
} }
DN_OS_FileClose(&logger->file); DN_OS_FileClose(&logger->file);
logger->file_path = DN_OS_PathFmtPool(pool, "%.*s", DN_Str8PrintFmt(file_path)); logger->file_path = DN_Str8FmtOsPathPool(pool, "%.*s", DN_Str8PrintFmt(file_path));
// NOTE: Clear the sticky file error flag if it was set // NOTE: Clear the sticky file error flag if it was set
logger->flags &= ~DN_OSLoggerFlags_FileError; logger->flags &= ~DN_OSLoggerFlags_FileError;
@@ -11624,7 +11816,7 @@ static void DN_OS_DoLogFileSetupAndRotation_(DN_OSLogger *logger)
// NOTE: Set a default file path to log to if it's not been set yet // NOTE: Set a default file path to log to if it's not been set yet
if (logger->file_path.count == 0) { if (logger->file_path.count == 0) {
DN_Str8 exe_dir = DN_OS_ExeDir(&scratch.arena); DN_Str8 exe_dir = DN_OS_ExeDir(&scratch.arena);
DN_Str8 default_file_path = DN_OS_PathFmtArena(&scratch.arena, "%.*s/dn.log", DN_Str8PrintFmt(exe_dir)); DN_Str8 default_file_path = DN_Str8FmtOsPathArena(&scratch.arena, "%.*s/dn.log", DN_Str8PrintFmt(exe_dir));
DN_OS_LoggerSetFilePathNoMutex_(logger, DN_TcMainPool(), default_file_path); DN_OS_LoggerSetFilePathNoMutex_(logger, DN_TcMainPool(), default_file_path);
} }
@@ -11823,26 +12015,26 @@ DN_API DN_Arena DN_OS_ArenaFromHeapBasic(DN_U64 size, DN_MemFlags flags)
} }
// NOTE: Date // NOTE: Date
DN_API DN_Str8x32 DN_OS_DateLocalTimeStr8(DN_Date time, char date_separator, char hms_separator) DN_API DN_Str8x32 DN_OS_DateLocalTimeStr8(DN_Date time, char date_seperator, char hms_seperator)
{ {
DN_Str8x32 result = DN_Str8x32FromFmt("%hu%c%02hhu%c%02hhu %02hhu%c%02hhu%c%02hhu", DN_Str8x32 result = DN_Str8x32FromFmt("%hu%c%02hhu%c%02hhu %02hhu%c%02hhu%c%02hhu",
time.year, time.year,
date_separator, date_seperator,
time.month, time.month,
date_separator, date_seperator,
time.day, time.day,
time.hour, time.hour,
hms_separator, hms_seperator,
time.minutes, time.minutes,
hms_separator, hms_seperator,
time.seconds); time.seconds);
return result; return result;
} }
DN_API DN_Str8x32 DN_OS_DateLocalTimeStr8Now(char date_separator, char hms_separator) DN_API DN_Str8x32 DN_OS_DateLocalTimeStr8Now(char date_seperator, char hms_seperator)
{ {
DN_Date time = DN_OS_DateLocalTimeNow(); DN_Date time = DN_OS_DateLocalTimeNow();
DN_Str8x32 result = DN_OS_DateLocalTimeStr8(time, date_separator, hms_separator); DN_Str8x32 result = DN_OS_DateLocalTimeStr8(time, date_seperator, hms_seperator);
return result; return result;
} }
@@ -11853,8 +12045,8 @@ DN_API DN_Str8 DN_OS_ExeDir(DN_Arena *arena)
return result; return result;
DN_TcScratch scratch = DN_TcScratchBeginArena(&arena, 1); DN_TcScratch scratch = DN_TcScratchBeginArena(&arena, 1);
DN_Str8 exe_path = DN_OS_ExePath(&scratch.arena); DN_Str8 exe_path = DN_OS_ExePath(&scratch.arena);
DN_Str8 separators[] = {DN_Str8Lit("/"), DN_Str8Lit("\\")}; DN_Str8 seperators[] = {DN_Str8Lit("/"), DN_Str8Lit("\\")};
DN_Str8BSplitResult split = DN_Str8BSplitLastArray(exe_path, separators, DN_ArrayCountU(separators)); DN_Str8BSplitResult split = DN_Str8BSplitLastArray(exe_path, seperators, DN_ArrayCountU(seperators));
result = DN_Str8FromStr8Arena(split.lhs, arena); result = DN_Str8FromStr8Arena(split.lhs, arena);
DN_TcScratchEnd(&scratch); DN_TcScratchEnd(&scratch);
return result; return result;
@@ -12183,201 +12375,6 @@ DN_API bool DN_OS_PathIsOlderThan(DN_Str8 path, DN_Str8 check_against)
return result; return result;
} }
DN_API bool DN_OS_PathAddRef(DN_Arena *arena, DN_OSPath *fs_path, DN_Str8 path)
{
if (!arena || !fs_path || path.count == 0)
return false;
if (path.count <= 0)
return true;
DN_Str8 const delimiter_array[] = {
DN_Str8Lit("\\"),
DN_Str8Lit("/")};
if (fs_path->links_size == 0)
fs_path->has_prefix_path_separator = (path.data[0] == '/');
for (;;) {
DN_Str8BSplitResult delimiter = DN_Str8BSplitArray(path, delimiter_array, DN_ArrayCountU(delimiter_array));
for (; delimiter.lhs.data; delimiter = DN_Str8BSplitArray(delimiter.rhs, delimiter_array, DN_ArrayCountU(delimiter_array))) {
if (delimiter.lhs.count <= 0)
continue;
DN_OSPathLink *link = DN_ArenaNew(arena, DN_OSPathLink, DN_ZMem_Yes);
if (!link)
return false;
link->string = delimiter.lhs;
link->prev = fs_path->tail;
if (fs_path->tail)
fs_path->tail->next = link;
else
fs_path->head = link;
fs_path->tail = link;
fs_path->links_size += 1;
fs_path->string_size += delimiter.lhs.count;
}
if (!delimiter.lhs.data)
break;
}
return true;
}
DN_API bool DN_OS_PathAdd(DN_Arena *arena, DN_OSPath *fs_path, DN_Str8 path)
{
DN_Str8 copy = DN_Str8FromStr8Arena(path, arena);
bool result = copy.count ? true : DN_OS_PathAddRef(arena, fs_path, copy);
return result;
}
DN_API bool DN_OS_PathAddF(DN_Arena *arena, DN_OSPath *fs_path, DN_FMT_ATTRIB char const *fmt, ...)
{
va_list args;
va_start(args, fmt);
DN_Str8 path = DN_Str8FmtVArena(arena, fmt, args);
va_end(args);
bool result = DN_OS_PathAddRef(arena, fs_path, path);
return result;
}
DN_API bool DN_OS_PathPop(DN_OSPath *fs_path)
{
if (!fs_path)
return false;
if (fs_path->tail) {
DN_Assert(fs_path->head);
fs_path->links_size -= 1;
fs_path->string_size -= fs_path->tail->string.count;
fs_path->tail = fs_path->tail->prev;
if (fs_path->tail)
fs_path->tail->next = nullptr;
else
fs_path->head = nullptr;
} else {
DN_Assert(!fs_path->head);
}
return true;
}
DN_API DN_Str8 DN_OS_PathBuildWithSeparatorAllocator(DN_Allocator allocator, DN_OSPath const *fs_path, DN_Str8 path_separator)
{
DN_Str8 result = {};
if (!fs_path || fs_path->links_size <= 0)
return result;
// NOTE: Each link except the last one needs the path separator appended to it, '/' or '\\'
DN_USize string_size = (fs_path->has_prefix_path_separator ? path_separator.count : 0) + fs_path->string_size + ((fs_path->links_size - 1) * path_separator.count);
result = DN_Str8AllocAllocator(string_size, DN_ZMem_No, allocator);
if (result.data) {
char *dest = result.data;
if (fs_path->has_prefix_path_separator) {
DN_Memcpy(dest, path_separator.data, path_separator.count);
dest += path_separator.count;
}
for (DN_OSPathLink *link = fs_path->head; link; link = link->next) {
DN_Str8 string = link->string;
DN_Memcpy(dest, string.data, string.count);
dest += string.count;
if (link != fs_path->tail) {
DN_Memcpy(dest, path_separator.data, path_separator.count);
dest += path_separator.count;
}
}
}
result.data[string_size] = 0;
return result;
}
DN_API DN_Str8 DN_OS_PathToArena(DN_Arena *arena, DN_Str8 path, DN_Str8 path_separator)
{
DN_OSPath fs_path = {};
DN_OS_PathAddRef(arena, &fs_path, path);
DN_Allocator allocator = DN_AllocatorFromArena(arena);
DN_Str8 result = DN_OS_PathBuildWithSeparatorAllocator(allocator, &fs_path, path_separator);
return result;
}
DN_API DN_Str8 DN_OS_PathToPool(DN_Pool *pool, DN_Str8 path, DN_Str8 path_separator)
{
DN_TcScratch scratch = DN_TcScratchBeginArena(&pool->arena, 1);
DN_OSPath fs_path = {};
DN_OS_PathAddRef(&scratch.arena, &fs_path, path);
DN_Allocator allocator = DN_AllocatorFromPool(pool);
DN_Str8 result = DN_OS_PathBuildWithSeparatorAllocator(allocator, &fs_path, path_separator);
DN_TcScratchEnd(&scratch);
return result;
}
DN_API DN_Str8 DN_OS_PathToFmtArena(DN_Arena *arena, DN_Str8 path_separator, DN_FMT_ATTRIB char const *fmt, ...)
{
DN_TcScratch scratch = DN_TcScratchBeginArena(&arena, 1);
va_list args;
va_start(args, fmt);
DN_Str8 path = DN_Str8FmtVArena(&scratch.arena, fmt, args);
va_end(args);
DN_Str8 result = DN_OS_PathToArena(arena, path, path_separator);
DN_TcScratchEnd(&scratch);
return result;
}
DN_API DN_Str8 DN_OS_PathToFmtPool(DN_Pool *pool, DN_Str8 path_separator, DN_FMT_ATTRIB char const *fmt, ...)
{
DN_TcScratch scratch = DN_TcScratchBeginArena(&pool->arena, 1);
va_list args;
va_start(args, fmt);
DN_Str8 path = DN_Str8FmtVArena(&scratch.arena, fmt, args);
va_end(args);
DN_Str8 result = DN_OS_PathToPool(pool, path, path_separator);
DN_TcScratchEnd(&scratch);
return result;
}
DN_API DN_Str8 DN_OS_PathArena(DN_Arena *arena, DN_Str8 path)
{
DN_Str8 result = DN_OS_PathToArena(arena, path, DN_OSPathSeparatorStr8);
return result;
}
DN_API DN_Str8 DN_OS_PathPool(DN_Pool *pool, DN_Str8 path)
{
DN_Str8 result = DN_OS_PathToPool(pool, path, DN_OSPathSeparatorStr8);
return result;
}
DN_API DN_Str8 DN_OS_PathFmtArena(DN_Arena *arena, DN_FMT_ATTRIB char const *fmt, ...)
{
DN_TcScratch scratch = DN_TcScratchBeginArena(&arena, 1);
va_list args;
va_start(args, fmt);
DN_Str8 path = DN_Str8FmtVArena(&scratch.arena, fmt, args);
va_end(args);
DN_Str8 result = DN_OS_PathArena(arena, path);
DN_TcScratchEnd(&scratch);
return result;
}
DN_API DN_Str8 DN_OS_PathFmtPool(DN_Pool *pool, DN_FMT_ATTRIB char const *fmt, ...)
{
DN_TcScratch scratch = DN_TcScratchBeginArena(&pool->arena, 1);
va_list args;
va_start(args, fmt);
DN_Str8 path = DN_Str8FmtVArena(&scratch.arena, fmt, args);
va_end(args);
DN_Str8 result = DN_OS_PathPool(pool, path);
DN_TcScratchEnd(&scratch);
return result;
}
DN_API DN_OSExecArgs DN_OS_ExecArgsDefault() DN_API DN_OSExecArgs DN_OS_ExecArgsDefault()
{ {
DN_OSExecArgs result = {}; DN_OSExecArgs result = {};
@@ -14288,17 +14285,17 @@ DN_NETRequestHandle DN_NET_EmcDoHTTP(DN_NETCore *net, DN_Str8 url, DN_Str8 metho
// NOTE: Setup the HTTP request via Emscripten // NOTE: Setup the HTTP request via Emscripten
emscripten_fetch_attr_t fetch_attribs = {}; emscripten_fetch_attr_t fetch_attribs = {};
{ {
DN_Assert(req->args.payload.data[req->args.payload.size] == 0); DN_Assert(req->args.payload.data[req->args.payload.count] == 0);
DN_Assert(req->url.data[req->url.size] == 0); DN_Assert(req->url.data[req->url.count] == 0);
// NOTE: Setup request for emscripten // NOTE: Setup request for emscripten
emscripten_fetch_attr_init(&fetch_attribs); emscripten_fetch_attr_init(&fetch_attribs);
fetch_attribs.requestData = req->args.payload.data; fetch_attribs.requestData = req->args.payload.data;
fetch_attribs.requestDataSize = req->args.payload.size; fetch_attribs.requestDataSize = req->args.payload.count;
DN_Assert(req->method.size < DN_ArrayCountU(fetch_attribs.requestMethod)); DN_Assert(req->method.count < DN_ArrayCountU(fetch_attribs.requestMethod));
DN_Memcpy(fetch_attribs.requestMethod, req->method.data, req->method.size); DN_Memcpy(fetch_attribs.requestMethod, req->method.data, req->method.count);
fetch_attribs.requestMethod[req->method.size] = 0; fetch_attribs.requestMethod[req->method.count] = 0;
// NOTE: Assign HTTP headers // NOTE: Assign HTTP headers
if (req->args.headers_size) { if (req->args.headers_size) {
@@ -14312,9 +14309,9 @@ DN_NETRequestHandle DN_NET_EmcDoHTTP(DN_NETCore *net, DN_Str8 url, DN_Str8 metho
// NOTE: Handle basic auth // NOTE: Handle basic auth
if (req->args.flags & DN_NETDoHTTPFlags_BasicAuth) { if (req->args.flags & DN_NETDoHTTPFlags_BasicAuth) {
if (req->args.username.size && req->args.password.size) { if (req->args.username.count && req->args.password.count) {
DN_Assert(req->args.username.data[req->args.username.size] == 0); DN_Assert(req->args.username.data[req->args.username.count] == 0);
DN_Assert(req->args.password.data[req->args.password.size] == 0); DN_Assert(req->args.password.data[req->args.password.count] == 0);
fetch_attribs.withCredentials = true; fetch_attribs.withCredentials = true;
fetch_attribs.userName = req->args.username.data; fetch_attribs.userName = req->args.username.data;
fetch_attribs.password = req->args.password.data; fetch_attribs.password = req->args.password.data;
@@ -14384,7 +14381,7 @@ void DN_NET_EmcDoWSSend(DN_NETRequestHandle handle, DN_Str8 data, DN_NETWSSend s
} break; } break;
case DN_NETWSSend_Binary: { case DN_NETWSSend_Binary: {
result = emscripten_websocket_send_binary(emc_request->socket, data.data, data.size); result = emscripten_websocket_send_binary(emc_request->socket, data.data, data.count);
} break; } break;
case DN_NETWSSend_Close: { case DN_NETWSSend_Close: {
+53 -54
View File
@@ -300,6 +300,7 @@
// NOTE: Platform identification // NOTE: Platform identification
#if !defined(DN_PLATFORM_EMSCRIPTEN) && \ #if !defined(DN_PLATFORM_EMSCRIPTEN) && \
!defined(DN_PLATFORM_POSIX) && \ !defined(DN_PLATFORM_POSIX) && \
!defined(DN_PLATFORM_ARM64) && \
!defined(DN_PLATFORM_WIN32) !defined(DN_PLATFORM_WIN32)
#if defined(__aarch64__) || defined(_M_ARM64) #if defined(__aarch64__) || defined(_M_ARM64)
#define DN_PLATFORM_ARM64 #define DN_PLATFORM_ARM64
@@ -1502,6 +1503,25 @@ enum DN_Str8BuilderAdd
DN_Str8BuilderAdd_Prepend, DN_Str8BuilderAdd_Prepend,
}; };
#if !defined(DN_OsPathSeperator)
#if defined(DN_PLATFORM_WIN32)
#define DN_OsPathSeperator "\\"
#else
#define DN_OsPathSeperator "/"
#endif
#define DN_OsPathSeperatorStr8 DN_Str8Lit(DN_OsPathSeperator)
#endif
typedef struct DN_Path DN_Path;
struct DN_Path
{
bool has_prefix_path_seperator;
DN_Str8Link *head;
DN_Str8Link *tail;
DN_USize string_size;
DN_U16 links_size;
};
typedef DN_U32 DN_AgeUnit; typedef DN_U32 DN_AgeUnit;
enum DN_AgeUnit_ enum DN_AgeUnit_
{ {
@@ -2297,7 +2317,6 @@ enum DN_OSFileRotateFlags_
DN_OSFileRotateFlags_KeepBaseFile = 1 << 0, DN_OSFileRotateFlags_KeepBaseFile = 1 << 0,
}; };
enum DN_OSPathInfoType enum DN_OSPathInfoType
{ {
DN_OSPathInfoType_Unknown, DN_OSPathInfoType_Unknown,
@@ -2356,34 +2375,6 @@ enum DN_OSFileAccess_
DN_OSFileAccess_All = DN_OSFileAccess_ReadWrite | DN_OSFileAccess_Execute | DN_OSFileAccess_AppendOnly, DN_OSFileAccess_All = DN_OSFileAccess_ReadWrite | DN_OSFileAccess_Execute | DN_OSFileAccess_AppendOnly,
}; };
// NOTE: DN_OSPath
#if !defined(DN_OSPathSeparator)
#if defined(DN_PLATFORM_WIN32)
#define DN_OSPathSeparator "\\"
#else
#define DN_OSPathSeparator "/"
#endif
#define DN_OSPathSeparatorStr8 DN_Str8Lit(DN_OSPathSeparator)
#endif
typedef struct DN_OSPathLink DN_OSPathLink;
struct DN_OSPathLink
{
DN_Str8 string;
DN_OSPathLink *next;
DN_OSPathLink *prev;
};
typedef struct DN_OSPath DN_OSPath;
struct DN_OSPath
{
bool has_prefix_path_separator;
DN_OSPathLink *head;
DN_OSPathLink *tail;
DN_USize string_size;
DN_U16 links_size;
};
typedef DN_U32 DN_OSExecFlags; typedef DN_U32 DN_OSExecFlags;
enum DN_OSExecFlags_ enum DN_OSExecFlags_
{ {
@@ -3098,7 +3089,7 @@ DN_API void DN_Str8x512AppendFmtV
DN_API void DN_Str8x1024AppendFmt (DN_Str8x1024 *str, DN_FMT_ATTRIB char const *fmt, ...); DN_API void DN_Str8x1024AppendFmt (DN_Str8x1024 *str, DN_FMT_ATTRIB char const *fmt, ...);
DN_API void DN_Str8x1024AppendFmtV (DN_Str8x1024 *str, DN_FMT_ATTRIB char const *fmt, va_list args); DN_API void DN_Str8x1024AppendFmtV (DN_Str8x1024 *str, DN_FMT_ATTRIB char const *fmt, va_list args);
DN_API DN_Str8x32 DN_Str8x32FromU64 (DN_U64 val, char separator); DN_API DN_Str8x32 DN_Str8x32FromU64 (DN_U64 val, char seperator);
DN_API bool DN_Str8Is (DN_Str8 string, DN_Str8IsFlags flags); DN_API bool DN_Str8Is (DN_Str8 string, DN_Str8IsFlags flags);
DN_API char * DN_Str8End (DN_Str8 string); DN_API char * DN_Str8End (DN_Str8 string);
DN_API DN_Str8 DN_Str8Subset (DN_Str8 string, DN_USize offset, DN_USize count); DN_API DN_Str8 DN_Str8Subset (DN_Str8 string, DN_USize offset, DN_USize count);
@@ -3174,13 +3165,13 @@ DN_API DN_USize DN_Str8SplitAVX512F
DN_API DN_Str8Slice DN_Str8SplitAllocAVX512F (DN_Arena *arena, DN_Str8 string, DN_Str8 delimiter, DN_Str8SplitFlags flags); DN_API DN_Str8Slice DN_Str8SplitAllocAVX512F (DN_Arena *arena, DN_Str8 string, DN_Str8 delimiter, DN_Str8SplitFlags flags);
#endif #endif
DN_API DN_Str8 DN_Str8SliceRender (DN_Str8Slice array, DN_Str8 separator, DN_Arena *arena); DN_API DN_Str8 DN_Str8SliceRender (DN_Str8Slice array, DN_Str8 seperator, DN_Arena *arena);
DN_API DN_Str8 DN_Str8RenderSpaceSep (DN_Str8Slice array, DN_Arena *arena); DN_API DN_Str8 DN_Str8RenderSpaceSep (DN_Str8Slice array, DN_Arena *arena);
DN_API int DN_Str8CompareNatural (DN_Str8 lhs, DN_Str8 rhs, DN_Str8EqCase eq_case); DN_API int DN_Str8CompareNatural (DN_Str8 lhs, DN_Str8 rhs, DN_Str8EqCase eq_case);
DN_API int DN_Str8CompareLexicographic (DN_Str8 lhs, DN_Str8 rhs, DN_Str8EqCase eq_case); DN_API int DN_Str8CompareLexicographic (DN_Str8 lhs, DN_Str8 rhs, DN_Str8EqCase eq_case);
DN_API bool DN_Str16Eq (DN_Str16 lhs, DN_Str16 rhs); DN_API bool DN_Str16Eq (DN_Str16 lhs, DN_Str16 rhs);
DN_API DN_Str16 DN_Str16SliceRender (DN_Str16Slice array, DN_Str16 separator, DN_Arena *arena); DN_API DN_Str16 DN_Str16SliceRender (DN_Str16Slice array, DN_Str16 seperator, DN_Arena *arena);
DN_API DN_Str16 DN_Str16RenderSpaceSep (DN_Str16Slice array, DN_Arena *arena); DN_API DN_Str16 DN_Str16RenderSpaceSep (DN_Str16Slice array, DN_Arena *arena);
DN_API DN_Str8Builder DN_Str8BuilderFromArena (DN_Arena *arena); DN_API DN_Str8Builder DN_Str8BuilderFromArena (DN_Arena *arena);
@@ -3216,6 +3207,18 @@ DN_API DN_Str8 DN_Str8FromStr8BuilderArena
DN_API DN_Str8 DN_Str8FromStr8BuilderDelimitAllocator (DN_Str8Builder const *builder, DN_Str8 delimiter, DN_Allocator allocator); DN_API DN_Str8 DN_Str8FromStr8BuilderDelimitAllocator (DN_Str8Builder const *builder, DN_Str8 delimiter, DN_Allocator allocator);
DN_API DN_Str8 DN_Str8FromStr8BuilderDelimitArena (DN_Str8Builder const *builder, DN_Str8 delimiter, DN_Arena *arena); DN_API DN_Str8 DN_Str8FromStr8BuilderDelimitArena (DN_Str8Builder const *builder, DN_Str8 delimiter, DN_Arena *arena);
DN_API bool DN_PathAddRef (DN_Path *path, DN_Str8 add, DN_Arena *arena);
DN_API bool DN_PathAdd (DN_Path *path, DN_Str8 add, DN_Arena *arena);
DN_API bool DN_PathAddF (DN_Path *path, DN_FMT_ATTRIB char const *fmt, ...);
DN_API bool DN_PathPop (DN_Path *path);
DN_API DN_Str8 DN_Str8FromPath (DN_Path const *path, DN_Str8 path_seperator, DN_Allocator allocator);
DN_API DN_Str8 DN_Str8FmtPathVArena (DN_Str8 path_seperator, DN_Arena *arena, char const *fmt, va_list args);
DN_API DN_Str8 DN_Str8FmtPathArena (DN_Str8 path_seperator, DN_Arena *arena, DN_FMT_ATTRIB char const *fmt, ...);
DN_API DN_Str8 DN_Str8FmtPathVPool (DN_Str8 path_seperator, DN_Pool *pool, char const *fmt, va_list args);
DN_API DN_Str8 DN_Str8FmtPathPool (DN_Str8 path_seperator, DN_Pool *pool, DN_FMT_ATTRIB char const *fmt, ...);
DN_API DN_Str8 DN_Str8FmtOsPathArena (DN_Arena *arena, DN_FMT_ATTRIB char const *fmt, ...);
DN_API DN_Str8 DN_Str8FmtOsPathPool (DN_Pool *pool, DN_FMT_ATTRIB char const *fmt, ...);
DN_API int DN_UTF8Encode (DN_U8 utf8[4], DN_U32 codepoint); DN_API int DN_UTF8Encode (DN_U8 utf8[4], DN_U32 codepoint);
DN_API int DN_UTF16Encode (DN_U16 utf16[2], DN_U32 codepoint); DN_API int DN_UTF16Encode (DN_U16 utf16[2], DN_U32 codepoint);
DN_API DN_UTF8DecodeResult DN_UTF8Decode (DN_Str8 stream); DN_API DN_UTF8DecodeResult DN_UTF8Decode (DN_Str8 stream);
@@ -3319,7 +3322,14 @@ DN_API void DN_ProfilerFmtToStdout
DN_API DN_F64 DN_ProfilerSecFromTsc (DN_Profiler *profiler, DN_U64 duration_tsc); DN_API DN_F64 DN_ProfilerSecFromTsc (DN_Profiler *profiler, DN_U64 duration_tsc);
DN_API DN_F64 DN_ProfilerMsFromTsc (DN_Profiler *profiler, DN_U64 duration_tsc); DN_API DN_F64 DN_ProfilerMsFromTsc (DN_Profiler *profiler, DN_U64 duration_tsc);
DN_API void DN_QSort (void *array, DN_USize array_size, DN_USize elem_size, void *user_context, DN_QSortCompareFunc *compare); DN_API void DN_QSort_ (void *array, DN_USize array_size, DN_USize elem_size, void *user_context, DN_QSortCompareFunc *compare);
#if defined(__cplusplus)
template <typename T> void DN_QSortT (T *array, DN_USize array_size, void *user_context, DN_QSortCompareFunc *compare);
#define DN_QSort(array, array_size, user_context, compare) DN_QSortT(array, array_size, user_context, compare)
#else
#define DN_QSort(array, array_size, user_context, compare) DN_QSort_(array, array_size, sizeof(*array), user_context, compare)
#endif
DN_API bool DN_QSortCompareStr8NaturalAsc (void const* lhs, void const *rhs, void *user_context); DN_API bool DN_QSortCompareStr8NaturalAsc (void const* lhs, void const *rhs, void *user_context);
DN_API bool DN_QSortCompareStr8NaturalDesc (void const* lhs, void const *rhs, void *user_context); DN_API bool DN_QSortCompareStr8NaturalDesc (void const* lhs, void const *rhs, void *user_context);
DN_API bool DN_QSortCompareStr8LexicographicAsc (void const* lhs, void const *rhs, void *user_context); DN_API bool DN_QSortCompareStr8LexicographicAsc (void const* lhs, void const *rhs, void *user_context);
@@ -3499,10 +3509,16 @@ DN_API DN_V2U16& operator/=
DN_API DN_V2U16& operator-= (DN_V2U16& lhs, DN_V2U16 rhs); DN_API DN_V2U16& operator-= (DN_V2U16& lhs, DN_V2U16 rhs);
DN_API DN_V2U16& operator+= (DN_V2U16& lhs, DN_V2U16 rhs); DN_API DN_V2U16& operator+= (DN_V2U16& lhs, DN_V2U16 rhs);
// NOTE: DN_V2F32
// API
// DN_V2F32Rotate
// Rotate a vector using the precomputed cosine and sine value of the angle (e.g.
// `cos_a => cos(your_angle * 2.f * DN_PiF32)` and `sin_a => sinf(your_angle * 2.f * DN_PiF32)`)
#define DN_V2U32Zero DN_Literal(DN_V2U32){{(DN_U32)(0), (DN_U32)(0)}} #define DN_V2U32Zero DN_Literal(DN_V2U32){{(DN_U32)(0), (DN_U32)(0)}}
#define DN_V2U32One DN_Literal(DN_V2U32){{(DN_U32)(1), (DN_U32)(1)}} #define DN_V2U32One DN_Literal(DN_V2U32){{(DN_U32)(1), (DN_U32)(1)}}
#define DN_V2U32From1N(x) DN_Literal(DN_V2U32){{(DN_U32)(x), (DN_U32)(x)}} #define DN_V2U32From1N(x) DN_Literal(DN_V2U32){{(DN_U32)(x), (DN_U32)(x)}}
#define DN_V2U32From2N(x, y) DN_Literal(DN_V2U32){{(DN_U32)(x), (DN_U32)(y)}} #define DN_V2U32From2N(x, y) DN_Literal(DN_V2U32){{(DN_U32)(x), (DN_U32)(y)}}
#define DN_V2U32FromV2(v2) DN_Literal(DN_V2U32){{(DN_U32)(v2.x), (DN_U32)(v2.y)}}
#define DN_V2F32Zero DN_Literal(DN_V2F32){{(DN_F32)(0), (DN_F32)(0)}} #define DN_V2F32Zero DN_Literal(DN_V2F32){{(DN_F32)(0), (DN_F32)(0)}}
#define DN_V2F32One DN_Literal(DN_V2F32){{(DN_F32)(1), (DN_F32)(1)}} #define DN_V2F32One DN_Literal(DN_V2F32){{(DN_F32)(1), (DN_F32)(1)}}
@@ -3511,6 +3527,7 @@ DN_API DN_V2U16& operator+=
#define DN_V2F32FromV2(xy) DN_Literal(DN_V2F32){{(DN_F32)(xy).x, (DN_F32)(xy).y}} #define DN_V2F32FromV2(xy) DN_Literal(DN_V2F32){{(DN_F32)(xy).x, (DN_F32)(xy).y}}
DN_API DN_V2F32 DN_V2F32Lerp (DN_V2F32 a, DN_F32 t, DN_V2F32 b); DN_API DN_V2F32 DN_V2F32Lerp (DN_V2F32 a, DN_F32 t, DN_V2F32 b);
DN_API DN_V2F32 DN_V2F32Rotate (DN_V2F32 v, DN_F32 cos_a, DN_F32 sin_a);
DN_API bool operator!= (DN_V2F32 lhs, DN_V2F32 rhs); DN_API bool operator!= (DN_V2F32 lhs, DN_V2F32 rhs);
DN_API bool operator== (DN_V2F32 lhs, DN_V2F32 rhs); DN_API bool operator== (DN_V2F32 lhs, DN_V2F32 rhs);
@@ -3580,7 +3597,7 @@ DN_API DN_F32 DN_V2F32Area
// NOTE: Grayscale co-efficients from: // NOTE: Grayscale co-efficients from:
// https://github.com/EpicGames/UnrealEngine/blob/260bb2e1c5610b31c63a36206eedd289409c5f11/Engine/Source/Runtime/Core/Private/Math/Color.cpp#L304 // https://github.com/EpicGames/UnrealEngine/blob/260bb2e1c5610b31c63a36206eedd289409c5f11/Engine/Source/Runtime/Core/Private/Math/Color.cpp#L304
DN_V3F32 static const DN_V3F32_Rgb_LUMINANCE = DN_V3F32From3N(0.3f, 0.59f, 0.11f); DN_V3F32 static const DN_V3F32_RGB_LUMINANCE = DN_V3F32From3N(0.3f, 0.59f, 0.11f);
DN_API bool operator== (DN_V3F32 lhs, DN_V3F32 rhs); DN_API bool operator== (DN_V3F32 lhs, DN_V3F32 rhs);
DN_API bool operator!= (DN_V3F32 lhs, DN_V3F32 rhs); DN_API bool operator!= (DN_V3F32 lhs, DN_V3F32 rhs);
@@ -4596,8 +4613,8 @@ DN_API void * DN_OS_MemAlloc (D
DN_API void DN_OS_MemDealloc (void *ptr); DN_API void DN_OS_MemDealloc (void *ptr);
DN_API DN_Date DN_OS_DateLocalTimeNow (); DN_API DN_Date DN_OS_DateLocalTimeNow ();
DN_API DN_Str8x32 DN_OS_DateLocalTimeStr8Now (char date_separator = '-', char hms_separator = ':'); DN_API DN_Str8x32 DN_OS_DateLocalTimeStr8Now (char date_seperator = '-', char hms_seperator = ':');
DN_API DN_Str8x32 DN_OS_DateLocalTimeStr8 (DN_Date time, char date_separator = '-', char hms_separator = ':'); DN_API DN_Str8x32 DN_OS_DateLocalTimeStr8 (DN_Date time, char date_seperator = '-', char hms_seperator = ':');
DN_API DN_U64 DN_OS_DateUnixTimeNs (); DN_API DN_U64 DN_OS_DateUnixTimeNs ();
#define DN_OS_DateUnixTimeUs() (DN_OS_DateUnixTimeNs() / 1000) #define DN_OS_DateUnixTimeUs() (DN_OS_DateUnixTimeNs() / 1000)
#define DN_OS_DateUnixTimeMs() (DN_OS_DateUnixTimeNs() / (1000 * 1000)) #define DN_OS_DateUnixTimeMs() (DN_OS_DateUnixTimeNs() / (1000 * 1000))
@@ -4696,24 +4713,6 @@ DN_API bool DN_OS_PathIsDir (D
DN_API bool DN_OS_PathMakeDir (DN_Str8 path); DN_API bool DN_OS_PathMakeDir (DN_Str8 path);
DN_API bool DN_OS_PathIterateDir (DN_Str8 path, DN_OSDirIterator *it); DN_API bool DN_OS_PathIterateDir (DN_Str8 path, DN_OSDirIterator *it);
DN_API bool DN_OS_PathAddRef (DN_Arena *arena, DN_OSPath *fs_path, DN_Str8 path);
DN_API bool DN_OS_PathAdd (DN_Arena *arena, DN_OSPath *fs_path, DN_Str8 path);
DN_API bool DN_OS_PathAddF (DN_Arena *arena, DN_OSPath *fs_path, DN_FMT_ATTRIB char const *fmt, ...);
DN_API bool DN_OS_PathPop (DN_OSPath *fs_path);
DN_API DN_Str8 DN_OS_PathBuildWithSeparatorAllocator (DN_Allocator allocator, DN_OSPath const *fs_path, DN_Str8 path_separator);
DN_API DN_Str8 DN_OS_PathToArena (DN_Arena *arena, DN_Str8 path, DN_Str8 path_separtor);
DN_API DN_Str8 DN_OS_PathToPool (DN_Pool *pool, DN_Str8 path, DN_Str8 path_separtor);
DN_API DN_Str8 DN_OS_PathToFmtArena (DN_Arena *arena, DN_Str8 path_separator, DN_FMT_ATTRIB char const *fmt, ...);
DN_API DN_Str8 DN_OS_PathToFmtPool (DN_Pool *pool, DN_Str8 path_separator, DN_FMT_ATTRIB char const *fmt, ...);
DN_API DN_Str8 DN_OS_PathArena (DN_Arena *arena, DN_Str8 path);
DN_API DN_Str8 DN_OS_PathPool (DN_Pool *pool, DN_Str8 path);
DN_API DN_Str8 DN_OS_PathFmtArena (DN_Arena *arena, DN_FMT_ATTRIB char const *fmt, ...);
DN_API DN_Str8 DN_OS_PathFmtPool (DN_Pool *pool, DN_FMT_ATTRIB char const *fmt, ...);
#define DN_OS_PathBuildFwdSlash(allocator, fs_path) DN_OS_PathBuildWithSeparatorAllocator(allocator, fs_path, DN_Str8Lit("/"))
#define DN_OS_PathBuildBackSlash(allocator, fs_path) DN_OS_PathBuildWithSeparatorAllocator(allocator, fs_path, DN_Str8Lit("\\"))
#define DN_OS_PathBuild(allocator, fs_path) DN_OS_PathBuildWithSeparatorAllocator(allocator, fs_path, DN_OSPathSeparatorStr8)
DN_API void DN_OS_Exit (int32_t exit_code); DN_API void DN_OS_Exit (int32_t exit_code);
DN_API DN_OSExecArgs DN_OS_ExecArgsDefault (); DN_API DN_OSExecArgs DN_OS_ExecArgsDefault ();
DN_API DN_OSExecResult DN_OS_ExecPump (DN_OSExecAsyncHandle handle, char *stdout_buffer, size_t *stdout_size, char *stderr_buffer, size_t *stderr_size, DN_U32 timeout_ms, DN_ErrSink *err); DN_API DN_OSExecResult DN_OS_ExecPump (DN_OSExecAsyncHandle handle, char *stdout_buffer, size_t *stdout_size, char *stderr_buffer, size_t *stderr_size, DN_U32 timeout_ms, DN_ErrSink *err);
+301
View File
@@ -0,0 +1,301 @@
#include "dn_seshc.h"
struct DN_SHMsgSendAsyncContext_
{
bool send_success;
DN_Arena* arena;
DN_SHCLIArgs args;
DN_SHMsgSendData send;
DN_Str8 msg;
bool detached;
};
DN_SHCLIArgs DN_SH_CLIArgsCopy(DN_SHCLIArgs const *src, DN_Arena *arena)
{
DN_SHCLIArgs result = {};
result = *src;
result.exe_path = DN_Str8FromStr8Arena(src->exe_path, arena);
result.ini_path = DN_Str8FromStr8Arena(src->ini_path, arena);
result.seed_node_url = DN_Str8FromStr8Arena(src->seed_node_url, arena);
return result;
}
DN_Str8 DN_SH_CLIOptionsStr8()
{
DN_Str8 result = DN_Str8Lit(
"SESHC OPTIONS (note all options must be set to activate Seshc):\n"
" --seshc-exe-path <path> Path to the Seshc EXE file to invoke for sending messages\n"
" --seshc-ini-path <path> Path to the .ini file to load Seshc arguments from\n"
" (such as account secrets, display name, recipient...)\n"
" --seshc-seed-node <url> URL to the Session seed node for determining the nodes to\n"
" send the message to\n"
);
return result;
}
DN_SHCLIEatArgResult DN_SH_CLIEatArg(DN_SHCLIArgs *args, char const **arg_ptr, int arg_count)
{
DN_SHCLIEatArgResult result = {};
result.arg_ptr = arg_ptr;
result.arg_count = arg_count;
DN_Str8 arg = {};
if (arg_count)
arg = DN_Str8FromCStr8(*result.arg_ptr);
// NOTE: Try handling the argument if we recognise it
{
if (!result.eaten && DN_Str8EqInsensitive(arg, DN_Str8Lit("--seshc-exe-path"))) {
(void)DN_ArgShift(result.arg_ptr, result.arg_count);
result.eaten = true;
args->exe_path = DN_Str8FromCStr8(DN_ArgShift(result.arg_ptr, result.arg_count));
if (DN_OS_PathInfo(args->exe_path).type != DN_OSPathInfoType_File) {
result.error_msg = DN_Str8Lit("Seshc executable path does not point to a file");
result.error_arg = args->exe_path;
args->exe_path = {};
}
}
if (!result.eaten && DN_Str8EqInsensitive(arg, DN_Str8Lit("--seshc-ini-path"))) {
(void)DN_ArgShift(result.arg_ptr, result.arg_count);
result.eaten = true;
args->ini_path = DN_Str8FromCStr8(DN_ArgShift(result.arg_ptr, result.arg_count));
if (DN_OS_PathInfo(args->ini_path).type != DN_OSPathInfoType_File) {
result.error_msg = DN_Str8Lit("Seshc ini path does not point to a file");
result.error_arg = args->ini_path;
args->ini_path = {};
}
}
if (!result.eaten && DN_Str8EqInsensitive(arg, DN_Str8Lit("--seshc-seed-node"))) {
(void)DN_ArgShift(result.arg_ptr, result.arg_count);
result.eaten = true;
args->seed_node_url = DN_Str8FromCStr8(DN_ArgShift(result.arg_ptr, result.arg_count));
}
}
if (args->seed_node_url.count && args->exe_path.count && args->ini_path.count)
args->valid = true;
return result;
}
bool DN_SH_MsgSendBlockingFmt(DN_SHMsgSendData send, DN_SHCLIArgs *cli_args, char const *fmt, ...)
{
bool result = false;
if (cli_args->valid) {
DN_TcScratch scratch = DN_TcScratchBeginArena(nullptr, 0);
va_list args;
va_start(args, fmt);
DN_Str8 msg = DN_Str8FmtVArena(&scratch.arena, fmt, args);
va_end(args);
DN_Str8 account_secret_arg = DN_Str8Lit("--account-secret");
DN_Str8 seed_node_url_arg = DN_Str8Lit("--seed-node-url");
DN_Str8 display_name_arg = DN_Str8Lit("--display-name");
DN_Str8 ini_path_arg = DN_Str8Lit("--ini-path");
DN_Str8 send_arg = DN_Str8Lit("send");
DN_Str8 cmds[16] = {};
DN_USize cmds_count = 0;
DN_LArrayAppend(cmds, &cmds_count, cli_args->exe_path);
DN_LArrayAppend(cmds, &cmds_count, account_secret_arg);
DN_LArrayAppend(cmds, &cmds_count, send.account_secret);
DN_LArrayAppend(cmds, &cmds_count, seed_node_url_arg);
DN_LArrayAppend(cmds, &cmds_count, cli_args->seed_node_url);
if (send.display_name.count) {
DN_LArrayAppend(cmds, &cmds_count, display_name_arg);
DN_LArrayAppend(cmds, &cmds_count, send.display_name);
}
DN_LArrayAppend(cmds, &cmds_count, ini_path_arg);
DN_LArrayAppend(cmds, &cmds_count, cli_args->ini_path);
DN_LArrayAppend(cmds, &cmds_count, send_arg);
DN_LArrayAppend(cmds, &cmds_count, send.recipient);
DN_LArrayAppend(cmds, &cmds_count, msg);
DN_Str8Slice cmd_line = {};
cmd_line.data = cmds;
cmd_line.count = cmds_count;
DN_OSExecResult exec = DN_OS_Exec(cmd_line, DN_OS_ExecArgsDefault(), &scratch.arena, nullptr);
result = exec.os_error_code == 0 && exec.exit_code == 0;
if (!result) {
DN_LogErrorF("Error sending message to %.*s (exit code: %d, os: %d): %.*s",
DN_Str8PrintFmt(send.recipient),
exec.exit_code,
exec.os_error_code,
DN_Str8PrintFmt(exec.stderr_text));
}
DN_TcScratchEnd(&scratch);
}
return result;
}
static int DN_SH_MsgSendDetachedFmtThreadFunc_(DN_OSThread *thread)
{
DN_SHMsgSendAsyncContext_ *context = DN_Cast(DN_SHMsgSendAsyncContext_ *) thread->user_context;
context->send_success = DN_SH_MsgSendBlockingFmt(context->send, &context->args, "%.*s", DN_Str8PrintFmt(context->msg));
if (context->detached)
DN_ArenaDeinit(context->arena);
return 0;
}
static DN_SHMsgSendAsyncHandle DN_SH_MsgSendAsyncFmtVMaybeDetached_(DN_SHMsgSendData send, DN_SHCLIArgs *cli_args, DN_Arena *arena, bool detached, char const *fmt, va_list args)
{
DN_SHMsgSendAsyncHandle result = {};
if (!cli_args->valid)
return result;
// NOTE: Setup context
DN_SHMsgSendAsyncContext_ *context = DN_ArenaNewZ(arena, DN_SHMsgSendAsyncContext_);
context->args = DN_SH_CLIArgsCopy(cli_args, arena);
context->send = send;
context->arena = arena;
context->msg = DN_Str8FmtVArena(arena, fmt, args);
context->detached = detached;
// NOTE: Execute and forget
DN_OSThreadInitArgs thread_args = DN_OS_ThreadInitArgsDefault();
if (detached)
thread_args.flags |= DN_OSThreadFlags_Detached;
DN_OS_ThreadInit(&result.thread, DN_SH_MsgSendDetachedFmtThreadFunc_, thread_args, context);
return result;
}
void DN_SH_MsgSendDetachedFmt(DN_SHMsgSendData send, DN_SHCLIArgs *cli_args, char const *fmt, ...)
{
DN_Arena arena_stack = DN_OS_ArenaFromHeapVirtual(0, 0, DN_MemFlags_Nil);
DN_Arena *arena = DN_ArenaNewZ(&arena_stack, DN_Arena);
*arena = arena_stack;
va_list args;
va_start(args, fmt);
DN_SH_MsgSendAsyncFmtVMaybeDetached_(send, cli_args, arena, /*detached=*/ true, fmt, args);
va_end(args);
}
DN_SHMsgSendAsyncHandle DN_SH_MsgSendAsyncFmt(DN_SHMsgSendData send, DN_SHCLIArgs *cli_args, DN_Arena *arena, char const *fmt, ...)
{
va_list args;
va_start(args, fmt);
DN_SHMsgSendAsyncHandle result = DN_SH_MsgSendAsyncFmtVMaybeDetached_(send, cli_args, arena, /*detached=*/ false, fmt, args);
va_end(args);
return result;
}
DN_SHMsgSendAsyncStatus DN_SH_MsgSendAsyncWait(DN_SHMsgSendAsyncHandle *handle, DN_U32 timeout_ms)
{
DN_SHMsgSendAsyncStatus result = DN_SHMsgSendAsyncStatus_Success;
if (handle && handle->thread.user_context) {
bool joined = DN_OS_ThreadJoin(&handle->thread, timeout_ms, DN_TcDeinitArenas_Yes);
if (joined) {
DN_SHMsgSendAsyncContext_ *context = DN_Cast(DN_SHMsgSendAsyncContext_ *) handle->thread.user_context;
result = context->send_success ? DN_SHMsgSendAsyncStatus_Success : DN_SHMsgSendAsyncStatus_Failed;
*handle = {};
} else {
result = DN_SHMsgSendAsyncStatus_Timeout;
}
}
return result;
}
void DN_SH_LogBroadcastFmtV(DN_SHLogMode mode, DN_LogType type, DN_SHMsgSendData send, DN_SHCLIArgs *cli_args, DN_Str8 short_desc, char const *fmt, va_list args)
{
DN_TcScratch scratch = DN_TcScratchBeginArena(nullptr, 0);
DN_Str8 msg = DN_Str8FmtVArena(&scratch.arena, fmt, args);
DN_Str8 prefix = {};
switch (type) {
case DN_LogType_Debug: prefix = DN_Str8Lit("🐞 "); break;
case DN_LogType_Info: prefix = DN_Str8Lit(""); break;
case DN_LogType_Warning: prefix = DN_Str8Lit("⚠️ "); break;
case DN_LogType_Error: prefix = DN_Str8Lit("🚨 "); break;
case DN_LogType_Count: break;
}
DN_LogF(type, "%.*s%.*s. %.*s", DN_Str8PrintFmt(prefix), DN_Str8PrintFmt(short_desc), DN_Str8PrintFmt(msg));
DN_Date date = DN_OS_DateLocalTimeNow();
// NOTE: 12-hour conversion
DN_U8 hour12 = date.hour % 12;
if (hour12 == 0)
hour12 = 12;
char const *am_pm = date.hour < 12 ? "AM" : "PM";
// Time-of-day emoji
DN_Str8 time_emoji = {};
if (date.hour >= 5 && date.hour <= 11)
time_emoji = DN_Str8Lit("☀️");
else if (date.hour >= 12 && date.hour <= 16)
time_emoji = DN_Str8Lit("🌤️");
else if (date.hour >= 17 && date.hour <= 19)
time_emoji = DN_Str8Lit("🌅");
else if (date.hour >= 20 && date.hour <= 23)
time_emoji = DN_Str8Lit("");
else
time_emoji = DN_Str8Lit("🌑");
if (mode == DN_SHLogMode_Detached) {
DN_SH_MsgSendDetachedFmt(send,
cli_args,
"%.*s%.*s\n"
"%.*s %u-%02u-%02u %u:%02u:%02u %s%s"
"%.*s",
DN_Str8PrintFmt(prefix),
DN_Str8PrintFmt(short_desc),
DN_Str8PrintFmt(time_emoji),
date.year,
date.month,
date.day,
hour12,
date.minutes,
date.seconds,
am_pm,
msg.count ? "\n" : "",
DN_Str8PrintFmt(msg));
} else {
DN_Assert(mode == DN_SHLogMode_Blocking);
DN_SH_MsgSendBlockingFmt(send,
cli_args,
"%.*s %.*s\n"
"%.*s %u-%02u-%02u %u:%02u:%02u %s%s"
"%.*s",
DN_Str8PrintFmt(prefix),
DN_Str8PrintFmt(short_desc),
DN_Str8PrintFmt(time_emoji),
date.year,
date.month,
date.day,
hour12,
date.minutes,
date.seconds,
am_pm,
msg.count ? "\n" : "",
DN_Str8PrintFmt(msg));
}
DN_TcScratchEnd(&scratch);
}
void DN_SH_LogBroadcastBlockingFmt(DN_LogType type, DN_SHMsgSendData send, DN_SHCLIArgs *cli_args, DN_Str8 short_desc, char const *fmt, ...)
{
va_list args;
va_start(args, fmt);
DN_SH_LogBroadcastFmtV(DN_SHLogMode_Blocking, type, send, cli_args, short_desc, fmt, args);
va_end(args);
}
void DN_SH_LogBroadcastDetachedFmt(DN_LogType type, DN_SHMsgSendData send, DN_SHCLIArgs *cli_args, DN_Str8 short_desc, char const *fmt, ...)
{
va_list args;
va_start(args, fmt);
DN_SH_LogBroadcastFmtV(DN_SHLogMode_Detached, type, send, cli_args, short_desc, fmt, args);
va_end(args);
}
+82
View File
@@ -0,0 +1,82 @@
#if !defined(DN_SESHC_H)
#define DN_SESHC_H
#if defined(_CLANGD)
#define DN_WITH_OS 1
#include "../dn.h"
#endif
struct DN_SHCLIArgs
{
bool valid;
DN_Str8 exe_path;
DN_Str8 ini_path;
DN_Str8 seed_node_url;
};
struct DN_SHCLIEatArgResult
{
bool eaten;
DN_Str8 error_msg; // Parsing error message. String is immutably stored in the data-segment w/ program lifetime.
DN_Str8 error_arg; // Argument that caused the parsing error
char const **arg_ptr; // Next argument pointer that that the caller should proceed from
DN_USize arg_count; // Next argument count that that the caller should assume
};
struct DN_SHMsgSendData
{
DN_Str8 recipient; // Either `ini:<section.key>` or "05-prefix session account ID"
DN_Str8 account_secret; // Seshc EXE --account-secret format
DN_Str8 display_name;
};
struct DN_SHMsgSendAsyncHandle
{
DN_OSThread thread;
};
enum DN_SHLogMode
{
DN_SHLogMode_Blocking,
DN_SHLogMode_Detached,
};
enum DN_SHMsgSendAsyncStatus
{
DN_SHMsgSendAsyncStatus_Timeout,
DN_SHMsgSendAsyncStatus_Success,
DN_SHMsgSendAsyncStatus_Failed,
};
// NOTE: Seshc
// Overview
// Helper library that provides some useful APIs for programatically calling the Seshc CLI
// executable to send messages from your C/C++ application.
// API
// DN_SH_MsgSendDetachedFmt
// Send a 1-on-1 message with a background thread that is spawned on demand and detached. If the
// application exits before this thread has completed sending the message, the message will not
// be sent.
// DN_SH_MsgSendBlockingFmt
// Send a 1-on-1 message using the current executing thread, blocking control-flow until the
// message has been sent. Returns true if the send was successful, false otherwise.
// DN_SH_MsgSendAsyncFmt
// Send a 1-on-1 message with a background thread that is spawned on demand. A handle to the
// thread is returned that can be waited on.
DN_SHCLIArgs DN_SH_CLIArgsCopy (DN_SHCLIArgs const *src, DN_Arena *arena);
DN_Str8 DN_SH_CLIOptionsStr8 ();
DN_SHCLIEatArgResult DN_SH_CLIEatArg (DN_SHCLIArgs *args, char const **arg_ptr, int arg_count);
bool DN_SH_MsgSendBlockingFmt (DN_SHMsgSendData send, DN_SHCLIArgs *cli_args, char const *fmt, ...);
void DN_SH_MsgSendDetachedFmt (DN_SHMsgSendData send, DN_SHCLIArgs *cli_args, char const *fmt, ...);
DN_SHMsgSendAsyncHandle DN_SH_MsgSendAsyncFmt (DN_SHMsgSendData send, DN_SHCLIArgs *cli_args, DN_Arena *arena, char const *fmt, ...);
DN_SHMsgSendAsyncStatus DN_SH_MsgSendAsyncWait (DN_SHMsgSendAsyncHandle *handle, DN_U32 timeout_ms);
void DN_SH_LogBroadcastFmtV (DN_SHLogMode mode, DN_LogType type, DN_SHMsgSendData send, DN_SHCLIArgs *cli_args, DN_Str8 short_desc, char const *fmt, va_list args);
void DN_SH_LogBroadcastBlockingFmt (DN_LogType type, DN_SHMsgSendData send, DN_SHCLIArgs *cli_args, DN_Str8 short_desc, char const *fmt, ...);
void DN_SH_LogBroadcastDetachedFmt (DN_LogType type, DN_SHMsgSendData send, DN_SHCLIArgs *cli_args, DN_Str8 short_desc, char const *fmt, ...);
#endif // #if !defined(DN_SESHC_H)
+6 -9
View File
@@ -1,5 +1,11 @@
#if DN_WITH_NET_CURL #if DN_WITH_NET_CURL
#define DN_NO_WINDOWS_H_REPLACEMENT_HEADER #define DN_NO_WINDOWS_H_REPLACEMENT_HEADER
#define CURL_STATICLIB
#include <curl/curl.h>
#endif
#if defined(__EMSCRIPTEN__)
#define DN_WITH_NET_EMSCRIPTEN 1
#endif #endif
#define DN_PARANOIA_LEVEL 1 #define DN_PARANOIA_LEVEL 1
@@ -7,15 +13,6 @@
#define DN_WITH_NET 1 #define DN_WITH_NET 1
#define DN_WITH_TESTS 1 #define DN_WITH_TESTS 1
#include "dn.h" #include "dn.h"
#if DN_WITH_NET_CURL
#define CURL_STATICLIB
#include <curl/curl.h>
#endif
#if defined(DN_PLATFORM_EMSCRIPTEN)
#define DN_WITH_NET_EMSCRIPTEN 1
#endif
#include "dn.cpp" #include "dn.cpp"
#define DN_SHA3_WITH_TESTS #define DN_SHA3_WITH_TESTS
+3 -3
View File
@@ -65,7 +65,7 @@ static void AppendCppFileLineByLine(DN_Str8Builder *dest, DN_Str8 cpp_path)
line = DN_Str8FmtArena(&scratch.arena, "%S// DN: Single header generator commented out => %S", find.start_to_before_match, DN_Str8TrimWhitespaceAround(find.match_to_end_of_buffer)); line = DN_Str8FmtArena(&scratch.arena, "%S// DN: Single header generator commented out => %S", find.start_to_before_match, DN_Str8TrimWhitespaceAround(find.match_to_end_of_buffer));
DN_Str8 rel_include_path = DN_Str8TrimWhitespaceAround(find.after_match_to_end_of_buffer); DN_Str8 rel_include_path = DN_Str8TrimWhitespaceAround(find.after_match_to_end_of_buffer);
DN_Str8 root_dir = DN_Str8FileDirectoryFromPath(cpp_path); DN_Str8 root_dir = DN_Str8FileDirectoryFromPath(cpp_path);
extra_include_path = DN_OS_PathFmtArena(&scratch.arena, "%S/%S", root_dir, DN_Str8TrimSuffixSensitive(rel_include_path, DN_Str8Lit("\""))); extra_include_path = DN_Str8FmtOsPathArena(&scratch.arena, "%S/%S", root_dir, DN_Str8TrimSuffixSensitive(rel_include_path, DN_Str8Lit("\"")));
} }
} }
} }
@@ -113,7 +113,7 @@ int main(int argc, char **argv)
DN_Str8Builder builder = DN_Str8BuilderFromArena(&scratch.arena); DN_Str8Builder builder = DN_Str8BuilderFromArena(&scratch.arena);
DN_Str8 suffix = type == FileType_Header ? DN_Str8Lit("h") : DN_Str8Lit("cpp"); DN_Str8 suffix = type == FileType_Header ? DN_Str8Lit("h") : DN_Str8Lit("cpp");
for (DN_ForItCArray(it, DN_Str8 const, REL_FILE_PATHS)) { for (DN_ForItCArray(it, DN_Str8 const, REL_FILE_PATHS)) {
DN_Str8 path = DN_OS_PathFmtArena(&scratch.arena, "%S/%S.%S", dn_root_dir, *it.data, suffix); DN_Str8 path = DN_Str8FmtOsPathArena(&scratch.arena, "%S/%S.%S", dn_root_dir, *it.data, suffix);
AppendCppFileLineByLine(&builder, path); AppendCppFileLineByLine(&builder, path);
} }
@@ -121,7 +121,7 @@ int main(int argc, char **argv)
DN_Str8BuilderPrependF(&builder, "// Generated by the DN single header generator %04u-%02u-%02u %02u:%02u:%02u\n\n", date.year, date.month, date.day, date.hour, date.minutes, date.seconds); DN_Str8BuilderPrependF(&builder, "// Generated by the DN single header generator %04u-%02u-%02u %02u:%02u:%02u\n\n", date.year, date.month, date.day, date.hour, date.minutes, date.seconds);
DN_Str8 buffer = DN_Str8TrimWhitespaceAround(DN_Str8FromStr8BuilderArena(&builder, &scratch.arena)); DN_Str8 buffer = DN_Str8TrimWhitespaceAround(DN_Str8FromStr8BuilderArena(&builder, &scratch.arena));
DN_Str8 single_header_path = DN_OS_PathFmtArena(&scratch.arena, "%S/dn_single_header.%S", output_dir, suffix); DN_Str8 single_header_path = DN_Str8FmtOsPathArena(&scratch.arena, "%S/dn_single_header.%S", output_dir, suffix);
DN_ErrSink *err = DN_TcErrSinkBeginDefault(); DN_ErrSink *err = DN_TcErrSinkBeginDefault();
DN_OS_FileWriteAllSafe(single_header_path, buffer, err); DN_OS_FileWriteAllSafe(single_header_path, buffer, err);
DN_ErrSinkEndExitIfErrorF(err, -1, "Failed to write Single header file '%S'", single_header_path); DN_ErrSinkEndExitIfErrorF(err, -1, "Failed to write Single header file '%S'", single_header_path);