• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 #![allow(missing_docs)]
16 use crate::common::sendmsg::send_msg;
17 use crate::common::uds::{PollNode, UdsAddr, UdsServer};
18 use crate::config::ErrCode;
19 use crate::config::HdcCommand;
20 use crate::config::TaskMessage;
21 use crate::transfer;
22 use libc::{POLLERR, POLLHUP, POLLNVAL, POLLRDHUP, SOCK_STREAM};
23 
24 use std::collections::HashMap;
25 use std::sync::Arc;
26 use ylong_runtime::sync::waiter::Waiter;
27 use ylong_runtime::sync::Mutex;
28 
29 const JPID_SOCKET_PATH: &str = "ohjpid-control";
30 const PATH_LEN: usize = JPID_SOCKET_PATH.as_bytes().len() + 1;
31 
32 type NodeMap = Arc<Mutex<HashMap<i32, PollNode>>>;
33 type Trackers = Arc<Mutex<Vec<(u32, u32, bool)>>>;
34 
35 pub trait JdwpBase: Send + Sync + 'static {}
36 pub struct Jdwp {
37     poll_node_map: NodeMap,
38     empty_waiter: Arc<Waiter>,
39     new_process_waiter: Arc<Waiter>,
40     trackers: Trackers,
41 }
42 
43 impl JdwpBase for Jdwp {}
44 
45 type JdWpShare = Arc<Jdwp>;
46 
47 impl Default for Jdwp {
default() -> Self48     fn default() -> Self {
49         Self::new()
50     }
51 }
52 
53 impl Jdwp {
get_instance() -> JdWpShare54     pub fn get_instance() -> JdWpShare {
55         static mut INSTANCE: Option<JdWpShare> = None;
56         unsafe {
57             INSTANCE
58                 .get_or_insert_with(|| Arc::new(Jdwp::new()))
59                 .clone()
60         }
61     }
62 
new() -> Self63     pub fn new() -> Self {
64         Self {
65             poll_node_map: Arc::new(Mutex::new(HashMap::default())),
66             empty_waiter: Arc::new(Waiter::new()),
67             new_process_waiter: Arc::new(Waiter::new()),
68             trackers: Arc::new(Mutex::new(Vec::new())),
69         }
70     }
71 }
72 
73 impl Jdwp {
send_fd_to_target(&self, target_pid: u32, fd: i32, parameter: &str) -> bool74     pub async fn send_fd_to_target(&self, target_pid: u32, fd: i32, parameter: &str) -> bool {
75         let map = self.poll_node_map.clone();
76         let map = map.lock().await;
77         let keys = map.keys();
78         for k in keys {
79             let v = map.get(k);
80             if let Some(node) = v {
81                 if node.ppid == target_pid {
82                     let bytes = fd.to_be_bytes();
83                     let fd_bytes = bytes.as_slice();
84                     let param_bytes = parameter.as_bytes();
85                     let param_bytes = [fd_bytes, param_bytes].concat();
86                     let param_bytes = param_bytes.as_slice();
87                     let ret = send_msg(node.fd, fd, param_bytes);
88                     println!("send_fd_to_target ret:{}", ret);
89                     return ret > 0;
90                 }
91             }
92         }
93         false
94     }
95 
send_process_list(trackers: Trackers, node_map: NodeMap)96     async fn send_process_list(trackers: Trackers, node_map: NodeMap) {
97         let trackers = trackers.lock().await;
98         for (channel_id2, session_id2, is_debug) in trackers.iter() {
99             let message = Self::get_process_list_with_pkg_name(node_map.clone(), *is_debug).await;
100             let len = message.as_bytes().len();
101             let len_str = format!("{:04x}\n", len);
102             let mut header = len_str.as_bytes().to_vec();
103             let mut buffer = Vec::<u8>::new();
104             buffer.append(&mut header);
105             buffer.append(&mut message.as_str().as_bytes().to_vec());
106 
107             let data = TaskMessage {
108                 channel_id: *channel_id2,
109                 command: HdcCommand::KernelEchoRaw,
110                 payload: buffer.to_vec(),
111             };
112             transfer::put(*session_id2, data).await;
113         }
114     }
115 
add_tracker(&self, channel_id: u32, session_id: u32, debug_or_release: bool)116     pub async fn add_tracker(&self, channel_id: u32, session_id: u32, debug_or_release: bool) {
117         let mut trackers_lock = self.trackers.lock().await;
118         trackers_lock.push((channel_id, session_id, debug_or_release));
119         drop(trackers_lock);
120 
121         let node_map = self.poll_node_map.clone();
122         Self::send_process_list(self.trackers.clone(), node_map).await;
123     }
124 
get_process_list(&self) -> String125     pub async fn get_process_list(&self) -> String {
126         let mut result = String::from("");
127         let map = self.poll_node_map.clone();
128         let map = map.lock().await;
129         let keys = map.keys();
130         for key in keys {
131             let value = map.get(key);
132             if let Some(v) = value {
133                 result.push_str((v.ppid.to_string() + "\n").as_str());
134             }
135         }
136         result
137     }
138 
get_process_list_with_pkg_name(map: NodeMap, debug_or_release: bool) -> String139     pub async fn get_process_list_with_pkg_name(map: NodeMap, debug_or_release: bool) -> String {
140         let mut result = String::from("");
141         let map = map.lock().await;
142         let keys = map.keys();
143         for key in keys {
144             let value = map.get(key);
145             if let Some(v) = value {
146                 if !debug_or_release || debug_or_release == v.debug_or_release {
147                     result
148                         .push_str((v.ppid.to_string() + " " + v.pkg_name.as_str() + "\n").as_str());
149                 }
150             }
151         }
152         result
153     }
154 
handle_client( fd: i32, waiter: Arc<Waiter>, node_map: NodeMap, trackers: Trackers, )155     pub async fn handle_client(
156         fd: i32,
157         waiter: Arc<Waiter>,
158         node_map: NodeMap,
159         trackers: Trackers,
160     ) {
161         println!("handle_client start...");
162         loop {
163             let mut buffer: [u8; 1024] = [0; 1024];
164             let size = UdsServer::wrap_recv(fd, &mut buffer);
165             let u32_size = std::mem::size_of::<u32>();
166             if size == u32_size.try_into().unwrap() {
167                 let _pid = u32::from_le_bytes(buffer[0..u32_size].try_into().unwrap());
168             } else if size > u32_size.try_into().unwrap() {
169                 let len = u32::from_le_bytes(buffer[0..u32_size].try_into().unwrap());
170                 let pid = u32::from_le_bytes(buffer[u32_size..2 * u32_size].try_into().unwrap());
171                 println!("pid:{}", pid);
172                 let debug_or_release =
173                     u32::from_le_bytes(buffer[u32_size * 2..3 * u32_size].try_into().unwrap()) == 1;
174                 println!("debug:{}", debug_or_release);
175                 let pkg_name =
176                     String::from_utf8(buffer[u32_size * 3..len as usize].to_vec()).unwrap();
177                 println!("pkg name:{}", pkg_name);
178 
179                 let node_map = node_map.clone();
180                 let mut map = node_map.lock().await;
181                 let node = PollNode::new(fd, pid, pkg_name.clone(), debug_or_release);
182                 let mut key_ = -1;
183                 for (key, value) in map.iter() {
184                     if value.pkg_name == pkg_name {
185                         key_ = *key;
186                         UdsServer::wrap_close(value.fd);
187                         break;
188                     }
189                 }
190                 map.remove(&key_);
191                 map.insert(fd, node);
192                 drop(map);
193 
194                 let trackers = trackers.clone();
195                 let node_map = node_map.clone();
196                 Self::send_process_list(trackers, node_map).await;
197 
198                 waiter.wake_one();
199             } else if size <= 0 {
200                 println!("size <= 0");
201                 break;
202             }
203         }
204     }
205 
jdwp_listen(&self) -> bool206     pub fn jdwp_listen(&self) -> bool {
207         let fd = UdsServer::wrap_socket(SOCK_STREAM);
208         let name = JPID_SOCKET_PATH.as_bytes();
209         let socket_name = &mut [0u8; PATH_LEN];
210         socket_name[0] = b'\0';
211         socket_name[1..].copy_from_slice(name);
212         let addr = UdsAddr::parse_abstract(&socket_name[1..]);
213         if let Ok(addr_obj) = &addr {
214             let ret = UdsServer::wrap_bind(fd, addr_obj);
215             if ret.is_err() {
216                 println!("bind fail");
217                 return false;
218             }
219             let ret = UdsServer::wrap_listen(fd);
220             if ret < 0 {
221                 println!("listen fail");
222                 return false;
223             }
224             let node_map = self.poll_node_map.clone();
225             let trackers = self.trackers.clone();
226             let waiter = self.new_process_waiter.clone();
227             ylong_runtime::spawn(async move {
228                 loop {
229                     let client_fd = UdsServer::wrap_accept(fd);
230                     if client_fd == -1 {
231                         break;
232                     }
233                     let map = node_map.clone();
234                     let trackers = trackers.clone();
235                     let w = waiter.clone();
236                     ylong_runtime::spawn(Self::handle_client(client_fd, w, map, trackers));
237                 }
238             });
239             true
240         } else {
241             println!("parse addr fail  ");
242             false
243         }
244     }
245 
start_data_looper(&self)246     pub fn start_data_looper(&self) {
247         let node_map = self.poll_node_map.clone();
248         let waiter = self.empty_waiter.clone();
249         let trackers = self.trackers.clone();
250         ylong_runtime::spawn(async move {
251             loop {
252                 let mut poll_nodes = Vec::<PollNode>::new();
253                 let mut size = poll_nodes.len();
254                 let node_map_value = node_map.lock().await;
255                 if node_map_value.is_empty() {
256                     let w = waiter.clone();
257                     drop(node_map_value);
258                     println!("start_data_looper, empty_waiter wait...");
259                     w.wait().await;
260                     println!("start_data_looper, empty_waiter wait continue...");
261                     continue;
262                 }
263                 let keys = node_map_value.keys();
264                 for k in keys {
265                     if let Some(n) = node_map_value.get(k) {
266                         poll_nodes.push(n.clone());
267                         size = poll_nodes.len();
268                     }
269                 }
270                 if poll_nodes.is_empty() {
271                     continue;
272                 }
273                 for pnode in &poll_nodes {
274                     println!(
275                         "before poll, node:{},{},{},{}",
276                         pnode.fd, pnode.events, pnode.revents, pnode.ppid
277                     );
278                 }
279                 drop(node_map_value);
280                 UdsServer::wrap_poll(poll_nodes.as_mut_slice(), size.try_into().unwrap(), -1);
281                 let mut node_map_value = node_map.lock().await;
282                 for pnode in &poll_nodes {
283                     println!(
284                         "after poll, node:{},{},{},{}",
285                         pnode.fd, pnode.events, pnode.revents, pnode.ppid
286                     );
287 
288                     if pnode.revents & (POLLNVAL | POLLRDHUP | POLLHUP | POLLERR) != 0 {
289                         node_map_value.remove(&pnode.fd);
290                         UdsServer::wrap_close(pnode.fd);
291                         break;
292                     }
293                 }
294                 drop(node_map_value);
295                 let trackers = trackers.clone();
296                 let node_map = node_map.clone();
297                 Self::send_process_list(trackers, node_map).await;
298             }
299         });
300     }
301 
create_fd_event_poll(&self)302     pub async fn create_fd_event_poll(&self) {
303         loop {
304             let waiter = self.new_process_waiter.clone();
305             waiter.wait().await;
306 
307             let node_map = self.poll_node_map.clone();
308             let node_map_value = node_map.lock().await;
309             if !node_map_value.is_empty() {
310                 let empty_waiter = self.empty_waiter.clone();
311                 empty_waiter.wake_one();
312             }
313         }
314     }
315 
init(&self) -> ErrCode316     pub async fn init(&self) -> ErrCode {
317         println!("jdwp init....");
318 
319         if !self.jdwp_listen() {
320             println!("jdwp_listen failed");
321             return ErrCode::ModuleJdwpFailed;
322         }
323 
324         self.start_data_looper();
325 
326         self.create_fd_event_poll().await;
327         ErrCode::Success
328     }
329 }
330