mirror of
https://github.com/libretro/scummvm.git
synced 2024-11-28 03:40:36 +00:00
COMMON: Move Archive API to Path
This commit is contained in:
parent
3c5fe56de6
commit
93a8f7f4d6
@ -239,7 +239,7 @@ SeekableReadStream *MemcachingCaseInsensitiveArchive::createReadStreamForMemberI
|
||||
return memStream;
|
||||
}
|
||||
|
||||
SharedArchiveContents MemcachingCaseInsensitiveArchive::readContentsForPathAltStream(const String &translatedPath, AltStreamType altStreamType) const {
|
||||
SharedArchiveContents MemcachingCaseInsensitiveArchive::readContentsForPathAltStream(const Path &translatedPath, AltStreamType altStreamType) const {
|
||||
return SharedArchiveContents();
|
||||
}
|
||||
|
||||
@ -251,7 +251,7 @@ bool MemcachingCaseInsensitiveArchive::CacheKey_EqualTo::operator()(const CacheK
|
||||
}
|
||||
|
||||
uint MemcachingCaseInsensitiveArchive::CacheKey_Hash::operator()(const CacheKey &x) const {
|
||||
return static_cast<uint>(hashit_lower(x.path) * 1000003u) ^ static_cast<uint>(x.altStreamType);
|
||||
return static_cast<uint>(x.path.hashIgnoreCase() * 1000003u) ^ static_cast<uint>(x.altStreamType);
|
||||
};
|
||||
|
||||
SearchSet::ArchiveNodeList::iterator SearchSet::find(const String &name) {
|
||||
|
@ -272,20 +272,18 @@ public:
|
||||
SeekableReadStream *createReadStreamForMember(const Path &path) const;
|
||||
SeekableReadStream *createReadStreamForMemberAltStream(const Path &path, Common::AltStreamType altStreamType) const;
|
||||
|
||||
virtual String translatePath(const Path &path) const {
|
||||
// Most of users of this class implement DOS-like archives.
|
||||
// Others override this method.
|
||||
return normalizePath(path.toString('\\'), '\\');
|
||||
virtual Path translatePath(const Path &path) const {
|
||||
return path.normalize();
|
||||
}
|
||||
|
||||
virtual SharedArchiveContents readContentsForPath(const String &translatedPath) const = 0;
|
||||
virtual SharedArchiveContents readContentsForPathAltStream(const String &translatedPath, AltStreamType altStreamType) const;
|
||||
virtual SharedArchiveContents readContentsForPath(const Path &translatedPath) const = 0;
|
||||
virtual SharedArchiveContents readContentsForPathAltStream(const Path &translatedPath, AltStreamType altStreamType) const;
|
||||
|
||||
private:
|
||||
struct CacheKey {
|
||||
CacheKey();
|
||||
|
||||
String path;
|
||||
Path path;
|
||||
AltStreamType altStreamType;
|
||||
};
|
||||
|
||||
|
@ -61,7 +61,7 @@ ClickteamInstaller::ClickteamFileDescriptor::ClickteamFileDescriptor(const Click
|
||||
char *strings = (char *)tag + stringsOffset;
|
||||
char *p;
|
||||
for (p = strings; p < (char*)tag + lmax && *p; p++);
|
||||
_fileName = Common::String(strings, p - strings);
|
||||
_fileName = Common::Path(Common::String(strings, p - strings), Common::Path::kNoSeparator);
|
||||
_fileDescriptorOffset = off;
|
||||
_supported = true;
|
||||
_isPatchFile = false;
|
||||
@ -81,7 +81,7 @@ ClickteamInstaller::ClickteamFileDescriptor::ClickteamFileDescriptor(const Click
|
||||
byte type = tag[7];
|
||||
if (type != 0) {
|
||||
_supported = false;
|
||||
_fileName = "";
|
||||
_fileName.clear();
|
||||
_fileDataOffset = 0;
|
||||
_fileDescriptorOffset = off;
|
||||
_compressedSize = 0;
|
||||
@ -119,7 +119,7 @@ ClickteamInstaller::ClickteamFileDescriptor::ClickteamFileDescriptor(const Click
|
||||
char *strings = (char *)tag + stringsOffset;
|
||||
char *p;
|
||||
for (p = strings; p < (char*)tag + lmax && *p; p++);
|
||||
_fileName = Common::String(strings, p - strings);
|
||||
_fileName = Common::Path(Common::String(strings, p - strings), Common::Path::kNoSeparator);
|
||||
_fileDescriptorOffset = off;
|
||||
_compressedSize = 0;
|
||||
_fileDataOffset = 0;
|
||||
@ -305,7 +305,7 @@ struct TagHead {
|
||||
};
|
||||
|
||||
int ClickteamInstaller::findPatchIdx(const ClickteamFileDescriptor &desc, Common::SeekableReadStream *refStream,
|
||||
const Common::String &fileName,
|
||||
const Common::Path &fileName,
|
||||
uint32 crcXor, bool doWarn) {
|
||||
bool hasMatching = refStream->size() == desc._uncompressedSize; // Maybe already patched?
|
||||
for (uint i = 0; !hasMatching && i < desc._patchEntries.size(); i++)
|
||||
@ -315,7 +315,7 @@ int ClickteamInstaller::findPatchIdx(const ClickteamFileDescriptor &desc, Common
|
||||
}
|
||||
if (!hasMatching) {
|
||||
if (doWarn)
|
||||
warning("Couldn't find matching patch entry for file %s size %d", fileName.c_str(), (int)refStream->size());
|
||||
warning("Couldn't find matching patch entry for file %s size %d", fileName.toString().c_str(), (int)refStream->size());
|
||||
return -1;
|
||||
}
|
||||
uint32 crcOriginal = 0;
|
||||
@ -336,7 +336,7 @@ int ClickteamInstaller::findPatchIdx(const ClickteamFileDescriptor &desc, Common
|
||||
if (patchDescIdx == -1 && refStream->size() == desc._uncompressedSize && crcOriginal == desc._expectedCRC)
|
||||
return -2;
|
||||
if (patchDescIdx < 0 && doWarn) {
|
||||
warning("Couldn't find matching patch entry for file %s size %d and CRC 0x%x", fileName.c_str(), (int)refStream->size(), crcOriginal);
|
||||
warning("Couldn't find matching patch entry for file %s size %d and CRC 0x%x", fileName.toString().c_str(), (int)refStream->size(), crcOriginal);
|
||||
}
|
||||
return patchDescIdx;
|
||||
}
|
||||
@ -348,7 +348,7 @@ ClickteamInstaller* ClickteamInstaller::open(Common::SeekableReadStream *stream,
|
||||
|
||||
ClickteamInstaller* ClickteamInstaller::openPatch(Common::SeekableReadStream *stream, bool verifyOriginal, bool verifyAllowSkip,
|
||||
Common::Archive *reference, DisposeAfterUse::Flag dispose) {
|
||||
Common::HashMap<Common::String, ClickteamFileDescriptor, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo> files;
|
||||
Common::HashMap<Common::Path, ClickteamFileDescriptor, Common::Path::IgnoreCase_Hash, Common::Path::IgnoreCase_EqualTo> files;
|
||||
HashMap<uint16, Common::SharedPtr<ClickteamTag>> tags;
|
||||
uint32 crc_xor;
|
||||
|
||||
@ -435,10 +435,10 @@ ClickteamInstaller* ClickteamInstaller::openPatch(Common::SeekableReadStream *st
|
||||
return nullptr;
|
||||
|
||||
if (verifyOriginal && reference) {
|
||||
for (Common::HashMap<Common::String, ClickteamFileDescriptor, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo>::iterator i = files.begin(), end = files.end();
|
||||
for (Common::HashMap<Common::Path, ClickteamFileDescriptor, Common::Path::IgnoreCase_Hash, Common::Path::IgnoreCase_EqualTo>::iterator i = files.begin(), end = files.end();
|
||||
i != end; ++i) {
|
||||
if (i->_value._isPatchFile) {
|
||||
Common::ScopedPtr<Common::SeekableReadStream> refStream(reference->createReadStreamForMember(Common::Path(i->_key, '\\')));
|
||||
Common::ScopedPtr<Common::SeekableReadStream> refStream(reference->createReadStreamForMember(i->_key));
|
||||
if (!refStream) {
|
||||
if (verifyAllowSkip) {
|
||||
i->_value._isReferenceMissing = true;
|
||||
@ -453,7 +453,7 @@ ClickteamInstaller* ClickteamInstaller::openPatch(Common::SeekableReadStream *st
|
||||
}
|
||||
|
||||
if (!reference) {
|
||||
for (Common::HashMap<Common::String, ClickteamFileDescriptor, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo>::iterator i = files.begin(), end = files.end();
|
||||
for (Common::HashMap<Common::Path, ClickteamFileDescriptor, Common::Path::IgnoreCase_Hash, Common::Path::IgnoreCase_EqualTo>::iterator i = files.begin(), end = files.end();
|
||||
i != end; ++i) {
|
||||
if (i->_value._isPatchFile) {
|
||||
i->_value._isReferenceMissing = true;
|
||||
@ -471,7 +471,7 @@ bool ClickteamInstaller::hasFile(const Path &path) const {
|
||||
int ClickteamInstaller::listMembers(ArchiveMemberList &list) const {
|
||||
int members = 0;
|
||||
|
||||
for (Common::HashMap<Common::String, ClickteamFileDescriptor, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo>::const_iterator i = _files.begin(), end = _files.end();
|
||||
for (Common::HashMap<Common::Path, ClickteamFileDescriptor, Common::Path::IgnoreCase_Hash, Common::Path::IgnoreCase_EqualTo>::const_iterator i = _files.begin(), end = _files.end();
|
||||
i != end; ++i) {
|
||||
if (!i->_value._isReferenceMissing) {
|
||||
list.push_back(ArchiveMemberList::value_type(new GenericArchiveMember(i->_key, *this)));
|
||||
@ -483,7 +483,7 @@ int ClickteamInstaller::listMembers(ArchiveMemberList &list) const {
|
||||
}
|
||||
|
||||
const ArchiveMemberPtr ClickteamInstaller::getMember(const Path &path) const {
|
||||
Common::String translated = translatePath(path);
|
||||
Common::Path translated = translatePath(path);
|
||||
ClickteamFileDescriptor el;
|
||||
if (!_files.tryGetVal(translated, el))
|
||||
return nullptr;
|
||||
@ -494,7 +494,7 @@ const ArchiveMemberPtr ClickteamInstaller::getMember(const Path &path) const {
|
||||
return Common::SharedPtr<Common::ArchiveMember>(new GenericArchiveMember(el._fileName, *this));
|
||||
}
|
||||
|
||||
Common::SharedArchiveContents ClickteamInstaller::readContentsForPath(const Common::String& translated) const {
|
||||
Common::SharedArchiveContents ClickteamInstaller::readContentsForPath(const Common::Path &translated) const {
|
||||
ClickteamFileDescriptor desc;
|
||||
byte *uncompressedBuffer = nullptr;
|
||||
|
||||
@ -504,9 +504,9 @@ Common::SharedArchiveContents ClickteamInstaller::readContentsForPath(const Comm
|
||||
return Common::SharedArchiveContents();
|
||||
|
||||
if (desc._isPatchFile) {
|
||||
Common::ScopedPtr<Common::SeekableReadStream> refStream(_reference->createReadStreamForMemberNext(Common::Path(translated, '\\'), this));
|
||||
Common::ScopedPtr<Common::SeekableReadStream> refStream(_reference->createReadStreamForMemberNext(translated, this));
|
||||
if (!refStream) {
|
||||
warning("Couldn't open reference file for %s. Skipping", translated.c_str());
|
||||
warning("Couldn't open reference file for %s. Skipping", translated.toString('\\').c_str());
|
||||
return Common::SharedArchiveContents();
|
||||
}
|
||||
int patchDescIdx = findPatchIdx(desc, refStream.get(), translated, _crcXor, true);
|
||||
@ -608,7 +608,7 @@ Common::SharedArchiveContents ClickteamInstaller::readContentsForPath(const Comm
|
||||
uint32 actualCrc = computeCRC(uncompressedBuffer, desc._uncompressedSize, 0);
|
||||
|
||||
if (actualCrc != expectedCrc) {
|
||||
warning("CRC mismatch for %s: expected=%08x (obfuscated %08x), actual=%08x (back %08x)", desc._fileName.c_str(), expectedCrc, desc._expectedCRC, actualCrc, actualCrc ^ _crcXor);
|
||||
warning("CRC mismatch for %s: expected=%08x (obfuscated %08x), actual=%08x (back %08x)", desc._fileName.toString().c_str(), expectedCrc, desc._expectedCRC, actualCrc, actualCrc ^ _crcXor);
|
||||
delete[] uncompressedBuffer;
|
||||
return Common::SharedArchiveContents();
|
||||
}
|
||||
|
@ -57,7 +57,7 @@ public:
|
||||
bool hasFile(const Common::Path &path) const override;
|
||||
int listMembers(Common::ArchiveMemberList&) const override;
|
||||
const ArchiveMemberPtr getMember(const Common::Path &path) const override;
|
||||
Common::SharedArchiveContents readContentsForPath(const Common::String& translated) const override;
|
||||
Common::SharedArchiveContents readContentsForPath(const Common::Path &translated) const override;
|
||||
|
||||
ClickteamTag* getTag(ClickteamTagId tagId) const;
|
||||
|
||||
@ -74,7 +74,7 @@ private:
|
||||
};
|
||||
class ClickteamFileDescriptor {
|
||||
private:
|
||||
Common::String _fileName;
|
||||
Common::Path _fileName;
|
||||
|
||||
// Offset of the file contents relative to the beginning of block3
|
||||
uint32 _fileDataOffset;
|
||||
@ -97,8 +97,8 @@ private:
|
||||
ClickteamFileDescriptor() : _fileDataOffset(0), _fileDescriptorOffset(0), _compressedSize(0), _uncompressedSize(0) {}
|
||||
};
|
||||
|
||||
ClickteamInstaller(Common::HashMap<Common::String, ClickteamFileDescriptor, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo> files,
|
||||
Common::HashMap<uint16, Common::SharedPtr<ClickteamTag>> tags,
|
||||
ClickteamInstaller(const Common::HashMap<Common::Path, ClickteamFileDescriptor, Common::Path::IgnoreCase_Hash, Common::Path::IgnoreCase_EqualTo> &files,
|
||||
const Common::HashMap<uint16, Common::SharedPtr<ClickteamTag>> &tags,
|
||||
uint32 crcXor, uint32 block3Offset, uint32 block3Size, Common::SeekableReadStream *stream,
|
||||
Common::Archive *reference,
|
||||
DisposeAfterUse::Flag dispose)
|
||||
@ -106,9 +106,9 @@ private:
|
||||
_reference(reference) {
|
||||
}
|
||||
|
||||
static int findPatchIdx(const ClickteamFileDescriptor &desc, Common::SeekableReadStream *refStream, const Common::String &fileName,
|
||||
static int findPatchIdx(const ClickteamFileDescriptor &desc, Common::SeekableReadStream *refStream, const Common::Path &fileName,
|
||||
uint32 crcXor, bool doWarn);
|
||||
Common::HashMap<Common::String, ClickteamFileDescriptor, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo> _files;
|
||||
Common::HashMap<Common::Path, ClickteamFileDescriptor, Common::Path::IgnoreCase_Hash, Common::Path::IgnoreCase_EqualTo> _files;
|
||||
Common::HashMap<uint16, Common::SharedPtr<ClickteamTag>> _tags;
|
||||
Common::DisposablePtr<Common::SeekableReadStream> _stream;
|
||||
uint32 _crcXor, _block3Offset/*, _block3Size*/;
|
||||
|
@ -581,29 +581,26 @@ bool DecompressingStream::rewind() {
|
||||
|
||||
class ArchiveItem : public Common::ArchiveMember {
|
||||
public:
|
||||
ArchiveItem(Common::SeekableReadStream *stream, Common::Mutex *guardMutex, const Common::String &path, const Common::String &name, int64 filePos, uint compressedSize, uint decompressedSize, bool isCompressed);
|
||||
ArchiveItem(Common::SeekableReadStream *stream, Common::Mutex *guardMutex, const Common::Path &path, int64 filePos, uint compressedSize, uint decompressedSize, bool isCompressed);
|
||||
|
||||
Common::SeekableReadStream *createReadStream() const override;
|
||||
Common::SeekableReadStream *createReadStreamForAltStream(Common::AltStreamType altStreamType) const override;
|
||||
Common::String getName() const override;
|
||||
Common::Path getPathInArchive() const override { return getName(); }
|
||||
Common::String getFileName() const override { return getName(); }
|
||||
|
||||
const Common::String &getPath() const;
|
||||
Common::String getName() const override { return getFileName(); }
|
||||
Common::Path getPathInArchive() const override { return _path; }
|
||||
Common::String getFileName() const override { return _path.getLastComponent().toString(); }
|
||||
|
||||
private:
|
||||
Common::SeekableReadStream *_stream;
|
||||
Common::Mutex *_guardMutex;
|
||||
Common::String _path;
|
||||
Common::String _name;
|
||||
Common::Path _path;
|
||||
int64 _filePos;
|
||||
uint _compressedSize;
|
||||
uint _decompressedSize;
|
||||
bool _isCompressed;
|
||||
};
|
||||
|
||||
ArchiveItem::ArchiveItem(Common::SeekableReadStream *stream, Common::Mutex *guardMutex, const Common::String &path, const Common::String &name, int64 filePos, uint compressedSize, uint decompressedSize, bool isCompressed)
|
||||
: _stream(stream), _guardMutex(guardMutex), _path(path), _name(name), _filePos(filePos), _compressedSize(compressedSize), _decompressedSize(decompressedSize), _isCompressed(isCompressed) {
|
||||
ArchiveItem::ArchiveItem(Common::SeekableReadStream *stream, Common::Mutex *guardMutex, const Common::Path &path, int64 filePos, uint compressedSize, uint decompressedSize, bool isCompressed)
|
||||
: _stream(stream), _guardMutex(guardMutex), _path(path), _filePos(filePos), _compressedSize(compressedSize), _decompressedSize(decompressedSize), _isCompressed(isCompressed) {
|
||||
}
|
||||
|
||||
Common::SeekableReadStream *ArchiveItem::createReadStream() const {
|
||||
@ -627,14 +624,6 @@ Common::SeekableReadStream *ArchiveItem::createReadStreamForAltStream(Common::Al
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
Common::String ArchiveItem::getName() const {
|
||||
return _name;
|
||||
}
|
||||
|
||||
const Common::String &ArchiveItem::getPath() const {
|
||||
return _path;
|
||||
}
|
||||
|
||||
class PackageArchive : public Common::Archive {
|
||||
public:
|
||||
explicit PackageArchive(Common::SeekableReadStream *stream);
|
||||
@ -656,7 +645,7 @@ private:
|
||||
static Common::String normalizePath(const Common::Path &path);
|
||||
|
||||
Common::Array<Common::SharedPtr<ArchiveItem> > _items;
|
||||
Common::HashMap<Common::String, uint> _pathToItemIndex;
|
||||
Common::HashMap<Common::Path, uint, Common::Path::IgnoreCase_Hash, Common::Path::IgnoreCase_EqualTo> _pathToItemIndex;
|
||||
|
||||
Common::SeekableReadStream *_stream;
|
||||
};
|
||||
@ -792,23 +781,12 @@ bool PackageArchive::load(const char *prefix) {
|
||||
|
||||
if (fileName.hasPrefix(prefix)) {
|
||||
fileName = fileName.substr(strlen(prefix));
|
||||
fileName.replace('\\', '/');
|
||||
Common::Path path(fileName, '/');
|
||||
|
||||
size_t bsPos = fileName.findFirstOf('\\');
|
||||
while (bsPos != Common::String::npos) {
|
||||
fileName.replace(bsPos, 1, "/");
|
||||
bsPos = fileName.findFirstOf('\\');
|
||||
}
|
||||
Common::SharedPtr<ArchiveItem> item(new ArchiveItem(_stream, getGuardMutex(), path, dataStart, static_cast<uint>(dataEnd - dataStart), decompressedSize, isCompressed));
|
||||
|
||||
Common::String fileNameNoDir = fileName;
|
||||
|
||||
size_t lastSlashPos = fileNameNoDir.findLastOf('/');
|
||||
if (lastSlashPos != Common::String::npos)
|
||||
fileNameNoDir = fileNameNoDir.substr(lastSlashPos + 1);
|
||||
|
||||
Common::SharedPtr<ArchiveItem> item(new ArchiveItem(_stream, getGuardMutex(), fileName, fileNameNoDir, dataStart, static_cast<uint>(dataEnd - dataStart), decompressedSize, isCompressed));
|
||||
|
||||
fileName.toLowercase();
|
||||
_pathToItemIndex[fileName] = _items.size();
|
||||
_pathToItemIndex[path] = _items.size();
|
||||
|
||||
_items.push_back(item);
|
||||
}
|
||||
@ -852,7 +830,7 @@ Common::String PackageArchive::normalizePath(const Common::Path &path) {
|
||||
}
|
||||
|
||||
bool PackageArchive::hasFile(const Common::Path &path) const {
|
||||
return _pathToItemIndex.find(normalizePath(path)) != _pathToItemIndex.end();
|
||||
return _pathToItemIndex.find(path) != _pathToItemIndex.end();
|
||||
}
|
||||
|
||||
int PackageArchive::listMembers(Common::ArchiveMemberList &list) const {
|
||||
@ -863,12 +841,11 @@ int PackageArchive::listMembers(Common::ArchiveMemberList &list) const {
|
||||
}
|
||||
|
||||
int PackageArchive::listMatchingMembers(Common::ArchiveMemberList &list, const Common::Path &pattern, bool matchPathComponents) const {
|
||||
Common::String patternString = pattern.toString();
|
||||
int matches = 0;
|
||||
const char *wildcardExclusions = matchPathComponents ? NULL : "/";
|
||||
|
||||
for (const Common::SharedPtr<ArchiveItem> &item : _items) {
|
||||
if (item->getPath().matchString(patternString, true, wildcardExclusions)) {
|
||||
if (normalizePath(item->getPathInArchive()).matchString(normalizePath(pattern), false, wildcardExclusions)) {
|
||||
list.push_back(item.staticCast<Common::ArchiveMember>());
|
||||
matches++;
|
||||
}
|
||||
@ -878,7 +855,7 @@ int PackageArchive::listMatchingMembers(Common::ArchiveMemberList &list, const C
|
||||
}
|
||||
|
||||
const Common::ArchiveMemberPtr PackageArchive::getMember(const Common::Path &path) const {
|
||||
Common::HashMap<Common::String, uint>::const_iterator it = _pathToItemIndex.find(normalizePath(path));
|
||||
Common::HashMap<Common::Path, uint, Common::Path::IgnoreCase_Hash, Common::Path::IgnoreCase_EqualTo>::const_iterator it = _pathToItemIndex.find(path);
|
||||
if (it == _pathToItemIndex.end())
|
||||
return nullptr;
|
||||
|
||||
|
@ -87,7 +87,7 @@ class InstallShieldCabinet : public Archive {
|
||||
public:
|
||||
InstallShieldCabinet();
|
||||
|
||||
bool open(const String *baseName, const FSNode *node);
|
||||
bool open(const Path *baseName, const FSNode *node);
|
||||
void close();
|
||||
|
||||
// Archive API implementation
|
||||
@ -123,22 +123,22 @@ private:
|
||||
};
|
||||
|
||||
int _version;
|
||||
typedef HashMap<String, FileEntry, IgnoreCase_Hash, IgnoreCase_EqualTo> FileMap;
|
||||
typedef HashMap<Path, FileEntry, Path::IgnoreCase_Hash, Path::IgnoreCase_EqualTo> FileMap;
|
||||
FileMap _map;
|
||||
String _baseName;
|
||||
Path _baseName;
|
||||
Common::Array<VolumeHeader> _volumeHeaders;
|
||||
bool _useSearchMan;
|
||||
|
||||
static bool readVolumeHeader(SeekableReadStream *volumeStream, VolumeHeader &inVolumeHeader);
|
||||
|
||||
String getHeaderName() const;
|
||||
String getVolumeName(uint volume) const;
|
||||
Path getHeaderName() const;
|
||||
Path getVolumeName(uint volume) const;
|
||||
};
|
||||
|
||||
InstallShieldCabinet::InstallShieldCabinet() : _version(0), _useSearchMan(false) {
|
||||
}
|
||||
|
||||
bool InstallShieldCabinet::open(const String *baseName, const FSNode *node) {
|
||||
bool InstallShieldCabinet::open(const Path *baseName, const FSNode *node) {
|
||||
// Store the base name so we can generate file names
|
||||
if (baseName) {
|
||||
_baseName = *baseName;
|
||||
@ -150,8 +150,10 @@ bool InstallShieldCabinet::open(const String *baseName, const FSNode *node) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (_baseName.hasSuffix(".cab") || _baseName.hasSuffix(".hdr")) {
|
||||
_baseName.erase(_baseName.size() - 5, String::npos);
|
||||
String strippedName = _baseName.baseName();
|
||||
if (strippedName.hasSuffix(".cab") || strippedName.hasSuffix(".hdr")) {
|
||||
strippedName.erase(strippedName.size() - 5, String::npos);
|
||||
_baseName = _baseName.getParent().appendComponent(strippedName);
|
||||
}
|
||||
|
||||
uint fileIndex = 0;
|
||||
@ -250,7 +252,7 @@ bool InstallShieldCabinet::open(const String *baseName, const FSNode *node) {
|
||||
|
||||
// Then let's get the string
|
||||
file->seek(headerHeader.cabDescriptorOffset + fileTableOffset + nameOffset);
|
||||
String fileName = file->readString();
|
||||
Path fileName(file->readString(), '\\');
|
||||
|
||||
// Entries can appear in multiple volumes (sometimes erroneously).
|
||||
// We keep the one with the lowest volume ID
|
||||
@ -303,10 +305,10 @@ bool InstallShieldCabinet::open(const String *baseName, const FSNode *node) {
|
||||
|
||||
// Then let's get the string
|
||||
file->seek(headerHeader.cabDescriptorOffset + fileTableOffset + nameOffset);
|
||||
String fileName = file->readString();
|
||||
Path fileName(file->readString(), '\\');
|
||||
|
||||
if (entry.volume == 0) {
|
||||
warning("Couldn't find the volume for file %s", fileName.c_str());
|
||||
warning("Couldn't find the volume for file %s", fileName.toString('\\').c_str());
|
||||
close();
|
||||
return false;
|
||||
}
|
||||
@ -331,8 +333,7 @@ void InstallShieldCabinet::close() {
|
||||
}
|
||||
|
||||
bool InstallShieldCabinet::hasFile(const Path &path) const {
|
||||
String name = path.toString();
|
||||
return _map.contains(name);
|
||||
return _map.contains(path);
|
||||
}
|
||||
|
||||
int InstallShieldCabinet::listMembers(ArchiveMemberList &list) const {
|
||||
@ -347,14 +348,13 @@ const ArchiveMemberPtr InstallShieldCabinet::getMember(const Path &path) const {
|
||||
}
|
||||
|
||||
SeekableReadStream *InstallShieldCabinet::createReadStreamForMember(const Path &path) const {
|
||||
String name = path.toString();
|
||||
if (!_map.contains(name))
|
||||
if (!_map.contains(path))
|
||||
return nullptr;
|
||||
|
||||
const FileEntry &entry = _map[name];
|
||||
const FileEntry &entry = _map[path];
|
||||
|
||||
if (entry.flags & kObfuscated) {
|
||||
warning("Cannot extract obfuscated file %s", name.c_str());
|
||||
warning("Cannot extract obfuscated file %s", path.toString().c_str());
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
@ -369,7 +369,7 @@ SeekableReadStream *InstallShieldCabinet::createReadStreamForMember(const Path &
|
||||
}
|
||||
|
||||
if (!stream) {
|
||||
warning("Failed to open volume for file '%s'", name.c_str());
|
||||
warning("Failed to open volume for file '%s'", path.toString().c_str());
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
@ -396,7 +396,7 @@ SeekableReadStream *InstallShieldCabinet::createReadStreamForMember(const Path &
|
||||
}
|
||||
|
||||
if (!stream.get()) {
|
||||
warning("Failed to read split file %s", name.c_str());
|
||||
warning("Failed to read split file %s", path.toString().c_str());
|
||||
free(src);
|
||||
return nullptr;
|
||||
}
|
||||
@ -428,7 +428,7 @@ SeekableReadStream *InstallShieldCabinet::createReadStreamForMember(const Path &
|
||||
// Entries with size 0 are valid, and do not need to be inflated
|
||||
if (entry.compressedSize != 0) {
|
||||
if (!inflateZlibInstallShield(dst, entry.uncompressedSize, src, entry.compressedSize)) {
|
||||
warning("failed to inflate CAB file '%s'", name.c_str());
|
||||
warning("failed to inflate CAB file '%s'", path.toString().c_str());
|
||||
free(dst);
|
||||
free(src);
|
||||
return nullptr;
|
||||
@ -499,17 +499,17 @@ bool InstallShieldCabinet::readVolumeHeader(SeekableReadStream *volumeStream, In
|
||||
return true;
|
||||
}
|
||||
|
||||
String InstallShieldCabinet::getHeaderName() const {
|
||||
return _baseName + "1.hdr";
|
||||
Path InstallShieldCabinet::getHeaderName() const {
|
||||
return _baseName.append("1.hdr");
|
||||
}
|
||||
|
||||
String InstallShieldCabinet::getVolumeName(uint volume) const {
|
||||
return String::format("%s%d.cab", _baseName.c_str(), volume);
|
||||
Path InstallShieldCabinet::getVolumeName(uint volume) const {
|
||||
return _baseName.append(String::format("%d.cab", volume));
|
||||
}
|
||||
|
||||
} // End of anonymous namespace
|
||||
|
||||
Archive *makeInstallShieldArchive(const String &baseName) {
|
||||
Archive *makeInstallShieldArchive(const Path &baseName) {
|
||||
InstallShieldCabinet *cab = new InstallShieldCabinet();
|
||||
if (!cab->open(&baseName, nullptr)) {
|
||||
delete cab;
|
||||
|
@ -49,7 +49,7 @@ class SeekableReadStream;
|
||||
*
|
||||
* @param baseName The base filename, e.g. the "data" in "data1.cab"
|
||||
*/
|
||||
Archive *makeInstallShieldArchive(const Common::String &baseName);
|
||||
Archive *makeInstallShieldArchive(const Common::Path &baseName);
|
||||
|
||||
/**
|
||||
* This factory method creates an Archive instance corresponding to the content
|
||||
|
@ -34,7 +34,7 @@ InstallShieldV3::~InstallShieldV3() {
|
||||
close();
|
||||
}
|
||||
|
||||
bool InstallShieldV3::open(const Common::String &filename) {
|
||||
bool InstallShieldV3::open(const Common::Path &filename) {
|
||||
close();
|
||||
|
||||
_stream = SearchMan.createReadStreamForMember(filename);
|
||||
@ -74,8 +74,7 @@ void InstallShieldV3::close() {
|
||||
}
|
||||
|
||||
bool InstallShieldV3::hasFile(const Common::Path &path) const {
|
||||
Common::String name = path.toString();
|
||||
return _map.contains(name);
|
||||
return _map.contains(path);
|
||||
}
|
||||
|
||||
int InstallShieldV3::listMembers(Common::ArchiveMemberList &list) const {
|
||||
@ -86,20 +85,14 @@ int InstallShieldV3::listMembers(Common::ArchiveMemberList &list) const {
|
||||
}
|
||||
|
||||
const Common::ArchiveMemberPtr InstallShieldV3::getMember(const Common::Path &path) const {
|
||||
Common::String name = path.toString();
|
||||
return Common::ArchiveMemberPtr(new Common::GenericArchiveMember(name, *this));
|
||||
return Common::ArchiveMemberPtr(new Common::GenericArchiveMember(path, *this));
|
||||
}
|
||||
|
||||
Common::SeekableReadStream *InstallShieldV3::createReadStreamForMember(const Common::Path &path) const {
|
||||
Common::String name = path.toString();
|
||||
// Make sure "/" is converted to "\"
|
||||
while (name.contains("/"))
|
||||
Common::replace(name, "/", "\\");
|
||||
|
||||
if (!_stream || !_map.contains(name))
|
||||
if (!_stream || !_map.contains(path))
|
||||
return nullptr;
|
||||
|
||||
const FileEntry &entry = _map[name];
|
||||
const FileEntry &entry = _map[path];
|
||||
|
||||
// Seek to our offset and then send it off to the decompressor
|
||||
_stream->seek(entry.offset);
|
||||
@ -178,7 +171,7 @@ bool InstallShieldV3::read() {
|
||||
if (!dirNames[i].empty())
|
||||
name = dirNames[i] + "\\" + name;
|
||||
|
||||
_map[name] = entry;
|
||||
_map[Path(name, '\\')] = entry;
|
||||
debug(3, "Found file '%s' at 0x%08x (Comp: 0x%08x, Uncomp: 0x%08x)", name.c_str(),
|
||||
entry.offset, entry.compressedSize, entry.uncompressedSize);
|
||||
}
|
||||
|
@ -37,7 +37,7 @@ public:
|
||||
InstallShieldV3();
|
||||
~InstallShieldV3() override;
|
||||
|
||||
bool open(const Common::String &filename);
|
||||
bool open(const Common::Path &filename);
|
||||
bool open(const Common::FSNode &node);
|
||||
bool open(Common::SeekableReadStream *stream);
|
||||
void close();
|
||||
@ -61,7 +61,7 @@ private:
|
||||
|
||||
Common::SeekableReadStream *_stream;
|
||||
|
||||
typedef Common::HashMap<Common::String, FileEntry, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo> FileMap;
|
||||
typedef Common::HashMap<Path, FileEntry, Path::IgnoreCase_Hash, Path::IgnoreCase_EqualTo> FileMap;
|
||||
FileMap _map;
|
||||
};
|
||||
|
||||
|
@ -43,7 +43,7 @@ public:
|
||||
StuffItArchive();
|
||||
~StuffItArchive() override;
|
||||
|
||||
bool open(const Common::String &filename, bool flattenTree);
|
||||
bool open(const Common::Path &filename, bool flattenTree);
|
||||
bool open(Common::SeekableReadStream *stream, bool flattenTree);
|
||||
void close();
|
||||
bool isOpen() const { return _stream != nullptr; }
|
||||
@ -52,9 +52,9 @@ public:
|
||||
bool hasFile(const Common::Path &path) const override;
|
||||
int listMembers(Common::ArchiveMemberList &list) const override;
|
||||
const Common::ArchiveMemberPtr getMember(const Common::Path &path) const override;
|
||||
Common::SharedArchiveContents readContentsForPath(const Common::String &name) const override;
|
||||
Common::SharedArchiveContents readContentsForPathAltStream(const String &translatedPath, Common::AltStreamType altStreamType) const override;
|
||||
Common::String translatePath(const Common::Path &path) const override;
|
||||
Common::SharedArchiveContents readContentsForPath(const Common::Path &name) const override;
|
||||
Common::SharedArchiveContents readContentsForPathAltStream(const Common::Path &translatedPath, Common::AltStreamType altStreamType) const override;
|
||||
Common::Path translatePath(const Common::Path &path) const override;
|
||||
char getPathSeparator() const override;
|
||||
|
||||
private:
|
||||
@ -82,10 +82,10 @@ private:
|
||||
|
||||
Common::SeekableReadStream *_stream;
|
||||
|
||||
typedef Common::HashMap<Common::String, FileEntry, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo> FileMap;
|
||||
typedef Common::HashMap<Common::Path, FileEntry, Common::Path::IgnoreCase_Hash, Common::Path::IgnoreCase_EqualTo> FileMap;
|
||||
FileMap _map;
|
||||
|
||||
typedef Common::HashMap<Common::String, Common::MacFinderInfoData, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo> MetadataMap;
|
||||
typedef Common::HashMap<Common::Path, Common::MacFinderInfoData, Common::Path::IgnoreCase_Hash, Common::Path::IgnoreCase_EqualTo> MetadataMap;
|
||||
MetadataMap _metadataMap;
|
||||
|
||||
bool _flattenTree;
|
||||
@ -98,7 +98,7 @@ private:
|
||||
void update14(uint16 first, uint16 last, byte *code, uint16 *freq) const;
|
||||
void readTree14(Common::BitStream8LSB *bits, SIT14Data *dat, uint16 codesize, uint16 *result) const;
|
||||
|
||||
Common::SharedArchiveContents readContentsForPathFork(const String &translatedPath, bool isResFork) const;
|
||||
Common::SharedArchiveContents readContentsForPathFork(const Common::Path &translatedPath, bool isResFork) const;
|
||||
};
|
||||
|
||||
StuffItArchive::StuffItArchive() : Common::MemcachingCaseInsensitiveArchive(), _flattenTree(false) {
|
||||
@ -117,7 +117,7 @@ static const uint32 s_magicNumbers[] = {
|
||||
MKTAG('S', 'T', 'i', '3'), MKTAG('S', 'T', 'i', '4'), MKTAG('S', 'T', '4', '6')
|
||||
};
|
||||
|
||||
bool StuffItArchive::open(const Common::String &filename, bool flattenTree) {
|
||||
bool StuffItArchive::open(const Common::Path &filename, bool flattenTree) {
|
||||
Common::SeekableReadStream *stream = SearchMan.createReadStreamForMember(filename);
|
||||
return open(stream, flattenTree);
|
||||
}
|
||||
@ -237,12 +237,14 @@ bool StuffItArchive::open(Common::SeekableReadStream *stream, bool flattenTree)
|
||||
if (!flattenTree)
|
||||
name = dirPrefix + name;
|
||||
|
||||
_metadataMap[name] = finfo.toData();
|
||||
Common::Path path(name, ':');
|
||||
|
||||
_metadataMap[path] = finfo.toData();
|
||||
|
||||
if (dataForkUncompressedSize != 0) {
|
||||
// We have a data fork
|
||||
|
||||
FileEntryFork &entryFork = _map[name].dataFork;
|
||||
FileEntryFork &entryFork = _map[path].dataFork;
|
||||
entryFork.compression = dataForkCompression;
|
||||
entryFork.uncompressedSize = dataForkUncompressedSize;
|
||||
entryFork.compressedSize = dataForkCompressedSize;
|
||||
@ -255,7 +257,7 @@ bool StuffItArchive::open(Common::SeekableReadStream *stream, bool flattenTree)
|
||||
if (resForkUncompressedSize != 0) {
|
||||
// We have a resource fork
|
||||
|
||||
FileEntryFork &entryFork = _map[name].resFork;
|
||||
FileEntryFork &entryFork = _map[path].resFork;
|
||||
entryFork.compression = resForkCompression;
|
||||
entryFork.uncompressedSize = resForkUncompressedSize;
|
||||
entryFork.compressedSize = resForkCompressedSize;
|
||||
@ -279,8 +281,7 @@ void StuffItArchive::close() {
|
||||
}
|
||||
|
||||
bool StuffItArchive::hasFile(const Common::Path &path) const {
|
||||
Common::String name = path.toString(':');
|
||||
return _map.contains(name);
|
||||
return _map.contains(path);
|
||||
}
|
||||
|
||||
int StuffItArchive::listMembers(Common::ArchiveMemberList &list) const {
|
||||
@ -294,11 +295,11 @@ const Common::ArchiveMemberPtr StuffItArchive::getMember(const Common::Path &pat
|
||||
return Common::ArchiveMemberPtr(new StuffItArchiveMember(path, *this));
|
||||
}
|
||||
|
||||
Common::SharedArchiveContents StuffItArchive::readContentsForPath(const Common::String &name) const {
|
||||
return readContentsForPathFork(name, false);
|
||||
Common::SharedArchiveContents StuffItArchive::readContentsForPath(const Common::Path &path) const {
|
||||
return readContentsForPathFork(path, false);
|
||||
}
|
||||
|
||||
Common::SharedArchiveContents StuffItArchive::readContentsForPathAltStream(const String &translatedPath, Common::AltStreamType altStreamType) const {
|
||||
Common::SharedArchiveContents StuffItArchive::readContentsForPathAltStream(const Common::Path &translatedPath, Common::AltStreamType altStreamType) const {
|
||||
if (altStreamType == Common::AltStreamType::MacFinderInfo) {
|
||||
if (_metadataMap.contains(translatedPath)) {
|
||||
const Common::MacFinderInfoData &metadata = _metadataMap[translatedPath];
|
||||
@ -315,13 +316,13 @@ Common::SharedArchiveContents StuffItArchive::readContentsForPathAltStream(const
|
||||
return Common::SharedArchiveContents();
|
||||
}
|
||||
|
||||
Common::SharedArchiveContents StuffItArchive::readContentsForPathFork(const Common::String &name, bool isResFork) const {
|
||||
FileMap::const_iterator entryIt = _map.find(name);
|
||||
Common::SharedArchiveContents StuffItArchive::readContentsForPathFork(const Common::Path &path, bool isResFork) const {
|
||||
FileMap::const_iterator entryIt = _map.find(path);
|
||||
|
||||
if (entryIt == _map.end())
|
||||
return Common::SharedArchiveContents();
|
||||
|
||||
const FileEntry &entry = _map[name];
|
||||
const FileEntry &entry = entryIt->_value;
|
||||
const FileEntryFork &entryFork = isResFork ? entry.resFork : entry.dataFork;
|
||||
|
||||
if (entryFork.uncompressedSize == 0) {
|
||||
@ -358,14 +359,14 @@ Common::SharedArchiveContents StuffItArchive::readContentsForPathFork(const Comm
|
||||
uint16 actualCRC = Common::CRC16().crcFast(uncompressedBlock, entryFork.uncompressedSize);
|
||||
|
||||
if (actualCRC != entryFork.crc) {
|
||||
error("StuffItArchive::readContentsForPath(): CRC mismatch: %04x vs %04x for file %s %s fork", actualCRC, entryFork.crc, name.c_str(), (isResFork ? "res" : "data"));
|
||||
error("StuffItArchive::readContentsForPath(): CRC mismatch: %04x vs %04x for file %s %s fork", actualCRC, entryFork.crc, path.toString().c_str(), (isResFork ? "res" : "data"));
|
||||
}
|
||||
|
||||
return Common::SharedArchiveContents(uncompressedBlock, entryFork.uncompressedSize);
|
||||
}
|
||||
|
||||
Common::String StuffItArchive::translatePath(const Common::Path &path) const {
|
||||
return _flattenTree ? path.getLastComponent().toString() : path.toString(':');
|
||||
Common::Path StuffItArchive::translatePath(const Common::Path &path) const {
|
||||
return _flattenTree ? path.getLastComponent() : path;
|
||||
}
|
||||
|
||||
char StuffItArchive::getPathSeparator() const {
|
||||
@ -1133,7 +1134,7 @@ bool StuffItArchive::StuffItArchiveMember::isInMacArchive() const {
|
||||
return true;
|
||||
}
|
||||
|
||||
Common::Archive *createStuffItArchive(const Common::String &fileName, bool flattenTree) {
|
||||
Common::Archive *createStuffItArchive(const Common::Path &fileName, bool flattenTree) {
|
||||
StuffItArchive *archive = new StuffItArchive();
|
||||
|
||||
if (!archive->open(fileName, flattenTree)) {
|
||||
|
@ -43,7 +43,7 @@ namespace Common {
|
||||
*/
|
||||
|
||||
class Archive;
|
||||
class String;
|
||||
class Path;
|
||||
class SeekableReadStream;
|
||||
|
||||
/**
|
||||
@ -55,7 +55,7 @@ class SeekableReadStream;
|
||||
*
|
||||
* @return The StuffIt archive
|
||||
*/
|
||||
Archive *createStuffItArchive(const String &fileName, bool flattenTree = false);
|
||||
Archive *createStuffItArchive(const Path &fileName, bool flattenTree = false);
|
||||
Archive *createStuffItArchive(SeekableReadStream *stream, bool flattenTree = false);
|
||||
|
||||
/** @} */
|
||||
|
@ -697,24 +697,24 @@ struct ArjFileChunk {
|
||||
ArjFileChunk(ArjHeader* header, uint volume) : _header(header), _volume(volume) {}
|
||||
};
|
||||
|
||||
typedef HashMap<String, Array<ArjFileChunk>, IgnoreCase_Hash, IgnoreCase_EqualTo> ArjHeadersMap;
|
||||
typedef HashMap<Path, Array<ArjFileChunk>, Path::IgnoreCase_Hash, Path::IgnoreCase_EqualTo> ArjHeadersMap;
|
||||
|
||||
class ArjArchive : public MemcachingCaseInsensitiveArchive {
|
||||
ArjHeadersMap _headers;
|
||||
Array<String> _arjFilenames;
|
||||
Array<Path> _arjFilenames;
|
||||
bool _flattenTree;
|
||||
|
||||
public:
|
||||
ArjArchive(const Array<String> &names, bool flattenTree);
|
||||
ArjArchive(const Array<Path> &names, bool flattenTree);
|
||||
virtual ~ArjArchive();
|
||||
|
||||
// Archive implementation
|
||||
bool hasFile(const Path &path) const override;
|
||||
int listMembers(ArchiveMemberList &list) const override;
|
||||
const ArchiveMemberPtr getMember(const Path &path) const override;
|
||||
Common::SharedArchiveContents readContentsForPath(const Common::String& translated) const override;
|
||||
Common::String translatePath(const Common::Path &path) const override {
|
||||
return _flattenTree ? path.getLastComponent().toString() : path.toString();
|
||||
Common::SharedArchiveContents readContentsForPath(const Common::Path &translated) const override;
|
||||
Common::Path translatePath(const Common::Path &path) const override {
|
||||
return _flattenTree ? path.getLastComponent() : path;
|
||||
}
|
||||
};
|
||||
|
||||
@ -727,7 +727,7 @@ ArjArchive::~ArjArchive() {
|
||||
}
|
||||
}
|
||||
|
||||
ArjArchive::ArjArchive(const Array<String> &filenames, bool flattenTree) : _arjFilenames(filenames), _flattenTree(flattenTree) {
|
||||
ArjArchive::ArjArchive(const Array<Path> &filenames, bool flattenTree) : _arjFilenames(filenames), _flattenTree(flattenTree) {
|
||||
for (uint i = 0; i < _arjFilenames.size(); i++) {
|
||||
File arjFile;
|
||||
|
||||
@ -753,21 +753,28 @@ ArjArchive::ArjArchive(const Array<String> &filenames, bool flattenTree) : _arjF
|
||||
while ((header = readHeader(arjFile)) != nullptr) {
|
||||
const char *name = header->filename;
|
||||
|
||||
if (_flattenTree)
|
||||
for (const char *p = header->filename; *p; p++)
|
||||
if (*p == '\\' || *p == '/')
|
||||
if (_flattenTree) {
|
||||
for (const char *p = header->filename; *p; p++) {
|
||||
if (*p == '\\' || *p == '/') {
|
||||
name = p + 1;
|
||||
_headers[name].push_back(ArjFileChunk(header, i));
|
||||
}
|
||||
}
|
||||
} else {
|
||||
for (char *p = header->filename; *p; p++) {
|
||||
if (*p == '\\')
|
||||
*p = '/';
|
||||
}
|
||||
}
|
||||
_headers[Path(name)].push_back(ArjFileChunk(header, i));
|
||||
arjFile.seek(header->compSize, SEEK_CUR);
|
||||
}
|
||||
}
|
||||
|
||||
debug(0, "ArjArchive::ArjArchive(%d volume(s) starting with %s): Located %d files", filenames.size(), filenames.empty() ? "" : filenames[0].c_str(), _headers.size());
|
||||
debug(0, "ArjArchive::ArjArchive(%d volume(s) starting with %s): Located %d files", filenames.size(), filenames.empty() ? "" : filenames[0].toString(Common::Path::kNativeSeparator).c_str(), _headers.size());
|
||||
}
|
||||
|
||||
bool ArjArchive::hasFile(const Path &path) const {
|
||||
String name = path.toString();
|
||||
return _headers.contains(name);
|
||||
return _headers.contains(path);
|
||||
}
|
||||
|
||||
int ArjArchive::listMembers(ArchiveMemberList &list) const {
|
||||
@ -775,7 +782,7 @@ int ArjArchive::listMembers(ArchiveMemberList &list) const {
|
||||
|
||||
ArjHeadersMap::const_iterator it = _headers.begin();
|
||||
for ( ; it != _headers.end(); ++it) {
|
||||
list.push_back(ArchiveMemberList::value_type(new GenericArchiveMember(Common::String(it->_value[0]._header->filename), *this)));
|
||||
list.push_back(ArchiveMemberList::value_type(new GenericArchiveMember(Path(it->_value[0]._header->filename), *this)));
|
||||
matches++;
|
||||
}
|
||||
|
||||
@ -783,19 +790,18 @@ int ArjArchive::listMembers(ArchiveMemberList &list) const {
|
||||
}
|
||||
|
||||
const ArchiveMemberPtr ArjArchive::getMember(const Path &path) const {
|
||||
String name = path.toString();
|
||||
if (!hasFile(name))
|
||||
if (!hasFile(path))
|
||||
return ArchiveMemberPtr();
|
||||
|
||||
return ArchiveMemberPtr(new GenericArchiveMember(name, *this));
|
||||
return ArchiveMemberPtr(new GenericArchiveMember(path, *this));
|
||||
}
|
||||
|
||||
Common::SharedArchiveContents ArjArchive::readContentsForPath(const Common::String& name) const {
|
||||
if (!_headers.contains(name)) {
|
||||
Common::SharedArchiveContents ArjArchive::readContentsForPath(const Common::Path &path) const {
|
||||
if (!_headers.contains(path)) {
|
||||
return Common::SharedArchiveContents();
|
||||
}
|
||||
|
||||
const Array <ArjFileChunk>& hdrs = _headers[name];
|
||||
const Array <ArjFileChunk>& hdrs = _headers[path];
|
||||
|
||||
uint64 uncompressedSize = 0;
|
||||
uint totalChunks;
|
||||
@ -848,11 +854,11 @@ Common::SharedArchiveContents ArjArchive::readContentsForPath(const Common::Stri
|
||||
return Common::SharedArchiveContents(uncompressedData, uncompressedSize);
|
||||
}
|
||||
|
||||
Archive *makeArjArchive(const String &name, bool flattenTree) {
|
||||
Archive *makeArjArchive(const Path &name, bool flattenTree) {
|
||||
return new ArjArchive({name}, flattenTree);
|
||||
}
|
||||
|
||||
Archive *makeArjArchive(const Array<String> &names, bool flattenTree) {
|
||||
Archive *makeArjArchive(const Array<Path> &names, bool flattenTree) {
|
||||
return new ArjArchive(names, flattenTree);
|
||||
}
|
||||
|
||||
|
@ -49,12 +49,12 @@ class Archive;
|
||||
*
|
||||
* May return 0 in case of a failure.
|
||||
*/
|
||||
Archive *makeArjArchive(const String &name, bool flattenTree = false);
|
||||
Archive *makeArjArchive(const Path &name, bool flattenTree = false);
|
||||
|
||||
/**
|
||||
* Similar to previous but for multi-volume archives
|
||||
*/
|
||||
Archive *makeArjArchive(const Array<String> &names, bool flattenTree = false);
|
||||
Archive *makeArjArchive(const Array<Path> &names, bool flattenTree = false);
|
||||
|
||||
/** @} */
|
||||
|
||||
|
@ -318,8 +318,8 @@ typedef struct {
|
||||
unz_file_info_internal cur_file_info_internal; /* private info about it*/
|
||||
} cached_file_in_zip;
|
||||
|
||||
typedef Common::HashMap<Common::String, cached_file_in_zip, Common::IgnoreCase_Hash,
|
||||
Common::IgnoreCase_EqualTo> ZipHash;
|
||||
typedef Common::HashMap<Common::Path, cached_file_in_zip, Common::Path::IgnoreCase_Hash,
|
||||
Common::Path::IgnoreCase_EqualTo> ZipHash;
|
||||
|
||||
/* unz_s contain internal information about the zipfile
|
||||
*/
|
||||
@ -535,12 +535,14 @@ unzFile unzOpen(Common::SeekableReadStream *stream, bool flattenTree) {
|
||||
fe.cur_file_info = us->cur_file_info;
|
||||
fe.cur_file_info_internal = us->cur_file_info_internal;
|
||||
|
||||
Common::String name(szCurrentFileName);
|
||||
|
||||
bool isDirectory = false;
|
||||
if (name.hasSuffix("/") || name.hasSuffix("\\")) {
|
||||
isDirectory = true;
|
||||
name = name.substr(0, name.size() - 1);
|
||||
if (*szCurrentFileName) {
|
||||
char *szCurrentFileNameSuffix = szCurrentFileName + strlen(szCurrentFileName) - 1;
|
||||
if (*szCurrentFileNameSuffix == '/' || *szCurrentFileNameSuffix == '\\') {
|
||||
isDirectory = true;
|
||||
// Strip trailing path terminator
|
||||
*szCurrentFileNameSuffix = '\0';
|
||||
}
|
||||
}
|
||||
|
||||
// If platform is specified as MS-DOS or Unix, check the directory flag
|
||||
@ -564,20 +566,21 @@ unzFile unzOpen(Common::SeekableReadStream *stream, bool flattenTree) {
|
||||
}
|
||||
}
|
||||
|
||||
const char *name = szCurrentFileName;
|
||||
if (flattenTree) {
|
||||
if (isDirectory)
|
||||
continue;
|
||||
|
||||
size_t slashPos = name.findLastOf('\\');
|
||||
if (slashPos != Common::String::npos)
|
||||
name = name.substr(slashPos + 1);
|
||||
|
||||
slashPos = name.findLastOf('/');
|
||||
if (slashPos != Common::String::npos)
|
||||
name = name.substr(slashPos + 1);
|
||||
for (const char *p = szCurrentFileName; *p; p++)
|
||||
if (*p == '\\' || *p == '/')
|
||||
name = p + 1;
|
||||
} else {
|
||||
for (char *p = szCurrentFileName; *p; p++)
|
||||
if (*p == '\\')
|
||||
*p = '/';
|
||||
}
|
||||
|
||||
us->_hash[name] = fe;
|
||||
us->_hash[Common::Path(name)] = fe;
|
||||
|
||||
// Move to the next file
|
||||
err = unzGoToNextFile((unzFile)us);
|
||||
@ -832,21 +835,18 @@ int unzGoToNextFile(unzFile file) {
|
||||
UNZ_OK if the file is found. It becomes the current file.
|
||||
UNZ_END_OF_LIST_OF_FILE if the file is not found
|
||||
*/
|
||||
int unzLocateFile(unzFile file, const char *szFileName, int iCaseSensitivity) {
|
||||
int unzLocateFile(unzFile file, const Common::Path &szFileName, int iCaseSensitivity) {
|
||||
unz_s *s;
|
||||
|
||||
if (file == nullptr)
|
||||
return UNZ_PARAMERROR;
|
||||
|
||||
if (strlen(szFileName) >= UNZ_MAXFILENAMEINZIP)
|
||||
return UNZ_PARAMERROR;
|
||||
|
||||
s=(unz_s *)file;
|
||||
if (!s->current_file_ok)
|
||||
return UNZ_END_OF_LIST_OF_FILE;
|
||||
|
||||
// Check to see if the entry exists
|
||||
ZipHash::iterator i = s->_hash.find(Common::String(szFileName));
|
||||
ZipHash::iterator i = s->_hash.find(szFileName);
|
||||
if (i == s->_hash.end())
|
||||
return UNZ_END_OF_LIST_OF_FILE;
|
||||
|
||||
@ -1039,9 +1039,9 @@ public:
|
||||
bool isPathDirectory(const Path &path) const override;
|
||||
int listMembers(ArchiveMemberList &list) const override;
|
||||
const ArchiveMemberPtr getMember(const Path &path) const override;
|
||||
Common::SharedArchiveContents readContentsForPath(const Common::String& translated) const override;
|
||||
Common::String translatePath(const Common::Path &path) const override {
|
||||
return _flattenTree ? path.getLastComponent().toString() : path.toString();
|
||||
Common::SharedArchiveContents readContentsForPath(const Common::Path &translated) const override;
|
||||
Common::Path translatePath(const Common::Path &path) const override {
|
||||
return _flattenTree ? path.getLastComponent() : path;
|
||||
}
|
||||
};
|
||||
|
||||
@ -1072,14 +1072,11 @@ ZipArchive::~ZipArchive() {
|
||||
}
|
||||
|
||||
bool ZipArchive::hasFile(const Path &path) const {
|
||||
String name = path.toString();
|
||||
return (unzLocateFile(_zipFile, name.c_str(), 2) == UNZ_OK);
|
||||
return (unzLocateFile(_zipFile, path, 2) == UNZ_OK);
|
||||
}
|
||||
|
||||
bool ZipArchive::isPathDirectory(const Path &path) const {
|
||||
String name = path.toString();
|
||||
|
||||
if (unzLocateFile(_zipFile, name.c_str(), 2) != UNZ_OK)
|
||||
if (unzLocateFile(_zipFile, path, 2) != UNZ_OK)
|
||||
return false;
|
||||
|
||||
unz_file_info fi;
|
||||
@ -1103,15 +1100,14 @@ int ZipArchive::listMembers(ArchiveMemberList &list) const {
|
||||
}
|
||||
|
||||
const ArchiveMemberPtr ZipArchive::getMember(const Path &path) const {
|
||||
String name = path.toString();
|
||||
if (!hasFile(name))
|
||||
if (!hasFile(path))
|
||||
return ArchiveMemberPtr();
|
||||
|
||||
return ArchiveMemberPtr(new GenericArchiveMember(path, *this));
|
||||
}
|
||||
|
||||
Common::SharedArchiveContents ZipArchive::readContentsForPath(const Common::String& name) const {
|
||||
if (unzLocateFile(_zipFile, name.c_str(), 2) != UNZ_OK)
|
||||
Common::SharedArchiveContents ZipArchive::readContentsForPath(const Common::Path &path) const {
|
||||
if (unzLocateFile(_zipFile, path, 2) != UNZ_OK)
|
||||
return Common::SharedArchiveContents();
|
||||
#ifndef USE_ZLIB
|
||||
return unzOpenCurrentFile(_zipFile, _crc);
|
||||
@ -1120,7 +1116,7 @@ Common::SharedArchiveContents ZipArchive::readContentsForPath(const Common::Stri
|
||||
#endif
|
||||
}
|
||||
|
||||
Archive *makeZipArchive(const String &name, bool flattenTree) {
|
||||
Archive *makeZipArchive(const Path &name, bool flattenTree) {
|
||||
return makeZipArchive(SearchMan.createReadStreamForMember(name), flattenTree);
|
||||
}
|
||||
|
||||
|
@ -45,7 +45,7 @@ class SeekableReadStream;
|
||||
*
|
||||
* May return 0 in case of a failure.
|
||||
*/
|
||||
Archive *makeZipArchive(const String &name, bool flattenTree = false);
|
||||
Archive *makeZipArchive(const Path &name, bool flattenTree = false);
|
||||
|
||||
/**
|
||||
* This factory method creates an Archive instance corresponding to the content
|
||||
|
@ -351,7 +351,7 @@ void ProDOSDisk::getVolumeBitmap(VolHeader *h) {
|
||||
|
||||
/* Gets the volume information and parses the filesystem, adding file objects to a map as it goes */
|
||||
|
||||
bool ProDOSDisk::open(const Common::String filename) {
|
||||
bool ProDOSDisk::open(const Common::Path &filename) {
|
||||
_disk.open(filename);
|
||||
_disk.read(_loader1, kBlockSize);
|
||||
_disk.read(_loader2, kBlockSize);
|
||||
@ -371,7 +371,7 @@ bool ProDOSDisk::open(const Common::String filename) {
|
||||
|
||||
/* Constructor simply calls open(), and if it is successful it prints a statement */
|
||||
|
||||
ProDOSDisk::ProDOSDisk(const Common::String filename) {
|
||||
ProDOSDisk::ProDOSDisk(const Common::Path &filename) {
|
||||
if (open(filename)) {
|
||||
//debug("%s has been loaded", filename.c_str());
|
||||
}
|
||||
|
@ -116,11 +116,11 @@ class ProDOSDisk : public Common::Archive {
|
||||
public:
|
||||
static const int kBlockSize = 512; // A ProDOS block is always 512 bytes (should this be an enum?)
|
||||
|
||||
ProDOSDisk(const Common::String filename);
|
||||
ProDOSDisk(const Common::Path &filename);
|
||||
~ProDOSDisk(); // Frees the memory used in the dictionary and the volume bitmap
|
||||
|
||||
// Called from the constructor, it parses the volume and fills the hashmap with files
|
||||
bool open(const Common::String filename);
|
||||
bool open(const Common::Path &filename);
|
||||
|
||||
// These are the Common::Archive related methods
|
||||
bool hasFile(const Common::Path &path) const override;
|
||||
|
@ -82,7 +82,7 @@ String WinResourceID::toString() const {
|
||||
return "";
|
||||
}
|
||||
|
||||
bool WinResources::loadFromEXE(const String &fileName) {
|
||||
bool WinResources::loadFromEXE(const Path &fileName) {
|
||||
if (fileName.empty())
|
||||
return false;
|
||||
|
||||
@ -96,7 +96,7 @@ bool WinResources::loadFromEXE(const String &fileName) {
|
||||
return loadFromEXE(file);
|
||||
}
|
||||
|
||||
bool WinResources::loadFromCompressedEXE(const String &fileName) {
|
||||
bool WinResources::loadFromCompressedEXE(const Path &fileName) {
|
||||
// Based on http://www.cabextract.org.uk/libmspack/doc/szdd_kwaj_format.html
|
||||
|
||||
// TODO: Merge this with with loadFromEXE() so the handling of the compressed
|
||||
@ -172,7 +172,7 @@ bool WinResources::loadFromCompressedEXE(const String &fileName) {
|
||||
}
|
||||
|
||||
|
||||
WinResources *WinResources::createFromEXE(const String &fileName) {
|
||||
WinResources *WinResources::createFromEXE(const Path &fileName) {
|
||||
WinResources *exe;
|
||||
|
||||
// First try loading via the NE code
|
||||
|
@ -37,6 +37,7 @@ namespace Common {
|
||||
* @{
|
||||
*/
|
||||
|
||||
class Path;
|
||||
class SeekableReadStream;
|
||||
|
||||
/** The default Windows resources. */
|
||||
@ -114,10 +115,10 @@ public:
|
||||
virtual void clear() = 0;
|
||||
|
||||
/** Load from an EXE file. */
|
||||
virtual bool loadFromEXE(const String &fileName);
|
||||
virtual bool loadFromEXE(const Path &fileName);
|
||||
|
||||
/** Load from a Windows compressed EXE file. */
|
||||
virtual bool loadFromCompressedEXE(const String &fileName);
|
||||
virtual bool loadFromCompressedEXE(const Path &fileName);
|
||||
|
||||
/** Load from a stream. */
|
||||
virtual bool loadFromEXE(SeekableReadStream *stream, DisposeAfterUse::Flag disposeFileHandle = DisposeAfterUse::YES) = 0;
|
||||
@ -139,7 +140,7 @@ public:
|
||||
return getResource(type, id);
|
||||
}
|
||||
|
||||
static WinResources *createFromEXE(const String &fileName);
|
||||
static WinResources *createFromEXE(const Path &fileName);
|
||||
static WinResources *createFromEXE(SeekableReadStream *stream);
|
||||
|
||||
typedef Common::HashMap<Common::String, Common::U32String, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo> VersionHash;
|
||||
|
@ -41,7 +41,7 @@ XMLParser::~XMLParser() {
|
||||
_layoutList.clear();
|
||||
}
|
||||
|
||||
bool XMLParser::loadFile(const String &filename) {
|
||||
bool XMLParser::loadFile(const Path &filename) {
|
||||
_stream = SearchMan.createReadStreamForMember(filename);
|
||||
if (!_stream)
|
||||
return false;
|
||||
@ -96,7 +96,7 @@ bool XMLParser::parserError(const String &errStr) {
|
||||
assert(_stream->pos() == startPosition);
|
||||
currentPosition = startPosition;
|
||||
|
||||
Common::String errorMessage = Common::String::format("\n File <%s>, line %d:\n", _fileName.c_str(), lineCount);
|
||||
Common::String errorMessage = Common::String::format("\n File <%s>, line %d:\n", _fileName.toString().c_str(), lineCount);
|
||||
|
||||
if (startPosition > 1) {
|
||||
int keyOpening = 0;
|
||||
|
@ -168,7 +168,7 @@ public:
|
||||
*
|
||||
* @param filename Name of the file to load.
|
||||
*/
|
||||
bool loadFile(const String &filename);
|
||||
bool loadFile(const Path &filename);
|
||||
|
||||
bool loadFile(const FSNode &node);
|
||||
|
||||
@ -377,7 +377,7 @@ private:
|
||||
char _char;
|
||||
bool _allowText; /** Allow text nodes in the doc (default false) */
|
||||
SeekableReadStream *_stream;
|
||||
String _fileName;
|
||||
Path _fileName;
|
||||
|
||||
ParserState _state; /** Internal state of the parser */
|
||||
|
||||
|
@ -29,7 +29,7 @@ LuaFileProxy *LuaFileProxy::create(const Common::String &filename, const Common:
|
||||
if (filename.contains("config.lua"))
|
||||
return new LuaFileConfig(filename, mode);
|
||||
|
||||
return new LuaFileRead(filename, mode);
|
||||
return new LuaFileRead(Common::Path(filename, '/'), mode);
|
||||
}
|
||||
|
||||
LuaFileConfig::LuaFileConfig(const Common::String &filename, const Common::String &mode) : _readPos(0) {
|
||||
@ -235,10 +235,10 @@ void LuaFileConfig::setLanguage(const Common::String &lang) {
|
||||
}
|
||||
|
||||
|
||||
LuaFileRead::LuaFileRead(const Common::String &filename, const Common::String &mode) {
|
||||
LuaFileRead::LuaFileRead(const Common::Path &filename, const Common::String &mode) {
|
||||
assert(mode == "r");
|
||||
if (!_file.open(filename))
|
||||
error("Could not open file %s", filename.c_str());
|
||||
error("Could not open file %s", filename.toString().c_str());
|
||||
|
||||
_size = _file.size();
|
||||
}
|
||||
|
@ -69,7 +69,7 @@ private:
|
||||
Common::File _file;
|
||||
int32 _size;
|
||||
public:
|
||||
LuaFileRead(const Common::String &filename, const Common::String &mode);
|
||||
LuaFileRead(const Common::Path &filename, const Common::String &mode);
|
||||
public:
|
||||
virtual ~LuaFileRead() {}
|
||||
|
||||
|
@ -177,7 +177,7 @@ SeekableReadStream *MacResManager::openAppleDoubleWithAppleOrOSXNaming(Archive&
|
||||
const Common::FSNode *plainFsNode = dynamic_cast<const Common::FSNode *>(archiveMember.get());
|
||||
|
||||
// Try finding __MACOSX
|
||||
Common::StringArray components = (plainFsNode ? Common::Path(plainFsNode->getPath(), '/') : fileName).splitComponents();
|
||||
Common::StringArray components = (plainFsNode ? plainFsNode->getPath() : fileName).splitComponents();
|
||||
if (components.empty() || components[components.size() - 1].empty())
|
||||
return nullptr;
|
||||
for (int i = components.size() - 1; i >= 0; i--) {
|
||||
@ -512,20 +512,20 @@ bool MacResManager::getFileFinderInfo(const Path &fileName, MacFinderInfo &outFi
|
||||
return getFileFinderInfo(fileName, SearchMan, outFinderInfo, outFinderExtendedInfo);
|
||||
}
|
||||
|
||||
void MacResManager::listFiles(StringArray &files, const String &pattern) {
|
||||
void MacResManager::listFiles(Array<Path> &files, const Path &pattern) {
|
||||
// Base names discovered so far.
|
||||
typedef HashMap<String, bool, IgnoreCase_Hash, IgnoreCase_EqualTo> BaseNameSet;
|
||||
typedef HashMap<Path, bool, Path::IgnoreCase_Hash, Path::IgnoreCase_EqualTo> BaseNameSet;
|
||||
BaseNameSet baseNames;
|
||||
|
||||
// List files itself.
|
||||
ArchiveMemberList memberList;
|
||||
SearchMan.listMatchingMembers(memberList, pattern);
|
||||
SearchMan.listMatchingMembers(memberList, pattern + ".rsrc");
|
||||
SearchMan.listMatchingMembers(memberList, pattern + ".bin");
|
||||
SearchMan.listMatchingMembers(memberList, pattern.append(".rsrc"));
|
||||
SearchMan.listMatchingMembers(memberList, pattern.append(".bin"));
|
||||
SearchMan.listMatchingMembers(memberList, constructAppleDoubleName(pattern));
|
||||
|
||||
for (ArchiveMemberList::const_iterator i = memberList.begin(), end = memberList.end(); i != end; ++i) {
|
||||
String filename = (*i)->getName();
|
||||
String filename = (*i)->getFileName();
|
||||
|
||||
// For raw resource forks and MacBinary files we strip the extension
|
||||
// here to obtain a valid base name.
|
||||
@ -560,12 +560,13 @@ void MacResManager::listFiles(StringArray &files, const String &pattern) {
|
||||
|
||||
// Strip AppleDouble '._' prefix if applicable.
|
||||
bool isAppleDoubleName = false;
|
||||
const String filenameAppleDoubleStripped = disassembleAppleDoubleName(filename, &isAppleDoubleName).toString();
|
||||
const Path filenameAppleDoubleStripped = disassembleAppleDoubleName(
|
||||
Common::Path(filename, Common::Path::kNoSeparator), &isAppleDoubleName);
|
||||
|
||||
if (isAppleDoubleName) {
|
||||
SeekableReadStream *stream = (*i)->createReadStream();
|
||||
if (stream->readUint32BE() == 0x00051607) {
|
||||
filename = filenameAppleDoubleStripped;
|
||||
filename = filenameAppleDoubleStripped.baseName();
|
||||
}
|
||||
// TODO: Should we really keep filenames suggesting AppleDouble
|
||||
// but not being AppleDouble around? This might depend on the
|
||||
@ -573,7 +574,8 @@ void MacResManager::listFiles(StringArray &files, const String &pattern) {
|
||||
delete stream;
|
||||
}
|
||||
|
||||
baseNames[filename] = true;
|
||||
Common::Path basePath((*i)->getPathInArchive().getParent().appendComponent(filename));
|
||||
baseNames[basePath] = true;
|
||||
}
|
||||
|
||||
// Append resulting base names to list to indicate found files.
|
||||
@ -1011,25 +1013,28 @@ void MacResManager::readMap() {
|
||||
}
|
||||
}
|
||||
|
||||
Path MacResManager::constructAppleDoubleName(Path name) {
|
||||
Path MacResManager::constructAppleDoubleName(const Path &name) {
|
||||
// Insert "._" before the last portion of a path name
|
||||
Path parent = name.getParent();
|
||||
Path ret = name.getParent();
|
||||
Path lastComponent = name.getLastComponent();
|
||||
return parent.append("._").append(lastComponent);
|
||||
return ret.appendInPlace("._").appendInPlace(lastComponent);
|
||||
}
|
||||
|
||||
Path MacResManager::disassembleAppleDoubleName(Path name, bool *isAppleDouble) {
|
||||
Path MacResManager::disassembleAppleDoubleName(const Path &name, bool *isAppleDouble) {
|
||||
if (isAppleDouble) {
|
||||
*isAppleDouble = false;
|
||||
}
|
||||
|
||||
// Remove "._" before the last portion of a path name.
|
||||
Path parent = name.getParent();
|
||||
Path lastComponent = name.getLastComponent();
|
||||
String lastComponentString = lastComponent.toString();
|
||||
if (!lastComponentString.hasPrefix("._"))
|
||||
Path ret = name.getParent();
|
||||
String lastComponent = name.baseName();
|
||||
if (!lastComponent.hasPrefix("._"))
|
||||
return name;
|
||||
return parent.appendComponent(lastComponentString.substr(2));
|
||||
ret = ret.appendComponent(lastComponent.substr(2));
|
||||
if (name.isSeparatorTerminated()) {
|
||||
ret.appendInPlace("/");
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
void MacResManager::dumpRaw() {
|
||||
@ -1048,10 +1053,10 @@ void MacResManager::dumpRaw() {
|
||||
dataSize = len;
|
||||
}
|
||||
|
||||
Common::String filename = Common::String::format("./dumps/%s-%s-%d", _baseFileName.toString().c_str(), tag2str(_resTypes[i].id), j);
|
||||
Common::String filename = Common::String::format("./dumps/%s-%s-%d", _baseFileName.baseName().c_str(), tag2str(_resTypes[i].id), j);
|
||||
_stream->read(data, len);
|
||||
|
||||
if (!out.open(filename)) {
|
||||
if (!out.open(Common::Path(filename, '/'))) {
|
||||
warning("MacResManager::dumpRaw(): Can not open dump file %s", filename.c_str());
|
||||
return;
|
||||
}
|
||||
|
@ -193,7 +193,7 @@ public:
|
||||
* @param pattern Pattern to match against. Taking String::matchPattern's
|
||||
* format.
|
||||
*/
|
||||
static void listFiles(StringArray &files, const String &pattern);
|
||||
static void listFiles(Array<Path> &files, const Path &pattern);
|
||||
|
||||
/**
|
||||
* Close the Mac data/resource fork pair.
|
||||
@ -321,8 +321,8 @@ private:
|
||||
|
||||
static bool readAndValidateMacBinaryHeader(SeekableReadStream &stream, byte (&outMacBinaryHeader)[MBI_INFOHDR]);
|
||||
|
||||
static Path constructAppleDoubleName(Path name);
|
||||
static Path disassembleAppleDoubleName(Path name, bool *isAppleDouble);
|
||||
static Path constructAppleDoubleName(const Path &name);
|
||||
static Path disassembleAppleDoubleName(const Path &name, bool *isAppleDouble);
|
||||
|
||||
static SeekableReadStream *openAppleDoubleWithAppleOrOSXNaming(Archive& archive, const Path &fileName);
|
||||
|
||||
|
@ -227,7 +227,7 @@ bool TranslationManager::openTranslationsFile(File &inFile) {
|
||||
|
||||
// Then try to open it using the SearchMan.
|
||||
ArchiveMemberList fileList;
|
||||
SearchMan.listMatchingMembers(fileList, _translationsFileName);
|
||||
SearchMan.listMatchingMembers(fileList, Common::Path(_translationsFileName, Common::Path::kNoSeparator));
|
||||
for (ArchiveMemberList::iterator it = fileList.begin(); it != fileList.end(); ++it) {
|
||||
ArchiveMember const &m = **it;
|
||||
SeekableReadStream *const stream = m.createReadStream();
|
||||
|
@ -59,7 +59,7 @@ RNCAArchive* RNCAArchive::open(Common::SeekableReadStream *stream, DisposeAfterU
|
||||
ptr++;
|
||||
uint32 off = READ_BE_UINT32(ptr);
|
||||
eptr = ptr + 4;
|
||||
files[fileName] = RNCAFileDescriptor(fileName, off);
|
||||
files[Common::Path(fileName, Common::Path::kNoSeparator)] = RNCAFileDescriptor(fileName, off);
|
||||
}
|
||||
|
||||
delete[] metadata;
|
||||
@ -80,14 +80,14 @@ int RNCAArchive::listMembers(Common::ArchiveMemberList &list) const {
|
||||
}
|
||||
|
||||
const Common::ArchiveMemberPtr RNCAArchive::getMember(const Common::Path &path) const {
|
||||
Common::String translated = translatePath(path);
|
||||
Common::Path translated = translatePath(path);
|
||||
if (!_files.contains(translated))
|
||||
return nullptr;
|
||||
|
||||
return Common::ArchiveMemberPtr(new Common::GenericArchiveMember(_files.getVal(translated)._fileName, *this));
|
||||
}
|
||||
|
||||
Common::SharedArchiveContents RNCAArchive::readContentsForPath(const Common::String& translated) const {
|
||||
Common::SharedArchiveContents RNCAArchive::readContentsForPath(const Common::Path &translated) const {
|
||||
if (!_files.contains(translated))
|
||||
return Common::SharedArchiveContents();
|
||||
const RNCAFileDescriptor& desc = _files.getVal(translated);
|
||||
|
@ -34,7 +34,7 @@ public:
|
||||
bool hasFile(const Common::Path &path) const override;
|
||||
int listMembers(Common::ArchiveMemberList&) const override;
|
||||
const Common::ArchiveMemberPtr getMember(const Common::Path &path) const override;
|
||||
Common::SharedArchiveContents readContentsForPath(const Common::String& translated) const override;
|
||||
Common::SharedArchiveContents readContentsForPath(const Common::Path &translated) const override;
|
||||
|
||||
static RNCAArchive* open(Common::SeekableReadStream *stream, DisposeAfterUse::Flag dispose = DisposeAfterUse::NO);
|
||||
|
||||
@ -53,7 +53,7 @@ private:
|
||||
RNCAFileDescriptor() : _fileDataOffset(0) {}
|
||||
};
|
||||
|
||||
typedef Common::HashMap<Common::String, RNCAFileDescriptor, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo> FileMap;
|
||||
typedef Common::HashMap<Common::Path, RNCAFileDescriptor, Common::Path::IgnoreCase_Hash, Common::Path::IgnoreCase_EqualTo> FileMap;
|
||||
|
||||
RNCAArchive(FileMap files, Common::SeekableReadStream *stream, DisposeAfterUse::Flag dispose)
|
||||
: _files(files), _stream(stream, dispose) {
|
||||
|
@ -76,14 +76,14 @@ int MpsInstaller::listMembers(Common::ArchiveMemberList &list) const {
|
||||
}
|
||||
|
||||
const Common::ArchiveMemberPtr MpsInstaller::getMember(const Common::Path &path) const {
|
||||
Common::String translated = translatePath(path);
|
||||
Common::Path translated = translatePath(path);
|
||||
if (!_files.contains(translated))
|
||||
return nullptr;
|
||||
|
||||
return Common::ArchiveMemberPtr(new Common::GenericArchiveMember(_files.getVal(translated)._fileName, *this));
|
||||
}
|
||||
|
||||
Common::SharedArchiveContents MpsInstaller::readContentsForPath(const Common::String& translated) const {
|
||||
Common::SharedArchiveContents MpsInstaller::readContentsForPath(const Common::Path &translated) const {
|
||||
if (!_files.contains(translated))
|
||||
return Common::SharedArchiveContents();
|
||||
FileDescriptor desc = _files.getVal(translated);
|
||||
|
@ -33,11 +33,11 @@ namespace MADS {
|
||||
class MpsInstaller : public Common::MemcachingCaseInsensitiveArchive {
|
||||
public:
|
||||
bool hasFile(const Common::Path &path) const override;
|
||||
int listMembers(Common::ArchiveMemberList&) const override;
|
||||
int listMembers(Common::ArchiveMemberList &) const override;
|
||||
const Common::ArchiveMemberPtr getMember(const Common::Path &path) const override;
|
||||
Common::SharedArchiveContents readContentsForPath(const Common::String& translatedPath) const override;
|
||||
Common::SharedArchiveContents readContentsForPath(const Common::Path &translatedPath) const override;
|
||||
|
||||
static MpsInstaller* open(const Common::Path& baseName);
|
||||
static MpsInstaller* open(const Common::Path &baseName);
|
||||
|
||||
private:
|
||||
// Similar to FileDescriptionBin but in native-endian and native strings.
|
||||
@ -73,7 +73,7 @@ private:
|
||||
friend class MpsInstaller;
|
||||
};
|
||||
|
||||
typedef Common::HashMap<Common::String, FileDescriptor, Common::IgnoreCase_Hash, Common::IgnoreCase_EqualTo> FileMap;
|
||||
typedef Common::HashMap<Common::Path, FileDescriptor, Common::Path::IgnoreCase_Hash, Common::Path::IgnoreCase_EqualTo> FileMap;
|
||||
|
||||
MpsInstaller(const FileMap& files,
|
||||
const Common::Path& baseName) : _files(files), _baseName(baseName) {}
|
||||
|
@ -349,12 +349,12 @@ Common::Error SagaEngine::run() {
|
||||
setTotalPlayTime(0);
|
||||
|
||||
if (getFeatures() & GF_INSTALLER) {
|
||||
Common::Array<Common::String> filenames;
|
||||
Common::Array<Common::Path> filenames;
|
||||
for (const ADGameFileDescription *gameArchiveDescription = getArchivesDescriptions();
|
||||
gameArchiveDescription->fileName; gameArchiveDescription++)
|
||||
filenames.push_back(gameArchiveDescription->fileName);
|
||||
Common::Archive *archive = nullptr;
|
||||
if (filenames.size() == 1 && filenames[0].hasSuffix(".exe"))
|
||||
if (filenames.size() == 1 && filenames[0].baseName().hasSuffix(".exe"))
|
||||
archive = Common::makeZipArchive(filenames[0], true);
|
||||
else
|
||||
archive = Common::makeArjArchive(filenames, true);
|
||||
|
@ -655,12 +655,13 @@ int ResourceManager::addAppropriateSources() {
|
||||
#endif
|
||||
} else if (Common::MacResManager::exists("Data1")) {
|
||||
// Mac SCI1.1+ file naming scheme
|
||||
Common::StringArray files;
|
||||
Common::Array<Common::Path> files;
|
||||
Common::MacResManager::listFiles(files, "Data#");
|
||||
Common::MacResManager::listFiles(files, "Data##");
|
||||
|
||||
for (Common::StringArray::const_iterator x = files.begin(); x != files.end(); ++x) {
|
||||
addSource(new MacResourceForkResourceSource(*x, atoi(x->c_str() + 4)));
|
||||
for (Common::Array<Common::Path>::const_iterator x = files.begin(); x != files.end(); ++x) {
|
||||
Common::String path(x->toString());
|
||||
addSource(new MacResourceForkResourceSource(path, atoi(path.c_str() + 4)));
|
||||
}
|
||||
|
||||
#ifdef ENABLE_SCI32
|
||||
|
Loading…
Reference in New Issue
Block a user