]> git-server-git.apps.pok.os.sepia.ceph.com Git - ceph.git/commitdiff
rgw/d4n: handling special characters in object names such that
authorPritha Srivastava <prsrivas@redhat.com>
Thu, 5 Sep 2024 06:31:11 +0000 (12:01 +0530)
committerPritha Srivastava <prsrivas@redhat.com>
Mon, 21 Apr 2025 04:04:07 +0000 (09:34 +0530)
parsing file names while restoring data from cache does not result
in errors.

1. Introduce a new delimiter # instead of _ for concatening bucket_id,
objectname etc to create a key, because "_" is a valid char in object names
and is not encoded and results in incorrect values while parsing filenames
for restorin data.
2. url encode the bucket id, version and object name before all are concatenated
to form a key
3. url_decode the bucket id, version and object name after parsing the filename
from cache while restoring data back.

Signed-off-by: Pritha Srivastava <prsrivas@redhat.com>
src/rgw/driver/d4n/d4n_policy.cc
src/rgw/driver/d4n/rgw_sal_d4n.cc
src/rgw/driver/d4n/rgw_sal_d4n.h
src/rgw/rgw_cache_driver.h
src/rgw/rgw_ssd_driver.cc

index 0f5edc2bfb0c95002fba7ac702ca002507492ae9..4fd195e398f3f1c6c6d325a7be601e660179ab25 100644 (file)
@@ -369,7 +369,7 @@ void LFUDAPolicy::update(const DoutPrefixProvider* dpp, const std::string& key,
 
   std::string oid_in_cache = key;
   if (dirty == true) {
-    oid_in_cache = "D_" + key;
+    oid_in_cache = DIRTY_BLOCK_PREFIX + key;
   }
 
   if (!restore_val.empty()) {
@@ -513,13 +513,13 @@ void LFUDAPolicy::cleaning(const DoutPrefixProvider* dpp)
         erase_dirty_object(dpp, e->key, null_yield);
       }
 
-      std::string prefix = e->bucket_id + "_" + e->version + "_" + c_obj->get_name();
+      std::string prefix = url_encode(e->bucket_id) + CACHE_DELIM + url_encode(e->version) + CACHE_DELIM + url_encode(c_obj->get_name());
       off_t lst = e->size;
       off_t fst = 0;
       off_t ofs = 0;
 
       rgw::sal::DataProcessor* filter = processor.get();
-      std::string head_oid_in_cache = "D_" + prefix;
+      std::string head_oid_in_cache = DIRTY_BLOCK_PREFIX + prefix;
       std::string new_head_oid_in_cache = prefix;
       ldpp_dout(dpp, 10) << __func__ << "(): head_oid_in_cache=" << head_oid_in_cache << dendl;
       ldpp_dout(dpp, 10) << __func__ << "(): new_head_oid_in_cache=" << new_head_oid_in_cache << dendl;
@@ -537,7 +537,7 @@ void LFUDAPolicy::cleaning(const DoutPrefixProvider* dpp)
         }
         off_t cur_size = std::min<off_t>(fst + dpp->get_cct()->_conf->rgw_max_chunk_size, lst);
         off_t cur_len = cur_size - fst;
-        std::string oid_in_cache = "D_" + prefix + "_" + std::to_string(fst) + "_" + std::to_string(cur_len);
+        std::string oid_in_cache = DIRTY_BLOCK_PREFIX + prefix + CACHE_DELIM + std::to_string(fst) + CACHE_DELIM + std::to_string(cur_len);
         ldpp_dout(dpp, 10) << __func__ << "(): oid_in_cache=" << oid_in_cache << dendl;
         rgw::sal::Attrs attrs;
         cacheDriver->get(dpp, oid_in_cache, 0, cur_len, data, attrs, null_yield);
@@ -583,9 +583,9 @@ void LFUDAPolicy::cleaning(const DoutPrefixProvider* dpp)
         off_t cur_size = std::min<off_t>(fst + dpp->get_cct()->_conf->rgw_max_chunk_size, lst);
         off_t cur_len = cur_size - fst;
 
-        std::string oid_in_cache = "D_" + prefix + "_" + std::to_string(fst) + "_" + std::to_string(cur_len);
+        std::string oid_in_cache = DIRTY_BLOCK_PREFIX + prefix + CACHE_DELIM + std::to_string(fst) + CACHE_DELIM + std::to_string(cur_len);
         ldpp_dout(dpp, 20) << __func__ << "(): oid_in_cache =" << oid_in_cache << dendl;
-        std::string new_oid_in_cache = prefix + "_" + std::to_string(fst) + "_" + std::to_string(cur_len);
+        std::string new_oid_in_cache = prefix + CACHE_DELIM + std::to_string(fst) + CACHE_DELIM + std::to_string(cur_len);
         //Rename block to remove "D" prefix
         cacheDriver->rename(dpp, oid_in_cache, new_oid_in_cache, null_yield);
         //Update in-memory data structure for each block
index 28ea81972f12b8e1569ec5732c9213bac508e78a..b04e9ae4a02c88363ec5bb2dde815f83242a34d9 100644 (file)
@@ -286,7 +286,7 @@ int D4NFilterObject::copy_object(const ACLOwner& owner,
   std::string key = get_cache_block_prefix(dest_object, dest_version, false);
   std::string head_oid_in_cache;
   if (dirty) {
-    head_oid_in_cache = std::format("{}{}","D_", key); //same as key, as there is no len or offset attached to head oid in cache
+    head_oid_in_cache = std::format("{}{}",DIRTY_BLOCK_PREFIX, key); //same as key, as there is no len or offset attached to head oid in cache
   } else {
     head_oid_in_cache = key;
   }
@@ -311,8 +311,7 @@ int D4NFilterObject::copy_object(const ACLOwner& owner,
         return ret;
       }
       if (dirty) {
-        std::string object_key = dest_object->get_bucket()->get_bucket_id() + "_" + dest_object->get_oid();
-        driver->get_policy_driver()->get_cache_policy()->update_dirty_object(dpp, object_key, dest_version, true, this->get_size(), creationTime, std::get<rgw_user>(dest_object->get_bucket()->get_owner()), *etag, dest_object->get_bucket()->get_name(), dest_object->get_bucket()->get_bucket_id(), dest_object->get_key(), y);
+        driver->get_policy_driver()->get_cache_policy()->update_dirty_object(dpp, key, dest_version, true, this->get_size(), creationTime, std::get<rgw_user>(dest_object->get_bucket()->get_owner()), *etag, dest_object->get_bucket()->get_name(), dest_object->get_bucket()->get_bucket_id(), dest_object->get_key(), y);
       }
     }
   }
@@ -681,7 +680,7 @@ int D4NFilterObject::delete_data_block_cache_entries(const DoutPrefixProvider* d
     std::string key =  get_key_in_cache(get_cache_block_prefix(this, version, false), std::to_string(fst), std::to_string(cur_len));
     std::string key_in_cache;
     if (dirty) {
-      key_in_cache = std::format("{}{}","D_", key);
+      key_in_cache = std::format("{}{}",DIRTY_BLOCK_PREFIX, key);
     } else {
       key_in_cache = key;
     }
@@ -1154,9 +1153,8 @@ int D4NFilterObject::D4NFilterReadOp::flush(const DoutPrefixProvider* dpp, rgw::
         dest_block.cacheObj.hostsList.insert(dpp->get_cct()->_conf->rgw_d4n_l1_datacache_address);
         dest_block.version = dest_version;
         dest_block.cacheObj.dirty = true;
-        std::string prefix = get_cache_block_prefix(source->dest_object, dest_version, false);
         std::string key =  get_key_in_cache(get_cache_block_prefix(source->dest_object, dest_version, false), std::to_string(ofs), std::to_string(len));
-        std::string dest_oid_in_cache = std::format("{}{}","D_", key);
+        std::string dest_oid_in_cache = std::format("{}{}",DIRTY_BLOCK_PREFIX, key);
         auto ret = source->driver->get_policy_driver()->get_cache_policy()->eviction(dpp, dest_block.size, y);
         if (ret == 0) {
           rgw::sal::Attrs attrs;
@@ -1266,7 +1264,7 @@ int D4NFilterObject::D4NFilterReadOp::iterate(const DoutPrefixProvider* dpp, int
           ldpp_dout(dpp, 20) << "D4NFilterObject::iterate:: " << __func__ << "(): READ FROM CACHE: block is dirty = " << block.cacheObj.dirty << dendl;
 
           if (block.cacheObj.dirty == true) {
-            key = "D_" + oid_in_cache; // we keep track of dirty data in the cache for the metadata failure case
+            key = DIRTY_BLOCK_PREFIX + oid_in_cache; // we keep track of dirty data in the cache for the metadata failure case
             ldpp_dout(dpp, 20) << "D4NFilterObject::iterate:: " << __func__ << "(): READ FROM CACHE: key=" << key << " data is Dirty." << dendl;
           }
 
@@ -1359,7 +1357,7 @@ int D4NFilterObject::D4NFilterReadOp::iterate(const DoutPrefixProvider* dpp, int
         if ((part_len != chunk_size) && source->driver->get_policy_driver()->get_cache_policy()->exist_key(oid_in_cache) > 0) {
           // Read From Cache
           if (block.cacheObj.dirty == true){
-      key = "D_" + oid_in_cache; //we keep track of dirty data in the cache for the metadata failure case
+      key = DIRTY_BLOCK_PREFIX + oid_in_cache;
           }
 
           ldpp_dout(dpp, 20) << "D4NFilterObject::iterate:: " << __func__  << "(): " << __LINE__ << ": READ FROM CACHE: block dirty =" << block.cacheObj.dirty << dendl;
@@ -1748,7 +1746,7 @@ int D4NFilterObject::D4NFilterReadOp::D4NFilterGetCB::handle_data(bufferlist& bl
       bl_rem.claim_append(bl_copy);
 
       if (bl_rem.length() == rgw_max_chunk_size) {
-        std::string oid = get_key_in_cache(prefix, std::to_string(adjusted_start_ofs), std::to_string(bl_rem.length()));
+        std::string oid = prefix + CACHE_DELIM + std::to_string(adjusted_start_ofs) + CACHE_DELIM + std::to_string(bl_rem.length());
           if (!filter->get_policy_driver()->get_cache_policy()->exist_key(oid)) {
           block.blockID = adjusted_start_ofs;
           block.size = bl_rem.length();
@@ -1787,7 +1785,7 @@ int D4NFilterObject::D4NFilterReadOp::D4NFilterGetCB::handle_data(bufferlist& bl
         if (source->dest_object && source->dest_bucket) {
           D4NFilterObject* d4n_dest_object = dynamic_cast<D4NFilterObject*>(source->dest_object);
           std::string dest_version = d4n_dest_object->get_object_version();
-          std::string dest_oid = get_key_in_cache(dest_prefix, std::to_string(adjusted_start_ofs), std::to_string(bl_rem.length()));
+          std::string dest_oid = dest_prefix + CACHE_DELIM + std::to_string(adjusted_start_ofs) + CACHE_DELIM + std::to_string(bl_rem.length());
           dest_block.blockID = adjusted_start_ofs;
           dest_block.size = bl_rem.length();
           auto ret = filter->get_policy_driver()->get_cache_policy()->eviction(dpp, dest_block.size, *y);
@@ -1967,7 +1965,7 @@ int D4NFilterObject::D4NFilterDeleteOp::delete_obj(const DoutPrefixProvider* dpp
        }
 
        if (block.cacheObj.dirty)
-         prefix = "D_" + prefix;
+         prefix = DIRTY_BLOCK_PREFIX + prefix;
 
        std::string oid_in_cache = get_key_in_cache(prefix, std::to_string(fst), std::to_string(cur_len));
 
@@ -1994,8 +1992,8 @@ int D4NFilterObject::D4NFilterDeleteOp::delete_obj(const DoutPrefixProvider* dpp
       if (!objDirty) { // object written to backend  
        return next->delete_obj(dpp, y, flags);
       } else {
-        std::string object_key = source->get_bucket()->get_bucket_id() + "_" + source->get_oid();
-       if (!(ret = source->driver->get_policy_driver()->get_cache_policy()->erase_dirty_object(dpp, object_key, y))) {
+        std::string key = policy_prefix;
+       if (!(ret = source->driver->get_policy_driver()->get_cache_policy()->erase_dirty_object(dpp, key, y))) {
          ldpp_dout(dpp, 0) << "Failed to delete policy object entry for: " << source->get_name() << ", ret=" << ret << dendl;
          return -ENOENT;
         } else {
@@ -2087,9 +2085,9 @@ int D4NFilterWriter::process(bufferlist&& data, uint64_t offset)
       return next->process(std::move(data), offset);
     } else {
       rgw::sal::Attrs attrs;
-      std::string oid = prefix + "_" + std::to_string(ofs);
-      std::string key = "D_" + oid + "_" + std::to_string(bl_len);
-      std::string oid_in_cache = oid + "_" + std::to_string(bl_len);
+      std::string oid = prefix + CACHE_DELIM + std::to_string(ofs);
+      std::string key = DIRTY_BLOCK_PREFIX + oid + CACHE_DELIM + std::to_string(bl_len);
+      std::string oid_in_cache = oid + CACHE_DELIM + std::to_string(bl_len);
       dirty = true;
       ret = driver->get_policy_driver()->get_cache_policy()->eviction(dpp, bl.length(), y);
       if (ret == 0) {     
@@ -2234,7 +2232,7 @@ int D4NFilterWriter::complete(size_t accounted_size, const std::string& etag,
   std::string head_oid_in_cache;
   //same as key, as there is no len or offset attached to head oid in cache
   if (dirty) {
-    head_oid_in_cache = std::format("{}{}","D_", key);;
+    head_oid_in_cache = std::format("{}{}",DIRTY_BLOCK_PREFIX, key);;
   } else {
     head_oid_in_cache = key;
   }
@@ -2259,11 +2257,9 @@ int D4NFilterWriter::complete(size_t accounted_size, const std::string& etag,
         return ret;
       }
       if (dirty) {
-        //using object oid here so that version is automatically picked for versioned buckets, and for non-versioned buckets the old version is replaced by the latest version
-        std::string object_key = obj->get_bucket()->get_bucket_id() + "_" + obj->get_oid();
         auto creationTime = ceph::real_clock::to_time_t(object->get_mtime());
-        ldpp_dout(dpp, 16) << "D4NFilterWriter::" << __func__ << "(): object_key=" << object_key << dendl;
-        driver->get_policy_driver()->get_cache_policy()->update_dirty_object(dpp, object_key, version, dirty, accounted_size, creationTime, std::get<rgw_user>(obj->get_bucket()->get_owner()), objEtag, obj->get_bucket()->get_name(), obj->get_bucket()->get_bucket_id(), obj->get_key(), y);
+        ldpp_dout(dpp, 16) << "D4NFilterWriter::" << __func__ << "(): key=" << key << dendl;
+        driver->get_policy_driver()->get_cache_policy()->update_dirty_object(dpp, key, version, dirty, accounted_size, creationTime, std::get<rgw_user>(obj->get_bucket()->get_owner()), objEtag, obj->get_bucket()->get_name(), obj->get_bucket()->get_bucket_id(), obj->get_key(), y);
       }
     } else { //if get_cache_driver()->put()
       ldpp_dout(dpp, 0) << "D4NFilterWriter::" << __func__ << "(): put failed for head_oid_in_cache, ret=" << ret << dendl;
index 48e364a66acde124bd84d3c7ba68c83568bf1da7..005b43331044d1202421b2e310c1456f31078dcd 100644 (file)
@@ -42,17 +42,15 @@ namespace rgw { namespace sal {
 inline std::string get_cache_block_prefix(rgw::sal::Object* object, const std::string& version, bool is_dirty)
 {
   if (is_dirty) {
-    //return "D_" + object->get_bucket()->get_bucket_id() + "_" + version + "_" + object->get_name();
-    return fmt::format("{}{}{}{}{}{}", "D_", object->get_bucket()->get_bucket_id(), "_", version, "_", object->get_name());
+    return fmt::format("{}{}{}{}{}{}", DIRTY_BLOCK_PREFIX, object->get_bucket()->get_bucket_id(), CACHE_DELIM, version, CACHE_DELIM, object->get_name());
   } else {
-    //return object->get_bucket()->get_bucket_id() + "_" + version + "_" + object->get_name();
-    return fmt::format("{}{}{}{}{}", object->get_bucket()->get_bucket_id(), "_", version, "_", object->get_name());
+    return fmt::format("{}{}{}{}{}", object->get_bucket()->get_bucket_id(), CACHE_DELIM, version, CACHE_DELIM, object->get_name());
   }
 }
 
 inline std::string get_key_in_cache(const std::string& prefix, const std::string& offset, const std::string& len)
 {
-  return fmt::format("{}{}{}{}{}", prefix, "_", offset, "_", len);
+  return fmt::format("{}{}{}{}{}", prefix, CACHE_DELIM, offset, CACHE_DELIM, len);
 }
 
 using boost::redis::connection;
index 8c3491666f3691037aa182db4122542655d26a0f..c3055be71a86a02e162897996fd97b8ab48e491a 100644 (file)
@@ -14,6 +14,9 @@ constexpr char RGW_CACHE_ATTR_VERSION_ID[] = "user.rgw.version_id";
 constexpr char RGW_CACHE_ATTR_SOURC_ZONE[] = "user.rgw.source_zone";
 constexpr char RGW_CACHE_ATTR_LOCAL_WEIGHT[] = "user.rgw.localWeight";
 
+constexpr char DIRTY_BLOCK_PREFIX[] = "D#";
+constexpr char CACHE_DELIM = '#';
+
 namespace rgw { namespace cache {
 
 typedef std::function<void(const DoutPrefixProvider* dpp, const std::string& key, const std::string& version, bool dirty, uint64_t size,
index 83647c3202954f06d7273662ce27665bc821cc4c..6aeb9b6bdf5db6e762fe0ea89bb8c19fd9d53b5d 100644 (file)
@@ -13,6 +13,11 @@ namespace efs = std::filesystem;
 
 namespace rgw { namespace cache {
 
+static inline std::string get_file_path(const std::string& location, const std::string& key)
+{
+    return location + "/" + key;
+}
+
 int SSDDriver::initialize(const DoutPrefixProvider* dpp)
 {
     if(partition_info.location.back() != '/') {
@@ -104,7 +109,7 @@ int SSDDriver::restore_blocks_objects(const DoutPrefixProvider* dpp, ObjectDataC
         ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): filename: " << file_name << dendl;
         try {
             std::stringstream ss(file_name);
-            while (std::getline(ss, part, '_')) {
+            while (std::getline(ss, part, CACHE_DELIM)) {
                 parts.push_back(part);
             }
             ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): parts.size(): " << parts.size() << dendl;
@@ -113,7 +118,7 @@ int SSDDriver::restore_blocks_objects(const DoutPrefixProvider* dpp, ObjectDataC
                 std::string key = file_name;
                 ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): file_name: " << file_name << dendl;
 
-                std::string version = parts[1];
+                std::string version = url_decode(parts[1]);
                 ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): version: " << version << dendl;
 
                 uint64_t offset = 0, len = 0;
@@ -136,20 +141,20 @@ int SSDDriver::restore_blocks_objects(const DoutPrefixProvider* dpp, ObjectDataC
             }
             //dirty blocks - "D", bucket_id, version, object_name in head block and offset, len in data blocks
             if ((parts.size() == 4 || parts.size() == 6) && parts[0] == "D") {
-                std::string prefix = "D_";
+                std::string prefix = DIRTY_BLOCK_PREFIX;
                 if (file_name.starts_with(prefix)) {
                     std::string key = file_name.substr(prefix.length());
                     ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): key: " << key << dendl;
 
                     bool dirty = true;
 
-                    std::string bucket_id = parts[1];
+                    std::string bucket_id = url_decode(parts[1]);
                     ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): bucket_id: " << bucket_id << dendl;
 
-                    std::string version = parts[2];
+                    std::string version = url_decode(parts[2]);
                     ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): version: " << version << dendl;
 
-                    std::string obj_name = parts[3];
+                    std::string obj_name = url_decode(parts[3]);
                     ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): obj_name: " << obj_name << dendl;
 
                     uint64_t len = 0, offset = 0;
@@ -267,8 +272,7 @@ int SSDDriver::put(const DoutPrefixProvider* dpp, const std::string& key, const
 int SSDDriver::get(const DoutPrefixProvider* dpp, const std::string& key, off_t offset, uint64_t len, bufferlist& bl, rgw::sal::Attrs& attrs, optional_yield y)
 {
     char buffer[len];
-    std::string location = partition_info.location + "/" + url_encode(key, true);
-
+    std::string location = get_file_path(partition_info.location, key);
     ldpp_dout(dpp, 20) << __func__ << "(): location=" << location << dendl;
     FILE *cache_file = nullptr;
     int r = 0;
@@ -309,7 +313,7 @@ int SSDDriver::get(const DoutPrefixProvider* dpp, const std::string& key, off_t
 int SSDDriver::append_data(const DoutPrefixProvider* dpp, const::std::string& key, const bufferlist& bl_data, optional_yield y)
 {
     bufferlist src = bl_data;
-    std::string location = partition_info.location + "/" + url_encode(key, true);
+    std::string location = get_file_path(partition_info.location, key);
 
     ldpp_dout(dpp, 20) << __func__ << "(): location=" << location << dendl;
     FILE *cache_file = nullptr;
@@ -367,7 +371,7 @@ auto SSDDriver::get_async(const DoutPrefixProvider *dpp, const Executor& ex, con
     auto p = Op::create(ex, handler);
     auto& op = p->user_data;
 
-    std::string location = partition_info.location + "/" + url_encode(key, true);
+    std::string location = get_file_path(partition_info.location, key);
     ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): location=" << location << dendl;
 
     int ret = op.prepare_libaio_read_op(dpp, location, read_ofs, read_len, p.get());
@@ -397,7 +401,7 @@ void SSDDriver::put_async(const DoutPrefixProvider *dpp, const Executor& ex, con
     auto p = Op::create(ex, handler);
     auto& op = p->user_data;
 
-    std::string location = partition_info.location + "/" + url_encode(key, true);
+    std::string location = get_file_path(partition_info.location, key);
     ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): location=" << location << dendl;
 
     int r = 0;
@@ -476,7 +480,7 @@ rgw::AioResultList SSDDriver::put_async(const DoutPrefixProvider* dpp, optional_
 
 int SSDDriver::delete_data(const DoutPrefixProvider* dpp, const::std::string& key, optional_yield y)
 {
-    std::string location = partition_info.location + "/" + url_encode(key, true);
+    std::string location = get_file_path(partition_info.location, key);
 
     if (!efs::remove(location)) {
         ldpp_dout(dpp, 0) << "ERROR: delete_data::remove has failed to remove the file: " << location << dendl;
@@ -491,11 +495,11 @@ int SSDDriver::delete_data(const DoutPrefixProvider* dpp, const::std::string& ke
 
 int SSDDriver::rename(const DoutPrefixProvider* dpp, const::std::string& oldKey, const::std::string& newKey, optional_yield y)
 { 
-    std::string location = partition_info.location;
-
-    int ret = std::rename((location + "/" + url_encode(oldKey, true)).c_str(), (location + "/" + url_encode(newKey, true)).c_str());
+    std::string old_file_path = get_file_path(partition_info.location, oldKey);
+    std::string new_file_path = get_file_path(partition_info.location, newKey);
+    int ret = std::rename(old_file_path.c_str(), new_file_path.c_str());
     if (ret < 0) {
-        ldpp_dout(dpp, 0) << "SSDDriver: ERROR: failed to rename the file: " << location + "/" + url_encode(oldKey, true) << dendl;
+        ldpp_dout(dpp, 0) << "SSDDriver: ERROR: failed to rename the file: " << old_file_path << dendl;
         return ret;
     }
 
@@ -505,7 +509,7 @@ int SSDDriver::rename(const DoutPrefixProvider* dpp, const::std::string& oldKey,
 
 int SSDDriver::AsyncWriteRequest::prepare_libaio_write_op(const DoutPrefixProvider *dpp, bufferlist& bl, unsigned int len, std::string key, std::string cache_location)
 {
-    std::string location = cache_location + "/" + url_encode(key, true);
+    std::string location = get_file_path(cache_location, key);
     int r = 0;
     ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): Write To Cache, location=" << location << dendl;
     cb.reset(new struct aiocb);
@@ -560,9 +564,8 @@ void SSDDriver::AsyncWriteRequest::libaio_write_cb(sigval sigval) {
     efs::space_info space = efs::space(partition_info.location);
     op.priv_data->set_free_space(op.dpp, space.available);
 
-    std::string new_path = partition_info.location + "/" + url_encode(op.key, true);
-    std::string old_path = partition_info.location + "/" + url_encode(op.temp_key, true);
-
+    std::string new_path = get_file_path(partition_info.location, op.key);
+    std::string old_path = get_file_path(partition_info.location, op.temp_key);
     ldpp_dout(op.dpp, 20) << "INFO: AsyncWriteRequest::libaio_write_yield_cb: temp_key: " << op.temp_key << dendl;
 
     ret = std::rename(old_path.c_str(), new_path.c_str());
@@ -618,7 +621,7 @@ void SSDDriver::AsyncReadOp::libaio_cb_aio_dispatch(sigval sigval)
 
 int SSDDriver::update_attrs(const DoutPrefixProvider* dpp, const std::string& key, const rgw::sal::Attrs& attrs, optional_yield y)
 {
-    std::string location = partition_info.location + "/" + url_encode(key, true);
+    std::string location = get_file_path(partition_info.location, key);
     ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): location=" << location << dendl;
 
     for (auto& it : attrs) {
@@ -643,7 +646,7 @@ int SSDDriver::update_attrs(const DoutPrefixProvider* dpp, const std::string& ke
 
 int SSDDriver::delete_attrs(const DoutPrefixProvider* dpp, const std::string& key, rgw::sal::Attrs& del_attrs, optional_yield y)
 {
-    std::string location = partition_info.location + "/" + url_encode(key, true);
+    std::string location = get_file_path(partition_info.location, key);
     ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): location=" << location << dendl;
 
     for (auto& it : del_attrs) {
@@ -662,7 +665,7 @@ int SSDDriver::delete_attrs(const DoutPrefixProvider* dpp, const std::string& ke
 
 int SSDDriver::get_attrs(const DoutPrefixProvider* dpp, const std::string& key, rgw::sal::Attrs& attrs, optional_yield y)
 {
-    std::string location = partition_info.location + "/" + url_encode(key, true);
+    std::string location = get_file_path(partition_info.location, key);
     ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): location=" << location << dendl;
 
     char namebuf[64 * 1024];
@@ -696,7 +699,7 @@ int SSDDriver::get_attrs(const DoutPrefixProvider* dpp, const std::string& key,
 
 int SSDDriver::set_attrs(const DoutPrefixProvider* dpp, const std::string& key, const rgw::sal::Attrs& attrs, optional_yield y)
 {
-    std::string location = partition_info.location + "/" + url_encode(key, true);
+    std::string location = get_file_path(partition_info.location, key);
     ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): location=" << location << dendl;
 
     for (auto& [attr_name, attr_val_bl] : attrs) {
@@ -718,7 +721,7 @@ int SSDDriver::set_attrs(const DoutPrefixProvider* dpp, const std::string& key,
 
 int SSDDriver::get_attr(const DoutPrefixProvider* dpp, const std::string& key, const std::string& attr_name, std::string& attr_val, optional_yield y)
 {
-    std::string location = partition_info.location + "/" + url_encode(key, true);
+    std::string location = get_file_path(partition_info.location, key);
     ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): location=" << location << dendl;
 
     ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): get_attr: key: " << attr_name << dendl;
@@ -749,7 +752,7 @@ int SSDDriver::get_attr(const DoutPrefixProvider* dpp, const std::string& key, c
 
 int SSDDriver::set_attr(const DoutPrefixProvider* dpp, const std::string& key, const std::string& attr_name, const std::string& attr_val, optional_yield y)
 {
-    std::string location = partition_info.location + "/" + url_encode(key, true);
+    std::string location = get_file_path(partition_info.location, key);
     ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): location=" << location << dendl;
 
     ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): set_attr: key: " << attr_name << " val: " << attr_val << dendl;
@@ -768,7 +771,7 @@ int SSDDriver::set_attr(const DoutPrefixProvider* dpp, const std::string& key, c
 
 int SSDDriver::delete_attr(const DoutPrefixProvider* dpp, const std::string& key, const std::string& attr_name)
 {
-    std::string location = partition_info.location + "/" + url_encode(key, true);
+    std::string location = get_file_path(partition_info.location, key);
     ldpp_dout(dpp, 20) << "SSDCache: " << __func__ << "(): location=" << location << dendl;
 
     auto ret = removexattr(location.c_str(), attr_name.c_str());