mirror of
https://github.com/apache/nuttx.git
synced 2025-01-13 13:18:50 +08:00
Fix a FAT error when trying to create file in a non-existent directory. Reported by Andrew Tridgell.
git-svn-id: svn://svn.code.sf.net/p/nuttx/code/trunk@5764 42af7a65-404d-4744-a932-0658087f49c3
This commit is contained in:
parent
7f8958d651
commit
d5d9fa89ab
3 changed files with 48 additions and 12 deletions
|
@ -4389,3 +4389,9 @@
|
|||
build different objects in the first and second pass kernel builds need
|
||||
to keep those objects in separate directories so that they are not
|
||||
constantly rebuilt (2013-93-19).
|
||||
* fs/fat: Create an error in FAT file creation. The FAT logic was
|
||||
not making a distinction between directory non-existence and file
|
||||
non-existence so when it you try to create a file in a non-existent
|
||||
directory, it would create a file with the nameof the missing
|
||||
directory. Reported by Andrew Tridgell.
|
||||
|
||||
|
|
|
@ -260,6 +260,12 @@ static int fat_open(FAR struct file *filep, const char *relpath,
|
|||
|
||||
/* fall through to finish the file open operations */
|
||||
}
|
||||
|
||||
/* ENOENT would be returned by fat_finddirentry() if the full
|
||||
* directory path was found, but the file was not found in the
|
||||
* final directory.
|
||||
*/
|
||||
|
||||
else if (ret == -ENOENT)
|
||||
{
|
||||
/* The file does not exist. Were we asked to create it? */
|
||||
|
@ -284,6 +290,9 @@ static int fat_open(FAR struct file *filep, const char *relpath,
|
|||
|
||||
direntry = &fs->fs_buffer[dirinfo.fd_seq.ds_offset];
|
||||
}
|
||||
|
||||
/* No other error is handled */
|
||||
|
||||
else
|
||||
{
|
||||
/* An error occurred while checking for file existence --
|
||||
|
@ -1406,6 +1415,7 @@ static int fat_opendir(struct inode *mountpt, const char *relpath, struct fs_dir
|
|||
{
|
||||
goto errout_with_semaphore;
|
||||
}
|
||||
|
||||
direntry = &fs->fs_buffer[dirinfo.fd_seq.ds_offset];
|
||||
|
||||
/* Check if this is the root directory */
|
||||
|
@ -1942,11 +1952,20 @@ static int fat_mkdir(struct inode *mountpt, const char *relpath, mode_t mode)
|
|||
|
||||
ret = fat_finddirentry(fs, &dirinfo, relpath);
|
||||
|
||||
/* If anything exists at this location, then we fail with EEXIST */
|
||||
/* Or if any error occurs other -ENOENT, then return the error. For
|
||||
* example, if one of the earlier directory path segments was not found
|
||||
* then ENOTDIR will be returned.
|
||||
*/
|
||||
|
||||
if (ret == OK)
|
||||
if (ret != -ENOENT)
|
||||
{
|
||||
ret = -EEXIST;
|
||||
/* If anything exists at this location, then we fail with EEXIST */
|
||||
|
||||
if (ret == OK)
|
||||
{
|
||||
ret = -EEXIST;
|
||||
}
|
||||
|
||||
goto errout_with_semaphore;
|
||||
}
|
||||
|
||||
|
@ -2224,13 +2243,6 @@ int fat_rename(struct inode *mountpt, const char *oldrelpath,
|
|||
/* Now find the directory where we should create the newpath object */
|
||||
|
||||
ret = fat_finddirentry(fs, &dirinfo, newrelpath);
|
||||
if (ret == OK)
|
||||
{
|
||||
/* It is an error if the object at newrelpath already exists */
|
||||
|
||||
ret = -EEXIST;
|
||||
goto errout_with_semaphore;
|
||||
}
|
||||
|
||||
/* What we expect is -ENOENT mean that the full directory path was
|
||||
* followed but that the object does not exists in the terminal directory.
|
||||
|
@ -2238,6 +2250,13 @@ int fat_rename(struct inode *mountpt, const char *oldrelpath,
|
|||
|
||||
if (ret != -ENOENT)
|
||||
{
|
||||
if (ret == OK)
|
||||
{
|
||||
/* It is an error if the object at newrelpath already exists */
|
||||
|
||||
ret = -EEXIST;
|
||||
}
|
||||
|
||||
goto errout_with_semaphore;
|
||||
}
|
||||
|
||||
|
|
|
@ -2343,6 +2343,17 @@ int fat_finddirentry(struct fat_mountpt_s *fs, struct fat_dirinfo_s *dirinfo,
|
|||
|
||||
if (ret < 0)
|
||||
{
|
||||
/* A return value of -ENOENT would mean that the path segement
|
||||
* was not found. Let's distinguish to cases: (1) the final
|
||||
* file was not found in the directory (-ENOENT), or (2) one
|
||||
* of the directory path segments does not exist (-ENOTDIR)
|
||||
*/
|
||||
|
||||
if (ret == -ENOENT && terminator != '\0')
|
||||
{
|
||||
return -ENOTDIR;
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
@ -2351,7 +2362,7 @@ int fat_finddirentry(struct fat_mountpt_s *fs, struct fat_dirinfo_s *dirinfo,
|
|||
* the path.
|
||||
*/
|
||||
|
||||
if (!terminator)
|
||||
if (terminator == '\0')
|
||||
{
|
||||
/* Return success meaning that the description the matching
|
||||
* directory entry is in dirinfo.
|
||||
|
@ -2795,7 +2806,7 @@ int fat_remove(struct fat_mountpt_s *fs, const char *relpath, bool directory)
|
|||
ret = fat_finddirentry(fs, &dirinfo, relpath);
|
||||
if (ret != OK)
|
||||
{
|
||||
/* No such path */
|
||||
/* Most likely, some element of the path does not exist. */
|
||||
|
||||
return -ENOENT;
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue