Skip to content

Commit 3075d49

Browse files
committed
handle lack of TCP connection from phone
Before this commit described situation was possible, leading to stuck and not trying to reconnect. The phone is mainly connecting in several seconds, once I had a 16 secs measured time, so set this timeout to 30 secs for now including a marigin.
1 parent 772e0b8 commit 3075d49

File tree

3 files changed

+43
-5
lines changed

3 files changed

+43
-5
lines changed

src/bluetooth.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,9 +8,11 @@ use bluer::{
88
};
99
use futures::StreamExt;
1010
use simplelog::*;
11+
use std::sync::Arc;
1112
use std::time::Duration;
1213
use tokio::io::AsyncReadExt;
1314
use tokio::io::AsyncWriteExt;
15+
use tokio::sync::Notify;
1416
use tokio::task::JoinHandle;
1517
use tokio::time::sleep;
1618
use tokio::time::timeout;
@@ -302,6 +304,7 @@ pub async fn bluetooth_stop(state: BluetoothState) -> Result<()> {
302304
pub async fn bluetooth_setup_connection(
303305
advertise: bool,
304306
connect: Option<Address>,
307+
tcp_start: Arc<Notify>,
305308
) -> Result<BluetoothState> {
306309
use WifiInfoResponse::WifiInfoResponse;
307310
use WifiStartRequest::WifiStartRequest;
@@ -326,6 +329,7 @@ pub async fn bluetooth_setup_connection(
326329
info.set_security_mode(SecurityMode::WPA2_PERSONAL);
327330
info.set_access_point_type(AccessPointType::DYNAMIC);
328331
send_message(&mut stream, MessageId::WifiInfoResponse, info).await?;
332+
tcp_start.notify_one();
329333
read_message(&mut stream, MessageId::WifiStartResponse).await?;
330334
read_message(&mut stream, MessageId::WifiConnectStatus).await?;
331335
let _ = stream.shutdown().await?;

src/io_uring.rs

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ const NAME: &str = "<i><bright-black> proxy: </>";
1414
const USB_ACCESSORY_PATH: &str = "/dev/usb_accessory";
1515
const BUFFER_LEN: usize = 16 * 1024;
1616
const READ_TIMEOUT: Duration = Duration::new(5, 0);
17+
const TCP_CLIENT_TIMEOUT: Duration = Duration::new(30, 0);
1718

1819
async fn copy_file_to_stream(
1920
from: Rc<tokio_uring::fs::File>,
@@ -152,6 +153,7 @@ async fn copy_stream_to_file(
152153
pub async fn io_loop(
153154
stats_interval: Option<Duration>,
154155
need_restart: Arc<Notify>,
156+
tcp_start: Arc<Notify>,
155157
) -> Result<(), Box<dyn std::error::Error>> {
156158
info!("{} 🛰️ Starting TCP server...", NAME);
157159
let bind_addr = format!("0.0.0.0:{}", TCP_SERVER_PORT).parse().unwrap();
@@ -161,8 +163,23 @@ pub async fn io_loop(
161163
NAME, bind_addr
162164
);
163165
loop {
166+
// wait for bluetooth handshake
167+
tcp_start.notified().await;
168+
164169
// Asynchronously wait for an inbound TCP connection
165-
let (stream, addr) = listener.accept().await?;
170+
let retval = listener.accept();
171+
let (stream, addr) = match timeout(TCP_CLIENT_TIMEOUT, retval).await? {
172+
Ok((stream, addr)) => (stream, addr),
173+
Err(_) => {
174+
error!(
175+
"{} 📵 TCP server: timed out waiting for phone connection, restarting...",
176+
NAME
177+
);
178+
// notify main loop to restart
179+
need_restart.notify_one();
180+
continue;
181+
}
182+
};
166183
info!(
167184
"{} 📳 TCP server: new client connected: <b>{:?}</b>",
168185
NAME, addr

src/main.rs

Lines changed: 21 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -106,6 +106,7 @@ async fn tokio_main(
106106
legacy: bool,
107107
connect: Option<Address>,
108108
need_restart: Arc<Notify>,
109+
tcp_start: Arc<Notify>,
109110
) {
110111
let accessory_started = Arc::new(Notify::new());
111112
let accessory_started_cloned = accessory_started.clone();
@@ -122,7 +123,7 @@ async fn tokio_main(
122123
}
123124

124125
loop {
125-
match bluetooth_setup_connection(advertise, connect).await {
126+
match bluetooth_setup_connection(advertise, connect, tcp_start.clone()).await {
126127
Ok(state) => {
127128
// we're ready, gracefully shutdown bluetooth in task
128129
tokio::spawn(async move { bluetooth_stop(state).await });
@@ -143,7 +144,10 @@ async fn tokio_main(
143144
need_restart.notified().await;
144145

145146
// TODO: make proper main loop with cancelation
146-
info!("{} 📵 TCP/USB connection closed, trying again...", NAME);
147+
info!(
148+
"{} 📵 TCP/USB connection closed or not started, trying again...",
149+
NAME
150+
);
147151
tokio::time::sleep(std::time::Duration::from_secs(1)).await;
148152
}
149153
}
@@ -183,13 +187,26 @@ fn main() {
183187
// notify for syncing threads
184188
let need_restart = Arc::new(Notify::new());
185189
let need_restart_cloned = need_restart.clone();
190+
let tcp_start = Arc::new(Notify::new());
191+
let tcp_start_cloned = tcp_start.clone();
186192

187193
// build and spawn main tokio runtime
188194
let runtime = Builder::new_multi_thread().enable_all().build().unwrap();
189195
runtime.spawn(async move {
190-
tokio_main(args.advertise, args.legacy, args.connect, need_restart).await
196+
tokio_main(
197+
args.advertise,
198+
args.legacy,
199+
args.connect,
200+
need_restart,
201+
tcp_start,
202+
)
203+
.await
191204
});
192205

193206
// start tokio_uring runtime simultaneously
194-
let _ = tokio_uring::start(io_loop(stats_interval, need_restart_cloned));
207+
let _ = tokio_uring::start(io_loop(
208+
stats_interval,
209+
need_restart_cloned,
210+
tcp_start_cloned,
211+
));
195212
}

0 commit comments

Comments
 (0)