Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
39 commits
Select commit Hold shift + click to select a range
6ae1030
Remove Permissions... template argument from Template and eliminate
xthexder Oct 25, 2024
d02d255
Add c abi headers and code-gen implementation (WIP)
xthexder Oct 20, 2024
8baf54b
Fix transaction id test race condition
xthexder Oct 20, 2024
f8d9a9a
Add TecsEntityView and start C++ wrapper APIs
xthexder Oct 21, 2024
f8d5f81
Build benchmark against c abi to test perf
xthexder Oct 25, 2024
c257bf8
Add tracing support to c abi and improve performance
xthexder Oct 26, 2024
610993d
Add direct storage access optimization to c abi
xthexder Oct 27, 2024
4c6ea14
Cleanup, and fix strcpy_s
xthexder Oct 27, 2024
032fe4c
Fix master rebase
xthexder Jan 31, 2025
dd41a75
Check types for being trivially copyable if sending over c abi
xthexder Feb 9, 2025
b9ea56d
Properly export c abi to shared DLL
xthexder May 14, 2025
30e255b
Implement TecsGenerateCHeaders() CMake function
xthexder May 15, 2025
5d284f5
Fix linux build issues
xthexder May 16, 2025
27bec6e
Merge branch 'master' into c_abi
xthexder May 17, 2025
b42adc7
Add SOURCES option to cmake codegen
xthexder May 18, 2025
84f0694
Reorder entity fields to match existing bit manipulation
xthexder May 21, 2025
9a25c1d
Fix warnings
xthexder May 30, 2025
8a21f63
Fix size_t include
xthexder May 30, 2025
73794f6
Fix linux build
xthexder May 30, 2025
de824bc
Codegen component accessors
xthexder May 31, 2025
c0f5ae3
Change TryLock to return DynamicLock
xthexder Jun 1, 2025
a157fa8
Adjust cmake dependencies
xthexder Jun 2, 2025
212ba6b
Try and fix dependencies
xthexder Jun 2, 2025
feae617
Add helper for checking lock types
xthexder Jun 2, 2025
5a2a06f
Fix Tecs_entity_get not tracking entity writes
xthexder Jun 8, 2025
5c85849
Adjust codegen output dir
xthexder Jun 8, 2025
a9041d5
Include fix
xthexder Jul 5, 2025
39fe727
Merge branch 'master' into c_abi
xthexder Jul 19, 2025
c1c59f1
Fix unused variable
xthexder Jul 19, 2025
79848d6
Slight optimizations for observer commit
xthexder Jul 20, 2025
fe2ab5b
Fix TypeToString on MSVC 2019
xthexder Aug 25, 2025
5459e28
Fix template compile error on MSVC 2019 and update Tracy
xthexder Aug 25, 2025
d058993
Fix missing include in c_abi
xthexder Aug 25, 2025
d749b47
Update Clang-format, fix warnings
xthexder Aug 25, 2025
3623a3b
Merge branch 'master' into c_abi
xthexder Aug 25, 2025
45420de
Change Modified events to include add/remove actions
xthexder Dec 1, 2025
4e6c5cd
Fix bool usage for C23
xthexder Dec 20, 2025
9025a16
Fix includes
xthexder Feb 1, 2026
0d51d31
Convert size_t usage to uint32 or uint64
xthexder Feb 8, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1 +1,2 @@
/.cache
/build
33 changes: 33 additions & 0 deletions .vscode/launch.json
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,39 @@
"environment": [],
"console": "integratedTerminal"
},
{
"name": "Launch Benchmark C-ABI (Windows)",
"type": "cppvsdbg",
"request": "launch",
"program": "${workspaceFolder}/build/tests/Tecs-benchmark-cabi.exe",
"args": [],
"stopAtEntry": false,
"cwd": "${workspaceFolder}/build/tests/",
"environment": [],
"console": "integratedTerminal"
},
{
"name": "Launch Benchmark Tracy C-ABI (Windows)",
"type": "cppvsdbg",
"request": "launch",
"program": "${workspaceFolder}/build/tests/Tecs-benchmark-tracy-cabi.exe",
"args": [],
"stopAtEntry": false,
"cwd": "${workspaceFolder}/build/tests/",
"environment": [],
"console": "integratedTerminal"
},
{
"name": "Launch C-ABI Tests (Windows)",
"type": "cppvsdbg",
"request": "launch",
"program": "${workspaceFolder}/build/tests/Tecs-c_abi_test.exe",
"args": [],
"stopAtEntry": false,
"cwd": "${workspaceFolder}/build/tests/",
"environment": [],
"console": "integratedTerminal"
},
{
"name": "Launch Tests (Linux)",
"type": "cppdbg",
Expand Down
2 changes: 2 additions & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,8 @@ if(TECS_UNCHECKED_MODE)
target_compile_definitions(${PROJECT_NAME} INTERFACE TECS_UNCHECKED_MODE)
endif()

include(gen_c_abi.cmake)

if(UNIX AND NOT ANDROID)
target_link_libraries(
${PROJECT_NAME}
Expand Down
5 changes: 1 addition & 4 deletions examples/tracing_example.cpp
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
#include "complex_component.hh"
#include "components.hh"

#include <fstream>
#include <iostream>
#include <vector>

Expand Down Expand Up @@ -124,9 +123,7 @@ int main(int /* argc */, char ** /* argv */) {
for (auto &[id, name] : threadNames) {
trace.SetThreadName(name, id);
}
std::ofstream traceFile("example-trace.csv");
trace.SaveToCSV(traceFile);
traceFile.close();
trace.SaveToCSV("example-trace.csv");

return 0;
}
103 changes: 103 additions & 0 deletions gen_c_abi.cmake
Original file line number Diff line number Diff line change
@@ -0,0 +1,103 @@
function(TecsGenerateCHeaders)
set(options OBJECT_TARGET)
set(oneValueArgs TARGET_NAME ECS_INCLUDE_PATH ECS_C_INCLUDE_PATH ECS_NAME COMPONENT_TYPE_PREFIX)
set(multiValueArgs SOURCES LINK_LIBRARIES INCLUDE_DIRECTORIES COMPILE_DEFINITIONS)
cmake_parse_arguments(PARSE_ARGV 0 arg "${options}" "${oneValueArgs}" "${multiValueArgs}")

include(CheckIPOSupported)
check_ipo_supported(RESULT lto_supported OUTPUT lto_error)

set(TECS_PROJECT_ROOT ${CMAKE_CURRENT_FUNCTION_LIST_DIR})

add_executable(${arg_TARGET_NAME}-codegen ${TECS_PROJECT_ROOT}/src/c_abi/codegen/gen_main.cc)
target_link_libraries(${arg_TARGET_NAME}-codegen PRIVATE ${arg_LINK_LIBRARIES})
target_include_directories(
${arg_TARGET_NAME}-codegen
PRIVATE
${TECS_PROJECT_ROOT}/inc
${arg_INCLUDE_DIRECTORIES}
)
target_compile_definitions(${arg_TARGET_NAME}-codegen PRIVATE
TECS_C_ABI_ECS_NAME=${arg_ECS_NAME}
TECS_C_ABI_TYPE_PREFIX="${arg_COMPONENT_TYPE_PREFIX}"
TECS_SHARED_INTERNAL
${arg_COMPILE_DEFINITIONS}
)
set_target_properties(${arg_TARGET_NAME}-codegen PROPERTIES
RUNTIME_OUTPUT_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}
)

if(DEFINED arg_ECS_INCLUDE_PATH)
target_compile_definitions(${arg_TARGET_NAME}-codegen PRIVATE
TECS_C_ABI_ECS_INCLUDE="${arg_ECS_INCLUDE_PATH}"
)
endif()

if(DEFINED arg_ECS_C_INCLUDE_PATH)
target_compile_definitions(${arg_TARGET_NAME}-codegen PRIVATE
TECS_C_ABI_ECS_C_INCLUDE="${arg_ECS_C_INCLUDE_PATH}"
)
endif()

string(REPLACE "-" "_" OUTPUT_PREFIX_NAME ${arg_TARGET_NAME})

add_custom_command(
OUTPUT
${CMAKE_CURRENT_BINARY_DIR}/include/c_abi/${OUTPUT_PREFIX_NAME}_lock_gen.h
${CMAKE_CURRENT_BINARY_DIR}/include/c_abi/${OUTPUT_PREFIX_NAME}_entity_gen.h
${CMAKE_CURRENT_BINARY_DIR}/${OUTPUT_PREFIX_NAME}_ecs_gen.cc
${CMAKE_CURRENT_BINARY_DIR}/${OUTPUT_PREFIX_NAME}_entity_gen.cc
${CMAKE_CURRENT_BINARY_DIR}/${OUTPUT_PREFIX_NAME}_lock_gen.cc
COMMAND
${arg_TARGET_NAME}-codegen
${CMAKE_CURRENT_BINARY_DIR}/include/c_abi/${OUTPUT_PREFIX_NAME}_lock_gen.h
${CMAKE_CURRENT_BINARY_DIR}/include/c_abi/${OUTPUT_PREFIX_NAME}_entity_gen.h
${CMAKE_CURRENT_BINARY_DIR}/${OUTPUT_PREFIX_NAME}_ecs_gen.cc
${CMAKE_CURRENT_BINARY_DIR}/${OUTPUT_PREFIX_NAME}_entity_gen.cc
${CMAKE_CURRENT_BINARY_DIR}/${OUTPUT_PREFIX_NAME}_lock_gen.cc
DEPENDS ${arg_TARGET_NAME}-codegen
)

add_custom_target(${arg_TARGET_NAME}-codegen-output
DEPENDS
${CMAKE_CURRENT_BINARY_DIR}/include/c_abi/${OUTPUT_PREFIX_NAME}_lock_gen.h
${CMAKE_CURRENT_BINARY_DIR}/include/c_abi/${OUTPUT_PREFIX_NAME}_entity_gen.h
${CMAKE_CURRENT_BINARY_DIR}/${OUTPUT_PREFIX_NAME}_ecs_gen.cc
${CMAKE_CURRENT_BINARY_DIR}/${OUTPUT_PREFIX_NAME}_entity_gen.cc
${CMAKE_CURRENT_BINARY_DIR}/${OUTPUT_PREFIX_NAME}_lock_gen.cc
)

set(BUILD_FILE_LIST
${TECS_PROJECT_ROOT}/src/c_abi/Tecs_entity_view.cc
${TECS_PROJECT_ROOT}/src/c_abi/Tecs_tracing.cc
${CMAKE_CURRENT_BINARY_DIR}/${OUTPUT_PREFIX_NAME}_ecs_gen.cc
${CMAKE_CURRENT_BINARY_DIR}/${OUTPUT_PREFIX_NAME}_entity_gen.cc
${CMAKE_CURRENT_BINARY_DIR}/${OUTPUT_PREFIX_NAME}_lock_gen.cc
${arg_SOURCES}
)

if(arg_OBJECT_TARGET)
add_library(${arg_TARGET_NAME} OBJECT ${BUILD_FILE_LIST})
else()
add_library(${arg_TARGET_NAME} SHARED ${BUILD_FILE_LIST})
endif()
target_link_libraries(${arg_TARGET_NAME} PRIVATE Tecs ${arg_LINK_LIBRARIES})
target_include_directories(
${arg_TARGET_NAME}
PUBLIC
${TECS_PROJECT_ROOT}/inc
${CMAKE_CURRENT_BINARY_DIR}/include
PRIVATE
${arg_INCLUDE_DIRECTORIES}
)
add_dependencies(${arg_TARGET_NAME} ${arg_TARGET_NAME}-codegen-output)
target_compile_definitions(${arg_TARGET_NAME} PRIVATE TECS_SHARED_INTERNAL ${arg_COMPILE_DEFINITIONS})
if(lto_supported)
if(NOT CMAKE_BUILD_TYPE STREQUAL "Debug")
message(STATUS "IPO / LTO enabled")
set_target_properties(${arg_TARGET_NAME} PROPERTIES INTERPROCEDURAL_OPTIMIZATION TRUE)
endif()
else()
message(STATUS "IPO / LTO not supported: ${lto_error}")
endif()
endfunction()
39 changes: 30 additions & 9 deletions inc/Tecs.hh
Original file line number Diff line number Diff line change
Expand Up @@ -80,18 +80,22 @@ namespace Tecs {
return (TECS_ENTITY_ECS_IDENTIFIER_TYPE)ecsId;
}

inline uint64_t GetNextTransactionId() const {
return nextTransactionId;
}

/**
* Returns the index of a Component type for use in a bitset.
*/
template<typename U>
inline static constexpr size_t GetComponentIndex() {
inline static constexpr uint32_t GetComponentIndex() {
return GetComponentIndex<0, U>();
}

/**
* Returns the number of Component types registered in this ECS instance.
*/
inline static constexpr size_t GetComponentCount() {
inline static constexpr uint32_t GetComponentCount() {
return sizeof...(Tn);
}

Expand All @@ -107,6 +111,13 @@ namespace Tecs {
}
}

/**
* Returns the registered name of the Nth Component type, or a default of "ComponentN" if none is set.
*/
inline static std::string GetComponentName(uint32_t componentIndex) {
return GetComponentName<Tn...>(componentIndex);
}

/**
* Returns true if the Component type is part of this ECS.
*/
Expand All @@ -120,17 +131,29 @@ namespace Tecs {
}

private:
template<size_t I, typename U>
inline static constexpr size_t GetComponentIndex() {
template<uint32_t I, typename U>
inline static constexpr uint32_t GetComponentIndex() {
static_assert(I < sizeof...(Tn), "Component does not exist");

if constexpr (std::is_same<U, typename std::tuple_element<I, std::tuple<Tn...>>::type>::value) {
if constexpr (std::is_same<U, typename std::tuple_element_t<I, std::tuple<Tn...>>>()) {
return I;
} else {
return GetComponentIndex<I + 1, U>();
}
}

template<typename U, typename... Un>
inline static std::string GetComponentName(uint32_t index) {
if (index == 0) {
return GetComponentName<U>();
}
if constexpr (sizeof...(Un) > 0) {
return GetComponentName<Un...>(index - 1);
} else {
throw std::runtime_error("Component does not exist");
}
}

using ComponentBitset = std::bitset<1 + sizeof...(Tn)>;

struct EntityMetadata : public ComponentBitset {
Expand Down Expand Up @@ -162,15 +185,13 @@ namespace Tecs {
#endif

#ifndef TECS_HEADER_ONLY
size_t ecsId;
uint64_t ecsId;
#endif

template<typename, typename...>
friend class Lock;
template<typename, typename...>
template<typename>
friend class Transaction;
template<template<typename...> typename, typename...>
friend class BaseTransaction;
friend struct Entity;
};
} // namespace Tecs
Loading