author | Ryan C. Gordon <icculus@icculus.org> |
Sun, 14 Feb 2010 23:07:19 -0500 | |
changeset 1052 | f87b0b7cca8e |
parent 1016 | 957c97389257 |
child 1053 | a277a93ac1aa |
permissions | -rw-r--r-- |
235 | 1 |
/* |
2 |
* Posix-esque support routines for PhysicsFS. |
|
3 |
* |
|
809
116b8fe30371
Renamed LICENSE to LICENSE.txt
Ryan C. Gordon <icculus@icculus.org>
parents:
808
diff
changeset
|
4 |
* Please see the file LICENSE.txt in the source's root directory. |
235 | 5 |
* |
6 |
* This file written by Ryan C. Gordon. |
|
7 |
*/ |
|
8 |
||
818
e36f23f49042
Now compiles everything whether we need it or not, removing whole files with
Ryan C. Gordon <icculus@icculus.org>
parents:
809
diff
changeset
|
9 |
#define __PHYSICSFS_INTERNAL__ |
e36f23f49042
Now compiles everything whether we need it or not, removing whole files with
Ryan C. Gordon <icculus@icculus.org>
parents:
809
diff
changeset
|
10 |
#include "physfs_platforms.h" |
e36f23f49042
Now compiles everything whether we need it or not, removing whole files with
Ryan C. Gordon <icculus@icculus.org>
parents:
809
diff
changeset
|
11 |
|
e36f23f49042
Now compiles everything whether we need it or not, removing whole files with
Ryan C. Gordon <icculus@icculus.org>
parents:
809
diff
changeset
|
12 |
#ifdef PHYSFS_PLATFORM_POSIX |
310
f8bca4a93fd5
Patched to compile on Cygwin.
Ryan C. Gordon <icculus@icculus.org>
parents:
292
diff
changeset
|
13 |
|
235 | 14 |
#include <stdio.h> |
15 |
#include <stdlib.h> |
|
16 |
#include <string.h> |
|
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
17 |
#include <unistd.h> |
235 | 18 |
#include <ctype.h> |
19 |
#include <sys/types.h> |
|
20 |
#include <sys/stat.h> |
|
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
21 |
#include <pwd.h> |
235 | 22 |
#include <dirent.h> |
23 |
#include <errno.h> |
|
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
24 |
#include <fcntl.h> |
235 | 25 |
|
259
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
26 |
#ifdef PHYSFS_HAVE_LLSEEK |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
27 |
#include <linux/unistd.h> |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
28 |
#endif |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
29 |
|
235 | 30 |
#include "physfs_internal.h" |
31 |
||
32 |
||
847
5e5e6c067413
Split out Mac OS X code from unix.c and added some Carbon-specific code...
Ryan C. Gordon <icculus@icculus.org>
parents:
845
diff
changeset
|
33 |
const char *__PHYSFS_platformDirSeparator = "/"; |
5e5e6c067413
Split out Mac OS X code from unix.c and added some Carbon-specific code...
Ryan C. Gordon <icculus@icculus.org>
parents:
845
diff
changeset
|
34 |
|
5e5e6c067413
Split out Mac OS X code from unix.c and added some Carbon-specific code...
Ryan C. Gordon <icculus@icculus.org>
parents:
845
diff
changeset
|
35 |
|
235 | 36 |
char *__PHYSFS_platformCopyEnvironmentVariable(const char *varname) |
37 |
{ |
|
38 |
const char *envr = getenv(varname); |
|
39 |
char *retval = NULL; |
|
40 |
||
41 |
if (envr != NULL) |
|
42 |
{ |
|
691
71d9affe0d8a
All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents:
657
diff
changeset
|
43 |
retval = (char *) allocator.Malloc(strlen(envr) + 1); |
235 | 44 |
if (retval != NULL) |
45 |
strcpy(retval, envr); |
|
46 |
} /* if */ |
|
47 |
||
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
48 |
return retval; |
235 | 49 |
} /* __PHYSFS_platformCopyEnvironmentVariable */ |
50 |
||
51 |
||
52 |
static char *getUserNameByUID(void) |
|
53 |
{ |
|
54 |
uid_t uid = getuid(); |
|
55 |
struct passwd *pw; |
|
56 |
char *retval = NULL; |
|
57 |
||
58 |
pw = getpwuid(uid); |
|
59 |
if ((pw != NULL) && (pw->pw_name != NULL)) |
|
60 |
{ |
|
691
71d9affe0d8a
All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents:
657
diff
changeset
|
61 |
retval = (char *) allocator.Malloc(strlen(pw->pw_name) + 1); |
235 | 62 |
if (retval != NULL) |
63 |
strcpy(retval, pw->pw_name); |
|
64 |
} /* if */ |
|
65 |
||
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
66 |
return retval; |
235 | 67 |
} /* getUserNameByUID */ |
68 |
||
69 |
||
70 |
static char *getUserDirByUID(void) |
|
71 |
{ |
|
72 |
uid_t uid = getuid(); |
|
73 |
struct passwd *pw; |
|
74 |
char *retval = NULL; |
|
75 |
||
76 |
pw = getpwuid(uid); |
|
77 |
if ((pw != NULL) && (pw->pw_dir != NULL)) |
|
78 |
{ |
|
691
71d9affe0d8a
All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents:
657
diff
changeset
|
79 |
retval = (char *) allocator.Malloc(strlen(pw->pw_dir) + 1); |
235 | 80 |
if (retval != NULL) |
81 |
strcpy(retval, pw->pw_dir); |
|
82 |
} /* if */ |
|
83 |
||
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
84 |
return retval; |
235 | 85 |
} /* getUserDirByUID */ |
86 |
||
87 |
||
88 |
char *__PHYSFS_platformGetUserName(void) |
|
89 |
{ |
|
90 |
char *retval = getUserNameByUID(); |
|
91 |
if (retval == NULL) |
|
92 |
retval = __PHYSFS_platformCopyEnvironmentVariable("USER"); |
|
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
93 |
return retval; |
235 | 94 |
} /* __PHYSFS_platformGetUserName */ |
95 |
||
96 |
||
97 |
char *__PHYSFS_platformGetUserDir(void) |
|
98 |
{ |
|
99 |
char *retval = __PHYSFS_platformCopyEnvironmentVariable("HOME"); |
|
100 |
if (retval == NULL) |
|
101 |
retval = getUserDirByUID(); |
|
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
102 |
return retval; |
235 | 103 |
} /* __PHYSFS_platformGetUserDir */ |
104 |
||
105 |
||
106 |
int __PHYSFS_platformExists(const char *fname) |
|
107 |
{ |
|
108 |
struct stat statbuf; |
|
832
adef86dfc331
Removed the strict-ANSI crap.
Ryan C. Gordon <icculus@icculus.org>
parents:
828
diff
changeset
|
109 |
BAIL_IF_MACRO(lstat(fname, &statbuf) == -1, strerror(errno), 0); |
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
110 |
return 1; |
235 | 111 |
} /* __PHYSFS_platformExists */ |
112 |
||
113 |
||
114 |
int __PHYSFS_platformIsSymLink(const char *fname) |
|
115 |
{ |
|
116 |
struct stat statbuf; |
|
467
99664d9842cb
Bunch of tedious corrections, optimizations, and cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
429
diff
changeset
|
117 |
BAIL_IF_MACRO(lstat(fname, &statbuf) == -1, strerror(errno), 0); |
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
118 |
return ( (S_ISLNK(statbuf.st_mode)) ? 1 : 0 ); |
235 | 119 |
} /* __PHYSFS_platformIsSymlink */ |
120 |
||
121 |
||
122 |
int __PHYSFS_platformIsDirectory(const char *fname) |
|
123 |
{ |
|
124 |
struct stat statbuf; |
|
467
99664d9842cb
Bunch of tedious corrections, optimizations, and cleanups.
Ryan C. Gordon <icculus@icculus.org>
parents:
429
diff
changeset
|
125 |
BAIL_IF_MACRO(stat(fname, &statbuf) == -1, strerror(errno), 0); |
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
126 |
return ( (S_ISDIR(statbuf.st_mode)) ? 1 : 0 ); |
235 | 127 |
} /* __PHYSFS_platformIsDirectory */ |
128 |
||
129 |
||
1052
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
130 |
int __PHYSFS_platformStat(const char *fname, PHYSFS_Stat *st) |
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
131 |
{ |
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
132 |
int retval = 0; |
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
133 |
struct stat pstat; |
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
134 |
|
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
135 |
/* !!! FIXME: lstat()? */ |
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
136 |
retval = stat(fname, &pstat); |
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
137 |
if (retval == 0) |
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
138 |
{ |
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
139 |
st->size = pstat.st_size; |
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
140 |
st->mtime = pstat.st_mtime; |
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
141 |
st->atime = pstat.st_atime; |
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
142 |
st->ctime = pstat.st_ctime; |
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
143 |
st->is_symlink = S_ISLNK(pstat.st_mode) ? 1 : 0; |
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
144 |
st->is_dir = S_ISDIR(pstat.st_mode) ? 1 : 0; |
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
145 |
} /* if */ |
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
146 |
|
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
147 |
return(retval); |
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
148 |
} /* __PHYSFS_platformStat */ |
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
149 |
|
f87b0b7cca8e
Added first work on PHYSFS_stat() API (thanks, Christoph!).
Ryan C. Gordon <icculus@icculus.org>
parents:
1016
diff
changeset
|
150 |
|
235 | 151 |
char *__PHYSFS_platformCvtToDependent(const char *prepend, |
152 |
const char *dirName, |
|
153 |
const char *append) |
|
154 |
{ |
|
155 |
int len = ((prepend) ? strlen(prepend) : 0) + |
|
156 |
((append) ? strlen(append) : 0) + |
|
157 |
strlen(dirName) + 1; |
|
691
71d9affe0d8a
All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents:
657
diff
changeset
|
158 |
char *retval = (char *) allocator.Malloc(len); |
235 | 159 |
|
160 |
BAIL_IF_MACRO(retval == NULL, ERR_OUT_OF_MEMORY, NULL); |
|
161 |
||
162 |
/* platform-independent notation is Unix-style already. :) */ |
|
163 |
||
164 |
if (prepend) |
|
165 |
strcpy(retval, prepend); |
|
166 |
else |
|
167 |
retval[0] = '\0'; |
|
168 |
||
169 |
strcat(retval, dirName); |
|
170 |
||
171 |
if (append) |
|
172 |
strcat(retval, append); |
|
173 |
||
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
174 |
return retval; |
235 | 175 |
} /* __PHYSFS_platformCvtToDependent */ |
176 |
||
177 |
||
178 |
||
657
dad3b5c307a9
Added callback APIs and ripped up the internals everywhere to use them.
Ryan C. Gordon <icculus@icculus.org>
parents:
648
diff
changeset
|
179 |
void __PHYSFS_platformEnumerateFiles(const char *dirname, |
dad3b5c307a9
Added callback APIs and ripped up the internals everywhere to use them.
Ryan C. Gordon <icculus@icculus.org>
parents:
648
diff
changeset
|
180 |
int omitSymLinks, |
754
e7cd7411eadf
API BREAKAGE: Changed PHYSFS_enumerateFilesCallback() to pass the originally
Ryan C. Gordon <icculus@icculus.org>
parents:
747
diff
changeset
|
181 |
PHYSFS_EnumFilesCallback callback, |
e7cd7411eadf
API BREAKAGE: Changed PHYSFS_enumerateFilesCallback() to pass the originally
Ryan C. Gordon <icculus@icculus.org>
parents:
747
diff
changeset
|
182 |
const char *origdir, |
657
dad3b5c307a9
Added callback APIs and ripped up the internals everywhere to use them.
Ryan C. Gordon <icculus@icculus.org>
parents:
648
diff
changeset
|
183 |
void *callbackdata) |
235 | 184 |
{ |
185 |
DIR *dir; |
|
186 |
struct dirent *ent; |
|
187 |
int bufsize = 0; |
|
188 |
char *buf = NULL; |
|
189 |
int dlen = 0; |
|
190 |
||
657
dad3b5c307a9
Added callback APIs and ripped up the internals everywhere to use them.
Ryan C. Gordon <icculus@icculus.org>
parents:
648
diff
changeset
|
191 |
if (omitSymLinks) /* !!! FIXME: this malloc sucks. */ |
235 | 192 |
{ |
193 |
dlen = strlen(dirname); |
|
194 |
bufsize = dlen + 256; |
|
691
71d9affe0d8a
All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents:
657
diff
changeset
|
195 |
buf = (char *) allocator.Malloc(bufsize); |
657
dad3b5c307a9
Added callback APIs and ripped up the internals everywhere to use them.
Ryan C. Gordon <icculus@icculus.org>
parents:
648
diff
changeset
|
196 |
if (buf == NULL) |
dad3b5c307a9
Added callback APIs and ripped up the internals everywhere to use them.
Ryan C. Gordon <icculus@icculus.org>
parents:
648
diff
changeset
|
197 |
return; |
235 | 198 |
strcpy(buf, dirname); |
199 |
if (buf[dlen - 1] != '/') |
|
200 |
{ |
|
201 |
buf[dlen++] = '/'; |
|
202 |
buf[dlen] = '\0'; |
|
203 |
} /* if */ |
|
204 |
} /* if */ |
|
205 |
||
206 |
errno = 0; |
|
207 |
dir = opendir(dirname); |
|
208 |
if (dir == NULL) |
|
209 |
{ |
|
852
9467e96abdf1
Replaced some Malloc and all the alloca() calls with __PHYSFS_smallAlloc(),
Ryan C. Gordon <icculus@icculus.org>
parents:
847
diff
changeset
|
210 |
allocator.Free(buf); |
657
dad3b5c307a9
Added callback APIs and ripped up the internals everywhere to use them.
Ryan C. Gordon <icculus@icculus.org>
parents:
648
diff
changeset
|
211 |
return; |
235 | 212 |
} /* if */ |
213 |
||
362
ac8c846a0a66
Changed enumeration code to use __PHYSFS_addToLinkedStringList().
Ryan C. Gordon <icculus@icculus.org>
parents:
310
diff
changeset
|
214 |
while ((ent = readdir(dir)) != NULL) |
235 | 215 |
{ |
216 |
if (strcmp(ent->d_name, ".") == 0) |
|
217 |
continue; |
|
218 |
||
219 |
if (strcmp(ent->d_name, "..") == 0) |
|
220 |
continue; |
|
221 |
||
222 |
if (omitSymLinks) |
|
223 |
{ |
|
224 |
char *p; |
|
225 |
int len = strlen(ent->d_name) + dlen + 1; |
|
226 |
if (len > bufsize) |
|
227 |
{ |
|
691
71d9affe0d8a
All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents:
657
diff
changeset
|
228 |
p = (char *) allocator.Realloc(buf, len); |
235 | 229 |
if (p == NULL) |
230 |
continue; |
|
231 |
buf = p; |
|
232 |
bufsize = len; |
|
233 |
} /* if */ |
|
234 |
||
235 |
strcpy(buf + dlen, ent->d_name); |
|
236 |
if (__PHYSFS_platformIsSymLink(buf)) |
|
237 |
continue; |
|
238 |
} /* if */ |
|
239 |
||
754
e7cd7411eadf
API BREAKAGE: Changed PHYSFS_enumerateFilesCallback() to pass the originally
Ryan C. Gordon <icculus@icculus.org>
parents:
747
diff
changeset
|
240 |
callback(callbackdata, origdir, ent->d_name); |
235 | 241 |
} /* while */ |
242 |
||
852
9467e96abdf1
Replaced some Malloc and all the alloca() calls with __PHYSFS_smallAlloc(),
Ryan C. Gordon <icculus@icculus.org>
parents:
847
diff
changeset
|
243 |
allocator.Free(buf); |
235 | 244 |
closedir(dir); |
245 |
} /* __PHYSFS_platformEnumerateFiles */ |
|
246 |
||
247 |
||
248 |
int __PHYSFS_platformMkDir(const char *path) |
|
249 |
{ |
|
250 |
int rc; |
|
251 |
errno = 0; |
|
252 |
rc = mkdir(path, S_IRWXU); |
|
253 |
BAIL_IF_MACRO(rc == -1, strerror(errno), 0); |
|
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
254 |
return 1; |
235 | 255 |
} /* __PHYSFS_platformMkDir */ |
256 |
||
257 |
||
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
258 |
static void *doOpen(const char *filename, int mode) |
235 | 259 |
{ |
939
684c583cb586
Fixed PHYSFS_openAppend() on Unix.
Ryan C. Gordon <icculus@icculus.org>
parents:
852
diff
changeset
|
260 |
const int appending = (mode & O_APPEND); |
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
261 |
int fd; |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
262 |
int *retval; |
235 | 263 |
errno = 0; |
264 |
||
939
684c583cb586
Fixed PHYSFS_openAppend() on Unix.
Ryan C. Gordon <icculus@icculus.org>
parents:
852
diff
changeset
|
265 |
/* O_APPEND doesn't actually behave as we'd like. */ |
684c583cb586
Fixed PHYSFS_openAppend() on Unix.
Ryan C. Gordon <icculus@icculus.org>
parents:
852
diff
changeset
|
266 |
mode &= ~O_APPEND; |
684c583cb586
Fixed PHYSFS_openAppend() on Unix.
Ryan C. Gordon <icculus@icculus.org>
parents:
852
diff
changeset
|
267 |
|
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
268 |
fd = open(filename, mode, S_IRUSR | S_IWUSR); |
292
99bf6ef5639a
Patched a bug where doOpen() reported success when the file couldn't be
Ryan C. Gordon <icculus@icculus.org>
parents:
259
diff
changeset
|
269 |
BAIL_IF_MACRO(fd < 0, strerror(errno), NULL); |
235 | 270 |
|
939
684c583cb586
Fixed PHYSFS_openAppend() on Unix.
Ryan C. Gordon <icculus@icculus.org>
parents:
852
diff
changeset
|
271 |
if (appending) |
684c583cb586
Fixed PHYSFS_openAppend() on Unix.
Ryan C. Gordon <icculus@icculus.org>
parents:
852
diff
changeset
|
272 |
{ |
684c583cb586
Fixed PHYSFS_openAppend() on Unix.
Ryan C. Gordon <icculus@icculus.org>
parents:
852
diff
changeset
|
273 |
if (lseek(fd, 0, SEEK_END) < 0) |
684c583cb586
Fixed PHYSFS_openAppend() on Unix.
Ryan C. Gordon <icculus@icculus.org>
parents:
852
diff
changeset
|
274 |
{ |
684c583cb586
Fixed PHYSFS_openAppend() on Unix.
Ryan C. Gordon <icculus@icculus.org>
parents:
852
diff
changeset
|
275 |
close(fd); |
684c583cb586
Fixed PHYSFS_openAppend() on Unix.
Ryan C. Gordon <icculus@icculus.org>
parents:
852
diff
changeset
|
276 |
BAIL_MACRO(strerror(errno), NULL); |
684c583cb586
Fixed PHYSFS_openAppend() on Unix.
Ryan C. Gordon <icculus@icculus.org>
parents:
852
diff
changeset
|
277 |
} /* if */ |
684c583cb586
Fixed PHYSFS_openAppend() on Unix.
Ryan C. Gordon <icculus@icculus.org>
parents:
852
diff
changeset
|
278 |
} /* if */ |
684c583cb586
Fixed PHYSFS_openAppend() on Unix.
Ryan C. Gordon <icculus@icculus.org>
parents:
852
diff
changeset
|
279 |
|
691
71d9affe0d8a
All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents:
657
diff
changeset
|
280 |
retval = (int *) allocator.Malloc(sizeof (int)); |
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
281 |
if (retval == NULL) |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
282 |
{ |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
283 |
close(fd); |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
284 |
BAIL_MACRO(ERR_OUT_OF_MEMORY, NULL); |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
285 |
} /* if */ |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
286 |
|
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
287 |
*retval = fd; |
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
288 |
return ((void *) retval); |
235 | 289 |
} /* doOpen */ |
290 |
||
291 |
||
292 |
void *__PHYSFS_platformOpenRead(const char *filename) |
|
293 |
{ |
|
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
294 |
return doOpen(filename, O_RDONLY); |
235 | 295 |
} /* __PHYSFS_platformOpenRead */ |
296 |
||
297 |
||
298 |
void *__PHYSFS_platformOpenWrite(const char *filename) |
|
299 |
{ |
|
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
300 |
return doOpen(filename, O_WRONLY | O_CREAT | O_TRUNC); |
235 | 301 |
} /* __PHYSFS_platformOpenWrite */ |
302 |
||
303 |
||
304 |
void *__PHYSFS_platformOpenAppend(const char *filename) |
|
305 |
{ |
|
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
306 |
return doOpen(filename, O_WRONLY | O_CREAT | O_APPEND); |
235 | 307 |
} /* __PHYSFS_platformOpenAppend */ |
308 |
||
309 |
||
310 |
PHYSFS_sint64 __PHYSFS_platformRead(void *opaque, void *buffer, |
|
311 |
PHYSFS_uint32 size, PHYSFS_uint32 count) |
|
312 |
{ |
|
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
313 |
int fd = *((int *) opaque); |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
314 |
int max = size * count; |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
315 |
int rc = read(fd, buffer, max); |
235 | 316 |
|
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
317 |
BAIL_IF_MACRO(rc == -1, strerror(errno), rc); |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
318 |
assert(rc <= max); |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
319 |
|
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
320 |
if ((rc < max) && (size > 1)) |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
321 |
lseek(fd, -(rc % size), SEEK_CUR); /* rollback to object boundary. */ |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
322 |
|
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
323 |
return (rc / size); |
235 | 324 |
} /* __PHYSFS_platformRead */ |
325 |
||
326 |
||
327 |
PHYSFS_sint64 __PHYSFS_platformWrite(void *opaque, const void *buffer, |
|
328 |
PHYSFS_uint32 size, PHYSFS_uint32 count) |
|
329 |
{ |
|
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
330 |
int fd = *((int *) opaque); |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
331 |
int max = size * count; |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
332 |
int rc = write(fd, (void *) buffer, max); |
235 | 333 |
|
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
334 |
BAIL_IF_MACRO(rc == -1, strerror(errno), rc); |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
335 |
assert(rc <= max); |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
336 |
|
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
337 |
if ((rc < max) && (size > 1)) |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
338 |
lseek(fd, -(rc % size), SEEK_CUR); /* rollback to object boundary. */ |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
339 |
|
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
340 |
return (rc / size); |
235 | 341 |
} /* __PHYSFS_platformWrite */ |
342 |
||
343 |
||
344 |
int __PHYSFS_platformSeek(void *opaque, PHYSFS_uint64 pos) |
|
345 |
{ |
|
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
346 |
int fd = *((int *) opaque); |
235 | 347 |
|
259
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
348 |
#ifdef PHYSFS_HAVE_LLSEEK |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
349 |
unsigned long offset_high = ((pos >> 32) & 0xFFFFFFFF); |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
350 |
unsigned long offset_low = (pos & 0xFFFFFFFF); |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
351 |
loff_t retoffset; |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
352 |
int rc = llseek(fd, offset_high, offset_low, &retoffset, SEEK_SET); |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
353 |
BAIL_IF_MACRO(rc == -1, strerror(errno), 0); |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
354 |
#else |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
355 |
BAIL_IF_MACRO(lseek(fd, (int) pos, SEEK_SET) == -1, strerror(errno), 0); |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
356 |
#endif |
235 | 357 |
|
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
358 |
return 1; |
235 | 359 |
} /* __PHYSFS_platformSeek */ |
360 |
||
361 |
||
362 |
PHYSFS_sint64 __PHYSFS_platformTell(void *opaque) |
|
363 |
{ |
|
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
364 |
int fd = *((int *) opaque); |
259
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
365 |
PHYSFS_sint64 retval; |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
366 |
|
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
367 |
#ifdef PHYSFS_HAVE_LLSEEK |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
368 |
loff_t retoffset; |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
369 |
int rc = llseek(fd, 0, &retoffset, SEEK_CUR); |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
370 |
BAIL_IF_MACRO(rc == -1, strerror(errno), -1); |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
371 |
retval = (PHYSFS_sint64) retoffset; |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
372 |
#else |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
373 |
retval = (PHYSFS_sint64) lseek(fd, 0, SEEK_CUR); |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
374 |
BAIL_IF_MACRO(retval == -1, strerror(errno), -1); |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
375 |
#endif |
bd65a0d74e9a
64-bit _llseek() support for the future.
Ryan C. Gordon <icculus@icculus.org>
parents:
255
diff
changeset
|
376 |
|
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
377 |
return retval; |
235 | 378 |
} /* __PHYSFS_platformTell */ |
379 |
||
380 |
||
381 |
PHYSFS_sint64 __PHYSFS_platformFileLength(void *opaque) |
|
382 |
{ |
|
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
383 |
int fd = *((int *) opaque); |
235 | 384 |
struct stat statbuf; |
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
385 |
BAIL_IF_MACRO(fstat(fd, &statbuf) == -1, strerror(errno), -1); |
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
386 |
return ((PHYSFS_sint64) statbuf.st_size); |
235 | 387 |
} /* __PHYSFS_platformFileLength */ |
388 |
||
389 |
||
390 |
int __PHYSFS_platformEOF(void *opaque) |
|
391 |
{ |
|
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
392 |
PHYSFS_sint64 pos = __PHYSFS_platformTell(opaque); |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
393 |
PHYSFS_sint64 len = __PHYSFS_platformFileLength(opaque); |
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
394 |
return (pos >= len); |
235 | 395 |
} /* __PHYSFS_platformEOF */ |
396 |
||
397 |
||
398 |
int __PHYSFS_platformFlush(void *opaque) |
|
399 |
{ |
|
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
400 |
int fd = *((int *) opaque); |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
401 |
BAIL_IF_MACRO(fsync(fd) == -1, strerror(errno), 0); |
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
402 |
return 1; |
235 | 403 |
} /* __PHYSFS_platformFlush */ |
404 |
||
405 |
||
406 |
int __PHYSFS_platformClose(void *opaque) |
|
407 |
{ |
|
251
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
408 |
int fd = *((int *) opaque); |
0f4615263e32
Actual POSIX calls to replace ANSI stdio routines.
Ryan C. Gordon <icculus@icculus.org>
parents:
249
diff
changeset
|
409 |
BAIL_IF_MACRO(close(fd) == -1, strerror(errno), 0); |
691
71d9affe0d8a
All memory management now goes through allocation hooks instead of directly to
Ryan C. Gordon <icculus@icculus.org>
parents:
657
diff
changeset
|
410 |
allocator.Free(opaque); |
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
411 |
return 1; |
235 | 412 |
} /* __PHYSFS_platformClose */ |
413 |
||
414 |
||
415 |
int __PHYSFS_platformDelete(const char *path) |
|
416 |
{ |
|
417 |
BAIL_IF_MACRO(remove(path) == -1, strerror(errno), 0); |
|
1016
957c97389257
Cleaned up returns that look like function calls for my updated coding style.
Ryan C. Gordon <icculus@icculus.org>
parents:
972
diff
changeset
|
418 |
return 1; |
235 | 419 |
} /* __PHYSFS_platformDelete */ |
420 |
||
240
052041af9001
Added PHYSFS_getLastModTime() API. (Thanks, John Hall!)
Ryan C. Gordon <icculus@icculus.org>
parents:
235
diff
changeset
|
421 |
|
052041af9001
Added PHYSFS_getLastModTime() API. (Thanks, John Hall!)
Ryan C. Gordon <icculus@icculus.org>
parents:
235
diff
changeset
|
422 |
PHYSFS_sint64 __PHYSFS_platformGetLastModTime(const char *fname) |
052041af9001
Added PHYSFS_getLastModTime() API. (Thanks, John Hall!)
Ryan C. Gordon <icculus@icculus.org>
parents:
235
diff
changeset
|
423 |
{ |
052041af9001
Added PHYSFS_getLastModTime() API. (Thanks, John Hall!)
Ryan C. Gordon <icculus@icculus.org>
parents:
235
diff
changeset
|
424 |
struct stat statbuf; |
052041af9001
Added PHYSFS_getLastModTime() API. (Thanks, John Hall!)
Ryan C. Gordon <icculus@icculus.org>
parents:
235
diff
changeset
|
425 |
BAIL_IF_MACRO(stat(fname, &statbuf) < 0, strerror(errno), -1); |
052041af9001
Added PHYSFS_getLastModTime() API. (Thanks, John Hall!)
Ryan C. Gordon <icculus@icculus.org>
parents:
235
diff
changeset
|
426 |
return statbuf.st_mtime; |
052041af9001
Added PHYSFS_getLastModTime() API. (Thanks, John Hall!)
Ryan C. Gordon <icculus@icculus.org>
parents:
235
diff
changeset
|
427 |
} /* __PHYSFS_platformGetLastModTime */ |
052041af9001
Added PHYSFS_getLastModTime() API. (Thanks, John Hall!)
Ryan C. Gordon <icculus@icculus.org>
parents:
235
diff
changeset
|
428 |
|
818
e36f23f49042
Now compiles everything whether we need it or not, removing whole files with
Ryan C. Gordon <icculus@icculus.org>
parents:
809
diff
changeset
|
429 |
#endif /* PHYSFS_PLATFORM_POSIX */ |
310
f8bca4a93fd5
Patched to compile on Cygwin.
Ryan C. Gordon <icculus@icculus.org>
parents:
292
diff
changeset
|
430 |
|
235 | 431 |
/* end of posix.c ... */ |
432 |