Skip to content

Commit 43e20a8

Browse files
committed
Fix os.putenv & test_os.test_envronb
1 parent 48299cd commit 43e20a8

File tree

2 files changed

+22
-23
lines changed

2 files changed

+22
-23
lines changed

Lib/test/test_os.py

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1109,9 +1109,6 @@ def test_get_exec_path(self):
11091109

11101110
@unittest.skipUnless(os.supports_bytes_environ,
11111111
"os.environb required for this test.")
1112-
# TODO: RUSTPYTHON (UnicodeDecodeError: can't decode bytes for utf-8)
1113-
# Need to fix 'surrogateescape'
1114-
@unittest.expectedFailure
11151112
def test_environb(self):
11161113
# os.environ -> os.environb
11171114
value = 'euro\u20ac'

vm/src/stdlib/os.rs

Lines changed: 22 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -370,18 +370,11 @@ pub(super) mod _os {
370370
Ok(list)
371371
}
372372

373-
fn pyref_as_str<'a>(
374-
obj: &'a Either<PyStrRef, PyBytesRef>,
375-
vm: &VirtualMachine,
376-
) -> PyResult<&'a str> {
377-
Ok(match obj {
378-
Either::A(ref s) => s.as_str(),
379-
Either::B(ref b) => super::bytes_as_osstr(b.as_bytes(), vm)?
380-
.to_str()
381-
.ok_or_else(|| {
382-
vm.new_unicode_decode_error("can't decode bytes for utf-8".to_owned())
383-
})?,
384-
})
373+
fn env_bytes_as_bytes(obj: &Either<PyStrRef, PyBytesRef>) -> &[u8] {
374+
match obj {
375+
Either::A(ref s) => s.as_str().as_bytes(),
376+
Either::B(ref b) => b.as_bytes(),
377+
}
385378
}
386379

387380
#[pyfunction]
@@ -390,27 +383,36 @@ pub(super) mod _os {
390383
value: Either<PyStrRef, PyBytesRef>,
391384
vm: &VirtualMachine,
392385
) -> PyResult<()> {
393-
let key = pyref_as_str(&key, vm)?;
394-
let value = pyref_as_str(&value, vm)?;
395-
if key.contains('\0') || value.contains('\0') {
386+
let key = env_bytes_as_bytes(&key);
387+
let value = env_bytes_as_bytes(&value);
388+
if key.contains(&b'\0') || value.contains(&b'\0') {
396389
return Err(vm.new_value_error("embedded null byte".to_string()));
397390
}
398-
if key.is_empty() || key.contains('=') {
391+
if key.is_empty() || key.contains(&b'=') {
399392
return Err(vm.new_value_error("illegal environment variable name".to_string()));
400393
}
394+
let key = super::bytes_as_osstr(key, vm)?;
395+
let value = super::bytes_as_osstr(value, vm)?;
401396
env::set_var(key, value);
402397
Ok(())
403398
}
404399

405400
#[pyfunction]
406401
fn unsetenv(key: Either<PyStrRef, PyBytesRef>, vm: &VirtualMachine) -> PyResult<()> {
407-
let key = pyref_as_str(&key, vm)?;
408-
if key.contains('\0') {
402+
let key = env_bytes_as_bytes(&key);
403+
if key.contains(&b'\0') {
409404
return Err(vm.new_value_error("embedded null byte".to_string()));
410405
}
411-
if key.is_empty() || key.contains('=') {
412-
return Err(vm.new_errno_error(22, format!("Invalid argument: {key}")));
406+
if key.is_empty() || key.contains(&b'=') {
407+
return Err(vm.new_errno_error(
408+
22,
409+
format!(
410+
"Invalid argument: {}",
411+
std::str::from_utf8(key).unwrap_or("<bytes encoding failure>")
412+
),
413+
));
413414
}
415+
let key = super::bytes_as_osstr(key, vm)?;
414416
env::remove_var(key);
415417
Ok(())
416418
}

0 commit comments

Comments
 (0)