1
0
Fork 0
mirror of https://github.com/ruby/ruby.git synced 2022-11-09 12:17:21 -05:00

flock,flatten,signal to main_thread

git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/branches/v1_1r@168 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
This commit is contained in:
matz 1998-04-16 07:42:49 +00:00
parent e004116073
commit 94a1bece4a
14 changed files with 242 additions and 122 deletions

View file

@ -1,3 +1,33 @@
Thu Apr 16 01:38:02 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
* array.c (ary_flatten): new method.
* eval.c (rb_longjmp): prints exception information with `-d'.
* object.c (any_to_s): remove class name restriction.
* file.c (thread_flock): do not block other threads.
* eval.c (thread_trap_eval): signals are now delivered to the
current thread again. In case that the current thread is dead,
signals are forwarded to the main thread.
* string.c (str_new4): need not to duplicate frozen strings.
Wed Apr 15 01:22:56 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
* string.c (str_dup_frozen): do not duplicate frozen strings.
* parse.y (yylex): allow nested parenthesises.
* io.c (obj_displayln): prints newline after `display'ing the
receiver.
* io.c (io_puts): avoid generating "\n" each time. use RS_default
instead.
* io.c (f_p): ditto.
Tue Apr 14 11:34:50 1998 Yukihiro Matsumoto <matz@netlab.co.jp>
* experimental release 1.1b9_10.

40
array.c
View file

@ -1234,6 +1234,44 @@ ary_nitems(ary)
return INT2FIX(n);
}
static VALUE
ary_flatten_bang(ary)
VALUE ary;
{
int i;
int mod = 0;
ary_modify(ary);
for (;;) {
int lmod = 0;
for (i=0; i<RARRAY(ary)->len; i++) {
if (TYPE(RARRAY(ary)->ptr[i]) == T_ARRAY) {
VALUE ary2 = RARRAY(ary)->ptr[i];
ary_replace(ary, i, RARRAY(ary2)->len, ary2);
i += RARRAY(ary2)->len - 1;
lmod++;
}
}
if (lmod == 0) break;
mod = lmod;
}
if (mod == 0) return Qnil;
return ary;
}
static VALUE
ary_flatten(ary)
VALUE ary;
{
VALUE v = ary_flatten_bang(ary_clone(ary));
if (NIL_P(v)) return ary;
return v;
}
extern VALUE mEnumerable;
void
@ -1304,6 +1342,8 @@ Init_Array()
rb_define_method(cArray, "uniq!", ary_uniq_bang, 0);
rb_define_method(cArray, "compact", ary_compact, 0);
rb_define_method(cArray, "compact!", ary_compact_bang, 0);
rb_define_method(cArray, "flatten", ary_flatten, 0);
rb_define_method(cArray, "flatten!", ary_flatten_bang, 0);
rb_define_method(cArray, "nitems", ary_nitems, 0);
cmp = rb_intern("<=>");

2
dir.c
View file

@ -413,7 +413,7 @@ dir_foreach(io, dirname)
{
VALUE dir;
dir = dir_s_open(cDir, dirname);
dir = rb_funcall(cDir, rb_intern("open"), 1, dirname);
return rb_ensure(dir_each, dir, dir_close, dir);
}

29
eval.c
View file

@ -727,17 +727,8 @@ error_print()
if (NIL_P(errinfo)) return;
if (!NIL_P(errat)) {
VALUE mesg = Qnil;
VALUE mesg = RARRAY(errat)->ptr[0];
switch (TYPE(errat)) {
case T_STRING:
mesg = errat;
errat = Qnil;
break;
case T_ARRAY:
mesg = RARRAY(errat)->ptr[0];
break;
}
if (NIL_P(mesg)) error_pos();
else {
fwrite(RSTRING(mesg)->ptr, 1, RSTRING(mesg)->len, stderr);
@ -2681,7 +2672,13 @@ rb_longjmp(tag, mesg, at)
if (NIL_P(errinfo) && NIL_P(mesg)) {
errinfo = exc_new(eRuntimeError, 0, 0);
}
#if 1
if (debug) {
fprintf(stderr, "Exception `%s' occurred at %s:%d\n",
rb_class2name(CLASS_OF(errinfo)),
sourcefile, sourceline);
}
#endif
if (!NIL_P(at)) {
errat = check_errat(at);
}
@ -2698,6 +2695,11 @@ rb_longjmp(tag, mesg, at)
}
str_freeze(errinfo);
}
#if 0
if (debug) {
error_print();
}
#endif
trap_restore_mask();
JUMP_TAG(tag);
@ -6272,11 +6274,12 @@ thread_trap_eval(cmd, sig)
int sig;
{
thread_critical = 0;
thread_ready(main_thread);
if (curr_thread == main_thread) {
if (!thread_dead(curr_thread)) {
thread_ready(curr_thread);
rb_trap_eval(cmd, sig);
return;
}
thread_ready(main_thread);
thread_save_context(curr_thread);
if (setjmp(curr_thread->context)) {
return;

47
file.c
View file

@ -189,7 +189,7 @@ file_tell(obj)
GetOpenFile(obj, fptr);
pos = ftell(fptr->f);
if (ferror(fptr->f) != 0) rb_sys_fail(0);
if (ferror(fptr->f) != 0) rb_sys_fail(fptr->path);
return int2inum(pos);
}
@ -203,10 +203,10 @@ file_seek(obj, offset, ptrname)
GetOpenFile(obj, fptr);
pos = fseek(fptr->f, NUM2INT(offset), NUM2INT(ptrname));
if (pos != 0) rb_sys_fail(0);
if (pos != 0) rb_sys_fail(fptr->path);
clearerr(fptr->f);
return obj;
return INT2FIX(0);
}
static VALUE
@ -218,10 +218,10 @@ file_set_pos(obj, offset)
GetOpenFile(obj, fptr);
pos = fseek(fptr->f, NUM2INT(offset), 0);
if (pos != 0) rb_sys_fail(0);
if (pos != 0) rb_sys_fail(fptr->path);
clearerr(fptr->f);
return obj;
return INT2NUM(pos);
}
static VALUE
@ -231,10 +231,10 @@ file_rewind(obj)
OpenFile *fptr;
GetOpenFile(obj, fptr);
if (fseek(fptr->f, 0L, 0) != 0) rb_sys_fail(0);
if (fseek(fptr->f, 0L, 0) != 0) rb_sys_fail(fptr->path);
clearerr(fptr->f);
return obj;
return INT2FIX(0);
}
static VALUE
@ -1100,7 +1100,7 @@ file_s_symlink(obj, from, to)
if (symlink(RSTRING(from)->ptr, RSTRING(to)->ptr) < 0)
rb_sys_fail(RSTRING(from)->ptr);
return TRUE;
return INT2FIX(0);
#else
rb_notimplement();
#endif
@ -1384,7 +1384,7 @@ file_s_truncate(obj, path, len)
rb_notimplement();
# endif
#endif
return TRUE;
return INT2FIX(0);
}
static VALUE
@ -1409,9 +1409,33 @@ file_truncate(obj, len)
rb_notimplement();
# endif
#endif
return TRUE;
return INT2FIX(0);
}
#if defined(THREAD) && defined(EWOULDBLOCK)
static int
thread_flock(fd, op)
int fd, op;
{
if (thread_alone() || (op & LOCK_NB)) {
return flock(fd, op);
}
op |= LOCK_NB;
while (flock(fd, op) < 0) {
switch (errno) {
case EINTR: /* can be happen? */
case EWOULDBLOCK:
thread_schedule(); /* busy wait */
break;
default:
return -1;
}
}
return 0;
}
#define flock thread_flock
#endif
static VALUE
file_flock(obj, operation)
VALUE obj;
@ -1430,8 +1454,9 @@ file_flock(obj, operation)
#endif
rb_sys_fail(fptr->path);
}
return obj;
return INT2FIX(0);
}
#undef flock
static void
test_check(n, argc, argv)

2
hash.c
View file

@ -450,7 +450,7 @@ hash_aset(hash, key, val)
return Qnil;
}
if (TYPE(key) == T_STRING) {
key = str_dup_freezed(key);
key = str_dup_frozen(key);
}
st_insert(RHASH(hash)->tbl, key, val);
return val;

View file

@ -251,7 +251,7 @@ VALUE str_times _((VALUE, VALUE));
VALUE str_substr _((VALUE, int, int));
void str_modify _((VALUE));
VALUE str_freeze _((VALUE));
VALUE str_dup_freezed _((VALUE));
VALUE str_dup_frozen _((VALUE));
VALUE str_taint _((VALUE));
VALUE str_tainted _((VALUE));
VALUE str_resize _((VALUE, int));

63
io.c
View file

@ -820,7 +820,7 @@ io_binmode(io)
fptr->mode |= FMODE_BINMODE;
#endif
return io;
return INT2FIX(0);
}
int
@ -1419,7 +1419,7 @@ io_puts(argc, argv, out)
/* if no argument given, print newline. */
if (argc == 0) {
io_write(out, str_new2("\n"));
io_write(out, RS_default);
return Qnil;
}
for (i=0; i<argc; i++) {
@ -1439,7 +1439,7 @@ io_puts(argc, argv, out)
line = obj_as_string(line);
io_write(out, line);
if (RSTRING(line)->ptr[RSTRING(line)->len-1] != '\n') {
io_write(out, str_new2("\n"));
io_write(out, RS_default);
}
}
@ -1456,20 +1456,11 @@ f_puts(argc, argv)
}
static VALUE
f_p(argc, argv, self)
int argc;
VALUE *argv;
VALUE self;
f_p(self, obj)
VALUE self, obj;
{
VALUE str;
if (argc > 0) {
rb_scan_args(argc, argv, "1", &self);
}
str = rb_inspect(self);
Check_Type(str, T_STRING);
io_write(rb_defout, str);
io_write(rb_defout, str_new2("\n"));
io_write(rb_defout, rb_inspect(obj));
io_write(rb_defout, RS_default);
return Qnil;
}
@ -1478,7 +1469,7 @@ void
rb_p(obj) /* for debug print within C code */
VALUE obj;
{
f_p(0, 0, obj);
f_p(0, obj);
}
static VALUE
@ -1500,6 +1491,26 @@ obj_display(argc, argv, self)
return Qnil;
}
static VALUE
obj_displayln(argc, argv, self)
int argc;
VALUE *argv;
VALUE self;
{
VALUE out;
VALUE str;
rb_scan_args(argc, argv, "01", &out);
if (NIL_P(out)) {
out = rb_defout;
}
io_write(out, self);
io_write(rb_defout, RS_default);
return Qnil;
}
static void
io_defset(val, id)
VALUE val;
@ -1546,15 +1557,15 @@ prep_stdio(f, mode, klass)
VALUE klass;
{
OpenFile *fp;
NEWOBJ(obj, struct RFile);
OBJSETUP(obj, klass, T_FILE);
NEWOBJ(io, struct RFile);
OBJSETUP(io, klass, T_FILE);
MakeOpenFile(obj, fp);
MakeOpenFile(io, fp);
fp->f = f;
fp->mode = mode;
obj_call_init((VALUE)obj);
obj_call_init((VALUE)io);
return (VALUE)obj;
return (VALUE)io;
}
static VALUE
@ -1735,8 +1746,8 @@ f_getc()
}
static VALUE
f_ungetc(obj, c)
VALUE obj, c;
f_ungetc(self, c)
VALUE self, c;
{
if (!next_argv()) {
ArgError("no stream to ungetc");
@ -2423,8 +2434,9 @@ Init_IO()
rb_define_global_function("`", f_backquote, 1);
rb_define_global_function("pipe", io_s_pipe, 0);
rb_define_method(mKernel, "p", f_p, -1);
rb_define_global_function("p", f_p, 1);
rb_define_method(mKernel, "display", obj_display, -1);
rb_define_method(mKernel, "displayln", obj_displayln, -1);
cIO = rb_define_class("IO", cObject);
rb_include_module(cIO, mEnumerable);
@ -2442,6 +2454,7 @@ Init_IO()
RS = RS_default = str_new2("\n"); ORS = Qnil;
rb_global_variable(&RS_default);
str_freeze(RS_default); /* avoid modifying RS_default */
rb_define_hooked_variable("$/", &RS, 0, rb_str_setter);
rb_define_hooked_variable("$-0", &RS, 0, rb_str_setter);
rb_define_hooked_variable("$\\", &ORS, 0, rb_str_setter);

View file

@ -118,10 +118,12 @@ VALUE
any_to_s(obj)
VALUE obj;
{
char buf[256];
char *s;
char *cname = rb_class2name(CLASS_OF(obj));
sprintf(buf, "#<%s:0x%x>", rb_class2name(CLASS_OF(obj)), obj);
return str_new2(buf);
s = ALLOCA_N(char, strlen(cname)+6+16+1); /* 6:tags 16:addr 1:eos */
sprintf(s, "#<%s:0x%x>", cname, obj);
return str_new2(s);
}
VALUE

55
parse.y
View file

@ -1824,12 +1824,13 @@ read_escape()
}
static int
parse_regx(term)
parse_regx(term, paren)
int term;
{
register int c;
char kcode = 0;
int once = 0;
int nest = 0;
int casefold = 0;
int in_brack = 0;
int re_start = sourceline;
@ -1837,7 +1838,7 @@ parse_regx(term)
newtok();
while ((c = nextc()) != -1) {
if (!in_brack && c == term) {
if ((!in_brack && c == term) || nest > 0) {
goto regx_end;
}
@ -1888,6 +1889,8 @@ parse_regx(term)
}
/* fall through */
default:
if (c == paren) nest++;
if (c == term) nest--;
if (c == '\n') {
sourceline++;
}
@ -1961,23 +1964,24 @@ parse_regx(term)
return 0;
}
static int parse_qstring();
static int parse_qstring _((int,int));
static int
parse_string(func,term)
int func, term;
parse_string(func, term, paren)
int func, term, paren;
{
int c;
NODE *list = 0;
int strstart;
int nest = 0;
if (func == '\'') {
return parse_qstring(term);
return parse_qstring(term, paren);
}
strstart = sourceline;
newtok();
while ((c = nextc()) != term) {
while ((c = nextc()) != term || nest > 0) {
if (c == -1) {
unterm_str:
sourceline = strstart;
@ -2011,6 +2015,8 @@ parse_string(func,term)
}
continue;
}
if (c == paren) nest++;
if (c == term) nest--;
tokadd(c);
}
@ -2037,15 +2043,16 @@ parse_string(func,term)
}
static int
parse_qstring(term)
parse_qstring(term, paren)
int term;
{
int strstart;
int c;
int nest = 0;
strstart = sourceline;
newtok();
while ((c = nextc()) != term) {
while ((c = nextc()) != term || nest > 0) {
if (c == -1) {
sourceline = strstart;
Error("unterminated string meets end of file");
@ -2079,6 +2086,8 @@ parse_qstring(term)
tokadd('\\');
}
}
if (c == paren) nest++;
if (c == term) nest--;
tokadd(c);
}
@ -2089,10 +2098,10 @@ parse_qstring(term)
}
static int
parse_quotedword(term)
int term;
parse_quotedword(term, paren)
int term, paren;
{
if (parse_qstring(term) == 0) return 0;
if (parse_qstring(term, paren) == 0) return 0;
yylval.node = NEW_CALL(NEW_STR(yylval.val), rb_intern("split"), 0);
return tDSTRING;
}
@ -2406,13 +2415,13 @@ retry:
return '>';
case '"':
return parse_string(c,c);
return parse_string(c,c,c);
case '`':
if (lex_state == EXPR_FNAME) return c;
return parse_string(c,c);
return parse_string(c,c,c);
case '\'':
return parse_qstring(c);
return parse_qstring(c,c);
case '?':
if (lex_state == EXPR_END) {
@ -2700,7 +2709,7 @@ retry:
case '/':
if (lex_state == EXPR_BEG || lex_state == EXPR_MID) {
return parse_regx('/');
return parse_regx('/', '/');
}
if ((c = nextc()) == '=') {
lex_state = EXPR_BEG;
@ -2711,7 +2720,7 @@ retry:
if (space_seen && !isspace(c)) {
pushback(c);
arg_ambiguous();
return parse_regx('/');
return parse_regx('/', '/');
}
}
lex_state = EXPR_BEG;
@ -2792,6 +2801,7 @@ retry:
case '%':
if (lex_state == EXPR_BEG || lex_state == EXPR_MID) {
int term;
int paren;
c = nextc();
quotation:
@ -2815,6 +2825,7 @@ retry:
Error("unterminated quoted string meets end of file");
return 0;
}
paren = term;
if (term == '(') term = ')';
else if (term == '[') term = ']';
else if (term == '{') term = '}';
@ -2822,19 +2833,19 @@ retry:
switch (c) {
case 'Q':
return parse_string('"', term);
return parse_string('"', term, paren);
case 'q':
return parse_qstring(term);
return parse_qstring(term, paren);
case 'w':
return parse_quotedword(term);
return parse_quotedword(term, paren);
case 'x':
return parse_string('`', term);
return parse_string('`', term, paren);
case 'r':
return parse_regx(term);
return parse_regx(term, paren);
default:
yyerror("unknown type of %string");

4
ruby.c
View file

@ -477,9 +477,7 @@ load_file(fname, script)
line = io_gets(f);
line_start++;
if (RSTRING(line)->len > 2
&& RSTRING(line)->ptr[0] == '!') {
if (RSTRING(line)->len > 2 && RSTRING(line)->ptr[0] == '!') {
if ((p = strstr(RSTRING(line)->ptr, "ruby")) == 0) {
/* not ruby script, kick the program */
char **argv;

View file

@ -646,7 +646,7 @@ An end of a defun is found by moving forward from the beginning of one."
"\\)[ \n\t()]")
2)
;; variables
'("\\(^\\|[^_]\\)\\b\\(nil\\|self\\|true\\|false\\)\\b[^_]"
'("\\(^\\|[^_]\\)\\b\\(nil\\|self\\|true\\|false\\)\\b\\([^_]\\|$\\)"
2 font-lock-variable-name-face)
;; variables
'("\\[$@].\\([a-zA-Z0-9_]\\)"

View file

@ -271,6 +271,11 @@ posix_signal(signum, handler)
}
#endif
#ifdef THREAD
# define rb_interrupt thread_interrupt
# define rb_trap_eval thread_trap_eval
#endif
static RETSIGTYPE
sighandle(sig)
int sig;
@ -285,11 +290,7 @@ sighandle(sig)
if (trap_immediate) {
trap_immediate = 0;
if (sig == SIGINT && !trap_list[SIGINT]) {
#ifdef THREAD
thread_interrupt();
#else
rb_interrupt();
#endif
}
rb_trap_eval(trap_list[sig], sig);
trap_immediate = 1;
@ -334,18 +335,10 @@ rb_trap_exec()
if (trap_pending_list[i]) {
trap_pending_list[i] = 0;
if (i == SIGINT && trap_list[SIGINT] == 0) {
#ifdef THREAD
thread_interrupt();
#else
rb_interrupt();
#endif
return;
}
#ifdef THREAD
thread_trap_eval(trap_list[i], i);
#else
rb_trap_eval(trap_list[i], i);
#endif
}
}
trap_pending = 0;

View file

@ -84,24 +84,26 @@ VALUE
str_new4(orig)
VALUE orig;
{
if (RSTRING(orig)->orig) {
return str_freeze(RSTRING(orig)->orig);
}
else if (FL_TEST(orig, STR_FREEZE)) {
return orig;
}
else {
NEWOBJ(str, struct RString);
OBJSETUP(str, cString, T_STRING);
str->len = RSTRING(orig)->len;
str->ptr = RSTRING(orig)->ptr;
if (RSTRING(orig)->orig) {
str->orig = RSTRING(orig)->orig;
}
else {
RSTRING(orig)->orig = (VALUE)str;
str->orig = 0;
}
if (rb_safe_level() >= 3) {
FL_SET(str, STR_TAINT);
}
return (VALUE)str;
}
}
static void
str_assign(str, str2)
@ -362,12 +364,15 @@ str_frozen_p(str)
}
VALUE
str_dup_freezed(str)
str_dup_frozen(str)
VALUE str;
{
str = str_dup(str);
str_freeze(str);
if (RSTRING(str)->orig) {
return str_freeze(RSTRING(str)->orig);
}
if (FL_TEST(str, STR_FREEZE))
return str;
return str_freeze(str_dup(str));
}
VALUE