xref: /openbsd-src/lib/libc/stdio/fgets.3 (revision dd39f797388913bbd4298865a899a336ff3de11a)
1.\"	$OpenBSD: fgets.3,v 1.35 2017/12/01 11:18:40 schwarze Exp $
2.\"
3.\" Copyright (c) 1990, 1991, 1993
4.\"	The Regents of the University of California.  All rights reserved.
5.\"
6.\" This code is derived from software contributed to Berkeley by
7.\" Chris Torek and the American National Standards Committee X3,
8.\" on Information Processing Systems.
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.\" 3. Neither the name of the University nor the names of its contributors
19.\"    may be used to endorse or promote products derived from this software
20.\"    without specific prior written permission.
21.\"
22.\" THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
23.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
24.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
25.\" ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
26.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
27.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
28.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
29.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
30.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
31.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
32.\" SUCH DAMAGE.
33.\"
34.Dd $Mdocdate: December 1 2017 $
35.Dt FGETS 3
36.Os
37.Sh NAME
38.Nm fgets
39.Nd get a line from a stream
40.Sh SYNOPSIS
41.In stdio.h
42.Ft char *
43.Fn fgets "char *str" "int size" "FILE *stream"
44.Sh DESCRIPTION
45The
46.Fn fgets
47function reads at most
48.Ar size Ns \-1
49characters from the given
50.Fa stream
51and stores them in the string
52.Fa str .
53Reading stops when a newline character is found,
54at end-of-file, on error, or after
55.Ar size Ns \-1
56bytes are read.
57The newline, if any, is retained.
58The string will be NUL-terminated if
59.Fn fgets
60succeeds; otherwise the contents of
61.Fa str
62are undefined.
63.Sh RETURN VALUES
64Upon successful completion,
65.Fn fgets
66returns a pointer to the string.
67If end-of-file or an error occurs before any characters are read,
68it returns
69.Dv NULL .
70The
71.Fn fgets
72function does not distinguish between end-of-file and error,
73and callers must use
74.Xr feof 3
75and
76.Xr ferror 3
77to determine which occurred.
78Whether
79.Fn fgets
80can possibly fail with a
81.Ar size
82argument of 1 is implementation-dependent.
83On
84.Ox ,
85.Fn fgets
86will never return
87.Dv NULL
88when
89.Ar size
90is 1.
91.Sh ERRORS
92.Bl -tag -width Er
93.It Bq Er EBADF
94The given
95.Fa stream
96is not a readable stream.
97.It Bq Er EINVAL
98The given
99.Fa size
100is less than or equal to 0.
101.El
102.Pp
103The function
104.Fn fgets
105may also fail and set
106.Va errno
107for any of the errors specified for the routines
108.Xr fflush 3 ,
109.Xr fstat 2 ,
110.Xr read 2 ,
111or
112.Xr malloc 3 .
113.Sh SEE ALSO
114.Xr feof 3 ,
115.Xr ferror 3 ,
116.Xr fgetws 3 ,
117.Xr getline 3
118.Sh STANDARDS
119The function
120.Fn fgets
121conforms to
122.St -ansiC .
123.Sh HISTORY
124The function
125.Fn fgets
126first appeared in
127.At v7 .
128.Sh CAVEATS
129The following bit of code illustrates a case where the programmer assumes a
130string is too long if it does not contain a newline:
131.Bd -literal -offset indent
132char buf[1024], *p;
133
134while (fgets(buf, sizeof(buf), fp) != NULL) {
135	if ((p = strchr(buf, '\en')) == NULL) {
136		fprintf(stderr, "input line too long.\en");
137		exit(1);
138	}
139	*p = '\e0';
140	printf("%s\en", buf);
141}
142.Ed
143.Pp
144While the error would be true if a line \*(Gt 1023 characters were read,
145it would be false in two other cases:
146.Bl -enum -offset indent
147.It
148If the last line in a file does not contain a newline, the string returned by
149.Fn fgets
150will not contain a newline either.
151Thus
152.Fn strchr
153will return
154.Dv NULL
155and the program will terminate, even if the line was valid.
156.It
157All C string functions, including
158.Fn strchr ,
159correctly assume the end of the string is represented by a NUL
160.Pq Sq \e0
161character.
162If the first character of a line returned by
163.Fn fgets
164were NUL,
165.Fn strchr
166would immediately return without considering the rest of the returned text
167which may indeed include a newline.
168.El
169.Pp
170Consider using
171.Xr getline 3
172instead when dealing with untrusted input.
173.Pp
174It is erroneous to assume that
175.Fn fgets
176never returns an empty string when successful.
177If a line starts with the NUL character, fgets will store the NUL and
178continue reading until it encounters a newline or end-of-file.
179This will result in an empty string being returned.
180The following bit of code illustrates a case where the programmer assumes
181the string cannot be zero length.
182.Bd -literal -offset indent
183char buf[1024];
184
185if (fgets(buf, sizeof(buf), fp) != NULL) {
186	/* WRONG */
187	if (buf[strlen(buf) - 1] == '\en')
188		buf[strlen(buf) - 1] = '\e0';
189}
190.Ed
191.Pp
192If
193.Fn strlen
194returns 0, the index into the buffer becomes \-1.
195One way to concisely and correctly trim a newline is shown below.
196.Bd -literal -offset indent
197char buf[1024];
198
199if (fgets(buf, sizeof(buf), fp) != NULL)
200	buf[strcspn(buf, "\en")] = '\e0';
201.Ed
202