Skip to content

Commit 2db0337

Browse files
committed
Map Windows ERROR_LOCK_VIOLATION to ErrorKind::WouldBlock
This changes decode_error_kind() on Windows to map ERROR_LOCK_VIOLATION to ErrorKind::WouldBlock instead of ErrorKind::Uncategorized
1 parent 2caf278 commit 2db0337

File tree

3 files changed

+29
-24
lines changed

3 files changed

+29
-24
lines changed

library/std/src/fs/tests.rs

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -358,6 +358,28 @@ fn file_lock_blocking_async() {
358358
t.join().unwrap();
359359
}
360360

361+
#[test]
362+
#[cfg(windows)]
363+
fn file_try_lock_async() {
364+
const FILE_FLAG_OVERLAPPED: u32 = 0x40000000;
365+
366+
let tmpdir = tmpdir();
367+
let filename = &tmpdir.join("file_try_lock_async.txt");
368+
let f1 = check!(File::create(filename));
369+
let f2 =
370+
check!(OpenOptions::new().custom_flags(FILE_FLAG_OVERLAPPED).write(true).open(filename));
371+
372+
// Check that shared locks block exclusive locks
373+
check!(f1.lock_shared());
374+
assert_matches!(f2.try_lock().unwrap_err().kind(), ErrorKind::WouldBlock);
375+
check!(f1.unlock());
376+
377+
// Check that exclusive locks block all locks
378+
check!(f1.lock());
379+
assert_matches!(f2.try_lock().unwrap_err().kind(), ErrorKind::WouldBlock);
380+
assert_matches!(f2.try_lock_shared().unwrap_err().kind(), ErrorKind::WouldBlock);
381+
}
382+
361383
#[test]
362384
fn file_test_io_seek_shakedown() {
363385
// 01234567890123

library/std/src/sys/fs/windows.rs

Lines changed: 6 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -400,7 +400,7 @@ impl File {
400400
}
401401

402402
pub fn try_lock(&self) -> io::Result<()> {
403-
let result = cvt(unsafe {
403+
cvt(unsafe {
404404
let mut overlapped = mem::zeroed();
405405
c::LockFileEx(
406406
self.handle.as_raw_handle(),
@@ -410,22 +410,13 @@ impl File {
410410
u32::MAX,
411411
&mut overlapped,
412412
)
413-
});
413+
})?;
414414

415-
match result {
416-
Ok(_) => Ok(()),
417-
Err(err)
418-
if err.raw_os_error() == Some(c::ERROR_IO_PENDING as i32)
419-
|| err.raw_os_error() == Some(c::ERROR_LOCK_VIOLATION as i32) =>
420-
{
421-
Err(io::ErrorKind::WouldBlock.into())
422-
}
423-
Err(err) => Err(err),
424-
}
415+
Ok(())
425416
}
426417

427418
pub fn try_lock_shared(&self) -> io::Result<()> {
428-
let result = cvt(unsafe {
419+
cvt(unsafe {
429420
let mut overlapped = mem::zeroed();
430421
c::LockFileEx(
431422
self.handle.as_raw_handle(),
@@ -435,18 +426,9 @@ impl File {
435426
u32::MAX,
436427
&mut overlapped,
437428
)
438-
});
429+
})?;
439430

440-
match result {
441-
Ok(_) => Ok(()),
442-
Err(err)
443-
if err.raw_os_error() == Some(c::ERROR_IO_PENDING as i32)
444-
|| err.raw_os_error() == Some(c::ERROR_LOCK_VIOLATION as i32) =>
445-
{
446-
Err(io::ErrorKind::WouldBlock.into())
447-
}
448-
Err(err) => Err(err),
449-
}
431+
Ok(())
450432
}
451433

452434
pub fn unlock(&self) -> io::Result<()> {

library/std/src/sys/pal/windows/mod.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -114,6 +114,7 @@ pub fn decode_error_kind(errno: i32) -> ErrorKind {
114114
c::ERROR_TOO_MANY_LINKS => return TooManyLinks,
115115
c::ERROR_FILENAME_EXCED_RANGE => return InvalidFilename,
116116
c::ERROR_CANT_RESOLVE_FILENAME => return FilesystemLoop,
117+
c::ERROR_LOCK_VIOLATION => return WouldBlock,
117118
_ => {}
118119
}
119120

0 commit comments

Comments
 (0)