* Added necessary dummy descriptor to every endpoint created
* Implemented _RemoveTransferFromEndpoint * Reworked _AppendChainDescriptorsToEndpoint as now every endpoint has (must have) a dummy descriptor git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@23741 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -524,6 +524,8 @@ OHCI::_FinishTransfer()
|
|||||||
TRACE(("usb_ohci: transfer failed! ohci error code: %d\n",
|
TRACE(("usb_ohci: transfer failed! ohci error code: %d\n",
|
||||||
conditionCode));
|
conditionCode));
|
||||||
|
|
||||||
|
// Remove remaining descriptors from the same transfer
|
||||||
|
if (!current->is_last)
|
||||||
_RemoveTransferFromEndpoint(transfer);
|
_RemoveTransferFromEndpoint(transfer);
|
||||||
|
|
||||||
// TODO: Fix the following with the appropriate error
|
// TODO: Fix the following with the appropriate error
|
||||||
@@ -586,33 +588,25 @@ OHCI::_AppendChainDescriptorsToEndpoint(ohci_endpoint_descriptor *endpoint,
|
|||||||
|
|
||||||
// TODO: Lock on endpoint
|
// TODO: Lock on endpoint
|
||||||
ohci_general_td *head = (ohci_general_td *)endpoint->head_logical_descriptor;
|
ohci_general_td *head = (ohci_general_td *)endpoint->head_logical_descriptor;
|
||||||
if (head) {
|
|
||||||
// There is at least one descriptor to this endpoint
|
|
||||||
ohci_general_td *tail = (ohci_general_td *)endpoint->tail_logical_descriptor;
|
ohci_general_td *tail = (ohci_general_td *)endpoint->tail_logical_descriptor;
|
||||||
if (tail) {
|
if (head != tail) {
|
||||||
// There is more than one descriptor
|
// Find the last real descriptor
|
||||||
tail->next_logical_descriptor = first;
|
ohci_general_td *current = head;
|
||||||
tail->next_physical_descriptor = first->physical_address;
|
while (current->next_logical_descriptor != tail)
|
||||||
|
current = (ohci_general_td *)current->next_logical_descriptor;
|
||||||
|
// Append to current
|
||||||
|
current->next_logical_descriptor = first;
|
||||||
|
current->next_physical_descriptor = first->physical_address;
|
||||||
} else {
|
} else {
|
||||||
// There is only one descriptor to this endpoint
|
// Endpoint has only the dummy descriptor
|
||||||
head->next_logical_descriptor = first;
|
|
||||||
head->next_physical_descriptor = first->physical_address;
|
|
||||||
}
|
|
||||||
endpoint->tail_logical_descriptor = last;
|
|
||||||
endpoint->tail_physical_descriptor = last->physical_address;
|
|
||||||
} else {
|
|
||||||
// Endpoint is empty
|
|
||||||
endpoint->head_logical_descriptor = first;
|
endpoint->head_logical_descriptor = first;
|
||||||
endpoint->head_physical_descriptor = first->physical_address;
|
endpoint->head_physical_descriptor = first->physical_address;
|
||||||
// Update tail only if we are appending more than one descriptor
|
|
||||||
// otherwise the controller won't process the descriptor as
|
|
||||||
// head will be the same as tail.
|
|
||||||
if (first != last) {
|
|
||||||
endpoint->tail_logical_descriptor = last;
|
|
||||||
endpoint->tail_physical_descriptor = last->physical_address;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Make the last descriptor point to the dummy
|
||||||
|
last->next_logical_descriptor = tail;
|
||||||
|
last->next_physical_descriptor = tail->physical_address;
|
||||||
|
|
||||||
endpoint->flags &= ~OHCI_ENDPOINT_SKIP;
|
endpoint->flags &= ~OHCI_ENDPOINT_SKIP;
|
||||||
return B_OK;
|
return B_OK;
|
||||||
}
|
}
|
||||||
@@ -621,7 +615,17 @@ OHCI::_AppendChainDescriptorsToEndpoint(ohci_endpoint_descriptor *endpoint,
|
|||||||
void
|
void
|
||||||
OHCI::_RemoveTransferFromEndpoint(transfer_data *transfer)
|
OHCI::_RemoveTransferFromEndpoint(transfer_data *transfer)
|
||||||
{
|
{
|
||||||
// TODO
|
// TODO: Add lock for endpoint
|
||||||
|
ohci_endpoint_descriptor *endpoint = transfer->endpoint;
|
||||||
|
ohci_general_td *next = (ohci_general_td *)endpoint->head_logical_descriptor;
|
||||||
|
|
||||||
|
// Find the first descriptor of a different transfer.
|
||||||
|
// Worst scenario we get the dummy descriptor
|
||||||
|
while ((transfer_data *)next->transfer == transfer)
|
||||||
|
next = (ohci_general_td *)next->next_logical_descriptor;
|
||||||
|
// Update head
|
||||||
|
endpoint->head_logical_descriptor = next;
|
||||||
|
endpoint->head_physical_descriptor = next->physical_address;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -1357,6 +1361,22 @@ OHCI::_InsertEndpointForPipe(Pipe *pipe)
|
|||||||
return B_ERROR;
|
return B_ERROR;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Create (necessary) dummy descriptor
|
||||||
|
if (pipe->Type() & USB_OBJECT_ISO_PIPE) {
|
||||||
|
// TODO
|
||||||
|
} else {
|
||||||
|
ohci_general_td *dummy = _CreateGeneralDescriptor(0);
|
||||||
|
dummy->next_logical_descriptor = NULL;
|
||||||
|
dummy->next_physical_descriptor = NULL;
|
||||||
|
endpoint->head_logical_descriptor
|
||||||
|
= endpoint->tail_logical_descriptor
|
||||||
|
= dummy;
|
||||||
|
endpoint->head_physical_descriptor
|
||||||
|
= endpoint->tail_physical_descriptor
|
||||||
|
= dummy->physical_address;
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO: Change lock lo LockEndpoint()
|
||||||
Lock();
|
Lock();
|
||||||
pipe->SetControllerCookie((void *)endpoint);
|
pipe->SetControllerCookie((void *)endpoint);
|
||||||
endpoint->next_logical_endpoint = head->next_logical_endpoint;
|
endpoint->next_logical_endpoint = head->next_logical_endpoint;
|
||||||
|
|||||||
@@ -115,6 +115,8 @@ static int32 _FinishThread(void *data);
|
|||||||
ohci_endpoint_descriptor *endpoint,
|
ohci_endpoint_descriptor *endpoint,
|
||||||
ohci_general_td *first,
|
ohci_general_td *first,
|
||||||
ohci_general_td *last);
|
ohci_general_td *last);
|
||||||
|
void _RemoveTransferFromEndpoint(
|
||||||
|
transfer_data *);
|
||||||
|
|
||||||
// Endpoint related methods
|
// Endpoint related methods
|
||||||
ohci_endpoint_descriptor *_AllocateEndpoint();
|
ohci_endpoint_descriptor *_AllocateEndpoint();
|
||||||
@@ -122,8 +124,6 @@ static int32 _FinishThread(void *data);
|
|||||||
ohci_endpoint_descriptor *endpoint);
|
ohci_endpoint_descriptor *endpoint);
|
||||||
status_t _InsertEndpointForPipe(Pipe *pipe);
|
status_t _InsertEndpointForPipe(Pipe *pipe);
|
||||||
status_t _RemoveEndpointForPipe(Pipe *pipe);
|
status_t _RemoveEndpointForPipe(Pipe *pipe);
|
||||||
void _RemoveTransferFromEndpoint(
|
|
||||||
transfer_data *transfer);
|
|
||||||
ohci_endpoint_descriptor *_FindInterruptEndpoint(uint8 interval);
|
ohci_endpoint_descriptor *_FindInterruptEndpoint(uint8 interval);
|
||||||
|
|
||||||
// Transfer descriptor related methods
|
// Transfer descriptor related methods
|
||||||
|
|||||||
Reference in New Issue
Block a user