Return errors from AutoFdEntity::Open (#2296)

Found via pjdfstest which creates a PATH_MAX path that should return
NAMETOOLONG.
This commit is contained in:
Andrew Gaul 2023-08-29 06:57:30 -07:00 committed by GitHub
parent 82107f4b6c
commit 7bb9609827
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
7 changed files with 38 additions and 36 deletions

View File

@ -155,18 +155,13 @@ int FdManager::DeleteCacheFile(const char* path)
}else{
S3FS_PRN_ERR("failed to delete file(%s): errno=%d", path, errno);
}
result = -errno;
return -errno;
}
if(!CacheFileStat::DeleteCacheFileStat(path)){
if(ENOENT == errno){
S3FS_PRN_DBG("failed to delete stat file(%s): errno=%d", path, errno);
if(0 != (result = CacheFileStat::DeleteCacheFileStat(path))){
if(-ENOENT == result){
S3FS_PRN_DBG("failed to delete stat file(%s): errno=%d", path, result);
}else{
S3FS_PRN_ERR("failed to delete stat file(%s): errno=%d", path, errno);
}
if(0 != errno){
result = -errno;
}else{
result = -EIO;
S3FS_PRN_ERR("failed to delete stat file(%s): errno=%d", path, result);
}
}
return result;
@ -595,7 +590,7 @@ FdEntity* FdManager::Open(int& fd, const char* path, const headers_t* pmeta, off
// open
if(0 > (fd = ent->Open(pmeta, size, ts_mctime, flags, type))){
S3FS_PRN_ERR("failed to open and create new pseudo fd for path(%s).", path);
S3FS_PRN_ERR("failed to open and create new pseudo fd for path(%s) errno:%d.", path, fd);
delete ent;
return nullptr;
}

View File

@ -78,11 +78,14 @@ FdEntity* AutoFdEntity::Attach(const char* path, int existfd)
return pFdEntity;
}
FdEntity* AutoFdEntity::Open(const char* path, const headers_t* pmeta, off_t size, const struct timespec& ts_mctime, int flags, bool force_tmpfile, bool is_create, bool ignore_modify, AutoLock::Type type)
FdEntity* AutoFdEntity::Open(const char* path, const headers_t* pmeta, off_t size, const struct timespec& ts_mctime, int flags, bool force_tmpfile, bool is_create, bool ignore_modify, AutoLock::Type type, int* error)
{
Close();
if(nullptr == (pFdEntity = FdManager::get()->Open(pseudo_fd, path, pmeta, size, ts_mctime, flags, force_tmpfile, is_create, ignore_modify, type))){
if(error){
*error = pseudo_fd;
}
pseudo_fd = -1;
return nullptr;
}

View File

@ -55,7 +55,7 @@ class AutoFdEntity
FdEntity* Attach(const char* path, int existfd);
int GetPseudoFd() const { return pseudo_fd; }
FdEntity* Open(const char* path, const headers_t* pmeta, off_t size, const struct timespec& ts_mctime, int flags, bool force_tmpfile, bool is_create, bool ignore_modify, AutoLock::Type type);
FdEntity* Open(const char* path, const headers_t* pmeta, off_t size, const struct timespec& ts_mctime, int flags, bool force_tmpfile, bool is_create, bool ignore_modify, AutoLock::Type type, int* error = nullptr);
FdEntity* GetExistFdEntity(const char* path, int existfd = -1);
FdEntity* OpenExistFdEntity(const char* path, int flags = O_RDONLY);
};

View File

@ -544,12 +544,13 @@ int FdEntity::Open(const headers_t* pmeta, off_t size, const struct timespec& ts
S3FS_PRN_ERR("failed to open file(%s). errno(%d)", cachepath.c_str(), errno);
// remove cache stat file if it is existed
if(!CacheFileStat::DeleteCacheFileStat(path.c_str())){
if(ENOENT != errno){
S3FS_PRN_WARN("failed to delete current cache stat file(%s) by errno(%d), but continue...", path.c_str(), errno);
int result;
if(0 != (result = CacheFileStat::DeleteCacheFileStat(path.c_str()))){
if(-ENOENT != result){
S3FS_PRN_WARN("failed to delete current cache stat file(%s) by errno(%d), but continue...", path.c_str(), result);
}
}
return (0 == errno ? -EIO : -errno);
return result;
}
need_save_csf = true; // need to update page info
inode = FdEntity::GetInode(physical_fd);

View File

@ -48,19 +48,19 @@ std::string CacheFileStat::GetCacheFileStatTopDir()
return top_path;
}
bool CacheFileStat::MakeCacheFileStatPath(const char* path, std::string& sfile_path, bool is_create_dir)
int CacheFileStat::MakeCacheFileStatPath(const char* path, std::string& sfile_path, bool is_create_dir)
{
std::string top_path = CacheFileStat::GetCacheFileStatTopDir();
if(top_path.empty()){
S3FS_PRN_ERR("The path to cache top dir is empty.");
return false;
return -EIO;
}
if(is_create_dir){
int result;
if(0 != (result = mkdirp(top_path + mydirname(path), 0777))){
S3FS_PRN_ERR("failed to create dir(%s) by errno(%d).", path, result);
return false;
return result;
}
}
if(!path || '\0' == path[0]){
@ -68,7 +68,7 @@ bool CacheFileStat::MakeCacheFileStatPath(const char* path, std::string& sfile_p
}else{
sfile_path = top_path + SAFESTRPTR(path);
}
return true;
return 0;
}
bool CacheFileStat::CheckCacheFileStatTopDir()
@ -82,26 +82,28 @@ bool CacheFileStat::CheckCacheFileStatTopDir()
return check_exist_dir_permission(top_path.c_str());
}
bool CacheFileStat::DeleteCacheFileStat(const char* path)
int CacheFileStat::DeleteCacheFileStat(const char* path)
{
if(!path || '\0' == path[0]){
return false;
return -EINVAL;
}
// stat path
std::string sfile_path;
if(!CacheFileStat::MakeCacheFileStatPath(path, sfile_path, false)){
int result;
if(0 != (result = CacheFileStat::MakeCacheFileStatPath(path, sfile_path, false))){
S3FS_PRN_ERR("failed to create cache stat file path(%s)", path);
return false;
return result;
}
if(0 != unlink(sfile_path.c_str())){
if(ENOENT == errno){
S3FS_PRN_DBG("failed to delete file(%s): errno=%d", path, errno);
result = -errno;
if(-ENOENT == result){
S3FS_PRN_DBG("failed to delete file(%s): errno=%d", path, result);
}else{
S3FS_PRN_ERR("failed to delete file(%s): errno=%d", path, errno);
S3FS_PRN_ERR("failed to delete file(%s): errno=%d", path, result);
}
return false;
return result;
}
return true;
return 0;
}
// [NOTE]
@ -127,7 +129,7 @@ bool CacheFileStat::RenameCacheFileStat(const char* oldpath, const char* newpath
// stat path
std::string old_filestat;
std::string new_filestat;
if(!CacheFileStat::MakeCacheFileStatPath(oldpath, old_filestat, false) || !CacheFileStat::MakeCacheFileStatPath(newpath, new_filestat, false)){
if(0 != CacheFileStat::MakeCacheFileStatPath(oldpath, old_filestat, false) || 0 != CacheFileStat::MakeCacheFileStatPath(newpath, new_filestat, false)){
return false;
}
@ -201,7 +203,7 @@ bool CacheFileStat::RawOpen(bool readonly)
}
// stat path
std::string sfile_path;
if(!CacheFileStat::MakeCacheFileStatPath(path.c_str(), sfile_path, true)){
if(0 != CacheFileStat::MakeCacheFileStatPath(path.c_str(), sfile_path, true)){
S3FS_PRN_ERR("failed to create cache stat file path(%s)", path.c_str());
return false;
}

View File

@ -33,13 +33,13 @@ class CacheFileStat
int fd;
private:
static bool MakeCacheFileStatPath(const char* path, std::string& sfile_path, bool is_create_dir = true);
static int MakeCacheFileStatPath(const char* path, std::string& sfile_path, bool is_create_dir = true);
bool RawOpen(bool readonly);
public:
static std::string GetCacheFileStatTopDir();
static bool DeleteCacheFileStat(const char* path);
static int DeleteCacheFileStat(const char* path);
static bool CheckCacheFileStatTopDir();
static bool DeleteCacheFileStatDirectory();
static bool RenameCacheFileStat(const char* oldpath, const char* newpath);

View File

@ -1225,9 +1225,10 @@ static int s3fs_create(const char* _path, mode_t mode, struct fuse_file_info* fi
AutoFdEntity autoent;
FdEntity* ent;
if(nullptr == (ent = autoent.Open(path, &meta, 0, S3FS_OMIT_TS, fi->flags, false, true, false, AutoLock::NONE))){
int error = 0;
if(nullptr == (ent = autoent.Open(path, &meta, 0, S3FS_OMIT_TS, fi->flags, false, true, false, AutoLock::NONE, &error))){
StatCache::getStatCacheData()->DelStat(path);
return -EIO;
return error;
}
ent->MarkDirtyNewFile();
fi->fh = autoent.Detach(); // KEEP fdentity open;