1 // Copyright 2019 The Chromium OS Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 use std::mem::drop; 6 use std::sync::Arc; 7 8 use super::error::*; 9 use super::usb_endpoint::UsbEndpoint; 10 use super::utils::{submit_transfer, update_transfer_state}; 11 use crate::usb::xhci::scatter_gather_buffer::ScatterGatherBuffer; 12 use crate::usb::xhci::xhci_backend_device::{BackendType, UsbDeviceAddress, XhciBackendDevice}; 13 use crate::usb::xhci::xhci_transfer::{XhciTransfer, XhciTransferState, XhciTransferType}; 14 use crate::utils::AsyncJobQueue; 15 use crate::utils::FailHandle; 16 use base::{error, warn}; 17 use data_model::DataInit; 18 use std::collections::HashMap; 19 use std::mem; 20 use sync::Mutex; 21 use usb_util::{ 22 ConfigDescriptorTree, ControlRequestDataPhaseTransferDirection, ControlRequestRecipient, 23 Device, StandardControlRequest, Transfer, TransferStatus, UsbRequestSetup, 24 }; 25 26 #[derive(PartialEq)] 27 pub enum ControlEndpointState { 28 /// Control endpoint should receive setup stage next. 29 SetupStage, 30 /// Control endpoint should receive data stage next. 31 DataStage, 32 /// Control endpoint should receive status stage next. 33 StatusStage, 34 } 35 36 /// Host device is a device connected to host. 37 pub struct HostDevice { 38 fail_handle: Arc<dyn FailHandle>, 39 // Endpoints only contains data endpoints (1 to 30). Control transfers are handled at device 40 // level. 41 endpoints: Vec<UsbEndpoint>, 42 device: Arc<Mutex<Device>>, 43 ctl_ep_state: ControlEndpointState, 44 alt_settings: HashMap<u8, u8>, 45 claimed_interfaces: Vec<u8>, 46 control_request_setup: UsbRequestSetup, 47 executed: bool, 48 job_queue: Arc<AsyncJobQueue>, 49 } 50 51 impl Drop for HostDevice { drop(&mut self)52 fn drop(&mut self) { 53 self.release_interfaces(); 54 } 55 } 56 57 impl HostDevice { 58 /// Create a new host device. new( fail_handle: Arc<dyn FailHandle>, job_queue: Arc<AsyncJobQueue>, device: Arc<Mutex<Device>>, ) -> HostDevice59 pub fn new( 60 fail_handle: Arc<dyn FailHandle>, 61 job_queue: Arc<AsyncJobQueue>, 62 device: Arc<Mutex<Device>>, 63 ) -> HostDevice { 64 HostDevice { 65 fail_handle, 66 endpoints: vec![], 67 device, 68 ctl_ep_state: ControlEndpointState::SetupStage, 69 alt_settings: HashMap::new(), 70 claimed_interfaces: vec![], 71 control_request_setup: UsbRequestSetup::new(0, 0, 0, 0, 0), 72 executed: false, 73 job_queue, 74 } 75 } 76 77 // Check for requests that should be intercepted and emulated using libusb 78 // functions rather than passed directly to the device. 79 // Returns true if the request has been intercepted or false if the request 80 // should be passed through to the device. intercepted_control_transfer(&mut self, xhci_transfer: &XhciTransfer) -> Result<bool>81 fn intercepted_control_transfer(&mut self, xhci_transfer: &XhciTransfer) -> Result<bool> { 82 let direction = self.control_request_setup.get_direction(); 83 let recipient = self.control_request_setup.get_recipient(); 84 let standard_request = self.control_request_setup.get_standard_request(); 85 86 if direction != ControlRequestDataPhaseTransferDirection::HostToDevice { 87 // Only host to device requests are intercepted currently. 88 return Ok(false); 89 } 90 91 let status = match standard_request { 92 Some(StandardControlRequest::SetAddress) => { 93 if recipient != ControlRequestRecipient::Device { 94 return Ok(false); 95 } 96 usb_debug!("host device handling set address"); 97 let addr = self.control_request_setup.value as u32; 98 self.set_address(addr); 99 TransferStatus::Completed 100 } 101 Some(StandardControlRequest::SetConfiguration) => { 102 if recipient != ControlRequestRecipient::Device { 103 return Ok(false); 104 } 105 usb_debug!("host device handling set config"); 106 self.set_config()? 107 } 108 Some(StandardControlRequest::SetInterface) => { 109 if recipient != ControlRequestRecipient::Interface { 110 return Ok(false); 111 } 112 usb_debug!("host device handling set interface"); 113 self.set_interface()? 114 } 115 Some(StandardControlRequest::ClearFeature) => { 116 if recipient != ControlRequestRecipient::Endpoint { 117 return Ok(false); 118 } 119 usb_debug!("host device handling clear feature"); 120 self.clear_feature()? 121 } 122 _ => { 123 // Other requests will be passed through to the device. 124 return Ok(false); 125 } 126 }; 127 128 xhci_transfer 129 .on_transfer_complete(&status, 0) 130 .map_err(Error::TransferComplete)?; 131 Ok(true) 132 } 133 execute_control_transfer( &mut self, xhci_transfer: Arc<XhciTransfer>, buffer: Option<ScatterGatherBuffer>, ) -> Result<()>134 fn execute_control_transfer( 135 &mut self, 136 xhci_transfer: Arc<XhciTransfer>, 137 buffer: Option<ScatterGatherBuffer>, 138 ) -> Result<()> { 139 if self.intercepted_control_transfer(&xhci_transfer)? { 140 return Ok(()); 141 } 142 143 // Allocate a buffer for the control transfer. 144 // This buffer will hold a UsbRequestSetup struct followed by the data. 145 let control_buffer_len = 146 mem::size_of::<UsbRequestSetup>() + self.control_request_setup.length as usize; 147 let mut control_buffer = vec![0u8; control_buffer_len]; 148 149 // Copy the control request header. 150 control_buffer[..mem::size_of::<UsbRequestSetup>()] 151 .copy_from_slice(self.control_request_setup.as_slice()); 152 153 let direction = self.control_request_setup.get_direction(); 154 let buffer = if direction == ControlRequestDataPhaseTransferDirection::HostToDevice { 155 if let Some(buffer) = buffer { 156 buffer 157 .read(&mut control_buffer[mem::size_of::<UsbRequestSetup>()..]) 158 .map_err(Error::ReadBuffer)?; 159 } 160 // buffer is consumed here for HostToDevice transfers. 161 None 162 } else { 163 // buffer will be used later in the callback for DeviceToHost transfers. 164 buffer 165 }; 166 167 let mut control_transfer = 168 Transfer::new_control(control_buffer).map_err(Error::CreateTransfer)?; 169 170 let tmp_transfer = xhci_transfer.clone(); 171 let callback = move |t: Transfer| { 172 usb_debug!("setup token control transfer callback invoked"); 173 update_transfer_state(&xhci_transfer, &t)?; 174 let state = xhci_transfer.state().lock(); 175 match *state { 176 XhciTransferState::Cancelled => { 177 usb_debug!("transfer cancelled"); 178 drop(state); 179 xhci_transfer 180 .on_transfer_complete(&TransferStatus::Cancelled, 0) 181 .map_err(Error::TransferComplete)?; 182 } 183 XhciTransferState::Completed => { 184 let status = t.status(); 185 let actual_length = t.actual_length(); 186 if direction == ControlRequestDataPhaseTransferDirection::DeviceToHost { 187 if let Some(control_request_data) = 188 t.buffer.get(mem::size_of::<UsbRequestSetup>()..) 189 { 190 if let Some(buffer) = &buffer { 191 buffer 192 .write(&control_request_data) 193 .map_err(Error::WriteBuffer)?; 194 } 195 } 196 } 197 drop(state); 198 usb_debug!("transfer completed with actual length {}", actual_length); 199 xhci_transfer 200 .on_transfer_complete(&status, actual_length as u32) 201 .map_err(Error::TransferComplete)?; 202 } 203 _ => { 204 // update_transfer_state is already invoked before match. 205 // This transfer could only be `Cancelled` or `Completed`. 206 // Any other state means there is a bug in crosvm implementation. 207 error!("should not take this branch"); 208 return Err(Error::BadXhciTransferState); 209 } 210 } 211 Ok(()) 212 }; 213 214 let fail_handle = self.fail_handle.clone(); 215 control_transfer.set_callback(move |t: Transfer| match callback(t) { 216 Ok(_) => {} 217 Err(e) => { 218 error!("control transfer callback failed {:?}", e); 219 fail_handle.fail(); 220 } 221 }); 222 submit_transfer( 223 self.fail_handle.clone(), 224 &self.job_queue, 225 tmp_transfer, 226 &mut self.device.lock(), 227 control_transfer, 228 ) 229 } 230 handle_control_transfer(&mut self, transfer: XhciTransfer) -> Result<()>231 fn handle_control_transfer(&mut self, transfer: XhciTransfer) -> Result<()> { 232 let xhci_transfer = Arc::new(transfer); 233 match xhci_transfer 234 .get_transfer_type() 235 .map_err(Error::GetXhciTransferType)? 236 { 237 XhciTransferType::SetupStage(setup) => { 238 if self.ctl_ep_state != ControlEndpointState::SetupStage { 239 error!("Control endpoint is in an inconsistant state"); 240 return Ok(()); 241 } 242 usb_debug!("setup stage setup buffer: {:?}", setup); 243 self.control_request_setup = setup; 244 xhci_transfer 245 .on_transfer_complete(&TransferStatus::Completed, 0) 246 .map_err(Error::TransferComplete)?; 247 self.ctl_ep_state = ControlEndpointState::DataStage; 248 } 249 XhciTransferType::DataStage(buffer) => { 250 if self.ctl_ep_state != ControlEndpointState::DataStage { 251 error!("Control endpoint is in an inconsistant state"); 252 return Ok(()); 253 } 254 // Requests with a DataStage will be executed here. 255 // Requests without a DataStage will be executed in StatusStage. 256 self.execute_control_transfer(xhci_transfer, Some(buffer))?; 257 self.executed = true; 258 self.ctl_ep_state = ControlEndpointState::StatusStage; 259 } 260 XhciTransferType::StatusStage => { 261 if self.ctl_ep_state == ControlEndpointState::SetupStage { 262 error!("Control endpoint is in an inconsistant state"); 263 return Ok(()); 264 } 265 if self.executed { 266 // Request was already executed during DataStage. 267 // Just complete the StatusStage transfer. 268 xhci_transfer 269 .on_transfer_complete(&TransferStatus::Completed, 0) 270 .map_err(Error::TransferComplete)?; 271 } else { 272 // Execute the request now since there was no DataStage. 273 self.execute_control_transfer(xhci_transfer, None)?; 274 } 275 self.executed = false; 276 self.ctl_ep_state = ControlEndpointState::SetupStage; 277 } 278 _ => { 279 // Non control transfer should not be handled in this function. 280 error!("Non control (could be noop) transfer sent to control endpoint."); 281 xhci_transfer 282 .on_transfer_complete(&TransferStatus::Completed, 0) 283 .map_err(Error::TransferComplete)?; 284 } 285 } 286 Ok(()) 287 } 288 set_config(&mut self) -> Result<TransferStatus>289 fn set_config(&mut self) -> Result<TransferStatus> { 290 // It's a standard, set_config, device request. 291 let config = (self.control_request_setup.value & 0xff) as u8; 292 usb_debug!( 293 "Set config control transfer is received with config: {}", 294 config 295 ); 296 self.release_interfaces(); 297 if self.device.lock().get_num_configurations() > 1 { 298 let cur_config = match self.device.lock().get_active_configuration() { 299 Ok(c) => Some(c), 300 Err(e) => { 301 // The device may be in the default state, in which case 302 // GET_CONFIGURATION may fail. Assume the device needs to be 303 // reconfigured. 304 usb_debug!("Failed to get active configuration: {}", e); 305 error!("Failed to get active configuration: {}", e); 306 None 307 } 308 }; 309 if Some(config) != cur_config { 310 self.device 311 .lock() 312 .set_active_configuration(config) 313 .map_err(Error::SetActiveConfig)?; 314 } 315 } else { 316 usb_debug!("Only one configuration - not calling set_active_configuration"); 317 } 318 let config_descriptor = self 319 .device 320 .lock() 321 .get_config_descriptor(config) 322 .map_err(Error::GetActiveConfig)?; 323 self.claim_interfaces(&config_descriptor); 324 self.create_endpoints(&config_descriptor)?; 325 Ok(TransferStatus::Completed) 326 } 327 set_interface(&mut self) -> Result<TransferStatus>328 fn set_interface(&mut self) -> Result<TransferStatus> { 329 usb_debug!("set interface"); 330 // It's a standard, set_interface, interface request. 331 let interface = self.control_request_setup.index as u8; 332 let alt_setting = self.control_request_setup.value as u8; 333 self.device 334 .lock() 335 .set_interface_alt_setting(interface, alt_setting) 336 .map_err(Error::SetInterfaceAltSetting)?; 337 self.alt_settings.insert(interface, alt_setting); 338 let config = self 339 .device 340 .lock() 341 .get_active_configuration() 342 .map_err(Error::GetActiveConfig)?; 343 let config_descriptor = self 344 .device 345 .lock() 346 .get_config_descriptor(config) 347 .map_err(Error::GetActiveConfig)?; 348 self.create_endpoints(&config_descriptor)?; 349 Ok(TransferStatus::Completed) 350 } 351 clear_feature(&mut self) -> Result<TransferStatus>352 fn clear_feature(&mut self) -> Result<TransferStatus> { 353 usb_debug!("clear feature"); 354 let request_setup = &self.control_request_setup; 355 // It's a standard, clear_feature, endpoint request. 356 const STD_FEATURE_ENDPOINT_HALT: u16 = 0; 357 if request_setup.value == STD_FEATURE_ENDPOINT_HALT { 358 self.device 359 .lock() 360 .clear_halt(request_setup.index as u8) 361 .map_err(Error::ClearHalt)?; 362 } 363 Ok(TransferStatus::Completed) 364 } 365 claim_interfaces(&mut self, config_descriptor: &ConfigDescriptorTree)366 fn claim_interfaces(&mut self, config_descriptor: &ConfigDescriptorTree) { 367 for i in 0..config_descriptor.num_interfaces() { 368 match self.device.lock().claim_interface(i) { 369 Ok(()) => { 370 usb_debug!("claimed interface {}", i); 371 self.claimed_interfaces.push(i); 372 } 373 Err(e) => { 374 error!("unable to claim interface {}: {:?}", i, e); 375 } 376 } 377 } 378 } 379 create_endpoints(&mut self, config_descriptor: &ConfigDescriptorTree) -> Result<()>380 fn create_endpoints(&mut self, config_descriptor: &ConfigDescriptorTree) -> Result<()> { 381 self.endpoints = Vec::new(); 382 for i in &self.claimed_interfaces { 383 let alt_setting = self.alt_settings.get(i).unwrap_or(&0); 384 let interface = config_descriptor 385 .get_interface_descriptor(*i, *alt_setting) 386 .ok_or(Error::GetInterfaceDescriptor((*i, *alt_setting)))?; 387 for ep_idx in 0..interface.bNumEndpoints { 388 let ep_dp = interface 389 .get_endpoint_descriptor(ep_idx) 390 .ok_or(Error::GetEndpointDescriptor(ep_idx))?; 391 let ep_num = ep_dp.get_endpoint_number(); 392 if ep_num == 0 { 393 usb_debug!("endpoint 0 in endpoint descriptors"); 394 continue; 395 } 396 let direction = ep_dp.get_direction(); 397 let ty = ep_dp.get_endpoint_type().ok_or(Error::GetEndpointType)?; 398 self.endpoints.push(UsbEndpoint::new( 399 self.fail_handle.clone(), 400 self.job_queue.clone(), 401 self.device.clone(), 402 ep_num, 403 direction, 404 ty, 405 )); 406 } 407 } 408 Ok(()) 409 } 410 release_interfaces(&mut self)411 fn release_interfaces(&mut self) { 412 for i in &self.claimed_interfaces { 413 if let Err(e) = self.device.lock().release_interface(*i) { 414 error!("could not release interface: {:?}", e); 415 } 416 } 417 self.claimed_interfaces = Vec::new(); 418 } 419 submit_transfer_helper(&mut self, transfer: XhciTransfer) -> Result<()>420 fn submit_transfer_helper(&mut self, transfer: XhciTransfer) -> Result<()> { 421 if transfer.get_endpoint_number() == 0 { 422 return self.handle_control_transfer(transfer); 423 } 424 for ep in &self.endpoints { 425 if ep.match_ep(transfer.get_endpoint_number(), transfer.get_transfer_dir()) { 426 return ep.handle_transfer(transfer); 427 } 428 } 429 warn!("Could not find endpoint for transfer"); 430 transfer 431 .on_transfer_complete(&TransferStatus::Error, 0) 432 .map_err(Error::TransferComplete) 433 } 434 } 435 436 impl XhciBackendDevice for HostDevice { get_backend_type(&self) -> BackendType437 fn get_backend_type(&self) -> BackendType { 438 let d = match self.device.lock().get_device_descriptor() { 439 Ok(d) => d, 440 Err(_) => return BackendType::Usb2, 441 }; 442 443 // See definition of bcdUsb. 444 const USB3_MASK: u16 = 0x0300; 445 match d.bcdUSB & USB3_MASK { 446 USB3_MASK => BackendType::Usb3, 447 _ => BackendType::Usb2, 448 } 449 } 450 get_vid(&self) -> u16451 fn get_vid(&self) -> u16 { 452 match self.device.lock().get_device_descriptor() { 453 Ok(d) => d.idVendor, 454 Err(e) => { 455 error!("cannot get device descriptor: {:?}", e); 456 0 457 } 458 } 459 } 460 get_pid(&self) -> u16461 fn get_pid(&self) -> u16 { 462 match self.device.lock().get_device_descriptor() { 463 Ok(d) => d.idProduct, 464 Err(e) => { 465 error!("cannot get device descriptor: {:?}", e); 466 0 467 } 468 } 469 } 470 submit_transfer(&mut self, transfer: XhciTransfer) -> Result<()>471 fn submit_transfer(&mut self, transfer: XhciTransfer) -> Result<()> { 472 self.submit_transfer_helper(transfer) 473 } 474 set_address(&mut self, _address: UsbDeviceAddress)475 fn set_address(&mut self, _address: UsbDeviceAddress) { 476 // It's a standard, set_address, device request. We do nothing here. As described in XHCI 477 // spec. See set address command ring trb. 478 usb_debug!( 479 "Set address control transfer is received with address: {}", 480 _address 481 ); 482 } 483 reset(&mut self) -> Result<()>484 fn reset(&mut self) -> Result<()> { 485 usb_debug!("resetting host device"); 486 self.device.lock().reset().map_err(Error::Reset) 487 } 488 } 489