1extern crate serde;
9#[macro_use] extern crate serde_derive;
10#[macro_use] extern crate serde_json;
11extern crate chrono;
12#[macro_use] extern crate error_chain;
13#[macro_use] extern crate log;
14
15use std::net::{ToSocketAddrs, TcpStream};
16use std::io::{BufRead, BufReader, Write};
17use std::time::Duration;
18
19pub mod errors {
20 error_chain! {
23 types {
24 Error, ErrorKind, ResultExt, GpsdResult;
25 }
26 foreign_links {
27 Io(::std::io::Error);
28 Serde(::serde_json::Error);
29 }
30 errors {
31 DeserFailed(s: String, e: ::serde_json::Error) {
32 display("failed to deserialize text '{}': {}", s, e)
33 }
34 GpsdFailed(s: String) {
35 display("gpsd connection closed")
36 }
37 }
38 }
39}
40pub use errors::GpsdResult;
41pub mod types;
42#[cfg(test)]
43pub mod tests;
44use types::*;
45
46pub struct GpsdConnection {
48 raw_data: bool,
49 inner: BufReader<TcpStream>
50}
51impl GpsdConnection {
52 pub fn new<A: ToSocketAddrs>(addr: A) -> GpsdResult<Self> {
54 let stream = TcpStream::connect(addr)?;
55 let inner = BufReader::new(stream);
56 Ok(Self { inner, raw_data: false })
57 }
58 fn _watch(&mut self, watch: bool, json: bool, raw: u8) -> GpsdResult<()> {
60 let stream = self.inner.get_mut();
61 let watch_data = json!({
62 "class": "WATCH",
63 "enable": watch,
64 "json": json,
65 "raw": raw,
66 });
67 self.raw_data = raw > 0;
68 let msg = format!("?WATCH={}\n", watch_data.to_string());
69 stream.write_all(msg.as_bytes())?;
70 Ok(())
71 }
72 pub fn watch(&mut self, watch: bool) -> GpsdResult<()> {
74 self._watch(watch, true, 0)
75 }
76 pub fn watch_raw(&mut self, watch: bool, json: bool, raw: u8) -> GpsdResult<()> {
83 self._watch(watch, json, raw)
84 }
85 pub fn poll(&mut self) -> GpsdResult<()> {
89 let stream = self.inner.get_mut();
90 stream.write_all("?POLL;\n".as_bytes())?;
91 Ok(())
92 }
93 pub fn version(&mut self) -> GpsdResult<()> {
95 let stream = self.inner.get_mut();
96 stream.write_all("?VERSION;\n".as_bytes())?;
97 Ok(())
98 }
99 pub fn devices(&mut self) -> GpsdResult<()> {
101 let stream = self.inner.get_mut();
102 stream.write_all("?DEVICES;\n".as_bytes())?;
103 Ok(())
104 }
105 pub fn set_read_timeout(&mut self, dur: Option<Duration>) -> GpsdResult<()> {
109 self.inner.get_ref().set_read_timeout(dur)?;
110 Ok(())
111 }
112 pub fn get_response(&mut self) -> GpsdResult<Response> {
116 loop {
117 let mut buf = String::new();
118 if self.inner.read_line(&mut buf)? == 0 {
119 bail!(errors::ErrorKind::GpsdFailed(String::from("Gpsd Connection Closed")));
120 }
121
122 if buf == "" {
123 debug!("empty line received from GPSD");
124 continue;
125 }
126 debug!("raw GPSD data: {}", buf);
127 let data = serde_json::from_str(&buf);
128 debug!("serde output: {:?}", data);
129 match data {
130 Err(e) => {
131 if self.raw_data {
132 return Ok(Response::Raw(buf))
133 } else {
134 debug!("deserializing response failed: {:?}", e);
135 bail!(errors::ErrorKind::DeserFailed(buf, e));
136 }
137 },
138 Ok(x) => return Ok(x)
139 }
140 }
141 }
142}