diff --git a/src/xenia/base/memory_posix.cc b/src/xenia/base/memory_posix.cc index 4098a3394b..2ff36a603d 100644 --- a/src/xenia/base/memory_posix.cc +++ b/src/xenia/base/memory_posix.cc @@ -85,11 +85,8 @@ void* AllocFixed(void* base_address, size_t length, AllocationType allocation_type, PageAccess access) { // mmap does not support reserve / commit, so ignore allocation_type. uint32_t prot = ToPosixProtectFlags(access); - int flags = MAP_PRIVATE | MAP_ANONYMOUS; - if (base_address != nullptr) { - flags |= MAP_FIXED; - } - void* result = mmap(base_address, length, prot, flags, -1, 0); + void* result = mmap(base_address, length, prot, + MAP_PRIVATE | MAP_FIXED | MAP_ANONYMOUS, -1, 0); if (result == MAP_FAILED) { return nullptr; } else { diff --git a/src/xenia/cpu/backend/x64/x64_backend.cc b/src/xenia/cpu/backend/x64/x64_backend.cc index a567a4baaf..4b520b6b2a 100644 --- a/src/xenia/cpu/backend/x64/x64_backend.cc +++ b/src/xenia/cpu/backend/x64/x64_backend.cc @@ -480,9 +480,9 @@ HostToGuestThunk X64ThunkEmitter::EmitHostToGuestThunk() { code_offsets.prolog = getSize(); // rsp + 0 = return address - mov(qword[rsp + 8 * 3], rdx); - mov(qword[rsp + 8 * 2], rsi); - mov(qword[rsp + 8 * 1], rdi); + // mov(qword[rsp + 8 * 3], rdx); + // mov(qword[rsp + 8 * 2], rsi); + // mov(qword[rsp + 8 * 1], rdi); sub(rsp, stack_size); code_offsets.prolog_stack_alloc = getSize(); @@ -501,9 +501,9 @@ HostToGuestThunk X64ThunkEmitter::EmitHostToGuestThunk() { code_offsets.epilog = getSize(); add(rsp, stack_size); - mov(rdi, qword[rsp + 8 * 1]); - mov(rsi, qword[rsp + 8 * 2]); - mov(rdx, qword[rsp + 8 * 3]); + // mov(rdi, qword[rsp + 8 * 1]); + // mov(rsi, qword[rsp + 8 * 2]); + // mov(rdx, qword[rsp + 8 * 3]); ret(); #else assert_always("Unknown platform ABI in host to guest thunk!"); diff --git a/src/xenia/vfs/devices/stfs_container_device.cc b/src/xenia/vfs/devices/stfs_container_device.cc index 1381786322..2400da0e0c 100644 --- a/src/xenia/vfs/devices/stfs_container_device.cc +++ b/src/xenia/vfs/devices/stfs_container_device.cc @@ -17,33 +17,9 @@ #include "xenia/base/math.h" #include "xenia/vfs/devices/stfs_container_entry.h" -#if XE_PLATFORM_WIN32 -#include "xenia/base/platform_win.h" -#define timegm _mkgmtime -#endif - namespace xe { namespace vfs { -// Convert FAT timestamp to 100-nanosecond intervals since January 1, 1601 (UTC) -uint64_t decode_fat_timestamp(uint32_t date, uint32_t time) { - struct tm tm = {0}; - // 80 is the difference between 1980 (FAT) and 1900 (tm); - tm.tm_year = ((0xFE00 & date) >> 9) + 80; - tm.tm_mon = (0x01E0 & date) >> 5; - tm.tm_mday = (0x001F & date) >> 0; - tm.tm_hour = (0xF800 & time) >> 11; - tm.tm_min = (0x07E0 & time) >> 5; - tm.tm_sec = (0x001F & time) << 1; // the value stored in 2-seconds intervals - tm.tm_isdst = 0; - time_t timet = timegm(&tm); - if (timet == -1) { - return 0; - } - // 11644473600LL is a difference between 1970 and 1601 - return (timet + 11644473600LL) * 10000000; -} - StfsContainerDevice::StfsContainerDevice(const std::string_view mount_path, const std::filesystem::path& host_path) : Device(mount_path), diff --git a/src/xenia/vfs/devices/stfs_xbox.h b/src/xenia/vfs/devices/stfs_xbox.h index 0cba213937..54eaabb47c 100644 --- a/src/xenia/vfs/devices/stfs_xbox.h +++ b/src/xenia/vfs/devices/stfs_xbox.h @@ -10,12 +10,40 @@ #ifndef XENIA_VFS_DEVICES_STFS_XBOX_H_ #define XENIA_VFS_DEVICES_STFS_XBOX_H_ +#include + +#include "xenia/xbox.h" #include "xenia/base/string_util.h" #include "xenia/kernel/util/xex2_info.h" namespace xe { namespace vfs { +// Convert FAT timestamp to 100-nanosecond intervals since January 1, 1601 (UTC) +inline uint64_t decode_fat_timestamp(const uint32_t date, const uint32_t time) { + struct tm tm = {0}; + // 80 is the difference between 1980 (FAT) and 1900 (tm); + tm.tm_year = ((0xFE00 & date) >> 9) + 80; + tm.tm_mon = ((0x01E0 & date) >> 5) - 1; + tm.tm_mday = (0x001F & date) >> 0; + tm.tm_hour = (0xF800 & time) >> 11; + tm.tm_min = (0x07E0 & time) >> 5; + tm.tm_sec = (0x001F & time) << 1; // the value stored in 2-seconds intervals + tm.tm_isdst = 0; + +#if XE_PLATFORM_WIN32 + time_t timet = _mkgmtime(&tm); +#else + time_t timet = timegm(&tm); +#endif + + if (timet == -1) { + return 0; + } + // 11644473600LL is a difference between 1970 and 1601 + return (timet + 11644473600LL) * 10000000; +} + // Structs used for interchange between Xenia and actual Xbox360 kernel/XAM inline uint32_t load_uint24_be(const uint8_t* p) { diff --git a/src/xenia/vfs/premake5.lua b/src/xenia/vfs/premake5.lua index f312d93c6b..bd39df6f05 100644 --- a/src/xenia/vfs/premake5.lua +++ b/src/xenia/vfs/premake5.lua @@ -32,4 +32,5 @@ project("xenia-vfs-dump") resincludedirs({ project_root, }) +include("testing") diff --git a/src/xenia/vfs/testing/premake5.lua b/src/xenia/vfs/testing/premake5.lua new file mode 100644 index 0000000000..d9cd89626f --- /dev/null +++ b/src/xenia/vfs/testing/premake5.lua @@ -0,0 +1,8 @@ +project_root = "../../../.." +include(project_root.."/tools/build") + +test_suite("xenia-vfs-tests", project_root, ".", { + links = { + "xenia-vfs", + }, +}) diff --git a/src/xenia/vfs/testing/vfs_test.cc b/src/xenia/vfs/testing/vfs_test.cc new file mode 100644 index 0000000000..70a1c0f884 --- /dev/null +++ b/src/xenia/vfs/testing/vfs_test.cc @@ -0,0 +1,28 @@ +/** + ****************************************************************************** + * Xenia : Xbox 360 Emulator Research Project * + ****************************************************************************** + * Copyright 2023 Ben Vanik. All rights reserved. * + * Released under the BSD license - see LICENSE in the root for more details. * + ****************************************************************************** + */ + +#include "xenia/vfs/devices/stfs_xbox.h" + +#include "third_party/catch/include/catch.hpp" + +namespace xe::vfs::test { + +TEST_CASE("STFS Decode date and time", "[stfs_decode]") { + SECTION("10 June 2022 19:46:00 UTC - Decode") { + const uint16_t date = 0x54CA; + const uint16_t time = 0x9DBD; + const uint64_t result = 132993639580000000; + + const uint64_t timestamp = decode_fat_timestamp(date, time); + + REQUIRE(timestamp == result); + } +} + +} // namespace xe::vfs::test