diff --git a/src/core/libraries/kernel/time_management.cpp b/src/core/libraries/kernel/time_management.cpp index f32e2b8e3..aeb9a76d2 100644 --- a/src/core/libraries/kernel/time_management.cpp +++ b/src/core/libraries/kernel/time_management.cpp @@ -4,6 +4,7 @@ #include "common/native_clock.h" #include "core/libraries/kernel/time_management.h" #include "core/libraries/libs.h" +#include "core/libraries/error_codes.h" namespace Libraries::Kernel { @@ -30,6 +31,31 @@ u64 PS4_SYSV_ABI sceKernelReadTsc() { return clock->GetUptime(); } +int PS4_SYSV_ABI sceKernelGettimeofday(OrbisKernelTimeval *tp) { + if (!tp) { + return ORBIS_KERNEL_ERROR_EFAULT; + } + + auto now = std::chrono::system_clock::now(); + auto duration = now.time_since_epoch(); + auto seconds = std::chrono::duration_cast(duration); + auto microsecs = std::chrono::duration_cast(duration - seconds); + + tp->tv_sec = seconds.count(); + tp->tv_usec = microsecs.count(); + return ORBIS_OK; +} + +int PS4_SYSV_ABI gettimeofday(OrbisKernelTimeval *tp, OrbisKernelTimezone* tz) { + // FreeBSD docs mention that the kernel generally does not track these values + // and they are usually returned as zero. + if (tz) { + tz->tz_minuteswest = 0; + tz->tz_dsttime = 0; + } + return sceKernelGettimeofday(tp); +} + void timeSymbolsRegister(Core::Loader::SymbolsResolver* sym) { clock = std::make_unique(); initial_ptc = clock->GetUptime(); @@ -39,6 +65,9 @@ void timeSymbolsRegister(Core::Loader::SymbolsResolver* sym) { sceKernelGetProcessTimeCounterFrequency); LIB_FUNCTION("-2IRUCO--PM", "libkernel", 1, "libkernel", 1, 1, sceKernelReadTsc); LIB_FUNCTION("1j3S3n-tTW4", "libkernel", 1, "libkernel", 1, 1, sceKernelGetTscFrequency); + LIB_FUNCTION("ejekcaNQNq0", "libkernel", 1, "libkernel", 1, 1, sceKernelGettimeofday); + LIB_FUNCTION("n88vx3C5nW8", "libkernel", 1, "libkernel", 1, 1, gettimeofday); + LIB_FUNCTION("n88vx3C5nW8", "libScePosix", 1, "libkernel", 1, 1, gettimeofday); } } // namespace Libraries::Kernel diff --git a/src/core/libraries/kernel/time_management.h b/src/core/libraries/kernel/time_management.h index ad420f7cf..beda41366 100644 --- a/src/core/libraries/kernel/time_management.h +++ b/src/core/libraries/kernel/time_management.h @@ -11,6 +11,16 @@ class SymbolsResolver; namespace Libraries::Kernel { +struct OrbisKernelTimeval { + time_t tv_sec; + u64 tv_usec; +}; + +struct OrbisKernelTimezone { + s32 tz_minuteswest; + s32 tz_dsttime; +}; + u64 PS4_SYSV_ABI sceKernelGetTscFrequency(); u64 PS4_SYSV_ABI sceKernelGetProcessTime(); u64 PS4_SYSV_ABI sceKernelGetProcessTimeCounter();