XObject::GetObject->GetNativeObject
This commit is contained in:
parent
d746743d20
commit
120e09f8e7
|
@ -118,7 +118,7 @@ SHIM_CALL ObDereferenceObject_shim(PPCContext* ppc_state, KernelState* state) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void* object_ptr = SHIM_MEM_ADDR(native_ptr);
|
void* object_ptr = SHIM_MEM_ADDR(native_ptr);
|
||||||
XObject* object = XObject::GetObject(state, object_ptr);
|
auto object = XObject::GetNativeObject<XObject>(state, object_ptr);
|
||||||
if (object) {
|
if (object) {
|
||||||
object->Release();
|
object->Release();
|
||||||
}
|
}
|
||||||
|
|
|
@ -176,8 +176,8 @@ SHIM_CALL KeResumeThread_shim(PPCContext* ppc_state, KernelState* state) {
|
||||||
XELOGD("KeResumeThread(%.8X)", thread_ptr);
|
XELOGD("KeResumeThread(%.8X)", thread_ptr);
|
||||||
|
|
||||||
X_STATUS result;
|
X_STATUS result;
|
||||||
XThread* thread =
|
auto thread =
|
||||||
(XThread*)XObject::GetObject(state, SHIM_MEM_ADDR(thread_ptr));
|
XObject::GetNativeObject<XThread>(state, SHIM_MEM_ADDR(thread_ptr));
|
||||||
if (thread) {
|
if (thread) {
|
||||||
result = thread->Resume();
|
result = thread->Resume();
|
||||||
}
|
}
|
||||||
|
@ -215,8 +215,8 @@ SHIM_CALL KeSetAffinityThread_shim(PPCContext* ppc_state, KernelState* state) {
|
||||||
|
|
||||||
XELOGD("KeSetAffinityThread(%.8X, %.8X)", thread_ptr, affinity);
|
XELOGD("KeSetAffinityThread(%.8X, %.8X)", thread_ptr, affinity);
|
||||||
|
|
||||||
XThread* thread =
|
auto thread =
|
||||||
(XThread*)XObject::GetObject(state, SHIM_MEM_ADDR(thread_ptr));
|
XObject::GetNativeObject<XThread>(state, SHIM_MEM_ADDR(thread_ptr));
|
||||||
if (thread) {
|
if (thread) {
|
||||||
thread->SetAffinity(affinity);
|
thread->SetAffinity(affinity);
|
||||||
}
|
}
|
||||||
|
@ -232,8 +232,8 @@ SHIM_CALL KeQueryBasePriorityThread_shim(PPCContext* ppc_state,
|
||||||
|
|
||||||
int32_t priority = 0;
|
int32_t priority = 0;
|
||||||
|
|
||||||
XThread* thread =
|
auto thread =
|
||||||
(XThread*)XObject::GetObject(state, SHIM_MEM_ADDR(thread_ptr));
|
XObject::GetNativeObject<XThread>(state, SHIM_MEM_ADDR(thread_ptr));
|
||||||
if (thread) {
|
if (thread) {
|
||||||
priority = thread->QueryPriority();
|
priority = thread->QueryPriority();
|
||||||
}
|
}
|
||||||
|
@ -259,8 +259,7 @@ SHIM_CALL KeSetBasePriorityThread_shim(PPCContext* ppc_state,
|
||||||
// Log it in case this is the source of any problems in the future
|
// Log it in case this is the source of any problems in the future
|
||||||
XELOGD("KeSetBasePriorityThread - Interpreting thread ptr as handle!");
|
XELOGD("KeSetBasePriorityThread - Interpreting thread ptr as handle!");
|
||||||
} else {
|
} else {
|
||||||
thread = (XThread*)XObject::GetObject(state, SHIM_MEM_ADDR(thread_ptr));
|
thread = XObject::GetNativeObject<XThread>(state, SHIM_MEM_ADDR(thread_ptr)).release();
|
||||||
thread->Retain();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (thread) {
|
if (thread) {
|
||||||
|
@ -279,8 +278,8 @@ SHIM_CALL KeSetDisableBoostThread_shim(PPCContext* ppc_state,
|
||||||
|
|
||||||
XELOGD("KeSetDisableBoostThread(%.8X, %.8X)", thread_ptr, disabled);
|
XELOGD("KeSetDisableBoostThread(%.8X, %.8X)", thread_ptr, disabled);
|
||||||
|
|
||||||
XThread* thread =
|
auto thread =
|
||||||
(XThread*)XObject::GetObject(state, SHIM_MEM_ADDR(thread_ptr));
|
XObject::GetNativeObject<XThread>(state, SHIM_MEM_ADDR(thread_ptr));
|
||||||
if (thread) {
|
if (thread) {
|
||||||
// Uhm?
|
// Uhm?
|
||||||
}
|
}
|
||||||
|
@ -490,8 +489,7 @@ SHIM_CALL KeSetEvent_shim(PPCContext* ppc_state, KernelState* state) {
|
||||||
|
|
||||||
void* event_ptr = SHIM_MEM_ADDR(event_ref);
|
void* event_ptr = SHIM_MEM_ADDR(event_ref);
|
||||||
|
|
||||||
XEvent* ev = (XEvent*)XObject::GetObject(state, event_ptr);
|
auto ev = XObject::GetNativeObject<XEvent>(state, event_ptr);
|
||||||
assert_not_null(ev);
|
|
||||||
if (!ev) {
|
if (!ev) {
|
||||||
SHIM_SET_RETURN_64(0);
|
SHIM_SET_RETURN_64(0);
|
||||||
return;
|
return;
|
||||||
|
@ -533,8 +531,7 @@ SHIM_CALL KePulseEvent_shim(PPCContext* ppc_state, KernelState* state) {
|
||||||
int32_t result = 0;
|
int32_t result = 0;
|
||||||
|
|
||||||
void* event_ptr = SHIM_MEM_ADDR(event_ref);
|
void* event_ptr = SHIM_MEM_ADDR(event_ref);
|
||||||
XEvent* ev = (XEvent*)XObject::GetObject(state, event_ptr);
|
auto ev = XObject::GetNativeObject<XEvent>(state, event_ptr);
|
||||||
assert_not_null(ev);
|
|
||||||
if (ev) {
|
if (ev) {
|
||||||
result = ev->Pulse(increment, !!wait);
|
result = ev->Pulse(increment, !!wait);
|
||||||
}
|
}
|
||||||
|
@ -570,8 +567,7 @@ SHIM_CALL KeResetEvent_shim(PPCContext* ppc_state, KernelState* state) {
|
||||||
XELOGD("KeResetEvent(%.8X)", event_ref);
|
XELOGD("KeResetEvent(%.8X)", event_ref);
|
||||||
|
|
||||||
void* event_ptr = SHIM_MEM_ADDR(event_ref);
|
void* event_ptr = SHIM_MEM_ADDR(event_ref);
|
||||||
XEvent* ev = (XEvent*)XEvent::GetObject(state, event_ptr);
|
auto ev = XObject::GetNativeObject<XEvent>(state, event_ptr);
|
||||||
assert_not_null(ev);
|
|
||||||
if (!ev) {
|
if (!ev) {
|
||||||
SHIM_SET_RETURN_64(0);
|
SHIM_SET_RETURN_64(0);
|
||||||
return;
|
return;
|
||||||
|
@ -613,7 +609,7 @@ SHIM_CALL NtCreateSemaphore_shim(PPCContext* ppc_state, KernelState* state) {
|
||||||
AssertNoNameCollision(state, obj_attributes_ptr);
|
AssertNoNameCollision(state, obj_attributes_ptr);
|
||||||
}
|
}
|
||||||
|
|
||||||
XSemaphore* sem = new XSemaphore(state);
|
auto sem = object_ref<XSemaphore>(new XSemaphore(state));
|
||||||
sem->Initialize(count, limit);
|
sem->Initialize(count, limit);
|
||||||
|
|
||||||
// obj_attributes may have a name inside of it, if != NULL.
|
// obj_attributes may have a name inside of it, if != NULL.
|
||||||
|
@ -637,9 +633,8 @@ SHIM_CALL KeInitializeSemaphore_shim(PPCContext* ppc_state,
|
||||||
XELOGD("KeInitializeSemaphore(%.8X, %d, %d)", semaphore_ref, count, limit);
|
XELOGD("KeInitializeSemaphore(%.8X, %d, %d)", semaphore_ref, count, limit);
|
||||||
|
|
||||||
void* semaphore_ptr = SHIM_MEM_ADDR(semaphore_ref);
|
void* semaphore_ptr = SHIM_MEM_ADDR(semaphore_ref);
|
||||||
XSemaphore* sem = (XSemaphore*)XSemaphore::GetObject(state, semaphore_ptr,
|
auto sem = XObject::GetNativeObject<XSemaphore>(state, semaphore_ptr,
|
||||||
5 /* SemaphoreObject */);
|
5 /* SemaphoreObject */);
|
||||||
assert_not_null(sem);
|
|
||||||
if (!sem) {
|
if (!sem) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -657,8 +652,7 @@ SHIM_CALL KeReleaseSemaphore_shim(PPCContext* ppc_state, KernelState* state) {
|
||||||
adjustment, wait);
|
adjustment, wait);
|
||||||
|
|
||||||
void* semaphore_ptr = SHIM_MEM_ADDR(semaphore_ref);
|
void* semaphore_ptr = SHIM_MEM_ADDR(semaphore_ref);
|
||||||
XSemaphore* sem = (XSemaphore*)XSemaphore::GetObject(state, semaphore_ptr);
|
auto sem = XObject::GetNativeObject<XSemaphore>(state, semaphore_ptr);
|
||||||
assert_not_null(sem);
|
|
||||||
if (!sem) {
|
if (!sem) {
|
||||||
SHIM_SET_RETURN_64(0);
|
SHIM_SET_RETURN_64(0);
|
||||||
return;
|
return;
|
||||||
|
@ -848,7 +842,8 @@ SHIM_CALL KeWaitForSingleObject_shim(PPCContext* ppc_state,
|
||||||
XELOGD("KeWaitForSingleObject(%.8X, %.8X, %.8X, %.1X, %.8X)", object_ptr,
|
XELOGD("KeWaitForSingleObject(%.8X, %.8X, %.8X, %.1X, %.8X)", object_ptr,
|
||||||
wait_reason, processor_mode, alertable, timeout_ptr);
|
wait_reason, processor_mode, alertable, timeout_ptr);
|
||||||
|
|
||||||
XObject* object = XObject::GetObject(state, SHIM_MEM_ADDR(object_ptr));
|
auto object =
|
||||||
|
XObject::GetNativeObject<XObject>(state, SHIM_MEM_ADDR(object_ptr));
|
||||||
if (!object) {
|
if (!object) {
|
||||||
// The only kind-of failure code.
|
// The only kind-of failure code.
|
||||||
SHIM_SET_RETURN_32(X_STATUS_ABANDONED_WAIT_0);
|
SHIM_SET_RETURN_32(X_STATUS_ABANDONED_WAIT_0);
|
||||||
|
@ -906,11 +901,11 @@ SHIM_CALL KeWaitForMultipleObjects_shim(PPCContext* ppc_state,
|
||||||
|
|
||||||
X_STATUS result = X_STATUS_SUCCESS;
|
X_STATUS result = X_STATUS_SUCCESS;
|
||||||
|
|
||||||
XObject** objects = (XObject**)alloca(sizeof(XObject*) * count);
|
std::vector<object_ref<XObject>> objects(count);
|
||||||
for (uint32_t n = 0; n < count; n++) {
|
for (uint32_t n = 0; n < count; n++) {
|
||||||
uint32_t object_ptr_ptr = SHIM_MEM_32(objects_ptr + n * 4);
|
uint32_t object_ptr_ptr = SHIM_MEM_32(objects_ptr + n * 4);
|
||||||
void* object_ptr = SHIM_MEM_ADDR(object_ptr_ptr);
|
void* object_ptr = SHIM_MEM_ADDR(object_ptr_ptr);
|
||||||
objects[n] = XObject::GetObject(state, object_ptr);
|
objects[n] = XObject::GetNativeObject<XObject>(state, object_ptr);
|
||||||
if (!objects[n]) {
|
if (!objects[n]) {
|
||||||
SHIM_SET_RETURN_32(X_STATUS_INVALID_PARAMETER);
|
SHIM_SET_RETURN_32(X_STATUS_INVALID_PARAMETER);
|
||||||
return;
|
return;
|
||||||
|
@ -918,9 +913,9 @@ SHIM_CALL KeWaitForMultipleObjects_shim(PPCContext* ppc_state,
|
||||||
}
|
}
|
||||||
|
|
||||||
uint64_t timeout = timeout_ptr ? SHIM_MEM_64(timeout_ptr) : 0;
|
uint64_t timeout = timeout_ptr ? SHIM_MEM_64(timeout_ptr) : 0;
|
||||||
result = XObject::WaitMultiple(count, objects, wait_type, wait_reason,
|
result = XObject::WaitMultiple(
|
||||||
processor_mode, alertable,
|
count, reinterpret_cast<XObject**>(objects.data()), wait_type,
|
||||||
timeout_ptr ? &timeout : NULL);
|
wait_reason, processor_mode, alertable, timeout_ptr ? &timeout : nullptr);
|
||||||
|
|
||||||
SHIM_SET_RETURN_32(result);
|
SHIM_SET_RETURN_32(result);
|
||||||
}
|
}
|
||||||
|
@ -1150,8 +1145,8 @@ SHIM_CALL KeInsertQueueApc_shim(PPCContext* ppc_state, KernelState* state) {
|
||||||
priority_increment);
|
priority_increment);
|
||||||
|
|
||||||
uint32_t thread_ptr = SHIM_MEM_32(apc_ptr + 4);
|
uint32_t thread_ptr = SHIM_MEM_32(apc_ptr + 4);
|
||||||
XThread* thread =
|
auto thread =
|
||||||
(XThread*)XObject::GetObject(state, SHIM_MEM_ADDR(thread_ptr));
|
XObject::GetNativeObject<XThread>(state, SHIM_MEM_ADDR(thread_ptr));
|
||||||
if (!thread) {
|
if (!thread) {
|
||||||
SHIM_SET_RETURN_64(0);
|
SHIM_SET_RETURN_64(0);
|
||||||
return;
|
return;
|
||||||
|
@ -1192,8 +1187,8 @@ SHIM_CALL KeRemoveQueueApc_shim(PPCContext* ppc_state, KernelState* state) {
|
||||||
bool result = false;
|
bool result = false;
|
||||||
|
|
||||||
uint32_t thread_ptr = SHIM_MEM_32(apc_ptr + 4);
|
uint32_t thread_ptr = SHIM_MEM_32(apc_ptr + 4);
|
||||||
XThread* thread =
|
auto thread =
|
||||||
(XThread*)XObject::GetObject(state, SHIM_MEM_ADDR(thread_ptr));
|
XObject::GetNativeObject<XThread>(state, SHIM_MEM_ADDR(thread_ptr));
|
||||||
if (!thread) {
|
if (!thread) {
|
||||||
SHIM_SET_RETURN_64(0);
|
SHIM_SET_RETURN_64(0);
|
||||||
return;
|
return;
|
||||||
|
|
|
@ -175,10 +175,9 @@ void XObject::SetNativePointer(uint32_t native_ptr, bool uninitialized) {
|
||||||
header->wait_list_blink = (uint32_t)(object_ptr & 0xFFFFFFFF);
|
header->wait_list_blink = (uint32_t)(object_ptr & 0xFFFFFFFF);
|
||||||
}
|
}
|
||||||
|
|
||||||
XObject* XObject::GetObject(KernelState* kernel_state, void* native_ptr,
|
object_ref<XObject> XObject::GetNativeObject(KernelState* kernel_state,
|
||||||
int32_t as_type) {
|
void* native_ptr,
|
||||||
assert_not_null(native_ptr);
|
int32_t as_type) {
|
||||||
|
|
||||||
// Unfortunately the XDK seems to inline some KeInitialize calls, meaning
|
// Unfortunately the XDK seems to inline some KeInitialize calls, meaning
|
||||||
// we never see it and just randomly start getting passed events/timers/etc.
|
// we never see it and just randomly start getting passed events/timers/etc.
|
||||||
// Luckily it seems like all other calls (Set/Reset/Wait/etc) are used and
|
// Luckily it seems like all other calls (Set/Reset/Wait/etc) are used and
|
||||||
|
@ -202,28 +201,28 @@ XObject* XObject::GetObject(KernelState* kernel_state, void* native_ptr,
|
||||||
((header->wait_list_blink) & ~0x1);
|
((header->wait_list_blink) & ~0x1);
|
||||||
XObject* object = reinterpret_cast<XObject*>(object_ptr);
|
XObject* object = reinterpret_cast<XObject*>(object_ptr);
|
||||||
// TODO(benvanik): assert nothing has been changed in the struct.
|
// TODO(benvanik): assert nothing has been changed in the struct.
|
||||||
return object;
|
return retain_object<XObject>(object);
|
||||||
} else {
|
} else {
|
||||||
// First use, create new.
|
// First use, create new.
|
||||||
// http://www.nirsoft.net/kernel_struct/vista/KOBJECTS.html
|
// http://www.nirsoft.net/kernel_struct/vista/KOBJECTS.html
|
||||||
XObject* object = NULL;
|
XObject* object = nullptr;
|
||||||
switch (as_type) {
|
switch (as_type) {
|
||||||
case 0: // EventNotificationObject
|
case 0: // EventNotificationObject
|
||||||
case 1: // EventSynchronizationObject
|
case 1: // EventSynchronizationObject
|
||||||
{
|
{
|
||||||
XEvent* ev = new XEvent(kernel_state);
|
auto ev = new XEvent(kernel_state);
|
||||||
ev->InitializeNative(native_ptr, *header);
|
ev->InitializeNative(native_ptr, *header);
|
||||||
object = ev;
|
object = ev;
|
||||||
} break;
|
} break;
|
||||||
case 2: // MutantObject
|
case 2: // MutantObject
|
||||||
{
|
{
|
||||||
XMutant* mutant = new XMutant(kernel_state);
|
auto mutant = new XMutant(kernel_state);
|
||||||
mutant->InitializeNative(native_ptr, *header);
|
mutant->InitializeNative(native_ptr, *header);
|
||||||
object = mutant;
|
object = mutant;
|
||||||
} break;
|
} break;
|
||||||
case 5: // SemaphoreObject
|
case 5: // SemaphoreObject
|
||||||
{
|
{
|
||||||
XSemaphore* sem = new XSemaphore(kernel_state);
|
auto sem = new XSemaphore(kernel_state);
|
||||||
sem->InitializeNative(native_ptr, *header);
|
sem->InitializeNative(native_ptr, *header);
|
||||||
object = sem;
|
object = sem;
|
||||||
} break;
|
} break;
|
||||||
|
@ -251,7 +250,9 @@ XObject* XObject::GetObject(KernelState* kernel_state, void* native_ptr,
|
||||||
header->wait_list_flink = (uint32_t)(object_ptr >> 32);
|
header->wait_list_flink = (uint32_t)(object_ptr >> 32);
|
||||||
header->wait_list_blink = (uint32_t)(object_ptr & 0xFFFFFFFF);
|
header->wait_list_blink = (uint32_t)(object_ptr & 0xFFFFFFFF);
|
||||||
|
|
||||||
return object;
|
// NOTE: we are double-retaining, as the object is implicitly created and
|
||||||
|
// can never be released.
|
||||||
|
return retain_object<XObject>(object);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -81,8 +81,15 @@ class XObject {
|
||||||
uint32_t processor_mode, uint32_t alertable,
|
uint32_t processor_mode, uint32_t alertable,
|
||||||
uint64_t* opt_timeout);
|
uint64_t* opt_timeout);
|
||||||
|
|
||||||
static XObject* GetObject(KernelState* kernel_state, void* native_ptr,
|
static object_ref<XObject> GetNativeObject(KernelState* kernel_state,
|
||||||
int32_t as_type = -1);
|
void* native_ptr,
|
||||||
|
int32_t as_type = -1);
|
||||||
|
template <typename T>
|
||||||
|
static object_ref<T> GetNativeObject(KernelState* kernel_state,
|
||||||
|
void* native_ptr, int32_t as_type = -1) {
|
||||||
|
return object_ref<T>(reinterpret_cast<T*>(
|
||||||
|
GetNativeObject(kernel_state, native_ptr, as_type).release()));
|
||||||
|
}
|
||||||
|
|
||||||
virtual void* GetWaitHandle() { return 0; }
|
virtual void* GetWaitHandle() { return 0; }
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue