1use std::path::PathBuf;
2
3use bon::Builder;
4
5use crate::common::OnOff;
6use crate::to_command::{ToArg, ToCommand};
7
8#[derive(Builder)]
9pub struct VC {
10 is_pixel: bool,
11 w: usize,
12 h: usize,
13}
14
15#[derive(Builder)]
16pub struct Udp {
17 remote_host: Option<String>,
18 remote_port: u16,
19 src_ip: Option<String>,
20 src_port: Option<u16>,
21}
22
23#[derive(Builder)]
24pub struct Tcp {
25 host: String,
26 port: u16,
27 server: Option<OnOff>,
28 wait: Option<OnOff>,
29 nodelay: Option<OnOff>,
30 reconnect_ms: Option<usize>,
31}
32
33#[derive(Builder)]
34pub struct Telnet {
35 host: String,
36 port: u16,
37 server: Option<OnOff>,
38 wait: Option<OnOff>,
39 nodelay: Option<OnOff>,
40}
41
42#[derive(Builder)]
43pub struct Websocket {
44 host: String,
45 port: u16,
46 server: Option<OnOff>,
47 wait: Option<OnOff>,
48 nodelay: Option<OnOff>,
49}
50
51#[derive(Builder)]
52pub struct Unix {
53 path: PathBuf,
54 server: Option<OnOff>,
55 wait: Option<OnOff>,
56 reconnect_ms: Option<usize>,
57}
58
59pub enum SpecialDevice {
60 VC(Option<VC>),
61 Pty(Option<PathBuf>),
62 None,
63 Null,
64 Chardev(String),
65 Dev(String),
66 Parport(usize),
67 File(PathBuf),
68 Stdio,
69 Pipe(PathBuf),
70 Com(usize),
71 Udp(Udp),
72 Tcp(Tcp),
73 Telnet(Telnet),
74 Websocket(Websocket),
75 Unix(Unix),
76 Mon(String),
77 Braille,
78 Msmouse,
79}
80
81impl ToCommand for SpecialDevice {
82 fn to_command(&self) -> Vec<String> {
83 let mut cmd = vec![];
84
85 let mut args = vec![];
86
87 match self {
88 SpecialDevice::VC(vc) => {
89 if let Some(vc) = vc {
90 if vc.is_pixel {
91 args.push(format!("vc:{}x{}", vc.w, vc.h));
92 } else {
93 args.push(format!("vc:{}Cx{}C", vc.w, vc.h));
94 }
95 } else {
96 args.push("vc".to_string());
97 }
98 }
99 SpecialDevice::Pty(pty) => {
100 if let Some(pty) = pty {
101 args.push(format!("pty:{}", pty.display()));
102 } else {
103 args.push("pty".to_string());
104 }
105 }
106 SpecialDevice::None => {
107 args.push("none".to_string());
108 }
109 SpecialDevice::Null => {
110 args.push("null".to_string());
111 }
112 SpecialDevice::Chardev(chardev) => {
113 args.push(format!("chardev:{}", chardev));
114 }
115 SpecialDevice::Dev(dev) => {
116 args.push(format!("/dev/{}", dev));
117 }
118 SpecialDevice::Parport(parport) => {
119 args.push(format!("/dev/parport{}", parport));
120 }
121 SpecialDevice::File(file) => {
122 args.push(format!("file:{}", file.display()));
123 }
124 SpecialDevice::Stdio => {
125 args.push("stdio".to_string());
126 }
127 SpecialDevice::Pipe(pipe) => {
128 args.push(format!("pipe:{}", pipe.display()));
129 }
130 SpecialDevice::Com(com) => {
131 args.push(format!("COM{}", com));
132 }
133 SpecialDevice::Udp(udp) => {
134 let mut udpargs = vec![];
135
136 udpargs.push("udp".to_string());
137 if let Some(remote_host) = &udp.remote_host {
138 udpargs.push(remote_host.to_string());
139 }
140 udpargs.push(format!("{}", udp.remote_port));
141 if let Some(src_ip) = &udp.src_ip {
142 udpargs.push(format!("@{}", src_ip));
143 }
144 if let Some(src_port) = &udp.src_port {
145 udpargs.push(format!("{}", src_port));
146 }
147 args.push(udpargs.join(":"));
148 }
149 SpecialDevice::Tcp(tcp) => {
150 let mut tcpargs = vec![];
151
152 tcpargs.push(format!("tcp:{}:{}", tcp.host, tcp.port));
153 if let Some(server) = &tcp.server {
154 tcpargs.push(format!("server={}", server.to_arg()));
155 }
156 if let Some(wait) = &tcp.wait {
157 tcpargs.push(format!("wait={}", wait.to_arg()));
158 }
159 if let Some(nodelay) = &tcp.nodelay {
160 tcpargs.push(format!("nodelay={}", nodelay.to_arg()));
161 }
162 if let Some(reconnect_ms) = &tcp.reconnect_ms {
163 tcpargs.push(format!("reconnect-ms={}", reconnect_ms));
164 }
165 args.push(tcpargs.join(","));
166 }
167 SpecialDevice::Telnet(telnet) => {
168 let mut telnetargs = vec![];
169
170 telnetargs.push(format!("telnet:{}:{}", telnet.host, telnet.port));
171 if let Some(server) = &telnet.server {
172 telnetargs.push(format!("server={}", server.to_arg()));
173 }
174 if let Some(wait) = &telnet.wait {
175 telnetargs.push(format!("wait={}", wait.to_arg()));
176 }
177 if let Some(nodelay) = &telnet.nodelay {
178 telnetargs.push(format!("nodelay={}", nodelay.to_arg()));
179 }
180 args.push(telnetargs.join(","));
181 }
182 SpecialDevice::Websocket(ws) => {
183 let mut wsargs = vec![];
184
185 wsargs.push(format!("websocket:{}:{}", ws.host, ws.port));
186 if let Some(server) = &ws.server {
187 wsargs.push(format!("server={}", server.to_arg()));
188 }
189 if let Some(wait) = &ws.wait {
190 wsargs.push(format!("wait={}", wait.to_arg()));
191 }
192 if let Some(nodelay) = &ws.nodelay {
193 wsargs.push(format!("nodelay={}", nodelay.to_arg()));
194 }
195 args.push(wsargs.join(","));
196 }
197 SpecialDevice::Unix(uds) => {
198 let mut udsargs = vec![];
199
200 udsargs.push(format!("unix:{}", uds.path.display()));
201 if let Some(server) = &uds.server {
202 udsargs.push(format!("server={}", server.to_arg()));
203 }
204 if let Some(wait) = &uds.wait {
205 udsargs.push(format!("wait={}", wait.to_arg()));
206 }
207 if let Some(reconnect_ms) = &uds.reconnect_ms {
208 udsargs.push(format!("reconnect-ms={}", reconnect_ms));
209 }
210 args.push(udsargs.join(","));
211 }
212 SpecialDevice::Mon(mon) => {
213 args.push(format!("mon:{}", mon));
214 }
215 SpecialDevice::Braille => {
216 args.push("braille".to_string());
217 }
218 SpecialDevice::Msmouse => {
219 args.push("msmouse".to_string());
220 }
221 }
222 cmd.push(args.join("").to_string());
223 cmd
224 }
225}