/* Try to crash the visitors */ static void test_visitor_in_fuzz(TestInputVisitorData *data, const void *unused) { int64_t ires; intList *ilres; bool bres; double nres; char *sres; EnumOne eres; Visitor *v; unsigned int i; char buf[10000]; for (i = 0; i < 100; i++) { unsigned int j; j = g_test_rand_int_range(0, sizeof(buf) - 1); buf[j] = '\0'; if (j != 0) { for (j--; j != 0; j--) { buf[j - 1] = (char)g_test_rand_int_range(0, 256); } } v = visitor_input_test_init(data, buf); visit_type_int(v, NULL, &ires, NULL); visitor_input_teardown(data, NULL); v = visitor_input_test_init(data, buf); visit_type_intList(v, NULL, &ilres, NULL); visitor_input_teardown(data, NULL); v = visitor_input_test_init(data, buf); visit_type_bool(v, NULL, &bres, NULL); visitor_input_teardown(data, NULL); v = visitor_input_test_init(data, buf); visit_type_number(v, NULL, &nres, NULL); visitor_input_teardown(data, NULL); v = visitor_input_test_init(data, buf); sres = NULL; visit_type_str(v, NULL, &sres, NULL); g_free(sres); visitor_input_teardown(data, NULL); v = visitor_input_test_init(data, buf); visit_type_EnumOne(v, NULL, &eres, NULL); visitor_input_teardown(data, NULL); } }
/* create a randomly-sized iovec with random vectors */ static void iov_random(struct iovec **iovp, unsigned *iov_cntp) { unsigned niov = g_test_rand_int_range(3,8); struct iovec *iov = g_malloc(niov * sizeof(*iov)); unsigned i; for (i = 0; i < niov; ++i) { iov[i].iov_len = g_test_rand_int_range(5,20); iov[i].iov_base = g_malloc(iov[i].iov_len); } *iovp = iov; *iov_cntp = niov; }
/* success if no crash or abort */ static void fuzz_registers(void) { unsigned int i; for (i = 0; i < 1000; i++) { uint8_t reg, val; reg = (uint8_t)g_test_rand_int_range(0, 8); val = (uint8_t)g_test_rand_int_range(0, 256); outb(FLOPPY_BASE + reg, val); inb(FLOPPY_BASE + reg); } }
static void encode_decode_range(void) { uint8_t *buffer = g_malloc0(PAGE_SIZE); uint8_t *compressed = g_malloc(PAGE_SIZE); uint8_t *test = g_malloc0(PAGE_SIZE); int i = 0, rc = 0; int dlen = 0; int diff_len = g_test_rand_int_range(0, PAGE_SIZE - 1006); for (i = diff_len; i > 0; i--) { buffer[1000 + i] = i; test[1000 + i] = i + 4; } buffer[1000 + diff_len + 3] = 103; test[1000 + diff_len + 3] = 107; buffer[1000 + diff_len + 5] = 105; test[1000 + diff_len + 5] = 109; /* test encode/decode */ dlen = xbzrle_encode_buffer(test, buffer, PAGE_SIZE, compressed, PAGE_SIZE); rc = xbzrle_decode_buffer(compressed, dlen, test, PAGE_SIZE); g_assert(rc < PAGE_SIZE); g_assert(memcmp(test, buffer, PAGE_SIZE) == 0); g_free(buffer); g_free(compressed); g_free(test); }
static void test_remove_node (void) { GtkRBTree *tree; tree = create_rbtree (3, 16, g_test_thorough ()); while (tree->root->count > 1) { GtkRBTree *find_tree; GtkRBNode *find_node; guint i; i = g_test_rand_int_range (0, tree->root->total_count); if (!_gtk_rbtree_find_index (tree, i, &find_tree, &find_node)) { /* We search an available index, so we mustn't fail. */ g_assert_not_reached (); } _gtk_rbtree_test (find_tree); if (find_tree->root->count == 1) { _gtk_rbtree_remove (find_tree); } else _gtk_rbtree_remove_node (find_tree, find_node); _gtk_rbtree_test (tree); } _gtk_rbtree_free (tree); }
static void setup (TestInfo *info, gconstpointer context) { gint i; i = GPOINTER_TO_INT (context); *info = tests[i]; /* Sadly, we can't use ONE location per test because GLib * caches XDG env vars, so g_get_*dir() will not change if we * update the environment, this sucks majorly. */ if (!xdg_location) { gchar *basename; /* NOTE: g_test_build_filename() doesn't work env vars G_TEST_* are not defined?? */ basename = g_strdup_printf ("%d", g_test_rand_int_range (0, G_MAXINT)); xdg_location = g_build_path (G_DIR_SEPARATOR_S, tests_data_dir, basename, NULL); g_free (basename); g_assert_true (g_setenv ("XDG_DATA_HOME", xdg_location, TRUE)); g_assert_true (g_setenv ("XDG_CACHE_HOME", xdg_location, TRUE)); g_assert_true (g_setenv ("TRACKER_DB_ONTOLOGIES_DIR", TOP_SRCDIR "/src/ontologies/", TRUE)); } }
static void test_qof_object_register( Fixture *fixture, gconstpointer pData ) { GList *books = NULL; gint32 list_length = g_test_rand_int_range( 0, 5 ); int i; QofObject *simple_object = NULL; for (i = 0; i < list_length; i++ ) { QofBook *book = qof_book_new(); g_assert( book ); books = g_list_prepend ( books, book ); g_assert_cmpint( g_list_length( books ), == , (i + 1) ); } g_assert_cmpint( list_length, == , g_list_length( books ) ); g_test_message( "Test null check" ); g_assert( qof_object_register( NULL ) == FALSE ); g_test_message( "Test new object register with book_begin specified" ); fixture->qofobject->book_begin = mock_book_begin; book_begin_struct.books = books; book_begin_struct.call_count = 0; g_assert( qof_object_register( fixture->qofobject ) == TRUE ); g_assert( qof_object_lookup( "my type object" ) == fixture->qofobject ); g_assert_cmpint( book_begin_struct.call_count, == , list_length ); g_test_message( "Test registering the same object one more time" ); book_begin_struct.call_count = 0; g_assert( qof_object_register( fixture->qofobject ) == FALSE ); g_assert( qof_object_lookup( "my type object" ) == fixture->qofobject ); g_assert_cmpint( book_begin_struct.call_count, == , 0 ); g_test_message( "Test new object register without book_begin specified" ); simple_object = new_object( "my type simple", "simple desc", EMPTY ); g_assert( qof_object_register( simple_object ) == TRUE ); g_assert( qof_object_lookup( "my type simple" ) == simple_object ); g_assert_cmpint( book_begin_struct.call_count, == , 0 ); g_test_message( "Test register simple object one more time" ); g_assert( qof_object_register( simple_object ) == FALSE ); g_assert( qof_object_lookup( "my type simple" ) == simple_object ); g_test_message( "Test book begin is called only one time when object is registered" ); simple_object->book_begin = mock_book_begin; book_begin_struct.books = books; book_begin_struct.call_count = 0; g_assert( qof_object_register( simple_object ) == FALSE ); g_assert_cmpint( book_begin_struct.call_count, == , 0 ); g_list_foreach( books, (GFunc) qof_book_destroy, NULL ); g_list_free( books ); g_free( simple_object ); }
/* * Safely generates objects and registers them * * Input: min_objects - minimum number of objects to be generated (should be between 0 and 5) * mock_filed - function in qofobject to be mocked * Output: number of generated objects */ static gint32 generate_and_register_objects( guint min_objects, MockFields mock_field ) { gint32 list_length = g_test_rand_int_range( min_objects, 5 ); const char *types[5] = {"type1", "type2", "type3", "type4", "type5"}; int i; g_assert_cmpint( min_objects, >= , 0 ); g_assert_cmpint( min_objects, < , 5 ); for (i = 0; i < list_length; i++ ) { QofObject *object = new_object( types[i], "desc", mock_field ); g_assert( object ); g_assert( qof_object_register( object ) ); g_assert_cmpint( g_list_length( get_object_modules() ), == , (i + 1) ); } g_assert_cmpint( list_length, == , g_list_length( get_object_modules() ) ); return list_length; }
static void test_encode_decode_unchanged(void) { uint8_t *compressed = g_malloc0(PAGE_SIZE); uint8_t *test = g_malloc0(PAGE_SIZE); int i = 0; int dlen = 0; int diff_len = g_test_rand_int_range(0, PAGE_SIZE - 1006); for (i = diff_len; i > 0; i--) { test[1000 + i] = i + 4; } test[1000 + diff_len + 3] = 107; test[1000 + diff_len + 5] = 109; /* test unchanged buffer */ dlen = xbzrle_encode_buffer(test, test, PAGE_SIZE, compressed, PAGE_SIZE); g_assert(dlen == 0); g_free(test); g_free(compressed); }
static void test_encode_decode_zero(void) { uint8_t *buffer = g_malloc0(PAGE_SIZE); uint8_t *compressed = g_malloc0(PAGE_SIZE); int i = 0; int dlen = 0; int diff_len = g_test_rand_int_range(0, PAGE_SIZE - 1006); for (i = diff_len; i > 0; i--) { buffer[1000 + i] = i; } buffer[1000 + diff_len + 3] = 103; buffer[1000 + diff_len + 5] = 105; /* encode zero page */ dlen = xbzrle_encode_buffer(buffer, buffer, PAGE_SIZE, compressed, PAGE_SIZE); g_assert(dlen == 0); g_free(buffer); g_free(compressed); }
static void test_qof_object_foreach_sorted( Fixture *fixture, gconstpointer pData ) { int i; gint32 list_length = g_test_rand_int_range( 0, 5 ); gint user_data; QofBook *book = NULL; QofCollection *col = NULL; foreach_for_sorted_struct.instances = NULL; /* setup */ book = qof_book_new(); g_assert( book ); g_assert_cmpint( g_list_length( get_object_modules() ), == , 0 ); qof_object_register( fixture->qofobject ); g_assert_cmpint( g_list_length( get_object_modules() ), == , 1 ); fixture->qofobject->foreach = mock_foreach_for_sorted; /* init instances */ col = qof_book_get_collection( book, fixture->qofobject->e_type ); for (i = 0; i < list_length; i++ ) { QofInstance * inst = g_object_new( QOF_TYPE_INSTANCE, NULL ); g_assert( QOF_IS_INSTANCE( inst ) ); foreach_for_sorted_struct.instances = g_list_append( foreach_for_sorted_struct.instances, inst ); qof_collection_insert_entity( col, inst ); } g_assert_cmpint( list_length, == , g_list_length( foreach_for_sorted_struct.instances ) ); foreach_for_sorted_struct.call_count = 0; foreach_for_sorted_struct.user_data = &user_data; qof_object_foreach_sorted( fixture->qofobject->e_type, book, mock_instance_foreach_cb_for_sorted, ( gpointer ) &user_data ); g_assert_cmpint( list_length, == , foreach_for_sorted_struct.call_count ); qof_book_destroy( book ); g_list_free( foreach_for_sorted_struct.instances ); }
static void wmem_test_allocator(wmem_allocator_type_t type, wmem_verify_func verify, int iterations) { int i; char *ptrs[MAX_SIMULTANEOUS_ALLOCS]; wmem_allocator_t *allocator; allocator = wmem_allocator_force_new(type); if (verify) (*verify)(allocator); /* start with some fairly simple deterministic tests */ wmem_test_allocator_det(allocator, verify, 8); wmem_test_allocator_det(allocator, verify, 64); wmem_test_allocator_det(allocator, verify, 512); for (i=0; i<MAX_SIMULTANEOUS_ALLOCS; i++) { ptrs[i] = wmem_alloc0_array(allocator, char, 32); } if (verify) (*verify)(allocator); wmem_free_all(allocator); wmem_gc(allocator); if (verify) (*verify)(allocator); /* now do some random fuzz-like tests */ /* reset our ptr array */ for (i=0; i<MAX_SIMULTANEOUS_ALLOCS; i++) { ptrs[i] = NULL; } /* Run enough iterations to fill the array 32 times */ for (i=0; i<iterations; i++) { gint ptrs_index; gint new_size; /* returns value 0 <= x < MAX_SIMULTANEOUS_ALLOCS which is a valid * index into ptrs */ ptrs_index = g_test_rand_int_range(0, MAX_SIMULTANEOUS_ALLOCS); if (ptrs[ptrs_index] == NULL) { /* if that index is unused, allocate some random amount of memory * between 0 and MAX_ALLOC_SIZE */ new_size = g_test_rand_int_range(0, MAX_ALLOC_SIZE); ptrs[ptrs_index] = (char *) wmem_alloc0(allocator, new_size); } else if (g_test_rand_bit()) { /* the index is used, and our random bit has determined we will be * reallocating instead of freeing. Do so to some random size * between 0 and MAX_ALLOC_SIZE, then manually zero the * new memory */ new_size = g_test_rand_int_range(0, MAX_ALLOC_SIZE); ptrs[ptrs_index] = (char *) wmem_realloc(allocator, ptrs[ptrs_index], new_size); memset(ptrs[ptrs_index], 0, new_size); } else { /* the index is used, and our random bit has determined we will be * freeing instead of reallocating. Do so and NULL the pointer for * the next iteration. */ wmem_free(allocator, ptrs[ptrs_index]); ptrs[ptrs_index] = NULL; } if (verify) (*verify)(allocator); } wmem_destroy_allocator(allocator); }
/* --- test functions --- */ static void pspec_select_value (GParamSpec *pspec, GValue *value, double dvalue) { /* generate a value suitable for pspec */ if (G_IS_PARAM_SPEC_CHAR (pspec)) ASSIGN_VALUE (g_value_set_char, value, GParamSpecChar*, pspec, default_value, minimum, maximum, dvalue); else if (G_IS_PARAM_SPEC_UCHAR (pspec)) ASSIGN_VALUE (g_value_set_uchar, value, GParamSpecUChar*, pspec, default_value, minimum, maximum, dvalue); else if (G_IS_PARAM_SPEC_INT (pspec)) ASSIGN_VALUE (g_value_set_int, value, GParamSpecInt*, pspec, default_value, minimum, maximum, dvalue); else if (G_IS_PARAM_SPEC_UINT (pspec)) ASSIGN_VALUE (g_value_set_uint, value, GParamSpecUInt*, pspec, default_value, minimum, maximum, dvalue); else if (G_IS_PARAM_SPEC_LONG (pspec)) ASSIGN_VALUE (g_value_set_long, value, GParamSpecLong*, pspec, default_value, minimum, maximum, dvalue); else if (G_IS_PARAM_SPEC_ULONG (pspec)) ASSIGN_VALUE (g_value_set_ulong, value, GParamSpecULong*, pspec, default_value, minimum, maximum, dvalue); else if (G_IS_PARAM_SPEC_INT64 (pspec)) ASSIGN_VALUE (g_value_set_int64, value, GParamSpecInt64*, pspec, default_value, minimum, maximum, dvalue); else if (G_IS_PARAM_SPEC_UINT64 (pspec)) ASSIGN_VALUE (g_value_set_uint64, value, GParamSpecUInt64*, pspec, default_value, minimum, maximum, dvalue); else if (G_IS_PARAM_SPEC_FLOAT (pspec)) ASSIGN_VALUE (g_value_set_float, value, GParamSpecFloat*, pspec, default_value, minimum, maximum, dvalue); else if (G_IS_PARAM_SPEC_DOUBLE (pspec)) ASSIGN_VALUE (g_value_set_double, value, GParamSpecDouble*, pspec, default_value, minimum, maximum, dvalue); else if (G_IS_PARAM_SPEC_BOOLEAN (pspec)) g_value_set_boolean (value, SELECT_VALUE (dvalue, ((GParamSpecBoolean*) pspec)->default_value, FALSE, TRUE)); else if (G_IS_PARAM_SPEC_UNICHAR (pspec)) g_value_set_uint (value, SELECT_VALUE (dvalue, ((GParamSpecUnichar*) pspec)->default_value, FALSE, TRUE)); else if (G_IS_PARAM_SPEC_GTYPE (pspec)) g_value_set_gtype (value, SELECT_VALUE ((int) dvalue, ((GParamSpecGType*) pspec)->is_a_type, 0, GTK_TYPE_WIDGET)); else if (G_IS_PARAM_SPEC_STRING (pspec)) { GParamSpecString *sspec = (GParamSpecString*) pspec; if (dvalue >= +2) g_value_set_string (value, sspec->default_value); if (dvalue > 0 && sspec->cset_first && sspec->cset_nth) g_value_take_string (value, g_strdup_printf ("%c%c", sspec->cset_first[0], sspec->cset_nth[0])); else /* if (sspec->ensure_non_null) */ g_value_set_string (value, ""); } else if (G_IS_PARAM_SPEC_ENUM (pspec)) { GParamSpecEnum *espec = (GParamSpecEnum*) pspec; if (dvalue >= +2) g_value_set_enum (value, espec->default_value); if (dvalue >= 0 && dvalue <= 1) g_value_set_enum (value, espec->enum_class->values[(int) ((espec->enum_class->n_values - 1) * dvalue)].value); else if (dvalue <= -1) g_value_set_enum (value, espec->enum_class->values[g_test_rand_int_range (0, espec->enum_class->n_values)].value); } else if (G_IS_PARAM_SPEC_FLAGS (pspec)) { GParamSpecFlags *fspec = (GParamSpecFlags*) pspec; if (dvalue >= +2) g_value_set_flags (value, fspec->default_value); if (dvalue >= 0 && dvalue <= 1) g_value_set_flags (value, fspec->flags_class->values[(int) ((fspec->flags_class->n_values - 1) * dvalue)].value); else if (dvalue <= -1) g_value_set_flags (value, fspec->flags_class->values[g_test_rand_int_range (0, fspec->flags_class->n_values)].value); } /* unimplemented: * G_IS_PARAM_SPEC_PARAM * G_IS_PARAM_SPEC_BOXED * G_IS_PARAM_SPEC_POINTER * G_IS_PARAM_SPEC_VALUE_ARRAY * G_IS_PARAM_SPEC_OBJECT */ }
static void test_discard_back(void) { struct iovec *iov; unsigned int iov_cnt; unsigned int iov_cnt_tmp; void *old_base; size_t size; size_t ret; /* Discard zero bytes */ iov_random(&iov, &iov_cnt); iov_cnt_tmp = iov_cnt; ret = iov_discard_back(iov, &iov_cnt_tmp, 0); g_assert(ret == 0); g_assert(iov_cnt_tmp == iov_cnt); iov_free(iov, iov_cnt); /* Discard more bytes than vector size */ iov_random(&iov, &iov_cnt); iov_cnt_tmp = iov_cnt; size = iov_size(iov, iov_cnt); ret = iov_discard_back(iov, &iov_cnt_tmp, size + 1); g_assert(ret == size); g_assert(iov_cnt_tmp == 0); iov_free(iov, iov_cnt); /* Discard entire vector */ iov_random(&iov, &iov_cnt); iov_cnt_tmp = iov_cnt; size = iov_size(iov, iov_cnt); ret = iov_discard_back(iov, &iov_cnt_tmp, size); g_assert(ret == size); g_assert(iov_cnt_tmp == 0); iov_free(iov, iov_cnt); /* Discard within last element */ iov_random(&iov, &iov_cnt); iov_cnt_tmp = iov_cnt; old_base = iov[iov_cnt - 1].iov_base; size = g_test_rand_int_range(1, iov[iov_cnt - 1].iov_len); ret = iov_discard_back(iov, &iov_cnt_tmp, size); g_assert(ret == size); g_assert(iov_cnt_tmp == iov_cnt); g_assert(iov[iov_cnt - 1].iov_base == old_base); iov_free(iov, iov_cnt); /* Discard entire last element */ iov_random(&iov, &iov_cnt); iov_cnt_tmp = iov_cnt; old_base = iov[iov_cnt - 1].iov_base; size = iov[iov_cnt - 1].iov_len; ret = iov_discard_back(iov, &iov_cnt_tmp, size); g_assert(ret == size); g_assert(iov_cnt_tmp == iov_cnt - 1); iov_free(iov, iov_cnt); /* Discard within second-to-last element */ iov_random(&iov, &iov_cnt); iov_cnt_tmp = iov_cnt; old_base = iov[iov_cnt - 2].iov_base; size = iov[iov_cnt - 1].iov_len + g_test_rand_int_range(1, iov[iov_cnt - 2].iov_len); ret = iov_discard_back(iov, &iov_cnt_tmp, size); g_assert(ret == size); g_assert(iov_cnt_tmp == iov_cnt - 1); g_assert(iov[iov_cnt - 2].iov_base == old_base); iov_free(iov, iov_cnt); }
static void test_discard_front(void) { struct iovec *iov; struct iovec *iov_tmp; unsigned int iov_cnt; unsigned int iov_cnt_tmp; void *old_base; size_t size; size_t ret; /* Discard zero bytes */ iov_random(&iov, &iov_cnt); iov_tmp = iov; iov_cnt_tmp = iov_cnt; ret = iov_discard_front(&iov_tmp, &iov_cnt_tmp, 0); g_assert(ret == 0); g_assert(iov_tmp == iov); g_assert(iov_cnt_tmp == iov_cnt); iov_free(iov, iov_cnt); /* Discard more bytes than vector size */ iov_random(&iov, &iov_cnt); iov_tmp = iov; iov_cnt_tmp = iov_cnt; size = iov_size(iov, iov_cnt); ret = iov_discard_front(&iov_tmp, &iov_cnt_tmp, size + 1); g_assert(ret == size); g_assert(iov_cnt_tmp == 0); iov_free(iov, iov_cnt); /* Discard entire vector */ iov_random(&iov, &iov_cnt); iov_tmp = iov; iov_cnt_tmp = iov_cnt; size = iov_size(iov, iov_cnt); ret = iov_discard_front(&iov_tmp, &iov_cnt_tmp, size); g_assert(ret == size); g_assert(iov_cnt_tmp == 0); iov_free(iov, iov_cnt); /* Discard within first element */ iov_random(&iov, &iov_cnt); iov_tmp = iov; iov_cnt_tmp = iov_cnt; old_base = iov->iov_base; size = g_test_rand_int_range(1, iov->iov_len); ret = iov_discard_front(&iov_tmp, &iov_cnt_tmp, size); g_assert(ret == size); g_assert(iov_tmp == iov); g_assert(iov_cnt_tmp == iov_cnt); g_assert(iov_tmp->iov_base == old_base + size); iov_tmp->iov_base = old_base; /* undo before g_free() */ iov_free(iov, iov_cnt); /* Discard entire first element */ iov_random(&iov, &iov_cnt); iov_tmp = iov; iov_cnt_tmp = iov_cnt; ret = iov_discard_front(&iov_tmp, &iov_cnt_tmp, iov->iov_len); g_assert(ret == iov->iov_len); g_assert(iov_tmp == iov + 1); g_assert(iov_cnt_tmp == iov_cnt - 1); iov_free(iov, iov_cnt); /* Discard within second element */ iov_random(&iov, &iov_cnt); iov_tmp = iov; iov_cnt_tmp = iov_cnt; old_base = iov[1].iov_base; size = iov->iov_len + g_test_rand_int_range(1, iov[1].iov_len); ret = iov_discard_front(&iov_tmp, &iov_cnt_tmp, size); g_assert(ret == size); g_assert(iov_tmp == iov + 1); g_assert(iov_cnt_tmp == iov_cnt - 1); g_assert(iov_tmp->iov_base == old_base + (size - iov->iov_len)); iov_tmp->iov_base = old_base; /* undo before g_free() */ iov_free(iov, iov_cnt); }
static void test_io(void) { #ifndef _WIN32 /* socketpair(PF_UNIX) which does not exist on windows */ int sv[2]; int r; unsigned i, j, k, s, t; fd_set fds; unsigned niov; struct iovec *iov, *siov; unsigned char *buf; size_t sz; iov_random(&iov, &niov); sz = iov_size(iov, niov); buf = g_malloc(sz); for (i = 0; i < sz; ++i) { buf[i] = i & 255; } iov_from_buf(iov, niov, 0, buf, sz); siov = g_malloc(sizeof(*iov) * niov); memcpy(siov, iov, sizeof(*iov) * niov); if (socketpair(PF_UNIX, SOCK_STREAM, 0, sv) < 0) { perror("socketpair"); exit(1); } FD_ZERO(&fds); t = 0; if (fork() == 0) { /* writer */ close(sv[0]); FD_SET(sv[1], &fds); fcntl(sv[1], F_SETFL, O_RDWR|O_NONBLOCK); r = g_test_rand_int_range(sz / 2, sz); setsockopt(sv[1], SOL_SOCKET, SO_SNDBUF, &r, sizeof(r)); for (i = 0; i <= sz; ++i) { for (j = i; j <= sz; ++j) { k = i; do { s = g_test_rand_int_range(0, j - k + 1); r = iov_send(sv[1], iov, niov, k, s); g_assert(memcmp(iov, siov, sizeof(*iov)*niov) == 0); if (r >= 0) { k += r; t += r; usleep(g_test_rand_int_range(0, 30)); } else if (errno == EAGAIN) { select(sv[1]+1, NULL, &fds, NULL, NULL); continue; } else { perror("send"); exit(1); } } while(k < j); } } exit(0); } else { /* reader & verifier */ close(sv[1]); FD_SET(sv[0], &fds); fcntl(sv[0], F_SETFL, O_RDWR|O_NONBLOCK); r = g_test_rand_int_range(sz / 2, sz); setsockopt(sv[0], SOL_SOCKET, SO_RCVBUF, &r, sizeof(r)); usleep(500000); for (i = 0; i <= sz; ++i) { for (j = i; j <= sz; ++j) { k = i; iov_memset(iov, niov, 0, 0xff, -1); do { s = g_test_rand_int_range(0, j - k + 1); r = iov_recv(sv[0], iov, niov, k, s); g_assert(memcmp(iov, siov, sizeof(*iov)*niov) == 0); if (r > 0) { k += r; t += r; } else if (!r) { if (s) { break; } } else if (errno == EAGAIN) { select(sv[0]+1, &fds, NULL, NULL, NULL); continue; } else { perror("recv"); exit(1); } } while(k < j); test_iov_bytes(iov, niov, i, j - i); } } } #endif }