Skip to content

Commit de316c9

Browse files
authored
Merge pull request #28 from qudix/dev/misc
feat: misc
2 parents 07d8f5d + 9dbb466 commit de316c9

10 files changed

Lines changed: 226 additions & 15 deletions

File tree

CommonLibF4/cmake/sourcelist.cmake

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -216,6 +216,7 @@ set(SOURCES
216216
include/RE/Bethesda/Settings.h
217217
include/RE/Bethesda/Sky.h
218218
include/RE/Bethesda/SplineUtils.h
219+
include/RE/Bethesda/TaskQueueInterface.h
219220
include/RE/Bethesda/TESBoundAnimObjects.h
220221
include/RE/Bethesda/TESBoundObjects.h
221222
include/RE/Bethesda/TESCamera.h
@@ -230,7 +231,7 @@ set(SOURCES
230231
include/RE/Bethesda/TESRace.h
231232
include/RE/Bethesda/TESWaterForm.h
232233
include/RE/Bethesda/TESWorldSpace.h
233-
include/RE/Bethesda/TaskQueueInterface.h
234+
include/RE/Bethesda/TLS.h
234235
include/RE/Bethesda/UI.h
235236
include/RE/Bethesda/UIMessage.h
236237
include/RE/Bethesda/UIMessageQueue.h
@@ -390,6 +391,7 @@ set(SOURCES
390391
include/REX/W32/DXGI_5.h
391392
include/REX/W32/DXGI_6.h
392393
include/REX/W32/KERNEL32.h
394+
include/REX/W32/NT.h
393395
include/REX/W32/OLE32.h
394396
include/REX/W32/SHELL32.h
395397
include/REX/W32/USER32.h

CommonLibF4/include/RE/Bethesda/TESCondition.h

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -80,11 +80,18 @@ namespace RE
8080

8181
[[nodiscard]] bool IsTrue(TESObjectREFR* a_actionRef, TESObjectREFR* a_targetRef)
8282
{
83-
using func_t = decltype(&TESConditionItem::IsTrue);
83+
using func_t = bool(*)(TESConditionItem*, TESObjectREFR*, TESObjectREFR*);
8484
static REL::Relocation<func_t> func{ REL::ID(2212008) };
8585
return func(this, a_actionRef, a_targetRef);
8686
}
8787

88+
[[nodiscard]] bool IsTrue(ConditionCheckParams& a_params)
89+
{
90+
using func_t = bool(*)(TESConditionItem*, ConditionCheckParams&);
91+
static REL::Relocation<func_t> func{ REL::ID(2212009) };
92+
return func(this, a_params);
93+
}
94+
8895
// members
8996
TESConditionItem* next; // 00
9097
CONDITION_ITEM_DATA data; // 08
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
#pragma once
2+
3+
#include "REX/W32/NT.h"
4+
5+
namespace RE
6+
{
7+
struct TLS
8+
{
9+
[[nodiscard]] static TLS* GetSingleton()
10+
{
11+
return *static_cast<TLS**>(REX::W32::NtCurrentTeb()->threadLocalStoragePointer);
12+
}
13+
14+
// members
15+
std::byte pad000[0x830]; // 000
16+
bool consoleMode; // 830
17+
};
18+
}

CommonLibF4/include/RE/Fallout.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -211,6 +211,7 @@
211211
#include "RE/Bethesda/Settings.h"
212212
#include "RE/Bethesda/Sky.h"
213213
#include "RE/Bethesda/SplineUtils.h"
214+
#include "RE/Bethesda/TaskQueueInterface.h"
214215
#include "RE/Bethesda/TESBoundAnimObjects.h"
215216
#include "RE/Bethesda/TESBoundObjects.h"
216217
#include "RE/Bethesda/TESCamera.h"
@@ -225,7 +226,7 @@
225226
#include "RE/Bethesda/TESRace.h"
226227
#include "RE/Bethesda/TESWaterForm.h"
227228
#include "RE/Bethesda/TESWorldSpace.h"
228-
#include "RE/Bethesda/TaskQueueInterface.h"
229+
#include "RE/Bethesda/TLS.h"
229230
#include "RE/Bethesda/UI.h"
230231
#include "RE/Bethesda/UIMessage.h"
231232
#include "RE/Bethesda/UIMessageQueue.h"

CommonLibF4/include/REL/Relocation.h

Lines changed: 16 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -300,28 +300,32 @@ namespace REL
300300
safe_write(address(), a_data.data(), a_data.size_bytes());
301301
}
302302

303-
template <std::size_t N>
304-
std::uintptr_t write_branch(const std::uintptr_t a_dst) requires(std::same_as<value_type, std::uintptr_t>)
303+
template <std::size_t N, std::ptrdiff_t O = 0>
304+
std::uintptr_t write_branch(const std::uintptr_t a_dst)
305+
requires(std::same_as<value_type, std::uintptr_t>)
305306
{
306-
return F4SE::GetTrampoline().write_branch<N>(address(), a_dst);
307+
return F4SE::GetTrampoline().write_branch<N>(address() + O, a_dst);
307308
}
308309

309-
template <std::size_t N, class F>
310-
std::uintptr_t write_branch(const F a_dst) requires(std::same_as<value_type, std::uintptr_t>)
310+
template <std::size_t N, std::ptrdiff_t O = 0, class F>
311+
std::uintptr_t write_branch(const F a_dst)
312+
requires(std::same_as<value_type, std::uintptr_t>)
311313
{
312-
return F4SE::GetTrampoline().write_branch<N>(address(), stl::unrestricted_cast<std::uintptr_t>(a_dst));
314+
return F4SE::GetTrampoline().write_branch<N>(address() + O, stl::unrestricted_cast<std::uintptr_t>(a_dst));
313315
}
314316

315-
template <std::size_t N>
316-
std::uintptr_t write_call(const std::uintptr_t a_dst) requires(std::same_as<value_type, std::uintptr_t>)
317+
template <std::size_t N, std::ptrdiff_t O = 0>
318+
std::uintptr_t write_call(const std::uintptr_t a_dst)
319+
requires(std::same_as<value_type, std::uintptr_t>)
317320
{
318-
return F4SE::GetTrampoline().write_call<N>(address(), a_dst);
321+
return F4SE::GetTrampoline().write_call<N>(address() + O , a_dst);
319322
}
320323

321-
template <std::size_t N, class F>
322-
std::uintptr_t write_call(const F a_dst) requires(std::same_as<value_type, std::uintptr_t>)
324+
template <std::size_t N, std::ptrdiff_t O = 0, class F>
325+
std::uintptr_t write_call(const F a_dst)
326+
requires(std::same_as<value_type, std::uintptr_t>)
323327
{
324-
return F4SE::GetTrampoline().write_call<N>(address(), stl::unrestricted_cast<std::uintptr_t>(a_dst));
328+
return F4SE::GetTrampoline().write_call<N>(address() + O, stl::unrestricted_cast<std::uintptr_t>(a_dst));
325329
}
326330

327331
void write_fill(const std::uint8_t a_value, const std::size_t a_count) requires(std::same_as<value_type, std::uintptr_t>)

CommonLibF4/include/REX/REX.h

Lines changed: 65 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,70 @@
11
#pragma once
22

3+
namespace REX
4+
{
5+
template <
6+
class E,
7+
class U = std::underlying_type_t<E>>
8+
class Enum
9+
{
10+
public:
11+
using enum_type = E;
12+
using underlying_type = U;
13+
14+
static_assert(std::is_enum_v<E>, "Enum<E, ...> must be an enum");
15+
static_assert(std::is_integral_v<U>, "Enum<..., U> must be an integral");
16+
17+
constexpr Enum() noexcept = default;
18+
constexpr Enum(const Enum&) noexcept = default;
19+
constexpr Enum(Enum&&) noexcept = default;
20+
21+
template <class U2> // NOLINTNEXTLINE(google-explicit-constructor)
22+
constexpr Enum(Enum<E, U2> a_rhs) noexcept :
23+
_impl(static_cast<U>(a_rhs.get()))
24+
{}
25+
26+
constexpr Enum(E a_value) noexcept :
27+
_impl(static_cast<U>(a_value))
28+
{}
29+
30+
~Enum() noexcept = default;
31+
32+
constexpr Enum& operator=(const Enum&) noexcept = default;
33+
constexpr Enum& operator=(Enum&&) noexcept = default;
34+
35+
template <class U2>
36+
constexpr Enum& operator=(Enum<E, U2> a_rhs) noexcept
37+
{
38+
_impl = static_cast<U>(a_rhs.get());
39+
}
40+
41+
constexpr Enum& operator=(E a_value) noexcept
42+
{
43+
_impl = static_cast<U>(a_value);
44+
return *this;
45+
}
46+
47+
public:
48+
[[nodiscard]] explicit constexpr operator bool() const noexcept { return _impl != static_cast<U>(0); }
49+
[[nodiscard]] constexpr E operator*() const noexcept { return get(); }
50+
[[nodiscard]] constexpr E get() const noexcept { return static_cast<E>(_impl); }
51+
[[nodiscard]] constexpr U underlying() const noexcept { return _impl; }
52+
53+
public:
54+
friend constexpr bool operator==(Enum a_lhs, Enum a_rhs) noexcept { return a_lhs.underlying() == a_rhs.underlying(); }
55+
friend constexpr bool operator==(Enum a_lhs, E a_rhs) noexcept { return a_lhs.underlying() == static_cast<U>(a_rhs); }
56+
friend constexpr bool operator==(E a_lhs, Enum a_rhs) noexcept { return static_cast<U>(a_lhs) == a_rhs.underlying(); }
57+
58+
private:
59+
U _impl{ 0 };
60+
};
61+
template <class... Args>
62+
Enum(Args...) -> Enum<
63+
std::common_type_t<Args...>,
64+
std::underlying_type_t<
65+
std::common_type_t<Args...>>>;
66+
}
67+
368
namespace REX
469
{
570
template <

CommonLibF4/include/REX/W32.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
#include "REX/W32/DXGI_5.h"
2222
#include "REX/W32/DXGI_6.h"
2323
#include "REX/W32/KERNEL32.h"
24+
#include "REX/W32/NT.h"
2425
#include "REX/W32/OLE32.h"
2526
#include "REX/W32/USER32.h"
2627
#include "REX/W32/VERSION.h"

CommonLibF4/include/REX/W32/BASE.h

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -162,6 +162,7 @@ namespace REX::W32
162162
};
163163
std::int64_t value;
164164
};
165+
static_assert(sizeof(LARGE_INTEGER) == 0x8);
165166

166167
union ULARGE_INTEGER
167168
{
@@ -172,6 +173,15 @@ namespace REX::W32
172173
};
173174
std::uint64_t value;
174175
};
176+
static_assert(sizeof(ULARGE_INTEGER) == 0x8);
177+
178+
struct UNICODE_STRING
179+
{
180+
std::uint16_t length;
181+
std::uint16_t maxLength;
182+
wchar_t* buffer;
183+
};
184+
static_assert(sizeof(UNICODE_STRING) == 0x10);
175185
}
176186

177187
namespace REX::W32

CommonLibF4/include/REX/W32/NT.h

Lines changed: 92 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,92 @@
1+
#pragma once
2+
3+
#include "REX/W32/BASE.h"
4+
5+
namespace REX::W32
6+
{
7+
struct EXCEPTION_REGISTRATION_RECORD;
8+
struct PEB_LDR_DATA;
9+
struct RTL_USER_PROCESS_PARAMETERS;
10+
struct UNICODE_STRING;
11+
12+
using PS_POST_PROCESS_INIT_ROUTINE = void (*)();
13+
14+
struct LIST_ENTRY
15+
{
16+
struct LIST_ENTRY* fLink;
17+
struct LIST_ENTRY* bLink;
18+
};
19+
20+
struct NT_TIB
21+
{
22+
EXCEPTION_REGISTRATION_RECORD* exceptionList;
23+
void* stackBase;
24+
void* stackLimit;
25+
void* subSystemTib;
26+
union
27+
{
28+
void* fiberData;
29+
std::uint32_t version;
30+
};
31+
void* arbitraryUserPointer;
32+
struct NT_TIB* self;
33+
};
34+
35+
struct PEB
36+
{
37+
std::byte reserved1[2];
38+
std::byte beingDebugged;
39+
std::byte reserved2[1];
40+
void* reserved3[2];
41+
PEB_LDR_DATA* ldr;
42+
RTL_USER_PROCESS_PARAMETERS* processParameters;
43+
void* reserved4[3];
44+
void* atlThunkSListPtr;
45+
void* reserved5;
46+
std::uint32_t reserved6;
47+
void* reserved7;
48+
std::uint32_t reserved8;
49+
std::uint32_t atlThunkSListPtr32;
50+
void* reserved9[45];
51+
std::byte reserved10[96];
52+
PS_POST_PROCESS_INIT_ROUTINE postProcessInitRoutine;
53+
std::byte reserved11[128];
54+
void* reserved12[1];
55+
std::uint32_t sessionID;
56+
};
57+
58+
struct PEB_LDR_DATA
59+
{
60+
std::byte reserved1[8];
61+
void* reserved2[3];
62+
LIST_ENTRY inMemoryOrderModuleList;
63+
};
64+
65+
struct RTL_USER_PROCESS_PARAMETERS
66+
{
67+
std::byte reserved1[16];
68+
void* reserved2[10];
69+
UNICODE_STRING imagePathName;
70+
UNICODE_STRING commandLine;
71+
};
72+
73+
struct TEB
74+
{
75+
void* reserved1[11];
76+
void* threadLocalStoragePointer;
77+
PEB* processEnvironmentBlock;
78+
void* reserved2[399];
79+
std::byte reserved3[1952];
80+
void* tlsSlots[64];
81+
std::byte reserved4[8];
82+
void* reserved5[26];
83+
void* reservedForOle;
84+
void* reserved6[4];
85+
void* tlsExpansionSlots;
86+
};
87+
}
88+
89+
namespace REX::W32
90+
{
91+
TEB* NtCurrentTeb() noexcept;
92+
}

CommonLibF4/src/REX/W32.cpp

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
#include "REX/W32/DBGHELP.h"
66
#include "REX/W32/DXGI.h"
77
#include "REX/W32/KERNEL32.h"
8+
#include "REX/W32/NT.h"
89
#include "REX/W32/OLE32.h"
910
#include "REX/W32/SHELL32.h"
1011
#include "REX/W32/USER32.h"
@@ -796,6 +797,16 @@ namespace REX::W32
796797
}
797798
}
798799

800+
// NT
801+
802+
namespace REX::W32
803+
{
804+
TEB* NtCurrentTeb() noexcept
805+
{
806+
return reinterpret_cast<TEB*>(__readgsqword(offsetof(NT_TIB, self)));
807+
}
808+
}
809+
799810
// OLE32
800811

801812
REX_W32_IMPORT(void, CoTaskMemFree, void*);

0 commit comments

Comments
 (0)