From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: by sourceware.org (Postfix, from userid 2201) id D67B9385842D; Fri, 14 Jul 2023 15:28:28 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org D67B9385842D DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=sourceware.org; s=default; t=1689348508; bh=MFDea/TuPVRIT0azVAbMmbb5UMkwg0w23n6iuxWkVGI=; h=From:To:Subject:Date:From; b=K6P+6VDF/3YJRzmVdH/T+Mr9J95554UQUS9nmoqHbJd/0GrXoq16bNFtckQlcE59/ h1if2ysP69TcHA7VLrVAp9xRFcXfGBYMg3HeP7+cspKx7GWEDjZxexiLunhQP1PbjW vmf5yPmoNvqOAhLgqQoYVMgTdBl4jO2UGUmjwjNA= Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable From: Jon Turney To: cygwin-cvs@sourceware.org Subject: [newlib-cygwin] Cygwin: testsuite: Busy-wait in cancel3 and cancel5 X-Act-Checkin: newlib-cygwin X-Git-Author: Jon Turney X-Git-Refname: refs/heads/master X-Git-Oldrev: 7d50e65a8442546a6bdce7636d67ad65f154de46 X-Git-Newrev: e867f8c3e89f4f6a85de3a96ddfd2de8f4bb882f Message-Id: <20230714152828.D67B9385842D@sourceware.org> Date: Fri, 14 Jul 2023 15:28:28 +0000 (GMT) List-Id: https://sourceware.org/git/gitweb.cgi?p=3Dnewlib-cygwin.git;h=3De867f8c3e89= f4f6a85de3a96ddfd2de8f4bb882f commit e867f8c3e89f4f6a85de3a96ddfd2de8f4bb882f Author: Jon Turney Date: Mon Jul 10 19:04:58 2023 +0100 Cygwin: testsuite: Busy-wait in cancel3 and cancel5 =20 These tests async thread cancellation of a thread that doesn't have any cancellation points. =20 Unfortunately, since 2b165a45 the async cancellation silently fails when the thread is inside the kernel function Sleep(), so it just exits normally after 10 seconds. (See the commentary in pthread::cancel() in thread.cc, where it checks if the target thread is inside the kernel, and silently converts the cancellation into a deferred one) =20 Work around this by busy-waiting rather than Sleep()ing for 10 seconds. =20 This is still somewhat fragile: the async cancel could still fail, if it happens to occur while we're inside the kernel function that time() calls. =20 v2: Do nothing more efficiently =20 Signed-off-by: Jon Turney Diff: --- winsup/testsuite/winsup.api/pthread/cancel3.c | 24 ++++++++++++++++++------ winsup/testsuite/winsup.api/pthread/cancel5.c | 24 ++++++++++++++++++------ 2 files changed, 36 insertions(+), 12 deletions(-) diff --git a/winsup/testsuite/winsup.api/pthread/cancel3.c b/winsup/testsui= te/winsup.api/pthread/cancel3.c index 832fe2e3f..07feb7c9b 100644 --- a/winsup/testsuite/winsup.api/pthread/cancel3.c +++ b/winsup/testsuite/winsup.api/pthread/cancel3.c @@ -75,11 +75,22 @@ mythread(void * arg) assert(pthread_setcanceltype(PTHREAD_CANCEL_ASYNCHRONOUS, NULL) =3D=3D 0= ); =20 /* - * We wait up to 10 seconds, waking every 0.1 seconds, - * for a cancelation to be applied to us. + * We wait up to 10 seconds for a cancelation to be applied to us. */ - for (bag->count =3D 0; bag->count < 100; bag->count++) - Sleep(100); + for (bag->count =3D 0; bag->count < 10; bag->count++) + { + /* Busy wait to avoid Sleep(), since we can't asynchronous cancel in= side a + kernel function. (This is still somewhat fragile as if the async cancel + can fail if it happens to occur while we're inside the kernel function + that time() calls...) */ + time_t start =3D time(NULL); + while ((time(NULL) - start) < 1) + { + int i; + for (i =3D 0; i < 1E7; i++) + __asm__ volatile ("pause":::); + } + } =20 return result; } @@ -149,10 +160,11 @@ main() =20 if (fail) { - fprintf(stderr, "Thread %d: started %d: count %d\n", + fprintf(stderr, "Thread %d: started %d: count %d: result %d \n", i, threadbag[i].started, - threadbag[i].count); + threadbag[i].count, + result); } failed =3D (failed || fail); } diff --git a/winsup/testsuite/winsup.api/pthread/cancel5.c b/winsup/testsui= te/winsup.api/pthread/cancel5.c index 8b7240615..999b3c95c 100644 --- a/winsup/testsuite/winsup.api/pthread/cancel5.c +++ b/winsup/testsuite/winsup.api/pthread/cancel5.c @@ -76,11 +76,22 @@ mythread(void * arg) assert(pthread_setcanceltype(PTHREAD_CANCEL_ASYNCHRONOUS, NULL) =3D=3D 0= ); =20 /* - * We wait up to 10 seconds, waking every 0.1 seconds, - * for a cancelation to be applied to us. + * We wait up to 10 seconds for a cancelation to be applied to us. */ - for (bag->count =3D 0; bag->count < 100; bag->count++) - Sleep(100); + for (bag->count =3D 0; bag->count < 10; bag->count++) + { + /* Busy wait to avoid Sleep(), since we can't asynchronous cancel in= side a + kernel function. (This is still somewhat fragile as if the async cancel + can fail if it happens to occur while we're inside the kernel function + that time() calls...) */ + time_t start =3D time(NULL); + while ((time(NULL) - start) < 1) + { + int i; + for (i =3D 0; i < 1E7; i++) + __asm__ volatile ("pause":::); + } + } =20 return result; } @@ -148,10 +159,11 @@ main() =20 if (fail) { - fprintf(stderr, "Thread %d: started %d: count %d\n", + fprintf(stderr, "Thread %d: started %d: count %d: result %d\n", i, threadbag[i].started, - threadbag[i].count); + threadbag[i].count, + result); } failed =3D (failed || fail); }