📄 control_ep0.c
字号:
/*
** CmdGetStatus
*
* FILENAME: control_ep0.c
*
* PARAMETERS: None
*
* DESCRIPTION: Returns various status information to the HOST about the state of the device
* only valid in the Default and Configured State. If a request for status is
* made that is invalid, then the device STALLs the request per the USB spec.
* Note that there is no valid information for INTERFACE status, but the
* device just returns 0x00 0x00 per the spec. Valid endpoint status is
* also returned with this command. Linked to SET/CLEAR FEATURE requests.
* Note also that word fields are converted to bytes here locally for ease
* of code readability.
*
* RETURNS: Nothing
*
*/
void CmdGetStatus(void){
unsigned char wValue = SetupPacket.wValueLow | SetupPacket.wValueHigh;
unsigned char wIndex = SetupPacket.wIndexLow | SetupPacket.wIndexHigh;
unsigned char wLength = SetupPacket.wLengthLow | SetupPacket.wLengthHigh;
if ( (wValue != 0x00) || (wLength != 0x02) ){
ep0cs = 0x1040; // since these values do not match USB spec
return; // send STALL and leave function
}
if ( !USBFlags.Addressed ){ // Response not defined in USB spec in default state
ep0cs = 0x1040; // send STALL and leave function
return;
}
ep0ic = 0x00; // Disable to remove extra interrupt
if ( !USBFlags.Configured ){ // If device is in Address state, use these responses
switch ( SetupPacket.bmRequestType & 0x03 ){
case 0: // Device status
ep0cs = 0x2040; // Clear OBR flag
ep0il = 0x01; // Self powered and no remote wakeup support
ep0il = 0x00; // fill byte per spec
ep0cs = 0x2280; // Set DATA_END, IPR, and DATA_END mask
break; // exit function
case 1: // Interface status
ep0cs = 0x1040; // Not supported here so STALL
break;
case 2: // Endpoint status
switch ( SetupPacket.wIndexLow ){ // Determine which endpoint
case 0: // Only EP0 responds here
ep0cs = 0x2040; // Clear OBR flag
ep0il = 0x00; // fill byte per spec
ep0il = 0x00; // fill byte per spec
ep0cs = 0x2280; // Set DATA_END, IPR, and DATA_END mask
break; // exit function
default:
ep0cs = 0x1040; // If not supported then STALL
}
}
ir_ep0ic = 0;
ep0ic = 0x03; // Enable the EP0 interrupt (level 3)
return;
}
switch ( SetupPacket.bmRequestType & 0x03 ){ // Configured responses
case 0: // Device status
ep0cs = 0x2040; // Clear OBR flag
ep0il = 0x01; // Self powered and no remote wakeup support
break; // exit function
case 1: // Interface status
ep0cs = 0x2040; // Clear OBR flag
ep0il = 0x00; // fill byte per spec
break; // exit function
case 2: // Endpoint status
switch ( SetupPacket.wIndexLow ){ // Determine which endpoint
case 0:
ep0cs = 0x2040; // Clear OBR flag
ep0il = 0x00; // EP0 is never stalled
break; // exit function
case 1:
ep0cs = 0x2040; // Clear OBR flag
ep0il = USBFlags.EP1OUTStallStatus; // Get EP status
break; // exit function
case 3:
ep0cs = 0x2040; // Clear OBR flag
ep0il = USBFlags.EP3OUTStallStatus; // Get EP status
break; // exit function
case 129:
ep0cs = 0x2040; // Clear OBR flag
ep0il = USBFlags.EP1INStallStatus; // Get EP status
break; // exit function
case 130:
ep0cs = 0x2040; // Clear OBR flag
ep0il = USBFlags.EP2INStallStatus; // Get EP status
break; // exit function
case 131:
ep0cs = 0x2040; // Clear OBR flag
ep0il = USBFlags.EP3INStallStatus; // Get EP status
break; // exit function
default:
ep0cs = 0x1040; // EP Not supported so STALL
ir_ep0ic = 0;
ep0ic = 0x03; // Enable the EP0 interrupt (level 3)
return;
}
}
ep0il = 0x00; // fill byte per spec
ep0cs = 0x2280; // Set DATA_END, IPR, and DATA_END mask
ir_ep0ic = 0;
ep0ic = 0x03; // Enable the EP0 interrupt (level 3)
}
/*
** CmdClearFeature
*
* FILENAME: control_ep0.c
*
* PARAMETERS: None
*
* DESCRIPTION: The USB specification supports the clearing of certain 'features'
* of a device. These can include remote wakeup support and endpoint
* halting (STALL). Since this firmware does not support device
* or interface features, those requests are stalled. Only endpoints
* which exist are allowed to be unSTALLed with this request.
*
* RETURNS: Nothing
*
*/
void CmdClearFeature(void){
unsigned char wValue = SetupPacket.wValueLow | SetupPacket.wValueHigh;
unsigned char wIndex = SetupPacket.wIndexLow | SetupPacket.wIndexHigh;
unsigned char wLength = SetupPacket.wLengthLow | SetupPacket.wLengthHigh;
if ( wLength != 0x00 ){ // Is wLength non zero?
ep0cs = 0x1040; // STALL since this does not match USB spec
return; // CLR_SETUP and set OUT_PKT_RDY and leave function
}
if ( !USBFlags.Addressed ){ // Is device in the DEFAULT state?
ep0cs = 0x1040; // Device should not respond if not so STALL
return; // CLR_SETUP and set OUT_PKT_RDY and leave function
}
if ( !USBFlags.Configured ){ // Is the device configured?
switch ( (SetupPacket.bmRequestType & 0x03) ){ // What feature is to be cleared
case 0: // Device features...not supported here
break;
case 1: // Interface features...not supported here
break;
case 2: // Endpoint features...only EP0 here
if ( SetupPacket.wValueLow != 0x00 ){ // Is this a valid feature?
break; // If not then STALL
}
switch ( SetupPacket.wIndexLow ){ // Determine which endpoint
case 0: // Only EP0 supported in this case
ep0cs = 0x2240; // Set OPR, IPR, SETUP, DATA_END flags
return;
}
}
ep0cs = 0x1040; // Unconfigured state does not
return; // support clearing of many features, so STALL
}
switch ( (SetupPacket.bmRequestType & 0x03) ){ // What feature is to be cleared
case 0: // Device features...not supported here
break;
case 1: // Interface features...not supported here
break;
case 2: // Endpoint features
if ( SetupPacket.wValueLow != 0x00 ){ // Is this a valid EP feature?
ep0cs = 0x1040; // If not then STALL and exit function
return;
}
switch ( SetupPacket.wIndexLow ){ // Which endpoint?
case 1:
out1csr12 = 0; // Clear EP1 OUT STALL
USBFlags.EP1OUTStallStatus = 0;
break;
case 3: // Clear EP3 OUT STALL
out3csr12 = 0;
USBFlags.EP3OUTStallStatus = 0;
break;
case 129: // Clear EP1 IN STALL
in1csr9 = 0;
USBFlags.EP1INStallStatus = 0;
break;
case 130: // Clear EP2 IN STALL
in2csr9 = 0;
USBFlags.EP2INStallStatus = 0;
break;
case 131: // Clear EP3 IN STALL
in3csr9 = 0;
USBFlags.EP3INStallStatus = 0;
break;
default:
ep0cs = 0x1040; // Not a defined endpoint
return; // so STALL
}
ep0cs = 0x2240; // Set DATA_END, OBR, and MASK
return;
}
ep0cs = 0x1040; // None of these so STALL and exit function
}
/*
** CmdSetFeature
*
* FILENAME: control_ep0.c
*
* PARAMETERS: None
*
* DESCRIPTION: The USB specification supports the setting of certain 'features'
* of a device. These can include remote wakeup support and endpoint
* halting (STALL). Since this firmware does not support device
* or interface features, those requests are stalled. Only endpoints
* which exist are allowed to be STALL with this request.
*
* RETURNS: Nothing
*
*/
void CmdSetFeature(void){
unsigned char wValue = SetupPacket.wValueLow | SetupPacket.wValueHigh;
unsigned char wIndex = SetupPacket.wIndexLow | SetupPacket.wIndexHigh;
unsigned char wLength = SetupPacket.wLengthLow | SetupPacket.wLengthHigh;
if ( wLength != 0x00 ){ // Is wLength non zero?
ep0cs = 0x1040; // STALL since this does not match USB spec
return;
}
if ( !USBFlags.Addressed ){ // Is device in the DEFAULT state?
ep0cs = 0x1040; // Device should not respond if not so STALL
return;
}
if ( !USBFlags.Configured ){ // Is the device configured?
switch ( (SetupPacket.bmRequestType & 0x03) ){ // What feature is to be set
case 0: // Device features...not supported here
break;
case 1: // Interface features...not supported here
break;
case 2: // Endpoint features...only EP0 here
if ( SetupPacket.wValueLow != 0x00 ){ // Is this a valid EP feature?
break; // If not then STALL
}
switch ( SetupPacket.wIndexLow ){ // Determine which endpoint
case 0: // Only EP0 supported in this case
ep0cs = 0x2240; // Set OBR, mask, DATA_END flags
return;
}
}
ep0cs = 0x1040; // Unconfigured state does not
return; // support clearing of many features, so STALL
}
switch ( (SetupPacket.bmRequestType & 0x03) ){ // What feature is to be set
case 0: // Device features...not supported here
break;
case 1: // Interface features...not supported here
break;
case 2: // Endpoint features
if ( SetupPacket.wValueLow != 0x00 ){ // Is this a valid EP feature?
ep0cs = 0x1040; // If not then STALL and exit function
return;
}
switch ( SetupPacket.wIndexLow ){ // Which endpoint?
case 1:
out1csr12 = 1; // Set EP1 OUT STALL
USBFlags.EP1OUTStallStatus = 1;
break;
case 3: // Set EP3 OUT STALL
out3csr12 = 1;
USBFlags.EP3OUTStallStatus = 1;
break;
case 129: // Set EP1 IN STALL
in1csr9 = 1;
USBFlags.EP1INStallStatus = 1;
break;
case 130: // Set EP2 IN STALL
in2csr9 = 1;
USBFlags.EP2INStallStatus = 1;
break;
case 131: // Set EP3 IN STALL
in3csr9 = 1;
USBFlags.EP3INStallStatus = 1;
break;
default:
ep0cs = 0x1140; // Not a defined endpoint
return; // so STALL
}
ep0cs = 0x2240; // Set DATA_END, mask, & OBR
return;
}
ep0cs = 0x1040; // If none of these then STALL
}
/*
** CmdGetCongfiguration
*
* FILENAME: control_ep0.c
*
* PARAMETERS: None
*
* DESCRIPTION: Returns the current configuration value to the HOST. If the device
* is unconfigured then this rewuest should return 0x00. Associated
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -