summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ChangeLog37
-rw-r--r--MANIFEST3
-rw-r--r--Makefile.in43
-rw-r--r--array.c8
-rw-r--r--configure.in142
-rw-r--r--dbm.c417
-rw-r--r--defines.h15
-rw-r--r--dict.c628
-rw-r--r--dir.c8
-rw-r--r--dln.c461
-rw-r--r--dln.h15
-rw-r--r--error.c2
-rw-r--r--eval.c31
-rw-r--r--gc.c16
-rw-r--r--inits.c8
-rwxr-xr-xinstall-sh238
-rw-r--r--io.c21
-rw-r--r--parse.y7
-rw-r--r--re.c2
-rw-r--r--regex.c369
-rw-r--r--ruby.c15
-rw-r--r--ruby.h6
-rw-r--r--sample/dbm.rb12
-rw-r--r--socket.c758
-rw-r--r--spec585
-rw-r--r--util.c9
-rw-r--r--util.h2
-rw-r--r--version.h4
28 files changed, 999 insertions, 2863 deletions
diff --git a/ChangeLog b/ChangeLog
index eac8efba2a..d888fbed01 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,40 @@
+Mon Apr 3 15:19:41 1995 Yukihiro Matsumoto (matz@ix-02)
+
+ * regexp.c(re_match): バグがあった.match_2を削除した時にenbugして
+ いたのだった.
+
+Mon Mar 27 15:41:43 1995 Yukihiro Matsumoto (matz@ix-02)
+
+ * dict.c: Dict->Hashに全面的に移行.
+
+Thu Mar 23 20:30:00 1995 Yukihiro Matsumoto (matz@ix-02)
+
+ * dbm.c,socket.c: extディレクトリに分離.
+
+ * configure: dln周りのチェックの強化
+
+ * dln.c: initの呼び出しをdlopen()版に合わせた.
+
+Mon Mar 20 17:45:08 1995 Yukihiro Matsumoto (matz@ix-02)
+
+ * configure: autoconf 2.2に対応(一部).
+
+Fri Mar 17 15:56:44 1995 Yukihiro Matsumoto (matz@ix-02)
+
+ * dln.c: dlopenのあるマシンではそちらを使うように.ただし,ちゃん
+ と動いているかどうかは自信がない.
+
+ * regex.c: virtual concatinationをやめた.
+
+Thu Mar 16 11:32:57 1995 Yukihiro Matsumoto (matz@ix-02)
+
+ * version 0.70
+
+ * eval.c,regex.c: gccでのコンパイルエラー.
+
+ * io.c: inplace-editで拡張子が指定されない場合,もとのファイルを削
+ 除する.
+
Wed Mar 15 14:59:18 1995 Yukihiro Matsumoto (matz@ix-02)
* version 0.69
diff --git a/MANIFEST b/MANIFEST
index 06b4a8ccb2..afde81ab88 100644
--- a/MANIFEST
+++ b/MANIFEST
@@ -12,7 +12,6 @@ compar.c
configure
configure.in
cons.c
-dbm.c
defines.h
dict.c
dir.c
@@ -30,6 +29,7 @@ gc.c
glob.c
ident.h
inits.c
+install-sh
io.c
io.h
main.c
@@ -50,7 +50,6 @@ ruby.1
ruby.c
ruby.h
signal.c
-socket.c
spec
sprintf.c
st.c
diff --git a/Makefile.in b/Makefile.in
index 8f818473ad..35efe604f6 100644
--- a/Makefile.in
+++ b/Makefile.in
@@ -1,4 +1,4 @@
-SHELL = /bin/sh
+2SHELL = /bin/sh
#### Start of system configuration section. ####
@@ -6,44 +6,30 @@ srcdir = @srcdir@
VPATH = @srcdir@
CC = @CC@
-DBMCC = cc
YACC = @YACC@
INSTALL = @INSTALL@
INSTALL_PROGRAM = @INSTALL_PROGRAM@
INSTALL_DATA = @INSTALL_DATA@
PURIFY=
-CFLAGS = -g
+CFLAGS = @CFLAGS@
STATIC = @STATIC@
-LDFLAGS = $(CFLAGS)
+LDFLAGS = $(CFLAGS) @LDFLAGS@
LIBS = @LIBS@
MISSING = @LIBOBJS@ @ALLOCA@
-prefix = /usr/local
+prefix = @prefix@
binprefix =
-exec_prefix = $(prefix)
+exec_prefix = @exec_prefix@
bindir = $(exec_prefix)/bin
#### End of system configuration section. ####
-HDRS = defines.h \
- dln.h \
- ident.h \
- io.h \
- node.h \
- re.h \
- regex.h \
- ruby.h \
- st.h \
- version.h
-
OBJS = array.o \
bignum.o \
class.o \
compar.o \
cons.o \
- dbm.o \
- dict.o \
dir.o \
dln.o \
enum.o \
@@ -54,6 +40,7 @@ OBJS = array.o \
fnmatch.o \
gc.o \
glob.o \
+ hash.o \
inits.o \
io.o \
main.o \
@@ -69,7 +56,6 @@ OBJS = array.o \
regex.o \
ruby.o \
signal.o \
- socket.o \
sprintf.o \
st.o \
string.o \
@@ -82,12 +68,14 @@ OBJS = array.o \
PROGRAM = ruby
-all: $(PROGRAM)
+all: $(PROGRAM) @EXTMAKE@
$(PROGRAM): $(OBJS)
@rm -f $(PROGRAM)
$(PURIFY) $(CC) $(STATIC) $(LDFLAGS) $(OBJS) $(LIBS) -o $(PROGRAM)
+extmake:; cd ext; make
+
$(bindir)/$(PROGRAM): $(PROGRAM)
$(INSTALL_PROGRAM) $(PROGRAM) $(bindir)/$(PROGRAM)
@@ -100,9 +88,6 @@ realclean:; @rm -f $(OBJS)
.c.o:
$(CC) $(CFLAGS) $(CPPFLAGS) -c $<
-dbm.o:dbm.c
- $(DBMCC) $(CFLAGS) $(CPPFLAGS) -c dbm.c
-
alloca.o: missing/alloca.c
$(CC) -I. $(CFLAGS) $(CPPFLAGS) -c missing/alloca.c
@@ -140,18 +125,17 @@ bignum.o: bignum.c ruby.h config.h defines.h
class.o: class.c ruby.h config.h defines.h env.h node.h st.h
compar.o: compar.c ruby.h config.h defines.h
cons.o: cons.c ruby.h config.h defines.h
-dbm.o: dbm.c ruby.h config.h defines.h
-dict.o: dict.c ruby.h config.h defines.h st.h
dir.o: dir.c ruby.h config.h defines.h
-dln.o: dln.c config.h defines.h dln.h st.h
+dln.o: dln.c config.h defines.h dln.h
enum.o: enum.c ruby.h config.h defines.h
error.o: error.c ruby.h config.h defines.h env.h
etc.o: etc.c ruby.h config.h defines.h
-eval.o: eval.c ruby.h config.h defines.h ident.h env.h node.h st.h
+eval.o: eval.c ruby.h config.h defines.h ident.h env.h node.h st.h dln.h
file.o: file.c ruby.h config.h defines.h io.h
fnmatch.o: fnmatch.c config.h fnmatch.h
gc.o: gc.c ruby.h config.h defines.h env.h st.h node.h
glob.o: glob.c config.h fnmatch.h
+hash.o: hash.c ruby.h config.h defines.h st.h
inits.o: inits.c ruby.h config.h defines.h
io.o: io.c ruby.h config.h defines.h io.h
main.o: main.c
@@ -164,9 +148,8 @@ random.o: random.c ruby.h config.h defines.h
range.o: range.c ruby.h config.h defines.h
re.o: re.c ruby.h config.h defines.h re.h regex.h
regex.o: regex.c config.h defines.h regex.h util.h
-ruby.o: ruby.c ruby.h config.h defines.h re.h regex.h
+ruby.o: ruby.c ruby.h config.h defines.h re.h regex.h dln.h
signal.o: signal.c ruby.h config.h defines.h
-socket.o: socket.c ruby.h config.h defines.h io.h
sprintf.o: sprintf.c ruby.h config.h defines.h
st.o: st.c config.h st.h
string.o: string.c ruby.h config.h defines.h re.h regex.h
diff --git a/array.c b/array.c
index 120fd13019..a15f0530ae 100644
--- a/array.c
+++ b/array.c
@@ -322,21 +322,21 @@ Fary_indexes(ary, args)
struct RArray *ary, *args;
{
VALUE *p, *pend;
- VALUE new;
+ VALUE new_ary;
int i = 0;
if (!args || args->len == 1) {
args = (struct RArray*)rb_to_a(args->ptr[0]);
}
- new = ary_new2(args->len);
+ new_ary = ary_new2(args->len);
p = args->ptr; pend = p + args->len;
while (p < pend) {
- astore(new, i++, ary_entry(ary, NUM2INT(*p)));
+ astore(new_ary, i++, ary_entry(ary, NUM2INT(*p)));
p++;
}
- return new;
+ return new_ary;
}
static VALUE
diff --git a/configure.in b/configure.in
index efe87a287c..943a3dab45 100644
--- a/configure.in
+++ b/configure.in
@@ -3,62 +3,98 @@ AC_INIT(ruby.h)
PROGS="ruby"
AC_SUBST(PROGS)dnl
AC_PROG_CC
-AC_GCC_TRADITIONAL
-if test "$HOSTTYPE" = sparc; then
- if test "$GCC" = 1 ; then
- STATIC=-static
- else
- STATIC=-Bstatic
- fi
-else
- STATIC=
-fi
-AC_SUBST(STATIC)dnl
+AC_PROG_GCC_TRADITIONAL
AC_PROG_YACC
AC_PROG_INSTALL
-AC_HAVE_HEADERS(unistd.h stdlib.h syscall.h a.out.h dirent.h\
- string.h strings.h)
-AC_DIR_HEADER
-AC_GETGROUPS_T
-AC_RETSIGTYPE
-AC_HAVE_LIBRARY(m, [LIBS="$LIBS -lm"])
-AC_HAVE_LIBRARY(dbm, [LIBS="$LIBS -ldbm"])
-AC_HAVE_LIBRARY(socket, [LIBS="$LIBS -lsocket"])
-AC_HAVE_LIBRARY(crypt, [LIBS="$LIBS -lcrypt"])
-AC_VFORK
+AC_CHECK_HEADERS(unistd.h stdlib.h syscall.h a.out.h dirent.h\
+ string.h)
+AC_HEADER_DIRENT
+AC_TYPE_GETGROUPS
+AC_TYPE_SIGNAL
+AC_CHECK_LIB(m, pow, [LIBS="$LIBS -lm"])
+AC_CHECK_LIB(dbm, dbm_open, AC_DEFINE(HAVE_LIBDBM))
+AC_CHECK_LIB(socket, socket, AC_DEFINE(HAVE_LIBSOKCET))
+AC_CHECK_LIB(crypt, crypt, [LIBS="$LIBS -lcrypt"])
+AC_FUNC_VFORK
AC_REPLACE_FUNCS(memmove mkdir strerror strftime\
- strstr strtol strtoul strdup)
-AC_HAVE_FUNCS(fmod killpg socket random wait4 waitpid syscall getcwd\
+ strstr strtoul strdup)
+AC_CHECK_FUNCS(fmod killpg socket random wait4 waitpid syscall getcwd\
setruid seteuid setreuid setrgid setegid setregid\
- getpriority sigprocmask)
-AC_FUNC_CHECK(setenv, [], AC_HAVE_FUNCS(putenv))
+ getpriority sigprocmask dlopen)
+AC_CHECK_FUNC(setenv, [], AC_CHECK_FUNCS(putenv))
+if test $ac_cv_func strftime = no; then
+ AC_STRUCT_TIMEZONE
+ AC_TRY_LINK([],
+ [extern int daylight; int i = daylight;], AC_DEFINE(HAVE_DAYLIGHT))
+fi
+
+AC_FUNC_ALLOCA
+AC_C_BIGENDIAN
+AC_STRUCT_ST_BLKSIZE
+AC_STRUCT_ST_BLOCKS
+AC_STRUCT_ST_RDEV
+AC_MSG_CHECKING(std stdio)
+AC_CACHE_VAL(rb_cv_stdstdio,
+[AC_TRY_COMPILE([#include <stdio.h>],
+ [stdin->_cnt > 0;],
+ rb_cv_stdstdio=yes,
+ rb_cv_stdstdio=no)])
+AC_MSG_RESULT($rb_cv_stdstdio)
+if test $rb_cv_stdstdio = yes; then
+ AC_DEFINE(STDSTDIO)
+fi
+AC_MSG_CHECKING(struct passwd)
+AC_EGREP_HEADER(pw_change, pwd.h, AC_DEFINE(PW_CHANGE))
+AC_EGREP_HEADER(pw_quota, pwd.h, AC_DEFINE(PW_QUOTA))
+AC_EGREP_HEADER(pw_age, pwd.h, AC_DEFINE(PW_AGE))
+AC_EGREP_HEADER(pw_class, pwd.h, AC_DEFINE(PW_CLASS))
+AC_EGREP_HEADER(pw_comment, pwd.h, AC_DEFINE(PW_COMMENT))
+AC_EGREP_HEADER(pw_expire, pwd.h, AC_DEFINE(PW_EXPIRE))
+AC_MSG_RESULT(done)
+AC_MSG_CHECKING(whether matz's dln works)
+cp confdefs.h config.h
+if test $ac_cv_header_a_out_h = yes; then
+ AC_CACHE_VAL(rb_cv_mydln,
+ [AC_TRY_COMPILE([#include "config.h"],
+ [],
+ rb_cv_mydln=yes,
+ rb_cv_mydln=no)])
+ AC_MSG_RESULT($rb_cv_mydln)
+ if test $rb_cv_mydln = yes; then
+ AC_DEFINE(USE_MY_DLN)
+ fi
+fi
+
+AC_SUBST(STATIC)dnl
+AC_SUBST(CCDLFLAGS)dnl
+AC_SUBST(EXT)dnl
+AC_SUBST(EXTMAKE)dnl
+
+EXTMAKE=
+STATIC=
-case "$LIBOBJS" in
- *) ;;
- *strftime*)
- AC_TIMEZONE
- AC_COMPILE_CHECK([daylight], [],
- [extern int daylight; int i = daylight;], AC_DEFINE(HAVE_DAYLIGHT));;
-esac
+if test $ac_cv_func_dlopen = yes -o $rb_cv_mydln = yes; then
+ EXTMAKE=extmake
+ if test "$rb_cv_mydln" = yes; then
+ if test "$HOSTTYPE" = sparc; then
+ if test $ac_cv_prog_CC = gcc; then
+ STATIC=-static
+ else
+ STATIC=-Bstatic
+ fi
+ fi
+ EXT=o
+ CCDLFLAGS=
+ LDCMD=
+ else
+ EXT=so
+ if test $ac_cv_prog_CC = gcc; then
+ CCDLFLAGS=-fpic
+ else
+ CCDLFLAGS=-pic
+ fi
+ fi
+fi
-AC_ALLOCA
-AC_WORDS_BIGENDIAN
-AC_ST_BLKSIZE
-AC_ST_BLOCKS
-AC_ST_RDEV
-AC_COMPILE_CHECK([std stdio], [#include <stdio.h>],
-[stdin->_cnt > 0;], AC_DEFINE(STDSTDIO))
-AC_COMPILE_CHECK([pw_change in struct passwd], [#include <pwd.h>],
-[struct passwd pw; pw.pw_change;], AC_DEFINE(PW_CHANGE))
-AC_COMPILE_CHECK([pw_quota in struct passwd], [#include <pwd.h>],
-[struct passwd pw; pw.pw_quota;], AC_DEFINE(PW_QUOTA))
-AC_COMPILE_CHECK([pw_age in struct passwd], [#include <pwd.h>],
-[struct passwd pw; pw.pw_age;], AC_DEFINE(PW_AGE))
-AC_COMPILE_CHECK([pw_class in struct passwd], [#include <pwd.h>],
-[struct passwd pw; pw.pw_class;], AC_DEFINE(PW_CLASSS))
-AC_COMPILE_CHECK([pw_comment in struct passwd], [#include <pwd.h>],
-[struct passwd pw; pw.pw_comment;], AC_DEFINE(PW_COMMENT))
-AC_COMPILE_CHECK([pw_expire in struct passwd], [#include <pwd.h>],
-[struct passwd pw; pw.pw_expire;], AC_DEFINE(PW_EXPIRE))
-AC_OUTPUT(Makefile)
-mv confdefs.h config.h
+cp confdefs.h config.h
+AC_OUTPUT(Makefile ext/Makefile)
diff --git a/dbm.c b/dbm.c
deleted file mode 100644
index dfe0a8bf83..0000000000
--- a/dbm.c
+++ /dev/null
@@ -1,417 +0,0 @@
-/************************************************
-
- dbm.c -
-
- $Author: matz $
- $Date: 1995/01/10 10:42:24 $
- created at: Mon Jan 24 15:59:52 JST 1994
-
- Copyright (C) 1995 Yukihiro Matsumoto
-
-************************************************/
-
-#include "ruby.h"
-
-#ifdef USE_DBM
-
-#include <ndbm.h>
-#include <fcntl.h>
-#include <errno.h>
-
-VALUE C_DBM;
-static ID id_dbm;
-
-extern VALUE M_Enumerable;
-
-static void
-closeddbm()
-{
- Fail("closed DBM file");
-}
-
-#define GetDBM(obj, dbmp) {\
- DBM **_dbm;\
- if (!id_dbm) id_dbm = rb_intern("dbm");\
- Get_Data_Struct(obj, id_dbm, DBM*, _dbm);\
- dbmp = *_dbm;\
- if (dbmp == Qnil) closeddbm();\
-}
-
-static void
-free_dbm(dbmp)
- DBM **dbmp;
-{
- if (*dbmp) dbm_close(*dbmp);
-}
-
-#define MakeDBM(obj, dp) {\
- DBM **_dbm;\
- Make_Data_Struct(obj,id_dbm,DBM*,Qnil,free_dbm,_dbm);\
- *_dbm=dp;\
-}
-
-static VALUE
-Sdbm_open(argc, argv, class)
- int argc;
- VALUE *argv;
- VALUE class;
-{
- VALUE file, vmode;
- DBM *dbm, **dbm2;
- int mode;
- VALUE obj;
-
- if (rb_scan_args(argc, argv, "11", &file, &vmode) == 1) {
- mode = 0666; /* default value */
- }
- else if (NIL_P(vmode)) {
- mode = -1; /* return nil if DB not exist */
- }
- else {
- mode = NUM2INT(vmode);
- }
- Check_Type(file, T_STRING);
-
- dbm = Qnil;
- if (mode >= 0)
- dbm = dbm_open(RSTRING(file)->ptr, O_RDWR|O_CREAT, mode);
- if (!dbm)
- dbm = dbm_open(RSTRING(file)->ptr, O_RDWR, mode);
- if (!dbm)
- dbm = dbm_open(RSTRING(file)->ptr, O_RDONLY, mode);
-
- if (!dbm) {
- if (mode == -1) return Qnil;
- rb_sys_fail(RSTRING(file)->ptr);
- }
-
- obj = obj_alloc(class);
- MakeDBM(obj, dbm);
-
- return obj;
-}
-
-static VALUE
-Fdbm_close(obj)
- VALUE obj;
-{
- DBM **dbmp;
-
- Get_Data_Struct(obj, id_dbm, DBM*, dbmp);
- if (*dbmp == Qnil) Fail("already closed DBM file");
- dbm_close(*dbmp);
- *dbmp = Qnil;
-
- return Qnil;
-}
-
-static VALUE
-Fdbm_fetch(obj, keystr)
- VALUE obj, keystr;
-{
- datum key, value;
- DBM *dbm;
-
- Check_Type(keystr, T_STRING);
- key.dptr = RSTRING(keystr)->ptr;
- key.dsize = RSTRING(keystr)->len;
-
- GetDBM(obj, dbm);
- value = dbm_fetch(dbm, key);
- if (value.dptr == Qnil) {
- return Qnil;
- }
- return str_new(value.dptr, value.dsize);
-}
-
-static VALUE
-Fdbm_indexes(obj, args)
- VALUE obj;
- struct RArray *args;
-{
- VALUE *p, *pend;
- struct RArray *new;
- int i = 0;
-
- if (!args || args->len == 1 && TYPE(args->ptr) != T_ARRAY) {
- args = (struct RArray*)rb_to_a(args->ptr[0]);
- }
-
- new = (struct RArray*)ary_new2(args->len);
-
- p = args->ptr; pend = p + args->len;
- while (p < pend) {
- new->ptr[i++] = Fdbm_fetch(obj, *p++);
- new->len = i;
- }
- return (VALUE)new;
-}
-
-static VALUE
-Fdbm_delete(obj, keystr)
- VALUE obj, keystr;
-{
- datum key;
- DBM *dbm;
-
- Check_Type(keystr, T_STRING);
- key.dptr = RSTRING(keystr)->ptr;
- key.dsize = RSTRING(keystr)->len;
-
- GetDBM(obj, dbm);
- if (dbm_delete(dbm, key)) {
- Fail("dbm_delete failed");
- }
- return obj;
-}
-
-static VALUE
-Fdbm_delete_if(obj)
- VALUE obj;
-{
- datum key, val;
- DBM *dbm;
- VALUE keystr, valstr;
-
- GetDBM(obj, dbm);
- for (key = dbm_firstkey(dbm); key.dptr; key = dbm_nextkey(dbm)) {
- val = dbm_fetch(dbm, key);
- keystr = str_new(key.dptr, key.dsize);
- valstr = str_new(val.dptr, val.dsize);
- if (rb_yield(assoc_new(keystr, valstr))
- && dbm_delete(dbm, key)) {
- Fail("dbm_delete failed");
- }
- }
- return obj;
-}
-
-static VALUE
-Fdbm_clear(obj)
- VALUE obj;
-{
- datum key;
- DBM *dbm;
-
- GetDBM(obj, dbm);
- for (key = dbm_firstkey(dbm); key.dptr; key = dbm_nextkey(dbm)) {
- if (dbm_delete(dbm, key)) {
- Fail("dbm_delete failed");
- }
- }
- return obj;
-}
-
-static VALUE
-Fdbm_store(obj, keystr, valstr)
- VALUE obj, keystr, valstr;
-{
- datum key, val;
- DBM *dbm;
-
- if (valstr == Qnil) {
- Fdbm_delete(obj, keystr);
- return Qnil;
- }
-
- Check_Type(keystr, T_STRING);
- key.dptr = RSTRING(keystr)->ptr;
- key.dsize = RSTRING(keystr)->len;
- Check_Type(valstr, T_STRING);
- val.dptr = RSTRING(valstr)->ptr;
- val.dsize = RSTRING(valstr)->len;
-
- GetDBM(obj, dbm);
- if (dbm_store(dbm, key, val, DBM_REPLACE)) {
- dbm_clearerr(dbm);
- if (errno == EPERM) rb_sys_fail(Qnil);
- Fail("dbm_store failed");
- }
- return valstr;
-}
-
-static VALUE
-Fdbm_length(obj)
- VALUE obj;
-{
- datum key;
- DBM *dbm;
- int i = 0;
-
- GetDBM(obj, dbm);
- for (key = dbm_firstkey(dbm); key.dptr; key = dbm_nextkey(dbm)) {
- i++;
- }
- return INT2FIX(i);
-}
-
-static VALUE
-Fdbm_each_value(obj)
- VALUE obj;
-{
- datum key, val;
- DBM *dbm;
-
- GetDBM(obj, dbm);
- for (key = dbm_firstkey(dbm); key.dptr; key = dbm_nextkey(dbm)) {
- val = dbm_fetch(dbm, key);
- rb_yield(str_new(val.dptr, val.dsize));
- }
- return obj;
-}
-
-static VALUE
-Fdbm_each_key(obj)
- VALUE obj;
-{
- datum key;
- DBM *dbm;
-
- GetDBM(obj, dbm);
- for (key = dbm_firstkey(dbm); key.dptr; key = dbm_nextkey(dbm)) {
- rb_yield(str_new(key.dptr, key.dsize));
- }
- return obj;
-}
-
-static VALUE
-Fdbm_each_pair(obj)
- VALUE obj;
-{
- datum key, val;
- DBM *dbm;
- VALUE keystr, valstr;
-
- GetDBM(obj, dbm);
-
- for (key = dbm_firstkey(dbm); key.dptr; key = dbm_nextkey(dbm)) {
- val = dbm_fetch(dbm, key);
- keystr = str_new(key.dptr, key.dsize);
- valstr = str_new(val.dptr, val.dsize);
- rb_yield(assoc_new(keystr, valstr));
- }
-
- return obj;
-}
-
-static VALUE
-Fdbm_keys(obj)
- VALUE obj;
-{
- datum key;
- DBM *dbm;
- VALUE ary;
-
- ary = ary_new();
- GetDBM(obj, dbm);
- for (key = dbm_firstkey(dbm); key.dptr; key = dbm_nextkey(dbm)) {
- ary_push(ary, str_new(key.dptr, key.dsize));
- }
-
- return ary;
-}
-
-static VALUE
-Fdbm_values(obj)
- VALUE obj;
-{
- datum key, val;
- DBM *dbm;
- VALUE ary;
-
- ary = ary_new();
- GetDBM(obj, dbm);
- for (key = dbm_firstkey(dbm); key.dptr; key = dbm_nextkey(dbm)) {
- val = dbm_fetch(dbm, key);
- ary_push(ary, str_new(val.dptr, val.dsize));
- }
-
- return ary;
-}
-
-static VALUE
-Fdbm_has_key(obj, keystr)
- VALUE obj, keystr;
-{
- datum key, val;
- DBM *dbm;
-
- Check_Type(keystr, T_STRING);
- key.dptr = RSTRING(keystr)->ptr;
- key.dsize = RSTRING(keystr)->len;
-
- GetDBM(obj, dbm);
- val = dbm_fetch(dbm, key);
- if (val.dptr) return TRUE;
- return FALSE;
-}
-
-static VALUE
-Fdbm_has_value(obj, valstr)
- VALUE obj, valstr;
-{
- datum key, val;
- DBM *dbm;
-
- Check_Type(valstr, T_STRING);
- val.dptr = RSTRING(valstr)->ptr;
- val.dsize = RSTRING(valstr)->len;
-
- GetDBM(obj, dbm);
- for (key = dbm_firstkey(dbm); key.dptr; key = dbm_nextkey(dbm)) {
- val = dbm_fetch(dbm, key);
- if (val.dsize == RSTRING(valstr)->len &&
- memcmp(val.dptr, RSTRING(valstr)->ptr, val.dsize) == 0)
- return TRUE;
- }
- return FALSE;
-}
-
-static VALUE
-Fdbm_to_a(obj)
- VALUE obj;
-{
- datum key, val;
- DBM *dbm;
- VALUE ary;
-
- GetDBM(obj, dbm);
-
- ary = ary_new();
- for (key = dbm_firstkey(dbm); key.dptr; key = dbm_nextkey(dbm)) {
- val = dbm_fetch(dbm, key);
- ary_push(ary, assoc_new(str_new(key.dptr, key.dsize),
- str_new(val.dptr, val.dsize)));
- }
-
- return ary;
-}
-
-Init_DBM()
-{
- C_DBM = rb_define_class("DBM", C_Object);
- rb_include_module(C_DBM, M_Enumerable);
-
- rb_define_single_method(C_DBM, "open", Sdbm_open, -1);
- rb_define_method(C_DBM, "close", Fdbm_close, 0);
- rb_define_method(C_DBM, "[]", Fdbm_fetch, 1);
- rb_define_method(C_DBM, "[]=", Fdbm_store, 2);
- rb_define_method(C_DBM, "indexes", Fdbm_indexes, -2);
- rb_define_method(C_DBM, "length", Fdbm_length, 0);
- rb_define_alias(C_DBM, "size", "length");
- rb_define_method(C_DBM, "each", Fdbm_each_pair, 0);
- rb_define_method(C_DBM, "each_value", Fdbm_each_value, 0);
- rb_define_method(C_DBM, "each_key", Fdbm_each_key, 0);
- rb_define_method(C_DBM, "each_pair", Fdbm_each_pair, 0);
- rb_define_method(C_DBM, "keys", Fdbm_keys, 0);
- rb_define_method(C_DBM, "values", Fdbm_values, 0);
- rb_define_method(C_DBM, "delete", Fdbm_delete, 1);
- rb_define_method(C_DBM, "delete_if", Fdbm_delete_if, 0);
- rb_define_method(C_DBM, "clear", Fdbm_clear, 0);
- rb_define_method(C_DBM, "includes", Fdbm_has_key, 1);
- rb_define_method(C_DBM, "has_key", Fdbm_has_key, 1);
- rb_define_method(C_DBM, "has_value", Fdbm_has_value, 1);
-
- rb_define_method(C_DBM, "to_a", Fdbm_to_a, 0);
-}
-#endif /* USE_DBM */
diff --git a/defines.h b/defines.h
index ac4ca46075..cba0c4c3f0 100644
--- a/defines.h
+++ b/defines.h
@@ -16,15 +16,18 @@
#define EUC
#undef SJIS
-#ifdef HAVE_A_OUT_H
-/* define USE_DLN to load object file(.o). */
-#define USE_DLN
-#ifdef USE_DLN
-#define LIBC_NAME "libc.a"
-#define DLN_DEFAULT_PATH "/lib:/usr/lib:."
+/* define USE_DL to load object file(.o). */
+#define USE_DL
+
+/* a.out.h or dlopen() needed to load object */
+#if !defined(HAVE_DLOPEN) || !defined(HAVE_A_OUT_H)
+# undef USE_DL
#endif
+#ifdef USE_MY_DLN
+# define LIBC_NAME "libc.a"
+# define DLN_DEFAULT_PATH "/lib:/usr/lib:."
#endif
/* define USE_DBM to use dbm class. */
diff --git a/dict.c b/dict.c
deleted file mode 100644
index c7bc6d454d..0000000000
--- a/dict.c
+++ /dev/null
@@ -1,628 +0,0 @@
-/************************************************
-
- dict.c -
-
- $Author: matz $
- $Date: 1995/01/10 10:42:26 $
- created at: Mon Nov 22 18:51:18 JST 1993
-
- Copyright (C) 1995 Yukihiro Matsumoto
-
-************************************************/
-
-#include "ruby.h"
-#include "st.h"
-
-VALUE C_Dict;
-
-static VALUE envtbl;
-static ID hash;
-VALUE Fgetenv(), Fsetenv();
-
-static VALUE
-rb_cmp(a, b)
- VALUE a, b;
-{
- return rb_equal(a, b)?0:1;
-}
-
-static VALUE
-rb_hash(a, mod)
- VALUE a;
- int mod;
-{
- return rb_funcall(a, hash, 0) % mod;
-}
-
-#define ASSOC_KEY(a) RCONS(a)->car
-#define ASSOC_VAL(a) RCONS(a)->cdr
-
-static VALUE
-Sdic_new(class)
- VALUE class;
-{
- NEWOBJ(dic, struct RDict);
- OBJSETUP(dic, class, T_DICT);
-
- dic->tbl = st_init_table(rb_cmp, rb_hash);
-
- return (VALUE)dic;
-}
-
-static VALUE Fdic_clone();
-
-static VALUE
-Sdic_create(argc, argv, class)
- int argc;
- VALUE *argv;
- VALUE class;
-{
- struct RDict *dic;
- int i;
-
- if (argc == 1 && TYPE(argv[0]) == T_DICT) {
- if (class == CLASS_OF(argv[0])) return argv[0];
- else {
- NEWOBJ(dic, struct RDict);
- OBJSETUP(dic, class, T_DICT);
- dic->tbl = (st_table*)st_copy(RDICT(argv[0])->tbl);
-
- return (VALUE)dic;
- }
- }
-
- if (argc % 2 != 0) {
- Fail("odd number args for Dict");
- }
- dic = (struct RDict*)Sdic_new(class);
-
- for (i=0; i<argc; i+=2) {
- st_insert(dic->tbl, argv[i], argv[i+1]);
- }
-
- return (VALUE)dic;
-}
-
-VALUE
-dic_new()
-{
- return Sdic_new(C_Dict);
-}
-
-static VALUE
-Fdic_clone(dic)
- struct RDict *dic;
-{
- NEWOBJ(dic2, struct RDict);
- CLONESETUP(dic2, dic);
-
- dic2->tbl = (st_table*)st_copy(dic->tbl);
-
- return (VALUE)dic2;
-}
-
-static VALUE
-Fdic_aref(dic, key)
- struct RDict *dic;
- VALUE key;
-{
- VALUE val = Qnil;
-
- if (!st_lookup(dic->tbl, key, &val)) {
- return Qnil;
- }
- return val;
-}
-
-static VALUE
-Fdic_indexes(dic, args)
- struct RDict *dic;
- struct RArray *args;
-{
- VALUE *p, *pend;
- struct RArray *new;
- int i = 0;
-
- if (!args || args->len == 0) {
- Fail("wrong # of argment");
- }
- else if (args->len == 1) {
- if (TYPE(args->ptr[0])) {
- args = (struct RArray*)rb_to_a(args->ptr[0]);
- }
- else {
- args = (struct RArray*)args->ptr[0];
- }
- }
-
- new = (struct RArray*)ary_new2(args->len);
-
- p = args->ptr; pend = p + args->len;
- while (p < pend) {
- new->ptr[i++] = Fdic_aref(dic, *p++);
- }
- new->len = i;
- return (VALUE)new;
-}
-
-static VALUE
-Fdic_delete(dic, key)
- struct RDict *dic;
- VALUE key;
-{
- VALUE val;
-
- if (st_delete(dic->tbl, &key, &val))
- return val;
- return Qnil;
-}
-
-static int
-dic_delete_if(key, value)
- VALUE key, value;
-{
- if (rb_yield(assoc_new(key, value)))
- return ST_DELETE;
- return ST_CONTINUE;
-}
-
-static VALUE
-Fdic_delete_if(dic)
- struct RDict *dic;
-{
- st_foreach(dic->tbl, dic_delete_if, Qnil);
-
- return (VALUE)dic;
-}
-
-static
-dic_clear(key, value)
- VALUE key, value;
-{
- return ST_DELETE;
-}
-
-static VALUE
-Fdic_clear(dic)
- struct RDict *dic;
-{
- st_foreach(dic->tbl, dic_clear, Qnil);
-
- return (VALUE)dic;
-}
-
-VALUE
-Fdic_aset(dic, key, val)
- struct RDict *dic;
- VALUE key, val;
-{
- if (val == Qnil) {
- Fdic_delete(dic, key);
- return Qnil;
- }
- st_insert(dic->tbl, key, val);
- return val;
-}
-
-static VALUE
-Fdic_length(dic)
- struct RDict *dic;
-{
- return INT2FIX(dic->tbl->num_entries);
-}
-
-static
-dic_each_value(key, value)
- VALUE key, value;
-{
- rb_yield(value);
- return ST_CONTINUE;
-}
-
-static VALUE
-Fdic_each_value(dic)
- struct RDict *dic;
-{
- st_foreach(dic->tbl, dic_each_value);
- return (VALUE)dic;
-}
-
-static
-dic_each_key(key, value)
- VALUE key, value;
-{
- rb_yield(key);
- return ST_CONTINUE;
-}
-
-static VALUE
-Fdic_each_key(dic)
- struct RDict *dic;
-{
- st_foreach(dic->tbl, dic_each_key);
- return (VALUE)dic;
-}
-
-static
-dic_each_pair(key, value)
- VALUE key, value;
-{
- rb_yield(assoc_new(key, value));
- return ST_CONTINUE;
-}
-
-static VALUE
-Fdic_each_pair(dic)
- struct RDict *dic;
-{
- st_foreach(dic->tbl, dic_each_pair);
- return (VALUE)dic;
-}
-
-static
-dic_to_a(key, value, ary)
- VALUE key, value, ary;
-{
- ary_push(ary, assoc_new(key, value));
- return ST_CONTINUE;
-}
-
-static VALUE
-Fdic_to_a(dic)
- struct RDict *dic;
-{
- VALUE ary;
-
- ary = ary_new();
- st_foreach(dic->tbl, dic_to_a, ary);
-
- return ary;
-}
-
-static
-dic_inspect(key, value, str)
- VALUE key, value;
- struct RString *str;
-{
- VALUE str2;
- ID inspect = rb_intern("_inspect");
-
- if (str->len > 1) {
- str_cat(str, ", ", 2);
- }
- str2 = rb_funcall(key, inspect, 0, Qnil);
- str_cat(str, RSTRING(str2)->ptr, RSTRING(str2)->len);
- str_cat(str, "=>", 2);
- str2 = rb_funcall(value, inspect, 0, Qnil);
- str_cat(str, RSTRING(str2)->ptr, RSTRING(str2)->len);
-
- return ST_CONTINUE;
-}
-
-static VALUE
-Fdic_inspect(dic)
- struct RDict *dic;
-{
- VALUE str;
-
- str = str_new2("{");
- st_foreach(dic->tbl, dic_inspect, str);
- str_cat(str, "}", 1);
-
- return str;
-}
-
-static VALUE
-Fdic_to_s(dic)
- VALUE dic;
-{
- return Fary_to_s(Fdic_to_a(dic));
-}
-
-static
-dic_keys(key, value, ary)
- VALUE key, value, ary;
-{
- ary_push(ary, key);
- return ST_CONTINUE;
-}
-
-static VALUE
-Fdic_keys(dic)
- struct RDict *dic;
-{
- VALUE ary;
-
- ary = ary_new();
- st_foreach(dic->tbl, dic_keys, ary);
-
- return ary;
-}
-
-static
-dic_values(key, value, ary)
- VALUE key, value, ary;
-{
- ary_push(ary, key);
- return ST_CONTINUE;
-}
-
-static VALUE
-Fdic_values(dic)
- struct RDict *dic;
-{
- VALUE ary;
-
- ary = ary_new();
- st_foreach(dic->tbl, dic_values, ary);
-
- return ary;
-}
-
-static VALUE
-Fdic_has_key(dic, key)
- struct RDict *dic;
- VALUE key;
-{
- VALUE val;
-
- if (st_lookup(dic->tbl, key, &val))
- return TRUE;
- return FALSE;
-}
-
-static int
-dic_search_value(key, value, data)
- VALUE key, value, *data;
-{
- if (rb_equal(value, data[1])) {
- data[0] = TRUE;
- return ST_STOP;
- }
- return ST_CONTINUE;
-}
-
-static VALUE
-Fdic_has_value(dic, val)
- struct RDict *dic;
- VALUE val;
-{
- VALUE data[2];
-
- data[0] = FALSE;
- data[1] = val;
- st_foreach(dic->tbl, dic_search_value, data);
- return data[0];
-}
-
-struct equal_data {
- int result;
- st_table *tbl;
-};
-
-static int
-dic_equal(key, val1, data)
- VALUE key, val1;
- struct equal_data *data;
-{
- VALUE val2;
-
- if (!st_lookup(data->tbl, key, &val2)) {
- data->result = FALSE;
- return ST_STOP;
- }
- if (!rb_equal(val1, val2)) {
- data->result = FALSE;
- return ST_STOP;
- }
- return ST_CONTINUE;
-}
-
-static VALUE
-Fdic_equal(dic1, dic2)
- struct RDict *dic1, *dic2;
-{
- struct equal_data data;
-
- if (TYPE(dic2) != T_DICT) return FALSE;
- if (dic1->tbl->num_entries != dic2->tbl->num_entries)
- return FALSE;
-
- data.tbl = dic2->tbl;
- data.result = TRUE;
- st_foreach(dic1->tbl, dic_equal, &data);
-
- return data.result;
-}
-
-static int
-dic_hash(key, val, data)
- VALUE key, val;
- int *data;
-{
- *data ^= rb_funcall(key, hash, 0);
- *data ^= rb_funcall(val, hash, 0);
- return ST_CONTINUE;
-}
-
-static VALUE
-Fdic_hash(dic)
- struct RDict *dic;
-{
- int h;
-
- st_foreach(dic->tbl, dic_hash, &h);
- return INT2FIX(h);
-}
-
-char *strchr();
-extern VALUE rb_readonly_hook();
-
-extern char **environ;
-
-static VALUE
-Fenv_each(dic)
- VALUE dic;
-{
- char **env;
-
- env = environ;
- while (*env) {
- VALUE var, val;
- char *s = strchr(*env, '=');
-
- var = str_new(*env, s-*env);
- val = str_new2(s+1);
- rb_yield(assoc_new(var, val));
- env++;
- }
- return dic;
-}
-
-static VALUE
-Fenv_delete(obj, name)
- VALUE obj;
- struct RString *name;
-{
- int i, len;
- char *nam, *val = Qnil;
-
- Check_Type(name, T_STRING);
- nam = name->ptr;
- len = strlen(nam);
- for(i=0; environ[i]; i++) {
- if (strncmp(environ[i], nam, len) == 0 && environ[i][len] == '=') {
- val = environ[i]+len+1;
- break;
- }
- }
- while (environ[i]) {
- environ[i] = environ[i+1];
- i++;
- }
- if (val) {
- return str_new2(val);
- }
- return Qnil;
-}
-
-VALUE
-Fgetenv(obj, name)
- VALUE obj;
- struct RString *name;
-{
- extern char *getenv();
- char *env;
-
- Check_Type(name, T_STRING);
-
- if (strlen(name->ptr) != name->len)
- Fail("Bad environment name");
-
- env = getenv(name->ptr);
- if (env) {
- return str_new2(env);
- }
- return Qnil;
-}
-
-VALUE
-Fsetenv(obj, name, value)
- VALUE obj;
- struct RString *name, *value;
-{
- Check_Type(name, T_STRING);
- if (value == Qnil) {
- Fenv_delete(obj, name);
- return Qnil;
- }
-
- Check_Type(value, T_STRING);
-
- if (strlen(name->ptr) != name->len)
- Fail("Bad environment name");
- if (strlen(value->ptr) != value->len)
- Fail("Bad environment value");
-
-#ifdef HAVE_SETENV
- if (setenv(name->ptr, value->ptr, 1) == 0) return TRUE;
-#else
-#ifdef HAVE_PUTENV
- {
- char *str;
- int len;
-
- str = ALLOC_N(char, name->len + value->len + 2);
- sprintf("%s=%s", name->ptr, value->ptr);
- if (putenv(str) == 0) return TRUE;
- }
-#else
- Fail("setenv is not supported on this system");
-#endif
-#endif
-
- Fail("setenv failed");
- return FALSE; /* not reached */
-}
-
-static VALUE
-Fenv_to_s()
-{
- return str_new2("$ENV");
-}
-
-Init_Dict()
-{
- extern VALUE C_Kernel;
- extern VALUE M_Enumerable;
-
- hash = rb_intern("hash");
-
- C_Dict = rb_define_class("Dict", C_Object);
-
- rb_include_module(C_Dict, M_Enumerable);
-
- rb_define_single_method(C_Dict, "new", Sdic_new, 0);
- rb_define_single_method(C_Dict, "[]", Sdic_create, -1);
-
- rb_define_method(C_Dict,"clone", Fdic_clone, 0);
-
- rb_define_method(C_Dict,"to_a", Fdic_to_a, 0);
- rb_define_method(C_Dict,"to_s", Fdic_to_s, 0);
- rb_define_method(C_Dict,"_inspect", Fdic_inspect, 0);
-
- rb_define_method(C_Dict,"==", Fdic_equal, 1);
- rb_define_method(C_Dict,"hash", Fdic_hash, 0);
- rb_define_method(C_Dict,"[]", Fdic_aref, 1);
- rb_define_method(C_Dict,"[]=", Fdic_aset, 2);
- rb_define_method(C_Dict,"indexes", Fdic_indexes, -2);
- rb_define_method(C_Dict,"length", Fdic_length, 0);
- rb_define_alias(C_Dict, "size", "length");
- rb_define_method(C_Dict,"each", Fdic_each_pair, 0);
- rb_define_method(C_Dict,"each_value", Fdic_each_value, 0);
- rb_define_method(C_Dict,"each_key", Fdic_each_key, 0);
- rb_define_method(C_Dict,"each_pair", Fdic_each_pair, 0);
-
- rb_define_method(C_Dict,"keys", Fdic_keys, 0);
- rb_define_method(C_Dict,"values", Fdic_values, 0);
-
- rb_define_method(C_Dict,"delete", Fdic_delete, 1);
- rb_define_method(C_Dict,"delete_if", Fdic_delete_if, 0);
- rb_define_method(C_Dict,"clear", Fdic_clear, 0);
-
- rb_define_method(C_Dict,"includes", Fdic_has_key, 1);
- rb_define_method(C_Dict,"has_key", Fdic_has_key, 1);
- rb_define_method(C_Dict,"has_value", Fdic_has_value, 1);
-
- envtbl = obj_alloc(C_Object);
- rb_extend_object(envtbl, M_Enumerable);
-
- rb_define_single_method(envtbl,"[]", Fgetenv, 1);
- rb_define_single_method(envtbl,"[]=", Fsetenv, 2);
- rb_define_single_method(envtbl,"each", Fenv_each, 0);
- rb_define_single_method(envtbl,"delete", Fenv_delete, 1);
- rb_define_single_method(envtbl,"to_s", Fenv_to_s, 0);
-
- rb_define_variable("$ENV", &envtbl, Qnil, rb_readonly_hook, 0);
- rb_define_const(C_Kernel, "ENV", envtbl);
-}
diff --git a/dir.c b/dir.c
index f50c760e2f..c3ec434ea2 100644
--- a/dir.c
+++ b/dir.c
@@ -18,6 +18,12 @@
#include <unistd.h>
#endif
+#ifdef HAVE_STDLIB_H
+#include <stdlib.h>
+#else
+char *getenv();
+#endif
+
/* unistd.h defines _POSIX_VERSION on POSIX.1 systems. */
#if defined(DIRENT) || defined(_POSIX_VERSION)
#include <dirent.h>
@@ -145,8 +151,6 @@ Fdir_close(dir)
return Qnil;
}
-char *getenv();
-
static VALUE
Sdir_chdir(argc, argv, obj)
int argc;
diff --git a/dln.c b/dln.c
index e0be1808eb..13b6930f37 100644
--- a/dln.c
+++ b/dln.c
@@ -10,162 +10,132 @@
************************************************/
-#include <stdio.h>
-#include <sys/param.h>
-#include <sys/file.h>
#include "config.h"
#include "defines.h"
#include "dln.h"
-#include <sys/types.h>
-#ifdef HAVE_UNISTD_H
-#include <unistd.h>
-#endif
-char *strdup();
+#if defined(HAVE_ALLOCA_H) && !defined(__GNUC__)
+#include <alloca.h>
+#endif
-extern int errno;
-int dln_errno;
+#include <stdio.h>
+#include <sys/param.h>
+#include <sys/file.h>
-static int dln_init_p = 0;
+#ifdef HAVE_STDLIB_H
+# include <stdlib.h>
+#else
+char *getenv();
+#endif
-#include <sys/stat.h>
+#if defined (HAVE_STRING_H)
+# include <string.h>
+#else /* !HAVE_STRING_H */
+# include <strings.h>
+#endif /* !HAVE_STRING_H */
-static char fbuf[MAXPATHLEN];
-static char *dln_find_1();
-char *getenv();
-char *strchr();
-int strcmp();
+#ifdef RUBY
+int eaccess();
+#endif
-char *
-dln_find_exe(fname, path)
- char *fname;
- char *path;
+#ifdef USE_DL
+static void
+init_funcname(buf, file)
+ char *buf, *file;
{
- if (!path) path = getenv("PATH");
- if (!path) path = "/usr/local/bin:/usr/ucb:/usr/bin:/bin:.";
- return dln_find_1(fname, path, 1);
+ char *p, *slash;
+
+ /* Load the file as an object one */
+ for (p = file, slash = p-1; *p; p++) /* Find position of last '/' */
+ if (*p == '/') slash = p;
+
+ sprintf(buf, "init_%s", slash + 1);
+ for (p = buf; *p; p++) { /* Delete suffix it it exists */
+ if (*p == '.') {
+ *p = '\0'; break;
+ }
+ }
}
-char *
-dln_find_file(fname, path)
- char *fname;
- char *path;
+# if defined(HAVE_DLOPEN) && !defined(USE_MY_DLN)
+
+/* dynamic load with dlopen() */
+#include <dlfcn.h>
+
+int
+dln_init(file)
+ char *file;
{
- if (!path) path = ".";
- return dln_find_1(fname, path, 0);
+ return 0;
}
-static char *
-dln_find_1(fname, path, exe_flag)
- char *fname;
- char *path;
- int exe_flag; /* non 0 if looking for executable. */
+int
+dln_load(file)
+ char *file;
{
- register char *dp;
- register char *ep;
- register char *bp;
- struct stat st;
+ void *handle;
+ char buf[MAXPATHLEN];
+ void (*init_fct)();
+ int len = strlen(file);
+#ifndef RTLD_LAZY
+# define RTLD_LAZY 1
+#endif
- if (fname[0] == '/') return fname;
+ strcpy(buf, file);
+ if (len > 3
+ && (buf[len-1] == 'o' || buf[len-1] == 'a')
+ && buf[len-2] == '.') {
+ buf[len-1] = 's'; buf[len] = 'o'; buf[len+1] = '\0';
+ }
- for (dp = path;; dp = ++ep)
- {
- register int l;
- int i;
- int fspace;
+ /* Load file */
+ if ((handle = dlopen(buf, RTLD_LAZY)) == NULL) {
+ return -1;
+ }
- /* extract a component */
- ep = strchr(dp, ':');
- if (ep == NULL)
- ep = dp+strlen(dp);
+ /* Load the file as an object one */
+ init_funcname(buf, file);
- /* find the length of that component */
- l = ep - dp;
- bp = fbuf;
- fspace = sizeof fbuf - 2;
- if (l > 0)
- {
- /*
- ** If the length of the component is zero length,
- ** start from the current directory. If the
- ** component begins with "~", start from the
- ** user's $HOME environment variable. Otherwise
- ** take the path literally.
- */
+ if ((init_fct = dlsym(handle, buf)) == NULL) {
+ buf[0] = 'I'; /* try Init_.. */
+ if ((init_fct = dlsym(handle, buf)) == NULL) {
+ return -1;
+ }
+ }
+ /* Call the init code */
+ (*init_fct)();
- if (*dp == '~' && (l == 1 || dp[1] == '/'))
- {
- char *home;
+ return 0;
+}
- home = getenv("HOME");
- if (home != NULL)
- {
- i = strlen(home);
- if ((fspace -= i) < 0)
- goto toolong;
- memcpy(bp, home, i);
- bp += i;
- }
- dp++;
- l--;
- }
- if (l > 0)
- {
- if ((fspace -= l) < 0)
- goto toolong;
- memcpy(bp, dp, l);
- bp += l;
- }
+char *
+dln_strerror()
+{
+ return dlerror();
+}
- /* add a "/" between directory and filename */
- if (ep[-1] != '/')
- *bp++ = '/';
- }
+int
+dln_load_lib(lib)
+ char *lib;
+{
+ return 0;
+}
- /* now append the file name */
- i = strlen(fname);
- if ((fspace -= i) < 0)
- {
- toolong:
- fprintf(stderr, "openpath: pathname too long (ignored)\n");
- *bp = '\0';
- fprintf(stderr, "\tDirectory \"%s\"\n", fbuf);
- fprintf(stderr, "\tFile \"%s\"\n", fname);
- continue;
- }
- memcpy(bp, fname, i + 1);
+# else
- if (stat(fbuf, &st) == 0) {
- if (exe_flag == 0) return fbuf;
- /* looking for executable */
-#ifdef RUBY
- if (eaccess(fbuf, X_OK) == 0) return fbuf;
-#else
- {
- uid_t uid = getuid();
- gid_t gid = getgid();
+#include <errno.h>
- if (uid == st.st_uid &&
- (st.st_mode & S_IEXEC) ||
- gid == st.st_gid &&
- (st.st_mode & (S_IEXEC>>3)) ||
- st.st_mode & (S_IEXEC>>6)) {
- return fbuf;
- }
- }
-#endif
- }
- /* if not, and no other alternatives, life is bleak */
- if (*ep == '\0') {
- dln_errno = DLN_ENOENT;
- return NULL;
- }
+static int dln_errno;
- /* otherwise try the next component in the search path */
- }
-}
+#define DLN_ENOEXEC ENOEXEC /* Exec format error */
+#define DLN_ECONFL 101 /* Symbol name conflict */
+#define DLN_ENOINIT 102 /* No inititalizer given */
+#define DLN_EUNDEF 103 /* Undefine symbol remains */
+#define DLN_ENOTLIB 104 /* Not a library file */
+#define DLN_EBADLIB 105 /* Malformed library file */
+#define DLN_EINIT 106 /* Not initialized */
-#ifdef USE_DLN
+static int dln_init_p = 0;
#include "st.h"
#include <ar.h>
@@ -573,10 +543,11 @@ unlink_undef(name, value)
st_foreach(reloc_tbl, reloc_undef, &arg);
}
-static int dln_load_1(fd, disp, need_init)
+static int
+dln_load_1(fd, disp, need_init)
int fd;
long disp;
- int need_init;
+ char *need_init;
{
static char *libc = LIBC_NAME;
struct exec hdr;
@@ -587,6 +558,7 @@ static int dln_load_1(fd, disp, need_init)
struct nlist *sym;
struct nlist *end;
int init_p = 0;
+ char buf[256];
if (dln_load_header(fd, &hdr, disp) == -1) return -1;
if (INVALID_OBJECT(hdr)) {
@@ -764,21 +736,38 @@ static int dln_load_1(fd, disp, need_init)
}
if (need_init) {
+ int len;
+
if (undef_tbl->num_entries > 0) {
if (dln_load_lib(libc) == -1) goto err_exit;
}
+ init_funcname(buf, need_init);
+ len = strlen(buf);
+
+#if 1
sym = syms;
while (sym < end) {
char *name = sym->n_un.n_name;
if (name[0] == '_' && sym->n_value >= block
- && ((bcmp (name, "_Init_", 6) == 0
+ && ((bcmp (name, "_Init_", 6) == 0
|| bcmp (name, "_init_", 6) == 0) && name[6] != '_')) {
init_p = 1;
((int (*)())sym->n_value)();
}
sym++;
}
+#else
+ for (sym = syms; sym<end; sym++) {
+ char *name = sym->n_un.n_name;
+ if (name[0] == '_' && sym->n_value >= block
+ && (name[1] == 'i' || name[1] == 'I')
+ && bcmp(name+2, buf+1, len-1) == 0) {
+ init_p = 1;
+ ((int (*)())sym->n_value)();
+ }
+ }
+#endif
}
free(reloc);
free(syms);
@@ -815,13 +804,17 @@ dln_load(file)
dln_errno = DLN_ENOINIT;
return -1;
}
+ result = strlen(file);
+ if (file[result-1] == 'a') {
+ return dln_load_lib(file);
+ }
fd = open(file, O_RDONLY);
if (fd == -1) {
dln_errno = errno;
return -1;
}
- result = dln_load_1(fd, 0, 1);
+ result = dln_load_1(fd, 0, file);
close(fd);
return result;
@@ -873,6 +866,12 @@ dln_load_lib(lib)
if (undef_tbl->num_entries == 0) return 0;
dln_errno = DLN_EBADLIB;
+ if (lib[0] == '-' && lib[1] == 'l') {
+ char *p = alloca(strlen(lib) + 4);
+ sprintf(p, "lib%s.a", lib+2);
+ lib = p;
+ }
+
/* library search path: */
/* look for environment variable DLN_LIBRARY_PATH first. */
/* then variable dln_library_path. */
@@ -983,6 +982,17 @@ dln_load_lib(lib)
return -1;
}
+void*
+dln_sym(name)
+ char *name;
+{
+ struct nlist *sym;
+
+ if (st_lookup(sym_tbl, name, &sym))
+ return (void*)sym->n_value;
+ return NULL;
+}
+
char *
dln_strerror()
{
@@ -1006,87 +1016,144 @@ dln_strerror()
}
}
-dln_perror(str)
- char *str;
-{
- fprintf(stderr, "%s: %s\n", str, dln_strerror());
-}
-
-void*
-dln_get_sym(name)
- char *name;
-{
- struct nlist *sym;
+# endif
+#endif /* USE_DL */
- if (st_lookup(sym_tbl, name, &sym))
- return (void*)sym->n_value;
- return NULL;
-}
+static char *dln_find_1();
-#ifdef TEST
-xmalloc(size)
- int size;
+char *
+dln_find_exe(fname, path)
+ char *fname;
+ char *path;
{
- return malloc(size);
+ if (!path) path = getenv("PATH");
+ if (!path) path = "/usr/local/bin:/usr/ucb:/usr/bin:/bin:.";
+ return dln_find_1(fname, path, 1);
}
-xcalloc(size, n)
- int size, n;
+char *
+dln_find_file(fname, path)
+ char *fname;
+ char *path;
{
- return calloc(size, n);
+ if (!path) path = ".";
+ return dln_find_1(fname, path, 0);
}
-main(argc, argv)
- int argc;
- char **argv;
+static char fbuf[MAXPATHLEN];
+
+static char *
+dln_find_1(fname, path, exe_flag)
+ char *fname;
+ char *path;
+ int exe_flag; /* non 0 if looking for executable. */
{
- if (dln_init(argv[0]) == -1) {
- dln_perror("dln_init");
- exit(1);
- }
+ register char *dp;
+ register char *ep;
+ register char *bp;
+ struct stat st;
+
+ if (fname[0] == '/') return fname;
+
+ for (dp = path;; dp = ++ep)
+ {
+ register int l;
+ int i;
+ int fspace;
+
+ /* extract a component */
+ ep = strchr(dp, ':');
+ if (ep == NULL)
+ ep = dp+strlen(dp);
+
+ /* find the length of that component */
+ l = ep - dp;
+ bp = fbuf;
+ fspace = sizeof fbuf - 2;
+ if (l > 0)
+ {
+ /*
+ ** If the length of the component is zero length,
+ ** start from the current directory. If the
+ ** component begins with "~", start from the
+ ** user's $HOME environment variable. Otherwise
+ ** take the path literally.
+ */
+
+ if (*dp == '~' && (l == 1 || dp[1] == '/'))
+ {
+ char *home;
+
+ home = getenv("HOME");
+ if (home != NULL)
+ {
+ i = strlen(home);
+ if ((fspace -= i) < 0)
+ goto toolong;
+ memcpy(bp, home, i);
+ bp += i;
+ }
+ dp++;
+ l--;
+ }
+ if (l > 0)
+ {
+ if ((fspace -= l) < 0)
+ goto toolong;
+ memcpy(bp, dp, l);
+ bp += l;
+ }
- while (argc > 1) {
- printf("obj: %s\n", argv[1]);
- if (dln_load(argv[1]) == -1) {
- dln_perror("dln_load");
- exit(1);
+ /* add a "/" between directory and filename */
+ if (ep[-1] != '/')
+ *bp++ = '/';
}
- argc--;
- argv++;
- }
- if (dln_load_lib("libdln.a") == -1) {
- dln_perror("dln_init");
- exit(1);
- }
- if (dln_get_sym("_foo"))
- printf("_foo defined\n");
- else
- printf("_foo undefined\n");
-}
-#endif /* TEST */
+ /* now append the file name */
+ i = strlen(fname);
+ if ((fspace -= i) < 0)
+ {
+ toolong:
+ fprintf(stderr, "openpath: pathname too long (ignored)\n");
+ *bp = '\0';
+ fprintf(stderr, "\tDirectory \"%s\"\n", fbuf);
+ fprintf(stderr, "\tFile \"%s\"\n", fname);
+ continue;
+ }
+ memcpy(bp, fname, i + 1);
-#else /* USE_DLN */
+ if (stat(fbuf, &st) == 0) {
+ if (exe_flag == 0) return fbuf;
+ /* looking for executable */
+#ifdef RUBY
+ if (eaccess(fbuf, X_OK) == 0) return fbuf;
+#else
+ {
+ uid_t uid = getuid();
+ gid_t gid = getgid();
-int
-dln_init(file)
- char *file;
-{
- return 0;
-}
+ if (uid == st.st_uid &&
+ (st.st_mode & S_IEXEC) ||
+ gid == st.st_gid &&
+ (st.st_mode & (S_IEXEC>>3)) ||
+ st.st_mode & (S_IEXEC>>6)) {
+ return fbuf;
+ }
+ }
+#endif
+ }
+ /* if not, and no other alternatives, life is bleak */
+ if (*ep == '\0') {
+ return NULL;
+ }
-int
-dln_load(file)
- char *file;
-{
- return 0;
+ /* otherwise try the next component in the search path */
+ }
}
-int
-dln_load_lib(file)
- char *file;
+void
+dln_perror(str)
+ char *str;
{
- return 0;
+ fprintf(stderr, "%s: %s\n", str, dln_strerror());
}
-
-#endif /* USE_DLN */
diff --git a/dln.h b/dln.h
index e2370e1aa1..ce39b29ae5 100644
--- a/dln.h
+++ b/dln.h
@@ -13,21 +13,14 @@
#include <sys/errno.h>
+char *dln_find_exe();
+char *dln_find_file();
+
int dln_init();
int dln_load();
int dln_load_lib();
-extern int dln_errno;
-
-#define DLN_ENOENT ENOENT /* No such file or directory */
-#define DLN_ENOEXEC ENOEXEC /* Exec format error */
-#define DLN_ECONFL 101 /* Symbol name conflict */
-#define DLN_ENOINIT 102 /* No inititalizer given */
-#define DLN_EUNDEF 103 /* Undefine symbol remains */
-#define DLN_ENOTLIB 104 /* Not a library file */
-#define DLN_EBADLIB 105 /* Malformed library file */
-#define DLN_EINIT 106 /* Not initialized */
-
char *dln_strerror();
+void dln_perror();
#endif
diff --git a/error.c b/error.c
index 1e0363e736..89c38065da 100644
--- a/error.c
+++ b/error.c
@@ -166,7 +166,7 @@ static char *builtin_types[] = {
"Regexp",
"Array",
"Fixnum",
- "Dict",
+ "Hash",
"Data",
"Method",
"Struct",
diff --git a/eval.c b/eval.c
index 58a8354864..ed3860a2ee 100644
--- a/eval.c
+++ b/eval.c
@@ -18,6 +18,19 @@
#include <stdio.h>
#include <setjmp.h>
#include "st.h"
+#include "dln.h"
+
+#ifdef HAVE_STRING_H
+# include <string.h>
+#else
+char *strchr();
+#endif
+
+#ifdef HAVE_STDLIB_H
+#include <stdlib.h>
+#else
+char *getenv();
+#endif
static void rb_clear_cache_body();
static void rb_clear_cache_entry();
@@ -1113,7 +1126,7 @@ rb_eval(node)
case NODE_HASH:
{
NODE *list;
- VALUE hash = dic_new();
+ VALUE hash = hash_new();
VALUE key, val;
list = node->nd_head;
@@ -1121,10 +1134,10 @@ rb_eval(node)
key = rb_eval(list->nd_head);
list = list->nd_next;
if (list == Qnil)
- Bug("odd number list for Dict");
+ Bug("odd number list for Hash");
val = rb_eval(list->nd_head);
list = list->nd_next;
- Fdic_aset(hash, key, val);
+ Fhash_aset(hash, key, val);
}
return hash;
}
@@ -1266,7 +1279,7 @@ rb_eval(node)
while (TYPE(tmp) == T_ICLASS) {
tmp = RCLASS(tmp)->super;
}
- if (tmp != super)
+ if (tmp != RCLASS(super))
Fail("%s's superclass differs",
rb_id2name(node->nd_cname));
}
@@ -2220,13 +2233,16 @@ Fload(obj, fname)
Check_Type(fname, T_STRING);
file = find_file(fname->ptr);
-#ifdef USE_DLN
+#ifdef USE_DL
{
static int rb_dln_init = 0;
extern char *rb_dln_argv0;
int len = strlen(file);
- if (len > 2 && file[len-1] == 'o' && file[len-2] == '.') {
+ if (len > 3
+ && file[len-1] == 'o' && file[len-2] == '.'
+ || len > 4
+ && file[len-1] == 'o' && file[len-2] == 's' && file[len-3] == '.'){
if (rb_dln_init == 0 && dln_init(rb_dln_argv0) == -1) {
Fail("%s: %s", rb_dln_argv0, dln_strerror());
}
@@ -2288,9 +2304,6 @@ Frequire(obj, fname)
return TRUE;
}
-char *getenv();
-char *strchr();
-
#ifndef RUBY_LIB
#define RUBY_LIB "/usr/local/lib/ruby:."
#endif
diff --git a/gc.c b/gc.c
index 9c9a2a2ed9..2daf0d1270 100644
--- a/gc.c
+++ b/gc.c
@@ -177,7 +177,7 @@ typedef struct RVALUE {
struct RString string;
struct RArray array;
struct RRegexp regexp;
- struct RDict dict;
+ struct RHash hash;
struct RData data;
struct RStruct rstruct;
struct RBignum bignum;
@@ -326,7 +326,7 @@ mark_tbl(tbl)
}
static
-mark_dicentry(key, value)
+mark_hashentry(key, value)
ID key;
VALUE value;
{
@@ -336,10 +336,10 @@ mark_dicentry(key, value)
}
static
-mark_dict(tbl)
+mark_hash(tbl)
st_table *tbl;
{
- st_foreach(tbl, mark_dicentry, 0);
+ st_foreach(tbl, mark_hashentry, 0);
}
void
@@ -408,8 +408,8 @@ gc_mark(obj)
}
break;
- case T_DICT:
- mark_dict(obj->as.dict.tbl);
+ case T_HASH:
+ mark_hash(obj->as.hash.tbl);
break;
case T_STRING:
@@ -523,8 +523,8 @@ obj_free(obj)
case T_ARRAY:
free(obj->as.array.ptr);
break;
- case T_DICT:
- st_free_table(obj->as.dict.tbl);
+ case T_HASH:
+ st_free_table(obj->as.hash.tbl);
break;
case T_REGEXP:
reg_free(obj->as.regexp.ptr);
diff --git a/inits.c b/inits.c
index ce93514a47..e575e4bccd 100644
--- a/inits.c
+++ b/inits.c
@@ -24,7 +24,7 @@ rb_call_inits()
Init_Numeric();
Init_Bignum();
Init_Array();
- Init_Dict();
+ Init_Hash();
Init_Struct();
Init_String();
Init_Regexp();
@@ -40,12 +40,6 @@ rb_call_inits()
Init_load();
Init_Block();
Init_Math();
-#ifdef USE_DBM
- Init_DBM();
-#endif
-#ifdef HAVE_SOCKET
- Init_Socket();
-#endif
/* new Inits comes between here.. */
/* .. and here. */
diff --git a/install-sh b/install-sh
new file mode 100755
index 0000000000..89fc9b098b
--- /dev/null
+++ b/install-sh
@@ -0,0 +1,238 @@
+#! /bin/sh
+#
+# install - install a program, script, or datafile
+# This comes from X11R5.
+#
+# Calling this script install-sh is preferred over install.sh, to prevent
+# `make' implicit rules from creating a file called install from it
+# when there is no Makefile.
+#
+# This script is compatible with the BSD install script, but was written
+# from scratch.
+#
+
+
+# set DOITPROG to echo to test this script
+
+# Don't use :- since 4.3BSD and earlier shells don't like it.
+doit="${DOITPROG-}"
+
+
+# put in absolute paths if you don't have them in your path; or use env. vars.
+
+mvprog="${MVPROG-mv}"
+cpprog="${CPPROG-cp}"
+chmodprog="${CHMODPROG-chmod}"
+chownprog="${CHOWNPROG-chown}"
+chgrpprog="${CHGRPPROG-chgrp}"
+stripprog="${STRIPPROG-strip}"
+rmprog="${RMPROG-rm}"
+mkdirprog="${MKDIRPROG-mkdir}"
+
+tranformbasename=""
+transform_arg=""
+instcmd="$mvprog"
+chmodcmd="$chmodprog 0755"
+chowncmd=""
+chgrpcmd=""
+stripcmd=""
+rmcmd="$rmprog -f"
+mvcmd="$mvprog"
+src=""
+dst=""
+dir_arg=""
+
+while [ x"$1" != x ]; do
+ case $1 in
+ -c) instcmd="$cpprog"
+ shift
+ continue;;
+
+ -d) dir_arg=true
+ shift
+ continue;;
+
+ -m) chmodcmd="$chmodprog $2"
+ shift
+ shift
+ continue;;
+
+ -o) chowncmd="$chownprog $2"
+ shift
+ shift
+ continue;;
+
+ -g) chgrpcmd="$chgrpprog $2"
+ shift
+ shift
+ continue;;
+
+ -s) stripcmd="$stripprog"
+ shift
+ continue;;
+
+ -t=*) transformarg=`echo $1 | sed 's/-t=//'`
+ shift
+ continue;;
+
+ -b=*) transformbasename=`echo $1 | sed 's/-b=//'`
+ shift
+ continue;;
+
+ *) if [ x"$src" = x ]
+ then
+ src=$1
+ else
+ # this colon is to work around a 386BSD /bin/sh bug
+ :
+ dst=$1
+ fi
+ shift
+ continue;;
+ esac
+done
+
+if [ x"$src" = x ]
+then
+ echo "install: no input file specified"
+ exit 1
+else
+ true
+fi
+
+if [ x"$dir_arg" != x ]; then
+ dst=$src
+ src=""
+
+ if [ -d $dst ]; then
+ instcmd=:
+ else
+ instcmd=mkdir
+ fi
+else
+
+# Waiting for this to be detected by the "$instcmd $src $dsttmp" command
+# might cause directories to be created, which would be especially bad
+# if $src (and thus $dsttmp) contains '*'.
+
+ if [ -f $src -o -d $src ]
+ then
+ true
+ else
+ echo "install: $src does not exist"
+ exit 1
+ fi
+
+ if [ x"$dst" = x ]
+ then
+ echo "install: no destination specified"
+ exit 1
+ else
+ true
+ fi
+
+# If destination is a directory, append the input filename; if your system
+# does not like double slashes in filenames, you may need to add some logic
+
+ if [ -d $dst ]
+ then
+ dst="$dst"/`basename $src`
+ else
+ true
+ fi
+fi
+
+## this sed command emulates the dirname command
+dstdir=`echo $dst | sed -e 's,[^/]*$,,;s,/$,,;s,^$,.,'`
+
+# Make sure that the destination directory exists.
+# this part is taken from Noah Friedman's mkinstalldirs script
+
+# Skip lots of stat calls in the usual case.
+if [ ! -d "$dstdir" ]; then
+defaultIFS='
+'
+IFS="${IFS-${defaultIFS}}"
+
+oIFS="${IFS}"
+# Some sh's can't handle IFS=/ for some reason.
+IFS='%'
+set - `echo ${dstdir} | sed -e 's@/@%@g' -e 's@^%@/@'`
+IFS="${oIFS}"
+
+pathcomp=''
+
+while [ $# -ne 0 ] ; do
+ pathcomp="${pathcomp}${1}"
+ shift
+
+ if [ ! -d "${pathcomp}" ] ;
+ then
+ $mkdirprog "${pathcomp}"
+ else
+ true
+ fi
+
+ pathcomp="${pathcomp}/"
+done
+fi
+
+if [ x"$dir_arg" != x ]
+then
+ $doit $instcmd $dst &&
+
+ if [ x"$chowncmd" != x ]; then $doit $chowncmd $dst; else true ; fi &&
+ if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dst; else true ; fi &&
+ if [ x"$stripcmd" != x ]; then $doit $stripcmd $dst; else true ; fi &&
+ if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dst; else true ; fi
+else
+
+# If we're going to rename the final executable, determine the name now.
+
+ if [ x"$transformarg" = x ]
+ then
+ dstfile=`basename $dst`
+ else
+ dstfile=`basename $dst $transformbasename |
+ sed $transformarg`$transformbasename
+ fi
+
+# don't allow the sed command to completely eliminate the filename
+
+ if [ x"$dstfile" = x ]
+ then
+ dstfile=`basename $dst`
+ else
+ true
+ fi
+
+# Make a temp file name in the proper directory.
+
+ dsttmp=$dstdir/#inst.$$#
+
+# Move or copy the file name to the temp name
+
+ $doit $instcmd $src $dsttmp &&
+
+ trap "rm -f ${dsttmp}" 0 &&
+
+# and set any options; do chmod last to preserve setuid bits
+
+# If any of these fail, we abort the whole thing. If we want to
+# ignore errors from any of these, just make sure not to ignore
+# errors from the above "$doit $instcmd $src $dsttmp" command.
+
+ if [ x"$chowncmd" != x ]; then $doit $chowncmd $dsttmp; else true;fi &&
+ if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dsttmp; else true;fi &&
+ if [ x"$stripcmd" != x ]; then $doit $stripcmd $dsttmp; else true;fi &&
+ if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dsttmp; else true;fi &&
+
+# Now rename the file to the real destination.
+
+ $doit $rmcmd -f $dstdir/$dstfile &&
+ $doit $mvcmd $dsttmp $dstdir/$dstfile
+
+fi &&
+
+
+exit 0
diff --git a/io.c b/io.c
index 583353c609..8b7fb21542 100644
--- a/io.c
+++ b/io.c
@@ -816,18 +816,23 @@ next_argv()
VALUE str;
FILE *fw;
- if (!*inplace) {
- Fatal("Can't do inplace edit without backup");
- }
if (rb_defout != rb_stdout) {
Fio_close(rb_defout);
}
fstat(fileno(fr), &st);
- str = str_new2(fn);
- str_cat(str, inplace, strlen(inplace));
- if (rename(fn, RSTRING(str)->ptr) < 0) {
- Warning("Can't rename %s to %s: %s, skipping file",
- fn, RSTRING(str)->ptr, strerror(errno));
+ if (*inplace) {
+ str = str_new2(fn);
+ str_cat(str, inplace, strlen(inplace));
+ if (rename(fn, RSTRING(str)->ptr) < 0) {
+ Warning("Can't rename %s to %s: %s, skipping file",
+ fn, RSTRING(str)->ptr, strerror(errno));
+ fclose(fr);
+ goto retry;
+ }
+ }
+ else if (unlink(fn) < 0) {
+ Warning("Can't remove %s: %s, skipping file",
+ fn, strerror(errno));
fclose(fr);
goto retry;
}
diff --git a/parse.y b/parse.y
index 12e6672ca1..1e560f109e 100644
--- a/parse.y
+++ b/parse.y
@@ -1034,7 +1034,7 @@ assoc_list : /* none */
| args trailer
{
if ($1->nd_alen%2 != 0) {
- Error("odd number list for Dict");
+ Error("odd number list for Hash");
}
$$ = $1;
}
@@ -2117,12 +2117,13 @@ read_escape(flag)
break;
case 'c':
- if (c == '?')
+ if ((c = nextc()) == '?')
tokadd(0177);
else {
if (islower(c))
c = toupper(c);
- tokadd(c ^ 64);
+ c = c - '@';
+ tokadd(c);
}
break;
diff --git a/re.c b/re.c
index 0814f287a4..2744f6fae4 100644
--- a/re.c
+++ b/re.c
@@ -345,7 +345,7 @@ Freg_match(re, str)
Check_Type(str, T_STRING);
start = research(re, str, 0);
- if (start == -1) {
+ if (start < 0) {
return Qnil;
}
return INT2FIX(start);
diff --git a/regex.c b/regex.c
index 1a6d9fa97f..7cdde621d5 100644
--- a/regex.c
+++ b/regex.c
@@ -21,7 +21,7 @@
/* To test, compile with -Dtest. This Dtestable feature turns this into
a self-contained program which reads a pattern, describes how it
compiles, then reads a string and searches for it.
-
+
On the other hand, if you compile with both -Dtest and -Dcanned you
can run some tests we've already thought of. */
@@ -99,12 +99,6 @@ char *alloca ();
/* Get the interface, including the syntax bits. */
#include "regex.h"
-static int re_search_2 P((struct re_pattern_buffer *, char *, int,
- char *, int, int, int,
- struct re_registers *));
-static int re_match_2 P((struct re_pattern_buffer *, char *, int,
- char *, int, int, struct re_registers *));
-
static void store_jump P((char *, int, char *));
static void insert_jump P((int, char *, char *, char *));
static void store_jump_n P((char *, int, char *, unsigned));
@@ -149,7 +143,7 @@ init_syntax_once ()
for (c = '0'; c <= '9'; c++)
re_syntax_table[c] = Sword;
-
+
/* Add specific syntax for ISO Latin-1. */
for (c = 0300; c <= 0377; c++)
re_syntax_table[c] = Sword;
@@ -169,7 +163,7 @@ init_syntax_once ()
argument bytes. A command code can specify any interpretation
whatsoever for its arguments. Zero-bytes may appear in the compiled
regular expression.
-
+
The value of `exactn' is needed in search.c (search_buffer) in emacs.
So regex.h defines a symbol `RE_EXACTN_VALUE' to be 1; the value of
`exactn' we use here must also be 1. */
@@ -235,7 +229,7 @@ enum regexpcode
notwordbound,/* Succeeds if not at a word boundary. */
};
-
+
/* Number of failure points to allocate space for initially,
when matching. If this number is exceeded, more space is allocated,
so it is not a hard limit. */
@@ -250,13 +244,13 @@ enum regexpcode
#ifndef SIGN_EXTEND_CHAR
#define SIGN_EXTEND_CHAR(x) (x)
#endif
-
+
/* Store NUMBER in two contiguous bytes starting at DESTINATION. */
#define STORE_NUMBER(destination, number) \
{ (destination)[0] = (number) & 0377; \
(destination)[1] = (number) >> 8; }
-
+
/* Same as STORE_NUMBER, except increment the destination pointer to
the byte after where the number is stored. Watch out that values for
DESTINATION such as p + 1 won't work, whereas p will. */
@@ -282,7 +276,7 @@ enum regexpcode
/* Specify the precise syntax of regexps for compilation. This provides
for compatibility for various utilities which historically have
different, incompatible syntaxes.
-
+
The argument SYNTAX is a bit-mask comprised of the various bits
defined in regex.h. */
@@ -328,7 +322,7 @@ long re_syntax_options = DEFAULT_MBCTYPE;
GET_BUFFER_SPACE (1); \
*b++ = (char) (ch); \
}
-
+
/* Extend the buffer by twice its current size via reallociation and
reset the pointers that pointed into the old allocation to point to
the correct places in the new allocation. If extending the buffer
@@ -532,71 +526,71 @@ re_compile_pattern (pattern, size, bufp)
register unsigned c, c1;
char *p0;
int numlen;
-
+
/* Address of the count-byte of the most recently inserted `exactn'
command. This makes it possible to tell whether a new exact-match
character can be added to that command or requires a new `exactn'
command. */
-
+
char *pending_exact = 0;
-
+
/* Address of the place where a forward-jump should go to the end of
the containing expression. Each alternative of an `or', except the
last, ends with a forward-jump of this sort. */
-
+
char *fixup_jump = 0;
-
+
/* Address of start of the most recently finished expression.
This tells postfix * where to find the start of its operand. */
-
+
char *laststart = 0;
-
+
/* In processing a repeat, 1 means zero matches is allowed. */
-
+
char zero_times_ok;
-
+
/* In processing a repeat, 1 means many matches is allowed. */
-
+
char many_times_ok;
-
+
/* Address of beginning of regexp, or inside of last \(. */
-
+
char *begalt = b;
-
+
/* In processing an interval, at least this many matches must be made. */
int lower_bound;
-
+
/* In processing an interval, at most this many matches can be made. */
int upper_bound;
-
+
/* Place in pattern (i.e., the {) to which to go back if the interval
is invalid. */
char *beg_interval = 0;
-
+
/* Stack of information saved by \( and restored by \).
Four stack elements are pushed by each \(:
First, the value of b.
Second, the value of fixup_jump.
Third, the value of regnum.
Fourth, the value of begalt. */
-
+
int stackb[40];
int *stackp = stackb;
int *stacke = stackb + 40;
int *stackt;
-
+
/* Counts \('s as they are encountered. Remembered for the matching \),
where it becomes the register number to put in the stop_memory
command. */
-
+
int regnum = 1;
int range = 0;
bufp->fastmap_accurate = 0;
-
+
/* Initialize the syntax table. */
init_syntax_once();
-
+
if (bufp->allocated == 0)
{
bufp->allocated = INIT_BUF_SIZE;
@@ -663,7 +657,7 @@ re_compile_pattern (pattern, size, bufp)
case '^':
/* ^ means succeed if at beg of line, but only if no preceding
pattern. */
-
+
if ((re_syntax_options & RE_CONTEXTUAL_INVALID_OPS) && laststart)
goto invalid_pattern;
if (laststart && p - 2 >= pattern && p[-2] != '\n'
@@ -792,7 +786,7 @@ re_compile_pattern (pattern, size, bufp)
BUFPUSH ((1 << BYTEWIDTH) / BYTEWIDTH);
/* Clear the whole map */
memset (b, 0, (1 << BYTEWIDTH) / BYTEWIDTH + 2);
-
+
if ((re_syntax_options & RE_HAT_NOT_NEWLINE) && b[-2] == charset_not)
SET_LIST_BIT ('\n');
@@ -907,7 +901,7 @@ re_compile_pattern (pattern, size, bufp)
break;
}
}
-
+
/* Get a range. */
if (range) {
if (last > c)
@@ -980,7 +974,7 @@ re_compile_pattern (pattern, size, bufp)
goto normal_char;
else
goto handle_interval;
-
+
case '\\':
if (p == pend) goto invalid_pattern;
PATFETCH(c);
@@ -1042,7 +1036,7 @@ re_compile_pattern (pattern, size, bufp)
final destination. */
if (fixup_jump)
store_jump (fixup_jump, jump, b);
-
+
/* Leave space for a jump after previous alternative---to be
filled in later. */
fixup_jump = b;
@@ -1084,12 +1078,12 @@ re_compile_pattern (pattern, size, bufp)
{
if (re_syntax_options & RE_NO_BK_CURLY_BRACES)
goto normal_char;
-
+
/* Posix extended syntax is handled in previous
statement; this is for Posix basic syntax. */
if (re_syntax_options & RE_INTERVALS)
goto invalid_pattern;
-
+
goto normal_backsl;
}
lower_bound = -1; /* So can see if are set. */
@@ -1123,7 +1117,7 @@ re_compile_pattern (pattern, size, bufp)
/* If upper_bound is zero, don't want to succeed at all;
jump from laststart to b + 3, which will be the end of
the buffer after this jump is inserted. */
-
+
if (upper_bound == 0)
{
GET_BUFFER_SPACE (3);
@@ -1140,9 +1134,9 @@ re_compile_pattern (pattern, size, bufp)
the buffer; then only space for the succeed_n is
needed. Otherwise, need space for both the
succeed_n and the jump_n. */
-
+
unsigned slots_needed = upper_bound == 1 ? 5 : 10;
-
+
GET_BUFFER_SPACE (slots_needed);
/* Initialize the succeed_n to n, even though it will
be set by its attendant set_number_at, because
@@ -1190,7 +1184,7 @@ re_compile_pattern (pattern, size, bufp)
"regex: no interval beginning to which to backtrack.\n");
exit (1);
}
-
+
beg_interval = 0;
PATFETCH (c); /* normal_char expects char in `c'. */
goto normal_char;
@@ -1429,7 +1423,7 @@ insert_jump (op, from, to, current_end)
Store in the location FROM a jump operation to jump to relative
address FROM - TO. OPCODE is the opcode to store, N is a number the
jump uses, say, to decide how many times to jump.
-
+
If you call this function, you must zero out pending_exact. */
static void
@@ -1484,7 +1478,7 @@ insert_op_2 (op, there, current_end, num_1, num_2)
while (pfrom != there)
*--pto = *--pfrom;
-
+
there[0] = (char)op;
STORE_NUMBER (there + 1, num_1);
STORE_NUMBER (there + 3, num_2);
@@ -1522,7 +1516,7 @@ re_compile_fastmap (bufp)
memset (fastmap, 0, (1 << BYTEWIDTH));
bufp->fastmap_accurate = 1;
bufp->can_be_null = 0;
-
+
while (p)
{
is_a_succeed_n = 0;
@@ -1554,7 +1548,7 @@ re_compile_fastmap (bufp)
fastmap[translate['\n']] = 1;
else
fastmap['\n'] = 1;
-
+
if (bufp->can_be_null != 1)
bufp->can_be_null = 2;
break;
@@ -1584,7 +1578,7 @@ re_compile_fastmap (bufp)
if (stackp != stackb && *stackp == p)
stackp--;
continue;
-
+
case on_failure_jump:
handle_on_failure_jump:
EXTRACT_NUMBER_AND_INCR (j, p);
@@ -1605,7 +1599,7 @@ re_compile_fastmap (bufp)
goto handle_on_failure_jump;
}
continue;
-
+
case set_number_at:
p += 4;
continue;
@@ -1727,59 +1721,34 @@ re_compile_fastmap (bufp)
-/* Like re_search_2, below, but only one string is specified, and
- doesn't let you say where to stop matching. */
-
-int
-re_search (pbufp, string, size, startpos, range, regs)
- struct re_pattern_buffer *pbufp;
- char *string;
- int size, startpos, range;
- struct re_registers *regs;
-{
- return re_search_2 (pbufp, (char*)0, 0, string, size, startpos, range, regs);
-}
-
-/* Using the compiled pattern in PBUFP->buffer, first tries to match the
- virtual concatenation of STRING1 and STRING2, starting first at index
- STARTPOS, then at STARTPOS + 1, and so on. RANGE is the number of
- places to try before giving up. If RANGE is negative, it searches
- backwards, i.e., the starting positions tried are STARTPOS, STARTPOS
- - 1, etc. STRING1 and STRING2 are of SIZE1 and SIZE2, respectively.
- In REGS, return the indices of the virtual concatenation of STRING1
- and STRING2 that matched the entire PBUFP->buffer and its contained
- subexpressions.
+/* Using the compiled pattern in PBUFP->buffer, first tries to match
+ STRING, starting first at index STARTPOS, then at STARTPOS + 1, and
+ so on. RANGE is the number of places to try before giving up. If
+ RANGE is negative, it searches backwards, i.e., the starting
+ positions tried are STARTPOS, STARTPOS - 1, etc. STRING is of SIZE.
+ In REGS, return the indices of STRING that matched the entire
+ PBUFP->buffer and its contained subexpressions.
The value returned is the position in the strings at which the match
was found, or -1 if no match was found, or -2 if error (such as
failure stack overflow). */
-static int
-re_search_2 (pbufp, string1, size1, string2, size2, startpos, range, regs)
+int
+re_search (pbufp, string, size, startpos, range, regs)
struct re_pattern_buffer *pbufp;
- char *string1, *string2;
- int size1, size2;
- int startpos;
- register int range;
+ char *string;
+ int size, startpos, range;
struct re_registers *regs;
{
register char *fastmap = pbufp->fastmap;
register unsigned char *translate = (unsigned char *) pbufp->translate;
- int total_size = size1 + size2;
int endpos = startpos + range;
int val;
/* Check for out-of-range starting position. */
- if (startpos < 0 || startpos > total_size)
+ if (startpos < 0 || startpos > size)
return -1;
-
- /* Fix up range if it would eventually take startpos outside of the
- virtual concatenation of string1 and string2. */
- if (endpos < -1)
- range = -1 - startpos;
- else if (endpos > total_size)
- range = total_size - startpos;
/* Update the fastmap now if not correct already. */
if (fastmap && !pbufp->fastmap_accurate) {
@@ -1794,18 +1763,16 @@ re_search_2 (pbufp, string1, size1, string2, size2, startpos, range, regs)
test it at each starting point so that we take the first null
string we get. */
- if (fastmap && startpos < total_size && pbufp->can_be_null != 1)
+ if (fastmap && startpos < size && pbufp->can_be_null != 1)
{
if (range > 0) /* Searching forwards. */
{
register int lim = 0;
register unsigned char *p, c;
int irange = range;
- if (startpos < size1 && startpos + range >= size1)
- lim = range - (size1 - startpos);
- p = ((unsigned char *)
- &(startpos >= size1 ? string2 - size1 : string1)[startpos]);
+ lim = range - (size - startpos);
+ p = (unsigned char *)&(string[startpos]);
while (range > lim) {
c = *p++;
@@ -1826,23 +1793,18 @@ re_search_2 (pbufp, string1, size1, string2, size2, startpos, range, regs)
{
register unsigned char c;
- if (string1 == 0 || startpos >= size1)
- c = string2[startpos - size1];
- else
- c = string1[startpos];
-
+ c = string[startpos];
c &= 0xff;
if (translate ? !fastmap[translate[c]] : !fastmap[c])
goto advance;
}
}
- if (range >= 0 && startpos == total_size
+ if (range >= 0 && startpos == size
&& fastmap && pbufp->can_be_null == 0)
return -1;
- val = re_match_2 (pbufp, string1, size1, string2, size2, startpos,
- regs);
+ val = re_match (pbufp, string, size, startpos, regs);
if (val >= 0)
return startpos;
if (val == -2)
@@ -1858,8 +1820,7 @@ re_search_2 (pbufp, string1, size1, string2, size2, startpos, range, regs)
if (!range)
break;
else if (range > 0) {
- const char *d = ((startpos >= size1 ? string2 - size1 : string1)
- + startpos);
+ const char *d = string + startpos;
if (ismbchar (*d)) {
range--, startpos++;
@@ -1873,10 +1834,7 @@ re_search_2 (pbufp, string1, size1, string2, size2, startpos, range, regs)
{
const char *s, *d, *p;
- if (startpos < size1)
- s = string1, d = string1 + startpos;
- else
- s = string2, d = string2 + startpos - size1;
+ s = string; d = string + startpos;
for (p = d; p-- > s && ismbchar(*p); )
/* --p >= s would not work on 80[12]?86.
(when the offset of s equals 0 other than huge model.) */
@@ -1894,29 +1852,19 @@ re_search_2 (pbufp, string1, size1, string2, size2, startpos, range, regs)
-int
-re_match (pbufp, string, size, pos, regs)
- struct re_pattern_buffer *pbufp;
- char *string;
- int size, pos;
- struct re_registers *regs;
-{
- return re_match_2 (pbufp, (char *) 0, 0, string, size, pos, regs, size);
-}
-
-/* The following are used for re_match_2, defined below: */
+/* The following are used for re_match, defined below: */
/* Roughly the maximum number of failure points on the stack. Would be
exactly that if always pushed MAX_NUM_FAILURE_ITEMS each time we failed. */
-
+
int re_max_failures = 2000;
-/* Routine used by re_match_2. */
+/* Routine used by re_match. */
/* static int memcmp_translate (); *//* already declared */
-/* Structure and accessing macros used in re_match_2: */
+/* Structure and accessing macros used in re_match: */
struct register_info
{
@@ -1928,8 +1876,7 @@ struct register_info
#define MATCHED_SOMETHING(R) ((R).matched_something)
-/* Macros used by re_match_2: */
-
+/* Macros used by re_match: */
/* I.e., regstart, regend, and reg_info. */
@@ -1992,7 +1939,7 @@ struct register_info
*stackp++ = pattern_place; \
*stackp++ = string_place; \
}
-
+
/* This pops what PUSH_FAILURE_POINT pushes. */
@@ -2005,29 +1952,7 @@ struct register_info
stackp -= temp; /* Remove the register info. */ \
}
-
-#define MATCHING_IN_FIRST_STRING (dend == end_match_1)
-
-/* Is true if there is a first string and if PTR is pointing anywhere
- inside it or just past the end. */
-
-#define IS_IN_FIRST_STRING(ptr) \
- (size1 && string1 <= (ptr) && (ptr) <= string1 + size1)
-
-/* Call before fetching a character with *d. This switches over to
- string2 if necessary. */
-
-#define PREFETCH \
- while (d == dend) \
- { \
- /* end of string2 => fail. */ \
- if (dend == end_match_2) \
- goto fail; \
- /* end of string1 => advance to string2. */ \
- d = string2; \
- dend = end_match_2; \
- }
-
+#define PREFETCH if (d == dend) goto fail
/* Call this when have matched something; it sets `matched' flags for the
registers corresponding to the subexpressions of which we currently
@@ -2047,8 +1972,8 @@ struct register_info
of string1 and string2. If there is only one string, we've put it in
string2. */
-#define AT_STRINGS_BEG (d == (size1 ? string1 : string2) || !size2)
-#define AT_STRINGS_END (d == end2)
+#define AT_STRINGS_BEG (d == string)
+#define AT_STRINGS_END (d == dend)
#define AT_WORD_BOUNDARY \
(AT_STRINGS_BEG || AT_STRINGS_END || IS_A_LETTER (d - 1) != IS_A_LETTER (d))
@@ -2059,9 +1984,7 @@ struct register_info
2) if we're before the beginning of string2, we have to look at the
last character in string1; we assume there is a string1, so use
this in conjunction with AT_STRINGS_BEG. */
-#define IS_A_LETTER(d) \
- (SYNTAX ((d) == end1 ? *string2 : (d) == string2 - 1 ? *(end1 - 1) : *(d))\
- == Sword)
+#define IS_A_LETTER(d) (SYNTAX (*(d)) == Sword)
static void
init_regs(regs, num_regs)
@@ -2088,12 +2011,10 @@ init_regs(regs, num_regs)
}
}
-/* Match the pattern described by PBUFP against the virtual
- concatenation of STRING1 and STRING2, which are of SIZE1 and SIZE2,
- respectively. Start the match at index POS in the virtual
- concatenation of STRING1 and STRING2. In REGS, return the indices of
- the virtual concatenation of STRING1 and STRING2 that matched the
- entire PBUFP->buffer and its contained subexpressions.
+/* Match the pattern described by PBUFP against STRING, which is of
+ SIZE. Start the match at index POS in STRING. In REGS, return the
+ indices of STRING that matched the entire PBUFP->buffer and its
+ contained subexpressions.
If pbufp->fastmap is nonzero, then it had better be up to date.
@@ -2105,12 +2026,11 @@ init_regs(regs, num_regs)
error (such as match stack overflow). Otherwise the value is the
length of the substring which was matched. */
-static int
-re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
+int
+re_match (pbufp, string_arg, size, pos, regs)
struct re_pattern_buffer *pbufp;
- char *string1_arg, *string2_arg;
- int size1, size2;
- int pos;
+ char *string_arg;
+ int size, pos;
struct re_registers *regs;
{
register unsigned char *p = (unsigned char *) pbufp->buffer;
@@ -2120,14 +2040,7 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
unsigned num_regs = pbufp->re_nsub + 1;
- unsigned char *string1 = (unsigned char *) string1_arg;
- unsigned char *string2 = (unsigned char *) string2_arg;
- unsigned char *end1; /* Just past end of first string. */
- unsigned char *end2; /* Just past end of second string. */
-
- /* Pointers into string1 and string2, just past the last characters in
- each to consider matching. */
- unsigned char *end_match_1, *end_match_2;
+ unsigned char *string = (unsigned char *) string_arg;
register unsigned char *d, *dend;
register int mcnt; /* Multipurpose. */
@@ -2156,7 +2069,7 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
matching and the regnum-th regend points to right after where we
stopped matching the regnum-th subexpression. (The zeroth register
keeps track of what the whole pattern matches.) */
-
+
unsigned char **regstart = RE_TALLOC(num_regs, unsigned char*);
unsigned char **regend = RE_TALLOC(num_regs, unsigned char*);
@@ -2181,7 +2094,7 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
if (regs) {
init_regs(regs, num_regs);
}
-
+
/* Initialize the stack. */
stackb = RE_TALLOC(MAX_NUM_FAILURE_ITEMS * NFAILURES, unsigned char*);
@@ -2189,7 +2102,7 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
stacke = &stackb[MAX_NUM_FAILURE_ITEMS * NFAILURES];
#ifdef DEBUG_REGEX
- fprintf (stderr, "Entering re_match_2(%s%s)\n", string1_arg, string2_arg);
+ fprintf (stderr, "Entering re_match(%s%s)\n", string1_arg, string2_arg);
#endif
/* Initialize subexpression text positions to -1 to mark ones that no
@@ -2201,21 +2114,10 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
IS_ACTIVE (reg_info[mcnt]) = 0;
MATCHED_SOMETHING (reg_info[mcnt]) = 0;
}
-
+
/* Set up pointers to ends of strings.
Don't allow the second string to be empty unless both are empty. */
- if (size2 == 0) {
- string2 = string1;
- size2 = size1;
- string1 = 0;
- size1 = 0;
- }
- end1 = string1 + size1;
- end2 = string2 + size2;
- /* Compute where to stop matching, within the two strings. */
- end_match_1 = end1;
- end_match_2 = string2 + size2 - size1;
/* `p' scans through the pattern as `d' scans through the data. `dend'
is the end of the input string that `d' points within. `d' is
@@ -2224,10 +2126,7 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
loop, `d' can be pointing at the end of a string, but it cannot
equal string2. */
- if (size1 != 0 && pos <= size1)
- d = string1 + pos, dend = end_match_1;
- else
- d = string2 + pos - size1, dend = end_match_2;
+ d = string + pos, dend = string + size;
/* This loops over pattern commands. It exits by returning from the
@@ -2247,24 +2146,18 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
if (p == pend)
{
/* If not end of string, try backtracking. Otherwise done. */
- if (d != end_match_2)
+ if (d != dend)
{
if (stackp != stackb)
{
/* More failure points to try. */
- unsigned in_same_string =
- IS_IN_FIRST_STRING (best_regend[0])
- == MATCHING_IN_FIRST_STRING;
-
/* If exceeds best match so far, save it. */
- if (! best_regs_set
- || (in_same_string && d > best_regend[0])
- || (! in_same_string && ! MATCHING_IN_FIRST_STRING))
+ if (! best_regs_set || (d > best_regend[0]))
{
best_regs_set = 1;
best_regend[0] = d; /* Never use regstart[0]. */
-
+
for (mcnt = 1; mcnt < num_regs; mcnt++)
{
best_regstart[mcnt] = regstart[mcnt];
@@ -2279,7 +2172,7 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
restore_best_regs:
/* Restore best match. */
d = best_regend[0];
-
+
for (mcnt = 0; mcnt < num_regs; mcnt++)
{
regstart[mcnt] = best_regstart[mcnt];
@@ -2293,10 +2186,7 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
if (regs)
{
regs->beg[0] = pos;
- if (MATCHING_IN_FIRST_STRING)
- regs->end[0] = d - string1;
- else
- regs->end[0] = d - string2 + size1;
+ regs->end[0] = d - string;
for (mcnt = 1; mcnt < num_regs; mcnt++)
{
if (regend[mcnt] == (unsigned char *)(-1L))
@@ -2305,22 +2195,12 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
regs->end[mcnt] = -1;
continue;
}
- if (IS_IN_FIRST_STRING (regstart[mcnt]))
- regs->beg[mcnt] = regstart[mcnt] - string1;
- else
- regs->beg[mcnt] = regstart[mcnt] - string2 + size1;
-
- if (IS_IN_FIRST_STRING (regend[mcnt]))
- regs->end[mcnt] = regend[mcnt] - string1;
- else
- regs->end[mcnt] = regend[mcnt] - string2 + size1;
+ regs->beg[mcnt] = regstart[mcnt] - string;
+ regs->end[mcnt] = regend[mcnt] - string;
}
}
FREE_VARIABLES();
- FREE_AND_RETURN(stackb,
- (d - pos - (MATCHING_IN_FIRST_STRING ?
- string1 :
- string2 - size1)));
+ FREE_AND_RETURN(stackb, (d - pos - string));
}
/* Otherwise match next pattern command. */
@@ -2368,7 +2248,7 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
break;
}
p2 += mcnt;
-
+
/* If the next operation is a jump backwards in the pattern
to an on_failure_jump, exit from the loop by forcing a
failure after pushing on the stack the on_failure_jump's
@@ -2392,25 +2272,15 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
/* Where in input to try to start matching. */
d2 = regstart[regno];
-
+
/* Where to stop matching; if both the place to start and
the place to stop matching are in the same string, then
set to the place to stop, otherwise, for now have to use
the end of the first string. */
- dend2 = ((IS_IN_FIRST_STRING (regstart[regno])
- == IS_IN_FIRST_STRING (regend[regno]))
- ? regend[regno] : end_match_1);
+ dend2 = regend[regno];
while (1)
{
- /* If necessary, advance to next segment in register
- contents. */
- while (d2 == dend2)
- {
- if (dend2 == end_match_2) break;
- if (dend2 == regend[regno]) break;
- d2 = string2, dend2 = regend[regno]; /* end of string1 => advance to string2. */
- }
/* At end of register contents => success */
if (d2 == dend2) break;
@@ -2419,12 +2289,12 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
/* How many characters left in this segment to match. */
mcnt = dend - d;
-
+
/* Want how many consecutive characters we can match in
one shot, so, if necessary, adjust the count. */
if (mcnt > dend2 - d2)
mcnt = dend2 - d2;
-
+
/* Compare that many; failure if mismatch, else move
past them. */
if (translate
@@ -2437,7 +2307,7 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
break;
case anychar:
- PREFETCH; /* Fetch a data character. */
+ PREFETCH;
/* Match anything but a newline, maybe even a null. */
if (ismbchar (*d)) {
if (d + 1 == dend || d[1] == '\n' || d[1] == '\0')
@@ -2460,8 +2330,7 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
int not; /* Nonzero for charset_not. */
int c;
- PREFETCH; /* Fetch a data character. */
-
+ PREFETCH;
c = (unsigned char) *d;
if (ismbchar (c)) {
c <<= 8;
@@ -2487,17 +2356,15 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
}
case begline:
- if ((size1 != 0 && d == string1)
- || (size1 == 0 && size2 != 0 && d == string2)
- || (d && d[-1] == '\n')
- || (size1 == 0 && size2 == 0))
+ if (size == 0
+ || d == string
+ || (d && d[-1] == '\n'))
break;
else
goto fail;
-
+
case endline:
- if (d == end2
- || (d == end1 ? (size2 == 0 || *string2 == '\n') : *d == '\n'))
+ if (d == dend || *d == '\n')
break;
goto fail;
@@ -2580,7 +2447,7 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
case finalize_jump:
POP_FAILURE_POINT ();
/* Note fall through. */
-
+
/* Jump without taking off any failure points. */
case jump:
nofinalize:
@@ -2621,7 +2488,7 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
exit (1);
}
break;
-
+
case jump_n:
EXTRACT_NUMBER (mcnt, p + 2);
/* Originally, this is how many times we CAN jump. */
@@ -2636,7 +2503,7 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
else
p += 4;
break;
-
+
case set_number_at:
{
register unsigned char *p1;
@@ -2670,7 +2537,7 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
d++;
SET_REGS_MATCHED;
break;
-
+
case notwordchar:
PREFETCH;
if (IS_A_LETTER (d))
@@ -2730,7 +2597,7 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
/* A restart point is known. Restart there and pop it. */
{
short last_used_reg, this_reg;
-
+
/* If this failure point is from a dummy_failure_point, just
skip it. */
if (!stackp[-2])
@@ -2741,11 +2608,9 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
d = *--stackp;
p = *--stackp;
- if (d >= string1 && d <= end1)
- dend = end_match_1;
/* Restore register info. */
last_used_reg = (long) *--stackp;
-
+
/* Make the ones that weren't saved -1 or 0 again. */
for (this_reg = num_regs - 1; this_reg > last_used_reg; this_reg--)
{
@@ -2754,7 +2619,7 @@ re_match_2 (pbufp, string1_arg, size1, string2_arg, size2, pos, regs)
IS_ACTIVE (reg_info[this_reg]) = 0;
MATCHED_SOMETHING (reg_info[this_reg]) = 0;
}
-
+
/* And restore the rest from the stack. */
for ( ; this_reg > 0; this_reg--)
{
diff --git a/ruby.c b/ruby.c
index 7b029cd84c..330ce30def 100644
--- a/ruby.c
+++ b/ruby.c
@@ -17,6 +17,14 @@
#include <sys/types.h>
#include <sys/stat.h>
#include <signal.h>
+#include "dln.h"
+
+#ifdef HAVE_STRING_H
+# include <string.h>
+#else
+char *strchr();
+char *strstr();
+#endif
static int version, copyright;
@@ -26,16 +34,13 @@ static int sflag = FALSE;
char *inplace = Qnil;
char *strdup();
-char *strstr();
-char *strchr();
-char *dln_find_file();
extern int yydebug;
extern int nerrs;
int xflag = FALSE;
-#ifdef USE_DLN
+#ifdef USE_DL
char *rb_dln_argv0;
#endif
@@ -455,7 +460,7 @@ ruby_init0(argc, argv, envp)
rb_define_variable("$VERBOSE", &verbose, Qnil, Qnil, 0);
rb_define_variable("$DEBUG", &debug, Qnil, Qnil, 0);
-#ifdef USE_DLN
+#ifdef USE_DL
rb_dln_argv0 = argv[0];
#endif
diff --git a/ruby.h b/ruby.h
index a08a6082a2..aed41eef35 100644
--- a/ruby.h
+++ b/ruby.h
@@ -97,7 +97,7 @@ extern VALUE C_Data;
#define T_REGEXP 0x07
#define T_ARRAY 0x08
#define T_FIXNUM 0x09
-#define T_DICT 0x0a
+#define T_HASH 0x0a
#define T_STRUCT 0x0b
#define T_BIGNUM 0x0c
#define T_CONS 0x0f
@@ -166,7 +166,7 @@ struct RRegexp {
char *str;
};
-struct RDict {
+struct RHash {
struct RBasic basic;
struct st_table *tbl;
};
@@ -232,7 +232,7 @@ struct RCons {
#define RSTRING(obj) (R_CAST(RString)(obj))
#define RREGEXP(obj) (R_CAST(RRegexp)(obj))
#define RARRAY(obj) (R_CAST(RArray)(obj))
-#define RDICT(obj) (R_CAST(RDict)(obj))
+#define RHASH(obj) (R_CAST(RHash)(obj))
#define RDATA(obj) (R_CAST(RData)(obj))
#define RSTRUCT(obj) (R_CAST(RStruct)(obj))
#define RBIGNUM(obj) (R_CAST(RBignum)(obj))
diff --git a/sample/dbm.rb b/sample/dbm.rb
index cdec665a79..a2e0659bf5 100644
--- a/sample/dbm.rb
+++ b/sample/dbm.rb
@@ -1,4 +1,12 @@
# ruby dbm acess
d = DBM.open("test")
-for k in d.keys; print k, "\n"; end
-for v in d.values; print v, "\n"; end
+keys = d.keys
+if keys.length > 0 then
+ for k in keys; print k, "\n"; end
+ for v in d.values; print v, "\n"; end
+else
+ d['foobar'] = 'FB'
+ d['baz'] = 'BZ'
+ d['quux'] = 'QX'
+end
+
diff --git a/socket.c b/socket.c
deleted file mode 100644
index 58a2a8e9e7..0000000000
--- a/socket.c
+++ /dev/null
@@ -1,758 +0,0 @@
-/************************************************
-
- socket.c -
-
- $Author: matz $
- $Date: 1995/01/10 10:42:55 $
- created at: Thu Mar 31 12:21:29 JST 1994
-
-************************************************/
-
-#include "ruby.h"
-#ifdef HAVE_SOCKET
-#include "io.h"
-#include <stdio.h>
-#include <sys/types.h>
-#include <sys/socket.h>
-#include <netinet/in.h>
-#include <netdb.h>
-#include <errno.h>
-#include <sys/un.h>
-
-extern VALUE C_IO;
-VALUE C_BasicSocket;
-VALUE C_TCPsocket;
-VALUE C_TCPserver;
-VALUE C_UNIXsocket;
-VALUE C_UNIXserver;
-VALUE C_Socket;
-
-FILE *rb_fdopen();
-char *strdup();
-
-static VALUE
-sock_new(class, fd)
- VALUE class;
- int fd;
-{
- VALUE sock = obj_alloc(class);
- OpenFile *fp;
-
- MakeOpenFile(sock, fp);
- fp->f = rb_fdopen(fd, "r");
- setbuf(fp->f, NULL);
- fp->f2 = rb_fdopen(fd, "w");
- fp->mode = FMODE_READWRITE|FMODE_SYNC;
-
- return sock;
-}
-
-static VALUE
-Fbsock_shutdown(argc, argv, sock)
- int argc;
- VALUE *argv;
- VALUE sock;
-{
- VALUE howto;
- int how;
- OpenFile *fptr;
-
- rb_scan_args(argc, argv, "01", &howto);
- if (howto == Qnil)
- how = 2;
- else {
- how = NUM2INT(howto);
- if (how < 0 && how > 2) how = 2;
- }
- GetOpenFile(sock, fptr);
- if (shutdown(fileno(fptr->f), how) == -1)
- rb_sys_fail(Qnil);
-
- return INT2FIX(0);
-}
-
-static VALUE
-Fbsock_setopt(sock, lev, optname, val)
- VALUE sock, lev, optname;
- struct RString *val;
-{
- int level, option;
- OpenFile *fptr;
-
- level = NUM2INT(lev);
- option = NUM2INT(optname);
- Check_Type(val, T_STRING);
-
- GetOpenFile(sock, fptr);
- if (setsockopt(fileno(fptr->f), level, option, val->ptr, val->len) < 0)
- rb_sys_fail(fptr->path);
-
- return INT2FIX(0);
-}
-
-static VALUE
-Fbsock_getopt(sock, lev, optname)
- VALUE sock, lev, optname;
-{
- int level, option, len;
- struct RString *val;
- OpenFile *fptr;
-
- level = NUM2INT(lev);
- option = NUM2INT(optname);
- len = 256;
- val = (struct RString*)str_new(0, len);
- Check_Type(val, T_STRING);
-
- GetOpenFile(sock, fptr);
- if (getsockopt(fileno(fptr->f), level, option, val->ptr, &len) < 0)
- rb_sys_fail(fptr->path);
- val->len = len;
- return (VALUE)val;
-}
-
-static VALUE
-Fbsock_getsockname(sock)
- VALUE sock;
-{
- char buf[1024];
- int len = sizeof buf;
- OpenFile *fptr;
-
- GetOpenFile(sock, fptr);
- if (getsockname(fileno(fptr->f), (struct sockaddr*)buf, &len) < 0)
- rb_sys_fail("getsockname(2)");
- return str_new(buf, len);
-}
-
-static VALUE
-Fbsock_getpeername(sock)
- VALUE sock;
-{
- char buf[1024];
- int len = sizeof buf;
- OpenFile *fptr;
-
- GetOpenFile(sock, fptr);
- if (getpeername(fileno(fptr->f), (struct sockaddr*)buf, &len) < 0)
- rb_sys_fail("getpeername(2)");
- return str_new(buf, len);
-}
-
-static VALUE
-open_inet(class, h, serv, server)
- VALUE class, h, serv;
- int server;
-{
- char *host;
- struct hostent *hostent, _hostent;
- struct servent *servent, _servent;
- struct protoent *protoent;
- struct sockaddr_in sockaddr;
- int fd, status;
- int hostaddr, hostaddrPtr[2];
- int servport;
- char *syscall;
- VALUE sock;
-
- if (h) {
- Check_Type(h, T_STRING);
- host = RSTRING(h)->ptr;
- hostent = gethostbyname(host);
- if (hostent == NULL) {
- hostaddr = inet_addr(host);
- if (hostaddr == -1) {
- if (server && !strlen(host))
- hostaddr = INADDR_ANY;
- else
- rb_sys_fail(host);
- }
- _hostent.h_addr_list = (char **)hostaddrPtr;
- _hostent.h_addr_list[0] = (char *)&hostaddr;
- _hostent.h_addr_list[1] = NULL;
- _hostent.h_length = sizeof(hostaddr);
- _hostent.h_addrtype = AF_INET;
- hostent = &_hostent;
- }
- }
- servent = NULL;
- if (FIXNUM_P(serv)) {
- servport = FIX2UINT(serv);
- goto setup_servent;
- }
- Check_Type(serv, T_STRING);
- servent = getservbyname(RSTRING(serv)->ptr, "tcp");
- if (servent == NULL) {
- servport = strtoul(RSTRING(serv)->ptr, Qnil, 0);
- if (servport == -1) Fail("no such servce %s", RSTRING(serv)->ptr);
- setup_servent:
- _servent.s_port = servport;
- _servent.s_proto = "tcp";
- servent = &_servent;
- }
- protoent = getprotobyname(servent->s_proto);
- if (protoent == NULL) Fail("no such proto %s", servent->s_proto);
-
- fd = socket(PF_INET, SOCK_STREAM, protoent->p_proto);
-
- sockaddr.sin_family = AF_INET;
- if (h == Qnil) {
- sockaddr.sin_addr.s_addr = INADDR_ANY;
- }
- else {
- memcpy((char *)&(sockaddr.sin_addr.s_addr),
- (char *) hostent->h_addr_list[0],
- (size_t) hostent->h_length);
- }
- sockaddr.sin_port = servent->s_port;
-
- if (server) {
- status = bind(fd, (struct sockaddr*)&sockaddr, sizeof(sockaddr));
- syscall = "bind(2)";
- }
- else {
- status = connect(fd, (struct sockaddr*)&sockaddr, sizeof(sockaddr));
- syscall = "connect(2)";
- }
-
- if (status < 0) {
- close (fd);
- rb_sys_fail(syscall);
- }
- if (server) listen(fd, 5);
-
- /* create new instance */
- sock = sock_new(class, fd);
-
- return sock;
-}
-
-static VALUE
-Stcp_sock_open(class, host, serv)
- VALUE class, host, serv;
-{
- Check_Type(host, T_STRING);
- return open_inet(class, host, serv, 0);
-}
-
-static VALUE
-Stcp_svr_open(argc, argv, class)
- int argc;
- VALUE *argv;
- VALUE class;
-{
- VALUE arg1, arg2;
-
- if (rb_scan_args(argc, argv, "11", &arg1, &arg2) == 2)
- return open_inet(class, arg1, arg2, 1);
- else
- return open_inet(class, Qnil, arg1, 1);
-}
-
-static VALUE
-sock_accept(class, fd, sockaddr, len)
- VALUE class;
- int fd;
- struct sockaddr *sockaddr;
- int *len;
-{
- int fd2;
-
- retry:
- fd2 = accept(fd, sockaddr, len);
- if (fd2 < 0) {
- if (errno == EINTR) goto retry;
- rb_sys_fail(Qnil);
- }
- return sock_new(class, fd2);
-}
-
-static VALUE
-Ftcp_accept(sock)
- VALUE sock;
-{
- OpenFile *fptr;
- struct sockaddr_in from;
- int fromlen;
-
- GetOpenFile(sock, fptr);
- fromlen = sizeof(struct sockaddr_in);
- return sock_accept(C_TCPsocket, fileno(fptr->f),
- (struct sockaddr*)&from, &fromlen);
-}
-
-static VALUE
-open_unix(class, path, server)
- VALUE class;
- struct RString *path;
- int server;
-{
- struct sockaddr_un sockaddr;
- int fd, status;
- char *syscall;
- VALUE sock;
- OpenFile *fptr;
-
- Check_Type(path, T_STRING);
- fd = socket(PF_UNIX, SOCK_STREAM, 0);
- if (fd < 0) rb_sys_fail("socket(2)");
-
- sockaddr.sun_family = AF_UNIX;
- strncpy(sockaddr.sun_path, path->ptr, sizeof(sockaddr.sun_path)-1);
- sockaddr.sun_path[sizeof(sockaddr.sun_path)-1] = '\0';
-
- if (server) {
- status = bind(fd, (struct sockaddr*)&sockaddr, sizeof(sockaddr));
- syscall = "bind(2)";
- }
- else {
- status = connect(fd, (struct sockaddr*)&sockaddr, sizeof(sockaddr));
- syscall = "connect(2)";
- }
-
- if (status < 0) {
- close (fd);
- rb_sys_fail(syscall);
- }
-
- if (server) listen(fd, 5);
-
- sock = sock_new(class, fd);
- GetOpenFile(sock, fptr);
- fptr->path = strdup(path->ptr);
-
- return sock;
-}
-
-static VALUE
-tcp_addr(sockaddr)
- struct sockaddr_in *sockaddr;
-{
- VALUE family, port, addr;
- VALUE ary;
- struct hostent *hostent;
-
- family = str_new2("AF_INET");
- hostent = gethostbyaddr((char*)&sockaddr->sin_addr.s_addr,
- sizeof(sockaddr->sin_addr),
- AF_INET);
- if (hostent) {
- addr = str_new2(hostent->h_name);
- }
- else {
- char buf[16];
- char *a = (char*)&sockaddr->sin_addr;
- sprintf(buf, "%d.%d.%d.%d", a[0], a[1], a[2], a[3]);
- addr = str_new2(buf);
- }
- port = INT2FIX(sockaddr->sin_port);
- ary = ary_new3(3, family, port, addr);
-
- return ary;
-}
-
-static VALUE
-Ftcp_addr(sock)
- VALUE sock;
-{
- OpenFile *fptr;
- struct sockaddr_in addr;
- int len = sizeof addr;
-
- GetOpenFile(sock, fptr);
-
- if (getsockname(fileno(fptr->f), (struct sockaddr*)&addr, &len) < 0)
- rb_sys_fail("getsockname(2)");
- return tcp_addr(&addr);
-}
-
-static VALUE
-Ftcp_peeraddr(sock)
- VALUE sock;
-{
- OpenFile *fptr;
- struct sockaddr_in addr;
- int len = sizeof addr;
-
- GetOpenFile(sock, fptr);
-
- if (getpeername(fileno(fptr->f), (struct sockaddr*)&addr, &len) < 0)
- rb_sys_fail("getsockname(2)");
- return tcp_addr(&addr);
-}
-
-static VALUE
-Sunix_sock_open(sock, path)
- VALUE sock, path;
-{
- return open_unix(sock, path, 0);
-}
-
-static VALUE
-Funix_path(sock)
- VALUE sock;
-{
- OpenFile *fptr;
-
- GetOpenFile(sock, fptr);
- if (fptr->path == Qnil) {
- struct sockaddr_un addr;
- int len = sizeof(addr);
- if (getsockname(fileno(fptr->f), (struct sockaddr*)&addr, &len) < 0)
- rb_sys_fail(Qnil);
- fptr->path = strdup(addr.sun_path);
- }
- return str_new2(fptr->path);
-}
-
-static VALUE
-Sunix_svr_open(class, path)
- VALUE class, path;
-{
- return open_unix(class, path, 1);
-}
-
-static VALUE
-Funix_accept(sock)
- VALUE sock;
-{
- OpenFile *fptr;
- struct sockaddr_un from;
- int fromlen;
-
- GetOpenFile(sock, fptr);
- fromlen = sizeof(struct sockaddr_un);
- return sock_accept(C_UNIXsocket, fileno(fptr->f),
- (struct sockaddr*)&from, &fromlen);
-}
-
-static VALUE
-unix_addr(sockaddr)
- struct sockaddr_un *sockaddr;
-{
- return assoc_new(str_new2("AF_UNIX"),str_new2(sockaddr->sun_path));
-}
-
-static VALUE
-Funix_addr(sock)
- VALUE sock;
-{
- OpenFile *fptr;
- struct sockaddr_un addr;
- int len = sizeof addr;
-
- GetOpenFile(sock, fptr);
-
- if (getsockname(fileno(fptr->f), (struct sockaddr*)&addr, &len) < 0)
- rb_sys_fail("getsockname(2)");
- return unix_addr(&addr);
-}
-
-static VALUE
-Funix_peeraddr(sock)
- VALUE sock;
-{
- OpenFile *fptr;
- struct sockaddr_un addr;
- int len = sizeof addr;
-
- GetOpenFile(sock, fptr);
-
- if (getpeername(fileno(fptr->f), (struct sockaddr*)&addr, &len) < 0)
- rb_sys_fail("getsockname(2)");
- return unix_addr(&addr);
-}
-
-static void
-setup_domain_and_type(domain, dv, type, tv)
- VALUE domain, type;
- int *dv, *tv;
-{
- char *ptr;
-
- if (TYPE(domain) == T_STRING) {
- ptr = RSTRING(domain)->ptr;
- if (strcmp(ptr, "PF_UNIX") == 0)
- *dv = PF_UNIX;
- else if (strcmp(ptr, "PF_INET") == 0)
- *dv = PF_INET;
-#ifdef PF_IMPLINK
- else if (strcmp(ptr, "PF_IMPLINK") == 0)
- *dv = PF_IMPLINK;
-#endif
-#ifdef PF_AX25
- else if (strcmp(ptr, "PF_AX25") == 0)
- *dv = PF_AX25;
-#endif
-#ifdef PF_IPX
- else if (strcmp(ptr, "PF_IPX") == 0)
- *dv = PF_IPX;
-#endif
- else
- Fail("Unknown socket domain %s", ptr);
- }
- else {
- *dv = NUM2INT(domain);
- }
- if (TYPE(type) == T_STRING) {
- ptr = RSTRING(type)->ptr;
- if (strcmp(ptr, "SOCK_STREAM") == 0)
- *tv = SOCK_STREAM;
- else if (strcmp(ptr, "SOCK_DGRAM") == 0)
- *tv = SOCK_DGRAM;
-#ifdef SOCK_RAW
- else if (strcmp(ptr, "SOCK_RAW") == 0)
- *tv = SOCK_RAW;
-#endif
-#ifdef SOCK_SEQPACKET
- else if (strcmp(ptr, "SOCK_SEQPACKET") == 0)
- *tv = SOCK_SEQPACKET;
-#endif
-#ifdef SOCK_RDM
- else if (strcmp(ptr, "SOCK_RDM") == 0)
- *tv = SOCK_RDM;
-#endif
-#ifdef SOCK_PACKET
- else if (strcmp(ptr, "SOCK_PACKET") == 0)
- *tv = SOCK_PACKET;
-#endif
- else
- Fail("Unknown socket type %s", ptr);
- }
- else {
- *tv = NUM2INT(type);
- }
-}
-
-static VALUE
-Ssock_open(class, domain, type, protocol)
- VALUE class, domain, type, protocol;
-{
- int fd;
- int d, t;
-
- setup_domain_and_type(domain, &d, type, &t);
- fd = socket(d, t, NUM2INT(protocol));
- if (fd < 0) rb_sys_fail("socke(2)");
- return sock_new(class, fd);
-}
-
-static VALUE
-Ssock_for_fd(class, fd)
- VALUE class, fd;
-{
- return sock_new(class, NUM2INT(fd));
-}
-
-static VALUE
-Ssock_socketpair(class, domain, type, protocol)
- VALUE class, domain, type, protocol;
-{
- int fd;
- int d, t, sp[2];
-
- setup_domain_and_type(domain, &d, type, &t);
- if (socketpair(d, t, NUM2INT(protocol), sp) < 0)
- rb_sys_fail("socketpair(2)");
-
- return assoc_new(sock_new(class, sp[0]), sock_new(class, sp[1]));
-}
-
-static VALUE
-Fsock_connect(sock, addr)
- VALUE sock;
- struct RString *addr;
-{
- OpenFile *fptr;
-
- Check_Type(addr, T_STRING);
- str_modify(addr);
-
- GetOpenFile(sock, fptr);
- if (connect(fileno(fptr->f), (struct sockaddr*)addr->ptr, addr->len) < 0)
- rb_sys_fail("connect(2)");
-
- return INT2FIX(0);
-}
-
-static VALUE
-Fsock_bind(sock, addr)
- VALUE sock;
- struct RString *addr;
-{
- OpenFile *fptr;
-
- Check_Type(addr, T_STRING);
- str_modify(addr);
-
- GetOpenFile(sock, fptr);
- if (bind(fileno(fptr->f), (struct sockaddr*)addr->ptr, addr->len) < 0)
- rb_sys_fail("bind(2)");
-
- return INT2FIX(0);
-}
-
-static VALUE
-Fsock_listen(sock, log)
- VALUE sock, log;
-{
- OpenFile *fptr;
-
- GetOpenFile(sock, fptr);
- if (listen(fileno(fptr->f), NUM2INT(log)) < 0)
- rb_sys_fail("listen(2)");
-
- return INT2FIX(0);
-}
-
-static VALUE
-Fsock_accept(sock)
- VALUE sock;
-{
- OpenFile *fptr;
- VALUE addr, sock2;
- char buf[1024];
- int len = sizeof buf;
-
- GetOpenFile(sock, fptr);
- sock2 = sock_accept(C_Socket,fileno(fptr->f),(struct sockaddr*)buf,&len);
-
- return assoc_new(sock2, str_new(buf, len));
-}
-
-static VALUE
-Fsock_send(argc, argv, sock)
- int argc;
- VALUE *argv;
- VALUE sock;
-{
- struct RString *msg, *to;
- VALUE flags;
- OpenFile *fptr;
- FILE *f;
- int fd, n;
-
- rb_scan_args(argc, argv, "21", &msg, &flags, &to);
-
- Check_Type(msg, T_STRING);
-
- GetOpenFile(sock, fptr);
- f = fptr->f2?fptr->f2:fptr->f;
- fd = fileno(f);
- if (to) {
- Check_Type(to, T_STRING);
- n = sendto(fd, msg->ptr, msg->len, NUM2INT(flags),
- (struct sockaddr*)to->ptr, to->len);
- }
- else {
- n = send(fd, msg->ptr, msg->len, NUM2INT(flags));
- }
- if (n < 0) {
- rb_sys_fail("send(2)");
- }
- return INT2FIX(n);
-}
-
-static VALUE
-sock_recv(sock, argc, argv, from)
- VALUE sock;
- int argc;
- VALUE *argv;
- int from;
-{
- OpenFile *fptr;
- FILE f;
- struct RString *str;
- char buf[1024];
- int fd, alen = sizeof buf;
- VALUE len, flg;
- int flags;
-
- rb_scan_args(argc, argv, "11", &len, &flg);
-
- if (flg == Qnil) flags = 0;
- else flags = NUM2INT(flg);
-
- str = (struct RString*)str_new(0, NUM2INT(len));
-
- GetOpenFile(sock, fptr);
- fd = fileno(fptr->f);
- if ((str->len = recvfrom(fd, str->ptr, str->len, flags,
- (struct sockaddr*)buf, &alen)) < 0) {
- rb_sys_fail("recvfrom(2)");
- }
-
- if (from)
- return assoc_new(str, str_new(buf, alen));
- else
- return (VALUE)str;
-}
-
-static VALUE
-Fsock_recv(argc, argv, sock)
- int argc;
- VALUE *argv;
- VALUE sock;
-{
- return sock_recv(sock, argc, argv, 0);
-}
-
-static VALUE
-Fsock_recvfrom(argc, argv, sock)
- int argc;
- VALUE *argv;
- VALUE sock;
-{
- return sock_recv(sock, argc, argv, 1);
-}
-
-Init_Socket ()
-{
- C_BasicSocket = rb_define_class("BasicSocket", C_IO);
- rb_undef_method(C_BasicSocket, "new");
- rb_define_method(C_BasicSocket, "shutdown", Fbsock_shutdown, -1);
- rb_define_method(C_BasicSocket, "setopt", Fbsock_setopt, 3);
- rb_define_method(C_BasicSocket, "getopt", Fbsock_getopt, 2);
- rb_define_method(C_BasicSocket, "getsockname", Fbsock_getsockname, 0);
- rb_define_method(C_BasicSocket, "getpeername", Fbsock_getpeername, 0);
-
- C_TCPsocket = rb_define_class("TCPsocket", C_BasicSocket);
- rb_define_single_method(C_TCPsocket, "open", Stcp_sock_open, 2);
- rb_define_single_method(C_TCPsocket, "new", Stcp_sock_open, 2);
- rb_define_method(C_TCPsocket, "addr", Ftcp_addr, 0);
- rb_define_method(C_TCPsocket, "peeraddr", Ftcp_peeraddr, 0);
-
- C_TCPserver = rb_define_class("TCPserver", C_TCPsocket);
- rb_define_single_method(C_TCPserver, "open", Stcp_svr_open, -1);
- rb_define_single_method(C_TCPserver, "new", Stcp_svr_open, -1);
- rb_define_method(C_TCPserver, "accept", Ftcp_accept, 0);
-
- C_UNIXsocket = rb_define_class("UNIXsocket", C_BasicSocket);
- rb_define_single_method(C_UNIXsocket, "open", Sunix_sock_open, 1);
- rb_define_single_method(C_UNIXsocket, "new", Sunix_sock_open, 1);
- rb_define_method(C_UNIXsocket, "path", Funix_path, 0);
- rb_define_method(C_UNIXsocket, "addr", Funix_addr, 0);
- rb_define_method(C_UNIXsocket, "peeraddr", Funix_peeraddr, 0);
-
- C_UNIXserver = rb_define_class("UNIXserver", C_UNIXsocket);
- rb_define_single_method(C_UNIXserver, "open", Sunix_svr_open, 1);
- rb_define_single_method(C_UNIXserver, "new", Sunix_svr_open, 1);
- rb_define_method(C_UNIXserver, "accept", Funix_accept, 0);
-
- C_Socket = rb_define_class("Socket", C_BasicSocket);
- rb_define_single_method(C_Socket, "open", Ssock_open, 3);
- rb_define_single_method(C_Socket, "new", Ssock_open, 3);
- rb_define_single_method(C_Socket, "for_fd", Ssock_for_fd, 1);
-
- rb_define_method(C_Socket, "connect", Fsock_connect, 1);
- rb_define_method(C_Socket, "bind", Fsock_bind, 1);
- rb_define_method(C_Socket, "listen", Fsock_listen, 1);
- rb_define_method(C_Socket, "accept", Fsock_accept, 0);
-
- rb_define_method(C_Socket, "send", Fsock_send, -1);
- rb_define_method(C_Socket, "recv", Fsock_recv, -1);
- rb_define_method(C_Socket, "recvfrom", Fsock_recv, -1);
-
- rb_define_single_method(C_Socket, "socketpair", Ssock_socketpair, 3);
-}
-#endif /* HAVE_SOCKET */
diff --git a/spec b/spec
index a067075b67..eaec5a37c4 100644
--- a/spec
+++ b/spec
@@ -227,11 +227,12 @@ Rubyの変数はスコープ(有効範囲)と寿命(有効期限)によって4種類に分類され,
FOOBAR
-大文字で始まる識別子はクラス定数へのアクセスであり,そのクラスと全ての
-サブクラスのスコープ内で参照できる.定数への代入はトップレベル,すなわ
-ちメソッドが定義できるレベルでのみ可能である.この変数はクラス間で値が
-共有され,一度代入すると値を変更することができない.クラス定数の寿命は
-クラスの寿命と等しい.
+大文字で始まる識別子は定数へのアクセスであり,最初に定義されたクラスと
+全てのサブクラスのスコープ内で参照できる.定数の定義は代入か,定数を定
+義しているモジュールをインクルードすることによって行なわれる.定数への
+代入はトップレベル,すなわちメソッドが定義できるレベルでのみ可能である.
+定数はクラス間で値が共有され,一度代入すると値を変更することができない
+(代入は例外を発生させる).クラス定数の寿命はクラスの寿命と等しい.
クラス定義は自動的に定数を定義するので,クラス名は定数である.
@@ -254,23 +255,13 @@ Rubyの変数はスコープ(有効範囲)と寿命(有効期限)によって4種類に分類され,
通常の変数以外に疑似変数と呼ばれる特殊な変数が4つある.
self | 現在のメソッドの実行主体
- nil | Nilクラスの唯一のインスタンス(偽を表す)
+ nil | Nilクラスの唯一のインスタンス(偽を表す)
__FILE__ | スクリプトのファイル名(文字列)
__LINE__ | 現在の行番号(整数)
これらの疑似変数は代入によってその値を変更することはできない.これらの
変数への代入は例外を発生させる.
-** 括弧によるグルーピング
-
-例:
-
- (1+2)*3
-
-式は括弧によってグルーピングすることができる.
-
- `(' 式 `)'
-
** 配列式
例:
@@ -296,8 +287,8 @@ Rubyの変数はスコープ(有効範囲)と寿命(有効期限)によって4種類に分類され,
{1=>2, 2=>4, 3=>6}
連想配列とは任意のオブジェクトをキー(添字)として持つ配列である.Ruby
-の連想配列はDict(辞書)クラスのインスタンスである.詳細はクラスDictの項
-を参照されたい.連想配列を生成する連想配列式は以下の形式である.
+の連想配列はHash(ハッシュ表)クラスのインスタンスである.詳細はクラス
+Hashの項を参照されたい.連想配列を生成する連想配列式は以下の形式である.
`{' 式 `=>' 式.. `}'
@@ -332,7 +323,7 @@ Rubyの変数はスコープ(有効範囲)と寿命(有効期限)によって4種類に分類され,
下の文字または予約語で始まる場合は,優先順位の関係で予想通りの結果が得
られない場合がある.
- (, [, {, <, /, +, -, if, while
+ (, [, {, /, +, -, if, while
どのように評価されるか曖昧な場合には括弧をつける事.
@@ -350,10 +341,9 @@ Rubyの変数はスコープ(有効範囲)と寿命(有効期限)によって4種類に分類され,
でも小文字でも構わない.変数名とは識別子の名前空間が違うので重複しても
構わない.
-クラスModuleで定義されているメソッド(public,protected,private)でメソッ
-ドの呼び出し方を制御することが出来る.protectedまたは privateで指定さ
-れた制限されたメソッドは関数形式でしか呼び出すことが出来ず,さらに
-privateメソッドは同じクラスで定義されたメソッドからしか呼び出せない.
+クラスModuleで定義されているメソッド(public,private)でメソッドの呼び出
+し方を制御することが出来る.privateで指定された制限されたメソッドは関
+数形式でしか呼び出すことが出来ない.
** SUPER
@@ -519,6 +509,16 @@ privateメソッドは同じクラスで定義されたメソッドからしか呼び出せない.
これはあくまでもそういう形式のメソッド呼び出しとして解釈されるというだ
けで,rubyプログラムでこういう記述が許されるというわけではない.
+** 括弧によるグルーピング
+
+例:
+
+ (1+2)*3
+
+式は括弧によってグルーピングすることができる.
+
+ `(' 式 `)'
+
** IF
if 式1 [then]
@@ -724,6 +724,14 @@ begin式の値は一番最後に評価された式の値である.begin式の処理中に発生し
begin式を終了する前に必ず(正常終了時だけでなく,例外, return, break,
continue, redoなどによる脱出でも)ensure節の式を評価する.
+** RETRY
+
+ retry
+
+begin式のresque節で使い,begin式を始めからもう一度実行する.例外処理を
+行なってから再試行するのに使う.resque節以外でretryが用いられた場合例
+外が発生する.
+
** RETURN
return [式[`,' 式..]]
@@ -751,14 +759,6 @@ continueはもっとも内側のループの次の繰り返しを始める.
redoはループ条件のチェックを行なわず,現在の繰り返しをやり直す.
-** RETRY
-
- retry
-
-begin式のresque節で使い,begin式を始めから実行する.例外処理を行なって
-から再試行するのに使う.resque節以外でretryが用いられた場合例外が発生
-する.
-
** クラス定義
クラスを定義する構式は以下の通りである.
@@ -794,17 +794,16 @@ begin式のresque節で使い,begin式を始めから実行する.例外処理を行なって
実引数は,最後の引数に配列として与えられる(足りない時にはエラー).
-メソッドには呼び出し制限を加えることが出来,制限を加えられたメソッドは,
-関数形式でしか呼び出せない(protected),あるいは関数形式でしかも同じク
-ラスのメソッドからしか呼べない(private).
+メソッドには呼び出し制限を加えることができ,制限を加えられたメソッドは,
+関数形式でしか呼び出せない(privateメソッド).
新規にメソッドを定義する場合,クラス定義式の外にあるdef式はデフォルト
-ではprotectedメソッドを定義し,クラス定義式の中にあるdef式はpublicメソッ
+ではprivateメソッドを定義し,クラス定義式の中にあるdef式はpublicメソッ
ドを定義する.スーパークラスのメソッドを再定義する場合には定義されるメ
ソッドの可視性はスーパークラスのメソッドのものを受け継ぐ.
メソッドの可視性を変更する場合にはModuleクラスで定義されているpublic,
-protected, privateの各メソッドを用いる.
+privateの各メソッドを用いる.
** 特異メソッド定義
@@ -824,6 +823,8 @@ protected, privateの各メソッドを用いる.
サブクラスにも継承される.言い替えればクラスの特異メソッドは他のオブジェ
クト指向システムにおけるクラスメソッドの働きをする.
+注意: インクルードしたモジュールの特異メソッドは継承しない.
+
** ALIAS
以下の形式でメソッドに別名をつけることができる.
@@ -1551,193 +1552,6 @@ Methods:
CONSペアからなるリストの各要素を与えるイテレータ.
-** DBM(クラス)
-
-NDBMファイルをアクセスするクラス.キー,データともに文字列でなければな
-らないという制限と,データがファイルに保存されるという点を除いては
-Dictクラスと全く同様に扱うことができる.NDBMを備えていないシステムでは
-このクラスは定義されない.
-
-SuperClass: Object
-
-Included Modules: Enumerable
-
-Methods:
-
- self [key]
-
- keyをキーとする値を返す.
-
- self [key]= value
-
- keyをキーとして,valueを格納する.valueとしてnilを指定すると,
- keyに対する項目の削除となる.
-
- clear
-
- DBMファイルの中身を空にする.
-
- close
-
- DBMファイルをクローズする.以後の操作は例外を発生させる.
-
- delete(key)
-
- keyをキーとする組を削除する.
-
- delete_if
-
- 要素を削除するイテレータ.key::valueというペアを与えて,ブロッ
- クを評価した値が真の時,該当する項目を削除する.
-
- each
- each_pair
-
- key::valueなるペアを与えるイテレータ.
-
- each_key
-
- 全てのkeyに対して繰り返すイテレータ.
-
- each_value
-
- 全てのvalueに対して繰り返すイテレータ.
-
- has_key(key)
- includes(key)
-
- keyがデータベース中に存在する時,真を返す
-
- has_value(value)
-
- valueを値とする組がデータベース中に存在する時,真を
- 返す
-
- indexes(ary)
- indexes(key-1, ..., key-n)
-
- 1番目の形式では文字列の配列を引数として受けて,その要素をキー
- とする要素を含む配列を返す.2番目の形式では各引数の値をキーと
- する要素を含む配列を返す.
-
- keys
-
- データベース中に存在するキー全てを含む配列を返す.
-
- length
- size
-
- データベース中の要素の数を返す.(注意:現在の実現では要素数を数
- えるためにデータベースを全部検索するので,結構コストが高い.気
- をつけて使うこと.)
-
- to_a
-
- データベース中のkey-valueペアを要素とする配列を返す.
-
- values
-
- データベース中に存在する値全てを含む配列を返す.
-
-Single Methods:
-
- open(dbname[, mode])
-
- dbnameで指定したデータベースをモードをmodeに設定してオープンす
- る.modeの省略値は0666である.modeとしてnilを指定するとデータ
- ベースが既に存在しない時には新たにオープンせず,nilを返す.
-
-** Dict(クラス)
-
-辞書あるいは連想配列.任意のオブジェクトを添字とできる配列のクラスであ
-る.連想配列オブジェクトの生成は一般的には連想配列式``{a=>b,..}'' で行
-なわれる.
-
-SuperClass: Object
-
-Included Modules: Enumerable
-
-Methods:
-
- self [key]
-
- keyをキーとする値を返す.
-
- self [key]= value
-
- keyをキーとして,valueを格納する.valueとしてnilを指定するとそ
- のkeyに対する項目の削除となる.つまり,Dictは値としてnilを持つ
- ことはできない.
-
- clear
-
- 連想配列を空にする.
-
- delete(key)
-
- keyをキーとする組を削除する.
-
- delete_if
-
- 要素を削除するイテレータ.key::valueというペアを与えて,ブロッ
- クを評価した値が真の時,該当する項目を削除する.
-
- each
- each_pair
-
- key::valueなるペアを与えるイテレータ.
-
- each_key
-
- 全てのkeyに対して繰り返すイテレータ.
-
- each_value
-
- 全てのvalueに対して繰り返すイテレータ.
-
- has_key(key)
- includes(key)
-
- keyが辞書中に存在する時,真を返す
-
- has_value(value)
-
- valueを値とする組が辞書中に存在する時,真を返す
-
- indexes(ary)
- indexes(key-1, ..., key-n)
-
- 1番目の形式では配列を引数として受けて,その要素をキーとする要
- 素を含む配列を返す.2番目の形式では各引数の値をキーとする要素
- を含む配列を返す.
-
- keys
-
- 辞書中に存在するキー全てを含む配列を返す.
-
- length
- size
-
- 辞書中の要素の数を返す.
-
- to_a
-
- 辞書中のkey-valueペアを要素とする配列を返す.
-
- values
-
- 辞書中に存在する値全てを含む配列を返す.
-
-Single Methods:
-
- Dict[key, value..]
-
- 奇数番目の引数をkey,偶数番目の引数をvalueとする辞書を生成する.
-
- new
-
- 新しい(空の)辞書オブジェクトを返す.
-
** Dir(クラス)
ディレクトリ内の要素を順に返すディレクトリストリーム操作のためのクラス.
@@ -2367,6 +2181,100 @@ Single Methods:
文字列をワイルドカードに変換したオブジェクトを返す.
+** Hash(クラス)
+
+連想配列あるいはハッシュ表.任意のオブジェクトを添字とできる配列のクラ
+スである.連想配列オブジェクトの生成は一般的には連想配列式
+
+ ``{a=>b,..}''
+
+で行なわれる.
+
+SuperClass: Object
+
+Included Modules: Enumerable
+
+Methods:
+
+ self [key]
+
+ keyをキーとする値を返す.
+
+ self [key]= value
+
+ keyをキーとして,valueを格納する.valueとしてnilを指定するとそ
+ のkeyに対する項目の削除となる.つまり,Hashは値としてnilを持つ
+ ことはできない.
+
+ clear
+
+ 連想配列を空にする.
+
+ delete(key)
+
+ keyをキーとする組を削除する.
+
+ delete_if
+
+ 要素を削除するイテレータ.key::valueというペアを与えて,ブロッ
+ クを評価した値が真の時,該当する項目を削除する.
+
+ each
+ each_pair
+
+ key::valueなるペアを与えるイテレータ.
+
+ each_key
+
+ 全てのkeyに対して繰り返すイテレータ.
+
+ each_value
+
+ 全てのvalueに対して繰り返すイテレータ.
+
+ has_key(key)
+ includes(key)
+
+ keyが辞書中に存在する時,真を返す
+
+ has_value(value)
+
+ valueを値とする組が辞書中に存在する時,真を返す
+
+ indexes(ary)
+ indexes(key-1, ..., key-n)
+
+ 1番目の形式では配列を引数として受けて,その要素をキーとする要
+ 素を含む配列を返す.2番目の形式では各引数の値をキーとする要素
+ を含む配列を返す.
+
+ keys
+
+ 辞書中に存在するキー全てを含む配列を返す.
+
+ length
+ size
+
+ 辞書中の要素の数を返す.
+
+ to_a
+
+ 辞書中のkey-valueペアを要素とする配列を返す.
+
+ values
+
+ 辞書中に存在する値全てを含む配列を返す.
+
+Single Methods:
+
+ Hash[key, value..]
+
+ 奇数番目の引数をkey,偶数番目の引数をvalueとする辞書を生成する.
+
+ new
+
+ 新しい(空の)辞書オブジェクトを返す.
+
** Integer(クラス)
整数クラス.実際はその大きさによってFixnumとBignumいう二つのサブクラス
@@ -2564,7 +2472,7 @@ Methods:
hash
- オブジェクトのハッシュ値(Fixnum)を返す.Dictクラスでキーとなる
+ オブジェクトのハッシュ値(Fixnum)を返す.Hashクラスでキーとなる
オブジェクトを格納するのに用いられている.「A == B」が成立する
時は必ず「A.hash == B.hash」が成立する必要があるので,"=="を再
定義した時には必ずこちらもそれに合わせて再定義すること.
@@ -2668,14 +2576,8 @@ Methods:
private(name[, name..])
- nameで指定されたメソッドを同じクラスで定義されたメソッドからだ
- け,関数形式でだけ呼び出し可能にする.すでにprivateメソッドで
- ある場合には何もしない.
-
- protected(name[, name..])
-
nameで指定されたメソッドを関数形式でだけ呼び出し可能にする.す
- でにprotectedメソッドである場合には何もしない.
+ でにprivateメソッドである場合には何もしない.
public(name[, name..])
@@ -2905,66 +2807,6 @@ Methods:
範囲の始点を返す.
-** Socket(クラス)
-
-SuperClass: BasicSocket
-
-ソケットそのものに対するシステムコールレベルのアクセスを提供するクラス.
-Perlのソケットに対するアクセスと同レベルの機能を提供している.このクラ
-スではソケットアドレスはpackされた文字列で,指定する.UDPソケットはこ
-のクラスを使って利用する.
-
-Methods:
-
- accept
-
- 新しい接続を受け付けて,新しい接続に対するソケットとアドレスの
- ペアを返す.accept(2)を参照.
-
- bind(addr)
-
- bind(2)と同じ働きをする.addrはpackされたソケットアドレス構造
- 体である.
-
- connect(addr)
-
- connect(2)と同じ働きをする.addrはpackされたソケットアドレス構
- 造体である.
-
- listen(backlog)
-
- listen(2)と同じ働きをする.
-
- recv(len[, flags])
-
- ソケットからデータを受け取り,文字列として返す.lenは受け取る
- 最大の長さを指定する.flagsについてはrecv(2)を参照.flagsのデ
- フォルト値は0である.
-
- recvfrom(len[, flags])
-
- recvと同様にソケットからデータを受け取るが,戻り値は文字列と相
- 手ソケットのアドレスのペアである.引数についてはrecvと同様.
-
- send(mesg, flags[, to])
-
- ソケットを介してデータを送る.flagsに関してはsend(2)を参照の事.
- connectしていないソケットに対しては送り先であるtoを指定する必
- 要がある.実際に送ったデータの長さを返す.
-
-Single Methods:
-
- open(domain, type, protocol)
- new(domain, type, protocol)
-
- 新しいソケットを生成する.domain,type,protocolはインクルード
- ファイルで定義されている定数値で指定する.domainとtypeに関して
- は,文字列で指定できるが,すべてをカバーしている保証はない.
-
- socketpair(domain, type, protocol)
-
- ソケットのペアを返す.引数の指定は openと同じである.
-
** Regexp(クラス)
正規表現のクラス.正規表現のリテラルは/.../という形式で表すが,動的に
@@ -3005,40 +2847,6 @@ Single Methods:
文字列の中の正規表現で意味を持つ文字をエスケープする.新しい文
字列を返す.
-** BasicSocket(クラス)
-
-ソケットを表す抽象クラス.具体的なソケット操作はサブクラスで定義される.
-例えばインターネットドメインの場合はTCPsocketを用いる.
-
-SuperClass: IO
-
-Methods:
-
- getopt(level, optname)
-
- ソケットのオプションを取得する.getsockopt(2)を参照のこと.取
- 得したオプションの内容を含む文字列を返す.
-
- getpeername
-
- 接続の相手先のソケットの情報を得る.パックされたsockaddr構造体
- をベタにダンプした文字列が返される.getpeername(2)を参照のこと.
-
- getsockname
-
- ソケットの情報を得る.パックされたsockaddr構造体をベタにダンプ
- した文字列が返される.getsockname(2)を参照のこと.
-
- setopt(level, optname, optval)
-
- ソケットのオプションを設定する.setsockopt(2)を参照のこと.
-
- shutdown(how)
-
- ソケットの以降の接続を終了させる.howが0である時,以降の受信が,
- howが1である時は,以降の送信が拒否される.howが2の時には,それ
- 以降の送信,受信ともに拒否される.shutdown(2)を参照.
-
** String(クラス)
文字列クラス.Rubyの文字列はヌルターミネートではないので,バイナリデー
@@ -3417,90 +3225,6 @@ Single Methods:
バで指定された名前の特異メソッドが定義されていて,そのメソッド
によってメンバの内容を得ることができる.
-** TCPserver(クラス)
-
-TCP/IPストリーム型接続のサーバ側のソケットのクラス.このクラスによって
-簡単にソケットを利用したサーバのプログラミングができる.例えばechoサー
-バは以下のようになる.
-
- gs = TCPserver.open(4444)
- socks = [gs]
-
- while TRUE
- nsock = select(socks);
- if nsock == nil; continue end
- for s in nsock[0]
- if s == gs
- socks.push(s.accept)
- else
- if s.eof
- s.close
- socks.delete(s)
- else
- str = s.gets
- s.write(str)
- end
- end
- end
- end
-
-SuperClass: TCPsocket
-
-Methods:
-
- accept
-
- クライアントからの接続要求を受け付け,接続したTCPsocketのイン
- スタンスを返す.
-
-Single Methods:
-
- new([host, ]service)
- open([host, ]service)
-
- serviceは/etc/services(またはNIS)に登録されているサービス名か
- ポート番号で指定する.hostを指定した時は指定したホストからの接
- 続だけを受け付ける.省略時は全てのホストからの接続要求を受け付
- ける.
-
-** TCPsocket
-
-インターネットドメインのストリーム型ソケットのクラス.通常のIOクラスの
-サブクラスと同様の入出力ができる.このクラスによってソケットを用いたク
-ライアントを簡単に記述できる.ユーザの入力をそのままサーバに転送するプ
-ログラムは以下のようになる.
-
- s = TCPsocket("localhost", 4444)
- while gets()
- s.write($_)
- print(s.read)
- end
-
-SuperClass: BasicSocket
-
-Methods:
-
- addr
-
- ソケットの接続情報を表す配列を返す.その配列の各要素は第1要素
- が文字列 "AF_INET",第2要素がport番号,第3要素がホストを表す文
- 字列である.
-
- peeraddr
-
- 接続相手先ソケットの情報を表す配列を返す.その配列の各要素は
- addrメソッドが返す配列と同じである.
-
-Single Methods:
-
- open(host, service)
- new(host, service)
-
- hostで指定したホストのserviceで指定したポートと接続したソケッ
- トを返す.hostはホスト名,またはインターネットアドレスを示す文
- 字列,serviceは/etc/services(またはNIS)に登録されているサービ
- ス名かポート番号である.
-
** Time(クラス)
時間を表すクラス.大小比較などができる.Time.nowで現在の時間を得ること
@@ -3624,49 +3348,6 @@ Single Methods:
時間の単位は秒であり,浮動小数点数で与えられる.詳細は
times(3)を参照のこと.
-** UNIXserver
-
-UNIXストリーム型接続のサーバ側のソケットのクラス.
-
-SuperClass: UNIXsocket
-
-Methods:
-
- accept
-
- クライアントからの接続要求を受け付け,接続したUNIXsocketのイン
- スタンスを返す.
-
-** UNIXsocket
-
-UNIXドメインのストリーム型ソケットのクラス.通常のIOクラスのサブクラス
-と同様の入出力ができる.
-
-SuperClass: BasicSocket
-
-Methods:
-
- addr
-
- ソケットの接続情報を表す配列を返す.その配列の各要素は第1要素
- が文字列 "AF_UNIX",第2要素がpathである.
-
- path
-
- UNIXソケットのパスを返す.
-
- peeraddr
-
- 接続相手先ソケットの情報を表す配列を返す.その配列の各要素は
- addrメソッドが返す配列と同じである.
-
-Single Methods:
-
- open(path)
- new(path)
-
- pathで指定したパス名を用いて接続したソケットを返す.
-
* C言語とのインタフェース
rubyはC言語とのインターフェースを提供し,C言語からのクラス,モジュール
diff --git a/util.c b/util.c
index 62e34f5753..585e5d5a86 100644
--- a/util.c
+++ b/util.c
@@ -7,11 +7,18 @@
$Date$
created at: Fri Mar 10 17:22:34 JST 1995
+ Copyright (C) 1995 Yukihiro Matsumoto
+
************************************************/
#include "defines.h"
#include "config.h"
#include "util.h"
+#ifdef HAVE_STRING_H
+# include <string.h>
+#else
+char *strchr();
+#endif
unsigned long
scan_oct(start, len, retlen)
@@ -30,8 +37,6 @@ int *retlen;
return retval;
}
-extern char *strchr();
-
unsigned long
scan_hex(start, len, retlen)
char *start;
diff --git a/util.h b/util.h
index e2ada4176b..17f70459a8 100644
--- a/util.h
+++ b/util.h
@@ -6,6 +6,8 @@
$Date$
created at: Thu Mar 9 11:55:53 JST 1995
+ Copyright (C) 1995 Yukihiro Matsumoto
+
************************************************/
#ifndef UTIL_H
#define UTIL_H
diff --git a/version.h b/version.h
index 231f54afb1..c0108942bd 100644
--- a/version.h
+++ b/version.h
@@ -1,2 +1,2 @@
-#define RUBY_VERSION "0.69"
-#define VERSION_DATE "95/03/15"
+#define RUBY_VERSION "0.71"
+#define VERSION_DATE "95/04/03"