1
2 /*
3 * Author:
4 * Guido Draheim <guidod@gmx.de>
5 * Tomi Ollila <Tomi.Ollila@iki.fi>
6 *
7 * Copyright (c) 1999,2000,2001,2002,2003 Guido Draheim
8 * All rights reserved,
9 * use under the restrictions of the
10 * Lesser GNU General Public License
11 * or alternatively the restrictions
12 * of the Mozilla Public License 1.1
13 */
14
15 #define _CRT_SECURE_NO_WARNINGS
16
17 #include <zzip/lib.h> /* exported... */
18 #include <zlib.h>
19
20 #include <string.h>
21 #include <errno.h>
22
23 #include <zzip/file.h>
24
25 /* *INDENT-OFF* */
26 static struct errlistentry { int code; const char* mesg; }
27 errlist[] =
28 {
29 { ZZIP_NO_ERROR, "No error" },
30 { ZZIP_OUTOFMEM,
31 "could not get temporary memory for internal structures" },
32 { ZZIP_DIR_OPEN, "Failed to open zip-file %s" },
33 { ZZIP_DIR_STAT, "Failed to fstat zip-file %s" },
34 { ZZIP_DIR_SEEK, "Failed to lseek zip-file %s" },
35 { ZZIP_DIR_READ, "Failed to read zip-file %s"},
36 { ZZIP_DIR_TOO_SHORT, "zip-file %s too short" },
37 { ZZIP_DIR_EDH_MISSING, "zip-file central directory not found" },
38 { ZZIP_DIRSIZE, "Directory size too big..." },
39 { ZZIP_ENOENT, "No such file found in zip-file %s" },
40 { ZZIP_UNSUPP_COMPR, "Unsupported compression format" },
41 { ZZIP_CORRUPTED, "Zipfile corrupted" },
42 { ZZIP_UNDEF, "Some undefined error occurred" },
43 { ZZIP_DIR_LARGEFILE, "Directory is largefile variant" },
44 { 0, 0 },
45 };
46 /* *INDENT-ON* */
47
48
49 #define errlistSIZE (sizeof(errlist)/sizeof(*errlist))
50
51 /**
52 * returns the static string for the given error code. The
53 * error code can be either a normal system error (a
54 * positive error code will flag this), it can be => libz
55 * error code (a small negative error code will flag this)
56 * or it can be an error code from => libzzip, which is an
57 * negative value lower than => ZZIP_ERROR
58 */
59 zzip_char_t *
zzip_strerror(int errcode)60 zzip_strerror(int errcode)
61 {
62 if (errcode < ZZIP_ERROR && errcode > ZZIP_ERROR - 32)
63 {
64 struct errlistentry *err = errlist;
65
66 for (; err->mesg; err++)
67 {
68 if (err->code == errcode)
69 return err->mesg;
70 }
71 errcode = EINVAL;
72 }
73
74 if (errcode < 0)
75 {
76 if (errcode == -1)
77 return strerror(errcode);
78 else
79 return zError(errcode);
80 }
81
82 return strerror(errcode);
83 }
84
85 /** => zzip_strerror
86 * This function fetches the errorcode from the => DIR-handle and
87 * runs it through => zzip_strerror to obtain the static string
88 * describing the error.
89 */
90 zzip_char_t *
zzip_strerror_of(ZZIP_DIR * dir)91 zzip_strerror_of(ZZIP_DIR * dir)
92 {
93 if (! dir)
94 return strerror(errno);
95 return zzip_strerror(dir->errcode);
96 }
97
98 /* *INDENT-OFF* */
99 static struct errnolistentry { int code; int e_no; }
100 errnolist[] =
101 {
102 { Z_STREAM_ERROR, EPIPE },
103 { Z_DATA_ERROR, ESPIPE },
104 { Z_MEM_ERROR, ENOMEM },
105 { Z_BUF_ERROR, EMFILE },
106 { Z_VERSION_ERROR, ENOEXEC },
107
108 { ZZIP_DIR_OPEN, ENOTDIR },
109 { ZZIP_DIR_STAT, EREMOTE },
110 { ZZIP_DIR_SEEK, ESPIPE },
111 # ifdef ESTRPIPE
112 { ZZIP_DIR_READ, ESTRPIPE},
113 # else
114 { ZZIP_DIR_READ, EPIPE},
115 # endif
116 { ZZIP_DIR_TOO_SHORT, ENOEXEC },
117 # ifdef ENOMEDIUM
118 { ZZIP_DIR_EDH_MISSING, ENOMEDIUM },
119 # else
120 { ZZIP_DIR_EDH_MISSING, EIO },
121 # endif
122 { ZZIP_DIRSIZE, EFBIG },
123 { ZZIP_OUTOFMEM, ENOMEM },
124 { ZZIP_ENOENT, ENOENT },
125 # ifdef EPFNOSUPPORT
126 { ZZIP_UNSUPP_COMPR, EPFNOSUPPORT },
127 # else
128 { ZZIP_UNSUPP_COMPR, EACCES },
129 # endif
130 # ifdef EILSEQ
131 { ZZIP_CORRUPTED, EILSEQ },
132 # else
133 { ZZIP_CORRUPTED, ELOOP },
134 # endif
135 { ZZIP_UNDEF, EINVAL },
136 { 0, 0 },
137 };
138 /* *INDENT-ON* */
139
140 /**
141 * map the error code to a system error code. This is used
142 * for the drop-in replacement functions to return a value
143 * that can be interpreted correctly by code sections that
144 * are unaware of the fact they their => open(2) call had been
145 * diverted to a file inside a zip-archive.
146 */
147 int
zzip_errno(int errcode)148 zzip_errno(int errcode)
149 {
150 if (errcode >= -1)
151 {
152 return errno;
153 } else
154 {
155 struct errnolistentry *err = errnolist;
156
157 for (; err->code; err++)
158 {
159 if (err->code == errcode)
160 return err->e_no;
161 }
162 return EINVAL;
163 }
164 }
165
166 /*
167 * Local variables:
168 * c-file-style: "stroustrup"
169 * End:
170 */
171