eval: Allow user override of 'missing'
[nbdkit/ericb.git] / tests / test-streaming.c
blobac8df5fa74260283b82fc064d082fd4faffc17d7
1 /* nbdkit
2 * Copyright (C) 2014-2019 Red Hat Inc.
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions are
6 * met:
8 * * Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.
11 * * Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
15 * * Neither the name of Red Hat nor the names of its contributors may be
16 * used to endorse or promote products derived from this software without
17 * specific prior written permission.
19 * THIS SOFTWARE IS PROVIDED BY RED HAT AND CONTRIBUTORS ''AS IS'' AND
20 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
21 * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
22 * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL RED HAT OR
23 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
24 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
25 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
26 * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
27 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
28 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
29 * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
30 * SUCH DAMAGE.
33 #include <config.h>
35 #include <stdio.h>
36 #include <stdlib.h>
37 #include <string.h>
38 #include <fcntl.h>
39 #include <unistd.h>
40 #include <sys/types.h>
41 #include <sys/stat.h>
42 #include <sys/wait.h>
44 #include <libnbd.h>
46 static char data[65536];
48 int
49 main (int argc, char *argv[])
51 pid_t md5pid;
52 struct nbd_handle *nbd;
53 size_t i;
54 int pipefd[2];
55 char md5[33];
56 int status;
58 unlink ("streaming.fifo");
59 if (mknod ("streaming.fifo", S_IFIFO | 0600, 0) == -1) {
60 perror ("streaming.fifo");
61 exit (EXIT_FAILURE);
64 nbd = nbd_create ();
65 if (nbd == NULL) {
66 fprintf (stderr, "%s\n", nbd_get_error ());
67 exit (EXIT_FAILURE);
70 char *args[] = {
71 "nbdkit", "-s", "--exit-with-parent",
72 "streaming", "pipe=streaming.fifo", "size=640k", NULL
74 if (nbd_connect_command (nbd, args) == -1) {
75 fprintf (stderr, "%s\n", nbd_get_error ());
76 exit (EXIT_FAILURE);
79 /* Fork to run a second process which reads from streaming.fifo and
80 * checks that the content is correct. The test doesn't care about
81 * fd leaks, so we don't bother with CLOEXEC.
83 if (pipe (pipefd) == -1) {
84 perror ("pipe");
85 exit (EXIT_FAILURE);
88 md5pid = fork ();
89 if (md5pid == -1) {
90 perror ("fork");
91 exit (EXIT_FAILURE);
94 if (md5pid == 0) {
95 /* Child: run md5sum on the pipe. */
96 char *exec_argv[] = { "md5sum", NULL };
98 close (0);
99 open ("streaming.fifo", O_RDONLY);
100 close (1);
101 dup2 (pipefd[1], 1);
102 close (pipefd[0]);
104 execvp ("md5sum", exec_argv);
105 perror ("md5sum");
106 _exit (EXIT_FAILURE);
109 close (pipefd[1]);
111 /* Write linearly to the virtual disk. */
112 memset (data, 1, sizeof data);
113 for (i = 0; i < 10; ++i) {
114 if (nbd_pwrite (nbd, data, sizeof data, i * sizeof data, 0) == -1) {
115 fprintf (stderr, "%s\n", nbd_get_error ());
116 exit (EXIT_FAILURE);
120 /* This kills the nbdkit subprocess, which implicitly closes the
121 * pipe.
123 nbd_close (nbd);
125 /* Check the hash computed by the child process. */
126 if (read (pipefd[0], md5, 32) != 32) {
127 perror ("read");
128 exit (EXIT_FAILURE);
130 md5[32] = '\0';
132 printf ("md5 = %s\n", md5);
133 if (strcmp (md5, "2c7f81c580f7f9eb52c1bd2f6f493b6f") != 0) {
134 fprintf (stderr, "unexpected hash: %s\n", md5);
135 exit (EXIT_FAILURE);
138 if (waitpid (md5pid, &status, 0) == -1) {
139 perror ("waitpid");
140 exit (EXIT_FAILURE);
142 if (status != 0) {
143 fprintf (stderr, "md5sum subprocess failed\n");
144 exit (EXIT_FAILURE);
147 exit (EXIT_SUCCESS);