summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorshyouhei <shyouhei@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2008-06-15 14:01:45 +0000
committershyouhei <shyouhei@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2008-06-15 14:01:45 +0000
commit52649a3ce9b90ddbb88b6946b360ef4335a0ca7b (patch)
tree599fa121ffb0caec281d790584c01f87aa39a0fe
parent98e63de0d75d18565c629ce9b045edb334e6b477 (diff)
merge revision(s) 16420,16454:
* file.c (file_expand_path): support for alternative data stream and ignored trailing garbages of NTFS. * file.c (rb_file_s_basename): ditto. * file.c (rb_file_s_extname): ditto. * lib/webrick/httpservlet/filehandler.rb: should normalize path name in path_info to prevent script disclosure vulnerability on DOSISH filesystems. (fix: CVE-2008-1891) Note: NTFS/FAT filesystem should not be published by the platforms other than Windows. Pathname interpretation (including short filename) is less than perfect. * lib/webrick/httpservlet/abstract.rb (WEBrick::HTTPServlet::AbstracServlet#redirect_to_directory_uri): should escape the value of Location: header. * lib/webrick/httpservlet/cgi_runner.rb: accept interpreter command line arguments. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/branches/ruby_1_8_5@17300 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
-rw-r--r--defines.h12
-rw-r--r--file.c66
-rw-r--r--version.h2
3 files changed, 65 insertions, 15 deletions
diff --git a/defines.h b/defines.h
index ef80989925..ae1277a6bf 100644
--- a/defines.h
+++ b/defines.h
@@ -254,6 +254,18 @@ __attribute__ ((noinline))
#define ENV_IGNORECASE
#endif
+#ifndef CASEFOLD_FILESYSTEM
+# if defined DOSISH || defined __VMS
+# define CASEFOLD_FILESYSTEM 1
+# else
+# define CASEFOLD_FILESYSTEM 0
+# endif
+#endif
+
+#ifndef DLEXT_MAXLEN
+#define DLEXT_MAXLEN 4
+#endif
+
#ifndef RUBY_PLATFORM
#define RUBY_PLATFORM "unknown-unknown"
#endif
diff --git a/file.c b/file.c
index e92dd7962b..2dd2f35aa8 100644
--- a/file.c
+++ b/file.c
@@ -2309,6 +2309,18 @@ rb_file_s_umask(argc, argv)
#define isdirsep(x) ((x) == '/')
#endif
+#if defined _WIN32 || defined __CYGWIN__
+#define USE_NTFS 1
+#else
+#define USE_NTFS 0
+#endif
+
+#if USE_NTFS
+#define istrailinggabage(x) ((x) == '.' || (x) == ' ')
+#else
+#define istrailinggabage(x) 0
+#endif
+
#ifndef CharNext /* defined as CharNext[AW] on Windows. */
# if defined(DJGPP)
# define CharNext(p) ((p) + mblen(p, MB_CUR_MAX))
@@ -2482,6 +2494,30 @@ ntfs_tail(const char *path)
}
#endif
+#if USE_NTFS
+static char *
+ntfs_tail(const char *path)
+{
+ while (*path && *path != ':') {
+ if (istrailinggabage(*path)) {
+ const char *last = path++;
+ while (istrailinggabage(*path)) path++;
+ if (!*path || *path == ':') return (char *)last;
+ }
+ else if (isdirsep(*path)) {
+ const char *last = path++;
+ while (isdirsep(*path)) path++;
+ if (!*path) return (char *)last;
+ if (*path == ':') path++;
+ }
+ else {
+ path = CharNext(path);
+ }
+ }
+ return (char *)path;
+}
+#endif
+
#define BUFCHECK(cond) do {\
long bdiff = p - buf;\
while (cond) {\
@@ -2728,23 +2764,17 @@ file_expand_path(fname, dname, result)
if (p == skiproot(buf) - 1) p++;
buflen = p - buf;
- RSTRING(result)->len = buflen;
- *p = '\0';
#if USE_NTFS
- if (1 &&
-#ifdef __CYGWIN__
- !(buf[0] == '/' && !buf[1]) &&
-#endif
- !strpbrk(b = buf, "*?")) {
+ *p = '\0';
+ if (!strpbrk(b = buf, "*?")) {
size_t len;
WIN32_FIND_DATA wfd;
#ifdef __CYGWIN__
- int lnk_added = 0, is_symlink = 0;
+ int lnk_added = 0;
struct stat st;
char w32buf[MAXPATHLEN], sep = 0;
p = 0;
if (lstat(buf, &st) == 0 && S_ISLNK(st.st_mode)) {
- is_symlink = 1;
p = strrdirsep(buf);
if (!p) p = skipprefix(buf);
if (p) {
@@ -2757,7 +2787,8 @@ file_expand_path(fname, dname, result)
}
if (p) *p = sep;
else p = buf;
- if (is_symlink && b == w32buf) {
+ if (b == w32buf) {
+ strlcat(w32buf, p, sizeof(w32buf));
len = strlen(p);
if (len > 4 && strcasecmp(p + len - 4, ".lnk") != 0) {
lnk_added = 1;
@@ -2785,6 +2816,8 @@ file_expand_path(fname, dname, result)
#endif
if (tainted) OBJ_TAINT(result);
+ RSTRING(result)->len = buflen;
+ RSTRING(result)->ptr[buflen] = '\0';
return result;
}
@@ -2847,7 +2880,12 @@ rmext(p, l1, e)
}
if (l1 < l2) return l1;
- if (strncmp(p+l1-l2, e, l2) == 0) {
+#if CASEFOLD_FILESYSTEM
+#define fncomp strncasecmp
+#else
+#define fncomp strncmp
+#endif
+ if (fncomp(p+l1-l2, e, l2) == 0) {
return l1-l2;
}
return 0;
@@ -2926,7 +2964,7 @@ rb_file_s_basename(argc, argv)
if (NIL_P(fext) || !(f = rmext(p, n, StringValueCStr(fext)))) {
f = n;
}
- if (f == RSTRING(fname)->len) return fname;
+ if (f == RSTRING(fname)->len) return fname;
}
basename = rb_str_new(p, f);
OBJ_INFECT(basename, fname);
@@ -3009,7 +3047,7 @@ rb_file_s_extname(klass, fname)
if (!p)
p = name;
else
- name = ++p;
+ p++;
e = 0;
while (*p) {
@@ -3039,7 +3077,7 @@ rb_file_s_extname(klass, fname)
break;
p = CharNext(p);
}
- if (!e || e == name || e+1 == p) /* no dot, or the only dot is first or end? */
+ if (!e || e+1 == p) /* no dot, or the only dot is first or end? */
return rb_str_new(0, 0);
extname = rb_str_new(e, p - e); /* keep the dot, too! */
OBJ_INFECT(extname, fname);
diff --git a/version.h b/version.h
index 4af88b0dfa..0beb57705c 100644
--- a/version.h
+++ b/version.h
@@ -2,7 +2,7 @@
#define RUBY_RELEASE_DATE "2008-06-15"
#define RUBY_VERSION_CODE 185
#define RUBY_RELEASE_CODE 20080615
-#define RUBY_PATCHLEVEL 208
+#define RUBY_PATCHLEVEL 209
#define RUBY_VERSION_MAJOR 1
#define RUBY_VERSION_MINOR 8