xref: /netbsd-src/tests/lib/libc/stdio/t_popen.c (revision 9bb501f7a58018fb6787149e5148ba6a537b2272)
1*9bb501f7Schristos /*	$NetBSD: t_popen.c,v 1.4 2013/02/15 23:27:19 christos Exp $ */
2546ea3ceSpgoyette 
3546ea3ceSpgoyette /*-
4546ea3ceSpgoyette  * Copyright (c) 1999 The NetBSD Foundation, Inc.
5546ea3ceSpgoyette  * All rights reserved.
6546ea3ceSpgoyette  *
7546ea3ceSpgoyette  * This code is derived from software contributed to The NetBSD Foundation
8546ea3ceSpgoyette  * by Matthias Scheler.
9546ea3ceSpgoyette  *
10546ea3ceSpgoyette  * Redistribution and use in source and binary forms, with or without
11546ea3ceSpgoyette  * modification, are permitted provided that the following conditions
12546ea3ceSpgoyette  * are met:
13546ea3ceSpgoyette  * 1. Redistributions of source code must retain the above copyright
14546ea3ceSpgoyette  *    notice, this list of conditions and the following disclaimer.
15546ea3ceSpgoyette  * 2. Redistributions in binary form must reproduce the above copyright
16546ea3ceSpgoyette  *    notice, this list of conditions and the following disclaimer in the
17546ea3ceSpgoyette  *    documentation and/or other materials provided with the distribution.
18546ea3ceSpgoyette  *
19546ea3ceSpgoyette  * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
20546ea3ceSpgoyette  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
21546ea3ceSpgoyette  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22546ea3ceSpgoyette  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
23546ea3ceSpgoyette  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24546ea3ceSpgoyette  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25546ea3ceSpgoyette  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26546ea3ceSpgoyette  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27546ea3ceSpgoyette  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28546ea3ceSpgoyette  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29546ea3ceSpgoyette  * POSSIBILITY OF SUCH DAMAGE.
30546ea3ceSpgoyette  */
31546ea3ceSpgoyette 
32546ea3ceSpgoyette #include <sys/cdefs.h>
33546ea3ceSpgoyette #ifndef lint
34546ea3ceSpgoyette __COPYRIGHT("@(#) Copyright (c) 1999\
35546ea3ceSpgoyette  The NetBSD Foundation, Inc.  All rights reserved.");
36546ea3ceSpgoyette #endif /* not lint */
37546ea3ceSpgoyette 
38546ea3ceSpgoyette #ifndef lint
39*9bb501f7Schristos __RCSID("$NetBSD: t_popen.c,v 1.4 2013/02/15 23:27:19 christos Exp $");
40546ea3ceSpgoyette #endif /* not lint */
41546ea3ceSpgoyette 
42546ea3ceSpgoyette #include <atf-c.h>
43546ea3ceSpgoyette 
44546ea3ceSpgoyette #include <sys/param.h>
45546ea3ceSpgoyette 
46546ea3ceSpgoyette #include <errno.h>
472a18cea9Schristos #include <err.h>
48546ea3ceSpgoyette #include <paths.h>
49546ea3ceSpgoyette #include <stdio.h>
50546ea3ceSpgoyette #include <stdlib.h>
51546ea3ceSpgoyette #include <time.h>
52546ea3ceSpgoyette #include <unistd.h>
53546ea3ceSpgoyette 
54546ea3ceSpgoyette #define _PATH_CAT	"/bin/cat"
55546ea3ceSpgoyette #define BUFSIZE		(640*1024)
56546ea3ceSpgoyette 			/* 640KB ought to be enough for everyone. */
57546ea3ceSpgoyette #define DATAFILE	"popen.data"
58546ea3ceSpgoyette 
59546ea3ceSpgoyette #define TEST_ERROR(a)						\
60546ea3ceSpgoyette 	do							\
61546ea3ceSpgoyette 	{							\
622a18cea9Schristos 		warn(a);					\
63546ea3ceSpgoyette 		atf_tc_fail("Check stderr for error details.");	\
64546ea3ceSpgoyette 	} while ( /*CONSTCOND*/ 0 )
65546ea3ceSpgoyette 
66d808fe5fSjruoho ATF_TC_WITH_CLEANUP(popen_zeropad);
ATF_TC_HEAD(popen_zeropad,tc)67d808fe5fSjruoho ATF_TC_HEAD(popen_zeropad, tc)
68546ea3ceSpgoyette {
69546ea3ceSpgoyette 
70546ea3ceSpgoyette 	atf_tc_set_md_var(tc, "descr", "output format zero padding");
71546ea3ceSpgoyette }
72546ea3ceSpgoyette 
ATF_TC_BODY(popen_zeropad,tc)73d808fe5fSjruoho ATF_TC_BODY(popen_zeropad, tc)
74546ea3ceSpgoyette {
75546ea3ceSpgoyette 	char *buffer, command[MAXPATHLEN];
76*9bb501f7Schristos 	int idx, in;
77546ea3ceSpgoyette 	FILE *my_pipe;
78546ea3ceSpgoyette 
79d808fe5fSjruoho 	if ((buffer = malloc(BUFSIZE)) == NULL)
80546ea3ceSpgoyette 		atf_tc_skip("Unable to allocate buffer.");
81546ea3ceSpgoyette 
82546ea3ceSpgoyette 	srand ((unsigned int)time(NULL));
83d808fe5fSjruoho 
84*9bb501f7Schristos 	for (idx = 0; idx < BUFSIZE; idx++)
85*9bb501f7Schristos 		buffer[idx]=(char)rand();
86546ea3ceSpgoyette 
87d808fe5fSjruoho 	(void)snprintf(command, sizeof(command), "%s >%s",
88d808fe5fSjruoho 	    _PATH_CAT, DATAFILE);
89d808fe5fSjruoho 
90546ea3ceSpgoyette 	if ((my_pipe = popen(command, "w")) == NULL)
91546ea3ceSpgoyette 		TEST_ERROR("popen write");
92546ea3ceSpgoyette 
93546ea3ceSpgoyette 	if (fwrite(buffer, sizeof(char), BUFSIZE, my_pipe) != BUFSIZE)
94546ea3ceSpgoyette 		TEST_ERROR("fwrite");
95546ea3ceSpgoyette 
96546ea3ceSpgoyette 	if (pclose(my_pipe) == -1)
97546ea3ceSpgoyette 		TEST_ERROR("pclose");
98546ea3ceSpgoyette 
99546ea3ceSpgoyette 	(void)snprintf(command, sizeof(command), "%s %s", _PATH_CAT, DATAFILE);
100d808fe5fSjruoho 
101546ea3ceSpgoyette 	if ((my_pipe = popen(command, "r")) == NULL)
102546ea3ceSpgoyette 		TEST_ERROR("popen read");
103546ea3ceSpgoyette 
104*9bb501f7Schristos 	idx = 0;
105546ea3ceSpgoyette 	while ((in = fgetc(my_pipe)) != EOF)
106*9bb501f7Schristos 		if (idx == BUFSIZE) {
107546ea3ceSpgoyette 			errno = EFBIG;
108546ea3ceSpgoyette 			TEST_ERROR("read");
109546ea3ceSpgoyette 		}
110*9bb501f7Schristos 		else if ((char)in != buffer[idx++]) {
111546ea3ceSpgoyette 		    	errno = EINVAL;
112546ea3ceSpgoyette 			TEST_ERROR("read");
113546ea3ceSpgoyette 		}
114546ea3ceSpgoyette 
115*9bb501f7Schristos 	if (idx < BUFSIZE) {
116546ea3ceSpgoyette 		errno = EIO;
117546ea3ceSpgoyette 		TEST_ERROR("read");
118546ea3ceSpgoyette 	}
119546ea3ceSpgoyette 
120546ea3ceSpgoyette 	if (pclose(my_pipe) == -1)
121546ea3ceSpgoyette 		TEST_ERROR("pclose");
122546ea3ceSpgoyette }
123546ea3ceSpgoyette 
ATF_TC_CLEANUP(popen_zeropad,tc)124d808fe5fSjruoho ATF_TC_CLEANUP(popen_zeropad, tc)
125546ea3ceSpgoyette {
126546ea3ceSpgoyette 	(void)unlink(DATAFILE);
127546ea3ceSpgoyette }
128546ea3ceSpgoyette 
ATF_TP_ADD_TCS(tp)129546ea3ceSpgoyette ATF_TP_ADD_TCS(tp)
130546ea3ceSpgoyette {
131d808fe5fSjruoho 
132d808fe5fSjruoho 	ATF_TP_ADD_TC(tp, popen_zeropad);
133546ea3ceSpgoyette 
134546ea3ceSpgoyette 	return atf_no_error();
135546ea3ceSpgoyette }
136