Exemplo n.º 1
0
TEST_END

static void *
thd_start_reincarnated(void *arg) {
	tsd_t *tsd = tsd_fetch();
	assert(tsd);

	void *p = malloc(1);
	assert_ptr_not_null(p, "Unexpected malloc() failure");

	/* Manually trigger reincarnation. */
	assert_ptr_not_null(tsd_arena_get(tsd),
	    "Should have tsd arena set.");
	tsd_cleanup((void *)tsd);
	assert_ptr_null(*tsd_arenap_get_unsafe(tsd),
	    "TSD arena should have been cleared.");
	assert_u_eq(tsd->state, tsd_state_purgatory,
	    "TSD state should be purgatory\n");

	free(p);
	assert_u_eq(tsd->state, tsd_state_reincarnated,
	    "TSD state should be reincarnated\n");
	p = mallocx(1, MALLOCX_TCACHE_NONE);
	assert_ptr_not_null(p, "Unexpected malloc() failure");
	assert_ptr_null(*tsd_arenap_get_unsafe(tsd),
	    "Should not have tsd arena set after reincarnation.");

	free(p);
	tsd_cleanup((void *)tsd);
	assert_ptr_null(*tsd_arenap_get_unsafe(tsd),
	    "TSD arena should have been cleared after 2nd cleanup.");

	return NULL;
}
Exemplo n.º 2
0
static void *
thd_start(void *arg) {
	int d = (int)(uintptr_t)arg;
	void *p;

	tsd_t *tsd = tsd_fetch();
	assert_x_eq(tsd_test_data_get(tsd), MALLOC_TSD_TEST_DATA_INIT,
	    "Initial tsd get should return initialization value");

	p = malloc(1);
	assert_ptr_not_null(p, "Unexpected malloc() failure");

	tsd_test_data_set(tsd, d);
	assert_x_eq(tsd_test_data_get(tsd), d,
	    "After tsd set, tsd get should return value that was set");

	d = 0;
	assert_x_eq(tsd_test_data_get(tsd), (int)(uintptr_t)arg,
	    "Resetting local data should have no effect on tsd");

	tsd_test_callback_set(tsd, &data_cleanup);

	free(p);
	return NULL;
}
Exemplo n.º 3
0
static void *
base_map(tsdn_t *tsdn, extent_hooks_t *extent_hooks, unsigned ind, size_t size) {
	void *addr;
	bool zero = true;
	bool commit = true;

	/* Use huge page sizes and alignment regardless of opt_metadata_thp. */
	assert(size == HUGEPAGE_CEILING(size));
	size_t alignment = HUGEPAGE;
	if (extent_hooks == &extent_hooks_default) {
		addr = extent_alloc_mmap(NULL, size, alignment, &zero, &commit);
	} else {
		/* No arena context as we are creating new arenas. */
		tsd_t *tsd = tsdn_null(tsdn) ? tsd_fetch() : tsdn_tsd(tsdn);
		pre_reentrancy(tsd, NULL);
		addr = extent_hooks->alloc(extent_hooks, NULL, size, alignment,
		    &zero, &commit, ind);
		post_reentrancy(tsd);
	}

	return addr;
}
Exemplo n.º 4
0
static void
base_unmap(tsdn_t *tsdn, extent_hooks_t *extent_hooks, unsigned ind, void *addr,
    size_t size) {
	/*
	 * Cascade through dalloc, decommit, purge_forced, and purge_lazy,
	 * stopping at first success.  This cascade is performed for consistency
	 * with the cascade in extent_dalloc_wrapper() because an application's
	 * custom hooks may not support e.g. dalloc.  This function is only ever
	 * called as a side effect of arena destruction, so although it might
	 * seem pointless to do anything besides dalloc here, the application
	 * may in fact want the end state of all associated virtual memory to be
	 * in some consistent-but-allocated state.
	 */
	if (extent_hooks == &extent_hooks_default) {
		if (!extent_dalloc_mmap(addr, size)) {
			goto label_done;
		}
		if (!pages_decommit(addr, size)) {
			goto label_done;
		}
		if (!pages_purge_forced(addr, size)) {
			goto label_done;
		}
		if (!pages_purge_lazy(addr, size)) {
			goto label_done;
		}
		/* Nothing worked.  This should never happen. */
		not_reached();
	} else {
		tsd_t *tsd = tsdn_null(tsdn) ? tsd_fetch() : tsdn_tsd(tsdn);
		pre_reentrancy(tsd, NULL);
		if (extent_hooks->dalloc != NULL &&
		    !extent_hooks->dalloc(extent_hooks, addr, size, true,
		    ind)) {
			goto label_post_reentrancy;
		}
		if (extent_hooks->decommit != NULL &&
		    !extent_hooks->decommit(extent_hooks, addr, size, 0, size,
		    ind)) {
			goto label_post_reentrancy;
		}
		if (extent_hooks->purge_forced != NULL &&
		    !extent_hooks->purge_forced(extent_hooks, addr, size, 0,
		    size, ind)) {
			goto label_post_reentrancy;
		}
		if (extent_hooks->purge_lazy != NULL &&
		    !extent_hooks->purge_lazy(extent_hooks, addr, size, 0, size,
		    ind)) {
			goto label_post_reentrancy;
		}
		/* Nothing worked.  That's the application's problem. */
	label_post_reentrancy:
		post_reentrancy(tsd);
	}
label_done:
	if (metadata_thp_madvise()) {
		/* Set NOHUGEPAGE after unmap to avoid kernel defrag. */
		assert(__builtin_is_aligned(addr, HUGEPAGE) &&
		    (size & HUGEPAGE_MASK) == 0);
		pages_nohuge(addr, size);
	}
}
Exemplo n.º 5
0
Arquivo: ckh.c Projeto: DawidvC/chapel
TEST_END

TEST_BEGIN(test_count_insert_search_remove)
{
	tsd_t *tsd;
	ckh_t ckh;
	const char *strs[] = {
	    "a string",
	    "A string",
	    "a string.",
	    "A string."
	};
	const char *missing = "A string not in the hash table.";
	size_t i;

	tsd = tsd_fetch();

	assert_false(ckh_new(tsd, &ckh, 2, ckh_string_hash,
	    ckh_string_keycomp), "Unexpected ckh_new() error");
	assert_zu_eq(ckh_count(&ckh), 0,
	    "ckh_count() should return %zu, but it returned %zu", ZU(0),
	    ckh_count(&ckh));

	/* Insert. */
	for (i = 0; i < sizeof(strs)/sizeof(const char *); i++) {
		ckh_insert(tsd, &ckh, strs[i], strs[i]);
		assert_zu_eq(ckh_count(&ckh), i+1,
		    "ckh_count() should return %zu, but it returned %zu", i+1,
		    ckh_count(&ckh));
	}

	/* Search. */
	for (i = 0; i < sizeof(strs)/sizeof(const char *); i++) {
		union {
			void *p;
			const char *s;
		} k, v;
		void **kp, **vp;
		const char *ks, *vs;

		kp = (i & 1) ? &k.p : NULL;
		vp = (i & 2) ? &v.p : NULL;
		k.p = NULL;
		v.p = NULL;
		assert_false(ckh_search(&ckh, strs[i], kp, vp),
		    "Unexpected ckh_search() error");

		ks = (i & 1) ? strs[i] : (const char *)NULL;
		vs = (i & 2) ? strs[i] : (const char *)NULL;
		assert_ptr_eq((void *)ks, (void *)k.s, "Key mismatch, i=%zu",
		    i);
		assert_ptr_eq((void *)vs, (void *)v.s, "Value mismatch, i=%zu",
		    i);
	}
	assert_true(ckh_search(&ckh, missing, NULL, NULL),
	    "Unexpected ckh_search() success");

	/* Remove. */
	for (i = 0; i < sizeof(strs)/sizeof(const char *); i++) {
		union {
			void *p;
			const char *s;
		} k, v;
		void **kp, **vp;
		const char *ks, *vs;

		kp = (i & 1) ? &k.p : NULL;
		vp = (i & 2) ? &v.p : NULL;
		k.p = NULL;
		v.p = NULL;
		assert_false(ckh_remove(tsd, &ckh, strs[i], kp, vp),
		    "Unexpected ckh_remove() error");

		ks = (i & 1) ? strs[i] : (const char *)NULL;
		vs = (i & 2) ? strs[i] : (const char *)NULL;
		assert_ptr_eq((void *)ks, (void *)k.s, "Key mismatch, i=%zu",
		    i);
		assert_ptr_eq((void *)vs, (void *)v.s, "Value mismatch, i=%zu",
		    i);
		assert_zu_eq(ckh_count(&ckh),
		    sizeof(strs)/sizeof(const char *) - i - 1,
		    "ckh_count() should return %zu, but it returned %zu",
		        sizeof(strs)/sizeof(const char *) - i - 1,
		    ckh_count(&ckh));
	}

	ckh_delete(tsd, &ckh);
}
Exemplo n.º 6
0
Arquivo: ckh.c Projeto: DawidvC/chapel
TEST_END

TEST_BEGIN(test_insert_iter_remove)
{
#define	NITEMS ZU(1000)
	tsd_t *tsd;
	ckh_t ckh;
	void **p[NITEMS];
	void *q, *r;
	size_t i;

	tsd = tsd_fetch();

	assert_false(ckh_new(tsd, &ckh, 2, ckh_pointer_hash,
	    ckh_pointer_keycomp), "Unexpected ckh_new() error");

	for (i = 0; i < NITEMS; i++) {
		p[i] = mallocx(i+1, 0);
		assert_ptr_not_null(p[i], "Unexpected mallocx() failure");
	}

	for (i = 0; i < NITEMS; i++) {
		size_t j;

		for (j = i; j < NITEMS; j++) {
			assert_false(ckh_insert(tsd, &ckh, p[j], p[j]),
			    "Unexpected ckh_insert() failure");
			assert_false(ckh_search(&ckh, p[j], &q, &r),
			    "Unexpected ckh_search() failure");
			assert_ptr_eq(p[j], q, "Key pointer mismatch");
			assert_ptr_eq(p[j], r, "Value pointer mismatch");
		}

		assert_zu_eq(ckh_count(&ckh), NITEMS,
		    "ckh_count() should return %zu, but it returned %zu",
		    NITEMS, ckh_count(&ckh));

		for (j = i + 1; j < NITEMS; j++) {
			assert_false(ckh_search(&ckh, p[j], NULL, NULL),
			    "Unexpected ckh_search() failure");
			assert_false(ckh_remove(tsd, &ckh, p[j], &q, &r),
			    "Unexpected ckh_remove() failure");
			assert_ptr_eq(p[j], q, "Key pointer mismatch");
			assert_ptr_eq(p[j], r, "Value pointer mismatch");
			assert_true(ckh_search(&ckh, p[j], NULL, NULL),
			    "Unexpected ckh_search() success");
			assert_true(ckh_remove(tsd, &ckh, p[j], &q, &r),
			    "Unexpected ckh_remove() success");
		}

		{
			bool seen[NITEMS];
			size_t tabind;

			memset(seen, 0, sizeof(seen));

			for (tabind = 0; !ckh_iter(&ckh, &tabind, &q, &r);) {
				size_t k;

				assert_ptr_eq(q, r, "Key and val not equal");

				for (k = 0; k < NITEMS; k++) {
					if (p[k] == q) {
						assert_false(seen[k],
						    "Item %zu already seen", k);
						seen[k] = true;
						break;
					}
				}
			}

			for (j = 0; j < i + 1; j++)
				assert_true(seen[j], "Item %zu not seen", j);
			for (; j < NITEMS; j++)
				assert_false(seen[j], "Item %zu seen", j);
		}
	}

	for (i = 0; i < NITEMS; i++) {
		assert_false(ckh_search(&ckh, p[i], NULL, NULL),
		    "Unexpected ckh_search() failure");
		assert_false(ckh_remove(tsd, &ckh, p[i], &q, &r),
		    "Unexpected ckh_remove() failure");
		assert_ptr_eq(p[i], q, "Key pointer mismatch");
		assert_ptr_eq(p[i], r, "Value pointer mismatch");
		assert_true(ckh_search(&ckh, p[i], NULL, NULL),
		    "Unexpected ckh_search() success");
		assert_true(ckh_remove(tsd, &ckh, p[i], &q, &r),
		    "Unexpected ckh_remove() success");
		dallocx(p[i], 0);
	}

	assert_zu_eq(ckh_count(&ckh), 0,
	    "ckh_count() should return %zu, but it returned %zu",
	    ZU(0), ckh_count(&ckh));
	ckh_delete(tsd, &ckh);
#undef NITEMS
}