1*4c87aefeSPatrick Mooney /*
2*4c87aefeSPatrick Mooney * This file and its contents are supplied under the terms of the
3*4c87aefeSPatrick Mooney * Common Development and Distribution License ("CDDL"), version 1.0.
4*4c87aefeSPatrick Mooney * You may only use this file in accordance with the terms of version
5*4c87aefeSPatrick Mooney * 1.0 of the CDDL.
6*4c87aefeSPatrick Mooney *
7*4c87aefeSPatrick Mooney * A full copy of the text of the CDDL should have accompanied this
8*4c87aefeSPatrick Mooney * source. A copy of the CDDL is also available via the Internet at
9*4c87aefeSPatrick Mooney * http://www.illumos.org/license/CDDL.
10*4c87aefeSPatrick Mooney */
11*4c87aefeSPatrick Mooney
12*4c87aefeSPatrick Mooney /*
13*4c87aefeSPatrick Mooney * Copyright 2018 Joyent, Inc.
14*4c87aefeSPatrick Mooney */
15*4c87aefeSPatrick Mooney
16*4c87aefeSPatrick Mooney /*
17*4c87aefeSPatrick Mooney * Test: read.requeue
18*4c87aefeSPatrick Mooney * Assertion: A sequence of writes turns into a sequence of events.
19*4c87aefeSPatrick Mooney *
20*4c87aefeSPatrick Mooney * Strategy: 1. Create a pipe
21*4c87aefeSPatrick Mooney * 2. Call mevent_add() to be notified of writes to the pipe. The
22*4c87aefeSPatrick Mooney * callback will signal a cv.
23*4c87aefeSPatrick Mooney * 3. In a loop, write to the pipe then wait on the cv.
24*4c87aefeSPatrick Mooney */
25*4c87aefeSPatrick Mooney
26*4c87aefeSPatrick Mooney #include <errno.h>
27*4c87aefeSPatrick Mooney #include <fcntl.h>
28*4c87aefeSPatrick Mooney #include <pthread.h>
29*4c87aefeSPatrick Mooney #include <signal.h>
30*4c87aefeSPatrick Mooney #include <stdio.h>
31*4c87aefeSPatrick Mooney #include <stdlib.h>
32*4c87aefeSPatrick Mooney #include <strings.h>
33*4c87aefeSPatrick Mooney #include <unistd.h>
34*4c87aefeSPatrick Mooney
35*4c87aefeSPatrick Mooney #include <sys/types.h>
36*4c87aefeSPatrick Mooney #include <sys/stat.h>
37*4c87aefeSPatrick Mooney
38*4c87aefeSPatrick Mooney #include "testlib.h"
39*4c87aefeSPatrick Mooney #include "mevent.h"
40*4c87aefeSPatrick Mooney
41*4c87aefeSPatrick Mooney static pthread_mutex_t mtx = PTHREAD_MUTEX_INITIALIZER;
42*4c87aefeSPatrick Mooney static pthread_cond_t cv = PTHREAD_COND_INITIALIZER;
43*4c87aefeSPatrick Mooney
44*4c87aefeSPatrick Mooney static char *cookie = "Chocolate chip with fudge stripes";
45*4c87aefeSPatrick Mooney
46*4c87aefeSPatrick Mooney static void
munch(int fd,enum ev_type ev,void * arg)47*4c87aefeSPatrick Mooney munch(int fd, enum ev_type ev, void *arg)
48*4c87aefeSPatrick Mooney {
49*4c87aefeSPatrick Mooney static int i = 0;
50*4c87aefeSPatrick Mooney char buf[8] = { 0 };
51*4c87aefeSPatrick Mooney ssize_t nbytes;
52*4c87aefeSPatrick Mooney
53*4c87aefeSPatrick Mooney ASSERT_INT_EQ(("bad event"), ev, EVF_READ);
54*4c87aefeSPatrick Mooney ASSERT_PTR_EQ(("bad cookie"), arg, cookie);
55*4c87aefeSPatrick Mooney
56*4c87aefeSPatrick Mooney if ((nbytes = read(fd, buf, sizeof (buf))) < 0) {
57*4c87aefeSPatrick Mooney ASSERT_INT64_EQ(("bad read: %s", strerror(errno)), nbytes, 1);
58*4c87aefeSPatrick Mooney }
59*4c87aefeSPatrick Mooney VERBOSE(("read %ld bytes '%s'", nbytes, buf));
60*4c87aefeSPatrick Mooney
61*4c87aefeSPatrick Mooney ASSERT_INT64_EQ(("wanted a byte of cookie"), nbytes, 1);
62*4c87aefeSPatrick Mooney
63*4c87aefeSPatrick Mooney ASSERT_CHAR_EQ(("bad byte %d of cookie", i), buf[0], cookie[i]);
64*4c87aefeSPatrick Mooney
65*4c87aefeSPatrick Mooney pthread_mutex_lock(&mtx);
66*4c87aefeSPatrick Mooney pthread_cond_signal(&cv);
67*4c87aefeSPatrick Mooney VERBOSE(("wakeup"));
68*4c87aefeSPatrick Mooney pthread_mutex_unlock(&mtx);
69*4c87aefeSPatrick Mooney
70*4c87aefeSPatrick Mooney i++;
71*4c87aefeSPatrick Mooney }
72*4c87aefeSPatrick Mooney
73*4c87aefeSPatrick Mooney int
main(int argc,const char * argv[])74*4c87aefeSPatrick Mooney main(int argc, const char *argv[])
75*4c87aefeSPatrick Mooney {
76*4c87aefeSPatrick Mooney int pipefds[2];
77*4c87aefeSPatrick Mooney struct mevent *evp;
78*4c87aefeSPatrick Mooney
79*4c87aefeSPatrick Mooney start_test(argv[0], 5);
80*4c87aefeSPatrick Mooney start_event_thread();
81*4c87aefeSPatrick Mooney
82*4c87aefeSPatrick Mooney if (pipe(pipefds) != 0) {
83*4c87aefeSPatrick Mooney FAIL_ERRNO("pipe");
84*4c87aefeSPatrick Mooney }
85*4c87aefeSPatrick Mooney if (fcntl(pipefds[0], F_SETFL, O_NONBLOCK) != 0) {
86*4c87aefeSPatrick Mooney FAIL_ERRNO("set pipe nonblocking");
87*4c87aefeSPatrick Mooney }
88*4c87aefeSPatrick Mooney
89*4c87aefeSPatrick Mooney evp = mevent_add(pipefds[0], EVF_READ, munch, cookie);
90*4c87aefeSPatrick Mooney ASSERT_PTR_NEQ(("mevent_add"), evp, NULL);
91*4c87aefeSPatrick Mooney
92*4c87aefeSPatrick Mooney for (int i = 0; cookie[i] != '\0'; i++) {
93*4c87aefeSPatrick Mooney ssize_t written;
94*4c87aefeSPatrick Mooney
95*4c87aefeSPatrick Mooney pthread_mutex_lock(&mtx);
96*4c87aefeSPatrick Mooney written = write(pipefds[1], cookie + i, 1);
97*4c87aefeSPatrick Mooney if (written < 0) {
98*4c87aefeSPatrick Mooney FAIL_ERRNO("bad write");
99*4c87aefeSPatrick Mooney }
100*4c87aefeSPatrick Mooney ASSERT_INT64_EQ(("write byte %d of cookie", i), written, 1);
101*4c87aefeSPatrick Mooney
102*4c87aefeSPatrick Mooney /* Wait for it to be read */
103*4c87aefeSPatrick Mooney pthread_cond_wait(&cv, &mtx);
104*4c87aefeSPatrick Mooney pthread_mutex_unlock(&mtx);
105*4c87aefeSPatrick Mooney }
106*4c87aefeSPatrick Mooney
107*4c87aefeSPatrick Mooney PASS();
108*4c87aefeSPatrick Mooney }
109