Skip to content

Commit d8a36c8

Browse files
committed
1. add getter of frame
2. add rtu client example
1 parent 9299878 commit d8a36c8

9 files changed

Lines changed: 284 additions & 24 deletions

File tree

Cargo.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
[package]
22
name = "easy-modbus"
3-
version = "0.0.4"
3+
version = "0.0.5"
44
edition = "2021"
55
authors = ["yangyize <yangyize@gmail.com>"]
66
license = "MIT"

README.md

Lines changed: 47 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -79,12 +79,58 @@ async fn main() -> Result<(), Box<dyn Error>> {
7979
let mut transport = Framed::new(stream, TcpClientCodec);
8080
let frame = Frame::tcp();
8181
let request = frame.read_coils_request(0x01, 0x02, 0x08);
82+
println!("{}", request);
83+
transport.send(request).await?;
84+
while let Some(response) = transport.next().await {
85+
return match response {
86+
Ok(response) => {
87+
println!("{}", response);
88+
Ok(())
89+
}
90+
Err(e) => {
91+
Err(e.into())
92+
}
93+
}
94+
}
95+
Ok(())
96+
}
97+
```
8298

99+
A simple Modbus RTU Client:
100+
``` rust,no_run
101+
use futures::{SinkExt, StreamExt};
102+
use tokio_serial::SerialStream;
103+
use tokio_util::codec::Framed;
104+
use easy_modbus::{Frame, Response};
105+
use easy_modbus::codec::RtuClientCodec;
106+
#[tokio::main(flavor = "current_thread")]
107+
async fn main() -> Result<(), Box<dyn std::error::Error>> {
108+
let tty_path = "COM4";
109+
let rate = 9600;
110+
let slave = 0x01;
111+
let serial_builder = tokio_serial::new(tty_path, rate);
112+
let port = SerialStream::open(&serial_builder).unwrap();
113+
let mut transport = Framed::new(port, RtuClientCodec);
114+
let frame = Frame::rtu();
115+
let request = frame.read_multiple_holding_registers_request(slave, 0x00, 0x02);
116+
println!("Request:\t{}", request);
83117
transport.send(request).await?;
84118
while let Some(response) = transport.next().await {
85119
match response {
86120
Ok(response) => {
87-
println!("{:?}", response);
121+
println!("Response:\t{}", response);
122+
match response {
123+
Response::ReadMultipleHoldingRegisters(_, res) => {
124+
let a = res.get_values();
125+
let h = ((a[0] as u16 * 256) + a[1] as u16) as f64 / 10.0;
126+
let t = ((a[2] as u16 * 256) + a[3] as u16) as f64 / 10.0;
127+
println!("h {} t {}", h, t);
128+
return Ok(())
129+
}
130+
_ => {
131+
println!("unknown")
132+
}
133+
}
88134
}
89135
Err(e) => {
90136
return Err(e.into());
Lines changed: 18 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,10 @@
1-
use easy_modbus::codec::RtuClientCodec;
2-
use easy_modbus::Frame;
31
use futures::{SinkExt, StreamExt};
42
use tokio_serial::SerialStream;
53
use tokio_util::codec::Framed;
64

5+
use easy_modbus::{Frame, Response};
6+
use easy_modbus::codec::RtuClientCodec;
7+
78
#[tokio::main(flavor = "current_thread")]
89
async fn main() -> Result<(), Box<dyn std::error::Error>> {
910
let tty_path = "COM4";
@@ -17,20 +18,31 @@ async fn main() -> Result<(), Box<dyn std::error::Error>> {
1718

1819
let frame = Frame::rtu();
1920
let request = frame.read_multiple_holding_registers_request(slave, 0x00, 0x02);
20-
println!("{}", request);
21-
transport.send(request).await?;
21+
println!("Request:\t{}", request);
2222

23+
transport.send(request).await?;
2324
while let Some(response) = transport.next().await {
2425
match response {
2526
Ok(response) => {
26-
println!("{}", response);
27+
println!("Response:\t{}", response);
28+
match response {
29+
Response::ReadMultipleHoldingRegisters(_, res) => {
30+
let a = res.get_values();
31+
let h = ((a[0] as u16 * 256) + a[1] as u16) as f64 / 10.0;
32+
let t = ((a[2] as u16 * 256) + a[3] as u16) as f64 / 10.0;
33+
println!("h {} t {}", h, t);
34+
return Ok(())
35+
}
36+
_ => {
37+
println!("unknown")
38+
}
39+
}
2740
}
2841
Err(e) => {
2942
return Err(e.into());
3043
}
3144
}
3245
}
3346

34-
println!("Hello, world!");
3547
Ok(())
3648
}

src/codec/decoder.rs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -79,8 +79,6 @@ impl Decoder for RtuServerCodec {
7979
return Ok(None);
8080
}
8181

82-
println!("decoder 接收到请求: {:02X}", &src);
83-
8482
let mut data_bytes = BytesMut::new();
8583
let head_bytes = src.copy_to_bytes(2);
8684
data_bytes.put_slice(&(head_bytes.to_vec()));

src/frame/request.rs

Lines changed: 64 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -94,6 +94,14 @@ impl ReadDiscreteInputsRequest {
9494
discrete_inputs_number,
9595
}
9696
}
97+
98+
pub fn get_first_address(&self) -> &u16 {
99+
&self.first_address
100+
}
101+
102+
pub fn get_discrete_input_number(&self) -> &u16 {
103+
&self.discrete_inputs_number
104+
}
97105
}
98106

99107
/// Function Code `0x03`
@@ -125,6 +133,14 @@ impl ReadMultipleHoldingRegistersRequest {
125133
registers_number,
126134
}
127135
}
136+
137+
pub fn get_first_address(&self) -> &u16 {
138+
&self.first_address
139+
}
140+
141+
pub fn get_registers_number(&self) -> &u16 {
142+
&self.registers_number
143+
}
128144
}
129145

130146
/// Function code `0x04`
@@ -153,6 +169,14 @@ impl ReadInputRegistersRequest {
153169
registers_number,
154170
}
155171
}
172+
173+
pub fn get_first_address(&self) -> &u16 {
174+
&self.first_address
175+
}
176+
177+
pub fn get_registers_number(&self) -> &u16 {
178+
&self.registers_number
179+
}
156180
}
157181

158182
/// Function Code `0x05`
@@ -180,6 +204,14 @@ impl WriteSingleCoilRequest {
180204
value,
181205
}
182206
}
207+
208+
pub fn get_coil_address(&self) -> &u16 {
209+
&self.coil_address
210+
}
211+
212+
pub fn get_value(&self) -> &u16 {
213+
&self.value
214+
}
183215
}
184216

185217
/// Function Code `0x06`
@@ -205,6 +237,14 @@ impl WriteSingleHoldingRegisterRequest {
205237
value,
206238
}
207239
}
240+
241+
pub fn get_register_address(&self) -> &u16 {
242+
&self.register_address
243+
}
244+
245+
pub fn get_value(&self) -> &u16 {
246+
&self.value
247+
}
208248
}
209249

210250
/// Function Code `0x0F`
@@ -249,6 +289,14 @@ impl WriteMultipleCoilsRequest {
249289
values,
250290
}
251291
}
292+
293+
pub fn first_address(&self) -> &u16 {
294+
&self.first_address
295+
}
296+
297+
pub fn coils_number(&self) -> &u16 {
298+
&self.coils_number
299+
}
252300
}
253301

254302
/// Function Code `0x10`
@@ -285,6 +333,22 @@ impl WriteMultipleHoldingRegistersRequest {
285333
values,
286334
}
287335
}
336+
337+
pub fn get_first_address(&self) -> &u16 {
338+
&self.first_address
339+
}
340+
341+
pub fn get_registers_number(&self) -> &u16 {
342+
&self.registers_number
343+
}
344+
345+
pub fn get_bytes_number(&self) -> &u8 {
346+
&self.bytes_number
347+
}
348+
349+
pub fn get_values(&self) -> &Vec<u8> {
350+
&self.values
351+
}
288352
}
289353

290354
impl From<ReadCoilsRequest> for BytesMut {

src/frame/response.rs

Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -66,6 +66,14 @@ impl ReadCoilsResponse {
6666
values,
6767
}
6868
}
69+
70+
pub fn get_bytes_number(&self) -> &u8 {
71+
&self.bytes_number
72+
}
73+
74+
pub fn get_values(&self) -> &Vec<u8> {
75+
&self.values
76+
}
6977
}
7078

7179
/// Function Code `0x02`
@@ -96,6 +104,14 @@ impl ReadDiscreteInputsResponse {
96104
values,
97105
}
98106
}
107+
108+
pub fn get_bytes_number(&self) -> &u8 {
109+
&self.bytes_number
110+
}
111+
112+
pub fn get_values(&self) -> &Vec<u8> {
113+
&self.values
114+
}
99115
}
100116

101117
/// Function Code `0x03`
@@ -122,6 +138,14 @@ impl ReadMultipleHoldingRegistersResponse {
122138
values,
123139
}
124140
}
141+
142+
pub fn get_bytes_number(&self) -> &u8 {
143+
&self.bytes_number
144+
}
145+
146+
pub fn get_values(&self) -> &Vec<u8> {
147+
&self.values
148+
}
125149
}
126150

127151
/// Function Code `0x04`
@@ -148,6 +172,14 @@ impl ReadInputRegistersResponse {
148172
values,
149173
}
150174
}
175+
176+
pub fn get_bytes_number(&self) -> &u8 {
177+
&self.bytes_number
178+
}
179+
180+
pub fn get_values(&self) -> &Vec<u8> {
181+
&self.values
182+
}
151183
}
152184

153185
/// Function Code `0x05`
@@ -175,6 +207,14 @@ impl WriteSingleCoilResponse {
175207
value,
176208
}
177209
}
210+
211+
pub fn get_coil_address(&self) -> &u16 {
212+
&self.coil_address
213+
}
214+
215+
pub fn get_value(&self) -> &u16 {
216+
&self.value
217+
}
178218
}
179219

180220
/// Function Code `0x06`
@@ -200,6 +240,14 @@ impl WriteSingleHoldingRegisterResponse {
200240
value,
201241
}
202242
}
243+
244+
pub fn get_register_address(&self) -> &u16 {
245+
&self.register_address
246+
}
247+
248+
pub fn get_value(&self) -> &u16 {
249+
&self.value
250+
}
203251
}
204252

205253
/// Function Code `0x0F`
@@ -225,6 +273,14 @@ impl WriteMultipleCoilsResponse {
225273
coils_number,
226274
}
227275
}
276+
277+
pub fn get_first_address(&self) -> &u16 {
278+
&self.first_address
279+
}
280+
281+
pub fn get_coils_number(&self) -> &u16 {
282+
&self.coils_number
283+
}
228284
}
229285

230286
/// Function Code `0x10`
@@ -253,6 +309,14 @@ impl WriteMultipleHoldingRegistersResponse {
253309
registers_number,
254310
}
255311
}
312+
313+
pub fn get_first_address(&self) -> &u16 {
314+
&self.first_address
315+
}
316+
317+
pub fn get_registers_number(&self) -> &u16 {
318+
&self.registers_number
319+
}
256320
}
257321

258322
#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
@@ -270,6 +334,10 @@ impl ExceptionResponse {
270334
pub(crate) fn new(exception: Exception) -> Self {
271335
ExceptionResponse { exception }
272336
}
337+
338+
pub fn get_exception(&self) -> &Exception {
339+
&self.exception
340+
}
273341
}
274342

275343
impl From<ReadCoilsResponse> for BytesMut {

0 commit comments

Comments
 (0)