Use std::shared_ptr to refer to FdEntity (#2541)
FdEntity may have multiple references due to ChangeEntityToTempPath. This relies on the std::enable_shared_from_this helper to create a std::shared_ptr from this. Fixes #2532.
This commit is contained in:
@ -587,7 +587,7 @@ FdEntity* FdManager::Open(int& fd, const char* path, const headers_t* pmeta, off
|
||||
return nullptr;
|
||||
}
|
||||
// make new obj
|
||||
std::unique_ptr<FdEntity> ent(new FdEntity(path, cache_path.c_str()));
|
||||
auto ent = std::make_shared<FdEntity>(path, cache_path.c_str());
|
||||
|
||||
// open
|
||||
if(0 > (fd = ent->Open(pmeta, size, ts_mctime, flags))){
|
||||
@ -696,7 +696,7 @@ void FdManager::Rename(const std::string &from, const std::string &to)
|
||||
// found
|
||||
S3FS_PRN_DBG("[from=%s][to=%s]", from.c_str(), to.c_str());
|
||||
|
||||
std::unique_ptr<FdEntity> ent(std::move(iter->second));
|
||||
auto ent(std::move(iter->second));
|
||||
|
||||
// retrieve old fd entity from map
|
||||
fent.erase(iter);
|
||||
@ -746,10 +746,10 @@ bool FdManager::Close(FdEntity* ent, int fd)
|
||||
return false;
|
||||
}
|
||||
|
||||
bool FdManager::ChangeEntityToTempPath(FdEntity* ent, const char* path)
|
||||
bool FdManager::ChangeEntityToTempPath(std::shared_ptr<FdEntity> ent, const char* path)
|
||||
{
|
||||
const std::lock_guard<std::mutex> lock(FdManager::except_entmap_lock);
|
||||
except_fent[path] = ent;
|
||||
except_fent[path] = std::move(ent);
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -762,7 +762,7 @@ bool FdManager::UpdateEntityToTempPath()
|
||||
FdManager::MakeRandomTempPath(except_iter->first.c_str(), tmppath);
|
||||
|
||||
auto iter = fent.find(except_iter->first);
|
||||
if(fent.cend() != iter && iter->second.get() == except_iter->second){
|
||||
if(fent.cend() != iter && iter->second.get() == except_iter->second.get()){
|
||||
// Move the entry to the new key
|
||||
fent[tmppath] = std::move(iter->second);
|
||||
fent.erase(iter);
|
||||
@ -778,7 +778,7 @@ bool FdManager::UpdateEntityToTempPath()
|
||||
S3FS_PRN_WARN("For some reason the FdEntity pointer(for %s) is not found in the fent map. Recovery procedures are being performed, but the cause needs to be identified.", except_iter->first.c_str());
|
||||
|
||||
// Add the entry for recovery procedures
|
||||
fent[tmppath] = std::unique_ptr<FdEntity>(except_iter->second);
|
||||
fent[tmppath] = except_iter->second;
|
||||
except_iter = except_fent.erase(except_iter);
|
||||
}
|
||||
}
|
||||
|
||||
@ -48,7 +48,7 @@ class FdManager
|
||||
static std::string tmp_dir;
|
||||
|
||||
fdent_map_t fent GUARDED_BY(fd_manager_lock);
|
||||
fdent_direct_map_t except_fent GUARDED_BY(except_entmap_lock); // A map of delayed deletion fdentity
|
||||
fdent_map_t except_fent GUARDED_BY(except_entmap_lock); // A map of delayed deletion fdentity
|
||||
|
||||
private:
|
||||
static off_t GetFreeDiskSpaceHasLock(const char* path) REQUIRES(FdManager::reserved_diskspace_lock);
|
||||
@ -115,7 +115,7 @@ class FdManager
|
||||
FdEntity* OpenExistFdEntity(const char* path, int& fd, int flags = O_RDONLY);
|
||||
void Rename(const std::string &from, const std::string &to);
|
||||
bool Close(FdEntity* ent, int fd);
|
||||
bool ChangeEntityToTempPath(FdEntity* ent, const char* path);
|
||||
bool ChangeEntityToTempPath(std::shared_ptr<FdEntity> ent, const char* path);
|
||||
void CleanupCacheDir();
|
||||
|
||||
bool CheckAllCache();
|
||||
|
||||
@ -1086,7 +1086,7 @@ int FdEntity::NoCacheLoadAndPost(PseudoFdInfo* pseudo_obj, off_t start, off_t si
|
||||
}
|
||||
|
||||
// Change entity key in manager mapping
|
||||
FdManager::get()->ChangeEntityToTempPath(this, path.c_str());
|
||||
FdManager::get()->ChangeEntityToTempPath(get_shared_ptr(), path.c_str());
|
||||
|
||||
// open temporary file
|
||||
int tmpfd;
|
||||
|
||||
@ -41,7 +41,7 @@ typedef std::map<int, std::unique_ptr<PseudoFdInfo>> fdinfo_map_t;
|
||||
//------------------------------------------------
|
||||
// class FdEntity
|
||||
//------------------------------------------------
|
||||
class FdEntity
|
||||
class FdEntity : public std::enable_shared_from_this<FdEntity>
|
||||
{
|
||||
private:
|
||||
// [NOTE]
|
||||
@ -109,6 +109,8 @@ class FdEntity
|
||||
|
||||
bool IsDirtyMetadata() const REQUIRES(FdEntity::fdent_data_lock);
|
||||
|
||||
std::shared_ptr<FdEntity> get_shared_ptr() { return shared_from_this(); }
|
||||
|
||||
public:
|
||||
static bool GetNoMixMultipart() { return mixmultipart; }
|
||||
static bool SetNoMixMultipart();
|
||||
@ -235,8 +237,7 @@ class FdEntity
|
||||
std::mutex* GetMutex() RETURN_CAPABILITY(fdent_lock);
|
||||
};
|
||||
|
||||
typedef std::map<std::string, std::unique_ptr<FdEntity>> fdent_map_t; // key=path, value=unique_ptr<FdEntity>
|
||||
typedef std::map<std::string, FdEntity*> fdent_direct_map_t; // key=path, value=FdEntity*
|
||||
typedef std::map<std::string, std::shared_ptr<FdEntity>> fdent_map_t; // key=path, value=FdEntity
|
||||
|
||||
#endif // S3FS_FDCACHE_ENTITY_H_
|
||||
|
||||
|
||||
Reference in New Issue
Block a user