2 * Copyright (c) 1996-1999
3 * HD Associates, Inc. All rights reserved.
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright
11 * notice, this list of conditions and the following disclaimer in the
12 * documentation and/or other materials provided with the distribution.
13 * 3. All advertising materials mentioning features or use of this software
14 * must display the following acknowledgement:
15 * This product includes software developed by HD Associates, Inc
16 * 4. Neither the name of the author nor the names of any co-contributors
17 * may be used to endorse or promote products derived from this software
18 * without specific prior written permission.
20 * THIS SOFTWARE IS PROVIDED BY HD ASSOCIATES AND CONTRIBUTORS ``AS IS'' AND
21 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
22 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
23 * ARE DISCLAIMED. IN NO EVENT SHALL HD ASSOCIATES OR CONTRIBUTORS BE LIABLE
24 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
25 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
26 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
27 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
28 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
29 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
34 #include <sys/types.h>
41 #include <sys/types.h>
49 /* buzz: busy wait a random amount of time.
51 static void buzz(int n)
54 int m = random() & 0x0ffff;
55 for (i = 0; i < m; i++)
59 /* Yield: Verify that "sched_yield" works for the FIFO case.
60 * This runs several processes and verifies that the yield seems
61 * to permit the next one on the ready queue to run.
63 int yield(int argc, char *argv[])
69 pid_t youngest = !0; /* Our youngest child */
70 struct sched_param set, got;
75 set.sched_priority = sched_get_priority_max(SCHED_FIFO);
76 if (set.sched_priority == -1 && errno) {
77 perror("sched_get_priority_max");
85 fprintf(stderr, "usage: prog [n_instances]\n");
89 n = nslaves = atoi(argv[1]);
91 p = (int *)mmap(0, sizeof(int),
92 PROT_READ|PROT_WRITE, MAP_ANON|MAP_SHARED, -1, 0);
99 if (sched_setscheduler(0, SCHED_FIFO, &set) == -1)
100 err(errno, "sched_setscheduler");
102 /* I better still be SCHED_FIFO and RT_PRIO_MAX:
104 (void)sched_is(__LINE__, &got, SCHED_FIFO);
105 if (got.sched_priority != set.sched_priority) {
106 fprintf(stderr, "line %d: scheduler screwup\n",
114 /* Fork off the slaves.
116 for (i = 0; i < nslaves; i++) {
117 if ((youngest = fork()) == 0) {
118 /* I better still be SCHED_FIFO and RT_PRIO_MAX:
120 (void)sched_is(__LINE__, &got, SCHED_FIFO);
122 if (got.sched_priority != set.sched_priority) {
123 fprintf(stderr, "line %d: scheduler screwup\n",
128 master = 0; /* I'm a slave */
129 slave = i + 1; /* With this flag */
130 *p = slave; /* And I live */
136 /* If we conform the slave processes haven't run yet.
137 * The master must yield to let the first slave run.
141 "Error at line %d: Writer %d has run\n", __LINE__, *p);
146 /* Now the master yields, the first slave runs, and yields,
147 * next runs, yields, ...
149 * So the master should get through this first.
152 if (sched_yield() == -1)
153 err(errno, "sched_yield");
158 /* The final slave process should be the last one started.
162 "Error at line %d: Final slave is %d not %d.\n",
163 __LINE__, *p, nslaves);
167 /* Wait for our youngest to exit:
169 waitpid(youngest, &status, 0);
171 exit(WEXITSTATUS(status)); /* Let the slaves continue */
174 /* Now the first one has started up.
176 for (i = 0; i < nloops; i++) {
177 if (((*p) % nslaves) !=
178 ((slave + nslaves - 1) % nslaves)) {
179 fprintf(stderr, "%d ran before %d on iteration %d.\n",
185 /* Delay some random amount of time.
189 if (sched_yield() == -1)
190 err(errno, "sched_yield");
195 #ifdef STANDALONE_TESTS
196 int main(int argc, char *argv[]) { return yield(argc, argv); }