All of lore.kernel.org
 help / color / mirror / Atom feed
* [LTP] [PATCH] msgctl11: process message queues by portions
@ 2013-12-16 13:39 Stanislav Kholmanskikh
  2014-02-06 13:29 ` chrubis
  0 siblings, 1 reply; 11+ messages in thread
From: Stanislav Kholmanskikh @ 2013-12-16 13:39 UTC (permalink / raw)
  To: ltp-list; +Cc: vasily.isaenko

As /proc/sys/kernel/msgmni value scales with an amount of host memory,
on systems with several tens gigabytes of ram this testcase fails
with "Not enough free pids" error.

Now if the amount of free pids is not enough to use all the queues at once
we process the queues by portions (with the size based on amount of free pids).

Signed-off-by: Stanislav Kholmanskikh <stanislav.kholmanskikh@oracle.com>
---
 testcases/kernel/syscalls/ipc/msgctl/msgctl11.c |   98 +++++++++++++----------
 1 files changed, 57 insertions(+), 41 deletions(-)

diff --git a/testcases/kernel/syscalls/ipc/msgctl/msgctl11.c b/testcases/kernel/syscalls/ipc/msgctl/msgctl11.c
index 57f4ae0..8bbb922 100644
--- a/testcases/kernel/syscalls/ipc/msgctl/msgctl11.c
+++ b/testcases/kernel/syscalls/ipc/msgctl/msgctl11.c
@@ -60,6 +60,7 @@ static int rkidarray[MAXNKIDS];
 static int wkidarray[MAXNKIDS];
 static int tid;
 static int nprocs, nreps, nkids, MSGMNI;
+static int maxnprocs;
 static int procstat;
 
 void setup(void);
@@ -67,6 +68,7 @@ void cleanup(void);
 
 static void term(int);
 static int dotest(key_t, int);
+static void dotest_iteration(int, int);
 static void cleanup_msgqueue(int i, int tid);
 
 #ifdef UCLINUX
@@ -84,8 +86,7 @@ static void do_child_3_uclinux();
 
 int main(int argc, char **argv)
 {
-	int i, j, ok, pid;
-	int count, status;
+	int i, j, ok;
 
 #ifdef UCLINUX
 	char *msg;
@@ -109,7 +110,6 @@ int main(int argc, char **argv)
 	if (argc == 1) {
 		/* Set default parameters */
 		nreps = MAXNREPS;
-		nprocs = MSGMNI;
 		nkids = maxnkids;
 	} else if (argc == 4) {
 		if (atoi(argv[1]) > MAXNREPS) {
@@ -120,13 +120,12 @@ int main(int argc, char **argv)
 		} else {
 			nreps = atoi(argv[1]);
 		}
-		if (atoi(argv[2]) > MSGMNI) {
+		if (atoi(argv[2]) > maxnprocs) {
 			tst_resm(TCONF,
 				 "Requested number of processes too large, setting to Max. of %d",
-				 MSGMNI);
-			nprocs = MSGMNI;
+				 maxnprocs);
 		} else {
-			nprocs = atoi(argv[2]);
+			maxnprocs = atoi(argv[2]);
 		}
 		if (atoi(argv[3]) > maxnkids) {
 			tst_resm(TCONF,
@@ -147,15 +146,14 @@ int main(int argc, char **argv)
 	srand48((unsigned)getpid() + (unsigned)(getppid() << 16));
 	tid = -1;
 
-	/* Setup signal handleing routine */
-	if (sigset(SIGTERM, term) == SIG_ERR) {
-		tst_resm(TFAIL, "Sigset SIGTERM failed");
-		tst_exit();
-	}
+	/* Setup signal handling routine */
+	if (sigset(SIGTERM, term) == SIG_ERR)
+		tst_brkm(TFAIL, cleanup, "Sigset SIGTERM failed");
+
 	/* Set up array of unique keys for use in allocating message
 	 * queues
 	 */
-	for (i = 0; i < nprocs; i++) {
+	for (i = 0; i < MSGMNI; i++) {
 		ok = 1;
 		do {
 			/* Get random key */
@@ -174,13 +172,45 @@ int main(int argc, char **argv)
 			}
 		} while (ok == 0);
 	}
-	/* Fork a number of processes (nprocs), each of which will
+	/* Fork a number of processes, each of which will
 	 * create a message queue with several (nkids) reader/writer
 	 * pairs which will read and write a number (iterations)
 	 * of random length messages with specific values (keys).
+	 *
+	 * We do not fork more than maxnprocs at a time and
+	 * we fork until all the message queues get used.
 	 */
 
+	if (MSGMNI < maxnprocs) {
+		dotest_iteration(0, MSGMNI);
+	} else {
+		for (i = 0; i < (MSGMNI / maxnprocs); i++)
+			dotest_iteration(i*(MSGMNI / maxnprocs),
+					maxnprocs);
+
+		dotest_iteration(i*(MSGMNI / maxnprocs),
+				MSGMNI % maxnprocs);
+	}
+
+	tst_resm(TPASS, "msgctl11 ran successfully!");
+
+	cleanup();
+	tst_exit();
+}
+
+static void dotest_iteration(int idx, int no_of_processes)
+{
+	key_t key;
+	int i, count, status;
+	pid_t pid;
+
+	nprocs = no_of_processes;
+
+	memset(pidarray, 0, MAXNPROCS * sizeof(*pidarray));
+
 	for (i = 0; i < nprocs; i++) {
+		key = keyarray[idx + i];
+
 		fflush(stdout);
 		if ((pid = FORK_OR_VFORK()) < 0) {
 			tst_resm(TFAIL,
@@ -190,13 +220,13 @@ int main(int argc, char **argv)
 		/* Child does this */
 		if (pid == 0) {
 #ifdef UCLINUX
-			if (self_exec(argv[0], "ndd", 1, keyarray[i], i) < 0) {
+			if (self_exec(argv0, "ndd", 1, key, i) < 0) {
 				tst_resm(TFAIL, "\tself_exec failed");
 				tst_exit();
 			}
 #else
 			procstat = 1;
-			exit(dotest(keyarray[i], i));
+			exit(dotest(key, i));
 #endif
 		}
 		pidarray[i] = pid;
@@ -227,13 +257,6 @@ int main(int argc, char **argv)
 			 count, nprocs);
 		tst_exit();
 	}
-
-	tst_resm(TPASS, "msgctl11 ran successfully!");
-
-	cleanup();
-
-	return (0);
-
 }
 
 #ifdef UCLINUX
@@ -453,33 +476,26 @@ void setup(void)
 
 	nr_msgqs = get_max_msgqueues();
 	if (nr_msgqs < 0)
-		cleanup();
+		tst_brkm(TBROK, cleanup, "get_max_msgqueues() failed");
 
 	MSGMNI = nr_msgqs - get_used_msgqueues();
-	if (MSGMNI <= 0) {
-		tst_resm(TBROK,
+	if (MSGMNI <= 0)
+		tst_brkm(TBROK, cleanup,
 			 "Max number of message queues already used, cannot create more.");
-		cleanup();
-	}
+
+	tst_resm(TINFO, "Found %d available message queues", MSGMNI);
 
 	free_pids = get_free_pids();
 	if (free_pids < 0) {
-		tst_resm(TBROK, "Can't obtain free_pid count");
-		tst_exit();
+		tst_brkm(TBROK, cleanup, "Can't obtain free_pid count");
+	} else if (!free_pids) {
+		tst_brkm(TBROK, cleanup, "No free pids");
 	}
 
-	else if (!free_pids) {
-		tst_resm(TBROK, "No free pids");
-		tst_exit();
-	}
+	maxnprocs = (free_pids / 2) / (1 + 2*maxnkids);
 
-	if ((MSGMNI * MAXNKIDS * 2) > (free_pids / 2)) {
-		maxnkids = ((free_pids / 4) / MSGMNI);
-		if (!maxnkids) {
-			tst_resm(TBROK, "Not enough free pids");
-			tst_exit();
-		}
-	}
+	if (!maxnprocs)
+		tst_brkm(TBROK, cleanup, "Not enough free pids");
 
 	tst_resm(TINFO, "Using upto %d pids", free_pids / 2);
 }
-- 
1.7.1


------------------------------------------------------------------------------
Rapidly troubleshoot problems before they affect your business. Most IT 
organizations don't have a clear picture of how application performance 
affects their revenue. With AppDynamics, you get 100% visibility into your 
Java,.NET, & PHP application. Start your 15-day FREE TRIAL of AppDynamics Pro!
http://pubads.g.doubleclick.net/gampad/clk?id=84349831&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] 11+ messages in thread

end of thread, other threads:[~2014-03-05 10:45 UTC | newest]

Thread overview: 11+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2013-12-16 13:39 [LTP] [PATCH] msgctl11: process message queues by portions Stanislav Kholmanskikh
2014-02-06 13:29 ` chrubis
     [not found]   ` <52F9EE70.9040700@oracle.com>
2014-02-11 14:23     ` chrubis
2014-02-11 15:19       ` [LTP] [PATCH V2 1/2] msgctl11: cleanup and fflush removed Stanislav Kholmanskikh
2014-02-11 15:19         ` [LTP] [PATCH V2 2/2] msgctl11: process message queues by portions Stanislav Kholmanskikh
2014-02-21 18:11           ` chrubis
     [not found]             ` <530C5E99.6050809@oracle.com>
2014-02-25 12:25               ` chrubis
     [not found]                 ` <530CA0A3.403@oracle.com>
2014-02-25 14:00                   ` chrubis
2014-02-25 14:40                     ` [LTP] [PATCH V3 1/2] msgctl11: cleanup and fflush removed Stanislav Kholmanskikh
2014-02-25 14:40                     ` [LTP] [PATCH V3 2/2] msgctl11: process message queues by portions Stanislav Kholmanskikh
2014-03-05 10:45                       ` 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.