VirtualBox

source: kBuild/trunk/src/kmk/w32/compat/dirent.c@ 2591

Last change on this file since 2591 was 2591, checked in by bird, 12 years ago

kmk: Merged in changes from GNU make 3.82. Previous GNU make base version was gnumake-2008-10-28-CVS.

  • Property svn:eol-style set to native
File size: 4.5 KB
Line 
1/* Directory entry code for Window platforms.
2Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005,
32006, 2007, 2008, 2009, 2010 Free Software Foundation, Inc.
4This file is part of GNU Make.
5
6GNU Make is free software; you can redistribute it and/or modify it under the
7terms of the GNU General Public License as published by the Free Software
8Foundation; either version 3 of the License, or (at your option) any later
9version.
10
11GNU Make is distributed in the hope that it will be useful, but WITHOUT ANY
12WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
13A PARTICULAR PURPOSE. See the GNU General Public License for more details.
14
15You should have received a copy of the GNU General Public License along with
16this program. If not, see <http://www.gnu.org/licenses/>. */
17
18
19#include <config.h>
20#include <sys/types.h>
21#include <sys/stat.h>
22#include <errno.h>
23#include <string.h>
24#include <stdlib.h>
25#ifdef KMK_PRF
26# include <stdio.h>
27#endif
28#include "dirent.h"
29
30
31DIR*
32opendir(const char* pDirName)
33{
34 struct stat sb;
35 DIR* pDir;
36 char* pEndDirName;
37 int nBufferLen;
38
39 /* sanity checks */
40 if (!pDirName) {
41 errno = EINVAL;
42 return NULL;
43 }
44 if (stat(pDirName, &sb) != 0) {
45 errno = ENOENT;
46 return NULL;
47 }
48 if ((sb.st_mode & S_IFMT) != S_IFDIR) {
49 errno = ENOTDIR;
50 return NULL;
51 }
52
53 /* allocate a DIR structure to return */
54 pDir = (DIR *) malloc(sizeof (DIR));
55
56 if (!pDir)
57 return NULL;
58
59 /* input directory name length */
60 nBufferLen = strlen(pDirName);
61
62 /* copy input directory name to DIR buffer */
63 strcpy(pDir->dir_pDirectoryName, pDirName);
64
65 /* point to end of the copied directory name */
66 pEndDirName = &pDir->dir_pDirectoryName[nBufferLen - 1];
67
68 /* if directory name did not end in '/' or '\', add '/' */
69 if ((*pEndDirName != '/') && (*pEndDirName != '\\')) {
70 pEndDirName++;
71 *pEndDirName = '/';
72 }
73
74 /* now append the wildcard character to the buffer */
75 pEndDirName++;
76 *pEndDirName = '*';
77 pEndDirName++;
78 *pEndDirName = '\0';
79
80 /* other values defaulted */
81 pDir->dir_nNumFiles = 0;
82 pDir->dir_hDirHandle = INVALID_HANDLE_VALUE;
83 pDir->dir_ulCookie = __DIRENT_COOKIE;
84
85#ifdef KMK_PRF
86 fprintf(stderr, "opendir(%s) -> %p\n", pDirName, pDir);
87#endif
88 return pDir;
89}
90
91void
92closedir(DIR *pDir)
93{
94 /* got a valid pointer? */
95 if (!pDir) {
96 errno = EINVAL;
97 return;
98 }
99
100 /* sanity check that this is a DIR pointer */
101 if (pDir->dir_ulCookie != __DIRENT_COOKIE) {
102 errno = EINVAL;
103 return;
104 }
105
106 /* close the WINDOWS32 directory handle */
107 if (pDir->dir_hDirHandle != INVALID_HANDLE_VALUE)
108 FindClose(pDir->dir_hDirHandle);
109
110 free(pDir);
111
112 return;
113}
114
115struct dirent *
116readdir(DIR* pDir)
117{
118 WIN32_FIND_DATA wfdFindData;
119
120 if (!pDir) {
121 errno = EINVAL;
122 return NULL;
123 }
124
125 /* sanity check that this is a DIR pointer */
126 if (pDir->dir_ulCookie != __DIRENT_COOKIE) {
127 errno = EINVAL;
128 return NULL;
129 }
130
131 if (pDir->dir_nNumFiles == 0) {
132 pDir->dir_hDirHandle = FindFirstFile(pDir->dir_pDirectoryName, &wfdFindData);
133 if (pDir->dir_hDirHandle == INVALID_HANDLE_VALUE)
134 return NULL;
135 } else if (!FindNextFile(pDir->dir_hDirHandle, &wfdFindData))
136 return NULL;
137
138 /* bump count for next call to readdir() or telldir() */
139 pDir->dir_nNumFiles++;
140
141 /* fill in struct dirent values */
142 pDir->dir_sdReturn.d_ino = (ino_t)-1;
143 strcpy(pDir->dir_sdReturn.d_name, wfdFindData.cFileName);
144
145 return &pDir->dir_sdReturn;
146}
147
148void
149rewinddir(DIR* pDir)
150{
151 if (!pDir) {
152 errno = EINVAL;
153 return;
154 }
155
156 /* sanity check that this is a DIR pointer */
157 if (pDir->dir_ulCookie != __DIRENT_COOKIE) {
158 errno = EINVAL;
159 return;
160 }
161
162 /* close the WINDOWS32 directory handle */
163 if (pDir->dir_hDirHandle != INVALID_HANDLE_VALUE)
164 if (!FindClose(pDir->dir_hDirHandle))
165 errno = EBADF;
166
167 /* reset members which control readdir() */
168 pDir->dir_hDirHandle = INVALID_HANDLE_VALUE;
169 pDir->dir_nNumFiles = 0;
170
171 return;
172}
173
174int
175telldir(DIR* pDir)
176{
177 if (!pDir) {
178 errno = EINVAL;
179 return -1;
180 }
181
182 /* sanity check that this is a DIR pointer */
183 if (pDir->dir_ulCookie != __DIRENT_COOKIE) {
184 errno = EINVAL;
185 return -1;
186 }
187
188 /* return number of times readdir() called */
189 return pDir->dir_nNumFiles;
190}
191
192void
193seekdir(DIR* pDir, long nPosition)
194{
195 if (!pDir)
196 return;
197
198 /* sanity check that this is a DIR pointer */
199 if (pDir->dir_ulCookie != __DIRENT_COOKIE)
200 return;
201
202 /* go back to beginning of directory */
203 rewinddir(pDir);
204
205 /* loop until we have found position we care about */
206 for (--nPosition; nPosition && readdir(pDir); nPosition--);
207
208 /* flag invalid nPosition value */
209 if (nPosition)
210 errno = EINVAL;
211
212 return;
213}
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette