USB host enumeration functions module


Data Structures

struct  S_interface
 Interface. More...
struct  S_usb_setup_data
 USB Setup Data. More...

Defines

#define CONTROL_CRC16   0x10
#define CONTROL_DATA_PID   0x02
#define CONTROL_DATA_TOGGLE   0x01
#define CONTROL_GOOD   0x00
#define CONTROL_NO_DEVICE   0x40
#define CONTROL_PID   0x04
#define CONTROL_STALL   0x20
#define CONTROL_TIMEOUT   0x08
#define Get_altset_nb(s_interface)   (interface_supported[(s_interface)].altset_nb)
 Number of alternate settings associated with a supported interface.
#define Get_class(s_interface)   (interface_supported[(s_interface)].uclass)
 USB class associated with the supported interface.
#define Get_ep_nbr(s_interface, n_ep)   (Host_get_pipe_endpoint_number(Get_ep_pipe(s_interface, n_ep)))
 Endpoint number associated with the supported interface.
#define Get_ep_pipe(s_interface, n_ep)   (interface_supported[(s_interface)].ep_pipe[(n_ep)])
 Endpoint pipe associated with the supported interface.
#define Get_ep_type(s_interface, n_ep)   (Host_get_pipe_type(Get_ep_pipe(s_interface, n_ep)))
 Endpoint type associated with the supported interface.
#define Get_interface_number(s_interface)   (interface_supported[(s_interface)].interface_nb)
 Number of interfaces associated with a supported interface.
#define Get_maxpower()   (maxpower)
 Maximal power consumption ot the connected device (unit is 2 mA).
#define Get_nb_ep(s_interface)   (interface_supported[(s_interface)].nb_ep)
 Number of endpoints associated with a supported interface.
#define Get_nb_supported_interface()   (nb_interface_supported)
 Number of supported interfaces in the connected device.
#define Get_PID()   (device_PID)
 PID of the connected device.
#define Get_pipe_token(ep_addr)   ((Get_desc_ep_dir(ep_addr)) ? TOKEN_IN : TOKEN_OUT)
 Extract token information from endpoint address.
#define Get_protocol(s_interface)   (interface_supported[(s_interface)].protocol)
 USB protocol associated with the supported interface.
#define Get_subclass(s_interface)   (interface_supported[(s_interface)].subclass)
 USB subclass associated with the supported interface.
#define Get_VID()   (device_VID)
 VID of the connected device.
#define host_clear_endpoint_feature(ep)
 Send a "clear endpoint feature" request.
#define host_get_configuration()
 Send a "get configuration" request.
#define host_get_configuration_descriptor(cfg_ix)
 Send a "get device configuration descriptor" request The configuration descriptor received is stored in the data_stage array.
#define host_get_device_descriptor()
 Send a "get device desriptor" request The descriptor received is stored in the data_stage array.
#define host_get_device_descriptor_incomplete()
 Send an incomplete "get device desriptor" request The descriptor received is stored in the data_stage array.
#define host_ms_get_max_lun()
 Send the mass-storage specific request "get max LUN".
#define host_set_address(addr)
 Send a "set address" request.
#define host_set_configuration(cfg_nb)
 Send a "set configuration" request.
#define host_set_feature_remote_wakeup()
 Send a "set feature" "device remote wake-up".
#define host_set_interface(interface_nb, alt_setting)
 Send a "set interface" request to specify an alternate setting for an interface.
#define Is_device_self_powered()   (Tst_bits(bmattributes, SELF_POWERED_MASK))
 TRUE if the connected device is self-powered.
#define Is_device_supports_remote_wakeup()   (Tst_bits(bmattributes, REMOTE_WAKEUP_MASK))
 TRUE if the connected device supports remote wake-up.
#define Is_ep_in(s_interface, n_ep)   (Host_get_pipe_token(Get_ep_pipe(s_interface, n_ep)) == TOKEN_IN)
 TRUE if the endpoint direction associated with the supported interface is IN.
#define OFFSET_DESCRIPTOR_LENGTH   0
 Offsets common to all descriptor types.
#define OFFSET_FIELD_ALT   3
#define OFFSET_FIELD_BMATTRIBUTES   7
#define OFFSET_FIELD_CLASS   5
#define OFFSET_FIELD_CONFIGURATION_NB   5
#define OFFSET_FIELD_DESCRIPTOR_TYPE   1
#define OFFSET_FIELD_EP_ADDR   2
 Offsets in endpoint descriptors.
#define OFFSET_FIELD_EP_INTERVAL   6
#define OFFSET_FIELD_EP_SIZE   4
#define OFFSET_FIELD_EP_TYPE   3
#define OFFSET_FIELD_INTERFACE_NB   2
 Offsets in interface descriptors.
#define OFFSET_FIELD_MAXPACKETSIZE   7
 Offsets in device descriptors.
#define OFFSET_FIELD_MAXPOWER   8
#define OFFSET_FIELD_NB_CONFIGURATION   17
#define OFFSET_FIELD_NB_INTERFACE   4
#define OFFSET_FIELD_NB_OF_EP   4
#define OFFSET_FIELD_PID   10
#define OFFSET_FIELD_PROTOCOL   7
#define OFFSET_FIELD_SUB_CLASS   6
#define OFFSET_FIELD_TOTAL_LENGTH   2
 Offsets in configuration descriptors.
#define OFFSET_FIELD_VID   8
#define REMOTE_WAKEUP_BIT   5
#define REMOTE_WAKEUP_MASK   (1 << REMOTE_WAKEUP_BIT)
#define SELF_POWERED_BIT   6
#define SELF_POWERED_MASK   (1 << SELF_POWERED_BIT)

Functions

Bool host_check_class (void)
 This function checks if the device class is supported.
Bool host_check_VID_PID (void)
 This function checks if the VID and the PID are supported (if the VID & PID belong to the VID_PID table).
Status_t host_transfer_control (void *data_pointer)
 This function is the generic control pipe management function.

Variables

volatile U8 bmattributes
 bmAttributes byte of connected device
volatile U16 device_PID
 PID of connected device.
volatile U16 device_VID
 VID of connected device.
volatile S_interface interface_supported [MAX_INTERFACE_SUPPORTED]
 Supported interfaces.
volatile U8 maxpower
 maxpower byte of connected device (unit is 2 mA)
volatile U8 nb_interface_supported
 Number of interfaces the host is able to support in the connected device.


Define Documentation

#define CONTROL_CRC16   0x10

Definition at line 105 of file usb_host_enum.h.

#define CONTROL_DATA_PID   0x02

Definition at line 102 of file usb_host_enum.h.

#define CONTROL_DATA_TOGGLE   0x01

Definition at line 101 of file usb_host_enum.h.

#define CONTROL_GOOD   0x00

Definition at line 100 of file usb_host_enum.h.

Referenced by host_transfer_control(), and usb_host_task().

#define CONTROL_NO_DEVICE   0x40

Definition at line 107 of file usb_host_enum.h.

#define CONTROL_PID   0x04

Definition at line 103 of file usb_host_enum.h.

#define CONTROL_STALL   0x20

Definition at line 106 of file usb_host_enum.h.

Referenced by host_transfer_control().

#define CONTROL_TIMEOUT   0x08

Definition at line 104 of file usb_host_enum.h.

Referenced by host_transfer_control().

#define Get_altset_nb ( s_interface   )     (interface_supported[(s_interface)].altset_nb)

Number of alternate settings associated with a supported interface.

Parameters:
s_interface U8: The supported interface number
Returns:
U8: Number of alternate settings

Definition at line 316 of file usb_host_enum.h.

#define Get_class ( s_interface   )     (interface_supported[(s_interface)].uclass)

USB class associated with the supported interface.

Parameters:
s_interface U8: The supported interface number
Returns:
U8: Class

Definition at line 321 of file usb_host_enum.h.

Referenced by host_template_task().

#define Get_ep_nbr ( s_interface,
n_ep   )     (Host_get_pipe_endpoint_number(Get_ep_pipe(s_interface, n_ep)))

Endpoint number associated with the supported interface.

Parameters:
s_interface U8: The supported interface number
n_ep U8: The endpoint number in this interface
Returns:
U8: Endpoint number

Definition at line 348 of file usb_host_enum.h.

#define Get_ep_pipe ( s_interface,
n_ep   )     (interface_supported[(s_interface)].ep_pipe[(n_ep)])

Endpoint pipe associated with the supported interface.

Parameters:
s_interface U8: The supported interface number
n_ep U8: The endpoint number in this interface
Returns:
U8: Endpoint pipe

Definition at line 342 of file usb_host_enum.h.

Referenced by host_template_task().

#define Get_ep_type ( s_interface,
n_ep   )     (Host_get_pipe_type(Get_ep_pipe(s_interface, n_ep)))

Endpoint type associated with the supported interface.

Parameters:
s_interface U8: The supported interface number
n_ep U8: The endpoint number in this interface
Returns:
U8: Endpoint type

Definition at line 354 of file usb_host_enum.h.

#define Get_interface_number ( s_interface   )     (interface_supported[(s_interface)].interface_nb)

Number of interfaces associated with a supported interface.

Parameters:
s_interface U8: The supported interface number
Returns:
U8: Number of interfaces

Definition at line 311 of file usb_host_enum.h.

 
#define Get_maxpower (  )     (maxpower)

Maximal power consumption ot the connected device (unit is 2 mA).

Returns:
U8: Maximal power

Definition at line 302 of file usb_host_enum.h.

#define Get_nb_ep ( s_interface   )     (interface_supported[(s_interface)].nb_ep)

Number of endpoints associated with a supported interface.

Parameters:
s_interface U8: The supported interface number
Returns:
U8: Number of endpoints

Definition at line 336 of file usb_host_enum.h.

 
#define Get_nb_supported_interface (  )     (nb_interface_supported)

Number of supported interfaces in the connected device.

Returns:
U8: Number of supported interfaces

Definition at line 306 of file usb_host_enum.h.

Referenced by host_template_task().

 
#define Get_PID (  )     (device_PID)

PID of the connected device.

Returns:
U16: PID

Definition at line 290 of file usb_host_enum.h.

#define Get_pipe_token ( ep_addr   )     ((Get_desc_ep_dir(ep_addr)) ? TOKEN_IN : TOKEN_OUT)

Extract token information from endpoint address.

Parameters:
ep_addr U8: Endpoint address
Returns:
TOKEN_IN/TOKEN_OUT: Pipe token

Definition at line 365 of file usb_host_enum.h.

Referenced by host_check_class().

#define Get_protocol ( s_interface   )     (interface_supported[(s_interface)].protocol)

USB protocol associated with the supported interface.

Parameters:
s_interface U8: The supported interface number
Returns:
U8: protocol

Definition at line 331 of file usb_host_enum.h.

#define Get_subclass ( s_interface   )     (interface_supported[(s_interface)].subclass)

USB subclass associated with the supported interface.

Parameters:
s_interface U8: The supported interface number
Returns:
U8: Subclass

Definition at line 326 of file usb_host_enum.h.

 
#define Get_VID (  )     (device_VID)

VID of the connected device.

Returns:
U16: VID

Definition at line 286 of file usb_host_enum.h.

#define host_clear_endpoint_feature ( ep   ) 

Value:

Send a "clear endpoint feature" request.

Parameters:
ep U8: Target endpoint
Returns:
Status

Definition at line 147 of file usb_host_enum.h.

 
#define host_get_configuration (  ) 

Value:

Send a "get configuration" request.

Returns:
Status

Definition at line 160 of file usb_host_enum.h.

#define host_get_configuration_descriptor ( cfg_ix   ) 

Value:

Send a "get device configuration descriptor" request The configuration descriptor received is stored in the data_stage array.

Parameters:
cfg_ix U8: Index of the configuration descriptor to get
Returns:
Status

Definition at line 233 of file usb_host_enum.h.

Referenced by usb_host_task().

 
#define host_get_device_descriptor (  ) 

Value:

Send a "get device desriptor" request The descriptor received is stored in the data_stage array.

Returns:
Status

Definition at line 218 of file usb_host_enum.h.

Referenced by usb_host_task().

 
#define host_get_device_descriptor_incomplete (  ) 

Value:

Send an incomplete "get device desriptor" request The descriptor received is stored in the data_stage array.

The received descriptors are limited to the length of the control pipe.

Returns:
Status

Definition at line 204 of file usb_host_enum.h.

Referenced by usb_host_task().

 
#define host_ms_get_max_lun (  ) 

Value:

Send the mass-storage specific request "get max LUN".

Returns:
Status

Definition at line 273 of file usb_host_enum.h.

#define host_set_address ( addr   ) 

Value:

Send a "set address" request.

Parameters:
addr U8: Address assigned to the device
Returns:
Status

Definition at line 247 of file usb_host_enum.h.

Referenced by usb_host_task().

#define host_set_configuration ( cfg_nb   ) 

Value:

Send a "set configuration" request.

Parameters:
cfg_nb U8: Configuration to activate
Returns:
Status

Definition at line 174 of file usb_host_enum.h.

Referenced by usb_host_task().

 
#define host_set_feature_remote_wakeup (  ) 

Value:

Send a "set feature" "device remote wake-up".

Returns:
Status

Definition at line 260 of file usb_host_enum.h.

Referenced by host_template_task(), and usb_host_task().

#define host_set_interface ( interface_nb,
alt_setting   ) 

Value:

Send a "set interface" request to specify an alternate setting for an interface.

Parameters:
interface_nb U8: Interface
alt_setting U8: Alternate setting
Returns:
Status

Definition at line 189 of file usb_host_enum.h.

 
#define Is_device_self_powered (  )     (Tst_bits(bmattributes, SELF_POWERED_MASK))

TRUE if the connected device is self-powered.

Returns:
Bool: Self-powered?

Definition at line 298 of file usb_host_enum.h.

 
#define Is_device_supports_remote_wakeup (  )     (Tst_bits(bmattributes, REMOTE_WAKEUP_MASK))

TRUE if the connected device supports remote wake-up.

Returns:
Bool: Remote wake-up supported?

Definition at line 294 of file usb_host_enum.h.

Referenced by usb_host_task().

#define Is_ep_in ( s_interface,
n_ep   )     (Host_get_pipe_token(Get_ep_pipe(s_interface, n_ep)) == TOKEN_IN)

TRUE if the endpoint direction associated with the supported interface is IN.

Parameters:
s_interface U8: The supported interface number
n_ep U8: The endpoint number in this interface
Returns:
Bool: Endpoint direction IN?

Definition at line 360 of file usb_host_enum.h.

Referenced by host_template_task().

#define OFFSET_DESCRIPTOR_LENGTH   0

Offsets common to all descriptor types.

Definition at line 110 of file usb_host_enum.h.

Referenced by host_check_class().

#define OFFSET_FIELD_ALT   3

Definition at line 132 of file usb_host_enum.h.

Referenced by host_check_class().

#define OFFSET_FIELD_BMATTRIBUTES   7

Definition at line 123 of file usb_host_enum.h.

Referenced by host_check_class().

#define OFFSET_FIELD_CLASS   5

Definition at line 134 of file usb_host_enum.h.

Referenced by host_check_class().

#define OFFSET_FIELD_CONFIGURATION_NB   5

Definition at line 122 of file usb_host_enum.h.

#define OFFSET_FIELD_DESCRIPTOR_TYPE   1

Definition at line 111 of file usb_host_enum.h.

Referenced by host_check_class().

#define OFFSET_FIELD_EP_ADDR   2

Offsets in endpoint descriptors.

Definition at line 139 of file usb_host_enum.h.

Referenced by host_check_class().

#define OFFSET_FIELD_EP_INTERVAL   6

Definition at line 142 of file usb_host_enum.h.

Referenced by host_check_class().

#define OFFSET_FIELD_EP_SIZE   4

Definition at line 141 of file usb_host_enum.h.

Referenced by host_check_class().

#define OFFSET_FIELD_EP_TYPE   3

Definition at line 140 of file usb_host_enum.h.

Referenced by host_check_class().

#define OFFSET_FIELD_INTERFACE_NB   2

Offsets in interface descriptors.

Definition at line 131 of file usb_host_enum.h.

Referenced by host_check_class().

#define OFFSET_FIELD_MAXPACKETSIZE   7

Offsets in device descriptors.

Definition at line 114 of file usb_host_enum.h.

Referenced by usb_host_task().

#define OFFSET_FIELD_MAXPOWER   8

Definition at line 128 of file usb_host_enum.h.

Referenced by host_check_class().

#define OFFSET_FIELD_NB_CONFIGURATION   17

Definition at line 117 of file usb_host_enum.h.

#define OFFSET_FIELD_NB_INTERFACE   4

Definition at line 121 of file usb_host_enum.h.

#define OFFSET_FIELD_NB_OF_EP   4

Definition at line 133 of file usb_host_enum.h.

Referenced by host_check_class().

#define OFFSET_FIELD_PID   10

Definition at line 116 of file usb_host_enum.h.

Referenced by host_check_VID_PID().

#define OFFSET_FIELD_PROTOCOL   7

Definition at line 136 of file usb_host_enum.h.

Referenced by host_check_class().

#define OFFSET_FIELD_SUB_CLASS   6

Definition at line 135 of file usb_host_enum.h.

Referenced by host_check_class().

#define OFFSET_FIELD_TOTAL_LENGTH   2

Offsets in configuration descriptors.

Definition at line 120 of file usb_host_enum.h.

Referenced by host_check_class().

#define OFFSET_FIELD_VID   8

Definition at line 115 of file usb_host_enum.h.

Referenced by host_check_VID_PID().

#define REMOTE_WAKEUP_BIT   5

Definition at line 124 of file usb_host_enum.h.

#define REMOTE_WAKEUP_MASK   (1 << REMOTE_WAKEUP_BIT)

Definition at line 125 of file usb_host_enum.h.

#define SELF_POWERED_BIT   6

Definition at line 126 of file usb_host_enum.h.

#define SELF_POWERED_MASK   (1 << SELF_POWERED_BIT)

Definition at line 127 of file usb_host_enum.h.


Function Documentation

Bool host_check_class ( void   ) 

This function checks if the device class is supported.

The function looks in all interfaces declared in the received descriptors if one of them matches an entry of the CLASS/SUB_CLASS/PROTOCOL table. If HOST_AUTO_CFG_ENDPOINT is enabled, a pipe is configured for each endpoint of supported interfaces.

Returns:
Bool: Status

Definition at line 141 of file usb_host_enum.c.

References S_interface::altset_nb, bmattributes, CONFIGURATION_DESCRIPTOR, data_stage, DOUBLE_BANK, ENDPOINT_DESCRIPTOR, S_interface::ep_pipe, Get_desc_ep_nbr, Get_pipe_token, Host_clear_configured, Host_configure_pipe, Host_configure_pipe_int_req_freq, Host_disable_pipe, Host_enable_ping, Host_enable_pipe, Host_get_pipe_token, Host_get_pipe_type, Host_set_configured, Host_unallocate_memory, Host_user_check_class_action, INTERFACE_DESCRIPTOR, S_interface::interface_nb, Is_host_pipe_enabled, Is_usb_full_speed_mode, MAX_EP_PER_INTERFACE, MAX_INTERFACE_SUPPORTED, MAX_PEP_NB, maxpower, S_interface::nb_ep, nb_interface_supported, OFFSET_DESCRIPTOR_LENGTH, OFFSET_FIELD_ALT, OFFSET_FIELD_BMATTRIBUTES, OFFSET_FIELD_CLASS, OFFSET_FIELD_DESCRIPTOR_TYPE, OFFSET_FIELD_EP_ADDR, OFFSET_FIELD_EP_INTERVAL, OFFSET_FIELD_EP_SIZE, OFFSET_FIELD_EP_TYPE, OFFSET_FIELD_INTERFACE_NB, OFFSET_FIELD_MAXPOWER, OFFSET_FIELD_NB_OF_EP, OFFSET_FIELD_PROTOCOL, OFFSET_FIELD_SUB_CLASS, OFFSET_FIELD_TOTAL_LENGTH, P_1, S_interface::protocol, REG_CLASS_CNT, registered_class, SINGLE_BANK, SIZEOF_DATA_STAGE, S_interface::subclass, TOKEN_OUT, TYPE_BULK, TYPE_INTERRUPT, S_interface::uclass, and usb_format_usb_to_mcu_data.

Referenced by usb_host_task().

00142 {
00143   U8 *descriptor, *conf_end;
00144   U8 device_class, device_subclass, device_protocol;
00145   U8 c;
00146 #if HOST_AUTO_CFG_ENDPOINT == ENABLE
00147   U8 nb_endpoint_to_configure = 0;
00148   U8 ep_index = 0;
00149   U8 physical_pipe = P_1;   // P_1 because physical pipe 0 is reserved for control
00150 
00151   // By default, the host is configured when returning
00152   Host_set_configured();
00153 #endif
00154 
00155   // First, assume no interface is supported
00156   nb_interface_supported = 0;
00157 
00158   // Check if configuration descriptor
00159   if (data_stage[OFFSET_FIELD_DESCRIPTOR_TYPE] != CONFIGURATION_DESCRIPTOR) return FALSE;
00160 
00161   bmattributes = data_stage[OFFSET_FIELD_BMATTRIBUTES];
00162   maxpower     = data_stage[OFFSET_FIELD_MAXPOWER];
00163 
00164   conf_end = data_stage +
00165              min(usb_format_usb_to_mcu_data(16, *(U16 *)(data_stage + OFFSET_FIELD_TOTAL_LENGTH)),
00166                  SIZEOF_DATA_STAGE - OFFSET_FIELD_PROTOCOL);
00167 
00168   // Look in all interfaces declared in the configuration
00169   for (descriptor = data_stage + data_stage[OFFSET_DESCRIPTOR_LENGTH]; descriptor < conf_end;
00170        descriptor += descriptor[OFFSET_DESCRIPTOR_LENGTH])
00171   {
00172     // Find next interface descriptor
00173     switch (descriptor[OFFSET_FIELD_DESCRIPTOR_TYPE])
00174     {
00175     case INTERFACE_DESCRIPTOR:
00176       // Check the number of supported interfaces does not exceed the maximum
00177       if (nb_interface_supported >= MAX_INTERFACE_SUPPORTED) return TRUE;
00178 
00179 #if HOST_AUTO_CFG_ENDPOINT == ENABLE
00180       // If there are still endpoints to configure although a new interface descriptor has been found
00181       if (nb_endpoint_to_configure)
00182       {
00183         // Mark the host as not configured
00184         Host_clear_configured();
00185 
00186         // Reset the number of endpoints to configure
00187         nb_endpoint_to_configure = 0;
00188       }
00189 #endif
00190 
00191       // Found an interface descriptor
00192       // Get charateristics of this interface
00193       device_class    = descriptor[OFFSET_FIELD_CLASS];
00194       device_subclass = descriptor[OFFSET_FIELD_SUB_CLASS];
00195       device_protocol = descriptor[OFFSET_FIELD_PROTOCOL];
00196 
00197       // Look in registered class table for match
00198       for (c = 0; c < REG_CLASS_CNT; c += 3)
00199       {
00200         if (registered_class[c]     == device_class    &&   // Class is correct
00201             registered_class[c + 1] == device_subclass &&   // Subclass is correct
00202             registered_class[c + 2] == device_protocol)     // Protocol is correct
00203         {
00204           // Store this interface as supported interface
00205           // Memorize its interface nb
00206           interface_supported[nb_interface_supported].interface_nb = descriptor[OFFSET_FIELD_INTERFACE_NB];
00207           //          its alternate setting
00208           interface_supported[nb_interface_supported].altset_nb    = descriptor[OFFSET_FIELD_ALT];
00209           //          its USB class
00210           interface_supported[nb_interface_supported].uclass        = device_class;
00211           //          its USB subclass
00212           interface_supported[nb_interface_supported].subclass     = device_subclass;
00213           //          its USB protocol
00214           interface_supported[nb_interface_supported].protocol     = device_protocol;
00215           //          the number of endpoints associated with this interface
00216 #if HOST_AUTO_CFG_ENDPOINT == ENABLE
00217           ep_index = 0;
00218           nb_endpoint_to_configure =
00219 #endif
00220           interface_supported[nb_interface_supported].nb_ep        = min(descriptor[OFFSET_FIELD_NB_OF_EP], MAX_EP_PER_INTERFACE);
00221 
00222           // Update the number of supported interfaces
00223           nb_interface_supported++;
00224 
00225           // Class/subclass/protocol is registered, so look for next interface descriptor
00226           break;
00227         }
00228       }
00229       break;
00230 
00231 #if HOST_AUTO_CFG_ENDPOINT == ENABLE
00232     case ENDPOINT_DESCRIPTOR:
00233       // If there are still endpoints to configure while there are free pipes
00234       if (physical_pipe < MAX_PEP_NB && nb_endpoint_to_configure)
00235       {
00236         nb_endpoint_to_configure--;
00237 
00238         // Reconfigure the new physical pipe to get rid of any previous configuration
00239   #if USB_HOST_PIPE_INTERRUPT_TRANSFER == ENABLE
00240         Disable_global_interrupt();
00241   #endif
00242         Host_disable_pipe(physical_pipe);
00243   #if USB_HOST_PIPE_INTERRUPT_TRANSFER == ENABLE
00244         (void)Is_host_pipe_enabled(physical_pipe);
00245         Enable_global_interrupt();
00246   #endif
00247         Host_unallocate_memory(physical_pipe);
00248         Host_enable_pipe(physical_pipe);
00249 
00250         // Fix HW, set freq at 0 in case of no interrupt endpoint
00251         if( TYPE_INTERRUPT != descriptor[OFFSET_FIELD_EP_TYPE] ) descriptor[OFFSET_FIELD_EP_INTERVAL] = 0;
00252 
00253         // Build the pipe configuration according to the endpoint descriptor fields received
00254         (void)Host_configure_pipe(
00255                 physical_pipe,                                      // Pipe nb in USB interface
00256                 descriptor[OFFSET_FIELD_EP_INTERVAL],               // Interrupt period (for interrupt pipe)
00257                 Get_desc_ep_nbr(descriptor[OFFSET_FIELD_EP_ADDR]),  // Pipe endpoint number
00258                 descriptor[OFFSET_FIELD_EP_TYPE],                   // Pipe type (isochronous/bulk/interrupt)
00259                 Get_pipe_token(descriptor[OFFSET_FIELD_EP_ADDR]),   // Pipe token (IN/OUT)
00260                 descriptor[OFFSET_FIELD_EP_SIZE] |
00261                 descriptor[OFFSET_FIELD_EP_SIZE + 1] << 8,          // Pipe size
00262                 (TYPE_BULK == descriptor[OFFSET_FIELD_EP_TYPE]) ? DOUBLE_BANK : SINGLE_BANK  // Number of banks to allocate for pipe
00263               );
00264         
00265 #if (USB_HIGH_SPEED_SUPPORT==ENABLED)
00266         if( (TYPE_BULK == Host_get_pipe_type(physical_pipe))
00267         &&  (TOKEN_OUT == Host_get_pipe_token(physical_pipe)) )
00268         {
00269            if( !Is_usb_full_speed_mode() )
00270            {
00271               // Enable PING management for bulk OUT endpoint each micro frame
00272               Host_configure_pipe_int_req_freq(physical_pipe,0);
00273               Host_enable_ping(physical_pipe);
00274            }
00275         }
00276 #endif
00277 
00278         // Update endpoint pipe table in supported interface structure
00279         interface_supported[nb_interface_supported - 1].ep_pipe[ep_index++] = physical_pipe++;
00280       }
00281       break;
00282 #endif
00283     }
00284 
00285     // Call user callback to look more deeply into the configuration descriptor
00286     Host_user_check_class_action(descriptor);
00287   }
00288 
00289 #if HOST_AUTO_CFG_ENDPOINT == ENABLE
00290   // If there are still endpoints to configure although all descriptors have been parsed
00291   if (nb_endpoint_to_configure)
00292   {
00293     // Mark the host as not configured
00294     Host_clear_configured();
00295   }
00296 #endif
00297 
00298   return (nb_interface_supported > 0);
00299 }

Bool host_check_VID_PID ( void   ) 

This function checks if the VID and the PID are supported (if the VID & PID belong to the VID_PID table).

Returns:
Bool: Status

Definition at line 108 of file usb_host_enum.c.

References data_stage, device_PID, device_VID, OFFSET_FIELD_PID, OFFSET_FIELD_VID, REG_VID_PID_CNT, registered_VID_PID, and usb_format_usb_to_mcu_data.

Referenced by usb_host_task().

00109 {
00110   U8 c, d;
00111 
00112   // Rebuild VID & PID from data stage
00113   device_VID = usb_format_usb_to_mcu_data(16, *(U16 *)(data_stage + OFFSET_FIELD_VID));
00114   device_PID = usb_format_usb_to_mcu_data(16, *(U16 *)(data_stage + OFFSET_FIELD_PID));
00115 
00116   // Look for received VID & PID in supported table
00117   for (c = 0; c < REG_VID_PID_CNT; )
00118   {
00119     if (registered_VID_PID[c] == device_VID)  // VID is correct
00120     {
00121       for (c += 2, d = c + registered_VID_PID[c - 1]; c < d; c++)
00122       {
00123         if (registered_VID_PID[c] == device_PID) return TRUE; // PID is correct
00124       }
00125     }
00126     else c += 2 + registered_VID_PID[c + 1];
00127   }
00128 
00129   return FALSE;
00130 }

Status_t host_transfer_control ( void *  data_pointer  ) 

This function is the generic control pipe management function.

This function is used to send and receive control requests over control pipe.

Todo:
Fix all time-out errors and disconnections in active wait loop.
Parameters:
data_pointer void *: Pointer to data to transfer
Returns:
Status_t: Status
Note:
This function uses the usb_request global structure. Hence, this structure should be filled before calling this function.

Definition at line 314 of file usb_host_enum.c.

References S_usb_setup_data::bmRequestType, S_usb_setup_data::bRequest, CONTROL_GOOD, CONTROL_STALL, CONTROL_TIMEOUT, data_length, EVT_HOST_SOF, Host_ack_all_errors, Host_ack_control_in_received, Host_ack_control_in_received_free, Host_ack_control_out_ready, Host_ack_control_out_ready_send, Host_ack_setup_ready, Host_ack_sof, Host_ack_stall, Host_byte_count, Host_configure_pipe_token, Host_disable_continuous_in_mode, Host_disable_sof_interrupt, Host_enable_sof_interrupt, Host_error_status, Host_free_control_in, Host_freeze_pipe, Host_get_pipe_size, host_get_timeout(), host_read_p_rxpacket(), Host_reset_pipe, Host_reset_pipe_fifo_access, Host_send_control_out, Host_send_setup, Host_unfreeze_pipe, host_write_p_txpacket(), Host_write_pipe_data, S_usb_setup_data::incomplete_read, Is_host_control_in_received, Is_host_control_out_ready, Is_host_emergency_exit, Is_host_pipe_error, Is_host_setup_ready, Is_host_sof_interrupt_enabled, Is_host_stall, Is_usb_event, Is_usb_low_speed_mode, P_CONTROL, private_sof_counter, TOKEN_IN, TOKEN_OUT, TOKEN_SETUP, Usb_ack_event, usb_format_mcu_to_usb_data, usb_request, S_usb_setup_data::wIndex, S_usb_setup_data::wLength, and S_usb_setup_data::wValue.

00315 {
00316   Bool sav_int_sof_enable;
00317   Bool sav_glob_int_en;
00318   U16 data_length;
00319   U8 c;
00320 
00321   Usb_ack_event(EVT_HOST_SOF);
00322   sav_int_sof_enable = Is_host_sof_interrupt_enabled();
00323   Host_enable_sof_interrupt();                // SOF software detection is in interrupt subroutine
00324   while (!Is_usb_event(EVT_HOST_SOF))         // Wait 1 SOF
00325   {
00326     if (Is_host_emergency_exit())
00327     {
00328       Host_freeze_pipe(P_CONTROL);
00329       Host_reset_pipe(P_CONTROL);
00330       return CONTROL_TIMEOUT;
00331     }
00332   }
00333   if (!sav_int_sof_enable)                    // Restore SOF interrupt enable
00334   {
00335     if ((sav_glob_int_en = Is_global_interrupt_enabled())) Disable_global_interrupt();
00336     Host_disable_sof_interrupt();
00337     (void)Is_host_sof_interrupt_enabled();
00338     if (sav_glob_int_en) Enable_global_interrupt();
00339   }
00340 
00341   Host_configure_pipe_token(P_CONTROL, TOKEN_SETUP);
00342   Host_ack_setup_ready();
00343   Host_unfreeze_pipe(P_CONTROL);
00344 
00345   // Build and send the setup request fields
00346   Host_reset_pipe_fifo_access(P_CONTROL);
00347   Host_write_pipe_data(P_CONTROL, 8, usb_request.bmRequestType);
00348   Host_write_pipe_data(P_CONTROL, 8, usb_request.bRequest);
00349   Host_write_pipe_data(P_CONTROL, 16, usb_format_mcu_to_usb_data(16, usb_request.wValue));
00350   Host_write_pipe_data(P_CONTROL, 16, usb_format_mcu_to_usb_data(16, usb_request.wIndex));
00351   Host_write_pipe_data(P_CONTROL, 16, usb_format_mcu_to_usb_data(16, usb_request.wLength));
00352   Host_send_setup();
00353 
00354   while (!Is_host_setup_ready())  // Wait for SETUP ack
00355   {
00356     if (Is_host_emergency_exit())
00357     {
00358       Host_freeze_pipe(P_CONTROL);
00359       Host_reset_pipe(P_CONTROL);
00360       return CONTROL_TIMEOUT;
00361     }
00362     if (Is_host_pipe_error(P_CONTROL))  // Any error?
00363     {
00364       c = Host_error_status(P_CONTROL);
00365       Host_ack_all_errors(P_CONTROL);
00366       return c;   // Send error status
00367     }
00368   }
00369 
00370   // Setup token sent; now send IN or OUT token
00371   // Before just wait 1 SOF
00372   Usb_ack_event(EVT_HOST_SOF);
00373   sav_int_sof_enable = Is_host_sof_interrupt_enabled();
00374   Host_enable_sof_interrupt();
00375   Host_freeze_pipe(P_CONTROL);
00376   data_length = usb_request.wLength;
00377   while (!Is_usb_event(EVT_HOST_SOF))         // Wait 1 SOF
00378   {
00379     if (Is_host_emergency_exit())
00380     {
00381       Host_freeze_pipe(P_CONTROL);
00382       Host_reset_pipe(P_CONTROL);
00383       return CONTROL_TIMEOUT;
00384     }
00385   }
00386   if (!sav_int_sof_enable)                    // Restore SOF interrupt enable
00387   {
00388     if ((sav_glob_int_en = Is_global_interrupt_enabled())) Disable_global_interrupt();
00389     Host_disable_sof_interrupt();
00390     (void)Is_host_sof_interrupt_enabled();
00391     if (sav_glob_int_en) Enable_global_interrupt();
00392   }
00393 
00394   // IN request management ---------------------------------------------
00395   if (usb_request.bmRequestType & 0x80)       // Data stage IN (bmRequestType.D7 == 1)
00396   {
00397     Host_disable_continuous_in_mode(P_CONTROL);
00398     Host_configure_pipe_token(P_CONTROL, TOKEN_IN);
00399     Host_ack_control_in_received_free();
00400     while (data_length)
00401     {
00402       Host_unfreeze_pipe(P_CONTROL);
00403       private_sof_counter = 0;        // Reset the counter in SOF detection subroutine
00404       while (!Is_host_control_in_received())
00405       {
00406         if (Is_host_emergency_exit())
00407         {
00408           Host_freeze_pipe(P_CONTROL);
00409           Host_reset_pipe(P_CONTROL);
00410           return CONTROL_TIMEOUT;
00411         }
00412         if (Is_host_pipe_error(P_CONTROL))  // Any error?
00413         {
00414           c = Host_error_status(P_CONTROL);
00415           Host_ack_all_errors(P_CONTROL);
00416           return c;   // Send error status
00417         }
00418         if (Is_host_stall(P_CONTROL))
00419         {
00420           Host_ack_stall(P_CONTROL);
00421           return CONTROL_STALL;
00422         }
00423 #if TIMEOUT_DELAY_ENABLE == ENABLE
00424       if (1000 < host_get_timeout()) // Count 1s
00425       {
00426           Host_freeze_pipe(P_CONTROL);
00427           Host_reset_pipe(P_CONTROL);
00428           return CONTROL_TIMEOUT;
00429       }
00430 #endif
00431       }
00432       Host_reset_pipe_fifo_access(P_CONTROL);
00433       c = Host_get_pipe_size(P_CONTROL) - Host_byte_count(P_CONTROL);
00434       data_length = host_read_p_rxpacket(P_CONTROL, data_pointer, data_length, &data_pointer);
00435       if (usb_request.incomplete_read || c) data_length = 0;
00436       Host_freeze_pipe(P_CONTROL);
00437       Host_ack_control_in_received_free();
00438 
00439       // In low-speed mode, the USB IP may have not yet sent the ACK at this
00440       // point. The USB IP does not support a new start of transaction request
00441       // from the firmware if the ACK has not been sent. The only means of
00442       // making sure the ACK has been sent is to wait for the next Keep-Alive
00443       // before starting a new transaction.
00444       if (Is_usb_low_speed_mode())
00445       {
00446         Usb_ack_event(EVT_HOST_SOF);
00447         sav_int_sof_enable = Is_host_sof_interrupt_enabled();
00448         if ((sav_glob_int_en = Is_global_interrupt_enabled())) Disable_global_interrupt();
00449         Host_ack_sof();
00450         (void)Is_host_sof_interrupt_enabled();
00451         if (sav_glob_int_en) Enable_global_interrupt();
00452         Host_enable_sof_interrupt();
00453         while (!Is_usb_event(EVT_HOST_SOF))         // Wait for next Keep-Alive
00454         {
00455           if (Is_host_emergency_exit())
00456           {
00457             Host_freeze_pipe(P_CONTROL);
00458             Host_reset_pipe(P_CONTROL);
00459             return CONTROL_TIMEOUT;
00460           }
00461         }
00462         if (!sav_int_sof_enable)                    // Restore SOF interrupt enable
00463         {
00464           if ((sav_glob_int_en = Is_global_interrupt_enabled())) Disable_global_interrupt();
00465           Host_disable_sof_interrupt();
00466           (void)Is_host_sof_interrupt_enabled();
00467           if (sav_glob_int_en) Enable_global_interrupt();
00468         }
00469       }
00470     }                                 // End of IN data stage
00471 
00472     Host_configure_pipe_token(P_CONTROL, TOKEN_OUT);
00473     Host_ack_control_out_ready_send();
00474     Host_unfreeze_pipe(P_CONTROL);
00475     while (!Is_host_control_out_ready())
00476     {
00477       if (Is_host_emergency_exit())
00478       {
00479         Host_freeze_pipe(P_CONTROL);
00480         Host_reset_pipe(P_CONTROL);
00481         return CONTROL_TIMEOUT;
00482       }
00483       if (Is_host_pipe_error(P_CONTROL))  // Any error?
00484       {
00485         c = Host_error_status(P_CONTROL);
00486         Host_ack_all_errors(P_CONTROL);
00487         return c;   // Send error status
00488       }
00489       if (Is_host_stall(P_CONTROL))
00490       {
00491         Host_ack_stall(P_CONTROL);
00492         return CONTROL_STALL;
00493       }
00494     }
00495     Host_ack_control_out_ready();
00496   }
00497 
00498   // OUT request management --------------------------------------------
00499   else                                        // Data stage OUT (bmRequestType.D7 == 0)
00500   {
00501     Host_configure_pipe_token(P_CONTROL, TOKEN_OUT);
00502     Host_ack_control_out_ready();
00503     while (data_length)
00504     {
00505       Host_unfreeze_pipe(P_CONTROL);
00506       Host_reset_pipe_fifo_access(P_CONTROL);
00507       data_length = host_write_p_txpacket(P_CONTROL, data_pointer, data_length, (const void **)&data_pointer);
00508       Host_send_control_out();
00509       while (!Is_host_control_out_ready())
00510       {
00511         if (Is_host_emergency_exit())
00512         {
00513           Host_freeze_pipe(P_CONTROL);
00514           Host_reset_pipe(P_CONTROL);
00515           return CONTROL_TIMEOUT;
00516         }
00517         if (Is_host_pipe_error(P_CONTROL))  // Any error?
00518         {
00519           c = Host_error_status(P_CONTROL);
00520           Host_ack_all_errors(P_CONTROL);
00521           return c;   // Send error status
00522         }
00523         if (Is_host_stall(P_CONTROL))
00524         {
00525           Host_ack_stall(P_CONTROL);
00526           return CONTROL_STALL;
00527         }
00528       }
00529       Host_ack_control_out_ready();
00530     }                                 // End of OUT data stage
00531 
00532     Host_freeze_pipe(P_CONTROL);
00533     Host_configure_pipe_token(P_CONTROL, TOKEN_IN);
00534     Host_ack_control_in_received_free();
00535     Host_unfreeze_pipe(P_CONTROL);
00536     while (!Is_host_control_in_received())
00537     {
00538       if (Is_host_emergency_exit())
00539       {
00540         Host_freeze_pipe(P_CONTROL);
00541         Host_reset_pipe(P_CONTROL);
00542         return CONTROL_TIMEOUT;
00543       }
00544       if (Is_host_pipe_error(P_CONTROL))  // Any error?
00545       {
00546         c = Host_error_status(P_CONTROL);
00547         Host_ack_all_errors(P_CONTROL);
00548         return c;   // Send error status
00549       }
00550       if (Is_host_stall(P_CONTROL))
00551       {
00552         Host_ack_stall(P_CONTROL);
00553         return CONTROL_STALL;
00554       }
00555     }
00556     Host_ack_control_in_received();
00557     Host_freeze_pipe(P_CONTROL);
00558     Host_free_control_in();
00559   }
00560 
00561   return CONTROL_GOOD;
00562 }


Variable Documentation

volatile U8 bmattributes

bmAttributes byte of connected device

Definition at line 90 of file usb_host_enum.c.

Referenced by host_check_class().

volatile U16 device_PID

PID of connected device.

Definition at line 87 of file usb_host_enum.c.

Referenced by host_check_VID_PID().

volatile U16 device_VID

VID of connected device.

Definition at line 84 of file usb_host_enum.c.

Referenced by host_check_VID_PID().

volatile S_interface interface_supported[MAX_INTERFACE_SUPPORTED]

Supported interfaces.

Definition at line 99 of file usb_host_enum.c.

volatile U8 maxpower

maxpower byte of connected device (unit is 2 mA)

Definition at line 93 of file usb_host_enum.c.

Referenced by host_check_class().

Number of interfaces the host is able to support in the connected device.

Definition at line 96 of file usb_host_enum.c.

Referenced by host_check_class(), and usb_host_task().


Generated on Fri Feb 19 02:27:52 2010 for AVR32 - USB Enumeration Example by  doxygen 1.5.5