1 /*
2 * Copyright (C) 2023 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15 //! uart
16 #![allow(missing_docs)]
17
18 use super::base;
19
20 use super::uart_wrapper;
21 use crate::config;
22 use crate::serializer;
23 #[allow(unused)]
24 use crate::serializer::native_struct::UartHead;
25 use crate::serializer::serialize::Serialization;
26 use crate::serializer::serialize::SerializedBuffer;
27 use crate::utils;
28 #[allow(unused)]
29 use crate::utils::hdc_log::*;
30
31 use std::ffi::CString;
32 use std::io::{self, Error, ErrorKind};
33
34 #[allow(unused)]
35 extern "C" {
access(_name: *const libc::c_char, _type: i32) -> i3236 fn access(_name: *const libc::c_char, _type: i32) -> i32;
free(ptr: *const libc::c_void)37 fn free(ptr: *const libc::c_void);
38
GetUartSpeedExt(speed: i32) -> i3239 fn GetUartSpeedExt(speed: i32) -> i32;
GetUartBitsExt(bits: i32) -> i3240 fn GetUartBitsExt(bits: i32) -> i32;
OpenSerialPortExt(port: *const libc::c_char) -> i3241 fn OpenSerialPortExt(port: *const libc::c_char) -> i32;
SetSerialExt(fd: i32, speed: i32, bits: i32, event: u8, stop: i32) -> i3242 fn SetSerialExt(fd: i32, speed: i32, bits: i32, event: u8, stop: i32) -> i32;
ReadUartDevExt(fd: i32, size: i32) -> SerializedBuffer43 fn ReadUartDevExt(fd: i32, size: i32) -> SerializedBuffer;
WriteUartDevExt(fd: i32, buf: SerializedBuffer) -> i3244 fn WriteUartDevExt(fd: i32, buf: SerializedBuffer) -> i32;
CloseSerialPortExt(fd: i32) -> u845 fn CloseSerialPortExt(fd: i32) -> u8;
46 }
47
uart_init() -> io::Result<i32>48 pub fn uart_init() -> io::Result<i32> {
49 let name = CString::new(config::UART_NODE).unwrap();
50 let fd = unsafe {
51 if access(name.as_ptr(), 0) != 0 {
52 return Err(utils::error_other("cannot access uart node".to_string()));
53 }
54 let fd = OpenSerialPortExt(name.as_ptr());
55 if fd < 0 {
56 return Err(utils::error_other("cannot open uart node".to_string()));
57 }
58 if SetSerialExt(
59 fd,
60 config::UART_DEFAULT_BAUD_RATE,
61 config::UART_DEFAULT_BITS,
62 config::UART_EVENT,
63 1,
64 ) != 0
65 {
66 return Err(utils::error_other("set uart config failed".to_string()));
67 }
68 println!("uart init fd: {fd}");
69 fd
70 };
71 Ok(fd)
72 }
73
uart_close(fd: i32)74 pub fn uart_close(fd: i32) {
75 unsafe {
76 CloseSerialPortExt(fd);
77 }
78 }
79
80 pub struct UartReader {
81 pub fd: i32,
82 pub head: Option<UartHead>,
83 }
84
85 pub struct UartWriter {
86 pub fd: i32,
87 }
88
89 impl base::Reader for UartReader {
read_frame(&self, expected_size: usize) -> io::Result<Vec<u8>>90 fn read_frame(&self, expected_size: usize) -> io::Result<Vec<u8>> {
91 if expected_size == 0 {
92 return Ok(vec![]);
93 }
94 let mut data = vec![];
95 let mut index = 0;
96 while index < expected_size {
97 crate::trace!("before read {index} / {expected_size}");
98 let buf = unsafe {
99 let recv = ReadUartDevExt(self.fd, (expected_size - index) as i32);
100 let slice = std::slice::from_raw_parts(
101 recv.ptr as *const libc::c_uchar,
102 recv.size as usize,
103 );
104 index += recv.size as usize;
105 slice.to_vec()
106 };
107 data = [data, buf].concat();
108 }
109 Ok(data)
110 }
111
check_protocol_head(&mut self) -> io::Result<(u32, u32)>112 fn check_protocol_head(&mut self) -> io::Result<(u32, u32)> {
113 let buf = self.read_frame(serializer::UART_HEAD_SIZE)?;
114 if buf[..config::PACKET_FLAG.len()] != config::PACKET_FLAG[..] {
115 return Err(Error::new(
116 ErrorKind::Other,
117 format!("uart PACKET_FLAG incorrect, content: {:#?}", buf),
118 ));
119 }
120 let mut head = serializer::native_struct::UartHead::default();
121
122 if let Err(e) = head.parse(buf) {
123 println!("parse uart head error {:#?}", e);
124 log::warn!("parse uart head error: {}", e.to_string());
125 return Err(e);
126 }
127
128 self.head = Some(head.clone());
129
130 Ok((head.data_size, head.package_index))
131 }
132
133 #[allow(unused)]
process_head(&self)134 fn process_head(&self) {
135 let head = self.head.clone();
136 if let Some(head) = head {
137 ylong_runtime::block_on(async move {
138 uart_wrapper::on_read_head(head).await;
139 });
140 }
141 }
142 }
143
144 impl base::Writer for UartWriter {
write_all(&self, data: Vec<u8>) -> io::Result<()>145 fn write_all(&self, data: Vec<u8>) -> io::Result<()> {
146 let buf = SerializedBuffer {
147 ptr: data.as_ptr() as *const libc::c_char,
148 size: data.len() as u64,
149 };
150 println!("write all start, fd:{}...", self.fd);
151 let write_count = unsafe { WriteUartDevExt(self.fd, buf) };
152 println!("write count:{}", write_count);
153 if write_count < 0 {
154 Err(utils::error_other("uart write failed".to_string()))
155 } else {
156 Ok(())
157 }
158 }
159 }
160
build_header(session_id: u32, option: u16, length: usize, package_index: u32) -> Vec<u8>161 pub fn build_header(session_id: u32, option: u16, length: usize, package_index: u32) -> Vec<u8> {
162 UartHead {
163 session_id: u32::to_le(session_id),
164 flag: [config::PACKET_FLAG[0], config::PACKET_FLAG[1]],
165 option,
166 data_size: u32::to_le(length as u32),
167 package_index,
168 data_checksum: 0,
169 head_checksum: 0,
170 }
171 .serialize()
172 }
173
build_header_obj( session_id: u32, option: u16, length: usize, package_index: u32, ) -> UartHead174 pub fn build_header_obj(
175 session_id: u32,
176 option: u16,
177 length: usize,
178 package_index: u32,
179 ) -> UartHead {
180 UartHead {
181 session_id: u32::to_le(session_id),
182 flag: [config::PACKET_FLAG[0], config::PACKET_FLAG[1]],
183 option,
184 data_size: u32::to_le(length as u32),
185 package_index,
186 data_checksum: 0,
187 head_checksum: 0,
188 }
189 }
190