[VFS] Fixed crash on filename extraction from path.

Names are in CP1252 which fails conversion to utf8.
This commit is contained in:
Gliniak 2024-08-31 18:15:13 +02:00
parent 59eed7818f
commit 02f5316562
18 changed files with 44 additions and 29 deletions

View File

@ -112,7 +112,7 @@ bool DiscImageDevice::VerifyMagic(ParseState* state, size_t offset) {
DiscImageDevice::Error DiscImageDevice::ReadAllEntries( DiscImageDevice::Error DiscImageDevice::ReadAllEntries(
ParseState* state, const uint8_t* root_buffer) { ParseState* state, const uint8_t* root_buffer) {
auto root_entry = new DiscImageEntry(this, nullptr, "", mmap_.get()); auto root_entry = new DiscImageEntry(this, nullptr, "", "", mmap_.get());
root_entry->attributes_ = kFileAttributeDirectory; root_entry->attributes_ = kFileAttributeDirectory;
root_entry_ = std::unique_ptr<Entry>(root_entry); root_entry_ = std::unique_ptr<Entry>(root_entry);

View File

@ -18,8 +18,9 @@ namespace xe {
namespace vfs { namespace vfs {
DiscImageEntry::DiscImageEntry(Device* device, Entry* parent, DiscImageEntry::DiscImageEntry(Device* device, Entry* parent,
const std::string_view path, MappedMemory* mmap) const std::string_view path,
: Entry(device, parent, path), const std::string_view name, MappedMemory* mmap)
: Entry(device, parent, path, name),
mmap_(mmap), mmap_(mmap),
data_offset_(0), data_offset_(0),
data_size_(0) {} data_size_(0) {}
@ -30,7 +31,8 @@ std::unique_ptr<DiscImageEntry> DiscImageEntry::Create(
Device* device, Entry* parent, const std::string_view name, Device* device, Entry* parent, const std::string_view name,
MappedMemory* mmap) { MappedMemory* mmap) {
auto path = xe::utf8::join_guest_paths(parent->path(), name); auto path = xe::utf8::join_guest_paths(parent->path(), name);
auto entry = std::make_unique<DiscImageEntry>(device, parent, path, mmap); auto entry =
std::make_unique<DiscImageEntry>(device, parent, path, name, mmap);
return std::move(entry); return std::move(entry);
} }

View File

@ -24,7 +24,7 @@ class DiscImageDevice;
class DiscImageEntry : public Entry { class DiscImageEntry : public Entry {
public: public:
DiscImageEntry(Device* device, Entry* parent, const std::string_view path, DiscImageEntry(Device* device, Entry* parent, const std::string_view path,
MappedMemory* mmap); const std::string_view name, MappedMemory* mmap);
~DiscImageEntry() override; ~DiscImageEntry() override;
static std::unique_ptr<DiscImageEntry> Create(Device* device, Entry* parent, static std::unique_ptr<DiscImageEntry> Create(Device* device, Entry* parent,

View File

@ -36,7 +36,7 @@ bool DiscZarchiveDevice::Initialize() {
const std::string root_path = std::string("/"); const std::string root_path = std::string("/");
const ZArchiveNodeHandle handle = reader_->LookUp(root_path); const ZArchiveNodeHandle handle = reader_->LookUp(root_path);
auto root_entry = new DiscZarchiveEntry(this, nullptr, root_path); auto root_entry = new DiscZarchiveEntry(this, nullptr, root_path, "");
root_entry->attributes_ = kFileAttributeDirectory; root_entry->attributes_ = kFileAttributeDirectory;
root_entry->handle_ = static_cast<uint32_t>(handle); root_entry->handle_ = static_cast<uint32_t>(handle);
root_entry->name_ = root_path; root_entry->name_ = root_path;
@ -79,7 +79,8 @@ bool DiscZarchiveDevice::ReadAllEntries(const std::string& path,
} }
if (reader_->IsFile(handle)) { if (reader_->IsFile(handle)) {
auto entry = new DiscZarchiveEntry(this, parent, path); auto entry = new DiscZarchiveEntry(
this, parent, path, xe::utf8::find_name_from_guest_path(path));
entry->attributes_ = kFileAttributeReadOnly; entry->attributes_ = kFileAttributeReadOnly;
entry->handle_ = static_cast<uint32_t>(handle); entry->handle_ = static_cast<uint32_t>(handle);
entry->parent_ = parent; entry->parent_ = parent;
@ -103,7 +104,8 @@ bool DiscZarchiveDevice::ReadAllEntries(const std::string& path,
return false; return false;
} }
auto entry = new DiscZarchiveEntry(this, parent, full_path); auto entry =
new DiscZarchiveEntry(this, parent, full_path, dirEntry.name);
entry->handle_ = static_cast<uint32_t>(fileHandle); entry->handle_ = static_cast<uint32_t>(fileHandle);
entry->data_offset_ = 0; entry->data_offset_ = 0;

View File

@ -20,8 +20,9 @@ namespace xe {
namespace vfs { namespace vfs {
DiscZarchiveEntry::DiscZarchiveEntry(Device* device, Entry* parent, DiscZarchiveEntry::DiscZarchiveEntry(Device* device, Entry* parent,
const std::string_view path) const std::string_view path,
: Entry(device, parent, path), const std::string_view name)
: Entry(device, parent, path, name),
data_offset_(0), data_offset_(0),
data_size_(0), data_size_(0),
handle_(ZARCHIVE_INVALID_NODE) {} handle_(ZARCHIVE_INVALID_NODE) {}
@ -31,7 +32,7 @@ DiscZarchiveEntry::~DiscZarchiveEntry() = default;
std::unique_ptr<DiscZarchiveEntry> DiscZarchiveEntry::Create( std::unique_ptr<DiscZarchiveEntry> DiscZarchiveEntry::Create(
Device* device, Entry* parent, const std::string_view name) { Device* device, Entry* parent, const std::string_view name) {
auto path = name; // xe::utf8::join_guest_paths(parent->path(), name); auto path = name; // xe::utf8::join_guest_paths(parent->path(), name);
auto entry = std::make_unique<DiscZarchiveEntry>(device, parent, path); auto entry = std::make_unique<DiscZarchiveEntry>(device, parent, path, name);
return std::move(entry); return std::move(entry);
} }

View File

@ -23,7 +23,8 @@ class DiscZarchiveDevice;
class DiscZarchiveEntry : public Entry { class DiscZarchiveEntry : public Entry {
public: public:
DiscZarchiveEntry(Device* device, Entry* parent, const std::string_view path); DiscZarchiveEntry(Device* device, Entry* parent, const std::string_view path,
const std::string_view name);
~DiscZarchiveEntry() override; ~DiscZarchiveEntry() override;
static std::unique_ptr<DiscZarchiveEntry> Create(Device* device, static std::unique_ptr<DiscZarchiveEntry> Create(Device* device,

View File

@ -39,7 +39,7 @@ bool HostPathDevice::Initialize() {
} }
} }
auto root_entry = new HostPathEntry(this, nullptr, "", host_path_); auto root_entry = new HostPathEntry(this, nullptr, "", "", host_path_);
root_entry->attributes_ = kFileAttributeDirectory; root_entry->attributes_ = kFileAttributeDirectory;
root_entry_ = std::unique_ptr<Entry>(root_entry); root_entry_ = std::unique_ptr<Entry>(root_entry);
PopulateEntry(root_entry); PopulateEntry(root_entry);

View File

@ -23,8 +23,9 @@ namespace vfs {
HostPathEntry::HostPathEntry(Device* device, Entry* parent, HostPathEntry::HostPathEntry(Device* device, Entry* parent,
const std::string_view path, const std::string_view path,
const std::string_view name,
const std::filesystem::path& host_path) const std::filesystem::path& host_path)
: Entry(device, parent, path), host_path_(host_path) {} : Entry(device, parent, path, name), host_path_(host_path) {}
HostPathEntry::~HostPathEntry() = default; HostPathEntry::~HostPathEntry() = default;
@ -33,7 +34,8 @@ HostPathEntry* HostPathEntry::Create(Device* device, Entry* parent,
xe::filesystem::FileInfo file_info) { xe::filesystem::FileInfo file_info) {
auto path = xe::utf8::join_guest_paths(parent->path(), auto path = xe::utf8::join_guest_paths(parent->path(),
xe::path_to_utf8(file_info.name)); xe::path_to_utf8(file_info.name));
auto entry = new HostPathEntry(device, parent, path, full_path); auto entry = new HostPathEntry(device, parent, path,
xe::path_to_utf8(file_info.name), full_path);
entry->create_timestamp_ = file_info.create_timestamp; entry->create_timestamp_ = file_info.create_timestamp;
entry->access_timestamp_ = file_info.access_timestamp; entry->access_timestamp_ = file_info.access_timestamp;

View File

@ -23,6 +23,7 @@ class HostPathDevice;
class HostPathEntry : public Entry { class HostPathEntry : public Entry {
public: public:
HostPathEntry(Device* device, Entry* parent, const std::string_view path, HostPathEntry(Device* device, Entry* parent, const std::string_view path,
const std::string_view name,
const std::filesystem::path& host_path); const std::filesystem::path& host_path);
~HostPathEntry() override; ~HostPathEntry() override;

View File

@ -26,7 +26,7 @@ NullDevice::NullDevice(const std::string& mount_path,
NullDevice::~NullDevice() = default; NullDevice::~NullDevice() = default;
bool NullDevice::Initialize() { bool NullDevice::Initialize() {
auto root_entry = new NullEntry(this, nullptr, mount_path_); auto root_entry = new NullEntry(this, nullptr, mount_path_, "");
root_entry->attributes_ = kFileAttributeDirectory; root_entry->attributes_ = kFileAttributeDirectory;
root_entry_ = std::unique_ptr<Entry>(root_entry); root_entry_ = std::unique_ptr<Entry>(root_entry);

View File

@ -20,14 +20,15 @@
namespace xe { namespace xe {
namespace vfs { namespace vfs {
NullEntry::NullEntry(Device* device, Entry* parent, std::string path) NullEntry::NullEntry(Device* device, Entry* parent, std::string path,
: Entry(device, parent, path) {} const std::string_view name)
: Entry(device, parent, path, name) {}
NullEntry::~NullEntry() = default; NullEntry::~NullEntry() = default;
NullEntry* NullEntry::Create(Device* device, Entry* parent, NullEntry* NullEntry::Create(Device* device, Entry* parent,
const std::string& path) { const std::string& path) {
auto entry = new NullEntry(device, parent, path); auto entry = new NullEntry(device, parent, path, "");
entry->create_timestamp_ = 0; entry->create_timestamp_ = 0;
entry->access_timestamp_ = 0; entry->access_timestamp_ = 0;

View File

@ -22,7 +22,8 @@ class NullDevice;
class NullEntry : public Entry { class NullEntry : public Entry {
public: public:
NullEntry(Device* device, Entry* parent, std::string path); NullEntry(Device* device, Entry* parent, std::string path,
const std::string_view name);
~NullEntry() override; ~NullEntry() override;
static NullEntry* Create(Device* device, Entry* parent, static NullEntry* Create(Device* device, Entry* parent,

View File

@ -17,8 +17,9 @@ namespace vfs {
XContentContainerEntry::XContentContainerEntry(Device* device, Entry* parent, XContentContainerEntry::XContentContainerEntry(Device* device, Entry* parent,
const std::string_view path, const std::string_view path,
const std::string_view name,
MultiFileHandles* files) MultiFileHandles* files)
: Entry(device, parent, path), : Entry(device, parent, path, name),
files_(files), files_(files),
data_offset_(0), data_offset_(0),
data_size_(0), data_size_(0),
@ -30,8 +31,8 @@ std::unique_ptr<XContentContainerEntry> XContentContainerEntry::Create(
Device* device, Entry* parent, const std::string_view name, Device* device, Entry* parent, const std::string_view name,
MultiFileHandles* files) { MultiFileHandles* files) {
auto path = xe::utf8::join_guest_paths(parent->path(), name); auto path = xe::utf8::join_guest_paths(parent->path(), name);
auto entry = auto entry = std::make_unique<XContentContainerEntry>(device, parent, path,
std::make_unique<XContentContainerEntry>(device, parent, path, files); name, files);
return std::move(entry); return std::move(entry);
} }

View File

@ -26,7 +26,8 @@ class XContentContainerDevice;
class XContentContainerEntry : public Entry { class XContentContainerEntry : public Entry {
public: public:
XContentContainerEntry(Device* device, Entry* parent, XContentContainerEntry(Device* device, Entry* parent,
const std::string_view path, MultiFileHandles* files); const std::string_view path,
const std::string_view name, MultiFileHandles* files);
~XContentContainerEntry() override; ~XContentContainerEntry() override;
static std::unique_ptr<XContentContainerEntry> Create( static std::unique_ptr<XContentContainerEntry> Create(

View File

@ -53,7 +53,7 @@ XContentContainerDevice::Result StfsContainerDevice::LoadHostFiles(
StfsContainerDevice::Result StfsContainerDevice::Read() { StfsContainerDevice::Result StfsContainerDevice::Read() {
auto& file = files_.at(0); auto& file = files_.at(0);
auto root_entry = new XContentContainerEntry(this, nullptr, "", &files_); auto root_entry = new XContentContainerEntry(this, nullptr, "", "", &files_);
root_entry->attributes_ = kFileAttributeDirectory; root_entry->attributes_ = kFileAttributeDirectory;
root_entry_ = std::unique_ptr<Entry>(root_entry); root_entry_ = std::unique_ptr<Entry>(root_entry);

View File

@ -99,7 +99,7 @@ XContentContainerDevice::Result SvodContainerDevice::Read() {
const uint64_t root_creation_timestamp = const uint64_t root_creation_timestamp =
decode_fat_timestamp(root_data.creation_date, root_data.creation_time); decode_fat_timestamp(root_data.creation_date, root_data.creation_time);
auto root_entry = new XContentContainerEntry(this, nullptr, "", &files_); auto root_entry = new XContentContainerEntry(this, nullptr, "", "", &files_);
root_entry->attributes_ = kFileAttributeDirectory; root_entry->attributes_ = kFileAttributeDirectory;
root_entry->access_timestamp_ = root_creation_timestamp; root_entry->access_timestamp_ = root_creation_timestamp;
root_entry->create_timestamp_ = root_creation_timestamp; root_entry->create_timestamp_ = root_creation_timestamp;

View File

@ -16,10 +16,12 @@
namespace xe { namespace xe {
namespace vfs { namespace vfs {
Entry::Entry(Device* device, Entry* parent, const std::string_view path) Entry::Entry(Device* device, Entry* parent, const std::string_view path,
const std::string_view name)
: device_(device), : device_(device),
parent_(parent), parent_(parent),
path_(path), path_(path),
name_(name),
attributes_(0), attributes_(0),
size_(0), size_(0),
allocation_size_(0), allocation_size_(0),
@ -29,7 +31,6 @@ Entry::Entry(Device* device, Entry* parent, const std::string_view path)
delete_on_close_(false) { delete_on_close_(false) {
assert_not_null(device); assert_not_null(device);
absolute_path_ = xe::utf8::join_guest_paths(device->mount_path(), path); absolute_path_ = xe::utf8::join_guest_paths(device->mount_path(), path);
name_ = xe::utf8::find_name_from_guest_path(path);
} }
Entry::~Entry() = default; Entry::~Entry() = default;

View File

@ -134,7 +134,8 @@ class Entry {
virtual void update() { return; } virtual void update() { return; }
protected: protected:
Entry(Device* device, Entry* parent, const std::string_view path); Entry(Device* device, Entry* parent, const std::string_view path,
const std::string_view name);
virtual std::unique_ptr<Entry> CreateEntryInternal( virtual std::unique_ptr<Entry> CreateEntryInternal(
const std::string_view name, uint32_t attributes) { const std::string_view name, uint32_t attributes) {