diff options
Diffstat (limited to 'src/osd/PG.cc')
-rw-r--r-- | src/osd/PG.cc | 36 |
1 files changed, 34 insertions, 2 deletions
diff --git a/src/osd/PG.cc b/src/osd/PG.cc index 2f38dac426e..bfcdf7e3d90 100644 --- a/src/osd/PG.cc +++ b/src/osd/PG.cc @@ -2682,8 +2682,13 @@ void PG::_scan_list(ScrubMap &map, vector<hobject_t> &ls) if (r == 0) { ScrubMap::object &o = map.objects[poid]; o.size = st.st_size; + o.nlinks = st.st_nlink; assert(!o.negative); osd->store->getattrs(coll, poid, o.attrs); + if (poid.snap != CEPH_SNAPDIR && poid.snap != CEPH_NOSNAP) { + // Check snap collections + check_snap_collections(poid, o.attrs, &o.snapcolls); + } dout(25) << "_scan_list " << poid << dendl; } else { dout(25) << "_scan_list " << poid << " got " << r << ", skipping" << dendl; @@ -3215,6 +3220,7 @@ void PG::_compare_scrubmaps(const map<int,ScrubMap*> &maps, map<hobject_t, set<int> > &missing, map<hobject_t, set<int> > &inconsistent, map<hobject_t, int> &authoritative, + map<hobject_t, set<int> > &invalid_snapcolls, ostream &errorstream) { map<hobject_t,ScrubMap::object>::const_iterator i; @@ -3241,6 +3247,18 @@ void PG::_compare_scrubmaps(const map<int,ScrubMap*> &maps, // Take first osd to have it as authoritative auth = j; } else { + // Check snapcolls + if (k->snap < CEPH_MAXSNAP) { + if (_report_snap_collection_errors( + *k, + j->first, + j->second->objects[*k].attrs, + j->second->objects[*k].snapcolls, + j->second->objects[*k].nlinks, + errorstream)) { + invalid_snapcolls[*k].insert(j->first); + } + } // Compare stringstream ss; if (!_compare_scrub_objects(auth->second->objects[*k], @@ -3300,6 +3318,7 @@ void PG::scrub_finalize() { // Maps from objects with erros to missing/inconsistent peers map<hobject_t, set<int> > missing; map<hobject_t, set<int> > inconsistent; + map<hobject_t, set<int> > inconsistent_snapcolls; // Map from object with errors to good peer map<hobject_t, int> authoritative; @@ -3314,9 +3333,22 @@ void PG::scrub_finalize() { maps[i] = &scrub_received_maps[acting[i]]; } - _compare_scrubmaps(maps, missing, inconsistent, authoritative, ss); + _compare_scrubmaps( + maps, missing, inconsistent, authoritative, + inconsistent_snapcolls, + ss); + + for (map<hobject_t, set<int> >::iterator obj = inconsistent_snapcolls.begin(); + obj != inconsistent_snapcolls.end(); + ++obj) { + for (set<int>::iterator j = obj->second.begin(); j != obj->second.end(); ++j) { + ++errors; + ss << info.pgid << " " << mode << " " << " object " << obj->first + << " has inconsistent snapcolls on " << *j << std::endl; + } + } - if (authoritative.size()) { + if (authoritative.size() || inconsistent_snapcolls.size()) { ss << info.pgid << " " << mode << " " << missing.size() << " missing, " << inconsistent.size() << " inconsistent objects\n"; dout(2) << ss.str() << dendl; |