[#22109] diffコマンドのオプションは? — Shibukawa Yoshiki <yoshiki@...>
渋川です。
[#22120] invalid parameter to fcntl in drb.rb — siena@... (Siena. / SHINAGAWA, Norihide)
Siena. です。
西山和広です。
Siena. です。
こんにちは、なかむら(う)です。
[#22144] core dump with ObjectSpace.each_object. — Tanaka Akira <akr@...17n.org>
次のように core を吐くことがあります。
まつもと ゆきひろです
なかだです。
[#22167] 1.8.1 preview3 — matz@... (Yukihiro Matsumoto)
まつもと ゆきひろです
In message <1070645035.747201.27874.nullmailer@picachu.netlab.jp>
まつもと ゆきひろです
In message <1070904807.535101.6285.nullmailer@picachu.netlab.jp>
まつもと ゆきひろです
[#22173] iconv map_charset on Solaris — Tanaka Akira <akr@...17n.org>
Solaris で、config.charset を用意しておいても
[#22190] override private methods — Hidetoshi NAGAI <nagai@...>
永井@知能.九工大です.
[#22195] IO::for_io and TCPServer#bind — GOTOU Yuuzou <gotoyuzo@...>
test_drb が IPv4 射影アドレスが有効な環境でないと動かないこ
まつもと ゆきひろです
なかだです。
まつもと ゆきひろです
まつもと ゆきひろです
なかだです。
なかだです。
なかだです。
まつもと ゆきひろです
[#22205] yet another inconsistency about EOF between StringIO and IO — Tanaka Akira <akr@...17n.org>
StringIO の
なかだです。
In article <200312100725.hBA7P8Ac011112@sharui.nakada.kanuma.tochigi.jp>,
なかだです。
In article <200312100917.hBA9HuAc013516@sharui.nakada.kanuma.tochigi.jp>,
さかいといいます。
In article <20031211.214041.71090239.sakai@tom.sfc.keio.ac.jp>,
In article <87k751dzyf.fsf@serein.a02.aist.go.jp>,
まつもと ゆきひろです
In article <1072167374.096702.13473.nullmailer@picachu.netlab.jp>,
まつもと ゆきひろです
In article <1072187210.052832.16566.nullmailer@picachu.netlab.jp>,
[#22235] block to method by proc — nobu.nakada@...
なかだです。
まつもと ゆきひろです
[#22238] errors in test/fileutils — siena@... (Siena. / SHINAGAWA, Norihide)
Siena. です。
[#22251] lib/fileutils.rb — Kazuhiro NISHIYAMA <zn@...>
西山和広です。
[#22289] mswin32 optimize — Tietew <tietew-ml-ruby-dev@...>
Tietew です。
[#22307] "rdoc -r" causes SEGV — akira yamada <akira@...>
まつもと ゆきひろです
[#22330] core dump with ungetc — Tanaka Akira <akr@...17n.org>
次のように ungetc を使うと core を吐く場合があります。
なかだです。
In article <200312230824.hBN8O5kM005374@sharui.nakada.kanuma.tochigi.jp>,
なかだです。
[#22344] pack('N') broken on 64bit platforms — Minero Aoki <aamine@...>
青木です。
[#22356] (OSX) TCPServer.open(hostname, 0) — Masatoshi SEKI <m_seki@...>
咳といいます。
まつもと ゆきひろです
まつもと ゆきひろです
[#22366] `to_s': method `to_s' overridden (TypeError) — Tanaka Akira <akr@...17n.org>
そういえば、次の `to_s': method `to_s' overridden (TypeError) というの
まつもと ゆきひろです
なかだです。
まつもと ゆきひろです
なかだです。
まつもと ゆきひろです
[#22375] win32 thread — matz@... (Yukihiro Matsumoto)
まつもと ゆきひろです
[#22385] Tk.callback_break causes seg-fault or hang-up — Hidetoshi NAGAI <nagai@...>
永井@知能.九工大です.
まつもと ゆきひろです
永井@知能.九工大です.
まつもと ゆきひろです
まつもと ゆきひろです
永井@知能.九工大です.
まつもと ゆきひろです
まつもと ゆきひろです
[#22389] patches for i386-os2-emx — siena@... (Siena. / SHINAGAWA, Norihide)
Siena. です。
[#22403] dlfcn.h on NetBSD — Minero Aoki <aamine@...>
青木です。
[#22418] ruby-1.8.1 build failed on HP-UX 11.11 — MIYAMUKO Katsuyuki <k-miyamuko@...>
みやむこです。
まつもと ゆきひろです
まつもと ゆきひろです
みやむこです。
みやむこです。
なかだです。
みやむこです。
なかだです。
みやむこです。
なかだです。
みやむこです。
なかだです。
みやむこです。
[#22433] ARGF.read(nil) — Tanaka Akira <akr@...17n.org>
というわけで気がついたのですが、
まつもと ゆきひろです
In article <1072453715.631656.23109.nullmailer@picachu.netlab.jp>,
まつもと ゆきひろです
[#22435] Re: [ruby-cvs] ruby: * io.c (rb_f_backquote): need not to check nil result. — Tanaka Akira <akr@...17n.org>
In article <20031226153432.0AF6A45A809@helium.ruby-lang.org>,
[#22469] ARGF.each {|x| ARGF.eof? } and number of Ctrl-Ds. — Tanaka Akira <akr@...17n.org>
次のプログラムは、a^D^D と入力すると終了します。この場合終了には ^D は
[ruby-dev:22441] Re: Dir.glob と Shjift_JIS について
山本です。
[ruby-dev:22303]での
|>これだと、readdir(a)を?magicの時と(child)の列挙のとき2度
|>行っているので、これを1度にできないか考えています。
|と書きましたが、recursiveなほうはlstat()で、そうでないほうはstat()なので、
|単純にまとめるわけにはいきませんでした。
を実装してみました。かなりいじったのでバグの可能性が高まってますが、
自分でテストした限りでは動いているようなのでパッチを送ります。
まずいところがありましたら、指摘してください。
パターンによっては、倍近く高速化しました。
# g: 4787files, 166dirs
# ruby -Ks -e "Dir.glob('g:/**/*'){}"
0:08.458 # [ruby-dev:22431]
0:07.850 # this patch
# ruby -Ks -e "Dir.glob('g:/**/*/'){}"
0:15.303 # [ruby-dev:22431]
0:07.722 # this patch
--- dir.c-22431 Sat Dec 27 23:35:54 2003
+++ dir.c Sat Dec 27 23:30:54 2003
@@ -892,3 +892,3 @@ remove_backslashes(p, pend)
static int
-fnmatch_for_substr(p, pend, string, flags)
+do_fnmatch(p, pend, string, flags)
char *p;
@@ -908,2 +908,34 @@ fnmatch_for_substr(p, pend, string, flag
+static int
+do_stat(path, pst)
+ const char *path;
+ struct stat *pst;
+{
+ int ret = stat(path, pst);
+ if (ret < 0 && errno != ENOENT)
+ rb_sys_warning(path);
+ return ret;
+}
+
+static int
+do_lstat(path, pst)
+ const char *path;
+ struct stat *pst;
+{
+ int ret = lstat(path, pst);
+ if (ret < 0 && errno != ENOENT)
+ rb_sys_warning(path);
+ return ret;
+}
+
+static DIR *
+do_opendir(path)
+ const char *path;
+{
+ DIR *dirp = opendir(path);
+ if (dirp == NULL && errno != ENOENT && errno != ENOTDIR)
+ rb_sys_warning(path);
+ return dirp;
+}
+
#ifndef S_ISDIR
@@ -912,2 +944,10 @@ fnmatch_for_substr(p, pend, string, flag
+#ifndef S_ISLNK
+# ifndef S_IFLNK
+# define S_ISLNK(m) (0)
+# else
+# define S_ISLNK(m) ((m & S_IFMT) == S_IFLNK)
+# endif
+#endif
+
struct glob_args {
@@ -961,5 +1001,6 @@ glob_helper(path, sub, separator, flags,
int recursive = 0;
+ int magical = 1;
struct d_link {
- char *path;
+ char *name;
struct d_link *next;
@@ -985,25 +1026,14 @@ glob_helper(path, sub, separator, flags,
if (*p == '\0') { /* magic not found */
- if (!separator) {
- if (lstat(path, &st) < 0) {
- /* In case stat error is other than ENOENT and
- we may want to know what is wrong. */
- if (errno != ENOENT) rb_sys_warning(path);
- }
- else {
- status = glob_call_func(func, path, arg);
- }
- }
- else {
- const char c = p[-1];
- p[-1] = '\0';
- if (lstat(path, &st) < 0) {
- if (errno != ENOENT) rb_sys_warning(path);
+ if (separator) {
+ char c = p[-1]; p[-1] = '\0';
+ if (do_lstat(path, &st) == 0 && S_ISDIR(st.st_mode)) {
p[-1] = c;
+ return glob_call_func(func, path, arg);
}
- else if (S_ISDIR(st.st_mode)) {
- p[-1] = c;
- status = glob_call_func(func, path, arg);
}
+ else {
+ if (do_lstat(path, &st) == 0)
+ return glob_call_func(func, path, arg);
}
- return status;
+ return 0;
}
@@ -1011,73 +1041,60 @@ glob_helper(path, sub, separator, flags,
if (p[0] == '*' && p[1] == '*' && p[2] == '/') {
- const int n = p - path;
recursive = 1;
- buf = ALLOC_N(char, n+strlen(p+3)+1);
- memcpy(buf, path, n);
- strcpy(buf+n, p+3);
- status = glob_helper(buf, buf+n, separator, flags, func, arg);
- free(buf);
+ memmove(p, p+3, strlen(p+3)+1); /* move '\0' too */
+ magical = has_magic(p, &m, flags); /* go to next element */
+ if (!magical) {
+ status = glob_helper(path, p, separator, flags, func, arg);
if (status) return status;
}
+ }
- {
- char *dir;
if (path == p) {
- dir = ALLOC_N(char, 2);
- dir[0] = '.';
- dir[1] = '\0';
+ dirp = do_opendir(".");
+ if (dirp == NULL) return 0;
}
else {
- const int n = separator ? (p - path) - 1 : (p - path);
- dir = ALLOC_N(char, n+1);
- memcpy(dir, path, n);
- dir[n] = '\0';
- }
- dirp = opendir(dir);
- if (dirp == NULL) {
- if (errno != ENOENT && errno != ENOTDIR) rb_sys_warning(dir);
- free(dir);
- return 0;
- }
- free(dir);
+ char *t = separator ? p-1 : p;
+ char c = *t; *t = '\0';
+ dirp = do_opendir(path);
+ *t = c;
+ if (dirp == NULL) return 0;
}
- for (dp = readdir(dirp); dp != NULL; dp = readdir(dirp)) {
+ for (dp = readdir(dirp); dp != NULL && status == 0; dp = readdir(dirp)) {
+ int notdir = 0;
+ if (recursive && strcmp(".", dp->d_name) != 0 && strcmp("..", dp->d_name) != 0) {
const int n = p - path;
- if (recursive) {
- if (strcmp(".", dp->d_name) == 0 || strcmp("..", dp->d_name) == 0)
- continue;
- buf = ALLOC_N(char, n+NAMLEN(dp)+strlen(m)+3+1);
+ buf = ALLOC_N(char, n+NAMLEN(dp)+1);
memcpy(buf, path, n);
strcpy(buf+n, dp->d_name);
- if (lstat(buf, &st) < 0) {
- if (errno != ENOENT) rb_sys_warning(buf);
- free(buf);
- continue;
- }
+ if (do_lstat(buf, &st) == 0)
if (S_ISDIR(st.st_mode)) {
- char *t = buf+strlen(buf);
- memcpy(t, "/**", 3);
- strcpy(t+3, m);
- status = glob_helper(buf, t+1, 1, flags, func, arg);
- free(buf);
- if (status) break;
- continue;
+ tmp = ALLOC(struct d_link);
+ tmp->name = ALLOC_N(char, NAMLEN(dp)+1);
+ strcpy(tmp->name, dp->d_name);
+ *tail = tmp;
+ tail = &tmp->next;
}
+ else if (!(S_ISLNK(st.st_mode) && do_stat(buf, &st) == 0 && S_ISDIR(st.st_mode)))
+ notdir = 1;
+ else
+ notdir = 1;
free(buf);
- continue;
}
- if (fnmatch_for_substr(p, m, dp->d_name, flags) == 0) {
- buf = ALLOC_N(char, n+NAMLEN(dp)+1);
- memcpy(buf, path, n);
- strcpy(buf+n, dp->d_name);
+ if (notdir && *m == '/')
+ continue;
+ if (magical && do_fnmatch(p, m, dp->d_name, flags) == 0) {
+ const int n1 = p - path;
+ const int n2 = NAMLEN(dp);
+ buf = ALLOC_N(char, n1+n2+strlen(m)+1);
+ memcpy(buf, path, n1);
+ strcpy(buf+n1, dp->d_name);
if (*m == '\0') {
status = glob_call_func(func, buf, arg);
- free(buf);
- if (status) break;
- continue;
}
- tmp = ALLOC(struct d_link);
- tmp->path = buf;
- *tail = tmp;
- tail = &tmp->next;
+ else {
+ strcpy(buf+n1+n2, m);
+ status = glob_helper(buf, buf+n1+n2+1, 1, flags, func, arg);
+ }
+ free(buf);
}
@@ -1088,19 +1105,15 @@ glob_helper(path, sub, separator, flags,
if (status == 0) {
- if (stat(link->path, &st) == 0) {
- if (S_ISDIR(st.st_mode)) {
- const int len = strlen(link->path);
- buf = ALLOC_N(char, len+strlen(m)+1);
- memcpy(buf, link->path, len);
- strcpy(buf+len, m);
- status = glob_helper(buf, buf+len+1, 1, flags, func, arg);
+ const int n1 = p - path;
+ const int n2 = strlen(link->name);
+ buf = ALLOC_N(char, n1+n2+4+strlen(p)+1);
+ memcpy(buf, path, n1);
+ strcpy(buf+n1, link->name);
+ strcpy(buf+n1+n2, "/**/");
+ strcpy(buf+n1+n2+4, p);
+ status = glob_helper(buf, buf+n1+n2+1, 1, flags, func, arg);
free(buf);
}
- }
- else {
- rb_sys_warning(link->path);
- }
- }
tmp = link;
link = link->next;
- free(tmp->path);
+ free(tmp->name);
free(tmp);