server-skynet-source-3rd-je.../test/unit/prof_thread_name.c

131 lines
3.7 KiB
C
Raw Normal View History

#include "test/jemalloc_test.h"
static void
mallctl_thread_name_get_impl(const char *thread_name_expected, const char *func,
int line) {
const char *thread_name_old;
size_t sz;
sz = sizeof(thread_name_old);
expect_d_eq(mallctl("thread.prof.name", (void *)&thread_name_old, &sz,
NULL, 0), 0,
"%s():%d: Unexpected mallctl failure reading thread.prof.name",
func, line);
expect_str_eq(thread_name_old, thread_name_expected,
"%s():%d: Unexpected thread.prof.name value", func, line);
}
static void
mallctl_thread_name_set_impl(const char *thread_name, const char *func,
int line) {
expect_d_eq(mallctl("thread.prof.name", NULL, NULL,
(void *)&thread_name, sizeof(thread_name)), 0,
"%s():%d: Unexpected mallctl failure writing thread.prof.name",
func, line);
mallctl_thread_name_get_impl(thread_name, func, line);
}
#define mallctl_thread_name_get(a) \
mallctl_thread_name_get_impl(a, __func__, __LINE__)
#define mallctl_thread_name_set(a) \
mallctl_thread_name_set_impl(a, __func__, __LINE__)
TEST_BEGIN(test_prof_thread_name_validation) {
test_skip_if(!config_prof);
test_skip_if(opt_prof_sys_thread_name);
mallctl_thread_name_get("");
const char *test_name1 = "test case1";
mallctl_thread_name_set(test_name1);
/* Test name longer than the max len. */
char long_name[] =
"test case longer than expected; test case longer than expected";
expect_zu_gt(strlen(long_name), PROF_THREAD_NAME_MAX_LEN,
"Long test name not long enough");
const char *test_name_long = long_name;
expect_d_eq(mallctl("thread.prof.name", NULL, NULL,
(void *)&test_name_long, sizeof(test_name_long)), 0,
"Unexpected mallctl failure from thread.prof.name");
/* Long name cut to match. */
long_name[PROF_THREAD_NAME_MAX_LEN - 1] = '\0';
mallctl_thread_name_get(test_name_long);
/* NULL input shouldn't be allowed. */
const char *test_name2 = NULL;
expect_d_eq(mallctl("thread.prof.name", NULL, NULL,
(void *)&test_name2, sizeof(test_name2)), EINVAL,
"Unexpected mallctl result writing to thread.prof.name");
/* '\n' shouldn't be allowed. */
const char *test_name3 = "test\ncase";
expect_d_eq(mallctl("thread.prof.name", NULL, NULL,
(void *)&test_name3, sizeof(test_name3)), EINVAL,
"Unexpected mallctl result writing \"%s\" to thread.prof.name",
test_name3);
/* Simultaneous read/write shouldn't be allowed. */
const char *thread_name_old;
size_t sz = sizeof(thread_name_old);
expect_d_eq(mallctl("thread.prof.name", (void *)&thread_name_old, &sz,
(void *)&test_name1, sizeof(test_name1)), EPERM,
"Unexpected mallctl result from thread.prof.name");
mallctl_thread_name_set("");
}
TEST_END
static void *
thd_start(void *varg) {
unsigned thd_ind = *(unsigned *)varg;
char thread_name[16] = "";
unsigned i;
malloc_snprintf(thread_name, sizeof(thread_name), "thread %u", thd_ind);
mallctl_thread_name_get("");
mallctl_thread_name_set(thread_name);
#define NRESET 25
for (i = 0; i < NRESET; i++) {
expect_d_eq(mallctl("prof.reset", NULL, NULL, NULL, 0), 0,
"Unexpected error while resetting heap profile data");
mallctl_thread_name_get(thread_name);
}
mallctl_thread_name_set(thread_name);
mallctl_thread_name_set("");
return NULL;
#undef NRESET
}
TEST_BEGIN(test_prof_thread_name_threaded) {
test_skip_if(!config_prof);
test_skip_if(opt_prof_sys_thread_name);
#define NTHREADS 4
thd_t thds[NTHREADS];
unsigned thd_args[NTHREADS];
unsigned i;
for (i = 0; i < NTHREADS; i++) {
thd_args[i] = i;
thd_create(&thds[i], thd_start, (void *)&thd_args[i]);
}
for (i = 0; i < NTHREADS; i++) {
thd_join(thds[i], NULL);
}
#undef NTHREADS
}
TEST_END
int
main(void) {
return test(
test_prof_thread_name_validation,
test_prof_thread_name_threaded);
}