about summary refs log tree commit diff
path: root/src/libstd/sys
diff options
context:
space:
mode:
authorTobias Bucher <tobiasbucher5991@gmail.com>2015-11-17 23:33:34 +0000
committerTobias Bucher <tobiasbucher5991@gmail.com>2015-11-19 20:00:36 +0000
commit14983477cacd5576fadd7ead609c24451b748e56 (patch)
tree9410ef10cf7b79e1078509dd7b53e4de7adf2483 /src/libstd/sys
parent3e48b0e380319dc586a329baac640b9457feb87a (diff)
downloadrust-14983477cacd5576fadd7ead609c24451b748e56.tar.gz
rust-14983477cacd5576fadd7ead609c24451b748e56.zip
Ignore malformed environment variables on Windows too
Leading equals symbols are treated as part of the variable name, if
there is no other equality symbol or none at all, the environment string
is ignored.
Diffstat (limited to 'src/libstd/sys')
-rw-r--r--src/libstd/sys/windows/os.rs39
1 files changed, 24 insertions, 15 deletions
diff --git a/src/libstd/sys/windows/os.rs b/src/libstd/sys/windows/os.rs
index 52740b2cad4..545dec270fb 100644
--- a/src/libstd/sys/windows/os.rs
+++ b/src/libstd/sys/windows/os.rs
@@ -78,22 +78,31 @@ impl Iterator for Env {
     type Item = (OsString, OsString);
 
     fn next(&mut self) -> Option<(OsString, OsString)> {
-        unsafe {
-            if *self.cur == 0 { return None }
-            let p = &*self.cur;
-            let mut len = 0;
-            while *(p as *const u16).offset(len) != 0 {
-                len += 1;
+        loop {
+            unsafe {
+                if *self.cur == 0 { return None }
+                let p = &*self.cur as *const u16;
+                let mut len = 0;
+                while *p.offset(len) != 0 {
+                    len += 1;
+                }
+                let s = slice::from_raw_parts(p, len as usize);
+                self.cur = self.cur.offset(len + 1);
+
+                // Windows allows environment variables to start with an equals
+                // symbol (in any other position, this is the separator between
+                // variable name and value). Since`s` has at least length 1 at
+                // this point (because the empty string terminates the array of
+                // environment variables), we can safely slice.
+                let pos = match s[1..].iter().position(|&u| u == b'=' as u16).map(|p| p + 1) {
+                    Some(p) => p,
+                    None => continue,
+                }
+                return Some((
+                    OsStringExt::from_wide(&s[..pos]),
+                    OsStringExt::from_wide(&s[pos+1..]),
+                ))
             }
-            let p = p as *const u16;
-            let s = slice::from_raw_parts(p, len as usize);
-            self.cur = self.cur.offset(len + 1);
-
-            let (k, v) = match s.iter().position(|&b| b == '=' as u16) {
-                Some(n) => (&s[..n], &s[n+1..]),
-                None => (s, &[][..]),
-            };
-            Some((OsStringExt::from_wide(k), OsStringExt::from_wide(v)))
         }
     }
 }