Skip to content

Commit

Permalink
Add GpuApi (#164)
Browse files Browse the repository at this point in the history
* Add GpuApi

* Fix Clang Formatting

* Remove whitespace

* Added CommandListContext src file and `GetFreeCommandList`

* Fix accidental build error

* Fix another accidental build error

* Add missing include in CommandListContext.hpp

* Clang

* Recreate D3D12MemAlloc

Recreated parts of the D3D12MemAlloc library as it was used in Cyberpunk, as well as some small fixes

* Fix formatting and some mistakes

* Formatting

* Formatting

* Whitespace

* Fix CreateResource

* Several updates

- Made `ResourceContainer` with templating
- Adjusted struct fields
- Adjusted several function arguments

* Formatting

* Formatting

* Several Updates

- Added vendor directory
- Included D3D12MA lib header
- Removed manual D3D12MA recreation
- UPDATED CMakeLists.text
- Adjusted ResourceContainer
- Adjusted SDeviceDataBase offsets

* Disable Clang for D3D12MemAlloc, Formatting

* Remove whitespace

* Update CMakeLists.txt

Co-authored-by: Octavian Dima <[email protected]>

* Update CMakeLists.txt

Co-authored-by: Octavian Dima <[email protected]>

* Fix some includes and struct offsets

* Formatting

* Add THIRD_PARTY_LICENSE.md

* Rename and adjust THIRD_PARTY_LICENSE

* Add `Close` method for CommandListContext

* Improve semantics

* Fix mistake

* Formatting

* Update THIRD_PARTY_LICENSES.md

Co-authored-by: Octavian Dima <[email protected]>

* Undo `D3D12MemAlloc.h`  changes & Improve semantics

* Fix typo

* Ignore *all* files in `vendor/`

* Fixes

- Added offset comments to SBufferData
- Added missing includes for Common.hpp
- Fixed typos
- Suffer clang formatting

* Clang

* Clang is the sound of my head against my PC

* Fix typos

Co-authored-by: Octavian Dima <[email protected]>

* Update include/RED4ext/GpuApi/Buffer.hpp

Co-authored-by: Octavian Dima <[email protected]>

* Remove whitespace

Co-authored-by: Octavian Dima <[email protected]>

* Remove more whitespace

Co-authored-by: Octavian Dima <[email protected]>

---------

Co-authored-by: Octavian Dima <[email protected]>
  • Loading branch information
Mozz3d and wopss authored Jan 11, 2025
1 parent 5a76fb7 commit 929c8e0
Show file tree
Hide file tree
Showing 13 changed files with 2,268 additions and 0 deletions.
3 changes: 3 additions & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ cmake_dependent_option(RED4EXT_USE_PCH "Use precompiled headers to speed up comp

set(RED4EXT_CMAKE_DIR "${PROJECT_SOURCE_DIR}/cmake")
set(RED4EXT_INCLUDE_DIR "${PROJECT_SOURCE_DIR}/include/")
set(RED4EXT_VENDOR_DIR "${PROJECT_SOURCE_DIR}/vendor/")

# -----------------------------------------------------------------------------
# Options related to warnings
Expand Down Expand Up @@ -67,6 +68,7 @@ if(RED4EXT_HEADER_ONLY)
RED4ext.SDK
INTERFACE
"$<BUILD_INTERFACE:${RED4EXT_INCLUDE_DIR}>"
"$<BUILD_INTERFACE:${RED4EXT_VENDOR_DIR}/D3D12MemAlloc>"
"$<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}>"
)
else()
Expand Down Expand Up @@ -99,6 +101,7 @@ else()
RED4ext.SDK
PUBLIC
"$<BUILD_INTERFACE:${RED4EXT_INCLUDE_DIR}>"
"$<BUILD_INTERFACE:${RED4EXT_VENDOR_DIR}/D3D12MemAlloc>"
"$<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}>"
)

Expand Down
16 changes: 16 additions & 0 deletions THIRD_PARTY_LICENSES.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
================ GPUOpen-LibrariesAndSDKs/D3D12MemoryAllocator ================

Copyright (c) 2019-2025 Advanced Micro Devices, Inc. All rights reserved.

Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation
files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,
modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the
Software is furnished to do so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in all copies or substantial portions of the
Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
15 changes: 15 additions & 0 deletions include/RED4ext/Detail/AddressHashes.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,13 @@ constexpr std::uint32_t CNamePool_AddPair = 0xD9840BD8;
constexpr std::uint32_t CNamePool_Get = 0x68DF07DC;
#pragma endregion

#pragma region CommandListContext
constexpr std::uint32_t GetFreeCommandList = 1926836641UL;
constexpr std::uint32_t CommandListContext_AddPendingBarrier = 2814122829UL;
constexpr std::uint32_t CommandListContext_Close = 1163138096UL;
constexpr std::uint32_t CommandListContext_FlushPendingBarriers = 2786924000UL;
#pragma endregion

#pragma region CRTTIRegistrator
constexpr std::uint32_t CRTTIRegistrator_RTTIAsyncId = 0xDDBD19E8;
#pragma endregion
Expand All @@ -101,10 +108,18 @@ constexpr std::uint32_t CString_copy = 0xE8B40B51;
constexpr std::uint32_t CString_dtor = 0x5405072C;
#pragma endregion

#pragma region DeviceData
constexpr std::uint32_t g_DeviceData = 1239944840UL;
#pragma endregion

#pragma region DynArray
constexpr std::uint32_t DynArray_Realloc = 0x7AA013D2;
#pragma endregion

#pragma region D3D12MA
constexpr std::uint32_t Allocator_CreateResource = 2508272872UL;
#pragma endregion

#pragma region Handle
constexpr std::uint32_t Handle_ctor = 0xBA0C115D;
constexpr std::uint32_t Handle_DecWeakRef = 0x333B1404;
Expand Down
21 changes: 21 additions & 0 deletions include/RED4ext/GpuApi/Buffer.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@

#include <REd4ext/Common.hpp>
#include <d3d12.h>
#include <wrl/client.h>

namespace RED4ext
{
namespace GpuApi
{
struct SBufferData
{
uint32_t bufferSize; // 00
uint8_t unk04[0x10 - 0x04]; // 04
Microsoft::WRL::ComPtr<ID3D12Resource> bufferResource; // 10
void* unk18; // 18
uint8_t unk20[0xa8 - 0x20]; // 20
};
RED4EXT_ASSERT_SIZE(SBufferData, 0xa8);
RED4EXT_ASSERT_OFFSET(SBufferData, bufferResource, 0xa8);
} // namespace GpuApi
} // namespace RED4ext
28 changes: 28 additions & 0 deletions include/RED4ext/GpuApi/CommandListContext-inl.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
#pragma once

#ifdef RED4EXT_STATIC_LIB
#include <RED4ext/GpuApi/CommandListContext.hpp>
#endif

#include <RED4ext/Relocation.hpp>

RED4EXT_INLINE void RED4ext::GpuApi::CommandListContext::AddPendingBarrier(const D3D12_RESOURCE_BARRIER& aBarrier)
{
using func_t = void (*)(CommandListContext*, const D3D12_RESOURCE_BARRIER&);
static UniversalRelocFunc<func_t> func(Detail::AddressHashes::CommandListContext_AddPendingBarrier);
func(this, aBarrier);
}

RED4EXT_INLINE void RED4ext::GpuApi::CommandListContext::Close()
{
using func_t = void (*)(CommandListContext*);
static UniversalRelocFunc<func_t> func(Detail::AddressHashes::CommandListContext_Close);
func(this);
}

RED4EXT_INLINE void RED4ext::GpuApi::CommandListContext::FlushPendingBarriers()
{
using func_t = void (*)(CommandListContext*);
static UniversalRelocFunc<func_t> func(Detail::AddressHashes::CommandListContext_FlushPendingBarriers);
func(this);
}
61 changes: 61 additions & 0 deletions include/RED4ext/GpuApi/CommandListContext.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
#pragma once

#include <RED4ext/DynArray.hpp>
#include <REd4ext/CString.hpp>
#include <REd4ext/Common.hpp>
#include <d3d12.h>
#include <wrl/client.h>

namespace RED4ext
{
namespace GpuApi
{
enum class CommandListType
{
Invalid,
Default,
CopySync,
CopyAsync,
Compute,
MAX
};

struct CommandListContext
{
void AddPendingBarrier(const D3D12_RESOURCE_BARRIER& aBarrier);
void Close();
void FlushPendingBarriers();

CString debugName; // 00
uint64_t hash; // 20
Microsoft::WRL::ComPtr<ID3D12CommandAllocator> commandAllocator; // 28
Microsoft::WRL::ComPtr<ID3D12GraphicsCommandList> commandList; // 30
uint8_t unk38[0x68 - 0x38]; // 48
CommandListType type; // 68
uint8_t unk6c[0x528 - 0x6c]; // 6C
DynArray<D3D12_RESOURCE_BARRIER> pendingBarriers; // 528
uint8_t unk538[0x650 - 0x538]; // 538
};
RED4EXT_ASSERT_SIZE(CommandListContext, 0x650);
RED4EXT_ASSERT_OFFSET(CommandListContext, commandAllocator, 0x28);
RED4EXT_ASSERT_OFFSET(CommandListContext, commandList, 0x30);
RED4EXT_ASSERT_OFFSET(CommandListContext, type, 0x68);
RED4EXT_ASSERT_OFFSET(CommandListContext, pendingBarriers, 0x528);

RED4EXT_INLINE CommandListContext* GetFreeCommandList(CommandListType aType)
{
// NOTE: this function has parameters for hash and name but they appear unused.
using func_t = CommandListContext** (*)(CommandListContext**, CommandListType, const char*, uint64_t);
static UniversalRelocFunc<func_t> func(Detail::AddressHashes::GetFreeCommandList);

CommandListContext* outContext;
func(&outContext, aType, "", 0);
return outContext;
}

} // namespace GpuApi
} // namespace RED4ext

#ifdef RED4EXT_HEADER_ONLY
#include <RED4ext/GpuApi/CommandListContext-inl.hpp>
#endif
22 changes: 22 additions & 0 deletions include/RED4ext/GpuApi/D3D12MemAlloc-inl.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
#pragma once

#ifdef RED4EXT_STATIC_LIB
#include <D3D12MemAlloc.h>
#endif

#include <RED4ext/Detail/AddressHashes.hpp>
#include <RED4ext/Relocation.hpp>

RED4EXT_INLINE HRESULT D3D12MA::Allocator::CreateResource(const ALLOCATION_DESC* pAllocDesc,
const D3D12_RESOURCE_DESC* pResourceDesc,
D3D12_RESOURCE_STATES InitialResourceState,
const D3D12_CLEAR_VALUE* pOptimizedClearValue,
Allocation** ppAllocation, REFIID riidResource,
void** ppvResource)
{
using func_t = HRESULT (*)(Allocator*, const ALLOCATION_DESC*, const D3D12_RESOURCE_DESC*, D3D12_RESOURCE_STATES,
const D3D12_CLEAR_VALUE*, Allocation**, REFIID, void**);
static RED4ext::UniversalRelocFunc<func_t> func(RED4ext::Detail::AddressHashes::Allocator_CreateResource);
return func(this, pAllocDesc, pResourceDesc, InitialResourceState, pOptimizedClearValue, ppAllocation, riidResource,
ppvResource);
}
5 changes: 5 additions & 0 deletions include/RED4ext/GpuApi/D3D12MemAlloc.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
#include <D3D12MemAlloc.h>

#ifdef RED4EXT_HEADER_ONLY
#include <RED4ext/GpuApi/D3D12MemAlloc-inl.hpp>
#endif
61 changes: 61 additions & 0 deletions include/RED4ext/GpuApi/DeviceData.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
#pragma once

#include <RED4ext/GpuApi/Buffer.hpp>
#include <RED4ext/GpuApi/CommandListContext.hpp>
#include <RED4ext/GpuApi/D3D12MemAlloc.hpp>
#include <REd4ext/Common.hpp>

namespace RED4ext
{
namespace GpuApi
{
template<typename T, size_t MAX_SIZE>
struct ResourceContainer
{
struct Resource
{
int32_t refCount;
T instance;
};

void* mutex; // 00 - spin lock?
int32_t defaultNumUnused; // 08 - defaults to MaxSize
Resource resources[MAX_SIZE];
uint16_t unusedIndices[MAX_SIZE];
};

struct SDeviceDataBase
{
uint8_t unk00[0x5c0ae0 - 0x00]; // 00
ResourceContainer<SBufferData, 32768> buffers; // 5C0AE0
uint8_t unkb40af8[0xd1ad80 - 0xb50af0]; // B50AF0
ResourceContainer<CommandListContext*, 128> commandLists; // D1AD80 - Uses unknown ptr wrapper
uint8_t unkd1b598[0x13bc240 - 0xd1b690]; // D1B690
};
RED4EXT_ASSERT_SIZE(SDeviceDataBase, 0x13bc240);
RED4EXT_ASSRT_OFFSET(SDeviceDataBase, buffers, 0x5C0AE0);
RED4EXT_ASSRT_OFFSET(SDeviceDataBase, commandLists, 0xD1AD80);

struct SDeviceData : SDeviceDataBase
{
uint8_t unk13bc240[0x13bc4a8 - 0x13bc240]; // 13BC240
Microsoft::WRL::ComPtr<ID3D12Device> device; // 13BC4A8
uint8_t unk13bc4b0[0x13bc4d0 - 0x13bc4b0]; // 13BC4B0
Microsoft::WRL::ComPtr<ID3D12CommandQueue> directCommandQueue; // 13BC4D0
Microsoft::WRL::ComPtr<ID3D12CommandQueue> computeCommandQueue; // 13BC4D8
uint8_t unk13bc4e0[0x13bc540 - 0x13bc4e0]; // 13BC4E0
Microsoft::WRL::ComPtr<D3D12MA::Allocator> memoryAllocator; // 13BC540
uint8_t unk13bc4b8[0x1a8f880 - 0x13bc548]; // 13BC548
};
RED4EXT_ASSERT_SIZE(SDeviceData, 0x1a8f880);
RED4EXT_ASSRT_OFFSET(SDeviceData, device, 0x13BC4A8);
RED4EXT_ASSRT_OFFSET(SDeviceData, directCommandQueue, 0x13BC4D0);
RED4EXT_ASSRT_OFFSET(SDeviceData, memoryAllocator, 0x13BC540);

RED4EXT_INLINE SDeviceData& GetDeviceData()
{
static UniversalRelocPtr<SDeviceData*> dd(Detail::AddressHashes::g_DeviceData);
return *dd;
}
} // namespace GpuApi
} // namespace RED4ext
5 changes: 5 additions & 0 deletions src/GpuApi/CommandListContext.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
#ifndef RED4EXT_STATIC_LIB
#error Please define 'RED4EXT_STATIC_LIB' to compile this file.
#endif

#include <RED4ext/GpuApi/CommandListContext-inl.hpp>
5 changes: 5 additions & 0 deletions src/GpuApi/D3D12MemAlloc.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
#ifndef RED4EXT_STATIC_LIB
#error Please define 'RED4EXT_STATIC_LIB' to compile this file.
#endif

#include <RED4ext/GpuApi/D3D12MemAlloc-inl.hpp>
1 change: 1 addition & 0 deletions vendor/.clang-format
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
DisableFormat: true
Loading

0 comments on commit 929c8e0

Please sign in to comment.