forked from 1148118271/ssh-rs
-
Notifications
You must be signed in to change notification settings - Fork 0
/
main.rs
127 lines (111 loc) · 3.25 KB
/
main.rs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
#[cfg(unix)]
use mio::unix::SourceFd;
use ssh_rs::ssh;
use std::fs::File;
#[cfg(unix)]
use std::os::unix::io::FromRawFd;
use std::{cell::RefCell, rc::Rc};
use std::time::Duration;
use mio::net::TcpStream;
use mio::{event::Source, Events, Interest, Poll, Token};
const SERVER: Token = Token(0);
const SHELL: Token = Token(1);
#[cfg(not(unix))]
fn main() {
panic!("This example can run on unix only")
}
#[cfg(unix)]
fn main() {
use std::{io::Read, os::unix::prelude::AsRawFd};
ssh::enable_log();
let tcp = TcpStream::connect("127.0.0.1:22".parse().unwrap()).unwrap();
let mut session = ssh::create_session()
.username("ubuntu")
.password("password")
.timeout(Some(Duration::from_millis(1000)))
.private_key_path("./id_rsa")
.connect_bio(tcp)
.unwrap()
.run_local();
let mut shell = session.open_shell().unwrap();
let mut tcp_wrap = TcpWrap::new(session.get_raw_io());
let mut std_in = unsafe { File::from_raw_fd(0) };
let mut poll = Poll::new().unwrap();
let mut events = Events::with_capacity(1024);
poll.registry()
.register(&mut tcp_wrap, SERVER, Interest::READABLE)
.unwrap();
poll.registry()
.register(
&mut SourceFd(&std_in.as_raw_fd()),
SHELL,
Interest::READABLE,
)
.unwrap();
let mut buf = [0; 2048];
'main_loop: loop {
poll.poll(&mut events, None).unwrap();
for event in &events {
match event.token() {
SERVER => match shell.read() {
Ok(buf) => print!("{}", String::from_utf8_lossy(&buf)),
_ => break 'main_loop,
},
SHELL => {
let len = std_in.read(&mut buf).unwrap();
shell.write(&buf[..len]).unwrap();
}
_ => break 'main_loop,
}
}
}
session.close();
}
struct TcpWrap {
server: Rc<RefCell<TcpStream>>,
}
impl TcpWrap {
fn new(tcp: Rc<RefCell<TcpStream>>) -> Self {
Self { server: tcp }
}
}
impl std::io::Read for TcpWrap {
fn read(&mut self, buf: &mut [u8]) -> std::io::Result<usize> {
println!("bio log: read {} bytes", buf.len());
self.server.borrow_mut().read(buf)
}
}
impl std::io::Write for TcpWrap {
fn write(&mut self, buf: &[u8]) -> std::io::Result<usize> {
println!("bio log: write {} bytes", buf.len());
self.server.borrow_mut().write(buf)
}
fn flush(&mut self) -> std::io::Result<()> {
self.server.borrow_mut().flush()
}
}
impl Source for TcpWrap {
fn deregister(&mut self, registry: &mio::Registry) -> std::io::Result<()> {
self.server.borrow_mut().deregister(registry)
}
fn register(
&mut self,
registry: &mio::Registry,
token: Token,
interests: Interest,
) -> std::io::Result<()> {
self.server
.borrow_mut()
.register(registry, token, interests)
}
fn reregister(
&mut self,
registry: &mio::Registry,
token: Token,
interests: Interest,
) -> std::io::Result<()> {
self.server
.borrow_mut()
.reregister(registry, token, interests)
}
}