1*cdebaff8SEnji Cooper /* $NetBSD: t_mutex.c,v 1.14 2016/10/31 23:51:20 christos Exp $ */ 257718be8SEnji Cooper 357718be8SEnji Cooper /* 457718be8SEnji Cooper * Copyright (c) 2008 The NetBSD Foundation, Inc. 557718be8SEnji Cooper * All rights reserved. 657718be8SEnji Cooper * 757718be8SEnji Cooper * Redistribution and use in source and binary forms, with or without 857718be8SEnji Cooper * modification, are permitted provided that the following conditions 957718be8SEnji Cooper * are met: 1057718be8SEnji Cooper * 1. Redistributions of source code must retain the above copyright 1157718be8SEnji Cooper * notice, this list of conditions and the following disclaimer. 1257718be8SEnji Cooper * 2. Redistributions in binary form must reproduce the above copyright 1357718be8SEnji Cooper * notice, this list of conditions and the following disclaimer in the 1457718be8SEnji Cooper * documentation and/or other materials provided with the distribution. 1557718be8SEnji Cooper * 1657718be8SEnji Cooper * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 1757718be8SEnji Cooper * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 1857718be8SEnji Cooper * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 1957718be8SEnji Cooper * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 2057718be8SEnji Cooper * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 2157718be8SEnji Cooper * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 2257718be8SEnji Cooper * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 2357718be8SEnji Cooper * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 2457718be8SEnji Cooper * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 2557718be8SEnji Cooper * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 2657718be8SEnji Cooper * POSSIBILITY OF SUCH DAMAGE. 2757718be8SEnji Cooper */ 2857718be8SEnji Cooper 2957718be8SEnji Cooper #include <sys/cdefs.h> 3057718be8SEnji Cooper __COPYRIGHT("@(#) Copyright (c) 2008\ 3157718be8SEnji Cooper The NetBSD Foundation, inc. All rights reserved."); 32*cdebaff8SEnji Cooper __RCSID("$NetBSD: t_mutex.c,v 1.14 2016/10/31 23:51:20 christos Exp $"); 3357718be8SEnji Cooper 34*cdebaff8SEnji Cooper #ifdef __FreeBSD__ 35*cdebaff8SEnji Cooper #include <sys/time.h> /* For timespecadd */ 36*cdebaff8SEnji Cooper #include <inttypes.h> /* For UINT16_MAX */ 37*cdebaff8SEnji Cooper #endif 3857718be8SEnji Cooper #include <pthread.h> 3957718be8SEnji Cooper #include <stdio.h> 4057718be8SEnji Cooper #include <string.h> 41640235e2SEnji Cooper #include <errno.h> 42*cdebaff8SEnji Cooper #include <time.h> 4357718be8SEnji Cooper #include <unistd.h> 44640235e2SEnji Cooper #include <sys/sched.h> 45640235e2SEnji Cooper #include <sys/param.h> 4657718be8SEnji Cooper 4757718be8SEnji Cooper #include <atf-c.h> 4857718be8SEnji Cooper 4957718be8SEnji Cooper #include "h_common.h" 5057718be8SEnji Cooper 5157718be8SEnji Cooper static pthread_mutex_t mutex; 5257718be8SEnji Cooper static pthread_mutex_t static_mutex = PTHREAD_MUTEX_INITIALIZER; 5357718be8SEnji Cooper static int global_x; 5457718be8SEnji Cooper 55*cdebaff8SEnji Cooper #ifdef TIMEDMUTEX 56*cdebaff8SEnji Cooper /* This code is used for verifying non-timed specific code */ 57*cdebaff8SEnji Cooper static struct timespec ts_lengthy = { 58*cdebaff8SEnji Cooper .tv_sec = UINT16_MAX, 59*cdebaff8SEnji Cooper .tv_nsec = 0 60*cdebaff8SEnji Cooper }; 61*cdebaff8SEnji Cooper /* This code is used for verifying timed-only specific code */ 62*cdebaff8SEnji Cooper static struct timespec ts_shortlived = { 63*cdebaff8SEnji Cooper .tv_sec = 0, 64*cdebaff8SEnji Cooper .tv_nsec = 120 65*cdebaff8SEnji Cooper }; 66*cdebaff8SEnji Cooper 67*cdebaff8SEnji Cooper static int 68*cdebaff8SEnji Cooper mutex_lock(pthread_mutex_t *m, const struct timespec *ts) 69*cdebaff8SEnji Cooper { 70*cdebaff8SEnji Cooper struct timespec ts_wait; 71*cdebaff8SEnji Cooper ATF_REQUIRE(clock_gettime(CLOCK_REALTIME, &ts_wait) != -1); 72*cdebaff8SEnji Cooper timespecadd(&ts_wait, ts, &ts_wait); 73*cdebaff8SEnji Cooper 74*cdebaff8SEnji Cooper return pthread_mutex_timedlock(m, &ts_wait); 75*cdebaff8SEnji Cooper } 76*cdebaff8SEnji Cooper #else 77*cdebaff8SEnji Cooper #define mutex_lock(a, b) pthread_mutex_lock(a) 78*cdebaff8SEnji Cooper #endif 79*cdebaff8SEnji Cooper 8057718be8SEnji Cooper static void * 8157718be8SEnji Cooper mutex1_threadfunc(void *arg) 8257718be8SEnji Cooper { 8357718be8SEnji Cooper int *param; 8457718be8SEnji Cooper 8557718be8SEnji Cooper printf("2: Second thread.\n"); 8657718be8SEnji Cooper 8757718be8SEnji Cooper param = arg; 8857718be8SEnji Cooper printf("2: Locking mutex\n"); 89*cdebaff8SEnji Cooper mutex_lock(&mutex, &ts_lengthy); 9057718be8SEnji Cooper printf("2: Got mutex. *param = %d\n", *param); 9157718be8SEnji Cooper ATF_REQUIRE_EQ(*param, 20); 9257718be8SEnji Cooper (*param)++; 9357718be8SEnji Cooper 9457718be8SEnji Cooper pthread_mutex_unlock(&mutex); 9557718be8SEnji Cooper 9657718be8SEnji Cooper return param; 9757718be8SEnji Cooper } 9857718be8SEnji Cooper 9957718be8SEnji Cooper ATF_TC(mutex1); 10057718be8SEnji Cooper ATF_TC_HEAD(mutex1, tc) 10157718be8SEnji Cooper { 10257718be8SEnji Cooper atf_tc_set_md_var(tc, "descr", "Checks mutexes"); 10357718be8SEnji Cooper } 10457718be8SEnji Cooper ATF_TC_BODY(mutex1, tc) 10557718be8SEnji Cooper { 10657718be8SEnji Cooper int x; 10757718be8SEnji Cooper pthread_t new; 10857718be8SEnji Cooper void *joinval; 10957718be8SEnji Cooper 11057718be8SEnji Cooper printf("1: Mutex-test 1\n"); 11157718be8SEnji Cooper 11257718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_init(&mutex, NULL)); 11357718be8SEnji Cooper x = 1; 114*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&mutex, &ts_lengthy)); 11557718be8SEnji Cooper PTHREAD_REQUIRE(pthread_create(&new, NULL, mutex1_threadfunc, &x)); 11657718be8SEnji Cooper printf("1: Before changing the value.\n"); 11757718be8SEnji Cooper sleep(2); 11857718be8SEnji Cooper x = 20; 11957718be8SEnji Cooper printf("1: Before releasing the mutex.\n"); 12057718be8SEnji Cooper sleep(2); 12157718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&mutex)); 12257718be8SEnji Cooper printf("1: After releasing the mutex.\n"); 12357718be8SEnji Cooper PTHREAD_REQUIRE(pthread_join(new, &joinval)); 12457718be8SEnji Cooper 125*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&mutex, &ts_lengthy)); 12657718be8SEnji Cooper printf("1: Thread joined. X was %d. Return value (int) was %d\n", 12757718be8SEnji Cooper x, *(int *)joinval); 12857718be8SEnji Cooper ATF_REQUIRE_EQ(x, 21); 12957718be8SEnji Cooper ATF_REQUIRE_EQ(*(int *)joinval, 21); 13057718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&mutex)); 13157718be8SEnji Cooper } 13257718be8SEnji Cooper 13357718be8SEnji Cooper static void * 13457718be8SEnji Cooper mutex2_threadfunc(void *arg) 13557718be8SEnji Cooper { 13657718be8SEnji Cooper long count = *(int *)arg; 13757718be8SEnji Cooper 13857718be8SEnji Cooper printf("2: Second thread (%p). Count is %ld\n", pthread_self(), count); 13957718be8SEnji Cooper 14057718be8SEnji Cooper while (count--) { 141*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&mutex, &ts_lengthy)); 14257718be8SEnji Cooper global_x++; 14357718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&mutex)); 14457718be8SEnji Cooper } 14557718be8SEnji Cooper 14657718be8SEnji Cooper return (void *)count; 14757718be8SEnji Cooper } 14857718be8SEnji Cooper 14957718be8SEnji Cooper ATF_TC(mutex2); 15057718be8SEnji Cooper ATF_TC_HEAD(mutex2, tc) 15157718be8SEnji Cooper { 15257718be8SEnji Cooper atf_tc_set_md_var(tc, "descr", "Checks mutexes"); 153190e1b1cSEnji Cooper #ifdef __NetBSD__ 15457718be8SEnji Cooper #if defined(__powerpc__) 15557718be8SEnji Cooper atf_tc_set_md_var(tc, "timeout", "40"); 15657718be8SEnji Cooper #endif 157190e1b1cSEnji Cooper #endif 15857718be8SEnji Cooper } 15957718be8SEnji Cooper ATF_TC_BODY(mutex2, tc) 16057718be8SEnji Cooper { 16157718be8SEnji Cooper int count, count2; 16257718be8SEnji Cooper pthread_t new; 16357718be8SEnji Cooper void *joinval; 16457718be8SEnji Cooper 16557718be8SEnji Cooper printf("1: Mutex-test 2\n"); 16657718be8SEnji Cooper 167190e1b1cSEnji Cooper #ifdef __NetBSD__ 16857718be8SEnji Cooper #if defined(__powerpc__) 16957718be8SEnji Cooper atf_tc_expect_timeout("PR port-powerpc/44387"); 17057718be8SEnji Cooper #endif 171190e1b1cSEnji Cooper #endif 17257718be8SEnji Cooper 17357718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_init(&mutex, NULL)); 17457718be8SEnji Cooper 17557718be8SEnji Cooper global_x = 0; 17657718be8SEnji Cooper count = count2 = 10000000; 17757718be8SEnji Cooper 178*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&mutex, &ts_lengthy)); 17957718be8SEnji Cooper PTHREAD_REQUIRE(pthread_create(&new, NULL, mutex2_threadfunc, &count2)); 18057718be8SEnji Cooper 18157718be8SEnji Cooper printf("1: Thread %p\n", pthread_self()); 18257718be8SEnji Cooper 18357718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&mutex)); 18457718be8SEnji Cooper 18557718be8SEnji Cooper while (count--) { 186*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&mutex, &ts_lengthy)); 18757718be8SEnji Cooper global_x++; 18857718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&mutex)); 18957718be8SEnji Cooper } 19057718be8SEnji Cooper 19157718be8SEnji Cooper PTHREAD_REQUIRE(pthread_join(new, &joinval)); 19257718be8SEnji Cooper 193*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&mutex, &ts_lengthy)); 19457718be8SEnji Cooper printf("1: Thread joined. X was %d. Return value (long) was %ld\n", 19557718be8SEnji Cooper global_x, (long)joinval); 19657718be8SEnji Cooper ATF_REQUIRE_EQ(global_x, 20000000); 19757718be8SEnji Cooper 198190e1b1cSEnji Cooper #ifdef __NetBSD__ 19957718be8SEnji Cooper #if defined(__powerpc__) 20057718be8SEnji Cooper /* XXX force a timeout in ppc case since an un-triggered race 20157718be8SEnji Cooper otherwise looks like a "failure" */ 20257718be8SEnji Cooper /* We sleep for longer than the timeout to make ATF not 20357718be8SEnji Cooper complain about unexpected success */ 20457718be8SEnji Cooper sleep(41); 20557718be8SEnji Cooper #endif 206190e1b1cSEnji Cooper #endif 20757718be8SEnji Cooper } 20857718be8SEnji Cooper 20957718be8SEnji Cooper static void * 21057718be8SEnji Cooper mutex3_threadfunc(void *arg) 21157718be8SEnji Cooper { 21257718be8SEnji Cooper long count = *(int *)arg; 21357718be8SEnji Cooper 21457718be8SEnji Cooper printf("2: Second thread (%p). Count is %ld\n", pthread_self(), count); 21557718be8SEnji Cooper 21657718be8SEnji Cooper while (count--) { 217*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&static_mutex, &ts_lengthy)); 21857718be8SEnji Cooper global_x++; 21957718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&static_mutex)); 22057718be8SEnji Cooper } 22157718be8SEnji Cooper 22257718be8SEnji Cooper return (void *)count; 22357718be8SEnji Cooper } 22457718be8SEnji Cooper 22557718be8SEnji Cooper ATF_TC(mutex3); 22657718be8SEnji Cooper ATF_TC_HEAD(mutex3, tc) 22757718be8SEnji Cooper { 22857718be8SEnji Cooper atf_tc_set_md_var(tc, "descr", "Checks mutexes using a static " 22957718be8SEnji Cooper "initializer"); 230190e1b1cSEnji Cooper #ifdef __NetBSD__ 23157718be8SEnji Cooper #if defined(__powerpc__) 23257718be8SEnji Cooper atf_tc_set_md_var(tc, "timeout", "40"); 23357718be8SEnji Cooper #endif 234190e1b1cSEnji Cooper #endif 23557718be8SEnji Cooper } 23657718be8SEnji Cooper ATF_TC_BODY(mutex3, tc) 23757718be8SEnji Cooper { 23857718be8SEnji Cooper int count, count2; 23957718be8SEnji Cooper pthread_t new; 24057718be8SEnji Cooper void *joinval; 24157718be8SEnji Cooper 24257718be8SEnji Cooper printf("1: Mutex-test 3\n"); 24357718be8SEnji Cooper 244190e1b1cSEnji Cooper #ifdef __NetBSD__ 24557718be8SEnji Cooper #if defined(__powerpc__) 24657718be8SEnji Cooper atf_tc_expect_timeout("PR port-powerpc/44387"); 24757718be8SEnji Cooper #endif 248190e1b1cSEnji Cooper #endif 24957718be8SEnji Cooper 25057718be8SEnji Cooper global_x = 0; 25157718be8SEnji Cooper count = count2 = 10000000; 25257718be8SEnji Cooper 253*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&static_mutex, &ts_lengthy)); 25457718be8SEnji Cooper PTHREAD_REQUIRE(pthread_create(&new, NULL, mutex3_threadfunc, &count2)); 25557718be8SEnji Cooper 25657718be8SEnji Cooper printf("1: Thread %p\n", pthread_self()); 25757718be8SEnji Cooper 25857718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&static_mutex)); 25957718be8SEnji Cooper 26057718be8SEnji Cooper while (count--) { 261*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&static_mutex, &ts_lengthy)); 26257718be8SEnji Cooper global_x++; 26357718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&static_mutex)); 26457718be8SEnji Cooper } 26557718be8SEnji Cooper 26657718be8SEnji Cooper PTHREAD_REQUIRE(pthread_join(new, &joinval)); 26757718be8SEnji Cooper 268*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&static_mutex, &ts_lengthy)); 26957718be8SEnji Cooper printf("1: Thread joined. X was %d. Return value (long) was %ld\n", 27057718be8SEnji Cooper global_x, (long)joinval); 27157718be8SEnji Cooper ATF_REQUIRE_EQ(global_x, 20000000); 27257718be8SEnji Cooper 273190e1b1cSEnji Cooper #ifdef __NetBSD__ 27457718be8SEnji Cooper #if defined(__powerpc__) 27557718be8SEnji Cooper /* XXX force a timeout in ppc case since an un-triggered race 27657718be8SEnji Cooper otherwise looks like a "failure" */ 27757718be8SEnji Cooper /* We sleep for longer than the timeout to make ATF not 27857718be8SEnji Cooper complain about unexpected success */ 27957718be8SEnji Cooper sleep(41); 28057718be8SEnji Cooper #endif 281190e1b1cSEnji Cooper #endif 28257718be8SEnji Cooper } 28357718be8SEnji Cooper 28457718be8SEnji Cooper static void * 28557718be8SEnji Cooper mutex4_threadfunc(void *arg) 28657718be8SEnji Cooper { 28757718be8SEnji Cooper int *param; 28857718be8SEnji Cooper 28957718be8SEnji Cooper printf("2: Second thread.\n"); 29057718be8SEnji Cooper 29157718be8SEnji Cooper param = arg; 29257718be8SEnji Cooper printf("2: Locking mutex\n"); 293*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&mutex, &ts_lengthy)); 29457718be8SEnji Cooper printf("2: Got mutex. *param = %d\n", *param); 29557718be8SEnji Cooper (*param)++; 29657718be8SEnji Cooper 29757718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&mutex)); 29857718be8SEnji Cooper 29957718be8SEnji Cooper return param; 30057718be8SEnji Cooper } 30157718be8SEnji Cooper 30257718be8SEnji Cooper ATF_TC(mutex4); 30357718be8SEnji Cooper ATF_TC_HEAD(mutex4, tc) 30457718be8SEnji Cooper { 30557718be8SEnji Cooper atf_tc_set_md_var(tc, "descr", "Checks mutexes"); 30657718be8SEnji Cooper } 30757718be8SEnji Cooper ATF_TC_BODY(mutex4, tc) 30857718be8SEnji Cooper { 30957718be8SEnji Cooper int x; 31057718be8SEnji Cooper pthread_t new; 31157718be8SEnji Cooper pthread_mutexattr_t mattr; 31257718be8SEnji Cooper void *joinval; 31357718be8SEnji Cooper 31457718be8SEnji Cooper printf("1: Mutex-test 4\n"); 31557718be8SEnji Cooper 31657718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutexattr_init(&mattr)); 31757718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutexattr_settype(&mattr, PTHREAD_MUTEX_RECURSIVE)); 31857718be8SEnji Cooper 31957718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_init(&mutex, &mattr)); 32057718be8SEnji Cooper 32157718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutexattr_destroy(&mattr)); 32257718be8SEnji Cooper 32357718be8SEnji Cooper x = 1; 324*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&mutex, &ts_lengthy)); 32557718be8SEnji Cooper PTHREAD_REQUIRE(pthread_create(&new, NULL, mutex4_threadfunc, &x)); 32657718be8SEnji Cooper 32757718be8SEnji Cooper printf("1: Before recursively acquiring the mutex.\n"); 328*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&mutex, &ts_lengthy)); 32957718be8SEnji Cooper 33057718be8SEnji Cooper printf("1: Before releasing the mutex once.\n"); 33157718be8SEnji Cooper sleep(2); 33257718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&mutex)); 33357718be8SEnji Cooper printf("1: After releasing the mutex once.\n"); 33457718be8SEnji Cooper 33557718be8SEnji Cooper x = 20; 33657718be8SEnji Cooper 33757718be8SEnji Cooper printf("1: Before releasing the mutex twice.\n"); 33857718be8SEnji Cooper sleep(2); 33957718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&mutex)); 34057718be8SEnji Cooper printf("1: After releasing the mutex twice.\n"); 34157718be8SEnji Cooper 34257718be8SEnji Cooper PTHREAD_REQUIRE(pthread_join(new, &joinval)); 34357718be8SEnji Cooper 344*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&mutex, &ts_lengthy)); 34557718be8SEnji Cooper printf("1: Thread joined. X was %d. Return value (int) was %d\n", 34657718be8SEnji Cooper x, *(int *)joinval); 34757718be8SEnji Cooper ATF_REQUIRE_EQ(x, 21); 34857718be8SEnji Cooper ATF_REQUIRE_EQ(*(int *)joinval, 21); 34957718be8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&mutex)); 35057718be8SEnji Cooper } 35157718be8SEnji Cooper 352640235e2SEnji Cooper #ifdef __NetBSD__ 353640235e2SEnji Cooper static pthread_mutexattr_t attr5; 354640235e2SEnji Cooper static pthread_mutex_t mutex5; 355640235e2SEnji Cooper static int min_fifo_prio, max_fifo_prio; 356640235e2SEnji Cooper 357640235e2SEnji Cooper static void * 358640235e2SEnji Cooper child_func(void* arg) 359640235e2SEnji Cooper { 360640235e2SEnji Cooper int res; 361640235e2SEnji Cooper 362640235e2SEnji Cooper printf("child is waiting\n"); 363640235e2SEnji Cooper res = _sched_protect(-2); 364640235e2SEnji Cooper ATF_REQUIRE_EQ_MSG(res, -1, "sched_protect returned %d", res); 365640235e2SEnji Cooper ATF_REQUIRE_EQ(errno, ENOENT); 366*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&mutex5, &ts_lengthy)); 367640235e2SEnji Cooper printf("child is owning resource\n"); 368640235e2SEnji Cooper res = _sched_protect(-2); 369640235e2SEnji Cooper ATF_REQUIRE_EQ(res, max_fifo_prio); 370640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&mutex5)); 371640235e2SEnji Cooper printf("child is done\n"); 372640235e2SEnji Cooper 373640235e2SEnji Cooper return 0; 374640235e2SEnji Cooper } 375640235e2SEnji Cooper 376640235e2SEnji Cooper ATF_TC(mutex5); 377640235e2SEnji Cooper ATF_TC_HEAD(mutex5, tc) 378640235e2SEnji Cooper { 379640235e2SEnji Cooper atf_tc_set_md_var(tc, "descr", "Checks mutexes for priority setting"); 380640235e2SEnji Cooper atf_tc_set_md_var(tc, "require.user", "root"); 381640235e2SEnji Cooper } 382640235e2SEnji Cooper 383640235e2SEnji Cooper ATF_TC_BODY(mutex5, tc) 384640235e2SEnji Cooper { 385640235e2SEnji Cooper int res; 386640235e2SEnji Cooper struct sched_param param; 387640235e2SEnji Cooper pthread_t child; 388640235e2SEnji Cooper 389640235e2SEnji Cooper min_fifo_prio = sched_get_priority_min(SCHED_FIFO); 390640235e2SEnji Cooper max_fifo_prio = sched_get_priority_max(SCHED_FIFO); 391640235e2SEnji Cooper printf("min prio for FIFO = %d\n", min_fifo_prio); 392640235e2SEnji Cooper param.sched_priority = min_fifo_prio; 393640235e2SEnji Cooper 394640235e2SEnji Cooper /* = 0 OTHER, 1 FIFO, 2 RR, -1 NONE */ 395640235e2SEnji Cooper res = sched_setscheduler(getpid(), SCHED_FIFO, ¶m); 396640235e2SEnji Cooper printf("previous policy used = %d\n", res); 397640235e2SEnji Cooper 398640235e2SEnji Cooper res = sched_getscheduler(getpid()); 399640235e2SEnji Cooper ATF_REQUIRE_EQ_MSG(res, SCHED_FIFO, "sched %d != FIFO %d", res, 400640235e2SEnji Cooper SCHED_FIFO); 401640235e2SEnji Cooper 402640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutexattr_init(&attr5)); 403640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutexattr_setprotocol(&attr5, 404640235e2SEnji Cooper PTHREAD_PRIO_PROTECT)); 405640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutexattr_setprioceiling(&attr5, 406640235e2SEnji Cooper max_fifo_prio)); 407640235e2SEnji Cooper 408640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_init(&mutex5, &attr5)); 409*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&mutex5, &ts_lengthy)); 410640235e2SEnji Cooper printf("enter critical section for main\n"); 411640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_create(&child, NULL, child_func, NULL)); 412640235e2SEnji Cooper printf("main starts to sleep\n"); 413640235e2SEnji Cooper sleep(10); 414640235e2SEnji Cooper printf("main completes\n"); 415640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&mutex5)); 416640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_join(child, NULL)); 417640235e2SEnji Cooper } 418640235e2SEnji Cooper 419640235e2SEnji Cooper static pthread_mutex_t mutex6; 420640235e2SEnji Cooper static int start = 0; 421640235e2SEnji Cooper static uintmax_t high_cnt = 0, low_cnt = 0, MAX_LOOP = 100000000; 422640235e2SEnji Cooper 423640235e2SEnji Cooper static void * 424640235e2SEnji Cooper high_prio(void* arg) 425640235e2SEnji Cooper { 426640235e2SEnji Cooper struct sched_param param; 427640235e2SEnji Cooper int policy; 428640235e2SEnji Cooper param.sched_priority = min_fifo_prio + 10; 429640235e2SEnji Cooper pthread_t childid = pthread_self(); 430640235e2SEnji Cooper 431640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_setschedparam(childid, 1, ¶m)); 432640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_getschedparam(childid, &policy, ¶m)); 433640235e2SEnji Cooper printf("high protect = %d, prio = %d\n", 434640235e2SEnji Cooper _sched_protect(-2), param.sched_priority); 435640235e2SEnji Cooper ATF_REQUIRE_EQ(policy, 1); 436640235e2SEnji Cooper printf("high prio = %d\n", param.sched_priority); 437640235e2SEnji Cooper sleep(1); 438640235e2SEnji Cooper long tmp = 0; 439640235e2SEnji Cooper for (int i = 0; i < 20; i++) { 440640235e2SEnji Cooper while (high_cnt < MAX_LOOP) { 441640235e2SEnji Cooper tmp += (123456789 % 1234) * (987654321 % 54321); 442640235e2SEnji Cooper high_cnt += 1; 443640235e2SEnji Cooper } 444640235e2SEnji Cooper high_cnt = 0; 445640235e2SEnji Cooper sleep(1); 446640235e2SEnji Cooper } 447*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&mutex6, &ts_lengthy)); 448640235e2SEnji Cooper if (start == 0) start = 2; 449640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&mutex6)); 450640235e2SEnji Cooper 451640235e2SEnji Cooper return 0; 452640235e2SEnji Cooper } 453640235e2SEnji Cooper 454640235e2SEnji Cooper static void * 455640235e2SEnji Cooper low_prio(void* arg) 456640235e2SEnji Cooper { 457640235e2SEnji Cooper struct sched_param param; 458640235e2SEnji Cooper int policy; 459640235e2SEnji Cooper param.sched_priority = min_fifo_prio; 460640235e2SEnji Cooper pthread_t childid = pthread_self(); 461640235e2SEnji Cooper int res = _sched_protect(max_fifo_prio); 462640235e2SEnji Cooper ATF_REQUIRE_EQ(res, 0); 463640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_setschedparam(childid, 1, ¶m)); 464640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_getschedparam(childid, &policy, ¶m)); 465640235e2SEnji Cooper printf("low protect = %d, prio = %d\n", _sched_protect(-2), 466640235e2SEnji Cooper param.sched_priority); 467640235e2SEnji Cooper ATF_REQUIRE_EQ(policy, 1); 468640235e2SEnji Cooper printf("low prio = %d\n", param.sched_priority); 469640235e2SEnji Cooper sleep(1); 470640235e2SEnji Cooper long tmp = 0; 471640235e2SEnji Cooper for (int i = 0; i < 20; i++) { 472640235e2SEnji Cooper while (low_cnt < MAX_LOOP) { 473640235e2SEnji Cooper tmp += (123456789 % 1234) * (987654321 % 54321); 474640235e2SEnji Cooper low_cnt += 1; 475640235e2SEnji Cooper } 476640235e2SEnji Cooper low_cnt = 0; 477640235e2SEnji Cooper sleep(1); 478640235e2SEnji Cooper } 479*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&mutex6, &ts_lengthy)); 480640235e2SEnji Cooper if (start == 0) 481640235e2SEnji Cooper start = 1; 482640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&mutex6)); 483640235e2SEnji Cooper 484640235e2SEnji Cooper return 0; 485640235e2SEnji Cooper } 486640235e2SEnji Cooper 487640235e2SEnji Cooper ATF_TC(mutex6); 488640235e2SEnji Cooper ATF_TC_HEAD(mutex6, tc) 489640235e2SEnji Cooper { 490640235e2SEnji Cooper atf_tc_set_md_var(tc, "descr", 491640235e2SEnji Cooper "Checks scheduling for priority ceiling"); 492640235e2SEnji Cooper atf_tc_set_md_var(tc, "require.user", "root"); 493640235e2SEnji Cooper } 494640235e2SEnji Cooper 495640235e2SEnji Cooper /* 496640235e2SEnji Cooper * 1. main thread sets itself to be a realtime task and launched two tasks, 497640235e2SEnji Cooper * one has higher priority and the other has lower priority. 498640235e2SEnji Cooper * 2. each child thread(low and high priority thread) sets its scheduler and 499640235e2SEnji Cooper * priority. 500640235e2SEnji Cooper * 3. each child thread did several rounds of computation, after each round it 501640235e2SEnji Cooper * sleep 1 second. 502640235e2SEnji Cooper * 4. the child thread with low priority will call _sched_protect to increase 503640235e2SEnji Cooper * its protect priority. 504640235e2SEnji Cooper * 5. We verify the thread with low priority runs first. 505640235e2SEnji Cooper * 506640235e2SEnji Cooper * Why does it work? From the main thread, we launched the high 507640235e2SEnji Cooper * priority thread first. This gives this thread the benefit of 508640235e2SEnji Cooper * starting first. The low priority thread did not call _sched_protect(2). 509640235e2SEnji Cooper * The high priority thread should finish the task first. After each 510640235e2SEnji Cooper * round of computation, we call sleep, to put the task into the 511640235e2SEnji Cooper * sleep queue, and wake up again after the timer expires. This 512640235e2SEnji Cooper * gives the scheduler the chance to decide which task to run. So, 513640235e2SEnji Cooper * the thread with real high priority will always block the thread 514640235e2SEnji Cooper * with real low priority. 515640235e2SEnji Cooper * 516640235e2SEnji Cooper */ 517640235e2SEnji Cooper ATF_TC_BODY(mutex6, tc) 518640235e2SEnji Cooper { 519640235e2SEnji Cooper struct sched_param param; 520640235e2SEnji Cooper int res; 521640235e2SEnji Cooper pthread_t high, low; 522640235e2SEnji Cooper 523640235e2SEnji Cooper min_fifo_prio = sched_get_priority_min(SCHED_FIFO); 524640235e2SEnji Cooper max_fifo_prio = sched_get_priority_max(SCHED_FIFO); 525640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_init(&mutex, NULL)); 526640235e2SEnji Cooper printf("min_fifo_prio = %d, max_fifo_info = %d\n", min_fifo_prio, 527640235e2SEnji Cooper max_fifo_prio); 528640235e2SEnji Cooper 529640235e2SEnji Cooper param.sched_priority = min_fifo_prio; 530640235e2SEnji Cooper res = sched_setscheduler(getpid(), SCHED_FIFO, ¶m); 531640235e2SEnji Cooper printf("previous policy used = %d\n", res); 532640235e2SEnji Cooper 533640235e2SEnji Cooper res = sched_getscheduler(getpid()); 534640235e2SEnji Cooper ATF_REQUIRE_EQ(res, 1); 535640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_create(&high, NULL, high_prio, NULL)); 536640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_create(&low, NULL, low_prio, NULL)); 537640235e2SEnji Cooper sleep(5); 538640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_join(low, NULL)); 539640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_join(high, NULL)); 540640235e2SEnji Cooper 541640235e2SEnji Cooper ATF_REQUIRE_EQ(start, 1); 542640235e2SEnji Cooper } 543640235e2SEnji Cooper #endif 544640235e2SEnji Cooper 545640235e2SEnji Cooper ATF_TC(mutexattr1); 546640235e2SEnji Cooper ATF_TC_HEAD(mutexattr1, tc) 547640235e2SEnji Cooper { 548640235e2SEnji Cooper atf_tc_set_md_var(tc, "descr", "Checks mutexattr"); 549640235e2SEnji Cooper } 550640235e2SEnji Cooper 551640235e2SEnji Cooper ATF_TC_BODY(mutexattr1, tc) 552640235e2SEnji Cooper { 553640235e2SEnji Cooper pthread_mutexattr_t mattr; 554640235e2SEnji Cooper int protocol, target; 555640235e2SEnji Cooper 556640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutexattr_init(&mattr)); 557640235e2SEnji Cooper 558640235e2SEnji Cooper target = PTHREAD_PRIO_NONE; 559640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutexattr_setprotocol(&mattr, target)); 560640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutexattr_getprotocol(&mattr, &protocol)); 561640235e2SEnji Cooper ATF_REQUIRE_EQ(protocol, target); 562640235e2SEnji Cooper 563640235e2SEnji Cooper /* 564640235e2SEnji Cooper target = PTHREAD_PRIO_INHERIT; 565640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutexattr_setprotocol(&mattr, target)); 566640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutexattr_getprotocol(&mattr, &protocol)); 567640235e2SEnji Cooper ATF_REQUIRE_EQ(protocol, target); 568640235e2SEnji Cooper */ 569640235e2SEnji Cooper 570640235e2SEnji Cooper target = PTHREAD_PRIO_PROTECT; 571640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutexattr_setprotocol(&mattr, target)); 572640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutexattr_getprotocol(&mattr, &protocol)); 573640235e2SEnji Cooper ATF_REQUIRE_EQ(protocol, target); 574640235e2SEnji Cooper } 575640235e2SEnji Cooper 576640235e2SEnji Cooper ATF_TC(mutexattr2); 577640235e2SEnji Cooper ATF_TC_HEAD(mutexattr2, tc) 578640235e2SEnji Cooper { 579640235e2SEnji Cooper atf_tc_set_md_var(tc, "descr", "Checks mutexattr"); 580640235e2SEnji Cooper } 581640235e2SEnji Cooper 582640235e2SEnji Cooper ATF_TC_BODY(mutexattr2, tc) 583640235e2SEnji Cooper { 584640235e2SEnji Cooper pthread_mutexattr_t mattr; 585640235e2SEnji Cooper 58682bc57c2SEnji Cooper #ifdef __FreeBSD__ 58782bc57c2SEnji Cooper atf_tc_expect_fail("fails on i == 0 with: " 58882bc57c2SEnji Cooper "pthread_mutexattr_setprioceiling(&mattr, i): Invalid argument " 58982bc57c2SEnji Cooper "-- PR # 211802"); 59082bc57c2SEnji Cooper #endif 59182bc57c2SEnji Cooper 592640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutexattr_init(&mattr)); 593640235e2SEnji Cooper int max_prio = sched_get_priority_max(SCHED_FIFO); 594640235e2SEnji Cooper int min_prio = sched_get_priority_min(SCHED_FIFO); 595640235e2SEnji Cooper for (int i = min_prio; i <= max_prio; i++) { 596640235e2SEnji Cooper int prioceiling; 59782bc57c2SEnji Cooper #ifdef __FreeBSD__ 59882bc57c2SEnji Cooper int protocol; 59982bc57c2SEnji Cooper 60082bc57c2SEnji Cooper PTHREAD_REQUIRE(pthread_mutexattr_getprotocol(&mattr, 60182bc57c2SEnji Cooper &protocol)); 60282bc57c2SEnji Cooper 60382bc57c2SEnji Cooper printf("priority: %d\nprotocol: %d\n", i, protocol); 60482bc57c2SEnji Cooper #endif 605640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutexattr_setprioceiling(&mattr, i)); 606640235e2SEnji Cooper PTHREAD_REQUIRE(pthread_mutexattr_getprioceiling(&mattr, 607640235e2SEnji Cooper &prioceiling)); 60882bc57c2SEnji Cooper #ifdef __FreeBSD__ 60982bc57c2SEnji Cooper printf("prioceiling: %d\n", prioceiling); 61082bc57c2SEnji Cooper #endif 611640235e2SEnji Cooper ATF_REQUIRE_EQ(i, prioceiling); 612640235e2SEnji Cooper } 613640235e2SEnji Cooper } 614640235e2SEnji Cooper 615*cdebaff8SEnji Cooper #ifdef TIMEDMUTEX 616*cdebaff8SEnji Cooper ATF_TC(timedmutex1); 617*cdebaff8SEnji Cooper ATF_TC_HEAD(timedmutex1, tc) 618*cdebaff8SEnji Cooper { 619*cdebaff8SEnji Cooper atf_tc_set_md_var(tc, "descr", "Checks timeout on selflock"); 620*cdebaff8SEnji Cooper } 621*cdebaff8SEnji Cooper 622*cdebaff8SEnji Cooper ATF_TC_BODY(timedmutex1, tc) 623*cdebaff8SEnji Cooper { 624*cdebaff8SEnji Cooper 625*cdebaff8SEnji Cooper printf("Timed mutex-test 1\n"); 626*cdebaff8SEnji Cooper 627*cdebaff8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_init(&mutex, NULL)); 628*cdebaff8SEnji Cooper 629*cdebaff8SEnji Cooper printf("Before acquiring mutex\n"); 630*cdebaff8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_lock(&mutex)); 631*cdebaff8SEnji Cooper 632*cdebaff8SEnji Cooper printf("Before endeavor to reacquire timed-mutex (timeout expected)\n"); 633*cdebaff8SEnji Cooper PTHREAD_REQUIRE_STATUS(mutex_lock(&mutex, &ts_shortlived), 634*cdebaff8SEnji Cooper ETIMEDOUT); 635*cdebaff8SEnji Cooper 636*cdebaff8SEnji Cooper printf("Unlocking mutex\n"); 637*cdebaff8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&mutex)); 638*cdebaff8SEnji Cooper } 639*cdebaff8SEnji Cooper 640*cdebaff8SEnji Cooper ATF_TC(timedmutex2); 641*cdebaff8SEnji Cooper ATF_TC_HEAD(timedmutex2, tc) 642*cdebaff8SEnji Cooper { 643*cdebaff8SEnji Cooper atf_tc_set_md_var(tc, "descr", 644*cdebaff8SEnji Cooper "Checks timeout on selflock with timedlock"); 645*cdebaff8SEnji Cooper } 646*cdebaff8SEnji Cooper 647*cdebaff8SEnji Cooper ATF_TC_BODY(timedmutex2, tc) 648*cdebaff8SEnji Cooper { 649*cdebaff8SEnji Cooper 650*cdebaff8SEnji Cooper printf("Timed mutex-test 2\n"); 651*cdebaff8SEnji Cooper 652*cdebaff8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_init(&mutex, NULL)); 653*cdebaff8SEnji Cooper 654*cdebaff8SEnji Cooper printf("Before acquiring mutex with timedlock\n"); 655*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&mutex, &ts_lengthy)); 656*cdebaff8SEnji Cooper 657*cdebaff8SEnji Cooper printf("Before endeavor to reacquire timed-mutex (timeout expected)\n"); 658*cdebaff8SEnji Cooper PTHREAD_REQUIRE_STATUS(mutex_lock(&mutex, &ts_shortlived), 659*cdebaff8SEnji Cooper ETIMEDOUT); 660*cdebaff8SEnji Cooper 661*cdebaff8SEnji Cooper printf("Unlocking mutex\n"); 662*cdebaff8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&mutex)); 663*cdebaff8SEnji Cooper } 664*cdebaff8SEnji Cooper 665*cdebaff8SEnji Cooper ATF_TC(timedmutex3); 666*cdebaff8SEnji Cooper ATF_TC_HEAD(timedmutex3, tc) 667*cdebaff8SEnji Cooper { 668*cdebaff8SEnji Cooper atf_tc_set_md_var(tc, "descr", 669*cdebaff8SEnji Cooper "Checks timeout on selflock in a new thread"); 670*cdebaff8SEnji Cooper } 671*cdebaff8SEnji Cooper 672*cdebaff8SEnji Cooper static void * 673*cdebaff8SEnji Cooper timedmtx_thrdfunc(void *arg) 674*cdebaff8SEnji Cooper { 675*cdebaff8SEnji Cooper printf("Before endeavor to reacquire timed-mutex (timeout expected)\n"); 676*cdebaff8SEnji Cooper PTHREAD_REQUIRE_STATUS(mutex_lock(&mutex, &ts_shortlived), 677*cdebaff8SEnji Cooper ETIMEDOUT); 678*cdebaff8SEnji Cooper 679*cdebaff8SEnji Cooper return NULL; 680*cdebaff8SEnji Cooper } 681*cdebaff8SEnji Cooper 682*cdebaff8SEnji Cooper ATF_TC_BODY(timedmutex3, tc) 683*cdebaff8SEnji Cooper { 684*cdebaff8SEnji Cooper pthread_t new; 685*cdebaff8SEnji Cooper 686*cdebaff8SEnji Cooper printf("Timed mutex-test 3\n"); 687*cdebaff8SEnji Cooper 688*cdebaff8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_init(&mutex, NULL)); 689*cdebaff8SEnji Cooper 690*cdebaff8SEnji Cooper printf("Before acquiring mutex with timedlock\n"); 691*cdebaff8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_lock(&mutex)); 692*cdebaff8SEnji Cooper 693*cdebaff8SEnji Cooper printf("Before creating new thread\n"); 694*cdebaff8SEnji Cooper PTHREAD_REQUIRE(pthread_create(&new, NULL, timedmtx_thrdfunc, NULL)); 695*cdebaff8SEnji Cooper 696*cdebaff8SEnji Cooper printf("Before joining the mutex\n"); 697*cdebaff8SEnji Cooper PTHREAD_REQUIRE(pthread_join(new, NULL)); 698*cdebaff8SEnji Cooper 699*cdebaff8SEnji Cooper printf("Unlocking mutex\n"); 700*cdebaff8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&mutex)); 701*cdebaff8SEnji Cooper } 702*cdebaff8SEnji Cooper 703*cdebaff8SEnji Cooper ATF_TC(timedmutex4); 704*cdebaff8SEnji Cooper ATF_TC_HEAD(timedmutex4, tc) 705*cdebaff8SEnji Cooper { 706*cdebaff8SEnji Cooper atf_tc_set_md_var(tc, "descr", 707*cdebaff8SEnji Cooper "Checks timeout on selflock with timedlock in a new thread"); 708*cdebaff8SEnji Cooper } 709*cdebaff8SEnji Cooper 710*cdebaff8SEnji Cooper ATF_TC_BODY(timedmutex4, tc) 711*cdebaff8SEnji Cooper { 712*cdebaff8SEnji Cooper pthread_t new; 713*cdebaff8SEnji Cooper 714*cdebaff8SEnji Cooper printf("Timed mutex-test 4\n"); 715*cdebaff8SEnji Cooper 716*cdebaff8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_init(&mutex, NULL)); 717*cdebaff8SEnji Cooper 718*cdebaff8SEnji Cooper printf("Before acquiring mutex with timedlock\n"); 719*cdebaff8SEnji Cooper PTHREAD_REQUIRE(mutex_lock(&mutex, &ts_lengthy)); 720*cdebaff8SEnji Cooper 721*cdebaff8SEnji Cooper printf("Before creating new thread\n"); 722*cdebaff8SEnji Cooper PTHREAD_REQUIRE(pthread_create(&new, NULL, timedmtx_thrdfunc, NULL)); 723*cdebaff8SEnji Cooper 724*cdebaff8SEnji Cooper printf("Before joining the mutex\n"); 725*cdebaff8SEnji Cooper PTHREAD_REQUIRE(pthread_join(new, NULL)); 726*cdebaff8SEnji Cooper 727*cdebaff8SEnji Cooper printf("Unlocking mutex\n"); 728*cdebaff8SEnji Cooper PTHREAD_REQUIRE(pthread_mutex_unlock(&mutex)); 729*cdebaff8SEnji Cooper } 730*cdebaff8SEnji Cooper #endif 731*cdebaff8SEnji Cooper 73257718be8SEnji Cooper ATF_TP_ADD_TCS(tp) 73357718be8SEnji Cooper { 73457718be8SEnji Cooper ATF_TP_ADD_TC(tp, mutex1); 73557718be8SEnji Cooper ATF_TP_ADD_TC(tp, mutex2); 73657718be8SEnji Cooper ATF_TP_ADD_TC(tp, mutex3); 73757718be8SEnji Cooper ATF_TP_ADD_TC(tp, mutex4); 738640235e2SEnji Cooper #ifdef __NetBSD__ 739640235e2SEnji Cooper ATF_TP_ADD_TC(tp, mutex5); 740640235e2SEnji Cooper ATF_TP_ADD_TC(tp, mutex6); 741640235e2SEnji Cooper #endif 742640235e2SEnji Cooper ATF_TP_ADD_TC(tp, mutexattr1); 743640235e2SEnji Cooper ATF_TP_ADD_TC(tp, mutexattr2); 74457718be8SEnji Cooper 745*cdebaff8SEnji Cooper #ifdef TIMEDMUTEX 746*cdebaff8SEnji Cooper ATF_TP_ADD_TC(tp, timedmutex1); 747*cdebaff8SEnji Cooper ATF_TP_ADD_TC(tp, timedmutex2); 748*cdebaff8SEnji Cooper ATF_TP_ADD_TC(tp, timedmutex3); 749*cdebaff8SEnji Cooper ATF_TP_ADD_TC(tp, timedmutex4); 750*cdebaff8SEnji Cooper #endif 751*cdebaff8SEnji Cooper 75257718be8SEnji Cooper return atf_no_error(); 75357718be8SEnji Cooper } 754