mirror of
https://github.com/shadps4-emu/shadPS4.git
synced 2026-04-26 12:55:14 -06:00
lseek on devices
fixed dirents not updating when RefreshDirents is called too fast after lseek
This commit is contained in:
parent
0ae2275e2d
commit
008b61d28d
@ -30,7 +30,6 @@ public:
|
||||
s64 read(void* buf, u64 count) override { DEVICE_STUB(); };
|
||||
s64 write(const void* buf, u64 count) override { DEVICE_STUB(); };
|
||||
s32 ioctl(u64 cmd, Common::VaCtx* args) override { DEVICE_STUB(); };
|
||||
s64 lseek(s64 current, s64 offset, s32 whence) override { DEVICE_STUB(); };
|
||||
s32 fstat(Libraries::Kernel::OrbisKernelStat* sb) override { DEVICE_STUB(); };
|
||||
s32 fsync() override { DEVICE_STUB(); };
|
||||
s32 ftruncate(s64 length) override { DEVICE_STUB(); };
|
||||
|
||||
@ -30,7 +30,6 @@ public:
|
||||
s64 read(void* buf, u64 count) override { DEVICE_STUB(); };
|
||||
s64 write(const void* buf, u64 count) override { DEVICE_STUB(); };
|
||||
s32 ioctl(u64 cmd, Common::VaCtx* args) override { DEVICE_STUB(); };
|
||||
s64 lseek(s64 current, s64 offset, s32 whence) override { DEVICE_STUB(); };
|
||||
s32 fstat(Libraries::Kernel::OrbisKernelStat* sb) override { DEVICE_STUB(); };
|
||||
s32 fsync() override { DEVICE_STUB(); };
|
||||
s32 ftruncate(s64 length) override { DEVICE_STUB(); };
|
||||
|
||||
@ -40,7 +40,6 @@ public:
|
||||
// clang-format off
|
||||
s64 read(void* buf, u64 count) override { DEVICE_STUB(); };
|
||||
s32 ioctl(u64 cmd, Common::VaCtx* args) override { DEVICE_STUB(); }
|
||||
s64 lseek(s64 current, s64 offset, s32 whence) override { DEVICE_STUB(); }
|
||||
s32 fstat(Libraries::Kernel::OrbisKernelStat* sb) override { DEVICE_STUB(); }
|
||||
s32 ftruncate(s64 length) override { DEVICE_STUB(); }
|
||||
s64 getdents(void* buf, u32 nbytes, s64 offset, s64* basep) override { DEVICE_STUB(); }
|
||||
|
||||
@ -23,7 +23,6 @@ public:
|
||||
s64 read(void* buf, u64 count) override { return 0; };
|
||||
s64 write(const void* buf, u64 count) override { return 0; };
|
||||
s32 ioctl(u64 cmd, Common::VaCtx* args) override { return 0; };
|
||||
s64 lseek(s64 current, s64 offset, s32 whence) override { return 0; };
|
||||
s32 fstat(Libraries::Kernel::OrbisKernelStat* sb) override { return 0; };
|
||||
s32 fsync() override { return 0; };
|
||||
s32 ftruncate(s64 length) override { return 0; };
|
||||
|
||||
@ -30,7 +30,6 @@ public:
|
||||
|
||||
// clang-format off
|
||||
s32 ioctl(u64 cmd, Common::VaCtx* args) override { DEVICE_STUB(); }
|
||||
s64 lseek(s64 current, s64 offset, s32 whence) override { DEVICE_STUB(); }
|
||||
s32 fstat(Libraries::Kernel::OrbisKernelStat* sb) override { DEVICE_STUB(); }
|
||||
s32 fsync() override { DEVICE_STUB(); }
|
||||
s32 ftruncate(s64 length) override { DEVICE_STUB(); }
|
||||
|
||||
@ -29,7 +29,6 @@ public:
|
||||
|
||||
// clang-format off
|
||||
s32 ioctl(u64 cmd, Common::VaCtx* args) override { DEVICE_STUB(); }
|
||||
s64 lseek(s64 current, s64 offset, s32 whence) override { DEVICE_STUB(); }
|
||||
s32 fstat(Libraries::Kernel::OrbisKernelStat* sb) override { DEVICE_STUB(); }
|
||||
s32 fsync() override { DEVICE_STUB(); }
|
||||
s32 ftruncate(s64 length) override { DEVICE_STUB(); }
|
||||
|
||||
@ -30,7 +30,6 @@ public:
|
||||
// clang-format off
|
||||
s64 read(void* buf, u64 count) override { DEVICE_STUB(); }
|
||||
s64 write(const void* buf, u64 count) override { DEVICE_STUB(); }
|
||||
s64 lseek(s64 current, s64 offset, s32 whence) override { DEVICE_STUB(); }
|
||||
s32 fstat(Libraries::Kernel::OrbisKernelStat* sb) override { DEVICE_STUB(); }
|
||||
s32 fsync() override { DEVICE_STUB(); }
|
||||
s32 ftruncate(s64 length) override { DEVICE_STUB(); }
|
||||
|
||||
@ -30,7 +30,6 @@ public:
|
||||
|
||||
// clang-format off
|
||||
s32 ioctl(u64 cmd, Common::VaCtx* args) override { DEVICE_STUB(); }
|
||||
s64 lseek(s64 current, s64 offset, s32 whence) override { DEVICE_STUB(); }
|
||||
s32 fstat(Libraries::Kernel::OrbisKernelStat* sb) override { DEVICE_STUB(); }
|
||||
s32 fsync() override { DEVICE_STUB(); }
|
||||
s32 ftruncate(s64 length) override { DEVICE_STUB(); }
|
||||
|
||||
@ -30,7 +30,6 @@ public:
|
||||
|
||||
// clang-format off
|
||||
s32 ioctl(u64 cmd, Common::VaCtx* args) override { DEVICE_STUB(); }
|
||||
s64 lseek(s64 current, s64 offset, s32 whence) override { DEVICE_STUB(); }
|
||||
s32 fstat(Libraries::Kernel::OrbisKernelStat* sb) override { DEVICE_STUB(); }
|
||||
s32 fsync() override { DEVICE_STUB(); }
|
||||
s32 ftruncate(s64 length) override { DEVICE_STUB(); }
|
||||
|
||||
@ -24,6 +24,7 @@ public:
|
||||
|
||||
s64 pread(void* buf, u64 count, s64 offset) final override;
|
||||
s64 pwrite(const void* buf, u64 count, s64 offset) final override;
|
||||
s64 lseek(s64 current, s64 offset, s32 whence) final override;
|
||||
};
|
||||
|
||||
} // namespace QuasiFS
|
||||
@ -30,7 +30,7 @@ protected:
|
||||
std::map<std::string, inode_ptr> entries{};
|
||||
|
||||
void RebuildDirents(void);
|
||||
time_t last_dirent_rebuild_time{0};
|
||||
bool dirents_changed{false};
|
||||
std::vector<u8> dirent_cache_bin{};
|
||||
|
||||
public:
|
||||
|
||||
@ -31,4 +31,11 @@ s64 Device::pwrite(const void* buf, u64 count, s64 offset) {
|
||||
return write(buf, count);
|
||||
}
|
||||
|
||||
s64 Device::lseek(s64 current, s64 offset, s32 whence) {
|
||||
return ((QuasiFS::SeekOrigin::ORIGIN == whence) * offset) +
|
||||
((QuasiFS::SeekOrigin::CURRENT == whence) * (current + offset)) +
|
||||
((QuasiFS::SeekOrigin::END == whence) * ((offset > 0) * offset));
|
||||
// ::END is pro-forma
|
||||
}
|
||||
|
||||
} // namespace QuasiFS
|
||||
@ -26,6 +26,7 @@ s64 QuasiDirectory::pread(void* buf, u64 count, s64 offset) {
|
||||
|
||||
s64 QuasiDirectory::lseek(s64 current, s64 offset, s32 whence) {
|
||||
RebuildDirents();
|
||||
this->dirents_changed = false;
|
||||
return Inode::lseek(current, offset, whence);
|
||||
}
|
||||
|
||||
@ -41,6 +42,7 @@ s32 QuasiDirectory::ftruncate(s64 length) {
|
||||
|
||||
s64 QuasiDirectory::getdents(void* buf, u32 count, s64 offset, s64* basep) {
|
||||
RebuildDirents();
|
||||
st.st_atim.tv_sec = time(0);
|
||||
|
||||
// at this point count is ALWAYS >512 (checked in VIO Driver)
|
||||
// always returns up to 512 bytes
|
||||
@ -122,10 +124,9 @@ std::vector<std::string> QuasiDirectory::list() {
|
||||
}
|
||||
|
||||
void QuasiDirectory::RebuildDirents(void) {
|
||||
// adding/removing entries changes mtime
|
||||
if (this->st.st_mtim.tv_sec == this->last_dirent_rebuild_time)
|
||||
if (this->dirents_changed)
|
||||
return;
|
||||
this->last_dirent_rebuild_time = this->st.st_mtim.tv_sec;
|
||||
this->dirents_changed = false;
|
||||
|
||||
constexpr u32 dirent_meta_size = sizeof(dirent_t::d_fileno) + sizeof(dirent_t::d_type) +
|
||||
sizeof(dirent_t::d_namlen) + sizeof(dirent_t::d_reclen);
|
||||
|
||||
@ -22,6 +22,7 @@ DirectoryPFS::~DirectoryPFS() = default;
|
||||
|
||||
s64 DirectoryPFS::pread(void* buf, u64 count, s64 offset) {
|
||||
RebuildDirents();
|
||||
st.st_atim.tv_sec = time(0);
|
||||
|
||||
// data is contiguous. i think that's how it's said
|
||||
// anyway, everything goes raw
|
||||
@ -67,6 +68,7 @@ s64 DirectoryPFS::lseek(s64 current, s64 offset, s32 whence) {
|
||||
// future
|
||||
s64 DirectoryPFS::getdents(void* buf, u32 count, s64 offset, s64* basep) {
|
||||
RebuildDirents();
|
||||
st.st_atim.tv_sec = time(0);
|
||||
|
||||
if (count != 65536)
|
||||
LOG_CRITICAL(Kernel_Fs, "PFS dirents read with count={} (which is not 65536) (report this)",
|
||||
@ -123,11 +125,9 @@ s64 DirectoryPFS::getdents(void* buf, u32 count, s64 offset, s64* basep) {
|
||||
}
|
||||
|
||||
void DirectoryPFS::RebuildDirents(void) {
|
||||
|
||||
// adding/removing entries changes mtime
|
||||
if (this->st.st_mtim.tv_sec == this->last_dirent_rebuild_time)
|
||||
if (this->dirents_changed)
|
||||
return;
|
||||
this->last_dirent_rebuild_time = this->st.st_mtim.tv_sec;
|
||||
this->dirents_changed = false;
|
||||
|
||||
constexpr u32 dirent_meta_size = sizeof(dirent_pfs_t::d_fileno) + sizeof(dirent_pfs_t::d_type) +
|
||||
sizeof(dirent_pfs_t::d_namlen) +
|
||||
|
||||
Loading…
Reference in New Issue
Block a user