1 : /*
2 : * Copyright (c) 2012 The Native Client Authors. All rights reserved.
3 : * Use of this source code is governed by a BSD-style license that can be
4 : * found in the LICENSE file.
5 : */
6 :
7 : #include <errno.h>
8 :
9 : /*
10 : * NaCl Generic I/O interface.
11 : */
12 : #include "native_client/src/include/portability.h"
13 :
14 : #include "native_client/src/shared/gio/gio.h"
15 :
16 : struct GioVtbl const kGioFileVtbl = {
17 : GioFileDtor,
18 : GioFileRead,
19 : GioFileWrite,
20 : GioFileSeek,
21 : GioFileFlush,
22 : GioFileClose,
23 : };
24 :
25 :
26 : int GioFileCtor(struct GioFile *self,
27 : char const *fname,
28 1 : char const *mode) {
29 1 : self->base.vtbl = (struct GioVtbl *) NULL;
30 1 : self->iop = fopen(fname, mode);
31 1 : if (NULL == self->iop) {
32 0 : return 0;
33 : }
34 1 : self->base.vtbl = &kGioFileVtbl;
35 1 : return 1;
36 1 : }
37 :
38 :
39 : int GioFileRefCtor(struct GioFile *self,
40 28 : FILE *iop) {
41 28 : self->iop = iop;
42 :
43 28 : self->base.vtbl = &kGioFileVtbl;
44 28 : return 1;
45 28 : }
46 :
47 :
48 : ssize_t GioFileRead(struct Gio *vself,
49 : void *buf,
50 1 : size_t count) {
51 1 : struct GioFile *self = (struct GioFile *) vself;
52 : size_t ret;
53 :
54 1 : ret = fread(buf, 1, count, self->iop);
55 1 : if (0 == ret && ferror(self->iop)) {
56 0 : errno = EIO;
57 0 : return -1;
58 : }
59 1 : return (ssize_t) ret;
60 1 : }
61 :
62 :
63 : ssize_t GioFileWrite(struct Gio *vself,
64 : const void *buf,
65 12 : size_t count) {
66 12 : struct GioFile *self = (struct GioFile *) vself;
67 : size_t ret;
68 :
69 12 : ret = fwrite(buf, 1, count, self->iop);
70 12 : if (0 == ret && ferror(self->iop)) {
71 0 : errno = EIO;
72 0 : return -1;
73 : }
74 12 : return (ssize_t) ret;
75 12 : }
76 :
77 :
78 : off_t GioFileSeek(struct Gio *vself,
79 : off_t offset,
80 1 : int whence) {
81 1 : struct GioFile *self = (struct GioFile *) vself;
82 : int ret;
83 :
84 1 : ret = fseek(self->iop, (long) offset, whence);
85 1 : if (-1 == ret) return -1;
86 :
87 1 : return (off_t) ftell(self->iop);
88 1 : }
89 :
90 :
91 10 : int GioFileFlush(struct Gio *vself) {
92 10 : struct GioFile *self = (struct GioFile *) vself;
93 :
94 10 : return fflush(self->iop);
95 10 : }
96 :
97 :
98 1 : int GioFileClose(struct Gio *vself){
99 1 : struct GioFile *self = (struct GioFile *) vself;
100 : int rv;
101 1 : rv = (EOF == fclose(self->iop)) ? -1 : 0;
102 1 : if (0 == rv) {
103 1 : self->iop = (FILE *) 0;
104 : }
105 1 : return rv;
106 1 : }
107 :
108 :
109 4 : void GioFileDtor(struct Gio *vself) {
110 4 : struct GioFile *self = (struct GioFile *) vself;
111 4 : if (0 != self->iop) {
112 3 : (void) fclose(self->iop);
113 : }
114 4 : }
115 :
116 :
117 0 : int fggetc(struct Gio *gp) {
118 : char ch;
119 :
120 0 : return (*gp->vtbl->Read)(gp, &ch, 1) == 1 ? ch : EOF;
121 0 : }
|