1use byteorder::{BigEndian, ByteOrder};
2use fd;
3use std::io;
4use std::os::raw::c_int;
5use Argdata;
6use ReadError;
7use Value;
8
9pub fn process_fd(fd: c_int) -> fd::Fd {
11 fd::Fd(fd)
12}
13
14pub fn encoded_fd<T: fd::ConvertFd>(raw: u32, convert_fd: T) -> fd::EncodedFd<T> {
16 fd::EncodedFd::new(raw, convert_fd)
17}
18
19pub fn invalid_fd() -> fd::InvalidFd {
21 fd::InvalidFd
22}
23
24impl<'d> Argdata<'d> for fd::Fd {
25 fn read<'a>(&'a self) -> Result<Value<'a, 'd>, ReadError>
26 where
27 'd: 'a,
28 {
29 Ok(Value::Fd(encoded_fd(self.0 as u32, &fd::Identity)))
30 }
31
32 fn serialized_length(&self) -> usize {
33 5
34 }
35
36 fn serialize(
37 &self,
38 writer: &mut io::Write,
39 fd_map: Option<&mut fd::FdMapping>,
40 ) -> io::Result<()> {
41 encoded_fd(self.0 as u32, fd::Identity).serialize(writer, fd_map)
42 }
43}
44
45impl<'d, T: fd::ConvertFd> Argdata<'d> for fd::EncodedFd<T> {
46 fn read<'a>(&'a self) -> Result<Value<'a, 'd>, ReadError>
47 where
48 'd: 'a,
49 {
50 Ok(Value::Fd(encoded_fd(self.raw, &self.convert_fd)))
51 }
52
53 fn serialized_length(&self) -> usize {
54 5
55 }
56
57 fn serialize(
58 &self,
59 writer: &mut io::Write,
60 fd_map: Option<&mut fd::FdMapping>,
61 ) -> io::Result<()> {
62 let raw: u32 = if let Some(fd_map) = fd_map {
63 self.convert_fd
64 .convert_fd(self.raw)
65 .ok()
66 .map_or(!0, |fd| fd_map.map(fd))
67 } else {
68 self.raw
69 };
70 let mut buf = [3, 0, 0, 0, 0];
71 BigEndian::write_u32(&mut buf[1..], raw);
72 writer.write_all(&buf)
73 }
74}
75
76impl<'d> Argdata<'d> for fd::InvalidFd {
77 fn read<'a>(&'a self) -> Result<Value<'a, 'd>, ReadError>
78 where
79 'd: 'a,
80 {
81 Ok(Value::Fd(encoded_fd(!0, &fd::NoConvert)))
82 }
83
84 fn serialized_length(&self) -> usize {
85 5
86 }
87
88 fn serialize(&self, writer: &mut io::Write, _: Option<&mut fd::FdMapping>) -> io::Result<()> {
89 writer.write_all(&[5, 0xFF, 0xFF, 0xFF, 0xFF])
90 }
91}