1/*	$NetBSD: t_fputc.c,v 1.1 2011/09/11 09:02:46 jruoho Exp $ */
2
3/*-
4 * Copyright (c) 2011 The NetBSD Foundation, Inc.
5 * All rights reserved.
6 *
7 * This code is derived from software contributed to The NetBSD Foundation
8 * by Jukka Ruohonen.
9 *
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 * 1. Redistributions of source code must retain the above copyright
14 *    notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 *    notice, this list of conditions and the following disclaimer in the
17 *    documentation and/or other materials provided with the distribution.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
20 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
21 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22 * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
23 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29 * POSSIBILITY OF SUCH DAMAGE.
30 */
31#include <sys/cdefs.h>
32__RCSID("$NetBSD: t_fputc.c,v 1.1 2011/09/11 09:02:46 jruoho Exp $");
33
34#include <atf-c.h>
35#include <errno.h>
36#include <stdio.h>
37#include <string.h>
38#include <unistd.h>
39
40static const char	*path = "fputc";
41static void		 puterr(int (*)(int, FILE *));
42static void		 putstr(int (*)(int, FILE *));
43
44static void
45puterr(int (*func)(int, FILE *))
46{
47	FILE *f;
48
49	f = fopen(path, "w+");
50
51	ATF_REQUIRE(f != NULL);
52	ATF_REQUIRE(fclose(f) == 0);
53	ATF_REQUIRE(unlink(path) == 0);
54	ATF_REQUIRE(func('x', f) == EOF);
55}
56
57static void
58putstr(int (*func)(int, FILE *))
59{
60	const char *str = "1234567890x";
61	unsigned short i = 0;
62	char buf[10];
63	FILE *f;
64
65	(void)memset(buf, 'x', sizeof(buf));
66
67	f = fopen(path, "w+");
68	ATF_REQUIRE(f != NULL);
69
70	while (str[i] != 'x') {
71		ATF_REQUIRE(func(str[i], f) == str[i]);
72		i++;
73	}
74
75	ATF_REQUIRE(fclose(f) == 0);
76
77	f = fopen(path, "r");
78	ATF_REQUIRE(f != NULL);
79
80	ATF_REQUIRE(fread(buf, 1, 10, f) == 10);
81	ATF_REQUIRE(strncmp(buf, str, 10) == 0);
82
83	ATF_REQUIRE(fclose(f) == 0);
84	ATF_REQUIRE(unlink(path) == 0);
85}
86
87ATF_TC_WITH_CLEANUP(fputc_basic);
88ATF_TC_HEAD(fputc_basic, tc)
89{
90	atf_tc_set_md_var(tc, "descr", "A basic test of fputc(3)");
91}
92
93ATF_TC_BODY(fputc_basic, tc)
94{
95	putstr(fputc);
96}
97
98ATF_TC_CLEANUP(fputc_basic, tc)
99{
100	(void)unlink(path);
101}
102
103ATF_TC_WITH_CLEANUP(fputc_err);
104ATF_TC_HEAD(fputc_err, tc)
105{
106	atf_tc_set_md_var(tc, "descr", "Test errors from fputc(3)");
107}
108
109ATF_TC_BODY(fputc_err, tc)
110{
111	puterr(fputc);
112}
113
114ATF_TC_CLEANUP(fputc_err, tc)
115{
116	(void)unlink(path);
117}
118
119ATF_TC_WITH_CLEANUP(putc_basic);
120ATF_TC_HEAD(putc_basic, tc)
121{
122	atf_tc_set_md_var(tc, "descr", "A basic test of putc(3)");
123}
124
125ATF_TC_BODY(putc_basic, tc)
126{
127	putstr(putc);
128}
129
130ATF_TC_CLEANUP(putc_basic, tc)
131{
132	(void)unlink(path);
133}
134
135ATF_TC_WITH_CLEANUP(putc_err);
136ATF_TC_HEAD(putc_err, tc)
137{
138	atf_tc_set_md_var(tc, "descr", "Test errors from putc(3)");
139}
140
141ATF_TC_BODY(putc_err, tc)
142{
143	puterr(putc);
144}
145
146ATF_TC_CLEANUP(putc_err, tc)
147{
148	(void)unlink(path);
149}
150
151ATF_TC_WITH_CLEANUP(putc_unlocked_basic);
152ATF_TC_HEAD(putc_unlocked_basic, tc)
153{
154	atf_tc_set_md_var(tc, "descr", "A basic test of putc_unlocked(3)");
155}
156
157ATF_TC_BODY(putc_unlocked_basic, tc)
158{
159	putstr(putc_unlocked);
160}
161
162ATF_TC_CLEANUP(putc_unlocked_basic, tc)
163{
164	(void)unlink(path);
165}
166
167ATF_TC_WITH_CLEANUP(putc_unlocked_err);
168ATF_TC_HEAD(putc_unlocked_err, tc)
169{
170	atf_tc_set_md_var(tc, "descr", "Test errors from putc_unlocked(3)");
171}
172
173ATF_TC_BODY(putc_unlocked_err, tc)
174{
175	puterr(putc_unlocked);
176}
177
178ATF_TC_CLEANUP(putc_unlocked_err, tc)
179{
180	(void)unlink(path);
181}
182
183ATF_TP_ADD_TCS(tp)
184{
185
186	ATF_TP_ADD_TC(tp, fputc_basic);
187	ATF_TP_ADD_TC(tp, fputc_err);
188	ATF_TP_ADD_TC(tp, putc_basic);
189	ATF_TP_ADD_TC(tp, putc_err);
190	ATF_TP_ADD_TC(tp, putc_unlocked_basic);
191	ATF_TP_ADD_TC(tp, putc_unlocked_err);
192
193	return atf_no_error();
194}
195