1 /*
2 * Copyright (C) 2004, 2007, 2011, 2012 Internet Systems Consortium, Inc. ("ISC")
3 * Copyright (C) 2000, 2001 Internet Software Consortium.
4 *
5 * Permission to use, copy, modify, and/or distribute this software for any
6 * purpose with or without fee is hereby granted, provided that the above
7 * copyright notice and this permission notice appear in all copies.
8 *
9 * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
10 * REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
11 * AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
12 * INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
13 * LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
14 * OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
15 * PERFORMANCE OF THIS SOFTWARE.
16 */
17
18 /* $Id$ */
19
20 #include <config.h>
21
22 #include <errno.h>
23 #include <unistd.h>
24
25 #include <isc/stdio.h>
26 #include <isc/stat.h>
27
28 #include "errno2result.h"
29
30 isc_result_t
isc_stdio_open(const char * filename,const char * mode,FILE ** fp)31 isc_stdio_open(const char *filename, const char *mode, FILE **fp) {
32 FILE *f;
33
34 f = fopen(filename, mode);
35 if (f == NULL)
36 return (isc__errno2result(errno));
37 *fp = f;
38 return (ISC_R_SUCCESS);
39 }
40
41 isc_result_t
isc_stdio_close(FILE * f)42 isc_stdio_close(FILE *f) {
43 int r;
44
45 r = fclose(f);
46 if (r == 0)
47 return (ISC_R_SUCCESS);
48 else
49 return (isc__errno2result(errno));
50 }
51
52 isc_result_t
isc_stdio_seek(FILE * f,long offset,int whence)53 isc_stdio_seek(FILE *f, long offset, int whence) {
54 int r;
55
56 r = fseek(f, offset, whence);
57 if (r == 0)
58 return (ISC_R_SUCCESS);
59 else
60 return (isc__errno2result(errno));
61 }
62
63 isc_result_t
isc_stdio_read(void * ptr,size_t size,size_t nmemb,FILE * f,size_t * nret)64 isc_stdio_read(void *ptr, size_t size, size_t nmemb, FILE *f, size_t *nret) {
65 isc_result_t result = ISC_R_SUCCESS;
66 size_t r;
67
68 clearerr(f);
69 r = fread(ptr, size, nmemb, f);
70 if (r != nmemb) {
71 if (feof(f))
72 result = ISC_R_EOF;
73 else
74 result = isc__errno2result(errno);
75 }
76 if (nret != NULL)
77 *nret = r;
78 return (result);
79 }
80
81 isc_result_t
isc_stdio_write(const void * ptr,size_t size,size_t nmemb,FILE * f,size_t * nret)82 isc_stdio_write(const void *ptr, size_t size, size_t nmemb, FILE *f,
83 size_t *nret)
84 {
85 isc_result_t result = ISC_R_SUCCESS;
86 size_t r;
87
88 clearerr(f);
89 r = fwrite(ptr, size, nmemb, f);
90 if (r != nmemb)
91 result = isc__errno2result(errno);
92 if (nret != NULL)
93 *nret = r;
94 return (result);
95 }
96
97 isc_result_t
isc_stdio_flush(FILE * f)98 isc_stdio_flush(FILE *f) {
99 int r;
100
101 r = fflush(f);
102 if (r == 0)
103 return (ISC_R_SUCCESS);
104 else
105 return (isc__errno2result(errno));
106 }
107
108 /*
109 * OpenBSD has deprecated ENOTSUP in favor of EOPNOTSUPP.
110 */
111 #if defined(EOPNOTSUPP) && !defined(ENOTSUP)
112 #define ENOTSUP EOPNOTSUPP
113 #endif
114
115 isc_result_t
isc_stdio_sync(FILE * f)116 isc_stdio_sync(FILE *f) {
117 int r;
118
119 r = fsync(fileno(f));
120 /*
121 * fsync is not supported on sockets and pipes which
122 * result in EINVAL / ENOTSUP.
123 */
124 if (r == 0 || errno == EINVAL || errno == ENOTSUP)
125 return (ISC_R_SUCCESS);
126 else
127 return (isc__errno2result(errno));
128 }
129
130