summaryrefslogtreecommitdiffstats
path: root/library/std/src/sys/windows/os.rs
diff options
context:
space:
mode:
Diffstat (limited to 'library/std/src/sys/windows/os.rs')
-rw-r--r--library/std/src/sys/windows/os.rs62
1 files changed, 51 insertions, 11 deletions
diff --git a/library/std/src/sys/windows/os.rs b/library/std/src/sys/windows/os.rs
index d7adeb266..58afca088 100644
--- a/library/std/src/sys/windows/os.rs
+++ b/library/std/src/sys/windows/os.rs
@@ -25,10 +25,6 @@ pub fn errno() -> i32 {
/// Gets a detailed string description for the given error number.
pub fn error_string(mut errnum: i32) -> String {
- // This value is calculated from the macro
- // MAKELANGID(LANG_SYSTEM_DEFAULT, SUBLANG_SYS_DEFAULT)
- let langId = 0x0800 as c::DWORD;
-
let mut buf = [0 as c::WCHAR; 2048];
unsafe {
@@ -56,13 +52,13 @@ pub fn error_string(mut errnum: i32) -> String {
flags | c::FORMAT_MESSAGE_FROM_SYSTEM | c::FORMAT_MESSAGE_IGNORE_INSERTS,
module,
errnum as c::DWORD,
- langId,
+ 0,
buf.as_mut_ptr(),
buf.len() as c::DWORD,
ptr::null(),
) as usize;
if res == 0 {
- // Sometimes FormatMessageW can fail e.g., system doesn't like langId,
+ // Sometimes FormatMessageW can fail e.g., system doesn't like 0 as langId,
let fm_err = errno();
return format!("OS Error {errnum} (FormatMessageW() returned error {fm_err})");
}
@@ -85,25 +81,69 @@ pub fn error_string(mut errnum: i32) -> String {
pub struct Env {
base: c::LPWCH,
- cur: c::LPWCH,
+ iter: EnvIterator,
+}
+
+// FIXME(https://github.com/rust-lang/rust/issues/114583): Remove this when <OsStr as Debug>::fmt matches <str as Debug>::fmt.
+pub struct EnvStrDebug<'a> {
+ iter: &'a EnvIterator,
+}
+
+impl fmt::Debug for EnvStrDebug<'_> {
+ fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
+ let Self { iter } = self;
+ let iter: EnvIterator = (*iter).clone();
+ let mut list = f.debug_list();
+ for (a, b) in iter {
+ list.entry(&(a.to_str().unwrap(), b.to_str().unwrap()));
+ }
+ list.finish()
+ }
+}
+
+impl Env {
+ pub fn str_debug(&self) -> impl fmt::Debug + '_ {
+ let Self { base: _, iter } = self;
+ EnvStrDebug { iter }
+ }
+}
+
+impl fmt::Debug for Env {
+ fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
+ let Self { base: _, iter } = self;
+ f.debug_list().entries(iter.clone()).finish()
+ }
}
impl Iterator for Env {
type Item = (OsString, OsString);
fn next(&mut self) -> Option<(OsString, OsString)> {
+ let Self { base: _, iter } = self;
+ iter.next()
+ }
+}
+
+#[derive(Clone)]
+struct EnvIterator(c::LPWCH);
+
+impl Iterator for EnvIterator {
+ type Item = (OsString, OsString);
+
+ fn next(&mut self) -> Option<(OsString, OsString)> {
+ let Self(cur) = self;
loop {
unsafe {
- if *self.cur == 0 {
+ if **cur == 0 {
return None;
}
- let p = self.cur as *const u16;
+ let p = *cur as *const u16;
let mut len = 0;
while *p.add(len) != 0 {
len += 1;
}
let s = slice::from_raw_parts(p, len);
- self.cur = self.cur.add(len + 1);
+ *cur = cur.add(len + 1);
// Windows allows environment variables to start with an equals
// symbol (in any other position, this is the separator between
@@ -137,7 +177,7 @@ pub fn env() -> Env {
if ch.is_null() {
panic!("failure getting env string from OS: {}", io::Error::last_os_error());
}
- Env { base: ch, cur: ch }
+ Env { base: ch, iter: EnvIterator(ch) }
}
}