diff --git a/headers/os/drivers/USB3.h b/headers/os/drivers/USB3.h index e02ba5a3e0..091c93da64 100644 --- a/headers/os/drivers/USB3.h +++ b/headers/os/drivers/USB3.h @@ -182,6 +182,11 @@ struct usb_module_info { usb_callback_func callback, void *callbackCookie); + status_t (*queue_bulk_v_physical)(usb_pipe pipe, + physical_entry *vectors, size_t vectorCount, + usb_callback_func callback, + void *callbackCookie); + status_t (*queue_isochronous)(usb_pipe pipe, void *data, size_t dataLength, usb_iso_packet_descriptor *packetDesc, @@ -206,6 +211,9 @@ struct usb_module_info { /* Cancel all pending async requests in a pipe */ status_t (*cancel_queued_transfers)(usb_pipe pipe); + /* Cancel all pending async requests in a device control pipe */ + status_t (*cancel_queued_requests)(usb_device device); + /* Tuning, configuration of timeouts, etc */ status_t (*usb_ioctl)(uint32 opcode, void *buffer, size_t bufferSize); @@ -247,14 +255,10 @@ struct usb_module_info { uint8 portIndex); status_t (*disable_port)(usb_device hub, uint8 portIndex); - - /* Cancel all pending async requests in a device control pipe */ - status_t (*cancel_queued_requests)(usb_device device); - }; -#define B_USB_MODULE_NAME "bus_managers/usb/v3" +#define B_USB_MODULE_NAME "bus_managers/usb/v3.1" #ifdef __cplusplus diff --git a/headers/private/kernel/util/iovec_support.h b/headers/private/kernel/util/iovec_support.h index 29a6653d33..22b46e8859 100644 --- a/headers/private/kernel/util/iovec_support.h +++ b/headers/private/kernel/util/iovec_support.h @@ -15,7 +15,32 @@ typedef struct generic_io_vec { } generic_io_vec; +#ifdef _KERNEL_VM_VM_H + +static inline status_t +generic_memcpy(generic_addr_t dest, bool destPhysical, generic_addr_t src, bool srcPhysical, + generic_size_t size, bool user = false) +{ + if (!srcPhysical && !destPhysical) { + if (user) + return user_memcpy((void*)dest, (void*)src, size); + memcpy((void*)dest, (void*)src, size); + return B_OK; + } else if (destPhysical && !srcPhysical) { + return vm_memcpy_to_physical(dest, (const void*)src, size, user); + } else if (!destPhysical && srcPhysical) { + return vm_memcpy_from_physical((void*)dest, src, size, user); + } + + panic("generic_memcpy: physical -> physical not supported!"); + return B_NOT_SUPPORTED; +} + +#endif + + #ifdef IS_USER_ADDRESS + static inline status_t get_iovecs_from_user(const iovec* userVecs, size_t vecCount, iovec*& vecs, bool permitNull = false) @@ -53,6 +78,7 @@ get_iovecs_from_user(const iovec* userVecs, size_t vecCount, iovec*& vecs, return B_OK; } + #endif diff --git a/src/add-ons/kernel/bus_managers/usb/Pipe.cpp b/src/add-ons/kernel/bus_managers/usb/Pipe.cpp index 0b91c788dd..624437a30e 100644 --- a/src/add-ons/kernel/bus_managers/usb/Pipe.cpp +++ b/src/add-ons/kernel/bus_managers/usb/Pipe.cpp @@ -227,7 +227,28 @@ BulkPipe::QueueBulk(void *data, size_t dataLength, usb_callback_func callback, status_t BulkPipe::QueueBulkV(iovec *vector, size_t vectorCount, - usb_callback_func callback, void *callbackCookie, bool physical) + usb_callback_func callback, void *callbackCookie) +{ + if (vectorCount > 0 && vector == NULL) + return B_BAD_VALUE; + + Transfer *transfer = new(std::nothrow) Transfer(this); + if (!transfer) + return B_NO_MEMORY; + + transfer->SetVector(vector, vectorCount); + transfer->SetCallback(callback, callbackCookie); + + status_t result = GetBusManager()->SubmitTransfer(transfer); + if (result < B_OK) + delete transfer; + return result; +} + + +status_t +BulkPipe::QueueBulkV(physical_entry *vector, size_t vectorCount, + usb_callback_func callback, void *callbackCookie) { if (vectorCount > 0 && vector == NULL) return B_BAD_VALUE; @@ -235,8 +256,6 @@ BulkPipe::QueueBulkV(iovec *vector, size_t vectorCount, Transfer *transfer = new(std::nothrow) Transfer(this); if (!transfer) return B_NO_MEMORY; - if (physical) - return B_NOT_SUPPORTED; transfer->SetVector(vector, vectorCount); transfer->SetCallback(callback, callbackCookie); diff --git a/src/add-ons/kernel/bus_managers/usb/Transfer.cpp b/src/add-ons/kernel/bus_managers/usb/Transfer.cpp index f8a8532e5a..268c17bfd8 100644 --- a/src/add-ons/kernel/bus_managers/usb/Transfer.cpp +++ b/src/add-ons/kernel/bus_managers/usb/Transfer.cpp @@ -85,6 +85,7 @@ void Transfer::SetVector(iovec *vector, size_t vectorCount) { fPhysical = false; + fVector = new(std::nothrow) generic_io_vec[vectorCount]; for (size_t i = 0; i < vectorCount; i++) { fVector[i].base = (generic_addr_t)vector[i].iov_base; @@ -93,6 +94,30 @@ Transfer::SetVector(iovec *vector, size_t vectorCount) fVectorCount = vectorCount; fBaseAddress = vector[0].iov_base; + _CheckFragmented(); +} + + +void +Transfer::SetVector(physical_entry *vector, size_t vectorCount) +{ + fPhysical = true; + + fVector = new(std::nothrow) generic_io_vec[vectorCount]; + for (size_t i = 0; i < vectorCount; i++) { + fVector[i].base = (generic_addr_t)vector[i].address; + fVector[i].length = vector[i].size; + } + fVectorCount = vectorCount; + fBaseAddress = NULL; + + _CheckFragmented(); +} + + +void +Transfer::_CheckFragmented() +{ size_t length = 0; for (size_t i = 0; i < fVectorCount && length <= USB_MAX_FRAGMENT_SIZE; i++) length += fVector[i].length; @@ -138,8 +163,8 @@ Transfer::AdvanceByFragment(size_t actualLength) status_t Transfer::InitKernelAccess() { - // nothing to do if we are already prepared - if (fClonedArea >= B_OK) + // nothing to do if we are already prepared, or have a physical request + if (fClonedArea >= B_OK || fPhysical) return B_OK; // we might need to access a buffer in userspace. this will not diff --git a/src/add-ons/kernel/bus_managers/usb/usb.cpp b/src/add-ons/kernel/bus_managers/usb/usb.cpp index 0706530705..ac1a70c7c3 100644 --- a/src/add-ons/kernel/bus_managers/usb/usb.cpp +++ b/src/add-ons/kernel/bus_managers/usb/usb.cpp @@ -462,12 +462,12 @@ queue_bulk_v(usb_pipe pipe, iovec *vector, size_t vectorCount, return B_DEV_INVALID_PIPE; return ((BulkPipe *)object.Get())->QueueBulkV(vector, vectorCount, - callback, callbackCookie, false); + callback, callbackCookie); } status_t -queue_bulk_v_physical(usb_pipe pipe, iovec *vector, size_t vectorCount, +queue_bulk_v_physical(usb_pipe pipe, physical_entry *vector, size_t vectorCount, usb_callback_func callback, void *callbackCookie) { TRACE_MODULE("queue_bulk_v_physical(%" B_PRId32 ", %p, %" B_PRIuSIZE @@ -477,7 +477,7 @@ queue_bulk_v_physical(usb_pipe pipe, iovec *vector, size_t vectorCount, return B_DEV_INVALID_PIPE; return ((BulkPipe *)object.Get())->QueueBulkV(vector, vectorCount, - callback, callbackCookie, true); + callback, callbackCookie); } @@ -667,7 +667,7 @@ struct usb_module_info gModuleInfoV3 = { // First the bus_manager_info: { { - "bus_managers/usb/v3", + "bus_managers/usb/v3.1", B_KEEP_LOADED, // Keep loaded, even if no driver requires it bus_std_ops }, @@ -690,18 +690,18 @@ struct usb_module_info gModuleInfoV3 = { queue_interrupt, // queue_interrupt queue_bulk, // queue_bulk queue_bulk_v, // queue_bulk_v + queue_bulk_v_physical, // queue_bulk_v_physical queue_isochronous, // queue_isochronous queue_request, // queue_request set_pipe_policy, // set_pipe_policy cancel_queued_transfers, // cancel_queued_transfers + cancel_queued_requests, // cancel_queued_requests usb_ioctl, // usb_ioctl get_nth_roothub, // get_nth_roothub get_nth_child, // get_nth_child get_device_parent, // get_device_parent reset_port, // reset_port disable_port, // disable_port - cancel_queued_requests // cancel_queued_requests - //queue_bulk_v_physical // queue_bulk_v_physical }; @@ -955,10 +955,10 @@ device_std_ops(int32 op, ...) // functions directly instead via official interface, so this // pointer is never read. module_info *dummy; - return get_module("bus_managers/usb/v3", &dummy); + return get_module(B_USB_MODULE_NAME, &dummy); } case B_MODULE_UNINIT: - return put_module("bus_managers/usb/v3"); + return put_module(B_USB_MODULE_NAME); default: return B_ERROR; diff --git a/src/add-ons/kernel/bus_managers/usb/usb_private.h b/src/add-ons/kernel/bus_managers/usb/usb_private.h index 55aede9453..ccc28e8fa0 100644 --- a/src/add-ons/kernel/bus_managers/usb/usb_private.h +++ b/src/add-ons/kernel/bus_managers/usb/usb_private.h @@ -16,6 +16,9 @@ #include "usbspec_private.h" #include #include + +// include vm.h before iovec_support.h for generic_memcpy, which is used by the bus drivers. +#include #include @@ -475,12 +478,10 @@ virtual const char * TypeName() const { return "bulk pipe"; } size_t dataLength, usb_callback_func callback, void *callbackCookie); - status_t QueueBulkV(iovec *vector, - size_t vectorCount, - usb_callback_func callback, - void *callbackCookie, - bool physical); -}; + status_t QueueBulkV(iovec *vector, size_t vectorCount, + usb_callback_func callback, void *callbackCookie); + status_t QueueBulkV(physical_entry *vector, size_t vectorCount, + usb_callback_func callback, void *callbackCookie);}; class IsochronousPipe : public Pipe { @@ -721,6 +722,7 @@ public: bool IsPhysical() const { return fPhysical; } void SetVector(iovec *vector, size_t vectorCount); + void SetVector(physical_entry *vector, size_t vectorCount); generic_io_vec * Vector() { return fVector; } size_t VectorCount() const { return fVectorCount; } @@ -747,6 +749,7 @@ public: const char * TypeName() const { return "transfer"; } private: + void _CheckFragmented(); status_t _CalculateBandwidth(); // Data that is related to the transfer diff --git a/src/add-ons/kernel/busses/usb/ehci.cpp b/src/add-ons/kernel/busses/usb/ehci.cpp index 327b18b0eb..934581dbcc 100644 --- a/src/add-ons/kernel/busses/usb/ehci.cpp +++ b/src/add-ons/kernel/busses/usb/ehci.cpp @@ -1023,7 +1023,7 @@ EHCI::CheckDebugTransfer(Transfer *transfer) size_t vectorCount = transfer->VectorCount(); ReadDescriptorChain(transferData->data_descriptor, - vector, vectorCount, &nextDataToggle); + vector, vectorCount, transfer->IsPhysical(), &nextDataToggle); } else if (transferData->data_descriptor != NULL) ReadActualLength(transferData->data_descriptor, &nextDataToggle); @@ -2010,7 +2010,7 @@ EHCI::FinishTransfers() if (callbackStatus == B_OK) { actualLength = ReadDescriptorChain( transfer->data_descriptor, - vector, vectorCount, + vector, vectorCount, transfer->transfer->IsPhysical(), &nextDataToggle); } } else if (transfer->data_descriptor) { @@ -2448,7 +2448,7 @@ EHCI::FillQueueWithRequest(Transfer *transfer, ehci_qh *queueHead, generic_io_vec vector; vector.base = (generic_addr_t)requestData; vector.length = sizeof(usb_request_data); - WriteDescriptorChain(setupDescriptor, &vector, 1); + WriteDescriptorChain(setupDescriptor, &vector, 1, false); ehci_qtd *strayDescriptor = queueHead->stray_log; statusDescriptor->token |= EHCI_QTD_IOC | EHCI_QTD_DATA_TOGGLE; @@ -2476,7 +2476,7 @@ EHCI::FillQueueWithRequest(Transfer *transfer, ehci_qh *queueHead, } } WriteDescriptorChain(dataDescriptor, transfer->Vector(), - transfer->VectorCount()); + transfer->VectorCount(), transfer->IsPhysical()); } LinkDescriptors(setupDescriptor, dataDescriptor, strayDescriptor); @@ -2523,7 +2523,7 @@ EHCI::FillQueueWithData(Transfer *transfer, ehci_qh *queueHead, } } WriteDescriptorChain(firstDescriptor, transfer->Vector(), - transfer->VectorCount()); + transfer->VectorCount(), transfer->IsPhysical()); } queueHead->element_log = firstDescriptor; @@ -2785,7 +2785,7 @@ EHCI::UnlinkSITDescriptors(ehci_sitd *sitd, ehci_sitd **last) size_t EHCI::WriteDescriptorChain(ehci_qtd *topDescriptor, generic_io_vec *vector, - size_t vectorCount) + size_t vectorCount, bool physical) { ehci_qtd *current = topDescriptor; size_t actualLength = 0; @@ -2801,8 +2801,10 @@ EHCI::WriteDescriptorChain(ehci_qtd *topDescriptor, generic_io_vec *vector, size_t length = min_c(current->buffer_size - bufferOffset, vector[vectorIndex].length - vectorOffset); - memcpy((uint8 *)current->buffer_log + bufferOffset, - (uint8 *)vector[vectorIndex].base + vectorOffset, length); + status_t status = generic_memcpy( + (generic_addr_t)current->buffer_log + bufferOffset, false, + vector[vectorIndex].base + vectorOffset, physical, length); + ASSERT(status == B_OK); actualLength += length; vectorOffset += length; @@ -2837,7 +2839,7 @@ EHCI::WriteDescriptorChain(ehci_qtd *topDescriptor, generic_io_vec *vector, size_t EHCI::ReadDescriptorChain(ehci_qtd *topDescriptor, generic_io_vec *vector, - size_t vectorCount, bool *nextDataToggle) + size_t vectorCount, bool physical, bool *nextDataToggle) { uint32 dataToggle = 0; ehci_qtd *current = topDescriptor; @@ -2859,8 +2861,10 @@ EHCI::ReadDescriptorChain(ehci_qtd *topDescriptor, generic_io_vec *vector, size_t length = min_c(bufferSize - bufferOffset, vector[vectorIndex].length - vectorOffset); - memcpy((uint8 *)vector[vectorIndex].base + vectorOffset, - (uint8 *)current->buffer_log + bufferOffset, length); + status_t status = generic_memcpy( + vector[vectorIndex].base + vectorOffset, physical, + (generic_addr_t)current->buffer_log + bufferOffset, false, length); + ASSERT(status == B_OK); actualLength += length; vectorOffset += length; @@ -2922,8 +2926,7 @@ EHCI::ReadActualLength(ehci_qtd *topDescriptor, bool *nextDataToggle) size_t -EHCI::WriteIsochronousDescriptorChain(isochronous_transfer_data *transfer, - uint32 packetCount, generic_io_vec *vector) +EHCI::WriteIsochronousDescriptorChain(isochronous_transfer_data *transfer) { // TODO implement return 0; @@ -2935,6 +2938,7 @@ EHCI::ReadIsochronousDescriptorChain(isochronous_transfer_data *transfer) { generic_io_vec *vector = transfer->transfer->Vector(); size_t vectorCount = transfer->transfer->VectorCount(); + const bool physical = transfer->transfer->IsPhysical(); size_t vectorOffset = 0; size_t vectorIndex = 0; usb_isochronous_data *isochronousData @@ -2972,8 +2976,11 @@ EHCI::ReadIsochronousDescriptorChain(isochronous_transfer_data *transfer) while (bufferSize > 0) { size_t length = min_c(bufferSize, vector[vectorIndex].length - vectorOffset); - memcpy((uint8 *)vector[vectorIndex].base + vectorOffset, - (uint8 *)transfer->buffer_log + bufferOffset, length); + status_t status = generic_memcpy( + vector[vectorIndex].base + vectorOffset, physical, + (generic_addr_t)transfer->buffer_log + bufferOffset, false, length); + ASSERT(status == B_OK); + offset += length; vectorOffset += length; bufferSize -= length; diff --git a/src/add-ons/kernel/busses/usb/ehci.h b/src/add-ons/kernel/busses/usb/ehci.h index f9bc64a16c..eaba43d881 100644 --- a/src/add-ons/kernel/busses/usb/ehci.h +++ b/src/add-ons/kernel/busses/usb/ehci.h @@ -178,16 +178,15 @@ static int32 FinishIsochronousThread(void *data); size_t WriteDescriptorChain( ehci_qtd *topDescriptor, - generic_io_vec *vector, size_t vectorCount); + generic_io_vec *vector, size_t vectorCount, + bool physical); size_t ReadDescriptorChain(ehci_qtd *topDescriptor, generic_io_vec *vector, size_t vectorCount, - bool *nextDataToggle); + bool physical, bool *nextDataToggle); size_t ReadActualLength(ehci_qtd *topDescriptor, bool *nextDataToggle); size_t WriteIsochronousDescriptorChain( - isochronous_transfer_data *transfer, - uint32 packetCount, - generic_io_vec *vector); + isochronous_transfer_data *transfer); size_t ReadIsochronousDescriptorChain( isochronous_transfer_data *transfer); diff --git a/src/add-ons/kernel/busses/usb/ohci.cpp b/src/add-ons/kernel/busses/usb/ohci.cpp index ca64a06f64..9599d9e666 100644 --- a/src/add-ons/kernel/busses/usb/ohci.cpp +++ b/src/add-ons/kernel/busses/usb/ohci.cpp @@ -1267,7 +1267,7 @@ OHCI::_FinishTransfers() transfer->transfer->PrepareKernelAccess(); actualLength = _ReadDescriptorChain( transfer->data_descriptor, - vector, vectorCount); + vector, vectorCount, transfer->transfer->IsPhysical()); } else if (transfer->data_descriptor) { // read the actual length that was sent actualLength = _ReadActualLength( @@ -1436,7 +1436,7 @@ OHCI::_FinishIsochronousTransfer(transfer_data *transfer, transfer->transfer->PrepareKernelAccess(); _ReadIsochronousDescriptorChain( (ohci_isochronous_td*)transfer->data_descriptor, - vector, vectorCount); + vector, vectorCount, transfer->transfer->IsPhysical()); } } @@ -1485,7 +1485,7 @@ OHCI::_SubmitRequest(Transfer *transfer) generic_io_vec vector; vector.base = (generic_addr_t)requestData; vector.length = sizeof(usb_request_data); - _WriteDescriptorChain(setupDescriptor, &vector, 1); + _WriteDescriptorChain(setupDescriptor, &vector, 1, false); status_t result; ohci_general_td *dataDescriptor = NULL; @@ -1502,7 +1502,7 @@ OHCI::_SubmitRequest(Transfer *transfer) if (!directionIn) { _WriteDescriptorChain(dataDescriptor, transfer->Vector(), - transfer->VectorCount()); + transfer->VectorCount(), transfer->IsPhysical()); } _LinkDescriptors(setupDescriptor, dataDescriptor); @@ -1562,7 +1562,7 @@ OHCI::_SubmitTransfer(Transfer *transfer) if (!directionIn) { _WriteDescriptorChain(firstDescriptor, transfer->Vector(), - transfer->VectorCount()); + transfer->VectorCount(), transfer->IsPhysical()); } // Add to the transfer list @@ -1631,7 +1631,7 @@ OHCI::_SubmitIsochronousTransfer(Transfer *transfer) // If direction is out set every descriptor data if (pipe->Direction() == Pipe::Out) _WriteIsochronousDescriptorChain(firstDescriptor, - transfer->Vector(), transfer->VectorCount()); + transfer->Vector(), transfer->VectorCount(), transfer->IsPhysical()); else // Initialize the packet descriptors for (uint32 i = 0; i < isochronousData->packet_count; i++) { @@ -2279,7 +2279,7 @@ OHCI::_FreeIsochronousDescriptorChain(ohci_isochronous_td *topDescriptor) size_t OHCI::_WriteDescriptorChain(ohci_general_td *topDescriptor, generic_io_vec *vector, - size_t vectorCount) + size_t vectorCount, bool physical) { ohci_general_td *current = topDescriptor; size_t actualLength = 0; @@ -2298,8 +2298,10 @@ OHCI::_WriteDescriptorChain(ohci_general_td *topDescriptor, generic_io_vec *vect TRACE("copying %ld bytes to bufferOffset %ld from" " vectorOffset %ld at index %ld of %ld\n", length, bufferOffset, vectorOffset, vectorIndex, vectorCount); - memcpy((uint8 *)current->buffer_logical + bufferOffset, - (uint8 *)vector[vectorIndex].base + vectorOffset, length); + status_t status = generic_memcpy( + (generic_addr_t)current->buffer_logical + bufferOffset, false, + vector[vectorIndex].base + vectorOffset, physical, length); + ASSERT(status == B_OK); actualLength += length; vectorOffset += length; @@ -2334,7 +2336,7 @@ OHCI::_WriteDescriptorChain(ohci_general_td *topDescriptor, generic_io_vec *vect size_t OHCI::_WriteIsochronousDescriptorChain(ohci_isochronous_td *topDescriptor, - generic_io_vec *vector, size_t vectorCount) + generic_io_vec *vector, size_t vectorCount, bool physical) { ohci_isochronous_td *current = topDescriptor; size_t actualLength = 0; @@ -2353,8 +2355,10 @@ OHCI::_WriteIsochronousDescriptorChain(ohci_isochronous_td *topDescriptor, TRACE("copying %ld bytes to bufferOffset %ld from" " vectorOffset %ld at index %ld of %ld\n", length, bufferOffset, vectorOffset, vectorIndex, vectorCount); - memcpy((uint8 *)current->buffer_logical + bufferOffset, - (uint8 *)vector[vectorIndex].base + vectorOffset, length); + status_t status = generic_memcpy( + (generic_addr_t)current->buffer_logical + bufferOffset, false, + vector[vectorIndex].base + vectorOffset, physical, length); + ASSERT(status == B_OK); actualLength += length; vectorOffset += length; @@ -2389,7 +2393,7 @@ OHCI::_WriteIsochronousDescriptorChain(ohci_isochronous_td *topDescriptor, size_t OHCI::_ReadDescriptorChain(ohci_general_td *topDescriptor, generic_io_vec *vector, - size_t vectorCount) + size_t vectorCount, bool physical) { ohci_general_td *current = topDescriptor; size_t actualLength = 0; @@ -2415,8 +2419,10 @@ OHCI::_ReadDescriptorChain(ohci_general_td *topDescriptor, generic_io_vec *vecto TRACE("copying %ld bytes to vectorOffset %ld from" " bufferOffset %ld at index %ld of %ld\n", length, vectorOffset, bufferOffset, vectorIndex, vectorCount); - memcpy((uint8 *)vector[vectorIndex].base + vectorOffset, - (uint8 *)current->buffer_logical + bufferOffset, length); + status_t status = generic_memcpy( + vector[vectorIndex].base + vectorOffset, physical, + (generic_addr_t)current->buffer_logical + bufferOffset, false, length); + ASSERT(status == B_OK); actualLength += length; vectorOffset += length; @@ -2448,7 +2454,7 @@ OHCI::_ReadDescriptorChain(ohci_general_td *topDescriptor, generic_io_vec *vecto void OHCI::_ReadIsochronousDescriptorChain(ohci_isochronous_td *topDescriptor, - generic_io_vec *vector, size_t vectorCount) + generic_io_vec *vector, size_t vectorCount, bool physical) { ohci_isochronous_td *current = topDescriptor; size_t actualLength = 0; @@ -2467,8 +2473,10 @@ OHCI::_ReadIsochronousDescriptorChain(ohci_isochronous_td *topDescriptor, TRACE("copying %ld bytes to vectorOffset %ld from bufferOffset" " %ld at index %ld of %ld\n", length, vectorOffset, bufferOffset, vectorIndex, vectorCount); - memcpy((uint8 *)vector[vectorIndex].base + vectorOffset, - (uint8 *)current->buffer_logical + bufferOffset, length); + status_t status = generic_memcpy( + vector[vectorIndex].base + vectorOffset, physical, + (generic_addr_t)current->buffer_logical + bufferOffset, false, length); + ASSERT(status == B_OK); actualLength += length; vectorOffset += length; diff --git a/src/add-ons/kernel/busses/usb/ohci.h b/src/add-ons/kernel/busses/usb/ohci.h index 8a790f6b44..cf3e43efa4 100644 --- a/src/add-ons/kernel/busses/usb/ohci.h +++ b/src/add-ons/kernel/busses/usb/ohci.h @@ -135,17 +135,21 @@ static int32 _FinishThread(void *data); size_t _WriteDescriptorChain( ohci_general_td *topDescriptor, - generic_io_vec *vector, size_t vectorCount); + generic_io_vec *vector, size_t vectorCount, + bool physical); size_t _ReadDescriptorChain( ohci_general_td *topDescriptor, - generic_io_vec *vector, size_t vectorCount); + generic_io_vec *vector, size_t vectorCount, + bool physical); size_t _WriteIsochronousDescriptorChain( ohci_isochronous_td *topDescriptor, - generic_io_vec *vector, size_t vectorCount); + generic_io_vec *vector, size_t vectorCount, + bool physical); void _ReadIsochronousDescriptorChain( ohci_isochronous_td *topDescriptor, - generic_io_vec *vector, size_t vectorCount); + generic_io_vec *vector, size_t vectorCount, + bool physical); size_t _ReadActualLength( ohci_general_td *topDescriptor); diff --git a/src/add-ons/kernel/busses/usb/uhci.cpp b/src/add-ons/kernel/busses/usb/uhci.cpp index 527bb4f2f6..303cb86369 100644 --- a/src/add-ons/kernel/busses/usb/uhci.cpp +++ b/src/add-ons/kernel/busses/usb/uhci.cpp @@ -934,7 +934,7 @@ UHCI::CheckDebugTransfer(Transfer *transfer) size_t vectorCount = transfer->VectorCount(); ReadDescriptorChain(transferData->first_descriptor, - vector, vectorCount, &lastDataToggle); + vector, vectorCount, transfer->IsPhysical(), &lastDataToggle); } else { // read the actual length that was sent ReadActualLength(transferData->first_descriptor, &lastDataToggle); @@ -1094,7 +1094,7 @@ UHCI::SubmitRequest(Transfer *transfer) generic_io_vec vector; vector.base = (generic_addr_t)requestData; vector.length = sizeof(usb_request_data); - WriteDescriptorChain(setupDescriptor, &vector, 1); + WriteDescriptorChain(setupDescriptor, &vector, 1, false); statusDescriptor->status |= TD_CONTROL_IOC; statusDescriptor->token |= TD_TOKEN_DATA1; @@ -1116,7 +1116,7 @@ UHCI::SubmitRequest(Transfer *transfer) if (!directionIn) { WriteDescriptorChain(dataDescriptor, transfer->Vector(), - transfer->VectorCount()); + transfer->VectorCount(), transfer->IsPhysical()); } LinkDescriptors(setupDescriptor, dataDescriptor); @@ -1619,7 +1619,7 @@ UHCI::FinishTransfers() transfer->transfer->PrepareKernelAccess(); actualLength = ReadDescriptorChain( transfer->data_descriptor, - vector, vectorCount, + vector, vectorCount, transfer->transfer->IsPhysical(), &lastDataToggle); } else if (transfer->data_descriptor) { // read the actual length that was sent @@ -2104,7 +2104,7 @@ UHCI::CreateFilledTransfer(Transfer *transfer, uhci_td **_firstDescriptor, if (!directionIn) { WriteDescriptorChain(firstDescriptor, transfer->Vector(), - transfer->VectorCount()); + transfer->VectorCount(), transfer->IsPhysical()); } uhci_qh *transferQueue = CreateTransferQueue(firstDescriptor); @@ -2277,7 +2277,7 @@ UHCI::LinkDescriptors(uhci_td *first, uhci_td *second) size_t UHCI::WriteDescriptorChain(uhci_td *topDescriptor, generic_io_vec *vector, - size_t vectorCount) + size_t vectorCount, bool physical) { uhci_td *current = topDescriptor; size_t actualLength = 0; @@ -2296,8 +2296,10 @@ UHCI::WriteDescriptorChain(uhci_td *topDescriptor, generic_io_vec *vector, TRACE("copying %ld bytes to bufferOffset %ld from" " vectorOffset %ld at index %ld of %ld\n", length, bufferOffset, vectorOffset, vectorIndex, vectorCount); - memcpy((uint8 *)current->buffer_log + bufferOffset, - (uint8 *)vector[vectorIndex].base + vectorOffset, length); + status_t status = generic_memcpy( + (generic_addr_t)current->buffer_log + bufferOffset, false, + vector[vectorIndex].base + vectorOffset, physical, length); + ASSERT(status == B_OK); actualLength += length; vectorOffset += length; @@ -2332,7 +2334,7 @@ UHCI::WriteDescriptorChain(uhci_td *topDescriptor, generic_io_vec *vector, size_t UHCI::ReadDescriptorChain(uhci_td *topDescriptor, generic_io_vec *vector, - size_t vectorCount, uint8 *lastDataToggle) + size_t vectorCount, bool physical, uint8 *lastDataToggle) { uint8 dataToggle = 0; uhci_td *current = topDescriptor; @@ -2355,8 +2357,10 @@ UHCI::ReadDescriptorChain(uhci_td *topDescriptor, generic_io_vec *vector, TRACE("copying %ld bytes to vectorOffset %ld from" " bufferOffset %ld at index %ld of %ld\n", length, vectorOffset, bufferOffset, vectorIndex, vectorCount); - memcpy((uint8 *)vector[vectorIndex].base + vectorOffset, - (uint8 *)current->buffer_log + bufferOffset, length); + status_t status = generic_memcpy( + vector[vectorIndex].base + vectorOffset, physical, + (generic_addr_t)current->buffer_log + bufferOffset, false, length); + ASSERT(status == B_OK); actualLength += length; vectorOffset += length; diff --git a/src/add-ons/kernel/busses/usb/uhci.h b/src/add-ons/kernel/busses/usb/uhci.h index a8e79b2bca..61046567b9 100644 --- a/src/add-ons/kernel/busses/usb/uhci.h +++ b/src/add-ons/kernel/busses/usb/uhci.h @@ -184,9 +184,9 @@ static int32 FinishIsochronousThread(void *data); uhci_td *second); size_t WriteDescriptorChain(uhci_td *topDescriptor, - generic_io_vec *vector, size_t vectorCount); + generic_io_vec *vector, size_t vectorCount, bool physical); size_t ReadDescriptorChain(uhci_td *topDescriptor, - generic_io_vec *vector, size_t vectorCount, + generic_io_vec *vector, size_t vectorCount, bool physical, uint8 *lastDataToggle); size_t ReadActualLength(uhci_td *topDescriptor, uint8 *lastDataToggle); diff --git a/src/add-ons/kernel/busses/usb/xhci.cpp b/src/add-ons/kernel/busses/usb/xhci.cpp index 3e15fd7767..cd8a1b4754 100644 --- a/src/add-ons/kernel/busses/usb/xhci.cpp +++ b/src/add-ons/kernel/busses/usb/xhci.cpp @@ -877,8 +877,8 @@ XHCI::SubmitControlRequest(Transfer *transfer) if (!directionIn) { transfer->PrepareKernelAccess(); - memcpy(descriptor->buffers[0], - (uint8 *)transfer->Vector()[0].base, requestData->Length); + WriteDescriptor(descriptor, transfer->Vector(), + transfer->VectorCount(), transfer->IsPhysical()); } index++; @@ -1045,7 +1045,8 @@ XHCI::SubmitNormalRequest(Transfer *transfer) FreeDescriptor(td); return status; } - WriteDescriptor(td, transfer->Vector(), transfer->VectorCount()); + WriteDescriptor(td, transfer->Vector(), + transfer->VectorCount(), transfer->IsPhysical()); } td->transfer = transfer; @@ -1236,8 +1237,10 @@ XHCI::CheckDebugTransfer(Transfer *transfer) status_t status = (td->trb_completion_code == COMP_SUCCESS || td->trb_completion_code == COMP_SHORT_PACKET) ? B_OK : B_ERROR; - if (status == B_OK && directionIn) - ReadDescriptor(td, transfer->Vector(), transfer->VectorCount()); + if (status == B_OK && directionIn) { + ReadDescriptor(td, transfer->Vector(), transfer->VectorCount(), + transfer->IsPhysical()); + } FreeDescriptor(td); transfer->SetCallback(NULL, NULL); @@ -1427,7 +1430,7 @@ XHCI::FreeDescriptor(xhci_td *descriptor) size_t -XHCI::WriteDescriptor(xhci_td *descriptor, generic_io_vec *vector, size_t vectorCount) +XHCI::WriteDescriptor(xhci_td *descriptor, generic_io_vec *vector, size_t vectorCount, bool physical) { size_t written = 0; @@ -1437,9 +1440,11 @@ XHCI::WriteDescriptor(xhci_td *descriptor, generic_io_vec *vector, size_t vector while (length > 0 && bufIdx < descriptor->buffer_count) { size_t toCopy = min_c(length, descriptor->buffer_size - bufUsed); - memcpy((uint8 *)descriptor->buffers[bufIdx] + bufUsed, - (uint8 *)vector[vecIdx].base + (vector[vecIdx].length - length), + status_t status = generic_memcpy( + (generic_addr_t)descriptor->buffers[bufIdx] + bufUsed, false, + vector[vecIdx].base + (vector[vecIdx].length - length), physical, toCopy); + ASSERT(status == B_OK); written += toCopy; bufUsed += toCopy; @@ -1457,7 +1462,7 @@ XHCI::WriteDescriptor(xhci_td *descriptor, generic_io_vec *vector, size_t vector size_t -XHCI::ReadDescriptor(xhci_td *descriptor, generic_io_vec *vector, size_t vectorCount) +XHCI::ReadDescriptor(xhci_td *descriptor, generic_io_vec *vector, size_t vectorCount, bool physical) { size_t read = 0; @@ -1467,8 +1472,10 @@ XHCI::ReadDescriptor(xhci_td *descriptor, generic_io_vec *vector, size_t vectorC while (length > 0 && bufIdx < descriptor->buffer_count) { size_t toCopy = min_c(length, descriptor->buffer_size - bufUsed); - memcpy((uint8 *)vector[vecIdx].base + (vector[vecIdx].length - length), - (uint8 *)descriptor->buffers[bufIdx] + bufUsed, toCopy); + status_t status = generic_memcpy( + vector[vecIdx].base + (vector[vecIdx].length - length), physical, + (generic_addr_t)descriptor->buffers[bufIdx] + bufUsed, false, toCopy); + ASSERT(status == B_OK); read += toCopy; bufUsed += toCopy; @@ -3116,7 +3123,7 @@ XHCI::FinishTransfers() status_t status = transfer->PrepareKernelAccess(); if (status == B_OK) { ReadDescriptor(td, transfer->Vector(), - transfer->VectorCount()); + transfer->VectorCount(), transfer->IsPhysical()); } else { callbackStatus = status; } diff --git a/src/add-ons/kernel/busses/usb/xhci.h b/src/add-ons/kernel/busses/usb/xhci.h index f52f998687..2c9da35c5e 100644 --- a/src/add-ons/kernel/busses/usb/xhci.h +++ b/src/add-ons/kernel/busses/usb/xhci.h @@ -162,9 +162,9 @@ private: void FreeDescriptor(xhci_td *descriptor); size_t WriteDescriptor(xhci_td *descriptor, - generic_io_vec *vector, size_t vectorCount); + generic_io_vec *vector, size_t vectorCount, bool physical); size_t ReadDescriptor(xhci_td *descriptor, - generic_io_vec *vector, size_t vectorCount); + generic_io_vec *vector, size_t vectorCount, bool physical); status_t _LinkDescriptorForPipe(xhci_td *descriptor, xhci_endpoint *endpoint);