xref: /illumos-gate/usr/src/cmd/sendmail/include/sm/io.h (revision 7c478bd9)
1*7c478bd9Sstevel@tonic-gate /*
2*7c478bd9Sstevel@tonic-gate  * Copyright (c) 2000-2002, 2004 Sendmail, Inc. and its suppliers.
3*7c478bd9Sstevel@tonic-gate  *      All rights reserved.
4*7c478bd9Sstevel@tonic-gate  * Copyright (c) 1990
5*7c478bd9Sstevel@tonic-gate  * 	 The Regents of the University of California.  All rights reserved.
6*7c478bd9Sstevel@tonic-gate  *
7*7c478bd9Sstevel@tonic-gate  * This code is derived from software contributed to Berkeley by
8*7c478bd9Sstevel@tonic-gate  * Chris Torek.
9*7c478bd9Sstevel@tonic-gate  *
10*7c478bd9Sstevel@tonic-gate  * By using this file, you agree to the terms and conditions set
11*7c478bd9Sstevel@tonic-gate  * forth in the LICENSE file which can be found at the top level of
12*7c478bd9Sstevel@tonic-gate  * the sendmail distribution.
13*7c478bd9Sstevel@tonic-gate  *
14*7c478bd9Sstevel@tonic-gate  *	$Id: io.h,v 1.24 2004/03/03 19:14:49 ca Exp $
15*7c478bd9Sstevel@tonic-gate  */
16*7c478bd9Sstevel@tonic-gate 
17*7c478bd9Sstevel@tonic-gate #pragma ident	"%Z%%M%	%I%	%E% SMI"
18*7c478bd9Sstevel@tonic-gate 
19*7c478bd9Sstevel@tonic-gate /*-
20*7c478bd9Sstevel@tonic-gate  *	@(#)stdio.h	5.17 (Berkeley) 6/3/91
21*7c478bd9Sstevel@tonic-gate  */
22*7c478bd9Sstevel@tonic-gate 
23*7c478bd9Sstevel@tonic-gate #ifndef	SM_IO_H
24*7c478bd9Sstevel@tonic-gate #define SM_IO_H
25*7c478bd9Sstevel@tonic-gate 
26*7c478bd9Sstevel@tonic-gate #include <stdio.h>
27*7c478bd9Sstevel@tonic-gate #include <sm/gen.h>
28*7c478bd9Sstevel@tonic-gate #include <sm/varargs.h>
29*7c478bd9Sstevel@tonic-gate 
30*7c478bd9Sstevel@tonic-gate /* mode for sm io (exposed) */
31*7c478bd9Sstevel@tonic-gate #define SM_IO_RDWR	1	/* read-write */
32*7c478bd9Sstevel@tonic-gate #define SM_IO_RDONLY	2	/* read-only */
33*7c478bd9Sstevel@tonic-gate #define SM_IO_WRONLY	3	/* write-only */
34*7c478bd9Sstevel@tonic-gate #define SM_IO_APPEND	4	/* write-only from eof */
35*7c478bd9Sstevel@tonic-gate #define SM_IO_APPENDRW	5	/* read-write from eof */
36*7c478bd9Sstevel@tonic-gate #define SM_IO_RDWRTR	6	/* read-write with truncation indicated */
37*7c478bd9Sstevel@tonic-gate 
38*7c478bd9Sstevel@tonic-gate # define SM_IO_BINARY	0x0	/* binary mode: not used in Unix */
39*7c478bd9Sstevel@tonic-gate #define SM_IS_BINARY(mode)	(((mode) & SM_IO_BINARY) != 0)
40*7c478bd9Sstevel@tonic-gate #define SM_IO_MODE(mode)	((mode) & 0x0f)
41*7c478bd9Sstevel@tonic-gate 
42*7c478bd9Sstevel@tonic-gate #define SM_IO_RDWR_B	(SM_IO_RDWR|SM_IO_BINARY)
43*7c478bd9Sstevel@tonic-gate #define SM_IO_RDONLY_B	(SM_IO_RDONLY|SM_IO_BINARY)
44*7c478bd9Sstevel@tonic-gate #define SM_IO_WRONLY_B	(SM_IO_WRONLY|SM_IO_BINARY)
45*7c478bd9Sstevel@tonic-gate #define SM_IO_APPEND_B	(SM_IO_APPEND|SM_IO_BINARY)
46*7c478bd9Sstevel@tonic-gate #define SM_IO_APPENDRW_B	(SM_IO_APPENDRW|SM_IO_BINARY)
47*7c478bd9Sstevel@tonic-gate #define SM_IO_RDWRTR_B	(SM_IO_RDWRTR|SM_IO_BINARY)
48*7c478bd9Sstevel@tonic-gate 
49*7c478bd9Sstevel@tonic-gate /* for sm_io_fseek, et al api's (exposed) */
50*7c478bd9Sstevel@tonic-gate #define SM_IO_SEEK_SET	0
51*7c478bd9Sstevel@tonic-gate #define SM_IO_SEEK_CUR	1
52*7c478bd9Sstevel@tonic-gate #define SM_IO_SEEK_END	2
53*7c478bd9Sstevel@tonic-gate 
54*7c478bd9Sstevel@tonic-gate /* flags for info what's with different types (exposed) */
55*7c478bd9Sstevel@tonic-gate #define SM_IO_WHAT_MODE		1
56*7c478bd9Sstevel@tonic-gate #define SM_IO_WHAT_VECTORS	2
57*7c478bd9Sstevel@tonic-gate #define SM_IO_WHAT_FD		3
58*7c478bd9Sstevel@tonic-gate #define SM_IO_WHAT_TYPE		4
59*7c478bd9Sstevel@tonic-gate #define SM_IO_WHAT_ISTYPE	5
60*7c478bd9Sstevel@tonic-gate #define SM_IO_IS_READABLE	6
61*7c478bd9Sstevel@tonic-gate #define SM_IO_WHAT_TIMEOUT	7
62*7c478bd9Sstevel@tonic-gate #define SM_IO_WHAT_SIZE		8
63*7c478bd9Sstevel@tonic-gate 
64*7c478bd9Sstevel@tonic-gate /* info flags (exposed) */
65*7c478bd9Sstevel@tonic-gate #define SM_IO_FTYPE_CREATE	1
66*7c478bd9Sstevel@tonic-gate #define SM_IO_FTYPE_MODIFY	2
67*7c478bd9Sstevel@tonic-gate #define SM_IO_FTYPE_DELETE	3
68*7c478bd9Sstevel@tonic-gate 
69*7c478bd9Sstevel@tonic-gate #define SM_IO_SL_PRIO		1
70*7c478bd9Sstevel@tonic-gate 
71*7c478bd9Sstevel@tonic-gate #define SM_IO_OPEN_MAX		20
72*7c478bd9Sstevel@tonic-gate 
73*7c478bd9Sstevel@tonic-gate /* for internal buffers */
74*7c478bd9Sstevel@tonic-gate struct smbuf
75*7c478bd9Sstevel@tonic-gate {
76*7c478bd9Sstevel@tonic-gate 	unsigned char	*smb_base;
77*7c478bd9Sstevel@tonic-gate 	int		smb_size;
78*7c478bd9Sstevel@tonic-gate };
79*7c478bd9Sstevel@tonic-gate 
80*7c478bd9Sstevel@tonic-gate /*
81*7c478bd9Sstevel@tonic-gate **  sm I/O state variables (internal only).
82*7c478bd9Sstevel@tonic-gate **
83*7c478bd9Sstevel@tonic-gate **	The following always hold:
84*7c478bd9Sstevel@tonic-gate **
85*7c478bd9Sstevel@tonic-gate **		if (flags&(SMLBF|SMWR)) == (SMLBF|SMWR),
86*7c478bd9Sstevel@tonic-gate **			lbfsize is -bf.size, else lbfsize is 0
87*7c478bd9Sstevel@tonic-gate **		if flags&SMRD, w is 0
88*7c478bd9Sstevel@tonic-gate **		if flags&SMWR, r is 0
89*7c478bd9Sstevel@tonic-gate **
90*7c478bd9Sstevel@tonic-gate **	This ensures that the getc and putc macros (or inline functions) never
91*7c478bd9Sstevel@tonic-gate **	try to write or read from a file that is in `read' or `write' mode.
92*7c478bd9Sstevel@tonic-gate **	(Moreover, they can, and do, automatically switch from read mode to
93*7c478bd9Sstevel@tonic-gate **	write mode, and back, on "r+" and "w+" files.)
94*7c478bd9Sstevel@tonic-gate **
95*7c478bd9Sstevel@tonic-gate **	lbfsize is used only to make the inline line-buffered output stream
96*7c478bd9Sstevel@tonic-gate **	code as compact as possible.
97*7c478bd9Sstevel@tonic-gate **
98*7c478bd9Sstevel@tonic-gate **	ub, up, and ur are used when ungetc() pushes back more characters
99*7c478bd9Sstevel@tonic-gate **	than fit in the current bf, or when ungetc() pushes back a character
100*7c478bd9Sstevel@tonic-gate **	that does not match the previous one in bf.  When this happens,
101*7c478bd9Sstevel@tonic-gate **	ub.base becomes non-nil (i.e., a stream has ungetc() data iff
102*7c478bd9Sstevel@tonic-gate **	ub.base!=NULL) and up and ur save the current values of p and r.
103*7c478bd9Sstevel@tonic-gate */
104*7c478bd9Sstevel@tonic-gate 
105*7c478bd9Sstevel@tonic-gate typedef struct sm_file SM_FILE_T;
106*7c478bd9Sstevel@tonic-gate 
107*7c478bd9Sstevel@tonic-gate struct sm_file
108*7c478bd9Sstevel@tonic-gate {
109*7c478bd9Sstevel@tonic-gate 	const char	*sm_magic;	/* This SM_FILE_T is free when NULL */
110*7c478bd9Sstevel@tonic-gate 	unsigned char	*f_p;		/* current position in (some) buffer */
111*7c478bd9Sstevel@tonic-gate 	int		f_r;		/* read space left for getc() */
112*7c478bd9Sstevel@tonic-gate 	int		f_w;		/* write space left for putc() */
113*7c478bd9Sstevel@tonic-gate 	long		f_flags;	/* flags, below */
114*7c478bd9Sstevel@tonic-gate 	short		f_file;		/* fileno, if Unix fd, else -1 */
115*7c478bd9Sstevel@tonic-gate 	struct smbuf	f_bf;		/* the buffer (>= 1 byte, if !NULL) */
116*7c478bd9Sstevel@tonic-gate 	int		f_lbfsize;	/* 0 or -bf.size, for inline putc */
117*7c478bd9Sstevel@tonic-gate 
118*7c478bd9Sstevel@tonic-gate 	/* These can be used for any purpose by a file type implementation: */
119*7c478bd9Sstevel@tonic-gate 	void		*f_cookie;
120*7c478bd9Sstevel@tonic-gate 	int		f_ival;
121*7c478bd9Sstevel@tonic-gate 
122*7c478bd9Sstevel@tonic-gate 	/* operations */
123*7c478bd9Sstevel@tonic-gate 	int		(*f_close) __P((SM_FILE_T *));
124*7c478bd9Sstevel@tonic-gate 	ssize_t		(*f_read)  __P((SM_FILE_T *, char *, size_t));
125*7c478bd9Sstevel@tonic-gate 	off_t		(*f_seek)  __P((SM_FILE_T *, off_t, int));
126*7c478bd9Sstevel@tonic-gate 	ssize_t		(*f_write) __P((SM_FILE_T *, const char *, size_t));
127*7c478bd9Sstevel@tonic-gate 	int		(*f_open) __P((SM_FILE_T *, const void *, int,
128*7c478bd9Sstevel@tonic-gate 					const void *));
129*7c478bd9Sstevel@tonic-gate 	int		(*f_setinfo) __P((SM_FILE_T *, int , void *));
130*7c478bd9Sstevel@tonic-gate 	int		(*f_getinfo) __P((SM_FILE_T *, int , void *));
131*7c478bd9Sstevel@tonic-gate 	int		f_timeout;
132*7c478bd9Sstevel@tonic-gate 	int		f_timeoutstate;   /* either blocking or non-blocking */
133*7c478bd9Sstevel@tonic-gate 	char		*f_type;	/* for by-type lookups */
134*7c478bd9Sstevel@tonic-gate 	struct sm_file	*f_flushfp;	/* flush this before reading parent */
135*7c478bd9Sstevel@tonic-gate 	struct sm_file	*f_modefp;	/* sync mode with this fp */
136*7c478bd9Sstevel@tonic-gate 
137*7c478bd9Sstevel@tonic-gate 	/* separate buffer for long sequences of ungetc() */
138*7c478bd9Sstevel@tonic-gate 	struct smbuf	f_ub;	/* ungetc buffer */
139*7c478bd9Sstevel@tonic-gate 	unsigned char	*f_up;	/* saved f_p when f_p is doing ungetc */
140*7c478bd9Sstevel@tonic-gate 	int		f_ur;	/* saved f_r when f_r is counting ungetc */
141*7c478bd9Sstevel@tonic-gate 
142*7c478bd9Sstevel@tonic-gate 	/* tricks to meet minimum requirements even when malloc() fails */
143*7c478bd9Sstevel@tonic-gate 	unsigned char	f_ubuf[3];	/* guarantee an ungetc() buffer */
144*7c478bd9Sstevel@tonic-gate 	unsigned char	f_nbuf[1];	/* guarantee a getc() buffer */
145*7c478bd9Sstevel@tonic-gate 
146*7c478bd9Sstevel@tonic-gate 	/* Unix stdio files get aligned to block boundaries on fseek() */
147*7c478bd9Sstevel@tonic-gate 	int		f_blksize;	/* stat.st_blksize (may be != bf.size) */
148*7c478bd9Sstevel@tonic-gate 	off_t		f_lseekoff;	/* current lseek offset */
149*7c478bd9Sstevel@tonic-gate 	int		f_dup_cnt;	/* count file dup'd */
150*7c478bd9Sstevel@tonic-gate };
151*7c478bd9Sstevel@tonic-gate 
152*7c478bd9Sstevel@tonic-gate __BEGIN_DECLS
153*7c478bd9Sstevel@tonic-gate extern SM_FILE_T	SmIoF[];
154*7c478bd9Sstevel@tonic-gate extern const char	SmFileMagic[];
155*7c478bd9Sstevel@tonic-gate extern SM_FILE_T	SmFtStdio_def;
156*7c478bd9Sstevel@tonic-gate extern SM_FILE_T	SmFtStdiofd_def;
157*7c478bd9Sstevel@tonic-gate extern SM_FILE_T	SmFtString_def;
158*7c478bd9Sstevel@tonic-gate extern SM_FILE_T	SmFtSyslog_def;
159*7c478bd9Sstevel@tonic-gate extern SM_FILE_T	SmFtRealStdio_def;
160*7c478bd9Sstevel@tonic-gate 
161*7c478bd9Sstevel@tonic-gate #define SMIOIN_FILENO		0
162*7c478bd9Sstevel@tonic-gate #define SMIOOUT_FILENO		1
163*7c478bd9Sstevel@tonic-gate #define SMIOERR_FILENO		2
164*7c478bd9Sstevel@tonic-gate #define SMIOSTDIN_FILENO	3
165*7c478bd9Sstevel@tonic-gate #define SMIOSTDOUT_FILENO	4
166*7c478bd9Sstevel@tonic-gate #define SMIOSTDERR_FILENO	5
167*7c478bd9Sstevel@tonic-gate 
168*7c478bd9Sstevel@tonic-gate /* Common predefined and already (usually) open files (exposed) */
169*7c478bd9Sstevel@tonic-gate #define smioin		(&SmIoF[SMIOIN_FILENO])
170*7c478bd9Sstevel@tonic-gate #define smioout		(&SmIoF[SMIOOUT_FILENO])
171*7c478bd9Sstevel@tonic-gate #define smioerr		(&SmIoF[SMIOERR_FILENO])
172*7c478bd9Sstevel@tonic-gate #define smiostdin	(&SmIoF[SMIOSTDIN_FILENO])
173*7c478bd9Sstevel@tonic-gate #define smiostdout	(&SmIoF[SMIOSTDOUT_FILENO])
174*7c478bd9Sstevel@tonic-gate #define smiostderr	(&SmIoF[SMIOSTDERR_FILENO])
175*7c478bd9Sstevel@tonic-gate 
176*7c478bd9Sstevel@tonic-gate #define SmFtStdio	(&SmFtStdio_def)
177*7c478bd9Sstevel@tonic-gate #define SmFtStdiofd	(&SmFtStdiofd_def)
178*7c478bd9Sstevel@tonic-gate #define SmFtString	(&SmFtString_def)
179*7c478bd9Sstevel@tonic-gate #define SmFtSyslog	(&SmFtSyslog_def)
180*7c478bd9Sstevel@tonic-gate #define SmFtRealStdio	(&SmFtRealStdio_def)
181*7c478bd9Sstevel@tonic-gate 
182*7c478bd9Sstevel@tonic-gate #ifdef __STDC__
183*7c478bd9Sstevel@tonic-gate # define SM_IO_SET_TYPE(f, name, open, close, read, write, seek, get, set, timeout) \
184*7c478bd9Sstevel@tonic-gate     (f) = {SmFileMagic, (unsigned char *) 0, 0, 0, 0L, -1, {0}, 0, (void *) 0,\
185*7c478bd9Sstevel@tonic-gate 	0, (close), (read), (seek), (write), (open), (set), (get), (timeout),\
186*7c478bd9Sstevel@tonic-gate 	0, (name)}
187*7c478bd9Sstevel@tonic-gate # define SM_IO_INIT_TYPE(f, name, open, close, read, write, seek, get, set, timeout)
188*7c478bd9Sstevel@tonic-gate 
189*7c478bd9Sstevel@tonic-gate #else /* __STDC__ */
190*7c478bd9Sstevel@tonic-gate # define SM_IO_SET_TYPE(f, name, open, close, read, write, seek, get, set, timeout) (f)
191*7c478bd9Sstevel@tonic-gate # define SM_IO_INIT_TYPE(f, name, open, close, read, write, seek, get, set, timeout) \
192*7c478bd9Sstevel@tonic-gate 	(f).sm_magic = SmFileMagic;	\
193*7c478bd9Sstevel@tonic-gate 	(f).f_p = (unsigned char *) 0;	\
194*7c478bd9Sstevel@tonic-gate 	(f).f_r = 0;	\
195*7c478bd9Sstevel@tonic-gate 	(f).f_w = 0;	\
196*7c478bd9Sstevel@tonic-gate 	(f).f_flags = 0L;	\
197*7c478bd9Sstevel@tonic-gate 	(f).f_file = 0;	\
198*7c478bd9Sstevel@tonic-gate 	(f).f_bf.smb_base = (unsigned char *) 0;	\
199*7c478bd9Sstevel@tonic-gate 	(f).f_bf.smb_size = 0;	\
200*7c478bd9Sstevel@tonic-gate 	(f).f_lbfsize = 0;	\
201*7c478bd9Sstevel@tonic-gate 	(f).f_cookie = (void *) 0;	\
202*7c478bd9Sstevel@tonic-gate 	(f).f_ival = 0;	\
203*7c478bd9Sstevel@tonic-gate 	(f).f_close = (close);	\
204*7c478bd9Sstevel@tonic-gate 	(f).f_read = (read);	\
205*7c478bd9Sstevel@tonic-gate 	(f).f_seek = (seek);	\
206*7c478bd9Sstevel@tonic-gate 	(f).f_write = (write);	\
207*7c478bd9Sstevel@tonic-gate 	(f).f_open = (open);	\
208*7c478bd9Sstevel@tonic-gate 	(f).f_setinfo = (set);	\
209*7c478bd9Sstevel@tonic-gate 	(f).f_getinfo = (get);	\
210*7c478bd9Sstevel@tonic-gate 	(f).f_timeout = (timeout);	\
211*7c478bd9Sstevel@tonic-gate 	(f).f_timeoutstate = 0;	\
212*7c478bd9Sstevel@tonic-gate 	(f).f_type = (name);
213*7c478bd9Sstevel@tonic-gate 
214*7c478bd9Sstevel@tonic-gate #endif /* __STDC__ */
215*7c478bd9Sstevel@tonic-gate 
216*7c478bd9Sstevel@tonic-gate __END_DECLS
217*7c478bd9Sstevel@tonic-gate 
218*7c478bd9Sstevel@tonic-gate /* Internal flags */
219*7c478bd9Sstevel@tonic-gate #define SMFBF		0x000001	/* XXXX fully buffered */
220*7c478bd9Sstevel@tonic-gate #define SMLBF		0x000002	/* line buffered */
221*7c478bd9Sstevel@tonic-gate #define SMNBF		0x000004	/* unbuffered */
222*7c478bd9Sstevel@tonic-gate #define SMNOW		0x000008	/* Flush each write; take read now */
223*7c478bd9Sstevel@tonic-gate #define SMRD		0x000010	/* OK to read */
224*7c478bd9Sstevel@tonic-gate #define SMWR		0x000020	/* OK to write */
225*7c478bd9Sstevel@tonic-gate 	/* RD and WR are never simultaneously asserted */
226*7c478bd9Sstevel@tonic-gate #define SMRW		0x000040	/* open for reading & writing */
227*7c478bd9Sstevel@tonic-gate #define SMFEOF		0x000080	/* found EOF */
228*7c478bd9Sstevel@tonic-gate #define SMERR		0x000100	/* found error */
229*7c478bd9Sstevel@tonic-gate #define SMMBF		0x000200	/* buf is from malloc */
230*7c478bd9Sstevel@tonic-gate #define SMAPP		0x000400	/* fdopen()ed in append mode */
231*7c478bd9Sstevel@tonic-gate #define SMSTR		0x000800	/* this is an snprintf string */
232*7c478bd9Sstevel@tonic-gate #define SMOPT		0x001000	/* do fseek() optimisation */
233*7c478bd9Sstevel@tonic-gate #define SMNPT		0x002000	/* do not do fseek() optimisation */
234*7c478bd9Sstevel@tonic-gate #define SMOFF		0x004000	/* set iff offset is in fact correct */
235*7c478bd9Sstevel@tonic-gate #define SMALC		0x010000	/* allocate string space dynamically */
236*7c478bd9Sstevel@tonic-gate 
237*7c478bd9Sstevel@tonic-gate #define SMMODEMASK	0x0070	/* read/write mode */
238*7c478bd9Sstevel@tonic-gate 
239*7c478bd9Sstevel@tonic-gate /* defines for timeout constants */
240*7c478bd9Sstevel@tonic-gate #define SM_TIME_IMMEDIATE	(0)
241*7c478bd9Sstevel@tonic-gate #define SM_TIME_FOREVER		(-1)
242*7c478bd9Sstevel@tonic-gate #define SM_TIME_DEFAULT		(-2)
243*7c478bd9Sstevel@tonic-gate 
244*7c478bd9Sstevel@tonic-gate /* timeout state for blocking */
245*7c478bd9Sstevel@tonic-gate #define SM_TIME_BLOCK		(0)	/* XXX just bool? */
246*7c478bd9Sstevel@tonic-gate #define SM_TIME_NONBLOCK	(1)
247*7c478bd9Sstevel@tonic-gate 
248*7c478bd9Sstevel@tonic-gate /* Exposed buffering type flags */
249*7c478bd9Sstevel@tonic-gate #define SM_IO_FBF	0	/* setvbuf should set fully buffered */
250*7c478bd9Sstevel@tonic-gate #define SM_IO_LBF	1	/* setvbuf should set line buffered */
251*7c478bd9Sstevel@tonic-gate #define SM_IO_NBF	2	/* setvbuf should set unbuffered */
252*7c478bd9Sstevel@tonic-gate 
253*7c478bd9Sstevel@tonic-gate /* setvbuf buffered, but through at lower file type layers */
254*7c478bd9Sstevel@tonic-gate #define SM_IO_NOW	3
255*7c478bd9Sstevel@tonic-gate 
256*7c478bd9Sstevel@tonic-gate /*
257*7c478bd9Sstevel@tonic-gate **  size of buffer used by setbuf.
258*7c478bd9Sstevel@tonic-gate **  If underlying filesystem blocksize is discoverable that is used instead
259*7c478bd9Sstevel@tonic-gate */
260*7c478bd9Sstevel@tonic-gate 
261*7c478bd9Sstevel@tonic-gate #define SM_IO_BUFSIZ	4096
262*7c478bd9Sstevel@tonic-gate 
263*7c478bd9Sstevel@tonic-gate #define SM_IO_EOF	(-1)
264*7c478bd9Sstevel@tonic-gate 
265*7c478bd9Sstevel@tonic-gate /* Functions defined in ANSI C standard.  */
266*7c478bd9Sstevel@tonic-gate __BEGIN_DECLS
267*7c478bd9Sstevel@tonic-gate SM_FILE_T *sm_io_autoflush __P((SM_FILE_T *, SM_FILE_T *));
268*7c478bd9Sstevel@tonic-gate void	 sm_io_automode __P((SM_FILE_T *, SM_FILE_T *));
269*7c478bd9Sstevel@tonic-gate void	 sm_io_clearerr __P((SM_FILE_T *));
270*7c478bd9Sstevel@tonic-gate int	 sm_io_close __P((SM_FILE_T *, int SM_NONVOLATILE));
271*7c478bd9Sstevel@tonic-gate SM_FILE_T *sm_io_dup __P((SM_FILE_T *));
272*7c478bd9Sstevel@tonic-gate int	 sm_io_eof __P((SM_FILE_T *));
273*7c478bd9Sstevel@tonic-gate int	 sm_io_error __P((SM_FILE_T *));
274*7c478bd9Sstevel@tonic-gate char	*sm_io_fgets __P((SM_FILE_T *, int, char *, int));
275*7c478bd9Sstevel@tonic-gate int	 sm_io_flush __P((SM_FILE_T *, int SM_NONVOLATILE));
276*7c478bd9Sstevel@tonic-gate 
277*7c478bd9Sstevel@tonic-gate int PRINTFLIKE(3, 4)
278*7c478bd9Sstevel@tonic-gate sm_io_fprintf __P((SM_FILE_T *, int, const char *, ...));
279*7c478bd9Sstevel@tonic-gate 
280*7c478bd9Sstevel@tonic-gate int	 sm_io_fputs __P((SM_FILE_T *, int, const char *));
281*7c478bd9Sstevel@tonic-gate 
282*7c478bd9Sstevel@tonic-gate int SCANFLIKE(3, 4)
283*7c478bd9Sstevel@tonic-gate sm_io_fscanf __P((SM_FILE_T *, int, const char *, ...));
284*7c478bd9Sstevel@tonic-gate 
285*7c478bd9Sstevel@tonic-gate int	 sm_io_getc __P((SM_FILE_T *, int));
286*7c478bd9Sstevel@tonic-gate int	 sm_io_getinfo __P((SM_FILE_T *, int, void *));
287*7c478bd9Sstevel@tonic-gate SM_FILE_T *sm_io_open __P((const SM_FILE_T *, int SM_NONVOLATILE, const void *,
288*7c478bd9Sstevel@tonic-gate 			   int, const void *));
289*7c478bd9Sstevel@tonic-gate int	 sm_io_purge __P((SM_FILE_T *));
290*7c478bd9Sstevel@tonic-gate int	 sm_io_putc __P((SM_FILE_T *, int, int));
291*7c478bd9Sstevel@tonic-gate size_t	 sm_io_read __P((SM_FILE_T *, int, void *, size_t));
292*7c478bd9Sstevel@tonic-gate SM_FILE_T *sm_io_reopen __P((const SM_FILE_T *, int SM_NONVOLATILE,
293*7c478bd9Sstevel@tonic-gate 			     const void *, int, const void *, SM_FILE_T *));
294*7c478bd9Sstevel@tonic-gate void	 sm_io_rewind __P((SM_FILE_T *, int));
295*7c478bd9Sstevel@tonic-gate int	 sm_io_seek __P((SM_FILE_T *, int SM_NONVOLATILE, long SM_NONVOLATILE,
296*7c478bd9Sstevel@tonic-gate 			 int SM_NONVOLATILE));
297*7c478bd9Sstevel@tonic-gate int	 sm_io_setinfo __P((SM_FILE_T *, int, void *));
298*7c478bd9Sstevel@tonic-gate int	 sm_io_setvbuf __P((SM_FILE_T *, int, char *, int, size_t));
299*7c478bd9Sstevel@tonic-gate 
300*7c478bd9Sstevel@tonic-gate int SCANFLIKE(2, 3)
301*7c478bd9Sstevel@tonic-gate sm_io_sscanf __P((const char *, char const *, ...));
302*7c478bd9Sstevel@tonic-gate 
303*7c478bd9Sstevel@tonic-gate long	 sm_io_tell __P((SM_FILE_T *, int SM_NONVOLATILE));
304*7c478bd9Sstevel@tonic-gate int	 sm_io_ungetc __P((SM_FILE_T *, int, int));
305*7c478bd9Sstevel@tonic-gate int	 sm_io_vfprintf __P((SM_FILE_T *, int, const char *, va_list));
306*7c478bd9Sstevel@tonic-gate size_t	 sm_io_write __P((SM_FILE_T *, int, const void *, size_t));
307*7c478bd9Sstevel@tonic-gate 
308*7c478bd9Sstevel@tonic-gate void	 sm_strio_init __P((SM_FILE_T *, char *, size_t));
309*7c478bd9Sstevel@tonic-gate 
310*7c478bd9Sstevel@tonic-gate extern SM_FILE_T *
311*7c478bd9Sstevel@tonic-gate sm_io_fopen __P((
312*7c478bd9Sstevel@tonic-gate 	char *_pathname,
313*7c478bd9Sstevel@tonic-gate 	int _flags,
314*7c478bd9Sstevel@tonic-gate 	...));
315*7c478bd9Sstevel@tonic-gate 
316*7c478bd9Sstevel@tonic-gate extern SM_FILE_T *
317*7c478bd9Sstevel@tonic-gate sm_io_stdioopen __P((
318*7c478bd9Sstevel@tonic-gate 	FILE *_stream,
319*7c478bd9Sstevel@tonic-gate 	char *_mode));
320*7c478bd9Sstevel@tonic-gate 
321*7c478bd9Sstevel@tonic-gate extern int
322*7c478bd9Sstevel@tonic-gate sm_vasprintf __P((
323*7c478bd9Sstevel@tonic-gate 	char **_str,
324*7c478bd9Sstevel@tonic-gate 	const char *_fmt,
325*7c478bd9Sstevel@tonic-gate 	va_list _ap));
326*7c478bd9Sstevel@tonic-gate 
327*7c478bd9Sstevel@tonic-gate extern int
328*7c478bd9Sstevel@tonic-gate sm_vsnprintf __P((
329*7c478bd9Sstevel@tonic-gate 	char *,
330*7c478bd9Sstevel@tonic-gate 	size_t,
331*7c478bd9Sstevel@tonic-gate 	const char *,
332*7c478bd9Sstevel@tonic-gate 	va_list));
333*7c478bd9Sstevel@tonic-gate 
334*7c478bd9Sstevel@tonic-gate extern void
335*7c478bd9Sstevel@tonic-gate sm_perror __P((
336*7c478bd9Sstevel@tonic-gate 	const char *));
337*7c478bd9Sstevel@tonic-gate 
338*7c478bd9Sstevel@tonic-gate __END_DECLS
339*7c478bd9Sstevel@tonic-gate 
340*7c478bd9Sstevel@tonic-gate /*
341*7c478bd9Sstevel@tonic-gate ** Functions internal to the implementation.
342*7c478bd9Sstevel@tonic-gate */
343*7c478bd9Sstevel@tonic-gate 
344*7c478bd9Sstevel@tonic-gate __BEGIN_DECLS
345*7c478bd9Sstevel@tonic-gate int	sm_rget __P((SM_FILE_T *, int));
346*7c478bd9Sstevel@tonic-gate int	sm_vfscanf __P((SM_FILE_T *, int SM_NONVOLATILE, const char *,
347*7c478bd9Sstevel@tonic-gate 			va_list SM_NONVOLATILE));
348*7c478bd9Sstevel@tonic-gate int	sm_wbuf __P((SM_FILE_T *, int, int));
349*7c478bd9Sstevel@tonic-gate __END_DECLS
350*7c478bd9Sstevel@tonic-gate 
351*7c478bd9Sstevel@tonic-gate /*
352*7c478bd9Sstevel@tonic-gate **  The macros are here so that we can
353*7c478bd9Sstevel@tonic-gate **  define function versions in the library.
354*7c478bd9Sstevel@tonic-gate */
355*7c478bd9Sstevel@tonic-gate 
356*7c478bd9Sstevel@tonic-gate #define sm_getc(f, t) \
357*7c478bd9Sstevel@tonic-gate 	(--(f)->f_r < 0 ? \
358*7c478bd9Sstevel@tonic-gate 		sm_rget(f, t) : \
359*7c478bd9Sstevel@tonic-gate 		(int)(*(f)->f_p++))
360*7c478bd9Sstevel@tonic-gate 
361*7c478bd9Sstevel@tonic-gate /*
362*7c478bd9Sstevel@tonic-gate **  This has been tuned to generate reasonable code on the vax using pcc.
363*7c478bd9Sstevel@tonic-gate **  (It also generates reasonable x86 code using gcc.)
364*7c478bd9Sstevel@tonic-gate */
365*7c478bd9Sstevel@tonic-gate 
366*7c478bd9Sstevel@tonic-gate #define sm_putc(f, t, c) \
367*7c478bd9Sstevel@tonic-gate 	(--(f)->f_w < 0 ? \
368*7c478bd9Sstevel@tonic-gate 		(f)->f_w >= (f)->f_lbfsize ? \
369*7c478bd9Sstevel@tonic-gate 			(*(f)->f_p = (c)), *(f)->f_p != '\n' ? \
370*7c478bd9Sstevel@tonic-gate 				(int)*(f)->f_p++ : \
371*7c478bd9Sstevel@tonic-gate 				sm_wbuf(f, t, '\n') : \
372*7c478bd9Sstevel@tonic-gate 			sm_wbuf(f, t, (int)(c)) : \
373*7c478bd9Sstevel@tonic-gate 		(*(f)->f_p = (c), (int)*(f)->f_p++))
374*7c478bd9Sstevel@tonic-gate 
375*7c478bd9Sstevel@tonic-gate #define sm_eof(p)	(((p)->f_flags & SMFEOF) != 0)
376*7c478bd9Sstevel@tonic-gate #define sm_error(p)	(((p)->f_flags & SMERR) != 0)
377*7c478bd9Sstevel@tonic-gate #define sm_clearerr(p)	((void)((p)->f_flags &= ~(SMERR|SMFEOF)))
378*7c478bd9Sstevel@tonic-gate 
379*7c478bd9Sstevel@tonic-gate #define sm_io_eof(p)	sm_eof(p)
380*7c478bd9Sstevel@tonic-gate #define sm_io_error(p)	sm_error(p)
381*7c478bd9Sstevel@tonic-gate 
382*7c478bd9Sstevel@tonic-gate #define sm_io_clearerr(p)	sm_clearerr(p)
383*7c478bd9Sstevel@tonic-gate 
384*7c478bd9Sstevel@tonic-gate #ifndef lint
385*7c478bd9Sstevel@tonic-gate # ifndef _POSIX_SOURCE
386*7c478bd9Sstevel@tonic-gate #  define sm_io_getc(fp, t)	sm_getc(fp, t)
387*7c478bd9Sstevel@tonic-gate #  define sm_io_putc(fp, t, x)	sm_putc(fp, t, x)
388*7c478bd9Sstevel@tonic-gate # endif /* _POSIX_SOURCE */
389*7c478bd9Sstevel@tonic-gate #endif /* lint */
390*7c478bd9Sstevel@tonic-gate 
391*7c478bd9Sstevel@tonic-gate #endif /* SM_IO_H */
392