]> git-server-git.apps.pok.os.sepia.ceph.com Git - ceph.git/commitdiff
Add get_*_with_header to StripObjectHeader
authorHaomai Wang <haomaiwang@gmail.com>
Thu, 20 Feb 2014 03:43:16 +0000 (11:43 +0800)
committerHaomai Wang <haomaiwang@gmail.com>
Sat, 22 Feb 2014 13:04:59 +0000 (21:04 +0800)
In some situations, we need to ensure header is held and try to read, so read
interfaces need to accept header argument to allow.

Signed-off-by: Haomai Wang <haomaiwang@gmail.com>
src/os/GenericObjectMap.h
src/os/KeyValueStore.cc
src/os/KeyValueStore.h

index fddbe53bdf3029078159e0ac66c31fee5f5daf86..88e7b87074a692f4237acaba9a60780c195450f8 100644 (file)
@@ -365,11 +365,17 @@ private:
     int adjust();
   };
 
+ protected:
   typedef ceph::shared_ptr<GenericObjectMapIteratorImpl> GenericObjectMapIterator;
   GenericObjectMapIterator _get_iterator(Header header, string prefix) {
     return GenericObjectMapIterator(new GenericObjectMapIteratorImpl(this, header, prefix));
   }
 
+  // Scan keys in header into out_keys and out_values (if nonnull)
+  int scan(Header header, const string &prefix, const set<string> &in_keys,
+           set<string> *out_keys, map<string, bufferlist> *out_values);
+
+ private:
   /// Removes node corresponding to header
   void clear_header(Header header, KeyValueDB::Transaction t);
 
@@ -399,10 +405,6 @@ private:
   // Lookup header node for input
   Header lookup_parent(Header input);
 
-  // Scan keys in header into out_keys and out_values (if nonnull)
-  int scan(Header header, const string &prefix, const set<string> &in_keys,
-           set<string> *out_keys, map<string, bufferlist> *out_values);
-
   // Remove header and all related prefixes
   int _clear(Header header, KeyValueDB::Transaction t);
 
index b77e7fc6fbc39631b1fe73b50901ea330cd0271d..a12606c875a2dcbdde7fee50b88ae7d0e603566c 100644 (file)
@@ -238,7 +238,39 @@ void StripObjectMap::rename_wrap(const coll_t &cid, const ghobject_t &oid,
   }
 }
 
+int StripObjectMap::get_values_with_header(const StripObjectHeader &header,
+                                           const string &prefix,
+                                           const set<string> &keys,
+                                           map<string, bufferlist> *out)
+{
+  return scan(header.header, prefix, keys, 0, out);
+}
 
+int StripObjectMap::get_keys_with_header(const StripObjectHeader &header,
+                                         const string &prefix,
+                                         set<string> *keys)
+{
+  ObjectMap::ObjectMapIterator iter = _get_iterator(header.header, prefix);
+  for (; iter->valid(); iter->next()) {
+    if (iter->status())
+      return iter->status();
+    keys->insert(iter->key());
+  }
+  return 0;
+}
+
+int StripObjectMap::get_with_header(const StripObjectHeader &header,
+                        const string &prefix, map<string, bufferlist> *out)
+{
+  ObjectMap::ObjectMapIterator iter = _get_iterator(header.header, prefix);
+  for (iter->seek_to_first(); iter->valid(); iter->next()) {
+    if (iter->status())
+      return iter->status();
+    out->insert(make_pair(iter->key(), iter->value()));
+  }
+
+  return 0;
+}
 // =========== KeyValueStore::SubmitManager Implementation ==============
 
 uint64_t KeyValueStore::SubmitManager::op_submit_start()
@@ -328,8 +360,8 @@ int KeyValueStore::BufferTransaction::get_buffer_key(
   set<string> keys;
   map<string, bufferlist> out;
   keys.insert(key);
-  int r = store->backend->get_values(strip_header->cid, strip_header->oid,
-                                     prefix, keys, &out);
+  int r = store->backend->get_values_with_header(*strip_header, prefix,
+                                                 keys, &out);
   if (r < 0) {
     dout(10) << __func__  << " " << strip_header->cid << "/"
              << strip_header->oid << " " << " r = " << r << dendl;
@@ -1653,7 +1685,7 @@ int KeyValueStore::_generic_read(coll_t cid, const ghobject_t& oid,
     }
   }
 
-  r = backend->get_values(cid, oid, OBJECT_STRIP_PREFIX, keys, &out);
+  r = backend->get_values_with_header(header, OBJECT_STRIP_PREFIX, keys, &out);
   if (r < 0) {
     dout(10) << __func__ << " " << cid << "/" << oid << " " << offset << "~"
              << len << " = " << r << dendl;
@@ -2138,7 +2170,7 @@ int KeyValueStore::_rmattrs(coll_t cid, const ghobject_t& oid,
     return r;
   }
 
-  r = backend->get_keys(cid, oid, OBJECT_XATTR, &attrs);
+  r = backend->get_keys_with_header(*header, OBJECT_XATTR, &attrs);
   if (r < 0 && r != -ENOENT) {
     dout(10) << __func__ << " could not get attrs r = " << r << dendl;
     assert(!m_fail_eio || r != -EIO);
@@ -2648,22 +2680,46 @@ int KeyValueStore::collection_version_current(coll_t c, uint32_t *version)
 // omap
 
 int KeyValueStore::omap_get(coll_t c, const ghobject_t &hoid,
-                            bufferlist *header, map<string, bufferlist> *out)
+                            bufferlist *bl, map<string, bufferlist> *out)
 {
   dout(15) << __func__ << " " << c << "/" << hoid << dendl;
 
+  StripObjectMap::StripObjectHeader header;
+
   int r = _check_coll(c);
   if (r < 0) {
     return r;
   }
 
-  r = backend->get(c, hoid, OBJECT_OMAP, out);
+  r = backend->lookup_strip_header(c, hoid, header);
+  if (r < 0) {
+    dout(10) << __func__ << " lookup_strip_header failed: r =" << r << dendl;
+    return r;
+  }
+
+
+  r = backend->get_with_header(header, OBJECT_OMAP, out);
   if (r < 0 && r != -ENOENT) {
     dout(10) << __func__ << " err r =" << r << dendl;
     return r;
   }
 
-  return omap_get_header(c, hoid, header, false);
+  set<string> keys;
+  map<string, bufferlist> got;
+
+  keys.insert(OBJECT_OMAP_HEADER_KEY);
+  r = backend->get_values_with_header(header, OBJECT_OMAP_HEADER, keys, &got);
+  if (r < 0 && r != -ENOENT) {
+    dout(10) << __func__ << " err r =" << r << dendl;
+    return r;
+  }
+
+  if (got.size()) {
+    assert(got.size() == 1);
+    bl->swap(got.begin()->second);
+  }
+
+  return 0;
 }
 
 int KeyValueStore::omap_get_header(coll_t c, const ghobject_t &hoid,
@@ -2771,7 +2827,7 @@ int KeyValueStore::_omap_clear(coll_t cid, const ghobject_t &hoid,
   }
 
   set<string> keys;
-  r = backend->get_keys(cid, hoid, OBJECT_OMAP, &keys);
+  r = backend->get_keys_with_header(*header, OBJECT_OMAP, &keys);
   if (r < 0 && r != -ENOENT) {
     dout(10) << __func__ << " could not get omap_keys r = " << r << dendl;
     assert(!m_fail_eio || r != -EIO);
index c22185ffd244975bc38d7a3b424a6ad006e9d146..2327b0e4076a1a75457aab9ef7ad4ba2f583d4ef 100644 (file)
@@ -119,7 +119,24 @@ class StripObjectMap: public GenericObjectMap {
                    KeyValueDB::Transaction t,
                    const SequencerPosition &spos,
                    StripObjectHeader *header);
-
+  // Already hold header to avoid lock header seq again
+  int get_with_header(
+    const StripObjectHeader &header,
+    const string &prefix,
+    map<string, bufferlist> *out
+    );
+
+  int get_values_with_header(
+    const StripObjectHeader &header,
+    const string &prefix,
+    const set<string> &keys,
+    map<string, bufferlist> *out
+    );
+  int get_keys_with_header(
+    const StripObjectHeader &header,
+    const string &prefix,
+    set<string> *keys
+    );
 
   StripObjectMap(KeyValueDB *db): GenericObjectMap(db) {}