diff --git a/BasiliskII/src/AmigaOS/extfs_amiga.cpp b/BasiliskII/src/AmigaOS/extfs_amiga.cpp index 2d6aaf68..2e680bb9 100644 --- a/BasiliskII/src/AmigaOS/extfs_amiga.cpp +++ b/BasiliskII/src/AmigaOS/extfs_amiga.cpp @@ -379,17 +379,48 @@ bool extfs_remove(const char *path) make_helper_path(path, helper_path, ".rsrc/", false); remove(helper_path); - // Now remove file or directory + // Now remove file or directory (and helper directories in the directory) if (remove(path) < 0) { - if (errno == EISDIR) + if (errno == EISDIR || errno == ENOTEMPTY) { + helper_path[0] = 0; + strncpy(helper_path, path, MAX_PATH_LENGTH-1); + add_path_component(helper_path, ".finf"); + rmdir(helper_path); + helper_path[0] = 0; + strncpy(helper_path, path, MAX_PATH_LENGTH-1); + add_path_component(helper_path, ".rsrc"); + rmdir(helper_path); return rmdir(path) == 0; - else + } else return false; } return true; } +/* + * Rename/move file/directory (and associated helper files), + * returns false on error (and sets errno) + */ + +bool extfs_rename(const char *old_path, const char *new_path) +{ + // Rename helpers first, don't complain if this fails + char old_helper_path[MAX_PATH_LENGTH], new_helper_path[MAX_PATH_LENGTH]; + make_helper_path(old_path, old_helper_path, ".finf/", false); + make_helper_path(new_path, new_helper_path, ".finf/", false); + create_helper_dir(new_path, ".finf/"); + rename(old_helper_path, new_helper_path); + make_helper_path(old_path, old_helper_path, ".rsrc/", false); + make_helper_path(new_path, new_helper_path, ".rsrc/", false); + create_helper_dir(new_path, ".rsrc/"); + rename(old_helper_path, new_helper_path); + + // Now rename file + return rename(old_path, new_path) == 0; +} + + /* * ftruncate() is missing from libnix */ diff --git a/BasiliskII/src/BeOS/extfs_beos.cpp b/BasiliskII/src/BeOS/extfs_beos.cpp index 606e0657..2f4e76e1 100644 --- a/BasiliskII/src/BeOS/extfs_beos.cpp +++ b/BasiliskII/src/BeOS/extfs_beos.cpp @@ -471,3 +471,13 @@ bool extfs_remove(const char *path) } return true; } + + +/* + * Rename/move file/directory, returns false on error (and sets errno) + */ + +bool extfs_rename(const char *old_path, const char *new_path) +{ + return rename(old_path, new_path) == 0; +} diff --git a/BasiliskII/src/Unix/extfs_unix.cpp b/BasiliskII/src/Unix/extfs_unix.cpp index de926553..d5763aea 100644 --- a/BasiliskII/src/Unix/extfs_unix.cpp +++ b/BasiliskII/src/Unix/extfs_unix.cpp @@ -384,12 +384,43 @@ bool extfs_remove(const char *path) make_helper_path(path, helper_path, ".rsrc/", false); remove(helper_path); - // Now remove file or directory + // Now remove file or directory (and helper directories in the directory) if (remove(path) < 0) { - if (errno == EISDIR) + if (errno == EISDIR || errno == ENOTEMPTY) { + helper_path[0] = 0; + strncpy(helper_path, path, MAX_PATH_LENGTH-1); + add_path_component(helper_path, ".finf"); + rmdir(helper_path); + helper_path[0] = 0; + strncpy(helper_path, path, MAX_PATH_LENGTH-1); + add_path_component(helper_path, ".rsrc"); + rmdir(helper_path); return rmdir(path) == 0; - else + } else return false; } return true; } + + +/* + * Rename/move file/directory (and associated helper files), + * returns false on error (and sets errno) + */ + +bool extfs_rename(const char *old_path, const char *new_path) +{ + // Rename helpers first, don't complain if this fails + char old_helper_path[MAX_PATH_LENGTH], new_helper_path[MAX_PATH_LENGTH]; + make_helper_path(old_path, old_helper_path, ".finf/", false); + make_helper_path(new_path, new_helper_path, ".finf/", false); + create_helper_dir(new_path, ".finf/"); + rename(old_helper_path, new_helper_path); + make_helper_path(old_path, old_helper_path, ".rsrc/", false); + make_helper_path(new_path, new_helper_path, ".rsrc/", false); + create_helper_dir(new_path, ".rsrc/"); + rename(old_helper_path, new_helper_path); + + // Now rename file + return rename(old_path, new_path) == 0; +} diff --git a/BasiliskII/src/extfs.cpp b/BasiliskII/src/extfs.cpp index c01c84fa..42daed02 100644 --- a/BasiliskII/src/extfs.cpp +++ b/BasiliskII/src/extfs.cpp @@ -1933,7 +1933,7 @@ static int16 fs_rename(uint32 pb, uint32 dirID) // Rename item D(bug(" renaming %s -> %s\n", old_path, full_path)); - if (rename(old_path, full_path) < 0) + if (!extfs_rename(old_path, full_path)) return errno2oserr(); else { // The ID of the old file/dir has to stay the same, so we swap the IDs of the FSItems @@ -1976,7 +1976,7 @@ static int16 fs_cat_move(uint32 pb) // Move item D(bug(" moving %s -> %s\n", old_path, full_path)); - if (rename(old_path, full_path) < 0) + if (!extfs_rename(old_path, full_path)) return errno2oserr(); else { // The ID of the old file/dir has to stay the same, so we swap the IDs of the FSItems diff --git a/BasiliskII/src/include/extfs.h b/BasiliskII/src/include/extfs.h index 897ec06b..46abc2b4 100644 --- a/BasiliskII/src/include/extfs.h +++ b/BasiliskII/src/include/extfs.h @@ -43,6 +43,7 @@ extern void close_rfork(const char *path, int fd); extern size_t extfs_read(int fd, void *buffer, size_t length); extern size_t extfs_write(int fd, void *buffer, size_t length); extern bool extfs_remove(const char *path); +extern bool extfs_rename(const char *old_path, const char *new_path); // Maximum length of full path name const int MAX_PATH_LENGTH = 1024;