157718be8SEnji Cooper /* $NetBSD: t_sysv.c,v 1.4 2014/03/02 20:13:12 jmmv Exp $ */
257718be8SEnji Cooper
357718be8SEnji Cooper /*-
457718be8SEnji Cooper * Copyright (c) 1999, 2007 The NetBSD Foundation, Inc.
557718be8SEnji Cooper * All rights reserved.
657718be8SEnji Cooper *
757718be8SEnji Cooper * This code is derived from software contributed to The NetBSD Foundation
857718be8SEnji Cooper * by Jason R. Thorpe of the Numerical Aerospace Simulation Facility,
957718be8SEnji Cooper * NASA Ames Research Center, and by Andrew Doran.
1057718be8SEnji Cooper *
1157718be8SEnji Cooper * Redistribution and use in source and binary forms, with or without
1257718be8SEnji Cooper * modification, are permitted provided that the following conditions
1357718be8SEnji Cooper * are met:
1457718be8SEnji Cooper * 1. Redistributions of source code must retain the above copyright
1557718be8SEnji Cooper * notice, this list of conditions and the following disclaimer.
1657718be8SEnji Cooper * 2. Redistributions in binary form must reproduce the above copyright
1757718be8SEnji Cooper * notice, this list of conditions and the following disclaimer in the
1857718be8SEnji Cooper * documentation and/or other materials provided with the distribution.
1957718be8SEnji Cooper *
2057718be8SEnji Cooper * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
2157718be8SEnji Cooper * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
2257718be8SEnji Cooper * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
2357718be8SEnji Cooper * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
2457718be8SEnji Cooper * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
2557718be8SEnji Cooper * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
2657718be8SEnji Cooper * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
2757718be8SEnji Cooper * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
2857718be8SEnji Cooper * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
2957718be8SEnji Cooper * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
3057718be8SEnji Cooper * POSSIBILITY OF SUCH DAMAGE.
3157718be8SEnji Cooper */
3257718be8SEnji Cooper
3357718be8SEnji Cooper /*
3457718be8SEnji Cooper * Test the SVID-compatible Message Queue facility.
3557718be8SEnji Cooper */
3657718be8SEnji Cooper
3757718be8SEnji Cooper #include <atf-c.h>
3857718be8SEnji Cooper
3957718be8SEnji Cooper #include <err.h>
4057718be8SEnji Cooper #include <errno.h>
4157718be8SEnji Cooper #include <fcntl.h>
4257718be8SEnji Cooper #include <signal.h>
4357718be8SEnji Cooper #include <stdio.h>
4457718be8SEnji Cooper #include <stdlib.h>
4557718be8SEnji Cooper #include <string.h>
4657718be8SEnji Cooper #include <time.h>
4757718be8SEnji Cooper #include <unistd.h>
4857718be8SEnji Cooper
4957718be8SEnji Cooper #include <sys/ipc.h>
50ea7e7006SKonstantin Belousov #include <sys/mman.h>
5157718be8SEnji Cooper #include <sys/msg.h>
5257718be8SEnji Cooper #include <sys/param.h>
5357718be8SEnji Cooper #include <sys/sem.h>
5457718be8SEnji Cooper #include <sys/shm.h>
5557718be8SEnji Cooper #include <sys/wait.h>
5657718be8SEnji Cooper
57*20917cacSEric van Gyzen volatile int did_sigsys;
5857718be8SEnji Cooper
5957718be8SEnji Cooper void sigsys_handler(int);
6057718be8SEnji Cooper
6157718be8SEnji Cooper key_t get_ftok(int);
6257718be8SEnji Cooper
6357718be8SEnji Cooper void print_msqid_ds(struct msqid_ds *, mode_t);
6457718be8SEnji Cooper void receiver(void);
6557718be8SEnji Cooper
6657718be8SEnji Cooper void print_semid_ds(struct semid_ds *, mode_t);
6757718be8SEnji Cooper void waiter(void);
6857718be8SEnji Cooper
6957718be8SEnji Cooper void print_shmid_ds(struct shmid_ds *, mode_t);
7057718be8SEnji Cooper void sharer(void);
7157718be8SEnji Cooper
7257718be8SEnji Cooper #define MESSAGE_TEXT_LEN 256
7357718be8SEnji Cooper
745e1e3ea2SBrooks Davis struct testmsg {
7557718be8SEnji Cooper long mtype;
7657718be8SEnji Cooper char mtext[MESSAGE_TEXT_LEN];
7757718be8SEnji Cooper };
7857718be8SEnji Cooper
7957718be8SEnji Cooper const char *m1_str = "California is overrated.";
8057718be8SEnji Cooper const char *m2_str = "The quick brown fox jumped over the lazy dog.";
8157718be8SEnji Cooper
8257718be8SEnji Cooper size_t pgsize;
8357718be8SEnji Cooper
8457718be8SEnji Cooper #define MTYPE_1 1
8557718be8SEnji Cooper #define MTYPE_1_ACK 2
8657718be8SEnji Cooper
8757718be8SEnji Cooper #define MTYPE_2 3
8857718be8SEnji Cooper #define MTYPE_2_ACK 4
8957718be8SEnji Cooper
9057718be8SEnji Cooper pid_t child_pid;
9157718be8SEnji Cooper
9257718be8SEnji Cooper key_t msgkey, semkey, shmkey;
9357718be8SEnji Cooper
9457718be8SEnji Cooper int maxloop = 1;
9557718be8SEnji Cooper
9657718be8SEnji Cooper union semun {
9757718be8SEnji Cooper int val; /* value for SETVAL */
9857718be8SEnji Cooper struct semid_ds *buf; /* buffer for IPC_{STAT,SET} */
9957718be8SEnji Cooper u_short *array; /* array for GETALL & SETALL */
10057718be8SEnji Cooper };
10157718be8SEnji Cooper
10257718be8SEnji Cooper
10357718be8SEnji Cooper /* Writes an integer to a file. To be used from the body of the test
10457718be8SEnji Cooper * cases below to pass any global identifiers to the cleanup routine. */
10557718be8SEnji Cooper static void
write_int(const char * path,const int value)10657718be8SEnji Cooper write_int(const char *path, const int value)
10757718be8SEnji Cooper {
10857718be8SEnji Cooper int output;
10957718be8SEnji Cooper
11057718be8SEnji Cooper output = open(path, O_WRONLY | O_CREAT | O_TRUNC, 0600);
11157718be8SEnji Cooper ATF_REQUIRE_MSG(output != -1, "Failed to create %s", path);
11257718be8SEnji Cooper write(output, &value, sizeof(value));
11357718be8SEnji Cooper close(output);
11457718be8SEnji Cooper }
11557718be8SEnji Cooper
11657718be8SEnji Cooper
11757718be8SEnji Cooper /* Reads an integer from a file. To be used from the cleanup routines
11857718be8SEnji Cooper * of the test cases below. */
11957718be8SEnji Cooper static int
read_int(const char * path)12057718be8SEnji Cooper read_int(const char *path)
12157718be8SEnji Cooper {
12257718be8SEnji Cooper int input;
12357718be8SEnji Cooper
12457718be8SEnji Cooper input = open(path, O_RDONLY);
12557718be8SEnji Cooper if (input == -1)
12657718be8SEnji Cooper return -1;
12757718be8SEnji Cooper else {
12857718be8SEnji Cooper int value;
129fa82818fSAlan Somers ATF_REQUIRE_EQ(read(input, &value, sizeof(value)), sizeof(value));
130fa82818fSAlan Somers close(input);
13157718be8SEnji Cooper return value;
13257718be8SEnji Cooper }
13357718be8SEnji Cooper }
13457718be8SEnji Cooper
13557718be8SEnji Cooper
13657718be8SEnji Cooper void
sigsys_handler(int signo)13757718be8SEnji Cooper sigsys_handler(int signo)
13857718be8SEnji Cooper {
13957718be8SEnji Cooper
14057718be8SEnji Cooper did_sigsys = 1;
14157718be8SEnji Cooper }
14257718be8SEnji Cooper
get_ftok(int id)14357718be8SEnji Cooper key_t get_ftok(int id)
14457718be8SEnji Cooper {
14557718be8SEnji Cooper int fd;
14657718be8SEnji Cooper char token_key[64], token_dir[64];
14757718be8SEnji Cooper char *tmpdir;
14857718be8SEnji Cooper key_t key;
14957718be8SEnji Cooper
15057718be8SEnji Cooper strlcpy(token_key, "/tmp/t_sysv.XXXXXX", sizeof(token_key));
15157718be8SEnji Cooper tmpdir = mkdtemp(token_key);
15257718be8SEnji Cooper ATF_REQUIRE_MSG(tmpdir != NULL, "mkdtemp() failed: %d", errno);
15357718be8SEnji Cooper
15457718be8SEnji Cooper strlcpy(token_dir, tmpdir, sizeof(token_dir));
15557718be8SEnji Cooper strlcpy(token_key, tmpdir, sizeof(token_key));
15657718be8SEnji Cooper strlcat(token_key, "/token_key", sizeof(token_key));
15757718be8SEnji Cooper
15857718be8SEnji Cooper /* Create the file, since ftok() requires it to exist! */
15957718be8SEnji Cooper
1605e1e3ea2SBrooks Davis fd = open(token_key, O_RDWR | O_CREAT | O_EXCL, 0600);
16157718be8SEnji Cooper if (fd == -1) {
16257718be8SEnji Cooper rmdir(tmpdir);
16357718be8SEnji Cooper atf_tc_fail("open() of temp file failed: %d", errno);
16457718be8SEnji Cooper return (key_t)-1;
16557718be8SEnji Cooper } else
16657718be8SEnji Cooper close(fd);
16757718be8SEnji Cooper
16857718be8SEnji Cooper key = ftok(token_key, id);
16957718be8SEnji Cooper
17057718be8SEnji Cooper ATF_REQUIRE_MSG(unlink(token_key) != -1, "unlink() failed: %d", errno);
17157718be8SEnji Cooper ATF_REQUIRE_MSG(rmdir(token_dir) != -1, "rmdir() failed: %d", errno);
17257718be8SEnji Cooper
17357718be8SEnji Cooper return key;
17457718be8SEnji Cooper }
17557718be8SEnji Cooper
17657718be8SEnji Cooper ATF_TC_WITH_CLEANUP(msg);
ATF_TC_HEAD(msg,tc)17757718be8SEnji Cooper ATF_TC_HEAD(msg, tc)
17857718be8SEnji Cooper {
17957718be8SEnji Cooper
18057718be8SEnji Cooper atf_tc_set_md_var(tc, "timeout", "3");
18157718be8SEnji Cooper atf_tc_set_md_var(tc, "descr", "Checks sysvmsg passing");
18257718be8SEnji Cooper }
18357718be8SEnji Cooper
ATF_TC_BODY(msg,tc)18457718be8SEnji Cooper ATF_TC_BODY(msg, tc)
18557718be8SEnji Cooper {
18657718be8SEnji Cooper struct sigaction sa;
18757718be8SEnji Cooper struct msqid_ds m_ds;
1885e1e3ea2SBrooks Davis struct testmsg m;
18957718be8SEnji Cooper int sender_msqid;
19057718be8SEnji Cooper int loop;
19157718be8SEnji Cooper int c_status;
192*20917cacSEric van Gyzen pid_t wait_result;
193f4beb2edSLi-Wen Hsu
19457718be8SEnji Cooper /*
19557718be8SEnji Cooper * Install a SIGSYS handler so that we can exit gracefully if
19657718be8SEnji Cooper * System V Message Queue support isn't in the kernel.
19757718be8SEnji Cooper */
19857718be8SEnji Cooper did_sigsys = 0;
19957718be8SEnji Cooper sa.sa_handler = sigsys_handler;
20057718be8SEnji Cooper sigemptyset(&sa.sa_mask);
20157718be8SEnji Cooper sa.sa_flags = 0;
20257718be8SEnji Cooper ATF_REQUIRE_MSG(sigaction(SIGSYS, &sa, NULL) != -1,
20357718be8SEnji Cooper "sigaction SIGSYS: %d", errno);
20457718be8SEnji Cooper
20557718be8SEnji Cooper msgkey = get_ftok(4160);
20657718be8SEnji Cooper ATF_REQUIRE_MSG(msgkey != (key_t)-1, "get_ftok failed");
20757718be8SEnji Cooper
20857718be8SEnji Cooper sender_msqid = msgget(msgkey, IPC_CREAT | 0640);
20957718be8SEnji Cooper ATF_REQUIRE_MSG(sender_msqid != -1, "msgget: %d", errno);
21057718be8SEnji Cooper write_int("sender_msqid", sender_msqid);
21157718be8SEnji Cooper
21257718be8SEnji Cooper if (did_sigsys) {
21357718be8SEnji Cooper atf_tc_skip("SYSV Message Queue not supported");
21457718be8SEnji Cooper return;
21557718be8SEnji Cooper }
21657718be8SEnji Cooper
21757718be8SEnji Cooper ATF_REQUIRE_MSG(msgctl(sender_msqid, IPC_STAT, &m_ds) != -1,
21857718be8SEnji Cooper "msgctl IPC_STAT 1: %d", errno);
21957718be8SEnji Cooper
22057718be8SEnji Cooper print_msqid_ds(&m_ds, 0640);
22157718be8SEnji Cooper
22257718be8SEnji Cooper m_ds.msg_perm.mode = (m_ds.msg_perm.mode & ~0777) | 0600;
22357718be8SEnji Cooper
22457718be8SEnji Cooper ATF_REQUIRE_MSG(msgctl(sender_msqid, IPC_SET, &m_ds) != -1,
22557718be8SEnji Cooper "msgctl IPC_SET: %d", errno);
22657718be8SEnji Cooper
22757718be8SEnji Cooper memset(&m_ds, 0, sizeof(m_ds));
22857718be8SEnji Cooper
22957718be8SEnji Cooper ATF_REQUIRE_MSG(msgctl(sender_msqid, IPC_STAT, &m_ds) != -1,
23057718be8SEnji Cooper "msgctl IPC_STAT 2: %d", errno);
23157718be8SEnji Cooper
23257718be8SEnji Cooper ATF_REQUIRE_MSG((m_ds.msg_perm.mode & 0777) == 0600,
23357718be8SEnji Cooper "IPC_SET of mode didn't hold");
23457718be8SEnji Cooper
23557718be8SEnji Cooper print_msqid_ds(&m_ds, 0600);
23657718be8SEnji Cooper
237*20917cacSEric van Gyzen fflush(stdout);
238*20917cacSEric van Gyzen
23957718be8SEnji Cooper switch ((child_pid = fork())) {
24057718be8SEnji Cooper case -1:
24157718be8SEnji Cooper atf_tc_fail("fork: %d", errno);
24257718be8SEnji Cooper return;
24357718be8SEnji Cooper
24457718be8SEnji Cooper case 0:
24557718be8SEnji Cooper receiver();
24657718be8SEnji Cooper break;
24757718be8SEnji Cooper
24857718be8SEnji Cooper default:
24957718be8SEnji Cooper break;
25057718be8SEnji Cooper }
25157718be8SEnji Cooper
25257718be8SEnji Cooper for (loop = 0; loop < maxloop; loop++) {
25357718be8SEnji Cooper /*
25457718be8SEnji Cooper * Send the first message to the receiver and wait for the ACK.
25557718be8SEnji Cooper */
25657718be8SEnji Cooper m.mtype = MTYPE_1;
257fa82818fSAlan Somers strlcpy(m.mtext, m1_str, sizeof(m.mtext));
25857718be8SEnji Cooper ATF_REQUIRE_MSG(msgsnd(sender_msqid, &m, MESSAGE_TEXT_LEN,
25957718be8SEnji Cooper 0) != -1, "sender: msgsnd 1: %d", errno);
26057718be8SEnji Cooper
26157718be8SEnji Cooper ATF_REQUIRE_MSG(msgrcv(sender_msqid, &m, MESSAGE_TEXT_LEN,
26257718be8SEnji Cooper MTYPE_1_ACK, 0) == MESSAGE_TEXT_LEN,
26357718be8SEnji Cooper "sender: msgrcv 1 ack: %d", errno);
26457718be8SEnji Cooper
26557718be8SEnji Cooper print_msqid_ds(&m_ds, 0600);
26657718be8SEnji Cooper
26757718be8SEnji Cooper /*
26857718be8SEnji Cooper * Send the second message to the receiver and wait for the ACK.
26957718be8SEnji Cooper */
27057718be8SEnji Cooper m.mtype = MTYPE_2;
271fa82818fSAlan Somers strlcpy(m.mtext, m2_str, sizeof(m.mtext));
27257718be8SEnji Cooper ATF_REQUIRE_MSG(msgsnd(sender_msqid, &m, MESSAGE_TEXT_LEN, 0) != -1,
27357718be8SEnji Cooper "sender: msgsnd 2: %d", errno);
27457718be8SEnji Cooper
27557718be8SEnji Cooper ATF_REQUIRE_MSG(msgrcv(sender_msqid, &m, MESSAGE_TEXT_LEN,
27657718be8SEnji Cooper MTYPE_2_ACK, 0) == MESSAGE_TEXT_LEN,
27757718be8SEnji Cooper "sender: msgrcv 2 ack: %d", errno);
27857718be8SEnji Cooper }
27957718be8SEnji Cooper
28057718be8SEnji Cooper /*
28157718be8SEnji Cooper * Wait for child to finish
28257718be8SEnji Cooper */
283*20917cacSEric van Gyzen wait_result = wait(&c_status);
284*20917cacSEric van Gyzen ATF_REQUIRE_EQ_MSG(wait_result, child_pid, "wait returned %d (%s)",
285*20917cacSEric van Gyzen wait_result, wait_result == -1 ? strerror(errno) : "");
286*20917cacSEric van Gyzen ATF_REQUIRE_MSG(WIFEXITED(c_status), "child abnormal exit: %d (sig %d)",
287*20917cacSEric van Gyzen c_status, WTERMSIG(c_status));
288*20917cacSEric van Gyzen ATF_REQUIRE_EQ_MSG(WEXITSTATUS(c_status), 0, "child status: %d",
289*20917cacSEric van Gyzen WEXITSTATUS(c_status));
29057718be8SEnji Cooper
291*20917cacSEric van Gyzen ATF_REQUIRE_MSG(msgctl(sender_msqid, IPC_STAT, &m_ds) != -1,
292*20917cacSEric van Gyzen "msgctl IPC_STAT: %d", errno);
29357718be8SEnji Cooper
29457718be8SEnji Cooper print_msqid_ds(&m_ds, 0600);
29557718be8SEnji Cooper }
29657718be8SEnji Cooper
ATF_TC_CLEANUP(msg,tc)29757718be8SEnji Cooper ATF_TC_CLEANUP(msg, tc)
29857718be8SEnji Cooper {
29957718be8SEnji Cooper int sender_msqid;
30057718be8SEnji Cooper
30157718be8SEnji Cooper /*
30257718be8SEnji Cooper * Remove the message queue if it exists.
30357718be8SEnji Cooper */
30457718be8SEnji Cooper sender_msqid = read_int("sender_msqid");
30557718be8SEnji Cooper if (sender_msqid != -1)
30657718be8SEnji Cooper if (msgctl(sender_msqid, IPC_RMID, NULL) == -1)
30757718be8SEnji Cooper err(1, "msgctl IPC_RMID");
30857718be8SEnji Cooper }
30957718be8SEnji Cooper
31057718be8SEnji Cooper void
print_msqid_ds(struct msqid_ds * mp,mode_t mode)3115e1e3ea2SBrooks Davis print_msqid_ds(struct msqid_ds *mp, mode_t mode)
31257718be8SEnji Cooper {
31357718be8SEnji Cooper uid_t uid = geteuid();
31457718be8SEnji Cooper gid_t gid = getegid();
31557718be8SEnji Cooper
31657718be8SEnji Cooper printf("PERM: uid %d, gid %d, cuid %d, cgid %d, mode 0%o\n",
31757718be8SEnji Cooper mp->msg_perm.uid, mp->msg_perm.gid,
31857718be8SEnji Cooper mp->msg_perm.cuid, mp->msg_perm.cgid,
31957718be8SEnji Cooper mp->msg_perm.mode & 0777);
32057718be8SEnji Cooper
32157718be8SEnji Cooper printf("qnum %lu, qbytes %lu, lspid %d, lrpid %d\n",
32257718be8SEnji Cooper mp->msg_qnum, (u_long)mp->msg_qbytes, mp->msg_lspid,
32357718be8SEnji Cooper mp->msg_lrpid);
32457718be8SEnji Cooper
32557718be8SEnji Cooper printf("stime: %s", ctime(&mp->msg_stime));
32657718be8SEnji Cooper printf("rtime: %s", ctime(&mp->msg_rtime));
32757718be8SEnji Cooper printf("ctime: %s", ctime(&mp->msg_ctime));
32857718be8SEnji Cooper
32957718be8SEnji Cooper /*
33057718be8SEnji Cooper * Sanity check a few things.
33157718be8SEnji Cooper */
33257718be8SEnji Cooper
33357718be8SEnji Cooper ATF_REQUIRE_MSG(mp->msg_perm.uid == uid && mp->msg_perm.cuid == uid,
33457718be8SEnji Cooper "uid mismatch");
33557718be8SEnji Cooper
33657718be8SEnji Cooper ATF_REQUIRE_MSG(mp->msg_perm.gid == gid && mp->msg_perm.cgid == gid,
33757718be8SEnji Cooper "gid mismatch");
33857718be8SEnji Cooper
33957718be8SEnji Cooper ATF_REQUIRE_MSG((mp->msg_perm.mode & 0777) == mode, "mode mismatch");
34057718be8SEnji Cooper }
34157718be8SEnji Cooper
34257718be8SEnji Cooper void
receiver(void)3435e1e3ea2SBrooks Davis receiver(void)
34457718be8SEnji Cooper {
3455e1e3ea2SBrooks Davis struct testmsg m;
34657718be8SEnji Cooper int msqid, loop;
34757718be8SEnji Cooper
34857718be8SEnji Cooper if ((msqid = msgget(msgkey, 0)) == -1)
34957718be8SEnji Cooper err(1, "receiver: msgget");
35057718be8SEnji Cooper
35157718be8SEnji Cooper for (loop = 0; loop < maxloop; loop++) {
35257718be8SEnji Cooper /*
35357718be8SEnji Cooper * Receive the first message, print it, and send an ACK.
35457718be8SEnji Cooper */
35557718be8SEnji Cooper if (msgrcv(msqid, &m, MESSAGE_TEXT_LEN, MTYPE_1, 0) != MESSAGE_TEXT_LEN)
35657718be8SEnji Cooper err(1, "receiver: msgrcv 1");
35757718be8SEnji Cooper
35857718be8SEnji Cooper printf("%s\n", m.mtext);
35957718be8SEnji Cooper if (strcmp(m.mtext, m1_str) != 0)
360*20917cacSEric van Gyzen errx(1, "receiver: message 1 data isn't correct");
36157718be8SEnji Cooper
36257718be8SEnji Cooper m.mtype = MTYPE_1_ACK;
36357718be8SEnji Cooper
36457718be8SEnji Cooper if (msgsnd(msqid, &m, MESSAGE_TEXT_LEN, 0) == -1)
36557718be8SEnji Cooper err(1, "receiver: msgsnd ack 1");
36657718be8SEnji Cooper
36757718be8SEnji Cooper /*
36857718be8SEnji Cooper * Receive the second message, print it, and send an ACK.
36957718be8SEnji Cooper */
37057718be8SEnji Cooper
37157718be8SEnji Cooper if (msgrcv(msqid, &m, MESSAGE_TEXT_LEN, MTYPE_2, 0) != MESSAGE_TEXT_LEN)
37257718be8SEnji Cooper err(1, "receiver: msgrcv 2");
37357718be8SEnji Cooper
37457718be8SEnji Cooper printf("%s\n", m.mtext);
37557718be8SEnji Cooper if (strcmp(m.mtext, m2_str) != 0)
376*20917cacSEric van Gyzen errx(1, "receiver: message 2 data isn't correct");
37757718be8SEnji Cooper
37857718be8SEnji Cooper m.mtype = MTYPE_2_ACK;
37957718be8SEnji Cooper
38057718be8SEnji Cooper if (msgsnd(msqid, &m, MESSAGE_TEXT_LEN, 0) == -1)
38157718be8SEnji Cooper err(1, "receiver: msgsnd ack 2");
38257718be8SEnji Cooper }
38357718be8SEnji Cooper
38457718be8SEnji Cooper exit(0);
38557718be8SEnji Cooper }
38657718be8SEnji Cooper
38757718be8SEnji Cooper /*
38857718be8SEnji Cooper * Test the SVID-compatible Semaphore facility.
38957718be8SEnji Cooper */
39057718be8SEnji Cooper
39157718be8SEnji Cooper ATF_TC_WITH_CLEANUP(sem);
ATF_TC_HEAD(sem,tc)39257718be8SEnji Cooper ATF_TC_HEAD(sem, tc)
39357718be8SEnji Cooper {
39457718be8SEnji Cooper
39557718be8SEnji Cooper atf_tc_set_md_var(tc, "timeout", "3");
39657718be8SEnji Cooper atf_tc_set_md_var(tc, "descr", "Checks sysvmsg passing");
39757718be8SEnji Cooper }
39857718be8SEnji Cooper
ATF_TC_BODY(sem,tc)39957718be8SEnji Cooper ATF_TC_BODY(sem, tc)
40057718be8SEnji Cooper {
40157718be8SEnji Cooper struct sigaction sa;
40257718be8SEnji Cooper union semun sun;
40357718be8SEnji Cooper struct semid_ds s_ds;
40457718be8SEnji Cooper int sender_semid;
40557718be8SEnji Cooper int i;
40657718be8SEnji Cooper int c_status;
407*20917cacSEric van Gyzen int child_count;
408*20917cacSEric van Gyzen pid_t wait_result;
40957718be8SEnji Cooper
41057718be8SEnji Cooper /*
41157718be8SEnji Cooper * Install a SIGSYS handler so that we can exit gracefully if
41257718be8SEnji Cooper * System V Semaphore support isn't in the kernel.
41357718be8SEnji Cooper */
41457718be8SEnji Cooper did_sigsys = 0;
41557718be8SEnji Cooper sa.sa_handler = sigsys_handler;
41657718be8SEnji Cooper sigemptyset(&sa.sa_mask);
41757718be8SEnji Cooper sa.sa_flags = 0;
41857718be8SEnji Cooper ATF_REQUIRE_MSG(sigaction(SIGSYS, &sa, NULL) != -1,
41957718be8SEnji Cooper "sigaction SIGSYS: %d", errno);
42057718be8SEnji Cooper
42157718be8SEnji Cooper semkey = get_ftok(4160);
42257718be8SEnji Cooper ATF_REQUIRE_MSG(semkey != (key_t)-1, "get_ftok failed");
42357718be8SEnji Cooper
42457718be8SEnji Cooper sender_semid = semget(semkey, 1, IPC_CREAT | 0640);
42557718be8SEnji Cooper ATF_REQUIRE_MSG(sender_semid != -1, "semget: %d", errno);
42657718be8SEnji Cooper write_int("sender_semid", sender_semid);
42757718be8SEnji Cooper
42857718be8SEnji Cooper if (did_sigsys) {
42957718be8SEnji Cooper atf_tc_skip("SYSV Semaphore not supported");
43057718be8SEnji Cooper return;
43157718be8SEnji Cooper }
43257718be8SEnji Cooper
43357718be8SEnji Cooper sun.buf = &s_ds;
43457718be8SEnji Cooper ATF_REQUIRE_MSG(semctl(sender_semid, 0, IPC_STAT, sun) != -1,
43557718be8SEnji Cooper "semctl IPC_STAT: %d", errno);
43657718be8SEnji Cooper
43757718be8SEnji Cooper print_semid_ds(&s_ds, 0640);
43857718be8SEnji Cooper
43957718be8SEnji Cooper s_ds.sem_perm.mode = (s_ds.sem_perm.mode & ~0777) | 0600;
44057718be8SEnji Cooper
44157718be8SEnji Cooper sun.buf = &s_ds;
44257718be8SEnji Cooper ATF_REQUIRE_MSG(semctl(sender_semid, 0, IPC_SET, sun) != -1,
44357718be8SEnji Cooper "semctl IPC_SET: %d", errno);
44457718be8SEnji Cooper
44557718be8SEnji Cooper memset(&s_ds, 0, sizeof(s_ds));
44657718be8SEnji Cooper
44757718be8SEnji Cooper sun.buf = &s_ds;
44857718be8SEnji Cooper ATF_REQUIRE_MSG(semctl(sender_semid, 0, IPC_STAT, sun) != -1,
44957718be8SEnji Cooper "semctl IPC_STAT: %d", errno);
45057718be8SEnji Cooper
45157718be8SEnji Cooper ATF_REQUIRE_MSG((s_ds.sem_perm.mode & 0777) == 0600,
45257718be8SEnji Cooper "IPC_SET of mode didn't hold");
45357718be8SEnji Cooper
45457718be8SEnji Cooper print_semid_ds(&s_ds, 0600);
45557718be8SEnji Cooper
456*20917cacSEric van Gyzen fflush(stdout);
457*20917cacSEric van Gyzen
45857718be8SEnji Cooper for (child_count = 0; child_count < 5; child_count++) {
45957718be8SEnji Cooper switch ((child_pid = fork())) {
46057718be8SEnji Cooper case -1:
46157718be8SEnji Cooper atf_tc_fail("fork: %d", errno);
46257718be8SEnji Cooper return;
46357718be8SEnji Cooper
46457718be8SEnji Cooper case 0:
46557718be8SEnji Cooper waiter();
46657718be8SEnji Cooper break;
46757718be8SEnji Cooper
46857718be8SEnji Cooper default:
46957718be8SEnji Cooper break;
47057718be8SEnji Cooper }
47157718be8SEnji Cooper }
47257718be8SEnji Cooper
47357718be8SEnji Cooper /*
47457718be8SEnji Cooper * Wait for all of the waiters to be attempting to acquire the
47557718be8SEnji Cooper * semaphore.
47657718be8SEnji Cooper */
47757718be8SEnji Cooper for (;;) {
47857718be8SEnji Cooper i = semctl(sender_semid, 0, GETNCNT);
47957718be8SEnji Cooper if (i == -1)
48057718be8SEnji Cooper atf_tc_fail("semctl GETNCNT: %d", i);
48157718be8SEnji Cooper if (i == 5)
48257718be8SEnji Cooper break;
48357718be8SEnji Cooper }
48457718be8SEnji Cooper
48557718be8SEnji Cooper /*
48657718be8SEnji Cooper * Now set the thundering herd in motion by initializing the
48757718be8SEnji Cooper * semaphore to the value 1.
48857718be8SEnji Cooper */
48957718be8SEnji Cooper sun.val = 1;
49057718be8SEnji Cooper ATF_REQUIRE_MSG(semctl(sender_semid, 0, SETVAL, sun) != -1,
49157718be8SEnji Cooper "sender: semctl SETVAL to 1: %d", errno);
49257718be8SEnji Cooper
49357718be8SEnji Cooper /*
49457718be8SEnji Cooper * Wait for all children to finish
49557718be8SEnji Cooper */
496*20917cacSEric van Gyzen while (child_count-- > 0) {
497*20917cacSEric van Gyzen wait_result = wait(&c_status);
498*20917cacSEric van Gyzen ATF_REQUIRE_MSG(wait_result != -1, "wait failed: %s",
499*20917cacSEric van Gyzen strerror(errno));
500*20917cacSEric van Gyzen ATF_REQUIRE_MSG(WIFEXITED(c_status),
501*20917cacSEric van Gyzen "child abnormal exit: %d (sig %d)",
502*20917cacSEric van Gyzen c_status, WTERMSIG(c_status));
503*20917cacSEric van Gyzen ATF_REQUIRE_EQ_MSG(WEXITSTATUS(c_status), 0, "child status: %d",
50457718be8SEnji Cooper WEXITSTATUS(c_status));
505*20917cacSEric van Gyzen
50657718be8SEnji Cooper sun.buf = &s_ds;
507*20917cacSEric van Gyzen ATF_REQUIRE_MSG(semctl(sender_semid, 0, IPC_STAT, sun) != -1,
50857718be8SEnji Cooper "semctl IPC_STAT: %d", errno);
50957718be8SEnji Cooper
51057718be8SEnji Cooper print_semid_ds(&s_ds, 0600);
51157718be8SEnji Cooper }
51257718be8SEnji Cooper }
51357718be8SEnji Cooper
ATF_TC_CLEANUP(sem,tc)51457718be8SEnji Cooper ATF_TC_CLEANUP(sem, tc)
51557718be8SEnji Cooper {
51657718be8SEnji Cooper int sender_semid;
51757718be8SEnji Cooper
51857718be8SEnji Cooper /*
51957718be8SEnji Cooper * Remove the semaphore if it exists
52057718be8SEnji Cooper */
52157718be8SEnji Cooper sender_semid = read_int("sender_semid");
52257718be8SEnji Cooper if (sender_semid != -1)
52357718be8SEnji Cooper if (semctl(sender_semid, 0, IPC_RMID) == -1)
52457718be8SEnji Cooper err(1, "semctl IPC_RMID");
52557718be8SEnji Cooper }
52657718be8SEnji Cooper
52757718be8SEnji Cooper void
print_semid_ds(struct semid_ds * sp,mode_t mode)5285e1e3ea2SBrooks Davis print_semid_ds(struct semid_ds *sp, mode_t mode)
52957718be8SEnji Cooper {
53057718be8SEnji Cooper uid_t uid = geteuid();
53157718be8SEnji Cooper gid_t gid = getegid();
53257718be8SEnji Cooper
53357718be8SEnji Cooper printf("PERM: uid %d, gid %d, cuid %d, cgid %d, mode 0%o\n",
53457718be8SEnji Cooper sp->sem_perm.uid, sp->sem_perm.gid,
53557718be8SEnji Cooper sp->sem_perm.cuid, sp->sem_perm.cgid,
53657718be8SEnji Cooper sp->sem_perm.mode & 0777);
53757718be8SEnji Cooper
53857718be8SEnji Cooper printf("nsems %u\n", sp->sem_nsems);
53957718be8SEnji Cooper
54057718be8SEnji Cooper printf("otime: %s", ctime(&sp->sem_otime));
54157718be8SEnji Cooper printf("ctime: %s", ctime(&sp->sem_ctime));
54257718be8SEnji Cooper
54357718be8SEnji Cooper /*
54457718be8SEnji Cooper * Sanity check a few things.
54557718be8SEnji Cooper */
54657718be8SEnji Cooper
54757718be8SEnji Cooper ATF_REQUIRE_MSG(sp->sem_perm.uid == uid && sp->sem_perm.cuid == uid,
54857718be8SEnji Cooper "uid mismatch");
54957718be8SEnji Cooper
55057718be8SEnji Cooper ATF_REQUIRE_MSG(sp->sem_perm.gid == gid && sp->sem_perm.cgid == gid,
55157718be8SEnji Cooper "gid mismatch");
55257718be8SEnji Cooper
55357718be8SEnji Cooper ATF_REQUIRE_MSG((sp->sem_perm.mode & 0777) == mode,
55457718be8SEnji Cooper "mode mismatch %o != %o", (sp->sem_perm.mode & 0777), mode);
55557718be8SEnji Cooper }
55657718be8SEnji Cooper
55757718be8SEnji Cooper void
waiter(void)5585e1e3ea2SBrooks Davis waiter(void)
55957718be8SEnji Cooper {
56057718be8SEnji Cooper struct sembuf s;
56157718be8SEnji Cooper int semid;
56257718be8SEnji Cooper
56357718be8SEnji Cooper if ((semid = semget(semkey, 1, 0)) == -1)
56457718be8SEnji Cooper err(1, "waiter: semget");
56557718be8SEnji Cooper
56657718be8SEnji Cooper /*
56757718be8SEnji Cooper * Attempt to acquire the semaphore.
56857718be8SEnji Cooper */
56957718be8SEnji Cooper s.sem_num = 0;
57057718be8SEnji Cooper s.sem_op = -1;
57157718be8SEnji Cooper s.sem_flg = SEM_UNDO;
57257718be8SEnji Cooper
57357718be8SEnji Cooper if (semop(semid, &s, 1) == -1)
57457718be8SEnji Cooper err(1, "waiter: semop -1");
57557718be8SEnji Cooper
57657718be8SEnji Cooper printf("WOO! GOT THE SEMAPHORE!\n");
577*20917cacSEric van Gyzen usleep(10000);
57857718be8SEnji Cooper
57957718be8SEnji Cooper /*
58057718be8SEnji Cooper * Release the semaphore and exit.
58157718be8SEnji Cooper */
58257718be8SEnji Cooper s.sem_num = 0;
58357718be8SEnji Cooper s.sem_op = 1;
58457718be8SEnji Cooper s.sem_flg = SEM_UNDO;
58557718be8SEnji Cooper
58657718be8SEnji Cooper if (semop(semid, &s, 1) == -1)
58757718be8SEnji Cooper err(1, "waiter: semop +1");
58857718be8SEnji Cooper
58957718be8SEnji Cooper exit(0);
59057718be8SEnji Cooper }
59157718be8SEnji Cooper
59257718be8SEnji Cooper /*
59357718be8SEnji Cooper * Test the SVID-compatible Shared Memory facility.
59457718be8SEnji Cooper */
59557718be8SEnji Cooper
59657718be8SEnji Cooper ATF_TC_WITH_CLEANUP(shm);
ATF_TC_HEAD(shm,tc)59757718be8SEnji Cooper ATF_TC_HEAD(shm, tc)
59857718be8SEnji Cooper {
59957718be8SEnji Cooper
60057718be8SEnji Cooper atf_tc_set_md_var(tc, "timeout", "3");
60157718be8SEnji Cooper atf_tc_set_md_var(tc, "descr", "Checks sysv shared memory");
60257718be8SEnji Cooper }
60357718be8SEnji Cooper
ATF_TC_BODY(shm,tc)60457718be8SEnji Cooper ATF_TC_BODY(shm, tc)
60557718be8SEnji Cooper {
60657718be8SEnji Cooper struct sigaction sa;
60757718be8SEnji Cooper struct shmid_ds s_ds;
60857718be8SEnji Cooper char *shm_buf;
60957718be8SEnji Cooper int sender_shmid;
61057718be8SEnji Cooper int c_status;
611*20917cacSEric van Gyzen pid_t wait_result;
61257718be8SEnji Cooper
61357718be8SEnji Cooper /*
61457718be8SEnji Cooper * Install a SIGSYS handler so that we can exit gracefully if
61557718be8SEnji Cooper * System V Shared Memory support isn't in the kernel.
61657718be8SEnji Cooper */
61757718be8SEnji Cooper did_sigsys = 0;
61857718be8SEnji Cooper sa.sa_handler = sigsys_handler;
61957718be8SEnji Cooper sigemptyset(&sa.sa_mask);
62057718be8SEnji Cooper sa.sa_flags = 0;
62157718be8SEnji Cooper ATF_REQUIRE_MSG(sigaction(SIGSYS, &sa, NULL) != -1,
62257718be8SEnji Cooper "sigaction SIGSYS: %d", errno);
62357718be8SEnji Cooper
62457718be8SEnji Cooper pgsize = sysconf(_SC_PAGESIZE);
62557718be8SEnji Cooper
62657718be8SEnji Cooper shmkey = get_ftok(4160);
62757718be8SEnji Cooper ATF_REQUIRE_MSG(shmkey != (key_t)-1, "get_ftok failed");
62857718be8SEnji Cooper
62957718be8SEnji Cooper ATF_REQUIRE_MSG((sender_shmid = shmget(shmkey, pgsize,
63057718be8SEnji Cooper IPC_CREAT | 0640)) != -1,
63157718be8SEnji Cooper "shmget: %d", errno);
63257718be8SEnji Cooper write_int("sender_shmid", sender_shmid);
63357718be8SEnji Cooper
63457718be8SEnji Cooper ATF_REQUIRE_MSG(shmctl(sender_shmid, IPC_STAT, &s_ds) != -1,
63557718be8SEnji Cooper "shmctl IPC_STAT: %d", errno);
63657718be8SEnji Cooper
63757718be8SEnji Cooper print_shmid_ds(&s_ds, 0640);
63857718be8SEnji Cooper
63957718be8SEnji Cooper s_ds.shm_perm.mode = (s_ds.shm_perm.mode & ~0777) | 0600;
64057718be8SEnji Cooper
64157718be8SEnji Cooper ATF_REQUIRE_MSG(shmctl(sender_shmid, IPC_SET, &s_ds) != -1,
64257718be8SEnji Cooper "shmctl IPC_SET: %d", errno);
64357718be8SEnji Cooper
64457718be8SEnji Cooper memset(&s_ds, 0, sizeof(s_ds));
64557718be8SEnji Cooper
64657718be8SEnji Cooper ATF_REQUIRE_MSG(shmctl(sender_shmid, IPC_STAT, &s_ds) != -1,
64757718be8SEnji Cooper "shmctl IPC_STAT: %d", errno);
64857718be8SEnji Cooper
64957718be8SEnji Cooper ATF_REQUIRE_MSG((s_ds.shm_perm.mode & 0777) == 0600,
65057718be8SEnji Cooper "IPC_SET of mode didn't hold");
65157718be8SEnji Cooper
65257718be8SEnji Cooper print_shmid_ds(&s_ds, 0600);
65357718be8SEnji Cooper
65457718be8SEnji Cooper shm_buf = shmat(sender_shmid, NULL, 0);
65557718be8SEnji Cooper ATF_REQUIRE_MSG(shm_buf != (void *) -1, "sender: shmat: %d", errno);
65657718be8SEnji Cooper
65757718be8SEnji Cooper /*
65857718be8SEnji Cooper * Write the test pattern into the shared memory buffer.
65957718be8SEnji Cooper */
66057718be8SEnji Cooper strcpy(shm_buf, m2_str);
66157718be8SEnji Cooper
662*20917cacSEric van Gyzen fflush(stdout);
663*20917cacSEric van Gyzen
66457718be8SEnji Cooper switch ((child_pid = fork())) {
66557718be8SEnji Cooper case -1:
66657718be8SEnji Cooper atf_tc_fail("fork: %d", errno);
66757718be8SEnji Cooper return;
66857718be8SEnji Cooper
66957718be8SEnji Cooper case 0:
67057718be8SEnji Cooper sharer();
67157718be8SEnji Cooper break;
67257718be8SEnji Cooper
67357718be8SEnji Cooper default:
67457718be8SEnji Cooper break;
67557718be8SEnji Cooper }
67657718be8SEnji Cooper
67757718be8SEnji Cooper /*
67857718be8SEnji Cooper * Wait for child to finish
67957718be8SEnji Cooper */
680*20917cacSEric van Gyzen wait_result = wait(&c_status);
681*20917cacSEric van Gyzen ATF_REQUIRE_EQ_MSG(wait_result, child_pid, "wait returned %d (%s)",
682*20917cacSEric van Gyzen wait_result, wait_result == -1 ? strerror(errno) : "");
683*20917cacSEric van Gyzen ATF_REQUIRE_MSG(WIFEXITED(c_status), "child abnormal exit: %d (sig %d)",
684*20917cacSEric van Gyzen c_status, WTERMSIG(c_status));
685*20917cacSEric van Gyzen ATF_REQUIRE_EQ_MSG(WEXITSTATUS(c_status), 0, "child status: %d",
686*20917cacSEric van Gyzen WEXITSTATUS(c_status));
68757718be8SEnji Cooper
688*20917cacSEric van Gyzen ATF_REQUIRE_MSG(shmctl(sender_shmid, IPC_STAT, &s_ds) != -1,
68957718be8SEnji Cooper "shmctl IPC_STAT: %d", errno);
69057718be8SEnji Cooper
69157718be8SEnji Cooper print_shmid_ds(&s_ds, 0600);
69257718be8SEnji Cooper }
69357718be8SEnji Cooper
694ea7e7006SKonstantin Belousov static void
shmid_cleanup(const char * name)695ea7e7006SKonstantin Belousov shmid_cleanup(const char *name)
69657718be8SEnji Cooper {
697ea7e7006SKonstantin Belousov int shmid;
69857718be8SEnji Cooper
69957718be8SEnji Cooper /*
70057718be8SEnji Cooper * Remove the shared memory area if it exists.
70157718be8SEnji Cooper */
702ea7e7006SKonstantin Belousov shmid = read_int(name);
703ea7e7006SKonstantin Belousov if (shmid != -1) {
704ea7e7006SKonstantin Belousov if (shmctl(shmid, IPC_RMID, NULL) == -1)
70557718be8SEnji Cooper err(1, "shmctl IPC_RMID");
70657718be8SEnji Cooper }
707ea7e7006SKonstantin Belousov }
708ea7e7006SKonstantin Belousov
ATF_TC_CLEANUP(shm,tc)709ea7e7006SKonstantin Belousov ATF_TC_CLEANUP(shm, tc)
710ea7e7006SKonstantin Belousov {
711ea7e7006SKonstantin Belousov
712ea7e7006SKonstantin Belousov shmid_cleanup("sender_shmid");
713ea7e7006SKonstantin Belousov }
71457718be8SEnji Cooper
71557718be8SEnji Cooper void
print_shmid_ds(struct shmid_ds * sp,mode_t mode)7165e1e3ea2SBrooks Davis print_shmid_ds(struct shmid_ds *sp, mode_t mode)
71757718be8SEnji Cooper {
71857718be8SEnji Cooper uid_t uid = geteuid();
71957718be8SEnji Cooper gid_t gid = getegid();
72057718be8SEnji Cooper
72157718be8SEnji Cooper printf("PERM: uid %d, gid %d, cuid %d, cgid %d, mode 0%o\n",
72257718be8SEnji Cooper sp->shm_perm.uid, sp->shm_perm.gid,
72357718be8SEnji Cooper sp->shm_perm.cuid, sp->shm_perm.cgid,
72457718be8SEnji Cooper sp->shm_perm.mode & 0777);
72557718be8SEnji Cooper
72657718be8SEnji Cooper printf("segsz %lu, lpid %d, cpid %d, nattch %u\n",
72757718be8SEnji Cooper (u_long)sp->shm_segsz, sp->shm_lpid, sp->shm_cpid,
72857718be8SEnji Cooper sp->shm_nattch);
72957718be8SEnji Cooper
73057718be8SEnji Cooper printf("atime: %s", ctime(&sp->shm_atime));
73157718be8SEnji Cooper printf("dtime: %s", ctime(&sp->shm_dtime));
73257718be8SEnji Cooper printf("ctime: %s", ctime(&sp->shm_ctime));
73357718be8SEnji Cooper
73457718be8SEnji Cooper /*
73557718be8SEnji Cooper * Sanity check a few things.
73657718be8SEnji Cooper */
73757718be8SEnji Cooper
73857718be8SEnji Cooper ATF_REQUIRE_MSG(sp->shm_perm.uid == uid && sp->shm_perm.cuid == uid,
73957718be8SEnji Cooper "uid mismatch");
74057718be8SEnji Cooper
74157718be8SEnji Cooper ATF_REQUIRE_MSG(sp->shm_perm.gid == gid && sp->shm_perm.cgid == gid,
74257718be8SEnji Cooper "gid mismatch");
74357718be8SEnji Cooper
74457718be8SEnji Cooper ATF_REQUIRE_MSG((sp->shm_perm.mode & 0777) == mode, "mode mismatch");
74557718be8SEnji Cooper }
74657718be8SEnji Cooper
74757718be8SEnji Cooper void
sharer(void)7485e1e3ea2SBrooks Davis sharer(void)
74957718be8SEnji Cooper {
75057718be8SEnji Cooper int shmid;
75157718be8SEnji Cooper void *shm_buf;
75257718be8SEnji Cooper
75357718be8SEnji Cooper shmid = shmget(shmkey, pgsize, 0);
754*20917cacSEric van Gyzen if (shmid == -1)
755*20917cacSEric van Gyzen err(1, "receiver: shmget");
75657718be8SEnji Cooper
75757718be8SEnji Cooper shm_buf = shmat(shmid, NULL, 0);
758*20917cacSEric van Gyzen if (shm_buf == (void *) -1)
759*20917cacSEric van Gyzen err(1, "receiver: shmat");
76057718be8SEnji Cooper
76157718be8SEnji Cooper printf("%s\n", (const char *)shm_buf);
76257718be8SEnji Cooper
763*20917cacSEric van Gyzen if (strcmp((const char *)shm_buf, m2_str) != 0)
764*20917cacSEric van Gyzen errx(1, "receiver: data isn't correct");
76557718be8SEnji Cooper
76657718be8SEnji Cooper exit(0);
76757718be8SEnji Cooper }
76857718be8SEnji Cooper
769ea7e7006SKonstantin Belousov #ifdef SHM_REMAP
770ea7e7006SKonstantin Belousov ATF_TC_WITH_CLEANUP(shm_remap);
ATF_TC_HEAD(shm_remap,tc)771ea7e7006SKonstantin Belousov ATF_TC_HEAD(shm_remap, tc)
772ea7e7006SKonstantin Belousov {
773ea7e7006SKonstantin Belousov
774ea7e7006SKonstantin Belousov atf_tc_set_md_var(tc, "descr", "Checks SHM_REMAP");
775ea7e7006SKonstantin Belousov }
776ea7e7006SKonstantin Belousov
ATF_TC_BODY(shm_remap,tc)777ea7e7006SKonstantin Belousov ATF_TC_BODY(shm_remap, tc)
778ea7e7006SKonstantin Belousov {
779ea7e7006SKonstantin Belousov char *shm_buf;
780ea7e7006SKonstantin Belousov int shmid_remap;
781ea7e7006SKonstantin Belousov
782ea7e7006SKonstantin Belousov pgsize = sysconf(_SC_PAGESIZE);
783ea7e7006SKonstantin Belousov
784ea7e7006SKonstantin Belousov shmkey = get_ftok(4160);
785ea7e7006SKonstantin Belousov ATF_REQUIRE_MSG(shmkey != (key_t)-1, "get_ftok failed");
786ea7e7006SKonstantin Belousov
787ea7e7006SKonstantin Belousov ATF_REQUIRE_MSG((shmid_remap = shmget(shmkey, pgsize,
788ea7e7006SKonstantin Belousov IPC_CREAT | 0640)) != -1, "shmget: %d", errno);
789ea7e7006SKonstantin Belousov write_int("shmid_remap", shmid_remap);
790ea7e7006SKonstantin Belousov
791ea7e7006SKonstantin Belousov ATF_REQUIRE_MSG((shm_buf = mmap(NULL, pgsize, PROT_READ | PROT_WRITE,
792ea7e7006SKonstantin Belousov MAP_ANON | MAP_PRIVATE, -1, 0)) != MAP_FAILED, "mmap: %d", errno);
793ea7e7006SKonstantin Belousov
794ea7e7006SKonstantin Belousov ATF_REQUIRE_MSG(shmat(shmid_remap, shm_buf, 0) == (void *)-1,
795ea7e7006SKonstantin Belousov "shmat without MAP_REMAP succeeded");
796ea7e7006SKonstantin Belousov ATF_REQUIRE_MSG(shmat(shmid_remap, shm_buf, SHM_REMAP) == shm_buf,
797ea7e7006SKonstantin Belousov "shmat(SHM_REMAP): %d", errno);
798ea7e7006SKonstantin Belousov }
799ea7e7006SKonstantin Belousov
ATF_TC_CLEANUP(shm_remap,tc)800ea7e7006SKonstantin Belousov ATF_TC_CLEANUP(shm_remap, tc)
801ea7e7006SKonstantin Belousov {
802ea7e7006SKonstantin Belousov
803ea7e7006SKonstantin Belousov shmid_cleanup("shmid_remap");
804ea7e7006SKonstantin Belousov }
805ea7e7006SKonstantin Belousov #endif /* SHM_REMAP */
806ea7e7006SKonstantin Belousov
ATF_TP_ADD_TCS(tp)80757718be8SEnji Cooper ATF_TP_ADD_TCS(tp)
80857718be8SEnji Cooper {
80957718be8SEnji Cooper
81057718be8SEnji Cooper ATF_TP_ADD_TC(tp, msg);
81157718be8SEnji Cooper ATF_TP_ADD_TC(tp, sem);
81257718be8SEnji Cooper ATF_TP_ADD_TC(tp, shm);
813ea7e7006SKonstantin Belousov #ifdef SHM_REMAP
814ea7e7006SKonstantin Belousov ATF_TP_ADD_TC(tp, shm_remap);
815ea7e7006SKonstantin Belousov #endif
81657718be8SEnji Cooper
81757718be8SEnji Cooper return atf_no_error();
81857718be8SEnji Cooper }
81957718be8SEnji Cooper
820