/* -*- mode: C++; c-basic-offset: 4; indent-tabs-mode: nil -*- */ // vim: ft=cpp:expandtab:ts=8:sw=4:softtabstop=4: #ident "Copyright (c) 2007 Tokutek Inc. All rights reserved." #ident "$Id$" #include "test.h" #include <stdio.h> #include <stdlib.h> #include <toku_pthread.h> #include <unistd.h> #include <memory.h> #include <sys/stat.h> #include <db.h> #include "threaded_stress_test_helpers.h" toku_pthread_t checkpoint_tid; static int cnt = 0; static bool starting_a_chkpt = false; int state_to_crash = 0; static void *do_checkpoint_and_crash(void *arg) { // first verify that checkpointed_data is correct; DB_ENV* CAST_FROM_VOIDP(env, arg); if (verbose) printf("starting a checkpoint\n"); int r = env->txn_checkpoint(env, 0, 0, 0); assert(r==0); if (verbose) printf("completed a checkpoint, about to crash\n"); toku_hard_crash_on_purpose(); return arg; } static void flt_callback(int flt_state, void* extra) { cnt++; if (verbose) printf("flt_state!! %d\n", flt_state); if (cnt > 0 && !starting_a_chkpt && flt_state == state_to_crash) { starting_a_chkpt = true; if (verbose) printf("flt_state %d\n", flt_state); int r = toku_pthread_create(&checkpoint_tid, NULL, do_checkpoint_and_crash, extra); assert(r==0); usleep(2*1000*1000); } } static void stress_table(DB_ENV *env, DB **dbp, struct cli_args *cli_args) { // // the threads that we want: // - one thread constantly updating random values // - one thread doing table scan with bulk fetch // - one thread doing table scan without bulk fetch // - one thread doing random point queries // if (verbose) printf("starting creation of pthreads\n"); const int num_threads = 1; struct arg myargs[num_threads]; for (int i = 0; i < num_threads; i++) { arg_init(&myargs[i], dbp, env, cli_args); } // make the guy that updates the db struct update_op_args uoe = get_update_op_args(cli_args, NULL); myargs[0].operation_extra = &uoe; myargs[0].operation = update_op; //myargs[0].update_pad_frequency = 0; db_env_set_flusher_thread_callback(flt_callback, env); run_workers(myargs, num_threads, cli_args->time_of_test, true, cli_args); } static int run_recover_flt_test(int argc, char *const argv[]) { struct cli_args args = get_default_args(); // make test time arbitrarily high because we expect a crash args.time_of_test = 1000000000; args.num_elements = 2000; // we want to induce a checkpoint args.env_args.checkpointing_period = 0; parse_stress_test_args(argc, argv, &args); if (args.do_test_and_crash) { stress_test_main(&args); } if (args.do_recover) { stress_recover(&args); } return 0; }