From: Tanaka Akira Date: 2010-01-25T01:11:56+09:00 Subject: [ruby-core:27761] Re: [Feature #2619] Proposed method: Process.fork_supported? 2010/1/23 Charles Oliver Nutter : > I'm also curious how this affects Windows behavior, since currently > MRI stubs out many methods to return nil on Windows (like all of 'etc' > library, for example). Should they raise NotImplementedError? Should > they return false for respond_to?. It may be good chance to change etc library. Index: etc.c =================================================================== --- etc.c (revision 26395) +++ etc.c (working copy) @@ -106,6 +106,7 @@ setup_passwd(struct passwd *pwd) } #endif +#if defined(HAVE_GETPWENT) /* Returns the /etc/passwd information for the user with specified integer * user id (uid). * @@ -118,7 +119,6 @@ setup_passwd(struct passwd *pwd) static VALUE etc_getpwuid(int argc, VALUE *argv, VALUE obj) { -#if defined(HAVE_GETPWENT) VALUE id; rb_uid_t uid; struct passwd *pwd; @@ -133,11 +133,12 @@ etc_getpwuid(int argc, VALUE *argv, VALU pwd = getpwuid(uid); if (pwd == 0) rb_raise(rb_eArgError, "can't find user for %d", (int)uid); return setup_passwd(pwd); +} #else - return Qnil; +#define etc_getpwuid rb_f_notimplement #endif -} +#ifdef HAVE_GETPWENT /* Returns the /etc/passwd information for the user with specified login name. * * The information is returned as a Struct::Passwd; see getpwent above for @@ -149,17 +150,16 @@ etc_getpwuid(int argc, VALUE *argv, VALU static VALUE etc_getpwnam(VALUE obj, VALUE nam) { -#ifdef HAVE_GETPWENT struct passwd *pwd; SafeStringValue(nam); pwd = getpwnam(RSTRING_PTR(nam)); if (pwd == 0) rb_raise(rb_eArgError, "can't find user for %s", RSTRING_PTR(nam)); return setup_passwd(pwd); +} #else - return Qnil; +#define etc_getpwnam rb_f_notimplement #endif -} #ifdef HAVE_GETPWENT static int passwd_blocking = 0; @@ -194,6 +194,7 @@ each_passwd(void) } #endif +#ifdef HAVE_GETPWENT /* Provides a convenient Ruby iterator which executes a block for each entry * in the /etc/passwd file. * @@ -212,7 +213,6 @@ each_passwd(void) static VALUE etc_passwd(VALUE obj) { -#ifdef HAVE_GETPWENT struct passwd *pw; rb_secure(4); @@ -222,10 +222,13 @@ etc_passwd(VALUE obj) else if (pw = getpwent()) { return setup_passwd(pw); } -#endif return Qnil; } +#else +#define etc_passwd rb_f_notimplement +#endif +#ifdef HAVE_GETPWENT /* Iterates for each entry in the /etc/passwd file if a block is given. * If no block is given, returns the enumerator. * @@ -247,37 +250,43 @@ etc_passwd(VALUE obj) static VALUE etc_each_passwd(VALUE obj) { -#ifdef HAVE_GETPWENT RETURN_ENUMERATOR(obj, 0, 0); each_passwd(); -#endif return obj; } +#else +#define etc_each_passwd rb_f_notimplement +#endif +#ifdef HAVE_GETPWENT /* Resets the process of reading the /etc/passwd file, so that the next call * to getpwent will return the first entry again. */ static VALUE etc_setpwent(VALUE obj) { -#ifdef HAVE_GETPWENT setpwent(); -#endif return Qnil; } +#else +#define etc_setpwent rb_f_notimplement +#endif +#ifdef HAVE_GETPWENT /* Ends the process of scanning through the /etc/passwd file begun with * getpwent, and closes the file. */ static VALUE etc_endpwent(VALUE obj) { -#ifdef HAVE_GETPWENT endpwent(); -#endif return Qnil; } +#else +#define etc_endpwent rb_f_notimplement +#endif +#ifdef HAVE_GETPWENT /* Returns an entry from the /etc/passwd file. The first time it is called it * opens the file and returns the first entry; each successive call returns * the next entry, or nil if the end of the file has been reached. @@ -307,15 +316,16 @@ etc_endpwent(VALUE obj) static VALUE etc_getpwent(VALUE obj) { -#ifdef HAVE_GETPWENT struct passwd *pw; if (pw = getpwent()) { return setup_passwd(pw); } -#endif return Qnil; } +#else +#define etc_getpwent rb_f_notimplement +#endif #ifdef HAVE_GETGRENT static VALUE @@ -340,6 +350,7 @@ setup_group(struct group *grp) } #endif +#ifdef HAVE_GETGRENT /* Returns information about the group with specified integer group id (gid), * as found in /etc/group. * @@ -353,7 +364,6 @@ setup_group(struct group *grp) static VALUE etc_getgrgid(int argc, VALUE *argv, VALUE obj) { -#ifdef HAVE_GETGRENT VALUE id; gid_t gid; struct group *grp; @@ -368,11 +378,12 @@ etc_getgrgid(int argc, VALUE *argv, VALU grp = getgrgid(gid); if (grp == 0) rb_raise(rb_eArgError, "can't find group for %d", (int)gid); return setup_group(grp); +} #else - return Qnil; +#define etc_getgrgid rb_f_notimplement #endif -} +#ifdef HAVE_GETGRENT /* Returns information about the group with specified String name, as found * in /etc/group. * @@ -386,7 +397,6 @@ etc_getgrgid(int argc, VALUE *argv, VALU static VALUE etc_getgrnam(VALUE obj, VALUE nam) { -#ifdef HAVE_GETGRENT struct group *grp; rb_secure(4); @@ -394,10 +404,10 @@ etc_getgrnam(VALUE obj, VALUE nam) grp = getgrnam(RSTRING_PTR(nam)); if (grp == 0) rb_raise(rb_eArgError, "can't find group for %s", RSTRING_PTR(nam)); return setup_group(grp); +} #else - return Qnil; +#define etc_getgrnam rb_f_notimplement #endif -} #ifdef HAVE_GETGRENT static int group_blocking = 0; @@ -432,6 +442,7 @@ each_group(void) } #endif +#ifdef HAVE_GETGRENT /* Provides a convenient Ruby iterator which executes a block for each entry * in the /etc/group file. * @@ -450,7 +461,6 @@ each_group(void) static VALUE etc_group(VALUE obj) { -#ifdef HAVE_GETGRENT struct group *grp; rb_secure(4); @@ -460,9 +470,11 @@ etc_group(VALUE obj) else if (grp = getgrent()) { return setup_group(grp); } -#endif return Qnil; } +#else +#define etc_group rb_f_notimplement +#endif #ifdef HAVE_GETGRENT /* Iterates for each entry in the /etc/group file if a block is given. @@ -490,32 +502,39 @@ etc_each_group(VALUE obj) each_group(); return obj; } +#else +#define etc_each_group rb_f_notimplement #endif +#ifdef HAVE_GETGRENT /* Resets the process of reading the /etc/group file, so that the next call * to getgrent will return the first entry again. */ static VALUE etc_setgrent(VALUE obj) { -#ifdef HAVE_GETGRENT setgrent(); -#endif return Qnil; } +#else +#define etc_setgrent rb_f_notimplement +#endif +#ifdef HAVE_GETGRENT /* Ends the process of scanning through the /etc/group file begun by * getgrent, and closes the file. */ static VALUE etc_endgrent(VALUE obj) { -#ifdef HAVE_GETGRENT endgrent(); -#endif return Qnil; } +#else +#define etc_endgrent rb_f_notimplement +#endif +#ifdef HAVE_GETGRENT /* Returns an entry from the /etc/group file. The first time it is called it * opens the file and returns the first entry; each successive call returns * the next entry, or nil if the end of the file has been reached. @@ -539,15 +558,16 @@ etc_endgrent(VALUE obj) static VALUE etc_getgrent(VALUE obj) { -#ifdef HAVE_GETGRENT struct group *gr; if (gr = getgrent()) { return setup_group(gr); } -#endif return Qnil; } +#else +#define etc_getgrent rb_f_notimplement +#endif /* The etc module provides access to information from the /etc/passwd and * /etc/group files on Linux and Unix systems. @@ -614,6 +634,6 @@ Init_etc(void) rb_define_const(mEtc, "Group", sGroup); rb_extend_object(sGroup, rb_mEnumerable); - rb_define_singleton_method(sGroup, "each", etc_each_group, 0); #endif + rb_define_singleton_method(sGroup, "each", etc_each_group, 0); } -- Tanaka Akira