mirror of
https://github.com/ruby/ruby.git
synced 2022-11-09 12:17:21 -05:00
* dir.c (glob_helper): get rid of possible memory leak.
* win32/win32.c (cmdglob, rb_w32_cmdvector, rb_w32_opendir, rb_w32_get_environ): not to use GC before initialization. [ruby-core:09024] git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/branches/ruby_1_8@11245 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
This commit is contained in:
parent
53f01519ab
commit
d630684687
3 changed files with 110 additions and 32 deletions
|
|
@ -1,3 +1,10 @@
|
||||||
|
Mon Oct 30 23:22:43 2006 Nobuyoshi Nakada <nobu@ruby-lang.org>
|
||||||
|
|
||||||
|
* dir.c (glob_helper): get rid of possible memory leak.
|
||||||
|
|
||||||
|
* win32/win32.c (cmdglob, rb_w32_cmdvector, rb_w32_opendir,
|
||||||
|
rb_w32_get_environ): not to use GC before initialization.
|
||||||
|
|
||||||
Mon Oct 30 19:29:20 2006 NAKAMURA Usaku <usa@ruby-lang.org>
|
Mon Oct 30 19:29:20 2006 NAKAMURA Usaku <usa@ruby-lang.org>
|
||||||
|
|
||||||
* bignum.c (rb_big2str0): use better approximation.
|
* bignum.c (rb_big2str0): use better approximation.
|
||||||
|
|
|
||||||
76
dir.c
76
dir.c
|
|
@ -158,7 +158,7 @@ fnmatch(pat, string, flags)
|
||||||
int period = !(flags & FNM_DOTMATCH);
|
int period = !(flags & FNM_DOTMATCH);
|
||||||
int nocase = flags & FNM_CASEFOLD;
|
int nocase = flags & FNM_CASEFOLD;
|
||||||
|
|
||||||
while (c = *pat++) {
|
while ((c = *pat++) != '\0') {
|
||||||
switch (c) {
|
switch (c) {
|
||||||
case '?':
|
case '?':
|
||||||
if (!*s || ISDIRSEP(*s) || PERIOD(s))
|
if (!*s || ISDIRSEP(*s) || PERIOD(s))
|
||||||
|
|
@ -821,7 +821,12 @@ sys_warning_1(mesg)
|
||||||
|
|
||||||
#define GLOB_VERBOSE (1U << (sizeof(int) * CHAR_BIT - 1))
|
#define GLOB_VERBOSE (1U << (sizeof(int) * CHAR_BIT - 1))
|
||||||
#define sys_warning(val) \
|
#define sys_warning(val) \
|
||||||
((flags & GLOB_VERBOSE) && rb_protect((VALUE (*)_((VALUE)))sys_warning_1, (VALUE)(val), 0))
|
(void)((flags & GLOB_VERBOSE) && rb_protect((VALUE (*)_((VALUE)))sys_warning_1, (VALUE)(val), 0))
|
||||||
|
|
||||||
|
#define GLOB_ALLOC(type) (type *)malloc(sizeof(type))
|
||||||
|
#define GLOB_ALLOC_N(type, n) (type *)malloc(sizeof(type) * (n))
|
||||||
|
#define GLOB_REALLOC_N(var, type, n) (type *)realloc((var), sizeof(type) * (n))
|
||||||
|
#define GLOB_JUMP_TAG(status) ((status == -1) ? rb_memerror() : rb_jump_tag(status))
|
||||||
|
|
||||||
/* Return nonzero if S has any special globbing chars in it. */
|
/* Return nonzero if S has any special globbing chars in it. */
|
||||||
static int
|
static int
|
||||||
|
|
@ -872,7 +877,8 @@ extract_path(p, pend)
|
||||||
int len;
|
int len;
|
||||||
|
|
||||||
len = pend - p;
|
len = pend - p;
|
||||||
alloc = ALLOC_N(char, len+1);
|
alloc = GLOB_ALLOC_N(char, len+1);
|
||||||
|
if (!alloc) return NULL;
|
||||||
memcpy(alloc, p, len);
|
memcpy(alloc, p, len);
|
||||||
if (len > 1 && pend[-1] == '/'
|
if (len > 1 && pend[-1] == '/'
|
||||||
#if defined DOSISH_DRIVE_LETTER
|
#if defined DOSISH_DRIVE_LETTER
|
||||||
|
|
@ -955,6 +961,7 @@ glob_helper(path, sub, flags, func, arg)
|
||||||
int status = 0;
|
int status = 0;
|
||||||
char *buf = 0;
|
char *buf = 0;
|
||||||
char *newpath = 0;
|
char *newpath = 0;
|
||||||
|
char *newbuf;
|
||||||
|
|
||||||
p = sub ? sub : path;
|
p = sub ? sub : path;
|
||||||
if (!has_magic(p, 0, flags)) {
|
if (!has_magic(p, 0, flags)) {
|
||||||
|
|
@ -963,6 +970,7 @@ glob_helper(path, sub, flags, func, arg)
|
||||||
#endif
|
#endif
|
||||||
{
|
{
|
||||||
newpath = strdup(path);
|
newpath = strdup(path);
|
||||||
|
if (!newpath) return -1;
|
||||||
if (sub) {
|
if (sub) {
|
||||||
p = newpath + (sub - path);
|
p = newpath + (sub - path);
|
||||||
remove_backslashes(newpath + (sub - path));
|
remove_backslashes(newpath + (sub - path));
|
||||||
|
|
@ -981,7 +989,7 @@ glob_helper(path, sub, flags, func, arg)
|
||||||
we may want to know what is wrong. */
|
we may want to know what is wrong. */
|
||||||
sys_warning(path);
|
sys_warning(path);
|
||||||
}
|
}
|
||||||
xfree(newpath);
|
if (newpath) free(newpath);
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1000,10 +1008,18 @@ glob_helper(path, sub, flags, func, arg)
|
||||||
} *tmp, *link, **tail = &link;
|
} *tmp, *link, **tail = &link;
|
||||||
|
|
||||||
base = extract_path(path, p);
|
base = extract_path(path, p);
|
||||||
|
if (!base) {
|
||||||
|
status = -1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
if (path == p) dir = ".";
|
if (path == p) dir = ".";
|
||||||
else dir = base;
|
else dir = base;
|
||||||
|
|
||||||
magic = extract_elem(p);
|
magic = extract_elem(p);
|
||||||
|
if (!magic) {
|
||||||
|
status = -1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
if (stat(dir, &st) < 0) {
|
if (stat(dir, &st) < 0) {
|
||||||
if (errno != ENOENT)
|
if (errno != ENOENT)
|
||||||
sys_warning(dir);
|
sys_warning(dir);
|
||||||
|
|
@ -1015,7 +1031,12 @@ glob_helper(path, sub, flags, func, arg)
|
||||||
if (m && strcmp(magic, "**") == 0) {
|
if (m && strcmp(magic, "**") == 0) {
|
||||||
int n = strlen(base);
|
int n = strlen(base);
|
||||||
recursive = 1;
|
recursive = 1;
|
||||||
REALLOC_N(buf, char, n+strlen(m)+3);
|
newbuf = GLOB_REALLOC_N(buf, char, n+strlen(m)+3);
|
||||||
|
if (!newbuf) {
|
||||||
|
status = -1;
|
||||||
|
goto finalize;
|
||||||
|
}
|
||||||
|
buf = newbuf;
|
||||||
sprintf(buf, "%s%s", base, *base ? m : m+1);
|
sprintf(buf, "%s%s", base, *base ? m : m+1);
|
||||||
status = glob_helper(buf, buf+n, flags, func, arg);
|
status = glob_helper(buf, buf+n, flags, func, arg);
|
||||||
if (status) goto finalize;
|
if (status) goto finalize;
|
||||||
|
|
@ -1046,7 +1067,12 @@ glob_helper(path, sub, flags, func, arg)
|
||||||
continue;
|
continue;
|
||||||
if (fnmatch("*", dp->d_name, flags) != 0)
|
if (fnmatch("*", dp->d_name, flags) != 0)
|
||||||
continue;
|
continue;
|
||||||
REALLOC_N(buf, char, strlen(base)+NAMLEN(dp)+strlen(m)+6);
|
newbuf = GLOB_REALLOC_N(buf, char, strlen(base)+NAMLEN(dp)+strlen(m)+6);
|
||||||
|
if (!newbuf) {
|
||||||
|
status = -1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
buf = newbuf;
|
||||||
sprintf(buf, "%s%s%s", base, (BASE) ? "/" : "", dp->d_name);
|
sprintf(buf, "%s%s%s", base, (BASE) ? "/" : "", dp->d_name);
|
||||||
if (lstat(buf, &st) < 0) {
|
if (lstat(buf, &st) < 0) {
|
||||||
if (errno != ENOENT)
|
if (errno != ENOENT)
|
||||||
|
|
@ -1064,14 +1090,23 @@ glob_helper(path, sub, flags, func, arg)
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
if (fnmatch(magic, dp->d_name, flags) == 0) {
|
if (fnmatch(magic, dp->d_name, flags) == 0) {
|
||||||
REALLOC_N(buf, char, strlen(base)+NAMLEN(dp)+2);
|
newbuf = GLOB_REALLOC_N(buf, char, strlen(base)+NAMLEN(dp)+2);
|
||||||
|
if (!newbuf) {
|
||||||
|
status = -1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
buf = newbuf;
|
||||||
sprintf(buf, "%s%s%s", base, (BASE) ? "/" : "", dp->d_name);
|
sprintf(buf, "%s%s%s", base, (BASE) ? "/" : "", dp->d_name);
|
||||||
if (!m) {
|
if (!m) {
|
||||||
status = glob_call_func(func, buf, arg);
|
status = glob_call_func(func, buf, arg);
|
||||||
if (status) break;
|
if (status) break;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
tmp = ALLOC(struct d_link);
|
tmp = GLOB_ALLOC(struct d_link);
|
||||||
|
if (!tmp) {
|
||||||
|
status = -1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
tmp->path = buf;
|
tmp->path = buf;
|
||||||
buf = 0;
|
buf = 0;
|
||||||
*tail = tmp;
|
*tail = tmp;
|
||||||
|
|
@ -1091,7 +1126,12 @@ glob_helper(path, sub, flags, func, arg)
|
||||||
int len = strlen(link->path);
|
int len = strlen(link->path);
|
||||||
int mlen = strlen(m);
|
int mlen = strlen(m);
|
||||||
|
|
||||||
REALLOC_N(buf, char, len+mlen+1);
|
newbuf = GLOB_REALLOC_N(buf, char, len+mlen+1);
|
||||||
|
if (!newbuf) {
|
||||||
|
status = -1;
|
||||||
|
goto next_elem;
|
||||||
|
}
|
||||||
|
buf = newbuf;
|
||||||
sprintf(buf, "%s%s", link->path, m);
|
sprintf(buf, "%s%s", link->path, m);
|
||||||
status = glob_helper(buf, buf+len, flags, func, arg);
|
status = glob_helper(buf, buf+len, flags, func, arg);
|
||||||
}
|
}
|
||||||
|
|
@ -1100,6 +1140,7 @@ glob_helper(path, sub, flags, func, arg)
|
||||||
sys_warning(link->path);
|
sys_warning(link->path);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
next_elem:
|
||||||
tmp = link;
|
tmp = link;
|
||||||
link = link->next;
|
link = link->next;
|
||||||
free(tmp->path);
|
free(tmp->path);
|
||||||
|
|
@ -1110,8 +1151,8 @@ glob_helper(path, sub, flags, func, arg)
|
||||||
}
|
}
|
||||||
p = m;
|
p = m;
|
||||||
}
|
}
|
||||||
xfree(buf);
|
if (buf) free(buf);
|
||||||
xfree(newpath);
|
if (newpath) free(newpath);
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1211,7 +1252,7 @@ push_braces(ary, str, flags)
|
||||||
int flags;
|
int flags;
|
||||||
{
|
{
|
||||||
char *buf = 0;
|
char *buf = 0;
|
||||||
char *b;
|
char *b, *newbuf;
|
||||||
const char *s, *p, *t;
|
const char *s, *p, *t;
|
||||||
const char *lbrace, *rbrace;
|
const char *lbrace, *rbrace;
|
||||||
int nest = 0;
|
int nest = 0;
|
||||||
|
|
@ -1249,7 +1290,12 @@ push_braces(ary, str, flags)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
REALLOC_N(buf, char, len+1);
|
newbuf = GLOB_REALLOC_N(buf, char, len+1);
|
||||||
|
if (!newbuf) {
|
||||||
|
status = -1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
buf = newbuf;
|
||||||
memcpy(buf, s, lbrace-s);
|
memcpy(buf, s, lbrace-s);
|
||||||
b = buf + (lbrace-s);
|
b = buf + (lbrace-s);
|
||||||
memcpy(b, t, p-t);
|
memcpy(b, t, p-t);
|
||||||
|
|
@ -1261,7 +1307,7 @@ push_braces(ary, str, flags)
|
||||||
else {
|
else {
|
||||||
status = push_globs(ary, str, flags);
|
status = push_globs(ary, str, flags);
|
||||||
}
|
}
|
||||||
xfree(buf);
|
if (buf) free(buf);
|
||||||
|
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
|
|
@ -1306,7 +1352,7 @@ rb_push_glob(str, flags)
|
||||||
}
|
}
|
||||||
/* else unmatched braces */
|
/* else unmatched braces */
|
||||||
}
|
}
|
||||||
if (status) rb_jump_tag(status);
|
if (status) GLOB_JUMP_TAG(status);
|
||||||
if (rb_block_given_p()) {
|
if (rb_block_given_p()) {
|
||||||
rb_ary_each(ary);
|
rb_ary_each(ary);
|
||||||
return Qnil;
|
return Qnil;
|
||||||
|
|
|
||||||
|
|
@ -431,7 +431,8 @@ getlogin()
|
||||||
|
|
||||||
if (NTLoginName == NULL) {
|
if (NTLoginName == NULL) {
|
||||||
if (GetUserName(buffer, &len)) {
|
if (GetUserName(buffer, &len)) {
|
||||||
NTLoginName = ALLOC_N(char, len+1);
|
NTLoginName = (char *)malloc(len+1);
|
||||||
|
if (!NTLoginName) return NULL;
|
||||||
strncpy(NTLoginName, buffer, len);
|
strncpy(NTLoginName, buffer, len);
|
||||||
NTLoginName[len] = '\0';
|
NTLoginName[len] = '\0';
|
||||||
}
|
}
|
||||||
|
|
@ -1068,10 +1069,12 @@ insert(const char *path, VALUE vinfo)
|
||||||
NtCmdLineElement *tmpcurr;
|
NtCmdLineElement *tmpcurr;
|
||||||
NtCmdLineElement ***tail = (NtCmdLineElement ***)vinfo;
|
NtCmdLineElement ***tail = (NtCmdLineElement ***)vinfo;
|
||||||
|
|
||||||
tmpcurr = ALLOC(NtCmdLineElement);
|
tmpcurr = (NtCmdLineElement *)malloc(sizeof(NtCmdLineElement));
|
||||||
|
if (!tmpcurr) return -1;
|
||||||
MEMZERO(tmpcurr, NtCmdLineElement, 1);
|
MEMZERO(tmpcurr, NtCmdLineElement, 1);
|
||||||
tmpcurr->len = strlen(path);
|
tmpcurr->len = strlen(path);
|
||||||
tmpcurr->str = ALLOC_N(char, tmpcurr->len + 1);
|
tmpcurr->str = (char *)malloc(tmpcurr->len + 1);
|
||||||
|
if (!tmpcurr->str) return -1;
|
||||||
tmpcurr->flags |= NTMALLOC;
|
tmpcurr->flags |= NTMALLOC;
|
||||||
strcpy(tmpcurr->str, path);
|
strcpy(tmpcurr->str, path);
|
||||||
**tail = tmpcurr;
|
**tail = tmpcurr;
|
||||||
|
|
@ -1093,20 +1096,21 @@ cmdglob(NtCmdLineElement *patt, NtCmdLineElement **tail)
|
||||||
char buffer[MAXPATHLEN], *buf = buffer;
|
char buffer[MAXPATHLEN], *buf = buffer;
|
||||||
char *p;
|
char *p;
|
||||||
NtCmdLineElement **last = tail;
|
NtCmdLineElement **last = tail;
|
||||||
|
int status;
|
||||||
|
|
||||||
if (patt->len >= MAXPATHLEN)
|
if (patt->len >= MAXPATHLEN)
|
||||||
buf = ruby_xmalloc(patt->len + 1);
|
if (!(buf = malloc(patt->len + 1))) return 0;
|
||||||
|
|
||||||
strncpy (buf, patt->str, patt->len);
|
strncpy (buf, patt->str, patt->len);
|
||||||
buf[patt->len] = '\0';
|
buf[patt->len] = '\0';
|
||||||
for (p = buf; *p; p = CharNext(p))
|
for (p = buf; *p; p = CharNext(p))
|
||||||
if (*p == '\\')
|
if (*p == '\\')
|
||||||
*p = '/';
|
*p = '/';
|
||||||
ruby_globi(buf, 0, insert, (VALUE)&tail);
|
status = ruby_globi(buf, 0, insert, (VALUE)&tail);
|
||||||
if (buf != buffer)
|
if (buf != buffer)
|
||||||
free(buf);
|
free(buf);
|
||||||
|
|
||||||
if (last == tail) return 0;
|
if (status || last == tail) return 0;
|
||||||
if (patt->flags & NTMALLOC)
|
if (patt->flags & NTMALLOC)
|
||||||
free(patt->str);
|
free(patt->str);
|
||||||
free(patt);
|
free(patt);
|
||||||
|
|
@ -1333,8 +1337,8 @@ rb_w32_cmdvector(const char *cmd, char ***vec)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
curr = ALLOC(NtCmdLineElement);
|
curr = (NtCmdLineElement *)calloc(sizeof(NtCmdLineElement), 1);
|
||||||
MEMZERO(curr, NtCmdLineElement, 1);
|
if (!curr) goto do_nothing;
|
||||||
curr->str = base;
|
curr->str = base;
|
||||||
curr->len = len;
|
curr->len = len;
|
||||||
|
|
||||||
|
|
@ -1359,7 +1363,18 @@ rb_w32_cmdvector(const char *cmd, char ***vec)
|
||||||
}
|
}
|
||||||
|
|
||||||
len = (elements+1)*sizeof(char *) + strsz;
|
len = (elements+1)*sizeof(char *) + strsz;
|
||||||
buffer = ALLOC_N(char, len);
|
buffer = (char *)malloc(len);
|
||||||
|
if (!buffer) {
|
||||||
|
do_nothing:
|
||||||
|
while (curr = cmdhead) {
|
||||||
|
cmdhead = curr->next;
|
||||||
|
if (curr->flags & NTMALLOC) free(curr->str);
|
||||||
|
free(curr);
|
||||||
|
}
|
||||||
|
free(cmdline);
|
||||||
|
for (vptr = *vec; *vptr; ++vptr);
|
||||||
|
return vptr - *vec;
|
||||||
|
}
|
||||||
|
|
||||||
//
|
//
|
||||||
// make vptr point to the start of the buffer
|
// make vptr point to the start of the buffer
|
||||||
|
|
@ -1456,6 +1471,7 @@ rb_w32_opendir(const char *filename)
|
||||||
fh = FindFirstFile(scanname, &fd);
|
fh = FindFirstFile(scanname, &fd);
|
||||||
if (fh == INVALID_HANDLE_VALUE) {
|
if (fh == INVALID_HANDLE_VALUE) {
|
||||||
errno = map_errno(GetLastError());
|
errno = map_errno(GetLastError());
|
||||||
|
free(p);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1465,7 +1481,13 @@ rb_w32_opendir(const char *filename)
|
||||||
//
|
//
|
||||||
|
|
||||||
idx = strlen(fd.cFileName)+1;
|
idx = strlen(fd.cFileName)+1;
|
||||||
p->start = ALLOC_N(char, idx);
|
if (!(p->start = (char *)malloc(idx))) {
|
||||||
|
error:
|
||||||
|
rb_w32_closedir(p);
|
||||||
|
FindClose(fh);
|
||||||
|
errno = ENOMEM;
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
strcpy(p->start, fd.cFileName);
|
strcpy(p->start, fd.cFileName);
|
||||||
p->nfiles++;
|
p->nfiles++;
|
||||||
|
|
||||||
|
|
@ -1476,6 +1498,8 @@ rb_w32_opendir(const char *filename)
|
||||||
// of the previous string found.
|
// of the previous string found.
|
||||||
//
|
//
|
||||||
while (FindNextFile(fh, &fd)) {
|
while (FindNextFile(fh, &fd)) {
|
||||||
|
char *newpath;
|
||||||
|
|
||||||
len = strlen(fd.cFileName);
|
len = strlen(fd.cFileName);
|
||||||
|
|
||||||
//
|
//
|
||||||
|
|
@ -1483,12 +1507,11 @@ rb_w32_opendir(const char *filename)
|
||||||
// new name and it's null terminator
|
// new name and it's null terminator
|
||||||
//
|
//
|
||||||
|
|
||||||
#define Renew(x, y, z) (x = (z *)xrealloc(x, y))
|
newpath = (char *)realloc(p->start, idx+len+1);
|
||||||
|
if (newpath == NULL) {
|
||||||
Renew (p->start, idx+len+1, char);
|
goto error;
|
||||||
if (p->start == NULL) {
|
|
||||||
rb_fatal ("opendir: malloc failed!\n");
|
|
||||||
}
|
}
|
||||||
|
p->start = newpath;
|
||||||
strcpy(&p->start[idx], fd.cFileName);
|
strcpy(&p->start[idx], fd.cFileName);
|
||||||
p->nfiles++;
|
p->nfiles++;
|
||||||
idx += len+1;
|
idx += len+1;
|
||||||
|
|
@ -3519,10 +3542,12 @@ rb_w32_get_environ(void)
|
||||||
for (env = envtop, num = 0; *env; env += strlen(env) + 1)
|
for (env = envtop, num = 0; *env; env += strlen(env) + 1)
|
||||||
if (*env != '=') num++;
|
if (*env != '=') num++;
|
||||||
|
|
||||||
myenvtop = ALLOC_N(char*, num + 1);
|
myenvtop = (char **)malloc(sizeof(char *) * (num + 1));
|
||||||
for (env = envtop, myenv = myenvtop; *env; env += strlen(env) + 1) {
|
for (env = envtop, myenv = myenvtop; *env; env += strlen(env) + 1) {
|
||||||
if (*env != '=') {
|
if (*env != '=') {
|
||||||
*myenv = ALLOC_N(char, strlen(env) + 1);
|
if (!(*myenv = (char *)malloc(strlen(env) + 1))) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
strcpy(*myenv, env);
|
strcpy(*myenv, env);
|
||||||
myenv++;
|
myenv++;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue