[#22815] File.fnmatch が "*?" のパターンを正しく処理しない? — "H.Yamamoto" <ocean@...2.ccsnet.ne.jp>
山本です。
山本です。
山本です。
山本です。補足します。
なかだです。
山本です。
山本です。
まつもと ゆきひろです
[#22816] YAML.load(time) on OpenBSD3.4 — "Kawaji, Shinya" <kawaji@...>
かわじ、です
In article <20040207005319=tuYR!@hoppeta.com>,
かわじ、です。
[#22832] Dir.glob("**/") のバグ — "H.Yamamoto" <ocean@...2.ccsnet.ne.jp>
山本です。
[#22859] Re: io/nonblock — nobu.nakada@...
なかだです。
[#22862] File.fnmatch と Dir.glob — "H.Yamamoto" <ocean@...2.ccsnet.ne.jp>
山本です。
まつもと ゆきひろです
山本です。
山本です。誤記がありました。
まつもと ゆきひろです
山本です。
山本です。
まつもと ゆきひろです
山本です。
まつもと ゆきひろです
山本です。
山本です。
まつもと ゆきひろです
山本です。
まつもと ゆきひろです
山本です。
山本です。
まつもと ゆきひろです
山本です。
まつもと ゆきひろです
まつもと ゆきひろです
わたなべです。
山本です。
山本です。
山本です。
山本です。
山本です。
山本です。
山本です。
山本です。
山本です。
山本です。
まつもと ゆきひろです
山本です。
まつもと ゆきひろです
山本です。
山本です。
山本です。
山本です。
山本です。
山本です。
まつもと ゆきひろです
山本です。
まつもと ゆきひろです
山本です。
山本です。
山本です。
山本です。
山本です。
山本です。
山本です。
山本です。
まつもと ゆきひろです
山本です。
なかだです。
山本です。
なかだです。
山本です。
なかだです。
山本です。
[#22870] path for RUBY — GOTOU Yuuzou <gotoyuzo@...>
mkmf.rbでMakefileを作ると、$(RUBY)にディレクトリ名が含まれな
[#22877] Process.spawn & IO.popen w/o shell — nobu.nakada@...
なかだです。
まつもと ゆきひろです
なかだです。
まつもと ゆきひろです
なかだです。
まつもと ゆきひろです
なかだです。
まつもと ゆきひろです
なかだです。
まつもと ゆきひろです
In message <200402141156.i1EBuYFH018029@sharui.nakada.niregi.kanuma.tochigi.jp>
なかだです。
In message <200402160353.i1G3rGNK007935@sharui.nakada.niregi.kanuma.tochigi.jp>
なかだです。
[#22890] rb_glob(i) & constness — "H.Yamamoto" <ocean@...2.ccsnet.ne.jp>
山本です。
In article <20040215161805.6541D650.ocean@m2.ccsnet.ne.jp>,
[#22906] bcc32 の makefile — "H.Yamamoto" <ocean@...2.ccsnet.ne.jp>
山本です。
なかだです。
山本です。
山本です。
[#22911] core dump with /#{Thread.pass}/o — Tanaka Akira <akr@...17n.org>
ついに捕まえたのですが、次のようにすると core を吐きます。
[#22928] [BUG] make distclean が失敗する — "H.Yamamoto" <ocean@...2.ccsnet.ne.jp>
山本です。
山本です。
山本です。
こんにちは、なかむら(う)です。
山本です。
こんにちは、なかむら(う)です。
山本です。
なかだです。
山本です。
山本です。
こんにちは、なかむら(う)です。
山本です。
山本です。
山本です。
こんにちは、なかむら(う)です。
山本です。
こんにちは、なかむら(う)です。
山本です。
山本です。
こんにちは、なかむら(う)です。
山本です。
山本です。
こんにちは、なかむら(う)です。
山本です。
山本です。
こんにちは、なかむら(う)です。
[#22956] Dir#glob proposal — nobu.nakada@...
なかだです。
まつもと ゆきひろです
なかだです。
山本です。
山本です。
[#23032] Re: [Oniguruma] Version 2.2.0 — kkosako@...
> -----Original Message-----
斉藤です。
まつもと ゆきひろです
[#23035] Re: [ruby-talk:93584] date/format.rb fix — "NAKAMURA, Hiroshi" <nakahiro@...>
なひです。
[#23038] Re: [ruby-cvs] ruby: * eval.c (localjump_destination): lambda should not interfere — nobu.nakada@...
なかだです。
まつもと ゆきひろです
なかだです。
まつもと ゆきひろです
なかだです。
[#23039] rss/dublincore.rb: dc:date format — "NAKAMURA, Hiroshi" <nakahiro@...>
なひです。
[ruby-dev:22815] File.fnmatch が "*?" のパターンを正しく処理しない?
山本です。
File.fnmatch で、* のあとに ? が続く場合のマッチが正しくないようなので、
修正してみました。File.fnmatch は把握しきれてないのですが、こんな感じで
いいでしょうか?
# 修正前
E:\ruby-cvs\ruby>..\miniruby -ve "puts File.fnmatch('*?', 'a')"
ruby 1.9.0 (2004-01-31) [i386-bccwin32]
false
# 修正後
E:\ruby-cvs\ruby>miniruby -ve "puts File.fnmatch('*?', 'a')"
ruby 1.9.0 (2004-01-31) [i386-bccwin32]
true
fnmatch 以外の部分は、コメントの修正とか、見栄えの修正とかです。
動作にはまったく影響ありません。
cvs diff -u -wb -p dir.c (in directory E:\ruby-cvs\ruby\)
Index: dir.c
===================================================================
RCS file: /ruby/ruby/dir.c,v
retrieving revision 1.100
diff -u -w -b -p -r1.100 dir.c
--- dir.c 29 Jan 2004 11:59:55 -0000 1.100
+++ dir.c 6 Feb 2004 15:30:10 -0000
@@ -267,7 +267,7 @@ fnmatch(pat, string, flags)
test = escape && c == '\\' ? pat+1 : pat;
while (*s) {
- if ((c == '[' || Compare(s, test) == 0) &&
+ if ((c == '?' || c == '[' || Compare(s, test) == 0) &&
!fnmatch(pat, s, flags | FNM_DOTMATCH))
return 0;
else if (ISDIRSEP(*s))
@@ -884,6 +884,7 @@ do_stat(path, pst)
int ret = stat(path, pst);
if (ret < 0 && errno != ENOENT)
rb_sys_warning(path);
+
return ret;
}
@@ -895,6 +896,7 @@ do_lstat(path, pst)
int ret = lstat(path, pst);
if (ret < 0 && errno != ENOENT)
rb_sys_warning(path);
+
return ret;
}
@@ -905,6 +907,7 @@ do_opendir(path)
DIR *dirp = opendir(path);
if (dirp == NULL && errno != ENOENT && errno != ENOTDIR)
rb_sys_warning(path);
+
return dirp;
}
@@ -971,7 +974,13 @@ remove_backslashes(p)
}
/* Globing pattern */
-enum glob_pattern_type { PLAIN, MAGICAL, RECURSIVE, MATCH_ALL, MATCH_DIR };
+enum glob_pattern_type {
+ PLAIN,
+ MAGICAL,
+ RECURSIVE,
+ MATCH_ALL,
+ MATCH_DIR
+};
struct glob_pattern {
char *str;
@@ -985,13 +994,14 @@ glob_make_pattern(p, flags)
int flags;
{
char *buf;
- int dirsep = 0; /* pattern terminates with '/' */
+ int dirsep = 0;
struct glob_pattern *list, *tmp, **tail = &list;
while (*p) {
tmp = ALLOC(struct glob_pattern);
if (p[0] == '*' && p[1] == '*' && p[2] == '/') {
- do { p += 3; } while (p[0] == '*' && p[1] == '*' && p[2] == '/'); /* fold continuous RECURSIVEs */
+ /* fold continuous recursive patterns */
+ do { p += 3; } while (p[0] == '*' && p[1] == '*' && p[2] == '/');
tmp->type = RECURSIVE;
tmp->str = 0;
dirsep = 1;
@@ -1046,7 +1056,6 @@ join_path(path, dirsep, name)
const char *name;
{
const int len = strlen(path);
-
char *buf = ALLOC_N(char, len+1+strlen(name)+1);
strcpy(buf, path);
if (dirsep) {
@@ -1056,11 +1065,14 @@ join_path(path, dirsep, name)
else {
strcpy(buf+len, name);
}
-
return buf;
}
-enum answer { YES, NO, UNKNOWN };
+enum answer {
+ YES,
+ NO,
+ UNKNOWN
+};
#ifndef S_ISDIR
# define S_ISDIR(m) ((m & S_IFMT) == S_IFDIR)
@@ -1111,9 +1123,9 @@ glob_call_func(func, path, arg)
static int
glob_helper(path, dirsep, exist, isdir, beg, end, flags, func, arg)
const char *path;
- int dirsep; /* '/' should be placed before appending child entry's name to 'path'. */
- enum answer exist; /* exist? */
- enum answer isdir; /* a directory or a symlink to a directory? */
+ int dirsep; /* '/' is needed before appending name to 'path' */
+ enum answer exist; /* Does 'path' indicates an existing entry? */
+ enum answer isdir; /* Does 'path' indicates a directory or a symlink to a directory? */
struct glob_pattern **beg;
struct glob_pattern **end;
int flags;
@@ -1121,24 +1133,23 @@ glob_helper(path, dirsep, exist, isdir,
VALUE arg;
{
struct stat st;
- int status = 0;
struct glob_pattern **cur, **new_beg, **new_end;
- int recursive = 0, need_readdir = 0, need_plain = 0, match_all = 0, match_dir = 0;
- const int escape = !(flags & FNM_NOESCAPE);
+ int plain = 0, magical = 0, recursive = 0, match_all = 0, match_dir = 0;
+ int status = 0;
+ int escape = !(flags & FNM_NOESCAPE);
for (cur = beg; cur < end; ++cur) {
struct glob_pattern *p = *cur;
if (p->type == RECURSIVE) {
recursive = 1;
- need_readdir = 1;
p = p->next;
}
switch (p->type) {
case PLAIN:
- need_plain = 1; /* ignored if need_readdir is set */
+ plain = 1;
break;
case MAGICAL:
- need_readdir = 1;
+ magical = 1;
break;
case MATCH_ALL:
match_all = 1;
@@ -1173,29 +1184,25 @@ glob_helper(path, dirsep, exist, isdir,
if (match_all && exist == YES) {
status = glob_call_func(func, path, arg);
+ if (status) return status;
}
if (match_dir && isdir == YES) {
char *buf = join_path(path, dirsep, "");
status = glob_call_func(func, buf, arg);
free(buf);
- }
-
if (status) return status;
+ }
if (exist == NO || isdir == NO) return 0;
- if (need_readdir) {
-
+ if (magical || recursive) {
struct dirent *dp;
-
DIR *dirp = do_opendir(*path ? path : ".");
if (dirp == NULL) return 0;
for (dp = readdir(dirp); dp != NULL; dp = readdir(dirp)) {
-
char *buf = join_path(path, dirsep, dp->d_name);
-
enum answer new_isdir = UNKNOWN;
if (recursive && strcmp(dp->d_name, ".") != 0 && strcmp(dp->d_name, "..") != 0) {
@@ -1213,13 +1220,11 @@ glob_helper(path, dirsep, exist, isdir,
for (cur = beg; cur < end; ++cur) {
struct glob_pattern *p = *cur;
-
if (p->type == RECURSIVE) {
if (new_isdir == YES) /* not symlink but real directory */
*new_end++ = p; /* append recursive pattern */
p = p->next; /* 0 times recursion */
}
-
if (p->type == PLAIN || p->type == MAGICAL) {
if (fnmatch(p->str, dp->d_name, flags) == 0)
*new_end++ = p->next;
@@ -1236,8 +1241,7 @@ glob_helper(path, dirsep, exist, isdir,
closedir(dirp);
}
- else if (need_plain) {
-
+ else if (plain) {
struct glob_pattern **copy_beg, **copy_end, **cur2;
copy_beg = copy_end = ALLOC_N(struct glob_pattern *, end - beg);
@@ -1246,11 +1250,8 @@ glob_helper(path, dirsep, exist, isdir,
*copy_end++ = (*cur)->type == PLAIN ? *cur : 0;
for (cur = copy_beg; cur < copy_end; ++cur) {
-
if (*cur) {
-
- char *buf, *name;
-
+ char *name, *buf;
name = ALLOC_N(char, strlen((*cur)->str) + 1);
strcpy(name, (*cur)->str);
if (escape) remove_backslashes(name);
@@ -1258,7 +1259,6 @@ glob_helper(path, dirsep, exist, isdir,
new_beg = new_end = ALLOC_N(struct glob_pattern *, end - beg);
*new_end++ = (*cur)->next;
-
for (cur2 = cur + 1; cur2 < copy_end; ++cur2) {
if (*cur2 && fnmatch((*cur2)->str, name, flags) == 0) {
*new_end++ = (*cur2)->next;
@@ -1276,7 +1276,6 @@ glob_helper(path, dirsep, exist, isdir,
if (status) break;
}
-
}
free(copy_beg);