summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ChangeLog6
-rw-r--r--eval.c5
-rw-r--r--file.c59
-rw-r--r--lib/debug.rb4
-rw-r--r--object.c3
-rw-r--r--variable.c8
6 files changed, 52 insertions, 33 deletions
diff --git a/ChangeLog b/ChangeLog
index b138cdc72b3..8a0ca195057 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,9 @@
+Mon Feb 4 15:38:29 2002 Yukihiro Matsumoto <matz@ruby-lang.org>
+
+ * object.c (rb_class_real): should not follow ICLASS link
+
+ * variable.c (classname): should follow ICLASS link explicitly.
+
Fri Feb 1 19:10:04 2002 Nobuyoshi Nakada <nobu.nakada@nifty.ne.jp>
* intern.h: prototypes for new functions; rb_cstr_to_inum(),
diff --git a/eval.c b/eval.c
index 576b98b5290..a9b79403b5c 100644
--- a/eval.c
+++ b/eval.c
@@ -1803,7 +1803,7 @@ is_defined(self, node, buf)
case NODE_VCALL:
case NODE_FCALL:
- val = CLASS_OF(self);
+ val = self;
goto check_bound;
case NODE_CALL:
@@ -1811,7 +1811,6 @@ is_defined(self, node, buf)
PUSH_TAG(PROT_NONE);
if ((state = EXEC_TAG()) == 0) {
val = rb_eval(self, node->nd_recv);
- val = CLASS_OF(val);
}
POP_TAG();
if (state) {
@@ -1821,6 +1820,8 @@ is_defined(self, node, buf)
check_bound:
{
int call = nd_type(node)== NODE_CALL;
+
+ val = CLASS_OF(val);
if (call) {
int noex;
ID id = node->nd_mid;
diff --git a/file.c b/file.c
index ddd282c6c9f..b358c526b4d 100644
--- a/file.c
+++ b/file.c
@@ -1377,22 +1377,33 @@ strrdirsep(path)
return last;
}
+#define BUFCHECK(cond) while (cond) {\
+ long bdiff = p - buf;\
+ buflen *= 2;\
+ rb_str_resize(result, buflen);\
+ buf = RSTRING(result)->ptr;\
+ p = buf + bdiff;\
+ pend = buf + buflen;\
+}
+
VALUE
rb_file_s_expand_path(argc, argv)
int argc;
VALUE *argv;
{
- VALUE fname, dname;
- char *s, *p, *b;
- char buf[MAXPATHLEN+2];
- char *bend = buf + sizeof(buf) - 2;
+ VALUE fname, dname, result;
+ char *s, *buf, *b, *p, *pend;
+ long buflen = MAXPATHLEN;
int tainted;
rb_scan_args(argc, argv, "11", &fname, &dname);
+ result = rb_str_new(0, buflen + 2);
- tainted = OBJ_TAINTED(fname);
s = StringValuePtr(fname);
- p = buf;
+ p = buf = RSTRING(result)->ptr;
+ pend = p + buflen;
+ tainted = OBJ_TAINTED(fname);
+
if (s[0] == '~') {
if (isdirsep(s[1]) || s[1] == '\0') {
char *dir = getenv("HOME");
@@ -1400,9 +1411,9 @@ rb_file_s_expand_path(argc, argv)
if (!dir) {
rb_raise(rb_eArgError, "couldn't find HOME environment -- expanding `%s'", s);
}
- if (strlen(dir) > MAXPATHLEN) goto toolong;
+ BUFCHECK (strlen(dir) > buflen);
strcpy(buf, dir);
- p = &buf[strlen(buf)];
+ p = buf + strlen(dir);
s++;
tainted = 1;
}
@@ -1415,7 +1426,7 @@ rb_file_s_expand_path(argc, argv)
while (*s && !isdirsep(*s)) {
s = CharNext(s);
}
- if (p + (s-b) >= bend) goto toolong;
+ BUFCHECK (p + (s-b) >= pend);
memcpy(p, b, s-b);
p += s-b;
*p = '\0';
@@ -1425,9 +1436,9 @@ rb_file_s_expand_path(argc, argv)
endpwent();
rb_raise(rb_eArgError, "user %s doesn't exist", buf);
}
- if (strlen(pwPtr->pw_dir) > MAXPATHLEN) goto toolong;
+ BUFCHECK (strlen(pwPtr->pw_dir) > buflen);
strcpy(buf, pwPtr->pw_dir);
- p = &buf[strlen(buf)];
+ p = buf + strlen(pwPtr->pw_dir);
endpwent();
#endif
}
@@ -1439,7 +1450,7 @@ rb_file_s_expand_path(argc, argv)
while (*s && !isdirsep(*s)) {
s = CharNext(s);
}
- if (p + (s-b) >= bend) goto toolong;
+ BUFCHECK (p + (s-b) >= pend);
memcpy(p, b, s-b);
p += s-b;
}
@@ -1448,12 +1459,15 @@ rb_file_s_expand_path(argc, argv)
if (!NIL_P(dname)) {
dname = rb_file_s_expand_path(1, &dname);
if (OBJ_TAINTED(dname)) tainted = 1;
- if (strlen(RSTRING(dname)->ptr) > MAXPATHLEN) goto toolong;
+ BUFCHECK (strlen(RSTRING(dname)->ptr) > buflen);
strcpy(buf, RSTRING(dname)->ptr);
}
else {
+ char *dir = my_getcwd();
+
tainted = 1;
- getcwd(buf, MAXPATHLEN);
+ BUFCHECK (strlen(dir) > buflen);
+ strcpy(buf, dir);
}
p = &buf[strlen(buf)];
while (p > buf && *(p - 1) == '/') p--;
@@ -1461,7 +1475,7 @@ rb_file_s_expand_path(argc, argv)
else {
while (*s && isdirsep(*s)) {
*p++ = '/';
- if (p >= bend) goto toolong;
+ BUFCHECK (p >= pend);
s++;
}
if (p > buf && *s) p--;
@@ -1507,7 +1521,7 @@ rb_file_s_expand_path(argc, argv)
case '\\':
#endif
if (s > b) {
- if (p + (s-b+1) >= bend) goto toolong;
+ BUFCHECK (p + (s-b+1) >= pend);
memcpy(++p, b, s-b);
p += s-b;
*p = '/';
@@ -1521,7 +1535,7 @@ rb_file_s_expand_path(argc, argv)
}
if (s > b) {
- if (p + (s-b) >= bend) goto toolong;
+ BUFCHECK (p + (s-b) >= pend);
memcpy(++p, b, s-b);
p += s-b;
}
@@ -1539,13 +1553,9 @@ rb_file_s_expand_path(argc, argv)
}
#endif
- fname = rb_str_new(buf, p - buf);
- if (tainted) OBJ_TAINT(fname);
- return fname;
-
- toolong:
- rb_raise(rb_eArgError, "argument too long (size=%d)", RSTRING(fname)->len);
- return Qnil; /* not reached */
+ if (tainted) OBJ_TAINT(result);
+ RSTRING(result)->len = p - buf;
+ return result;
}
static int
@@ -2297,6 +2307,7 @@ path_check_1(path)
for (;;) {
if (stat(p0, &st) == 0 && (st.st_mode & 002)) {
if (p) *p = '/';
+ rb_warn("Bad mode 0%o on %s", st.st_mode, p0);
return 0;
}
s = strrdirsep(p0);
diff --git a/lib/debug.rb b/lib/debug.rb
index 6c4d80e5a79..b9703ed7de3 100644
--- a/lib/debug.rb
+++ b/lib/debug.rb
@@ -450,7 +450,7 @@ class DEBUGGER__
stdout.print "At toplevel\n"
end
binding, binding_file, binding_line = @frames[frame_pos]
- stdout.printf "#%d %s:%s\n", frame_pos, binding_file, binding_line
+ stdout.printf "#%d %s:%s\n", frame_pos+1, binding_file, binding_line
when /^\s*down(?:\s+(\d+))?$/
previous_line = nil
@@ -465,7 +465,7 @@ class DEBUGGER__
stdout.print "At stack bottom\n"
end
binding, binding_file, binding_line = @frames[frame_pos]
- stdout.printf "#%d %s:%s\n", frame_pos, binding_file, binding_line
+ stdout.printf "#%d %s:%s\n", frame_pos+1, binding_file, binding_line
when /^\s*fin(?:ish)?$/
if frame_pos == @frames.size
diff --git a/object.c b/object.c
index 35517e963a9..240a51c3f90 100644
--- a/object.c
+++ b/object.c
@@ -75,9 +75,6 @@ VALUE
rb_class_real(cl)
VALUE cl;
{
- if (TYPE(cl) == T_ICLASS) {
- cl = RBASIC(cl)->klass;
- }
while (FL_TEST(cl, FL_SINGLETON) || TYPE(cl) == T_ICLASS) {
cl = RCLASS(cl)->super;
}
diff --git a/variable.c b/variable.c
index b44ea009ed8..1c7a2601e07 100644
--- a/variable.c
+++ b/variable.c
@@ -145,6 +145,10 @@ classname(klass)
VALUE path = Qnil;
ID classpath = rb_intern("__classpath__");
+ if (TYPE(klass) == T_ICLASS) {
+ klass = RBASIC(klass)->klass;
+ }
+ klass = rb_class_real(klass);
if (!klass) klass = rb_cObject;
if (ROBJECT(klass)->iv_tbl &&
!st_lookup(ROBJECT(klass)->iv_tbl, classpath, &path)) {
@@ -172,7 +176,7 @@ VALUE
rb_mod_name(mod)
VALUE mod;
{
- VALUE path = classname(rb_class_real(mod));
+ VALUE path = classname(mod);
if (path) return rb_str_dup(path);
return rb_str_new(0,0);
@@ -182,7 +186,7 @@ VALUE
rb_class_path(klass)
VALUE klass;
{
- VALUE path = classname(rb_class_real(klass));
+ VALUE path = classname(klass);
if (path) return path;
else {