diff --git a/Bootloaders/CDC/BootloaderCDC.c b/Bootloaders/CDC/BootloaderCDC.c
index 6b69421e0373f4e98d895bd14021854c480d692d..708ba359d5d53b18cb115e1f9c3f67450e0230d2 100644
--- a/Bootloaders/CDC/BootloaderCDC.c
+++ b/Bootloaders/CDC/BootloaderCDC.c
@@ -152,13 +152,11 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 {
 	uint8_t* LineCodingData = (uint8_t*)&LineCoding;
 
-	Endpoint_Discard_Word();
-
 	/* Process CDC specific control requests */
-	switch (bRequest)
+	switch (USB_ControlRequest.bRequest)
 	{
 		case REQ_GetLineEncoding:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				Endpoint_ClearSETUP();
 
@@ -174,7 +172,7 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 			
 			break;
 		case REQ_SetLineEncoding:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				Endpoint_ClearSETUP();
 
@@ -192,7 +190,7 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 	
 			break;
 		case REQ_SetControlLineState:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				Endpoint_ClearSETUP();
 				
diff --git a/Bootloaders/DFU/BootloaderDFU.c b/Bootloaders/DFU/BootloaderDFU.c
index 289b4eb22329e4c038b6ed7c3bd67f69d75373b3..83881f13ec836136298435df665f3b06c53ffc8f 100644
--- a/Bootloaders/DFU/BootloaderDFU.c
+++ b/Bootloaders/DFU/BootloaderDFU.c
@@ -151,16 +151,10 @@ EVENT_HANDLER(USB_Disconnect)
  */
 EVENT_HANDLER(USB_UnhandledControlPacket)
 {
-	/* Discard unused wIndex value */
-	Endpoint_Discard_Word();
-	
-	/* Discard unused wValue value */
-	Endpoint_Discard_Word();
-
 	/* Get the size of the command and data from the wLength value */
-	SentCommand.DataSize = Endpoint_Read_Word_LE();
+	SentCommand.DataSize = USB_ControlRequest.wLength;
 
-	switch (bRequest)
+	switch (USB_ControlRequest.bRequest)
 	{
 		case DFU_DNLOAD:
 			Endpoint_ClearSETUP();
diff --git a/Bootloaders/TeensyHID/TeensyHID.c b/Bootloaders/TeensyHID/TeensyHID.c
index e81c462a0a8263e4283b3a2f088a556b69b6f03c..cb1407ad4beb73199239f6af3e2e3b9b81873fee 100644
--- a/Bootloaders/TeensyHID/TeensyHID.c
+++ b/Bootloaders/TeensyHID/TeensyHID.c
@@ -96,10 +96,10 @@ EVENT_HANDLER(USB_ConfigurationChanged)
 EVENT_HANDLER(USB_UnhandledControlPacket)
 {
 	/* Handle HID Class specific requests */
-	switch (bRequest)
+	switch (USB_ControlRequest.bRequest)
 	{
 		case REQ_SetReport:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				Endpoint_ClearSETUP();
 				
diff --git a/Demos/Device/AudioInput/AudioInput.c b/Demos/Device/AudioInput/AudioInput.c
index 45b9971f8ce6f0e0609be29d30a7ca04065f8b13..05094c2b888d7e553c300c7fcdd9abba061d45ae 100644
--- a/Demos/Device/AudioInput/AudioInput.c
+++ b/Demos/Device/AudioInput/AudioInput.c
@@ -131,18 +131,16 @@ EVENT_HANDLER(USB_ConfigurationChanged)
 EVENT_HANDLER(USB_UnhandledControlPacket)
 {
 	/* Process General and Audio specific control requests */
-	switch (bRequest)
+	switch (USB_ControlRequest.bRequest)
 	{
 		case REQ_SetInterface:
 			/* Set Interface is not handled by the library, as its function is application-specific */
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_INTERFACE))
 			{
-				uint16_t wValue = Endpoint_Read_Word_LE();
-				
 				Endpoint_ClearSETUP();
 				
 				/* Check if the host is enabling the audio interface (setting AlternateSetting to 1) */
-				if (wValue)
+				if (USB_ControlRequest.wValue)
 				{
 					/* Start audio task */
 					Scheduler_SetTaskMode(USB_Audio_Task, TASK_RUN);
diff --git a/Demos/Device/AudioOutput/AudioOutput.c b/Demos/Device/AudioOutput/AudioOutput.c
index ba9a499a4031c46257211349bea1704a3bb58fa6..640462da16ce5bf170dae099aaf64b7beb68c7bc 100644
--- a/Demos/Device/AudioOutput/AudioOutput.c
+++ b/Demos/Device/AudioOutput/AudioOutput.c
@@ -158,18 +158,16 @@ EVENT_HANDLER(USB_ConfigurationChanged)
 EVENT_HANDLER(USB_UnhandledControlPacket)
 {
 	/* Process General and Audio specific control requests */
-	switch (bRequest)
+	switch (USB_ControlRequest.bRequest)
 	{
 		case REQ_SetInterface:
 			/* Set Interface is not handled by the library, as its function is application-specific */
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_INTERFACE))
 			{
-				uint16_t wValue = Endpoint_Read_Word_LE();
-				
 				Endpoint_ClearSETUP();
 				
 				/* Check if the host is enabling the audio interface (setting AlternateSetting to 1) */
-				if (wValue)
+				if (USB_ControlRequest.wValue)
 				{
 					/* Start audio task */
 					Scheduler_SetTaskMode(USB_Audio_Task, TASK_RUN);
diff --git a/Demos/Device/CDC/CDC.c b/Demos/Device/CDC/CDC.c
index fb7d74b073f56271475c033fe12f0bd663b61b88..28bce1ebcdbcafd093c87bde5875bcf259c3965c 100644
--- a/Demos/Device/CDC/CDC.c
+++ b/Demos/Device/CDC/CDC.c
@@ -160,10 +160,10 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 	uint8_t* LineCodingData = (uint8_t*)&LineCoding;
 
 	/* Process CDC specific control requests */
-	switch (bRequest)
+	switch (USB_ControlRequest.bRequest)
 	{
 		case REQ_GetLineEncoding:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{	
 				/* Acknowledge the SETUP packet, ready for data transfer */
 				Endpoint_ClearSETUP();
@@ -177,7 +177,7 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 			
 			break;
 		case REQ_SetLineEncoding:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				/* Acknowledge the SETUP packet, ready for data transfer */
 				Endpoint_ClearSETUP();
@@ -191,18 +191,12 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 	
 			break;
 		case REQ_SetControlLineState:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
-#if 0
 				/* NOTE: Here you can read in the line state mask from the host, to get the current state of the output handshake
-				         lines. The mask is read in from the wValue parameter, and can be masked against the CONTROL_LINE_OUT_* masks
-				         to determine the RTS and DTR line states using the following code:
+				         lines. The mask is read in from the wValue parameter in USB_ControlRequest, and can be masked against the
+						 CONTROL_LINE_OUT_* masks to determine the RTS and DTR line states using the following code:
 				*/
-
-				uint16_t wIndex = Endpoint_Read_Word_LE();
-					
-				// Do something with the given line states in wIndex
-#endif
 				
 				/* Acknowledge the SETUP packet, ready for data transfer */
 				Endpoint_ClearSETUP();
diff --git a/Demos/Device/DualCDC/DualCDC.c b/Demos/Device/DualCDC/DualCDC.c
index bbcbecc3d4af69f389d32687bdecb000ec0a9f63..4185a76bd7499bdc19096c5eed171af69d105b7c 100644
--- a/Demos/Device/DualCDC/DualCDC.c
+++ b/Demos/Device/DualCDC/DualCDC.c
@@ -198,10 +198,10 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 	LineCodingData = (wIndex == 0) ? (uint8_t*)&LineCoding1 : (uint8_t*)&LineCoding2;
 
 	/* Process CDC specific control requests */
-	switch (bRequest)
+	switch (USB_ControlRequest.bRequest)
 	{
 		case REQ_GetLineEncoding:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{	
 				/* Acknowledge the SETUP packet, ready for data transfer */
 				Endpoint_ClearSETUP();
@@ -215,7 +215,7 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 			
 			break;
 		case REQ_SetLineEncoding:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				/* Acknowledge the SETUP packet, ready for data transfer */
 				Endpoint_ClearSETUP();
@@ -229,7 +229,7 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 	
 			break;
 		case REQ_SetControlLineState:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				/* Acknowledge the SETUP packet, ready for data transfer */
 				Endpoint_ClearSETUP();
diff --git a/Demos/Device/GenericHID/GenericHID.c b/Demos/Device/GenericHID/GenericHID.c
index 207f63c26469349ab80a458f3c0ddf004df16ee5..245ddaafc639da6a5f3b97fbfa73ef855448336a 100644
--- a/Demos/Device/GenericHID/GenericHID.c
+++ b/Demos/Device/GenericHID/GenericHID.c
@@ -160,10 +160,10 @@ EVENT_HANDLER(USB_ConfigurationChanged)
 EVENT_HANDLER(USB_UnhandledControlPacket)
 {
 	/* Handle HID Class specific requests */
-	switch (bRequest)
+	switch (USB_ControlRequest.bRequest)
 	{
 		case REQ_GetReport:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				Endpoint_ClearSETUP();
 	
@@ -180,7 +180,7 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 		
 			break;
 		case REQ_SetReport:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				Endpoint_ClearSETUP();
 				
diff --git a/Demos/Device/Joystick/Joystick.c b/Demos/Device/Joystick/Joystick.c
index e5d23bd6d5dd8773b93523048fc9af69a3c4382b..ee4bc6ad0e136803e1de16219158368eb9750e46 100644
--- a/Demos/Device/Joystick/Joystick.c
+++ b/Demos/Device/Joystick/Joystick.c
@@ -122,33 +122,20 @@ EVENT_HANDLER(USB_ConfigurationChanged)
 EVENT_HANDLER(USB_UnhandledControlPacket)
 {
 	/* Handle HID Class specific requests */
-	switch (bRequest)
+	switch (USB_ControlRequest.bRequest)
 	{
 		case REQ_GetReport:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				USB_JoystickReport_Data_t JoystickReportData;
 				
 				/* Create the next HID report to send to the host */				
 				GetNextReport(&JoystickReportData);
-
-				/* Ignore report type and ID number value */
-				Endpoint_Discard_Word();
-				
-				/* Ignore unused Interface number value */
-				Endpoint_Discard_Word();
-
-				/* Read in the number of bytes in the report to send to the host */
-				uint16_t wLength = Endpoint_Read_Word_LE();
 				
-				/* If trying to send more bytes than exist to the host, clamp the value at the report size */
-				if (wLength > sizeof(JoystickReportData))
-				  wLength = sizeof(JoystickReportData);
-
 				Endpoint_ClearSETUP();
 	
 				/* Write the report data to the control endpoint */
-				Endpoint_Write_Control_Stream_LE(&JoystickReportData, wLength);
+				Endpoint_Write_Control_Stream_LE(&JoystickReportData, sizeof(JoystickReportData));
 				
 				/* Finalize the stream transfer to send the last packet or clear the host abort */
 				Endpoint_ClearOUT();
diff --git a/Demos/Device/Keyboard/Keyboard.c b/Demos/Device/Keyboard/Keyboard.c
index 6d7ee3fcd1d06b0be35f7ce42568c69faa318cbb..088943bce6265a37ac1e9dfce1df3d5f398e72f7 100644
--- a/Demos/Device/Keyboard/Keyboard.c
+++ b/Demos/Device/Keyboard/Keyboard.c
@@ -193,33 +193,20 @@ EVENT_HANDLER(USB_ConfigurationChanged)
 EVENT_HANDLER(USB_UnhandledControlPacket)
 {
 	/* Handle HID Class specific requests */
-	switch (bRequest)
+	switch (USB_ControlRequest.bRequest)
 	{
 		case REQ_GetReport:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				USB_KeyboardReport_Data_t KeyboardReportData;
 
 				/* Create the next keyboard report for transmission to the host */
 				CreateKeyboardReport(&KeyboardReportData);
 
-				/* Ignore report type and ID number value */
-				Endpoint_Discard_Word();
-				
-				/* Ignore unused Interface number value */
-				Endpoint_Discard_Word();
-
-				/* Read in the number of bytes in the report to send to the host */
-				uint16_t wLength = Endpoint_Read_Word_LE();
-				
-				/* If trying to send more bytes than exist to the host, clamp the value at the report size */
-				if (wLength > sizeof(KeyboardReportData))
-				  wLength = sizeof(KeyboardReportData);
-
 				Endpoint_ClearSETUP();
 	
 				/* Write the report data to the control endpoint */
-				Endpoint_Write_Control_Stream_LE(&KeyboardReportData, wLength);
+				Endpoint_Write_Control_Stream_LE(&KeyboardReportData, sizeof(KeyboardReportData));
 				
 				/* Finalize the stream transfer to send the last packet or clear the host abort */
 				Endpoint_ClearOUT();
@@ -227,7 +214,7 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 		
 			break;
 		case REQ_SetReport:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				Endpoint_ClearSETUP();
 				
@@ -250,7 +237,7 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 			
 			break;
 		case REQ_GetProtocol:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				Endpoint_ClearSETUP();
 				
@@ -267,15 +254,12 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 			
 			break;
 		case REQ_SetProtocol:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
-				/* Read in the wValue parameter containing the new protocol mode */
-				uint16_t wValue = Endpoint_Read_Word_LE();
-								
 				Endpoint_ClearSETUP();
 
 				/* Set or clear the flag depending on what the host indicates that the current Protocol should be */
-				UsingReportProtocol = (wValue != 0x0000);
+				UsingReportProtocol = (USB_ControlRequest.wValue != 0x0000);
 
 				/* Acknowledge status stage */
 				while (!(Endpoint_IsINReady()));
@@ -284,15 +268,12 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 			
 			break;
 		case REQ_SetIdle:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
-				/* Read in the wValue parameter containing the idle period */
-				uint16_t wValue = Endpoint_Read_Word_LE();
-				
 				Endpoint_ClearSETUP();
 				
 				/* Get idle period in MSB */
-				IdleCount = (wValue >> 8);
+				IdleCount = (USB_ControlRequest.wValue >> 8);
 				
 				/* Acknowledge status stage */
 				while (!(Endpoint_IsINReady()));
@@ -301,7 +282,7 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 			
 			break;
 		case REQ_GetIdle:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{		
 				Endpoint_ClearSETUP();
 				
diff --git a/Demos/Device/KeyboardMouse/KeyboardMouse.c b/Demos/Device/KeyboardMouse/KeyboardMouse.c
index 9cae69a5e424ce6a703f8306269ee2763923950b..a85a3786dfc1139e2aa7ecffbbf2671402da024d 100644
--- a/Demos/Device/KeyboardMouse/KeyboardMouse.c
+++ b/Demos/Device/KeyboardMouse/KeyboardMouse.c
@@ -139,17 +139,13 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 	uint8_t  ReportSize;
 
 	/* Handle HID Class specific requests */
-	switch (bRequest)
+	switch (USB_ControlRequest.bRequest)
 	{
 		case REQ_GetReport:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
-				Endpoint_Discard_Word();
-			
-				uint16_t wIndex = Endpoint_Read_Word_LE();
-				
 				/* Determine if it is the mouse or the keyboard data that is being requested */
-				if (!(wIndex))
+				if (!(USB_ControlRequest.wIndex))
 				{
 					ReportData = (uint8_t*)&KeyboardReportData;
 					ReportSize = sizeof(KeyboardReportData);
@@ -160,17 +156,10 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 					ReportSize = sizeof(MouseReportData);
 				}
 
-				/* Read in the number of bytes in the report to send to the host */
-				uint16_t wLength = Endpoint_Read_Word_LE();
-				
-				/* If trying to send more bytes than exist to the host, clamp the value at the report size */
-				if (wLength > ReportSize)
-				  wLength = ReportSize;
-
 				Endpoint_ClearSETUP();
 	
 				/* Write the report data to the control endpoint */
-				Endpoint_Write_Control_Stream_LE(ReportData, wLength);
+				Endpoint_Write_Control_Stream_LE(ReportData, ReportSize);
 
 				/* Clear the report data afterwards */
 				memset(ReportData, 0, ReportSize);
@@ -181,7 +170,7 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 		
 			break;
 		case REQ_SetReport:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				Endpoint_ClearSETUP();
 				
diff --git a/Demos/Device/MassStorage/MassStorage.c b/Demos/Device/MassStorage/MassStorage.c
index 8c7db9322040354996cb1d728af3f848d3bb2178..e2c2424996693b96e7dcba5a5e2d0cc10679ce97 100644
--- a/Demos/Device/MassStorage/MassStorage.c
+++ b/Demos/Device/MassStorage/MassStorage.c
@@ -148,10 +148,10 @@ EVENT_HANDLER(USB_ConfigurationChanged)
 EVENT_HANDLER(USB_UnhandledControlPacket)
 {
 	/* Process UFI specific control requests */
-	switch (bRequest)
+	switch (USB_ControlRequest.bRequest)
 	{
 		case REQ_MassStorageReset:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				Endpoint_ClearSETUP();
 
@@ -165,7 +165,7 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 
 			break;
 		case REQ_GetMaxLUN:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				Endpoint_ClearSETUP();
 
diff --git a/Demos/Device/Mouse/Mouse.c b/Demos/Device/Mouse/Mouse.c
index 0959a4a12ee6ebc784535111c4adfc65c83b0047..2e5f05b42997a180ff6bf170f3872d0cbe2f0847 100644
--- a/Demos/Device/Mouse/Mouse.c
+++ b/Demos/Device/Mouse/Mouse.c
@@ -183,33 +183,20 @@ EVENT_HANDLER(USB_ConfigurationChanged)
 EVENT_HANDLER(USB_UnhandledControlPacket)
 {
 	/* Handle HID Class specific requests */
-	switch (bRequest)
+	switch (USB_ControlRequest.bRequest)
 	{
 		case REQ_GetReport:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				USB_MouseReport_Data_t MouseReportData;
 
 				/* Create the next mouse report for transmission to the host */
 				CreateMouseReport(&MouseReportData);
 
-				/* Ignore report type and ID number value */
-				Endpoint_Discard_Word();
-				
-				/* Ignore unused Interface number value */
-				Endpoint_Discard_Word();
-
-				/* Read in the number of bytes in the report to send to the host */
-				uint16_t wLength = Endpoint_Read_Word_LE();
-				
-				/* If trying to send more bytes than exist to the host, clamp the value at the report size */
-				if (wLength > sizeof(MouseReportData))
-				  wLength = sizeof(MouseReportData);
-
 				Endpoint_ClearSETUP();
 	
 				/* Write the report data to the control endpoint */
-				Endpoint_Write_Control_Stream_LE(&MouseReportData, wLength);
+				Endpoint_Write_Control_Stream_LE(&MouseReportData, sizeof(MouseReportData));
 				
 				/* Clear the report data afterwards */
 				memset(&MouseReportData, 0, sizeof(MouseReportData));
@@ -220,7 +207,7 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 		
 			break;
 		case REQ_GetProtocol:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				Endpoint_ClearSETUP();
 				
@@ -237,15 +224,12 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 			
 			break;
 		case REQ_SetProtocol:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
-				/* Read in the wValue parameter containing the new protocol mode */
-				uint16_t wValue = Endpoint_Read_Word_LE();
-				
 				Endpoint_ClearSETUP();
 				
 				/* Set or clear the flag depending on what the host indicates that the current Protocol should be */
-				UsingReportProtocol = (wValue != 0x0000);
+				UsingReportProtocol = (USB_ControlRequest.wValue != 0x0000);
 				
 				/* Acknowledge status stage */
 				while (!(Endpoint_IsINReady()));
@@ -254,15 +238,12 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 			
 			break;
 		case REQ_SetIdle:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
-				/* Read in the wValue parameter containing the idle period */
-				uint16_t wValue = Endpoint_Read_Word_LE();
-				
 				Endpoint_ClearSETUP();
 				
 				/* Get idle period in MSB */
-				IdleCount = (wValue >> 8);
+				IdleCount = (USB_ControlRequest.wValue >> 8);
 				
 				/* Acknowledge status stage */
 				while (!(Endpoint_IsINReady()));
@@ -271,7 +252,7 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 			
 			break;
 		case REQ_GetIdle:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{		
 				Endpoint_ClearSETUP();
 				
diff --git a/Demos/Device/RNDISEthernet/RNDISEthernet.c b/Demos/Device/RNDISEthernet/RNDISEthernet.c
index ec8eb7b8770736beca19b8152265a47f369b1223..7b81ad85f0338cf2c10d21a96d3339dbd4d7273a 100644
--- a/Demos/Device/RNDISEthernet/RNDISEthernet.c
+++ b/Demos/Device/RNDISEthernet/RNDISEthernet.c
@@ -150,10 +150,10 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 	uint16_t wLength = Endpoint_Read_Word_LE();
 
 	/* Process RNDIS class commands */
-	switch (bRequest)
+	switch (USB_ControlRequest.bRequest)
 	{
 		case REQ_SendEncapsulatedCommand:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				/* Clear the SETUP packet, ready for data transfer */
 				Endpoint_ClearSETUP();
@@ -170,7 +170,7 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 			
 			break;
 		case REQ_GetEncapsulatedResponse:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				/* Check if a response to the last message is ready */
 				if (!(MessageHeader->MessageLength))
@@ -180,15 +180,11 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 					MessageHeader->MessageLength = 1;
 				}
 
-				/* Check if less than the requested number of bytes to transfer */
-				if (MessageHeader->MessageLength < wLength)
-				  wLength = MessageHeader->MessageLength;
-
 				/* Clear the SETUP packet, ready for data transfer */
 				Endpoint_ClearSETUP();
 				
 				/* Write the message response data to the endpoint */
-				Endpoint_Write_Control_Stream_LE(RNDISMessageBuffer, wLength);
+				Endpoint_Write_Control_Stream_LE(RNDISMessageBuffer, MessageHeader->MessageLength);
 				
 				/* Finalize the stream transfer to send the last packet or clear the host abort */
 				Endpoint_ClearOUT();
diff --git a/Demos/Device/USBtoSerial/USBtoSerial.c b/Demos/Device/USBtoSerial/USBtoSerial.c
index e1c22fc13a2fa8ef63617ba75fede2ab86c522ef..dbf4b1b0d656443279b9d5b29814f644b538fe1f 100644
--- a/Demos/Device/USBtoSerial/USBtoSerial.c
+++ b/Demos/Device/USBtoSerial/USBtoSerial.c
@@ -153,10 +153,10 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 	uint8_t* LineCodingData = (uint8_t*)&LineCoding;
 
 	/* Process CDC specific control requests */
-	switch (bRequest)
+	switch (USB_ControlRequest.bRequest)
 	{
 		case REQ_GetLineEncoding:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{	
 				/* Acknowledge the SETUP packet, ready for data transfer */
 				Endpoint_ClearSETUP();
@@ -170,7 +170,7 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 			
 			break;
 		case REQ_SetLineEncoding:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				/* Acknowledge the SETUP packet, ready for data transfer */
 				Endpoint_ClearSETUP();
@@ -187,18 +187,12 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 	
 			break;
 		case REQ_SetControlLineState:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
-#if 0
 				/* NOTE: Here you can read in the line state mask from the host, to get the current state of the output handshake
-				         lines. The mask is read in from the wValue parameter, and can be masked against the CONTROL_LINE_OUT_* masks
-				         to determine the RTS and DTR line states using the following code:
+				         lines. The mask is read in from the wValue parameter in USB_ControlRequest, and can be masked against the
+						 CONTROL_LINE_OUT_* masks to determine the RTS and DTR line states using the following code:
 				*/
-
-				uint16_t wIndex = Endpoint_Read_Word_LE();
-					
-				// Do something with the given line states in wIndex
-#endif
 				
 				/* Acknowledge the SETUP packet, ready for data transfer */
 				Endpoint_ClearSETUP();
diff --git a/Demos/Host/CDCHost/CDCHost.c b/Demos/Host/CDCHost/CDCHost.c
index aa999645a53168e8e06e84784c7a1b7c512cd172..b499a275e3d139c4e191ec00930855de71f4cd18 100644
--- a/Demos/Host/CDCHost/CDCHost.c
+++ b/Demos/Host/CDCHost/CDCHost.c
@@ -181,7 +181,7 @@ TASK(USB_CDC_Host)
 	{
 		case HOST_STATE_Addressed:
 			/* Standard request to set the device configuration to configuration 1 */
-			USB_HostRequest = (USB_Host_Request_Header_t)
+			USB_ControlRequest = (USB_Request_Header_t)
 				{
 					.bmRequestType = (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_DEVICE),
 					.bRequest      = REQ_SetConfiguration,
diff --git a/Demos/Host/GenericHIDHost/GenericHIDHost.c b/Demos/Host/GenericHIDHost/GenericHIDHost.c
index f0d196768c9815adc0b9ff4c8bc71e04604dbe4a..9f419ad6d87b32134007eaea26b5ba88936adca2 100644
--- a/Demos/Host/GenericHIDHost/GenericHIDHost.c
+++ b/Demos/Host/GenericHIDHost/GenericHIDHost.c
@@ -257,7 +257,7 @@ void WriteNextReport(uint8_t* ReportOUTData, uint8_t ReportIndex, uint8_t Report
 	else
 	{
 		/* Class specific request to send a HID report to the device */
-		USB_HostRequest = (USB_Host_Request_Header_t)
+		USB_ControlRequest = (USB_Request_Header_t)
 			{
 				.bmRequestType = (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE),
 				.bRequest      = REQ_SetReport,
@@ -286,7 +286,7 @@ TASK(USB_HID_Host)
 	{
 		case HOST_STATE_Addressed:
 			/* Standard request to set the device configuration to configuration 1 */
-			USB_HostRequest = (USB_Host_Request_Header_t)
+			USB_ControlRequest = (USB_Request_Header_t)
 				{
 					.bmRequestType = (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_DEVICE),
 					.bRequest      = REQ_SetConfiguration,
diff --git a/Demos/Host/KeyboardHost/KeyboardHost.c b/Demos/Host/KeyboardHost/KeyboardHost.c
index bc75bd3f3a07f70b8414bbc304272bea549b7655..f17f950bedf33fdb27e24225af53daa3dc708dc7 100644
--- a/Demos/Host/KeyboardHost/KeyboardHost.c
+++ b/Demos/Host/KeyboardHost/KeyboardHost.c
@@ -253,7 +253,7 @@ TASK(USB_Keyboard_Host)
 	{
 		case HOST_STATE_Addressed:
 			/* Standard request to set the device configuration to configuration 1 */
-			USB_HostRequest = (USB_Host_Request_Header_t)
+			USB_ControlRequest = (USB_Request_Header_t)
 				{
 					.bmRequestType = (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_DEVICE),
 					.bRequest      = REQ_SetConfiguration,
@@ -303,7 +303,7 @@ TASK(USB_Keyboard_Host)
 			}
 		
 			/* HID class request to set the keyboard protocol to the Boot Protocol */
-			USB_HostRequest = (USB_Host_Request_Header_t)
+			USB_ControlRequest = (USB_Request_Header_t)
 				{
 					.bmRequestType = (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE),
 					.bRequest      = REQ_SetProtocol,
diff --git a/Demos/Host/KeyboardHostWithParser/HIDReport.c b/Demos/Host/KeyboardHostWithParser/HIDReport.c
index 14b803840cdb1fbd02aa25bc1f6bd33d3eb17af3..6ac1f5a65b35e35a1444200c9ceeaabb8792524b 100644
--- a/Demos/Host/KeyboardHostWithParser/HIDReport.c
+++ b/Demos/Host/KeyboardHostWithParser/HIDReport.c
@@ -47,7 +47,7 @@ uint8_t GetHIDReportData(void)
 	/* Create a buffer big enough to hold the entire returned HID report */
 	uint8_t HIDReportData[HIDReportSize];
 	
-	USB_HostRequest = (USB_Host_Request_Header_t)
+	USB_ControlRequest = (USB_Request_Header_t)
 		{
 			.bmRequestType = (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_INTERFACE),
 			.bRequest      = REQ_GetDescriptor,
diff --git a/Demos/Host/KeyboardHostWithParser/KeyboardHostWithParser.c b/Demos/Host/KeyboardHostWithParser/KeyboardHostWithParser.c
index 76ad5f258383cd0745cf0f7844a5248d2bdf918d..9eb3d108ade8710f073471c728962cf1394d462a 100644
--- a/Demos/Host/KeyboardHostWithParser/KeyboardHostWithParser.c
+++ b/Demos/Host/KeyboardHostWithParser/KeyboardHostWithParser.c
@@ -184,7 +184,7 @@ TASK(USB_Keyboard_Host)
 	{
 		case HOST_STATE_Addressed:
 			/* Standard request to set the device configuration to configuration 1 */
-			USB_HostRequest = (USB_Host_Request_Header_t)
+			USB_ControlRequest = (USB_Request_Header_t)
 				{
 					.bmRequestType = (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_DEVICE),
 					.bRequest      = REQ_SetConfiguration,
diff --git a/Demos/Host/MassStorageHost/MassStorageHost.c b/Demos/Host/MassStorageHost/MassStorageHost.c
index 9352562de5700824517da6d444028b9c19636a02..c55a167cc2e29e09b658e6572001983148526827 100644
--- a/Demos/Host/MassStorageHost/MassStorageHost.c
+++ b/Demos/Host/MassStorageHost/MassStorageHost.c
@@ -155,7 +155,7 @@ TASK(USB_MassStore_Host)
 	{
 		case HOST_STATE_Addressed:
 			/* Standard request to set the device configuration to configuration 1 */
-			USB_HostRequest = (USB_Host_Request_Header_t)
+			USB_ControlRequest = (USB_Request_Header_t)
 				{
 					.bmRequestType = (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_DEVICE),
 					.bRequest      = REQ_SetConfiguration,
diff --git a/Demos/Host/MassStorageHost/MassStoreCommands.c b/Demos/Host/MassStorageHost/MassStoreCommands.c
index 864edf30c4f32569e6e2cabc90b3b7780a298494..d4df205b1d0dcd2aa76c042b71f939871bac394e 100644
--- a/Demos/Host/MassStorageHost/MassStoreCommands.c
+++ b/Demos/Host/MassStorageHost/MassStoreCommands.c
@@ -250,7 +250,7 @@ static uint8_t MassStore_GetReturnedStatus(void)
  */
 uint8_t MassStore_ClearPipeStall(const uint8_t EndpointNum)
 {
-	USB_HostRequest = (USB_Host_Request_Header_t)
+	USB_ControlRequest = (USB_Request_Header_t)
 		{
 			.bmRequestType = (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_ENDPOINT),
 			.bRequest      = REQ_ClearFeature,
@@ -272,7 +272,7 @@ uint8_t MassStore_ClearPipeStall(const uint8_t EndpointNum)
  */
 uint8_t MassStore_MassStorageReset(void)
 {
-	USB_HostRequest = (USB_Host_Request_Header_t)
+	USB_ControlRequest = (USB_Request_Header_t)
 		{
 			.bmRequestType = (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE),
 			.bRequest      = REQ_MassStorageReset,
@@ -298,7 +298,7 @@ uint8_t MassStore_GetMaxLUN(uint8_t* const MaxLUNIndex)
 {
 	uint8_t ErrorCode;
 
-	USB_HostRequest = (USB_Host_Request_Header_t)
+	USB_ControlRequest = (USB_Request_Header_t)
 		{
 			.bmRequestType = (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE),
 			.bRequest      = REQ_GetMaxLUN,
diff --git a/Demos/Host/MouseHost/MouseHost.c b/Demos/Host/MouseHost/MouseHost.c
index a11ecc86bd9c1a1f28063078cf2b47386e7a41ae..3c858a890830696feb9de06a50974c2cbe36cfc2 100644
--- a/Demos/Host/MouseHost/MouseHost.c
+++ b/Demos/Host/MouseHost/MouseHost.c
@@ -248,7 +248,7 @@ TASK(USB_Mouse_Host)
 	{
 		case HOST_STATE_Addressed:
 			/* Standard request to set the device configuration to configuration 1 */
-			USB_HostRequest = (USB_Host_Request_Header_t)
+			USB_ControlRequest = (USB_Request_Header_t)
 				{
 					.bmRequestType = (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_DEVICE),
 					.bRequest      = REQ_SetConfiguration,
@@ -298,7 +298,7 @@ TASK(USB_Mouse_Host)
 			}
 		
 			/* HID class request to set the mouse protocol to the Boot Protocol */
-			USB_HostRequest = (USB_Host_Request_Header_t)
+			USB_ControlRequest = (USB_Request_Header_t)
 				{
 					.bmRequestType = (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE),
 					.bRequest      = REQ_SetProtocol,
diff --git a/Demos/Host/MouseHostWithParser/HIDReport.c b/Demos/Host/MouseHostWithParser/HIDReport.c
index 68d6580f4442493cb436856b673c710f8fb93387..4d895908e707974938567ba4e5f27acf207213b0 100644
--- a/Demos/Host/MouseHostWithParser/HIDReport.c
+++ b/Demos/Host/MouseHostWithParser/HIDReport.c
@@ -47,7 +47,7 @@ uint8_t GetHIDReportData(void)
 	/* Create a buffer big enough to hold the entire returned HID report */
 	uint8_t HIDReportData[HIDReportSize];
 	
-	USB_HostRequest = (USB_Host_Request_Header_t)
+	USB_ControlRequest = (USB_Request_Header_t)
 		{
 			.bmRequestType = (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_INTERFACE),
 			.bRequest      = REQ_GetDescriptor,
diff --git a/Demos/Host/MouseHostWithParser/MouseHostWithParser.c b/Demos/Host/MouseHostWithParser/MouseHostWithParser.c
index df063dab32df7138ca85d5c11c38d24a61a08636..58a189f6b14d0e6d221ab8e119a2727665a1c7f3 100644
--- a/Demos/Host/MouseHostWithParser/MouseHostWithParser.c
+++ b/Demos/Host/MouseHostWithParser/MouseHostWithParser.c
@@ -185,7 +185,7 @@ TASK(USB_Mouse_Host)
 	{
 		case HOST_STATE_Addressed:	
 			/* Standard request to set the device configuration to configuration 1 */
-			USB_HostRequest = (USB_Host_Request_Header_t)
+			USB_ControlRequest = (USB_Request_Header_t)
 				{
 					.bmRequestType = (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_DEVICE),
 					.bRequest      = REQ_SetConfiguration,
diff --git a/Demos/Host/StillImageHost/StillImageCommands.c b/Demos/Host/StillImageHost/StillImageCommands.c
index 233e5b116f6e986ba3327c7fffa646de941ecb52..49ab0df01c652599ef02bad2f3187b1f47335eef 100644
--- a/Demos/Host/StillImageHost/StillImageCommands.c
+++ b/Demos/Host/StillImageHost/StillImageCommands.c
@@ -263,7 +263,7 @@ bool SImage_IsEventReceived(void)
  */
 uint8_t SImage_ClearPipeStall(const uint8_t EndpointNum)
 {
-	USB_HostRequest = (USB_Host_Request_Header_t)
+	USB_ControlRequest = (USB_Request_Header_t)
 		{
 			.bmRequestType = (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_ENDPOINT),
 			.bRequest      = REQ_ClearFeature,
diff --git a/Demos/Host/StillImageHost/StillImageHost.c b/Demos/Host/StillImageHost/StillImageHost.c
index 4b196c3edf30abe2d59fcb2e6f4e99f7195e0b0c..ca5292ba2101abd59accc6c2fd2c0cf3470ccf10 100644
--- a/Demos/Host/StillImageHost/StillImageHost.c
+++ b/Demos/Host/StillImageHost/StillImageHost.c
@@ -151,7 +151,7 @@ TASK(USB_SImage_Host)
 	{
 		case HOST_STATE_Addressed:
 			/* Standard request to set the device configuration to configuration 1 */
-			USB_HostRequest = (USB_Host_Request_Header_t)
+			USB_ControlRequest = (USB_Request_Header_t)
 				{
 					.bmRequestType = (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_DEVICE),
 					.bRequest      = REQ_SetConfiguration,
diff --git a/Demos/OTG/TestApp/TestEvents.c b/Demos/OTG/TestApp/TestEvents.c
index 8f05b820866a4438564fb81a49666623bdaa7ac7..17514774fe5308a487ffdb3f1624cd46f4be8510 100644
--- a/Demos/OTG/TestApp/TestEvents.c
+++ b/Demos/OTG/TestApp/TestEvents.c
@@ -193,8 +193,9 @@ EVENT_HANDLER(USB_DeviceError)
 EVENT_HANDLER(USB_UnhandledControlPacket)
 {
 	puts_P(PSTR(EVENT_PREFIX "Ctrl Request\r\n"));
-	printf_P(PSTR(" -- Req Data %d\r\n"), bRequest);
-	printf_P(PSTR(" -- Req Type %d\r\n"), bmRequestType);
+	printf_P(PSTR(" -- Req Data %d\r\n"), USB_ControlRequest.bRequest);
+	printf_P(PSTR(" -- Req Type %d\r\n"), USB_ControlRequest.bmRequestType);
+	printf_P(PSTR(" -- Req Length %d\r\n"), USB_ControlRequest.wLength);
 }
 
 /** Event handler for the USB_ConfigurationChanged event. When fired, the event is logged to the USART. */
diff --git a/LUFA/ChangeLog.txt b/LUFA/ChangeLog.txt
index f0c33e01af7604805fc1c8808fb5dca222a0aadd..3825cd3435b92abffeb4ad012bf568975f94dcca 100644
--- a/LUFA/ChangeLog.txt
+++ b/LUFA/ChangeLog.txt
@@ -55,6 +55,10 @@
   *  - Capitalised the "Descriptor_Search" and "Descriptor_Search_Comp" prefixes of the values in the DSearch_Return_ErrorCodes_t and
   *    DSearch_Comp_Return_ErrorCodes_t enums
   *  - Changed over all deprecated GCC structure tag initializers to the standardized C99 format (thanks to Mike Alexander)
+  *  - USB_HostRequest renamed to USB_ControlRequest, entire control request header is now read into USB_ControlRequest in Device mode
+  *    rather than having the library pass only partially read header data to the application
+  *  - The USB_UnhandledControlPacket event has had its parameters removed, in favour of accessing the new USB_ControlRequest structure
+  *  - The Endpoint control stream functions now correctly send a ZLP to the host when less data than requested is sent
   *    
   *
   *  \section Sec_ChangeLog090401 Version 090401
diff --git a/LUFA/Drivers/USB/Class/ConfigDescriptor.c b/LUFA/Drivers/USB/Class/ConfigDescriptor.c
index dd782c81d2d454675dd75d5bb09e8a82fe9a741d..367b28ae3f3d29f4188cbbcb071c41bb5e169bf2 100644
--- a/LUFA/Drivers/USB/Class/ConfigDescriptor.c
+++ b/LUFA/Drivers/USB/Class/ConfigDescriptor.c
@@ -35,7 +35,7 @@ uint8_t USB_GetDeviceConfigDescriptor(uint16_t* const ConfigSizePtr, void* Buffe
 {
 	uint8_t ErrorCode;
 
-	USB_HostRequest = (USB_Host_Request_Header_t)
+	USB_ControlRequest = (USB_Request_Header_t)
 		{
 			.bmRequestType = (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_DEVICE),
 			.bRequest      = REQ_GetDescriptor,
@@ -60,7 +60,7 @@ uint8_t USB_GetDeviceConfigDescriptor(uint16_t* const ConfigSizePtr, void* Buffe
 	}
 	else
 	{
-		USB_HostRequest.wLength = *ConfigSizePtr;
+		USB_ControlRequest.wLength = *ConfigSizePtr;
 		
 		ErrorCode      = USB_Host_SendControlRequest(BufferPtr);				
 	}
diff --git a/LUFA/Drivers/USB/HighLevel/Events.h b/LUFA/Drivers/USB/HighLevel/Events.h
index 9638afee3a4b187ccf492ee20739a181236f0bd1..73a804c35d5a5990f31846e14f9760c2fd0f7a93 100644
--- a/LUFA/Drivers/USB/HighLevel/Events.h
+++ b/LUFA/Drivers/USB/HighLevel/Events.h
@@ -305,7 +305,7 @@
 			 *        parameters (wValue, wIndex, wLength, and Data) remain in the control endpoint bank until
 			 *        read out by the user application for processing.
 			 */
-			void USB_UnhandledControlPacket(const uint8_t bRequest, const uint8_t bmRequestType);
+			void USB_UnhandledControlPacket(void);
 
 			/** Event for USB configuration number changed. This event fires when a the USB host changes the
 			 *  selected configuration number while in device mode. This event should be hooked in device
@@ -392,7 +392,7 @@
 			#endif
 			
 			#if defined(USB_CAN_BE_DEVICE)
-				#define USB_UnhandledControlPacket_P    (const uint8_t bRequest, const uint8_t bmRequestType)
+				#define USB_UnhandledControlPacket_P    (void)
 				#define USB_ConfigurationChanged_P      (void)
 				#define USB_Suspend_P                   (void)
 				#define USB_WakeUp_P                    (void)
diff --git a/LUFA/Drivers/USB/HighLevel/StdRequestType.h b/LUFA/Drivers/USB/HighLevel/StdRequestType.h
index 27c179497fce4b28456ae0b0feb9b769ef91e267..6f214893bc1860cfc14c662c5922c368d4c1ecc6 100644
--- a/LUFA/Drivers/USB/HighLevel/StdRequestType.h
+++ b/LUFA/Drivers/USB/HighLevel/StdRequestType.h
@@ -135,6 +135,20 @@
 			 */
 			#define FEATURE_REMOTE_WAKEUP           0x01
 
+		/* Type Defines: */
+			/** Type define for a standard USB control request.
+			 *
+			 *  \see The USB 2.0 specification for more information on standard control requests.
+			 */
+			typedef struct
+			{
+				uint8_t  bmRequestType; /**< Type of the request. */
+				uint8_t  bRequest; /**< Request command code. */
+				uint16_t wValue; /**< wValue parameter of the request. */
+				uint16_t wIndex; /**< wIndex parameter of the request. */
+				uint16_t wLength; /**< Length of the data to transfer in bytes. */
+			} USB_Request_Header_t;
+
 		/* Enums: */
 			/** Enumeration for the various standard request commands. These commands are applicable when the
 			 *  request type is REQTYPE_STANDARD (with the exception of REQ_GetDescriptor, which is always
diff --git a/LUFA/Drivers/USB/HighLevel/USBTask.c b/LUFA/Drivers/USB/HighLevel/USBTask.c
index e1c065905caad673bdb8777b7316b718638382f3..aa04c56baa65c19cb06a51da863a16970c5caa1e 100644
--- a/LUFA/Drivers/USB/HighLevel/USBTask.c
+++ b/LUFA/Drivers/USB/HighLevel/USBTask.c
@@ -33,9 +33,10 @@
 #define  INCLUDE_FROM_USBTASK_C
 #include "USBTask.h"
 
-volatile bool      USB_IsSuspended;
-volatile bool      USB_IsConnected;
-volatile bool      USB_IsInitialized;
+volatile bool        USB_IsSuspended;
+volatile bool        USB_IsConnected;
+volatile bool        USB_IsInitialized;
+USB_Request_Header_t USB_ControlRequest;
 
 #if defined(USB_CAN_BE_HOST)
 volatile uint8_t   USB_HostState;
@@ -169,7 +170,7 @@ static void USB_HostTask(void)
 			USB_HostState = HOST_STATE_Default;
 			break;
 		case HOST_STATE_Default:
-			USB_HostRequest = (USB_Host_Request_Header_t)
+			USB_ControlRequest = (USB_Request_Header_t)
 				{
 					.bmRequestType = (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_DEVICE),
 					.bRequest      = REQ_GetDescriptor,
@@ -214,7 +215,7 @@ static void USB_HostTask(void)
 
 			Pipe_SetInfiniteINRequests();
 			
-			USB_HostRequest = (USB_Host_Request_Header_t)
+			USB_ControlRequest = (USB_Request_Header_t)
 				{
 					.bmRequestType = (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_DEVICE),
 					.bRequest      = REQ_SetAddress,
diff --git a/LUFA/Drivers/USB/HighLevel/USBTask.h b/LUFA/Drivers/USB/HighLevel/USBTask.h
index 833fd9ec78b7f5394163d0860b7542db28952dd1..7e88ce88b33333266b99ca5a8a3afb1aae8a7639 100644
--- a/LUFA/Drivers/USB/HighLevel/USBTask.h
+++ b/LUFA/Drivers/USB/HighLevel/USBTask.h
@@ -40,6 +40,7 @@
 		
 		#include "../../../Scheduler/Scheduler.h"
 		#include "../LowLevel/LowLevel.h"
+		#include "StdRequestType.h"
 		#include "USBMode.h"
 		#include "Events.h"
 		#include "StdDescriptors.h"
@@ -82,6 +83,14 @@
 			 */
 			extern volatile bool USB_IsInitialized;
 
+			/** Structure containing the last received Control request when in Device mode (for use in user-applications
+			 *  inside of the USB_UnhandledControlPacket() event, or for filling up with a control request to issue when
+			 *  in Host mode before calling USB_Host_SendControlRequest().
+			 *
+			 *  \ingroup Group_USBManagement
+			 */
+			 extern USB_Request_Header_t USB_ControlRequest;
+			
 			#if defined(USB_CAN_BE_DEVICE) || defined(__DOXYGEN__)
 			/** Indicates if the USB interface is currently suspended by the host when in device mode. When suspended,
 			 *  the device should consume minimal power, and cannot communicate to the host. If Remote Wakeup is
diff --git a/LUFA/Drivers/USB/LowLevel/DevChapter9.c b/LUFA/Drivers/USB/LowLevel/DevChapter9.c
index 3f2805c5a70c7b39f2ca12904d71a27366fc4748..bf2b1276110ddeabbace61b8c3f0fdf517ea4e12 100644
--- a/LUFA/Drivers/USB/LowLevel/DevChapter9.c
+++ b/LUFA/Drivers/USB/LowLevel/DevChapter9.c
@@ -41,17 +41,19 @@ bool    USB_CurrentlySelfPowered;
 
 void USB_Device_ProcessControlPacket(void)
 {
-	uint8_t bmRequestType  = Endpoint_Read_Byte();
-	uint8_t bRequest       = Endpoint_Read_Byte();
-	bool    RequestHandled = false;	
+	bool     RequestHandled = false;
+	uint8_t* RequestHeader  = (uint8_t*)&USB_ControlRequest;
 	
-	switch (bRequest)
+	for (uint8_t RequestHeaderByte = 0; RequestHeaderByte < sizeof(USB_Request_Header_t); RequestHeaderByte++)
+	  *(RequestHeader++) = Endpoint_Read_Byte();
+	
+	switch (USB_ControlRequest.bRequest)
 	{
 		case REQ_GetStatus:
-			if ((bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_DEVICE)) ||
-			    (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_ENDPOINT)))
+			if ((USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_DEVICE)) ||
+			    (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_ENDPOINT)))
 			{
-				USB_Device_GetStatus(bmRequestType);
+				USB_Device_GetStatus();
 				RequestHandled = true;
 			}
 
@@ -59,16 +61,16 @@ void USB_Device_ProcessControlPacket(void)
 #if !defined(FEATURELESS_CONTROL_ONLY_DEVICE)
 		case REQ_ClearFeature:
 		case REQ_SetFeature:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_ENDPOINT))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_ENDPOINT))
 			{
-				USB_Device_ClearSetFeature(bRequest, bmRequestType);
+				USB_Device_ClearSetFeature();
 				RequestHandled = true;
 			}
 
 			break;
 #endif
 		case REQ_SetAddress:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_DEVICE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_DEVICE))
 			{
 				USB_Device_SetAddress();
 				RequestHandled = true;
@@ -76,8 +78,8 @@ void USB_Device_ProcessControlPacket(void)
 
 			break;
 		case REQ_GetDescriptor:
-			if ((bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_DEVICE)) ||
-			    (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_INTERFACE)))
+			if ((USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_DEVICE)) ||
+			    (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_INTERFACE)))
 			{
 				USB_Device_GetDescriptor();
 				RequestHandled = true;
@@ -85,7 +87,7 @@ void USB_Device_ProcessControlPacket(void)
 			
 			break;
 		case REQ_GetConfiguration:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_DEVICE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_DEVICE))
 			{
 				USB_Device_GetConfiguration();
 				RequestHandled = true;
@@ -93,7 +95,7 @@ void USB_Device_ProcessControlPacket(void)
 
 			break;
 		case REQ_SetConfiguration:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_DEVICE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_DEVICE))
 			{
 				USB_Device_SetConfiguration();
 				RequestHandled = true;
@@ -103,7 +105,7 @@ void USB_Device_ProcessControlPacket(void)
 	}
 
 	if (!(RequestHandled))
-	  RAISE_EVENT(USB_UnhandledControlPacket, bRequest, bmRequestType);
+	  RAISE_EVENT(USB_UnhandledControlPacket);
 	  
 	if (Endpoint_IsSETUPReceived())
 	{
@@ -114,8 +116,6 @@ void USB_Device_ProcessControlPacket(void)
 
 static void USB_Device_SetAddress(void)
 {
-	uint8_t wValue_LSB = Endpoint_Read_Byte();
-
 	Endpoint_ClearSETUP();
 	
 	while (!(Endpoint_IsINReady()));
@@ -124,28 +124,27 @@ static void USB_Device_SetAddress(void)
 	
 	while (!(Endpoint_IsINReady()));
 
-	UDADDR = ((1 << ADDEN) | (wValue_LSB & 0x7F));
+	UDADDR = ((1 << ADDEN) | (USB_ControlRequest.wValue & 0x7F));
 
 	return;
 }
 
 static void USB_Device_SetConfiguration(void)
 {
-	uint8_t wValue_LSB        = Endpoint_Read_Byte();
 	bool    AlreadyConfigured = (USB_ConfigurationNumber != 0);
 
 #if defined(USE_SINGLE_DEVICE_CONFIGURATION)
-	if (wValue_LSB > 1)
+	if (USB_ControlRequest.wValue > 1)
 #else
 	USB_Descriptor_Device_t* DevDescriptorPtr;
 
 	if ((USB_GetDescriptor((DTYPE_Device << 8), 0, (void*)&DevDescriptorPtr) == NO_DESCRIPTOR) ||
 	#if defined(USE_RAM_DESCRIPTORS)
-	    (wValue_LSB > DevDescriptorPtr->NumberOfConfigurations))
+	    (USB_ControlRequest.wValue > DevDescriptorPtr->NumberOfConfigurations))
 	#elif defined (USE_EEPROM_DESCRIPTORS)
-	    (wValue_LSB > eeprom_read_byte(&DevDescriptorPtr->NumberOfConfigurations)))
+	    (USB_ControlRequest.wValue > eeprom_read_byte(&DevDescriptorPtr->NumberOfConfigurations)))
 	#else
-	    (wValue_LSB > pgm_read_byte(&DevDescriptorPtr->NumberOfConfigurations)))
+	    (USB_ControlRequest.wValue > pgm_read_byte(&DevDescriptorPtr->NumberOfConfigurations)))
 	#endif
 #endif
 	{
@@ -154,7 +153,7 @@ static void USB_Device_SetConfiguration(void)
 	
 	Endpoint_ClearSETUP();
 
-	USB_ConfigurationNumber = wValue_LSB;
+	USB_ConfigurationNumber = USB_ControlRequest.wValue;
 
 	Endpoint_ClearIN();
 
@@ -178,24 +177,23 @@ void USB_Device_GetConfiguration(void)
 
 static void USB_Device_GetDescriptor(void)
 {
-	uint16_t wValue  = Endpoint_Read_Word_LE();
-	uint16_t wIndex  = Endpoint_Read_Word_LE();
-	uint16_t wLength = Endpoint_Read_Word_LE();
-	
 	void*    DescriptorPointer;
 	uint16_t DescriptorSize;
 	
-	bool     SendZLP;
-	
-	if ((DescriptorSize = USB_GetDescriptor(wValue, wIndex, &DescriptorPointer)) == NO_DESCRIPTOR)
+	if ((DescriptorSize = USB_GetDescriptor(USB_ControlRequest.wValue, USB_ControlRequest.wIndex, &DescriptorPointer)) == NO_DESCRIPTOR)
 	  return;
 	
-	Endpoint_ClearSETUP();	
+	Endpoint_ClearSETUP();
+	
+	#if defined(USE_RAM_DESCRIPTORS)
+	Endpoint_Write_Control_Stream_LE(DescriptorPointer, DescriptorSize);
+	#else
+	bool     SendZLP;
 	
-	if (wLength > DescriptorSize)
-	  wLength = DescriptorSize;
+	if (USB_ControlRequest.wLength > DescriptorSize)
+	  USB_ControlRequest.wLength = DescriptorSize;
 	
-	while (wLength)
+	while (USB_ControlRequest.wLength)
 	{
 		while (!(Endpoint_IsINReady()))
 		{
@@ -206,17 +204,15 @@ static void USB_Device_GetDescriptor(void)
 			}		
 		}
 		
-		while (wLength && (Endpoint_BytesInEndpoint() < USB_ControlEndpointSize))
+		while (USB_ControlRequest.wLength && (Endpoint_BytesInEndpoint() < USB_ControlEndpointSize))
 		{
-			#if defined(USE_RAM_DESCRIPTORS)
-			Endpoint_Write_Byte(*((uint8_t*)DescriptorPointer++));
-			#elif defined (USE_EEPROM_DESCRIPTORS)
+			#if defined (USE_EEPROM_DESCRIPTORS)
 			Endpoint_Write_Byte(eeprom_read_byte(DescriptorPointer++));			
 			#else
 			Endpoint_Write_Byte(pgm_read_byte(DescriptorPointer++));
 			#endif
 			
-			wLength--;
+			USB_ControlRequest.wLength--;
 		}
 		
 		SendZLP = (Endpoint_BytesInEndpoint() == USB_ControlEndpointSize);
@@ -230,20 +226,16 @@ static void USB_Device_GetDescriptor(void)
 	}
 
 	while (!(Endpoint_IsOUTReceived()));
+	#endif
+	
 	Endpoint_ClearOUT();
 }
 
-static void USB_Device_GetStatus(const uint8_t bmRequestType)
+static void USB_Device_GetStatus(void)
 {
 	uint8_t CurrentStatus = 0;
 
-	Endpoint_Discard_Word();
-
-#if !defined(FEATURELESS_CONTROL_ONLY_DEVICE)
-	uint8_t wIndex_LSB = Endpoint_Read_Byte();
-#endif
-	
-	switch (bmRequestType)
+	switch (USB_ControlRequest.bmRequestType)
 	{
 		case (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_DEVICE):
 			if (USB_CurrentlySelfPowered)
@@ -255,15 +247,16 @@ static void USB_Device_GetStatus(const uint8_t bmRequestType)
 			break;
 #if !defined(FEATURELESS_CONTROL_ONLY_DEVICE)
 		case (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_ENDPOINT):
-			Endpoint_SelectEndpoint(wIndex_LSB);
+			Endpoint_SelectEndpoint(USB_ControlRequest.wIndex);
 
 			CurrentStatus = Endpoint_IsStalled();
 
+			Endpoint_SelectEndpoint(ENDPOINT_CONTROLEP);			  
+
 			break;
 #endif
 	}
-	
-	Endpoint_SelectEndpoint(ENDPOINT_CONTROLEP);			  
+
 	Endpoint_ClearSETUP();
 
 	Endpoint_Write_Word_LE(CurrentStatus);
@@ -275,17 +268,14 @@ static void USB_Device_GetStatus(const uint8_t bmRequestType)
 }
 
 #if !defined(FEATURELESS_CONTROL_ONLY_DEVICE)
-static void USB_Device_ClearSetFeature(const uint8_t bRequest, const uint8_t bmRequestType)
-{
-	uint16_t wValue = Endpoint_Read_Word_LE();
-	uint16_t wIndex = Endpoint_Read_Word_LE();
-	
-	switch (bmRequestType & CONTROL_REQTYPE_RECIPIENT)
+static void USB_Device_ClearSetFeature(void)
+{	
+	switch (USB_ControlRequest.bmRequestType & CONTROL_REQTYPE_RECIPIENT)
 	{
 		case REQREC_ENDPOINT:
-			if (wValue == FEATURE_ENDPOINT_HALT)
+			if (USB_ControlRequest.wValue == FEATURE_ENDPOINT_HALT)
 			{
-				uint8_t EndpointIndex = (wIndex & ENDPOINT_EPNUM_MASK);
+				uint8_t EndpointIndex = (USB_ControlRequest.wIndex & ENDPOINT_EPNUM_MASK);
 				
 				if (EndpointIndex != ENDPOINT_CONTROLEP)
 				{
@@ -293,7 +283,7 @@ static void USB_Device_ClearSetFeature(const uint8_t bRequest, const uint8_t bmR
 
 					if (Endpoint_IsEnabled())
 					{				
-						if (bRequest == REQ_ClearFeature)
+						if (USB_ControlRequest.bRequest == REQ_ClearFeature)
 						{
 							Endpoint_ClearStall();
 							Endpoint_ResetFIFO(EndpointIndex);
diff --git a/LUFA/Drivers/USB/LowLevel/DevChapter9.h b/LUFA/Drivers/USB/LowLevel/DevChapter9.h
index 23b7b4620103e107f273e28cc3ee32114422185c..10a91937f9e81640af16333298ecfaddef7d497a 100644
--- a/LUFA/Drivers/USB/LowLevel/DevChapter9.h
+++ b/LUFA/Drivers/USB/LowLevel/DevChapter9.h
@@ -39,6 +39,7 @@
 		#include "../HighLevel/StdDescriptors.h"
 		#include "../HighLevel/Events.h"
 		#include "../HighLevel/StdRequestType.h"
+		#include "../HighLevel/USBTask.h"
 		#include "LowLevel.h"
 
 	/* Enable C linkage for C++ Compilers: */
@@ -118,9 +119,9 @@
 				static void USB_Device_SetConfiguration(void);
 				static void USB_Device_GetConfiguration(void);
 				static void USB_Device_GetDescriptor(void);
-				static void USB_Device_GetStatus(const uint8_t bmRequestType);
+				static void USB_Device_GetStatus(void);
 				#if !defined(FEATURELESS_CONTROL_ONLY_DEVICE)
-				static void USB_Device_ClearSetFeature(const uint8_t bRequest, const uint8_t bmRequestType);
+				static void USB_Device_ClearSetFeature(void);
 				#endif
 			#endif
 	#endif
diff --git a/LUFA/Drivers/USB/LowLevel/Endpoint.c b/LUFA/Drivers/USB/LowLevel/Endpoint.c
index e196b6aeec458cb656a6bcfcf523a09f2b9ffe8d..efa1a2db4a0466e7a7217f57961e953885a0fc90 100644
--- a/LUFA/Drivers/USB/LowLevel/Endpoint.c
+++ b/LUFA/Drivers/USB/LowLevel/Endpoint.c
@@ -292,8 +292,9 @@ uint8_t Endpoint_Read_Stream_BE(void* Buffer, uint16_t Length
 
 uint8_t Endpoint_Write_Control_Stream_LE(const void* Buffer, uint16_t Length)
 {
-	uint8_t* DataStream = (uint8_t*)Buffer;
-	bool     SendZLP    = true;
+	uint8_t* DataStream    = (uint8_t*)Buffer;
+	bool     LastPacketFull = false;
+	bool     ShortTransfer = (Length < USB_ControlRequest.wLength);
 	
 	while (Length && !(Endpoint_IsOUTReceived()))
 	{
@@ -306,14 +307,14 @@ uint8_t Endpoint_Write_Control_Stream_LE(const void* Buffer, uint16_t Length)
 			Length--;
 		}
 		
-		SendZLP = (Endpoint_BytesInEndpoint() == USB_ControlEndpointSize);
+		LastPacketFull = (Endpoint_BytesInEndpoint() == USB_ControlEndpointSize);
 		Endpoint_ClearIN();
 	}
 	
 	if (Endpoint_IsOUTReceived())
 	  return ENDPOINT_RWCSTREAM_ERROR_HostAborted;
 	
-	if (SendZLP)
+	if (LastPacketFull || ShortTransfer)
 	{
 		while (!(Endpoint_IsINReady()));
 		Endpoint_ClearIN();
@@ -326,8 +327,9 @@ uint8_t Endpoint_Write_Control_Stream_LE(const void* Buffer, uint16_t Length)
 
 uint8_t Endpoint_Write_Control_Stream_BE(const void* Buffer, uint16_t Length)
 {
-	uint8_t* DataStream = (uint8_t*)(Buffer + Length - 1);
-	bool     SendZLP    = true;
+	uint8_t* DataStream     = (uint8_t*)(Buffer + Length - 1);
+	bool     LastPacketFull = false;
+	bool     ShortTransfer  = (Length < USB_ControlRequest.wLength);
 	
 	while (Length && !(Endpoint_IsOUTReceived()))
 	{
@@ -340,14 +342,14 @@ uint8_t Endpoint_Write_Control_Stream_BE(const void* Buffer, uint16_t Length)
 			Length--;
 		}
 		
-		SendZLP = (Endpoint_BytesInEndpoint() == USB_ControlEndpointSize);
+		LastPacketFull = (Endpoint_BytesInEndpoint() == USB_ControlEndpointSize);
 		Endpoint_ClearIN();
 	}
 	
 	if (Endpoint_IsOUTReceived())
 	  return ENDPOINT_RWCSTREAM_ERROR_HostAborted;
 	
-	if (SendZLP)
+	if (LastPacketFull || ShortTransfer)
 	{
 		while (!(Endpoint_IsINReady()));
 		Endpoint_ClearIN();
diff --git a/LUFA/Drivers/USB/LowLevel/HostChapter9.c b/LUFA/Drivers/USB/LowLevel/HostChapter9.c
index dfc3f44836673616b771eac08f2cb232da4beec6..ee51cf3aecb5c29ca6bc9906643ee6f1e713c7d6 100644
--- a/LUFA/Drivers/USB/LowLevel/HostChapter9.c
+++ b/LUFA/Drivers/USB/LowLevel/HostChapter9.c
@@ -35,15 +35,13 @@
 #define  INCLUDE_FROM_HOSTCHAPTER9_C
 #include "HostChapter9.h"
 
-USB_Host_Request_Header_t USB_HostRequest;
-
 uint8_t USB_Host_SendControlRequest(void* BufferPtr)
 {
-	uint8_t* HeaderStream   = (uint8_t*)&USB_HostRequest;
+	uint8_t* HeaderStream   = (uint8_t*)&USB_ControlRequest;
 	uint8_t* DataStream     = (uint8_t*)BufferPtr;
 	bool     BusSuspended   = USB_Host_IsBusSuspended();
 	uint8_t  ReturnStatus   = HOST_SENDCONTROL_Successful;
-	uint16_t DataLen        = USB_HostRequest.wLength;
+	uint16_t DataLen        = USB_ControlRequest.wLength;
 
 	USB_Host_ResumeBus();
 	
@@ -55,7 +53,7 @@ uint8_t USB_Host_SendControlRequest(void* BufferPtr)
 
 	Pipe_Unfreeze();
 
-	for (uint8_t HeaderByte = 0; HeaderByte < sizeof(USB_Host_Request_Header_t); HeaderByte++)
+	for (uint8_t HeaderByte = 0; HeaderByte < sizeof(USB_Request_Header_t); HeaderByte++)
 	  Pipe_Write_Byte(*(HeaderStream++));
 
 	Pipe_ClearSETUP();
@@ -68,7 +66,7 @@ uint8_t USB_Host_SendControlRequest(void* BufferPtr)
 	if ((ReturnStatus = USB_Host_WaitMS(1)) != HOST_WAITERROR_Successful)
 	  goto End_Of_Control_Send;
 
-	if ((USB_HostRequest.bmRequestType & CONTROL_REQTYPE_DIRECTION) == REQDIR_DEVICETOHOST)
+	if ((USB_ControlRequest.bmRequestType & CONTROL_REQTYPE_DIRECTION) == REQDIR_DEVICETOHOST)
 	{
 		Pipe_SetToken(PIPE_TOKEN_IN);
 		
diff --git a/LUFA/Drivers/USB/LowLevel/HostChapter9.h b/LUFA/Drivers/USB/LowLevel/HostChapter9.h
index c2c4ece7a8c0f9ca301929714e52926a20410695..cbb5ba5a8bb271d0efcd97e47c310e0bb7cb9891 100644
--- a/LUFA/Drivers/USB/LowLevel/HostChapter9.h
+++ b/LUFA/Drivers/USB/LowLevel/HostChapter9.h
@@ -45,23 +45,6 @@
 		#endif
 
 	/* Public Interface - May be used in end-application: */
-		/* Type Defines: */
-			/** Type define for a standard USB control request.
-			 *
-			 *  \see StdRequestType.h for information on the request type and data.
-			 *  \see The USB 2.0 specification for more information on standard control requests.
-			 *
-			 *  \ingroup Group_PipeControlReq
-			 */
-			typedef struct
-			{
-				uint8_t  bmRequestType; /**< Type of the request. */
-				uint8_t  bRequest; /**< Request command code. */
-				uint16_t wValue; /**< wValue parameter of the request. */
-				uint16_t wIndex; /**< wIndex parameter of the request. */
-				uint16_t wLength; /**< Length of the data to transfer in bytes. */
-			} USB_Host_Request_Header_t;
-
 		/* Enums: */
 			/** Enum for the USB_Host_SendControlRequest() return code, indicating the reason for the error
 			 *  if the transfer of the request is unsuccessful.
@@ -81,17 +64,8 @@
 				HOST_SENDCONTROL_SoftwareTimeOut  = 4, /**< The request or data transfer timed out. */
 			};
 			
-		/* Global Variables: */
-			/** Global for the request to send via the USB_Host_SendControlRequest() function. This
-			 *  global should be filled with the correct control request data before sending the request to
-			 *  the attached device while in host mode.
-			 *
-			 *  \ingroup Group_PipeControlReq
-			 */
-			extern USB_Host_Request_Header_t USB_HostRequest;
-			
 		/* Function Prototypes: */
-			/** Sends the request stored in the USB_HostRequest global structure to the attached device,
+			/** Sends the request stored in the USB_ControlRequest global structure to the attached device,
 			 *  and transfers the data stored in the buffer to the device, or from the device to the buffer
 			 *  as requested. The transfer is made on the currently selected pipe.
 			 *
diff --git a/LUFA/Drivers/USB/LowLevel/Pipe.c b/LUFA/Drivers/USB/LowLevel/Pipe.c
index 5850fcf7c15d17a6c3320c70963a02c09b1a00a6..ff4318c9950763242925fea9dafcef400794e965 100644
--- a/LUFA/Drivers/USB/LowLevel/Pipe.c
+++ b/LUFA/Drivers/USB/LowLevel/Pipe.c
@@ -37,7 +37,7 @@
 
 uint8_t USB_ControlPipeSize = PIPE_CONTROLPIPE_DEFAULT_SIZE;
 
-bool Pipe_ConfigurePipe(const uint8_t  Number, const uint8_t Type, const uint8_t Token, const uint8_t EndpointNumber,
+bool Pipe_ConfigurePipe(const uint8_t Number, const uint8_t Type, const uint8_t Token, const uint8_t EndpointNumber,
 						const uint16_t Size, const uint8_t Banks)
 {
 	Pipe_SelectPipe(Number);
diff --git a/LUFA/Drivers/USB/LowLevel/Pipe.h b/LUFA/Drivers/USB/LowLevel/Pipe.h
index 3f512c0d235fd7bf71a6e60d92a96d1bd00c091e..25121cafa8dddcb59331709afe68271bf26bb612 100644
--- a/LUFA/Drivers/USB/LowLevel/Pipe.h
+++ b/LUFA/Drivers/USB/LowLevel/Pipe.h
@@ -389,6 +389,8 @@
 				 *  is an IN direction and no packet (or an empty packet) has been received, or if the pipe is an OUT
 				 *  direction and the pipe bank is full.
 				 *
+				 *  \note This function is not valid on CONTROL type pipes.
+				 *
 				 *  \ingroup Group_PipePacketManagement
 				 *  
 				 *  \return Boolean true if the currently selected pipe may be read from or written to, depending on its direction
diff --git a/LUFA/MigrationInformation.txt b/LUFA/MigrationInformation.txt
index 576ba648a47f32727bb03c12fe24ae3cf220a554..efec274df399dab1f8058ac18239ecf1ceca8b85 100644
--- a/LUFA/MigrationInformation.txt
+++ b/LUFA/MigrationInformation.txt
@@ -33,6 +33,9 @@
  *    - The Endpoint_ClearSetupReceived() macro has been renamed to Endpoint_ClearSETUP().
  *    - All endpoint read/write/discard aliases which did not have an explicitly endianness specifier (such as Endpoint_Read_Word()) have
  *      been removed for clarity. Existing projects should use the "_LE" suffix on such calls to use the explicit Little Endian versions.
+ *    - The USB_UnhandledControlPacket event no longer has any parameters. User code should no longer attempt to read in the remainder of
+ *      the Control Request header as all Control Request header data is now preloaded by the library and made available in the
+ *      USB_ControlRequest structure.
  *
  *  <b>Host Mode</b>
  *    - The USB_Host_SendControlRequest() function no longer automatically selects the Control pipe (pipe 0) to allow it to be used on
@@ -61,6 +64,8 @@
  *      and SetReportItemInfo() has been renamed to USB_GetHIDReportItemInfo().
  *    - The values of the DSearch_Return_ErrorCodes_t and DSearch_Comp_Return_ErrorCodes_t enums have had their respective "Descriptor_Search"
  *      and "Descriptor_Search_Comp" prefixes changed to all caps.
+ *    - The USB_HostRequest global has been renamed to USB_ControlRequest, and is used in Device mode also. The USB_Host_Request_Header_t
+ *      structure type has been renamed to USB_Request_Header_t.
  *
  * \section Sec_Migration090401 Migrating from 090209 to 090401
  *
diff --git a/Projects/Magstripe/Magstripe.c b/Projects/Magstripe/Magstripe.c
index 94eed314dae4c0afb3300dc1b3832c27e48c175d..24172d82cf1e45e0d8f4e304a08c9bb03ae44d62 100644
--- a/Projects/Magstripe/Magstripe.c
+++ b/Projects/Magstripe/Magstripe.c
@@ -155,33 +155,20 @@ EVENT_HANDLER(USB_ConfigurationChanged)
 EVENT_HANDLER(USB_UnhandledControlPacket)
 {
 	/* Handle HID Class specific requests */
-	switch (bRequest)
+	switch (USB_ControlRequest.bRequest)
 	{
 		case REQ_GetReport:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				USB_KeyboardReport_Data_t KeyboardReportData;
 
 				/* Create the next keyboard report for transmission to the host */
 				GetNextReport(&KeyboardReportData);
 
-				/* Ignore report type and ID number value */
-				Endpoint_Discard_Word();
-				
-				/* Ignore unused Interface number value */
-				Endpoint_Discard_Word();
-
-				/* Read in the number of bytes in the report to send to the host */
-				uint16_t wLength = Endpoint_Read_Word_LE();
-				
-				/* If trying to send more bytes than exist to the host, clamp the value at the report size */
-				if (wLength > sizeof(KeyboardReportData))
-				  wLength = sizeof(KeyboardReportData);
-
 				Endpoint_ClearSETUP();
 	
 				/* Write the report data to the control endpoint */
-				Endpoint_Write_Control_Stream_LE(&KeyboardReportData, wLength);
+				Endpoint_Write_Control_Stream_LE(&KeyboardReportData, sizeof(KeyboardReportData));
 				
 				/* Finalize the stream transfer to send the last packet or clear the host abort */
 				Endpoint_ClearOUT();
@@ -189,7 +176,7 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 		
 			break;
 		case REQ_GetProtocol:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
 				Endpoint_ClearSETUP();
 				
@@ -206,15 +193,12 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 			
 			break;
 		case REQ_SetProtocol:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
-				/* Read in the wValue parameter containing the new protocol mode */
-				uint16_t wValue = Endpoint_Read_Word_LE();
-				
 				Endpoint_ClearSETUP();
 
 				/* Set or clear the flag depending on what the host indicates that the current Protocol should be */
-				UsingReportProtocol = (wValue != 0x0000);
+				UsingReportProtocol = (USB_ControlRequest.wValue != 0x0000);
 				
 				/* Acknowledge status stage */
 				while (!(Endpoint_IsINReady()));
@@ -223,15 +207,12 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 			
 			break;
 		case REQ_SetIdle:
-			if (bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_HOSTTODEVICE | REQTYPE_CLASS | REQREC_INTERFACE))
 			{
-				/* Read in the wValue parameter containing the idle period */
-				uint16_t wValue = Endpoint_Read_Word_LE();
-				
 				Endpoint_ClearSETUP();
 				
 				/* Get idle period in MSB */
-				IdleCount = (wValue >> 8);
+				IdleCount = (USB_ControlRequest.wValue >> 8);
 				
 				/* Acknowledge status stage */
 				while (!(Endpoint_IsINReady()));
@@ -240,7 +221,7 @@ EVENT_HANDLER(USB_UnhandledControlPacket)
 			
 			break;
 		case REQ_GetIdle:
-			if (bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
+			if (USB_ControlRequest.bmRequestType == (REQDIR_DEVICETOHOST | REQTYPE_CLASS | REQREC_INTERFACE))
 			{		
 				Endpoint_ClearSETUP();