1use ::io::{SendableFile, SendableSocket};
2use ::ser::{SerializeWrapper, SerializeWrapperGuard};
3
4extern crate mio_named_pipes;
5
6mod channel;
7mod sharedmem;
8mod sync;
9
10pub use self::channel::*;
11pub(crate) use self::sharedmem::*;
12pub(crate) use self::sync::*;
13
14use std::{io, fs, mem, ptr, fmt};
15use std::cell::RefCell;
16use std::borrow::Borrow;
17use std::sync::{Once, ONCE_INIT};
18use std::net::UdpSocket;
19use std::os::raw::{c_int, c_ulong, c_ushort, c_uchar};
20use std::os::windows::prelude::*;
21
22use serde::{Serialize, Deserialize, Serializer, Deserializer};
23use winapi::shared::ntdef::{HANDLE, WCHAR};
24use winapi::shared::guiddef::{GUID};
25use winapi::shared::minwindef::{DWORD, FALSE};
26use winapi::um::winnt::{DUPLICATE_CLOSE_SOURCE, DUPLICATE_SAME_ACCESS};
27use winapi::um::handleapi::{CloseHandle, DuplicateHandle};
28use winapi::um::processthreadsapi::{GetCurrentProcess, GetCurrentProcessId};
29use winapi::um::winsock2::{WSADuplicateSocketW, WSAGetLastError, WSASocketW};
30use winapi::um::winsock2::{INVALID_SOCKET};
31use winhandle::*;
32
33thread_local! {
34 static CURRENT_SERIALIZE_CHANNEL_REMOTE_PROCESS: RefCell<Option<HandleSender>> = RefCell::new(None);
35 static CURRENT_DESERIALIZE_CHANNEL_REMOTE_PROCESS: RefCell<Option<HandleReceiver>> = RefCell::new(None);
36}
37
38#[derive(Debug)]
39pub struct SendableWinHandle<B = WinHandle>(pub B);
40
41impl From<WinHandle> for SendableWinHandle {
42 fn from(h: WinHandle) -> Self { SendableWinHandle(h) }
43}
44
45impl<'a, B> Serialize for SendableWinHandle<&'a B> where
46 B: AsRawHandle,
47{
48 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
49 where S: Serializer
50 {
51 use serde::ser::Error;
52
53 CURRENT_SERIALIZE_CHANNEL_REMOTE_PROCESS.with(|sender_guard| {
54 let mut sender_guard = sender_guard.borrow_mut();
55 let sender = sender_guard.as_mut()
56 .ok_or_else(|| S::Error::custom("attempted to serialize handle outside of IPC channel"))?;
57 let remote_handle = sender.send(self.0.borrow().as_raw_handle())
58 .map_err(|x| S::Error::custom(x))?;
59 (remote_handle as usize).serialize(serializer)
60 })
61 }
62}
63
64impl Serialize for SendableWinHandle {
65 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
66 where S: Serializer
67 {
68 SendableWinHandle(&self.0).serialize(serializer)
69 }
70}
71
72impl<'de> Deserialize<'de> for SendableWinHandle {
73 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
74 where D: Deserializer<'de>
75 {
76 use serde::de::Error;
77
78 CURRENT_DESERIALIZE_CHANNEL_REMOTE_PROCESS.with(|receiver_guard| {
79 let mut receiver_guard = receiver_guard.borrow_mut();
80 let _receiver = receiver_guard.as_mut()
81 .ok_or_else(|| D::Error::custom("attempted to deserialize handle outside of IPC channel"))?;
82 let handle = usize::deserialize(deserializer)? as HANDLE;
83 let handle = WinHandle::from_raw(handle)
84 .ok_or_else(|| D::Error::custom("invalid Windows handle received"))?;
85 Ok(SendableWinHandle(handle))
86 })
87 }
88}
89
90impl<B> Serialize for SendableFile<B> where
91 B: Borrow<fs::File>,
92{
93 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
94 where S: Serializer
95 {
96 SendableWinHandle(self.0.borrow()).serialize(serializer)
97 }
98}
99
100impl<'de> Deserialize<'de> for SendableFile {
101 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
102 where D: Deserializer<'de>
103 {
104 let handle = SendableWinHandle::deserialize(deserializer)?;
105 Ok(SendableFile(unsafe { fs::File::from_raw_handle(handle.0.into_raw()) }))
106 }
107}
108
109impl<'a, T> Serialize for SendableSocket<T> where
110 T: AsRawSocket,
111{
112 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
113 where S: Serializer,
114 {
115 use serde::ser::Error;
116
117 CURRENT_SERIALIZE_CHANNEL_REMOTE_PROCESS.with(|sender_guard| {
118 let mut sender_guard = sender_guard.borrow_mut();
119 let sender = sender_guard.as_mut()
120 .ok_or_else(|| S::Error::custom("attempted to serialize handle outside of IPC channel"))?;
121 let proto_info = unsafe {
122 let mut proto_info: WsaProtoInfo = mem::zeroed();
123 if WSADuplicateSocketW(
124 self.0.as_raw_socket() as usize,
125 sender.remote_process_id().map_err(|x| S::Error::custom(x))?,
126 &mut proto_info as *mut WsaProtoInfo as _,
127 ) != 0 {
128 return Err(S::Error::custom(io::Error::from_raw_os_error(WSAGetLastError())));
129 }
130 proto_info
131 };
132 proto_info.serialize(serializer)
133 })
134 }
135}
136
137static CALLED_WSASTARTUP: Once = ONCE_INIT;
138
139impl<'de, T> Deserialize<'de> for SendableSocket<T> where
140 T: FromRawSocket,
141{
142 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
143 where D: Deserializer<'de>,
144 {
145 use serde::de::Error;
146
147 CALLED_WSASTARTUP.call_once(|| {
149 let _ = UdpSocket::bind("127.0.0.1:9999");
151 });
152
153 CURRENT_DESERIALIZE_CHANNEL_REMOTE_PROCESS.with(|receiver_guard| {
154 let mut receiver_guard = receiver_guard.borrow_mut();
155 let _receiver = receiver_guard.as_mut()
156 .ok_or_else(|| D::Error::custom("attempted to deserialize handle outside of IPC channel"))?;
157 let mut proto_info: WsaProtoInfo = WsaProtoInfo::deserialize(deserializer)?;
158 let raw_socket = unsafe { WSASocketW(
159 proto_info.iAddressFamily,
160 proto_info.iSocketType,
161 proto_info.iProtocol,
162 &mut proto_info as *mut WsaProtoInfo as _,
163 0,
164 0, )};
166 if raw_socket == INVALID_SOCKET {
167 return Err(D::Error::custom(io::Error::from_raw_os_error(unsafe { WSAGetLastError() })));
168 }
169 Ok(SendableSocket(unsafe { T::from_raw_socket(raw_socket as RawSocket) }))
170 })
171 }
172}
173
174#[allow(bad_style)]
175#[repr(C)]
176#[derive(Serialize, Deserialize)]
177struct WsaProtoInfo {
178 dwServiceFlags1: DWORD,
179 dwServiceFlags2: DWORD,
180 dwServiceFlags3: DWORD,
181 dwServiceFlags4: DWORD,
182 dwProviderFlags: DWORD,
183 #[serde(with = "serde_guid")]
184 ProviderId: GUID,
185 dwCatalogEntryId: DWORD,
186 ProtocolChain: WsaProtocolChain,
187 iVersion: c_int,
188 iAddressFamily: c_int,
189 iMaxSockAddr: c_int,
190 iMinSockAddr: c_int,
191 iSocketType: c_int,
192 iProtocol: c_int,
193 iProtocolMaxOffset: c_int,
194 iNetworkByteOrder: c_int,
195 iSecurityScheme: c_int,
196 dwMessageSize: DWORD,
197 dwProviderReserved: DWORD,
198 #[serde(with = "serde_wchar256")]
199 szProtocol: [WCHAR; 256],
200}
201
202#[allow(bad_style)]
203#[repr(C)]
204#[derive(Serialize, Deserialize, Debug)]
205struct WsaProtocolChain {
206 ChainLen: c_int,
207 ChainEntries: [DWORD; 7],
208}
209
210mod serde_guid {
211 use super::*;
212
213 pub fn serialize<S>(f: &GUID, serializer: S) -> Result<S::Ok, S::Error> where
214 S: Serializer,
215 {
216 (f.Data1, f.Data2, f.Data3, f.Data4).serialize(serializer)
217 }
218
219 pub fn deserialize<'de, D>(deserializer: D) -> Result<GUID, D::Error> where
220 D: Deserializer<'de>,
221 {
222 let data: (c_ulong, c_ushort, c_ushort, [c_uchar; 8]) = Deserialize::deserialize(deserializer)?;
223 Ok(GUID {
224 Data1: data.0,
225 Data2: data.1,
226 Data3: data.2,
227 Data4: data.3,
228 })
229 }
230}
231
232mod serde_wchar256 {
233 use super::*;
234
235 pub fn serialize<S>(f: &[WCHAR; 256], serializer: S) -> Result<S::Ok, S::Error> where
236 S: Serializer,
237 {
238 use serde::ser::{SerializeTuple};
239
240 let mut serializer = serializer.serialize_tuple(256)?;
241 for wchar in f.iter() {
242 serializer.serialize_element::<WCHAR>(wchar)?;
243 }
244 serializer.end()
245 }
246
247 pub fn deserialize<'de, D>(deserializer: D) -> Result<[WCHAR; 256], D::Error> where
248 D: Deserializer<'de>,
249 {
250 use serde::de::{Visitor, SeqAccess, Error};
251
252 struct AVisitor;
253
254 impl<'de> Visitor<'de> for AVisitor {
255 type Value = [WCHAR; 256];
256
257 fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
258 formatter.write_str("WCHAR string of length 256")
259 }
260
261 fn visit_seq<V>(self, mut seq: V) -> Result<[WCHAR; 256], V::Error>
262 where V: SeqAccess<'de>
263 {
264 let mut buffer: [WCHAR; 256] = [0; 256];
265 for (i, c) in buffer.iter_mut().enumerate() {
266 let read_c: WCHAR = seq.next_element()?
267 .ok_or_else(|| Error::invalid_length(i, &self))?;
268 *c = read_c;
269 }
270 Ok(buffer)
271 }
272 }
273
274 deserializer.deserialize_tuple(256, AVisitor)
275 }
276}
277
278pub(crate) struct ChannelSerializeWrapper;
279
280impl<'a, C> SerializeWrapper<'a, C> for ChannelSerializeWrapper where
281 C: Channel,
282{
283 type SerializeGuard = ChannelSerializeGuard;
284 type DeserializeGuard = ChannelDeserializeGuard;
285
286 fn before_serialize(channel: &'a mut C) -> ChannelSerializeGuard {
287 let mut sender = Some(HandleSender {
288 target: unsafe { mem::transmute::<HandleTarget<&ProcessHandle>, HandleTarget<&'static ProcessHandle>>(channel.handle_target()) },
289 handles: Vec::new(),
290 });
291
292 CURRENT_SERIALIZE_CHANNEL_REMOTE_PROCESS.with(|x|
293 mem::swap(
294 &mut *x.borrow_mut(),
295 &mut sender,
296 )
297 );
298 ChannelSerializeGuard(sender)
299 }
300
301 fn before_deserialize(_channel: &'a mut C) -> ChannelDeserializeGuard {
302 let mut receiver = Some(HandleReceiver);
303 CURRENT_DESERIALIZE_CHANNEL_REMOTE_PROCESS.with(|x|
304 mem::swap(
305 &mut *x.borrow_mut(),
306 &mut receiver,
307 )
308 );
309 ChannelDeserializeGuard(receiver)
310 }
311}
312
313pub(crate) struct ChannelSerializeGuard(Option<HandleSender>);
314
315impl Drop for ChannelSerializeGuard {
316 fn drop(&mut self) {
317 CURRENT_SERIALIZE_CHANNEL_REMOTE_PROCESS.with(|sender_guard| {
318 let mut sender_guard = sender_guard.borrow_mut();
319 *sender_guard = self.0.take()
320 });
321 }
322}
323
324impl<'a> SerializeWrapperGuard<'a> for ChannelSerializeGuard {
325 fn commit(self) {
326 CURRENT_SERIALIZE_CHANNEL_REMOTE_PROCESS.with(|sender_guard| {
327 let mut sender_guard = sender_guard.borrow_mut();
328 sender_guard.as_mut().unwrap().handles.clear();
329 });
330 }
331}
332
333pub(crate) struct ChannelDeserializeGuard(Option<HandleReceiver>);
334
335impl Drop for ChannelDeserializeGuard {
336 fn drop(&mut self) {
337 CURRENT_DESERIALIZE_CHANNEL_REMOTE_PROCESS.with(|x| *x.borrow_mut() = self.0.take());
338 }
339}
340
341impl<'a> SerializeWrapperGuard<'a> for ChannelDeserializeGuard {
342 fn commit(self) {
343 }
344}
345
346pub(crate) trait Channel {
347 fn handle_target(&self) -> HandleTarget<&ProcessHandle>;
348}
349
350struct HandleSender {
351 target: HandleTarget<&'static ProcessHandle>,
352 handles: Vec<HANDLE>,
353}
354
355impl Drop for HandleSender {
356 fn drop(&mut self) {
357 match self.target {
360 HandleTarget::CurrentProcess => {
361 for &handle in self.handles.iter() {
362 unsafe { CloseHandle(handle); }
363 }
364 },
365 HandleTarget::RemoteProcess(process_handle) => {
366 for &handle in self.handles.iter() {
367 if unsafe { DuplicateHandle(
368 process_handle.handle.0.get(), handle,
369 ptr::null_mut(), ptr::null_mut(),
370 0, FALSE, DUPLICATE_CLOSE_SOURCE,
371 ) } == FALSE {
372 error!("Closing remote handle via DuplicateHandle failed: {}", io::Error::last_os_error());
373 }
374 }
375 },
376 HandleTarget::None => {},
377 }
378 }
379}
380
381struct HandleReceiver;
382
383impl HandleSender {
384 fn send(&mut self, handle: HANDLE) -> io::Result<HANDLE> {
385 let remote_process_handle = match self.target {
386 HandleTarget::CurrentProcess => unsafe { GetCurrentProcess() },
387 HandleTarget::RemoteProcess(remote) => remote.handle.0.get(),
388 HandleTarget::None => return Err(io::Error::new(io::ErrorKind::BrokenPipe, "this pipe is not configured to send handles")),
389 };
390
391 unsafe {
392 let mut remote_handle = ptr::null_mut();
393 winapi_bool_call!(log: DuplicateHandle(
394 GetCurrentProcess(), handle,
395 remote_process_handle, &mut remote_handle,
396 0, FALSE, DUPLICATE_SAME_ACCESS,
397 ))?;
398
399 self.handles.push(remote_handle);
400
401 Ok(remote_handle)
402 }
403 }
404
405 fn remote_process_id(&self) -> io::Result<DWORD> {
406 Ok(match self.target {
407 HandleTarget::CurrentProcess => unsafe { GetCurrentProcessId() },
408 HandleTarget::RemoteProcess(remote) => remote.id,
409 HandleTarget::None => return Err(io::Error::new(io::ErrorKind::BrokenPipe, "this pipe is not configured to send handles")),
410 })
411 }
412}