Skip to content

Commit

Permalink
Fix hang in wkwebview implemenation of webview::cookies()
Browse files Browse the repository at this point in the history
  • Loading branch information
acharron-hl committed Feb 11, 2025
1 parent cf18194 commit 48893e4
Show file tree
Hide file tree
Showing 2 changed files with 17 additions and 3 deletions.
6 changes: 6 additions & 0 deletions .changes/wkwebview-race-condition.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
---
wry: minor
---

Fix a bug in the wkwebview implementation that could cause hangs and crashes
when wait_for_blocking_operation() was called multiple times in quick succession.
14 changes: 11 additions & 3 deletions src/wkwebview/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -78,7 +78,7 @@ use std::{
panic::AssertUnwindSafe,
ptr::{null_mut, NonNull},
str::{self, FromStr},
sync::{Arc, Mutex},
sync::{Arc, Mutex}, thread, time::Duration,
};

#[cfg(feature = "mac-proxy")]
Expand Down Expand Up @@ -1054,16 +1054,24 @@ unsafe fn window_position(view: &NSView, x: i32, y: i32, height: f64) -> CGPoint
CGPoint::new(x as f64, frame.size.height - y as f64 - height)
}

/// Wait synchronously for the NSRunLoop to run until a receiver has a message.
unsafe fn wait_for_blocking_operation<T>(rx: std::sync::mpsc::Receiver<T>) -> Result<T> {
let interval = 0.0002;
let limit = 1.;
let mut elapsed = 0.;
// run event loop until we get the response back, blocking for at most 3 seconds
loop {
let rl = objc2_foundation::NSRunLoop::mainRunLoop();
let d = NSDate::dateWithTimeIntervalSinceNow(interval);
rl.runUntilDate(&d);
let limit_date = NSDate::dateWithTimeIntervalSinceNow(interval);

let mode = NSString::from_str("NSDefaultRunLoopMode");
rl.acceptInputForMode_beforeDate(&mode, &limit_date);
thread::sleep(Duration::from_secs_f64(interval));

if let Ok(response) = rx.try_recv() {
// Extra 1ms just to make sure our runloop is cleared.
// See https://github.com/tauri-apps/wry/pull/1486 for a writeup of why this was added.
thread::sleep(Duration::from_millis(1));
return Ok(response);
}
elapsed += interval;
Expand Down

0 comments on commit 48893e4

Please sign in to comment.