aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNiteHawk <n1tehawk@users.noreply.github.com>2016-10-15 00:46:54 +0200
committerHisham Muhammad <hisham@gobolinux.org>2016-10-14 15:46:54 -0700
commit3c4e563d9c140319e28c419f2710b51a2f6d6d24 (patch)
tree440c52e0185f080ae4ba5af05d8dea615ba25d30
parent50919ed69ff64df51d8d586d00834fde3e901785 (diff)
downloadluafilesystem-3c4e563d9c140319e28c419f2710b51a2f6d6d24.tar.gz
luafilesystem-3c4e563d9c140319e28c419f2710b51a2f6d6d24.tar.bz2
luafilesystem-3c4e563d9c140319e28c419f2710b51a2f6d6d24.zip
Dynamically size getcwd() buffer in get_dir function (#84)
* Dynamically size getcwd() buffer in get_dir function This should fix issue 42. * Fixup: Properly respect NO_GETCWD * Fixup: Get rid of getcwd_error, handle NO_GETCWD in a single place
-rw-r--r--src/lfs.c87
1 files changed, 46 insertions, 41 deletions
diff --git a/src/lfs.c b/src/lfs.c
index 8154a46..25122a3 100644
--- a/src/lfs.c
+++ b/src/lfs.c
@@ -41,22 +41,26 @@
41#include <sys/stat.h> 41#include <sys/stat.h>
42 42
43#ifdef _WIN32 43#ifdef _WIN32
44#include <direct.h> 44 #include <direct.h>
45#include <windows.h> 45 #include <windows.h>
46#include <io.h> 46 #include <io.h>
47#include <sys/locking.h> 47 #include <sys/locking.h>
48#ifdef __BORLANDC__ 48 #ifdef __BORLANDC__
49 #include <utime.h> 49 #include <utime.h>
50#else 50 #else
51 #include <sys/utime.h> 51 #include <sys/utime.h>
52#endif 52 #endif
53#include <fcntl.h> 53 #include <fcntl.h>
54 /* MAX_PATH seems to be 260. Seems kind of small. Is there a better one? */
55 #define LFS_MAXPATHLEN MAX_PATH
54#else 56#else
55#include <unistd.h> 57 #include <unistd.h>
56#include <dirent.h> 58 #include <dirent.h>
57#include <fcntl.h> 59 #include <fcntl.h>
58#include <sys/types.h> 60 #include <sys/types.h>
59#include <utime.h> 61 #include <utime.h>
62 #include <sys/param.h> /* for MAXPATHLEN */
63 #define LFS_MAXPATHLEN MAXPATHLEN
60#endif 64#endif
61 65
62#include <lua.h> 66#include <lua.h>
@@ -85,22 +89,6 @@
85#define strerror(_) "System unable to describe the error" 89#define strerror(_) "System unable to describe the error"
86#endif 90#endif
87 91
88/* Define 'getcwd' for systems that do not implement it */
89#ifdef NO_GETCWD
90#define getcwd(p,s) NULL
91#define getcwd_error "Function 'getcwd' not provided by system"
92#else
93#define getcwd_error strerror(errno)
94 #ifdef _WIN32
95 /* MAX_PATH seems to be 260. Seems kind of small. Is there a better one? */
96 #define LFS_MAXPATHLEN MAX_PATH
97 #else
98 /* For MAXPATHLEN: */
99 #include <sys/param.h>
100 #define LFS_MAXPATHLEN MAXPATHLEN
101 #endif
102#endif
103
104#define DIR_METATABLE "directory metatable" 92#define DIR_METATABLE "directory metatable"
105typedef struct dir_data { 93typedef struct dir_data {
106 int closed; 94 int closed;
@@ -178,18 +166,35 @@ static int change_dir (lua_State *L) {
178** and a string describing the error 166** and a string describing the error
179*/ 167*/
180static int get_dir (lua_State *L) { 168static int get_dir (lua_State *L) {
181 char *path; 169#ifdef NO_GETCWD
182 /* Passing (NULL, 0) is not guaranteed to work. Use a temp buffer and size instead. */
183 char buf[LFS_MAXPATHLEN];
184 if ((path = getcwd(buf, LFS_MAXPATHLEN)) == NULL) {
185 lua_pushnil(L); 170 lua_pushnil(L);
186 lua_pushstring(L, getcwd_error); 171 lua_pushstring(L, "Function 'getcwd' not provided by system");
187 return 2; 172 return 2;
188 } 173#else
189 else { 174 char *path = NULL;
190 lua_pushstring(L, path); 175 /* Passing (NULL, 0) is not guaranteed to work. Use a temp buffer and size instead. */
191 return 1; 176 size_t size = LFS_MAXPATHLEN; /* initial buffer size */
192 } 177 int result;
178 while (1) {
179 path = realloc(path, size);
180 if (!path) /* failed to allocate */
181 return pusherror(L, "get_dir realloc() failed");
182 if (getcwd(path, size) != NULL) {
183 /* success, push the path to the Lua stack */
184 lua_pushstring(L, path);
185 result = 1;
186 break;
187 }
188 if (errno != ERANGE) { /* unexpected error */
189 result = pusherror(L, "get_dir getcwd() failed");
190 break;
191 }
192 /* ERANGE = insufficient buffer capacity, double size and retry */
193 size *= 2;
194 }
195 free(path);
196 return result;
197#endif
193} 198}
194 199
195/* 200/*