All of lore.kernel.org
 help / color / mirror / Atom feed
* [LTP] [PATCH 1/2] open_posix_testsuite/../mq_timedsend/12-1: fix long lines
@ 2013-07-24  6:39 Jan Stancek
  2013-07-24  6:39 ` [LTP] [PATCH 2/2] open_posix_testsuite/../mq_timedsend/12-1: fix race Jan Stancek
  0 siblings, 1 reply; 12+ messages in thread
From: Jan Stancek @ 2013-07-24  6:39 UTC (permalink / raw)
  To: ltp-list

Fix lines going over 80 characters.

Signed-off-by: Jan Stancek <jstancek@redhat.com>
---
 .../conformance/interfaces/mq_timedsend/12-1.c     |   77 ++++++++++----------
 1 files changed, 40 insertions(+), 37 deletions(-)

diff --git a/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c b/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
index 1984063..29780d0 100644
--- a/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
+++ b/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
@@ -11,12 +11,12 @@
  *
  * Steps:
  * 1. Create a thread and set up a signal handler for SIGUSR1
- * 2. Thread indicates to main that it is ready to start calling mq_timedsend until it
- *    blocks for a timeout of 10 seconds.
- * 3. In main, send the thread the SIGUSR1 signal while mq_timedsend is blocking.
- * 4. Check to make sure that mq_timedsend blocked, and that it returned EINTR when it was
- *    interrupted by SIGUSR1.
- *
+ * 2. Thread indicates to main that it is ready to start calling mq_timedsend
+ *    until it blocks for a timeout of 10 seconds.
+ * 3. In main, send the thread the SIGUSR1 signal while mq_timedsend is
+ *    blocking.
+ * 4. Check to make sure that mq_timedsend blocked, and that it returned
+ *    EINTR when it was interrupted by SIGUSR1.
  */
 
 #include <stdio.h>
@@ -43,10 +43,15 @@
 #define INTHREAD 0
 #define INMAIN 1
 
-int sem;			/* manual semaphore */
-int in_handler;			/* flag to indicate signal handler was called */
-int errno_eintr;		/* flag to indicate that errno was set to eintr when mq_timedsend()
-				   was interruped. */
+/* manual semaphore */
+int sem;
+
+/* flag to indicate signal handler was called */
+int in_handler;
+
+/* flag to indicate that errno was set to eintr when mq_timedsend()
+ * was interruped. */
+int errno_eintr;
 
 /*
  * This handler is just used to catch the signal and stop sleep (so the
@@ -61,8 +66,7 @@ void justreturn_handler(int signo)
 
 void *a_thread_func()
 {
-
-	int i;
+	int i, ret;
 	struct sigaction act;
 	char gqname[NAMESIZE];
 	mqd_t gqueue;
@@ -96,26 +100,26 @@ void *a_thread_func()
 	sem = INMAIN;
 
 	for (i = 0; i < MAXMSG + 1; i++) {
-		if (mq_timedsend(gqueue, msgptr, strlen(msgptr), 1, &ts) == -1) {
-			if (errno == EINTR) {
-				if (mq_unlink(gqname) != 0) {
-					perror
-					    ("mq_unlink() did not return success");
-					pthread_exit((void *)PTS_UNRESOLVED);
-					return NULL;
-				}
-				printf
-				    ("thread: mq_timedsend interrupted by signal and correctly set errno to EINTR\n");
-				errno_eintr = 1;
-				pthread_exit((void *)PTS_PASS);
-				return NULL;
-			} else {
-				printf
-				    ("mq_timedsend not interrupted by signal or set errno to incorrect code: %d\n",
-				     errno);
-				pthread_exit((void *)PTS_FAIL);
+		ret = mq_timedsend(gqueue, msgptr, strlen(msgptr), 1, &ts);
+		if (ret	!= -1)
+			continue;
+
+		if (errno == EINTR) {
+			if (mq_unlink(gqname) != 0) {
+				perror("mq_unlink() did not return success");
+				pthread_exit((void *)PTS_UNRESOLVED);
 				return NULL;
 			}
+			printf("thread: mq_timedsend interrupted by signal"
+				" and correctly set errno to EINTR\n");
+			errno_eintr = 1;
+			pthread_exit((void *)PTS_PASS);
+			return NULL;
+		} else {
+			printf("mq_timedsend not interrupted by signal or"
+				" set errno to incorrect code: %d\n", errno);
+			pthread_exit((void *)PTS_FAIL);
+			return NULL;
 		}
 	}
 
@@ -161,23 +165,22 @@ int main(void)
 		return PTS_UNRESOLVED;
 	}
 
-	/* Test to see if the thread blocked correctly in mq_timedsend, and if it returned
-	 * EINTR when it caught the signal */
+	/* Test to see if the thread blocked correctly in mq_timedsend,
+	 * and if it returned EINTR when it caught the signal */
 	if (errno_eintr != 1) {
 		if (sem == INTHREAD) {
-			printf
-			    ("Test FAILED: mq_timedsend() never blocked for any timeout period.\n");
+			printf("Test FAILED: mq_timedsend() never"
+				" blocked for any timeout period.\n");
 			return PTS_FAIL;
 		}
 
 		if (in_handler != 0) {
-			perror
-			    ("Error: signal SIGUSR1 was never received, and/or the signal handler was never called.\n");
+			perror("Error: signal SIGUSR1 was never received and/or"
+				" the signal handler was never called.\n");
 			return PTS_UNRESOLVED;
 		}
 	}
 
 	printf("Test PASSED\n");
 	return PTS_PASS;
-
 }
-- 
1.7.1


------------------------------------------------------------------------------
See everything from the browser to the database with AppDynamics
Get end-to-end visibility with application monitoring from AppDynamics
Isolate bottlenecks and diagnose root cause in seconds.
Start your free trial of AppDynamics Pro today!
http://pubads.g.doubleclick.net/gampad/clk?id=48808831&iu=/4140/ostg.clktrk
_______________________________________________
Ltp-list mailing list
Ltp-list@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/ltp-list

^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [LTP] [PATCH 2/2] open_posix_testsuite/../mq_timedsend/12-1: fix race
  2013-07-24  6:39 [LTP] [PATCH 1/2] open_posix_testsuite/../mq_timedsend/12-1: fix long lines Jan Stancek
@ 2013-07-24  6:39 ` Jan Stancek
  2013-07-25 10:07   ` [LTP] [PATCH v2 " Jan Stancek
  2013-07-30 17:35   ` [LTP] [PATCH " chrubis
  0 siblings, 2 replies; 12+ messages in thread
From: Jan Stancek @ 2013-07-24  6:39 UTC (permalink / raw)
  To: ltp-list

Test can send SIGUSR1 signal after thread has already completed
and report failure from main() and success from a_thread_func():

  conformance/interfaces/mq_timedsend/12-1: execution: UNRESOLVED: Output:
  Error: in pthread_kill
  : Success
  thread: mq_timedsend interrupted by signal and correctly set errno to EINTR

Synchronize exit of a_thread_func(), so that thread can exit only
after loop sending SIGUSR1 completed.

Signed-off-by: Jan Stancek <jstancek@redhat.com>
---
 .../conformance/interfaces/mq_timedsend/12-1.c     |   94 +++++++++++---------
 1 files changed, 51 insertions(+), 43 deletions(-)

diff --git a/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c b/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
index 29780d0..df53a72 100644
--- a/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
+++ b/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
@@ -39,19 +39,25 @@
 #define MSGSTR "0123456789"
 #define BUFFER 40
 #define MAXMSG 10
+#define TIMEOUT 10
 
-#define INTHREAD 0
-#define INMAIN 1
+#define SAFE(op) \
+	do {\
+		if ((op) == -1) {\
+			perror("unexpected failure"); \
+			exit(PTS_UNRESOLVED); \
+		} \
+	} while (0)
 
-/* manual semaphore */
-int sem;
+/* variable to indicate how many times signal handler was called */
+static volatile sig_atomic_t in_handler;
 
-/* flag to indicate signal handler was called */
-int in_handler;
+/* errno returned by mq_timedsend() */
+static volatile int mq_timedsend_errno = -1;
 
-/* flag to indicate that errno was set to eintr when mq_timedsend()
- * was interruped. */
-int errno_eintr;
+/* pipes to synchronize thread calling mq_timedsend */
+static int pipefd_start[2];
+static int pipefd_exit[2];
 
 /*
  * This handler is just used to catch the signal and stop sleep (so the
@@ -59,14 +65,12 @@ int errno_eintr;
  */
 void justreturn_handler(int signo)
 {
-	/* Indicate that the signal handler was called */
-	in_handler = 1;
-	return;
+	in_handler++;
 }
 
-void *a_thread_func()
+void *a_thread_func(void *arg)
 {
-	int i, ret;
+	int i, ret, dummy;
 	struct sigaction act;
 	char gqname[NAMESIZE];
 	mqd_t gqueue;
@@ -92,18 +96,19 @@ void *a_thread_func()
 		return NULL;
 	}
 
-	/* mq_timedsend will block for 10 seconds when it waits */
-	ts.tv_sec = time(NULL) + 10;
+	/* mq_timedsend will block for TIMEOUT seconds when it waits */
+	ts.tv_sec = time(NULL) + TIMEOUT;
 	ts.tv_nsec = 0;
 
 	/* Tell main it can go ahead and start sending SIGUSR1 signal */
-	sem = INMAIN;
+	SAFE(write(pipefd_start[1], "", 1));
 
 	for (i = 0; i < MAXMSG + 1; i++) {
 		ret = mq_timedsend(gqueue, msgptr, strlen(msgptr), 1, &ts);
 		if (ret	!= -1)
 			continue;
 
+		mq_timedsend_errno = errno;
 		if (errno == EINTR) {
 			if (mq_unlink(gqname) != 0) {
 				perror("mq_unlink() did not return success");
@@ -112,21 +117,24 @@ void *a_thread_func()
 			}
 			printf("thread: mq_timedsend interrupted by signal"
 				" and correctly set errno to EINTR\n");
-			errno_eintr = 1;
+			/* wait for main to stop sending SIGUSR1 */
+			SAFE(read(pipefd_exit[0], &dummy, 1));
 			pthread_exit((void *)PTS_PASS);
 			return NULL;
 		} else {
 			printf("mq_timedsend not interrupted by signal or"
 				" set errno to incorrect code: %d\n", errno);
+			/* wait for main to stop sending SIGUSR1 */
+			SAFE(read(pipefd_exit[0], &dummy, 1));
 			pthread_exit((void *)PTS_FAIL);
 			return NULL;
 		}
 	}
 
-	/* Tell main that it the thread did not block like it should have */
-	sem = INTHREAD;
-
-	perror("Error: thread never blocked\n");
+	mq_timedsend_errno = 0;
+	printf("Error: mq_timedsend wasn't interrupted\n");
+	/* wait for main to stop sending SIGUSR1 */
+	SAFE(read(pipefd_exit[0], &dummy, 1));
 	pthread_exit((void *)PTS_FAIL);
 	return NULL;
 }
@@ -134,13 +142,10 @@ void *a_thread_func()
 int main(void)
 {
 	pthread_t new_th;
-	int i;
+	int i = 0, ret, dummy;
 
-	/* Initialized values */
-	i = 0;
-	in_handler = 0;
-	errno_eintr = 0;
-	sem = INTHREAD;
+	SAFE(pipe(pipefd_start));
+	SAFE(pipe(pipefd_exit));
 
 	if (pthread_create(&new_th, NULL, a_thread_func, NULL) != 0) {
 		perror("Error: in pthread_create\n");
@@ -148,18 +153,22 @@ int main(void)
 	}
 
 	/* Wait for thread to set up handler for SIGUSR1 */
-	while (sem == INTHREAD)
-		sleep(1);
+	SAFE(read(pipefd_start[0], &dummy, 1));
 
-	while ((i != 10) && (sem == INMAIN)) {
+	while (i < TIMEOUT && mq_timedsend_errno < 0) {
 		/* signal thread while it's in mq_timedsend */
-		if (pthread_kill(new_th, SIGUSR1) != 0) {
-			perror("Error: in pthread_kill\n");
+		ret = pthread_kill(new_th, SIGUSR1);
+		if (ret	!= 0) {
+			printf("Error: in pthread_kill: %d\n", ret);
 			return PTS_UNRESOLVED;
 		}
 		i++;
+		sleep(1);
 	}
 
+	/* signal thread it's OK to exit now */
+	SAFE(write(pipefd_exit[1], "", 1));
+
 	if (pthread_join(new_th, NULL) != 0) {
 		perror("Error: in pthread_join()\n");
 		return PTS_UNRESOLVED;
@@ -167,18 +176,17 @@ int main(void)
 
 	/* Test to see if the thread blocked correctly in mq_timedsend,
 	 * and if it returned EINTR when it caught the signal */
-	if (errno_eintr != 1) {
-		if (sem == INTHREAD) {
-			printf("Test FAILED: mq_timedsend() never"
-				" blocked for any timeout period.\n");
-			return PTS_FAIL;
-		}
-
-		if (in_handler != 0) {
-			perror("Error: signal SIGUSR1 was never received and/or"
-				" the signal handler was never called.\n");
+	if (mq_timedsend_errno != EINTR) {
+		printf("Error: mq_timedsend was NOT interrupted\n");
+		printf(" signal handler was called %d times\n", in_handler);
+		printf(" SIGUSR1 signals sent: %d\n", i);
+		printf(" last mq_timedsend errno: %d %s\n",
+			mq_timedsend_errno, strerror(mq_timedsend_errno));
+		if (in_handler == 0) {
+			printf("Error: SIGUSR1 was never received\n");
 			return PTS_UNRESOLVED;
 		}
+		return PTS_FAIL;
 	}
 
 	printf("Test PASSED\n");
-- 
1.7.1


------------------------------------------------------------------------------
See everything from the browser to the database with AppDynamics
Get end-to-end visibility with application monitoring from AppDynamics
Isolate bottlenecks and diagnose root cause in seconds.
Start your free trial of AppDynamics Pro today!
http://pubads.g.doubleclick.net/gampad/clk?id=48808831&iu=/4140/ostg.clktrk
_______________________________________________
Ltp-list mailing list
Ltp-list@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/ltp-list

^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [LTP] [PATCH v2 2/2] open_posix_testsuite/../mq_timedsend/12-1: fix race
  2013-07-24  6:39 ` [LTP] [PATCH 2/2] open_posix_testsuite/../mq_timedsend/12-1: fix race Jan Stancek
@ 2013-07-25 10:07   ` Jan Stancek
  2013-07-31 14:30     ` [LTP] [PATCH v3 " Jan Stancek
  2013-07-30 17:35   ` [LTP] [PATCH " chrubis
  1 sibling, 1 reply; 12+ messages in thread
From: Jan Stancek @ 2013-07-25 10:07 UTC (permalink / raw)
  To: ltp-list

Test can send SIGUSR1 signal after thread has already completed
and report failure from main() and success from a_thread_func():

  conformance/interfaces/mq_timedsend/12-1: execution: UNRESOLVED: Output:
  Error: in pthread_kill
  : Success
  thread: mq_timedsend interrupted by signal and correctly set errno to EINTR

Synchronize exit of a_thread_func(), so that thread can exit only
after loop sending SIGUSR1 completed.

Signed-off-by: Jan Stancek <jstancek@redhat.com>
---
Changes in v2: SIGUSR1 can interrupt reading from pipe too,
so swap SAFE() with loop to restart read() if we got EINTR.

 .../conformance/interfaces/mq_timedsend/12-1.c     |  100 +++++++++++---------
 1 files changed, 57 insertions(+), 43 deletions(-)

diff --git a/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c b/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
index 29780d0..040c097 100644
--- a/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
+++ b/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
@@ -39,19 +39,25 @@
 #define MSGSTR "0123456789"
 #define BUFFER 40
 #define MAXMSG 10
+#define TIMEOUT 10
 
-#define INTHREAD 0
-#define INMAIN 1
+#define SAFE(op) \
+	do {\
+		if ((op) == -1) {\
+			perror("unexpected failure"); \
+			exit(PTS_UNRESOLVED); \
+		} \
+	} while (0)
 
-/* manual semaphore */
-int sem;
+/* variable to indicate how many times signal handler was called */
+static volatile sig_atomic_t in_handler;
 
-/* flag to indicate signal handler was called */
-int in_handler;
+/* errno returned by mq_timedsend() */
+static volatile int mq_timedsend_errno = -1;
 
-/* flag to indicate that errno was set to eintr when mq_timedsend()
- * was interruped. */
-int errno_eintr;
+/* pipes to synchronize thread calling mq_timedsend */
+static int pipefd_start[2];
+static int pipefd_exit[2];
 
 /*
  * This handler is just used to catch the signal and stop sleep (so the
@@ -59,14 +65,12 @@ int errno_eintr;
  */
 void justreturn_handler(int signo)
 {
-	/* Indicate that the signal handler was called */
-	in_handler = 1;
-	return;
+	in_handler++;
 }
 
-void *a_thread_func()
+void *a_thread_func(void *arg)
 {
-	int i, ret;
+	int i, ret, dummy;
 	struct sigaction act;
 	char gqname[NAMESIZE];
 	mqd_t gqueue;
@@ -92,18 +96,19 @@ void *a_thread_func()
 		return NULL;
 	}
 
-	/* mq_timedsend will block for 10 seconds when it waits */
-	ts.tv_sec = time(NULL) + 10;
+	/* mq_timedsend will block for TIMEOUT seconds when it waits */
+	ts.tv_sec = time(NULL) + TIMEOUT;
 	ts.tv_nsec = 0;
 
 	/* Tell main it can go ahead and start sending SIGUSR1 signal */
-	sem = INMAIN;
+	SAFE(write(pipefd_start[1], "", 1));
 
 	for (i = 0; i < MAXMSG + 1; i++) {
 		ret = mq_timedsend(gqueue, msgptr, strlen(msgptr), 1, &ts);
 		if (ret	!= -1)
 			continue;
 
+		mq_timedsend_errno = errno;
 		if (errno == EINTR) {
 			if (mq_unlink(gqname) != 0) {
 				perror("mq_unlink() did not return success");
@@ -112,21 +117,30 @@ void *a_thread_func()
 			}
 			printf("thread: mq_timedsend interrupted by signal"
 				" and correctly set errno to EINTR\n");
-			errno_eintr = 1;
+			/* wait for main to stop sending SIGUSR1 */
+			do {
+				ret = read(pipefd_exit[0], &dummy, 1);
+			} while (ret == -1 && errno == EINTR);
 			pthread_exit((void *)PTS_PASS);
 			return NULL;
 		} else {
 			printf("mq_timedsend not interrupted by signal or"
 				" set errno to incorrect code: %d\n", errno);
+			/* wait for main to stop sending SIGUSR1 */
+			do {
+				ret = read(pipefd_exit[0], &dummy, 1);
+			} while (ret == -1 && errno == EINTR);
 			pthread_exit((void *)PTS_FAIL);
 			return NULL;
 		}
 	}
 
-	/* Tell main that it the thread did not block like it should have */
-	sem = INTHREAD;
-
-	perror("Error: thread never blocked\n");
+	mq_timedsend_errno = 0;
+	printf("Error: mq_timedsend wasn't interrupted\n");
+	/* wait for main to stop sending SIGUSR1 */
+	do {
+		ret = read(pipefd_exit[0], &dummy, 1);
+	} while (ret == -1 && errno == EINTR);
 	pthread_exit((void *)PTS_FAIL);
 	return NULL;
 }
@@ -134,13 +148,10 @@ void *a_thread_func()
 int main(void)
 {
 	pthread_t new_th;
-	int i;
+	int i = 0, ret, dummy;
 
-	/* Initialized values */
-	i = 0;
-	in_handler = 0;
-	errno_eintr = 0;
-	sem = INTHREAD;
+	SAFE(pipe(pipefd_start));
+	SAFE(pipe(pipefd_exit));
 
 	if (pthread_create(&new_th, NULL, a_thread_func, NULL) != 0) {
 		perror("Error: in pthread_create\n");
@@ -148,18 +159,22 @@ int main(void)
 	}
 
 	/* Wait for thread to set up handler for SIGUSR1 */
-	while (sem == INTHREAD)
-		sleep(1);
+	SAFE(read(pipefd_start[0], &dummy, 1));
 
-	while ((i != 10) && (sem == INMAIN)) {
+	while (i < TIMEOUT && mq_timedsend_errno < 0) {
 		/* signal thread while it's in mq_timedsend */
-		if (pthread_kill(new_th, SIGUSR1) != 0) {
-			perror("Error: in pthread_kill\n");
+		ret = pthread_kill(new_th, SIGUSR1);
+		if (ret	!= 0) {
+			printf("Error: in pthread_kill: %d\n", ret);
 			return PTS_UNRESOLVED;
 		}
 		i++;
+		sleep(1);
 	}
 
+	/* signal thread it's OK to exit now */
+	SAFE(write(pipefd_exit[1], "", 1));
+
 	if (pthread_join(new_th, NULL) != 0) {
 		perror("Error: in pthread_join()\n");
 		return PTS_UNRESOLVED;
@@ -167,18 +182,17 @@ int main(void)
 
 	/* Test to see if the thread blocked correctly in mq_timedsend,
 	 * and if it returned EINTR when it caught the signal */
-	if (errno_eintr != 1) {
-		if (sem == INTHREAD) {
-			printf("Test FAILED: mq_timedsend() never"
-				" blocked for any timeout period.\n");
-			return PTS_FAIL;
-		}
-
-		if (in_handler != 0) {
-			perror("Error: signal SIGUSR1 was never received and/or"
-				" the signal handler was never called.\n");
+	if (mq_timedsend_errno != EINTR) {
+		printf("Error: mq_timedsend was NOT interrupted\n");
+		printf(" signal handler was called %d times\n", in_handler);
+		printf(" SIGUSR1 signals sent: %d\n", i);
+		printf(" last mq_timedsend errno: %d %s\n",
+			mq_timedsend_errno, strerror(mq_timedsend_errno));
+		if (in_handler == 0) {
+			printf("Error: SIGUSR1 was never received\n");
 			return PTS_UNRESOLVED;
 		}
+		return PTS_FAIL;
 	}
 
 	printf("Test PASSED\n");
-- 
1.7.1


------------------------------------------------------------------------------
See everything from the browser to the database with AppDynamics
Get end-to-end visibility with application monitoring from AppDynamics
Isolate bottlenecks and diagnose root cause in seconds.
Start your free trial of AppDynamics Pro today!
http://pubads.g.doubleclick.net/gampad/clk?id=48808831&iu=/4140/ostg.clktrk
_______________________________________________
Ltp-list mailing list
Ltp-list@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/ltp-list

^ permalink raw reply related	[flat|nested] 12+ messages in thread

* Re: [LTP] [PATCH 2/2] open_posix_testsuite/../mq_timedsend/12-1: fix race
  2013-07-24  6:39 ` [LTP] [PATCH 2/2] open_posix_testsuite/../mq_timedsend/12-1: fix race Jan Stancek
  2013-07-25 10:07   ` [LTP] [PATCH v2 " Jan Stancek
@ 2013-07-30 17:35   ` chrubis
       [not found]     ` <111760967.10033378.1375213746603.JavaMail.root@redhat.com>
  1 sibling, 1 reply; 12+ messages in thread
From: chrubis @ 2013-07-30 17:35 UTC (permalink / raw)
  To: Jan Stancek; +Cc: ltp-list

Hi!
> -#define INTHREAD 0
> -#define INMAIN 1
> +#define SAFE(op) \
> +	do {\
> +		if ((op) == -1) {\
> +			perror("unexpected failure"); \
> +			exit(PTS_UNRESOLVED); \
> +		} \
> +	} while (0)

I do not like this approach, this does not tell what call has failed. It
would be really hard to figure out what exact line of code has failed
from the test error messages.

> -/* manual semaphore */
> -int sem;
> +/* variable to indicate how many times signal handler was called */
> +static volatile sig_atomic_t in_handler;
>  
> -/* flag to indicate signal handler was called */
> -int in_handler;
> +/* errno returned by mq_timedsend() */
> +static volatile int mq_timedsend_errno = -1;
>  
> -/* flag to indicate that errno was set to eintr when mq_timedsend()
> - * was interruped. */
> -int errno_eintr;
> +/* pipes to synchronize thread calling mq_timedsend */
> +static int pipefd_start[2];
> +static int pipefd_exit[2];

What about using mutexes? (it's multithread application anyway).

-- 
Cyril Hrubis
chrubis@suse.cz

------------------------------------------------------------------------------
Get your SQL database under version control now!
Version control is standard for application code, but databases havent 
caught up. So what steps can you take to put your SQL databases under 
version control? Why should you start doing it? Read more to find out.
http://pubads.g.doubleclick.net/gampad/clk?id=49501711&iu=/4140/ostg.clktrk
_______________________________________________
Ltp-list mailing list
Ltp-list@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/ltp-list

^ permalink raw reply	[flat|nested] 12+ messages in thread

* Re: [LTP] [PATCH 2/2] open_posix_testsuite/../mq_timedsend/12-1: fix race
       [not found]     ` <111760967.10033378.1375213746603.JavaMail.root@redhat.com>
@ 2013-07-31 11:07       ` chrubis
  0 siblings, 0 replies; 12+ messages in thread
From: chrubis @ 2013-07-31 11:07 UTC (permalink / raw)
  To: Jan Stancek; +Cc: ltp-list

Hi!
> > > -#define INTHREAD 0
> > > -#define INMAIN 1
> > > +#define SAFE(op) \
> > > +	do {\
> > > +		if ((op) == -1) {\
> > > +			perror("unexpected failure"); \
> > > +			exit(PTS_UNRESOLVED); \
> > > +		} \
> > > +	} while (0)
> > 
> > I do not like this approach, this does not tell what call has failed. It
> > would be really hard to figure out what exact line of code has failed
> > from the test error messages.
> 
> True, I'll remove that. I took if from other testcase, so we may
> want to fix that one too (some day).

Agreed.

> > > -/* manual semaphore */
> > > -int sem;
> > > +/* variable to indicate how many times signal handler was called */
> > > +static volatile sig_atomic_t in_handler;
> > >  
> > > -/* flag to indicate signal handler was called */
> > > -int in_handler;
> > > +/* errno returned by mq_timedsend() */
> > > +static volatile int mq_timedsend_errno = -1;
> > >  
> > > -/* flag to indicate that errno was set to eintr when mq_timedsend()
> > > - * was interruped. */
> > > -int errno_eintr;
> > > +/* pipes to synchronize thread calling mq_timedsend */
> > > +static int pipefd_start[2];
> > > +static int pipefd_exit[2];
> > 
> > What about using mutexes? (it's multithread application anyway).
> 
> Pipes seemed like less typing, but I can change that.

It just looks strange to synchronize multithread application with pipes,
not that it's wrong...

-- 
Cyril Hrubis
chrubis@suse.cz

------------------------------------------------------------------------------
Get your SQL database under version control now!
Version control is standard for application code, but databases havent 
caught up. So what steps can you take to put your SQL databases under 
version control? Why should you start doing it? Read more to find out.
http://pubads.g.doubleclick.net/gampad/clk?id=49501711&iu=/4140/ostg.clktrk
_______________________________________________
Ltp-list mailing list
Ltp-list@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/ltp-list

^ permalink raw reply	[flat|nested] 12+ messages in thread

* [LTP] [PATCH v3 2/2] open_posix_testsuite/../mq_timedsend/12-1: fix race
  2013-07-25 10:07   ` [LTP] [PATCH v2 " Jan Stancek
@ 2013-07-31 14:30     ` Jan Stancek
  2013-08-12 14:43       ` chrubis
  2013-08-13 13:38       ` [LTP] [PATCH v4 " Jan Stancek
  0 siblings, 2 replies; 12+ messages in thread
From: Jan Stancek @ 2013-07-31 14:30 UTC (permalink / raw)
  To: ltp-list

Test can send SIGUSR1 signal after thread has already completed
and report failure from main() and success from a_thread_func():

  conformance/interfaces/mq_timedsend/12-1: execution: UNRESOLVED: Output:
  Error: in pthread_kill
  : Success
  thread: mq_timedsend interrupted by signal and correctly set errno to EINTR

Synchronize exit of a_thread_func(), so that thread can exit only
after loop sending SIGUSR1 completed.

Signed-off-by: Jan Stancek <jstancek@redhat.com>
---
Changes in v3:
  remove SAFE() macro
  convert pipes to mutex and condition

 .../conformance/interfaces/mq_timedsend/12-1.c     |  175 ++++++++++++--------
 1 files changed, 107 insertions(+), 68 deletions(-)

diff --git a/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c b/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
index 29780d0..fdcb6ec 100644
--- a/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
+++ b/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
@@ -39,19 +39,23 @@
 #define MSGSTR "0123456789"
 #define BUFFER 40
 #define MAXMSG 10
+#define TIMEOUT 10		/* seconds mq_timedsend will block */
+#define SIGNAL_DELAY_MS 50	/* delay in ms between 2 signals */
+#define STATE_THREAD_READY 1
+#define STATE_DONE_SENDING 2
 
-#define INTHREAD 0
-#define INMAIN 1
+#define handle_error_en(en, msg) \
+	do { errno = en; perror(msg); exit(PTS_UNRESOLVED); } while (0)
 
-/* manual semaphore */
-int sem;
+/* variable to indicate how many times signal handler was called */
+static volatile sig_atomic_t in_handler;
 
-/* flag to indicate signal handler was called */
-int in_handler;
+/* errno returned by mq_timedsend() */
+static int mq_timedsend_errno = -1;
 
-/* flag to indicate that errno was set to eintr when mq_timedsend()
- * was interruped. */
-int errno_eintr;
+static int state;
+pthread_mutex_t mutex;
+pthread_cond_t cond;
 
 /*
  * This handler is just used to catch the signal and stop sleep (so the
@@ -59,12 +63,46 @@ int errno_eintr;
  */
 void justreturn_handler(int signo)
 {
-	/* Indicate that the signal handler was called */
-	in_handler = 1;
-	return;
+	in_handler++;
 }
 
-void *a_thread_func()
+void set_state(int n)
+{
+	int ret;
+
+	ret = pthread_mutex_lock(&mutex);
+	if (ret != 0)
+		handle_error_en(ret, "set_state pthread_mutex_lock");
+
+	state = n;
+	ret = pthread_cond_signal(&cond);
+	if (ret != 0)
+		handle_error_en(ret, "set_state pthread_cond_signal");
+
+	ret = pthread_mutex_unlock(&mutex);
+	if (ret != 0)
+		handle_error_en(ret, "set_state pthread_mutex_unlock");
+}
+
+void wait_for_state(int n)
+{
+	int ret;
+
+	ret = pthread_mutex_lock(&mutex);
+	if (ret != 0)
+		handle_error_en(ret, "wait_for_state pthread_mutex_lock");
+
+	while (state != n) {
+		ret = pthread_cond_wait(&cond, &mutex);
+		if (ret != 0)
+			handle_error_en(ret, "pthread_cond_wait");
+	}
+	ret = pthread_mutex_unlock(&mutex);
+	if (ret != 0)
+		handle_error_en(ret, "wait_for_state pthread_mutex_unlock");
+}
+
+void *a_thread_func(void *arg)
 {
 	int i, ret;
 	struct sigaction act;
@@ -86,101 +124,102 @@ void *a_thread_func()
 	attr.mq_maxmsg = MAXMSG;
 	attr.mq_msgsize = BUFFER;
 	gqueue = mq_open(gqname, O_CREAT | O_RDWR, S_IRUSR | S_IWUSR, &attr);
-	if (gqueue == (mqd_t) - 1) {
-		perror("mq_open() did not return success");
-		pthread_exit((void *)PTS_UNRESOLVED);
-		return NULL;
-	}
+	if (gqueue == (mqd_t) -1)
+		handle_error_en(errno, "mq_open");
 
-	/* mq_timedsend will block for 10 seconds when it waits */
-	ts.tv_sec = time(NULL) + 10;
+	/* mq_timedsend will block for TIMEOUT seconds when it waits */
+	ts.tv_sec = time(NULL) + TIMEOUT;
 	ts.tv_nsec = 0;
 
 	/* Tell main it can go ahead and start sending SIGUSR1 signal */
-	sem = INMAIN;
+	set_state(STATE_THREAD_READY);
 
 	for (i = 0; i < MAXMSG + 1; i++) {
 		ret = mq_timedsend(gqueue, msgptr, strlen(msgptr), 1, &ts);
-		if (ret	!= -1)
+		if (ret != -1)
 			continue;
 
+		mq_timedsend_errno = errno;
 		if (errno == EINTR) {
-			if (mq_unlink(gqname) != 0) {
-				perror("mq_unlink() did not return success");
-				pthread_exit((void *)PTS_UNRESOLVED);
-				return NULL;
-			}
+			if (mq_unlink(gqname) != 0)
+				handle_error_en(errno, "mq_unlink");
 			printf("thread: mq_timedsend interrupted by signal"
 				" and correctly set errno to EINTR\n");
-			errno_eintr = 1;
+			wait_for_state(STATE_DONE_SENDING);
 			pthread_exit((void *)PTS_PASS);
-			return NULL;
 		} else {
 			printf("mq_timedsend not interrupted by signal or"
 				" set errno to incorrect code: %d\n", errno);
+			wait_for_state(STATE_DONE_SENDING);
 			pthread_exit((void *)PTS_FAIL);
-			return NULL;
 		}
 	}
 
-	/* Tell main that it the thread did not block like it should have */
-	sem = INTHREAD;
-
-	perror("Error: thread never blocked\n");
+	mq_timedsend_errno = 0;
+	printf("Error: mq_timedsend wasn't interrupted\n");
+	wait_for_state(STATE_DONE_SENDING);
 	pthread_exit((void *)PTS_FAIL);
-	return NULL;
 }
 
 int main(void)
 {
 	pthread_t new_th;
-	int i;
+	int i = 0, ret;
 
-	/* Initialized values */
-	i = 0;
-	in_handler = 0;
-	errno_eintr = 0;
-	sem = INTHREAD;
+	ret = pthread_mutex_init(&mutex, NULL);
+	if (ret != 0)
+		handle_error_en(ret, "pthread_mutex_init");
 
-	if (pthread_create(&new_th, NULL, a_thread_func, NULL) != 0) {
-		perror("Error: in pthread_create\n");
-		return PTS_UNRESOLVED;
-	}
+	ret = pthread_cond_init(&cond, NULL);
+	if (ret != 0)
+		handle_error_en(ret, "pthread_cond_init");
 
-	/* Wait for thread to set up handler for SIGUSR1 */
-	while (sem == INTHREAD)
-		sleep(1);
+	ret = pthread_create(&new_th, NULL, a_thread_func, NULL);
+	if (ret != 0)
+		handle_error_en(ret, "pthread_create");
 
-	while ((i != 10) && (sem == INMAIN)) {
+	/* wait for thread to start */
+	wait_for_state(STATE_THREAD_READY);
+
+	while (i < TIMEOUT*1000 && mq_timedsend_errno < 0) {
 		/* signal thread while it's in mq_timedsend */
-		if (pthread_kill(new_th, SIGUSR1) != 0) {
-			perror("Error: in pthread_kill\n");
-			return PTS_UNRESOLVED;
-		}
-		i++;
+		ret = pthread_kill(new_th, SIGUSR1);
+		if (ret != 0)
+			handle_error_en(ret, "pthread_kill");
+		usleep(SIGNAL_DELAY_MS*1000);
+		i += SIGNAL_DELAY_MS;
 	}
 
-	if (pthread_join(new_th, NULL) != 0) {
-		perror("Error: in pthread_join()\n");
-		return PTS_UNRESOLVED;
-	}
+	/* signal thread we are done sending SIGUSR1 */
+	set_state(STATE_DONE_SENDING);
+
+	ret = pthread_join(new_th, NULL);
+	if (ret != 0)
+		handle_error_en(ret, "pthread_join");
 
 	/* Test to see if the thread blocked correctly in mq_timedsend,
 	 * and if it returned EINTR when it caught the signal */
-	if (errno_eintr != 1) {
-		if (sem == INTHREAD) {
-			printf("Test FAILED: mq_timedsend() never"
-				" blocked for any timeout period.\n");
-			return PTS_FAIL;
-		}
-
-		if (in_handler != 0) {
-			perror("Error: signal SIGUSR1 was never received and/or"
-				" the signal handler was never called.\n");
+	if (mq_timedsend_errno != EINTR) {
+		printf("Error: mq_timedsend was NOT interrupted\n");
+		printf(" signal handler was called %d times\n", in_handler);
+		printf(" SIGUSR1 signals sent: %d\n", i);
+		printf(" last mq_timedsend errno: %d %s\n",
+			mq_timedsend_errno, strerror(mq_timedsend_errno));
+		if (in_handler == 0) {
+			printf("Error: SIGUSR1 was never received\n");
 			return PTS_UNRESOLVED;
 		}
+		return PTS_FAIL;
 	}
 
+	ret = pthread_cond_destroy(&cond);
+	if (ret != 0)
+		handle_error_en(ret, "pthread_cond_destroy");
+
+	ret = pthread_mutex_destroy(&mutex);
+	if (ret != 0)
+		handle_error_en(ret, "pthread_mutex_destroy");
+
 	printf("Test PASSED\n");
 	return PTS_PASS;
 }
-- 
1.7.1

------------------------------------------------------------------------------
Get your SQL database under version control now!
Version control is standard for application code, but databases havent 
caught up. So what steps can you take to put your SQL databases under 
version control? Why should you start doing it? Read more to find out.
http://pubads.g.doubleclick.net/gampad/clk?id=49501711&iu=/4140/ostg.clktrk
_______________________________________________
Ltp-list mailing list
Ltp-list@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/ltp-list

^ permalink raw reply related	[flat|nested] 12+ messages in thread

* Re: [LTP] [PATCH v3 2/2] open_posix_testsuite/../mq_timedsend/12-1: fix race
  2013-07-31 14:30     ` [LTP] [PATCH v3 " Jan Stancek
@ 2013-08-12 14:43       ` chrubis
  2013-08-13 13:38       ` [LTP] [PATCH v4 " Jan Stancek
  1 sibling, 0 replies; 12+ messages in thread
From: chrubis @ 2013-08-12 14:43 UTC (permalink / raw)
  To: Jan Stancek; +Cc: ltp-list

Hi!
> Signed-off-by: Jan Stancek <jstancek@redhat.com>
> ---
> Changes in v3:
>   remove SAFE() macro
>   convert pipes to mutex and condition
> 
>  .../conformance/interfaces/mq_timedsend/12-1.c     |  175 ++++++++++++--------
>  1 files changed, 107 insertions(+), 68 deletions(-)
> 
> diff --git a/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c b/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
> index 29780d0..fdcb6ec 100644
> --- a/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
> +++ b/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
> @@ -39,19 +39,23 @@
>  #define MSGSTR "0123456789"
>  #define BUFFER 40
>  #define MAXMSG 10
> +#define TIMEOUT 10		/* seconds mq_timedsend will block */
> +#define SIGNAL_DELAY_MS 50	/* delay in ms between 2 signals */
> +#define STATE_THREAD_READY 1
> +#define STATE_DONE_SENDING 2
>  
> -#define INTHREAD 0
> -#define INMAIN 1
> +#define handle_error_en(en, msg) \
> +	do { errno = en; perror(msg); exit(PTS_UNRESOLVED); } while (0)

Maybe error_and_exit() would be a bit better name, but that is very
minor.

> -/* manual semaphore */
> -int sem;
> +/* variable to indicate how many times signal handler was called */
> +static volatile sig_atomic_t in_handler;
>  
> -/* flag to indicate signal handler was called */
> -int in_handler;
> +/* errno returned by mq_timedsend() */
> +static int mq_timedsend_errno = -1;
>  
> -/* flag to indicate that errno was set to eintr when mq_timedsend()
> - * was interruped. */
> -int errno_eintr;
> +static int state;
> +pthread_mutex_t mutex;
> +pthread_cond_t cond;
>  
>  /*
>   * This handler is just used to catch the signal and stop sleep (so the
> @@ -59,12 +63,46 @@ int errno_eintr;
>   */
>  void justreturn_handler(int signo)
>  {
> -	/* Indicate that the signal handler was called */
> -	in_handler = 1;
> -	return;
> +	in_handler++;
>  }
>  
> -void *a_thread_func()
> +void set_state(int n)
> +{
> +	int ret;
> +
> +	ret = pthread_mutex_lock(&mutex);
> +	if (ret != 0)
> +		handle_error_en(ret, "set_state pthread_mutex_lock");
> +
> +	state = n;
> +	ret = pthread_cond_signal(&cond);
> +	if (ret != 0)
> +		handle_error_en(ret, "set_state pthread_cond_signal");
> +
> +	ret = pthread_mutex_unlock(&mutex);
> +	if (ret != 0)
> +		handle_error_en(ret, "set_state pthread_mutex_unlock");
> +}
> +
> +void wait_for_state(int n)
> +{
> +	int ret;
> +
> +	ret = pthread_mutex_lock(&mutex);
> +	if (ret != 0)
> +		handle_error_en(ret, "wait_for_state pthread_mutex_lock");
> +
> +	while (state != n) {
> +		ret = pthread_cond_wait(&cond, &mutex);
> +		if (ret != 0)
> +			handle_error_en(ret, "pthread_cond_wait");
> +	}
> +	ret = pthread_mutex_unlock(&mutex);
> +	if (ret != 0)
> +		handle_error_en(ret, "wait_for_state pthread_mutex_unlock");
> +}

Hmm, that gets unnecessary complicated :(

And all we need is to get first thread wait until the second is ready
and then the second until the first has finished sending signals. I
wonder if pthread_barrier or two wouldn't be easier way around.

> +void *a_thread_func(void *arg)
>  {
>  	int i, ret;
>  	struct sigaction act;
> @@ -86,101 +124,102 @@ void *a_thread_func()
>  	attr.mq_maxmsg = MAXMSG;
>  	attr.mq_msgsize = BUFFER;
>  	gqueue = mq_open(gqname, O_CREAT | O_RDWR, S_IRUSR | S_IWUSR, &attr);
> -	if (gqueue == (mqd_t) - 1) {
> -		perror("mq_open() did not return success");
> -		pthread_exit((void *)PTS_UNRESOLVED);
> -		return NULL;
> -	}
> +	if (gqueue == (mqd_t) -1)
> +		handle_error_en(errno, "mq_open");
>  
> -	/* mq_timedsend will block for 10 seconds when it waits */
> -	ts.tv_sec = time(NULL) + 10;
> +	/* mq_timedsend will block for TIMEOUT seconds when it waits */
> +	ts.tv_sec = time(NULL) + TIMEOUT;
>  	ts.tv_nsec = 0;
>  
>  	/* Tell main it can go ahead and start sending SIGUSR1 signal */
> -	sem = INMAIN;
> +	set_state(STATE_THREAD_READY);
>  
>  	for (i = 0; i < MAXMSG + 1; i++) {
>  		ret = mq_timedsend(gqueue, msgptr, strlen(msgptr), 1, &ts);
> -		if (ret	!= -1)
> +		if (ret != -1)
>  			continue;
>  
> +		mq_timedsend_errno = errno;
>  		if (errno == EINTR) {
> -			if (mq_unlink(gqname) != 0) {
> -				perror("mq_unlink() did not return success");
> -				pthread_exit((void *)PTS_UNRESOLVED);
> -				return NULL;
> -			}
> +			if (mq_unlink(gqname) != 0)
> +				handle_error_en(errno, "mq_unlink");
>  			printf("thread: mq_timedsend interrupted by signal"
>  				" and correctly set errno to EINTR\n");
> -			errno_eintr = 1;
> +			wait_for_state(STATE_DONE_SENDING);
>  			pthread_exit((void *)PTS_PASS);
> -			return NULL;
>  		} else {
>  			printf("mq_timedsend not interrupted by signal or"
>  				" set errno to incorrect code: %d\n", errno);
> +			wait_for_state(STATE_DONE_SENDING);
>  			pthread_exit((void *)PTS_FAIL);
> -			return NULL;
>  		}
>  	}
>  
> -	/* Tell main that it the thread did not block like it should have */
> -	sem = INTHREAD;
> -
> -	perror("Error: thread never blocked\n");
> +	mq_timedsend_errno = 0;
> +	printf("Error: mq_timedsend wasn't interrupted\n");
> +	wait_for_state(STATE_DONE_SENDING);
>  	pthread_exit((void *)PTS_FAIL);
> -	return NULL;
>  }
>  
>  int main(void)
>  {
>  	pthread_t new_th;
> -	int i;
> +	int i = 0, ret;
>  
> -	/* Initialized values */
> -	i = 0;
> -	in_handler = 0;
> -	errno_eintr = 0;
> -	sem = INTHREAD;
> +	ret = pthread_mutex_init(&mutex, NULL);
> +	if (ret != 0)
> +		handle_error_en(ret, "pthread_mutex_init");

You can initialize the mutex statically with PTHRED_MUTEX_INITIALIZER.

> -	if (pthread_create(&new_th, NULL, a_thread_func, NULL) != 0) {
> -		perror("Error: in pthread_create\n");
> -		return PTS_UNRESOLVED;
> -	}
> +	ret = pthread_cond_init(&cond, NULL);
> +	if (ret != 0)
> +		handle_error_en(ret, "pthread_cond_init");

Here as well with PTHREAD_COND_INIT.

> -	/* Wait for thread to set up handler for SIGUSR1 */
> -	while (sem == INTHREAD)
> -		sleep(1);
> +	ret = pthread_create(&new_th, NULL, a_thread_func, NULL);
> +	if (ret != 0)
> +		handle_error_en(ret, "pthread_create");
>  
> -	while ((i != 10) && (sem == INMAIN)) {
> +	/* wait for thread to start */
> +	wait_for_state(STATE_THREAD_READY);
> +
> +	while (i < TIMEOUT*1000 && mq_timedsend_errno < 0) {
>  		/* signal thread while it's in mq_timedsend */
> -		if (pthread_kill(new_th, SIGUSR1) != 0) {
> -			perror("Error: in pthread_kill\n");
> -			return PTS_UNRESOLVED;
> -		}
> -		i++;
> +		ret = pthread_kill(new_th, SIGUSR1);
> +		if (ret != 0)
> +			handle_error_en(ret, "pthread_kill");
> +		usleep(SIGNAL_DELAY_MS*1000);
> +		i += SIGNAL_DELAY_MS;
>  	}
>  
> -	if (pthread_join(new_th, NULL) != 0) {
> -		perror("Error: in pthread_join()\n");
> -		return PTS_UNRESOLVED;
> -	}
> +	/* signal thread we are done sending SIGUSR1 */
> +	set_state(STATE_DONE_SENDING);
> +
> +	ret = pthread_join(new_th, NULL);
> +	if (ret != 0)
> +		handle_error_en(ret, "pthread_join");
>  
>  	/* Test to see if the thread blocked correctly in mq_timedsend,
>  	 * and if it returned EINTR when it caught the signal */
> -	if (errno_eintr != 1) {
> -		if (sem == INTHREAD) {
> -			printf("Test FAILED: mq_timedsend() never"
> -				" blocked for any timeout period.\n");
> -			return PTS_FAIL;
> -		}
> -
> -		if (in_handler != 0) {
> -			perror("Error: signal SIGUSR1 was never received and/or"
> -				" the signal handler was never called.\n");
> +	if (mq_timedsend_errno != EINTR) {
> +		printf("Error: mq_timedsend was NOT interrupted\n");
> +		printf(" signal handler was called %d times\n", in_handler);
> +		printf(" SIGUSR1 signals sent: %d\n", i);
> +		printf(" last mq_timedsend errno: %d %s\n",
> +			mq_timedsend_errno, strerror(mq_timedsend_errno));
> +		if (in_handler == 0) {
> +			printf("Error: SIGUSR1 was never received\n");
>  			return PTS_UNRESOLVED;
>  		}
> +		return PTS_FAIL;
>  	}

-- 
Cyril Hrubis
chrubis@suse.cz

------------------------------------------------------------------------------
Get 100% visibility into Java/.NET code with AppDynamics Lite!
It's a free troubleshooting tool designed for production.
Get down to code-level detail for bottlenecks, with <2% overhead. 
Download for free and get started troubleshooting in minutes. 
http://pubads.g.doubleclick.net/gampad/clk?id=48897031&iu=/4140/ostg.clktrk
_______________________________________________
Ltp-list mailing list
Ltp-list@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/ltp-list

^ permalink raw reply	[flat|nested] 12+ messages in thread

* [LTP] [PATCH v4 2/2] open_posix_testsuite/../mq_timedsend/12-1: fix race
  2013-07-31 14:30     ` [LTP] [PATCH v3 " Jan Stancek
  2013-08-12 14:43       ` chrubis
@ 2013-08-13 13:38       ` Jan Stancek
  2013-08-13 15:13         ` chrubis
  2013-08-14 11:28         ` [LTP] [PATCH v5 " Jan Stancek
  1 sibling, 2 replies; 12+ messages in thread
From: Jan Stancek @ 2013-08-13 13:38 UTC (permalink / raw)
  To: ltp-list

Test can send SIGUSR1 signal after thread has already completed
and report failure from main() and success from a_thread_func():

  conformance/interfaces/mq_timedsend/12-1: execution: UNRESOLVED: Output:
  Error: in pthread_kill
  : Success
  thread: mq_timedsend interrupted by signal and correctly set errno to EINTR

Synchronize exit of a_thread_func(), so that thread can exit only
after loop sending SIGUSR1 completed.

Signed-off-by: Jan Stancek <jstancek@redhat.com>
---
Changes in v4:
- renamed handle_error to error_and_exit
- use pthread_barrier instead of mutex/cond
- for loop in a_thread_func modified to minimize code duplication in each branch

 .../conformance/interfaces/mq_timedsend/12-1.c     |  166 ++++++++++---------
 1 files changed, 87 insertions(+), 79 deletions(-)

diff --git a/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c b/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
index 29780d0..96a6656 100644
--- a/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
+++ b/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
@@ -39,19 +39,19 @@
 #define MSGSTR "0123456789"
 #define BUFFER 40
 #define MAXMSG 10
+#define TIMEOUT 10		/* seconds mq_timedsend will block */
+#define SIGNAL_DELAY_MS 50	/* delay in ms between 2 signals */
 
-#define INTHREAD 0
-#define INMAIN 1
+#define error_and_exit(en, msg) \
+	do { errno = en; perror(msg); exit(PTS_UNRESOLVED); } while (0)
 
-/* manual semaphore */
-int sem;
+/* variable to indicate how many times signal handler was called */
+static volatile sig_atomic_t in_handler;
 
-/* flag to indicate signal handler was called */
-int in_handler;
+/* errno returned by mq_timedsend() */
+static int mq_timedsend_errno = -1;
 
-/* flag to indicate that errno was set to eintr when mq_timedsend()
- * was interruped. */
-int errno_eintr;
+pthread_barrier_t barrier;
 
 /*
  * This handler is just used to catch the signal and stop sleep (so the
@@ -59,12 +59,10 @@ int errno_eintr;
  */
 void justreturn_handler(int signo)
 {
-	/* Indicate that the signal handler was called */
-	in_handler = 1;
-	return;
+	in_handler++;
 }
 
-void *a_thread_func()
+void *a_thread_func(void *arg)
 {
 	int i, ret;
 	struct sigaction act;
@@ -86,101 +84,111 @@ void *a_thread_func()
 	attr.mq_maxmsg = MAXMSG;
 	attr.mq_msgsize = BUFFER;
 	gqueue = mq_open(gqname, O_CREAT | O_RDWR, S_IRUSR | S_IWUSR, &attr);
-	if (gqueue == (mqd_t) - 1) {
-		perror("mq_open() did not return success");
-		pthread_exit((void *)PTS_UNRESOLVED);
-		return NULL;
-	}
+	if (gqueue == (mqd_t) -1)
+		error_and_exit(errno, "mq_open");
 
-	/* mq_timedsend will block for 10 seconds when it waits */
-	ts.tv_sec = time(NULL) + 10;
+	/* mq_timedsend will block for TIMEOUT seconds when it waits */
+	ts.tv_sec = time(NULL) + TIMEOUT;
 	ts.tv_nsec = 0;
 
-	/* Tell main it can go ahead and start sending SIGUSR1 signal */
-	sem = INMAIN;
+	/* main can now start sending SIGUSR1 signal */
+	ret = pthread_barrier_wait(&barrier);
+	if (ret != 0 && ret != PTHREAD_BARRIER_SERIAL_THREAD)
+		error_and_exit(ret, "pthread_barrier_wait start");
 
 	for (i = 0; i < MAXMSG + 1; i++) {
 		ret = mq_timedsend(gqueue, msgptr, strlen(msgptr), 1, &ts);
-		if (ret	!= -1)
-			continue;
-
-		if (errno == EINTR) {
-			if (mq_unlink(gqname) != 0) {
-				perror("mq_unlink() did not return success");
-				pthread_exit((void *)PTS_UNRESOLVED);
-				return NULL;
-			}
-			printf("thread: mq_timedsend interrupted by signal"
-				" and correctly set errno to EINTR\n");
-			errno_eintr = 1;
-			pthread_exit((void *)PTS_PASS);
-			return NULL;
-		} else {
-			printf("mq_timedsend not interrupted by signal or"
-				" set errno to incorrect code: %d\n", errno);
-			pthread_exit((void *)PTS_FAIL);
-			return NULL;
+		if (ret == -1) {
+			mq_timedsend_errno = errno;
+			break;
 		}
 	}
 
-	/* Tell main that it the thread did not block like it should have */
-	sem = INTHREAD;
+	if (mq_unlink(gqname) != 0)
+		error_and_exit(errno, "mq_unlink");
+
+	switch (mq_timedsend_errno) {
+	case -1:
+		mq_timedsend_errno = 0;
+		printf("Error: mq_timedsend wasn't interrupted\n");
+		break;
+	case EINTR:
+		printf("thread: mq_timedsend interrupted by signal"
+			" and correctly set errno to EINTR\n");
+		break;
+	default:
+		printf("mq_timedsend not interrupted by signal or"
+			" set errno to incorrect code: %d\n",
+			mq_timedsend_errno);
+		break;
+	}
+
+	/* wait until main stops sending signals */
+	ret = pthread_barrier_wait(&barrier);
+	if (ret != 0 && ret != PTHREAD_BARRIER_SERIAL_THREAD)
+		error_and_exit(ret, "pthread_barrier_wait end");
 
-	perror("Error: thread never blocked\n");
-	pthread_exit((void *)PTS_FAIL);
-	return NULL;
+	if (mq_timedsend_errno == EINTR)
+		pthread_exit((void *)PTS_PASS);
+	else
+		pthread_exit((void *)PTS_FAIL);
 }
 
 int main(void)
 {
 	pthread_t new_th;
-	int i;
+	int i = 0, ret;
 
-	/* Initialized values */
-	i = 0;
-	in_handler = 0;
-	errno_eintr = 0;
-	sem = INTHREAD;
+	ret = pthread_barrier_init(&barrier, NULL, 2);
+	if (ret != 0)
+		error_and_exit(ret, "pthread_barrier_init");
 
-	if (pthread_create(&new_th, NULL, a_thread_func, NULL) != 0) {
-		perror("Error: in pthread_create\n");
-		return PTS_UNRESOLVED;
-	}
+	ret = pthread_create(&new_th, NULL, a_thread_func, NULL);
+	if (ret != 0)
+		error_and_exit(ret, "pthread_create");
 
-	/* Wait for thread to set up handler for SIGUSR1 */
-	while (sem == INTHREAD)
-		sleep(1);
+	/* wait for thread to start */
+	ret = pthread_barrier_wait(&barrier);
+	if (ret != 0 && ret != PTHREAD_BARRIER_SERIAL_THREAD)
+		error_and_exit(ret, "pthread_barrier_wait start");
 
-	while ((i != 10) && (sem == INMAIN)) {
+	while (i < TIMEOUT*1000 && mq_timedsend_errno < 0) {
 		/* signal thread while it's in mq_timedsend */
-		if (pthread_kill(new_th, SIGUSR1) != 0) {
-			perror("Error: in pthread_kill\n");
-			return PTS_UNRESOLVED;
-		}
-		i++;
+		ret = pthread_kill(new_th, SIGUSR1);
+		if (ret != 0)
+			error_and_exit(ret, "pthread_kill");
+		usleep(SIGNAL_DELAY_MS*1000);
+		i += SIGNAL_DELAY_MS;
 	}
 
-	if (pthread_join(new_th, NULL) != 0) {
-		perror("Error: in pthread_join()\n");
-		return PTS_UNRESOLVED;
-	}
+	/* thread can now safely exit */
+	ret = pthread_barrier_wait(&barrier);
+	if (ret != 0 && ret != PTHREAD_BARRIER_SERIAL_THREAD)
+		error_and_exit(ret, "pthread_barrier_wait end");
+
+	ret = pthread_join(new_th, NULL);
+	if (ret != 0)
+		error_and_exit(ret, "pthread_join");
 
 	/* Test to see if the thread blocked correctly in mq_timedsend,
 	 * and if it returned EINTR when it caught the signal */
-	if (errno_eintr != 1) {
-		if (sem == INTHREAD) {
-			printf("Test FAILED: mq_timedsend() never"
-				" blocked for any timeout period.\n");
-			return PTS_FAIL;
-		}
-
-		if (in_handler != 0) {
-			perror("Error: signal SIGUSR1 was never received and/or"
-				" the signal handler was never called.\n");
+	if (mq_timedsend_errno != EINTR) {
+		printf("Error: mq_timedsend was NOT interrupted\n");
+		printf(" signal handler was called %d times\n", in_handler);
+		printf(" SIGUSR1 signals sent: %d\n", i);
+		printf(" last mq_timedsend errno: %d %s\n",
+			mq_timedsend_errno, strerror(mq_timedsend_errno));
+		if (in_handler == 0) {
+			printf("Error: SIGUSR1 was never received\n");
 			return PTS_UNRESOLVED;
 		}
+		return PTS_FAIL;
 	}
 
+	ret = pthread_barrier_destroy(&barrier);
+	if (ret != 0)
+		error_and_exit(ret, "pthread_barrier_destroy");
+
 	printf("Test PASSED\n");
 	return PTS_PASS;
 }
-- 
1.7.1


------------------------------------------------------------------------------
Get 100% visibility into Java/.NET code with AppDynamics Lite!
It's a free troubleshooting tool designed for production.
Get down to code-level detail for bottlenecks, with <2% overhead. 
Download for free and get started troubleshooting in minutes. 
http://pubads.g.doubleclick.net/gampad/clk?id=48897031&iu=/4140/ostg.clktrk
_______________________________________________
Ltp-list mailing list
Ltp-list@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/ltp-list

^ permalink raw reply related	[flat|nested] 12+ messages in thread

* Re: [LTP] [PATCH v4 2/2] open_posix_testsuite/../mq_timedsend/12-1: fix race
  2013-08-13 13:38       ` [LTP] [PATCH v4 " Jan Stancek
@ 2013-08-13 15:13         ` chrubis
  2013-08-14 11:28         ` [LTP] [PATCH v5 " Jan Stancek
  1 sibling, 0 replies; 12+ messages in thread
From: chrubis @ 2013-08-13 15:13 UTC (permalink / raw)
  To: Jan Stancek; +Cc: ltp-list

>  /*
>   * This handler is just used to catch the signal and stop sleep (so the
> @@ -59,12 +59,10 @@ int errno_eintr;
>   */
>  void justreturn_handler(int signo)
>  {
> -	/* Indicate that the signal handler was called */
> -	in_handler = 1;
> -	return;
> +	in_handler++;
>  }
>  
> -void *a_thread_func()
> +void *a_thread_func(void *arg)
>  {
>  	int i, ret;
>  	struct sigaction act;
> @@ -86,101 +84,111 @@ void *a_thread_func()
>  	attr.mq_maxmsg = MAXMSG;
>  	attr.mq_msgsize = BUFFER;
>  	gqueue = mq_open(gqname, O_CREAT | O_RDWR, S_IRUSR | S_IWUSR, &attr);
> -	if (gqueue == (mqd_t) - 1) {
> -		perror("mq_open() did not return success");
> -		pthread_exit((void *)PTS_UNRESOLVED);
> -		return NULL;
> -	}
> +	if (gqueue == (mqd_t) -1)
> +		error_and_exit(errno, "mq_open");
>  
> -	/* mq_timedsend will block for 10 seconds when it waits */
> -	ts.tv_sec = time(NULL) + 10;
> +	/* mq_timedsend will block for TIMEOUT seconds when it waits */
> +	ts.tv_sec = time(NULL) + TIMEOUT;
>  	ts.tv_nsec = 0;
>  
> -	/* Tell main it can go ahead and start sending SIGUSR1 signal */
> -	sem = INMAIN;
> +	/* main can now start sending SIGUSR1 signal */
> +	ret = pthread_barrier_wait(&barrier);
> +	if (ret != 0 && ret != PTHREAD_BARRIER_SERIAL_THREAD)
> +		error_and_exit(ret, "pthread_barrier_wait start");
>  
>  	for (i = 0; i < MAXMSG + 1; i++) {
>  		ret = mq_timedsend(gqueue, msgptr, strlen(msgptr), 1, &ts);
> -		if (ret	!= -1)
> -			continue;
> -
> -		if (errno == EINTR) {
> -			if (mq_unlink(gqname) != 0) {
> -				perror("mq_unlink() did not return success");
> -				pthread_exit((void *)PTS_UNRESOLVED);
> -				return NULL;
> -			}
> -			printf("thread: mq_timedsend interrupted by signal"
> -				" and correctly set errno to EINTR\n");
> -			errno_eintr = 1;
> -			pthread_exit((void *)PTS_PASS);
> -			return NULL;
> -		} else {
> -			printf("mq_timedsend not interrupted by signal or"
> -				" set errno to incorrect code: %d\n", errno);
> -			pthread_exit((void *)PTS_FAIL);
> -			return NULL;
> +		if (ret == -1) {
> +			mq_timedsend_errno = errno;
> +			break;
>  		}
>  	}
>  
> -	/* Tell main that it the thread did not block like it should have */
> -	sem = INTHREAD;
> +	if (mq_unlink(gqname) != 0)
> +		error_and_exit(errno, "mq_unlink");
> +
> +	switch (mq_timedsend_errno) {
> +	case -1:
> +		mq_timedsend_errno = 0;
> +		printf("Error: mq_timedsend wasn't interrupted\n");
> +		break;
> +	case EINTR:
> +		printf("thread: mq_timedsend interrupted by signal"
> +			" and correctly set errno to EINTR\n");
> +		break;
> +	default:
> +		printf("mq_timedsend not interrupted by signal or"
> +			" set errno to incorrect code: %d\n",
> +			mq_timedsend_errno);
> +		break;
> +	}
> +
> +	/* wait until main stops sending signals */
> +	ret = pthread_barrier_wait(&barrier);
> +	if (ret != 0 && ret != PTHREAD_BARRIER_SERIAL_THREAD)
> +		error_and_exit(ret, "pthread_barrier_wait end");
>  
> -	perror("Error: thread never blocked\n");
> -	pthread_exit((void *)PTS_FAIL);
> -	return NULL;
> +	if (mq_timedsend_errno == EINTR)
> +		pthread_exit((void *)PTS_PASS);
> +	else
> +		pthread_exit((void *)PTS_FAIL);

Are these even used? The pthread_join() below has NULL parameter and the
mq_timedsend_errno is used directly.

The rests looks OK.

-- 
Cyril Hrubis
chrubis@suse.cz

------------------------------------------------------------------------------
Get 100% visibility into Java/.NET code with AppDynamics Lite!
It's a free troubleshooting tool designed for production.
Get down to code-level detail for bottlenecks, with <2% overhead. 
Download for free and get started troubleshooting in minutes. 
http://pubads.g.doubleclick.net/gampad/clk?id=48897031&iu=/4140/ostg.clktrk
_______________________________________________
Ltp-list mailing list
Ltp-list@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/ltp-list

^ permalink raw reply	[flat|nested] 12+ messages in thread

* [LTP] [PATCH v5 2/2] open_posix_testsuite/../mq_timedsend/12-1: fix race
  2013-08-13 13:38       ` [LTP] [PATCH v4 " Jan Stancek
  2013-08-13 15:13         ` chrubis
@ 2013-08-14 11:28         ` Jan Stancek
  2013-08-15 12:53           ` chrubis
  1 sibling, 1 reply; 12+ messages in thread
From: Jan Stancek @ 2013-08-14 11:28 UTC (permalink / raw)
  To: ltp-list

Test can send SIGUSR1 signal after thread has already completed
and report failure from main() and success from a_thread_func():

  conformance/interfaces/mq_timedsend/12-1: execution: UNRESOLVED: Output:
  Error: in pthread_kill
  : Success
  thread: mq_timedsend interrupted by signal and correctly set errno to EINTR

Synchronize exit of a_thread_func(), so that thread can exit only
after loop sending SIGUSR1 completed.

Signed-off-by: Jan Stancek <jstancek@redhat.com>
---
Changes in v5:
- return value from pthread_exit is not used, always return NULL

 .../conformance/interfaces/mq_timedsend/12-1.c     |  162 ++++++++++----------
 1 files changed, 83 insertions(+), 79 deletions(-)

diff --git a/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c b/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
index 29780d0..f99e2fb 100644
--- a/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
+++ b/testcases/open_posix_testsuite/conformance/interfaces/mq_timedsend/12-1.c
@@ -39,19 +39,19 @@
 #define MSGSTR "0123456789"
 #define BUFFER 40
 #define MAXMSG 10
+#define TIMEOUT 10		/* seconds mq_timedsend will block */
+#define SIGNAL_DELAY_MS 50	/* delay in ms between 2 signals */
 
-#define INTHREAD 0
-#define INMAIN 1
+#define error_and_exit(en, msg) \
+	do { errno = en; perror(msg); exit(PTS_UNRESOLVED); } while (0)
 
-/* manual semaphore */
-int sem;
+/* variable to indicate how many times signal handler was called */
+static volatile sig_atomic_t in_handler;
 
-/* flag to indicate signal handler was called */
-int in_handler;
+/* errno returned by mq_timedsend() */
+static int mq_timedsend_errno = -1;
 
-/* flag to indicate that errno was set to eintr when mq_timedsend()
- * was interruped. */
-int errno_eintr;
+pthread_barrier_t barrier;
 
 /*
  * This handler is just used to catch the signal and stop sleep (so the
@@ -59,12 +59,10 @@ int errno_eintr;
  */
 void justreturn_handler(int signo)
 {
-	/* Indicate that the signal handler was called */
-	in_handler = 1;
-	return;
+	in_handler++;
 }
 
-void *a_thread_func()
+void *a_thread_func(void *arg)
 {
 	int i, ret;
 	struct sigaction act;
@@ -86,101 +84,107 @@ void *a_thread_func()
 	attr.mq_maxmsg = MAXMSG;
 	attr.mq_msgsize = BUFFER;
 	gqueue = mq_open(gqname, O_CREAT | O_RDWR, S_IRUSR | S_IWUSR, &attr);
-	if (gqueue == (mqd_t) - 1) {
-		perror("mq_open() did not return success");
-		pthread_exit((void *)PTS_UNRESOLVED);
-		return NULL;
-	}
+	if (gqueue == (mqd_t) -1)
+		error_and_exit(errno, "mq_open");
 
-	/* mq_timedsend will block for 10 seconds when it waits */
-	ts.tv_sec = time(NULL) + 10;
+	/* mq_timedsend will block for TIMEOUT seconds when it waits */
+	ts.tv_sec = time(NULL) + TIMEOUT;
 	ts.tv_nsec = 0;
 
-	/* Tell main it can go ahead and start sending SIGUSR1 signal */
-	sem = INMAIN;
+	/* main can now start sending SIGUSR1 signal */
+	ret = pthread_barrier_wait(&barrier);
+	if (ret != 0 && ret != PTHREAD_BARRIER_SERIAL_THREAD)
+		error_and_exit(ret, "pthread_barrier_wait start");
 
 	for (i = 0; i < MAXMSG + 1; i++) {
 		ret = mq_timedsend(gqueue, msgptr, strlen(msgptr), 1, &ts);
-		if (ret	!= -1)
-			continue;
-
-		if (errno == EINTR) {
-			if (mq_unlink(gqname) != 0) {
-				perror("mq_unlink() did not return success");
-				pthread_exit((void *)PTS_UNRESOLVED);
-				return NULL;
-			}
-			printf("thread: mq_timedsend interrupted by signal"
-				" and correctly set errno to EINTR\n");
-			errno_eintr = 1;
-			pthread_exit((void *)PTS_PASS);
-			return NULL;
-		} else {
-			printf("mq_timedsend not interrupted by signal or"
-				" set errno to incorrect code: %d\n", errno);
-			pthread_exit((void *)PTS_FAIL);
-			return NULL;
+		if (ret == -1) {
+			mq_timedsend_errno = errno;
+			break;
 		}
 	}
 
-	/* Tell main that it the thread did not block like it should have */
-	sem = INTHREAD;
+	if (mq_unlink(gqname) != 0)
+		error_and_exit(errno, "mq_unlink");
+
+	switch (mq_timedsend_errno) {
+	case -1:
+		mq_timedsend_errno = 0;
+		printf("Error: mq_timedsend wasn't interrupted\n");
+		break;
+	case EINTR:
+		printf("thread: mq_timedsend interrupted by signal"
+			" and correctly set errno to EINTR\n");
+		break;
+	default:
+		printf("mq_timedsend not interrupted by signal or"
+			" set errno to incorrect code: %d\n",
+			mq_timedsend_errno);
+		break;
+	}
 
-	perror("Error: thread never blocked\n");
-	pthread_exit((void *)PTS_FAIL);
-	return NULL;
+	/* wait until main stops sending signals */
+	ret = pthread_barrier_wait(&barrier);
+	if (ret != 0 && ret != PTHREAD_BARRIER_SERIAL_THREAD)
+		error_and_exit(ret, "pthread_barrier_wait end");
+	pthread_exit(NULL);
 }
 
 int main(void)
 {
 	pthread_t new_th;
-	int i;
+	int i = 0, ret;
 
-	/* Initialized values */
-	i = 0;
-	in_handler = 0;
-	errno_eintr = 0;
-	sem = INTHREAD;
+	ret = pthread_barrier_init(&barrier, NULL, 2);
+	if (ret != 0)
+		error_and_exit(ret, "pthread_barrier_init");
 
-	if (pthread_create(&new_th, NULL, a_thread_func, NULL) != 0) {
-		perror("Error: in pthread_create\n");
-		return PTS_UNRESOLVED;
-	}
+	ret = pthread_create(&new_th, NULL, a_thread_func, NULL);
+	if (ret != 0)
+		error_and_exit(ret, "pthread_create");
 
-	/* Wait for thread to set up handler for SIGUSR1 */
-	while (sem == INTHREAD)
-		sleep(1);
+	/* wait for thread to start */
+	ret = pthread_barrier_wait(&barrier);
+	if (ret != 0 && ret != PTHREAD_BARRIER_SERIAL_THREAD)
+		error_and_exit(ret, "pthread_barrier_wait start");
 
-	while ((i != 10) && (sem == INMAIN)) {
+	while (i < TIMEOUT*1000 && mq_timedsend_errno < 0) {
 		/* signal thread while it's in mq_timedsend */
-		if (pthread_kill(new_th, SIGUSR1) != 0) {
-			perror("Error: in pthread_kill\n");
-			return PTS_UNRESOLVED;
-		}
-		i++;
+		ret = pthread_kill(new_th, SIGUSR1);
+		if (ret != 0)
+			error_and_exit(ret, "pthread_kill");
+		usleep(SIGNAL_DELAY_MS*1000);
+		i += SIGNAL_DELAY_MS;
 	}
 
-	if (pthread_join(new_th, NULL) != 0) {
-		perror("Error: in pthread_join()\n");
-		return PTS_UNRESOLVED;
-	}
+	/* thread can now safely exit */
+	ret = pthread_barrier_wait(&barrier);
+	if (ret != 0 && ret != PTHREAD_BARRIER_SERIAL_THREAD)
+		error_and_exit(ret, "pthread_barrier_wait end");
+
+	ret = pthread_join(new_th, NULL);
+	if (ret != 0)
+		error_and_exit(ret, "pthread_join");
 
 	/* Test to see if the thread blocked correctly in mq_timedsend,
 	 * and if it returned EINTR when it caught the signal */
-	if (errno_eintr != 1) {
-		if (sem == INTHREAD) {
-			printf("Test FAILED: mq_timedsend() never"
-				" blocked for any timeout period.\n");
-			return PTS_FAIL;
-		}
-
-		if (in_handler != 0) {
-			perror("Error: signal SIGUSR1 was never received and/or"
-				" the signal handler was never called.\n");
+	if (mq_timedsend_errno != EINTR) {
+		printf("Error: mq_timedsend was NOT interrupted\n");
+		printf(" signal handler was called %d times\n", in_handler);
+		printf(" SIGUSR1 signals sent: %d\n", i);
+		printf(" last mq_timedsend errno: %d %s\n",
+			mq_timedsend_errno, strerror(mq_timedsend_errno));
+		if (in_handler == 0) {
+			printf("Error: SIGUSR1 was never received\n");
 			return PTS_UNRESOLVED;
 		}
+		return PTS_FAIL;
 	}
 
+	ret = pthread_barrier_destroy(&barrier);
+	if (ret != 0)
+		error_and_exit(ret, "pthread_barrier_destroy");
+
 	printf("Test PASSED\n");
 	return PTS_PASS;
 }
-- 
1.7.1


------------------------------------------------------------------------------
Get 100% visibility into Java/.NET code with AppDynamics Lite!
It's a free troubleshooting tool designed for production.
Get down to code-level detail for bottlenecks, with <2% overhead. 
Download for free and get started troubleshooting in minutes. 
http://pubads.g.doubleclick.net/gampad/clk?id=48897031&iu=/4140/ostg.clktrk
_______________________________________________
Ltp-list mailing list
Ltp-list@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/ltp-list

^ permalink raw reply related	[flat|nested] 12+ messages in thread

* Re: [LTP] [PATCH v5 2/2] open_posix_testsuite/../mq_timedsend/12-1: fix race
  2013-08-14 11:28         ` [LTP] [PATCH v5 " Jan Stancek
@ 2013-08-15 12:53           ` chrubis
  2013-08-27 11:51             ` chrubis
  0 siblings, 1 reply; 12+ messages in thread
From: chrubis @ 2013-08-15 12:53 UTC (permalink / raw)
  To: Jan Stancek; +Cc: ltp-list

Hi!
> Test can send SIGUSR1 signal after thread has already completed
> and report failure from main() and success from a_thread_func():
> 
>   conformance/interfaces/mq_timedsend/12-1: execution: UNRESOLVED: Output:
>   Error: in pthread_kill
>   : Success
>   thread: mq_timedsend interrupted by signal and correctly set errno to EINTR
> 
> Synchronize exit of a_thread_func(), so that thread can exit only
> after loop sending SIGUSR1 completed.
> 
> Signed-off-by: Jan Stancek <jstancek@redhat.com>
> ---
> Changes in v5:
> - return value from pthread_exit is not used, always return NULL

Looks good to me. Acked.

-- 
Cyril Hrubis
chrubis@suse.cz

------------------------------------------------------------------------------
Get 100% visibility into Java/.NET code with AppDynamics Lite!
It's a free troubleshooting tool designed for production.
Get down to code-level detail for bottlenecks, with <2% overhead. 
Download for free and get started troubleshooting in minutes. 
http://pubads.g.doubleclick.net/gampad/clk?id=48897031&iu=/4140/ostg.clktrk
_______________________________________________
Ltp-list mailing list
Ltp-list@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/ltp-list

^ permalink raw reply	[flat|nested] 12+ messages in thread

* Re: [LTP] [PATCH v5 2/2] open_posix_testsuite/../mq_timedsend/12-1: fix race
  2013-08-15 12:53           ` chrubis
@ 2013-08-27 11:51             ` chrubis
  0 siblings, 0 replies; 12+ messages in thread
From: chrubis @ 2013-08-27 11:51 UTC (permalink / raw)
  To: Jan Stancek; +Cc: ltp-list

Hi!
> > Test can send SIGUSR1 signal after thread has already completed
> > and report failure from main() and success from a_thread_func():
> > 
> >   conformance/interfaces/mq_timedsend/12-1: execution: UNRESOLVED: Output:
> >   Error: in pthread_kill
> >   : Success
> >   thread: mq_timedsend interrupted by signal and correctly set errno to EINTR
> > 
> > Synchronize exit of a_thread_func(), so that thread can exit only
> > after loop sending SIGUSR1 completed.
> > 
> > Signed-off-by: Jan Stancek <jstancek@redhat.com>
> > ---
> > Changes in v5:
> > - return value from pthread_exit is not used, always return NULL
> 
> Looks good to me. Acked.
> 

Did you forget to commit this patch?

-- 
Cyril Hrubis
chrubis@suse.cz

------------------------------------------------------------------------------
Introducing Performance Central, a new site from SourceForge and 
AppDynamics. Performance Central is your source for news, insights, 
analysis and resources for efficient Application Performance Management. 
Visit us today!
http://pubads.g.doubleclick.net/gampad/clk?id=48897511&iu=/4140/ostg.clktrk
_______________________________________________
Ltp-list mailing list
Ltp-list@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/ltp-list

^ permalink raw reply	[flat|nested] 12+ messages in thread

end of thread, other threads:[~2013-08-27 11:51 UTC | newest]

Thread overview: 12+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2013-07-24  6:39 [LTP] [PATCH 1/2] open_posix_testsuite/../mq_timedsend/12-1: fix long lines Jan Stancek
2013-07-24  6:39 ` [LTP] [PATCH 2/2] open_posix_testsuite/../mq_timedsend/12-1: fix race Jan Stancek
2013-07-25 10:07   ` [LTP] [PATCH v2 " Jan Stancek
2013-07-31 14:30     ` [LTP] [PATCH v3 " Jan Stancek
2013-08-12 14:43       ` chrubis
2013-08-13 13:38       ` [LTP] [PATCH v4 " Jan Stancek
2013-08-13 15:13         ` chrubis
2013-08-14 11:28         ` [LTP] [PATCH v5 " Jan Stancek
2013-08-15 12:53           ` chrubis
2013-08-27 11:51             ` chrubis
2013-07-30 17:35   ` [LTP] [PATCH " chrubis
     [not found]     ` <111760967.10033378.1375213746603.JavaMail.root@redhat.com>
2013-07-31 11:07       ` chrubis

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.