ruby-changes:30108
From: nobu <ko1@a...>
Date: Thu, 25 Jul 2013 13:07:03 +0900 (JST)
Subject: [ruby-changes:30108] nobu:r42160 (trunk): file.c: split rb_home_dir
nobu 2013-07-25 13:06:50 +0900 (Thu, 25 Jul 2013) New Revision: 42160 http://svn.ruby-lang.org/cgi-bin/viewvc.cgi?view=rev&revision=42160 Log: file.c: split rb_home_dir * dir.c (dir_s_home): use rb_home_dir_of and rb_default_home_dir. * file.c (rb_home_dir_of): split from rb_home_dir() for the home directry of the given user, and the user name is a VALUE, not a bare pointer. should raise if the user does not exist. * file.c (rb_default_home_dir): split from rb_home_dir() for the home directry of the current user. Modified files: trunk/ChangeLog trunk/dir.c trunk/file.c trunk/internal.h trunk/test/ruby/test_dir.rb Index: ChangeLog =================================================================== --- ChangeLog (revision 42159) +++ ChangeLog (revision 42160) @@ -1,3 +1,14 @@ https://github.com/ruby/ruby/blob/trunk/ChangeLog#L1 +Thu Jul 25 13:06:46 2013 Nobuyoshi Nakada <nobu@r...> + + * dir.c (dir_s_home): use rb_home_dir_of and rb_default_home_dir. + + * file.c (rb_home_dir_of): split from rb_home_dir() for the home + directry of the given user, and the user name is a VALUE, not a bare + pointer. should raise if the user does not exist. + + * file.c (rb_default_home_dir): split from rb_home_dir() for the home + directry of the current user. + Thu Jul 25 12:32:11 2013 Koichi Sasada <ko1@a...> * ext/openssl/ossl.c: support additional three thread synchronization Index: dir.c =================================================================== --- dir.c (revision 42159) +++ dir.c (revision 42160) @@ -2125,12 +2125,18 @@ dir_s_home(int argc, VALUE *argv, VALUE https://github.com/ruby/ruby/blob/trunk/dir.c#L2125 VALUE user; const char *u = 0; - rb_scan_args(argc, argv, "01", &user); + rb_check_arity(argc, 0, 1); + user = (argc > 0) argv[0] : Qnil; if (!NIL_P(user)) { SafeStringValue(user); + rb_must_asciicompat(user); u = StringValueCStr(user); + if (*u) { + return rb_home_dir_of(user, rb_str_new(0, 0)); + } } - return rb_home_dir(u, rb_str_new(0, 0)); + return rb_default_home_dir(rb_str_new(0, 0)); + } #if 0 Index: internal.h =================================================================== --- internal.h (revision 42159) +++ internal.h (revision 42160) @@ -246,7 +246,8 @@ void rb_call_end_proc(VALUE data); https://github.com/ruby/ruby/blob/trunk/internal.h#L246 void rb_mark_end_proc(void); /* file.c */ -VALUE rb_home_dir(const char *user, VALUE result); +VALUE rb_home_dir_of(VALUE user, VALUE result); +VALUE rb_default_home_dir(VALUE result); VALUE rb_realpath_internal(VALUE basedir, VALUE path, int strict); void rb_file_const(const char*, VALUE); int rb_file_load_ok(const char *); Index: test/ruby/test_dir.rb =================================================================== --- test/ruby/test_dir.rb (revision 42159) +++ test/ruby/test_dir.rb (revision 42160) @@ -217,4 +217,26 @@ class TestDir < Test::Unit::TestCase https://github.com/ruby/ruby/blob/trunk/test/ruby/test_dir.rb#L217 bug8597 = '[ruby-core:55764] [Bug #8597]' assert_empty(Dir.glob(File.join(@root, "<")), bug8597) end + + def test_home + env_home = ENV["HOME"] + env_logdir = ENV["LOGDIR"] + ENV.delete("HOME") + ENV.delete("LOGDIR") + + assert_raise(ArgumentError) { Dir.home } + assert_raise(ArgumentError) { Dir.home("") } + ENV["HOME"] = @nodir + assert_nothing_raised(ArgumentError) { + assert_equal(@nodir, Dir.home) + assert_equal(@nodir, Dir.home("")) + } + %W[no:such:user \u{7559 5b88}:\u{756a}].each do |user| + assert_raise_with_message(ArgumentError, /#{user}/) {Dir.home(user)} + end + ensure + ENV["HOME"] = env_home + ENV["LOGDIR"] = env_logdir + end + end Index: file.c =================================================================== --- file.c (revision 42159) +++ file.c (revision 42160) @@ -2885,10 +2885,9 @@ ntfs_tail(const char *path, const char * https://github.com/ruby/ruby/blob/trunk/file.c#L2885 buflen = RSTRING_LEN(result),\ pend = p + buflen) -VALUE -rb_home_dir(const char *user, VALUE result) +static VALUE +copy_home_path(VALUE result, const char *dir) { - const char *dir; char *buf; #if defined DOSISH || defined __CYGWIN__ char *p, *bend; @@ -2896,29 +2895,9 @@ rb_home_dir(const char *user, VALUE resu https://github.com/ruby/ruby/blob/trunk/file.c#L2895 long dirlen; rb_encoding *enc; - if (!user || !*user) { - if (!(dir = getenv("HOME"))) { - rb_raise(rb_eArgError, "couldn't find HOME environment -- expanding `~'"); - } - dirlen = strlen(dir); - rb_str_resize(result, dirlen); - memcpy(buf = RSTRING_PTR(result), dir, dirlen); - } - else { -#ifdef HAVE_PWD_H - struct passwd *pwPtr = getpwnam(user); - if (!pwPtr) { - endpwent(); - return Qnil; - } - dirlen = strlen(pwPtr->pw_dir); - rb_str_resize(result, dirlen); - memcpy(buf = RSTRING_PTR(result), pwPtr->pw_dir, dirlen + 1); - endpwent(); -#else - return Qnil; -#endif - } + dirlen = strlen(dir); + rb_str_resize(result, dirlen); + memcpy(buf = RSTRING_PTR(result), dir, dirlen); enc = rb_filesystem_encoding(); rb_enc_associate(result, enc); #if defined DOSISH || defined __CYGWIN__ @@ -2931,6 +2910,33 @@ rb_home_dir(const char *user, VALUE resu https://github.com/ruby/ruby/blob/trunk/file.c#L2910 return result; } +VALUE +rb_home_dir_of(VALUE user, VALUE result) +{ +#ifdef HAVE_PWD_H + struct passwd *pwPtr = getpwnam(RSTRING_PTR(user)); + if (!pwPtr) { + endpwent(); +#endif + rb_raise(rb_eArgError, "user %"PRIsVALUE" doesn't exist", user); +#ifdef HAVE_PWD_H + } + copy_home_path(result, pwPtr->pw_dir); + endpwent(); +#endif + return result; +} + +VALUE +rb_default_home_dir(VALUE result) +{ + const char *dir = getenv("HOME"); + if (!dir) { + rb_raise(rb_eArgError, "couldn't find HOME environment -- expanding `~'"); + } + return copy_home_path(result, dir); +} + #ifndef _WIN32 static char * append_fspath(VALUE result, VALUE fname, char *dir, rb_encoding **enc, rb_encoding *fsenc) @@ -2980,6 +2986,7 @@ rb_file_expand_path_internal(VALUE fname https://github.com/ruby/ruby/blob/trunk/file.c#L2986 b = 0; rb_str_set_len(result, 0); if (*++s) ++s; + rb_default_home_dir(result); } else { s = nextdirsep(b = s, fend, enc); @@ -2987,13 +2994,11 @@ rb_file_expand_path_internal(VALUE fname https://github.com/ruby/ruby/blob/trunk/file.c#L2994 BUFCHECK(bdiff + userlen >= buflen); memcpy(p, b, userlen); rb_str_set_len(result, userlen); + rb_enc_associate(result, enc); + rb_home_dir_of(result, result); buf = p + 1; p += userlen; } - if (NIL_P(rb_home_dir(buf, result))) { - rb_enc_raise(enc, rb_eArgError, "%.0"PRIsVALUE"user %s doesn't exist", fname, - buf); - } if (!rb_is_absolute_path(RSTRING_PTR(result))) { if (userlen) { rb_enc_raise(enc, rb_eArgError, "non-absolute home of %.*s%.0"PRIsVALUE, -- ML: ruby-changes@q... Info: http://www.atdot.net/~ko1/quickml/