diff options
-rw-r--r-- | ChangeLog | 12 | ||||
-rw-r--r-- | Makefile.in | 6 | ||||
-rw-r--r-- | eval.c | 4 | ||||
-rw-r--r-- | ext/etc/etc.c | 78 | ||||
-rw-r--r-- | ext/socket/extconf.rb | 1 | ||||
-rw-r--r-- | ext/socket/socket.c | 365 | ||||
-rw-r--r-- | intern.h | 2 |
7 files changed, 237 insertions, 231 deletions
@@ -9,6 +9,13 @@ Wed Oct 1 20:36:49 2003 WATANABE Hirofumi <eban@ruby-lang.org> * MANIFEST: add wince/mkconfig_wce.rb. +Wed Oct 1 17:22:33 2003 Yukihiro Matsumoto <matz@ruby-lang.org> + + * ext/etc/etc.c: add new functions: setpwent, getpwent, endpwent, + setgrent, getgrent, endgrent. + + * ext/socket/socket.c (sock_s_gethostbyname): do not reverse lookup. + Wed Oct 1 17:01:30 2003 Nobuyoshi Nakada <nobu@ruby-lang.org> * eval.c (rb_load): Object scope had priority over required file @@ -32,6 +39,11 @@ Wed Oct 01 08:02:52 2003 Takaaki Uematsu <uema2x@jcom.home.ne.jp> * wince/time_wce.c (time): add zero check. +Tue Sep 30 16:11:05 2003 Yukihiro Matsumoto <matz@ruby-lang.org> + + * Makefile.in: copy lex.c from $(srcdir) if it's not the current + directory. [ruby-dev:21437] + Tue Sep 30 11:29:23 2003 Tanaka Akira <akr@m17n.org> * process.c (pst_inspect): describe stopped process "stopped". diff --git a/Makefile.in b/Makefile.in index f6a3cb6609..13de20321a 100644 --- a/Makefile.in +++ b/Makefile.in @@ -218,7 +218,11 @@ $(srcdir)/configure: $(srcdir)/configure.in $(CC) $(CFLAGS) $(CPPFLAGS) -c $< lex.c: keywords - gperf -p -j1 -i 1 -g -o -t -N rb_reserved_word -k1,3,$$ $(srcdir)/keywords > lex.c + if test "$(srcdir)" = "."; then \ + gperf -p -j1 -i 1 -g -o -t -N rb_reserved_word -k1,3,$$ $> > $@; \ + else \ + cp $(srcdir)/lex.c .; \ + fi .y.c: $(YACC) $< @@ -9752,7 +9752,7 @@ static VALUE rb_thread_raise(argc, argv, th) int argc; VALUE *argv; - rb_thread_t th; + volatile rb_thread_t th; { if (rb_thread_dead(th)) return Qnil; if (curr_thread == th) { @@ -9924,7 +9924,7 @@ rb_callcc(self) VALUE self; { volatile VALUE cont; - rb_thread_t th; + volatile rb_thread_t th; struct tag *tag; struct RVarmap *vars; diff --git a/ext/etc/etc.c b/ext/etc/etc.c index 51668c400f..3d4052e27b 100644 --- a/ext/etc/etc.c +++ b/ext/etc/etc.c @@ -175,6 +175,40 @@ etc_passwd(obj) return Qnil; } +static VALUE +etc_setpwent(obj) + VALUE obj; +{ +#ifdef HAVE_GETPWENT + setpwent(); +#endif + return Qnil; +} + +static VALUE +etc_endpwent(obj) + VALUE obj; +{ +#ifdef HAVE_GETPWENT + endpwent(); +#endif + return Qnil; +} + +static VALUE +etc_getpwent(obj) + VALUE obj; +{ +#ifdef HAVE_GETPWENT + struct passwd *pw; + + if (pw = getpwent()) { + return setup_passwd(pw); + } +#endif + return Qnil; +} + #ifdef HAVE_GETGRENT static VALUE setup_group(grp) @@ -246,11 +280,11 @@ group_iterate() { struct group *pw; - setpwent(); + setgrent(); while (pw = getgrent()) { rb_yield(setup_group(pw)); } - endpwent(); + endgrent(); return Qnil; } #endif @@ -277,6 +311,40 @@ etc_group(obj) return Qnil; } +static VALUE +etc_setgrent(obj) + VALUE obj; +{ +#ifdef HAVE_GETGRENT + setgrent(); +#endif + return Qnil; +} + +static VALUE +etc_endgrent(obj) + VALUE obj; +{ +#ifdef HAVE_GETGRENT + endgrent(); +#endif + return Qnil; +} + +static VALUE +etc_getgrent(obj) + VALUE obj; +{ +#ifdef HAVE_GETGRENT + struct group *gr; + + if (gr = getgrent()) { + return setup_passwd(gr); + } +#endif + return Qnil; +} + static VALUE mEtc; void @@ -288,11 +356,17 @@ Init_etc() rb_define_module_function(mEtc, "getpwuid", etc_getpwuid, -1); rb_define_module_function(mEtc, "getpwnam", etc_getpwnam, 1); + rb_define_module_function(mEtc, "setpwent", etc_setpwent, 0); + rb_define_module_function(mEtc, "endpwent", etc_endpwent, 0); + rb_define_module_function(mEtc, "getpwent", etc_getpwent, 0); rb_define_module_function(mEtc, "passwd", etc_passwd, 0); rb_define_module_function(mEtc, "getgrgid", etc_getgrgid, 1); rb_define_module_function(mEtc, "getgrnam", etc_getgrnam, 1); rb_define_module_function(mEtc, "group", etc_group, 0); + rb_define_module_function(mEtc, "setgrent", etc_setgrent, 0); + rb_define_module_function(mEtc, "endgrent", etc_endgrent, 0); + rb_define_module_function(mEtc, "getgrent", etc_g,etgrent, 0); sPasswd = rb_struct_define("Passwd", "name", "passwd", "uid", "gid", diff --git a/ext/socket/extconf.rb b/ext/socket/extconf.rb index e888b2a197..234f373170 100644 --- a/ext/socket/extconf.rb +++ b/ext/socket/extconf.rb @@ -385,6 +385,7 @@ have_header("sys/uio.h") if have_func(test_func) have_func("hsterror") + have_func("getipnodebyname") or have_func("gethostbyname2") unless have_func("gethostname") have_func("uname") end diff --git a/ext/socket/socket.c b/ext/socket/socket.c index ca2528f549..ca7bdc50c2 100644 --- a/ext/socket/socket.c +++ b/ext/socket/socket.c @@ -492,7 +492,7 @@ bsock_do_not_rev_lookup_set(self, val) } static void -mkipaddr0(addr, buf, len) +make_ipaddr0(addr, buf, len) struct sockaddr *addr; char *buf; size_t len; @@ -506,17 +506,17 @@ mkipaddr0(addr, buf, len) } static VALUE -mkipaddr(addr) +make_ipaddr(addr) struct sockaddr *addr; { char buf[1024]; - mkipaddr0(addr, buf, sizeof(buf)); + make_ipaddr0(addr, buf, sizeof(buf)); return rb_str_new2(buf); } static void -mkinetaddr(host, buf, len) +make_inetaddr(host, buf, len) long host; char *buf; size_t len; @@ -527,7 +527,7 @@ mkinetaddr(host, buf, len) sin.sin_family = AF_INET; SET_SIN_LEN(&sin, sizeof(sin)); sin.sin_addr.s_addr = host; - mkipaddr0((struct sockaddr*)&sin, buf, len); + make_ipaddr0((struct sockaddr*)&sin, buf, len); } static int @@ -546,24 +546,20 @@ str_isnumber(p) return 0; } -static struct addrinfo* -sock_addrinfo(host, port, socktype, flags) - VALUE host, port; - int socktype, flags; +static char * +host_str(host, hbuf, len) + VALUE host; + char *hbuf; + size_t len; { - struct addrinfo hints, *hintsp, *res; - char *hostp, *portp; - int error; - char hbuf[1024], pbuf[32]; - if (NIL_P(host)) { - hostp = NULL; + return NULL; } else if (rb_obj_is_kind_of(host, rb_cInteger)) { long i = NUM2LONG(host); - mkinetaddr(htonl(i), hbuf, sizeof(hbuf)); - hostp = hbuf; + make_inetaddr(htonl(i), hbuf, len); + return hbuf; } else { char *name; @@ -571,30 +567,66 @@ sock_addrinfo(host, port, socktype, flags) SafeStringValue(host); name = RSTRING(host)->ptr; if (!name || *name == 0 || (name[0] == '<' && strcmp(name, "<any>") == 0)) { - mkinetaddr(INADDR_ANY, hbuf, sizeof(hbuf)); + make_inetaddr(INADDR_ANY, hbuf, len); } else if (name[0] == '<' && strcmp(name, "<broadcast>") == 0) { - mkinetaddr(INADDR_BROADCAST, hbuf, sizeof(hbuf)); + make_inetaddr(INADDR_BROADCAST, hbuf, len); } - else if (strlen(name) >= sizeof(hbuf)) { + else if (strlen(name) >= len) { rb_raise(rb_eArgError, "hostname too long (%d)", strlen(name)); } else { strcpy(hbuf, name); } - hostp = hbuf; + return hbuf; } +} + +static char * +port_str(port, pbuf, len) + VALUE port; + char *pbuf; + size_t len; +{ if (NIL_P(port)) { - portp = 0; + return 0; } else if (FIXNUM_P(port)) { - snprintf(pbuf, sizeof(pbuf), "%d", FIX2INT(port)); - portp = pbuf; + snprintf(pbuf, len, "%d", FIX2INT(port)); + return pbuf; } else { + char *serv; + SafeStringValue(port); - portp = RSTRING(port)->ptr; + serv = RSTRING(port)->ptr; + if (strlen(serv) >= len) { + rb_raise(rb_eArgError, "service name too long (%d)", strlen(serv)); + } + strcpy(pbuf, serv); + return pbuf; } +} + +#ifndef NI_MAXHOST +# define 1025 +#endif +#ifndef NI_MAXSERV +# define 32 +#endif + +static struct addrinfo* +sock_addrinfo(host, port, socktype, flags) + VALUE host, port; + int socktype, flags; +{ + struct addrinfo hints, *hintsp, *res; + char *hostp, *portp; + int error; + char hbuf[NI_MAXHOST], pbuf[NI_MAXSERV]; + + hostp = host_str(host, hbuf, sizeof(hbuf)); + portp = port_str(port, pbuf, sizeof(pbuf)); if (socktype == 0 && flags == 0 && str_isnumber(portp)) { socktype = SOCK_DGRAM; @@ -617,18 +649,6 @@ sock_addrinfo(host, port, socktype, flags) return res; } -static void -setipaddr(name, addr) - VALUE name; - struct sockaddr_storage *addr; -{ - struct addrinfo *res = sock_addrinfo(name, Qnil, SOCK_STREAM, 0); - - /* just take the first one */ - memcpy(addr, res->ai_addr, res->ai_addrlen); - freeaddrinfo(res); -} - static VALUE ipaddr(sockaddr) struct sockaddr *sockaddr; @@ -704,17 +724,6 @@ ruby_socket(domain, type, proto) } static void -thread_read_select(fd) - int fd; -{ - fd_set fds; - - FD_ZERO(&fds); - FD_SET(fd, &fds); - rb_thread_select(fd+1, &fds, 0, 0, 0); -} - -static void thread_write_select(fd) int fd; { @@ -845,46 +854,6 @@ ruby_connect(fd, sockaddr, len, socks) } } -static void -load_addr_info(h, serv, type, res) - VALUE h, serv; - int type; - struct addrinfo **res; -{ - char *host; - char pbuf[1024], *portp; - struct addrinfo hints; - int error; - - if (!NIL_P(h)) { - SafeStringValue(h); - host = RSTRING(h)->ptr; - } - else { - host = NULL; - } - if (FIXNUM_P(serv)) { - snprintf(pbuf, sizeof(pbuf), "%u", FIX2UINT(serv)); - portp = pbuf; - } - else { - SafeStringValue(serv); - if (RSTRING(serv)->len >= sizeof(pbuf)) - rb_raise(rb_eArgError, "servicename too long (%ld)", RSTRING(serv)->len); - strcpy(pbuf, RSTRING(serv)->ptr); - portp = pbuf; - } - MEMZERO(&hints, struct addrinfo, 1); - hints.ai_family = PF_UNSPEC; - if (type == INET_SERVER) { - hints.ai_flags = AI_PASSIVE; - } - error = getaddrinfo(host, portp, &hints, res); - if (error) { - rb_raise(rb_eSocket, "getaddrinfo: %s", gai_strerror(error)); - } -} - struct inetsock_arg { VALUE sock; @@ -1052,112 +1021,61 @@ socks_s_close(sock) #endif #endif -/* - * NOTE: using gethostbyname() against AF_INET6 is a bad idea, as it - * does not initialize sin_flowinfo nor sin_scope_id properly. - */ - -struct hostent* -sock_hostbyname(host) - VALUE host; -{ - struct sockaddr_storage addr; - struct hostent *h; - - rb_secure(3); - setipaddr(host, &addr); - switch (addr.ss_family) { - case AF_INET: - { - struct sockaddr_in *sin; - sin = (struct sockaddr_in*)&addr; - h = gethostbyaddr((char*)&sin->sin_addr, - sizeof(sin->sin_addr), - sin->sin_family); - break; - } -#ifdef INET6 - case AF_INET6: - { - struct sockaddr_in6 *sin6; - sin6 = (struct sockaddr_in6*)&addr; - h = gethostbyaddr((char*)&sin6->sin6_addr, - sizeof(sin6->sin6_addr), - sin6->sin6_family); - break; - } -#endif - default: - h = NULL; - break; - } - - if (h == NULL) { -#ifdef HAVE_HSTERROR - extern int h_errno; - rb_raise(rb_eSocket, "%s", (char*)hsterror(h_errno)); -#else - rb_raise(rb_eSocket, "host not found"); -#endif - } - return h; -} - static VALUE -tcp_s_gethostbyname(obj, host) - VALUE obj, host; +make_hostent(addr, ipaddr) + struct addrinfo *addr; + VALUE (*ipaddr) _((struct sockaddr*, size_t)); { - struct hostent *h = sock_hostbyname(host); + struct addrinfo *ai; + struct hostent *h; VALUE ary, names; char **pch; ary = rb_ary_new(); - rb_ary_push(ary, rb_str_new2(h->h_name)); + rb_ary_push(ary, rb_str_new2(addr->ai_canonname)); names = rb_ary_new(); rb_ary_push(ary, names); +#if defined(HAVE_GETIPNODEBYNAME) + { + int error; + + h = getipnodebyname(addr->ai_canonname, addr->ai_family, AI_ALL, &error); + } +#elif defined(HAVE_GETHOSTBYNAME2) + h = gethostbyname2(addr->ai_canonname, addr->ai_family); +#else + h = gethostbyname(addr->ai_canonname); +#endif for (pch = h->h_aliases; *pch; pch++) { rb_ary_push(names, rb_str_new2(*pch)); } - rb_ary_push(ary, INT2NUM(h->h_addrtype)); -#ifdef h_addr - for (pch = h->h_addr_list; *pch; pch++) { - switch (h->h_length) { - case 4: /* AF_INET */ { - struct sockaddr_in sin; - - MEMZERO(&sin, struct sockaddr_in, 1); - sin.sin_family = AF_INET; - SET_SIN_LEN(&sin, sizeof(sin)); - memcpy((char*)&sin.sin_addr, *pch, h->h_length); - rb_ary_push(ary, mkipaddr((struct sockaddr*)&sin)); - break; - } -#ifdef INET6 - case 8: /* AF_INET6 */ { - struct sockaddr_in6 sin6; - - MEMZERO(&sin6, struct sockaddr_in6, 1); - sin6.sin6_family = AF_INET6; -#ifdef SIN6_LEN - sin6.sin6_len = sizeof(sin6); +#if defined(HAVE_GETIPNODEBYNAME) + freehostent(h); #endif - memcpy((char*)&sin6.sin6_addr, *pch, h->h_length); - rb_ary_push(ary, mkipaddr((struct sockaddr*)&sin6)); - break; - } -#endif - default: - break; - } + rb_ary_push(ary, INT2NUM(addr->ai_family)); + for (ai = addr; ai; ai = ai->ai_next) { + rb_ary_push(ary, (*ipaddr)(ai->ai_addr, ai->ai_addrlen)); } -#else - memcpy((char*)&addr.sin_addr, h->h_addr, h->h_length); - rb_ary_push(ary, mkipaddr((struct sockaddr*)&addr)); -#endif return ary; } +VALUE +tcp_sockaddr(addr, len) + struct sockaddr *addr; + size_t len; +{ + return make_ipaddr(addr); +} + +static VALUE +tcp_s_gethostbyname(obj, host) + VALUE obj, host; +{ + rb_secure(3); + return make_hostent(sock_addrinfo(host, Qnil, SOCK_STREAM, AI_CANONNAME), tcp_sockaddr); +} + static VALUE tcp_svr_init(argc, argv, sock) int argc; @@ -1347,9 +1265,13 @@ ip_s_getaddress(obj, host) VALUE obj, host; { struct sockaddr_storage addr; + struct addrinfo *res = sock_addrinfo(host, Qnil, SOCK_STREAM, 0); + + /* just take the first one */ + memcpy(&addr, res->ai_addr, res->ai_addrlen); + freeaddrinfo(res); - setipaddr(host, &addr); - return mkipaddr((struct sockaddr*)&addr); + return make_ipaddr((struct sockaddr*)&addr); } static VALUE @@ -1500,13 +1422,6 @@ unix_path(sock) } static VALUE -unix_svr_s_open(klass, path) - VALUE klass, path; -{ - return init_unixsock(rb_obj_alloc(klass), path, 1); -} - -static VALUE unix_svr_init(sock, path) VALUE sock, path; { @@ -2023,41 +1938,7 @@ sock_gethostname(obj) #endif static VALUE -sock_mkhostent(h) - struct hostent *h; -{ - char **pch; - VALUE ary, names; - - if (h == NULL) { -#ifdef HAVE_HSTRERROR - extern int h_errno; - rb_raise(rb_eSocket, "%s", (char*)hstrerror(h_errno)); -#else - rb_raise(rb_eSocket, "host not found"); -#endif - } - ary = rb_ary_new(); - rb_ary_push(ary, rb_str_new2(h->h_name)); - names = rb_ary_new(); - rb_ary_push(ary, names); - for (pch = h->h_aliases; *pch; pch++) { - rb_ary_push(names, rb_str_new2(*pch)); - } - rb_ary_push(ary, INT2NUM(h->h_addrtype)); -#ifdef h_addr - for (pch = h->h_addr_list; *pch; pch++) { - rb_ary_push(ary, rb_str_new(*pch, h->h_length)); - } -#else - rb_ary_push(ary, rb_str_new(h->h_addr, h->h_length)); -#endif - - return ary; -} - -static VALUE -mkaddrinfo(res0) +make_addrinfo(res0) struct addrinfo *res0; { VALUE base, ary; @@ -2077,11 +1958,20 @@ mkaddrinfo(res0) return base; } +VALUE +sock_sockaddr(addr, len) + struct sockaddr *addr; + size_t len; +{ + return rb_str_new((char*)addr, len); +} + static VALUE sock_s_gethostbyname(obj, host) VALUE obj, host; { - return sock_mkhostent(sock_hostbyname(host)); + rb_secure(3); + return make_hostent(sock_addrinfo(host, Qnil, SOCK_STREAM, AI_CANONNAME), sock_sockaddr); } static VALUE @@ -2092,6 +1982,8 @@ sock_s_gethostbyaddr(argc, argv) VALUE addr, type; struct hostent *h; struct sockaddr *sa; + char **pch; + VALUE ary, names; int t = AF_INET; rb_scan_args(argc, argv, "11", &addr, &type); @@ -2105,8 +1997,31 @@ sock_s_gethostbyaddr(argc, argv) } #endif h = gethostbyaddr(RSTRING(addr)->ptr, RSTRING(addr)->len, t); + if (h == NULL) { +#ifdef HAVE_HSTRERROR + extern int h_errno; + rb_raise(rb_eSocket, "%s", (char*)hstrerror(h_errno)); +#else + rb_raise(rb_eSocket, "host not found"); +#endif + } + ary = rb_ary_new(); + rb_ary_push(ary, rb_str_new2(h->h_name)); + names = rb_ary_new(); + rb_ary_push(ary, names); + for (pch = h->h_aliases; *pch; pch++) { + rb_ary_push(names, rb_str_new2(*pch)); + } + rb_ary_push(ary, INT2NUM(h->h_addrtype)); +#ifdef h_addr + for (pch = h->h_addr_list; *pch; pch++) { + rb_ary_push(ary, rb_str_new(*pch, h->h_length)); + } +#else + rb_ary_push(ary, rb_str_new(h->h_addr, h->h_length)); +#endif - return sock_mkhostent(h); + return ary; } static VALUE @@ -2206,7 +2121,7 @@ sock_s_getaddrinfo(argc, argv) rb_raise(rb_eSocket, "getaddrinfo: %s", gai_strerror(error)); } - ret = mkaddrinfo(res); + ret = make_addrinfo(res); freeaddrinfo(res); return ret; } @@ -2369,7 +2284,7 @@ sock_s_unpack_sockaddr_in(self, addr) VALUE host; sockaddr = (struct sockaddr_in*)StringValuePtr(addr); - host = mkipaddr((struct sockaddr*)sockaddr); + host = make_ipaddr((struct sockaddr*)sockaddr); OBJ_INFECT(host, addr); return rb_assoc_new(INT2NUM(ntohs(sockaddr->sin_port)), host); } @@ -374,7 +374,7 @@ void posix_signal _((int, RETSIGTYPE (*)(int))); #endif void rb_trap_exit _((void)); void rb_trap_exec _((void)); -char *ruby_signal_name _((int)); +const char *ruby_signal_name _((int)); /* sprintf.c */ VALUE rb_f_sprintf _((int, VALUE*)); /* string.c */ |