Check for and allow null critical sections, but log them.
stub XeKeysGetConsoleType Removed the breakpoints in HandleCppException and RtlRaiseException until we have a real implementation of them. Some apps can continue fine afterwards. Stub version of HalGetCurrentAVPack Implement MmIsAddressValid Implement RtlGetStackLimits
This commit is contained in:
parent
779be8283d
commit
1f86dc0454
|
@ -686,6 +686,16 @@ dword_result_t XeKeysHmacShaUsingKey_entry(lpvoid_t obscured_key,
|
|||
}
|
||||
DECLARE_XBOXKRNL_EXPORT1(XeKeysHmacShaUsingKey, kNone, kImplemented);
|
||||
|
||||
//going off of usage in some hbrew xex
|
||||
//0 and 1 appear to be devkit, 2 is retail
|
||||
//we default to saying we're retail
|
||||
dword_result_t XeKeysGetConsoleType_entry(lpdword_t type_out) {
|
||||
*type_out = 2;
|
||||
return 0;
|
||||
}
|
||||
|
||||
DECLARE_XBOXKRNL_EXPORT1(XeKeysGetConsoleType, kNone, kImplemented);
|
||||
|
||||
} // namespace xboxkrnl
|
||||
} // namespace kernel
|
||||
} // namespace xe
|
||||
|
|
|
@ -120,7 +120,8 @@ void HandleCppException(pointer_t<X_EXCEPTION_RECORD> record) {
|
|||
kernel_memory()->TranslateVirtual<x_s__CatchableTypeArray*>(
|
||||
throw_info->catchable_type_array_ptr);
|
||||
|
||||
xe::debugging::Break();
|
||||
//xe::debugging::Break();
|
||||
XELOGE("Guest attempted to throw a C++ exception!");
|
||||
}
|
||||
|
||||
void RtlRaiseException_entry(pointer_t<X_EXCEPTION_RECORD> record) {
|
||||
|
@ -137,7 +138,10 @@ void RtlRaiseException_entry(pointer_t<X_EXCEPTION_RECORD> record) {
|
|||
|
||||
// TODO(benvanik): unwinding.
|
||||
// This is going to suck.
|
||||
xe::debugging::Break();
|
||||
// xe::debugging::Break();
|
||||
|
||||
//RtlRaiseException definitely wasn't a noreturn function, we can return safe-ish
|
||||
XELOGE("Guest attempted to trigger a breakpoint!");
|
||||
}
|
||||
DECLARE_XBOXKRNL_EXPORT2(RtlRaiseException, kDebug, kStub, kImportant);
|
||||
|
||||
|
|
|
@ -31,6 +31,13 @@ void HalReturnToFirmware_entry(dword_t routine) {
|
|||
}
|
||||
DECLARE_XBOXKRNL_EXPORT2(HalReturnToFirmware, kNone, kStub, kImportant);
|
||||
|
||||
// this seems to be able to return a number of different values in the range 0
|
||||
// - 8. just returning four for now, because thats probably a better option than
|
||||
// returning whatever was in r3 to begin with
|
||||
dword_result_t HalGetCurrentAVPack_entry() { return 4; }
|
||||
|
||||
DECLARE_XBOXKRNL_EXPORT1(HalGetCurrentAVPack, kNone, kStub);
|
||||
|
||||
} // namespace xboxkrnl
|
||||
} // namespace kernel
|
||||
} // namespace xe
|
||||
|
|
|
@ -675,6 +675,22 @@ dword_result_t MmDeleteKernelStack_entry(lpvoid_t stack_base,
|
|||
}
|
||||
DECLARE_XBOXKRNL_EXPORT1(MmDeleteKernelStack, kMemory, kImplemented);
|
||||
|
||||
dword_result_t MmIsAddressValid_entry(dword_t address,
|
||||
const ppc_context_t& ctx) {
|
||||
auto kernel = ctx->kernel_state;
|
||||
auto memory = kernel->memory();
|
||||
auto heap = memory->LookupHeap(address);
|
||||
if (!heap) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
return heap->QueryRangeAccess(address, address) !=
|
||||
memory::PageAccess::kNoAccess;
|
||||
}
|
||||
|
||||
DECLARE_XBOXKRNL_EXPORT1(MmIsAddressValid, kMemory, kImplemented);
|
||||
|
||||
|
||||
} // namespace xboxkrnl
|
||||
} // namespace kernel
|
||||
} // namespace xe
|
||||
|
|
|
@ -517,6 +517,10 @@ static void CriticalSectionPrefetchW(const void* vp) {
|
|||
}
|
||||
|
||||
void RtlEnterCriticalSection_entry(pointer_t<X_RTL_CRITICAL_SECTION> cs) {
|
||||
if (!cs.guest_address()) {
|
||||
XELOGE("Null critical section in RtlEnterCriticalSection!");
|
||||
return;
|
||||
}
|
||||
CriticalSectionPrefetchW(&cs->lock_count);
|
||||
uint32_t cur_thread = XThread::GetCurrentThread()->guest_object();
|
||||
uint32_t spin_count = cs->header.absolute * 256;
|
||||
|
@ -553,6 +557,10 @@ DECLARE_XBOXKRNL_EXPORT2(RtlEnterCriticalSection, kNone, kImplemented,
|
|||
|
||||
dword_result_t RtlTryEnterCriticalSection_entry(
|
||||
pointer_t<X_RTL_CRITICAL_SECTION> cs) {
|
||||
if (!cs.guest_address()) {
|
||||
XELOGE("Null critical section in RtlTryEnterCriticalSection!");
|
||||
return 1; // pretend we got the critical section.
|
||||
}
|
||||
CriticalSectionPrefetchW(&cs->lock_count);
|
||||
uint32_t thread = XThread::GetCurrentThread()->guest_object();
|
||||
|
||||
|
@ -575,6 +583,10 @@ DECLARE_XBOXKRNL_EXPORT2(RtlTryEnterCriticalSection, kNone, kImplemented,
|
|||
kHighFrequency);
|
||||
|
||||
void RtlLeaveCriticalSection_entry(pointer_t<X_RTL_CRITICAL_SECTION> cs) {
|
||||
if (!cs.guest_address()) {
|
||||
XELOGE("Null critical section in RtlLeaveCriticalSection!");
|
||||
return;
|
||||
}
|
||||
assert_true(cs->owning_thread == XThread::GetCurrentThread()->guest_object());
|
||||
|
||||
// Drop recursion count - if it isn't zero we still have the lock.
|
||||
|
@ -748,6 +760,26 @@ static void RtlRip_entry(const ppc_context_t& ctx) {
|
|||
//we should break here... not sure what to do exactly
|
||||
}
|
||||
DECLARE_XBOXKRNL_EXPORT1(RtlRip, kNone, kImportant);
|
||||
|
||||
void RtlGetStackLimits_entry(lpdword_t out_end, lpdword_t out_base,
|
||||
const ppc_context_t& ctx) {
|
||||
auto kpcr = ctx->TranslateVirtualGPR<X_KPCR*>(ctx->r[13]);
|
||||
|
||||
uint32_t stack_base;
|
||||
uint32_t stack_end;
|
||||
|
||||
if (kpcr->use_alternative_stack) {
|
||||
stack_base = kpcr->alt_stack_base_ptr;
|
||||
stack_end = kpcr->alt_stack_end_ptr;
|
||||
} else {
|
||||
stack_base = kpcr->stack_base_ptr;
|
||||
stack_end = kpcr->stack_end_ptr;
|
||||
}
|
||||
*out_base = stack_base;
|
||||
*out_end = stack_end;
|
||||
}
|
||||
DECLARE_XBOXKRNL_EXPORT1(RtlGetStackLimits, kNone, kImplemented);
|
||||
|
||||
} // namespace xboxkrnl
|
||||
} // namespace kernel
|
||||
} // namespace xe
|
||||
|
|
|
@ -73,10 +73,17 @@ struct X_KPCR {
|
|||
xe::be<uint32_t> msr_mask; // 0x4
|
||||
uint8_t unk_08[0x28]; // 0x8
|
||||
xe::be<uint32_t> pcr_ptr; // 0x30
|
||||
uint8_t unk_34[0x3C]; // 0x34
|
||||
uint8_t unk_34[0x38]; // 0x34
|
||||
xe::be<uint32_t> use_alternative_stack; //0x6C
|
||||
xe::be<uint32_t> stack_base_ptr; // 0x70 Stack base address (high addr)
|
||||
xe::be<uint32_t> stack_end_ptr; // 0x74 Stack end (low addr)
|
||||
uint8_t unk_78[0x88]; // 0x78
|
||||
|
||||
//maybe these are the stacks used in apcs?
|
||||
//i know they're stacks, RtlGetStackLimits returns them if another var here is set
|
||||
|
||||
xe::be<uint32_t> alt_stack_base_ptr; // 0x78
|
||||
xe::be<uint32_t> alt_stack_end_ptr; // 0x7C
|
||||
uint8_t unk_80[0x80]; // 0x80
|
||||
xe::be<uint32_t> current_thread; // 0x100
|
||||
uint8_t unk_104[0x8]; // 0x104
|
||||
uint8_t current_cpu; // 0x10C
|
||||
|
|
Loading…
Reference in New Issue