TestOpStat *stats,
int max_seconds,
bool ec_pool,
- bool balance_reads) :
+ bool balance_reads,
+ bool set_redirect) :
m_nextop(NULL), m_op(0), m_ops(ops), m_seconds(max_seconds),
m_objects(objects), m_stats(stats),
m_total_weight(0),
m_ec_pool(ec_pool),
- m_balance_reads(balance_reads)
+ m_balance_reads(balance_reads),
+ m_set_redirect(set_redirect)
{
m_start = time(0);
for (map<TestOpType, unsigned int>::const_iterator it = op_weights.begin();
m_weight_sums.insert(pair<TestOpType, unsigned int>(it->first,
m_total_weight));
}
+ if (m_set_redirect) {
+ /* create redirect objects + set-redirect*/
+ m_redirect_objects = objects*2; // for copy_from + set-redirect test
+ m_initial_redirected_objects = objects;
+ m_ops = ops+m_redirect_objects+m_initial_redirected_objects;
+ }
}
TestOp *next(RadosTestContext &context) override
} else if (m_op >= m_ops) {
return NULL;
}
+
+ if (m_set_redirect) {
+ /*
+ * set-redirect test
+ * 1. create objects (copy from)
+ * 2. set-redirect
+ */
+ int create_objects_end = m_objects + m_redirect_objects;
+ int set_redirect_end = create_objects_end + m_initial_redirected_objects;
+
+ if (m_op <= create_objects_end) {
+ stringstream oid;
+ int _oid = m_op;
+ oid << _oid;
+ if ((_oid) % 2) {
+ oid << " " << string(300, 'o');
+ }
+ stringstream oid2;
+ int _oid2 = _oid - m_objects;
+ oid2 << _oid2;
+ if ((_oid2) % 2) {
+ oid2 << " " << string(300, 'o');
+ }
+ cout << m_op << ": " << "(create redirect oid) copy_from oid " << oid.str()
+ << " from oid " << oid2.str() << std::endl;
+ return new CopyFromOp(m_op, &context, oid.str(), oid2.str(), m_stats);
+ } else if (m_op <= set_redirect_end) {
+ stringstream oid;
+ int _oid = m_op-create_objects_end;
+ oid << _oid;
+ if ((_oid) % 2) {
+ oid << " " << string(300, 'o');
+ }
+ stringstream oid2;
+ int _oid2 = _oid + m_objects;
+ oid2 << _oid2;
+ if ((_oid2) % 2) {
+ oid2 << " " << string(300, 'o');
+ }
+ cout << m_op << ": " << "set_redirect oid " << oid.str() << " target oid "
+ << oid2.str() << std::endl;
+ return new SetRedirectOp(m_op, &context, oid.str(), oid2.str(), context.pool_name);
+ }
+
+ if (!context.oid_redirect_not_in_use.size() && m_op > set_redirect_end) {
+ int set_size = context.oid_not_in_use.size();
+ if (set_size < m_objects + m_redirect_objects) {
+ return NULL;
+ }
+ for (int t_op = m_objects+1; t_op <= create_objects_end; t_op++) {
+ stringstream oid;
+ oid << t_op;
+ if (t_op % 2) {
+ oid << " " << string(300, 'o');
+ }
+ context.oid_not_flushing.erase(oid.str());
+ context.oid_not_in_use.erase(oid.str());
+ context.oid_in_use.erase(oid.str());
+ cout << m_op << ": " << " remove oid " << oid.str() << " from oid_*_use " << std::endl;
+ if (t_op > m_objects + m_initial_redirected_objects) {
+ context.oid_redirect_not_in_use.insert(oid.str());
+ }
+ }
+ cout << m_op << ": " << " oid_not_in_use: " << context.oid_not_in_use.size()
+ << " oid_in_use: " << context.oid_in_use.size() << std::endl;
+ }
+ }
if (m_nextop) {
retval = m_nextop;
TestOp *gen_op(RadosTestContext &context, TestOpType type)
{
string oid, oid2;
- //cout << "oids not in use " << context.oid_not_in_use.size() << std::endl;
assert(context.oid_not_in_use.size());
switch (type) {
<< context.current_snap << std::endl;
return new WriteOp(m_op, &context, oid, true, true, m_stats);
+ case TEST_OP_SET_REDIRECT:
+ oid = *(rand_choose(context.oid_not_in_use));
+ oid2 = *(rand_choose(context.oid_redirect_not_in_use));
+ cout << m_op << ": " << "set_redirect oid " << oid << " target oid " << oid2 << std::endl;
+ return new SetRedirectOp(m_op, &context, oid, oid2, context.pool_name, m_stats);
+
+ case TEST_OP_UNSET_REDIRECT:
+ oid = *(rand_choose(context.oid_not_in_use));
+ cout << m_op << ": " << "unset_redirect oid " << oid << std::endl;
+ return new UnsetRedirectOp(m_op, &context, oid, m_stats);
+
default:
cerr << m_op << ": Invalid op type " << type << std::endl;
ceph_abort();
unsigned int m_total_weight;
bool m_ec_pool;
bool m_balance_reads;
+ bool m_set_redirect;
+ int m_redirect_objects;
+ int m_initial_redirected_objects;
};
int main(int argc, char **argv)
{ TEST_OP_CACHE_EVICT, "cache_evict", true },
{ TEST_OP_APPEND, "append", true },
{ TEST_OP_APPEND_EXCL, "append_excl", true },
+ { TEST_OP_SET_REDIRECT, "set_redirect", true },
+ { TEST_OP_UNSET_REDIRECT, "unset_redirect", true },
{ TEST_OP_READ /* grr */, NULL },
};
bool no_omap = false;
bool no_sparse = false;
bool balance_reads = false;
+ bool set_redirect = false;
for (int i = 1; i < argc; ++i) {
if (strcmp(argv[i], "--max-ops") == 0)
cout << "adding op weight " << op_types[j].name << " -> " << weight << std::endl;
op_weights.insert(pair<TestOpType, unsigned int>(op_types[j].op, weight));
}
+ } else if (strcmp(argv[i], "--set_redirect") == 0) {
+ set_redirect = true;
} else {
cerr << "unknown arg " << argv[i] << std::endl;
- //usage();
exit(1);
}
}
if (op_weights.empty()) {
cerr << "No operations specified" << std::endl;
- //usage();
exit(1);
}
<< "\tWrite stride min: " << min_stride_size << std::endl
<< "\tWrite stride max: " << max_stride_size << std::endl;
- if (min_stride_size > max_stride_size) {
- cerr << "Error: min_stride_size cannot be more than max_stride_size"
+ if (min_stride_size >= max_stride_size) {
+ cerr << "Error: max_stride_size must be more than min_stride_size"
<< std::endl;
return 1;
}
WeightedTestGenerator gen = WeightedTestGenerator(
ops, objects,
op_weights, &stats, max_seconds,
- ec_pool, balance_reads);
+ ec_pool, balance_reads, set_redirect);
int r = context.init();
if (r < 0) {
cerr << "Error initializing rados test context: "