1/***********************************************************************
2*                                                                      *
3*               This software is part of the ast package               *
4*          Copyright (c) 1985-2010 AT&T Intellectual Property          *
5*                      and is licensed under the                       *
6*                  Common Public License, Version 1.0                  *
7*                    by AT&T Intellectual Property                     *
8*                                                                      *
9*                A copy of the License is available at                 *
10*            http://www.opensource.org/licenses/cpl1.0.txt             *
11*         (with md5 checksum 059e8cd6165cb4c31e351f2b69388fd9)         *
12*                                                                      *
13*              Information and Software Systems Research               *
14*                            AT&T Research                             *
15*                           Florham Park NJ                            *
16*                                                                      *
17*                 Glenn Fowler <gsf@research.att.com>                  *
18*                  David Korn <dgk@research.att.com>                   *
19*                   Phong Vo <kpv@research.att.com>                    *
20*                                                                      *
21***********************************************************************/
22#pragma prototyped
23
24#include "stdhdr.h"
25
26extern char*
27_stdgets(Sfio_t* f, char* us, int n, int isgets)
28{
29	int		p;
30	unsigned char*	is;
31	unsigned char*	ps;
32
33	if(n <= 0 || !us || (f->mode != SF_READ && _sfmode(f,SF_READ,0) < 0))
34		return NIL(char*);
35
36	SFLOCK(f,0);
37
38	n -= 1;
39	is = (uchar*)us;
40
41	while(n)
42	{	/* peek the read buffer for data */
43		if((p = f->endb - (ps = f->next)) <= 0 )
44		{	f->getr = '\n';
45			f->mode |= SF_RC;
46			if(SFRPEEK(f,ps,p) <= 0)
47				break;
48		}
49
50		if(p > n)
51			p = n;
52
53#if _lib_memccpy
54		if((ps = (uchar*)memccpy((char*)is,(char*)ps,'\n',p)) != NIL(uchar*))
55			p = ps-is;
56		is += p;
57		ps  = f->next+p;
58#else
59		if(!(f->flags&(SF_BOTH|SF_MALLOC)))
60		{	while(p-- && (*is++ = *ps++) != '\n')
61				;
62			p = ps-f->next;
63		}
64		else
65		{	reg int	c = ps[p-1];
66			if(c != '\n')
67				ps[p-1] = '\n';
68			while((*is++ = *ps++) != '\n')
69				;
70			if(c != '\n')
71			{	f->next[p-1] = c;
72				if((ps-f->next) >= p)
73					is[-1] = c;
74			}
75		}
76#endif
77
78		/* gobble up read data and continue */
79		f->next = ps;
80		if(is[-1] == '\n')
81			break;
82		else if(n > 0)
83			n -= p;
84	}
85
86	if((_Sfi = is - ((uchar*)us)) <= 0)
87		us = NIL(char*);
88	else if(isgets && is[-1] == '\n')
89	{	is[-1] = '\0';
90		_Sfi -= 1;
91	}
92	else	*is = '\0';
93
94	SFOPEN(f,0);
95	return us;
96}
97
98char*
99fgets(char* s, int n, Sfio_t* f)
100{
101	STDIO_PTR(f, "fgets", char*, (char*, int, Sfio_t*), (s, n, f))
102
103	return _stdgets(f, s, n, 0);
104}
105
106char*
107gets(char* s)
108{
109	return _stdgets(sfstdin, s, BUFSIZ, 1);
110}
111