Merge pull request #26 from QDarkRex/fix/kernel-error-codes

fix(kernel): use SCE kernel error codes in equeue, direct memory and mutex
| Constant | Before | After |
|---|---|---|
| `EQUEUE_ERROR_ETIMEDOUT` | `0x80010023` | `0x8002003C` |
| `EQUEUE_ERROR_EBADF` | `0x80010016` | `0x80020009` |
| `EQUEUE_ERROR_ENOENT` | `0x80010011` | `0x80020002` |
| `EQUEUE_ERROR_EINVAL` / `SCE_KERNEL_ERROR_EINVAL` (DirectMemory) | `0x80010005` | `0x80020016` |
| `EQUEUE_ERROR_EFAULT` / `SCE_KERNEL_ERROR_EFAULT` (DirectMemory) | `0x80010009` | `0x8002000E` |
| `SCE_KERNEL_ERROR_EAGAIN` (DirectMemory) | `0x80010002` | `0x80020023` |
| `SCE_KERNEL_ERROR_ENOMEM` (DirectMemory) | `0x80010007` | `0x8002000C` |
| `SCE_KERNEL_ERROR_EACCES` (DirectMemory) | `0x80010004` | `0x8002000D` |
| `SCE_KERNEL_ERROR_EDEADLK` (Mutex.cpp) | `0x80020023` (= EAGAIN) | `0x8002000B` |
This commit is contained in:
boykopovar 2026-09-28 11:18:14 +03:00 committed by GitHub
commit 8bd030d531
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
4 changed files with 76 additions and 10 deletions

View File

@ -314,6 +314,16 @@ if(BUILD_TESTING)
set_tests_properties(guest_signals PROPERTIES ENVIRONMENT_MODIFICATION
"PATH=path_list_prepend:$<TARGET_FILE_DIR:libkernel>")
endif()
add_executable(guest_kernel_error_tests tests/GuestKernelErrors.cpp)
target_include_directories(guest_kernel_error_tests PRIVATE ${CMAKE_CURRENT_SOURCE_DIR})
target_link_libraries(guest_kernel_error_tests PRIVATE libkernel libc)
configure_windows_unwind(guest_kernel_error_tests)
add_test(NAME guest_kernel_errors COMMAND guest_kernel_error_tests)
set_tests_properties(guest_kernel_errors PROPERTIES TIMEOUT 20)
if(WIN32)
set_tests_properties(guest_kernel_errors PROPERTIES ENVIRONMENT_MODIFICATION
"PATH=path_list_prepend:$<TARGET_FILE_DIR:libkernel>")
endif()
add_executable(guest_system_configuration_tests tests/GuestSystemConfiguration.cpp)
target_include_directories(guest_system_configuration_tests PRIVATE ${CMAKE_CURRENT_SOURCE_DIR})
target_link_libraries(guest_system_configuration_tests PRIVATE libkernel libc)

View File

@ -7,11 +7,11 @@
static constexpr size_t DIRECT_MEMORY_SIZE = 13824ULL * 1024 * 1024;
static constexpr size_t PS5_PAGE_SIZE = 0x4000;
static constexpr int SCE_KERNEL_ERROR_EINVAL = -2147418107;
static constexpr int SCE_KERNEL_ERROR_EAGAIN = -2147418110;
static constexpr int SCE_KERNEL_ERROR_ENOMEM = -2147418105;
static constexpr int SCE_KERNEL_ERROR_EACCES = -2147418108;
static constexpr int SCE_KERNEL_ERROR_EFAULT = -2147418103;
static constexpr int SCE_KERNEL_ERROR_EINVAL = 0x80020016;
static constexpr int SCE_KERNEL_ERROR_EAGAIN = 0x80020023;
static constexpr int SCE_KERNEL_ERROR_ENOMEM = 0x8002000C;
static constexpr int SCE_KERNEL_ERROR_EACCES = 0x8002000D;
static constexpr int SCE_KERNEL_ERROR_EFAULT = 0x8002000E;
int DirectMemoryAlloc(int64_t searchStart, int64_t searchEnd, size_t len, size_t alignment, int64_t* physOut);
void DirectMemoryFree(int64_t start, size_t len);

View File

@ -23,11 +23,11 @@ static constexpr uint16_t EV_CLEAR = 0x0020;
static constexpr uint16_t EV_ERROR = 0x4000;
static constexpr int EQUEUE_OK = 0;
static constexpr int EQUEUE_ERROR_EBADF = -2147418090;
static constexpr int EQUEUE_ERROR_EFAULT = -2147418103;
static constexpr int EQUEUE_ERROR_EINVAL = -2147418107;
static constexpr int EQUEUE_ERROR_ENOENT = -2147418095;
static constexpr int EQUEUE_ERROR_ETIMEDOUT = -2147418077;
static constexpr int EQUEUE_ERROR_EBADF = 0x80020009;
static constexpr int EQUEUE_ERROR_EFAULT = 0x8002000E;
static constexpr int EQUEUE_ERROR_EINVAL = 0x80020016;
static constexpr int EQUEUE_ERROR_ENOENT = 0x80020002;
static constexpr int EQUEUE_ERROR_ETIMEDOUT = 0x8002003C;
struct KernelEqueueEvent;

View File

@ -0,0 +1,56 @@
#include "SceTypes.hpp"
#include <cstdint>
#include <cstdlib>
extern "C" {
int APS5_VABI sceKernelCreateEqueue(KernelEqueue* eq, const char* name);
int APS5_VABI sceKernelDeleteEqueue(KernelEqueue eq);
int APS5_VABI sceKernelWaitEqueue(KernelEqueue eq, KernelEvent* ev, int num, int* out, const KernelUseconds* timo);
int APS5_VABI sceKernelDeleteUserEvent(KernelEqueue eq, int id);
int APS5_VABI scePthreadMutexattrInit(PthreadMutexattr* attr);
int APS5_VABI scePthreadMutexattrDestroy(PthreadMutexattr* attr);
int APS5_VABI scePthreadMutexattrSettype(PthreadMutexattr* attr, int type);
int APS5_VABI scePthreadMutexInit(PthreadMutex* mutex, const PthreadMutexattr* attr, const char* name);
int APS5_VABI scePthreadMutexDestroy(PthreadMutex* mutex);
int APS5_VABI scePthreadMutexLock(PthreadMutex* mutex);
int APS5_VABI scePthreadMutexUnlock(PthreadMutex* mutex);
}
static constexpr int SCE_OK = 0;
static constexpr int SCE_KERNEL_ERROR_ENOENT = static_cast<int>(0x80020002);
static constexpr int SCE_KERNEL_ERROR_EBADF = static_cast<int>(0x80020009);
static constexpr int SCE_KERNEL_ERROR_EDEADLK = static_cast<int>(0x8002000B);
static constexpr int SCE_KERNEL_ERROR_EFAULT = static_cast<int>(0x8002000E);
static constexpr int SCE_KERNEL_ERROR_EINVAL = static_cast<int>(0x80020016);
static constexpr int SCE_KERNEL_ERROR_ETIMEDOUT = static_cast<int>(0x8002003C);
static constexpr int MUTEX_TYPE_ERRORCHECK = 1;
static void Require(bool value) { if (!value) std::abort(); }
int main() {
KernelEqueue eq = 0;
Require(sceKernelCreateEqueue(&eq, "errors") == SCE_OK);
KernelEvent event{};
int count = -1;
const KernelUseconds timeout = 1000;
Require(sceKernelWaitEqueue(eq, &event, 1, &count, &timeout) == SCE_KERNEL_ERROR_ETIMEDOUT);
Require(count == 0);
Require(sceKernelWaitEqueue(eq, nullptr, 1, &count, &timeout) == SCE_KERNEL_ERROR_EFAULT);
Require(sceKernelWaitEqueue(eq, &event, 0, &count, &timeout) == SCE_KERNEL_ERROR_EINVAL);
Require(sceKernelDeleteUserEvent(eq, 7) == SCE_KERNEL_ERROR_ENOENT);
Require(sceKernelDeleteEqueue(eq) == SCE_OK);
Require(sceKernelDeleteEqueue(eq) == SCE_KERNEL_ERROR_EBADF);
Require(sceKernelWaitEqueue(eq, &event, 1, &count, &timeout) == SCE_KERNEL_ERROR_EBADF);
Require(sceKernelCreateEqueue(nullptr, "errors") == SCE_KERNEL_ERROR_EINVAL);
PthreadMutexattr attr = nullptr;
Require(scePthreadMutexattrInit(&attr) == SCE_OK);
Require(scePthreadMutexattrSettype(&attr, MUTEX_TYPE_ERRORCHECK) == SCE_OK);
PthreadMutex mutex = nullptr;
Require(scePthreadMutexInit(&mutex, &attr, nullptr) == SCE_OK);
Require(scePthreadMutexattrDestroy(&attr) == SCE_OK);
Require(scePthreadMutexLock(&mutex) == SCE_OK);
Require(scePthreadMutexLock(&mutex) == SCE_KERNEL_ERROR_EDEADLK);
Require(scePthreadMutexUnlock(&mutex) == SCE_OK);
Require(scePthreadMutexDestroy(&mutex) == SCE_OK);
}