/* * pocli_pmemobj_tx_abort -- pmemobj_tx_abort() command */ static enum pocli_ret pocli_pmemobj_tx_abort(struct pocli_ctx *ctx, struct pocli_args *args) { if (args->argc != 2) return POCLI_ERR_ARGS; if (pmemobj_tx_stage() != TX_STAGE_WORK) return pocli_err(ctx, POCLI_ERR_ARGS, "cannot use in stage different than TX_STAGE_WORK\n"); int err; int count = sscanf(args->argv[1], "%d", &err); if (count != 1) return POCLI_ERR_PARS; ctx->tx_aborted = true; free(args); pmemobj_tx_abort(err); pocli_printf(ctx, "pmemobj_tx_abort: %d", err); return POCLI_RET_OK; }
int main(int argc, char *argv[]) { START(argc, argv, "obj_tx_flow"); if (argc != 2) FATAL("usage: %s [file]", argv[0]); PMEMobjpool *pop; if ((pop = pmemobj_create(argv[1], LAYOUT_NAME, PMEMOBJ_MIN_POOL, S_IWUSR | S_IRUSR)) == NULL) FATAL("!pmemobj_create"); int a = 0; int b = 0; int c = 0; TX_BEGIN(pop) { a = TEST_VALUE_A; } TX_ONCOMMIT { ASSERT(a == TEST_VALUE_A); b = TEST_VALUE_B; } TX_ONABORT { /* not called */ a = TEST_VALUE_B; } TX_FINALLY { ASSERT(b == TEST_VALUE_B); c = TEST_VALUE_C; } TX_END ASSERT(a == TEST_VALUE_A); ASSERT(b == TEST_VALUE_B); ASSERT(c == TEST_VALUE_C); a = 0; b = 0; c = 0; TX_BEGIN(pop) { a = TEST_VALUE_A; pmemobj_tx_abort(EINVAL); a = TEST_VALUE_B; } TX_ONCOMMIT { /* not called */ a = TEST_VALUE_B; } TX_ONABORT { ASSERT(a == TEST_VALUE_A); b = TEST_VALUE_B; } TX_FINALLY { ASSERT(b == TEST_VALUE_B); c = TEST_VALUE_C; } TX_END ASSERT(a == TEST_VALUE_A); ASSERT(b == TEST_VALUE_B); ASSERT(c == TEST_VALUE_C); a = 0; b = 0; c = 0; TX_BEGIN(pop) { TX_BEGIN(pop) { a = TEST_VALUE_A; } TX_ONCOMMIT { ASSERT(a == TEST_VALUE_A); b = TEST_VALUE_B; } TX_END } TX_ONCOMMIT { c = TEST_VALUE_C; } TX_END ASSERT(a == TEST_VALUE_A); ASSERT(b == TEST_VALUE_B); ASSERT(c == TEST_VALUE_C); a = 0; b = 0; c = 0; TX_BEGIN(pop) { a = TEST_VALUE_C; TX_BEGIN(pop) { a = TEST_VALUE_A; pmemobj_tx_abort(EINVAL); a = TEST_VALUE_B; } TX_ONCOMMIT { /* not called */ a = TEST_VALUE_C; } TX_ONABORT { ASSERT(a == TEST_VALUE_A); b = TEST_VALUE_B; } TX_FINALLY { ASSERT(b == TEST_VALUE_B); c = TEST_VALUE_C; } TX_END a = TEST_VALUE_B; } TX_ONCOMMIT { /* not called */ ASSERT(a == TEST_VALUE_A); c = TEST_VALUE_C; } TX_ONABORT { ASSERT(a == TEST_VALUE_A); ASSERT(b == TEST_VALUE_B); ASSERT(c == TEST_VALUE_C); a = TEST_VALUE_B; } TX_FINALLY { ASSERT(a == TEST_VALUE_B); b = TEST_VALUE_A; } TX_END ASSERT(a == TEST_VALUE_B); ASSERT(b == TEST_VALUE_A); ASSERT(c == TEST_VALUE_C); a = 0; b = 0; c = 0; pmemobj_tx_begin(pop, NULL, TX_LOCK_NONE); pmemobj_tx_abort(EINVAL); ASSERT(pmemobj_tx_stage() == TX_STAGE_ONABORT); a = TEST_VALUE_A; pmemobj_tx_end(); ASSERT(a == TEST_VALUE_A); pmemobj_close(pop); DONE(NULL); }