Ticket #8762: getsavepath3.patch

File getsavepath3.patch, 17.7 KB (added by SF/david_corrales, 12 years ago)

Revision 3

  • home/david/Projects/scummvm/backends/platform/ds/arm9/source/gbampsave.h

    Property changes on: /home/david/Projects/scummvm
    ___________________________________________________________________
    Name: svn:ignore
       - config.log
    scummvm
    scummvm-static
    config.h
    config.mk
    .gdb_history
    dumps
    Credits.rtf
    *.mshark
    
       + .project
    config.h
    config.mk
    reconf.sh
    scummvm
    plugins
    
    
     
    2424#define _GBAMPSAVE_H_
    2525
    2626#include "system.h"
    27 #include "common/savefile.h"
     27#include "saves/default/default-saves.h"
    2828#include "ds-fs.h"
    2929
    3030#define SAVE_BUFFER_SIZE 100000
     
    5858};
    5959
    6060
    61 class GBAMPSaveFileManager : public Common::SaveFileManager {
    62 
    63        
     61class GBAMPSaveFileManager : public DefaultSaveFileManager {
    6462public:
    6563        GBAMPSaveFileManager();
    6664        ~GBAMPSaveFileManager();
     
    8179        void listFiles();
    8280};
    8381
    84 
    8582#endif
  • home/david/Projects/scummvm/backends/platform/ps2/savefile.cpp

     
    484484        _screen->wantAnim(false);
    485485}
    486486
    487 const char *Ps2SaveFileManager::getSavePath(void) const {
    488         return "mc0:";
    489 }
    490 
    491487bool Ps2SaveFileManager::setupIcon(const char *dest, const char *ico, const char *descr1, const char *descr2) {
    492488        mcIcon icon_sys;
    493489        memset(&icon_sys, 0, sizeof(mcIcon));
  • home/david/Projects/scummvm/backends/platform/ps2/savefile.h

     
    4242        virtual Common::OutSaveFile *openForSaving(const char *filename);
    4343        virtual void listSavefiles(const char *prefix, bool *marks, int num);
    4444
    45         /** Get the path to the save game directory. */
    46         virtual const char *getSavePath() const;
    47 
    4845        void writeSaveNonblocking(char *name, void *buf, uint32 size);
    4946        void saveThread(void);
    5047        void quit(void);
     48       
    5149private:
    5250        bool setupIcon(const char *dest, const char *ico, const char *descr1, const char *descr2);
    5351
  • home/david/Projects/scummvm/backends/saves/default/default-saves.cpp

     
    2929#include "common/util.h"
    3030#include "common/fs.h"
    3131#include "common/file.h"
     32#include "common/config-manager.h"
    3233#include "backends/saves/default/default-saves.h"
    3334#include "backends/saves/compressed/compressed-saves.h"
    3435
     
    128129        return results;
    129130}
    130131
    131 Common::InSaveFile *DefaultSaveFileManager::openForLoading(const char *filename) {
    132         char buf[256];
    133         join_paths(filename, getSavePath(), buf, sizeof(buf));
    134 
    135         StdioSaveFile *sf = new StdioSaveFile(buf, false);
    136 
    137         if (!sf->isOpen()) {
    138                 delete sf;
    139                 sf = 0;
    140         }
    141         return wrapInSaveFile(sf);
    142 }
    143 
    144 Common::OutSaveFile *DefaultSaveFileManager::openForSaving(const char *filename) {
    145         char buf[256];
    146 
    147         // Ensure that the savepath exists and is writeable. If not, generate
    148         // an appropriate error
    149         const char *savePath = getSavePath();
     132void DefaultSaveFileManager::checkPath(const char *path) {
     133        clearError();
     134        Common::String pathStr(path);
    150135
    151136#if defined(UNIX) || defined(__SYMBIAN32__)
    152137        struct stat sb;
    153         clearError();
    154138
    155139        // Check whether the dir exists
    156         if (stat(savePath, &sb) == -1) {
     140        if (stat(path, &sb) == -1) {
    157141                // The dir does not exist, or stat failed for some other reason.
    158142                // If the problem was that the path pointed to nothing, try
    159143                // to create the dir (ENOENT case).
     
    159143                // to create the dir (ENOENT case).
    160144                switch (errno) {
    161145                case EACCES:
    162                         setError(SFM_DIR_ACCESS, Common::String("Search or write permission denied"));
     146                        setError(SFM_DIR_ACCESS, "Search or write permission denied: "+pathStr);
    163147                        break;
    164148#if !defined(__SYMBIAN32__)
    165149                case ELOOP:
    166                         setError(SFM_DIR_LOOP, Common::String("Too many symbolic links encountered while traversing the path"));
     150                        setError(SFM_DIR_LOOP, "Too many symbolic links encountered while traversing the path: "+pathStr);
    167151                        break;
    168152#endif
    169153                case ENAMETOOLONG:
    170                         setError(SFM_DIR_NAMETOOLONG, Common::String("The path name is too long"));
     154                        setError(SFM_DIR_NAMETOOLONG, "The path name is too long: "+pathStr);
    171155                        break;
    172156                case ENOENT:
    173                         if (mkdir(savePath, 0755) != 0) {
     157                        if (mkdir(path, 0755) != 0) {
    174158                                // mkdir could fail for various reasons: The parent dir doesn't exist,
    175159                                // or is not writeable, the path could be completly bogus, etc.
    176                                 warning("mkdir for '%s' failed!", savePath);
     160                                warning("mkdir for '%s' failed!", path);
    177161                                perror("mkdir");
    178162
    179163                                switch (errno) {
     
    178162
    179163                                switch (errno) {
    180164                                case EACCES:
    181                                         setError(SFM_DIR_ACCESS, Common::String("Search or write permission denied"));
     165                                        setError(SFM_DIR_ACCESS, "Search or write permission denied: "+pathStr);
    182166                                        break;
    183167                                case EMLINK:
    184                                         setError(SFM_DIR_LINKMAX, Common::String("The link count of the parent directory would exceed {LINK_MAX}"));
     168                                        setError(SFM_DIR_LINKMAX, "The link count of the parent directory would exceed {LINK_MAX}: "+pathStr);
    185169                                        break;
    186170#if !defined(__SYMBIAN32__)
    187171                                case ELOOP:
    188                                         setError(SFM_DIR_LOOP, Common::String("Too many symbolic links encountered while traversing the path"));
     172                                        setError(SFM_DIR_LOOP, "Too many symbolic links encountered while traversing the path: "+pathStr);
    189173                                        break;
    190174#endif
    191175                                case ENAMETOOLONG:
    192                                         setError(SFM_DIR_NAMETOOLONG, Common::String("The path name is too long"));
     176                                        setError(SFM_DIR_NAMETOOLONG, "The path name is too long: "+pathStr);
    193177                                        break;
    194178                                case ENOENT:
    195                                         setError(SFM_DIR_NOENT, Common::String("A component of the path does not exist, or the path is an empty string"));
     179                                        setError(SFM_DIR_NOENT, "A component of the path does not exist, or the path is an empty string: "+pathStr);
    196180                                        break;
    197181                                case ENOTDIR:
    198                                         setError(SFM_DIR_NOTDIR, Common::String("A component of the path prefix is not a directory"));
     182                                        setError(SFM_DIR_NOTDIR, "A component of the path prefix is not a directory: "+pathStr);
    199183                                        break;
    200184                                case EROFS:
    201                                         setError(SFM_DIR_ROFS, Common::String("The parent directory resides on a read-only file system"));
     185                                        setError(SFM_DIR_ROFS, "The parent directory resides on a read-only file system:"+pathStr);
    202186                                        break;
    203187                                }
    204 
    205                                 return 0;
    206188                        }
    207189                        break;
    208190                case ENOTDIR:
    209                         setError(SFM_DIR_NOTDIR, Common::String("A component of the path prefix is not a directory"));
     191                        setError(SFM_DIR_NOTDIR, "A component of the path prefix is not a directory: "+pathStr);
    210192                        break;
    211193                }
    212194        } else {
     
    212194        } else {
    213195                // So stat() succeeded. But is the path actually pointing to a directory?
    214196                if (!S_ISDIR(sb.st_mode)) {
    215                         setError(SFM_DIR_NOTDIR, Common::String("The given savepath is not a directory"));
    216 
    217                         return 0;
     197                        setError(SFM_DIR_NOTDIR, "The given savepath is not a directory: "+pathStr);
    218198                }
    219199        }
    220200#endif
     201}
    221202
    222         join_paths(filename, savePath, buf, sizeof(buf));
     203Common::InSaveFile *DefaultSaveFileManager::openForLoading(const char *filename) {
     204        // Ensure that the savepath is valid. If not, generate an appropriate error.
     205        char buf[256];
     206        const char *savePath = getSavePath();
     207        checkPath(savePath);
     208       
     209        if (getError() == SFM_NO_ERROR) {
     210                join_paths(filename, savePath, buf, sizeof(buf));
     211                StdioSaveFile *sf = new StdioSaveFile(buf, false);
     212       
     213                if (!sf->isOpen()) {
     214                        delete sf;
     215                        sf = 0;
     216                }
     217               
     218                return wrapInSaveFile(sf);
     219        } else {
     220                return 0;
     221        }
     222}
    223223
    224         StdioSaveFile *sf = new StdioSaveFile(buf, true);
     224Common::OutSaveFile *DefaultSaveFileManager::openForSaving(const char *filename) {
     225        // Ensure that the savepath is valid. If not, generate an appropriate error.
     226        char buf[256];
     227        const char *savePath = getSavePath();
     228        checkPath(savePath);
    225229
    226         if (!sf->isOpen()) {
    227                 delete sf;
    228                 sf = 0;
     230        if (getError() == SFM_NO_ERROR) {
     231                join_paths(filename, savePath, buf, sizeof(buf));
     232                StdioSaveFile *sf = new StdioSaveFile(buf, true);
     233       
     234                if (!sf->isOpen()) {
     235                        delete sf;
     236                        sf = 0;
     237                }
     238       
     239                return wrapOutSaveFile(sf);
     240        } else {
     241                return 0;
    229242        }
    230 
    231         return wrapOutSaveFile(sf);
    232243}
    233244
    234245bool DefaultSaveFileManager::removeSavefile(const char *filename) {
     
    233244
    234245bool DefaultSaveFileManager::removeSavefile(const char *filename) {
    235246        char buf[256];
     247        clearError();
     248        Common::String filenameStr;
    236249        join_paths(filename, getSavePath(), buf, sizeof(buf));
    237250       
    238251        if (remove(buf) != 0) {
     
    238251        if (remove(buf) != 0) {
    239252#ifndef _WIN32_WCE
    240253                if (errno == EACCES)
    241                         setError(SFM_DIR_ACCESS, Common::String("Search or write permission denied"));
     254                        setError(SFM_DIR_ACCESS, "Search or write permission denied: "+filenameStr);
    242255               
    243256                if (errno == ENOENT)
    244                         setError(SFM_DIR_NOENT, Common::String("A component of the path does not exist, or the path is an empty string"));
     257                        setError(SFM_DIR_NOENT, "A component of the path does not exist, or the path is an empty string: "+filenameStr);
    245258#endif
    246259                return false;
    247260        } else {
     
    249262        }
    250263}
    251264
     265const char *DefaultSaveFileManager::getSavePath() const {
     266
     267#if defined(PALMOS_MODE) || defined(__PSP__)
     268        return SCUMMVM_SAVEPATH;
     269#else
     270
     271        const char *dir = NULL;
     272
     273        // Try to use game specific savepath from config
     274        dir = ConfMan.get("savepath").c_str();
     275
     276        // Work around a bug (#999122) in the original 0.6.1 release of
     277        // ScummVM, which would insert a bad savepath value into config files.
     278        if (0 == strcmp(dir, "None")) {
     279                ConfMan.removeKey("savepath", ConfMan.getActiveDomainName());
     280                ConfMan.flushToDisk();
     281                dir = ConfMan.get("savepath").c_str();
     282        }
     283
     284#ifdef _WIN32_WCE
     285        if (dir[0] == 0)
     286                dir = ConfMan.get("path").c_str();
     287#endif
     288
     289        assert(dir);
     290
     291        return dir;
     292#endif
     293}
     294
    252295#endif // !defined(DISABLE_DEFAULT_SAVEFILEMANAGER)
  • home/david/Projects/scummvm/backends/saves/default/default-saves.h

     
    2929#include "common/savefile.h"
    3030#include "common/str.h"
    3131
     32/**
     33 * Provides a default savefile manager implementation for common platforms.
     34 */
    3235class DefaultSaveFileManager : public Common::SaveFileManager {
    3336public:
    3437        virtual Common::StringList listSavefiles(const char *regex);
     
    3538        virtual Common::InSaveFile *openForLoading(const char *filename);
    3639        virtual Common::OutSaveFile *openForSaving(const char *filename);
    3740        virtual bool removeSavefile(const char *filename);
     41
     42protected:
     43        /**
     44         * Get the path to the savegame directory.
     45         * Should only be used internally since some platforms
     46         * might implement savefiles in a completely different way.
     47         */
     48        virtual const char *getSavePath() const;
     49       
     50        /**
     51         * Checks the given path for read access, existence, etc.
     52         * Sets the internal error and error message accordingly.
     53         */
     54        void checkPath(const char *path);
    3855};
    3956
    4057#endif
  • home/david/Projects/scummvm/backends/saves/savefile.cpp

     
    2424 */
    2525
    2626#include "common/util.h"
    27 #include "common/config-manager.h"
    2827#include "common/savefile.h"
    2928
    3029#include <stdio.h>
     
    7271        return success;
    7372}
    7473
    75 const char *SaveFileManager::getSavePath() const {
    76 
    77 #if defined(PALMOS_MODE) || defined(__PSP__)
    78         return SCUMMVM_SAVEPATH;
    79 #else
    80 
    81         const char *dir = NULL;
    82 
    83         // Try to use game specific savepath from config
    84         dir = ConfMan.get("savepath").c_str();
    85 
    86         // Work around a bug (#999122) in the original 0.6.1 release of
    87         // ScummVM, which would insert a bad savepath value into config files.
    88         if (0 == strcmp(dir, "None")) {
    89                 ConfMan.removeKey("savepath", ConfMan.getActiveDomainName());
    90                 ConfMan.flushToDisk();
    91                 dir = ConfMan.get("savepath").c_str();
    92         }
    93 
    94 #ifdef _WIN32_WCE
    95         if (dir[0] == 0)
    96                 dir = ConfMan.get("path").c_str();
    97 #endif
    98 
    99         assert(dir);
    100 
    101         return dir;
    102 #endif
     74String SaveFileManager::popErrorDesc() {
     75        String err = _errorDesc;
     76        clearError();
     77       
     78        return err;
    10379}
    10480
    10581} // End of namespace Common
  • home/david/Projects/scummvm/common/savefile.h

     
    109109         * @return A string describing the last error.
    110110         */
    111111        virtual String getErrorDesc() { return _errorDesc; }
    112 
     112       
     113        /**
     114         * Returns the last ocurred error description. If none ocurred, returns 0.
     115         * Also clears the last error state and description.
     116         *
     117         * @return A string describing the last error.
     118         */
     119        virtual String popErrorDesc();
     120       
    113121        /**
    114122         * Open the file with name filename in the given directory for saving.
    115123         * @param filename      the filename
     
    145153         * returns a list of strings for all present file names.
    146154         */
    147155        virtual Common::StringList listSavefiles(const char *regex) = 0;
    148 
    149         /**
    150          * Get the path to the save game directory.
    151          * Should only be used for error messages, *never* to construct file paths
    152          * from it, since that is highly unportable!
    153          */
    154         virtual const char *getSavePath() const;
    155156};
    156157
    157158} // End of namespace Common
  • home/david/Projects/scummvm/engines/sky/control.cpp

     
    944944                                                refreshNames = true;
    945945                                        }
    946946                                        if (clickRes == NO_DISK_SPACE) {
    947                                                 displayMessage(0, "Could not save game in directory '%s'", _saveFileMan->getSavePath());
     947                                                displayMessage(0, "Could not save the game. (%s)", _saveFileMan->popErrorDesc().c_str());
    948948                                                quitPanel = true;
    949949                                        }
    950950                                        if ((clickRes == CANCEL_PRESSED) || (clickRes == GAME_RESTORED))
     
    11531153                delete outf;
    11541154        }
    11551155        if (ioFailed)
    1156                 displayMessage(NULL, "Unable to store Savegame names to file SKY-VM.SAV in directory %s", _saveFileMan->getSavePath());
     1156                displayMessage(NULL, "Unable to store Savegame names to file SKY-VM.SAV. (%s)", _saveFileMan->popErrorDesc().c_str());
    11571157        free(tmpBuf);
    11581158}
    11591159
     
    11671167
    11681168        outf = _saveFileMan->openForSaving(fName);
    11691169        if (outf == NULL) {
    1170                 displayMessage(0, "Unable to create autosave file '%s' in directory '%s'", fName, _saveFileMan->getSavePath());
     1170                displayMessage(0, "Unable to create autosave file '%s'. (%s)", fName, _saveFileMan->popErrorDesc().c_str());
    11711171                return;
    11721172        }
    11731173        uint8 *saveData = (uint8 *)malloc(0x20000);
     
    11771177        outf->finalize();
    11781178
    11791179        if (outf->ioFailed())
    1180                 displayMessage(0, "Unable to write autosave file '%s' in directory '%s'. Disk full?", fName, _saveFileMan->getSavePath());
     1180                displayMessage(0, "Unable to write autosave file '%s'. Disk full?", fName, _saveFileMan->popErrorDesc().c_str());
    11811181
    11821182        delete outf;
    11831183        free(saveData);
  • home/david/Projects/scummvm/engines/sword1/control.cpp

     
    738738
    739739        if (!outf) {
    740740                // Display an error message, and do nothing
    741                 displayMessage(0, "Can't create SAVEGAME.INF in directory '%s'", _saveFileMan->getSavePath());
     741                displayMessage(0, "Can't create SAVEGAME.INF. (%s)", _saveFileMan->popErrorDesc().c_str());
    742742                return;
    743743        }
    744744
     
    757757        }
    758758        outf->finalize();
    759759        if (outf->ioFailed())
    760                 displayMessage(0, "Can't write to SAVEGAME.INF in directory '%s'. Device full?", _saveFileMan->getSavePath());
     760                displayMessage(0, "Can't write to SAVEGAME.INF. Device full? (%s)", _saveFileMan->popErrorDesc().c_str());
    761761        delete outf;
    762762}
    763763
     
    928928        outf = _saveFileMan->openForSaving(fName);
    929929        if (!outf) {
    930930                // Display an error message and do nothing
    931                 displayMessage(0, "Unable to create file '%s' in directory '%s'", fName, _saveFileMan->getSavePath());
     931                displayMessage(0, "Unable to create file '%s'. (%s)", fName, _saveFileMan->popErrorDesc().c_str());
    932932                return;
    933933        }
    934934
     
    952952                outf->writeUint32LE(playerRaw[cnt2]);
    953953        outf->finalize();
    954954        if (outf->ioFailed())
    955                 displayMessage(0, "Couldn't write to file '%s' in directory '%s'. Device full?", fName, _saveFileMan->getSavePath());
     955                displayMessage(0, "Couldn't write to file '%s'. Device full? (%s)", fName, _saveFileMan->popErrorDesc().c_str());
    956956        delete outf;
    957957}
    958958
     
    964964        inf = _saveFileMan->openForLoading(fName);
    965965        if (!inf) {
    966966                // Display an error message, and do nothing
    967                 displayMessage(0, "Can't open file '%s' in directory '%s'", fName, _saveFileMan->getSavePath());
     967                displayMessage(0, "Can't open file '%s'. (%s)", fName, _saveFileMan->popErrorDesc().c_str());
    968968                return false;
    969969        }
    970970
     
    988988                playerBuf[cnt2] = inf->readUint32LE();
    989989
    990990        if (inf->ioFailed()) {
    991                 displayMessage(0, "Can't read from file '%s' in directory '%s'", fName, _saveFileMan->getSavePath());
     991                displayMessage(0, "Can't read from file '%s'. (%s)", fName, _saveFileMan->popErrorDesc().c_str());
    992992                delete inf;
    993993                free(_restoreBuf);
    994994                _restoreBuf = NULL;