beta-0.89.2
[luatex.git] / source / libs / zziplib / zziplib-0.13.62 / zzip / __dirent.h
blobfc3e08f03d1593f2767f9ba4efd97d4b5d1112ac
1 #ifndef ZZIP_INTERNAL_DIRENT_H
2 #define ZZIP_INTERNAL_DIRENT_H
3 #include <zzip/conf.h>
5 /*
6 * DO NOT USE THIS CODE.
8 * It is an internal header file for zziplib that carries some inline
9 * functions (or just static members) and a few defines, simply to be
10 * able to reuse these across - and have everything in a specific place.
12 * Copyright (c) 2002,2003 Guido Draheim
13 * All rights reserved,
14 * use under the restrictions of the
15 * Lesser GNU General Public License
16 * or alternatively the restrictions
17 * of the Mozilla Public License 1.1
20 #ifdef ZZIP_HAVE_DIRENT_H
21 #define USE_DIRENT 1
23 #define _zzip_opendir opendir
24 #define _zzip_readdir readdir
25 #define _zzip_closedir closedir
26 #define _zzip_rewinddir rewinddir
27 #define _zzip_telldir telldir
28 #define _zzip_seekdir seekdir
29 #define _zzip_DIR DIR
31 #include <dirent.h>
33 #elif defined ZZIP_HAVE_WINBASE_H
34 #define USE_DIRENT 2
36 #define _zzip_opendir win32_opendir
37 #define _zzip_readdir win32_readdir
38 #define _zzip_closedir win32_closedir
39 #define _zzip_rewinddir win32_rewinddir
40 #define _zzip_telldir win32_telldir
41 #define _zzip_seekdir win32_seekdir
42 #define _zzip_DIR DIR
45 * DIRENT.H (formerly DIRLIB.H)
47 * by M. J. Weinstein Released to public domain 1-Jan-89
49 * Because I have heard that this feature (opendir, readdir, closedir)
50 * it so useful for programmers coming from UNIX or attempting to port
51 * UNIX code, and because it is reasonably light weight, I have included
52 * it in the Mingw32 package. I have also added an implementation of
53 * rewinddir, seekdir and telldir.
54 * - Colin Peters <colin@bird.fu.is.saga-u.ac.jp>
56 * This code is distributed in the hope that is will be useful but
57 * WITHOUT ANY WARRANTY. ALL WARRANTIES, EXPRESS OR IMPLIED ARE HEREBY
58 * DISCLAMED. This includeds but is not limited to warranties of
59 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
63 #include <io.h>
65 struct dirent
67 long d_ino; /* Always zero. */
68 unsigned short d_reclen; /* Always zero. */
69 unsigned short d_namlen; /* Length of name in d_name. */
70 char* d_name; /* File name. */
71 /* NOTE: The name in the dirent structure points to the name in the
72 * finddata_t structure in the DIR. */
76 * This is an internal data structure. Good programmers will not use it
77 * except as an argument to one of the functions below.
79 typedef struct
81 /* disk transfer area for this dir */
82 struct _finddata_t dd_dta;
84 /* dirent struct to return from dir (NOTE: this makes this thread
85 * safe as long as only one thread uses a particular DIR struct at
86 * a time) */
87 struct dirent dd_dir;
89 /* _findnext handle */
90 long dd_handle;
93 * Status of search:
94 * 0 = not started yet (next entry to read is first entry)
95 * -1 = off the end
96 * positive = 0 based index of next entry
98 short dd_stat;
100 /* given path for dir with search pattern (struct is extended) */
101 char dd_name[1];
102 } DIR;
105 * dirent.c
107 * Derived from DIRLIB.C by Matt J. Weinstein
108 * This note appears in the DIRLIB.H
109 * DIRLIB.H by M. J. Weinstein Released to public domain 1-Jan-89
111 * Updated by Jeremy Bettis <jeremy@hksys.com>
112 * Significantly revised and rewinddir, seekdir and telldir added by Colin
113 * Peters <colin@fu.is.saga-u.ac.jp>
116 #include <direct.h>
117 #include <errno.h>
118 #include <io.h>
119 #include <stdlib.h>
120 #include <string.h>
121 #include <sys/stat.h>
123 #define win32_SUFFIX "*"
124 #define win32_SLASH "\\"
126 #ifndef S_ISDIR
127 #define S_ISDIR(m) ((m & S_IFMT) == S_IFDIR) /* is a directory */
128 #endif S_ISDIR
132 opendir
134 Returns a pointer to a DIR structure appropriately filled in to begin
135 searching a directory.
137 static DIR*
138 win32_opendir (const char *szPath)
140 DIR *nd;
141 struct _stat statDir;
143 errno = 0;
145 if (!szPath) {
146 errno = EFAULT;
147 return (DIR *) 0;
150 if (szPath[0] == '\0') {
151 errno = ENOTDIR;
152 return (DIR *) 0;
155 /* Attempt to determine if the given path really is a directory. */
156 if (_stat (szPath, &statDir)) {
157 /* Error, stat should have set an error value. */
158 return (DIR *) 0;
161 if (!S_ISDIR (statDir.st_mode)) {
162 /* Error, stat reports not a directory. */
163 errno = ENOTDIR;
164 return (DIR *) 0;
167 /* Allocate enough space to store DIR structure and the complete *
168 directory path given. */
169 nd = (DIR *) calloc (1, sizeof (DIR) + strlen (szPath)
170 + strlen (win32_SLASH) + strlen (win32_SUFFIX));
172 if (!nd) {
173 /* Error, out of memory. */
174 errno = ENOMEM;
175 return (DIR *) 0;
178 /* Create the search expression. */
179 strcpy (nd->dd_name, szPath);
181 /* Add on a slash if the path does not end with one. */
182 if (nd->dd_name[0] != '\0' &&
183 nd->dd_name[strlen (nd->dd_name) - 1] != '/' &&
184 nd->dd_name[strlen (nd->dd_name) - 1] != '\\') {
185 strcat (nd->dd_name, win32_SLASH);
188 /* Add on the search pattern */
189 strcat (nd->dd_name, win32_SUFFIX);
191 /* Initialize handle to -1 so that a premature closedir doesn't try * to
192 call _findclose on it. */
193 nd->dd_handle = -1;
195 /* Initialize the status. */
196 nd->dd_stat = 0;
198 /* Initialize the dirent structure. ino and reclen are invalid under *
199 Win32, and name simply points at the appropriate part of the *
200 findfirst_t structure. */
201 nd->dd_dir.d_ino = 0;
202 nd->dd_dir.d_reclen = 0;
203 nd->dd_dir.d_namlen = 0;
204 nd->dd_dir.d_name = nd->dd_dta.name;
206 return nd;
210 readdir
212 Return a pointer to a dirent structure filled with the information on the
213 next entry in the directory.
215 static struct dirent *
216 win32_readdir (DIR * dirp)
218 errno = 0;
220 /* Check for valid DIR struct. */
221 if (!dirp) {
222 errno = EFAULT;
223 return (struct dirent *) 0;
226 if (dirp->dd_dir.d_name != dirp->dd_dta.name) {
227 /* The structure does not seem to be set up correctly. */
228 errno = EINVAL;
229 return (struct dirent *) 0;
232 if (dirp->dd_stat < 0) {
233 /* We have already returned all files in the directory * (or the
234 structure has an invalid dd_stat). */
235 return (struct dirent *) 0;
236 } else if (dirp->dd_stat == 0) {
237 /* We haven't started the search yet. */
238 /* Start the search */
239 dirp->dd_handle = _findfirst (dirp->dd_name, &(dirp->dd_dta));
241 if (dirp->dd_handle == -1) {
242 /* Whoops! Seems there are no files in that * directory. */
243 dirp->dd_stat = -1;
244 } else {
245 dirp->dd_stat = 1;
247 } else {
248 /* Get the next search entry. */
249 if (_findnext (dirp->dd_handle, &(dirp->dd_dta))) {
250 /* We are off the end or otherwise error. */
251 _findclose (dirp->dd_handle);
252 dirp->dd_handle = -1;
253 dirp->dd_stat = -1;
254 } else {
255 /* Update the status to indicate the correct * number. */
256 dirp->dd_stat++;
260 if (dirp->dd_stat > 0) {
261 /* Successfully got an entry. Everything about the file is * already
262 appropriately filled in except the length of the * file name. */
263 dirp->dd_dir.d_namlen = (unsigned short) strlen (dirp->dd_dir.d_name);
264 return &dirp->dd_dir;
267 return (struct dirent *) 0;
271 closedir
273 Frees up resources allocated by opendir.
275 static int
276 win32_closedir (DIR * dirp)
278 int rc;
280 errno = 0;
281 rc = 0;
283 if (!dirp) {
284 errno = EFAULT;
285 return -1;
288 if (dirp->dd_handle != -1) {
289 rc = _findclose (dirp->dd_handle);
292 /* Delete the dir structure. */
293 free (dirp);
295 return rc;
299 rewinddir
301 Return to the beginning of the directory "stream". We simply call findclose
302 and then reset things like an opendir.
304 static void
305 win32_rewinddir (DIR * dirp)
307 errno = 0;
309 if (!dirp) {
310 errno = EFAULT;
311 return;
314 if (dirp->dd_handle != -1) {
315 _findclose (dirp->dd_handle);
318 dirp->dd_handle = -1;
319 dirp->dd_stat = 0;
323 telldir
325 Returns the "position" in the "directory stream" which can be used with
326 seekdir to go back to an old entry. We simply return the value in stat.
328 static long
329 win32_telldir (DIR * dirp)
331 errno = 0;
333 if (!dirp) {
334 errno = EFAULT;
335 return -1;
337 return dirp->dd_stat;
341 seekdir
343 Seek to an entry previously returned by telldir. We rewind the directory
344 and call readdir repeatedly until either dd_stat is the position number
345 or -1 (off the end). This is not perfect, in that the directory may
346 have changed while we weren't looking. But that is probably the case with
347 any such system.
349 static void
350 win32_seekdir (DIR * dirp, long lPos)
352 errno = 0;
354 if (!dirp) {
355 errno = EFAULT;
356 return;
359 if (lPos < -1) {
360 /* Seeking to an invalid position. */
361 errno = EINVAL;
362 return;
363 } else if (lPos == -1) {
364 /* Seek past end. */
365 if (dirp->dd_handle != -1) {
366 _findclose (dirp->dd_handle);
368 dirp->dd_handle = -1;
369 dirp->dd_stat = -1;
370 } else {
371 /* Rewind and read forward to the appropriate index. */
372 win32_rewinddir (dirp);
374 while ((dirp->dd_stat < lPos) && win32_readdir (dirp));
378 #else
379 #define USE_DIRENT 0
381 #define _zzip_opendir(_N_) 0
382 #define _zzip_readdir(_D_) 0
383 #define _zzip_closedir(_D_) /* omit return code */
384 #define _zzip_rewinddir(_D_)
385 #define _zzip_telldir(_D_) 0
386 #define _zzip_seekdir(_D_,_V_) /* omit return code */
387 #define _zzip_DIR void*
389 /* end of DIRENT implementation */
390 #endif
392 /* once */
393 #endif