Merge pull request #13 from kchibisov/reader-crash
Fix crash when receiving non-utf8 data
This commit is contained in:
commit
b97ebc4321
3 changed files with 33 additions and 21 deletions
|
|
@ -2,6 +2,9 @@
|
||||||
|
|
||||||
## Unreleased
|
## Unreleased
|
||||||
|
|
||||||
|
- Fix crash when receiving non-utf8 data
|
||||||
|
- **Breaking** `load` and `load_primary` now return `Result<String>` to indicate errors
|
||||||
|
|
||||||
## 0.3.7 -- 2020-02-27
|
## 0.3.7 -- 2020-02-27
|
||||||
|
|
||||||
- Only bind seat with version up to 6, as version 7 is not yet supported by SCTK
|
- Only bind seat with version up to 6, as version 7 is not yet supported by SCTK
|
||||||
|
|
|
||||||
|
|
@ -37,7 +37,7 @@ fn main() {
|
||||||
} = event
|
} = event
|
||||||
{
|
{
|
||||||
if text == " " {
|
if text == " " {
|
||||||
*cb_contents_clone.lock().unwrap() = dbg!(clipboard.load(None));
|
*cb_contents_clone.lock().unwrap() = dbg!(clipboard.load(None).unwrap());
|
||||||
need_redraw_clone.store(true, atomic::Ordering::Relaxed)
|
need_redraw_clone.store(true, atomic::Ordering::Relaxed)
|
||||||
} else if text == "s" {
|
} else if text == "s" {
|
||||||
clipboard.store(
|
clipboard.store(
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,5 @@
|
||||||
use std::collections::HashMap;
|
use std::collections::HashMap;
|
||||||
use std::io::{Read, Write};
|
use std::io::{Read, Result, Write};
|
||||||
use std::ops::Deref;
|
use std::ops::Deref;
|
||||||
use std::os::unix::io::FromRawFd;
|
use std::os::unix::io::FromRawFd;
|
||||||
use std::sync::mpsc;
|
use std::sync::mpsc;
|
||||||
|
|
@ -50,7 +50,7 @@ type SeatMap = HashMap<
|
||||||
/// Object representing the Wayland clipboard
|
/// Object representing the Wayland clipboard
|
||||||
pub struct ThreadedClipboard {
|
pub struct ThreadedClipboard {
|
||||||
request_send: mpsc::Sender<ThreadRequest>,
|
request_send: mpsc::Sender<ThreadRequest>,
|
||||||
load_recv: mpsc::Receiver<String>,
|
load_recv: mpsc::Receiver<Result<String>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
// Kill thread when clipboard object is dropped
|
// Kill thread when clipboard object is dropped
|
||||||
|
|
@ -113,7 +113,7 @@ impl ThreadedClipboard {
|
||||||
/// focus to work. Otherwise if no seat name is provided
|
/// focus to work. Otherwise if no seat name is provided
|
||||||
/// the name of the seat to last generate a key or pointer event
|
/// the name of the seat to last generate a key or pointer event
|
||||||
/// is used
|
/// is used
|
||||||
pub fn load(&mut self, seat_name: Option<String>) -> String {
|
pub fn load(&mut self, seat_name: Option<String>) -> Result<String> {
|
||||||
self.request_send
|
self.request_send
|
||||||
.send(ThreadRequest::Load(seat_name))
|
.send(ThreadRequest::Load(seat_name))
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
@ -141,7 +141,7 @@ impl ThreadedClipboard {
|
||||||
/// focus to work. Otherwise if no seat name is provided
|
/// focus to work. Otherwise if no seat name is provided
|
||||||
/// the name of the seat to last generate a key or pointer event
|
/// the name of the seat to last generate a key or pointer event
|
||||||
/// is used
|
/// is used
|
||||||
pub fn load_primary(&mut self, seat_name: Option<String>) -> String {
|
pub fn load_primary(&mut self, seat_name: Option<String>) -> Result<String> {
|
||||||
self.request_send
|
self.request_send
|
||||||
.send(ThreadRequest::LoadPrimary(seat_name))
|
.send(ThreadRequest::LoadPrimary(seat_name))
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
@ -180,7 +180,7 @@ fn clipboard_thread(
|
||||||
display: &WlDisplay,
|
display: &WlDisplay,
|
||||||
event_queue: &mut EventQueue,
|
event_queue: &mut EventQueue,
|
||||||
request_recv: mpsc::Receiver<ThreadRequest>,
|
request_recv: mpsc::Receiver<ThreadRequest>,
|
||||||
load_send: mpsc::Sender<String>,
|
load_send: mpsc::Sender<Result<String>>,
|
||||||
) {
|
) {
|
||||||
// Create a seat map to register seats
|
// Create a seat map to register seats
|
||||||
let seat_map = Arc::new(Mutex::new(SeatMap::new()));
|
let seat_map = Arc::new(Mutex::new(SeatMap::new()));
|
||||||
|
|
@ -296,7 +296,7 @@ fn clipboard_thread(
|
||||||
// Get the clipboard contents of the requested seat from the seat map
|
// Get the clipboard contents of the requested seat from the seat map
|
||||||
let contents = seat_map
|
let contents = seat_map
|
||||||
.get(&seat_name.unwrap_or_else(|| last_seat_name.lock().unwrap().clone()))
|
.get(&seat_name.unwrap_or_else(|| last_seat_name.lock().unwrap().clone()))
|
||||||
.map_or(String::new(), |seat| {
|
.map_or(Ok(String::new()), |seat| {
|
||||||
let mut reader = None;
|
let mut reader = None;
|
||||||
seat.0.lock().unwrap().with_selection(|offer| {
|
seat.0.lock().unwrap().with_selection(|offer| {
|
||||||
if let Some(offer) = offer {
|
if let Some(offer) = offer {
|
||||||
|
|
@ -312,15 +312,18 @@ fn clipboard_thread(
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
event_queue.sync_roundtrip().unwrap();
|
event_queue.sync_roundtrip().unwrap();
|
||||||
reader.map_or(String::new(), |mut reader| {
|
reader.map_or(Ok(String::new()), |mut reader| {
|
||||||
let mut contents = String::new();
|
let mut contents = String::new();
|
||||||
reader.read_to_string(&mut contents).unwrap();
|
if let Err(err) = reader.read_to_string(&mut contents) {
|
||||||
contents
|
Err(err)
|
||||||
|
} else {
|
||||||
|
Ok(contents)
|
||||||
|
}
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
// Normalization should happen only on `text/plain;charset=utf-8`, in case we
|
// Normalization should happen only on `text/plain;charset=utf-8`, in case we
|
||||||
// add other mime types consult gtk for normalization.
|
// add other mime types consult gtk for normalization.
|
||||||
let contents = normilize_to_lf(contents);
|
let contents = contents.and_then(|contents| Ok(normilize_to_lf(contents)));
|
||||||
load_send.send(contents).unwrap();
|
load_send.send(contents).unwrap();
|
||||||
}
|
}
|
||||||
// Store text in the clipboard
|
// Store text in the clipboard
|
||||||
|
|
@ -361,9 +364,9 @@ fn clipboard_thread(
|
||||||
&seat_name
|
&seat_name
|
||||||
.unwrap_or_else(|| last_seat_name.lock().unwrap().clone()),
|
.unwrap_or_else(|| last_seat_name.lock().unwrap().clone()),
|
||||||
)
|
)
|
||||||
.map_or(String::new(), |seat| {
|
.map_or(Ok(String::new()), |seat| {
|
||||||
seat.3.lock().unwrap().as_ref().map_or(
|
seat.3.lock().unwrap().as_ref().map_or(
|
||||||
String::new(),
|
Ok(String::new()),
|
||||||
|primary_offer| {
|
|primary_offer| {
|
||||||
let (readfd, writefd) = pipe2(OFlag::O_CLOEXEC).unwrap();
|
let (readfd, writefd) = pipe2(OFlag::O_CLOEXEC).unwrap();
|
||||||
let mut file =
|
let mut file =
|
||||||
|
|
@ -375,8 +378,11 @@ fn clipboard_thread(
|
||||||
close(writefd).unwrap();
|
close(writefd).unwrap();
|
||||||
let mut contents = String::new();
|
let mut contents = String::new();
|
||||||
event_queue.sync_roundtrip().unwrap();
|
event_queue.sync_roundtrip().unwrap();
|
||||||
file.read_to_string(&mut contents).unwrap();
|
if let Err(err) = file.read_to_string(&mut contents) {
|
||||||
contents
|
Err(err)
|
||||||
|
} else {
|
||||||
|
Ok(contents)
|
||||||
|
}
|
||||||
},
|
},
|
||||||
)
|
)
|
||||||
})
|
})
|
||||||
|
|
@ -390,9 +396,9 @@ fn clipboard_thread(
|
||||||
&seat_name
|
&seat_name
|
||||||
.unwrap_or_else(|| last_seat_name.lock().unwrap().clone()),
|
.unwrap_or_else(|| last_seat_name.lock().unwrap().clone()),
|
||||||
)
|
)
|
||||||
.map_or(String::new(), |seat| {
|
.map_or(Ok(String::new()), |seat| {
|
||||||
seat.5.lock().unwrap().as_ref().map_or(
|
seat.5.lock().unwrap().as_ref().map_or(
|
||||||
String::new(),
|
Ok(String::new()),
|
||||||
|primary_offer| {
|
|primary_offer| {
|
||||||
let (readfd, writefd) = pipe2(OFlag::O_CLOEXEC).unwrap();
|
let (readfd, writefd) = pipe2(OFlag::O_CLOEXEC).unwrap();
|
||||||
let mut file =
|
let mut file =
|
||||||
|
|
@ -404,17 +410,20 @@ fn clipboard_thread(
|
||||||
close(writefd).unwrap();
|
close(writefd).unwrap();
|
||||||
let mut contents = String::new();
|
let mut contents = String::new();
|
||||||
event_queue.sync_roundtrip().unwrap();
|
event_queue.sync_roundtrip().unwrap();
|
||||||
file.read_to_string(&mut contents).unwrap();
|
if let Err(err) = file.read_to_string(&mut contents) {
|
||||||
contents
|
Err(err)
|
||||||
|
} else {
|
||||||
|
Ok(contents)
|
||||||
|
}
|
||||||
},
|
},
|
||||||
)
|
)
|
||||||
})
|
})
|
||||||
} else {
|
} else {
|
||||||
String::new()
|
Ok(String::new())
|
||||||
};
|
};
|
||||||
// Normalization should happen only on `text/plain;charset=utf-8`, in case we
|
// Normalization should happen only on `text/plain;charset=utf-8`, in case we
|
||||||
// add other mime types consult gtk for normalization.
|
// add other mime types consult gtk for normalization.
|
||||||
let contents = normilize_to_lf(contents);
|
let contents = contents.and_then(|contents| Ok(normilize_to_lf(contents)));
|
||||||
load_send.send(contents).unwrap();
|
load_send.send(contents).unwrap();
|
||||||
}
|
}
|
||||||
// Store text in the primary clipboard
|
// Store text in the primary clipboard
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue