/***************************************************************************** ** FILE NAME : dwc_otg_cil.h ** PROJECT : USB Host and Device driver ** MODULES : USB Host and Device driver ** SRC VERSION : 2.0 ** DATE : 1/March/2008 ** AUTHOR : Chen, Howard based on Synopsys Original ** DESCRIPTION : The Core Interface Layer provides basic services for accessing and ** managing the DWC_otg hardware. These services are used by both the ** Host Controller Driver and the Peripheral Controller Driver. ** ** The CIL manages the memory map for the core so that the HCD and PCD ** don't have to do this separately. It also handles basic tasks like ** reading/writing the registers and data FIFOs in the controller. ** Some of the data access functions provide encapsulation of several ** operations required to perform a task, such as writing multiple ** registers to start a transfer. Finally, the CIL performs basic ** services that are not specific to either the host or device modes ** of operation. These services include management of the OTG Host ** Negotiation Protocol (HNP) and Session Request Protocol (SRP). A ** Diagnostic API is also provided to allow testing of the controller ** hardware. ** FUNCTIONS : ** COMPILER : gcc ** REFERENCE : ** COPYRIGHT : ** Version Control Section ** ** $Author$ ** $Date$ ** $Revisions$ ** $Log$ Revision history *****************************************************************************/ /*! \file dwc_otg_cil.h \brief This file contains the interface to the Core Interface Layer. */ /*---------- Top Level Grouping ---------------------*/ /** \defgroup USB_DRIVER USB Driver \brief This section describes the USB drivers including control, host, device and debuging APIs */ /*---------- First Level Grouping ---------------------*/ /*\ingroup USB_DRIVER */ /** \defgroup USB_DRIVER_CIL Core Interface Layer APIs \brief The Core Interface Layer provides basic services for accessing and managing the DWC_otg hardware. These services are used by both the Host Controller Driver and the Peripheral Controller Driver. The CIL manages the memory map for the core so that the HCD and PCD don't have to do this separately. It also handles basic tasks like reading/writing the registers and data FIFOs in the controller. Some of the data access functions provide encapsulation of several operations required to perform a task, such as writing multiple registers to start a transfer. Finally, the CIL performs basic services that are not specific to either the host or device modes of operation. These services include management of the OTG Host Negotiation Protocol (HNP) and Session Request Protocol (SRP). A Diagnostic API is also provided to allow testing of the controller hardware. */ #if !defined(__DWC_CIL_H__) #define __DWC_CIL_H__ #include "dwc_otg_plat.h" #include "dwc_otg_cil_ifx.h" #include "dwc_otg_regs.h" #ifdef DEBUG #include "linux/timer.h" #endif /* the maximum speed of operation in host and device mode. */ #define DWC_SPEED_PARAM_HIGH 0 #define DWC_SPEED_PARAM_FULL 1 /** \ingroup USB_DRIVER_CIL * \brief The dwc_ep structure represents the state of a single * endpoint when acting in device mode. It contains the data items * needed for an endpoint to be activated and transfer packets. */ typedef struct dwc_ep { /** EP number used for register address lookup */ uint8_t num; /** EP direction 0 = OUT */ unsigned is_in : 1; /** EP active. */ unsigned active : 1; /** Periodic Tx FIFO # for IN EPs For INTR EP set to 0 to use non-periodic Tx FIFO */ unsigned tx_fifo_num : 4; /** EP type: 0 - Control, 1 - ISOC, 2 - BULK, 3 - INTR */ unsigned type : 2; #define DWC_OTG_EP_TYPE_CONTROL 0 #define DWC_OTG_EP_TYPE_ISOC 1 #define DWC_OTG_EP_TYPE_BULK 2 #define DWC_OTG_EP_TYPE_INTR 3 /** DATA start PID for INTR and BULK EP */ unsigned data_pid_start : 1; /** Frame (even/odd) for ISOC EP */ unsigned even_odd_frame : 1; /** Max Packet bytes */ unsigned maxpacket : 11; /** Pointer to the beginning of the transfer buffer -- do not modify during transfer. */ uint8_t *start_xfer_buff; /** pointer to the transfer buffer */ uint8_t *xfer_buff; /** Number of bytes to transfer */ unsigned xfer_len : 19; /** Number of bytes transferred. */ unsigned len_in_xfer: 19; /** Number of packet transferred. */ unsigned packet_in_xfer: 10; /** Number of bytes transferred. */ unsigned xfer_count : 19; /** Sent ZLP */ unsigned sent_zlp : 1; /** Total len for control transfer */ } dwc_ep_t; /* * Reasons for halting a host channel. */ typedef enum dwc_otg_halt_status { DWC_OTG_HC_XFER_NO_HALT_STATUS, DWC_OTG_HC_XFER_COMPLETE, DWC_OTG_HC_XFER_URB_COMPLETE, DWC_OTG_HC_XFER_ACK, DWC_OTG_HC_XFER_NAK, DWC_OTG_HC_XFER_NYET, DWC_OTG_HC_XFER_STALL, DWC_OTG_HC_XFER_XACT_ERR, DWC_OTG_HC_XFER_FRAME_OVERRUN, DWC_OTG_HC_XFER_BABBLE_ERR, DWC_OTG_HC_XFER_DATA_TOGGLE_ERR, DWC_OTG_HC_XFER_AHB_ERR, DWC_OTG_HC_XFER_PERIODIC_INCOMPLETE, DWC_OTG_HC_XFER_URB_DEQUEUE } dwc_otg_halt_status_e; /** \ingroup USB_DRIVER_CIL * \brief Host channel descriptor. This structure represents the state of a single * host channel when acting in host mode. It contains the data items needed to * transfer packets to an endpoint via a host channel. */ typedef struct dwc_hc { /** Host channel number used for register address lookup */ uint8_t hc_num; /** Device to access */ unsigned dev_addr : 7; /** EP to access */ unsigned ep_num : 4; /** EP direction. 0: OUT, 1: IN */ unsigned ep_is_in : 1; /** * EP speed. * One of the following values: * - DWC_OTG_EP_SPEED_LOW * - DWC_OTG_EP_SPEED_FULL * - DWC_OTG_EP_SPEED_HIGH */ unsigned speed : 2; #define DWC_OTG_EP_SPEED_LOW 0 #define DWC_OTG_EP_SPEED_FULL 1 #define DWC_OTG_EP_SPEED_HIGH 2 /** * Endpoint type. * One of the following values: * - DWC_OTG_EP_TYPE_CONTROL: 0 * - DWC_OTG_EP_TYPE_ISOC: 1 * - DWC_OTG_EP_TYPE_BULK: 2 * - DWC_OTG_EP_TYPE_INTR: 3 */ unsigned ep_type : 2; /** Max packet size in bytes */ unsigned max_packet : 11; /** * PID for initial transaction. * 0: DATA0,
* 1: DATA2,
* 2: DATA1,
* 3: MDATA (non-Control EP), * SETUP (Control EP) */ unsigned data_pid_start : 2; #define DWC_OTG_HC_PID_DATA0 0 #define DWC_OTG_HC_PID_DATA2 1 #define DWC_OTG_HC_PID_DATA1 2 #define DWC_OTG_HC_PID_MDATA 3 #define DWC_OTG_HC_PID_SETUP 3 /** Number of periodic transactions per (micro)frame */ unsigned multi_count: 2; /** Pointer to the current transfer buffer position. */ uint8_t *xfer_buff; #if defined(HCD_ALIGNADJ) uint8_t *xfer_buff_dma; #endif //unaligned #if defined(HOST_UNALIGNED_BUFFER_ADJUST) uint8_t using_aligned_tx_buf; uint8_t using_aligned_rx_buf; uint8_t *aligned_tx_buf; unsigned aligned_tx_buf_len : 19; uint8_t *aligned_rx_buf; unsigned aligned_rx_buf_len : 19; #endif /** Total number of bytes to transfer. */ uint32_t xfer_len; /** Number of bytes transferred so far. */ uint32_t xfer_count; /** Packet count at start of transfer.*/ uint16_t start_pkt_count; /** * Flag to indicate whether the transfer has been started. Set to 1 if * it has been started, 0 otherwise. */ uint8_t xfer_started; /** * Set to 1 to indicate that a PING request should be issued on this * channel. If 0, process normally. */ uint8_t do_ping; /** * Set to 1 to indicate that the error count for this transaction is * non-zero. Set to 0 if the error count is 0. */ uint8_t error_state; /** * Set to 1 to indicate that this channel should be halted the next * time a request is queued for the channel. This is necessary in * slave mode if no request queue space is available when an attempt * is made to halt the channel. */ uint8_t halt_on_queue; /** * Set to 1 if the host channel has been halted, but the core is not * finished flushing queued requests. Otherwise 0. */ uint8_t halt_pending; /** * Reason for halting the host channel. */ dwc_otg_halt_status_e halt_status; /* * Split settings for the host channel */ uint8_t do_split; /**< Enable split for the channel */ uint8_t complete_split; /**< Enable complete split */ uint8_t hub_addr; /**< Address of high speed hub */ uint8_t port_addr; /**< Port of the low/full speed device */ /** Split transaction position * One of the following values: * - DWC_HCSPLIT_XACTPOS_MID * - DWC_HCSPLIT_XACTPOS_BEGIN * - DWC_HCSPLIT_XACTPOS_END * - DWC_HCSPLIT_XACTPOS_ALL */ uint8_t xact_pos; /** Set when the host channel does a short read. */ uint8_t short_read; /** * Number of requests issued for this channel since it was assigned to * the current transfer (not counting PINGs). */ uint8_t requests; /** * Queue Head for the transfer being processed by this channel. */ struct dwc_otg_qh *qh; /** @} */ /** Entry in list of host channels. */ struct list_head hc_list_entry; } dwc_hc_t; /* * The following parameters may be specified when starting the module. These * parameters define how the DWC_otg controller should be configured. * Parameter values are passed to the CIL initialization function * dwc_otg_cil_init. */ /* Winder: The default value below is for Linux2.6. * The default value for Linux2.4 is in another file "dwc_otg_driver.c". * You could change this values by module params easily. * What I am thinking is to combine the two defaults to one file. */ typedef struct dwc_otg_core_params { int32_t opt; /** The DMA Burst size (applicable only for Internal DMA * Mode). 0, 1, 4, 8 16 (default 0) */ int32_t dma_burst_size; /* Translate this to GAHBCFG values */ /** * Specifies the maximum speed of operation in host and device mode. * The actual speed depends on the speed of the attached device and * the value of phy_type. The actual speed depends on the speed of the * attached device. * 0 - High Speed (default) * 1 - Full Speed */ int32_t speed; /** Total number of 4-byte words in the data FIFO memory. This * memory includes the Rx FIFO, non-periodic Tx FIFO, and periodic * Tx FIFOs. * 32 to 32768 (default 8192) * Note: The total FIFO memory depth in the FPGA configuration is 8192. */ int32_t data_fifo_size; #ifdef DWC_IS_DEVICE /** Number of 4-byte words in the Rx FIFO in device mode when dynamic * FIFO sizing is enabled. * 16 to 32768 (default 1064) */ int32_t dev_rx_fifo_size; /** Number of 4-byte words in the non-periodic Tx FIFO in device mode * when dynamic FIFO sizing is enabled. * 16 to 32768 (default 1024) */ int32_t dev_nperio_tx_fifo_size; /** Number of 4-byte words in each of the periodic Tx FIFOs in device * mode when dynamic FIFO sizing is enabled. * 4 to 768 (default 256) */ uint32_t dev_perio_tx_fifo_size[MAX_PERIO_FIFOS]; /** The number of endpoints in addition to EP0 available for device * mode operations. * 1 to 15 (default 6 IN and OUT) * Note: The FPGA configuration supports a maximum of 6 IN and OUT * endpoints in addition to EP0. */ int32_t dev_endpoints; #endif #ifdef DWC_IS_HOST /** Number of 4-byte words in the Rx FIFO in host mode when dynamic * FIFO sizing is enabled. * 16 to 32768 (default 1024) */ int32_t host_rx_fifo_size; /** Number of 4-byte words in the non-periodic Tx FIFO in host mode * when Dynamic FIFO sizing is enabled in the core. * 16 to 32768 (default 1024) */ int32_t host_nperio_tx_fifo_size; /** Number of 4-byte words in the host periodic Tx FIFO when dynamic * FIFO sizing is enabled. * 16 to 32768 (default 1024) */ int32_t host_perio_tx_fifo_size; /** The number of host channel registers to use. * 1 to 16 (default 12) * Note: The FPGA configuration supports a maximum of 12 host channels. */ int32_t host_channels; #endif /** The maximum transfer size supported in bytes. * 2047 to 65,535 (default 65,535) */ int32_t max_transfer_size; /** The maximum number of packets in a transfer. * 15 to 511 (default 511) */ int32_t max_packet_count; /** * Specifies the UTMI+ Data Width. This parameter is * applicable for a PHY_TYPE of UTMI+ or ULPI. (For a ULPI * PHY_TYPE, this parameter indicates the data width between * the MAC and the ULPI Wrapper.) Also, this parameter is * applicable only if the OTG_HSPHY_WIDTH cC parameter was set * to "8 and 16 bits", meaning that the core has been * configured to work at either data path width. * * 8 or 16 bits (default 16) */ int32_t phy_utmi_width; int32_t turn_around_time_hs; int32_t turn_around_time_fs; int32_t timeout_cal_hs; int32_t timeout_cal_fs; } dwc_otg_core_params_t; #ifdef DEBUG struct dwc_otg_core_if; typedef struct hc_xfer_info { struct dwc_otg_core_if *core_if; dwc_hc_t *hc; } hc_xfer_info_t; #endif /** \ingroup USB_DRIVER_CIL * \brief DWC_otg CIL callback structure. This structure allows the HCD and * PCD to register functions used for starting and stopping the PCD * and HCD for role change on for a DRD. */ typedef struct dwc_otg_cil_callbacks { /** Start function for role change */ int (*start) (void *_p); /** Stop Function for role change */ int (*stop) (void *_p); /** Disconnect Function for role change */ int (*disconnect) (void *_p); /** Suspend function */ int (*suspend) (void *_p); /** Suspend function */ int (*resume_wakeup) (void *_p); /** Session Start (SRP) */ int (*session_start) (void *_p); void *p; } dwc_otg_cil_callbacks_t; /** \ingroup USB_DRIVER_CIL * \brief The dwc_otg_core_if structure contains information needed to manage * the DWC_otg controller acting in either host or device mode. It * represents the programming view of the controller as a whole. */ typedef struct dwc_otg_core_if { /** Parameters that define how the core should be configured.*/ dwc_otg_core_params_t *core_params; /** Core Global registers starting at offset 000h. */ dwc_otg_core_global_regs_t *core_global_regs; #ifdef DWC_IS_DEVICE /** Device-specific information */ dwc_otg_dev_if_t *dev_if; #endif #ifdef DWC_IS_HOST /** Host-specific information */ dwc_otg_host_if_t *host_if; #endif /* * Set to 1 if the core PHY interface bits in USBCFG have been * initialized. */ uint8_t phy_init_done; /* Common configuration information */ /** Power and Clock Gating Control Register */ volatile uint32_t *pcgcctl; #define DWC_OTG_PCGCCTL_OFFSET 0xE00 /** Push/pop addresses for endpoints or host channels.*/ uint32_t *data_fifo[MAX_EPS_CHANNELS]; #define DWC_OTG_DATA_FIFO_OFFSET 0x1000 #define DWC_OTG_DATA_FIFO_SIZE 0x1000 uint32_t *data_fifo_dbg; /** Total RAM for FIFOs (Bytes) */ uint16_t total_fifo_size; /** Size of Rx FIFO (Bytes) */ uint16_t rx_fifo_size; /** Size of Non-periodic Tx FIFO (Bytes) */ uint16_t nperio_tx_fifo_size; /** 1 if DMA is enabled, 0 otherwise. */ //uint8_t dma_enable; /** Set to 1 if multiple packets of a high-bandwidth transfer is in * process of being queued */ #ifdef DWC_IS_HOST uint8_t queuing_high_bandwidth; #endif /** Hardware Configuration -- stored here for convenience.*/ hwcfg1_data_t hwcfg1; hwcfg2_data_t hwcfg2; hwcfg3_data_t hwcfg3; hwcfg4_data_t hwcfg4; /** PCD callbacks */ #ifdef DWC_IS_DEVICE struct dwc_otg_cil_callbacks *pcd_cb; #endif /** HCD callbacks */ #ifdef DWC_IS_HOST struct dwc_otg_cil_callbacks *hcd_cb; #endif #ifdef DEBUG #ifdef DWC_IS_HOST uint32_t start_hcchar_val[MAX_EPS_CHANNELS]; hc_xfer_info_t hc_xfer_info[MAX_EPS_CHANNELS]; struct timer_list hc_xfer_timer[MAX_EPS_CHANNELS]; uint32_t hfnum_7_samples; uint32_t hfnum_7_frrem_accum; uint32_t hfnum_0_samples; uint32_t hfnum_0_frrem_accum; uint32_t hfnum_other_samples; uint32_t hfnum_other_frrem_accum; #endif #endif } dwc_otg_core_if_t; /* * The following functions support initialization of the CIL driver component * and the DWC_otg controller. */ extern dwc_otg_core_if_t *dwc_otg_cil_init(uint32_t *_reg_base_addr, uint32_t *_fifo_base_addr, uint32_t *_fifo_dbg_addr, dwc_otg_core_params_t *_core_params); extern void dwc_otg_cil_remove(dwc_otg_core_if_t *_core_if); extern void dwc_otg_core_init(dwc_otg_core_if_t *_core_if); extern void dwc_otg_core_host_init(dwc_otg_core_if_t *_core_if); extern void dwc_otg_core_dev_init(dwc_otg_core_if_t *_core_if); extern void dwc_otg_enable_global_interrupts( dwc_otg_core_if_t *_core_if ); extern void dwc_otg_disable_global_interrupts( dwc_otg_core_if_t *_core_if ); #if defined(_USB_LED_) extern void dwc_otg_set_usb_led(dwc_otg_core_if_t *_core_if, int is_on); #endif //_USB_LED_ /** \ingroup USB_DRIVER_CIL \defgroup USB_DRIVER_CIL_PCD Core Interface Layer APIs(PCD) \brief The following functions support managing the DWC_otg controller in device mode. */ /** @{ */ /** * \brief This function reads a setup packet from the Rx FIFO into the destination * buffer. This function is called from the Rx Status Queue Level (RxStsQLvl) * Interrupt routine when a SETUP packet has been received in Slave mode. * * \param _core_if Programming view of DWC_otg controller. * \param _dest Destination buffer for packet data. */ extern void dwc_otg_read_setup_packet (dwc_otg_core_if_t *_core_if, uint32_t *_dest); /** * \brief Gets the current USB frame number. This is the frame number from the last * SOF packet. * * \param _core_if Programming view of DWC_otg controller. */ extern uint32_t dwc_otg_get_frame_number(dwc_otg_core_if_t *_core_if); /** * \brief This function enables EP0 OUT to receive SETUP packets and configures EP0 * IN for transmitting packets. It is normally called when the * "Enumeration Done" interrupt occurs. * * \param _core_if Programming view of DWC_otg controller. * \param _ep The EP0 data. */ extern void dwc_otg_ep0_activate(dwc_otg_core_if_t *_core_if, dwc_ep_t *_ep); /** * \brief This function activates an EP. The Device EP control register for * the EP is configured as defined in the ep structure. Note: This * function is not used for EP0. * * \param _core_if Programming view of DWC_otg controller. * \param _ep The EP to activate. */ extern void dwc_otg_ep_activate(dwc_otg_core_if_t *_core_if, dwc_ep_t *_ep); /** * \brief This function deactivates an EP. This is done by clearing the USB Active * EP bit in the Device EP control register. Note: This function is not used * for EP0. EP0 cannot be deactivated. * * \param _core_if Programming view of DWC_otg controller. * \param _ep The EP to deactivate. */ extern void dwc_otg_ep_deactivate(dwc_otg_core_if_t *_core_if, dwc_ep_t *_ep); /** * \brief This function does the setup for a data transfer for an EP and * starts the transfer. For an IN transfer, the packets will be * loaded into the appropriate Tx FIFO in the ISR. For OUT transfers, * the packets are unloaded from the Rx FIFO in the ISR. the ISR. * * \param _core_if Programming view of DWC_otg controller. * \param _ep The EP to start the transfer on. */ extern void dwc_otg_ep_start_transfer(dwc_otg_core_if_t *_core_if, dwc_ep_t *_ep); extern void dwc_otg_ep_start_tx_transfer(dwc_otg_core_if_t *_core_if, dwc_ep_t *_ep, signed char next); extern void dwc_otg_ep_start_rx_transfer(dwc_otg_core_if_t *_core_if, dwc_ep_t *_ep); /** * \brief This function does the setup for a data transfer for EP0 and starts * the transfer. For an IN transfer, the packets will be loaded into * the appropriate Tx FIFO in the ISR. For OUT transfers, the packets are * unloaded from the Rx FIFO in the ISR. * * \param _core_if Programming view of DWC_otg controller. * \param _ep The EP0 data. */ //extern void dwc_otg_ep0_start_transfer(dwc_otg_core_if_t *_core_if, dwc_ep_t *_ep); /** * \brief This function continues control IN transfers started by * dwc_otg_ep0_start_transfer, when the transfer does not fit in a * single packet. NOTE: The DIEPCTL0/DOEPCTL0 registers only have one * bit for the packet count. * * \param _core_if Programming view of DWC_otg controller. * \param _ep The EP0 data. */ //extern void dwc_otg_ep0_continue_transfer(dwc_otg_core_if_t *_core_if, dwc_ep_t *_ep); /** * \brief This function writes a packet into the Tx FIFO associated with the * EP. For non-periodic EPs the non-periodic Tx FIFO is written. For * periodic EPs the periodic Tx FIFO associated with the EP is written * with all packets for the next micro-frame. * * \param _core_if Programming view of DWC_otg controller. * \param _ep The EP to write packet for. */ #ifdef USE_INTERNAL_DMA extern void dwc_otg_ep_write_packet(dwc_otg_core_if_t *_core_if, dwc_ep_t *_ep); #endif /** * \brief Set the EP STALL. * * \param _core_if Programming view of DWC_otg controller. * \param _ep The EP to set the stall on. */ extern void dwc_otg_ep_set_stall(dwc_otg_core_if_t *_core_if, dwc_ep_t *_ep); /** * \brief Clear the EP STALL. * * \param _core_if Programming view of DWC_otg controller. * \param _ep The EP to clear stall from. */ extern void dwc_otg_ep_clear_stall(dwc_otg_core_if_t *_core_if, dwc_ep_t *_ep); extern void dwc_otg_enable_device_interrupts(dwc_otg_core_if_t *_core_if); /** * \brief This functions reads the device registers and prints them * * \param _core_if Programming view of DWC_otg controller. */ extern void dwc_otg_dump_dev_registers(dwc_otg_core_if_t *_core_if); /** * \brief Register PCD callbacks. The callbacks are used to start and stop * the PCD for interrupt processing. * * \param _core_if Programming view of DWC_otg controller. * \param _cb the PCD callback structure. * \param _p pointer to be passed to callback function (pcd*). */ extern void dwc_otg_cil_register_pcd_callbacks( dwc_otg_core_if_t *_core_if, dwc_otg_cil_callbacks_t *_cb, void *_p); /** @} */ /* USB_DRIVER_CIL_PCD */ /** \ingroup USB_DRIVER_CIL \defgroup USB_DRIVER_CIL_HCD Core Interface Layer APIs(HCD) \brief The following functions support managing the DWC_otg controller in host mode. */ /* @{ */ extern void dwc_otg_hc_init(dwc_otg_core_if_t *_core_if, dwc_hc_t *_hc); extern void dwc_otg_hc_halt(dwc_otg_core_if_t *_core_if, dwc_hc_t *_hc, dwc_otg_halt_status_e _halt_status); extern void dwc_otg_hc_cleanup(dwc_otg_core_if_t *_core_if, dwc_hc_t *_hc); extern void dwc_otg_hc_start_transfer(dwc_otg_core_if_t *_core_if, dwc_hc_t *_hc); extern int dwc_otg_hc_continue_transfer(dwc_otg_core_if_t *_core_if, dwc_hc_t *_hc); extern void dwc_otg_hc_do_ping(dwc_otg_core_if_t *_core_if, dwc_hc_t *_hc); extern void dwc_otg_hc_write_packet(dwc_otg_core_if_t *_core_if, dwc_hc_t *_hc); extern void dwc_otg_enable_host_interrupts(dwc_otg_core_if_t *_core_if); extern void dwc_otg_disable_host_interrupts(dwc_otg_core_if_t *_core_if); /* * \brief This function Reads HPRT0 in preparation to modify. It keeps the * WC bits 0 so that if they are read as 1, they won't clear when you * write it back */ #ifdef DWC_IS_HOST static inline uint32_t dwc_otg_read_hprt0(dwc_otg_core_if_t *_core_if) { hprt0_data_t hprt0; hprt0.d32 = dwc_read_reg32(_core_if->host_if->hprt0); hprt0.b.prtena = 0; hprt0.b.prtconndet = 0; hprt0.b.prtenchng = 0; hprt0.b.prtovrcurrchng = 0; return hprt0.d32; } #endif // DWC_IS_HOST /** * This function reads the host registers and prints them * * \param _core_if Programming view of DWC_otg controller. */ #ifdef DWC_IS_HOST extern void dwc_otg_dump_host_registers(dwc_otg_core_if_t *_core_if); #endif // DWC_IS_HOST /** * \brief Register HCD callbacks. The callbacks are used to start and stop * the HCD for interrupt processing. * * \param _core_if Programming view of DWC_otg controller. * \param _cb the HCD callback structure. * \param _p pointer to be passed to callback function (usb_hcd*). */ #ifdef DWC_IS_HOST extern void dwc_otg_cil_register_hcd_callbacks( dwc_otg_core_if_t *_core_if, dwc_otg_cil_callbacks_t *_cb, void *_p); #endif // DWC_IS_HOST /* @} */ /* USB_DRIVER_CIL_HCD */ /** \ingroup USB_DRIVER_CIL \defgroup USB_DRIVER_CIL_COMMON Core Interface Layer APIs(COMMON) \brief The following functions support managing the DWC_otg controller in either device or host mode */ /* @{ */ /** * \brief This function reads a packet from the Rx FIFO into the destination * buffer. To read SETUP data use dwc_otg_read_setup_packet. * * \param core_if Programming view of DWC_otg controller. * \param dest Destination buffer for the packet. * \param bytes Number of bytes to copy to the destination. */ extern void dwc_otg_read_packet(dwc_otg_core_if_t *core_if, uint8_t *dest, uint16_t bytes); /** * \brief This function reads the core global registers and prints them * * \param _core_if Programming view of DWC_otg controller. */ extern void dwc_otg_dump_global_registers(dwc_otg_core_if_t *_core_if); /** * \brief Flush a Tx FIFO. * * \param _core_if Programming view of DWC_otg controller. * \param _num Tx FIFO to flush. */ extern void dwc_otg_flush_tx_fifo( dwc_otg_core_if_t *_core_if, const int _num ); /** * \brief Flush Rx FIFO. * * \param _core_if Programming view of DWC_otg controller. */ extern void dwc_otg_flush_rx_fifo( dwc_otg_core_if_t *_core_if ); /** * \brief Do core a soft reset of the core. Be careful with this because it * resets all the internal state machines of the core. * * \param _core_if Programming view of DWC_otg controller. */ extern int dwc_otg_core_reset( dwc_otg_core_if_t *_core_if ); /* * \brief This function returns the Core Interrupt register. */ static inline uint32_t dwc_otg_read_core_intr(dwc_otg_core_if_t *_core_if) { return (dwc_read_reg32(&_core_if->core_global_regs->gintsts) & dwc_read_reg32(&_core_if->core_global_regs->gintmsk)); } /* * This function returns the OTG Interrupt register. */ static inline uint32_t dwc_otg_read_otg_intr (dwc_otg_core_if_t *_core_if) { return (dwc_read_reg32 (&_core_if->core_global_regs->gotgint)); } #ifdef DWC_IS_DEVICE /** * \brief This function reads the Device All Endpoints Interrupt register and * returns the IN endpoint interrupt bits. */ static inline uint32_t dwc_otg_read_dev_all_in_ep_intr(dwc_otg_core_if_t *_core_if) { uint32_t v; v = dwc_read_reg32(&_core_if->dev_if->dev_global_regs->daint) & dwc_read_reg32(&_core_if->dev_if->dev_global_regs->daintmsk); return (v & 0xffff); } /** * \brief This function reads the Device All Endpoints Interrupt register and * returns the OUT endpoint interrupt bits. */ static inline uint32_t dwc_otg_read_dev_all_out_ep_intr(dwc_otg_core_if_t *_core_if) { uint32_t v; v = dwc_read_reg32(&_core_if->dev_if->dev_global_regs->daint) & dwc_read_reg32(&_core_if->dev_if->dev_global_regs->daintmsk); return ((v & 0xffff0000) >> 16); } /** * \brief This function returns the Device IN EP Interrupt register */ static inline uint32_t dwc_otg_read_dev_in_ep_intr(dwc_otg_core_if_t *_core_if, dwc_ep_t *_ep) { dwc_otg_dev_if_t *dev_if = _core_if->dev_if; uint32_t v; v = dwc_read_reg32(&dev_if->in_ep_regs[_ep->num]->diepint) & dwc_read_reg32(&dev_if->dev_global_regs->diepmsk); return v; } /** * \brief This function returns the Device OUT EP Interrupt register */ static inline uint32_t dwc_otg_read_dev_out_ep_intr(dwc_otg_core_if_t *_core_if, dwc_ep_t *_ep) { dwc_otg_dev_if_t *dev_if = _core_if->dev_if; uint32_t v; v = dwc_read_reg32( &dev_if->out_ep_regs[_ep->num]->doepint) & dwc_read_reg32(&dev_if->dev_global_regs->diepmsk); return v; } #endif /** * \brief This function returns the Host All Channel Interrupt register */ #ifdef DWC_IS_HOST static inline uint32_t dwc_otg_read_host_all_channels_intr (dwc_otg_core_if_t *_core_if) { return (dwc_read_reg32 (&_core_if->host_if->host_global_regs->haint)); } static inline uint32_t dwc_otg_read_host_channel_intr (dwc_otg_core_if_t *_core_if, dwc_hc_t *_hc) { return (dwc_read_reg32 (&_core_if->host_if->hc_regs[_hc->hc_num]->hcint)); } #endif // DWC_IS_HOST /** * \brief This function returns the mode of the operation, host or device. * * @return 0 - Device Mode, 1 - Host Mode */ static inline uint32_t dwc_otg_mode(dwc_otg_core_if_t *_core_if) { return (dwc_read_reg32( &_core_if->core_global_regs->gintsts ) & 0x1); } static inline uint8_t dwc_otg_is_device_mode(dwc_otg_core_if_t *_core_if) { return (dwc_otg_mode(_core_if) != 1); } static inline uint8_t dwc_otg_is_host_mode(dwc_otg_core_if_t *_core_if) { return (dwc_otg_mode(_core_if) == 1); } /** * \brief Common interrupt handler. * * The common interrupts are those that occur in both Host and Device mode. * This handler handles the following interrupts: * - Mode Mismatch Interrupt * - Disconnect Interrupt * - OTG Interrupt * - Connector ID Status Change Interrupt * - Session Request Interrupt. * - Resume / Remote Wakeup Detected Interrupt. */ extern int32_t dwc_otg_handle_common_intr( dwc_otg_core_if_t *_core_if ); extern int restart_din(void); extern int restart_pin(void); extern int restart_cin(void); extern void set_cin_holding(void); extern void clr_cin_holding(void); extern void set_din_holding(void); extern void clr_din_holding(void); extern void set_pin_next(void); extern void clr_pin_next(void); extern void dwc_otg_ep_stop_perio(void); extern void dwc_otg_jump_ep(dwc_otg_core_if_t *_core_if,int from, uint8_t epnum); /* @} */ /* USB_DRIVER_CIL_COMMON */ extern void *usb_alloc_buf(size_t size, int clear); extern void usb_free_buf(void *vaddr); #endif