aboutsummaryrefslogtreecommitdiffstats
path: root/LUFA/Drivers/USB
diff options
context:
space:
mode:
authorDean Camera <dean@fourwalledcubicle.com>2012-04-14 14:41:17 +0000
committerDean Camera <dean@fourwalledcubicle.com>2012-04-14 14:41:17 +0000
commit47f6a35013b2c6a370e5dce29aa6da3a96844695 (patch)
tree3f5842347a696c92beb74bc255c9489e6c38f49d /LUFA/Drivers/USB
parente8570c4a37e41117e3fd1e989e0b41f1e9608f3c (diff)
downloadlufa-47f6a35013b2c6a370e5dce29aa6da3a96844695.tar.gz
lufa-47f6a35013b2c6a370e5dce29aa6da3a96844695.tar.bz2
lufa-47f6a35013b2c6a370e5dce29aa6da3a96844695.zip
Reintegrate the FullEPAddresses development branch into trunk.
Diffstat (limited to 'LUFA/Drivers/USB')
-rw-r--r--LUFA/Drivers/USB/Class/Device/AudioClassDevice.c57
-rw-r--r--LUFA/Drivers/USB/Class/Device/AudioClassDevice.h25
-rw-r--r--LUFA/Drivers/USB/Class/Device/CDCClassDevice.c61
-rw-r--r--LUFA/Drivers/USB/Class/Device/CDCClassDevice.h18
-rw-r--r--LUFA/Drivers/USB/Class/Device/HIDClassDevice.c14
-rw-r--r--LUFA/Drivers/USB/Class/Device/HIDClassDevice.h4
-rw-r--r--LUFA/Drivers/USB/Class/Device/MIDIClassDevice.c46
-rw-r--r--LUFA/Drivers/USB/Class/Device/MIDIClassDevice.h9
-rw-r--r--LUFA/Drivers/USB/Class/Device/MassStorageClassDevice.c62
-rw-r--r--LUFA/Drivers/USB/Class/Device/MassStorageClassDevice.h9
-rw-r--r--LUFA/Drivers/USB/Class/Device/RNDISClassDevice.c59
-rw-r--r--LUFA/Drivers/USB/Class/Device/RNDISClassDevice.h14
-rw-r--r--LUFA/Drivers/USB/Class/Host/AndroidAccessoryClassHost.c64
-rw-r--r--LUFA/Drivers/USB/Class/Host/AndroidAccessoryClassHost.h10
-rw-r--r--LUFA/Drivers/USB/Class/Host/AudioClassHost.c58
-rw-r--r--LUFA/Drivers/USB/Class/Host/AudioClassHost.h17
-rw-r--r--LUFA/Drivers/USB/Class/Host/CDCClassHost.c90
-rw-r--r--LUFA/Drivers/USB/Class/Host/CDCClassHost.h15
-rw-r--r--LUFA/Drivers/USB/Class/Host/HIDClassHost.c68
-rw-r--r--LUFA/Drivers/USB/Class/Host/HIDClassHost.h10
-rw-r--r--LUFA/Drivers/USB/Class/Host/MIDIClassHost.c58
-rw-r--r--LUFA/Drivers/USB/Class/Host/MIDIClassHost.h10
-rw-r--r--LUFA/Drivers/USB/Class/Host/MassStorageClassHost.c74
-rw-r--r--LUFA/Drivers/USB/Class/Host/MassStorageClassHost.h10
-rw-r--r--LUFA/Drivers/USB/Class/Host/PrinterClassHost.c64
-rw-r--r--LUFA/Drivers/USB/Class/Host/PrinterClassHost.h10
-rw-r--r--LUFA/Drivers/USB/Class/Host/RNDISClassHost.c80
-rw-r--r--LUFA/Drivers/USB/Class/Host/RNDISClassHost.h15
-rw-r--r--LUFA/Drivers/USB/Class/Host/StillImageClassHost.c92
-rw-r--r--LUFA/Drivers/USB/Class/Host/StillImageClassHost.h15
-rw-r--r--LUFA/Drivers/USB/Core/AVR8/Endpoint_AVR8.c15
-rw-r--r--LUFA/Drivers/USB/Core/AVR8/Endpoint_AVR8.h175
-rw-r--r--LUFA/Drivers/USB/Core/AVR8/Host_AVR8.c8
-rw-r--r--LUFA/Drivers/USB/Core/AVR8/Pipe_AVR8.c34
-rw-r--r--LUFA/Drivers/USB/Core/AVR8/Pipe_AVR8.h116
-rw-r--r--LUFA/Drivers/USB/Core/AVR8/USBController_AVR8.c3
-rw-r--r--LUFA/Drivers/USB/Core/AVR8/USBInterrupt_AVR8.c3
-rw-r--r--LUFA/Drivers/USB/Core/Endpoint.h12
-rw-r--r--LUFA/Drivers/USB/Core/Pipe.h18
-rw-r--r--LUFA/Drivers/USB/Core/UC3/Endpoint_UC3.c17
-rw-r--r--LUFA/Drivers/USB/Core/UC3/Endpoint_UC3.h205
-rw-r--r--LUFA/Drivers/USB/Core/UC3/Host_UC3.c8
-rw-r--r--LUFA/Drivers/USB/Core/UC3/Pipe_UC3.c34
-rw-r--r--LUFA/Drivers/USB/Core/UC3/Pipe_UC3.h124
-rw-r--r--LUFA/Drivers/USB/Core/UC3/USBController_UC3.c3
-rw-r--r--LUFA/Drivers/USB/Core/UC3/USBInterrupt_UC3.c3
-rw-r--r--LUFA/Drivers/USB/Core/USBController.h18
-rw-r--r--LUFA/Drivers/USB/Core/USBMode.h17
-rw-r--r--LUFA/Drivers/USB/Core/XMEGA/Device_XMEGA.h2
-rw-r--r--LUFA/Drivers/USB/Core/XMEGA/Endpoint_XMEGA.c30
-rw-r--r--LUFA/Drivers/USB/Core/XMEGA/Endpoint_XMEGA.h182
-rw-r--r--LUFA/Drivers/USB/Core/XMEGA/USBController_XMEGA.c13
-rw-r--r--LUFA/Drivers/USB/Core/XMEGA/USBController_XMEGA.h2
-rw-r--r--LUFA/Drivers/USB/Core/XMEGA/USBInterrupt_XMEGA.c3
-rw-r--r--LUFA/Drivers/USB/USB.h26
55 files changed, 823 insertions, 1386 deletions
diff --git a/LUFA/Drivers/USB/Class/Device/AudioClassDevice.c b/LUFA/Drivers/USB/Class/Device/AudioClassDevice.c
index 15fcd588d..ad79e9b2b 100644
--- a/LUFA/Drivers/USB/Class/Device/AudioClassDevice.c
+++ b/LUFA/Drivers/USB/Class/Device/AudioClassDevice.c
@@ -48,15 +48,16 @@ void Audio_Device_ProcessControlRequest(USB_ClassInfo_Audio_Device_t* const Audi
if ((InterfaceIndex != AudioInterfaceInfo->Config.ControlInterfaceNumber) &&
(InterfaceIndex != AudioInterfaceInfo->Config.StreamingInterfaceNumber))
-
- return;
+ {
+ return;
+ }
}
else if ((USB_ControlRequest.bmRequestType & CONTROL_REQTYPE_RECIPIENT) == REQREC_ENDPOINT)
{
- uint8_t EndpointIndex = (USB_ControlRequest.wIndex & 0xFF);
+ uint8_t EndpointAddress = (USB_ControlRequest.wIndex & 0xFF);
- if ((EndpointIndex != (ENDPOINT_DIR_IN | AudioInterfaceInfo->Config.DataINEndpointNumber)) &&
- (EndpointIndex != (ENDPOINT_DIR_OUT | AudioInterfaceInfo->Config.DataOUTEndpointNumber)))
+ if ((EndpointAddress != AudioInterfaceInfo->Config.DataINEndpoint.Address) &&
+ (EndpointAddress != AudioInterfaceInfo->Config.DataOUTEndpoint.Address))
{
return;
}
@@ -88,7 +89,7 @@ void Audio_Device_ProcessControlRequest(USB_ClassInfo_Audio_Device_t* const Audi
case AUDIO_REQ_SetMinimum:
case AUDIO_REQ_SetMaximum:
case AUDIO_REQ_SetResolution:
- if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_ENDPOINT))
+ if ((USB_ControlRequest.bmRequestType & CONTROL_REQTYPE_RECIPIENT) == REQREC_ENDPOINT)
{
uint8_t EndpointProperty = USB_ControlRequest.bRequest;
uint8_t EndpointAddress = (uint8_t)USB_ControlRequest.wIndex;
@@ -108,7 +109,7 @@ void Audio_Device_ProcessControlRequest(USB_ClassInfo_Audio_Device_t* const Audi
EndpointControl, &ValueLength, Value);
}
}
- else if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+ else if ((USB_ControlRequest.bmRequestType & CONTROL_REQTYPE_RECIPIENT) == REQREC_INTERFACE)
{
uint8_t Property = USB_ControlRequest.bRequest;
uint8_t Entity = (USB_ControlRequest.wIndex >> 8);
@@ -134,7 +135,7 @@ void Audio_Device_ProcessControlRequest(USB_ClassInfo_Audio_Device_t* const Audi
case AUDIO_REQ_GetMinimum:
case AUDIO_REQ_GetMaximum:
case AUDIO_REQ_GetResolution:
- if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_ENDPOINT))
+ if ((USB_ControlRequest.bmRequestType & CONTROL_REQTYPE_RECIPIENT) == REQREC_ENDPOINT)
{
uint8_t EndpointProperty = USB_ControlRequest.bRequest;
uint8_t EndpointAddress = (uint8_t)USB_ControlRequest.wIndex;
@@ -150,7 +151,7 @@ void Audio_Device_ProcessControlRequest(USB_ClassInfo_Audio_Device_t* const Audi
Endpoint_ClearOUT();
}
}
- else if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+ else if ((USB_ControlRequest.bmRequestType & CONTROL_REQTYPE_RECIPIENT) == REQREC_INTERFACE)
{
uint8_t Property = USB_ControlRequest.bRequest;
uint8_t Entity = (USB_ControlRequest.wIndex >> 8);
@@ -174,39 +175,15 @@ void Audio_Device_ProcessControlRequest(USB_ClassInfo_Audio_Device_t* const Audi
bool Audio_Device_ConfigureEndpoints(USB_ClassInfo_Audio_Device_t* const AudioInterfaceInfo)
{
memset(&AudioInterfaceInfo->State, 0x00, sizeof(AudioInterfaceInfo->State));
+
+ AudioInterfaceInfo->Config.DataINEndpoint.Type = EP_TYPE_ISOCHRONOUS;
+ AudioInterfaceInfo->Config.DataOUTEndpoint.Type = EP_TYPE_ISOCHRONOUS;
- for (uint8_t EndpointNum = 1; EndpointNum < ENDPOINT_TOTAL_ENDPOINTS; EndpointNum++)
- {
- uint16_t Size;
- uint8_t Type;
- uint8_t Direction;
- bool DoubleBanked;
+ if (!(Endpoint_ConfigureEndpointTable(&AudioInterfaceInfo->Config.DataINEndpoint, 1)))
+ return false;
- if (EndpointNum == AudioInterfaceInfo->Config.DataINEndpointNumber)
- {
- Size = AudioInterfaceInfo->Config.DataINEndpointSize;
- Direction = ENDPOINT_DIR_IN;
- Type = EP_TYPE_ISOCHRONOUS;
- DoubleBanked = true;
- }
- else if (EndpointNum == AudioInterfaceInfo->Config.DataOUTEndpointNumber)
- {
- Size = AudioInterfaceInfo->Config.DataOUTEndpointSize;
- Direction = ENDPOINT_DIR_OUT;
- Type = EP_TYPE_ISOCHRONOUS;
- DoubleBanked = true;
- }
- else
- {
- continue;
- }
-
- if (!(Endpoint_ConfigureEndpoint(EndpointNum, Type, Direction, Size,
- DoubleBanked ? ENDPOINT_BANK_DOUBLE : ENDPOINT_BANK_SINGLE)))
- {
- return false;
- }
- }
+ if (!(Endpoint_ConfigureEndpointTable(&AudioInterfaceInfo->Config.DataOUTEndpoint, 1)))
+ return false;
return true;
}
diff --git a/LUFA/Drivers/USB/Class/Device/AudioClassDevice.h b/LUFA/Drivers/USB/Class/Device/AudioClassDevice.h
index 239126607..a8bfc7833 100644
--- a/LUFA/Drivers/USB/Class/Device/AudioClassDevice.h
+++ b/LUFA/Drivers/USB/Class/Device/AudioClassDevice.h
@@ -86,19 +86,8 @@
* structure controls.
*/
- uint8_t DataINEndpointNumber; /**< Endpoint number of the incoming Audio Streaming data, if available
- * (zero if unused).
- */
- uint16_t DataINEndpointSize; /**< Size in bytes of the incoming Audio Streaming data endpoint, if available
- * (zero if unused).
- */
-
- uint8_t DataOUTEndpointNumber; /**< Endpoint number of the outgoing Audio Streaming data, if available
- * (zero if unused).
- */
- uint16_t DataOUTEndpointSize; /**< Size in bytes of the outgoing Audio Streaming data endpoint, if available
- * (zero if unused).
- */
+ USB_Endpoint_Table_t DataINEndpoint; /**< Data IN endpoint configuration table. */
+ USB_Endpoint_Table_t DataOUTEndpoint; /**< Data OUT endpoint configuration table. */
} Config; /**< Config data for the USB class interface within the device. All elements in this section
* <b>must</b> be set or the interface will fail to enumerate and operate correctly.
*/
@@ -226,7 +215,7 @@
if ((USB_DeviceState != DEVICE_STATE_Configured) || !(AudioInterfaceInfo->State.InterfaceEnabled))
return false;
- Endpoint_SelectEndpoint(AudioInterfaceInfo->Config.DataOUTEndpointNumber);
+ Endpoint_SelectEndpoint(AudioInterfaceInfo->Config.DataOUTEndpoint.Address);
return Endpoint_IsOUTReceived();
}
@@ -247,7 +236,7 @@
if ((USB_DeviceState != DEVICE_STATE_Configured) || !(AudioInterfaceInfo->State.InterfaceEnabled))
return false;
- Endpoint_SelectEndpoint(AudioInterfaceInfo->Config.DataINEndpointNumber);
+ Endpoint_SelectEndpoint(AudioInterfaceInfo->Config.DataINEndpoint.Address);
return Endpoint_IsINReady();
}
@@ -341,7 +330,7 @@
{
Endpoint_Write_8(Sample);
- if (Endpoint_BytesInEndpoint() == AudioInterfaceInfo->Config.DataINEndpointSize)
+ if (Endpoint_BytesInEndpoint() == AudioInterfaceInfo->Config.DataINEndpoint.Size)
Endpoint_ClearIN();
}
@@ -360,7 +349,7 @@
{
Endpoint_Write_16_LE(Sample);
- if (Endpoint_BytesInEndpoint() == AudioInterfaceInfo->Config.DataINEndpointSize)
+ if (Endpoint_BytesInEndpoint() == AudioInterfaceInfo->Config.DataINEndpoint.Size)
Endpoint_ClearIN();
}
@@ -380,7 +369,7 @@
Endpoint_Write_16_LE(Sample);
Endpoint_Write_8(Sample >> 16);
- if (Endpoint_BytesInEndpoint() == AudioInterfaceInfo->Config.DataINEndpointSize)
+ if (Endpoint_BytesInEndpoint() == AudioInterfaceInfo->Config.DataINEndpoint.Size)
Endpoint_ClearIN();
}
diff --git a/LUFA/Drivers/USB/Class/Device/CDCClassDevice.c b/LUFA/Drivers/USB/Class/Device/CDCClassDevice.c
index 5b5343860..a16949cfd 100644
--- a/LUFA/Drivers/USB/Class/Device/CDCClassDevice.c
+++ b/LUFA/Drivers/USB/Class/Device/CDCClassDevice.c
@@ -112,45 +112,18 @@ bool CDC_Device_ConfigureEndpoints(USB_ClassInfo_CDC_Device_t* const CDCInterfac
{
memset(&CDCInterfaceInfo->State, 0x00, sizeof(CDCInterfaceInfo->State));
- for (uint8_t EndpointNum = 1; EndpointNum < ENDPOINT_TOTAL_ENDPOINTS; EndpointNum++)
- {
- uint16_t Size;
- uint8_t Type;
- uint8_t Direction;
- bool DoubleBanked;
+ CDCInterfaceInfo->Config.DataINEndpoint.Type = EP_TYPE_BULK;
+ CDCInterfaceInfo->Config.DataOUTEndpoint.Type = EP_TYPE_BULK;
+ CDCInterfaceInfo->Config.NotificationEndpoint.Type = EP_TYPE_INTERRUPT;
- if (EndpointNum == CDCInterfaceInfo->Config.DataINEndpointNumber)
- {
- Size = CDCInterfaceInfo->Config.DataINEndpointSize;
- Direction = ENDPOINT_DIR_IN;
- Type = EP_TYPE_BULK;
- DoubleBanked = CDCInterfaceInfo->Config.DataINEndpointDoubleBank;
- }
- else if (EndpointNum == CDCInterfaceInfo->Config.DataOUTEndpointNumber)
- {
- Size = CDCInterfaceInfo->Config.DataOUTEndpointSize;
- Direction = ENDPOINT_DIR_OUT;
- Type = EP_TYPE_BULK;
- DoubleBanked = CDCInterfaceInfo->Config.DataOUTEndpointDoubleBank;
- }
- else if (EndpointNum == CDCInterfaceInfo->Config.NotificationEndpointNumber)
- {
- Size = CDCInterfaceInfo->Config.NotificationEndpointSize;
- Direction = ENDPOINT_DIR_IN;
- Type = EP_TYPE_INTERRUPT;
- DoubleBanked = CDCInterfaceInfo->Config.NotificationEndpointDoubleBank;
- }
- else
- {
- continue;
- }
+ if (!(Endpoint_ConfigureEndpointTable(&CDCInterfaceInfo->Config.DataINEndpoint, 1)))
+ return false;
- if (!(Endpoint_ConfigureEndpoint(EndpointNum, Type, Direction, Size,
- DoubleBanked ? ENDPOINT_BANK_DOUBLE : ENDPOINT_BANK_SINGLE)))
- {
- return false;
- }
- }
+ if (!(Endpoint_ConfigureEndpointTable(&CDCInterfaceInfo->Config.DataOUTEndpoint, 1)))
+ return false;
+
+ if (!(Endpoint_ConfigureEndpointTable(&CDCInterfaceInfo->Config.NotificationEndpoint, 1)))
+ return false;
return true;
}
@@ -171,7 +144,7 @@ uint8_t CDC_Device_SendString(USB_ClassInfo_CDC_Device_t* const CDCInterfaceInfo
if ((USB_DeviceState != DEVICE_STATE_Configured) || !(CDCInterfaceInfo->State.LineEncoding.BaudRateBPS))
return ENDPOINT_RWSTREAM_DeviceDisconnected;
- Endpoint_SelectEndpoint(CDCInterfaceInfo->Config.DataINEndpointNumber);
+ Endpoint_SelectEndpoint(CDCInterfaceInfo->Config.DataINEndpoint.Address);
return Endpoint_Write_Stream_LE(String, strlen(String), NULL);
}
@@ -182,7 +155,7 @@ uint8_t CDC_Device_SendData(USB_ClassInfo_CDC_Device_t* const CDCInterfaceInfo,
if ((USB_DeviceState != DEVICE_STATE_Configured) || !(CDCInterfaceInfo->State.LineEncoding.BaudRateBPS))
return ENDPOINT_RWSTREAM_DeviceDisconnected;
- Endpoint_SelectEndpoint(CDCInterfaceInfo->Config.DataINEndpointNumber);
+ Endpoint_SelectEndpoint(CDCInterfaceInfo->Config.DataINEndpoint.Address);
return Endpoint_Write_Stream_LE(Buffer, Length, NULL);
}
@@ -192,7 +165,7 @@ uint8_t CDC_Device_SendByte(USB_ClassInfo_CDC_Device_t* const CDCInterfaceInfo,
if ((USB_DeviceState != DEVICE_STATE_Configured) || !(CDCInterfaceInfo->State.LineEncoding.BaudRateBPS))
return ENDPOINT_RWSTREAM_DeviceDisconnected;
- Endpoint_SelectEndpoint(CDCInterfaceInfo->Config.DataINEndpointNumber);
+ Endpoint_SelectEndpoint(CDCInterfaceInfo->Config.DataINEndpoint.Address);
if (!(Endpoint_IsReadWriteAllowed()))
{
@@ -215,7 +188,7 @@ uint8_t CDC_Device_Flush(USB_ClassInfo_CDC_Device_t* const CDCInterfaceInfo)
uint8_t ErrorCode;
- Endpoint_SelectEndpoint(CDCInterfaceInfo->Config.DataINEndpointNumber);
+ Endpoint_SelectEndpoint(CDCInterfaceInfo->Config.DataINEndpoint.Address);
if (!(Endpoint_BytesInEndpoint()))
return ENDPOINT_READYWAIT_NoError;
@@ -240,7 +213,7 @@ uint16_t CDC_Device_BytesReceived(USB_ClassInfo_CDC_Device_t* const CDCInterface
if ((USB_DeviceState != DEVICE_STATE_Configured) || !(CDCInterfaceInfo->State.LineEncoding.BaudRateBPS))
return 0;
- Endpoint_SelectEndpoint(CDCInterfaceInfo->Config.DataOUTEndpointNumber);
+ Endpoint_SelectEndpoint(CDCInterfaceInfo->Config.DataOUTEndpoint.Address);
if (Endpoint_IsOUTReceived())
{
@@ -267,7 +240,7 @@ int16_t CDC_Device_ReceiveByte(USB_ClassInfo_CDC_Device_t* const CDCInterfaceInf
int16_t ReceivedByte = -1;
- Endpoint_SelectEndpoint(CDCInterfaceInfo->Config.DataOUTEndpointNumber);
+ Endpoint_SelectEndpoint(CDCInterfaceInfo->Config.DataOUTEndpoint.Address);
if (Endpoint_IsOUTReceived())
{
@@ -286,7 +259,7 @@ void CDC_Device_SendControlLineStateChange(USB_ClassInfo_CDC_Device_t* const CDC
if ((USB_DeviceState != DEVICE_STATE_Configured) || !(CDCInterfaceInfo->State.LineEncoding.BaudRateBPS))
return;
- Endpoint_SelectEndpoint(CDCInterfaceInfo->Config.NotificationEndpointNumber);
+ Endpoint_SelectEndpoint(CDCInterfaceInfo->Config.NotificationEndpoint.Address);
USB_Request_Header_t Notification = (USB_Request_Header_t)
{
diff --git a/LUFA/Drivers/USB/Class/Device/CDCClassDevice.h b/LUFA/Drivers/USB/Class/Device/CDCClassDevice.h
index cc0dd1b15..508c234d7 100644
--- a/LUFA/Drivers/USB/Class/Device/CDCClassDevice.h
+++ b/LUFA/Drivers/USB/Class/Device/CDCClassDevice.h
@@ -99,19 +99,11 @@
{
struct
{
- uint8_t ControlInterfaceNumber; /**< Interface number of the CDC control interface within the device. */
-
- uint8_t DataINEndpointNumber; /**< Endpoint number of the CDC interface's IN data endpoint. */
- uint16_t DataINEndpointSize; /**< Size in bytes of the CDC interface's IN data endpoint. */
- bool DataINEndpointDoubleBank; /**< Indicates if the CDC interface's IN data endpoint should use double banking. */
-
- uint8_t DataOUTEndpointNumber; /**< Endpoint number of the CDC interface's OUT data endpoint. */
- uint16_t DataOUTEndpointSize; /**< Size in bytes of the CDC interface's OUT data endpoint. */
- bool DataOUTEndpointDoubleBank; /**< Indicates if the CDC interface's OUT data endpoint should use double banking. */
-
- uint8_t NotificationEndpointNumber; /**< Endpoint number of the CDC interface's IN notification endpoint, if used. */
- uint16_t NotificationEndpointSize; /**< Size in bytes of the CDC interface's IN notification endpoint, if used. */
- bool NotificationEndpointDoubleBank; /**< Indicates if the CDC interface's notification endpoint should use double banking. */
+ uint8_t ControlInterfaceNumber; /**< Interface number of the CDC control interface within the device. */
+
+ USB_Endpoint_Table_t DataINEndpoint; /**< Data IN endpoint configuration table. */
+ USB_Endpoint_Table_t DataOUTEndpoint; /**< Data OUT endpoint configuration table. */
+ USB_Endpoint_Table_t NotificationEndpoint; /**< Notification IN Endpoint configuration table. */
} Config; /**< Config data for the USB class interface within the device. All elements in this section
* <b>must</b> be set or the interface will fail to enumerate and operate correctly.
*/
diff --git a/LUFA/Drivers/USB/Class/Device/HIDClassDevice.c b/LUFA/Drivers/USB/Class/Device/HIDClassDevice.c
index 5c8d878e7..e4b565327 100644
--- a/LUFA/Drivers/USB/Class/Device/HIDClassDevice.c
+++ b/LUFA/Drivers/USB/Class/Device/HIDClassDevice.c
@@ -141,13 +141,11 @@ bool HID_Device_ConfigureEndpoints(USB_ClassInfo_HID_Device_t* const HIDInterfac
HIDInterfaceInfo->State.UsingReportProtocol = true;
HIDInterfaceInfo->State.IdleCount = 500;
- if (!(Endpoint_ConfigureEndpoint(HIDInterfaceInfo->Config.ReportINEndpointNumber, EP_TYPE_INTERRUPT,
- ENDPOINT_DIR_IN, HIDInterfaceInfo->Config.ReportINEndpointSize,
- HIDInterfaceInfo->Config.ReportINEndpointDoubleBank ? ENDPOINT_BANK_DOUBLE : ENDPOINT_BANK_SINGLE)))
- {
- return false;
- }
+ HIDInterfaceInfo->Config.ReportINEndpoint.Type = EP_TYPE_INTERRUPT;
+ if (!(Endpoint_ConfigureEndpointTable(&HIDInterfaceInfo->Config.ReportINEndpoint, 1)))
+ return false;
+
return true;
}
@@ -159,7 +157,7 @@ void HID_Device_USBTask(USB_ClassInfo_HID_Device_t* const HIDInterfaceInfo)
if (HIDInterfaceInfo->State.PrevFrameNum == USB_Device_GetFrameNumber())
return;
- Endpoint_SelectEndpoint(HIDInterfaceInfo->Config.ReportINEndpointNumber);
+ Endpoint_SelectEndpoint(HIDInterfaceInfo->Config.ReportINEndpoint.Address);
if (Endpoint_IsReadWriteAllowed())
{
@@ -184,7 +182,7 @@ void HID_Device_USBTask(USB_ClassInfo_HID_Device_t* const HIDInterfaceInfo)
{
HIDInterfaceInfo->State.IdleMSRemaining = HIDInterfaceInfo->State.IdleCount;
- Endpoint_SelectEndpoint(HIDInterfaceInfo->Config.ReportINEndpointNumber);
+ Endpoint_SelectEndpoint(HIDInterfaceInfo->Config.ReportINEndpoint.Address);
if (ReportID)
Endpoint_Write_8(ReportID);
diff --git a/LUFA/Drivers/USB/Class/Device/HIDClassDevice.h b/LUFA/Drivers/USB/Class/Device/HIDClassDevice.h
index a6361c6b0..e358dec75 100644
--- a/LUFA/Drivers/USB/Class/Device/HIDClassDevice.h
+++ b/LUFA/Drivers/USB/Class/Device/HIDClassDevice.h
@@ -85,9 +85,7 @@
{
uint8_t InterfaceNumber; /**< Interface number of the HID interface within the device. */
- uint8_t ReportINEndpointNumber; /**< Endpoint number of the HID interface's IN report endpoint. */
- uint16_t ReportINEndpointSize; /**< Size in bytes of the HID interface's IN report endpoint. */
- bool ReportINEndpointDoubleBank; /**< Indicates if the HID interface's IN report endpoint should use double banking. */
+ USB_Endpoint_Table_t ReportINEndpoint; /**< Data IN HID report endpoint configuration table. */
void* PrevReportINBuffer; /**< Pointer to a buffer where the previously created HID input report can be
* stored by the driver, for comparison purposes to detect report changes that
diff --git a/LUFA/Drivers/USB/Class/Device/MIDIClassDevice.c b/LUFA/Drivers/USB/Class/Device/MIDIClassDevice.c
index 9f0506e56..c9553a413 100644
--- a/LUFA/Drivers/USB/Class/Device/MIDIClassDevice.c
+++ b/LUFA/Drivers/USB/Class/Device/MIDIClassDevice.c
@@ -41,38 +41,14 @@ bool MIDI_Device_ConfigureEndpoints(USB_ClassInfo_MIDI_Device_t* const MIDIInter
{
memset(&MIDIInterfaceInfo->State, 0x00, sizeof(MIDIInterfaceInfo->State));
- for (uint8_t EndpointNum = 1; EndpointNum < ENDPOINT_TOTAL_ENDPOINTS; EndpointNum++)
- {
- uint16_t Size;
- uint8_t Type;
- uint8_t Direction;
- bool DoubleBanked;
-
- if (EndpointNum == MIDIInterfaceInfo->Config.DataINEndpointNumber)
- {
- Size = MIDIInterfaceInfo->Config.DataINEndpointSize;
- Direction = ENDPOINT_DIR_IN;
- Type = EP_TYPE_BULK;
- DoubleBanked = MIDIInterfaceInfo->Config.DataINEndpointDoubleBank;
- }
- else if (EndpointNum == MIDIInterfaceInfo->Config.DataOUTEndpointNumber)
- {
- Size = MIDIInterfaceInfo->Config.DataOUTEndpointSize;
- Direction = ENDPOINT_DIR_OUT;
- Type = EP_TYPE_BULK;
- DoubleBanked = MIDIInterfaceInfo->Config.DataOUTEndpointDoubleBank;
- }
- else
- {
- continue;
- }
-
- if (!(Endpoint_ConfigureEndpoint(EndpointNum, Type, Direction, Size,
- DoubleBanked ? ENDPOINT_BANK_DOUBLE : ENDPOINT_BANK_SINGLE)))
- {
- return false;
- }
- }
+ MIDIInterfaceInfo->Config.DataINEndpoint.Type = EP_TYPE_BULK;
+ MIDIInterfaceInfo->Config.DataOUTEndpoint.Type = EP_TYPE_BULK;
+
+ if (!(Endpoint_ConfigureEndpointTable(&MIDIInterfaceInfo->Config.DataINEndpoint, 1)))
+ return false;
+
+ if (!(Endpoint_ConfigureEndpointTable(&MIDIInterfaceInfo->Config.DataOUTEndpoint, 1)))
+ return false;
return true;
}
@@ -95,7 +71,7 @@ uint8_t MIDI_Device_SendEventPacket(USB_ClassInfo_MIDI_Device_t* const MIDIInter
uint8_t ErrorCode;
- Endpoint_SelectEndpoint(MIDIInterfaceInfo->Config.DataINEndpointNumber);
+ Endpoint_SelectEndpoint(MIDIInterfaceInfo->Config.DataINEndpoint.Address);
if ((ErrorCode = Endpoint_Write_Stream_LE(Event, sizeof(MIDI_EventPacket_t), NULL)) != ENDPOINT_RWSTREAM_NoError)
return ErrorCode;
@@ -113,7 +89,7 @@ uint8_t MIDI_Device_Flush(USB_ClassInfo_MIDI_Device_t* const MIDIInterfaceInfo)
uint8_t ErrorCode;
- Endpoint_SelectEndpoint(MIDIInterfaceInfo->Config.DataINEndpointNumber);
+ Endpoint_SelectEndpoint(MIDIInterfaceInfo->Config.DataINEndpoint.Address);
if (Endpoint_BytesInEndpoint())
{
@@ -132,7 +108,7 @@ bool MIDI_Device_ReceiveEventPacket(USB_ClassInfo_MIDI_Device_t* const MIDIInter
if (USB_DeviceState != DEVICE_STATE_Configured)
return false;
- Endpoint_SelectEndpoint(MIDIInterfaceInfo->Config.DataOUTEndpointNumber);
+ Endpoint_SelectEndpoint(MIDIInterfaceInfo->Config.DataOUTEndpoint.Address);
if (!(Endpoint_IsReadWriteAllowed()))
return false;
diff --git a/LUFA/Drivers/USB/Class/Device/MIDIClassDevice.h b/LUFA/Drivers/USB/Class/Device/MIDIClassDevice.h
index 4fe49af1f..2703600ea 100644
--- a/LUFA/Drivers/USB/Class/Device/MIDIClassDevice.h
+++ b/LUFA/Drivers/USB/Class/Device/MIDIClassDevice.h
@@ -81,13 +81,8 @@
{
uint8_t StreamingInterfaceNumber; /**< Index of the Audio Streaming interface within the device this structure controls. */
- uint8_t DataINEndpointNumber; /**< Endpoint number of the incoming MIDI IN data, if available (zero if unused). */
- uint16_t DataINEndpointSize; /**< Size in bytes of the incoming MIDI IN data endpoint, if available (zero if unused). */
- bool DataINEndpointDoubleBank; /**< Indicates if the MIDI interface's IN data endpoint should use double banking. */
-
- uint8_t DataOUTEndpointNumber; /**< Endpoint number of the outgoing MIDI OUT data, if available (zero if unused). */
- uint16_t DataOUTEndpointSize; /**< Size in bytes of the outgoing MIDI OUT data endpoint, if available (zero if unused). */
- bool DataOUTEndpointDoubleBank; /**< Indicates if the MIDI interface's OUT data endpoint should use double banking. */
+ USB_Endpoint_Table_t DataINEndpoint; /**< Data IN endpoint configuration table. */
+ USB_Endpoint_Table_t DataOUTEndpoint; /**< Data OUT endpoint configuration table. */
} Config; /**< Config data for the USB class interface within the device. All elements in this section
* <b>must</b> be set or the interface will fail to enumerate and operate correctly.
*/
diff --git a/LUFA/Drivers/USB/Class/Device/MassStorageClassDevice.c b/LUFA/Drivers/USB/Class/Device/MassStorageClassDevice.c
index 6294a0a94..153ebbc89 100644
--- a/LUFA/Drivers/USB/Class/Device/MassStorageClassDevice.c
+++ b/LUFA/Drivers/USB/Class/Device/MassStorageClassDevice.c
@@ -75,38 +75,14 @@ bool MS_Device_ConfigureEndpoints(USB_ClassInfo_MS_Device_t* const MSInterfaceIn
{
memset(&MSInterfaceInfo->State, 0x00, sizeof(MSInterfaceInfo->State));
- for (uint8_t EndpointNum = 1; EndpointNum < ENDPOINT_TOTAL_ENDPOINTS; EndpointNum++)
- {
- uint16_t Size;
- uint8_t Type;
- uint8_t Direction;
- bool DoubleBanked;
+ MSInterfaceInfo->Config.DataINEndpoint.Type = EP_TYPE_BULK;
+ MSInterfaceInfo->Config.DataOUTEndpoint.Type = EP_TYPE_BULK;
- if (EndpointNum == MSInterfaceInfo->Config.DataINEndpointNumber)
- {
- Size = MSInterfaceInfo->Config.DataINEndpointSize;
- Direction = ENDPOINT_DIR_IN;
- Type = EP_TYPE_BULK;
- DoubleBanked = MSInterfaceInfo->Config.DataINEndpointDoubleBank;
- }
- else if (EndpointNum == MSInterfaceInfo->Config.DataOUTEndpointNumber)
- {
- Size = MSInterfaceInfo->Config.DataOUTEndpointSize;
- Direction = ENDPOINT_DIR_OUT;
- Type = EP_TYPE_BULK;
- DoubleBanked = MSInterfaceInfo->Config.DataOUTEndpointDoubleBank;
- }
- else
- {
- continue;
- }
+ if (!(Endpoint_ConfigureEndpointTable(&MSInterfaceInfo->Config.DataINEndpoint, 1)))
+ return false;
- if (!(Endpoint_ConfigureEndpoint(EndpointNum, Type, Direction, Size,
- DoubleBanked ? ENDPOINT_BANK_DOUBLE : ENDPOINT_BANK_SINGLE)))
- {
- return false;
- }
- }
+ if (!(Endpoint_ConfigureEndpointTable(&MSInterfaceInfo->Config.DataOUTEndpoint, 1)))
+ return false;
return true;
}
@@ -116,14 +92,14 @@ void MS_Device_USBTask(USB_ClassInfo_MS_Device_t* const MSInterfaceInfo)
if (USB_DeviceState != DEVICE_STATE_Configured)
return;
- Endpoint_SelectEndpoint(MSInterfaceInfo->Config.DataOUTEndpointNumber);
+ Endpoint_SelectEndpoint(MSInterfaceInfo->Config.DataOUTEndpoint.Address);
- if (Endpoint_IsReadWriteAllowed())
+ if (Endpoint_IsOUTReceived())
{
if (MS_Device_ReadInCommandBlock(MSInterfaceInfo))
{
if (MSInterfaceInfo->State.CommandBlock.Flags & MS_COMMAND_DIR_DATA_IN)
- Endpoint_SelectEndpoint(MSInterfaceInfo->Config.DataINEndpointNumber);
+ Endpoint_SelectEndpoint(MSInterfaceInfo->Config.DataINEndpoint.Address);
bool SCSICommandResult = CALLBACK_MS_Device_SCSICommandReceived(MSInterfaceInfo);
@@ -141,13 +117,13 @@ void MS_Device_USBTask(USB_ClassInfo_MS_Device_t* const MSInterfaceInfo)
if (MSInterfaceInfo->State.IsMassStoreReset)
{
- Endpoint_ResetEndpoint(MSInterfaceInfo->Config.DataOUTEndpointNumber);
- Endpoint_ResetEndpoint(MSInterfaceInfo->Config.DataINEndpointNumber);
+ Endpoint_ResetEndpoint(MSInterfaceInfo->Config.DataOUTEndpoint.Address);
+ Endpoint_ResetEndpoint(MSInterfaceInfo->Config.DataINEndpoint.Address);
- Endpoint_SelectEndpoint(MSInterfaceInfo->Config.DataOUTEndpointNumber);
+ Endpoint_SelectEndpoint(MSInterfaceInfo->Config.DataOUTEndpoint.Address);
Endpoint_ClearStall();
Endpoint_ResetDataToggle();
- Endpoint_SelectEndpoint(MSInterfaceInfo->Config.DataINEndpointNumber);
+ Endpoint_SelectEndpoint(MSInterfaceInfo->Config.DataINEndpoint.Address);
Endpoint_ClearStall();
Endpoint_ResetDataToggle();
@@ -159,8 +135,8 @@ static bool MS_Device_ReadInCommandBlock(USB_ClassInfo_MS_Device_t* const MSInte
{
uint16_t BytesProcessed;
- Endpoint_SelectEndpoint(MSInterfaceInfo->Config.DataOUTEndpointNumber);
-
+ Endpoint_SelectEndpoint(MSInterfaceInfo->Config.DataOUTEndpoint.Address);
+
BytesProcessed = 0;
while (Endpoint_Read_Stream_LE(&MSInterfaceInfo->State.CommandBlock,
(sizeof(MS_CommandBlockWrapper_t) - 16), &BytesProcessed) ==
@@ -175,9 +151,9 @@ static bool MS_Device_ReadInCommandBlock(USB_ClassInfo_MS_Device_t* const MSInte
(MSInterfaceInfo->State.CommandBlock.Flags & 0x1F) ||
(MSInterfaceInfo->State.CommandBlock.SCSICommandLength == 0) ||
(MSInterfaceInfo->State.CommandBlock.SCSICommandLength > 16))
- {
+ {
Endpoint_StallTransaction();
- Endpoint_SelectEndpoint(MSInterfaceInfo->Config.DataINEndpointNumber);
+ Endpoint_SelectEndpoint(MSInterfaceInfo->Config.DataINEndpoint.Address);
Endpoint_StallTransaction();
return false;
@@ -199,7 +175,7 @@ static bool MS_Device_ReadInCommandBlock(USB_ClassInfo_MS_Device_t* const MSInte
static void MS_Device_ReturnCommandStatus(USB_ClassInfo_MS_Device_t* const MSInterfaceInfo)
{
- Endpoint_SelectEndpoint(MSInterfaceInfo->Config.DataOUTEndpointNumber);
+ Endpoint_SelectEndpoint(MSInterfaceInfo->Config.DataOUTEndpoint.Address);
while (Endpoint_IsStalled())
{
@@ -211,7 +187,7 @@ static void MS_Device_ReturnCommandStatus(USB_ClassInfo_MS_Device_t* const MSInt
return;
}
- Endpoint_SelectEndpoint(MSInterfaceInfo->Config.DataINEndpointNumber);
+ Endpoint_SelectEndpoint(MSInterfaceInfo->Config.DataINEndpoint.Address);
while (Endpoint_IsStalled())
{
diff --git a/LUFA/Drivers/USB/Class/Device/MassStorageClassDevice.h b/LUFA/Drivers/USB/Class/Device/MassStorageClassDevice.h
index c2d536ce2..6b490eca1 100644
--- a/LUFA/Drivers/USB/Class/Device/MassStorageClassDevice.h
+++ b/LUFA/Drivers/USB/Class/Device/MassStorageClassDevice.h
@@ -81,13 +81,8 @@
{
uint8_t InterfaceNumber; /**< Interface number of the Mass Storage interface within the device. */
- uint8_t DataINEndpointNumber; /**< Endpoint number of the Mass Storage interface's IN data endpoint. */
- uint16_t DataINEndpointSize; /**< Size in bytes of the Mass Storage interface's IN data endpoint. */
- bool DataINEndpointDoubleBank; /**< Indicates if the Mass Storage interface's IN data endpoint should use double banking. */
-
- uint8_t DataOUTEndpointNumber; /**< Endpoint number of the Mass Storage interface's OUT data endpoint. */
- uint16_t DataOUTEndpointSize; /**< Size in bytes of the Mass Storage interface's OUT data endpoint. */
- bool DataOUTEndpointDoubleBank; /**< Indicates if the Mass Storage interface's OUT data endpoint should use double banking. */
+ USB_Endpoint_Table_t DataINEndpoint; /**< Data IN endpoint configuration table. */
+ USB_Endpoint_Table_t DataOUTEndpoint; /**< Data OUT endpoint configuration table. */
uint8_t TotalLUNs; /**< Total number of logical drives in the Mass Storage interface. */
} Config; /**< Config data for the USB class interface within the device. All elements in this section
diff --git a/LUFA/Drivers/USB/Class/Device/RNDISClassDevice.c b/LUFA/Drivers/USB/Class/Device/RNDISClassDevice.c
index f78a5abf2..e5aa40cd0 100644
--- a/LUFA/Drivers/USB/Class/Device/RNDISClassDevice.c
+++ b/LUFA/Drivers/USB/Class/Device/RNDISClassDevice.c
@@ -115,45 +115,18 @@ bool RNDIS_Device_ConfigureEndpoints(USB_ClassInfo_RNDIS_Device_t* const RNDISIn
{
memset(&RNDISInterfaceInfo->State, 0x00, sizeof(RNDISInterfaceInfo->State));
- for (uint8_t EndpointNum = 1; EndpointNum < ENDPOINT_TOTAL_ENDPOINTS; EndpointNum++)
- {
- uint16_t Size;
- uint8_t Type;
- uint8_t Direction;
- bool DoubleBanked;
-
- if (EndpointNum == RNDISInterfaceInfo->Config.DataINEndpointNumber)
- {
- Size = RNDISInterfaceInfo->Config.DataINEndpointSize;
- Direction = ENDPOINT_DIR_IN;
- Type = EP_TYPE_BULK;
- DoubleBanked = RNDISInterfaceInfo->Config.DataINEndpointDoubleBank;
- }
- else if (EndpointNum == RNDISInterfaceInfo->Config.DataOUTEndpointNumber)
- {
- Size = RNDISInterfaceInfo->Config.DataOUTEndpointSize;
- Direction = ENDPOINT_DIR_OUT;
- Type = EP_TYPE_BULK;
- DoubleBanked = RNDISInterfaceInfo->Config.DataOUTEndpointDoubleBank;
- }
- else if (EndpointNum == RNDISInterfaceInfo->Config.NotificationEndpointNumber)
- {
- Size = RNDISInterfaceInfo->Config.NotificationEndpointSize;
- Direction = ENDPOINT_DIR_IN;
- Type = EP_TYPE_INTERRUPT;
- DoubleBanked = RNDISInterfaceInfo->Config.NotificationEndpointDoubleBank;
- }
- else
- {
- continue;
- }
-
- if (!(Endpoint_ConfigureEndpoint(EndpointNum, Type, Direction, Size,
- DoubleBanked ? ENDPOINT_BANK_DOUBLE : ENDPOINT_BANK_SINGLE)))
- {
- return false;
- }
- }
+ RNDISInterfaceInfo->Config.DataINEndpoint.Type = EP_TYPE_BULK;
+ RNDISInterfaceInfo->Config.DataOUTEndpoint.Type = EP_TYPE_BULK;
+ RNDISInterfaceInfo->Config.NotificationEndpoint.Type = EP_TYPE_INTERRUPT;
+
+ if (!(Endpoint_ConfigureEndpointTable(&RNDISInterfaceInfo->Config.DataINEndpoint, 1)))
+ return false;
+
+ if (!(Endpoint_ConfigureEndpointTable(&RNDISInterfaceInfo->Config.DataOUTEndpoint, 1)))
+ return false;
+
+ if (!(Endpoint_ConfigureEndpointTable(&RNDISInterfaceInfo->Config.NotificationEndpoint, 1)))
+ return false;
return true;
}
@@ -163,7 +136,7 @@ void RNDIS_Device_USBTask(USB_ClassInfo_RNDIS_Device_t* const RNDISInterfaceInfo
if (USB_DeviceState != DEVICE_STATE_Configured)
return;
- Endpoint_SelectEndpoint(RNDISInterfaceInfo->Config.NotificationEndpointNumber);
+ Endpoint_SelectEndpoint(RNDISInterfaceInfo->Config.NotificationEndpoint.Address);
if (Endpoint_IsINReady() && RNDISInterfaceInfo->State.ResponseReady)
{
@@ -454,7 +427,7 @@ bool RNDIS_Device_IsPacketReceived(USB_ClassInfo_RNDIS_Device_t* const RNDISInte
return false;
}
- Endpoint_SelectEndpoint(RNDISInterfaceInfo->Config.DataOUTEndpointNumber);
+ Endpoint_SelectEndpoint(RNDISInterfaceInfo->Config.DataOUTEndpoint.Address);
return Endpoint_IsOUTReceived();
}
@@ -468,7 +441,7 @@ uint8_t RNDIS_Device_ReadPacket(USB_ClassInfo_RNDIS_Device_t* const RNDISInterfa
return ENDPOINT_RWSTREAM_DeviceDisconnected;
}
- Endpoint_SelectEndpoint(RNDISInterfaceInfo->Config.DataOUTEndpointNumber);
+ Endpoint_SelectEndpoint(RNDISInterfaceInfo->Config.DataOUTEndpoint.Address);
*PacketLength = 0;
@@ -505,7 +478,7 @@ uint8_t RNDIS_Device_SendPacket(USB_ClassInfo_RNDIS_Device_t* const RNDISInterfa
return ENDPOINT_RWSTREAM_DeviceDisconnected;
}
- Endpoint_SelectEndpoint(RNDISInterfaceInfo->Config.DataINEndpointNumber);
+ Endpoint_SelectEndpoint(RNDISInterfaceInfo->Config.DataINEndpoint.Address);
if ((ErrorCode = Endpoint_WaitUntilReady()) != ENDPOINT_READYWAIT_NoError)
return ErrorCode;
diff --git a/LUFA/Drivers/USB/Class/Device/RNDISClassDevice.h b/LUFA/Drivers/USB/Class/Device/RNDISClassDevice.h
index ccd20e38e..33b807da9 100644
--- a/LUFA/Drivers/USB/Class/Device/RNDISClassDevice.h
+++ b/LUFA/Drivers/USB/Class/Device/RNDISClassDevice.h
@@ -81,17 +81,9 @@
{
uint8_t ControlInterfaceNumber; /**< Interface number of the RNDIS control interface within the device. */
- uint8_t DataINEndpointNumber; /**< Endpoint number of the RNDIS interface's IN data endpoint. */
- uint16_t DataINEndpointSize; /**< Size in bytes of the RNDIS interface's IN data endpoint. */
- bool DataINEndpointDoubleBank; /**< Indicates if the RNDIS interface's IN data endpoint should use double banking. */
-
- uint8_t DataOUTEndpointNumber; /**< Endpoint number of the RNDIS interface's OUT data endpoint. */
- uint16_t DataOUTEndpointSize; /**< Size in bytes of the RNDIS interface's OUT data endpoint. */
- bool DataOUTEndpointDoubleBank; /**< Indicates if the RNDIS interface's OUT data endpoint should use double banking. */
-
- uint8_t NotificationEndpointNumber; /**< Endpoint number of the RNDIS interface's IN notification endpoint, if used. */
- uint16_t NotificationEndpointSize; /**< Size in bytes of the RNDIS interface's IN notification endpoint, if used. */
- bool NotificationEndpointDoubleBank; /**< Indicates if the RNDIS interface's notification endpoint should use double banking. */
+ USB_Endpoint_Table_t DataINEndpoint; /**< Data IN endpoint configuration table. */
+ USB_Endpoint_Table_t DataOUTEndpoint; /**< Data OUT endpoint configuration table. */
+ USB_Endpoint_Table_t NotificationEndpoint; /**< Notification IN Endpoint configuration table. */
char* AdapterVendorDescription; /**< String description of the adapter vendor. */
MAC_Address_t AdapterMACAddress; /**< MAC address of the adapter. */
diff --git a/LUFA/Drivers/USB/Class/Host/AndroidAccessoryClassHost.c b/LUFA/Drivers/USB/Class/Host/AndroidAccessoryClassHost.c
index eb4c2530d..7c564e012 100644
--- a/LUFA/Drivers/USB/Class/Host/AndroidAccessoryClassHost.c
+++ b/LUFA/Drivers/USB/Class/Host/AndroidAccessoryClassHost.c
@@ -89,45 +89,19 @@ uint8_t AOA_Host_ConfigurePipes(USB_ClassInfo_AOA_Host_t* const AOAInterfaceInfo
DataOUTEndpoint = EndpointData;
}
- for (uint8_t PipeNum = 1; PipeNum < PIPE_TOTAL_PIPES; PipeNum++)
- {
- uint16_t Size;
- uint8_t Type;
- uint8_t Token;
- uint8_t EndpointAddress;
- bool DoubleBanked;
-
- if (PipeNum == AOAInterfaceInfo->Config.DataINPipeNumber)
- {
- Size = le16_to_cpu(DataINEndpoint->EndpointSize);
- EndpointAddress = DataINEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_IN;
- Type = EP_TYPE_BULK;
- DoubleBanked = AOAInterfaceInfo->Config.DataINPipeDoubleBank;
-
- AOAInterfaceInfo->State.DataINPipeSize = DataINEndpoint->EndpointSize;
- }
- else if (PipeNum == AOAInterfaceInfo->Config.DataOUTPipeNumber)
- {
- Size = le16_to_cpu(DataOUTEndpoint->EndpointSize);
- EndpointAddress = DataOUTEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_OUT;
- Type = EP_TYPE_BULK;
- DoubleBanked = AOAInterfaceInfo->Config.DataOUTPipeDoubleBank;
-
- AOAInterfaceInfo->State.DataOUTPipeSize = DataOUTEndpoint->EndpointSize;
- }
- else
- {
- continue;
- }
-
- if (!(Pipe_ConfigurePipe(PipeNum, Type, Token, EndpointAddress, Size,
- DoubleBanked ? PIPE_BANK_DOUBLE : PIPE_BANK_SINGLE)))
- {
- return AOA_ENUMERROR_PipeConfigurationFailed;
- }
- }
+ AOAInterfaceInfo->Config.DataINPipe.Size = le16_to_cpu(DataINEndpoint->EndpointSize);
+ AOAInterfaceInfo->Config.DataINPipe.EndpointAddress = DataINEndpoint->EndpointAddress;
+ AOAInterfaceInfo->Config.DataINPipe.Type = EP_TYPE_BULK;
+
+ AOAInterfaceInfo->Config.DataOUTPipe.Size = le16_to_cpu(DataOUTEndpoint->EndpointSize);
+ AOAInterfaceInfo->Config.DataOUTPipe.EndpointAddress = DataOUTEndpoint->EndpointAddress;
+ AOAInterfaceInfo->Config.DataOUTPipe.Type = EP_TYPE_BULK;
+
+ if (!(Pipe_ConfigurePipeTable(&AOAInterfaceInfo->Config.DataINPipe, 1)))
+ return false;
+
+ if (!(Pipe_ConfigurePipeTable(&AOAInterfaceInfo->Config.DataOUTPipe, 1)))
+ return false;
AOAInterfaceInfo->State.IsActive = true;
AOAInterfaceInfo->State.InterfaceNumber = AOAInterface->InterfaceNumber;
@@ -260,7 +234,7 @@ uint8_t AOA_Host_SendData(USB_ClassInfo_AOA_Host_t* const AOAInterfaceInfo,
uint8_t ErrorCode;
- Pipe_SelectPipe(AOAInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(AOAInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
ErrorCode = Pipe_Write_Stream_LE(Buffer, Length, NULL);
@@ -277,7 +251,7 @@ uint8_t AOA_Host_SendString(USB_ClassInfo_AOA_Host_t* const AOAInterfaceInfo,
uint8_t ErrorCode;
- Pipe_SelectPipe(AOAInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(AOAInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
ErrorCode = Pipe_Write_Stream_LE(String, strlen(String), NULL);
@@ -294,7 +268,7 @@ uint8_t AOA_Host_SendByte(USB_ClassInfo_AOA_Host_t* const AOAInterfaceInfo,
uint8_t ErrorCode;
- Pipe_SelectPipe(AOAInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(AOAInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
if (!(Pipe_IsReadWriteAllowed()))
@@ -316,7 +290,7 @@ uint16_t AOA_Host_BytesReceived(USB_ClassInfo_AOA_Host_t* const AOAInterfaceInfo
if ((USB_HostState != HOST_STATE_Configured) || !(AOAInterfaceInfo->State.IsActive))
return 0;
- Pipe_SelectPipe(AOAInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(AOAInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
if (Pipe_IsINReceived())
@@ -348,7 +322,7 @@ int16_t AOA_Host_ReceiveByte(USB_ClassInfo_AOA_Host_t* const AOAInterfaceInfo)
int16_t ReceivedByte = -1;
- Pipe_SelectPipe(AOAInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(AOAInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
if (Pipe_IsINReceived())
@@ -372,7 +346,7 @@ uint8_t AOA_Host_Flush(USB_ClassInfo_AOA_Host_t* const AOAInterfaceInfo)
uint8_t ErrorCode;
- Pipe_SelectPipe(AOAInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(AOAInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
if (!(Pipe_BytesInPipe()))
diff --git a/LUFA/Drivers/USB/Class/Host/AndroidAccessoryClassHost.h b/LUFA/Drivers/USB/Class/Host/AndroidAccessoryClassHost.h
index 0ec44e715..678feda45 100644
--- a/LUFA/Drivers/USB/Class/Host/AndroidAccessoryClassHost.h
+++ b/LUFA/Drivers/USB/Class/Host/AndroidAccessoryClassHost.h
@@ -85,11 +85,8 @@
{
struct
{
- uint8_t DataINPipeNumber; /**< Pipe number of the AOA interface's IN data pipe. */
- bool DataINPipeDoubleBank; /**< Indicates if the AOA interface's IN data pipe should use double banking. */
-
- uint8_t DataOUTPipeNumber; /**< Pipe number of the AOA interface's OUT data pipe. */
- bool DataOUTPipeDoubleBank; /**< Indicates if the AOA interface's OUT data pipe should use double banking. */
+ USB_Pipe_Table_t DataINPipe; /**< Data IN Pipe configuration table. */
+ USB_Pipe_Table_t DataOUTPipe; /**< Data OUT Pipe configuration table. */
char* PropertyStrings[AOA_STRING_TOTAL_STRINGS]; /**< Android Accessory property strings, sent to identify the accessory when the
* Android device is switched into Open Accessory mode. */
@@ -103,9 +100,6 @@
* Configured state.
*/
uint8_t InterfaceNumber; /**< Interface index of the AOA interface within the attached device. */
-
- uint16_t DataINPipeSize; /**< Size in bytes of the AOA interface's IN data pipe. */
- uint16_t DataOUTPipeSize; /**< Size in bytes of the AOA interface's OUT data pipe. */
} State; /**< State data for the USB class interface within the device. All elements in this section
* <b>may</b> be set to initial values, but may also be ignored to default to sane values when
* the interface is enumerated.
diff --git a/LUFA/Drivers/USB/Class/Host/AudioClassHost.c b/LUFA/Drivers/USB/Class/Host/AudioClassHost.c
index e5591ec1d..12783a6a0 100644
--- a/LUFA/Drivers/USB/Class/Host/AudioClassHost.c
+++ b/LUFA/Drivers/USB/Class/Host/AudioClassHost.c
@@ -51,8 +51,8 @@ uint8_t Audio_Host_ConfigurePipes(USB_ClassInfo_Audio_Host_t* const AudioInterfa
if (DESCRIPTOR_TYPE(ConfigDescriptorData) != DTYPE_Configuration)
return AUDIO_ENUMERROR_InvalidConfigDescriptor;
- while ((AudioInterfaceInfo->Config.DataINPipeNumber && !(DataINEndpoint)) ||
- (AudioInterfaceInfo->Config.DataOUTPipeNumber && !(DataOUTEndpoint)))
+ while ((AudioInterfaceInfo->Config.DataINPipe.Address && !(DataINEndpoint)) ||
+ (AudioInterfaceInfo->Config.DataOUTPipe.Address && !(DataOUTEndpoint)))
{
if (!(AudioControlInterface) ||
USB_GetNextDescriptorComp(&ConfigDescriptorSize, &ConfigDescriptorData,
@@ -93,45 +93,21 @@ uint8_t Audio_Host_ConfigurePipes(USB_ClassInfo_Audio_Host_t* const AudioInterfa
DataOUTEndpoint = EndpointData;
}
- for (uint8_t PipeNum = 1; PipeNum < PIPE_TOTAL_PIPES; PipeNum++)
- {
- uint16_t Size;
- uint8_t Type;
- uint8_t Token;
- uint8_t EndpointAddress;
- bool DoubleBanked;
-
- if (PipeNum == AudioInterfaceInfo->Config.DataINPipeNumber)
- {
- Size = le16_to_cpu(DataINEndpoint->EndpointSize);
- EndpointAddress = DataINEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_IN;
- Type = EP_TYPE_ISOCHRONOUS;
- DoubleBanked = true;
-
- AudioInterfaceInfo->State.DataINPipeSize = DataINEndpoint->EndpointSize;
- }
- else if (PipeNum == AudioInterfaceInfo->Config.DataOUTPipeNumber)
- {
- Size = le16_to_cpu(DataOUTEndpoint->EndpointSize);
- EndpointAddress = DataOUTEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_OUT;
- Type = EP_TYPE_ISOCHRONOUS;
- DoubleBanked = true;
-
- AudioInterfaceInfo->State.DataOUTPipeSize = DataOUTEndpoint->EndpointSize;
- }
- else
- {
- continue;
- }
-
- if (!(Pipe_ConfigurePipe(PipeNum, Type, Token, EndpointAddress, Size,
- DoubleBanked ? PIPE_BANK_DOUBLE : PIPE_BANK_SINGLE)))
- {
- return AUDIO_ENUMERROR_PipeConfigurationFailed;
- }
- }
+ AudioInterfaceInfo->Config.DataINPipe.Size = le16_to_cpu(DataINEndpoint->EndpointSize);
+ AudioInterfaceInfo->Config.DataINPipe.EndpointAddress = DataINEndpoint->EndpointAddress;
+ AudioInterfaceInfo->Config.DataINPipe.Type = EP_TYPE_ISOCHRONOUS;
+ AudioInterfaceInfo->Config.DataINPipe.Banks = 2;
+
+ AudioInterfaceInfo->Config.DataOUTPipe.Size = le16_to_cpu(DataOUTEndpoint->EndpointSize);
+ AudioInterfaceInfo->Config.DataOUTPipe.EndpointAddress = DataOUTEndpoint->EndpointAddress;
+ AudioInterfaceInfo->Config.DataOUTPipe.Type = EP_TYPE_ISOCHRONOUS;
+ AudioInterfaceInfo->Config.DataOUTPipe.Banks = 2;
+
+ if (!(Pipe_ConfigurePipeTable(&AudioInterfaceInfo->Config.DataINPipe, 1)))
+ return false;
+
+ if (!(Pipe_ConfigurePipeTable(&AudioInterfaceInfo->Config.DataOUTPipe, 1)))
+ return false;
AudioInterfaceInfo->State.ControlInterfaceNumber = AudioControlInterface->InterfaceNumber;
AudioInterfaceInfo->State.StreamingInterfaceNumber = AudioStreamingInterface->InterfaceNumber;
diff --git a/LUFA/Drivers/USB/Class/Host/AudioClassHost.h b/LUFA/Drivers/USB/Class/Host/AudioClassHost.h
index a6e425d5f..2d39aa9ca 100644
--- a/LUFA/Drivers/USB/Class/Host/AudioClassHost.h
+++ b/LUFA/Drivers/USB/Class/Host/AudioClassHost.h
@@ -79,14 +79,8 @@
{
struct
{
- uint8_t DataINPipeNumber; /**< Pipe number of the Audio interface's IN data pipe. If this interface should not
- * bind to an IN endpoint, this may be set to 0 to disable audio input streaming for
- * this driver instance.
- */
- uint8_t DataOUTPipeNumber; /**< Pipe number of the Audio interface's OUT data pipe. If this interface should not
- * bind to an OUT endpoint, this may be set to 0 to disable audio output streaming for
- * this driver instance.
- */
+ USB_Pipe_Table_t DataINPipe; /**< Data IN Pipe configuration table. */
+ USB_Pipe_Table_t DataOUTPipe; /**< Data OUT Pipe configuration table. */
} Config; /**< Config data for the USB class interface within the device. All elements in this section
* <b>must</b> be set or the interface will fail to enumerate and operate correctly.
*/
@@ -100,9 +94,6 @@
uint8_t StreamingInterfaceNumber; /**< Interface index of the Audio Streaming interface within the attached device. */
uint8_t EnabledStreamingAltIndex; /**< Alternative setting index of the Audio Streaming interface when the stream is enabled. */
-
- uint16_t DataINPipeSize; /**< Size in bytes of the Audio interface's IN data pipe. */
- uint16_t DataOUTPipeSize; /**< Size in bytes of the Audio interface's OUT data pipe. */
} State; /**< State data for the USB class interface within the device. All elements in this section
* <b>may</b> be set to initial values, but may also be ignored to default to sane values when
* the interface is enumerated.
@@ -201,7 +192,7 @@
bool SampleReceived = false;
- Pipe_SelectPipe(AudioInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(AudioInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
SampleReceived = Pipe_IsINReceived();
Pipe_Freeze();
@@ -226,7 +217,7 @@
if ((USB_HostState != HOST_STATE_Configured) || !(AudioInterfaceInfo->State.IsActive))
return false;
- Pipe_SelectPipe(AudioInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(AudioInterfaceInfo->Config.DataOUTPipe.Address);
return Pipe_IsOUTReady();
}
diff --git a/LUFA/Drivers/USB/Class/Host/CDCClassHost.c b/LUFA/Drivers/USB/Class/Host/CDCClassHost.c
index 63df6b0c5..8c79e9c22 100644
--- a/LUFA/Drivers/USB/Class/Host/CDCClassHost.c
+++ b/LUFA/Drivers/USB/Class/Host/CDCClassHost.c
@@ -99,62 +99,26 @@ uint8_t CDC_Host_ConfigurePipes(USB_ClassInfo_CDC_Host_t* const CDCInterfaceInfo
}
}
- for (uint8_t PipeNum = 1; PipeNum < PIPE_TOTAL_PIPES; PipeNum++)
- {
- uint16_t Size;
- uint8_t Type;
- uint8_t Token;
- uint8_t EndpointAddress;
- uint8_t InterruptPeriod;
- bool DoubleBanked;
-
- if (PipeNum == CDCInterfaceInfo->Config.DataINPipeNumber)
- {
- Size = le16_to_cpu(DataINEndpoint->EndpointSize);
- EndpointAddress = DataINEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_IN;
- Type = EP_TYPE_BULK;
- DoubleBanked = CDCInterfaceInfo->Config.DataINPipeDoubleBank;
- InterruptPeriod = 0;
-
- CDCInterfaceInfo->State.DataINPipeSize = DataINEndpoint->EndpointSize;
- }
- else if (PipeNum == CDCInterfaceInfo->Config.DataOUTPipeNumber)
- {
- Size = le16_to_cpu(DataOUTEndpoint->EndpointSize);
- EndpointAddress = DataOUTEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_OUT;
- Type = EP_TYPE_BULK;
- DoubleBanked = CDCInterfaceInfo->Config.DataOUTPipeDoubleBank;
- InterruptPeriod = 0;
-
- CDCInterfaceInfo->State.DataOUTPipeSize = DataOUTEndpoint->EndpointSize;
- }
- else if (PipeNum == CDCInterfaceInfo->Config.NotificationPipeNumber)
- {
- Size = le16_to_cpu(NotificationEndpoint->EndpointSize);
- EndpointAddress = NotificationEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_IN;
- Type = EP_TYPE_INTERRUPT;
- DoubleBanked = CDCInterfaceInfo->Config.NotificationPipeDoubleBank;
- InterruptPeriod = NotificationEndpoint->PollingIntervalMS;
-
- CDCInterfaceInfo->State.NotificationPipeSize = NotificationEndpoint->EndpointSize;
- }
- else
- {
- continue;
- }
-
- if (!(Pipe_ConfigurePipe(PipeNum, Type, Token, EndpointAddress, Size,
- DoubleBanked ? PIPE_BANK_DOUBLE : PIPE_BANK_SINGLE)))
- {
- return CDC_ENUMERROR_PipeConfigurationFailed;
- }
-
- if (InterruptPeriod)
- Pipe_SetInterruptPeriod(InterruptPeriod);
- }
+ CDCInterfaceInfo->Config.DataINPipe.Size = le16_to_cpu(DataINEndpoint->EndpointSize);
+ CDCInterfaceInfo->Config.DataINPipe.EndpointAddress = DataINEndpoint->EndpointAddress;
+ CDCInterfaceInfo->Config.DataINPipe.Type = EP_TYPE_BULK;
+
+ CDCInterfaceInfo->Config.DataOUTPipe.Size = le16_to_cpu(DataOUTEndpoint->EndpointSize);
+ CDCInterfaceInfo->Config.DataOUTPipe.EndpointAddress = DataOUTEndpoint->EndpointAddress;
+ CDCInterfaceInfo->Config.DataOUTPipe.Type = EP_TYPE_BULK;
+
+ CDCInterfaceInfo->Config.NotificationPipe.Size = le16_to_cpu(NotificationEndpoint->EndpointSize);
+ CDCInterfaceInfo->Config.NotificationPipe.EndpointAddress = NotificationEndpoint->EndpointAddress;
+ CDCInterfaceInfo->Config.NotificationPipe.Type = EP_TYPE_INTERRUPT;
+
+ if (!(Pipe_ConfigurePipeTable(&CDCInterfaceInfo->Config.DataINPipe, 1)))
+ return false;
+
+ if (!(Pipe_ConfigurePipeTable(&CDCInterfaceInfo->Config.DataOUTPipe, 1)))
+ return false;
+
+ if (!(Pipe_ConfigurePipeTable(&CDCInterfaceInfo->Config.NotificationPipe, 1)))
+ return false;
CDCInterfaceInfo->State.ControlInterfaceNumber = CDCControlInterface->InterfaceNumber;
CDCInterfaceInfo->State.ControlLineStates.HostToDevice = (CDC_CONTROL_LINE_OUT_RTS | CDC_CONTROL_LINE_OUT_DTR);
@@ -231,7 +195,7 @@ void CDC_Host_USBTask(USB_ClassInfo_CDC_Host_t* const CDCInterfaceInfo)
if ((USB_HostState != HOST_STATE_Configured) || !(CDCInterfaceInfo->State.IsActive))
return;
- Pipe_SelectPipe(CDCInterfaceInfo->Config.NotificationPipeNumber);
+ Pipe_SelectPipe(CDCInterfaceInfo->Config.NotificationPipe.Address);
Pipe_Unfreeze();
if (Pipe_IsINReceived())
@@ -321,7 +285,7 @@ uint8_t CDC_Host_SendData(USB_ClassInfo_CDC_Host_t* const CDCInterfaceInfo,
uint8_t ErrorCode;
- Pipe_SelectPipe(CDCInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(CDCInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
ErrorCode = Pipe_Write_Stream_LE(Buffer, Length, NULL);
@@ -338,7 +302,7 @@ uint8_t CDC_Host_SendString(USB_ClassInfo_CDC_Host_t* const CDCInterfaceInfo,
uint8_t ErrorCode;
- Pipe_SelectPipe(CDCInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(CDCInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
ErrorCode = Pipe_Write_Stream_LE(String, strlen(String), NULL);
@@ -355,7 +319,7 @@ uint8_t CDC_Host_SendByte(USB_ClassInfo_CDC_Host_t* const CDCInterfaceInfo,
uint8_t ErrorCode;
- Pipe_SelectPipe(CDCInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(CDCInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
if (!(Pipe_IsReadWriteAllowed()))
@@ -377,7 +341,7 @@ uint16_t CDC_Host_BytesReceived(USB_ClassInfo_CDC_Host_t* const CDCInterfaceInfo
if ((USB_HostState != HOST_STATE_Configured) || !(CDCInterfaceInfo->State.IsActive))
return 0;
- Pipe_SelectPipe(CDCInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(CDCInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
if (Pipe_IsINReceived())
@@ -409,7 +373,7 @@ int16_t CDC_Host_ReceiveByte(USB_ClassInfo_CDC_Host_t* const CDCInterfaceInfo)
int16_t ReceivedByte = -1;
- Pipe_SelectPipe(CDCInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(CDCInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
if (Pipe_IsINReceived())
@@ -433,7 +397,7 @@ uint8_t CDC_Host_Flush(USB_ClassInfo_CDC_Host_t* const CDCInterfaceInfo)
uint8_t ErrorCode;
- Pipe_SelectPipe(CDCInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(CDCInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
if (!(Pipe_BytesInPipe()))
diff --git a/LUFA/Drivers/USB/Class/Host/CDCClassHost.h b/LUFA/Drivers/USB/Class/Host/CDCClassHost.h
index 5a8df2414..4d79ed951 100644
--- a/LUFA/Drivers/USB/Class/Host/CDCClassHost.h
+++ b/LUFA/Drivers/USB/Class/Host/CDCClassHost.h
@@ -81,14 +81,9 @@
{
struct
{
- uint8_t DataINPipeNumber; /**< Pipe number of the CDC interface's IN data pipe. */
- bool DataINPipeDoubleBank; /**< Indicates if the CDC interface's IN data pipe should use double banking. */
-
- uint8_t DataOUTPipeNumber; /**< Pipe number of the CDC interface's OUT data pipe. */
- bool DataOUTPipeDoubleBank; /**< Indicates if the CDC interface's OUT data pipe should use double banking. */
-
- uint8_t NotificationPipeNumber; /**< Pipe number of the CDC interface's IN notification endpoint, if used. */
- bool NotificationPipeDoubleBank; /**< Indicates if the CDC interface's notification pipe should use double banking. */
+ USB_Pipe_Table_t DataINPipe; /**< Data IN Pipe configuration table. */
+ USB_Pipe_Table_t DataOUTPipe; /**< Data OUT Pipe configuration table. */
+ USB_Pipe_Table_t NotificationPipe; /**< Notification IN Pipe configuration table. */
} Config; /**< Config data for the USB class interface within the device. All elements in this section
* <b>must</b> be set or the interface will fail to enumerate and operate correctly.
*/
@@ -100,10 +95,6 @@
*/
uint8_t ControlInterfaceNumber; /**< Interface index of the CDC-ACM control interface within the attached device. */
- uint16_t DataINPipeSize; /**< Size in bytes of the CDC interface's IN data pipe. */
- uint16_t DataOUTPipeSize; /**< Size in bytes of the CDC interface's OUT data pipe. */
- uint16_t NotificationPipeSize; /**< Size in bytes of the CDC interface's IN notification pipe, if used. */
-
struct
{
uint16_t HostToDevice; /**< Control line states from the host to device, as a set of \c CDC_CONTROL_LINE_OUT_*
diff --git a/LUFA/Drivers/USB/Class/Host/HIDClassHost.c b/LUFA/Drivers/USB/Class/Host/HIDClassHost.c
index f51bdf74f..dad6a5afc 100644
--- a/LUFA/Drivers/USB/Class/Host/HIDClassHost.c
+++ b/LUFA/Drivers/USB/Class/Host/HIDClassHost.c
@@ -94,55 +94,19 @@ uint8_t HID_Host_ConfigurePipes(USB_ClassInfo_HID_Host_t* const HIDInterfaceInfo
DataOUTEndpoint = EndpointData;
}
- for (uint8_t PipeNum = 1; PipeNum < PIPE_TOTAL_PIPES; PipeNum++)
- {
- uint16_t Size;
- uint8_t Type;
- uint8_t Token;
- uint8_t EndpointAddress;
- uint8_t InterruptPeriod;
- bool DoubleBanked;
-
- if (PipeNum == HIDInterfaceInfo->Config.DataINPipeNumber)
- {
- Size = le16_to_cpu(DataINEndpoint->EndpointSize);
- EndpointAddress = DataINEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_IN;
- Type = EP_TYPE_INTERRUPT;
- DoubleBanked = HIDInterfaceInfo->Config.DataINPipeDoubleBank;
- InterruptPeriod = DataINEndpoint->PollingIntervalMS;
-
- HIDInterfaceInfo->State.DataINPipeSize = DataINEndpoint->EndpointSize;
- }
- else if (PipeNum == HIDInterfaceInfo->Config.DataOUTPipeNumber)
- {
- if (DataOUTEndpoint == NULL)
- continue;
-
- Size = le16_to_cpu(DataOUTEndpoint->EndpointSize);
- EndpointAddress = DataOUTEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_OUT;
- Type = EP_TYPE_INTERRUPT;
- DoubleBanked = HIDInterfaceInfo->Config.DataOUTPipeDoubleBank;
- InterruptPeriod = DataOUTEndpoint->PollingIntervalMS;
-
- HIDInterfaceInfo->State.DataOUTPipeSize = DataOUTEndpoint->EndpointSize;
- HIDInterfaceInfo->State.DeviceUsesOUTPipe = true;
- }
- else
- {
- continue;
- }
-
- if (!(Pipe_ConfigurePipe(PipeNum, Type, Token, EndpointAddress, Size,
- DoubleBanked ? PIPE_BANK_DOUBLE : PIPE_BANK_SINGLE)))
- {
- return HID_ENUMERROR_PipeConfigurationFailed;
- }
-
- if (InterruptPeriod)
- Pipe_SetInterruptPeriod(InterruptPeriod);
- }
+ HIDInterfaceInfo->Config.DataINPipe.Size = le16_to_cpu(DataINEndpoint->EndpointSize);
+ HIDInterfaceInfo->Config.DataINPipe.EndpointAddress = DataINEndpoint->EndpointAddress;
+ HIDInterfaceInfo->Config.DataINPipe.Type = EP_TYPE_INTERRUPT;
+
+ HIDInterfaceInfo->Config.DataOUTPipe.Size = le16_to_cpu(DataOUTEndpoint->EndpointSize);
+ HIDInterfaceInfo->Config.DataOUTPipe.EndpointAddress = DataOUTEndpoint->EndpointAddress;
+ HIDInterfaceInfo->Config.DataOUTPipe.Type = EP_TYPE_INTERRUPT;
+
+ if (!(Pipe_ConfigurePipeTable(&HIDInterfaceInfo->Config.DataINPipe, 1)))
+ return false;
+
+ if (!(Pipe_ConfigurePipeTable(&HIDInterfaceInfo->Config.DataOUTPipe, 1)))
+ return false;
HIDInterfaceInfo->State.InterfaceNumber = HIDInterface->InterfaceNumber;
HIDInterfaceInfo->State.HIDReportSize = LE16_TO_CPU(HIDDescriptor->HIDReportLength);
@@ -227,7 +191,7 @@ uint8_t HID_Host_ReceiveReport(USB_ClassInfo_HID_Host_t* const HIDInterfaceInfo,
uint8_t ErrorCode;
- Pipe_SelectPipe(HIDInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(HIDInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
uint16_t ReportSize;
@@ -277,7 +241,7 @@ uint8_t HID_Host_SendReportByID(USB_ClassInfo_HID_Host_t* const HIDInterfaceInfo
{
uint8_t ErrorCode;
- Pipe_SelectPipe(HIDInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(HIDInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
if (ReportID)
@@ -320,7 +284,7 @@ bool HID_Host_IsReportReceived(USB_ClassInfo_HID_Host_t* const HIDInterfaceInfo)
bool ReportReceived;
- Pipe_SelectPipe(HIDInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(HIDInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
ReportReceived = Pipe_IsINReceived();
diff --git a/LUFA/Drivers/USB/Class/Host/HIDClassHost.h b/LUFA/Drivers/USB/Class/Host/HIDClassHost.h
index 7bdaad18b..882cc31df 100644
--- a/LUFA/Drivers/USB/Class/Host/HIDClassHost.h
+++ b/LUFA/Drivers/USB/Class/Host/HIDClassHost.h
@@ -83,11 +83,8 @@
{
struct
{
- uint8_t DataINPipeNumber; /**< Pipe number of the HID interface's IN data pipe. */
- bool DataINPipeDoubleBank; /**< Indicates if the HID interface's IN data pipe should use double banking. */
-
- uint8_t DataOUTPipeNumber; /**< Pipe number of the HID interface's OUT data pipe. */
- bool DataOUTPipeDoubleBank; /**< Indicates if the HID interface's OUT data pipe should use double banking. */
+ USB_Pipe_Table_t DataINPipe; /**< Data IN Pipe configuration table. */
+ USB_Pipe_Table_t DataOUTPipe; /**< Data OUT Pipe configuration table. */
uint8_t HIDInterfaceProtocol; /**< HID interface protocol value to match against if a specific
* boot subclass protocol is required, a protocol value from the
@@ -112,9 +109,6 @@
*/
uint8_t InterfaceNumber; /**< Interface index of the HID interface within the attached device. */
- uint16_t DataINPipeSize; /**< Size in bytes of the HID interface's IN data pipe. */
- uint16_t DataOUTPipeSize; /**< Size in bytes of the HID interface's OUT data pipe. */
-
bool SupportsBootProtocol; /**< Indicates if the current interface instance supports the HID Boot
* Protocol when enabled via \ref HID_Host_SetBootProtocol().
*/
diff --git a/LUFA/Drivers/USB/Class/Host/MIDIClassHost.c b/LUFA/Drivers/USB/Class/Host/MIDIClassHost.c
index 5aadbcc7f..0d33bfec4 100644
--- a/LUFA/Drivers/USB/Class/Host/MIDIClassHost.c
+++ b/LUFA/Drivers/USB/Class/Host/MIDIClassHost.c
@@ -78,45 +78,19 @@ uint8_t MIDI_Host_ConfigurePipes(USB_ClassInfo_MIDI_Host_t* const MIDIInterfaceI
DataOUTEndpoint = EndpointData;
}
- for (uint8_t PipeNum = 1; PipeNum < PIPE_TOTAL_PIPES; PipeNum++)
- {
- uint16_t Size;
- uint8_t Type;
- uint8_t Token;
- uint8_t EndpointAddress;
- bool DoubleBanked;
-
- if (PipeNum == MIDIInterfaceInfo->Config.DataINPipeNumber)
- {
- Size = le16_to_cpu(DataINEndpoint->EndpointSize);
- EndpointAddress = DataINEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_IN;
- Type = EP_TYPE_BULK;
- DoubleBanked = MIDIInterfaceInfo->Config.DataINPipeDoubleBank;
-
- MIDIInterfaceInfo->State.DataINPipeSize = DataINEndpoint->EndpointSize;
- }
- else if (PipeNum == MIDIInterfaceInfo->Config.DataOUTPipeNumber)
- {
- Size = le16_to_cpu(DataOUTEndpoint->EndpointSize);
- EndpointAddress = DataOUTEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_OUT;
- Type = EP_TYPE_BULK;
- DoubleBanked = MIDIInterfaceInfo->Config.DataOUTPipeDoubleBank;
-
- MIDIInterfaceInfo->State.DataOUTPipeSize = DataOUTEndpoint->EndpointSize;
- }
- else
- {
- continue;
- }
-
- if (!(Pipe_ConfigurePipe(PipeNum, Type, Token, EndpointAddress, Size,
- DoubleBanked ? PIPE_BANK_DOUBLE : PIPE_BANK_SINGLE)))
- {
- return MIDI_ENUMERROR_PipeConfigurationFailed;
- }
- }
+ MIDIInterfaceInfo->Config.DataINPipe.Size = le16_to_cpu(DataINEndpoint->EndpointSize);
+ MIDIInterfaceInfo->Config.DataINPipe.EndpointAddress = DataINEndpoint->EndpointAddress;
+ MIDIInterfaceInfo->Config.DataINPipe.Type = EP_TYPE_BULK;
+
+ MIDIInterfaceInfo->Config.DataOUTPipe.Size = le16_to_cpu(DataOUTEndpoint->EndpointSize);
+ MIDIInterfaceInfo->Config.DataOUTPipe.EndpointAddress = DataOUTEndpoint->EndpointAddress;
+ MIDIInterfaceInfo->Config.DataOUTPipe.Type = EP_TYPE_BULK;
+
+ if (!(Pipe_ConfigurePipeTable(&MIDIInterfaceInfo->Config.DataINPipe, 1)))
+ return false;
+
+ if (!(Pipe_ConfigurePipeTable(&MIDIInterfaceInfo->Config.DataOUTPipe, 1)))
+ return false;
MIDIInterfaceInfo->State.InterfaceNumber = MIDIInterface->InterfaceNumber;
MIDIInterfaceInfo->State.IsActive = true;
@@ -181,7 +155,7 @@ uint8_t MIDI_Host_Flush(USB_ClassInfo_MIDI_Host_t* const MIDIInterfaceInfo)
uint8_t ErrorCode;
- Pipe_SelectPipe(MIDIInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(MIDIInterfaceInfo->Config.DataOUTPipe.Address);
if (Pipe_BytesInPipe())
{
@@ -202,7 +176,7 @@ uint8_t MIDI_Host_SendEventPacket(USB_ClassInfo_MIDI_Host_t* const MIDIInterface
uint8_t ErrorCode;
- Pipe_SelectPipe(MIDIInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(MIDIInterfaceInfo->Config.DataOUTPipe.Address);
if ((ErrorCode = Pipe_Write_Stream_LE(Event, sizeof(MIDI_EventPacket_t), NULL)) != PIPE_RWSTREAM_NoError)
return ErrorCode;
@@ -219,7 +193,7 @@ bool MIDI_Host_ReceiveEventPacket(USB_ClassInfo_MIDI_Host_t* const MIDIInterface
if ((USB_HostState != HOST_STATE_Configured) || !(MIDIInterfaceInfo->State.IsActive))
return HOST_SENDCONTROL_DeviceDisconnected;
- Pipe_SelectPipe(MIDIInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(MIDIInterfaceInfo->Config.DataINPipe.Address);
if (!(Pipe_IsReadWriteAllowed()))
return false;
diff --git a/LUFA/Drivers/USB/Class/Host/MIDIClassHost.h b/LUFA/Drivers/USB/Class/Host/MIDIClassHost.h
index e934ddacb..b9e861143 100644
--- a/LUFA/Drivers/USB/Class/Host/MIDIClassHost.h
+++ b/LUFA/Drivers/USB/Class/Host/MIDIClassHost.h
@@ -79,11 +79,8 @@
{
struct
{
- uint8_t DataINPipeNumber; /**< Pipe number of the MIDI interface's streaming IN data pipe. */
- bool DataINPipeDoubleBank; /**< Indicates if the MIDI interface's IN data pipe should use double banking. */
-
- uint8_t DataOUTPipeNumber; /**< Pipe number of the MIDI interface's streaming OUT data pipe. */
- bool DataOUTPipeDoubleBank; /**< Indicates if the MIDI interface's OUT data pipe should use double banking. */
+ USB_Pipe_Table_t DataINPipe; /**< Data IN Pipe configuration table. */
+ USB_Pipe_Table_t DataOUTPipe; /**< Data OUT Pipe configuration table. */
} Config; /**< Config data for the USB class interface within the device. All elements in this section
* <b>must</b> be set or the interface will fail to enumerate and operate correctly.
*/
@@ -94,9 +91,6 @@
* Configured state.
*/
uint8_t InterfaceNumber; /**< Interface index of the MIDI interface within the attached device. */
-
- uint16_t DataINPipeSize; /**< Size in bytes of the MIDI Streaming Data interface's IN data pipe. */
- uint16_t DataOUTPipeSize; /**< Size in bytes of the MIDI Streaming Data interface's OUT data pipe. */
} State; /**< State data for the USB class interface within the device. All elements in this section
* <b>may</b> be set to initial values, but may also be ignored to default to sane values when
* the interface is enumerated.
diff --git a/LUFA/Drivers/USB/Class/Host/MassStorageClassHost.c b/LUFA/Drivers/USB/Class/Host/MassStorageClassHost.c
index 24b4edc76..f145881fd 100644
--- a/LUFA/Drivers/USB/Class/Host/MassStorageClassHost.c
+++ b/LUFA/Drivers/USB/Class/Host/MassStorageClassHost.c
@@ -78,45 +78,19 @@ uint8_t MS_Host_ConfigurePipes(USB_ClassInfo_MS_Host_t* const MSInterfaceInfo,
DataOUTEndpoint = EndpointData;
}
- for (uint8_t PipeNum = 1; PipeNum < PIPE_TOTAL_PIPES; PipeNum++)
- {
- uint16_t Size;
- uint8_t Type;
- uint8_t Token;
- uint8_t EndpointAddress;
- bool DoubleBanked;
-
- if (PipeNum == MSInterfaceInfo->Config.DataINPipeNumber)
- {
- Size = le16_to_cpu(DataINEndpoint->EndpointSize);
- EndpointAddress = DataINEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_IN;
- Type = EP_TYPE_BULK;
- DoubleBanked = MSInterfaceInfo->Config.DataINPipeDoubleBank;
-
- MSInterfaceInfo->State.DataINPipeSize = DataINEndpoint->EndpointSize;
- }
- else if (PipeNum == MSInterfaceInfo->Config.DataOUTPipeNumber)
- {
- Size = le16_to_cpu(DataOUTEndpoint->EndpointSize);
- EndpointAddress = DataOUTEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_OUT;
- Type = EP_TYPE_BULK;
- DoubleBanked = MSInterfaceInfo->Config.DataOUTPipeDoubleBank;
-
- MSInterfaceInfo->State.DataOUTPipeSize = DataOUTEndpoint->EndpointSize;
- }
- else
- {
- continue;
- }
-
- if (!(Pipe_ConfigurePipe(PipeNum, Type, Token, EndpointAddress, Size,
- DoubleBanked ? PIPE_BANK_DOUBLE : PIPE_BANK_SINGLE)))
- {
- return MS_ENUMERROR_PipeConfigurationFailed;
- }
- }
+ MSInterfaceInfo->Config.DataINPipe.Size = le16_to_cpu(DataINEndpoint->EndpointSize);
+ MSInterfaceInfo->Config.DataINPipe.EndpointAddress = DataINEndpoint->EndpointAddress;
+ MSInterfaceInfo->Config.DataINPipe.Type = EP_TYPE_BULK;
+
+ MSInterfaceInfo->Config.DataOUTPipe.Size = le16_to_cpu(DataOUTEndpoint->EndpointSize);
+ MSInterfaceInfo->Config.DataOUTPipe.EndpointAddress = DataOUTEndpoint->EndpointAddress;
+ MSInterfaceInfo->Config.DataOUTPipe.Type = EP_TYPE_BULK;
+
+ if (!(Pipe_ConfigurePipeTable(&MSInterfaceInfo->Config.DataINPipe, 1)))
+ return false;
+
+ if (!(Pipe_ConfigurePipeTable(&MSInterfaceInfo->Config.DataOUTPipe, 1)))
+ return false;
MSInterfaceInfo->State.InterfaceNumber = MassStorageInterface->InterfaceNumber;
MSInterfaceInfo->State.IsActive = true;
@@ -178,7 +152,7 @@ static uint8_t MS_Host_SendCommand(USB_ClassInfo_MS_Host_t* const MSInterfaceInf
SCSICommandBlock->Signature = CPU_TO_LE32(MS_CBW_SIGNATURE);
SCSICommandBlock->Tag = cpu_to_le32(MSInterfaceInfo->State.TransactionTag);
- Pipe_SelectPipe(MSInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(MSInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
if ((ErrorCode = Pipe_Write_Stream_LE(SCSICommandBlock, sizeof(MS_CommandBlockWrapper_t),
@@ -212,7 +186,7 @@ static uint8_t MS_Host_WaitForDataReceived(USB_ClassInfo_MS_Host_t* const MSInte
uint16_t TimeoutMSRem = MS_COMMAND_DATA_TIMEOUT_MS;
uint16_t PreviousFrameNumber = USB_Host_GetFrameNumber();
- Pipe_SelectPipe(MSInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(MSInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
while (!(Pipe_IsINReceived()))
@@ -228,7 +202,7 @@ static uint8_t MS_Host_WaitForDataReceived(USB_ClassInfo_MS_Host_t* const MSInte
}
Pipe_Freeze();
- Pipe_SelectPipe(MSInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(MSInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
if (Pipe_IsStalled())
@@ -238,7 +212,7 @@ static uint8_t MS_Host_WaitForDataReceived(USB_ClassInfo_MS_Host_t* const MSInte
}
Pipe_Freeze();
- Pipe_SelectPipe(MSInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(MSInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
if (Pipe_IsStalled())
@@ -251,10 +225,10 @@ static uint8_t MS_Host_WaitForDataReceived(USB_ClassInfo_MS_Host_t* const MSInte
return PIPE_RWSTREAM_DeviceDisconnected;
};
- Pipe_SelectPipe(MSInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(MSInterfaceInfo->Config.DataINPipe.Address);
Pipe_Freeze();
- Pipe_SelectPipe(MSInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(MSInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Freeze();
return PIPE_RWSTREAM_NoError;
@@ -275,7 +249,7 @@ static uint8_t MS_Host_SendReceiveData(USB_ClassInfo_MS_Host_t* const MSInterfac
return ErrorCode;
}
- Pipe_SelectPipe(MSInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(MSInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
if ((ErrorCode = Pipe_Read_Stream_LE(BufferPtr, BytesRem, NULL)) != PIPE_RWSTREAM_NoError)
@@ -285,7 +259,7 @@ static uint8_t MS_Host_SendReceiveData(USB_ClassInfo_MS_Host_t* const MSInterfac
}
else
{
- Pipe_SelectPipe(MSInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(MSInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
if ((ErrorCode = Pipe_Write_Stream_LE(BufferPtr, BytesRem, NULL)) != PIPE_RWSTREAM_NoError)
@@ -313,7 +287,7 @@ static uint8_t MS_Host_GetReturnedStatus(USB_ClassInfo_MS_Host_t* const MSInterf
if ((ErrorCode = MS_Host_WaitForDataReceived(MSInterfaceInfo)) != PIPE_RWSTREAM_NoError)
return ErrorCode;
- Pipe_SelectPipe(MSInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(MSInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
if ((ErrorCode = Pipe_Read_Stream_LE(SCSICommandStatus, sizeof(MS_CommandStatusWrapper_t),
@@ -349,12 +323,12 @@ uint8_t MS_Host_ResetMSInterface(USB_ClassInfo_MS_Host_t* const MSInterfaceInfo)
if ((ErrorCode = USB_Host_SendControlRequest(NULL)) != HOST_SENDCONTROL_Successful)
return ErrorCode;
- Pipe_SelectPipe(MSInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(MSInterfaceInfo->Config.DataINPipe.Address);
if ((ErrorCode = USB_Host_ClearEndpointStall(Pipe_GetBoundEndpointAddress())) != HOST_SENDCONTROL_Successful)
return ErrorCode;
- Pipe_SelectPipe(MSInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(MSInterfaceInfo->Config.DataOUTPipe.Address);
if ((ErrorCode = USB_Host_ClearEndpointStall(Pipe_GetBoundEndpointAddress())) != HOST_SENDCONTROL_Successful)
return ErrorCode;
diff --git a/LUFA/Drivers/USB/Class/Host/MassStorageClassHost.h b/LUFA/Drivers/USB/Class/Host/MassStorageClassHost.h
index 25d7e1e5e..a8763dd5b 100644
--- a/LUFA/Drivers/USB/Class/Host/MassStorageClassHost.h
+++ b/LUFA/Drivers/USB/Class/Host/MassStorageClassHost.h
@@ -83,11 +83,8 @@
{
struct
{
- uint8_t DataINPipeNumber; /**< Pipe number of the Mass Storage interface's IN data pipe. */
- bool DataINPipeDoubleBank; /**< Indicates if the Mass Storage interface's IN data pipe should use double banking. */
-
- uint8_t DataOUTPipeNumber; /**< Pipe number of the Mass Storage interface's OUT data pipe. */
- bool DataOUTPipeDoubleBank; /**< Indicates if the Mass Storage interface's OUT data pipe should use double banking. */
+ USB_Pipe_Table_t DataINPipe; /**< Data IN Pipe configuration table. */
+ USB_Pipe_Table_t DataOUTPipe; /**< Data OUT Pipe configuration table. */
} Config; /**< Config data for the USB class interface within the device. All elements in this section
* <b>must</b> be set or the interface will fail to enumerate and operate correctly.
*/
@@ -99,9 +96,6 @@
*/
uint8_t InterfaceNumber; /**< Interface index of the Mass Storage interface within the attached device. */
- uint16_t DataINPipeSize; /**< Size in bytes of the Mass Storage interface's IN data pipe. */
- uint16_t DataOUTPipeSize; /**< Size in bytes of the Mass Storage interface's OUT data pipe. */
-
uint32_t TransactionTag; /**< Current transaction tag for data synchronizing of packets. */
} State; /**< State data for the USB class interface within the device. All elements in this section
* <b>may</b> be set to initial values, but may also be ignored to default to sane values when
diff --git a/LUFA/Drivers/USB/Class/Host/PrinterClassHost.c b/LUFA/Drivers/USB/Class/Host/PrinterClassHost.c
index 379ccb01c..dd33b115b 100644
--- a/LUFA/Drivers/USB/Class/Host/PrinterClassHost.c
+++ b/LUFA/Drivers/USB/Class/Host/PrinterClassHost.c
@@ -78,45 +78,19 @@ uint8_t PRNT_Host_ConfigurePipes(USB_ClassInfo_PRNT_Host_t* const PRNTInterfaceI
DataOUTEndpoint = EndpointData;
}
- for (uint8_t PipeNum = 1; PipeNum < PIPE_TOTAL_PIPES; PipeNum++)
- {
- uint16_t Size;
- uint8_t Type;
- uint8_t Token;
- uint8_t EndpointAddress;
- bool DoubleBanked;
-
- if (PipeNum == PRNTInterfaceInfo->Config.DataINPipeNumber)
- {
- Size = le16_to_cpu(DataINEndpoint->EndpointSize);
- EndpointAddress = DataINEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_IN;
- Type = EP_TYPE_BULK;
- DoubleBanked = PRNTInterfaceInfo->Config.DataINPipeDoubleBank;
-
- PRNTInterfaceInfo->State.DataINPipeSize = DataINEndpoint->EndpointSize;
- }
- else if (PipeNum == PRNTInterfaceInfo->Config.DataOUTPipeNumber)
- {
- Size = le16_to_cpu(DataOUTEndpoint->EndpointSize);
- EndpointAddress = DataOUTEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_OUT;
- Type = EP_TYPE_BULK;
- DoubleBanked = PRNTInterfaceInfo->Config.DataOUTPipeDoubleBank;
-
- PRNTInterfaceInfo->State.DataOUTPipeSize = DataOUTEndpoint->EndpointSize;
- }
- else
- {
- continue;
- }
-
- if (!(Pipe_ConfigurePipe(PipeNum, Type, Token, EndpointAddress, Size,
- DoubleBanked ? PIPE_BANK_DOUBLE : PIPE_BANK_SINGLE)))
- {
- return PRNT_ENUMERROR_PipeConfigurationFailed;
- }
- }
+ PRNTInterfaceInfo->Config.DataINPipe.Size = le16_to_cpu(DataINEndpoint->EndpointSize);
+ PRNTInterfaceInfo->Config.DataINPipe.EndpointAddress = DataINEndpoint->EndpointAddress;
+ PRNTInterfaceInfo->Config.DataINPipe.Type = EP_TYPE_BULK;
+
+ PRNTInterfaceInfo->Config.DataOUTPipe.Size = le16_to_cpu(DataOUTEndpoint->EndpointSize);
+ PRNTInterfaceInfo->Config.DataOUTPipe.EndpointAddress = DataOUTEndpoint->EndpointAddress;
+ PRNTInterfaceInfo->Config.DataOUTPipe.Type = EP_TYPE_BULK;
+
+ if (!(Pipe_ConfigurePipeTable(&PRNTInterfaceInfo->Config.DataINPipe, 1)))
+ return false;
+
+ if (!(Pipe_ConfigurePipeTable(&PRNTInterfaceInfo->Config.DataOUTPipe, 1)))
+ return false;
PRNTInterfaceInfo->State.InterfaceNumber = PrinterInterface->InterfaceNumber;
PRNTInterfaceInfo->State.AlternateSetting = PrinterInterface->AlternateSetting;
@@ -229,7 +203,7 @@ uint8_t PRNT_Host_Flush(USB_ClassInfo_PRNT_Host_t* const PRNTInterfaceInfo)
uint8_t ErrorCode;
- Pipe_SelectPipe(PRNTInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(PRNTInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
if (!(Pipe_BytesInPipe()))
@@ -260,7 +234,7 @@ uint8_t PRNT_Host_SendByte(USB_ClassInfo_PRNT_Host_t* const PRNTInterfaceInfo,
uint8_t ErrorCode;
- Pipe_SelectPipe(PRNTInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(PRNTInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
if (!(Pipe_IsReadWriteAllowed()))
@@ -285,7 +259,7 @@ uint8_t PRNT_Host_SendString(USB_ClassInfo_PRNT_Host_t* const PRNTInterfaceInfo,
if ((USB_HostState != HOST_STATE_Configured) || !(PRNTInterfaceInfo->State.IsActive))
return PIPE_RWSTREAM_DeviceDisconnected;
- Pipe_SelectPipe(PRNTInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(PRNTInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
if ((ErrorCode = Pipe_Write_Stream_LE(String, strlen(String), NULL)) != PIPE_RWSTREAM_NoError)
@@ -309,7 +283,7 @@ uint8_t PRNT_Host_SendData(USB_ClassInfo_PRNT_Host_t* const PRNTInterfaceInfo,
if ((USB_HostState != HOST_STATE_Configured) || !(PRNTInterfaceInfo->State.IsActive))
return PIPE_RWSTREAM_DeviceDisconnected;
- Pipe_SelectPipe(PRNTInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(PRNTInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
if ((ErrorCode = Pipe_Write_Stream_LE(Buffer, Length, NULL)) != PIPE_RWSTREAM_NoError)
@@ -329,7 +303,7 @@ uint16_t PRNT_Host_BytesReceived(USB_ClassInfo_PRNT_Host_t* const PRNTInterfaceI
if ((USB_HostState != HOST_STATE_Configured) || !(PRNTInterfaceInfo->State.IsActive))
return 0;
- Pipe_SelectPipe(PRNTInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(PRNTInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
if (Pipe_IsINReceived())
@@ -361,7 +335,7 @@ int16_t PRNT_Host_ReceiveByte(USB_ClassInfo_PRNT_Host_t* const PRNTInterfaceInfo
int16_t ReceivedByte = -1;
- Pipe_SelectPipe(PRNTInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(PRNTInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
if (Pipe_IsINReceived())
diff --git a/LUFA/Drivers/USB/Class/Host/PrinterClassHost.h b/LUFA/Drivers/USB/Class/Host/PrinterClassHost.h
index c8c997f74..25878276f 100644
--- a/LUFA/Drivers/USB/Class/Host/PrinterClassHost.h
+++ b/LUFA/Drivers/USB/Class/Host/PrinterClassHost.h
@@ -79,11 +79,8 @@
{
struct
{
- uint8_t DataINPipeNumber; /**< Pipe number of the Printer interface's IN data pipe. */
- bool DataINPipeDoubleBank; /**< Indicates if the Printer interface's IN data pipe should use double banking. */
-
- uint8_t DataOUTPipeNumber; /**< Pipe number of the Printer interface's OUT data pipe. */
- bool DataOUTPipeDoubleBank; /**< Indicates if the Printer interface's OUT data pipe should use double banking. */
+ USB_Pipe_Table_t DataINPipe; /**< Data IN Pipe configuration table. */
+ USB_Pipe_Table_t DataOUTPipe; /**< Data OUT Pipe configuration table. */
} Config; /**< Config data for the USB class interface within the device. All elements in this section
* <b>must</b> be set or the interface will fail to enumerate and operate correctly.
*/
@@ -95,9 +92,6 @@
*/
uint8_t InterfaceNumber; /**< Interface index of the Printer interface within the attached device. */
uint8_t AlternateSetting; /**< Alternate setting within the Printer Interface in the attached device. */
-
- uint16_t DataINPipeSize; /**< Size in bytes of the Printer interface's IN data pipe. */
- uint16_t DataOUTPipeSize; /**< Size in bytes of the Printer interface's OUT data pipe. */
} State; /**< State data for the USB class interface within the device. All elements in this section
* <b>may</b> be set to initial values, but may also be ignored to default to sane values when
* the interface is enumerated.
diff --git a/LUFA/Drivers/USB/Class/Host/RNDISClassHost.c b/LUFA/Drivers/USB/Class/Host/RNDISClassHost.c
index a03011d64..e457b5dff 100644
--- a/LUFA/Drivers/USB/Class/Host/RNDISClassHost.c
+++ b/LUFA/Drivers/USB/Class/Host/RNDISClassHost.c
@@ -101,62 +101,26 @@ uint8_t RNDIS_Host_ConfigurePipes(USB_ClassInfo_RNDIS_Host_t* const RNDISInterfa
}
}
- for (uint8_t PipeNum = 1; PipeNum < PIPE_TOTAL_PIPES; PipeNum++)
- {
- uint16_t Size;
- uint8_t Type;
- uint8_t Token;
- uint8_t EndpointAddress;
- uint8_t InterruptPeriod;
- bool DoubleBanked;
-
- if (PipeNum == RNDISInterfaceInfo->Config.DataINPipeNumber)
- {
- Size = le16_to_cpu(DataINEndpoint->EndpointSize);
- EndpointAddress = DataINEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_IN;
- Type = EP_TYPE_BULK;
- DoubleBanked = RNDISInterfaceInfo->Config.DataINPipeDoubleBank;
- InterruptPeriod = 0;
-
- RNDISInterfaceInfo->State.DataINPipeSize = DataINEndpoint->EndpointSize;
- }
- else if (PipeNum == RNDISInterfaceInfo->Config.DataOUTPipeNumber)
- {
- Size = le16_to_cpu(DataOUTEndpoint->EndpointSize);
- EndpointAddress = DataOUTEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_OUT;
- Type = EP_TYPE_BULK;
- DoubleBanked = RNDISInterfaceInfo->Config.DataOUTPipeDoubleBank;
- InterruptPeriod = 0;
-
- RNDISInterfaceInfo->State.DataOUTPipeSize = DataOUTEndpoint->EndpointSize;
- }
- else if (PipeNum == RNDISInterfaceInfo->Config.NotificationPipeNumber)
- {
- Size = le16_to_cpu(NotificationEndpoint->EndpointSize);
- EndpointAddress = NotificationEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_IN;
- Type = EP_TYPE_INTERRUPT;
- DoubleBanked = RNDISInterfaceInfo->Config.NotificationPipeDoubleBank;
- InterruptPeriod = NotificationEndpoint->PollingIntervalMS;
-
- RNDISInterfaceInfo->State.NotificationPipeSize = NotificationEndpoint->EndpointSize;
- }
- else
- {
- continue;
- }
-
- if (!(Pipe_ConfigurePipe(PipeNum, Type, Token, EndpointAddress, Size,
- DoubleBanked ? PIPE_BANK_DOUBLE : PIPE_BANK_SINGLE)))
- {
- return CDC_ENUMERROR_PipeConfigurationFailed;
- }
+ RNDISInterfaceInfo->Config.DataINPipe.Size = le16_to_cpu(DataINEndpoint->EndpointSize);
+ RNDISInterfaceInfo->Config.DataINPipe.EndpointAddress = DataINEndpoint->EndpointAddress;
+ RNDISInterfaceInfo->Config.DataINPipe.Type = EP_TYPE_BULK;
+
+ RNDISInterfaceInfo->Config.DataOUTPipe.Size = le16_to_cpu(DataOUTEndpoint->EndpointSize);
+ RNDISInterfaceInfo->Config.DataOUTPipe.EndpointAddress = DataOUTEndpoint->EndpointAddress;
+ RNDISInterfaceInfo->Config.DataOUTPipe.Type = EP_TYPE_BULK;
+
+ RNDISInterfaceInfo->Config.NotificationPipe.Size = le16_to_cpu(NotificationEndpoint->EndpointSize);
+ RNDISInterfaceInfo->Config.NotificationPipe.EndpointAddress = NotificationEndpoint->EndpointAddress;
+ RNDISInterfaceInfo->Config.NotificationPipe.Type = EP_TYPE_INTERRUPT;
+
+ if (!(Pipe_ConfigurePipeTable(&RNDISInterfaceInfo->Config.DataINPipe, 1)))
+ return false;
+
+ if (!(Pipe_ConfigurePipeTable(&RNDISInterfaceInfo->Config.DataOUTPipe, 1)))
+ return false;
- if (InterruptPeriod)
- Pipe_SetInterruptPeriod(InterruptPeriod);
- }
+ if (!(Pipe_ConfigurePipeTable(&RNDISInterfaceInfo->Config.NotificationPipe, 1)))
+ return false;
RNDISInterfaceInfo->State.ControlInterfaceNumber = RNDISControlInterface->InterfaceNumber;
RNDISInterfaceInfo->State.IsActive = true;
@@ -419,7 +383,7 @@ bool RNDIS_Host_IsPacketReceived(USB_ClassInfo_RNDIS_Host_t* const RNDISInterfac
if ((USB_HostState != HOST_STATE_Configured) || !(RNDISInterfaceInfo->State.IsActive))
return false;
- Pipe_SelectPipe(RNDISInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(RNDISInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
PacketWaiting = Pipe_IsINReceived();
@@ -437,7 +401,7 @@ uint8_t RNDIS_Host_ReadPacket(USB_ClassInfo_RNDIS_Host_t* const RNDISInterfaceIn
if ((USB_HostState != HOST_STATE_Configured) || !(RNDISInterfaceInfo->State.IsActive))
return PIPE_READYWAIT_DeviceDisconnected;
- Pipe_SelectPipe(RNDISInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(RNDISInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
if (!(Pipe_IsReadWriteAllowed()))
@@ -491,7 +455,7 @@ uint8_t RNDIS_Host_SendPacket(USB_ClassInfo_RNDIS_Host_t* const RNDISInterfaceIn
DeviceMessage.DataOffset = CPU_TO_LE32(sizeof(RNDIS_Packet_Message_t) - sizeof(RNDIS_Message_Header_t));
DeviceMessage.DataLength = cpu_to_le32(PacketLength);
- Pipe_SelectPipe(RNDISInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(RNDISInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
if ((ErrorCode = Pipe_Write_Stream_LE(&DeviceMessage, sizeof(RNDIS_Packet_Message_t),
diff --git a/LUFA/Drivers/USB/Class/Host/RNDISClassHost.h b/LUFA/Drivers/USB/Class/Host/RNDISClassHost.h
index 085bde22c..57087edf9 100644
--- a/LUFA/Drivers/USB/Class/Host/RNDISClassHost.h
+++ b/LUFA/Drivers/USB/Class/Host/RNDISClassHost.h
@@ -80,14 +80,9 @@
{
struct
{
- uint8_t DataINPipeNumber; /**< Pipe number of the RNDIS interface's IN data pipe. */
- bool DataINPipeDoubleBank; /**< Indicates if the RNDIS interface's IN data pipe should use double banking. */
-
- uint8_t DataOUTPipeNumber; /**< Pipe number of the RNDIS interface's OUT data pipe. */
- bool DataOUTPipeDoubleBank; /**< Indicates if the RNDIS interface's OUT data pipe should use double banking. */
-
- uint8_t NotificationPipeNumber; /**< Pipe number of the RNDIS interface's IN notification endpoint, if used. */
- bool NotificationPipeDoubleBank; /**< Indicates if the RNDIS interface's notification pipe should use double banking. */
+ USB_Pipe_Table_t DataINPipe; /**< Data IN Pipe configuration table. */
+ USB_Pipe_Table_t DataOUTPipe; /**< Data OUT Pipe configuration table. */
+ USB_Pipe_Table_t NotificationPipe; /**< Notification IN Pipe configuration table. */
uint32_t HostMaxPacketSize; /**< Maximum size of a packet which can be buffered by the host. */
} Config; /**< Config data for the USB class interface within the device. All elements in this section
@@ -101,10 +96,6 @@
*/
uint8_t ControlInterfaceNumber; /**< Interface index of the RNDIS control interface within the attached device. */
- uint16_t DataINPipeSize; /**< Size in bytes of the RNDIS interface's IN data pipe. */
- uint16_t DataOUTPipeSize; /**< Size in bytes of the RNDIS interface's OUT data pipe. */
- uint16_t NotificationPipeSize; /**< Size in bytes of the RNDIS interface's IN notification pipe, if used. */
-
uint32_t DeviceMaxPacketSize; /**< Maximum size of a packet which can be buffered by the attached RNDIS device. */
uint32_t RequestID; /**< Request ID counter to give a unique ID for each command/response pair. */
diff --git a/LUFA/Drivers/USB/Class/Host/StillImageClassHost.c b/LUFA/Drivers/USB/Class/Host/StillImageClassHost.c
index 2b5514a28..5c18d7503 100644
--- a/LUFA/Drivers/USB/Class/Host/StillImageClassHost.c
+++ b/LUFA/Drivers/USB/Class/Host/StillImageClassHost.c
@@ -87,63 +87,27 @@ uint8_t SI_Host_ConfigurePipes(USB_ClassInfo_SI_Host_t* const SIInterfaceInfo,
}
}
- for (uint8_t PipeNum = 1; PipeNum < PIPE_TOTAL_PIPES; PipeNum++)
- {
- uint16_t Size;
- uint8_t Type;
- uint8_t Token;
- uint8_t EndpointAddress;
- uint8_t InterruptPeriod;
- bool DoubleBanked;
-
- if (PipeNum == SIInterfaceInfo->Config.DataINPipeNumber)
- {
- Size = DataINEndpoint->EndpointSize;
- EndpointAddress = DataINEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_IN;
- Type = EP_TYPE_BULK;
- DoubleBanked = SIInterfaceInfo->Config.DataINPipeDoubleBank;
- InterruptPeriod = 0;
-
- SIInterfaceInfo->State.DataINPipeSize = DataINEndpoint->EndpointSize;
- }
- else if (PipeNum == SIInterfaceInfo->Config.DataOUTPipeNumber)
- {
- Size = DataOUTEndpoint->EndpointSize;
- EndpointAddress = DataOUTEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_OUT;
- Type = EP_TYPE_BULK;
- DoubleBanked = SIInterfaceInfo->Config.DataOUTPipeDoubleBank;
- InterruptPeriod = 0;
-
- SIInterfaceInfo->State.DataOUTPipeSize = DataOUTEndpoint->EndpointSize;
- }
- else if (PipeNum == SIInterfaceInfo->Config.EventsPipeNumber)
- {
- Size = EventsEndpoint->EndpointSize;
- EndpointAddress = EventsEndpoint->EndpointAddress;
- Token = PIPE_TOKEN_IN;
- Type = EP_TYPE_INTERRUPT;
- DoubleBanked = SIInterfaceInfo->Config.EventsPipeDoubleBank;
- InterruptPeriod = EventsEndpoint->PollingIntervalMS;
-
- SIInterfaceInfo->State.EventsPipeSize = EventsEndpoint->EndpointSize;
- }
- else
- {
- continue;
- }
-
- if (!(Pipe_ConfigurePipe(PipeNum, Type, Token, EndpointAddress, Size,
- DoubleBanked ? PIPE_BANK_DOUBLE : PIPE_BANK_SINGLE)))
- {
- return SI_ENUMERROR_PipeConfigurationFailed;
- }
-
- if (InterruptPeriod)
- Pipe_SetInterruptPeriod(InterruptPeriod);
- }
+ SIInterfaceInfo->Config.DataINPipe.Size = le16_to_cpu(DataINEndpoint->EndpointSize);
+ SIInterfaceInfo->Config.DataINPipe.EndpointAddress = DataINEndpoint->EndpointAddress;
+ SIInterfaceInfo->Config.DataINPipe.Type = EP_TYPE_BULK;
+
+ SIInterfaceInfo->Config.DataOUTPipe.Size = le16_to_cpu(DataOUTEndpoint->EndpointSize);
+ SIInterfaceInfo->Config.DataOUTPipe.EndpointAddress = DataOUTEndpoint->EndpointAddress;
+ SIInterfaceInfo->Config.DataOUTPipe.Type = EP_TYPE_BULK;
+
+ SIInterfaceInfo->Config.EventsPipe.Size = le16_to_cpu(EventsEndpoint->EndpointSize);
+ SIInterfaceInfo->Config.EventsPipe.EndpointAddress = EventsEndpoint->EndpointAddress;
+ SIInterfaceInfo->Config.EventsPipe.Type = EP_TYPE_INTERRUPT;
+
+ if (!(Pipe_ConfigurePipeTable(&SIInterfaceInfo->Config.DataINPipe, 1)))
+ return false;
+
+ if (!(Pipe_ConfigurePipeTable(&SIInterfaceInfo->Config.DataOUTPipe, 1)))
+ return false;
+ if (!(Pipe_ConfigurePipeTable(&SIInterfaceInfo->Config.EventsPipe, 1)))
+ return false;
+
SIInterfaceInfo->State.InterfaceNumber = StillImageInterface->InterfaceNumber;
SIInterfaceInfo->State.IsActive = true;
@@ -204,7 +168,7 @@ uint8_t SI_Host_SendBlockHeader(USB_ClassInfo_SI_Host_t* const SIInterfaceInfo,
if (SIInterfaceInfo->State.IsSessionOpen)
PIMAHeader->TransactionID = cpu_to_le32(SIInterfaceInfo->State.TransactionID++);
- Pipe_SelectPipe(SIInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(SIInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
if ((ErrorCode = Pipe_Write_Stream_LE(PIMAHeader, PIMA_COMMAND_SIZE(0), NULL)) != PIPE_RWSTREAM_NoError)
@@ -233,7 +197,7 @@ uint8_t SI_Host_ReceiveBlockHeader(USB_ClassInfo_SI_Host_t* const SIInterfaceInf
if ((USB_HostState != HOST_STATE_Configured) || !(SIInterfaceInfo->State.IsActive))
return PIPE_RWSTREAM_DeviceDisconnected;
- Pipe_SelectPipe(SIInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(SIInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
while (!(Pipe_IsINReceived()))
@@ -249,7 +213,7 @@ uint8_t SI_Host_ReceiveBlockHeader(USB_ClassInfo_SI_Host_t* const SIInterfaceInf
}
Pipe_Freeze();
- Pipe_SelectPipe(SIInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(SIInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
if (Pipe_IsStalled())
@@ -259,7 +223,7 @@ uint8_t SI_Host_ReceiveBlockHeader(USB_ClassInfo_SI_Host_t* const SIInterfaceInf
}
Pipe_Freeze();
- Pipe_SelectPipe(SIInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(SIInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
if (Pipe_IsStalled())
@@ -298,7 +262,7 @@ uint8_t SI_Host_SendData(USB_ClassInfo_SI_Host_t* const SIInterfaceInfo,
if ((USB_HostState != HOST_STATE_Configured) || !(SIInterfaceInfo->State.IsActive))
return PIPE_RWSTREAM_DeviceDisconnected;
- Pipe_SelectPipe(SIInterfaceInfo->Config.DataOUTPipeNumber);
+ Pipe_SelectPipe(SIInterfaceInfo->Config.DataOUTPipe.Address);
Pipe_Unfreeze();
ErrorCode = Pipe_Write_Stream_LE(Buffer, Bytes, NULL);
@@ -318,7 +282,7 @@ uint8_t SI_Host_ReadData(USB_ClassInfo_SI_Host_t* const SIInterfaceInfo,
if ((USB_HostState != HOST_STATE_Configured) || !(SIInterfaceInfo->State.IsActive))
return PIPE_RWSTREAM_DeviceDisconnected;
- Pipe_SelectPipe(SIInterfaceInfo->Config.DataINPipeNumber);
+ Pipe_SelectPipe(SIInterfaceInfo->Config.DataINPipe.Address);
Pipe_Unfreeze();
ErrorCode = Pipe_Read_Stream_LE(Buffer, Bytes, NULL);
@@ -335,7 +299,7 @@ bool SI_Host_IsEventReceived(USB_ClassInfo_SI_Host_t* const SIInterfaceInfo)
if ((USB_HostState != HOST_STATE_Configured) || !(SIInterfaceInfo->State.IsActive))
return false;
- Pipe_SelectPipe(SIInterfaceInfo->Config.EventsPipeNumber);
+ Pipe_SelectPipe(SIInterfaceInfo->Config.EventsPipe.Address);
Pipe_Unfreeze();
if (Pipe_BytesInPipe())
@@ -354,7 +318,7 @@ uint8_t SI_Host_ReceiveEventHeader(USB_ClassInfo_SI_Host_t* const SIInterfaceInf
if ((USB_HostState != HOST_STATE_Configured) || !(SIInterfaceInfo->State.IsActive))
return PIPE_RWSTREAM_DeviceDisconnected;
- Pipe_SelectPipe(SIInterfaceInfo->Config.EventsPipeNumber);
+ Pipe_SelectPipe(SIInterfaceInfo->Config.EventsPipe.Address);
Pipe_Unfreeze();
ErrorCode = Pipe_Read_Stream_LE(PIMAHeader, sizeof(PIMA_Container_t), NULL);
diff --git a/LUFA/Drivers/USB/Class/Host/StillImageClassHost.h b/LUFA/Drivers/USB/Class/Host/StillImageClassHost.h
index 4cda70d2e..be616b459 100644
--- a/LUFA/Drivers/USB/Class/Host/StillImageClassHost.h
+++ b/LUFA/Drivers/USB/Class/Host/StillImageClassHost.h
@@ -83,14 +83,9 @@
{
struct
{
- uint8_t DataINPipeNumber; /**< Pipe number of the Still Image interface's IN data pipe. */
- bool DataINPipeDoubleBank; /**< Indicates if the Still Image interface's IN data pipe should use double banking. */
-
- uint8_t DataOUTPipeNumber; /**< Pipe number of the Still Image interface's OUT data pipe. */
- bool DataOUTPipeDoubleBank; /**< Indicates if the Still Image interface's OUT data pipe should use double banking. */
-
- uint8_t EventsPipeNumber; /**< Pipe number of the Still Image interface's IN events endpoint, if used. */
- bool EventsPipeDoubleBank; /**< Indicates if the Still Image interface's events data pipe should use double banking. */
+ USB_Pipe_Table_t DataINPipe; /**< Data IN Pipe configuration table. */
+ USB_Pipe_Table_t DataOUTPipe; /**< Data OUT Pipe configuration table. */
+ USB_Pipe_Table_t EventsPipe; /**< Event notification IN Pipe configuration table. */
} Config; /**< Config data for the USB class interface within the device. All elements in this section
* <b>must</b> be set or the interface will fail to enumerate and operate correctly.
*/
@@ -102,10 +97,6 @@
*/
uint8_t InterfaceNumber; /**< Interface index of the Still Image interface within the attached device. */
- uint16_t DataINPipeSize; /**< Size in bytes of the Still Image interface's IN data pipe. */
- uint16_t DataOUTPipeSize; /**< Size in bytes of the Still Image interface's OUT data pipe. */
- uint16_t EventsPipeSize; /**< Size in bytes of the Still Image interface's IN events pipe. */
-
bool IsSessionOpen; /**< Indicates if a PIMA session is currently open with the attached device. */
uint32_t TransactionID; /**< Transaction ID for the next transaction to send to the device. */
} State; /**< State data for the USB class interface within the device. All elements in this section
diff --git a/LUFA/Drivers/USB/Core/AVR8/Endpoint_AVR8.c b/LUFA/Drivers/USB/Core/AVR8/Endpoint_AVR8.c
index bcf904d99..4440b7631 100644
--- a/LUFA/Drivers/USB/Core/AVR8/Endpoint_AVR8.c
+++ b/LUFA/Drivers/USB/Core/AVR8/Endpoint_AVR8.c
@@ -42,6 +42,21 @@
uint8_t USB_Device_ControlEndpointSize = ENDPOINT_CONTROLEP_DEFAULT_SIZE;
#endif
+bool Endpoint_ConfigureEndpointTable(const USB_Endpoint_Table_t* const Table,
+ const uint8_t Entries)
+{
+ for (uint8_t i = 0; i < Entries; i++)
+ {
+ if (!(Table[i].Address))
+ continue;
+
+ if (!(Endpoint_ConfigureEndpoint(Table[i].Address, Table[i].Type, Table[i].Size, Table[i].Banks)))
+ return false;
+ }
+
+ return true;
+}
+
bool Endpoint_ConfigureEndpoint_Prv(const uint8_t Number,
const uint8_t UECFG0XData,
const uint8_t UECFG1XData)
diff --git a/LUFA/Drivers/USB/Core/AVR8/Endpoint_AVR8.h b/LUFA/Drivers/USB/Core/AVR8/Endpoint_AVR8.h
index 10f69a8fd..37ff220e3 100644
--- a/LUFA/Drivers/USB/Core/AVR8/Endpoint_AVR8.h
+++ b/LUFA/Drivers/USB/Core/AVR8/Endpoint_AVR8.h
@@ -89,35 +89,6 @@
/* Private Interface - For use in library only: */
#if !defined(__DOXYGEN__)
- /* Macros: */
- #define _ENDPOINT_GET_MAXSIZE(EPIndex) _ENDPOINT_GET_MAXSIZE2(ENDPOINT_DETAILS_EP ## EPIndex)
- #define _ENDPOINT_GET_MAXSIZE2(EPDetails) _ENDPOINT_GET_MAXSIZE3(EPDetails)
- #define _ENDPOINT_GET_MAXSIZE3(MaxSize, Banks) (MaxSize)
-
- #define _ENDPOINT_GET_BANKS(EPIndex) _ENDPOINT_GET_BANKS2(ENDPOINT_DETAILS_EP ## EPIndex)
- #define _ENDPOINT_GET_BANKS2(EPDetails) _ENDPOINT_GET_BANKS3(EPDetails)
- #define _ENDPOINT_GET_BANKS3(MaxSize, Banks) (Banks)
-
- #if defined(USB_SERIES_4_AVR) || defined(USB_SERIES_6_AVR) || defined(USB_SERIES_7_AVR)
- #define ENDPOINT_DETAILS_MAXEP 7
-
- #define ENDPOINT_DETAILS_EP0 64, 1
- #define ENDPOINT_DETAILS_EP1 256, 2
- #define ENDPOINT_DETAILS_EP2 64, 2
- #define ENDPOINT_DETAILS_EP3 64, 2
- #define ENDPOINT_DETAILS_EP4 64, 2
- #define ENDPOINT_DETAILS_EP5 64, 2
- #define ENDPOINT_DETAILS_EP6 64, 2
- #else
- #define ENDPOINT_DETAILS_MAXEP 5
-
- #define ENDPOINT_DETAILS_EP0 64, 1
- #define ENDPOINT_DETAILS_EP1 64, 1
- #define ENDPOINT_DETAILS_EP2 64, 1
- #define ENDPOINT_DETAILS_EP3 64, 2
- #define ENDPOINT_DETAILS_EP4 64, 2
- #endif
-
/* Inline Functions: */
static inline uint8_t Endpoint_BytesToEPSizeMask(const uint16_t Bytes) ATTR_WARN_UNUSED_RESULT ATTR_CONST
ATTR_ALWAYS_INLINE;
@@ -145,23 +116,6 @@
/* Public Interface - May be used in end-application: */
/* Macros: */
- /** \name Endpoint Bank Mode Masks */
- //@{
- /** Mask for the bank mode selection for the \ref Endpoint_ConfigureEndpoint() macro. This indicates
- * that the endpoint should have one single bank, which requires less USB FIFO memory but results
- * in slower transfers as only one USB device (the AVR or the host) can access the endpoint's
- * bank at the one time.
- */
- #define ENDPOINT_BANK_SINGLE (0 << EPBK0)
-
- /** Mask for the bank mode selection for the \ref Endpoint_ConfigureEndpoint() macro. This indicates
- * that the endpoint should have two banks, which requires more USB FIFO memory but results
- * in faster transfers as one USB device (the AVR or the host) can access one bank while the other
- * accesses the second bank.
- */
- #define ENDPOINT_BANK_DOUBLE (1 << EPBK0)
- //@}
-
#if (!defined(FIXED_CONTROL_ENDPOINT_SIZE) || defined(__DOXYGEN__))
/** Default size of the default control endpoint's bank, until altered by the control endpoint bank size
* value in the device descriptor. Not available if the \c FIXED_CONTROL_ENDPOINT_SIZE token is defined.
@@ -169,30 +123,16 @@
#define ENDPOINT_CONTROLEP_DEFAULT_SIZE 8
#endif
- /** Retrieves the maximum bank size in bytes of a given endpoint.
- *
- * \attention This macro will only work correctly on endpoint indexes that are compile-time constants
- * defined by the preprocessor.
- *
- * \param[in] EPIndex Endpoint number, a value between 0 and (\ref ENDPOINT_TOTAL_ENDPOINTS - 1)
- */
- #define ENDPOINT_MAX_SIZE(EPIndex) _ENDPOINT_GET_MAXSIZE(EPIndex)
-
- /** Retrieves the total number of banks supported by the given endpoint.
- *
- * \attention This macro will only work correctly on endpoint indexes that are compile-time constants
- * defined by the preprocessor.
- *
- * \param[in] EPIndex Endpoint number, a value between 0 and (\ref ENDPOINT_TOTAL_ENDPOINTS - 1)
- */
- #define ENDPOINT_BANKS_SUPPORTED(EPIndex) _ENDPOINT_GET_BANKS(EPIndex)
-
#if !defined(CONTROL_ONLY_DEVICE) || defined(__DOXYGEN__)
- /** Total number of endpoints (including the default control endpoint at address 0) which may
- * be used in the device. Different USB AVR models support different amounts of endpoints,
- * this value reflects the maximum number of endpoints for the currently selected AVR model.
- */
- #define ENDPOINT_TOTAL_ENDPOINTS ENDPOINT_DETAILS_MAXEP
+ #if defined(USB_SERIES_4_AVR) || defined(USB_SERIES_6_AVR) || defined(USB_SERIES_7_AVR)
+ #define ENDPOINT_TOTAL_ENDPOINTS 7
+ #else
+ /** Total number of endpoints (including the default control endpoint at address 0) which may
+ * be used in the device. Different USB AVR models support different amounts of endpoints,
+ * this value reflects the maximum number of endpoints for the currently selected AVR model.
+ */
+ #define ENDPOINT_TOTAL_ENDPOINTS 5
+ #endif
#else
#define ENDPOINT_TOTAL_ENDPOINTS 1
#endif
@@ -222,28 +162,20 @@
};
/* Inline Functions: */
- /** Configures the specified endpoint number with the given endpoint type, direction, bank size
- * and banking mode. Once configured, the endpoint may be read from or written to, depending
- * on its direction.
+ /** Configures the specified endpoint address with the given endpoint type, bank size and number of hardware
+ * banks. Once configured, the endpoint may be read from or written to, depending on its direction.
*
- * \param[in] Number Endpoint number to configure. This must be more than 0 and less than
- * \ref ENDPOINT_TOTAL_ENDPOINTS.
+ * \param[in] Address Endpoint address to configure.
*
* \param[in] Type Type of endpoint to configure, a \c EP_TYPE_* mask. Not all endpoint types
* are available on Low Speed USB devices - refer to the USB 2.0 specification.
*
- * \param[in] Direction Endpoint data direction, either \ref ENDPOINT_DIR_OUT or \ref ENDPOINT_DIR_IN.
- * All endpoints (except Control type) are unidirectional - data may only be read
- * from or written to the endpoint bank based on its direction, not both.
- *
* \param[in] Size Size of the endpoint's bank, where packets are stored before they are transmitted
* to the USB host, or after they have been received from the USB host (depending on
* the endpoint's data direction). The bank size must indicate the maximum packet size
* that the endpoint can handle.
*
- * \param[in] Banks Number of banks to use for the endpoint being configured, an \c ENDPOINT_BANK_* mask.
- * More banks uses more USB DPRAM, but offers better performance. Isochronous type
- * endpoints <b>must</b> have at least two banks.
+ * \param[in] Banks Number of banks to use for the endpoint being configured.
*
* \attention When the \c ORDERED_EP_CONFIG compile time option is used, Endpoints <b>must</b> be configured in
* ascending order, or bank corruption will occur.
@@ -261,19 +193,18 @@
*
* \return Boolean \c true if the configuration succeeded, \c false otherwise.
*/
- static inline bool Endpoint_ConfigureEndpoint(const uint8_t Number,
+ static inline bool Endpoint_ConfigureEndpoint(const uint8_t Address,
const uint8_t Type,
- const uint8_t Direction,
const uint16_t Size,
const uint8_t Banks) ATTR_ALWAYS_INLINE;
- static inline bool Endpoint_ConfigureEndpoint(const uint8_t Number,
+ static inline bool Endpoint_ConfigureEndpoint(const uint8_t Address,
const uint8_t Type,
- const uint8_t Direction,
const uint16_t Size,
const uint8_t Banks)
{
- return Endpoint_ConfigureEndpoint_Prv(Number, ((Type << EPTYPE0) | (Direction ? (1 << EPDIR) : 0)),
- ((1 << ALLOC) | Banks | Endpoint_BytesToEPSizeMask(Size)));
+ return Endpoint_ConfigureEndpoint_Prv((Address & ENDPOINT_EPNUM_MASK),
+ ((Type << EPTYPE0) | ((Address & ENDPOINT_DIR_IN) ? (1 << EPDIR) : 0)),
+ ((1 << ALLOC) | ((Banks > 1) ? (1 << EPBK0) : 0) | Endpoint_BytesToEPSizeMask(Size)));
}
/** Indicates the number of bytes currently stored in the current endpoint's selected bank.
@@ -294,9 +225,19 @@
#endif
}
+ /** Determines the currently selected endpoint's direction.
+ *
+ * \return The currently selected endpoint's direction, as a \c ENDPOINT_DIR_* mask.
+ */
+ static inline uint8_t Endpoint_GetEndpointDirection(void) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
+ static inline uint8_t Endpoint_GetEndpointDirection(void)
+ {
+ return (UECFG0X & (1 << EPDIR)) ? ENDPOINT_DIR_IN : ENDPOINT_DIR_OUT;
+ }
+
/** Get the endpoint address of the currently selected endpoint. This is typically used to save
- * the currently selected endpoint number so that it can be restored after another endpoint has
- * been manipulated.
+ * the currently selected endpoint so that it can be restored after another endpoint has been
+ * manipulated.
*
* \return Index of the currently selected endpoint.
*/
@@ -304,38 +245,36 @@
static inline uint8_t Endpoint_GetCurrentEndpoint(void)
{
#if !defined(CONTROL_ONLY_DEVICE)
- return (UENUM & ENDPOINT_EPNUM_MASK);
+ return ((UENUM & ENDPOINT_EPNUM_MASK) | Endpoint_GetEndpointDirection());
#else
return ENDPOINT_CONTROLEP;
#endif
}
- /** Selects the given endpoint number. If the address from the device descriptors is used, the
- * value should be masked with the \ref ENDPOINT_EPNUM_MASK constant to extract only the endpoint
- * number (and discarding the endpoint direction bit).
+ /** Selects the given endpoint address.
*
- * Any endpoint operations which do not require the endpoint number to be indicated will operate on
+ * Any endpoint operations which do not require the endpoint address to be indicated will operate on
* the currently selected endpoint.
*
- * \param[in] EndpointNumber Endpoint number to select.
+ * \param[in] Address Endpoint address to select.
*/
- static inline void Endpoint_SelectEndpoint(const uint8_t EndpointNumber) ATTR_ALWAYS_INLINE;
- static inline void Endpoint_SelectEndpoint(const uint8_t EndpointNumber)
+ static inline void Endpoint_SelectEndpoint(const uint8_t Address) ATTR_ALWAYS_INLINE;
+ static inline void Endpoint_SelectEndpoint(const uint8_t Address)
{
#if !defined(CONTROL_ONLY_DEVICE)
- UENUM = EndpointNumber;
+ UENUM = (Address & ENDPOINT_EPNUM_MASK);
#endif
}
/** Resets the endpoint bank FIFO. This clears all the endpoint banks and resets the USB controller's
* data In and Out pointers to the bank's contents.
*
- * \param[in] EndpointNumber Endpoint number whose FIFO buffers are to be reset.
+ * \param[in] Address Endpoint address whose FIFO buffers are to be reset.
*/
- static inline void Endpoint_ResetEndpoint(const uint8_t EndpointNumber) ATTR_ALWAYS_INLINE;
- static inline void Endpoint_ResetEndpoint(const uint8_t EndpointNumber)
+ static inline void Endpoint_ResetEndpoint(const uint8_t Address) ATTR_ALWAYS_INLINE;
+ static inline void Endpoint_ResetEndpoint(const uint8_t Address)
{
- UERST = (1 << EndpointNumber);
+ UERST = (1 << (Address & ENDPOINT_EPNUM_MASK));
UERST = 0;
}
@@ -441,14 +380,14 @@
/** Determines if the specified endpoint number has interrupted (valid only for INTERRUPT type
* endpoints).
*
- * \param[in] EndpointNumber Index of the endpoint whose interrupt flag should be tested.
+ * \param[in] Address Address of the endpoint whose interrupt flag should be tested.
*
* \return Boolean \c true if the specified endpoint has interrupted, \c false otherwise.
*/
- static inline bool Endpoint_HasEndpointInterrupted(const uint8_t EndpointNumber) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
- static inline bool Endpoint_HasEndpointInterrupted(const uint8_t EndpointNumber)
+ static inline bool Endpoint_HasEndpointInterrupted(const uint8_t Address) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
+ static inline bool Endpoint_HasEndpointInterrupted(const uint8_t Address)
{
- return ((Endpoint_GetEndpointInterrupts() & (1 << EndpointNumber)) ? true : false);
+ return ((Endpoint_GetEndpointInterrupts() & (1 << (Address & ENDPOINT_EPNUM_MASK))) ? true : false);
}
/** Determines if the selected IN endpoint is ready for a new packet to be sent to the host.
@@ -576,16 +515,6 @@
UECONX |= (1 << RSTDT);
}
- /** Determines the currently selected endpoint's direction.
- *
- * \return The currently selected endpoint's direction, as a \c ENDPOINT_DIR_* mask.
- */
- static inline uint8_t Endpoint_GetEndpointDirection(void) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
- static inline uint8_t Endpoint_GetEndpointDirection(void)
- {
- return (UECFG0X & (1 << EPDIR)) ? ENDPOINT_DIR_IN : ENDPOINT_DIR_OUT;
- }
-
/** Sets the direction of the currently selected endpoint.
*
* \param[in] DirectionMask New endpoint direction, as a \c ENDPOINT_DIR_* mask.
@@ -841,6 +770,20 @@
#endif
/* Function Prototypes: */
+ /** Configures a table of endpoint descriptions, in sequence. This function can be used to configure multiple
+ * endpoints at the same time.
+ *
+ * \note Endpoints with a zero address will be ignored, thus this function cannot be used to configure the
+ * control endpoint.
+ *
+ * \param[in] Table Pointer to a table of endpoint descriptions.
+ * \param[in] Entries Number of entries in the endpoint table to configure.
+ *
+ * \return Boolean \c true if all endpoints configured successfully, \c false otherwise.
+ */
+ bool Endpoint_ConfigureEndpointTable(const USB_Endpoint_Table_t* const Table,
+ const uint8_t Entries);
+
/** Completes the status stage of a control transfer on a CONTROL type endpoint automatically,
* with respect to the data direction. This is a convenience function which can be used to
* simplify user control request handling.
diff --git a/LUFA/Drivers/USB/Core/AVR8/Host_AVR8.c b/LUFA/Drivers/USB/Core/AVR8/Host_AVR8.c
index 3f27c7631..a1e0fd371 100644
--- a/LUFA/Drivers/USB/Core/AVR8/Host_AVR8.c
+++ b/LUFA/Drivers/USB/Core/AVR8/Host_AVR8.c
@@ -114,9 +114,7 @@ void USB_Host_ProcessNextHostState(void)
HOST_TASK_NONBLOCK_WAIT(200, HOST_STATE_Powered_ConfigPipe);
break;
case HOST_STATE_Powered_ConfigPipe:
- if (!(Pipe_ConfigurePipe(PIPE_CONTROLPIPE, EP_TYPE_CONTROL,
- PIPE_TOKEN_SETUP, ENDPOINT_CONTROLEP,
- PIPE_CONTROLPIPE_DEFAULT_SIZE, PIPE_BANK_SINGLE)))
+ if (!(Pipe_ConfigurePipe(PIPE_CONTROLPIPE, EP_TYPE_CONTROL, ENDPOINT_CONTROLEP, PIPE_CONTROLPIPE_DEFAULT_SIZE, 1)))
{
ErrorCode = HOST_ENUMERROR_PipeConfigError;
SubErrorCode = 0;
@@ -151,9 +149,7 @@ void USB_Host_ProcessNextHostState(void)
HOST_TASK_NONBLOCK_WAIT(200, HOST_STATE_Default_PostReset);
break;
case HOST_STATE_Default_PostReset:
- if (!(Pipe_ConfigurePipe(PIPE_CONTROLPIPE, EP_TYPE_CONTROL,
- PIPE_TOKEN_SETUP, ENDPOINT_CONTROLEP,
- USB_Host_ControlPipeSize, PIPE_BANK_SINGLE)))
+ if (!(Pipe_ConfigurePipe(PIPE_CONTROLPIPE, EP_TYPE_CONTROL, ENDPOINT_CONTROLEP, USB_Host_ControlPipeSize, 1)))
{
ErrorCode = HOST_ENUMERROR_PipeConfigError;
SubErrorCode = 0;
diff --git a/LUFA/Drivers/USB/Core/AVR8/Pipe_AVR8.c b/LUFA/Drivers/USB/Core/AVR8/Pipe_AVR8.c
index 5e68cc725..1ddffb51e 100644
--- a/LUFA/Drivers/USB/Core/AVR8/Pipe_AVR8.c
+++ b/LUFA/Drivers/USB/Core/AVR8/Pipe_AVR8.c
@@ -40,21 +40,43 @@
uint8_t USB_Host_ControlPipeSize = PIPE_CONTROLPIPE_DEFAULT_SIZE;
-bool Pipe_ConfigurePipe(const uint8_t Number,
+bool Pipe_ConfigurePipeTable(const USB_Pipe_Table_t* const Table,
+ const uint8_t Entries)
+{
+ for (uint8_t i = 0; i < Entries; i++)
+ {
+ if (!(Table[i].Address))
+ continue;
+
+ if (!(Pipe_ConfigurePipe(Table[i].Address, Table[i].Type, Table[i].EndpointAddress, Table[i].Size, Table[i].Banks)))
+ {
+ return false;
+ }
+ }
+
+ return true;
+}
+
+bool Pipe_ConfigurePipe(const uint8_t Address,
const uint8_t Type,
- const uint8_t Token,
- const uint8_t EndpointNumber,
+ const uint8_t EndpointAddress,
const uint16_t Size,
const uint8_t Banks)
{
+ uint8_t Number = (Address & PIPE_EPNUM_MASK);
+ uint8_t Token = (Address & PIPE_DIR_IN) ? PIPE_TOKEN_IN : PIPE_TOKEN_OUT;
+
+ if (Type == EP_TYPE_CONTROL)
+ Token = PIPE_TOKEN_SETUP;
+
#if defined(ORDERED_EP_CONFIG)
Pipe_SelectPipe(Number);
Pipe_EnablePipe();
UPCFG1X = 0;
- UPCFG0X = ((Type << EPTYPE0) | Token | ((EndpointNumber & PIPE_EPNUM_MASK) << PEPNUM0));
- UPCFG1X = ((1 << ALLOC) | Banks | Pipe_BytesToEPSizeMask(Size));
+ UPCFG0X = ((Type << EPTYPE0) | Token | ((EndpointAddress & PIPE_EPNUM_MASK) << PEPNUM0));
+ UPCFG1X = ((1 << ALLOC) | ((Banks > 1) ? (1 << EPBK0) : 0) | Pipe_BytesToEPSizeMask(Size));
Pipe_SetInfiniteINRequests();
@@ -71,7 +93,7 @@ bool Pipe_ConfigurePipe(const uint8_t Number,
if (PNum == Number)
{
- UPCFG0XTemp = ((Type << EPTYPE0) | Token | ((EndpointNumber & PIPE_EPNUM_MASK) << PEPNUM0));
+ UPCFG0XTemp = ((Type << EPTYPE0) | Token | ((EndpointAddress & PIPE_EPNUM_MASK) << PEPNUM0));
UPCFG1XTemp = ((1 << ALLOC) | Banks | Pipe_BytesToEPSizeMask(Size));
UPCFG2XTemp = 0;
UPIENXTemp = 0;
diff --git a/LUFA/Drivers/USB/Core/AVR8/Pipe_AVR8.h b/LUFA/Drivers/USB/Core/AVR8/Pipe_AVR8.h
index 86792bf22..1012fa060 100644
--- a/LUFA/Drivers/USB/Core/AVR8/Pipe_AVR8.h
+++ b/LUFA/Drivers/USB/Core/AVR8/Pipe_AVR8.h
@@ -124,38 +124,22 @@
/** \name Pipe Token Masks */
//@{
- /** Token mask for \ref Pipe_ConfigurePipe(). This sets the pipe as a SETUP token (for CONTROL type pipes),
+ /** Token mask for \ref Pipe_SetPipeToken() and \ref Pipe_GetPipeToken(). This sets the pipe as a SETUP token (for CONTROL type pipes),
* which will trigger a control request on the attached device when data is written to the pipe.
*/
#define PIPE_TOKEN_SETUP (0 << PTOKEN0)
- /** Token mask for \ref Pipe_ConfigurePipe(). This sets the pipe as a IN token (for non-CONTROL type pipes),
+ /** Token mask for \ref Pipe_SetPipeToken() and \ref Pipe_GetPipeToken(). This sets the pipe as a IN token (for non-CONTROL type pipes),
* indicating that the pipe data will flow from device to host.
*/
#define PIPE_TOKEN_IN (1 << PTOKEN0)
- /** Token mask for \ref Pipe_ConfigurePipe(). This sets the pipe as a OUT token (for non-CONTROL type pipes),
+ /** Token mask for \ref Pipe_SetPipeToken() and \ref Pipe_GetPipeToken(). This sets the pipe as a OUT token (for non-CONTROL type pipes),
* indicating that the pipe data will flow from host to device.
*/
#define PIPE_TOKEN_OUT (2 << PTOKEN0)
//@}
- /** \name Pipe Bank Mode Masks */
- //@{
- /** Mask for the bank mode selection for the \ref Pipe_ConfigurePipe() macro. This indicates that the pipe
- * should have one single bank, which requires less USB FIFO memory but results in slower transfers as
- * only one USB device (the AVR or the attached device) can access the pipe's bank at the one time.
- */
- #define PIPE_BANK_SINGLE (0 << EPBK0)
-
- /** Mask for the bank mode selection for the \ref Pipe_ConfigurePipe() macro. This indicates that the pipe
- * should have two banks, which requires more USB FIFO memory but results in faster transfers as one
- * USB device (the AVR or the attached device) can access one bank while the other accesses the second
- * bank.
- */
- #define PIPE_BANK_DOUBLE (1 << EPBK0)
- //@}
-
/** Default size of the default control pipe's bank, until altered by the Endpoint0Size value
* in the device descriptor of the attached device.
*/
@@ -203,36 +187,46 @@
return UPBCX;
}
+ /** Determines the currently selected pipe's direction.
+ *
+ * \return The currently selected pipe's direction, as a \c PIPE_DIR_* mask.
+ */
+ static inline uint8_t Pipe_GetPipeDirection(void) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
+ static inline uint8_t Pipe_GetPipeDirection(void)
+ {
+ return (UPCFG0X & (1 << EPDIR)) ? PIPE_DIR_IN : PIPE_DIR_OUT;
+ }
+
/** Returns the pipe address of the currently selected pipe. This is typically used to save the
- * currently selected pipe number so that it can be restored after another pipe has been manipulated.
+ * currently selected pipe address so that it can be restored after another pipe has been manipulated.
*
* \return Index of the currently selected pipe.
*/
static inline uint8_t Pipe_GetCurrentPipe(void) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
static inline uint8_t Pipe_GetCurrentPipe(void)
{
- return (UPNUM & PIPE_PIPENUM_MASK);
+ return ((UPNUM & PIPE_PIPENUM_MASK) | Pipe_GetPipeDirection());
}
- /** Selects the given pipe number. Any pipe operations which do not require the pipe number to be
+ /** Selects the given pipe address. Any pipe operations which do not require the pipe address to be
* indicated will operate on the currently selected pipe.
*
- * \param[in] PipeNumber Index of the pipe to select.
+ * \param[in] Address Address of the pipe to select.
*/
- static inline void Pipe_SelectPipe(const uint8_t PipeNumber) ATTR_ALWAYS_INLINE;
- static inline void Pipe_SelectPipe(const uint8_t PipeNumber)
+ static inline void Pipe_SelectPipe(const uint8_t Address) ATTR_ALWAYS_INLINE;
+ static inline void Pipe_SelectPipe(const uint8_t Address)
{
- UPNUM = PipeNumber;
+ UPNUM = (Address & PIPE_PIPENUM_MASK);
}
/** Resets the desired pipe, including the pipe banks and flags.
*
- * \param[in] PipeNumber Index of the pipe to reset.
+ * \param[in] Address Address of the pipe to reset.
*/
- static inline void Pipe_ResetPipe(const uint8_t PipeNumber) ATTR_ALWAYS_INLINE;
- static inline void Pipe_ResetPipe(const uint8_t PipeNumber)
+ static inline void Pipe_ResetPipe(const uint8_t Address) ATTR_ALWAYS_INLINE;
+ static inline void Pipe_ResetPipe(const uint8_t Address)
{
- UPRST = (1 << PipeNumber);
+ UPRST = (1 << (Address & PIPE_PIPENUM_MASK));
UPRST = 0;
}
@@ -326,8 +320,9 @@
static inline uint8_t Pipe_GetBoundEndpointAddress(void) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
static inline uint8_t Pipe_GetBoundEndpointAddress(void)
{
- return (((UPCFG0X >> PEPNUM0) & PIPE_EPNUM_MASK) |
- ((Pipe_GetPipeToken() == PIPE_TOKEN_IN) ? PIPE_EPDIR_MASK : 0));
+ uint8_t UPCFG0X_Temp = UPCFG0X;
+
+ return (((UPCFG0X_Temp >> PEPNUM0) & PIPE_EPNUM_MASK) | ((UPCFG0X_Temp & PEPNUM1) ? ENDPOINT_DIR_OUT : ENDPOINT_DIR_IN));
}
/** Sets the period between interrupts for an INTERRUPT type pipe to a specified number of milliseconds.
@@ -351,17 +346,17 @@
return UPINT;
}
- /** Determines if the specified pipe number has interrupted (valid only for INTERRUPT type
+ /** Determines if the specified pipe address has interrupted (valid only for INTERRUPT type
* pipes).
*
- * \param[in] PipeNumber Index of the pipe whose interrupt flag should be tested.
+ * \param[in] Address Address of the pipe whose interrupt flag should be tested.
*
* \return Boolean \c true if the specified pipe has interrupted, \c false otherwise.
*/
- static inline bool Pipe_HasPipeInterrupted(const uint8_t PipeNumber) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
- static inline bool Pipe_HasPipeInterrupted(const uint8_t PipeNumber)
+ static inline bool Pipe_HasPipeInterrupted(const uint8_t Address) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
+ static inline bool Pipe_HasPipeInterrupted(const uint8_t Address)
{
- return ((UPINT & (1 << PipeNumber)) ? true : false);
+ return ((UPINT & (1 << (Address & PIPE_PIPENUM_MASK))) ? true : false);
}
/** Unfreezes the selected pipe, allowing it to communicate with an attached device. */
@@ -810,8 +805,22 @@
extern uint8_t USB_Host_ControlPipeSize;
/* Function Prototypes: */
- /** Configures the specified pipe number with the given pipe type, token, target endpoint number in the
- * attached device, bank size and banking mode.
+ /** Configures a table of pipe descriptions, in sequence. This function can be used to configure multiple
+ * pipes at the same time.
+ *
+ * \note Pipe with a zero address will be ignored, thus this function cannot be used to configure the
+ * control pipe.
+ *
+ * \param[in] Table Pointer to a table of pipe descriptions.
+ * \param[in] Entries Number of entries in the pipe table to configure.
+ *
+ * \return Boolean \c true if all pipes configured successfully, \c false otherwise.
+ */
+ bool Pipe_ConfigurePipeTable(const USB_Pipe_Table_t* const Table,
+ const uint8_t Entries);
+
+ /** Configures the specified pipe address with the given pipe type, endpoint address within the attached device, bank size
+ * and number of hardware banks.
*
* A newly configured pipe is frozen by default, and must be unfrozen before use via the \ref Pipe_Unfreeze()
* before being used. Pipes should be kept frozen unless waiting for data from a device while in IN mode, or
@@ -819,25 +828,19 @@
* numbers of IN requests without automatic freezing - this can be overridden by a call to
* \ref Pipe_SetFiniteINRequests().
*
- * \param[in] Number Pipe number to configure. This must be more than 0 and less than \ref PIPE_TOTAL_PIPES.
- *
- * \param[in] Type Type of pipe to configure, an \c EP_TYPE_* mask. Not all pipe types are available on Low
- * Speed USB devices - refer to the USB 2.0 specification.
+ * \param[in] Address Pipe address to configure.
*
- * \param[in] Token Pipe data token, either \ref PIPE_TOKEN_SETUP, \ref PIPE_TOKEN_OUT or \ref PIPE_TOKEN_IN.
- * All pipes (except Control type) are unidirectional - data may only be read from or
- * written to the pipe bank based on its direction, not both.
+ * \param[in] Type Type of pipe to configure, an \c EP_TYPE_* mask. Not all pipe types are available on Low
+ * Speed USB devices - refer to the USB 2.0 specification.
*
- * \param[in] EndpointNumber Endpoint index within the attached device that the pipe should interface to.
+ * \param[in] EndpointAddress Endpoint address within the attached device that the pipe should interface to.
*
- * \param[in] Size Size of the pipe's bank, where packets are stored before they are transmitted to
- * the USB device, or after they have been received from the USB device (depending on
- * the pipe's data direction). The bank size must indicate the maximum packet size that
- * the pipe can handle.
+ * \param[in] Size Size of the pipe's bank, where packets are stored before they are transmitted to
+ * the USB device, or after they have been received from the USB device (depending on
+ * the pipe's data direction). The bank size must indicate the maximum packet size that
+ * the pipe can handle.
*
- * \param[in] Banks Number of banks to use for the pipe being configured, a \c PIPE_BANK_* mask. More banks
- * uses more USB DPRAM, but offers better performance. Isochronous type pipes <b>must</b>
- * have at least two banks.
+ * \param[in] Banks Number of banks to use for the pipe being configured.
*
* \attention When the \c ORDERED_EP_CONFIG compile time option is used, Pipes <b>must</b> be configured in ascending order,
* or bank corruption will occur.
@@ -855,10 +858,9 @@
*
* \return Boolean \c true if the configuration succeeded, \c false otherwise.
*/
- bool Pipe_ConfigurePipe(const uint8_t Number,
+ bool Pipe_ConfigurePipe(const uint8_t Address,
const uint8_t Type,
- const uint8_t Token,
- const uint8_t EndpointNumber,
+ const uint8_t EndpointAddress,
const uint16_t Size,
const uint8_t Banks);
diff --git a/LUFA/Drivers/USB/Core/AVR8/USBController_AVR8.c b/LUFA/Drivers/USB/Core/AVR8/USBController_AVR8.c
index e31b88d5f..1f37dfd49 100644
--- a/LUFA/Drivers/USB/Core/AVR8/USBController_AVR8.c
+++ b/LUFA/Drivers/USB/Core/AVR8/USBController_AVR8.c
@@ -232,8 +232,7 @@ static void USB_Init_Device(void)
#endif
Endpoint_ConfigureEndpoint(ENDPOINT_CONTROLEP, EP_TYPE_CONTROL,
- ENDPOINT_DIR_OUT, USB_Device_ControlEndpointSize,
- ENDPOINT_BANK_SINGLE);
+ USB_Device_ControlEndpointSize, 1);
USB_INT_Clear(USB_INT_SUSPI);
USB_INT_Enable(USB_INT_SUSPI);
diff --git a/LUFA/Drivers/USB/Core/AVR8/USBInterrupt_AVR8.c b/LUFA/Drivers/USB/Core/AVR8/USBInterrupt_AVR8.c
index f63cf3eb9..e26c86f12 100644
--- a/LUFA/Drivers/USB/Core/AVR8/USBInterrupt_AVR8.c
+++ b/LUFA/Drivers/USB/Core/AVR8/USBInterrupt_AVR8.c
@@ -171,8 +171,7 @@ ISR(USB_GEN_vect, ISR_BLOCK)
USB_INT_Enable(USB_INT_WAKEUPI);
Endpoint_ConfigureEndpoint(ENDPOINT_CONTROLEP, EP_TYPE_CONTROL,
- ENDPOINT_DIR_OUT, USB_Device_ControlEndpointSize,
- ENDPOINT_BANK_SINGLE);
+ USB_Device_ControlEndpointSize, 1);
#if defined(INTERRUPT_CONTROL_ENDPOINT)
USB_INT_Enable(USB_INT_RXSTPI);
diff --git a/LUFA/Drivers/USB/Core/Endpoint.h b/LUFA/Drivers/USB/Core/Endpoint.h
index 1fcc6b6f3..b349adfc9 100644
--- a/LUFA/Drivers/USB/Core/Endpoint.h
+++ b/LUFA/Drivers/USB/Core/Endpoint.h
@@ -87,6 +87,18 @@
#endif
/* Public Interface - May be used in end-application: */
+ /* Type Defines: */
+ /** Type define for a endpoint table entry, used to configure endpoints in groups via
+ * \ref Endpoint_ConfigureEndpointTable().
+ */
+ typedef struct
+ {
+ uint8_t Address; /**< Address of the endpoint to configure, or zero if the table entry is to be unused. */
+ uint16_t Size; /**< Size of the endpoint bank, in bytes. */
+ uint8_t Type; /**< Type of the endpoint, a \c EP_TYPE_* mask. */
+ uint8_t Banks; /**< Number of hardware banks to use for the endpoint. */
+ } USB_Endpoint_Table_t;
+
/* Macros: */
/** Endpoint number mask, for masking against endpoint addresses to retrieve the endpoint's
* numerical address in the device.
diff --git a/LUFA/Drivers/USB/Core/Pipe.h b/LUFA/Drivers/USB/Core/Pipe.h
index bb56b8102..faa803b6d 100644
--- a/LUFA/Drivers/USB/Core/Pipe.h
+++ b/LUFA/Drivers/USB/Core/Pipe.h
@@ -97,6 +97,19 @@
#endif
/* Public Interface - May be used in end-application: */
+ /* Type Defines: */
+ /** Type define for a pipe table entry, used to configure pipes in groups via
+ * \ref Pipe_ConfigurePipeTable().
+ */
+ typedef struct
+ {
+ uint8_t Address; /**< Address of the pipe to configure, or zero if the table entry is to be unused. */
+ uint16_t Size; /**< Size of the pipe bank, in bytes. */
+ uint8_t EndpointAddress; /** Address of the endpoint in the connected device. */
+ uint8_t Type; /**< Type of the endpoint, a \c EP_TYPE_* mask. */
+ uint8_t Banks; /**< Number of hardware banks to use for the pipe. */
+ } USB_Pipe_Table_t;
+
/* Macros: */
/** Pipe address for the default control pipe, which always resides in address 0. This is
* defined for convenience to give more readable code when used with the pipe macros.
@@ -113,11 +126,6 @@
*/
#define PIPE_EPNUM_MASK 0x0F
- /** Endpoint direction mask, for masking against endpoint addresses to retrieve the endpoint's
- * direction for comparing with the \c ENDPOINT_DIR_* masks.
- */
- #define PIPE_EPDIR_MASK 0x80
-
/* Architecture Includes: */
#if (ARCH == ARCH_AVR8)
#include "AVR8/Pipe_AVR8.h"
diff --git a/LUFA/Drivers/USB/Core/UC3/Endpoint_UC3.c b/LUFA/Drivers/USB/Core/UC3/Endpoint_UC3.c
index fc1b18a2e..c027585a6 100644
--- a/LUFA/Drivers/USB/Core/UC3/Endpoint_UC3.c
+++ b/LUFA/Drivers/USB/Core/UC3/Endpoint_UC3.c
@@ -45,6 +45,23 @@ uint8_t USB_Device_ControlEndpointSize = ENDPOINT_CONTROLEP_DEFAULT_SIZE;
volatile uint32_t USB_Endpoint_SelectedEndpoint = ENDPOINT_CONTROLEP;
volatile uint8_t* USB_Endpoint_FIFOPos[ENDPOINT_TOTAL_ENDPOINTS];
+bool Endpoint_ConfigureEndpointTable(const USB_Endpoint_Table_t* const Table,
+ const uint8_t Entries)
+{
+ for (uint8_t i = 0; i < Entries; i++)
+ {
+ if (!(Table[i].Address))
+ continue;
+
+ if (!(Endpoint_ConfigureEndpoint(Table[i].Address, Table[i].Type, Table[i].Size, Table[i].Banks)))
+ {
+ return false;
+ }
+ }
+
+ return true;
+}
+
bool Endpoint_ConfigureEndpoint_Prv(const uint8_t Number,
const uint32_t UECFG0Data)
{
diff --git a/LUFA/Drivers/USB/Core/UC3/Endpoint_UC3.h b/LUFA/Drivers/USB/Core/UC3/Endpoint_UC3.h
index c919effa7..84801a13f 100644
--- a/LUFA/Drivers/USB/Core/UC3/Endpoint_UC3.h
+++ b/LUFA/Drivers/USB/Core/UC3/Endpoint_UC3.h
@@ -90,47 +90,6 @@
/* Private Interface - For use in library only: */
#if !defined(__DOXYGEN__)
/* Macros: */
- #define _ENDPOINT_GET_MAXSIZE(EPIndex) _ENDPOINT_GET_MAXSIZE2(ENDPOINT_DETAILS_EP ## EPIndex)
- #define _ENDPOINT_GET_MAXSIZE2(EPDetails) _ENDPOINT_GET_MAXSIZE3(EPDetails)
- #define _ENDPOINT_GET_MAXSIZE3(MaxSize, Banks) (MaxSize)
-
- #define _ENDPOINT_GET_BANKS(EPIndex) _ENDPOINT_GET_BANKS2(ENDPOINT_DETAILS_EP ## EPIndex)
- #define _ENDPOINT_GET_BANKS2(EPDetails) _ENDPOINT_GET_BANKS3(EPDetails)
- #define _ENDPOINT_GET_BANKS3(MaxSize, Banks) (Banks)
-
- #if defined(USB_SERIES_UC3A0_AVR32) || defined(USB_SERIES_UC3A1_AVR32)
- #define ENDPOINT_DETAILS_MAXEP 7
-
- #define ENDPOINT_DETAILS_EP0 64, 1
- #define ENDPOINT_DETAILS_EP1 256, 2
- #define ENDPOINT_DETAILS_EP2 256, 2
- #define ENDPOINT_DETAILS_EP3 64, 2
- #define ENDPOINT_DETAILS_EP4 64, 2
- #define ENDPOINT_DETAILS_EP5 256, 2
- #define ENDPOINT_DETAILS_EP6 256, 2
- #elif defined(USB_SERIES_UC3A3_AVR32) || defined(USB_SERIES_UC3A4_AVR32)
- #define ENDPOINT_DETAILS_MAXEP 8
-
- #define ENDPOINT_DETAILS_EP0 64, 1
- #define ENDPOINT_DETAILS_EP1 512, 3
- #define ENDPOINT_DETAILS_EP2 512, 3
- #define ENDPOINT_DETAILS_EP3 512, 3
- #define ENDPOINT_DETAILS_EP4 512, 3
- #define ENDPOINT_DETAILS_EP5 512, 3
- #define ENDPOINT_DETAILS_EP6 512, 3
- #define ENDPOINT_DETAILS_EP7 512, 3
- #elif defined(USB_SERIES_UC3B0_AVR32) || defined(USB_SERIES_UC3B1_AVR32)
- #define ENDPOINT_DETAILS_MAXEP 7
-
- #define ENDPOINT_DETAILS_EP0 64, 1
- #define ENDPOINT_DETAILS_EP1 64, 2
- #define ENDPOINT_DETAILS_EP2 64, 2
- #define ENDPOINT_DETAILS_EP3 64, 2
- #define ENDPOINT_DETAILS_EP4 64, 2
- #define ENDPOINT_DETAILS_EP5 256, 2
- #define ENDPOINT_DETAILS_EP6 256, 2
- #endif
-
#define ENDPOINT_HSB_ADDRESS_SPACE_SIZE (64 * 1024UL)
/* Inline Functions: */
@@ -162,34 +121,6 @@
/* Public Interface - May be used in end-application: */
/* Macros: */
- /** \name Endpoint Bank Mode Masks */
- //@{
- /** Mask for the bank mode selection for the \ref Endpoint_ConfigureEndpoint() macro. This indicates
- * that the endpoint should have one single bank, which requires less USB FIFO memory but results
- * in slower transfers as only one USB device (the AVR or the host) can access the endpoint's
- * bank at the one time.
- */
- #define ENDPOINT_BANK_SINGLE AVR32_USBB_UECFG0_EPBK_SINGLE
-
- /** Mask for the bank mode selection for the \ref Endpoint_ConfigureEndpoint() macro. This indicates
- * that the endpoint should have two banks, which requires more USB FIFO memory but results
- * in faster transfers as one USB device (the AVR or the host) can access one bank while the other
- * accesses the second bank.
- */
- #define ENDPOINT_BANK_DOUBLE AVR32_USBB_UECFG0_EPBK_DOUBLE
-
- #if defined(USB_SERIES_UC3A3_AVR32) || defined(USB_SERIES_UC3A4_AVR32) || defined(__DOXYGEN__)
- /** Mask for the bank mode selection for the \ref Endpoint_ConfigureEndpoint() macro. This indicates
- * that the endpoint should have three banks, which requires more USB FIFO memory but results
- * in faster transfers as one USB device (the AVR or the host) can access one bank while the other
- * accesses the remaining banks.
- *
- * \note Not available on all AVR models.
- */
- #define ENDPOINT_BANK_TRIPLE AVR32_USBB_UECFG0_EPBK_TRIPLE
- #endif
- //@}
-
#if (!defined(FIXED_CONTROL_ENDPOINT_SIZE) || defined(__DOXYGEN__))
/** Default size of the default control endpoint's bank, until altered by the control endpoint bank size
* value in the device descriptor. Not available if the \c FIXED_CONTROL_ENDPOINT_SIZE token is defined.
@@ -197,30 +128,16 @@
#define ENDPOINT_CONTROLEP_DEFAULT_SIZE 8
#endif
- /** Retrieves the maximum bank size in bytes of a given endpoint.
- *
- * \attention This macro will only work correctly on endpoint indexes that are compile-time constants
- * defined by the preprocessor.
- *
- * \param[in] EPIndex Endpoint number, a value between 0 and (\ref ENDPOINT_TOTAL_ENDPOINTS - 1)
- */
- #define ENDPOINT_MAX_SIZE(EPIndex) _ENDPOINT_GET_MAXSIZE(EPIndex)
-
- /** Retrieves the total number of banks supported by the given endpoint.
- *
- * \attention This macro will only work correctly on endpoint indexes that are compile-time constants
- * defined by the preprocessor.
- *
- * \param[in] EPIndex Endpoint number, a value between 0 and (\ref ENDPOINT_TOTAL_ENDPOINTS - 1)
- */
- #define ENDPOINT_BANKS_SUPPORTED(EPIndex) _ENDPOINT_GET_BANKS(EPIndex)
-
#if !defined(CONTROL_ONLY_DEVICE) || defined(__DOXYGEN__)
- /** Total number of endpoints (including the default control endpoint at address 0) which may
- * be used in the device. Different AVR models support different amounts of endpoints,
- * this value reflects the maximum number of endpoints for the currently selected AVR model.
- */
- #define ENDPOINT_TOTAL_ENDPOINTS ENDPOINT_DETAILS_MAXEP
+ #if defined(USB_SERIES_UC3A3_AVR32) || defined(USB_SERIES_UC3A4_AVR32)
+ #define ENDPOINT_TOTAL_ENDPOINTS 8
+ #else
+ /** Total number of endpoints (including the default control endpoint at address 0) which may
+ * be used in the device. Different AVR models support different amounts of endpoints,
+ * this value reflects the maximum number of endpoints for the currently selected AVR model.
+ */
+ #define ENDPOINT_TOTAL_ENDPOINTS 7
+ #endif
#else
#define ENDPOINT_TOTAL_ENDPOINTS 1
#endif
@@ -250,28 +167,21 @@
};
/* Inline Functions: */
- /** Configures the specified endpoint number with the given endpoint type, direction, bank size
+ /** Configures the specified endpoint address with the given endpoint type, direction, bank size
* and banking mode. Once configured, the endpoint may be read from or written to, depending
* on its direction.
*
- * \param[in] Number Endpoint number to configure. This must be more than 0 and less than
- * \ref ENDPOINT_TOTAL_ENDPOINTS.
+ * \param[in] Address Endpoint address to configure.
*
* \param[in] Type Type of endpoint to configure, a \c EP_TYPE_* mask. Not all endpoint types
* are available on Low Speed USB devices - refer to the USB 2.0 specification.
*
- * \param[in] Direction Endpoint data direction, either \ref ENDPOINT_DIR_OUT or \ref ENDPOINT_DIR_IN.
- * All endpoints (except Control type) are unidirectional - data may only be read
- * from or written to the endpoint bank based on its direction, not both.
- *
* \param[in] Size Size of the endpoint's bank, where packets are stored before they are transmitted
* to the USB host, or after they have been received from the USB host (depending on
* the endpoint's data direction). The bank size must indicate the maximum packet size
* that the endpoint can handle.
*
- * \param[in] Banks Number of banks to use for the endpoint being configured, an \c ENDPOINT_BANK_* mask.
- * More banks uses more USB DPRAM, but offers better performance. Isochronous type
- * endpoints <b>must</b> have at least two banks.
+ * \param[in] Banks Number of hardware banks to use for the endpoint being configured.
*
* \attention When the \c ORDERED_EP_CONFIG compile time option is used, Endpoints <b>must</b> be configured in
* ascending order, or bank corruption will occur.
@@ -289,22 +199,21 @@
*
* \return Boolean \c true if the configuration succeeded, \c false otherwise.
*/
- static inline bool Endpoint_ConfigureEndpoint(const uint8_t Number,
+ static inline bool Endpoint_ConfigureEndpoint(const uint8_t Address,
const uint8_t Type,
- const uint8_t Direction,
const uint16_t Size,
const uint8_t Banks) ATTR_ALWAYS_INLINE;
- static inline bool Endpoint_ConfigureEndpoint(const uint8_t Number,
+ static inline bool Endpoint_ConfigureEndpoint(const uint8_t Address,
const uint8_t Type,
- const uint8_t Direction,
const uint16_t Size,
const uint8_t Banks)
{
- return Endpoint_ConfigureEndpoint_Prv(Number, (AVR32_USBB_ALLOC_MASK |
- ((uint32_t)Type << AVR32_USBB_EPTYPE_OFFSET) |
- ((uint32_t)(Direction ? AVR32_USBB_UECFG0_EPDIR_MASK : 0) |
- ((uint32_t)Banks << AVR32_USBB_EPBK_OFFSET) |
- Endpoint_BytesToEPSizeMask(Size))));
+ return Endpoint_ConfigureEndpoint_Prv((Address & ENDPOINT_EPNUM_MASK),
+ (AVR32_USBB_ALLOC_MASK |
+ ((uint32_t)Type << AVR32_USBB_EPTYPE_OFFSET) |
+ ((uint32_t)(Address & ENDPOINT_DIR_IN) ? AVR32_USBB_UECFG0_EPDIR_MASK : 0) |
+ ((uint32_t)Banks << AVR32_USBB_EPBK_OFFSET) |
+ Endpoint_BytesToEPSizeMask(Size)));
}
/** Indicates the number of bytes currently stored in the current endpoint's selected bank.
@@ -319,41 +228,51 @@
return (&AVR32_USBB.UESTA0)[USB_Endpoint_SelectedEndpoint].byct;
}
+ /** Determines the currently selected endpoint's direction.
+ *
+ * \return The currently selected endpoint's direction, as a \c ENDPOINT_DIR_* mask.
+ */
+ static inline uint32_t Endpoint_GetEndpointDirection(void) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
+ static inline uint32_t Endpoint_GetEndpointDirection(void)
+ {
+ return ((&AVR32_USBB.UECFG0)[USB_Endpoint_SelectedEndpoint].epdir ? ENDPOINT_DIR_IN : ENDPOINT_DIR_OUT);
+ }
+
/** Get the endpoint address of the currently selected endpoint. This is typically used to save
- * the currently selected endpoint number so that it can be restored after another endpoint has
- * been manipulated.
+ * the currently selected endpoint so that it can be restored after another endpoint has been
+ * manipulated.
*
* \return Index of the currently selected endpoint.
*/
static inline uint8_t Endpoint_GetCurrentEndpoint(void) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
static inline uint8_t Endpoint_GetCurrentEndpoint(void)
{
- return USB_Endpoint_SelectedEndpoint;
+ return (USB_Endpoint_SelectedEndpoint | Endpoint_GetEndpointDirection());
}
- /** Selects the given endpoint number. If the address from the device descriptors is used, the
- * value should be masked with the \ref ENDPOINT_EPNUM_MASK constant to extract only the endpoint
- * number (and discarding the endpoint direction bit).
+ /** Selects the given endpoint address.
*
- * Any endpoint operations which do not require the endpoint number to be indicated will operate on
+ * Any endpoint operations which do not require the endpoint address to be indicated will operate on
* the currently selected endpoint.
*
- * \param[in] EndpointNumber Endpoint number to select.
+ * \param[in] Address Endpoint address to select.
*/
- static inline void Endpoint_SelectEndpoint(const uint8_t EndpointNumber) ATTR_ALWAYS_INLINE;
- static inline void Endpoint_SelectEndpoint(const uint8_t EndpointNumber)
+ static inline void Endpoint_SelectEndpoint(const uint8_t Address) ATTR_ALWAYS_INLINE;
+ static inline void Endpoint_SelectEndpoint(const uint8_t Address)
{
- USB_Endpoint_SelectedEndpoint = EndpointNumber;
+ USB_Endpoint_SelectedEndpoint = (Address & ENDPOINT_EPNUM_MASK);
}
/** Resets the endpoint bank FIFO. This clears all the endpoint banks and resets the USB controller's
* data In and Out pointers to the bank's contents.
*
- * \param[in] EndpointNumber Endpoint number whose FIFO buffers are to be reset.
+ * \param[in] Address Endpoint number whose FIFO buffers are to be reset.
*/
- static inline void Endpoint_ResetEndpoint(const uint8_t EndpointNumber) ATTR_ALWAYS_INLINE;
- static inline void Endpoint_ResetEndpoint(const uint8_t EndpointNumber)
+ static inline void Endpoint_ResetEndpoint(const uint8_t Address) ATTR_ALWAYS_INLINE;
+ static inline void Endpoint_ResetEndpoint(const uint8_t Address)
{
+ uint32_t EndpointNumber = (Address & ENDPOINT_EPNUM_MASK);
+
AVR32_USBB.uerst |= (AVR32_USBB_EPRST0_MASK << EndpointNumber);
AVR32_USBB.uerst &= ~(AVR32_USBB_EPRST0_MASK << EndpointNumber);
USB_Endpoint_FIFOPos[EndpointNumber] = &AVR32_USBB_SLAVE[EndpointNumber * ENDPOINT_HSB_ADDRESS_SPACE_SIZE];
@@ -452,8 +371,8 @@
*
* \return Mask whose bits indicate which endpoints have interrupted.
*/
- static inline uint8_t Endpoint_GetEndpointInterrupts(void) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
- static inline uint8_t Endpoint_GetEndpointInterrupts(void)
+ static inline uint32_t Endpoint_GetEndpointInterrupts(void) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
+ static inline uint32_t Endpoint_GetEndpointInterrupts(void)
{
return ((AVR32_USBB.udint & (AVR32_USBB_EP6INT_MASK | AVR32_USBB_EP5INT_MASK |
AVR32_USBB_EP4INT_MASK | AVR32_USBB_EP3INT_MASK |
@@ -464,14 +383,14 @@
/** Determines if the specified endpoint number has interrupted (valid only for INTERRUPT type
* endpoints).
*
- * \param[in] EndpointNumber Index of the endpoint whose interrupt flag should be tested.
+ * \param[in] Address Address of the endpoint whose interrupt flag should be tested.
*
* \return Boolean \c true if the specified endpoint has interrupted, \c false otherwise.
*/
- static inline bool Endpoint_HasEndpointInterrupted(const uint8_t EndpointNumber) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
- static inline bool Endpoint_HasEndpointInterrupted(const uint8_t EndpointNumber)
+ static inline bool Endpoint_HasEndpointInterrupted(const uint8_t Address) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
+ static inline bool Endpoint_HasEndpointInterrupted(const uint8_t Address)
{
- return ((Endpoint_GetEndpointInterrupts() & (AVR32_USBB_EP0INT_MASK << EndpointNumber)) ? true : false);
+ return ((Endpoint_GetEndpointInterrupts() & (AVR32_USBB_EP0INT_MASK << (Address & ENDPOINT_EPNUM_MASK))) ? true : false);
}
/** Determines if the selected IN endpoint is ready for a new packet to be sent to the host.
@@ -596,16 +515,6 @@
(&AVR32_USBB.UECON0SET)[USB_Endpoint_SelectedEndpoint].rstdts = true;
}
- /** Determines the currently selected endpoint's direction.
- *
- * \return The currently selected endpoint's direction, as a \c ENDPOINT_DIR_* mask.
- */
- static inline uint32_t Endpoint_GetEndpointDirection(void) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
- static inline uint32_t Endpoint_GetEndpointDirection(void)
- {
- return ((&AVR32_USBB.UECFG0)[USB_Endpoint_SelectedEndpoint].epdir ? ENDPOINT_DIR_IN : ENDPOINT_DIR_OUT);
- }
-
/** Sets the direction of the currently selected endpoint.
*
* \param[in] DirectionMask New endpoint direction, as a \c ENDPOINT_DIR_* mask.
@@ -837,6 +746,20 @@
#endif
/* Function Prototypes: */
+ /** Configures a table of endpoint descriptions, in sequence. This function can be used to configure multiple
+ * endpoints at the same time.
+ *
+ * \note Endpoints with a zero address will be ignored, thus this function cannot be used to configure the
+ * control endpoint.
+ *
+ * \param[in] Table Pointer to a table of endpoint descriptions.
+ * \param[in] Entries Number of entries in the endpoint table to configure.
+ *
+ * \return Boolean \c true if all endpoints configured successfully, \c false otherwise.
+ */
+ bool Endpoint_ConfigureEndpointTable(const USB_Endpoint_Table_t* const Table,
+ const uint8_t Entries);
+
/** Completes the status stage of a control transfer on a CONTROL type endpoint automatically,
* with respect to the data direction. This is a convenience function which can be used to
* simplify user control request handling.
diff --git a/LUFA/Drivers/USB/Core/UC3/Host_UC3.c b/LUFA/Drivers/USB/Core/UC3/Host_UC3.c
index 49d43f9b5..932381a14 100644
--- a/LUFA/Drivers/USB/Core/UC3/Host_UC3.c
+++ b/LUFA/Drivers/USB/Core/UC3/Host_UC3.c
@@ -114,9 +114,7 @@ void USB_Host_ProcessNextHostState(void)
HOST_TASK_NONBLOCK_WAIT(200, HOST_STATE_Powered_ConfigPipe);
break;
case HOST_STATE_Powered_ConfigPipe:
- if (!(Pipe_ConfigurePipe(PIPE_CONTROLPIPE, EP_TYPE_CONTROL,
- PIPE_TOKEN_SETUP, ENDPOINT_CONTROLEP,
- PIPE_CONTROLPIPE_DEFAULT_SIZE, PIPE_BANK_SINGLE)))
+ if (!(Pipe_ConfigurePipe(PIPE_CONTROLPIPE, EP_TYPE_CONTROL, ENDPOINT_CONTROLEP, PIPE_CONTROLPIPE_DEFAULT_SIZE, 1)))
{
ErrorCode = HOST_ENUMERROR_PipeConfigError;
SubErrorCode = 0;
@@ -151,9 +149,7 @@ void USB_Host_ProcessNextHostState(void)
HOST_TASK_NONBLOCK_WAIT(200, HOST_STATE_Default_PostReset);
break;
case HOST_STATE_Default_PostReset:
- if (!(Pipe_ConfigurePipe(PIPE_CONTROLPIPE, EP_TYPE_CONTROL,
- PIPE_TOKEN_SETUP, ENDPOINT_CONTROLEP,
- USB_Host_ControlPipeSize, PIPE_BANK_SINGLE)))
+ if (!(Pipe_ConfigurePipe(PIPE_CONTROLPIPE, EP_TYPE_CONTROL, ENDPOINT_CONTROLEP, USB_Host_ControlPipeSize, 1)))
{
ErrorCode = HOST_ENUMERROR_PipeConfigError;
SubErrorCode = 0;
diff --git a/LUFA/Drivers/USB/Core/UC3/Pipe_UC3.c b/LUFA/Drivers/USB/Core/UC3/Pipe_UC3.c
index 4e77a28ff..787244b97 100644
--- a/LUFA/Drivers/USB/Core/UC3/Pipe_UC3.c
+++ b/LUFA/Drivers/USB/Core/UC3/Pipe_UC3.c
@@ -43,13 +43,35 @@ uint8_t USB_Host_ControlPipeSize = PIPE_CONTROLPIPE_DEFAULT_SIZE;
volatile uint32_t USB_Pipe_SelectedPipe = PIPE_CONTROLPIPE;
volatile uint8_t* USB_Pipe_FIFOPos[PIPE_TOTAL_PIPES];
-bool Pipe_ConfigurePipe(const uint8_t Number,
+bool Pipe_ConfigurePipeTable(const USB_Pipe_Table_t* const Table,
+ const uint8_t Entries)
+{
+ for (uint8_t i = 0; i < Entries; i++)
+ {
+ if (!(Table[i].Address))
+ continue;
+
+ if (!(Pipe_ConfigurePipe(Table[i].Address, Table[i].Type, Table[i].EndpointAddress, Table[i].Size, Table[i].Banks)))
+ {
+ return false;
+ }
+ }
+
+ return true;
+}
+
+bool Pipe_ConfigurePipe(const uint8_t Address,
const uint8_t Type,
- const uint8_t Token,
- const uint8_t EndpointNumber,
+ const uint8_t EndpointAddress,
const uint16_t Size,
const uint8_t Banks)
{
+ uint8_t Number = (Address & PIPE_EPNUM_MASK);
+ uint8_t Token = (Address & PIPE_DIR_IN) ? PIPE_TOKEN_IN : PIPE_TOKEN_OUT;
+
+ if (Type == EP_TYPE_CONTROL)
+ Token = PIPE_TOKEN_SETUP;
+
USB_Pipe_FIFOPos[Number] = &AVR32_USBB_SLAVE[Number * 0x10000];
#if defined(ORDERED_EP_CONFIG)
@@ -60,7 +82,7 @@ bool Pipe_ConfigurePipe(const uint8_t Number,
(&AVR32_USBB.upcfg0)[Number] = (AVR32_USBB_ALLOC_MASK |
((uint32_t)Type << AVR32_USBB_PTYPE_OFFSET) |
((uint32_t)Token << AVR32_USBB_PTOKEN_OFFSET) |
- ((uint32_t)Banks << AVR32_USBB_PBK_OFFSET) |
+ ((Banks > 1) ? AVR32_USBB_PBK_MASK : 0) |
Pipe_BytesToEPSizeMask(Size) |
((EndpointNumber & PIPE_EPNUM_MASK) << AVR32_USBB_PEPNUM_OFFSET));
@@ -79,9 +101,9 @@ bool Pipe_ConfigurePipe(const uint8_t Number,
UPCFG0Temp = (AVR32_USBB_ALLOC_MASK |
((uint32_t)Type << AVR32_USBB_PTYPE_OFFSET) |
((uint32_t)Token << AVR32_USBB_PTOKEN_OFFSET) |
- ((uint32_t)Banks << AVR32_USBB_PBK_OFFSET) |
+ ((Banks > 1) ? AVR32_USBB_PBK_MASK : 0) |
Pipe_BytesToEPSizeMask(Size) |
- ((EndpointNumber & PIPE_EPNUM_MASK) << AVR32_USBB_PEPNUM_OFFSET));
+ ((EndpointAddress & PIPE_EPNUM_MASK) << AVR32_USBB_PEPNUM_OFFSET));
}
else
{
diff --git a/LUFA/Drivers/USB/Core/UC3/Pipe_UC3.h b/LUFA/Drivers/USB/Core/UC3/Pipe_UC3.h
index f17fa5376..837afe8b8 100644
--- a/LUFA/Drivers/USB/Core/UC3/Pipe_UC3.h
+++ b/LUFA/Drivers/USB/Core/UC3/Pipe_UC3.h
@@ -131,49 +131,22 @@
/** \name Pipe Token Masks */
//@{
- /** Token mask for \ref Pipe_ConfigurePipe(). This sets the pipe as a SETUP token (for CONTROL type pipes),
+ /** Token mask for \ref Pipe_SetPipeToken() and \ref Pipe_GetPipeToken(). This sets the pipe as a SETUP token (for CONTROL type pipes),
* which will trigger a control request on the attached device when data is written to the pipe.
*/
#define PIPE_TOKEN_SETUP AVR32_USBB_UPCFG0_PTOKEN_SETUP
- /** Token mask for \ref Pipe_ConfigurePipe(). This sets the pipe as a IN token (for non-CONTROL type pipes),
+ /** Token mask for \ref Pipe_SetPipeToken() and \ref Pipe_GetPipeToken(). This sets the pipe as a IN token (for non-CONTROL type pipes),
* indicating that the pipe data will flow from device to host.
*/
#define PIPE_TOKEN_IN AVR32_USBB_UPCFG0_PTOKEN_IN
- /** Token mask for \ref Pipe_ConfigurePipe(). This sets the pipe as a OUT token (for non-CONTROL type pipes),
+ /** Token mask for \ref Pipe_SetPipeToken() and \ref Pipe_GetPipeToken(). This sets the pipe as a OUT token (for non-CONTROL type pipes),
* indicating that the pipe data will flow from host to device.
*/
#define PIPE_TOKEN_OUT AVR32_USBB_UPCFG0_PTOKEN_OUT
//@}
- /** \name Pipe Bank Mode Masks */
- //@{
- /** Mask for the bank mode selection for the \ref Pipe_ConfigurePipe() macro. This indicates that the pipe
- * should have one single bank, which requires less USB FIFO memory but results in slower transfers as
- * only one USB device (the AVR or the attached device) can access the pipe's bank at the one time.
- */
- #define PIPE_BANK_SINGLE AVR32_USBB_UPCFG0_PBK_SINGLE
-
- /** Mask for the bank mode selection for the \ref Pipe_ConfigurePipe() macro. This indicates that the pipe
- * should have two banks, which requires more USB FIFO memory but results in faster transfers as one
- * USB device (the AVR or the attached device) can access one bank while the other accesses the second
- * bank.
- */
- #define PIPE_BANK_DOUBLE AVR32_USBB_UPCFG0_PBK_DOUBLE
-
- #if defined(USB_SERIES_UC3A3_AVR32) || defined(USB_SERIES_UC3A4_AVR32) || defined(__DOXYGEN__)
- /** Mask for the bank mode selection for the \ref Pipe_ConfigurePipe() macro. This indicates that the
- * pipe should have three banks, which requires more USB FIFO memory but results in faster transfers
- * as one USB device (the AVR or the attached device) can access one bank while the other accesses the
- * remaining banks.
- *
- * \note Not available on all AVR models.
- */
- #define PIPE_BANK_TRIPLE AVR32_USBB_UPCFG0_PBK_TRIPLE
- #endif
- //@}
-
/** Default size of the default control pipe's bank, until altered by the Endpoint0Size value
* in the device descriptor of the attached device.
*/
@@ -224,6 +197,16 @@
return (&AVR32_USBB.UPSTA0)[USB_Pipe_SelectedPipe].pbyct;
}
+ /** Determines the currently selected pipe's direction.
+ *
+ * \return The currently selected pipe's direction, as a \c PIPE_DIR_* mask.
+ */
+ static inline uint8_t Pipe_GetPipeDirection(void) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
+ static inline uint8_t Pipe_GetPipeDirection(void)
+ {
+ return (((&AVR32_USBB.UPCFG0)[USB_Endpoint_SelectedEndpoint].ptoken == PIPE_TOKEN_OUT) ? PIPE_DIR_OUT : PIPE_DIR_IN);
+ }
+
/** Returns the pipe address of the currently selected pipe. This is typically used to save the
* currently selected pipe number so that it can be restored after another pipe has been manipulated.
*
@@ -232,30 +215,32 @@
static inline uint8_t Pipe_GetCurrentPipe(void) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
static inline uint8_t Pipe_GetCurrentPipe(void)
{
- return USB_Pipe_SelectedPipe;
+ return (USB_Pipe_SelectedPipe | Pipe_GetPipeDirection());
}
- /** Selects the given pipe number. Any pipe operations which do not require the pipe number to be
+ /** Selects the given pipe address. Any pipe operations which do not require the pipe address to be
* indicated will operate on the currently selected pipe.
*
- * \param[in] PipeNumber Index of the pipe to select.
+ * \param[in] Address Address of the pipe to select.
*/
- static inline void Pipe_SelectPipe(const uint8_t PipeNumber) ATTR_ALWAYS_INLINE;
- static inline void Pipe_SelectPipe(const uint8_t PipeNumber)
+ static inline void Pipe_SelectPipe(const uint8_t Address) ATTR_ALWAYS_INLINE;
+ static inline void Pipe_SelectPipe(const uint8_t Address)
{
- USB_Pipe_SelectedPipe = PipeNumber;
+ USB_Pipe_SelectedPipe = (Address & PIPE_EPNUM_MASK);
}
/** Resets the desired pipe, including the pipe banks and flags.
*
- * \param[in] PipeNumber Index of the pipe to reset.
+ * \param[in] Address Index of the pipe to reset.
*/
- static inline void Pipe_ResetPipe(const uint8_t PipeNumber) ATTR_ALWAYS_INLINE;
- static inline void Pipe_ResetPipe(const uint8_t PipeNumber)
+ static inline void Pipe_ResetPipe(const uint8_t Address) ATTR_ALWAYS_INLINE;
+ static inline void Pipe_ResetPipe(const uint8_t Address)
{
+ uint32_t PipeNumber = (Address & PIPE_EPNUM_MASK);
+
AVR32_USBB.uprst |= (AVR32_USBB_PRST0_MASK << PipeNumber);
AVR32_USBB.uprst &= ~(AVR32_USBB_PRST0_MASK << PipeNumber);
- USB_Pipe_FIFOPos[USB_Pipe_SelectedPipe] = &AVR32_USBB_SLAVE[USB_Pipe_SelectedPipe * PIPE_HSB_ADDRESS_SPACE_SIZE];
+ USB_Pipe_FIFOPos[PipeNumber] = &AVR32_USBB_SLAVE[PipeNumber * PIPE_HSB_ADDRESS_SPACE_SIZE];
}
/** Enables the currently selected pipe so that data can be sent and received through it to and from
@@ -349,7 +334,7 @@
static inline uint8_t Pipe_GetBoundEndpointAddress(void)
{
return ((&AVR32_USBB.UPCFG0)[USB_Pipe_SelectedPipe].pepnum |
- ((Pipe_GetPipeToken() == PIPE_TOKEN_IN) ? PIPE_EPDIR_MASK : 0));
+ ((Pipe_GetPipeToken() == PIPE_TOKEN_IN) ? PIPE_DIR_IN : PIPE_DIR_OUT));
}
/** Sets the period between interrupts for an INTERRUPT type pipe to a specified number of milliseconds.
@@ -376,17 +361,17 @@
AVR32_USBB_P0INT_MASK)) >> AVR32_USBB_P0INT_OFFSET);
}
- /** Determines if the specified pipe number has interrupted (valid only for INTERRUPT type
+ /** Determines if the specified pipe address has interrupted (valid only for INTERRUPT type
* pipes).
*
- * \param[in] PipeNumber Index of the pipe whose interrupt flag should be tested.
+ * \param[in] Address Address of the pipe whose interrupt flag should be tested.
*
* \return Boolean \c true if the specified pipe has interrupted, \c false otherwise.
*/
- static inline bool Pipe_HasPipeInterrupted(const uint8_t PipeNumber) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
- static inline bool Pipe_HasPipeInterrupted(const uint8_t PipeNumber)
+ static inline bool Pipe_HasPipeInterrupted(const uint8_t Address) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
+ static inline bool Pipe_HasPipeInterrupted(const uint8_t Address)
{
- return ((AVR32_USBB.uhint & (AVR32_USBB_P0INTES_MASK << PipeNumber)) ? true : false);
+ return ((AVR32_USBB.uhint & (AVR32_USBB_P0INTES_MASK << (Address & PIPE_EPNUM_MASK))) ? true : false);
}
/** Unfreezes the selected pipe, allowing it to communicate with an attached device. */
@@ -821,8 +806,22 @@
extern uint8_t USB_Host_ControlPipeSize;
/* Function Prototypes: */
- /** Configures the specified pipe number with the given pipe type, token, target endpoint number in the
- * attached device, bank size and banking mode.
+ /** Configures a table of pipe descriptions, in sequence. This function can be used to configure multiple
+ * pipes at the same time.
+ *
+ * \note Pipe with a zero address will be ignored, thus this function cannot be used to configure the
+ * control pipe.
+ *
+ * \param[in] Table Pointer to a table of pipe descriptions.
+ * \param[in] Entries Number of entries in the pipe table to configure.
+ *
+ * \return Boolean \c true if all pipes configured successfully, \c false otherwise.
+ */
+ bool Pipe_ConfigurePipeTable(const USB_Pipe_Table_t* const Table,
+ const uint8_t Entries);
+
+ /** Configures the specified pipe address with the given pipe type, endpoint address within the attached device, bank size
+ * and number of hardware banks.
*
* A newly configured pipe is frozen by default, and must be unfrozen before use via the \ref Pipe_Unfreeze()
* before being used. Pipes should be kept frozen unless waiting for data from a device while in IN mode, or
@@ -830,25 +829,19 @@
* numbers of IN requests without automatic freezing - this can be overridden by a call to
* \ref Pipe_SetFiniteINRequests().
*
- * \param[in] Number Pipe number to configure. This must be more than 0 and less than \ref PIPE_TOTAL_PIPES.
- *
- * \param[in] Type Type of pipe to configure, an \c EP_TYPE_* mask. Not all pipe types are available on Low
- * Speed USB devices - refer to the USB 2.0 specification.
+ * \param[in] Address Pipe address to configure.
*
- * \param[in] Token Pipe data token, either \ref PIPE_TOKEN_SETUP, \ref PIPE_TOKEN_OUT or \ref PIPE_TOKEN_IN.
- * All pipes (except Control type) are unidirectional - data may only be read from or
- * written to the pipe bank based on its direction, not both.
+ * \param[in] Type Type of pipe to configure, an \c EP_TYPE_* mask. Not all pipe types are available on Low
+ * Speed USB devices - refer to the USB 2.0 specification.
*
- * \param[in] EndpointNumber Endpoint index within the attached device that the pipe should interface to.
+ * \param[in] EndpointAddress Endpoint address within the attached device that the pipe should interface to.
*
- * \param[in] Size Size of the pipe's bank, where packets are stored before they are transmitted to
- * the USB device, or after they have been received from the USB device (depending on
- * the pipe's data direction). The bank size must indicate the maximum packet size that
- * the pipe can handle.
+ * \param[in] Size Size of the pipe's bank, where packets are stored before they are transmitted to
+ * the USB device, or after they have been received from the USB device (depending on
+ * the pipe's data direction). The bank size must indicate the maximum packet size that
+ * the pipe can handle.
*
- * \param[in] Banks Number of banks to use for the pipe being configured, a \c PIPE_BANK_* mask. More banks
- * uses more USB DPRAM, but offers better performance. Isochronous type pipes <b>must</b>
- * have at least two banks.
+ * \param[in] Banks Number of banks to use for the pipe being configured.
*
* \note When the \c ORDERED_EP_CONFIG compile time option is used, Pipes <b>must</b> be configured in ascending order,
* or bank corruption will occur.
@@ -867,10 +860,9 @@
*
* \return Boolean \c true if the configuration succeeded, \c false otherwise.
*/
- bool Pipe_ConfigurePipe(const uint8_t Number,
+ bool Pipe_ConfigurePipe(const uint8_t Address,
const uint8_t Type,
- const uint8_t Token,
- const uint8_t EndpointNumber,
+ const uint8_t EndpointAddress,
const uint16_t Size,
const uint8_t Banks);
diff --git a/LUFA/Drivers/USB/Core/UC3/USBController_UC3.c b/LUFA/Drivers/USB/Core/UC3/USBController_UC3.c
index 95ca7d9aa..32772446e 100644
--- a/LUFA/Drivers/USB/Core/UC3/USBController_UC3.c
+++ b/LUFA/Drivers/USB/Core/UC3/USBController_UC3.c
@@ -191,8 +191,7 @@ static void USB_Init_Device(void)
USB_INT_Enable(USB_INT_VBUSTI);
Endpoint_ConfigureEndpoint(ENDPOINT_CONTROLEP, EP_TYPE_CONTROL,
- ENDPOINT_DIR_OUT, USB_Device_ControlEndpointSize,
- ENDPOINT_BANK_SINGLE);
+ USB_Device_ControlEndpointSize, 1);
USB_INT_Clear(USB_INT_SUSPI);
USB_INT_Enable(USB_INT_SUSPI);
diff --git a/LUFA/Drivers/USB/Core/UC3/USBInterrupt_UC3.c b/LUFA/Drivers/USB/Core/UC3/USBInterrupt_UC3.c
index d411a9305..a2a5c4a96 100644
--- a/LUFA/Drivers/USB/Core/UC3/USBInterrupt_UC3.c
+++ b/LUFA/Drivers/USB/Core/UC3/USBInterrupt_UC3.c
@@ -121,8 +121,7 @@ ISR(USB_GEN_vect)
USB_Device_SetDeviceAddress(0);
Endpoint_ConfigureEndpoint(ENDPOINT_CONTROLEP, EP_TYPE_CONTROL,
- ENDPOINT_DIR_OUT, USB_Device_ControlEndpointSize,
- ENDPOINT_BANK_SINGLE);
+ USB_Device_ControlEndpointSize, 1);
#if defined(INTERRUPT_CONTROL_ENDPOINT)
USB_INT_Enable(USB_INT_RXSTPI);
diff --git a/LUFA/Drivers/USB/Core/USBController.h b/LUFA/Drivers/USB/Core/USBController.h
index a91e18c27..44a10e371 100644
--- a/LUFA/Drivers/USB/Core/USBController.h
+++ b/LUFA/Drivers/USB/Core/USBController.h
@@ -81,6 +81,24 @@
#define ENDPOINT_DIR_IN 0x80
//@}
+ /** \name Pipe Direction Masks */
+ //@{
+ /** Pipe direction mask, for masking against pipe addresses to retrieve the pipe's
+ * direction for comparing with the \c PIPE_DIR_* masks.
+ */
+ #define PIPE_DIR_MASK 0x80
+
+ /** Endpoint address direction mask for an OUT direction (Host to Device) endpoint. This may be ORed with
+ * the index of the address within a device to obtain the full endpoint address.
+ */
+ #define PIPE_DIR_OUT 0x00
+
+ /** Endpoint address direction mask for an IN direction (Device to Host) endpoint. This may be ORed with
+ * the index of the address within a device to obtain the full endpoint address.
+ */
+ #define PIPE_DIR_IN 0x80
+ //@}
+
/** \name Endpoint/Pipe Type Masks */
//@{
/** Mask for determining the type of an endpoint from an endpoint descriptor. This should then be compared
diff --git a/LUFA/Drivers/USB/Core/USBMode.h b/LUFA/Drivers/USB/Core/USBMode.h
index bc2f86dd5..56e5b5e84 100644
--- a/LUFA/Drivers/USB/Core/USBMode.h
+++ b/LUFA/Drivers/USB/Core/USBMode.h
@@ -137,6 +137,16 @@
*/
#define USB_SERIES_B3_XMEGA
+ /** Indicates that the target AVR microcontroller belongs to the XMEGA C3 Series USB controller
+ * (i.e. ATXMEGA*C3) when defined.
+ */
+ #define USB_SERIES_C3_XMEGA
+
+ /** Indicates that the target AVR microcontroller belongs to the XMEGA C4 Series USB controller
+ * (i.e. ATXMEGA*C4) when defined.
+ */
+ #define USB_SERIES_C4_XMEGA
+
/** Indicates that the target microcontroller and compilation settings allow for the
* target to be configured in USB Device mode when defined.
*/
@@ -219,6 +229,13 @@
#elif (defined(__AVR_ATxmega128B3__) || defined(__AVR_ATxmega64B3__))
#define USB_SERIES_B3_XMEGA
#define USB_CAN_BE_DEVICE
+ #elif (defined(__AVR_ATxmega128C3__) || defined(__AVR_ATxmega64C3__) || \
+ defined(__AVR_ATxmega192C3__) || defined(__AVR_ATxmega256C3__))
+ #define USB_SERIES_C3_XMEGA
+ #define USB_CAN_BE_DEVICE
+ #elif (defined(__AVR_ATxmega16C4__) || defined(__AVR_ATxmega32C4__))
+ #define USB_SERIES_C4_XMEGA
+ #define USB_CAN_BE_DEVICE
#endif
#if (defined(USB_CAN_BE_DEVICE) && defined(USB_CAN_BE_HOST))
diff --git a/LUFA/Drivers/USB/Core/XMEGA/Device_XMEGA.h b/LUFA/Drivers/USB/Core/XMEGA/Device_XMEGA.h
index 85be0f1bf..268fe95c0 100644
--- a/LUFA/Drivers/USB/Core/XMEGA/Device_XMEGA.h
+++ b/LUFA/Drivers/USB/Core/XMEGA/Device_XMEGA.h
@@ -157,7 +157,7 @@
static inline uint16_t USB_Device_GetFrameNumber(void) ATTR_ALWAYS_INLINE ATTR_WARN_UNUSED_RESULT;
static inline uint16_t USB_Device_GetFrameNumber(void)
{
- return USB_EndpointTable.FrameNum;
+ return ((USB_EndpointTable_t*)USB.EPPTR)->FrameNum;
}
#if !defined(NO_SOF_EVENTS)
diff --git a/LUFA/Drivers/USB/Core/XMEGA/Endpoint_XMEGA.c b/LUFA/Drivers/USB/Core/XMEGA/Endpoint_XMEGA.c
index 98e35e59a..1aeb985f8 100644
--- a/LUFA/Drivers/USB/Core/XMEGA/Endpoint_XMEGA.c
+++ b/LUFA/Drivers/USB/Core/XMEGA/Endpoint_XMEGA.c
@@ -48,20 +48,36 @@ volatile uint8_t USB_Endpoint_SelectedEndpoint;
volatile USB_EP_t* USB_Endpoint_SelectedHandle;
volatile Endpoint_FIFO_t* USB_Endpoint_SelectedFIFO;
-bool Endpoint_ConfigureEndpoint_PRV(const uint8_t Number,
- const uint8_t Direction,
+bool Endpoint_ConfigureEndpointTable(const USB_Endpoint_Table_t* const Table,
+ const uint8_t Entries)
+{
+ for (uint8_t i = 0; i < Entries; i++)
+ {
+ if (!(Table[i].Address))
+ continue;
+
+ if (!(Endpoint_ConfigureEndpoint(Table[i].Address, Table[i].Type, Table[i].Size, Table[i].Banks)))
+ {
+ return false;
+ }
+ }
+
+ return true;
+}
+
+bool Endpoint_ConfigureEndpoint_PRV(const uint8_t Address,
const uint8_t Config,
const uint8_t Size)
{
- Endpoint_SelectEndpoint(Number | Direction);
+ Endpoint_SelectEndpoint(Address);
USB_Endpoint_SelectedHandle->CTRL = 0;
- USB_Endpoint_SelectedHandle->STATUS = (Direction == ENDPOINT_DIR_IN) ? USB_EP_BUSNACK0_bm : 0;
+ USB_Endpoint_SelectedHandle->STATUS = (Address & ENDPOINT_DIR_IN) ? USB_EP_BUSNACK0_bm : 0;
USB_Endpoint_SelectedHandle->CTRL = Config;
USB_Endpoint_SelectedHandle->CNT = 0;
USB_Endpoint_SelectedHandle->DATAPTR = (intptr_t)USB_Endpoint_SelectedFIFO->Data;
- USB_Endpoint_SelectedFIFO->Length = (Direction == ENDPOINT_DIR_IN) ? Size : 0;
+ USB_Endpoint_SelectedFIFO->Length = (Address & ENDPOINT_DIR_IN) ? Size : 0;
USB_Endpoint_SelectedFIFO->Position = 0;
return true;
@@ -71,8 +87,8 @@ void Endpoint_ClearEndpoints(void)
{
for (uint8_t EPNum = 0; EPNum < ENDPOINT_TOTAL_ENDPOINTS; EPNum++)
{
- USB_EndpointTable.Endpoints[EPNum].IN.CTRL = 0;
- USB_EndpointTable.Endpoints[EPNum].OUT.CTRL = 0;
+ ((USB_EndpointTable_t*)USB.EPPTR)->Endpoints[EPNum].IN.CTRL = 0;
+ ((USB_EndpointTable_t*)USB.EPPTR)->Endpoints[EPNum].OUT.CTRL = 0;
}
}
diff --git a/LUFA/Drivers/USB/Core/XMEGA/Endpoint_XMEGA.h b/LUFA/Drivers/USB/Core/XMEGA/Endpoint_XMEGA.h
index 7828f308a..720b5f3b4 100644
--- a/LUFA/Drivers/USB/Core/XMEGA/Endpoint_XMEGA.h
+++ b/LUFA/Drivers/USB/Core/XMEGA/Endpoint_XMEGA.h
@@ -88,14 +88,20 @@
#error Do not include this file directly. Include LUFA/Drivers/USB/USB.h instead.
#endif
- /* Private Interface - For use in library only: */
- #if !defined(__DOXYGEN__)
+ /* Public Interface - May be used in end-application: */
/* Macros: */
- #define _ENDPOINT_GET_MAXSIZE(EPIndex) 1023
- #define _ENDPOINT_GET_BANKS(EPIndex) 2
-
- #define ENDPOINT_DETAILS_MAXEP 16
+ #if !defined(CONTROL_ONLY_DEVICE) || defined(__DOXYGEN__)
+ /** Total number of endpoints (including the default control endpoint at address 0) which may
+ * be used in the device. Different USB AVR models support different amounts of endpoints,
+ * this value reflects the maximum number of endpoints for the currently selected AVR model.
+ */
+ #define ENDPOINT_TOTAL_ENDPOINTS 16
+ #else
+ #define ENDPOINT_TOTAL_ENDPOINTS 1
+ #endif
+ /* Private Interface - For use in library only: */
+ #if !defined(__DOXYGEN__)
/* Type Defines: */
typedef struct
{
@@ -112,7 +118,7 @@
} Endpoint_FIFOPair_t;
/* External Variables: */
- extern Endpoint_FIFOPair_t USB_Endpoint_FIFOs[ENDPOINT_DETAILS_MAXEP];
+ extern Endpoint_FIFOPair_t USB_Endpoint_FIFOs[ENDPOINT_TOTAL_ENDPOINTS];
extern volatile uint8_t USB_Endpoint_SelectedEndpoint;
extern volatile USB_EP_t* USB_Endpoint_SelectedHandle;
extern volatile Endpoint_FIFO_t* USB_Endpoint_SelectedFIFO;
@@ -135,8 +141,7 @@
}
/* Function Prototypes: */
- bool Endpoint_ConfigureEndpoint_PRV(const uint8_t Number,
- const uint8_t Direction,
+ bool Endpoint_ConfigureEndpoint_PRV(const uint8_t Address,
const uint8_t Config,
const uint8_t Size);
void Endpoint_ClearEndpoints(void);
@@ -144,23 +149,6 @@
/* Public Interface - May be used in end-application: */
/* Macros: */
- /** \name Endpoint Bank Mode Masks */
- //@{
- /** Mask for the bank mode selection for the \ref Endpoint_ConfigureEndpoint() macro. This indicates
- * that the endpoint should have one single bank, which requires less USB FIFO memory but results
- * in slower transfers as only one USB device (the AVR or the host) can access the endpoint's
- * bank at the one time.
- */
- #define ENDPOINT_BANK_SINGLE 0
-
- /** Mask for the bank mode selection for the \ref Endpoint_ConfigureEndpoint() macro. This indicates
- * that the endpoint should have two banks, which requires more USB FIFO memory but results
- * in faster transfers as one USB device (the AVR or the host) can access one bank while the other
- * accesses the second bank.
- */
- #define ENDPOINT_BANK_DOUBLE USB_EP_PINGPONG_bm
- //@}
-
#if (!defined(FIXED_CONTROL_ENDPOINT_SIZE) || defined(__DOXYGEN__))
/** Default size of the default control endpoint's bank, until altered by the control endpoint bank size
* value in the device descriptor. Not available if the \c FIXED_CONTROL_ENDPOINT_SIZE token is defined.
@@ -168,34 +156,6 @@
#define ENDPOINT_CONTROLEP_DEFAULT_SIZE 8
#endif
- /** Retrieves the maximum bank size in bytes of a given endpoint.
- *
- * \attention This macro will only work correctly on endpoint indexes that are compile-time constants
- * defined by the preprocessor.
- *
- * \param[in] EPIndex Endpoint number, a value between 0 and (\ref ENDPOINT_TOTAL_ENDPOINTS - 1)
- */
- #define ENDPOINT_MAX_SIZE(EPIndex) _ENDPOINT_GET_MAXSIZE(EPIndex)
-
- /** Retrieves the total number of banks supported by the given endpoint.
- *
- * \attention This macro will only work correctly on endpoint indexes that are compile-time constants
- * defined by the preprocessor.
- *
- * \param[in] EPIndex Endpoint number, a value between 0 and (\ref ENDPOINT_TOTAL_ENDPOINTS - 1)
- */
- #define ENDPOINT_BANKS_SUPPORTED(EPIndex) _ENDPOINT_GET_BANKS(EPIndex)
-
- #if !defined(CONTROL_ONLY_DEVICE) || defined(__DOXYGEN__)
- /** Total number of endpoints (including the default control endpoint at address 0) which may
- * be used in the device. Different USB AVR models support different amounts of endpoints,
- * this value reflects the maximum number of endpoints for the currently selected AVR model.
- */
- #define ENDPOINT_TOTAL_ENDPOINTS ENDPOINT_DETAILS_MAXEP
- #else
- #define ENDPOINT_TOTAL_ENDPOINTS 1
- #endif
-
/* Enums: */
/** Enum for the possible error return codes of the \ref Endpoint_WaitUntilReady() function.
*
@@ -221,54 +181,47 @@
};
/* Inline Functions: */
- /** Selects the given endpoint number. If the address from the device descriptors is used, the
- * value should be masked with the \ref ENDPOINT_EPNUM_MASK constant to extract only the endpoint
- * number (and discarding the endpoint direction bit).
+ /** Selects the given endpoint address.
*
- * Any endpoint operations which do not require the endpoint number to be indicated will operate on
+ * Any endpoint operations which do not require the endpoint address to be indicated will operate on
* the currently selected endpoint.
*
- * \param[in] EndpointNumber Endpoint number to select.
+ * \param[in] Address Endpoint address to select.
*/
- static inline void Endpoint_SelectEndpoint(const uint8_t EndpointNumber);
- static inline void Endpoint_SelectEndpoint(const uint8_t EndpointNumber)
+ static inline void Endpoint_SelectEndpoint(const uint8_t Address);
+ static inline void Endpoint_SelectEndpoint(const uint8_t Address)
{
- USB_Endpoint_SelectedEndpoint = EndpointNumber;
+ uint8_t EndpointNumber = (Address & ENDPOINT_EPNUM_MASK);
+
+ USB_Endpoint_SelectedEndpoint = Address;
- if (EndpointNumber & ENDPOINT_DIR_IN)
+ if (Address & ENDPOINT_DIR_IN)
{
- USB_Endpoint_SelectedFIFO = &USB_Endpoint_FIFOs[EndpointNumber & ENDPOINT_EPNUM_MASK].IN;
- USB_Endpoint_SelectedHandle = &USB_EndpointTable.Endpoints[EndpointNumber & ENDPOINT_EPNUM_MASK].IN;
+ USB_Endpoint_SelectedFIFO = &USB_Endpoint_FIFOs[EndpointNumber].IN;
+ USB_Endpoint_SelectedHandle = &((USB_EndpointTable_t*)USB.EPPTR)->Endpoints[EndpointNumber].IN;
}
else
{
- USB_Endpoint_SelectedFIFO = &USB_Endpoint_FIFOs[EndpointNumber & ENDPOINT_EPNUM_MASK].OUT;
- USB_Endpoint_SelectedHandle = &USB_EndpointTable.Endpoints[EndpointNumber & ENDPOINT_EPNUM_MASK].OUT;
+ USB_Endpoint_SelectedFIFO = &USB_Endpoint_FIFOs[EndpointNumber].OUT;
+ USB_Endpoint_SelectedHandle = &((USB_EndpointTable_t*)USB.EPPTR)->Endpoints[EndpointNumber].OUT;
}
}
- /** Configures the specified endpoint number with the given endpoint type, direction, bank size
+ /** Configures the specified endpoint address with the given endpoint type, direction, bank size
* and banking mode. Once configured, the endpoint may be read from or written to, depending
* on its direction.
*
- * \param[in] Number Endpoint number to configure. This must be more than 0 and less than
- * \ref ENDPOINT_TOTAL_ENDPOINTS.
+ * \param[in] Address Endpoint address to configure.
*
* \param[in] Type Type of endpoint to configure, a \c EP_TYPE_* mask. Not all endpoint types
* are available on Low Speed USB devices - refer to the USB 2.0 specification.
*
- * \param[in] Direction Endpoint data direction, either \ref ENDPOINT_DIR_OUT or \ref ENDPOINT_DIR_IN.
- * All endpoints (except Control type) are unidirectional - data may only be read
- * from or written to the endpoint bank based on its direction, not both.
- *
* \param[in] Size Size of the endpoint's bank, where packets are stored before they are transmitted
* to the USB host, or after they have been received from the USB host (depending on
* the endpoint's data direction). The bank size must indicate the maximum packet size
* that the endpoint can handle.
*
- * \param[in] Banks Number of banks to use for the endpoint being configured, an \c ENDPOINT_BANK_* mask.
- * More banks uses more USB DPRAM, but offers better performance. Isochronous type
- * endpoints <b>must</b> have at least two banks.
+ * \param[in] Banks Number of hardware banks to use for the endpoint being configured.
*
* \note The default control endpoint should not be manually configured by the user application, as
* it is automatically configured by the library internally.
@@ -278,21 +231,19 @@
*
* \return Boolean \c true if the configuration succeeded, \c false otherwise.
*/
- static inline bool Endpoint_ConfigureEndpoint(const uint8_t Number,
+ static inline bool Endpoint_ConfigureEndpoint(const uint8_t Address,
const uint8_t Type,
- const uint8_t Direction,
const uint16_t Size,
const uint8_t Banks) ATTR_ALWAYS_INLINE;
- static inline bool Endpoint_ConfigureEndpoint(const uint8_t Number,
+ static inline bool Endpoint_ConfigureEndpoint(const uint8_t Address,
const uint8_t Type,
- const uint8_t Direction,
const uint16_t Size,
const uint8_t Banks)
{
- uint8_t EPConfigMask = (USB_EP_INTDSBL_bm | Banks | Endpoint_BytesToEPSizeMask(Size));
+ uint8_t EPConfigMask = (USB_EP_INTDSBL_bm | ((Banks > 1) ? USB_EP_PINGPONG_bm : 0) | Endpoint_BytesToEPSizeMask(Size));
// TODO - Fix once limitations are lifted
- if ((Banks != ENDPOINT_BANK_SINGLE) || (Size > 64))
+ if ((Banks > 1) || (Size > 64))
return false;
switch (Type)
@@ -309,9 +260,9 @@
}
if (Type == EP_TYPE_CONTROL)
- Endpoint_ConfigureEndpoint_PRV(Number, (Direction ^ ENDPOINT_DIR_IN), EPConfigMask, Size);
+ Endpoint_ConfigureEndpoint_PRV(Address ^ ENDPOINT_DIR_IN, EPConfigMask, Size);
- return Endpoint_ConfigureEndpoint_PRV(Number, Direction, EPConfigMask, Size);
+ return Endpoint_ConfigureEndpoint_PRV(Address, EPConfigMask, Size);
}
/** Indicates the number of bytes currently stored in the current endpoint's selected bank.
@@ -327,8 +278,8 @@
}
/** Get the endpoint address of the currently selected endpoint. This is typically used to save
- * the currently selected endpoint number so that it can be restored after another endpoint has
- * been manipulated.
+ * the currently selected endpoint so that it can be restored after another endpoint has been
+ * manipulated.
*
* \return Index of the currently selected endpoint.
*/
@@ -341,15 +292,15 @@
/** Resets the endpoint bank FIFO. This clears all the endpoint banks and resets the USB controller's
* data In and Out pointers to the bank's contents.
*
- * \param[in] EndpointNumber Endpoint number whose FIFO buffers are to be reset.
+ * \param[in] Address Endpoint address whose FIFO buffers are to be reset.
*/
- static inline void Endpoint_ResetEndpoint(const uint8_t EndpointNumber) ATTR_ALWAYS_INLINE;
- static inline void Endpoint_ResetEndpoint(const uint8_t EndpointNumber)
+ static inline void Endpoint_ResetEndpoint(const uint8_t Address) ATTR_ALWAYS_INLINE;
+ static inline void Endpoint_ResetEndpoint(const uint8_t Address)
{
- if (EndpointNumber & ENDPOINT_DIR_IN)
- USB_Endpoint_FIFOs[EndpointNumber & ENDPOINT_EPNUM_MASK].IN.Position = 0;
+ if (Address & ENDPOINT_DIR_IN)
+ USB_Endpoint_FIFOs[Address & ENDPOINT_EPNUM_MASK].IN.Position = 0;
else
- USB_Endpoint_FIFOs[EndpointNumber & ENDPOINT_EPNUM_MASK].OUT.Position = 0;
+ USB_Endpoint_FIFOs[Address & ENDPOINT_EPNUM_MASK].OUT.Position = 0;
}
/** Determines if the currently selected endpoint is enabled, but not necessarily configured.
@@ -388,10 +339,7 @@
static inline bool Endpoint_IsReadWriteAllowed(void) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
static inline bool Endpoint_IsReadWriteAllowed(void)
{
- if (USB_Endpoint_SelectedEndpoint & ENDPOINT_DIR_IN)
- return (USB_Endpoint_SelectedFIFO->Position < USB_Endpoint_SelectedFIFO->Length);
- else
- return (USB_Endpoint_SelectedFIFO->Position > 0);
+ return (USB_Endpoint_SelectedFIFO->Position < USB_Endpoint_SelectedFIFO->Length);
}
/** Determines if the currently selected endpoint is configured.
@@ -404,32 +352,6 @@
return ((USB_Endpoint_SelectedHandle->CTRL & USB_EP_TYPE_gm) ? true : false);
}
- /** Returns a mask indicating which INTERRUPT type endpoints have interrupted - i.e. their
- * interrupt duration has elapsed. Which endpoints have interrupted can be determined by
- * masking the return value against <tt>(1 << <i>{Endpoint Number}</i>)</tt>.
- *
- * \return Mask whose bits indicate which endpoints have interrupted.
- */
- static inline uint8_t Endpoint_GetEndpointInterrupts(void) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
- static inline uint8_t Endpoint_GetEndpointInterrupts(void)
- {
- return 0; // TODO
- }
-
- /** Determines if the specified endpoint number has interrupted (valid only for INTERRUPT type
- * endpoints).
- *
- * \param[in] EndpointNumber Index of the endpoint whose interrupt flag should be tested.
- *
- * \return Boolean \c true if the specified endpoint has interrupted, \c false otherwise.
- */
- static inline bool Endpoint_HasEndpointInterrupted(const uint8_t EndpointNumber) ATTR_WARN_UNUSED_RESULT ATTR_ALWAYS_INLINE;
- static inline bool Endpoint_HasEndpointInterrupted(const uint8_t EndpointNumber)
- {
- (void)EndpointNumber;
- return 0; // TODO
- }
-
/** Determines if the selected IN endpoint is ready for a new packet to be sent to the host.
*
* \ingroup Group_EndpointPacketManagement_XMEGA
@@ -800,6 +722,20 @@
#endif
/* Function Prototypes: */
+ /** Configures a table of endpoint descriptions, in sequence. This function can be used to configure multiple
+ * endpoints at the same time.
+ *
+ * \note Endpoints with a zero address will be ignored, thus this function cannot be used to configure the
+ * control endpoint.
+ *
+ * \param[in] Table Pointer to a table of endpoint descriptions.
+ * \param[in] Entries Number of entries in the endpoint table to configure.
+ *
+ * \return Boolean \c true if all endpoints configured successfully, \c false otherwise.
+ */
+ bool Endpoint_ConfigureEndpointTable(const USB_Endpoint_Table_t* const Table,
+ const uint8_t Entries);
+
/** Completes the status stage of a control transfer on a CONTROL type endpoint automatically,
* with respect to the data direction. This is a convenience function which can be used to
* simplify user control request handling.
diff --git a/LUFA/Drivers/USB/Core/XMEGA/USBController_XMEGA.c b/LUFA/Drivers/USB/Core/XMEGA/USBController_XMEGA.c
index 387e8e417..ffdca3adf 100644
--- a/LUFA/Drivers/USB/Core/XMEGA/USBController_XMEGA.c
+++ b/LUFA/Drivers/USB/Core/XMEGA/USBController_XMEGA.c
@@ -43,7 +43,8 @@ volatile uint8_t USB_CurrentMode = USB_MODE_None;
volatile uint8_t USB_Options;
#endif
-USB_EndpointTable_t USB_EndpointTable ATTR_ALIGNED(4);
+/* Ugly workaround to ensure an aligned table, since __BIGGEST_ALIGNMENT__ == 1 for 8-bit AVR-GCC */
+uint8_t USB_EndpointTable[sizeof(USB_EndpointTable_t) + 1];
void USB_Init(
#if defined(USB_CAN_BE_BOTH)
@@ -75,8 +76,9 @@ void USB_Init(
USB.CAL1 = pgm_read_byte(offsetof(NVM_PROD_SIGNATURES_t, USBCAL1));
NVM.CMD = 0;
- USB.EPPTR = (intptr_t)&USB_EndpointTable;
- USB.CTRLA = (USB_STFRNUM_bm | USB_MAXEP_gm);
+ /* Ugly workaround to ensure an aligned table, since __BIGGEST_ALIGNMENT__ == 1 for 8-bit AVR-GCC */
+ USB.EPPTR = ((intptr_t)&USB_EndpointTable[1] & ~(1 << 0));
+ USB.CTRLA = (USB_STFRNUM_bm | ((ENDPOINT_TOTAL_ENDPOINTS - 1) << USB_MAXEP_gp));
if ((USB_Options & USB_OPT_BUSEVENT_PRIHIGH) == USB_OPT_BUSEVENT_PRIHIGH)
USB.INTCTRLA = (3 << USB_INTLVL_gp);
@@ -109,7 +111,7 @@ void USB_ResetInterface(void)
CLK.USBCTRL = (((F_USB / 48000000) - 1) << CLK_USBPSDIV_gp);
if (USB_Options & USB_OPT_PLLCLKSRC)
- CLK.USBCTRL |= (CLK_USBSRC_PLL_gc | CLK_USBSEN_bm);
+ CLK.USBCTRL |= (CLK_USBSRC_PLL_gc | CLK_USBSEN_bm);
else
CLK.USBCTRL |= (CLK_USBSRC_RC32M_gc | CLK_USBSEN_bm);
@@ -172,8 +174,7 @@ static void USB_Init_Device(void)
USB_Device_SetFullSpeed();
Endpoint_ConfigureEndpoint(ENDPOINT_CONTROLEP, EP_TYPE_CONTROL,
- ENDPOINT_DIR_OUT, USB_Device_ControlEndpointSize,
- ENDPOINT_BANK_SINGLE);
+ USB_Device_ControlEndpointSize, 1);
USB_INT_Enable(USB_INT_BUSEVENTI);
diff --git a/LUFA/Drivers/USB/Core/XMEGA/USBController_XMEGA.h b/LUFA/Drivers/USB/Core/XMEGA/USBController_XMEGA.h
index 2f14f758a..1cdb6f03c 100644
--- a/LUFA/Drivers/USB/Core/XMEGA/USBController_XMEGA.h
+++ b/LUFA/Drivers/USB/Core/XMEGA/USBController_XMEGA.h
@@ -69,7 +69,7 @@
} ATTR_PACKED USB_EndpointTable_t;
/* External Variables: */
- extern USB_EndpointTable_t USB_EndpointTable;
+ extern uint8_t USB_EndpointTable[];
#endif
diff --git a/LUFA/Drivers/USB/Core/XMEGA/USBInterrupt_XMEGA.c b/LUFA/Drivers/USB/Core/XMEGA/USBInterrupt_XMEGA.c
index b0e52d06e..3554165c1 100644
--- a/LUFA/Drivers/USB/Core/XMEGA/USBInterrupt_XMEGA.c
+++ b/LUFA/Drivers/USB/Core/XMEGA/USBInterrupt_XMEGA.c
@@ -97,8 +97,7 @@ ISR(USB_BUSEVENT_vect)
Endpoint_ClearEndpoints();
Endpoint_ConfigureEndpoint(ENDPOINT_CONTROLEP, EP_TYPE_CONTROL,
- ENDPOINT_DIR_OUT, USB_Device_ControlEndpointSize,
- ENDPOINT_BANK_SINGLE);
+ USB_Device_ControlEndpointSize, 1);
EVENT_USB_Device_Reset();
}
diff --git a/LUFA/Drivers/USB/USB.h b/LUFA/Drivers/USB/USB.h
index 35b285c6d..c99c1d267 100644
--- a/LUFA/Drivers/USB/USB.h
+++ b/LUFA/Drivers/USB/USB.h
@@ -166,9 +166,12 @@
* .Config =
* {
* .StreamingInterfaceNumber = 1,
- *
- * .DataINEndpointNumber = 1,
- * .DataINEndpointSize = 256,
+ * .DataINEndpoint =
+ * {
+ * .Address = (ENDPOINT_DIR_IN | 1),
+ * .Size = 64,
+ * .Banks = 1,
+ * },
* },
* };
* \endcode
@@ -262,11 +265,18 @@
* {
* .Config =
* {
- * .DataINPipeNumber = 1,
- * .DataINPipeDoubleBank = false,
- *
- * .DataOUTPipeNumber = 2,
- * .DataOUTPipeDoubleBank = false,
+ * .DataINPipe =
+ * {
+ * .Address = (PIPE_DIR_IN | 1),
+ * .Size = 64,
+ * .Banks = 1,
+ * },
+ * .DataOUTPipe =
+ * {
+ * .Address = (PIPE_DIR_OUT | 2),
+ * .Size = 64,
+ * .Banks = 1,
+ * },
* },
* };
* \endcode