compat.incompat.insert(CEPH_MON_FEATURE_INCOMPAT_OSDMAP_ENC);
compat.incompat.insert(CEPH_MON_FEATURE_INCOMPAT_ERASURE_CODE_PLUGINS_V2);
compat.incompat.insert(CEPH_MON_FEATURE_INCOMPAT_ERASURE_CODE_PLUGINS_V3);
+ compat.incompat.insert(CEPH_MON_FEATURE_INCOMPAT_KRAKEN);
return compat;
}
void Monitor::finish_election()
{
apply_quorum_to_compatset_features();
+ apply_monmap_to_compatset_features();
timecheck_finish();
exited_quorum = utime_t();
finish_contexts(g_ceph_context, waitfor_quorum);
}
}
+void Monitor::_apply_compatset_features(CompatSet &new_features)
+{
+ if (new_features.compare(features) != 0) {
+ CompatSet diff = features.unsupported(new_features);
+ dout(1) << __func__ << " enabling new quorum features: " << diff << dendl;
+ features = new_features;
+
+ auto t = std::make_shared<MonitorDBStore::Transaction>();
+ write_features(t);
+ store->apply_transaction(t);
+
+ apply_compatset_features_to_quorum_requirements();
+ }
+}
+
void Monitor::apply_quorum_to_compatset_features()
{
CompatSet new_features(features);
if (quorum_con_features & CEPH_FEATURE_ERASURE_CODE_PLUGINS_V3) {
new_features.incompat.insert(CEPH_MON_FEATURE_INCOMPAT_ERASURE_CODE_PLUGINS_V3);
}
- if (new_features.compare(features) != 0) {
- CompatSet diff = features.unsupported(new_features);
- dout(1) << __func__ << " enabling new quorum features: " << diff << dendl;
- features = new_features;
-
- MonitorDBStore::TransactionRef t(new MonitorDBStore::Transaction);
- write_features(t);
- store->apply_transaction(t);
+ dout(5) << __func__ << dendl;
+ _apply_compatset_features(new_features);
+}
- apply_compatset_features_to_quorum_requirements();
+void Monitor::apply_monmap_to_compatset_features()
+{
+ CompatSet new_features(features);
+ mon_feature_t monmap_features = monmap->get_required_features();
+
+ /* persistent monmap features may go into the compatset.
+ * optional monmap features may not - why?
+ * because optional monmap features may be set/unset by the admin,
+ * and possibly by other means that haven't yet been thought out,
+ * so we can't make the monitor enforce them on start - because they
+ * may go away.
+ * this, of course, does not invalidate setting a compatset feature
+ * for an optional feature - as long as you make sure to clean it up
+ * once you unset it.
+ */
+ if (monmap_features.contains_all(ceph::features::mon::FEATURE_KRAKEN)) {
+ assert(ceph::features::mon::get_persistent().contains_all(
+ ceph::features::mon::FEATURE_KRAKEN));
+ // this feature should only ever be set if the quorum supports it.
+ assert(quorum_con_features & CEPH_FEATURE_SERVER_KRAKEN);
+ new_features.incompat.insert(CEPH_MON_FEATURE_INCOMPAT_KRAKEN);
}
+ dout(5) << __func__ << dendl;
+ _apply_compatset_features(new_features);
}
void Monitor::apply_compatset_features_to_quorum_requirements()
if (features.incompat.contains(CEPH_MON_FEATURE_INCOMPAT_ERASURE_CODE_PLUGINS_V3)) {
required_features |= CEPH_FEATURE_ERASURE_CODE_PLUGINS_V3;
}
+ if (features.incompat.contains(CEPH_MON_FEATURE_INCOMPAT_KRAKEN)) {
+ required_features |= CEPH_FEATURE_SERVER_KRAKEN;
+ }
dout(10) << __func__ << " required_features " << required_features << dendl;
}
void cancel_probe_timeout();
void probe_timeout(int r);
+ void _apply_compatset_features(CompatSet &new_features);
+
public:
epoch_t get_epoch();
int get_leader() { return leader; }
return monmap->get_required_features();
}
void apply_quorum_to_compatset_features();
+ void apply_monmap_to_compatset_features();
void apply_compatset_features_to_quorum_requirements();
private:
#define CEPH_MON_FEATURE_INCOMPAT_OSDMAP_ENC CompatSet::Feature(5, "new-style osdmap encoding")
#define CEPH_MON_FEATURE_INCOMPAT_ERASURE_CODE_PLUGINS_V2 CompatSet::Feature(6, "support isa/lrc erasure code")
#define CEPH_MON_FEATURE_INCOMPAT_ERASURE_CODE_PLUGINS_V3 CompatSet::Feature(7, "support shec erasure code")
+#define CEPH_MON_FEATURE_INCOMPAT_KRAKEN CompatSet::Feature(8, "support monmap features")
// make sure you add your feature to Monitor::get_supported_features
long parse_pos_long(const char *s, ostream *pss = NULL);