Unit test for vector
This commit is contained in:
@@ -115,6 +115,7 @@
|
||||
<CustomBuild Include="src\Core\Application\ApplicationManager.cpp" />
|
||||
<CustomBuild Include="src\Core\Common\CoreUtils.cpp" />
|
||||
<CustomBuild Include="src\Core\Common\String.cpp" />
|
||||
<CustomBuild Include="src\Core\Container\Vector.cpp" />
|
||||
<CustomBuild Include="src\Core\HAL\Display\Display.cpp" />
|
||||
<CustomBuild Include="src\Core\HAL\Display\Display_Private.h" />
|
||||
<CustomBuild Include="src\Core\HAL\Display\DisplayDevice.h" />
|
||||
@@ -218,9 +219,10 @@
|
||||
<CustomBuild Include="src\Graphics\Graphics.cpp" />
|
||||
<CustomBuild Include="src\Graphics\GraphicsDevice.h" />
|
||||
<CustomBuild Include="src\Graphics\ImGuiRenderer.cpp" />
|
||||
<CustomBuild Include="src\UnitTest\Container\VectorUnitTest.cpp" />
|
||||
<CustomBuild Include="src\UnitTest\RunUnitTests.cpp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="src\Core\Container\Vector.cpp" />
|
||||
</ItemGroup>
|
||||
<PropertyGroup Label="Globals">
|
||||
<ProjectGuid>{ab9c7e88-6c94-4f93-bc2a-7f5284b7d434}</ProjectGuid>
|
||||
|
||||
@@ -192,6 +192,9 @@
|
||||
<CustomBuild Include="src\Core\Common\String.cpp">
|
||||
<Filter>src\Core\Common</Filter>
|
||||
</CustomBuild>
|
||||
<CustomBuild Include="src\Core\Container\Vector.cpp">
|
||||
<Filter>src\Core\Container</Filter>
|
||||
</CustomBuild>
|
||||
<CustomBuild Include="src\Core\HAL\Display\Display.cpp">
|
||||
<Filter>src\Core\HAL\Display</Filter>
|
||||
</CustomBuild>
|
||||
@@ -501,6 +504,12 @@
|
||||
<CustomBuild Include="src\Graphics\ImGuiRenderer.cpp">
|
||||
<Filter>src\Graphics</Filter>
|
||||
</CustomBuild>
|
||||
<CustomBuild Include="src\UnitTest\Container\VectorUnitTest.cpp">
|
||||
<Filter>src\UnitTest\Container</Filter>
|
||||
</CustomBuild>
|
||||
<CustomBuild Include="src\UnitTest\RunUnitTests.cpp">
|
||||
<Filter>src\UnitTest</Filter>
|
||||
</CustomBuild>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Filter Include="include\Core\Application">
|
||||
@@ -642,6 +651,11 @@
|
||||
<UniqueIdentifier>{f763d340-6c94-4f93-bc2a-7f5284b7d434}</UniqueIdentifier>
|
||||
</Filter>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Filter Include="src\Core\Container">
|
||||
<UniqueIdentifier>{3e286bee-6c94-4f93-bc2a-7f5284b7d434}</UniqueIdentifier>
|
||||
</Filter>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Filter Include="src\Core\HAL\Display">
|
||||
<UniqueIdentifier>{82da0982-6c94-4f93-bc2a-7f5284b7d434}</UniqueIdentifier>
|
||||
@@ -772,4 +786,14 @@
|
||||
<UniqueIdentifier>{0fd13bb0-6c94-4f93-bc2a-7f5284b7d434}</UniqueIdentifier>
|
||||
</Filter>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Filter Include="src\UnitTest\Container">
|
||||
<UniqueIdentifier>{3fba0971-6c94-4f93-bc2a-7f5284b7d434}</UniqueIdentifier>
|
||||
</Filter>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Filter Include="src\UnitTest">
|
||||
<UniqueIdentifier>{a650fa16-6c94-4f93-bc2a-7f5284b7d434}</UniqueIdentifier>
|
||||
</Filter>
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
@@ -14,17 +14,62 @@ namespace Juliet
|
||||
|
||||
#define global static
|
||||
|
||||
// 1. Stringify helpers
|
||||
#define JULIET_STR(x) #x
|
||||
#define JULIET_TOSTRING(x) JULIET_STR(x)
|
||||
|
||||
// 2. Define the pragma operator based on compiler
|
||||
#if defined(__clang__) || defined(__GNUC__)
|
||||
#define JULIET_PRAGMA(x) _Pragma(#x)
|
||||
#define JULIET_SUPPRESS_MSVC(id)
|
||||
#define JULIET_SUPPRESS_CLANG(str) JULIET_PRAGMA(clang diagnostic ignored str)
|
||||
#elif defined(_MSC_VER)
|
||||
#define JULIET_PRAGMA(x) __pragma(x)
|
||||
#define JULIET_SUPPRESS_MSVC(id) JULIET_PRAGMA(warning(disable : id))
|
||||
#define JULIET_SUPPRESS_CLANG(str)
|
||||
#else
|
||||
#define JULIET_PRAGMA(x)
|
||||
#define JULIET_SUPPRESS_MSVC(id)
|
||||
#define JULIET_SUPPRESS_CLANG(str)
|
||||
#endif
|
||||
|
||||
// 3. The Agnostic "Push/Pop"
|
||||
#if defined(__clang__)
|
||||
#define JULIET_WARNING_PUSH JULIET_PRAGMA(clang diagnostic push)
|
||||
#define JULIET_WARNING_POP JULIET_PRAGMA(clang diagnostic pop)
|
||||
#elif defined(_MSC_VER)
|
||||
#define JULIET_WARNING_PUSH JULIET_PRAGMA(warning(push))
|
||||
#define JULIET_WARNING_POP JULIET_PRAGMA(warning(pop))
|
||||
#else
|
||||
#define JULIET_WARNING_PUSH
|
||||
#define JULIET_WARNING_POP
|
||||
#endif
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
// MSVC specific intrinsic
|
||||
#define JULIET_PLATFORM_BREAK() (__nop(), __debugbreak())
|
||||
#elif defined(__clang__) || defined(__GNUC__)
|
||||
// Clang/GCC specific intrinsic
|
||||
#define JULIET_PLATFORM_BREAK() __builtin_trap()
|
||||
#else
|
||||
#include <signal.h>
|
||||
#define JULIET_PLATFORM_BREAK() raise(SIGTRAP)
|
||||
#endif
|
||||
|
||||
#if JULIET_DEBUG
|
||||
#define JULIET_ASSERT_INTERNAL(expression, message) \
|
||||
__pragma(warning(push)) __pragma(warning(disable : 4127)) __pragma(warning(disable : 4548)) do \
|
||||
JULIET_WARNING_PUSH \
|
||||
JULIET_SUPPRESS_CLANG("-Wextra-semi-stmt") \
|
||||
JULIET_SUPPRESS_MSVC(4127) \
|
||||
JULIET_SUPPRESS_MSVC(4548) \
|
||||
{ \
|
||||
if (!(expression)) \
|
||||
if (!(expression)) [[unlikely]] \
|
||||
{ \
|
||||
Juliet::JulietAssert(#expression, message); \
|
||||
} \
|
||||
} \
|
||||
while (0) \
|
||||
__pragma(warning(pop))
|
||||
JULIET_WARNING_POP \
|
||||
static_assert(true, "")
|
||||
|
||||
#define AssertHR(hr_expression, message) \
|
||||
do \
|
||||
@@ -117,11 +162,11 @@ namespace Juliet
|
||||
return (x + alignment - 1) & ~(alignment - 1);
|
||||
}
|
||||
|
||||
inline void Swap(auto* Restrict& a, auto* Restrict& b)
|
||||
inline void Swap(auto* Restrict a, auto* Restrict b)
|
||||
{
|
||||
auto* temp = a;
|
||||
a = b;
|
||||
b = temp;
|
||||
auto temp = *a;
|
||||
*a = *b;
|
||||
*b = temp;
|
||||
}
|
||||
|
||||
// Move to another file dedicated to those
|
||||
|
||||
@@ -10,6 +10,7 @@ namespace Juliet
|
||||
template <typename Type>
|
||||
struct VectorArena
|
||||
{
|
||||
public:
|
||||
VectorArena()
|
||||
: First(nullptr)
|
||||
, Count(0)
|
||||
@@ -39,12 +40,13 @@ namespace Juliet
|
||||
Assert(index < Count);
|
||||
Assert(Count > 0);
|
||||
|
||||
Type* baseAdr = First;
|
||||
Type* elementAdr = First + index;
|
||||
|
||||
// Swap Last and element
|
||||
Swap(Last, elementAdr);
|
||||
--Last;
|
||||
--Count;
|
||||
ArenaPop(Arena, Stride);
|
||||
}
|
||||
|
||||
void Clear()
|
||||
|
||||
@@ -12,9 +12,7 @@ namespace Juliet
|
||||
Log(LogLevel::Error, LogCategory::Core, "--- ASSERTION FAILED ---");
|
||||
Log(LogLevel::Error, LogCategory::Core, "Expression: %s", expression);
|
||||
Log(LogLevel::Error, LogCategory::Core, "Message: %s", message);
|
||||
Log(LogLevel::Error, LogCategory::Core, "Location: %s(%u): %s",
|
||||
location.file_name(),
|
||||
location.line(),
|
||||
Log(LogLevel::Error, LogCategory::Core, "Location: %s(%u): %s", location.file_name(), location.line(),
|
||||
location.function_name());
|
||||
|
||||
if (handleResult < 0)
|
||||
@@ -26,14 +24,7 @@ namespace Juliet
|
||||
|
||||
Log(LogLevel::Error, LogCategory::Core, "-------------------------");
|
||||
|
||||
if (IsDebuggerPresent())
|
||||
{
|
||||
__debugbreak();
|
||||
}
|
||||
else
|
||||
{
|
||||
exit(1);
|
||||
}
|
||||
JULIET_PLATFORM_BREAK();
|
||||
}
|
||||
|
||||
void Free(ByteBuffer& buffer)
|
||||
|
||||
@@ -89,8 +89,8 @@ namespace Juliet::UnitTest
|
||||
Assert(reservedSizePreBigArray == testArena->Current->BasePosition);
|
||||
|
||||
// TODO Get page size from os kernel call (dwPageSize)
|
||||
constexpr uint64 k_PageSize = Kilobytes(4);
|
||||
size_t reserve_sizeAlignToPage = AlignPow2(reserve_size, k_PageSize);
|
||||
constexpr uint64 k_PageSizeUnitTest = Kilobytes(4);
|
||||
size_t reserve_sizeAlignToPage = AlignPow2(reserve_size, k_PageSizeUnitTest);
|
||||
|
||||
bool isReserveSizeSame = testArena->Current->Reserved == reserve_sizeAlignToPage;
|
||||
Assert(isReserveSizeSame);
|
||||
|
||||
@@ -17,9 +17,9 @@
|
||||
|
||||
namespace Juliet
|
||||
{
|
||||
#ifdef JULIET_DEBUG
|
||||
#if JULIET_DEBUG
|
||||
extern void RunUnitTests();
|
||||
#endif
|
||||
#endif
|
||||
|
||||
namespace
|
||||
{
|
||||
@@ -136,9 +136,9 @@ namespace Juliet
|
||||
InitializeLogManager();
|
||||
MemoryArenasInit();
|
||||
|
||||
#ifdef JULIET_DEBUG
|
||||
#if JULIET_DEBUG
|
||||
RunUnitTests();
|
||||
#endif
|
||||
#endif
|
||||
|
||||
InitFilesystem();
|
||||
|
||||
|
||||
@@ -1,57 +1,117 @@
|
||||
#ifdef JULIET_DEBUG
|
||||
#if JULIET_DEBUG
|
||||
|
||||
#include <Core/Container/Vector.h>
|
||||
#include <Core/Common/CoreUtils.h>
|
||||
#include <Core/Container/Vector.h>
|
||||
|
||||
namespace Juliet
|
||||
{
|
||||
void VectorUnitTest()
|
||||
{
|
||||
// Basic usage test
|
||||
// Test 1: Integer VectorArena - Basic PushBack and Access
|
||||
{
|
||||
Vector<int> vec;
|
||||
Assert(vec.empty());
|
||||
Assert(vec.size() == 0);
|
||||
VectorArena<int> vec;
|
||||
Assert(vec.Size() == 0);
|
||||
Assert(vec.begin() == vec.end());
|
||||
|
||||
vec.push_back(10);
|
||||
Assert(!vec.empty());
|
||||
Assert(vec.size() == 1);
|
||||
vec.PushBack(10);
|
||||
Assert(vec.Size() == 1);
|
||||
Assert(vec[0] == 10);
|
||||
Assert(*vec.begin() == 10);
|
||||
|
||||
vec.push_back(20);
|
||||
Assert(vec.size() == 2);
|
||||
vec.PushBack(20);
|
||||
Assert(vec.Size() == 2);
|
||||
Assert(vec[0] == 10);
|
||||
Assert(vec[1] == 20);
|
||||
|
||||
// Test iteration (std::vector iterator compatibility)
|
||||
vec.PushBack(30);
|
||||
Assert(vec.Size() == 3);
|
||||
Assert(vec[2] == 30);
|
||||
|
||||
// Test Iteration
|
||||
int sum = 0;
|
||||
for (int val : vec)
|
||||
{
|
||||
sum += val;
|
||||
}
|
||||
Assert(sum == 30);
|
||||
|
||||
vec.clear();
|
||||
Assert(vec.empty());
|
||||
Assert(vec.size() == 0);
|
||||
Assert(sum == 60);
|
||||
}
|
||||
|
||||
// Test with complex types (std::string) to ensure proper construction/destruction
|
||||
// Note: Vector.h currently inherits from std::vector, so this tests std::vector really.
|
||||
// Test 2: RemoveAtFast
|
||||
{
|
||||
struct TestStruct
|
||||
VectorArena<int> vec;
|
||||
vec.PushBack(10);
|
||||
vec.PushBack(20);
|
||||
vec.PushBack(30);
|
||||
|
||||
// Initial: [10, 20, 30]
|
||||
// Remove index 0 (value 10). Should swap with Last (30) and pop last.
|
||||
// Expected: [30, 20]
|
||||
vec.RemoveAtFast(0);
|
||||
Assert(vec.Size() == 2);
|
||||
Assert(vec[0] == 30);
|
||||
Assert(vec[1] == 20);
|
||||
|
||||
// Remove index 1 (value 20). Last is 20. Swap 20 with 20.
|
||||
// Expected: [30]
|
||||
vec.RemoveAtFast(1);
|
||||
Assert(vec.Size() == 1);
|
||||
Assert(vec[0] == 30);
|
||||
|
||||
// Remove remaining element
|
||||
vec.RemoveAtFast(0);
|
||||
Assert(vec.Size() == 0);
|
||||
}
|
||||
|
||||
// Test 3: Clear and Reuse
|
||||
{
|
||||
int Value;
|
||||
bool Active;
|
||||
VectorArena<int> vec;
|
||||
vec.PushBack(100);
|
||||
vec.PushBack(200);
|
||||
Assert(vec.Size() == 2);
|
||||
|
||||
vec.Clear();
|
||||
Assert(vec.Size() == 0);
|
||||
Assert(vec.begin() == vec.end());
|
||||
|
||||
// Should be able to push again
|
||||
vec.PushBack(300);
|
||||
Assert(vec.Size() == 1);
|
||||
Assert(vec[0] == 300);
|
||||
}
|
||||
|
||||
// Test 4: Struct VectorArena (Testing Move Semantics and Complex Types)
|
||||
{
|
||||
struct TestItem
|
||||
{
|
||||
int A;
|
||||
float B;
|
||||
|
||||
bool operator==(const TestItem& other) const
|
||||
{
|
||||
float diff = B - other.B;
|
||||
return A == other.A && (diff > -0.0001f && diff < 0.0001f);
|
||||
}
|
||||
};
|
||||
|
||||
Vector<TestStruct> structVec;
|
||||
structVec.push_back({ 42, true });
|
||||
VectorArena<TestItem> vec;
|
||||
vec.PushBack({ 1, 1.0f });
|
||||
vec.PushBack({ 2, 2.0f });
|
||||
vec.PushBack({ 3, 3.0f });
|
||||
|
||||
Assert(structVec.size() == 1);
|
||||
Assert(structVec[0].Value == 42);
|
||||
Assert(structVec[0].Active == true);
|
||||
Assert(vec.Size() == 3);
|
||||
Assert(vec[0].A == 1);
|
||||
Assert(vec[1].A == 2);
|
||||
|
||||
// Remove middle element (index 1, value {2, 2.0f})
|
||||
// Should swap with last ({3, 3.0f})
|
||||
// Result: [{1, 1.0f}, {3, 3.0f}]
|
||||
vec.RemoveAtFast(1);
|
||||
Assert(vec.Size() == 2);
|
||||
// Use operator== to verify entire struct including float
|
||||
Assert(vec[0] == (TestItem{ 1, 1.0f }));
|
||||
Assert(vec[1] == (TestItem{ 3, 3.0f }));
|
||||
}
|
||||
}
|
||||
}
|
||||
} // namespace Juliet
|
||||
|
||||
#endif
|
||||
@@ -1,9 +1,8 @@
|
||||
#ifdef JULIET_DEBUG
|
||||
#if JULIET_DEBUG
|
||||
|
||||
#include <Core/Common/CoreUtils.h>
|
||||
#include <Core/Logging/LogManager.h>
|
||||
#include <Core/Logging/LogTypes.h>
|
||||
#include <Core/Common/CoreUtils.h>
|
||||
|
||||
|
||||
namespace Juliet
|
||||
{
|
||||
@@ -18,6 +17,6 @@ namespace Juliet
|
||||
|
||||
LogMessage(LogCategory::Core, "Unit Tests Completed Successfully.");
|
||||
}
|
||||
}
|
||||
} // namespace Juliet
|
||||
|
||||
#endif
|
||||
0
current_run.log
Normal file
0
current_run.log
Normal file
15
test.txt
Normal file
15
test.txt
Normal file
@@ -0,0 +1,15 @@
|
||||
--- Launching JulietApp.exe ---
|
||||
Platform: x64Clang
|
||||
Config: Debug
|
||||
Running Paged Memory Arena Tests...
|
||||
[2026-02-08 02:56:49.1217020] Allocating from W:\Classified\Juliet\Juliet\src\Core\Memory\MemoryArenaTests.cpp : 23l
|
||||
[2026-02-08 02:56:49.1220553] Allocating from W:\Classified\Juliet\Juliet\src\Core\Memory\MemoryArena.cpp : 99l
|
||||
[Success] Arena Pop
|
||||
All Paged MemoryArena tests passed.
|
||||
[2026-02-08 02:56:49.1319769] Starting Unit Tests...
|
||||
[2026-02-08 02:56:49.1320761] Allocating from Juliet/include\Core/Container/Vector.h : 19l
|
||||
[2026-02-08 02:56:49.1321474] --- ASSERTION FAILED ---
|
||||
[2026-02-08 02:56:49.1321999] Expression: vec[0] == 30
|
||||
[2026-02-08 02:56:49.1322519] Message: No additional information provided.
|
||||
[2026-02-08 02:56:49.1323083] Location: W:\Classified\Juliet\Juliet\src\UnitTest\Container\VectorUnitTest.cpp(45): void __cdecl Juliet::VectorUnitTest(void)
|
||||
[2026-02-08 02:56:49.1323588] -------------------------
|
||||
Reference in New Issue
Block a user