[前][次][番号順一覧][スレッド一覧]

ruby-changes:36910

From: nobu <ko1@a...>
Date: Thu, 25 Dec 2014 16:01:31 +0900 (JST)
Subject: [ruby-changes:36910] nobu:r48991 (trunk): file.c: drop ignored chars

nobu	2014-12-25 16:01:22 +0900 (Thu, 25 Dec 2014)

  New Revision: 48991

  http://svn.ruby-lang.org/cgi-bin/viewvc.cgi?view=revision&revision=48991

  Log:
    file.c: drop ignored chars
    
    * file.c (rb_file_expand_path_internal): drop characters ignored
      by filesystem on Mac OS X.

  Modified files:
    trunk/ChangeLog
    trunk/file.c
    trunk/test/ruby/test_file_exhaustive.rb
Index: ChangeLog
===================================================================
--- ChangeLog	(revision 48990)
+++ ChangeLog	(revision 48991)
@@ -1,3 +1,8 @@ https://github.com/ruby/ruby/blob/trunk/ChangeLog#L1
+Thu Dec 25 16:01:19 2014  Nobuyoshi Nakada  <nobu@r...>
+
+	* file.c (rb_file_expand_path_internal): drop characters ignored
+	  by filesystem on Mac OS X.
+
 Thu Dec 25 15:36:15 2014  Nobuyoshi Nakada  <nobu@r...>
 
 	* dir.c (replace_real_basename): get the real name and replace the
Index: test/ruby/test_file_exhaustive.rb
===================================================================
--- test/ruby/test_file_exhaustive.rb	(revision 48990)
+++ test/ruby/test_file_exhaustive.rb	(revision 48991)
@@ -440,13 +440,25 @@ class TestFileExhaustive < Test::Unit::T https://github.com/ruby/ruby/blob/trunk/test/ruby/test_file_exhaustive.rb#L440
 
   def test_expand_path
     assert_equal(@file, File.expand_path(File.basename(@file), File.dirname(@file)))
-    if /cygwin|mingw|mswin|bccwin/ =~ RUBY_PLATFORM
+    case RUBY_PLATFORM
+    when /cygwin|mingw|mswin|bccwin/
       assert_equal(@file, File.expand_path(@file + " "))
       assert_equal(@file, File.expand_path(@file + "."))
       assert_equal(@file, File.expand_path(@file + "::$DATA"))
       assert_match(/\Ac:\//i, File.expand_path('c:'), '[ruby-core:31591]')
       assert_match(/\Ac:\//i, File.expand_path('c:foo', 'd:/bar'))
       assert_match(%r'\Ac:/bar/foo\z'i, File.expand_path('c:foo', 'c:/bar'))
+    when /darwin/
+      ["\u{feff}", *"\u{2000}"..."\u{2100}"].each do |c|
+        file = @file + c
+        begin
+          open(file) {}
+        rescue
+          assert_equal(file, File.expand_path(file), c.dump)
+        else
+          assert_equal(@file, File.expand_path(file), c.dump)
+        end
+      end
     end
     if DRIVE
       assert_match(%r"\Az:/foo\z"i, File.expand_path('/foo', "z:/bar"))
Index: file.c
===================================================================
--- file.c	(revision 48990)
+++ file.c	(revision 48991)
@@ -315,6 +315,38 @@ rb_str_normalize_ospath(const char *ptr, https://github.com/ruby/ruby/blob/trunk/file.c#L315
 
     return str;
 }
+
+static int
+ignored_char_p(const char *p, const char *e, rb_encoding *enc)
+{
+    unsigned char c;
+    if (p+3 > e) return 0;
+    switch ((unsigned char)*p) {
+      case 0xe2:
+	switch ((unsigned char)p[1]) {
+	  case 0x80:
+	    c = (unsigned char)p[2];
+	    /* c >= 0x200c && c <= 0x200f */
+	    if (c >= 0x8c && c <= 0x8f) return 3;
+	    /* c >= 0x202a && c <= 0x202e */
+	    if (c >= 0xaa && c <= 0xae) return 3;
+	    return 0;
+	  case 0x81:
+	    c = (unsigned char)p[2];
+	    /* c >= 0x206a && c <= 0x206f */
+	    if (c >= 0xaa && c <= 0xaf) return 3;
+	    return 0;
+	}
+	break;
+      case 0xef:
+	/* c == 0xfeff */
+	if ((unsigned char)p[1] == 0xbb &&
+	    (unsigned char)p[2] == 0xbf)
+	    return 3;
+	break;
+    }
+    return 0;
+}
 #endif
 
 static long
@@ -3103,6 +3135,27 @@ ntfs_tail(const char *path, const char * https://github.com/ruby/ruby/blob/trunk/file.c#L3135
     buflen = RSTRING_LEN(result),\
     pend = p + buflen)
 
+#ifdef __APPLE__
+# define SKIPPATHSEP(p) ((*(p)) ? 1 : 0)
+#else
+# define SKIPPATHSEP(p) 1
+#endif
+
+#define BUFCOPY(srcptr, srclen) do { \
+    const int skip = SKIPPATHSEP(p); \
+    rb_str_set_len(result, p-buf+skip); \
+    BUFCHECK(bdiff + ((srclen)+skip) >= buflen); \
+    p += skip; \
+    memcpy(p, (srcptr), (srclen)); \
+    p += (srclen); \
+} while (0)
+
+#define WITH_ROOTDIFF(stmt) do { \
+    long rootdiff = root - buf; \
+    stmt; \
+    root = buf + rootdiff; \
+} while (0)
+
 static VALUE
 copy_home_path(VALUE result, const char *dir)
 {
@@ -3374,17 +3427,25 @@ rb_file_expand_path_internal(VALUE fname https://github.com/ruby/ruby/blob/trunk/file.c#L3427
 	  case '\\':
 #endif
 	    if (s > b) {
-		long rootdiff = root - buf;
-		rb_str_set_len(result, p-buf+1);
-		BUFCHECK(bdiff + (s-b+1) >= buflen);
-		root = buf + rootdiff;
-		memcpy(++p, b, s-b);
-		p += s-b;
+		WITH_ROOTDIFF(BUFCOPY(b, s-b));
 		*p = '/';
 	    }
 	    b = ++s;
 	    break;
 	  default:
+#ifdef __APPLE__
+	    {
+		int n = ignored_char_p(s, fend, enc);
+		if (n) {
+		    if (s > b) {
+			WITH_ROOTDIFF(BUFCOPY(b, s-b));
+			*p = '\0';
+		    }
+		    b = s += n;
+		    break;
+		}
+	    }
+#endif
 	    Inc(s, fend, enc);
 	    break;
 	}
@@ -3406,10 +3467,7 @@ rb_file_expand_path_internal(VALUE fname https://github.com/ruby/ruby/blob/trunk/file.c#L3467
 	    }
 	}
 #endif
-	rb_str_set_len(result, p-buf+1);
-	BUFCHECK(bdiff + (s-b) >= buflen);
-	memcpy(++p, b, s-b);
-	p += s-b;
+	BUFCOPY(b, s-b);
 	rb_str_set_len(result, p-buf);
     }
     if (p == skiproot(buf, p + !!*p, enc) - 1) p++;

--
ML: ruby-changes@q...
Info: http://www.atdot.net/~ko1/quickml/

[前][次][番号順一覧][スレッド一覧]