diff options
Diffstat (limited to 'src/fs')
39 files changed, 0 insertions, 5732 deletions
diff --git a/src/fs/files.cpp b/src/fs/files.cpp deleted file mode 100644 index d5c600fb9..000000000 --- a/src/fs/files.cpp +++ /dev/null @@ -1,319 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "fs/files.h" - -#include "fs/mkdir.h" -#if defined(ANDROID) || defined(__native_client__) -#include "fs/paths.h" - -#include "fs/virtfs/fs.h" -#include "fs/virtfs/tools.h" -#include "fs/virtfs/list.h" -#endif // defined(ANDROID) || defined(__native_client__) - -#if defined(ANDROID) || defined(__native_client__) -#include "utils/foreach.h" -#endif // defined(ANDROID) || defined(__native_client__) - -#include "utils/checkutils.h" -#include "utils/stringutils.h" - -#include <dirent.h> -#include <sys/stat.h> - -#include "debug.h" - -extern const char *dirSeparator; - -#ifdef ANDROID -void Files::extractLocale() -{ - // in future need also remove all locales in local dir - - const std::string fileName2 = pathJoin(getenv("APPDIR"), "locale.zip"); - VirtFs::mountZip(fileName2, Append_false); - - const std::string localDir = std::string(getenv("APPDIR")); - VirtFs::List *const rootDirs = VirtFs::enumerateFiles("locale"); - FOR_EACH (StringVectCIter, i, rootDirs->names) - { - const std::string dir = pathJoin("locale", *i); - if (VirtFs::isDirectory(dir)) - { - const std::string moFile = dir + "/LC_MESSAGES/manaplus.mo"; - if (VirtFs::exists((moFile))) - { - const std::string localFile = pathJoin(localDir, moFile); - const std::string localDir2 = pathJoin(localDir, - dir, - "LC_MESSAGES"); - mkdir_r(localDir2.c_str()); - copyVirtFsFile(moFile, localFile); - } - } - } - VirtFs::freeList(rootDirs); - VirtFs::unmountZip(fileName2); - remove(fileName2.c_str()); -} -#endif // ANDROID - -#if defined(ANDROID) || defined(__native_client__) - -namespace -{ -#ifdef ANDROID - int mFilesCount = 0; -#endif // ANDROID - - Files::CopyFileCallbackPtr mCallbackPtr = nullptr; -} // namespace - -void Files::setCopyCallBack(Files::CopyFileCallbackPtr callback) -{ - mCallbackPtr = callback; -} - -void Files::copyVirtFsFile(const std::string &restrict inFile, - const std::string &restrict outFile) -{ - int size = 0; - const char *const buf = VirtFs::loadFile(inFile, size); - FILE *const file = fopen(outFile.c_str(), "w"); - fwrite(buf, 1, size, file); - fclose(file); - delete [] buf; -#ifdef ANDROID - if (mCallbackPtr) - { - mCallbackPtr(mFilesCount); - mFilesCount ++; - } -#endif // ANDROID -} - -void Files::copyVirtFsDir(const std::string &restrict inDir, - const std::string &restrict outDir) -{ - mkdir_r(outDir.c_str()); - VirtFs::List *const files = VirtFs::enumerateFiles(inDir); - FOR_EACH (StringVectCIter, i, files->names) - { - const std::string file = pathJoin(inDir, *i); - const std::string outDir2 = pathJoin(outDir, *i); - if (VirtFs::isDirectory(file)) - copyVirtFsDir(file, outDir2); - else - copyVirtFsFile(file, outDir2); - } - VirtFs::freeList(files); -} - -#endif // ANDROID __native_client__ - -int Files::renameFile(const std::string &restrict srcName, - const std::string &restrict dstName) -{ -#if defined __native_client__ - FILE *srcFile = fopen(srcName.c_str(), "rb"); - if (srcFile == nullptr) - return -1; - FILE *dstFile = fopen(dstName.c_str(), "w+b"); - if (dstFile == nullptr) - { - fclose(srcFile); - return -1; - } - - const int chunkSize = 500000; - char *buf = new char[chunkSize]; - size_t sz = 0; - while ((sz = fread(buf, 1, chunkSize, srcFile))) - { - if (fwrite(buf, 1, sz, dstFile) != sz) - { - delete [] buf; - fclose(srcFile); - fclose(dstFile); - ::remove(dstName.c_str()); - return -1; - } - } - - delete [] buf; - fclose(srcFile); - fclose(dstFile); - if (!::remove(srcName.c_str())) - return 0; - - return -1; -#else // defined __native_client__ - - return ::rename(srcName.c_str(), dstName.c_str()); -#endif // defined __native_client__ -} - -int Files::copyFile(const std::string &restrict srcName, - const std::string &restrict dstName) -{ - FILE *srcFile = fopen(srcName.c_str(), "rb"); - if (srcFile == nullptr) - return -1; - FILE *dstFile = fopen(dstName.c_str(), "w+b"); - if (dstFile == nullptr) - { - fclose(srcFile); - return -1; - } - - const int chunkSize = 512000; - char *buf = new char[chunkSize]; - size_t sz = 0; - while ((sz = fread(buf, 1, chunkSize, srcFile)) != 0u) - { - if (fwrite(buf, 1, sz, dstFile) != sz) - { - delete [] buf; - fclose(srcFile); - fclose(dstFile); - return -1; - } - } - - delete [] buf; - fclose(srcFile); - fclose(dstFile); - return 0; -} - -bool Files::existsLocal(const std::string &path) -{ - struct stat statbuf; -#ifdef WIN32 - // in windows path\file.ext\ by default detected as exists - // if file.ext is not directory, need return false - const bool res = (stat(path.c_str(), &statbuf) == 0); - if (res == false) - return false; - if ((findLast(path, "/") == true || findLast(path, "\\") == true) && - S_ISDIR(statbuf.st_mode) == 0) - { - return false; - } - return true; -#else // WIN32 - return stat(path.c_str(), &statbuf) == 0; -#endif // WIN32 -} - -bool Files::loadTextFileLocal(const std::string &fileName, - StringVect &lines) -{ - std::ifstream file; - char line[501]; - - file.open(fileName.c_str(), std::ios::in); - - if (!file.is_open()) - { - reportAlways("Couldn't load text file: %s", - fileName.c_str()); - return false; - } - - while (file.getline(line, 500)) - lines.push_back(line); - - return true; -} - -void Files::saveTextFile(const std::string &path, - const std::string &restrict name, - const std::string &restrict text) -{ - if (mkdir_r(path.c_str()) == 0) - { - std::ofstream file; - std::string fileName = pathJoin(path, name); - file.open(fileName.c_str(), std::ios::out); - if (file.is_open()) - { - file << text << std::endl; - } - else - { - reportAlways("Error opening file for writing: %s", - fileName.c_str()); - } - file.close(); - } -} - -void Files::deleteFilesInDirectory(std::string path) -{ - path = pathJoin(path, dirSeparator); - const struct dirent *next_file = nullptr; - DIR *const dir = opendir(path.c_str()); - - if (dir != nullptr) - { - while ((next_file = readdir(dir)) != nullptr) - { - const std::string file = next_file->d_name; - if (file != "." && file != "..") - remove((path + file).c_str()); - } - closedir(dir); - } -} - -void Files::enumFiles(StringVect &files, - std::string path, - const bool skipSymlinks A_WIN_UNUSED) -{ - if (findLast(path, dirSeparator) == false) - path += dirSeparator; - DIR *const dir = opendir(path.c_str()); - - if (dir != nullptr) - { - const struct dirent *next_file = nullptr; - while ((next_file = readdir(dir)) != nullptr) - { - const std::string file = next_file->d_name; - if (file == "." || file == "..") - continue; -#ifndef WIN32 - if (skipSymlinks == true) - { - struct stat statbuf; - if (lstat(path.c_str(), &statbuf) == 0 && - S_ISLNK(statbuf.st_mode) != 0) - { - continue; - } - } -#endif // WIN32 - files.push_back(file); - } - closedir(dir); - } -} diff --git a/src/fs/files.h b/src/fs/files.h deleted file mode 100644 index 146a85ff1..000000000 --- a/src/fs/files.h +++ /dev/null @@ -1,69 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_FILES_H -#define UTILS_FILES_H - -#include "utils/stringvector.h" - -#include "localconsts.h" - -namespace Files -{ -#ifdef ANDROID - void extractLocale(); -#endif // ANDROID - -#if defined(ANDROID) || defined(__native_client__) - typedef void (*CopyFileCallbackPtr) (int cnt); - - void setCopyCallBack(CopyFileCallbackPtr callback); - - void copyVirtFsFile(const std::string &restrict inFile, - const std::string &restrict outFile); - - void copyVirtFsDir(const std::string &restrict inDir, - const std::string &restrict outDir); - -#endif // ANDROID __native_client__ - - int renameFile(const std::string &restrict pFrom, - const std::string &restrict pTo); - - int copyFile(const std::string &restrict pFrom, - const std::string &restrict pTo); - - bool existsLocal(const std::string &path); - - bool loadTextFileLocal(const std::string &fileName, - StringVect &lines); - - void saveTextFile(const std::string &path, - const std::string &restrict name, - const std::string &restrict text); - - void deleteFilesInDirectory(std::string path); - - void enumFiles(StringVect &files, - std::string path, - const bool skipSymlinks); -} // namespace Files - -#endif // UTILS_FILES_H diff --git a/src/fs/mkdir.cpp b/src/fs/mkdir.cpp deleted file mode 100644 index 341f138da..000000000 --- a/src/fs/mkdir.cpp +++ /dev/null @@ -1,166 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2010 The Mana Developers - * Copyright (C) 2011-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "fs/mkdir.h" - -#include "utils/cast.h" - -#if defined WIN32 -#include <limits.h> -#include <windows.h> -#endif // defined WIN32 - -#include <sys/stat.h> - -#include "debug.h" - -#if defined WIN32 -int mkdir_r(const char *const pathname) -{ - if (!pathname) - return -1; - - char tmp[PATH_MAX]; - char tmp2[PATH_MAX]; - char *p; - - if (strlen(pathname) >= PATH_MAX - 2) - return -1; - - strncpy(tmp, pathname, sizeof(tmp) - 1); - tmp[PATH_MAX - 1] = '\0'; - - const int len = CAST_S32(strlen(tmp)); - - if (len < 1 || len >= INT_MAX) - return -1; - - // terminate the pathname with '/' - if (tmp[len - 1] != '/') - { - tmp[len] = '/'; - tmp[len + 1] = '\0'; - } - - for (p = tmp; *p; p++) - { - if (*p == '/' || *p == '\\') - { - *p = '\0'; - // ignore a slash at the beginning of a path - if (tmp[0] == 0) - { - *p = '/'; - continue; - } - - strcpy(tmp2, tmp); - char *p2 = tmp2 + strlen(tmp2) - 1; - if (*p2 == '/' || *p2 == '\\') - *p2 = 0; - // check if the name already exists, but not as directory - struct stat statbuf; - if (!stat(tmp2, &statbuf)) - { - if (S_ISDIR(statbuf.st_mode)) - { - *p = '/'; - continue; - } - else - return -1; - } - - if (!CreateDirectory(tmp2, nullptr)) - { - // hack, hack. just assume that x: might be a drive - // letter, and try again - if (!(strlen(tmp2) == 2 && !strcmp(tmp2 + 1, ":"))) - return -1; - } - - *p = '/'; - } - } - return 0; -} -#else // WIN32 - -/// Create a directory, making leading components first if necessary -int mkdir_r(const char *const pathname) -{ - if (pathname == nullptr) - return -1; - - const size_t len = CAST_SIZE(strlen(pathname)); - char *tmp = new char[len + 2]; - char *p = nullptr; - - strcpy(tmp, pathname); - - // terminate the pathname with '/' - if (tmp[len - 1] != '/') - { - tmp[len] = '/'; - tmp[len + 1] = '\0'; - } - - for (p = tmp; *p != 0; p++) - { - if (*p == '/') - { - *p = '\0'; - // ignore a slash at the beginning of a path - if (tmp[0] == 0) - { - *p = '/'; - continue; - } - - // check if the name already exists, but not as directory - struct stat statbuf; - if (stat(tmp, &statbuf) == 0) - { - if (S_ISDIR(statbuf.st_mode)) - { - *p = '/'; - continue; - } - else - { - delete []tmp; - return -1; - } - } - - if (mkdir(tmp, S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH) != 0) - { - delete []tmp; - return -1; - } - - *p = '/'; - } - } - delete []tmp; - return 0; -} -#endif // WIN32 diff --git a/src/fs/mkdir.h b/src/fs/mkdir.h deleted file mode 100644 index a662daca3..000000000 --- a/src/fs/mkdir.h +++ /dev/null @@ -1,27 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2010 The Mana Developers - * Copyright (C) 2011-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_MKDIR_H -#define UTILS_MKDIR_H - -int mkdir_r(const char *const pathname); - -#endif // UTILS_MKDIR_H diff --git a/src/fs/paths.cpp b/src/fs/paths.cpp deleted file mode 100644 index 5698ffa7d..000000000 --- a/src/fs/paths.cpp +++ /dev/null @@ -1,279 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2011-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifdef _MSC_VER -# include "msvc/config.h" -#elif defined(HAVE_CONFIG_H) -#include "config.h" -#endif // _MSC_VER - -#include "fs/paths.h" - -#include "fs/virtfs/fs.h" - -#include "utils/checkutils.h" -#include "utils/stringutils.h" - -#ifdef USE_X11 -#include "fs/files.h" - -#include "utils/foreach.h" -#endif // USE_X11 - -#ifdef __native_client__ -#include <limits.h> -#define realpath(N, R) strcpy(R, N) -#endif // __native_client__ - -#ifdef WIN32 -#include "fs/specialfolder.h" -#define realpath(N, R) _fullpath((R), (N), _MAX_PATH) -#elif defined __OpenBSD__ -#include <limits> -#elif defined __native_client__ -#include <limits.h> -#endif // WIN32 - -#ifndef WIN32 -#include <unistd.h> -#include <sys/types.h> -#include <pwd.h> -#endif // WIN32 - -PRAGMA48(GCC diagnostic push) -PRAGMA48(GCC diagnostic ignored "-Wshadow") -#ifdef ANDROID -#ifdef USE_SDL2 -#include <SDL_system.h> -#endif // USE_SDL2 -#endif // ANDROID -PRAGMA48(GCC diagnostic pop) - -#include "debug.h" - -namespace -{ - std::string mPackageDir; -} // namespace - -std::string getRealPath(const std::string &str) -{ -#if defined(__OpenBSD__) || defined(__ANDROID__) || defined(__native_client__) - char *realPath = reinterpret_cast<char*>(calloc(PATH_MAX, sizeof(char))); - if (!realPath) - return ""; - realpath(str.c_str(), realPath); -#else // defined(__OpenBSD__) || defined(__ANDROID__) || - // defined(__native_client__) - - char *realPath = realpath(str.c_str(), nullptr); - if (realPath == nullptr) - return ""; -#endif // defined(__OpenBSD__) || defined(__ANDROID__) || - // defined(__native_client__) - - std::string path = realPath; - free(realPath); - return path; -} - -bool isRealPath(const std::string &str) -{ - return str == getRealPath(str); -} - -bool checkPath(const std::string &path) -{ - if (path.empty()) - return true; - return path.find("../") == std::string::npos - && path.find("..\\") == std::string::npos - && path.find("/..") == std::string::npos - && path.find("\\..") == std::string::npos; -} - -void prepareFsPath(std::string &path) -{ -#ifdef DEBUGFS - std::string path2 = path; -#endif - sanitizePath(path); -// can be enabled for debugging -#ifdef DEBUGFS - if (path != path2) - { - reportAlways("Path can be improved: '%s' -> '%s'", - path2.c_str(), - path.c_str()); - } -#endif -} - -std::string &fixDirSeparators(std::string &str) -{ -#ifdef WIN32 - return replaceAll(str, "/", "\\"); -#else - return str; -#endif -} - -std::string removeLast(const std::string &str) -{ - size_t pos2 = str.rfind('/'); - const size_t pos3 = str.rfind('\\'); - if (pos3 != std::string::npos) - { - if (pos2 == std::string::npos || pos3 > pos2) - pos2 = pos3; - } - if (pos2 != std::string::npos) - return str.substr(0, pos2); - return str; -} - -#ifdef WIN32 -std::string getSelfName() -{ - return "manaplus.exe"; -} - -#elif defined(__APPLE__) -std::string getSelfName() -{ - return "manaplus.exe"; -} - -#elif defined __linux__ || defined __linux - -std::string getSelfName() -{ - char buf[257]; - const ssize_t sz = readlink("/proc/self/exe", buf, 256); - if (sz > 0 && sz < 256) - { - buf[sz] = 0; - return buf; - } - return ""; -} - -#else // WIN32 - -std::string getSelfName() -{ - return ""; -} - -#endif // WIN32 - -std::string getPicturesDir() -{ -#ifdef WIN32 - std::string dir = getSpecialFolderLocation(CSIDL_MYPICTURES); - if (dir.empty()) - dir = getSpecialFolderLocation(CSIDL_DESKTOP); - return dir; -#elif defined USE_X11 - char *xdg = getenv("XDG_CONFIG_HOME"); - std::string file; - if (!xdg) - { - file = pathJoin(VirtFs::getUserDir(), - ".config/user-dirs.dirs"); - } - else - { - file = pathJoin(xdg, "user-dirs.dirs"); - } - - if (Files::existsLocal(file)) - { - StringVect arr; - Files::loadTextFileLocal(file, arr); - FOR_EACH (StringVectCIter, it, arr) - { - std::string str = *it; - if (findCutFirst(str, "XDG_PICTURES_DIR=\"")) - { - str = str.substr(0, str.size() - 1); - // use hack to replace $HOME var. - // if in string other vars, fallback to default path - replaceAll(str, "$HOME/", VirtFs::getUserDir()); - str = getRealPath(str); - if (str.empty()) - str = pathJoin(VirtFs::getUserDir(), "Desktop"); - return str; - } - } - } -#endif // WIN32 - - return pathJoin(VirtFs::getUserDir(), "Desktop"); -} - -std::string getHomePath() -{ -#if defined(UNITTESTS) && defined(UNITESTSDIR) - std::string dir = UNITESTSDIR; - if (findLast(dir, std::string(dirSeparator)) == false) - dir += dirSeparator; - return dir; -#else // defined(UNITTESTS) && defined(UNITESTSDIR) -#ifdef WIN32 - return getSpecialFolderLocation(CSIDL_LOCAL_APPDATA); -#else - const char *path = getenv("HOME"); - if (path == nullptr) - { - const uid_t uid = getuid(); - const struct passwd *const pw = getpwuid(uid); - if (pw != nullptr && - pw->pw_dir != nullptr) - { - path = pw->pw_dir; - } - if (path == nullptr) - return dirSeparator; - } - std::string dir = path; - if (findLast(dir, std::string(dirSeparator)) == false) - dir += dirSeparator; - return dir; -#endif // WIN32 -#endif // defined(UNITTESTS) && defined(UNITESTSDIR) -} - -#ifdef ANDROID -std::string getSdStoragePath() -{ - return getenv("DATADIR2"); -} -#endif // ANDROID - -std::string getPackageDir() -{ - return mPackageDir; -} - -void setPackageDir(const std::string &dir) -{ - mPackageDir = dir; -} diff --git a/src/fs/paths.h b/src/fs/paths.h deleted file mode 100644 index be431f9c3..000000000 --- a/src/fs/paths.h +++ /dev/null @@ -1,54 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2011-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_PATHS_H -#define UTILS_PATHS_H - -#include <string> - -#include "localconsts.h" - -std::string getRealPath(const std::string &str) A_WARN_UNUSED; - -bool isRealPath(const std::string &str) A_WARN_UNUSED; - -bool checkPath(const std::string &path) A_WARN_UNUSED; - -void prepareFsPath(std::string &path); - -std::string &fixDirSeparators(std::string &str); - -std::string removeLast(const std::string &str) A_WARN_UNUSED; - -std::string getSelfName() A_WARN_UNUSED; - -std::string getPicturesDir() A_WARN_UNUSED; - -#ifdef ANDROID -std::string getSdStoragePath() A_WARN_UNUSED; -#endif // ANDROID - -std::string getPackageDir() A_WARN_UNUSED; - -void setPackageDir(const std::string &dir); - -std::string getHomePath(); - -#endif // UTILS_PATHS_H diff --git a/src/fs/specialfolder.cpp b/src/fs/specialfolder.cpp deleted file mode 100644 index ee27dab4b..000000000 --- a/src/fs/specialfolder.cpp +++ /dev/null @@ -1,59 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2010 The Mana Developers - * Copyright (C) 2011-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifdef WIN32 -#include "fs/specialfolder.h" -#include <windows.h> - -#include "debug.h" - -/* - * Retrieve the pathname of special folders on win32, or an empty string - * on error / if the folder does not exist. - * See http://msdn.microsoft.com/en-us/library/bb762494(VS.85).aspx for - * a list of folder ids - */ -std::string getSpecialFolderLocation(const int folderId) -{ - std::string ret; - LPITEMIDLIST pItemIdList; - LPMALLOC pMalloc; - char szPath[_MAX_PATH]; - - // get the item ID list for folderId - HRESULT hr = SHGetSpecialFolderLocation(nullptr, folderId, &pItemIdList); - if (hr != S_OK) - return ret; - - // convert the ID list into a file system path - if (SHGetPathFromIDList(pItemIdList, szPath) == FALSE) - return ret; - - // get the IMalloc pointer and free all resources we used - hr = SHGetMalloc(&pMalloc); - pMalloc->Free(pItemIdList); - pMalloc->Release(); - - ret = szPath; - return ret; -} - -#endif // WIN32 diff --git a/src/fs/specialfolder.h b/src/fs/specialfolder.h deleted file mode 100644 index f2cc93c9b..000000000 --- a/src/fs/specialfolder.h +++ /dev/null @@ -1,33 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2010 The Mana Developers - * Copyright (C) 2011-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_SPECIALFOLDER_H -#define UTILS_SPECIALFOLDER_H - -#ifdef WIN32 -#include <shlobj.h> -#include <string> - -#include "localconsts.h" -std::string getSpecialFolderLocation(const int folderId) A_WARN_UNUSED; -#endif // WIN32 - -#endif // UTILS_SPECIALFOLDER_H diff --git a/src/fs/virtfs/direntry.cpp b/src/fs/virtfs/direntry.cpp deleted file mode 100644 index c178d4c88..000000000 --- a/src/fs/virtfs/direntry.cpp +++ /dev/null @@ -1,45 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "fs/virtfs/direntry.h" - -#include "debug.h" - -namespace VirtFs -{ - -DirEntry::DirEntry(const std::string &userDir0, - const std::string &rootDir, - const std::string &subDir0, - const std::string &rootSubDir0, - FsFuncs *restrict const funcs0) : - FsEntry(FsEntryType::Dir, funcs0), - userDir(userDir0), - rootSubDir(rootSubDir0) -{ - root = rootDir; - subDir = subDir0; -} - -DirEntry::~DirEntry() -{ -} - -} // namespace VirtFs diff --git a/src/fs/virtfs/direntry.h b/src/fs/virtfs/direntry.h deleted file mode 100644 index 18e700a6a..000000000 --- a/src/fs/virtfs/direntry.h +++ /dev/null @@ -1,49 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_VIRTDIRENTRY_H -#define UTILS_VIRTDIRENTRY_H - -#include "fs/virtfs/fsentry.h" - -#include "localconsts.h" - -namespace VirtFs -{ - -struct DirEntry final : public FsEntry -{ - DirEntry(const std::string &userDir0, - const std::string &rootDir, - const std::string &subDir0, - const std::string &rootSubDir0, - FsFuncs *restrict const funcs0); - - A_DELETE_COPY(DirEntry) - - virtual ~DirEntry(); - - std::string userDir; - std::string rootSubDir; -}; - -} // namespace VirtFs - -#endif // UTILS_VIRTDIRENTRY_H diff --git a/src/fs/virtfs/file.cpp b/src/fs/virtfs/file.cpp deleted file mode 100644 index fb7fcee11..000000000 --- a/src/fs/virtfs/file.cpp +++ /dev/null @@ -1,56 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "fs/virtfs/file.h" - -#include "debug.h" - -namespace VirtFs -{ - -File::File(const FsFuncs *restrict const funcs0, - const uint8_t *restrict const buf, - const size_t sz) : - funcs(funcs0), - mBuf(buf), - mPos(0U), - mSize(sz), - mFd(FILEHDEFAULT) -{ -} - -File::File(const FsFuncs *restrict const funcs0, - FILEHTYPE fd) : - funcs(funcs0), - mBuf(nullptr), - mPos(0U), - mSize(0U), - mFd(fd) -{ -} - -File::~File() -{ - if (mFd != FILEHDEFAULT) - FILECLOSE(mFd); - delete [] mBuf; -} - -} // namespace VirtFs diff --git a/src/fs/virtfs/file.h b/src/fs/virtfs/file.h deleted file mode 100644 index c564bade4..000000000 --- a/src/fs/virtfs/file.h +++ /dev/null @@ -1,61 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_VIRTFILE_H -#define UTILS_VIRTFILE_H - -#include "localconsts.h" - -#include "fs/virtfs/fileapi.h" - -namespace VirtFs -{ - -struct FsFuncs; - -struct File final -{ - File(const FsFuncs *restrict const funcs0, - const uint8_t *restrict const buf, - const size_t sz); - - File(const FsFuncs *restrict const funcs0, - FILEHTYPE fd); - - A_DELETE_COPY(File) - - ~File(); - - const FsFuncs *funcs; - - // zipfs fields - const uint8_t *mBuf; - - // zipfs fields - size_t mPos; - size_t mSize; - - // dirfs fields - FILEHTYPE mFd; -}; - -} // namespace VirtFs - -#endif // UTILS_VIRTFILE_H diff --git a/src/fs/virtfs/fileapi.h b/src/fs/virtfs/fileapi.h deleted file mode 100644 index 14e7b8204..000000000 --- a/src/fs/virtfs/fileapi.h +++ /dev/null @@ -1,48 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_VIRTFS_FILEAPI_H -#define UTILS_VIRTFS_FILEAPI_H - -#include "localconsts.h" - -#ifdef USE_FILE_FOPEN -#define FILEHTYPE FILE *const -#define FILEMTYPE char * -#define FILEHDEFAULT nullptr -#define FILEOPEN(path, mode) fopen(path, mode) -#define FILECLOSE fclose -#define FILESEEK fseek -#define FILEOPEN_FLAG_READ "rb" -#define FILEOPEN_FLAG_WRITE "wb" -#define FILEOPEN_FLAG_APPEND "ab" -#else // USE_FILE_FOPEN -#define FILEHTYPE const int -#define FILEMTYPE int -#define FILEHDEFAULT -1 -#define FILEOPEN(path, mode) open(path, mode, S_IRUSR | S_IWUSR) -#define FILECLOSE close -#define FILESEEK lseek -#define FILEOPEN_FLAG_READ O_RDONLY -#define FILEOPEN_FLAG_WRITE O_WRONLY | O_CREAT | O_TRUNC -#define FILEOPEN_FLAG_APPEND O_WRONLY | O_CREAT | O_APPEND -#endif // USE_FILE_FOPEN - -#endif // UTILS_VIRTFS_FILEAPI_H diff --git a/src/fs/virtfs/fs.cpp b/src/fs/virtfs/fs.cpp deleted file mode 100644 index 2ec75ac05..000000000 --- a/src/fs/virtfs/fs.cpp +++ /dev/null @@ -1,880 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "fs/virtfs/fs.h" - -#include "fs/files.h" -#include "fs/paths.h" - -#include "fs/virtfs/direntry.h" -#include "fs/virtfs/file.h" -#include "fs/virtfs/fsdir.h" -#include "fs/virtfs/fsfuncs.h" -#include "fs/virtfs/fszip.h" -#include "fs/virtfs/list.h" -#include "fs/virtfs/zipentry.h" -#include "fs/virtfs/zipreader.h" - -#include "utils/checkutils.h" -#include "utils/foreach.h" -#include "utils/stdmove.h" -#include "utils/stringutils.h" - -#include "debug.h" - -const char *dirSeparator = nullptr; - -#ifdef UNITTESTS -#define reportNonTests logger->log -#else // UNITTESTS -#define reportNonTests reportAlways -#endif // UNITTESTS - -namespace VirtFs -{ - namespace - { - STD_VECTOR<FsEntry*> mEntries; - } // namespace - - void init(const std::string &restrict name) - { - updateDirSeparator(); - FsDir::init(name); - FsZip::init(); - } - - void updateDirSeparator() - { -#ifdef WIN32 - dirSeparator = "\\"; -#else // WIN32 - dirSeparator = "/"; -#endif // WIN32 - } - - const char *getDirSeparator() - { - return dirSeparator; - } - - const char *getBaseDir() - { - return FsDir::getBaseDir(); - } - - const char *getUserDir() - { - return FsDir::getUserDir(); - } - - STD_VECTOR<FsEntry*> &getEntries() - { - return mEntries; - } - - FsEntry *searchByRootInternal(const std::string &restrict root, - const std::string &restrict subDir) - { - FOR_EACH (STD_VECTOR<FsEntry*>::const_iterator, it, mEntries) - { - const FsEntry *const entry = *it; - if (entry->root == root && - entry->subDir == subDir) - { - return *it; - } - } - return nullptr; - } - - FsEntry *searchByTypeInternal(const std::string &restrict root, - const FsEntryTypeT type) - { - FOR_EACH (STD_VECTOR<FsEntry*>::const_iterator, it, mEntries) - { - const FsEntry *const entry = *it; - if (entry->root == root && - entry->type == type) - { - return *it; - } - } - return nullptr; - } - - bool exists(std::string name) - { - prepareFsPath(name); - if (checkPath(name) == false) - { - reportAlways("FsDir::exists invalid path: %s", - name.c_str()); - return false; - } - - std::string rootDir = name; - if (findLast(rootDir, std::string(dirSeparator)) == false) - rootDir += dirSeparator; - - FOR_EACH (STD_VECTOR<FsEntry*>::const_iterator, it, mEntries) - { - FsEntry *const entry = *it; - if (entry->funcs->exists(entry, name, rootDir) == true) - return true; - } - return false; - } - - List *enumerateFiles(std::string dirName) - { - List *const list = new List; - prepareFsPath(dirName); - if (checkPath(dirName) == false) - { - reportAlways("VirtFs::enumerateFiles invalid path: %s", - dirName.c_str()); - return list; - } - - std::string rootDir = STD_MOVE(dirName); - if (findLast(rootDir, std::string(dirSeparator)) == false) - rootDir += dirSeparator; - StringVect &names = list->names; - - FOR_EACH (STD_VECTOR<FsEntry*>::const_iterator, it, mEntries) - { - FsEntry *const entry = *it; - entry->funcs->enumerate(entry, rootDir, names); - } - - return list; - } - - void getFiles(std::string dirName, - StringVect &list) - { - prepareFsPath(dirName); - if (checkPath(dirName) == false) - { - reportAlways("VirtFs::enumerateFiles invalid path: %s", - dirName.c_str()); - return; - } - - std::string rootDir = STD_MOVE(dirName); - if (findLast(rootDir, std::string(dirSeparator)) == false) - rootDir += dirSeparator; - - FOR_EACH (STD_VECTOR<FsEntry*>::const_iterator, it, mEntries) - { - FsEntry *const entry = *it; - entry->funcs->getFiles(entry, rootDir, list); - } - } - - void getFilesWithDir(std::string dirName, - StringVect &list) - { - prepareFsPath(dirName); - if (checkPath(dirName) == false) - { - reportAlways("VirtFs::enumerateFiles invalid path: %s", - dirName.c_str()); - return; - } - - std::string rootDir = STD_MOVE(dirName); - if (findLast(rootDir, std::string(dirSeparator)) == false) - rootDir += dirSeparator; - - FOR_EACH (STD_VECTOR<FsEntry*>::const_iterator, it, mEntries) - { - FsEntry *const entry = *it; - entry->funcs->getFilesWithDir(entry, rootDir, list); - } - } - - - void getDirs(std::string dirName, - StringVect &list) - { - prepareFsPath(dirName); - if (checkPath(dirName) == false) - { - reportAlways("VirtFs::enumerateFiles invalid path: %s", - dirName.c_str()); - return; - } - - std::string rootDir = STD_MOVE(dirName); - if (findLast(rootDir, std::string(dirSeparator)) == false) - rootDir += dirSeparator; - - FOR_EACH (STD_VECTOR<FsEntry*>::const_iterator, it, mEntries) - { - FsEntry *const entry = *it; - entry->funcs->getDirs(entry, rootDir, list); - } - } - - bool isDirectory(std::string name) - { - prepareFsPath(name); - if (checkPath(name) == false) - { - reportAlways("VirtFs::isDirectory invalid path: %s", - name.c_str()); - return false; - } - std::string dirName = STD_MOVE(name); - if (findLast(dirName, std::string(dirSeparator)) == false) - dirName += dirSeparator; - - FOR_EACH (STD_VECTOR<FsEntry*>::const_iterator, it, mEntries) - { - FsEntry *const entry = *it; - bool isDirFlag(false); - if (entry->funcs->isDirectory(entry, dirName, isDirFlag) == true) - { - return isDirFlag; - } - } - return false; - } - - bool isSymbolicLink(const std::string &restrict name) - { - return FsDir::isSymbolicLink(name); - } - - void freeList(List *restrict const handle) - { - delete handle; - } - - File *openRead(std::string filename) - { - prepareFsPath(filename); - if (checkPath(filename) == false) - { - reportAlways("VirtFs::openRead invalid path: %s", - filename.c_str()); - return nullptr; - } - FOR_EACH (STD_VECTOR<FsEntry*>::const_iterator, it, mEntries) - { - FsEntry *const entry = *it; - File *const file = entry->funcs->openRead(entry, filename); - if (file != nullptr) - return file; - } - return nullptr; - } - - File *openWrite(std::string filename) - { - prepareFsPath(filename); - if (checkPath(filename) == false) - { - reportAlways("VirtFs::openWrite invalid path: %s", - filename.c_str()); - return nullptr; - } - FOR_EACH (STD_VECTOR<FsEntry*>::const_iterator, it, mEntries) - { - FsEntry *const entry = *it; - File *const file = entry->funcs->openWrite(entry, filename); - if (file != nullptr) - return file; - } - return nullptr; - } - - File *openAppend(std::string filename) - { - prepareFsPath(filename); - if (checkPath(filename) == false) - { - reportAlways("VirtFs::openAppend invalid path: %s", - filename.c_str()); - return nullptr; - } - FOR_EACH (STD_VECTOR<FsEntry*>::const_iterator, it, mEntries) - { - FsEntry *const entry = *it; - File *const file = entry->funcs->openAppend(entry, filename); - if (file != nullptr) - return file; - } - return nullptr; - } - - bool setWriteDir(const std::string &restrict newDir) - { - return FsDir::setWriteDir(newDir); - } - - void addEntry(FsEntry *const entry, - const Append append) - { - if (append == Append_true) - mEntries.push_back(entry); - else - mEntries.insert(mEntries.begin(), entry); - } - - bool mountDirInternal(const std::string &restrict newDir, - std::string subDir, - const Append append) - { - if (newDir.find(".zip") != std::string::npos) - { - reportAlways("Called FsDir::mount with zip archive"); - return false; - } - std::string rootDir = newDir; - if (findLast(rootDir, std::string(dirSeparator)) == false) - rootDir += dirSeparator; - if (subDir == dirSeparator) - { - subDir.clear(); - } - else if (!subDir.empty() && - findLast(subDir, std::string(dirSeparator)) == false) - { - subDir += dirSeparator; - } - const FsEntry *const entry = searchByRootInternal(rootDir, subDir); - if (entry != nullptr) - { - reportAlways("VirtFs::mount already exists: %s", - newDir.c_str()); - return false; - } - if (subDir.empty()) - { - logger->log("Add virtual directory: " + newDir); - } - else - { - logger->log("Add virtual directory: %s with dir %s", - newDir.c_str(), - subDir.c_str()); - } - - addEntry(new DirEntry(newDir, - rootDir, - subDir, - rootDir + subDir, - FsDir::getFuncs()), - append); - return true; - } - - bool mountDir(std::string newDir, - const Append append) - { - prepareFsPath(newDir); - if (Files::existsLocal(newDir) == false) - { - reportNonTests("VirtFs::mount directory not exists: %s", - newDir.c_str()); - return false; - } - return mountDirInternal(newDir, dirSeparator, append); - } - - bool mountDir2(std::string newDir, - std::string subDir, - const Append append) - { - prepareFsPath(newDir); - prepareFsPath(subDir); - if (Files::existsLocal(newDir) == false) - { - reportNonTests("VirtFs::mount directory not exists: %s", - newDir.c_str()); - return false; - } - return mountDirInternal(newDir, subDir, append); - } - - bool mountDirSilent(std::string newDir, - const Append append) - { - prepareFsPath(newDir); - if (Files::existsLocal(newDir) == false) - { - logger->log("VirtFs::mount directory not exists: %s", - newDir.c_str()); - return false; - } - return mountDirInternal(newDir, std::string(), append); - } - - bool mountDirSilent2(std::string newDir, - std::string subDir, - const Append append) - { - prepareFsPath(newDir); - prepareFsPath(subDir); - if (Files::existsLocal(newDir) == false) - { - logger->log("VirtFs::mount directory not exists: %s", - newDir.c_str()); - return false; - } - return mountDirInternal(newDir, subDir, append); - } - -#ifdef UNITTESTS - bool mountDirSilentTest(std::string newDir, - const Append append) - { - prepareFsPath(newDir); - if (Files::existsLocal(newDir) == false) - { - logger->log("VirtFs::mount directory not exists: %s", - newDir.c_str()); - } - return mountDirInternal(newDir, std::string(), append); - } - - bool mountDirSilentTest2(std::string newDir, - std::string subDir, - const Append append) - { - prepareFsPath(newDir); - prepareFsPath(subDir); - if (Files::existsLocal(newDir) == false) - { - logger->log("VirtFs::mount directory not exists: %s", - newDir.c_str()); - } - return mountDirInternal(newDir, subDir, append); - } -#endif // UNITTESTS - - bool unmountDirInternal(std::string oldDir, - std::string subDir) - { - if (findLast(oldDir, std::string(dirSeparator)) == false) - oldDir += dirSeparator; - if (subDir == dirSeparator) - { - subDir.clear(); - } - else if (!subDir.empty() && - findLast(subDir, std::string(dirSeparator)) == false) - { - subDir += dirSeparator; - } - FOR_EACH (STD_VECTOR<FsEntry*>::iterator, it, mEntries) - { - FsEntry *const entry = *it; - if (entry->root == oldDir && - entry->type == FsEntryType::Dir && - entry->subDir == subDir) - { - DirEntry *const dirEntry = static_cast<DirEntry*>( - entry); - if (subDir.empty()) - { - logger->log("Remove virtual directory: " + oldDir); - } - else - { - logger->log("Remove virtual directory: %s with dir %s", - oldDir.c_str(), - subDir.c_str()); - } - mEntries.erase(it); - delete dirEntry; - return true; - } - } - return false; - } - - bool unmountDir(std::string oldDir) - { - prepareFsPath(oldDir); - if (oldDir.find(".zip") != std::string::npos) - { - reportAlways("Called unmount with zip archive"); - return false; - } - if (unmountDirInternal(oldDir, std::string()) == false) - { - reportAlways("VirtFs::unmountDir not exists: %s", - oldDir.c_str()); - return false; - } - return true; - } - - bool unmountDir2(std::string oldDir, - std::string subDir) - { - prepareFsPath(oldDir); - if (oldDir.find(".zip") != std::string::npos) - { - reportAlways("Called unmount with zip archive"); - return false; - } - prepareFsPath(subDir); - if (unmountDirInternal(oldDir, subDir) == false) - { - reportAlways("VirtFs::unmountDir not exists: %s", - oldDir.c_str()); - return false; - } - return true; - } - - bool unmountDirSilent(std::string oldDir) - { - prepareFsPath(oldDir); - if (oldDir.find(".zip") != std::string::npos) - { - reportAlways("Called unmount with zip archive"); - return false; - } - if (unmountDirInternal(oldDir, std::string()) == false) - { - logger->log("VirtFs::unmountDir not exists: %s", - oldDir.c_str()); - return false; - } - return true; - } - - bool unmountDirSilent2(std::string oldDir, - std::string subDir) - { - prepareFsPath(oldDir); - if (oldDir.find(".zip") != std::string::npos) - { - reportAlways("Called unmount with zip archive"); - return false; - } - prepareFsPath(subDir); - if (unmountDirInternal(oldDir, subDir) == false) - { - logger->log("VirtFs::unmountDir not exists: %s", - oldDir.c_str()); - return false; - } - return true; - } - - bool mountZip(std::string newDir, - const Append append) - { - prepareFsPath(newDir); - if (Files::existsLocal(newDir) == false) - { - reportNonTests("FsZip::mount file not exists: %s", - newDir.c_str()); - return false; - } - if (findLast(newDir, ".zip") == false) - { - reportAlways("Called VirtFs::mount without " - "zip archive"); - return false; - } - if (searchByRootInternal(newDir, std::string()) != nullptr) - { - reportAlways("FsZip::mount already exists: %s", - newDir.c_str()); - return false; - } - ZipEntry *const entry = new ZipEntry(newDir, - std::string(), - FsZip::getFuncs()); - if (ZipReader::readArchiveInfo(entry) == false) - { - delete entry; - return false; - } - - logger->log("Add virtual zip: " + newDir); - addEntry(entry, append); - return true; - } - - bool mountZip2(std::string newDir, - std::string subDir, - const Append append) - { - prepareFsPath(newDir); - if (Files::existsLocal(newDir) == false) - { - reportNonTests("FsZip::mount file not exists: %s", - newDir.c_str()); - return false; - } - if (findLast(newDir, ".zip") == false) - { - reportAlways("Called VirtFs::mount without " - "zip archive"); - return false; - } - prepareFsPath(subDir); - if (subDir == dirSeparator) - { - subDir.clear(); - } - else if (!subDir.empty() && - findLast(subDir, std::string(dirSeparator)) == false) - { - subDir += dirSeparator; - } - if (searchByRootInternal(newDir, subDir) != nullptr) - { - reportAlways("FsZip::mount already exists: %s", - newDir.c_str()); - return false; - } - ZipEntry *const entry = new ZipEntry(newDir, - subDir, - FsZip::getFuncs()); - if (ZipReader::readArchiveInfo(entry) == false) - { - delete entry; - return false; - } - - logger->log("Add virtual zip: %s with dir %s", - newDir.c_str(), - subDir.c_str()); - addEntry(entry, append); - return true; - } - - bool unmountZip(std::string oldDir) - { - prepareFsPath(oldDir); - if (findLast(oldDir, ".zip") == false) - { - reportAlways("Called unmount without zip archive"); - return false; - } - FOR_EACH (STD_VECTOR<FsEntry*>::iterator, it, mEntries) - { - FsEntry *const entry = *it; - if (entry->root == oldDir && - entry->type == FsEntryType::Zip && - entry->subDir.empty()) - { - ZipEntry *const zipEntry = static_cast<ZipEntry*>( - entry); - logger->log("Remove virtual zip: " + oldDir); - mEntries.erase(it); - delete zipEntry; - return true; - } - } - - reportAlways("VirtFs::unmountZip not exists: %s", - oldDir.c_str()); - return false; - } - - bool unmountZip2(std::string oldDir, - std::string subDir) - { - prepareFsPath(oldDir); - if (findLast(oldDir, ".zip") == false) - { - reportAlways("Called unmount without zip archive"); - return false; - } - prepareFsPath(subDir); - if (subDir == dirSeparator) - { - subDir.clear(); - } - else if (!subDir.empty() && - findLast(subDir, std::string(dirSeparator)) == false) - { - subDir += dirSeparator; - } - FOR_EACH (STD_VECTOR<FsEntry*>::iterator, it, mEntries) - { - FsEntry *const entry = *it; - if (entry->root == oldDir && - entry->type == FsEntryType::Zip && - entry->subDir == subDir) - { - ZipEntry *const zipEntry = static_cast<ZipEntry*>( - entry); - logger->log("Remove virtual zip: %s with dir %s", - oldDir.c_str(), - subDir.c_str()); - mEntries.erase(it); - delete zipEntry; - return true; - } - } - - reportAlways("VirtFs::unmountZip not exists: %s", - oldDir.c_str()); - return false; - } - - std::string getRealDir(std::string fileName) - { - prepareFsPath(fileName); - if (checkPath(fileName) == false) - { - reportAlways("FsDir::getRealDir invalid path: %s", - fileName.c_str()); - return std::string(); - } - - std::string rootDir = fileName; - if (findLast(rootDir, std::string(dirSeparator)) == false) - rootDir += dirSeparator; - - FOR_EACH (STD_VECTOR<FsEntry*>::const_iterator, it, mEntries) - { - FsEntry *const entry = *it; - std::string realDir; - if (entry->funcs->getRealDir(entry, - fileName, - rootDir, - realDir) == true) - { - return realDir; - } - } - return std::string(); - } - - bool mkdir(const std::string &restrict dirname) - { - return FsDir::mkdir(dirname); - } - - bool remove(const std::string &restrict filename) - { - return FsDir::remove(filename); - } - - bool deinit() - { - FsDir::deinit(); - FsZip::deinit(); - FOR_EACH (STD_VECTOR<FsEntry*>::iterator, it, mEntries) - { - FsEntry *const entry = *it; - if (entry->type == FsEntryType::Dir) - delete static_cast<DirEntry*>(entry); - else if (entry->type == FsEntryType::Zip) - delete static_cast<ZipEntry*>(entry); - else - delete entry; - } - mEntries.clear(); - return true; - } - - void permitLinks(const bool val) - { - FsDir::permitLinks(val); - } - - int close(File *restrict const file) - { - if (file == nullptr) - return 0; - return file->funcs->close(file); - } - - int64_t read(File *restrict const file, - void *restrict const buffer, - const uint32_t objSize, - const uint32_t objCount) - { - return file->funcs->read(file, - buffer, - objSize, - objCount); - } - - int64_t write(File *restrict const file, - const void *restrict const buffer, - const uint32_t objSize, - const uint32_t objCount) - { - return file->funcs->write(file, - buffer, - objSize, - objCount); - } - - int64_t fileLength(File *restrict const file) - { - return file->funcs->fileLength(file); - } - - int64_t tell(File *restrict const file) - { - return file->funcs->tell(file); - } - - int seek(File *restrict const file, - const uint64_t pos) - { - return file->funcs->seek(file, - pos); - } - - int eof(File *restrict const file) - { - return file->funcs->eof(file); - } - - const char *loadFile(std::string filename, - int &restrict fileSize) - { - prepareFsPath(filename); - if (checkPath(filename) == false) - { - reportAlways("VirtFs::loadFile invalid path: %s", - filename.c_str()); - return nullptr; - } - FOR_EACH (STD_VECTOR<FsEntry*>::const_iterator, it, mEntries) - { - FsEntry *const entry = *it; - const char *const buf = entry->funcs->loadFile(entry, - filename, - fileSize); - if (buf != nullptr) - return buf; - } - return nullptr; - } - -} // namespace VirtFs diff --git a/src/fs/virtfs/fs.h b/src/fs/virtfs/fs.h deleted file mode 100644 index 326a88d90..000000000 --- a/src/fs/virtfs/fs.h +++ /dev/null @@ -1,127 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef FS_VIRTFS_H -#define FS_VIRTFS_H - -#include "enums/fs/fsentrytype.h" - -#include "enums/simpletypes/append.h" - -#include "utils/stringvector.h" - -#include "localconsts.h" - -namespace VirtFs -{ - struct File; - struct FsEntry; - struct List; - - void init(const std::string &restrict name); - void updateDirSeparator(); - const char *getDirSeparator(); - const char *getBaseDir(); - const char *getUserDir(); - bool exists(std::string name); - List *enumerateFiles(std::string dir) RETURNS_NONNULL; - bool isDirectory(std::string name); - bool isSymbolicLink(const std::string &restrict name); - void freeList(List *restrict const handle); - File *openRead(std::string filename); - File *openWrite(std::string filename); - File *openAppend(std::string filename); - bool setWriteDir(const std::string &restrict newDir); - bool mountDir(std::string newDir, - const Append append); - bool mountDir2(std::string newDir, - std::string subDir, - const Append append); - bool mountDirSilent(std::string newDir, - const Append append); - bool mountDirSilent2(std::string newDir, - std::string subDir, - const Append append); - bool unmountDir(std::string oldDir); - bool unmountDir2(std::string oldDir, - std::string subDir); - bool unmountDirSilent(std::string oldDir); - bool unmountDirSilent2(std::string oldDir, - std::string subDir); - bool mountZip(std::string newDir, - const Append append); - bool mountZip2(std::string newDir, - std::string subDir, - const Append append); - bool unmountZip(std::string oldDir); - bool unmountZip2(std::string oldDir, - std::string subDir); - std::string getRealDir(std::string filename); - bool mkdir(const std::string &restrict dirName); - bool remove(const std::string &restrict filename); - bool deinit(); - void permitLinks(const bool val); - int64_t read(File *restrict const handle, - void *restrict const buffer, - const uint32_t objSize, - const uint32_t objCount); - int64_t write(File *restrict const file, - const void *restrict const buffer, - const uint32_t objSize, - const uint32_t objCount); - int close(File *restrict const file); - int64_t fileLength(File *restrict const file); - int64_t tell(File *restrict const file); - int seek(File *restrict const file, - const uint64_t pos); - int eof(File *restrict const file); - - bool mountDirInternal(const std::string &restrict newDir, - std::string subDir, - const Append append); - bool unmountDirInternal(std::string oldDir, - std::string subDir); - STD_VECTOR<FsEntry*> &getEntries(); - FsEntry *searchByRootInternal(const std::string &restrict root, - const std::string &restrict subDir); - FsEntry *searchByTypeInternal(const std::string &restrict root, - const FsEntryTypeT type); - void addEntry(FsEntry *const entry, - const Append append); -#ifdef UNITTESTS - bool mountDirSilentTest(std::string newDir, - const Append append); - bool mountDirSilentTest2(std::string newDir, - std::string subDir, - const Append append); -#endif // UNITTESTS - const char *loadFile(std::string filename, - int &restrict fileSize); - void getFiles(std::string dirName, - StringVect &list); - void getFilesWithDir(std::string dirName, - StringVect &list); - void getDirs(std::string dirName, - StringVect &list); -} // namespace VirtFs - -extern const char *dirSeparator; - -#endif // FS_VIRTFS_H diff --git a/src/fs/virtfs/fsdir.cpp b/src/fs/virtfs/fsdir.cpp deleted file mode 100644 index f32cbba4b..000000000 --- a/src/fs/virtfs/fsdir.cpp +++ /dev/null @@ -1,686 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "fs/virtfs/fsdir.h" - -#include "fs/files.h" -#include "fs/mkdir.h" -#include "fs/paths.h" - -#include "fs/virtfs/direntry.h" -#include "fs/virtfs/file.h" -#include "fs/virtfs/fsdirrwops.h" -#include "fs/virtfs/fsfuncs.h" -#include "fs/virtfs/list.h" - -#include "utils/cast.h" -#include "utils/checkutils.h" -#include "utils/foreach.h" -#include "utils/stdmove.h" -#include "utils/stringutils.h" - -#include <dirent.h> -#include <unistd.h> - -#include <sys/types.h> -#include <sys/stat.h> - -#include "debug.h" - -extern const char *dirSeparator; - -namespace VirtFs -{ - -namespace -{ - std::string mWriteDir; - std::string mBaseDir; - std::string mUserDir; - bool mPermitLinks = false; - FsFuncs funcs; -} // namespace - -namespace FsDir -{ - File *openInternal(FsEntry *restrict const entry, - const std::string &filename, - const FILEMTYPE mode) - { - const std::string path = static_cast<DirEntry*>(entry)->rootSubDir + - filename; - if (Files::existsLocal(path) == false) - return nullptr; - FILEHTYPE fd = FILEOPEN(path.c_str(), - mode); - if (fd == FILEHDEFAULT) - { - reportAlways("VirtFs::open file open error: %s", - filename.c_str()); - return nullptr; - } - return new File(&funcs, fd); - } - - File *openRead(FsEntry *restrict const entry, - std::string filename) - { - return openInternal(entry, filename, FILEOPEN_FLAG_READ); - } - - File *openWrite(FsEntry *restrict const entry, - const std::string &filename) - { - return openInternal(entry, filename, FILEOPEN_FLAG_WRITE); - } - - File *openAppend(FsEntry *restrict const entry, - const std::string &filename) - { - return openInternal(entry, filename, FILEOPEN_FLAG_APPEND); - } - - void deinit() - { - } - -#if defined(__native_client__) - void init(const std::string &restrict name A_UNUSED) - { - mBaseDir = "/"; -#elif defined(ANDROID) - void init(const std::string &restrict name A_UNUSED) - { - mBaseDir = getRealPath("."); -#else // defined(__native_client__) - - void init(const std::string &restrict name) - { - mBaseDir = getRealPath(getFileDir(name)); -#endif // defined(__native_client__) - - prepareFsPath(mBaseDir); - mUserDir = getHomePath(); - prepareFsPath(mUserDir); - initFuncs(&funcs); - } - - void initFuncs(FsFuncs *restrict const ptr) - { - ptr->close = &FsDir::close; - ptr->read = &FsDir::read; - ptr->write = &FsDir::write; - ptr->fileLength = &FsDir::fileLength; - ptr->tell = &FsDir::tell; - ptr->seek = &FsDir::seek; - ptr->eof = &FsDir::eof; - ptr->exists = &FsDir::exists; - ptr->getRealDir = &FsDir::getRealDir; - ptr->enumerate = &FsDir::enumerate; - ptr->isDirectory = &FsDir::isDirectory; - ptr->openRead = &FsDir::openRead; - ptr->openWrite = &FsDir::openWrite; - ptr->openAppend = &FsDir::openAppend; - ptr->loadFile = &FsDir::loadFile; - ptr->getFiles = &FsDir::getFiles; - ptr->getFilesWithDir = &FsDir::getFilesWithDir; - ptr->getDirs = &FsDir::getDirs; - ptr->rwops_seek = &FsDir::rwops_seek; - ptr->rwops_read = &FsDir::rwops_read; - ptr->rwops_write = &FsDir::rwops_write; - ptr->rwops_close = &FsDir::rwops_close; -#ifdef USE_SDL2 - ptr->rwops_size = &FsDir::rwops_size; -#endif // USE_SDL2 - } - - FsFuncs *getFuncs() - { - return &funcs; - } - - const char *getBaseDir() - { - return mBaseDir.c_str(); - } - - const char *getUserDir() - { - return mUserDir.c_str(); - } - - bool getRealDir(FsEntry *restrict const entry, - std::string filename, - std::string dirName A_UNUSED, - std::string &realDir) - { - const DirEntry *const dirEntry = static_cast<const DirEntry*>(entry); - if (Files::existsLocal(dirEntry->rootSubDir + filename)) - { - realDir = dirEntry->userDir; - return true; - } - return false; - } - - bool exists(FsEntry *restrict const entry, - std::string fileName, - std::string dirName A_UNUSED) - { - return Files::existsLocal(static_cast<DirEntry*>(entry)->rootSubDir + - fileName); - } - - void enumerate(FsEntry *restrict const entry, - std::string dirName, - StringVect &names) - { - const std::string path = static_cast<DirEntry*>(entry)->rootSubDir + - dirName; - const struct dirent *next_file = nullptr; - DIR *const dir = opendir(path.c_str()); - if (dir != nullptr) - { - while ((next_file = readdir(dir)) != nullptr) - { - const std::string file = next_file->d_name; - if (file == "." || file == "..") - continue; -#ifndef WIN32 - if (mPermitLinks == false) - { - struct stat statbuf; - if (lstat(path.c_str(), &statbuf) == 0 && - S_ISLNK(statbuf.st_mode) != 0) - { - continue; - } - } -#endif // WIN32 - - bool found(false); - FOR_EACH (StringVectCIter, itn, names) - { - if (*itn == file) - { - found = true; - break; - } - } - if (found == false) - names.push_back(file); - } - closedir(dir); - } - } - - bool isDirectory(FsEntry *restrict const entry, - std::string dirName, - bool &isDirFlag) - { - std::string path = static_cast<DirEntry*>(entry)->rootSubDir + dirName; - - struct stat statbuf; - if (stat(path.c_str(), &statbuf) == 0) - { - isDirFlag = (S_ISDIR(statbuf.st_mode) != 0); - return true; - } - return false; - } - - bool isSymbolicLink(std::string name) - { - prepareFsPath(name); - if (checkPath(name) == false) - { - reportAlways("FsDir::isSymbolicLink invalid path: %s", - name.c_str()); - return false; - } -#ifndef WIN32 - if (mPermitLinks == false) - return false; - - struct stat statbuf; - return lstat(name.c_str(), &statbuf) == 0 && - S_ISLNK(statbuf.st_mode) != 0; -#else - return false; -#endif // WIN32 - } - - void freeList(List *restrict const handle) - { - delete handle; - } - - bool setWriteDir(std::string newDir) - { - prepareFsPath(newDir); - mWriteDir = STD_MOVE(newDir); - if (findLast(mWriteDir, std::string(dirSeparator)) == false) - mWriteDir += dirSeparator; - return true; - } - - bool mkdir(std::string dirname) - { - prepareFsPath(dirname); - if (mWriteDir.empty()) - { - reportAlways("FsDir::mkdir write dir is empty"); - return false; - } - return mkdir_r((mWriteDir + dirname).c_str()) != -1; - } - - bool remove(std::string filename) - { - prepareFsPath(filename); - if (mWriteDir.empty()) - { - reportAlways("FsDir::remove write dir is empty"); - return false; - } - return ::remove((mWriteDir + filename).c_str()) != 0; - } - - void permitLinks(const bool val) - { - mPermitLinks = val; - } - - int close(File *restrict const file) - { - if (file == nullptr) - return 0; - delete file; - return 1; - } - - int64_t read(File *restrict const file, - void *restrict const buffer, - const uint32_t objSize, - const uint32_t objCount) - { - if (file == nullptr) - return 0; - FILEHTYPE fd = file->mFd; - if (fd == FILEHDEFAULT) - { - reportAlways("FsDir::read file not opened."); - return 0; - } -#ifdef USE_FILE_FOPEN - return fread(buffer, objSize, objCount, fd); -#else // USE_FILE_FOPEN - int max = objSize * objCount; - int cnt = ::read(fd, buffer, max); - if (cnt <= 0) - return cnt; - return cnt / objSize; -#endif // USE_FILE_FOPEN - } - - int64_t write(File *restrict const file, - const void *restrict const buffer, - const uint32_t objSize, - const uint32_t objCount) - { - if (file == nullptr) - return 0; - FILEHTYPE fd = file->mFd; - if (fd == FILEHDEFAULT) - { - reportAlways("FsDir::write file not opened."); - return 0; - } -#ifdef USE_FILE_FOPEN - return fwrite(buffer, objSize, objCount, fd); -#else // USE_FILE_FOPEN - int max = objSize * objCount; - int cnt = ::write(fd, buffer, max); - if (cnt <= 0) - return cnt; - return cnt / objSize; -#endif // USE_FILE_FOPEN - } - - int64_t fileLength(File *restrict const file) - { - if (file == nullptr) - return -1; - FILEHTYPE fd = file->mFd; - if (fd == FILEHDEFAULT) - { - reportAlways("FsDir::fileLength file not opened."); - return 0; - } -#ifdef USE_FILE_FOPEN - const long pos = ftell(fd); - if (pos < 0) - { - reportAlways("FsDir::fileLength ftell error."); - return -1; - } - fseek(fd, 0, SEEK_END); - const long sz = ftell(fd); - fseek(fd, pos, SEEK_SET); - return sz; -#else // USE_FILE_FOPEN - struct stat statbuf; - if (fstat(fd, &statbuf) == -1) - { - reportAlways("FsDir::fileLength error."); - return -1; - } - return static_cast<int64_t>(statbuf.st_size); -#endif // USE_FILE_FOPEN - } - - int64_t tell(File *restrict const file) - { - if (file == nullptr) - return -1; - - FILEHTYPE fd = file->mFd; - if (fd == FILEHDEFAULT) - { - reportAlways("FsDir::tell file not opened."); - return 0; - } -#ifdef USE_FILE_FOPEN - return ftell(fd); -#else // USE_FILE_FOPEN - return lseek(fd, 0, SEEK_CUR); -#endif // USE_FILE_FOPEN - } - - int seek(File *restrict const file, - const uint64_t pos) - { - if (file == nullptr) - return 0; - - FILEHTYPE fd = file->mFd; - if (fd == FILEHDEFAULT) - { - reportAlways("FsDir::seek file not opened."); - return 0; - } - const int64_t res = FILESEEK(fd, pos, SEEK_SET); - if (res == -1) - return 0; - return 1; - } - - int eof(File *restrict const file) - { - if (file == nullptr) - return -1; - - FILEHTYPE fd = file->mFd; - if (fd == FILEHDEFAULT) - { - reportAlways("FsDir::eof file not opened."); - return 0; - } -#ifdef USE_FILE_FOPEN - const int flag = feof(fd); - if (flag != 0) - return 1; - const int64_t pos = ftell(fd); - const int64_t len = fileLength(file); -#else // USE_FILE_FOPEN - const int64_t pos = lseek(fd, 0, SEEK_CUR); - struct stat statbuf; - if (fstat(fd, &statbuf) == -1) - { - reportAlways("FsDir::fileLength error."); - return -1; - } - const int64_t len = static_cast<int64_t>(statbuf.st_size); -#endif // USE_FILE_FOPEN - return static_cast<int>(pos < 0 || len < 0 || pos >= len); - } - - const char *loadFile(FsEntry *restrict const entry, - std::string filename, - int &restrict fileSize) - { - const DirEntry *const dirEntry = static_cast<DirEntry*>(entry); - const std::string path = dirEntry->rootSubDir + filename; - if (Files::existsLocal(path) == false) - return nullptr; - FILEHTYPE fd = FILEOPEN(path.c_str(), - FILEOPEN_FLAG_READ); - if (fd == FILEHDEFAULT) - { - reportAlways("VirtFs::loadFile file open error: %s", - filename.c_str()); - return nullptr; - } - - logger->log("Loaded %s/%s", - dirEntry->userDir.c_str(), - filename.c_str()); - -#ifdef USE_FILE_FOPEN - fseek(fd, 0, SEEK_END); - const long sz = ftell(fd); - if (sz < 0) - { - reportAlways("FsDir::fileLength ftell error."); - if (fd != FILEHDEFAULT) - FILECLOSE(fd); - return nullptr; - } - fseek(fd, 0, SEEK_SET); - fileSize = static_cast<int>(sz); -#else // USE_FILE_FOPEN - struct stat statbuf; - if (fstat(fd, &statbuf) == -1) - { - reportAlways("FsDir::fileLength error."); - if (fd != FILEHDEFAULT) - FILECLOSE(fd); - return nullptr; - } - fileSize = static_cast<int>(statbuf.st_size); -#endif // USE_FILE_FOPEN - - // Allocate memory and load the file - char *restrict const buffer = new char[CAST_SIZE(fileSize)]; - if (fileSize > 0) - buffer[fileSize - 1] = 0; - -#ifdef USE_FILE_FOPEN - const int cnt = CAST_S32(fread(buffer, 1, fileSize, fd)); -#else // USE_FILE_FOPEN - const int cnt = ::read(fd, buffer, fileSize); -#endif // USE_FILE_FOPEN - - if (cnt <= 0) - { - delete [] buffer; - if (fd != FILEHDEFAULT) - FILECLOSE(fd); - return nullptr; - } - - if (fd != FILEHDEFAULT) - FILECLOSE(fd); - - return buffer; - } - - void getFiles(FsEntry *restrict const entry, - std::string dirName, - StringVect &names) - { - const std::string path = static_cast<DirEntry*>(entry)->rootSubDir + - dirName; - const struct dirent *next_file = nullptr; - DIR *const dir = opendir(path.c_str()); - if (dir != nullptr) - { - while ((next_file = readdir(dir)) != nullptr) - { - struct stat statbuf; - const std::string file = next_file->d_name; - if (file == "." || file == "..") - continue; -#ifndef WIN32 - if (mPermitLinks == false) - { - if (lstat(path.c_str(), &statbuf) == 0 && - S_ISLNK(statbuf.st_mode) != 0) - { - continue; - } - } -#endif // WIN32 - - const std::string filePath = pathJoin(path, file); - if (stat(filePath.c_str(), &statbuf) == 0) - { - if (S_ISDIR(statbuf.st_mode) != 0) - continue; - } - - bool found(false); - FOR_EACH (StringVectCIter, itn, names) - { - if (*itn == file) - { - found = true; - break; - } - } - if (found == false) - names.push_back(file); - } - closedir(dir); - } - } - - void getFilesWithDir(FsEntry *restrict const entry, - const std::string &dirName, - StringVect &names) - { - const std::string path = static_cast<DirEntry*>(entry)->rootSubDir + - dirName; - const struct dirent *next_file = nullptr; - DIR *const dir = opendir(path.c_str()); - if (dir != nullptr) - { - while ((next_file = readdir(dir)) != nullptr) - { - struct stat statbuf; - const std::string file = next_file->d_name; - if (file == "." || file == "..") - continue; -#ifndef WIN32 - if (mPermitLinks == false) - { - if (lstat(path.c_str(), &statbuf) == 0 && - S_ISLNK(statbuf.st_mode) != 0) - { - continue; - } - } -#endif // WIN32 - - const std::string filePath = pathJoin(path, file); - if (stat(filePath.c_str(), &statbuf) == 0) - { - if (S_ISDIR(statbuf.st_mode) != 0) - continue; - } - - bool found(false); - FOR_EACH (StringVectCIter, itn, names) - { - if (*itn == file) - { - found = true; - break; - } - } - if (found == false) - names.push_back(pathJoin(dirName, file)); - } - closedir(dir); - } - } - - void getDirs(FsEntry *restrict const entry, - std::string dirName, - StringVect &names) - { - const std::string path = static_cast<DirEntry*>(entry)->rootSubDir + - dirName; - const struct dirent *next_file = nullptr; - DIR *const dir = opendir(path.c_str()); - if (dir != nullptr) - { - while ((next_file = readdir(dir)) != nullptr) - { - struct stat statbuf; - const std::string file = next_file->d_name; - if (file == "." || file == "..") - continue; -#ifndef WIN32 - if (mPermitLinks == false) - { - if (lstat(path.c_str(), &statbuf) == 0 && - S_ISLNK(statbuf.st_mode) != 0) - { - continue; - } - } -#endif // WIN32 - - const std::string filePath = pathJoin(path, file); - if (stat(filePath.c_str(), &statbuf) == 0) - { - if (S_ISDIR(statbuf.st_mode) == 0) - continue; - } - - bool found(false); - FOR_EACH (StringVectCIter, itn, names) - { - if (*itn == file) - { - found = true; - break; - } - } - if (found == false) - names.push_back(file); - } - closedir(dir); - } - } -} // namespace FsDir - -} // namespace VirtFs diff --git a/src/fs/virtfs/fsdir.h b/src/fs/virtfs/fsdir.h deleted file mode 100644 index 0c19fee2f..000000000 --- a/src/fs/virtfs/fsdir.h +++ /dev/null @@ -1,104 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_VIRTFSDIR_H -#define UTILS_VIRTFSDIR_H - -#include "fs/virtfs/fileapi.h" - -#include "utils/stringvector.h" - -#include "localconsts.h" - -namespace VirtFs -{ - -struct File; -struct FsEntry; -struct FsFuncs; -struct List; - -namespace FsDir -{ - File *openInternal(FsEntry *restrict const entry, - const std::string &filename, - const FILEMTYPE mode); - File *openRead(FsEntry *restrict const entry, - std::string filename); - File *openWrite(FsEntry *restrict const entry, - const std::string &filename); - File *openAppend(FsEntry *restrict const entry, - const std::string &filename); - const char *getBaseDir(); - const char *getUserDir(); - FsFuncs *getFuncs(); - void init(const std::string &restrict name); - void initFuncs(FsFuncs *restrict const ptr); - void deinit(); - bool exists(FsEntry *restrict const entry, - std::string fileName, - std::string dirName); - void enumerate(FsEntry *restrict const entry, - std::string dirName, - StringVect &names); - void getFiles(FsEntry *restrict const entry, - std::string dirName, - StringVect &names); - void getFilesWithDir(FsEntry *restrict const entry, - const std::string &dirName, - StringVect &names); - void getDirs(FsEntry *restrict const entry, - std::string dirName, - StringVect &names); - bool isDirectory(FsEntry *restrict const entry, - std::string dirName, - bool &isDirFlag); - bool isSymbolicLink(std::string name); - void freeList(List *restrict const handle); - bool setWriteDir(std::string newDir); - bool getRealDir(FsEntry *restrict const entry, - std::string filename, - std::string dirName, - std::string &realDir); - bool mkdir(std::string dirName); - bool remove(std::string filename); - void permitLinks(const bool val); - int64_t read(File *restrict const handle, - void *restrict const buffer, - const uint32_t objSize, - const uint32_t objCount); - int64_t write(File *restrict const file, - const void *restrict const buffer, - const uint32_t objSize, - const uint32_t objCount); - int close(File *restrict const file); - int64_t fileLength(File *restrict const file); - int64_t tell(File *restrict const file); - int seek(File *restrict const file, - const uint64_t pos); - int eof(File *restrict const file); - const char *loadFile(FsEntry *restrict const entry, - std::string fileName, - int &restrict fileSize); -} // namespace FsDir - -} // namespace VirtFs - -#endif // UTILS_VIRTFSDIR_H diff --git a/src/fs/virtfs/fsdirrwops.cpp b/src/fs/virtfs/fsdirrwops.cpp deleted file mode 100644 index 47497a9d3..000000000 --- a/src/fs/virtfs/fsdirrwops.cpp +++ /dev/null @@ -1,269 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "fs/virtfs/fsdirrwops.h" - -#include "fs/virtfs/file.h" - -#include "utils/cast.h" -#include "utils/checkutils.h" - -PRAGMA48(GCC diagnostic push) -PRAGMA48(GCC diagnostic ignored "-Wshadow") -#include <SDL_rwops.h> -PRAGMA48(GCC diagnostic pop) - -#include "debug.h" - -namespace VirtFs -{ - -namespace FsDir -{ - RWOPSINT rwops_seek(SDL_RWops *const rw, - const RWOPSINT offset, - const int whence) - { - if (rw == nullptr) - return -1; - File *const handle = static_cast<File *>( - rw->hidden.unknown.data1); - FILEHTYPE fd = handle->mFd; - RWOPSINT pos = 0; - - if (whence == SEEK_SET) - { - pos = offset; - } - else if (whence == SEEK_CUR) - { -#ifdef USE_FILE_FOPEN - const int64_t current = ftell(fd); -#else // USE_FILE_FOPEN - const int64_t current = lseek(fd, 0, SEEK_CUR); -#endif // USE_FILE_FOPEN - - if (current == -1) - { - logger->assertLog( - "VirtFs::rwops_seek: Can't find position in file."); - return -1; - } - - pos = CAST_S32(current); - if (static_cast<int64_t>(pos) != current) - { - logger->assertLog("VirtFs::rwops_seek: " - "Can't fit current file position in an int!"); - return -1; - } - - if (offset == 0) /* this is a "tell" call. We're done. */ - return pos; - - pos += offset; - } - else if (whence == SEEK_END) - { - int64_t len = 0; -#ifdef USE_FILE_FOPEN - const long curpos = ftell(fd); - if (curpos < 0) - { - reportAlways("FsDir::fileLength ftell error."); - return -1; - } - fseek(fd, 0, SEEK_END); - len = ftell(fd); -// fseek(fd, curpos, SEEK_SET); -#else // USE_FILE_FOPEN - struct stat statbuf; - if (fstat(fd, &statbuf) == -1) - { - reportAlways("FsDir::fileLength error."); - len = -1; - } - else - { - len = static_cast<int64_t>(statbuf.st_size); - } -#endif // USE_FILE_FOPEN - - if (len == -1) - { -#ifdef USE_FILE_FOPEN - if (fseek(fd, curpos, SEEK_SET) < 0) - { - reportAlways("FsDir::fileLength fseek error."); - } -#endif // USE_FILE_FOPEN - logger->assertLog( - "VirtFs::rwops_seek:Can't find end of file."); - return -1; - } - - pos = static_cast<RWOPSINT>(len); - if (static_cast<int64_t>(pos) != len) - { -#ifdef USE_FILE_FOPEN - fseek(fd, curpos, SEEK_SET); -#endif // USE_FILE_FOPEN - logger->assertLog("VirtFs::rwops_seek: " - "Can't fit end-of-file position in an int!"); - return -1; - } - - pos += offset; - } - else - { - logger->assertLog( - "VirtFs::rwops_seek: Invalid 'whence' parameter."); - return -1; - } - - if (pos < 0) - { - logger->assertLog("VirtFs::rwops_seek: " - "Attempt to seek past start of file."); - return -1; - } - - const int64_t res = FILESEEK(fd, pos, SEEK_SET); - if (res == -1) - { - logger->assertLog("VirtFs::rwops_seek: seek error."); - return -1; - } - - return pos; - } - - RWOPSSIZE rwops_read(SDL_RWops *const rw, - void *const ptr, - const RWOPSSIZE size, - const RWOPSSIZE maxnum) - { - if (rw == nullptr) - return 0; - File *const handle = static_cast<File *>( - rw->hidden.unknown.data1); - FILEHTYPE fd = handle->mFd; - -#ifdef USE_FILE_FOPEN - const int64_t rc = fread(ptr, size, maxnum, fd); -#else // USE_FILE_FOPEN - int max = size * maxnum; - int cnt = ::read(fd, ptr, max); - if (cnt <= 0) - return cnt; - const int64_t rc = cnt / size; -#endif // USE_FILE_FOPEN - -#ifndef USE_FILE_FOPEN - if (rc != static_cast<int64_t>(maxnum)) - { - const int64_t pos = lseek(fd, 0, SEEK_CUR); - struct stat statbuf; - if (fstat(fd, &statbuf) == -1) - { - reportAlways("FsDir::fileLength error."); - return CAST_S32(rc); - } - } -#endif // USE_FILE_FOPEN - return CAST_S32(rc); - } - - RWOPSSIZE rwops_write(SDL_RWops *const rw, - const void *const ptr, - const RWOPSSIZE size, - const RWOPSSIZE maxnum) - { - if (rw == nullptr) - return 0; - File *const handle = static_cast<File *>( - rw->hidden.unknown.data1); - FILEHTYPE fd = handle->mFd; - -#ifdef USE_FILE_FOPEN - const int64_t rc = fwrite(ptr, size, maxnum, fd); -#else // USE_FILE_FOPEN - int max = size * maxnum; - int cnt = ::write(fd, ptr, max); - if (cnt <= 0) - return cnt; - const int64_t rc = cnt / size; -#endif // USE_FILE_FOPEN - -#ifndef USE_FILE_FOPEN - if (rc != static_cast<int64_t>(maxnum)) - { - const int64_t pos = lseek(fd, 0, SEEK_CUR); - struct stat statbuf; - if (fstat(fd, &statbuf) == -1) - { - reportAlways("FsDir::fileLength error."); - return CAST_S32(rc); - } - } -#endif // USE_FILE_FOPEN - - return CAST_S32(rc); - } - - int rwops_close(SDL_RWops *const rw) - { - if (rw == nullptr) - return 0; - File *const handle = static_cast<File*>( - rw->hidden.unknown.data1); - delete handle; - SDL_FreeRW(rw); - return 0; - } - -#ifdef USE_SDL2 - RWOPSINT rwops_size(SDL_RWops *const rw) - { - File *const handle = static_cast<File *>( - rw->hidden.unknown.data1); - FILEHTYPE fd = handle->mFd; -#ifdef USE_FILE_FOPEN - const long pos = ftell(fd); - fseek(fd, 0, SEEK_END); - const long sz = ftell(fd); - fseek(fd, pos, SEEK_SET); - return sz; -#else // USE_FILE_FOPEN - struct stat statbuf; - if (fstat(fd, &statbuf) == -1) - { - reportAlways("FsDir::fileLength error."); - return -1; - } - return static_cast<int64_t>(statbuf.st_size); -#endif // USE_FILE_FOPEN - } -#endif // USE_SDL2 - -} // namespace FsDir - -} // namespace VirtFs diff --git a/src/fs/virtfs/fsdirrwops.h b/src/fs/virtfs/fsdirrwops.h deleted file mode 100644 index 1f20d97df..000000000 --- a/src/fs/virtfs/fsdirrwops.h +++ /dev/null @@ -1,55 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_VIRTFS_VIRTFSDIRRWOPS_H -#define UTILS_VIRTFS_VIRTFSDIRRWOPS_H - -#include "fs/virtfs/rwopstypes.h" - -struct SDL_RWops; - -#include "localconsts.h" - -namespace VirtFs -{ - -namespace FsDir -{ - RWOPSINT rwops_seek(SDL_RWops *const rw, - const RWOPSINT offset, - const int whence); - RWOPSSIZE rwops_read(SDL_RWops *const rw, - void *const ptr, - const RWOPSSIZE size, - const RWOPSSIZE maxnum); - RWOPSSIZE rwops_write(SDL_RWops *const rw, - const void *const ptr, - const RWOPSSIZE size, - const RWOPSSIZE maxnum); - int rwops_close(SDL_RWops *const rw); -#ifdef USE_SDL2 - RWOPSINT rwops_size(SDL_RWops *const rw); -#endif // USE_SDL2 - -} // namespace FsDir - -} // namespace VirtFs - -#endif // UTILS_VIRTFS_VIRTFSDIRRWOPS_H diff --git a/src/fs/virtfs/fsentry.cpp b/src/fs/virtfs/fsentry.cpp deleted file mode 100644 index 7078fdbc4..000000000 --- a/src/fs/virtfs/fsentry.cpp +++ /dev/null @@ -1,41 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "fs/virtfs/fsentry.h" - -#include "debug.h" - -namespace VirtFs -{ - -FsEntry::FsEntry(const FsEntryTypeT &type0, - FsFuncs *restrict const funcs0) : - root(), - subDir(), - type(type0), - funcs(funcs0) -{ -} - -FsEntry::~FsEntry() -{ -} - -} // namespace VirtFs diff --git a/src/fs/virtfs/fsentry.h b/src/fs/virtfs/fsentry.h deleted file mode 100644 index 09ca136b0..000000000 --- a/src/fs/virtfs/fsentry.h +++ /dev/null @@ -1,55 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_VIRTFSENTRY_H -#define UTILS_VIRTFSENTRY_H - -#include "enums/fs/fsentrytype.h" - -#include <string> - -#include "localconsts.h" - -namespace VirtFs -{ - -struct FsFuncs; - -struct FsEntry notfinal -{ - FsEntry(const FsEntryTypeT &type0, - FsFuncs *restrict const funcs); - - A_DELETE_COPY(FsEntry) - - virtual ~FsEntry(); - - std::string root; - - std::string subDir; - - FsEntryTypeT type; - - FsFuncs *funcs; -}; - -} // namespace VirtFs - -#endif // UTILS_VIRTFSENTRY_H diff --git a/src/fs/virtfs/fsfuncs.h b/src/fs/virtfs/fsfuncs.h deleted file mode 100644 index 49d10e12f..000000000 --- a/src/fs/virtfs/fsfuncs.h +++ /dev/null @@ -1,136 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_VIRTFSFUNCS_H -#define UTILS_VIRTFSFUNCS_H - -#include "fs/virtfs/rwopstypes.h" - -#include "utils/stringvector.h" - -#include "localconsts.h" - -struct SDL_RWops; - -namespace VirtFs -{ - -struct File; -struct FsEntry; - -struct FsFuncs final -{ - FsFuncs() : - close(nullptr), - read(nullptr), - write(nullptr), - fileLength(nullptr), - tell(nullptr), - seek(nullptr), - exists(nullptr), - getRealDir(nullptr), - enumerate(nullptr), - getFiles(nullptr), - getFilesWithDir(nullptr), - getDirs(nullptr), - isDirectory(nullptr), - openRead(nullptr), - openWrite(nullptr), - openAppend(nullptr), - eof(nullptr), - loadFile(nullptr), - rwops_seek(nullptr), - rwops_read(nullptr), - rwops_write(nullptr), -#ifdef USE_SDL2 - rwops_size(nullptr), -#endif // USE_SDL2 - rwops_close(nullptr) - { - } - - A_DELETE_COPY(FsFuncs) - - int (*close) (File *restrict const file); - int64_t (*read) (File *restrict const file, - void *restrict const buffer, - const uint32_t objSize, - const uint32_t objCount); - int64_t (*write) (File *restrict const file, - const void *restrict const buffer, - const uint32_t objSize, - const uint32_t objCount); - int64_t (*fileLength) (File *restrict const file); - int64_t (*tell) (File *restrict const file); - int (*seek) (File *restrict const file, - const uint64_t pos); - bool (*exists) (FsEntry *restrict const entry, - std::string filename, - std::string dirName); - bool (*getRealDir) (FsEntry *restrict const entry, - std::string filename, - std::string dirName, - std::string &realDir); - void (*enumerate) (FsEntry *restrict const entry, - std::string dirName, - StringVect &names); - void (*getFiles) (FsEntry *restrict const entry, - std::string dirName, - StringVect &names); - void (*getFilesWithDir) (FsEntry *restrict const entry, - const std::string &dirName, - StringVect &names); - void (*getDirs) (FsEntry *restrict const entry, - std::string dirName, - StringVect &names); - bool (*isDirectory) (FsEntry *restrict const entry, - std::string dirName, - bool &isDirFlag); - File *(*openRead) (FsEntry *restrict const entry, - std::string filename); - File *(*openWrite) (FsEntry *restrict const entry, - const std::string &filename); - File *(*openAppend) (FsEntry *restrict const entry, - const std::string &filename); - int (*eof) (File *restrict const file); - const char *(*loadFile) (FsEntry *restrict const entry, - std::string fileName, - int &restrict fileSize); - - RWOPSINT (*rwops_seek) (SDL_RWops *const rw, - const RWOPSINT offset, - const int whence); - RWOPSSIZE (*rwops_read) (SDL_RWops *const rw, - void *const ptr, - const RWOPSSIZE size, - const RWOPSSIZE maxnum); - RWOPSSIZE (*rwops_write) (SDL_RWops *const rw, - const void *const ptr, - const RWOPSSIZE size, - const RWOPSSIZE num); -#ifdef USE_SDL2 - RWOPSINT (*rwops_size) (SDL_RWops *const rw); -#endif // USE_SDL2 - int (*rwops_close) (SDL_RWops *const rw); -}; - -} // namespace VirtFs - -#endif // UTILS_VIRTFSFUNCS_H diff --git a/src/fs/virtfs/fszip.cpp b/src/fs/virtfs/fszip.cpp deleted file mode 100644 index fcb726173..000000000 --- a/src/fs/virtfs/fszip.cpp +++ /dev/null @@ -1,705 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "fs/virtfs/fszip.h" - -#include "fs/virtfs/file.h" -#include "fs/virtfs/fsfuncs.h" -#include "fs/virtfs/fsziprwops.h" -#include "fs/virtfs/list.h" -#include "fs/virtfs/zipentry.h" -#include "fs/virtfs/zipreader.h" -#include "fs/virtfs/ziplocalheader.h" - -#include "utils/cast.h" -#include "utils/checkutils.h" -#include "utils/foreach.h" -#include "utils/stringutils.h" - -#include "debug.h" - -extern const char *dirSeparator; - -namespace -{ - VirtFs::FsFuncs funcs; -} // namespace - -namespace VirtFs -{ - -namespace FsZip -{ - FsFuncs *getFuncs() - { - return &funcs; - } - - void deinit() - { - } - - void init() - { - initFuncs(&funcs); - } - - void initFuncs(FsFuncs *restrict const ptr) - { - ptr->close = &FsZip::close; - ptr->read = &FsZip::read; - ptr->write = &FsZip::write; - ptr->fileLength = &FsZip::fileLength; - ptr->tell = &FsZip::tell; - ptr->seek = &FsZip::seek; - ptr->eof = &FsZip::eof; - ptr->exists = &FsZip::exists; - ptr->getRealDir = &FsZip::getRealDir; - ptr->enumerate = &FsZip::enumerate; - ptr->isDirectory = &FsZip::isDirectory; - ptr->openRead = &FsZip::openRead; - ptr->openWrite = &FsZip::openWrite; - ptr->openAppend = &FsZip::openAppend; - ptr->loadFile = &FsZip::loadFile; - ptr->getFiles = &FsZip::getFiles; - ptr->getFilesWithDir = &FsZip::getFilesWithDir; - ptr->getDirs = &FsZip::getDirs; - ptr->rwops_seek = &FsZip::rwops_seek; - ptr->rwops_read = &FsZip::rwops_read; - ptr->rwops_write = &FsZip::rwops_write; - ptr->rwops_close = &FsZip::rwops_close; -#ifdef USE_SDL2 - ptr->rwops_size = &FsZip::rwops_size; -#endif // USE_SDL2 - } - - bool getRealDir(FsEntry *restrict const entry, - std::string filename, - std::string dirName, - std::string &realDir) - { - ZipEntry *const zipEntry = static_cast<ZipEntry*>(entry); - std::string subDir = zipEntry->subDir; - if (!subDir.empty()) - { - filename = pathJoin(subDir, filename); - dirName = pathJoin(subDir, dirName); - } - FOR_EACH (STD_VECTOR<ZipLocalHeader*>::const_iterator, - it2, - zipEntry->mHeaders) - { - if ((*it2)->fileName == filename) - { - realDir = entry->root; - return true; - } - } - FOR_EACH (STD_VECTOR<std::string>::const_iterator, - it2, - zipEntry->mDirs) - { - if (*it2 == dirName) - { - realDir = entry->root; - return true; - } - } - return false; - } - - bool exists(FsEntry *restrict const entry, - std::string filename, - std::string dirName) - { - ZipEntry *const zipEntry = static_cast<ZipEntry*>(entry); - std::string subDir = zipEntry->subDir; - if (!subDir.empty()) - { - filename = pathJoin(subDir, filename); - dirName = pathJoin(subDir, dirName); - } - FOR_EACH (STD_VECTOR<ZipLocalHeader*>::const_iterator, - it2, - zipEntry->mHeaders) - { - if ((*it2)->fileName == filename) - return true; - } - FOR_EACH (STD_VECTOR<std::string>::const_iterator, - it2, - zipEntry->mDirs) - { - if (*it2 == dirName) - return true; - } - return false; - } - - void enumerate(FsEntry *restrict const entry, - std::string dirName, - StringVect &names) - { - ZipEntry *const zipEntry = static_cast<ZipEntry*>(entry); - const std::string subDir = zipEntry->subDir; - if (!subDir.empty()) - dirName = pathJoin(subDir, dirName); - if (dirName == dirSeparator) - { - FOR_EACH (STD_VECTOR<ZipLocalHeader*>::const_iterator, - it2, - zipEntry->mHeaders) - { - ZipLocalHeader *const header = *it2; - std::string fileName = header->fileName; - // skip subdirs from enumeration - const size_t idx = fileName.find(dirSeparator); - if (idx != std::string::npos) - fileName.erase(idx); - bool found(false); - FOR_EACH (StringVectCIter, itn, names) - { - if (*itn == fileName) - { - found = true; - break; - } - } - if (found == false) - names.push_back(fileName); - } - } - else - { - FOR_EACH (STD_VECTOR<ZipLocalHeader*>::const_iterator, - it2, - zipEntry->mHeaders) - { - ZipLocalHeader *const header = *it2; - std::string fileName = header->fileName; - if (findCutFirst(fileName, dirName) == true) - { - // skip subdirs from enumeration - const size_t idx = fileName.find(dirSeparator); - if (idx != std::string::npos) - fileName.erase(idx); - bool found(false); - FOR_EACH (StringVectCIter, itn, names) - { - if (*itn == fileName) - { - found = true; - break; - } - } - if (found == false) - names.push_back(fileName); - } - } - } - } - - void getFiles(FsEntry *restrict const entry, - std::string dirName, - StringVect &names) - { - ZipEntry *const zipEntry = static_cast<ZipEntry*>(entry); - const std::string subDir = zipEntry->subDir; - if (!subDir.empty()) - dirName = pathJoin(subDir, dirName); - if (dirName == dirSeparator) - { - FOR_EACH (STD_VECTOR<ZipLocalHeader*>::const_iterator, - it2, - zipEntry->mHeaders) - { - ZipLocalHeader *const header = *it2; - std::string fileName = header->fileName; - // skip subdirs from enumeration - const size_t idx = fileName.find(dirSeparator); - if (idx != std::string::npos) - fileName.erase(idx); - bool found(false); - FOR_EACH (StringVectCIter, itn, names) - { - if (*itn == fileName) - { - found = true; - break; - } - } - if (found == false) - { - std::string dirName2 = pathJoin(dirName, fileName); - if (findLast(dirName2, std::string(dirSeparator)) == false) - dirName2 += dirSeparator; - FOR_EACH (STD_VECTOR<std::string>::const_iterator, - it, - zipEntry->mDirs) - { - if (*it == dirName2) - { - found = true; - break; - } - } - if (found == false) - names.push_back(fileName); - } - } - } - else - { - FOR_EACH (STD_VECTOR<ZipLocalHeader*>::const_iterator, - it2, - zipEntry->mHeaders) - { - ZipLocalHeader *const header = *it2; - std::string fileName = header->fileName; - if (findCutFirst(fileName, dirName) == true) - { - // skip subdirs from enumeration - const size_t idx = fileName.find(dirSeparator); - if (idx != std::string::npos) - fileName.erase(idx); - bool found(false); - FOR_EACH (StringVectCIter, itn, names) - { - if (*itn == fileName) - { - found = true; - break; - } - } - if (found == false) - { - std::string dirName2 = pathJoin(dirName, fileName); - if (findLast(dirName2, std::string(dirSeparator)) == - false) - { - dirName2 += dirSeparator; - } - FOR_EACH (STD_VECTOR<std::string>::const_iterator, - it, - zipEntry->mDirs) - { - if (*it == dirName2) - { - found = true; - break; - } - } - if (found == false) - names.push_back(fileName); - } - } - } - } - } - - void getFilesWithDir(FsEntry *restrict const entry, - const std::string &dirName, - StringVect &names) - { - ZipEntry *const zipEntry = static_cast<ZipEntry*>(entry); - const std::string subDir = zipEntry->subDir; - std::string dirNameFull; - if (!subDir.empty()) - dirNameFull = pathJoin(subDir, dirName); - else - dirNameFull = dirName; - if (dirNameFull == dirSeparator) - { - FOR_EACH (STD_VECTOR<ZipLocalHeader*>::const_iterator, - it2, - zipEntry->mHeaders) - { - ZipLocalHeader *const header = *it2; - std::string fileName = header->fileName; - // skip subdirs from enumeration - const size_t idx = fileName.find(dirSeparator); - if (idx != std::string::npos) - fileName.erase(idx); - bool found(false); - FOR_EACH (StringVectCIter, itn, names) - { - if (*itn == fileName) - { - found = true; - break; - } - } - if (found == false) - { - std::string dirName2 = pathJoin(dirNameFull, fileName); - if (findLast(dirName2, std::string(dirSeparator)) == false) - dirName2 += dirSeparator; - FOR_EACH (STD_VECTOR<std::string>::const_iterator, - it, - zipEntry->mDirs) - { - if (*it == dirName2) - { - found = true; - break; - } - } - if (found == false) - names.push_back(pathJoin(dirName, fileName)); - } - } - } - else - { - FOR_EACH (STD_VECTOR<ZipLocalHeader*>::const_iterator, - it2, - zipEntry->mHeaders) - { - ZipLocalHeader *const header = *it2; - std::string fileName = header->fileName; - if (findCutFirst(fileName, dirNameFull) == true) - { - // skip subdirs from enumeration - const size_t idx = fileName.find(dirSeparator); - if (idx != std::string::npos) - fileName.erase(idx); - bool found(false); - FOR_EACH (StringVectCIter, itn, names) - { - if (*itn == fileName) - { - found = true; - break; - } - } - if (found == false) - { - std::string dirName2 = pathJoin(dirNameFull, fileName); - if (findLast(dirName2, std::string(dirSeparator)) == - false) - { - dirName2 += dirSeparator; - } - FOR_EACH (STD_VECTOR<std::string>::const_iterator, - it, - zipEntry->mDirs) - { - if (*it == dirName2) - { - found = true; - break; - } - } - if (found == false) - names.push_back(pathJoin(dirName, fileName)); - } - } - } - } - } - - void getDirs(FsEntry *restrict const entry, - std::string dirName, - StringVect &names) - { - ZipEntry *const zipEntry = static_cast<ZipEntry*>(entry); - const std::string subDir = zipEntry->subDir; - if (!subDir.empty()) - dirName = pathJoin(subDir, dirName); - if (dirName == dirSeparator) - { - FOR_EACH (STD_VECTOR<ZipLocalHeader*>::const_iterator, - it2, - zipEntry->mHeaders) - { - ZipLocalHeader *const header = *it2; - std::string fileName = header->fileName; - // skip subdirs from enumeration - const size_t idx = fileName.find(dirSeparator); - if (idx != std::string::npos) - fileName.erase(idx); - bool found(false); - FOR_EACH (StringVectCIter, itn, names) - { - if (*itn == fileName) - { - found = true; - break; - } - } - if (found == false) - { - std::string dirName2 = pathJoin(dirName, fileName); - if (findLast(dirName2, std::string(dirSeparator)) == false) - dirName2 += dirSeparator; - FOR_EACH (STD_VECTOR<std::string>::const_iterator, - it, - zipEntry->mDirs) - { - if (*it == dirName2) - { - found = true; - break; - } - } - if (found == true) - names.push_back(fileName); - } - } - } - else - { - FOR_EACH (STD_VECTOR<ZipLocalHeader*>::const_iterator, - it2, - zipEntry->mHeaders) - { - ZipLocalHeader *const header = *it2; - std::string fileName = header->fileName; - if (findCutFirst(fileName, dirName) == true) - { - // skip subdirs from enumeration - const size_t idx = fileName.find(dirSeparator); - if (idx != std::string::npos) - fileName.erase(idx); - bool found(false); - FOR_EACH (StringVectCIter, itn, names) - { - if (*itn == fileName) - { - found = true; - break; - } - } - if (found == false) - { - std::string dirName2 = pathJoin(dirName, fileName); - if (findLast(dirName2, std::string(dirSeparator)) == - false) - { - dirName2 += dirSeparator; - } - FOR_EACH (STD_VECTOR<std::string>::const_iterator, - it, - zipEntry->mDirs) - { - if (*it == dirName2) - { - found = true; - break; - } - } - if (found == true) - names.push_back(fileName); - } - } - } - } - } - - bool isDirectory(FsEntry *restrict const entry, - std::string dirName, - bool &isDirFlag) - { - ZipEntry *const zipEntry = static_cast<ZipEntry*>(entry); - std::string subDir = zipEntry->subDir; - if (!subDir.empty()) - dirName = pathJoin(subDir, dirName); - FOR_EACH (STD_VECTOR<std::string>::const_iterator, - it2, - zipEntry->mDirs) - { - if (*it2 == dirName) - { - isDirFlag = true; - return true; - } - } - return false; - } - - void freeList(List *restrict const handle) - { - delete handle; - } - - File *openRead(FsEntry *restrict const entry, - std::string filename) - { - ZipEntry *const zipEntry = static_cast<ZipEntry*>(entry); - std::string subDir = zipEntry->subDir; - if (!subDir.empty()) - filename = pathJoin(subDir, filename); - FOR_EACH (STD_VECTOR<ZipLocalHeader*>::const_iterator, - it2, - zipEntry->mHeaders) - { - const ZipLocalHeader *restrict const header = *it2; - if (header->fileName == filename) - { - const uint8_t *restrict const buf = - ZipReader::readFile(header); - if (buf == nullptr) - return nullptr; - return new File(&funcs, - buf, - header->uncompressSize); - } - } - return nullptr; - } - - File *openWrite(FsEntry *restrict const entry A_UNUSED, - const std::string &filename A_UNUSED) - { - reportAlways("VirtFs::openWrite for zip not implemented."); - return nullptr; - } - - File *openAppend(FsEntry *restrict const entry A_UNUSED, - const std::string &filename A_UNUSED) - { - reportAlways("VirtFs::openAppend for zip not implemented."); - return nullptr; - } - - int close(File *restrict const file) - { - if (file == nullptr) - return 0; - delete file; - return 1; - } - - int64_t read(File *restrict const file, - void *restrict const buffer, - const uint32_t objSize, - const uint32_t objCount) - { - if (file == nullptr || - objSize == 0 || - objCount == 0) - { - return 0; - } - if (buffer == nullptr) - { - reportAlways("FsZip::read buffer is null"); - return 0; - } - const size_t pos = file->mPos; - const size_t sz = file->mSize; - // if outside of buffer, return - if (pos >= sz) - return 0; - // pointer to start for buffer ready to read - const uint8_t *restrict const memPtr = file->mBuf + pos; - // left buffer size from pos to end - const uint32_t memSize = CAST_U32(sz - pos); - // number of objects possible to read - uint32_t memCount = memSize / objSize; - if (memCount == 0) - return 0; - // limit number of possible objects to read to objCount - if (memCount > objCount) - memCount = objCount; - // number of bytes to read from buffer - const size_t memEnd = memCount * objSize; - memcpy(buffer, memPtr, memEnd); - file->mPos += memEnd; - return memCount; - } - - int64_t write(File *restrict const file A_UNUSED, - const void *restrict const buffer A_UNUSED, - const uint32_t objSize A_UNUSED, - const uint32_t objCount A_UNUSED) - { - return 0; - } - - int64_t fileLength(File *restrict const file) - { - if (file == nullptr) - return -1; - - return file->mSize; - } - - int64_t tell(File *restrict const file) - { - if (file == nullptr) - return -1; - - return file->mPos; - } - - int seek(File *restrict const file, - const uint64_t pos) - { - if (file == nullptr) - return 0; - - if (pos > file->mSize) - return 0; - file->mPos = pos; - return 1; - } - - int eof(File *restrict const file) - { - if (file == nullptr) - return -1; - - return static_cast<int>(file->mPos >= file->mSize); - } - - const char *loadFile(FsEntry *restrict const entry, - std::string filename, - int &restrict fileSize) - { - ZipEntry *const zipEntry = static_cast<ZipEntry*>(entry); - const std::string subDir = zipEntry->subDir; - if (!subDir.empty()) - filename = pathJoin(subDir, filename); - FOR_EACH (STD_VECTOR<ZipLocalHeader*>::const_iterator, - it2, - zipEntry->mHeaders) - { - const ZipLocalHeader *restrict const header = *it2; - if (header->fileName == filename) - { - const uint8_t *restrict const buf = - ZipReader::readFile(header); - if (buf == nullptr) - return nullptr; - - logger->log("Loaded %s/%s", - entry->root.c_str(), - filename.c_str()); - - fileSize = header->uncompressSize; - return reinterpret_cast<const char*>(buf); - } - } - return nullptr; - } -} // namespace FsZip - -} // namespace VirtFs diff --git a/src/fs/virtfs/fszip.h b/src/fs/virtfs/fszip.h deleted file mode 100644 index 92cfd0ab6..000000000 --- a/src/fs/virtfs/fszip.h +++ /dev/null @@ -1,93 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_VIRTFSZIP_H -#define UTILS_VIRTFSZIP_H - -#include "utils/stringvector.h" - -#include "localconsts.h" - -namespace VirtFs -{ - -struct File; -struct List; -struct FsFuncs; -struct FsEntry; - -namespace FsZip -{ - FsFuncs *getFuncs(); - void init(); - void initFuncs(FsFuncs *restrict const ptr); - void deinit(); - bool exists(FsEntry *restrict const entry, - std::string filename, - std::string dirName); - void enumerate(FsEntry *restrict const entry, - std::string dirName, - StringVect &names); - void getFiles(FsEntry *restrict const entry, - std::string dirName, - StringVect &names); - void getFilesWithDir(FsEntry *restrict const entry, - const std::string &dirName, - StringVect &names); - void getDirs(FsEntry *restrict const entry, - std::string dirName, - StringVect &names); - bool isDirectory(FsEntry *restrict const entry, - std::string dirName, - bool &isDirFlag); - void freeList(List *restrict const handle); - File *openRead(FsEntry *restrict const entry, - std::string filename); - File *openWrite(FsEntry *restrict const entry, - const std::string &filename); - File *openAppend(FsEntry *restrict const entry, - const std::string &filename); - File *openReadInternal(const std::string &filename); - bool getRealDir(FsEntry *restrict const entry, - std::string filename, - std::string dirName, - std::string &realDir); - int64_t read(File *restrict const handle, - void *restrict const buffer, - const uint32_t objSize, - const uint32_t objCount); - int64_t write(File *restrict const file, - const void *restrict const buffer, - const uint32_t objSize, - const uint32_t objCount); - int close(File *restrict const file); - int64_t fileLength(File *restrict const file); - int64_t tell(File *restrict const file); - int seek(File *restrict const file, - const uint64_t pos); - int eof(File *restrict const file); - const char *loadFile(FsEntry *restrict const entry, - std::string fileName, - int &restrict fileSize); -} // namespace FsZip - -} // namespace VirtFs - -#endif // UTILS_VIRTFSZIP_H diff --git a/src/fs/virtfs/fsziprwops.cpp b/src/fs/virtfs/fsziprwops.cpp deleted file mode 100644 index e9f72c469..000000000 --- a/src/fs/virtfs/fsziprwops.cpp +++ /dev/null @@ -1,160 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "fs/virtfs/fsziprwops.h" - -#include "logger.h" - -#include "fs/virtfs/file.h" -#include "fs/virtfs/fsfuncs.h" - -#include "utils/cast.h" - -PRAGMA48(GCC diagnostic push) -PRAGMA48(GCC diagnostic ignored "-Wshadow") -#include <SDL_rwops.h> -PRAGMA48(GCC diagnostic pop) - -#include "debug.h" - -namespace VirtFs -{ - -namespace FsZip -{ - RWOPSINT rwops_seek(SDL_RWops *const rw, - const RWOPSINT offset, - const int whence) - { - if (rw == nullptr) - return -1; - File *const handle = static_cast<File *>( - rw->hidden.unknown.data1); - size_t mPos = handle->mPos; - size_t mSize = handle->mSize; - - RWOPSINT pos = 0; - - if (whence == SEEK_SET) - { - pos = offset; - } - else if (whence == SEEK_CUR) - { - const int64_t current = mPos; - if (current == -1) - { - logger->assertLog( - "VirtFs::rwops_seek: Can't find position in file."); - return -1; - } - - pos = CAST_S32(current); - if (static_cast<int64_t>(pos) != current) - { - logger->assertLog("VirtFs::rwops_seek: " - "Can't fit current file position in an int!"); - return -1; - } - - if (offset == 0) /* this is a "tell" call. We're done. */ - return pos; - - pos += offset; - } - else if (whence == SEEK_END) - { - pos = static_cast<RWOPSINT>(mSize + offset); - } - else - { - logger->assertLog( - "VirtFs::rwops_seek: Invalid 'whence' parameter."); - return -1; - } - - if (pos < 0) - { - logger->assertLog("VirtFs::rwops_seek: " - "Attempt to seek past start of file."); - return -1; - } - - handle->mPos = pos; - - if (pos > static_cast<RWOPSINT>(mSize)) - { - logger->assertLog("VirtFs::rwops_seek: seek error."); - return -1; - } - - return pos; - } - - RWOPSSIZE rwops_read(SDL_RWops *const rw, - void *const ptr, - const RWOPSSIZE size, - const RWOPSSIZE maxnum) - { - if (rw == nullptr) - return 0; - File *const handle = static_cast<File *>( - rw->hidden.unknown.data1); - - const int64_t rc = handle->funcs->read(handle, - ptr, - CAST_U32(size), - CAST_U32(maxnum)); - return CAST_S32(rc); - } - - RWOPSSIZE rwops_write(SDL_RWops *const rw A_UNUSED, - const void *const ptr A_UNUSED, - const RWOPSSIZE size A_UNUSED, - const RWOPSSIZE num A_UNUSED) - { - return 0; - } - - int rwops_close(SDL_RWops *const rw) - { - if (rw == nullptr) - return 0; - File *const handle = static_cast<File*>( - rw->hidden.unknown.data1); - delete handle; - SDL_FreeRW(rw); - return 0; - } - -#ifdef USE_SDL2 - RWOPSINT rwops_size(SDL_RWops *const rw) - { - if (!rw) - return 0; - File *const handle = static_cast<File *>( - rw->hidden.unknown.data1); - return handle->mSize; - } -#endif // USE_SDL2 - -} // namespace FsZip - -} // namespace VirtFs diff --git a/src/fs/virtfs/fsziprwops.h b/src/fs/virtfs/fsziprwops.h deleted file mode 100644 index 508b2213c..000000000 --- a/src/fs/virtfs/fsziprwops.h +++ /dev/null @@ -1,55 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_VIRTFS_VIRTFSZIPRWOPS_H -#define UTILS_VIRTFS_VIRTFSZIPRWOPS_H - -#include "fs/virtfs/rwopstypes.h" - -#include "localconsts.h" - -struct SDL_RWops; - -namespace VirtFs -{ - -namespace FsZip -{ - RWOPSINT rwops_seek(SDL_RWops *const rw, - const RWOPSINT offset, - const int whence); - RWOPSSIZE rwops_read(SDL_RWops *const rw, - void *const ptr, - const RWOPSSIZE size, - const RWOPSSIZE maxnum); - RWOPSSIZE rwops_write(SDL_RWops *const rw, - const void *const ptr, - const RWOPSSIZE size, - const RWOPSSIZE num); - int rwops_close(SDL_RWops *const rw); -#ifdef USE_SDL2 - RWOPSINT rwops_size(SDL_RWops *const rw); -#endif // USE_SDL2 - -} // namespace FsZip - -} // namespace VirtFs - -#endif // UTILS_VIRTFS_VIRTFSZIPRWOPS_H diff --git a/src/fs/virtfs/list.cpp b/src/fs/virtfs/list.cpp deleted file mode 100644 index 2f0a23d66..000000000 --- a/src/fs/virtfs/list.cpp +++ /dev/null @@ -1,37 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "fs/virtfs/list.h" - -#include "debug.h" - -namespace VirtFs -{ - -List::List() : - names() -{ -} - -List::~List() -{ -} - -} // namespace VirtFs diff --git a/src/fs/virtfs/list.h b/src/fs/virtfs/list.h deleted file mode 100644 index 9dcb9e269..000000000 --- a/src/fs/virtfs/list.h +++ /dev/null @@ -1,44 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_VIRTLIST_H -#define UTILS_VIRTLIST_H - -#include "utils/stringvector.h" - -#include "localconsts.h" - -namespace VirtFs -{ - -struct List final -{ - List(); - - A_DELETE_COPY(List) - - ~List(); - - StringVect names; -}; - -} // namespace VirtFs - -#endif // UTILS_VIRTLIST_H diff --git a/src/fs/virtfs/rwops.cpp b/src/fs/virtfs/rwops.cpp deleted file mode 100644 index e6a7a5914..000000000 --- a/src/fs/virtfs/rwops.cpp +++ /dev/null @@ -1,149 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -/* - * This code provides a glue layer between PhysicsFS and Simple Directmedia - * Layer's (SDL) RWops i/o abstraction. - * - * License: this code is public domain. I make no warranty that it is useful, - * correct, harmless, or environmentally safe. - * - * This particular file may be used however you like, including copying it - * verbatim into a closed-source project, exploiting it commercially, and - * removing any trace of my name from the source (although I hope you won't - * do that). I welcome enhancements and corrections to this file, but I do - * not require you to send me patches if you make changes. This code has - * NO WARRANTY. - * - * Unless otherwise stated, the rest of PhysicsFS falls under the zlib license. - * Please see LICENSE.txt in the root of the source tree. - * - * SDL falls under the LGPL license. You can get SDL at http://www.libsdl.org/ - * - * This file was written by Ryan C. Gordon. (icculus@icculus.org). - * - * Copyright (C) 2012-2017 The ManaPlus Developers - */ - -#include "fs/virtfs/rwops.h" - -#include "logger.h" - -#include "fs/virtfs/file.h" -#include "fs/virtfs/fs.h" -#include "fs/virtfs/fsfuncs.h" - -#include "utils/fuzzer.h" - -PRAGMA48(GCC diagnostic push) -PRAGMA48(GCC diagnostic ignored "-Wshadow") -#include <SDL_rwops.h> -PRAGMA48(GCC diagnostic pop) - -#include "debug.h" - -namespace VirtFs -{ - -SDL_RWops *create_rwops(File *const file) -{ - SDL_RWops *retval = nullptr; - - if (file == nullptr) - { - logger->assertLog("VirtFs::rwops_seek: create rwops error."); - } - else - { - retval = SDL_AllocRW(); - if (retval != nullptr) - { -#ifdef USE_SDL2 - retval->size = file->funcs->rwops_size; -#endif // USE_SDL2 - - retval->seek = file->funcs->rwops_seek; - retval->read = file->funcs->rwops_read; - retval->write = file->funcs->rwops_write; - retval->close = file->funcs->rwops_close; - retval->hidden.unknown.data1 = file; - } /* if */ - } /* else */ - - return retval; -} /* VirtFs::create_rwops */ - -#ifdef __APPLE__ -static bool checkFilePath(const std::string &restrict fname) -{ - if (fname.empty()) - return false; - if (!exists(fname) || isDirectory(fname)) - return false; - return true; -} -#endif // __APPLE__ - -SDL_RWops *rwopsOpenRead(const std::string &restrict fname) -{ - BLOCK_START("RWopsopenRead") -#ifdef __APPLE__ - if (!checkFilePath(fname)) - return nullptr; -#endif // __APPLE__ -#ifdef USE_FUZZER - if (Fuzzer::conditionTerminate(fname)) - return nullptr; -#endif // USE_FUZZER -#ifdef USE_PROFILER - - SDL_RWops *const ret = create_rwops(openRead(fname)); - - BLOCK_END("RWopsopenRead") - return ret; -#else // USE_PROFILER - - return create_rwops(openRead(fname)); -#endif // USE_PROFILER -} /* RWopsopenRead */ - -SDL_RWops *rwopsOpenWrite(const std::string &restrict fname) -{ -#ifdef __APPLE__ - if (!checkFilePath(fname)) - return nullptr; -#endif // __APPLE__ - - return create_rwops(openWrite(fname)); -} /* RWopsopenWrite */ - -SDL_RWops *rwopsOpenAppend(const std::string &restrict fname) -{ -#ifdef __APPLE__ - if (!checkFilePath(fname)) - return nullptr; -#endif // __APPLE__ - - return create_rwops(openAppend(fname)); -} /* RWopsopenAppend */ - -} // namespace VirtFs - -/* end of virtfsrwops.c ... */ diff --git a/src/fs/virtfs/rwops.h b/src/fs/virtfs/rwops.h deleted file mode 100644 index 7be265ad2..000000000 --- a/src/fs/virtfs/rwops.h +++ /dev/null @@ -1,66 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -/* - * This code provides a glue layer between PhysicsFS and Simple Directmedia - * Layer's (SDL) RWops i/o abstraction. - * - * License: this code is public domain. I make no warranty that it is useful, - * correct, harmless, or environmentally safe. - * - * This particular file may be used however you like, including copying it - * verbatim into a closed-source project, exploiting it commercially, and - * removing any trace of my name from the source (although I hope you won't - * do that). I welcome enhancements and corrections to this file, but I do - * not require you to send me patches if you make changes. This code has - * NO WARRANTY. - * - * Unless otherwise stated, the rest of PhysicsFS falls under the zlib license. - * Please see LICENSE.txt in the root of the source tree. - * - * SDL falls under the LGPL license. You can get SDL at http://www.libsdl.org/ - * - * This file was written by Ryan C. Gordon. (icculus@icculus.org). - * - * Copyright (C) 2012-2017 The ManaPlus Developers - */ - -#ifndef SRC_FS_VIRTFSRWOPS_H -#define SRC_FS_VIRTFSRWOPS_H - -#include "localconsts.h" - -#include <string> - -struct SDL_RWops; - -namespace VirtFs -{ - struct File; - - SDL_RWops *create_rwops(File *const file); - - SDL_RWops *rwopsOpenRead(const std::string &restrict fname); - SDL_RWops *rwopsOpenWrite(const std::string &restrict fname) A_WARN_UNUSED; - SDL_RWops *rwopsOpenAppend(const std::string &restrict fname) - A_WARN_UNUSED; -} // namespace VirtFs - -#endif // SRC_FS_VIRTFSRWOPS_H diff --git a/src/fs/virtfs/rwopstypes.h b/src/fs/virtfs/rwopstypes.h deleted file mode 100644 index 36a87e5a4..000000000 --- a/src/fs/virtfs/rwopstypes.h +++ /dev/null @@ -1,34 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef SRC_FS_VIRTFS_RWOPSTYPES_H -#define SRC_FS_VIRTFS_RWOPSTYPES_H - -#include "localconsts.h" - -#ifdef USE_SDL2 -#define RWOPSINT int64_t -#define RWOPSSIZE size_t -#else // USE_SDL2 -#define RWOPSINT int32_t -#define RWOPSSIZE int -#endif // USE_SDL2 - -#endif // SRC_FS_VIRTFS_RWOPSTYPES_H diff --git a/src/fs/virtfs/tools.cpp b/src/fs/virtfs/tools.cpp deleted file mode 100644 index 64153fc52..000000000 --- a/src/fs/virtfs/tools.cpp +++ /dev/null @@ -1,157 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "fs/virtfs/tools.h" - -#include "logger.h" - -#include "fs/paths.h" - -#include "fs/virtfs/fs.h" -#include "fs/virtfs/list.h" - -#include "utils/foreach.h" -#include "utils/stringutils.h" - -#include <algorithm> -#include <sstream> - -#include "debug.h" - -namespace VirtFs -{ - void searchAndAddArchives(const std::string &restrict path, - const std::string &restrict ext, - const Append append) - { - List *const list = VirtFs::enumerateFiles(path); - FOR_EACH (StringVectCIter, i, list->names) - { - const std::string str = *i; - const size_t len = str.size(); - - if (len > ext.length() && - ext == str.substr(len - ext.length())) - { - const std::string file = path + str; - const std::string realPath = VirtFs::getRealDir(file); - VirtFs::mountZip(pathJoin(realPath, file), append); - } - } - VirtFs::freeList(list); - } - - void searchAndRemoveArchives(const std::string &restrict path, - const std::string &restrict ext) - { - List *const list = VirtFs::enumerateFiles(path); - FOR_EACH (StringVectCIter, i, list->names) - { - const std::string str = *i; - const size_t len = str.size(); - if (len > ext.length() && - ext == str.substr(len - ext.length())) - { - const std::string file = path + str; - const std::string realPath = VirtFs::getRealDir(file); - VirtFs::unmountZip(pathJoin(realPath, file)); - } - } - VirtFs::freeList(list); - } - - void getFilesInDir(const std::string &dir, - StringVect &list, - const std::string &ext) - { - const std::string &path = dir; - StringVect tempList; - VirtFs::getFilesWithDir(path, tempList); - FOR_EACH (StringVectCIter, it, tempList) - { - const std::string &str = *it; - if (findLast(str, ext)) - list.push_back(str); - } - std::sort(list.begin(), list.end()); - } - - std::string getPath(const std::string &file) - { - // get the real path to the file - const std::string tmp = VirtFs::getRealDir(file); - std::string path; - - // if the file is not in the search path, then its empty - if (!tmp.empty()) - { - path = pathJoin(tmp, file); -#if defined __native_client__ - std::string dataZip = "/http/data.zip/"; - if (path.substr(0, dataZip.length()) == dataZip) - path = path.replace(0, dataZip.length(), "/http/data/"); -#endif // defined __native_client__ - } - else - { - // if not found in search path return the default path - path = pathJoin(getPackageDir(), file); - } - - return path; - } - - std::string loadTextFileString(const std::string &fileName) - { - int contentsLength; - const char *fileContents = VirtFs::loadFile(fileName, contentsLength); - - if (fileContents == nullptr) - { - logger->log("Couldn't load text file: %s", fileName.c_str()); - return std::string(); - } - const std::string str = std::string(fileContents, contentsLength); - delete [] fileContents; - return str; - } - - bool loadTextFile(const std::string &fileName, - StringVect &lines) - { - int contentsLength; - const char *fileContents = VirtFs::loadFile(fileName, contentsLength); - - if (fileContents == nullptr) - { - logger->log("Couldn't load text file: %s", fileName.c_str()); - return false; - } - - std::istringstream iss(std::string(fileContents, contentsLength)); - std::string line; - - while (getline(iss, line)) - lines.push_back(line); - - delete [] fileContents; - return true; - } -} // namespace VirtFs diff --git a/src/fs/virtfs/tools.h b/src/fs/virtfs/tools.h deleted file mode 100644 index f00a976bb..000000000 --- a/src/fs/virtfs/tools.h +++ /dev/null @@ -1,46 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2013-2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_VIRTFSTOOLS_H -#define UTILS_VIRTFSTOOLS_H - -#include "enums/simpletypes/append.h" - -#include "utils/stringvector.h" - -#include "localconsts.h" - -namespace VirtFs -{ - void searchAndAddArchives(const std::string &restrict path, - const std::string &restrict ext, - const Append append); - void searchAndRemoveArchives(const std::string &restrict path, - const std::string &restrict ext); - void getFilesInDir(const std::string &dir, - StringVect &list, - const std::string &ext); - std::string getPath(const std::string &file); - bool loadTextFile(const std::string &fileName, - StringVect &lines); - std::string loadTextFileString(const std::string &fileName); -} // namespace VirtFs - -#endif // UTILS_VIRTFSTOOLS_H diff --git a/src/fs/virtfs/zipentry.cpp b/src/fs/virtfs/zipentry.cpp deleted file mode 100644 index d8440833b..000000000 --- a/src/fs/virtfs/zipentry.cpp +++ /dev/null @@ -1,48 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "fs/virtfs/zipentry.h" - -#include "fs/virtfs/ziplocalheader.h" - -#include "utils/dtor.h" - -#include "debug.h" - -namespace VirtFs -{ - -ZipEntry::ZipEntry(const std::string &restrict archiveName, - const std::string &subDir0, - FsFuncs *restrict const funcs0) : - FsEntry(FsEntryType::Zip, funcs0), - mHeaders(), - mDirs() -{ - root = archiveName; - subDir = subDir0; -} - -ZipEntry::~ZipEntry() -{ - delete_all(mHeaders); -} - -} // namespace VirtFs diff --git a/src/fs/virtfs/zipentry.h b/src/fs/virtfs/zipentry.h deleted file mode 100644 index eaf77889d..000000000 --- a/src/fs/virtfs/zipentry.h +++ /dev/null @@ -1,51 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_VIRTZIPENTRY_H -#define UTILS_VIRTZIPENTRY_H - -#include "fs/virtfs/fsentry.h" - -#include "utils/vector.h" - -#include "localconsts.h" - -namespace VirtFs -{ - -struct ZipLocalHeader; - -struct ZipEntry final : public FsEntry -{ - ZipEntry(const std::string &restrict archiveName, - const std::string &subDir0, - FsFuncs *restrict const funcs); - - A_DELETE_COPY(ZipEntry) - - virtual ~ZipEntry(); - - STD_VECTOR<ZipLocalHeader*> mHeaders; - STD_VECTOR<std::string> mDirs; -}; - -} // namespace VirtFs - -#endif // UTILS_VIRTZIPENTRY_H diff --git a/src/fs/virtfs/ziplocalheader.cpp b/src/fs/virtfs/ziplocalheader.cpp deleted file mode 100644 index 437140d07..000000000 --- a/src/fs/virtfs/ziplocalheader.cpp +++ /dev/null @@ -1,40 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "fs/virtfs/ziplocalheader.h" - -#include "localconsts.h" - -#include "debug.h" - -namespace VirtFs -{ - -ZipLocalHeader::ZipLocalHeader() : - fileName(), - zipEntry(nullptr), - dataOffset(0U), - compressSize(0U), - uncompressSize(0U), - compressed(false) -{ -} - -} // namespace VirtFs diff --git a/src/fs/virtfs/ziplocalheader.h b/src/fs/virtfs/ziplocalheader.h deleted file mode 100644 index 88bfc2458..000000000 --- a/src/fs/virtfs/ziplocalheader.h +++ /dev/null @@ -1,49 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_ZIPLOCALHEADER_H -#define UTILS_ZIPLOCALHEADER_H - -#include "localconsts.h" - -#include <string> - -namespace VirtFs -{ - -struct ZipEntry; - -struct ZipLocalHeader final -{ - ZipLocalHeader(); - - A_DELETE_COPY(ZipLocalHeader) - - std::string fileName; - ZipEntry *zipEntry; - uint32_t dataOffset; - uint32_t compressSize; - uint32_t uncompressSize; - bool compressed; -}; - -} // namespace VirtFs - -#endif // UTILS_ZIPLOCALHEADER_H diff --git a/src/fs/virtfs/zipreader.cpp b/src/fs/virtfs/zipreader.cpp deleted file mode 100644 index 2d473bec7..000000000 --- a/src/fs/virtfs/zipreader.cpp +++ /dev/null @@ -1,334 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#include "fs/virtfs/zipreader.h" - -#include "fs/paths.h" - -#include "fs/virtfs/zipentry.h" -#include "fs/virtfs/ziplocalheader.h" - -#include "utils/cast.h" -#include "utils/checkutils.h" -#include "utils/delete2.h" -#include "utils/stringutils.h" - -#include <zlib.h> -PRAGMA48(GCC diagnostic push) -PRAGMA48(GCC diagnostic ignored "-Wshadow") -#include <SDL_endian.h> -PRAGMA48(GCC diagnostic pop) - -#include "debug.h" - -#ifndef SDL_BIG_ENDIAN -#error missing SDL_endian.h -#endif // SDL_BYTEORDER - -// #define DEBUG_ZIP - -extern const char *dirSeparator; - -#define readVal(val, sz, msg) \ - cnt = fread(static_cast<void*>(val), 1, sz, arcFile); \ - if (cnt != sz) \ - { \ - reportAlways("Error reading " msg " in file %s", \ - archiveName.c_str()); \ - delete2(header); \ - delete [] buf; \ - fclose(arcFile); \ - return false; \ - } - -#if SDL_BYTEORDER == SDL_BIG_ENDIAN -#define swapVal16(val) val = __builtin_bswap16(val); -#define swapVal32(val) val = __builtin_bswap32(val); -#else // SDL_BYTEORDER == SDL_BIG_ENDIAN -#define swapVal16(val) -#define swapVal32(val) -#endif // SDL_BYTEORDER == SDL_BIG_ENDIAN - -namespace VirtFs -{ - -namespace ZipReader -{ - bool readArchiveInfo(ZipEntry *const entry) - { - if (entry == nullptr) - { - reportAlways("Entry is null."); - return false; - } - const std::string archiveName = entry->root; - STD_VECTOR<ZipLocalHeader*> &restrict headers = entry->mHeaders; - STD_VECTOR<std::string> &restrict dirs = entry->mDirs; - FILE *restrict const arcFile = fopen(archiveName.c_str(), - "rb"); - if (arcFile == nullptr) - { - reportAlways("Can't open zip file %s", - archiveName.c_str()); - return false; - } - uint8_t *const buf = new uint8_t[65535 + 10]; - uint16_t val16 = 0U; - uint16_t method = 0U; - ZipLocalHeader *header = nullptr; - -#ifdef DEBUG_ZIP - logger->log("Read archive: %s", archiveName.c_str()); -#endif // DEBUG_ZIP - - // format source https://en.wikipedia.org/wiki/Zip_%28file_format%29 - while (feof(arcFile) == 0) - { - size_t cnt = 0U; - // file header pointer on 0 - // read file header signature - readVal(buf, 4, "zip file header"); // + 4 - // pointer on 4 - - if (buf[0] == 0x50 && - buf[1] == 0x4B && - buf[2] == 0x03 && - buf[3] == 0x04) - { // local file header - header = new ZipLocalHeader; - header->zipEntry = entry; - // skip useless fields - fseek(arcFile, 4, SEEK_CUR); // + 4 - // file header pointer on 8 - readVal(&method, 2, "compression method") // + 2 - swapVal16(method) - header->compressed = (method != 0); - // file header pointer on 10 - fseek(arcFile, 8, SEEK_CUR); // + 8 - // file header pointer on 18 - readVal(&header->compressSize, 4, - "zip compressed size") // + 4 - swapVal32(header->compressSize) - // file header pointer on 22 - readVal(&header->uncompressSize, 4, - "zip uncompressed size") // + 4 - swapVal32(header->uncompressSize) - // file header pointer on 26 - readVal(&val16, 2, "file name length") // + 2 - swapVal16(val16) - // file header pointer on 28 - const uint32_t fileNameLen = CAST_U32(val16); - if (fileNameLen > 1000) - { - reportAlways("Error too long file name in file %s", - archiveName.c_str()); - delete header; - delete [] buf; - fclose(arcFile); - return false; - } - readVal(&val16, 2, "extra field length") // + 2 - swapVal16(val16) - // file header pointer on 30 - const uint32_t extraFieldLen = CAST_U32(val16); - readVal(buf, fileNameLen, "file name"); - // file header pointer on 30 + fileNameLen - buf[fileNameLen] = 0; - header->fileName = std::string( - reinterpret_cast<char*>(buf)); - prepareFsPath(header->fileName); - header->dataOffset = CAST_S32(ftell(arcFile) + extraFieldLen); - fseek(arcFile, extraFieldLen + header->compressSize, SEEK_CUR); - // pointer on 30 + fileNameLen + extraFieldLen + compressSize - if (findLast(header->fileName, dirSeparator) == false) - { - headers.push_back(header); -#ifdef DEBUG_ZIP - logger->log(" file name: %s", - header->fileName.c_str()); - logger->log(" compression method: %u", - CAST_U32(method)); - logger->log(" compressed size: %u", - header->compressSize); - logger->log(" uncompressed size: %u", - header->uncompressSize); -#endif // DEBUG_ZIP - } - else - { -#ifdef DEBUG_ZIP - logger->log(" dir name: %s", - header->fileName.c_str()); -#endif // DEBUG_ZIP - dirs.push_back(header->fileName); - delete header; - } - } - else if (buf[0] == 0x50 && - buf[1] == 0x4B && - buf[2] == 0x01 && - buf[3] == 0x02) - { // central directory file header - // !!! This is quick way for read zip archives. !!! - // !!! It ignore modified files in archive. !!! - // ignoring central directory entries - break; - } - else if (buf[0] == 0x50 && - buf[1] == 0x4B && - buf[2] == 0x05 && - buf[3] == 0x06) - { // end of central directory - // !!! This is quick way for read zip archives. !!! - // !!! It ignore modified files in archive. !!! - // ignoring end of central directory - break; - } - else - { - reportAlways("Error in header signature (0x%02x%02x%02x%02x)" - " in file %s", - buf[0], - buf[1], - buf[2], - buf[3], - archiveName.c_str()); - delete [] buf; - fclose(arcFile); - return false; - } - } - delete [] buf; - fclose(arcFile); - return true; - } - - void reportZlibError(const std::string &text, - const int err) - { - reportAlways("Zlib error: '%s' in %s", - text.c_str(), - getZlibError(err).c_str()); - } - - std::string getZlibError(const int err) - { - switch (err) - { - case Z_OK: - return std::string(); - default: - return "unknown zlib error"; - } - } - - uint8_t *readCompressedFile(const ZipLocalHeader *restrict const header) - { - if (header == nullptr) - { - reportAlways("ZipReader::readCompressedFile: header is null"); - return nullptr; - } - FILE *restrict const arcFile = fopen( - header->zipEntry->root.c_str(), - "rb"); - if (arcFile == nullptr) - { - reportAlways("Can't open zip file %s", - header->zipEntry->root.c_str()); - return nullptr; - } - - fseek(arcFile, header->dataOffset, SEEK_SET); - const uint32_t compressSize = header->compressSize; - uint8_t *const buf = new uint8_t[compressSize]; - if (fread(static_cast<void*>(buf), 1, compressSize, arcFile) != - compressSize) - { - reportAlways("Read zip compressed file error from archive: %s", - header->zipEntry->root.c_str()); - fclose(arcFile); - delete [] buf; - return nullptr; - } - fclose(arcFile); - return buf; - } - - const uint8_t *readFile(const ZipLocalHeader *restrict const header) - { - if (header == nullptr) - { - reportAlways("Open zip file error. header is null."); - return nullptr; - } - uint8_t *restrict const in = readCompressedFile(header); - if (in == nullptr) - return nullptr; - if (header->compressed == false) - return in; // return as is if data not compressed - const size_t outSize = header->uncompressSize; - uint8_t *restrict const out = new uint8_t[outSize]; - if (outSize == 0) - { - delete [] in; - return out; - } - - z_stream strm; - strm.zalloc = nullptr; - strm.zfree = nullptr; - strm.opaque = nullptr; - strm.next_in = in; - strm.avail_in = header->compressSize; - strm.next_out = out; - strm.avail_out = CAST_U32(outSize); - -PRAGMACLANG6GCC(GCC diagnostic push) -PRAGMACLANG6GCC(GCC diagnostic ignored "-Wold-style-cast") - int ret = inflateInit2(&strm, -MAX_WBITS); -PRAGMACLANG6GCC(GCC diagnostic pop) - - if (ret != Z_OK) - { - reportZlibError(header->zipEntry->root, ret); - delete [] in; - delete [] out; - return nullptr; - } - ret = inflate(&strm, Z_FINISH); -// ret = inflate(&strm, Z_SYNC_FLUSH); - if (ret != Z_OK && - ret != Z_STREAM_END) - { - reportZlibError("file decompression error", - ret); - inflateEnd(&strm); - delete [] in; - delete [] out; - return nullptr; - } - inflateEnd(&strm); - delete [] in; - return out; - } -} // namespace ZipReader - -} // namespace VirtFs diff --git a/src/fs/virtfs/zipreader.h b/src/fs/virtfs/zipreader.h deleted file mode 100644 index cf7a85033..000000000 --- a/src/fs/virtfs/zipreader.h +++ /dev/null @@ -1,46 +0,0 @@ -/* - * The ManaPlus Client - * Copyright (C) 2017 The ManaPlus Developers - * - * This file is part of The ManaPlus Client. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see <http://www.gnu.org/licenses/>. - */ - -#ifndef UTILS_ZIP_H -#define UTILS_ZIP_H - -#include "localconsts.h" - -#include <string> - -namespace VirtFs -{ - -struct ZipEntry; -struct ZipLocalHeader; - -namespace ZipReader -{ - bool readArchiveInfo(ZipEntry *const entry); - std::string getZlibError(const int err); - void reportZlibError(const std::string &text, - const int err); - uint8_t *readCompressedFile(const ZipLocalHeader *restrict const header); - const uint8_t *readFile(const ZipLocalHeader *restrict const header); -} // namespace ZipReader - -} // namespace VirtFs - -#endif // UTILS_ZIP_H |