int _tmain(int argc, TCHAR *argv[]) { int res = 0; program_state_t state; if (argc == 1) { // called without any arguments -- signal everybody to exit signal_all_processes_to_exit(); return 0; } if (argc != 7) { _tprintf(_T("Usage: %s <ip> <port> <in folder> <out folder> <interval ms> <num of threads>\n"), argv[0]); return -1; } _tcscpy_s(state.host, argv[1]); state.port = _tstoi(argv[2]); _tcscpy_s(state.in_dir, argv[3]); _tcscpy_s(state.out_dir, argv[4]); state.interval_ms = _tstoi(argv[5]); state.num_of_threads = _tstoi(argv[6]); if (!init_state(&state)) { res = -1; goto cleanup; } if (!run_stress(&state)) { res = -1; goto cleanup; } cleanup: if (!fini_state(&state)) { res = -1; } return res; }
int __cdecl main() { char *vm_path, *uuid, *t; size_t l; char **contents; unsigned count; HANDLE xs_handle2; HANDLE event; HANDLE event2; int watch_h; int watch_h2; int i; DWORD status; xs_handle = xs_domain_open(); if (!xs_handle) win_err(1, "openning xenstore interface"); /* Try to give ourselves a clean place to start */ xs_remove(xs_handle, "data/test"); /* Check basic xenstore reads with relative path... */ vm_path = xs_read(xs_handle, "vm", NULL); if (!vm_path) win_err(1, "reading vm path"); if (vm_path[0] != '/') { fail_test(__LINE__, "expected vm path to be absolute, got %s", vm_path); } /* and with an absolute path. */ uuid = gather_read(&l, vm_path, "uuid", NULL); if (!uuid) win_err(1, "reading uuid"); if (l != 36) { fail_test(__LINE__, "uuid length was %d bytes, expected 36"); } if (strlen(uuid) != 36) { fail_test(__LINE__, "uuid was %s, not right length (%d, should be 36), returned length %d", uuid, strlen(uuid), l); } /* Make sure read error sets a suitable code. */ xs_read_expected_error(__LINE__, "non_existent", ERROR_FILE_NOT_FOUND); xs_read_expected_error(__LINE__, "invalid\\path", ERROR_INVALID_PARAMETER); xs_read_expected_error(__LINE__, "/local/domain/0/name", ERROR_ACCESS_DENIED); /* Test basic xs_write functionality. */ if (!xs_write(xs_handle, "data/test/key1", "data1")) { fail_test(__LINE__, "write data/test/key1 failed with %lx", GetLastError()); } else { t = xs_read(xs_handle, "data/test/key1", &l); if (!t) { fail_test(__LINE__, "error reading from data/test/key1: %lx", GetLastError()); } else { if (l != 5) { fail_test(__LINE__, "manifest length wrong reading data/test/key1: %d should be 5.", l); } if (strcmp(t, "data1")) { fail_test(__LINE__, "got wrong data reading data/test/key1: %s should be data1.", t); } free(t); } } xs_write_expected_error(__LINE__, "foo", "bar", ERROR_ACCESS_DENIED); xs_write_expected_error(__LINE__, "/foo", "bar", ERROR_ACCESS_DENIED); /* Try a very large write and make sure that it fails in the expected way. */ t = malloc(65536); memset(t, 'a', 65536); t[65535] = 0; xs_write_expected_error(__LINE__,"data/test/key1", t, ERROR_DISK_FULL); free(t); /* Test that read and write work for keys containing nul bytes. */ if (!xs_write_bin(xs_handle, "data/test/key1", "xxx\0yyy", 7)) { fail_test(__LINE__, "failed to write nul bytes (%d)", GetLastError()); } t = xs_read(xs_handle, "data/test/key1", &l); if (!t) { fail_test(__LINE__, "failed to read nul bytes (%d)", GetLastError()); } else { if (l != 7) { fail_test(__LINE__, "read with nuls: expected 7, got %d.\n", l); } else if (memcmp(t, "xxx\0yyy", 7)) { fail_test(__LINE__, "bad data from read with nuls: %s", t); } free(t); } if (!xs_remove(xs_handle, "data/test/key1")) { fail_test(__LINE__, "failed to remove data/test/key1 (%d)", GetLastError()); } xs_read_expected_error(__LINE__, "data/test/key1", ERROR_FILE_NOT_FOUND); xs_ls_expected_error(__LINE__, "data/test/key1", ERROR_FILE_NOT_FOUND); if (!xs_write(xs_handle, "data/test/key1", "data1")) { fail_test(__LINE__, "failed to rewrite data/test/key1"); } contents = xs_directory(xs_handle, "data/test/key1", &count); if (!contents) { fail_test(__LINE__, "failed to ls data/test/key1: %x", GetLastError()); } else if (count != 0) { fail_test(__LINE__, "ls data/test/key1 had %d items", count); free(contents); } else { free(contents); } if (!xs_write(xs_handle, "data/test/key1/key2", "data2")) { fail_test(__LINE__, "failed to rewrite data/test/key1/key2"); } contents = xs_directory(xs_handle, "data/test/key1", &count); if (!contents) { fail_test(__LINE__, "failed to ls data/test/key1: %x", GetLastError()); } else if (count != 1) { fail_test(__LINE__, "ls data/test/key1 had %d items", count); free(contents); } else if (strcmp(contents[0], "key2")) { fail_test(__LINE__, "ls data/test/key1 gave unexpected result %s", contents[0]); } xs_remove(xs_handle, "data/test"); /* Looks like most of the basic functionality works. Try * transactions. */ xs_handle2 = xs_domain_open(); if (!xs_handle2) win_err(1, "couldn't re-open domain interface"); if (!xs_write(xs_handle, "data/test/key1", "before")) fail_test(__LINE__, "failed to write to data/test/key1: %x", GetLastError()); if (!xs_transaction_start(xs_handle2)) win_err(1, "couldn't open a transaction on second handle"); if (!xs_write(xs_handle2, "data/test/key1", "after")) fail_test(__LINE__, "failed to write to data/test/key1 under transaction: %x", GetLastError()); if (!xs_transaction_end(xs_handle2, FALSE)) fail_test(__LINE__, "failed to write to end transaction: %x", GetLastError()); if (strcmp(xs_read(xs_handle, "data/test/key1", NULL), "after")) fail_test(__LINE__, "transaction didn't stick"); /* Now try aborting the transaction. */ if (!xs_write(xs_handle, "data/test/key1", "before")) fail_test(__LINE__, "failed to write to data/test/key1: %x", GetLastError()); if (!xs_transaction_start(xs_handle2)) win_err(1, "couldn't open a transaction on second handle"); if (!xs_write(xs_handle2, "data/test/key1", "after")) fail_test(__LINE__, "failed to write to data/test/key1 under transaction: %x", GetLastError()); if (!xs_transaction_end(xs_handle2, TRUE)) fail_test(__LINE__, "failed to write to end transaction: %x", GetLastError()); if (strcmp(xs_read(xs_handle, "data/test/key1", NULL), "before")) fail_test(__LINE__, "transaction didn't abort"); /* Try to arrange that the transaction fails. */ if (!xs_write(xs_handle, "data/test/key1", "before")) fail_test(__LINE__, "failed to write to data/test/key1: %x", GetLastError()); if (!xs_transaction_start(xs_handle2)) win_err(1, "couldn't open a transaction on second handle"); if (!xs_write(xs_handle2, "data/test/key1", "after")) fail_test(__LINE__, "failed to write to data/test/key1 under transaction: %x", GetLastError()); if (!xs_write(xs_handle, "data/test/key1", "other")) fail_test(__LINE__, "failed to write to data/test/key1: %x", GetLastError()); if (xs_transaction_end(xs_handle2, FALSE)) fail_test(__LINE__, "transaction succeeded when it shouldn't", GetLastError()); if (strcmp(xs_read(xs_handle, "data/test/key1", NULL), "other")) fail_test(__LINE__, "transaction did something strange"); if (!xs_write(xs_handle, "data/test/key1", "before1")) fail_test(__LINE__, "failed to write to data/test/key1: %x", GetLastError()); if (!xs_write(xs_handle, "data/test/key2", "before2")) fail_test(__LINE__, "failed to write to data/test/key2: %x", GetLastError()); if (!xs_transaction_start(xs_handle2)) win_err(1, "couldn't open a transaction on second handle"); if (!xs_write(xs_handle2, "data/test/key1", "after")) fail_test(__LINE__, "failed to write to data/test/key1 under transaction: %x", GetLastError()); t = xs_read(xs_handle2, "data/test/key2", NULL); if (!t) { fail_test(__LINE__, "failed to read data/test/key2 under transaction: %x", GetLastError()); } else { if (strcmp(t, "before2")) fail_test(__LINE__, "got wrong thing reading dtaa/test/key2 (%s)", t); free(t); } if (!xs_write(xs_handle, "data/test/key2", "other")) fail_test(__LINE__, "failed to write to data/test/key1: %x", GetLastError()); if (xs_transaction_end(xs_handle2, FALSE)) fail_test(__LINE__, "transaction succeeded when it shouldn't", GetLastError()); if (strcmp(xs_read(xs_handle, "data/test/key1", NULL), "before1")) fail_test(__LINE__, "transaction did something strange"); xs_daemon_close(xs_handle2); /* Try a couple of transaction error cases. */ xs_handle2 = xs_domain_open(); if (!xs_handle2) win_err(1, "couldn't re-open domain interface a second time"); if (!xs_transaction_start(xs_handle2)) win_err(1, "couldn't open a transaction for re-test"); if (xs_transaction_start(xs_handle2)) { fail_test(__LINE__, "openned two transactions on same handle"); } xs_daemon_close(xs_handle2); xs_handle2 = xs_domain_open(); if (!xs_handle2) win_err(1, "couldn't re-open domain interface a third time"); if (xs_transaction_end(xs_handle2, FALSE)) { fail_test(__LINE__, "ended transaction without starting it"); } if (!xs_transaction_start(xs_handle2)) win_err(1, "couldn't open a transaction for re-test"); if (!xs_transaction_end(xs_handle2, FALSE)) fail_test(__LINE__, "failed to end transaction"); if (xs_transaction_end(xs_handle2, FALSE)) { fail_test(__LINE__, "double-ended transaction"); } xs_daemon_close(xs_handle2); /* Transactions appear to be working, at least in their most basic form. Have a go at watches. */ event = CreateEvent(NULL, FALSE, FALSE, NULL); watch_h = xs_watch(xs_handle, "data/test/key1", event); if (watch_h < 0) { fail_test(__LINE__, "couldn't watch data/test/key1"); } else { while (WaitForSingleObject(event, 100) != WAIT_TIMEOUT) ; xs_write(xs_handle, "data/test/key1", "foo"); if (WaitForSingleObject(event, INFINITE) != WAIT_OBJECT_0) fail_test(__LINE__, "failed wait for data/test/key1: %x", GetLastError()); xs_write(xs_handle, "data/test/key1", "foo"); if (WaitForSingleObject(event, INFINITE) != WAIT_OBJECT_0) fail_test(__LINE__, "failed wait for data/test/key1: %x", GetLastError()); xs_write(xs_handle, "data/test/key1", "foo"); if (WaitForSingleObject(event, INFINITE) != WAIT_OBJECT_0) fail_test(__LINE__, "failed wait for data/test/key1: %x", GetLastError()); status = WaitForSingleObject(event, 2000); if (status != WAIT_TIMEOUT) fail_test(__LINE__, "should have timed out waiting for data/test/key1 (%d, %d)", status, GetLastError()); if (!xs_unwatch(xs_handle, watch_h)) fail_test(__LINE__, "failed to unwatch"); } /* Create two watches on the same key, kill one of them, and then make sure that the other one still works. */ watch_h = xs_watch(xs_handle, "data/test/key1/subkey", event); if (watch_h < 0) { fail_test(__LINE__, "couldn't watch data/test/key1/subkey"); } else { event2 = CreateEvent(NULL, FALSE, FALSE, NULL); watch_h2 = xs_watch(xs_handle, "data/test/key1/subkey", event); if (watch_h2 < 0) { fail_test(__LINE__, "couldn't double watch data/test/key1/subkey"); } else { if (!xs_unwatch(xs_handle, watch_h2)) fail_test(__LINE__, "failed to unwatch h2"); ResetEvent(event); xs_remove(xs_handle, "data/test/key1"); if (WaitForSingleObject(event, 5000) != WAIT_OBJECT_0) fail_test(__LINE__, "failed wait for data/test/key1: %x", GetLastError()); if (!xs_unwatch(xs_handle, watch_h)) fail_test(__LINE__, "failed to unwatch"); } } /* Watch a node, then modify it in a transaction, and check that the watch fires. */ watch_h = xs_watch(xs_handle, "data/test/key1", event); if (watch_h < 0) { fail_test(__LINE__, "couldn't watch data/test/key1"); } else { for (i = 0; i < 100; i++) { ResetEvent(event); do { if (!xs_transaction_start(xs_handle)) win_err(1, "couldn't open a transaction for watch test"); xs_write(xs_handle, "data/test/key1", "foo"); } while (!xs_transaction_end(xs_handle, FALSE)); if (WaitForSingleObject(event, 5000) != WAIT_OBJECT_0) fail_test(__LINE__, "failed wait for data/test/key1(%d): %x", i, GetLastError()); } if (!xs_unwatch(xs_handle, watch_h)) fail_test(__LINE__, "failed to unwatch"); } /* Make a lot of watches, make sure they all work. */ test_many_watches(); /* Try some different sized requests */ test_write_sizes(4096); xs_daemon_close(xs_handle); run_stress(); if (failed) { printf("failed\n"); return 1; } else { printf("passed\n"); return 0; } }