mirror of
https://github.com/Rockbox/rockbox.git
synced 2025-10-14 10:37:38 -04:00
Bug fix: renaming a directory could cause a name clash. New feature: rename() can now move files/directories as well.
git-svn-id: svn://svn.rockbox.org/rockbox/trunk@5008 a1c6a512-1295-4272-9138-f99709370657
This commit is contained in:
parent
1a6a4812aa
commit
e0e0140f4e
3 changed files with 44 additions and 12 deletions
|
@ -277,12 +277,16 @@ int remove(const char* name)
|
||||||
int rename(const char* path, const char* newpath)
|
int rename(const char* path, const char* newpath)
|
||||||
{
|
{
|
||||||
int rc, fd;
|
int rc, fd;
|
||||||
|
DIR* dir;
|
||||||
char* nameptr;
|
char* nameptr;
|
||||||
|
char* dirptr;
|
||||||
struct filedesc* file;
|
struct filedesc* file;
|
||||||
|
char newpath2[MAX_PATH];
|
||||||
|
|
||||||
/* verify new path does not already exist */
|
/* verify new path does not already exist */
|
||||||
|
/* If it is a directory, errno == EISDIR if the name exists */
|
||||||
fd = open(newpath, O_RDONLY);
|
fd = open(newpath, O_RDONLY);
|
||||||
if ( fd >= 0 ) {
|
if ( fd >= 0 || errno == EISDIR) {
|
||||||
close(fd);
|
close(fd);
|
||||||
errno = EBUSY;
|
errno = EBUSY;
|
||||||
return -1;
|
return -1;
|
||||||
|
@ -295,25 +299,51 @@ int rename(const char* path, const char* newpath)
|
||||||
return fd * 10 - 2;
|
return fd * 10 - 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* strip path */
|
/* extract new file name */
|
||||||
nameptr = strrchr(newpath,'/');
|
nameptr = strrchr(newpath,'/');
|
||||||
if (nameptr)
|
if (nameptr)
|
||||||
nameptr++;
|
nameptr++;
|
||||||
else
|
else
|
||||||
nameptr = (char*)newpath;
|
return - 3;
|
||||||
|
|
||||||
|
/* Extract new path */
|
||||||
|
strcpy(newpath2, newpath);
|
||||||
|
|
||||||
|
dirptr = strrchr(newpath2,'/');
|
||||||
|
if(dirptr)
|
||||||
|
*dirptr = 0;
|
||||||
|
else
|
||||||
|
return - 4;
|
||||||
|
|
||||||
|
dirptr = newpath2;
|
||||||
|
|
||||||
|
if(strlen(dirptr) == 0) {
|
||||||
|
dirptr = "/";
|
||||||
|
}
|
||||||
|
|
||||||
|
dir = opendir(dirptr);
|
||||||
|
if(!dir)
|
||||||
|
return - 5;
|
||||||
|
|
||||||
file = &openfiles[fd];
|
file = &openfiles[fd];
|
||||||
rc = fat_rename(&file->fatfile, nameptr, file->size, file->attr);
|
rc = fat_rename(&file->fatfile, &dir->fatdir, nameptr,
|
||||||
|
file->size, file->attr);
|
||||||
if ( rc < 0 ) {
|
if ( rc < 0 ) {
|
||||||
DEBUGF("Failed renaming file: %d\n", rc);
|
DEBUGF("Failed renaming file: %d\n", rc);
|
||||||
errno = EIO;
|
errno = EIO;
|
||||||
return rc * 10 - 3;
|
return rc * 10 - 6;
|
||||||
}
|
}
|
||||||
|
|
||||||
rc = close(fd);
|
rc = close(fd);
|
||||||
if (rc<0) {
|
if (rc<0) {
|
||||||
errno = EIO;
|
errno = EIO;
|
||||||
return rc * 10 - 4;
|
return rc * 10 - 7;
|
||||||
|
}
|
||||||
|
|
||||||
|
rc = closedir(dir);
|
||||||
|
if (rc<0) {
|
||||||
|
errno = EIO;
|
||||||
|
return rc * 10 - 8;
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|
|
@ -1551,12 +1551,13 @@ int fat_remove(struct fat_file* file)
|
||||||
}
|
}
|
||||||
|
|
||||||
int fat_rename(struct fat_file* file,
|
int fat_rename(struct fat_file* file,
|
||||||
const unsigned char* newname,
|
struct fat_dir* dir,
|
||||||
int size,
|
const unsigned char* newname,
|
||||||
int attr)
|
int size,
|
||||||
|
int attr)
|
||||||
{
|
{
|
||||||
int rc;
|
int rc;
|
||||||
struct fat_dir dir;
|
struct fat_dir olddir;
|
||||||
struct fat_file newfile = *file;
|
struct fat_file newfile = *file;
|
||||||
|
|
||||||
if ( !file->dircluster ) {
|
if ( !file->dircluster ) {
|
||||||
|
@ -1565,12 +1566,12 @@ int fat_rename(struct fat_file* file,
|
||||||
}
|
}
|
||||||
|
|
||||||
/* create a temporary file handle */
|
/* create a temporary file handle */
|
||||||
rc = fat_opendir(&dir, file->dircluster, NULL);
|
rc = fat_opendir(&olddir, file->dircluster, NULL);
|
||||||
if (rc < 0)
|
if (rc < 0)
|
||||||
return rc * 10 - 2;
|
return rc * 10 - 2;
|
||||||
|
|
||||||
/* create new name */
|
/* create new name */
|
||||||
rc = add_dir_entry(&dir, &newfile, newname, false, false);
|
rc = add_dir_entry(dir, &newfile, newname, false, false);
|
||||||
if (rc < 0)
|
if (rc < 0)
|
||||||
return rc * 10 - 3;
|
return rc * 10 - 3;
|
||||||
|
|
||||||
|
|
|
@ -89,6 +89,7 @@ extern int fat_seek(struct fat_file *ent, unsigned int sector );
|
||||||
extern int fat_remove(struct fat_file *ent);
|
extern int fat_remove(struct fat_file *ent);
|
||||||
extern int fat_truncate(const struct fat_file *ent);
|
extern int fat_truncate(const struct fat_file *ent);
|
||||||
extern int fat_rename(struct fat_file* file,
|
extern int fat_rename(struct fat_file* file,
|
||||||
|
struct fat_dir* dir,
|
||||||
const unsigned char* newname,
|
const unsigned char* newname,
|
||||||
int size, int attr);
|
int size, int attr);
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue