Merge branch 'feature/sdio_slave' into 'master'

feature(sdio_slave): add support for sdio_slave

See merge request idf/esp-idf!1829
This commit is contained in:
Angus Gratton 2018-05-22 09:43:35 +08:00
commit b8312a26c0
15 changed files with 10404 additions and 0 deletions

View File

@ -0,0 +1,290 @@
// Copyright 2015-2018 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#ifndef _DRIVER_SDIO_SLAVE_H_
#define _DRIVER_SDIO_SLAVE_H_
#include "freertos/FreeRTOS.h"
#include "freertos/portmacro.h"
#include "esp_err.h"
#include "rom/queue.h"
#include "soc/host_reg.h"
#ifdef __cplusplus
extern "C" {
#endif
#define SDIO_SLAVE_RECV_MAX_BUFFER (4096-4)
typedef void(*sdio_event_cb_t)(uint8_t event);
/// Mask of interrupts sending to the host.
typedef enum {
SDIO_SLAVE_HOSTINT_SEND_NEW_PACKET = HOST_SLC0_RX_NEW_PACKET_INT_ENA, ///< New packet available
SDIO_SLAVE_HOSTINT_RECV_OVF = HOST_SLC0_TX_OVF_INT_ENA, ///< Slave receive buffer overflow
SDIO_SLAVE_HOSTINT_SEND_UDF = HOST_SLC0_RX_UDF_INT_ENA, ///< Slave sending buffer underflow (this case only happen when the host do not request for packet according to the packet len).
SDIO_SLAVE_HOSTINT_BIT7 = HOST_SLC0_TOHOST_BIT7_INT_ENA, ///< General purpose interrupt bits that can be used by the user.
SDIO_SLAVE_HOSTINT_BIT6 = HOST_SLC0_TOHOST_BIT6_INT_ENA,
SDIO_SLAVE_HOSTINT_BIT5 = HOST_SLC0_TOHOST_BIT5_INT_ENA,
SDIO_SLAVE_HOSTINT_BIT4 = HOST_SLC0_TOHOST_BIT4_INT_ENA,
SDIO_SLAVE_HOSTINT_BIT3 = HOST_SLC0_TOHOST_BIT3_INT_ENA,
SDIO_SLAVE_HOSTINT_BIT2 = HOST_SLC0_TOHOST_BIT2_INT_ENA,
SDIO_SLAVE_HOSTINT_BIT1 = HOST_SLC0_TOHOST_BIT1_INT_ENA,
SDIO_SLAVE_HOSTINT_BIT0 = HOST_SLC0_TOHOST_BIT0_INT_ENA,
} sdio_slave_hostint_t;
/// Timing of SDIO slave
typedef enum {
SDIO_SLAVE_TIMING_NSEND_PSAMPLE = 0,///< Send at negedge, and sample at posedge. Default value for SD protocol.
SDIO_SLAVE_TIMING_NSEND_NSAMPLE, ///< Send at negedge, and sample at negedge
SDIO_SLAVE_TIMING_PSEND_PSAMPLE, ///< Send at posedge, and sample at posedge
SDIO_SLAVE_TIMING_PSEND_NSAMPLE, ///< Send at posedge, and sample at negedge
} sdio_slave_timing_t;
/// Configuration of SDIO slave mode
typedef enum {
SDIO_SLAVE_SEND_STREAM = 0, ///< Stream mode, all packets to send will be combined as one if possible
SDIO_SLAVE_SEND_PACKET = 1, ///< Packet mode, one packets will be sent one after another (only increase packet_len if last packet sent).
} sdio_slave_sending_mode_t;
/// Configuration of SDIO slave
typedef struct {
sdio_slave_timing_t timing; ///< timing of sdio_slave. see `sdio_slave_timing_t`.
sdio_slave_sending_mode_t sending_mode; ///< mode of sdio_slave. `SDIO_SLAVE_MODE_STREAM` if the data needs to be sent as much as possible; `SDIO_SLAVE_MODE_PACKET` if the data should be sent in packets.
int send_queue_size; ///< max buffers that can be queued before sending.
size_t recv_buffer_size;
///< If buffer_size is too small, it costs more CPU time to handle larger number of buffers.
///< If buffer_size is too large, the space larger than the transaction length is left blank but still counts a buffer, and the buffers are easily run out.
///< Should be set according to length of data really transferred.
///< All data that do not fully fill a buffer is still counted as one buffer. E.g. 10 bytes data costs 2 buffers if the size is 8 bytes per buffer.
///< Buffer size of the slave pre-defined between host and slave before communication. All receive buffer given to the driver should be larger than this.
sdio_event_cb_t event_cb; ///< when the host interrupts slave, this callback will be called with interrupt number (0-7).
} sdio_slave_config_t;
/** Handle of a receive buffer, register a handle by calling ``sdio_slave_recv_register_buf``. Use the handle to load the buffer to the
* driver, or call ``sdio_slave_recv_unregister_buf`` if it is no longer used.
*/
typedef void *sdio_slave_buf_handle_t;
/** Initialize the sdio slave driver
*
* @param config Configuration of the sdio slave driver.
*
* @return
* - ESP_ERR_NOT_FOUND if no free interrupt found.
* - ESP_ERR_INVALID_STATE if already initialized.
* - ESP_ERR_NO_MEM if fail due to memory allocation failed.
* - ESP_OK if success
*/
esp_err_t sdio_slave_initialize(sdio_slave_config_t *config);
/** De-initialize the sdio slave driver to release the resources.
*/
void sdio_slave_deinit();
/** Start hardware for sending and receiving, as well as set the IOREADY1 to 1.
*
* @note The driver will continue sending from previous data and PKT_LEN counting, keep data received as well as start receiving from current TOKEN1 counting.
* See ``sdio_slave_reset``.
*
* @return
* - ESP_ERR_INVALID_STATE if already started.
* - ESP_OK otherwise.
*/
esp_err_t sdio_slave_start();
/** Stop hardware from sending and receiving, also set IOREADY1 to 0.
*
* @note this will not clear the data already in the driver, and also not reset the PKT_LEN and TOKEN1 counting. Call ``sdio_slave_reset`` to do that.
*/
void sdio_slave_stop();
/** Clear the data still in the driver, as well as reset the PKT_LEN and TOKEN1 counting.
*
* @return always return ESP_OK.
*/
esp_err_t sdio_slave_reset();
/*---------------------------------------------------------------------------
* Receive
*--------------------------------------------------------------------------*/
/** Register buffer used for receiving. All buffers should be registered before used, and then can be used (again) in the driver by the handle returned.
*
* @param start The start address of the buffer.
*
* @note The driver will use and only use the amount of space specified in the `recv_buffer_size` member set in the `sdio_slave_config_t`.
* All buffers should be larger than that. The buffer is used by the DMA, so it should be DMA capable and 32-bit aligned.
*
* @return The buffer handle if success, otherwise NULL.
*/
sdio_slave_buf_handle_t sdio_slave_recv_register_buf(uint8_t *start);
/** Unregister buffer from driver, and free the space used by the descriptor pointing to the buffer.
*
* @param handle Handle to the buffer to release.
*
* @return ESP_OK if success, ESP_ERR_INVALID_ARG if the handle is NULL or the buffer is being used.
*/
esp_err_t sdio_slave_recv_unregister_buf(sdio_slave_buf_handle_t handle);
/** Load buffer to the queue waiting to receive data. The driver takes ownership of the buffer until the buffer is returned by
* ``sdio_slave_send_get_finished`` after the transaction is finished.
*
* @param handle Handle to the buffer ready to receive data.
*
* @return
* - ESP_ERR_INVALID_ARG if invalid handle or the buffer is already in the queue. Only after the buffer is returened by
* ``sdio_slave_recv`` can you load it again.
* - ESP_OK if success
*/
esp_err_t sdio_slave_recv_load_buf(sdio_slave_buf_handle_t handle);
/** Get received data if exist. The driver returns the ownership of the buffer to the app.
*
* @param handle_ret Handle to the buffer holding received data. Use this handle in ``sdio_slave_recv_load_buf`` to receive in the same buffer again.
* @param start_o Start address output, set to NULL if not needed.
* @param len_o Actual length of the data in the buffer, set to NULL if not needed.
* @param wait Time to wait before data received.
*
* @note Call ``sdio_slave_load_buf`` with the handle to re-load the buffer onto the link list, and receive with the same buffer again.
* The address and length of the buffer got here is the same as got from `sdio_slave_get_buffer`.
*
* @return
* - ESP_ERR_INVALID_ARG if handle_ret is NULL
* - ESP_ERR_TIMEOUT if timeout before receiving new data
* - ESP_OK if success
*/
esp_err_t sdio_slave_recv(sdio_slave_buf_handle_t* handle_ret, uint8_t **start_o, size_t *len_o, TickType_t wait);
/** Retrieve the buffer corresponding to a handle.
*
* @param handle Handle to get the buffer.
* @param len_o Output of buffer length
*
* @return buffer address if success, otherwise NULL.
*/
uint8_t* sdio_slave_recv_get_buf( sdio_slave_buf_handle_t handle, size_t *len_o);
/*---------------------------------------------------------------------------
* Send
*--------------------------------------------------------------------------*/
/** Put a new sending transfer into the send queue. The driver takes ownership of the buffer until the buffer is returned by
* ``sdio_slave_send_get_finished`` after the transaction is finished.
*
* @param addr Address for data to be sent. The buffer should be DMA capable and 32-bit aligned.
* @param len Length of the data, should not be longer than 4092 bytes (may support longer in the future).
* @param arg Argument to returned in ``sdio_slave_send_get_finished``. The argument can be used to indicate which transaction is done,
* or as a parameter for a callback. Set to NULL if not needed.
* @param wait Time to wait if the buffer is full.
*
* @return
* - ESP_ERR_INVALID_ARG if the length is not greater than 0.
* - ESP_ERR_TIMEOUT if the queue is still full until timeout.
* - ESP_OK if success.
*/
esp_err_t sdio_slave_send_queue(uint8_t* addr, size_t len, void* arg, TickType_t wait);
/** Return the ownership of a finished transaction.
* @param arg_o Argument of the finished transaction.
* @param wait Time to wait if there's no finished sending transaction.
*
* @return ESP_ERR_TIMEOUT if no transaction finished, or ESP_OK if succeed.
*/
esp_err_t sdio_slave_send_get_finished(void** arg_o, TickType_t wait);
/** Start a new sending transfer, and wait for it (blocked) to be finished.
*
* @param addr Start address of the buffer to send
* @param len Length of buffer to send.
*
* @return
* - ESP_ERR_INVALID_ARG if the length of descriptor is not greater than 0.
* - ESP_ERR_TIMEOUT if the queue is full or host do not start a transfer before timeout.
* - ESP_OK if success.
*/
esp_err_t sdio_slave_transmit(uint8_t* addr, size_t len);
/*---------------------------------------------------------------------------
* Host
*--------------------------------------------------------------------------*/
/** Read the spi slave register shared with host.
*
* @param pos register address, 0-27 or 32-63.
*
* @note register 28 to 31 are reserved for interrupt vector.
*
* @return value of the register.
*/
uint8_t sdio_slave_read_reg(int pos);
/** Write the spi slave register shared with host.
*
* @param pos register address, 0-11, 14-15, 18-19, 24-27 and 32-63, other address are reserved.
* @param reg the value to write.
*
* @note register 29 and 31 are used for interrupt vector.
*
* @return ESP_ERR_INVALID_ARG if address wrong, otherwise ESP_OK.
*/
esp_err_t sdio_slave_write_reg(int pos, uint8_t reg);
/** Get the interrupt enable for host.
*
* @return the interrupt mask.
*/
sdio_slave_hostint_t sdio_slave_get_host_intena();
/** Set the interrupt enable for host.
*
* @param ena Enable mask for host interrupt.
*/
void sdio_slave_set_host_intena(sdio_slave_hostint_t ena);
/** Interrupt the host by general purpose interrupt.
*
* @param pos Interrupt num, 0-7.
*
* @return
* - ESP_ERR_INVALID_ARG if interrupt num error
* - ESP_OK otherwise
*/
esp_err_t sdio_slave_send_host_int( uint8_t pos );
/** Clear general purpose interrupt to host.
*
* @param mask Interrupt bits to clear, by bit mask.
*/
void sdio_slave_clear_host_int(uint8_t mask);
/** Wait for general purpose interrupt from host.
*
* @param pos Interrupt source number to wait for.
* is set.
* @param wait Time to wait before interrupt triggered.
*
* @note this clears the interrupt at the same time.
*
* @return ESP_OK if success, ESP_ERR_TIMEOUT if timeout.
*/
esp_err_t sdio_slave_wait_int(int pos, TickType_t wait);
#ifdef __cplusplus
}
#endif
#endif /*_DRIVER_SDIO_SLAVE_H */

File diff suppressed because it is too large Load Diff

View File

@ -6,14 +6,17 @@ PROVIDE ( SIGMADELTA = 0x3ff44f00 );
PROVIDE ( RTCCNTL = 0x3ff48000 );
PROVIDE ( RTCIO = 0x3ff48400 );
PROVIDE ( SENS = 0x3ff48800 );
PROVIDE ( HINF = 0x3ff4B000 );
PROVIDE ( UHCI1 = 0x3ff4C000 );
PROVIDE ( I2S0 = 0x3ff4F000 );
PROVIDE ( UART1 = 0x3ff50000 );
PROVIDE ( I2C0 = 0x3ff53000 );
PROVIDE ( UHCI0 = 0x3ff54000 );
PROVIDE ( HOST = 0x3ff55000 );
PROVIDE ( RMT = 0x3ff56000 );
PROVIDE ( RMTMEM = 0x3ff56800 );
PROVIDE ( PCNT = 0x3ff57000 );
PROVIDE ( SLC = 0x3ff58000 );
PROVIDE ( LEDC = 0x3ff59000 );
PROVIDE ( MCPWM0 = 0x3ff5E000 );
PROVIDE ( TIMERG0 = 0x3ff5F000 );

View File

@ -0,0 +1,248 @@
// Copyright 2015-2018 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#ifndef _SOC_HINF_REG_H_
#define _SOC_HINF_REG_H_
#include "soc.h"
#define HINF_CFG_DATA0_REG (DR_REG_HINF_BASE + 0x0)
/* HINF_DEVICE_ID_FN1 : R/W ;bitpos:[31:16] ;default: 16'h2222 ; */
/*description: */
#define HINF_DEVICE_ID_FN1 0x0000FFFF
#define HINF_DEVICE_ID_FN1_M ((HINF_DEVICE_ID_FN1_V)<<(HINF_DEVICE_ID_FN1_S))
#define HINF_DEVICE_ID_FN1_V 0xFFFF
#define HINF_DEVICE_ID_FN1_S 16
/* HINF_USER_ID_FN1 : R/W ;bitpos:[15:0] ;default: 16'h6666 ; */
/*description: */
#define HINF_USER_ID_FN1 0x0000FFFF
#define HINF_USER_ID_FN1_M ((HINF_USER_ID_FN1_V)<<(HINF_USER_ID_FN1_S))
#define HINF_USER_ID_FN1_V 0xFFFF
#define HINF_USER_ID_FN1_S 0
#define HINF_CFG_DATA1_REG (DR_REG_HINF_BASE + 0x4)
/* HINF_SDIO20_CONF1 : R/W ;bitpos:[31:29] ;default: 3'h0 ; */
/*description: */
#define HINF_SDIO20_CONF1 0x00000007
#define HINF_SDIO20_CONF1_M ((HINF_SDIO20_CONF1_V)<<(HINF_SDIO20_CONF1_S))
#define HINF_SDIO20_CONF1_V 0x7
#define HINF_SDIO20_CONF1_S 29
/* HINF_FUNC2_EPS : RO ;bitpos:[28] ;default: 1'b0 ; */
/*description: */
#define HINF_FUNC2_EPS (BIT(28))
#define HINF_FUNC2_EPS_M (BIT(28))
#define HINF_FUNC2_EPS_V 0x1
#define HINF_FUNC2_EPS_S 28
/* HINF_SDIO_VER : R/W ;bitpos:[27:16] ;default: 12'h111 ; */
/*description: */
#define HINF_SDIO_VER 0x00000FFF
#define HINF_SDIO_VER_M ((HINF_SDIO_VER_V)<<(HINF_SDIO_VER_S))
#define HINF_SDIO_VER_V 0xFFF
#define HINF_SDIO_VER_S 16
/* HINF_SDIO20_CONF0 : R/W ;bitpos:[15:12] ;default: 4'b0 ; */
/*description: */
#define HINF_SDIO20_CONF0 0x0000000F
#define HINF_SDIO20_CONF0_M ((HINF_SDIO20_CONF0_V)<<(HINF_SDIO20_CONF0_S))
#define HINF_SDIO20_CONF0_V 0xF
#define HINF_SDIO20_CONF0_S 12
/* HINF_IOENABLE1 : RO ;bitpos:[11] ;default: 1'b0 ; */
/*description: */
#define HINF_IOENABLE1 (BIT(11))
#define HINF_IOENABLE1_M (BIT(11))
#define HINF_IOENABLE1_V 0x1
#define HINF_IOENABLE1_S 11
/* HINF_EMP : RO ;bitpos:[10] ;default: 1'b0 ; */
/*description: */
#define HINF_EMP (BIT(10))
#define HINF_EMP_M (BIT(10))
#define HINF_EMP_V 0x1
#define HINF_EMP_S 10
/* HINF_FUNC1_EPS : RO ;bitpos:[9] ;default: 1'b0 ; */
/*description: */
#define HINF_FUNC1_EPS (BIT(9))
#define HINF_FUNC1_EPS_M (BIT(9))
#define HINF_FUNC1_EPS_V 0x1
#define HINF_FUNC1_EPS_S 9
/* HINF_CD_DISABLE : RO ;bitpos:[8] ;default: 1'b0 ; */
/*description: */
#define HINF_CD_DISABLE (BIT(8))
#define HINF_CD_DISABLE_M (BIT(8))
#define HINF_CD_DISABLE_V 0x1
#define HINF_CD_DISABLE_S 8
/* HINF_IOENABLE2 : RO ;bitpos:[7] ;default: 1'b0 ; */
/*description: */
#define HINF_IOENABLE2 (BIT(7))
#define HINF_IOENABLE2_M (BIT(7))
#define HINF_IOENABLE2_V 0x1
#define HINF_IOENABLE2_S 7
/* HINF_SDIO_INT_MASK : R/W ;bitpos:[6] ;default: 1'b0 ; */
/*description: */
#define HINF_SDIO_INT_MASK (BIT(6))
#define HINF_SDIO_INT_MASK_M (BIT(6))
#define HINF_SDIO_INT_MASK_V 0x1
#define HINF_SDIO_INT_MASK_S 6
/* HINF_SDIO_IOREADY2 : R/W ;bitpos:[5] ;default: 1'b0 ; */
/*description: */
#define HINF_SDIO_IOREADY2 (BIT(5))
#define HINF_SDIO_IOREADY2_M (BIT(5))
#define HINF_SDIO_IOREADY2_V 0x1
#define HINF_SDIO_IOREADY2_S 5
/* HINF_SDIO_CD_ENABLE : R/W ;bitpos:[4] ;default: 1'b1 ; */
/*description: */
#define HINF_SDIO_CD_ENABLE (BIT(4))
#define HINF_SDIO_CD_ENABLE_M (BIT(4))
#define HINF_SDIO_CD_ENABLE_V 0x1
#define HINF_SDIO_CD_ENABLE_S 4
/* HINF_HIGHSPEED_MODE : RO ;bitpos:[3] ;default: 1'b0 ; */
/*description: */
#define HINF_HIGHSPEED_MODE (BIT(3))
#define HINF_HIGHSPEED_MODE_M (BIT(3))
#define HINF_HIGHSPEED_MODE_V 0x1
#define HINF_HIGHSPEED_MODE_S 3
/* HINF_HIGHSPEED_ENABLE : R/W ;bitpos:[2] ;default: 1'b0 ; */
/*description: */
#define HINF_HIGHSPEED_ENABLE (BIT(2))
#define HINF_HIGHSPEED_ENABLE_M (BIT(2))
#define HINF_HIGHSPEED_ENABLE_V 0x1
#define HINF_HIGHSPEED_ENABLE_S 2
/* HINF_SDIO_IOREADY1 : R/W ;bitpos:[1] ;default: 1'b0 ; */
/*description: */
#define HINF_SDIO_IOREADY1 (BIT(1))
#define HINF_SDIO_IOREADY1_M (BIT(1))
#define HINF_SDIO_IOREADY1_V 0x1
#define HINF_SDIO_IOREADY1_S 1
/* HINF_SDIO_ENABLE : R/W ;bitpos:[0] ;default: 1'b1 ; */
/*description: */
#define HINF_SDIO_ENABLE (BIT(0))
#define HINF_SDIO_ENABLE_M (BIT(0))
#define HINF_SDIO_ENABLE_V 0x1
#define HINF_SDIO_ENABLE_S 0
#define HINF_CFG_DATA7_REG (DR_REG_HINF_BASE + 0x1C)
/* HINF_SDIO_IOREADY0 : R/W ;bitpos:[17] ;default: 1'b1 ; */
/*description: */
#define HINF_SDIO_IOREADY0 (BIT(17))
#define HINF_SDIO_IOREADY0_M (BIT(17))
#define HINF_SDIO_IOREADY0_V 0x1
#define HINF_SDIO_IOREADY0_S 17
/* HINF_SDIO_RST : R/W ;bitpos:[16] ;default: 1'b0 ; */
/*description: */
#define HINF_SDIO_RST (BIT(16))
#define HINF_SDIO_RST_M (BIT(16))
#define HINF_SDIO_RST_V 0x1
#define HINF_SDIO_RST_S 16
/* HINF_CHIP_STATE : R/W ;bitpos:[15:8] ;default: 8'b0 ; */
/*description: */
#define HINF_CHIP_STATE 0x000000FF
#define HINF_CHIP_STATE_M ((HINF_CHIP_STATE_V)<<(HINF_CHIP_STATE_S))
#define HINF_CHIP_STATE_V 0xFF
#define HINF_CHIP_STATE_S 8
/* HINF_PIN_STATE : R/W ;bitpos:[7:0] ;default: 8'b0 ; */
/*description: */
#define HINF_PIN_STATE 0x000000FF
#define HINF_PIN_STATE_M ((HINF_PIN_STATE_V)<<(HINF_PIN_STATE_S))
#define HINF_PIN_STATE_V 0xFF
#define HINF_PIN_STATE_S 0
#define HINF_CIS_CONF0_REG (DR_REG_HINF_BASE + 0x20)
/* HINF_CIS_CONF_W0 : R/W ;bitpos:[31:0] ;default: 32'hffffffff ; */
/*description: */
#define HINF_CIS_CONF_W0 0xFFFFFFFF
#define HINF_CIS_CONF_W0_M ((HINF_CIS_CONF_W0_V)<<(HINF_CIS_CONF_W0_S))
#define HINF_CIS_CONF_W0_V 0xFFFFFFFF
#define HINF_CIS_CONF_W0_S 0
#define HINF_CIS_CONF1_REG (DR_REG_HINF_BASE + 0x24)
/* HINF_CIS_CONF_W1 : R/W ;bitpos:[31:0] ;default: 32'hffffffff ; */
/*description: */
#define HINF_CIS_CONF_W1 0xFFFFFFFF
#define HINF_CIS_CONF_W1_M ((HINF_CIS_CONF_W1_V)<<(HINF_CIS_CONF_W1_S))
#define HINF_CIS_CONF_W1_V 0xFFFFFFFF
#define HINF_CIS_CONF_W1_S 0
#define HINF_CIS_CONF2_REG (DR_REG_HINF_BASE + 0x28)
/* HINF_CIS_CONF_W2 : R/W ;bitpos:[31:0] ;default: 32'hffffffff ; */
/*description: */
#define HINF_CIS_CONF_W2 0xFFFFFFFF
#define HINF_CIS_CONF_W2_M ((HINF_CIS_CONF_W2_V)<<(HINF_CIS_CONF_W2_S))
#define HINF_CIS_CONF_W2_V 0xFFFFFFFF
#define HINF_CIS_CONF_W2_S 0
#define HINF_CIS_CONF3_REG (DR_REG_HINF_BASE + 0x2C)
/* HINF_CIS_CONF_W3 : R/W ;bitpos:[31:0] ;default: 32'hffffffff ; */
/*description: */
#define HINF_CIS_CONF_W3 0xFFFFFFFF
#define HINF_CIS_CONF_W3_M ((HINF_CIS_CONF_W3_V)<<(HINF_CIS_CONF_W3_S))
#define HINF_CIS_CONF_W3_V 0xFFFFFFFF
#define HINF_CIS_CONF_W3_S 0
#define HINF_CIS_CONF4_REG (DR_REG_HINF_BASE + 0x30)
/* HINF_CIS_CONF_W4 : R/W ;bitpos:[31:0] ;default: 32'hffffffff ; */
/*description: */
#define HINF_CIS_CONF_W4 0xFFFFFFFF
#define HINF_CIS_CONF_W4_M ((HINF_CIS_CONF_W4_V)<<(HINF_CIS_CONF_W4_S))
#define HINF_CIS_CONF_W4_V 0xFFFFFFFF
#define HINF_CIS_CONF_W4_S 0
#define HINF_CIS_CONF5_REG (DR_REG_HINF_BASE + 0x34)
/* HINF_CIS_CONF_W5 : R/W ;bitpos:[31:0] ;default: 32'hffffffff ; */
/*description: */
#define HINF_CIS_CONF_W5 0xFFFFFFFF
#define HINF_CIS_CONF_W5_M ((HINF_CIS_CONF_W5_V)<<(HINF_CIS_CONF_W5_S))
#define HINF_CIS_CONF_W5_V 0xFFFFFFFF
#define HINF_CIS_CONF_W5_S 0
#define HINF_CIS_CONF6_REG (DR_REG_HINF_BASE + 0x38)
/* HINF_CIS_CONF_W6 : R/W ;bitpos:[31:0] ;default: 32'hffffffff ; */
/*description: */
#define HINF_CIS_CONF_W6 0xFFFFFFFF
#define HINF_CIS_CONF_W6_M ((HINF_CIS_CONF_W6_V)<<(HINF_CIS_CONF_W6_S))
#define HINF_CIS_CONF_W6_V 0xFFFFFFFF
#define HINF_CIS_CONF_W6_S 0
#define HINF_CIS_CONF7_REG (DR_REG_HINF_BASE + 0x3C)
/* HINF_CIS_CONF_W7 : R/W ;bitpos:[31:0] ;default: 32'hffffffff ; */
/*description: */
#define HINF_CIS_CONF_W7 0xFFFFFFFF
#define HINF_CIS_CONF_W7_M ((HINF_CIS_CONF_W7_V)<<(HINF_CIS_CONF_W7_S))
#define HINF_CIS_CONF_W7_V 0xFFFFFFFF
#define HINF_CIS_CONF_W7_S 0
#define HINF_CFG_DATA16_REG (DR_REG_HINF_BASE + 0x40)
/* HINF_DEVICE_ID_FN2 : R/W ;bitpos:[31:16] ;default: 16'h3333 ; */
/*description: */
#define HINF_DEVICE_ID_FN2 0x0000FFFF
#define HINF_DEVICE_ID_FN2_M ((HINF_DEVICE_ID_FN2_V)<<(HINF_DEVICE_ID_FN2_S))
#define HINF_DEVICE_ID_FN2_V 0xFFFF
#define HINF_DEVICE_ID_FN2_S 16
/* HINF_USER_ID_FN2 : R/W ;bitpos:[15:0] ;default: 16'h6666 ; */
/*description: */
#define HINF_USER_ID_FN2 0x0000FFFF
#define HINF_USER_ID_FN2_M ((HINF_USER_ID_FN2_V)<<(HINF_USER_ID_FN2_S))
#define HINF_USER_ID_FN2_V 0xFFFF
#define HINF_USER_ID_FN2_S 0
#define HINF_DATE_REG (DR_REG_HINF_BASE + 0xFC)
/* HINF_SDIO_DATE : R/W ;bitpos:[31:0] ;default: 32'h15030200 ; */
/*description: */
#define HINF_SDIO_DATE 0xFFFFFFFF
#define HINF_SDIO_DATE_M ((HINF_SDIO_DATE_V)<<(HINF_SDIO_DATE_S))
#define HINF_SDIO_DATE_V 0xFFFFFFFF
#define HINF_SDIO_DATE_S 0
#endif /*_SOC_HINF_REG_H_ */

View File

@ -0,0 +1,134 @@
// Copyright 2015-2018 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#ifndef _SOC_HINF_STRUCT_H_
#define _SOC_HINF_STRUCT_H_
#ifdef __cplusplus
extern "C" {
#endif
typedef volatile struct {
union {
struct {
uint32_t user_id_fn1: 16;
uint32_t device_id_fn1:16;
};
uint32_t val;
} cfg_data0;
union {
struct {
uint32_t sdio_enable: 1;
uint32_t sdio_ioready1: 1;
uint32_t highspeed_enable: 1;
uint32_t highspeed_mode: 1;
uint32_t sdio_cd_enable: 1;
uint32_t sdio_ioready2: 1;
uint32_t sdio_int_mask: 1;
uint32_t ioenable2: 1;
uint32_t cd_disable: 1;
uint32_t func1_eps: 1;
uint32_t emp: 1;
uint32_t ioenable1: 1;
uint32_t sdio20_conf0: 4;
uint32_t sdio_ver: 12;
uint32_t func2_eps: 1;
uint32_t sdio20_conf1: 3;
};
uint32_t val;
} cfg_data1;
uint32_t reserved_8;
uint32_t reserved_c;
uint32_t reserved_10;
uint32_t reserved_14;
uint32_t reserved_18;
union {
struct {
uint32_t pin_state: 8;
uint32_t chip_state: 8;
uint32_t sdio_rst: 1;
uint32_t sdio_ioready0: 1;
uint32_t reserved18: 14;
};
uint32_t val;
} cfg_data7;
uint32_t cis_conf0; /**/
uint32_t cis_conf1; /**/
uint32_t cis_conf2; /**/
uint32_t cis_conf3; /**/
uint32_t cis_conf4; /**/
uint32_t cis_conf5; /**/
uint32_t cis_conf6; /**/
uint32_t cis_conf7; /**/
union {
struct {
uint32_t user_id_fn2: 16;
uint32_t device_id_fn2:16;
};
uint32_t val;
} cfg_data16;
uint32_t reserved_44;
uint32_t reserved_48;
uint32_t reserved_4c;
uint32_t reserved_50;
uint32_t reserved_54;
uint32_t reserved_58;
uint32_t reserved_5c;
uint32_t reserved_60;
uint32_t reserved_64;
uint32_t reserved_68;
uint32_t reserved_6c;
uint32_t reserved_70;
uint32_t reserved_74;
uint32_t reserved_78;
uint32_t reserved_7c;
uint32_t reserved_80;
uint32_t reserved_84;
uint32_t reserved_88;
uint32_t reserved_8c;
uint32_t reserved_90;
uint32_t reserved_94;
uint32_t reserved_98;
uint32_t reserved_9c;
uint32_t reserved_a0;
uint32_t reserved_a4;
uint32_t reserved_a8;
uint32_t reserved_ac;
uint32_t reserved_b0;
uint32_t reserved_b4;
uint32_t reserved_b8;
uint32_t reserved_bc;
uint32_t reserved_c0;
uint32_t reserved_c4;
uint32_t reserved_c8;
uint32_t reserved_cc;
uint32_t reserved_d0;
uint32_t reserved_d4;
uint32_t reserved_d8;
uint32_t reserved_dc;
uint32_t reserved_e0;
uint32_t reserved_e4;
uint32_t reserved_e8;
uint32_t reserved_ec;
uint32_t reserved_f0;
uint32_t reserved_f4;
uint32_t reserved_f8;
uint32_t date; /**/
} hinf_dev_t;
extern hinf_dev_t HINF;
#ifdef __cplusplus
}
#endif
#endif /* _SOC_HINF_STRUCT_H_ */

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,891 @@
// Copyright 2015-2018 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#ifndef _SOC_HOST_STRUCT_H_
#define _SOC_HOST_STRUCT_H_
#ifdef __cplusplus
extern "C" {
#endif
typedef volatile struct {
uint32_t reserved_0;
uint32_t reserved_4;
uint32_t reserved_8;
uint32_t reserved_c;
union {
struct {
uint32_t reserved0: 24;
uint32_t func2_int: 1;
uint32_t reserved25: 7;
};
uint32_t val;
} func2_0;
union {
struct {
uint32_t func2_int_en: 1;
uint32_t reserved1: 31;
};
uint32_t val;
} func2_1;
uint32_t reserved_18;
uint32_t reserved_1c;
union {
struct {
uint32_t func1_mdstat: 1;
uint32_t reserved1: 31;
};
uint32_t val;
} func2_2;
uint32_t reserved_24;
uint32_t reserved_28;
uint32_t reserved_2c;
uint32_t reserved_30;
uint32_t gpio_status0; /**/
union {
struct {
uint32_t sdio_int1: 8;
uint32_t reserved8: 24;
};
uint32_t val;
} gpio_status1;
uint32_t gpio_in0; /**/
union {
struct {
uint32_t sdio_in1: 8;
uint32_t reserved8: 24;
};
uint32_t val;
} gpio_in1;
union {
struct {
uint32_t token0: 12;
uint32_t rx_pf_valid: 1;
uint32_t reserved13: 3;
uint32_t reg_token1: 12;
uint32_t rx_pf_eof: 4;
};
uint32_t val;
} slc0_token_rdata;
uint32_t slc0_pf; /**/
uint32_t slc1_pf; /**/
union {
struct {
uint32_t tohost_bit0: 1;
uint32_t tohost_bit1: 1;
uint32_t tohost_bit2: 1;
uint32_t tohost_bit3: 1;
uint32_t tohost_bit4: 1;
uint32_t tohost_bit5: 1;
uint32_t tohost_bit6: 1;
uint32_t tohost_bit7: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t token0_0to1: 1;
uint32_t token1_0to1: 1;
uint32_t rx_sof: 1;
uint32_t rx_eof: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t rx_pf_valid: 1;
uint32_t ext_bit0: 1;
uint32_t ext_bit1: 1;
uint32_t ext_bit2: 1;
uint32_t ext_bit3: 1;
uint32_t rx_new_packet: 1;
uint32_t rd_retry: 1;
uint32_t gpio_sdio: 1;
uint32_t reserved26: 6;
};
uint32_t val;
} slc0_int_raw;
union {
struct {
uint32_t tohost_bit0: 1;
uint32_t tohost_bit1: 1;
uint32_t tohost_bit2: 1;
uint32_t tohost_bit3: 1;
uint32_t tohost_bit4: 1;
uint32_t tohost_bit5: 1;
uint32_t tohost_bit6: 1;
uint32_t tohost_bit7: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t token0_0to1: 1;
uint32_t token1_0to1: 1;
uint32_t rx_sof: 1;
uint32_t rx_eof: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t rx_pf_valid: 1;
uint32_t ext_bit0: 1;
uint32_t ext_bit1: 1;
uint32_t ext_bit2: 1;
uint32_t ext_bit3: 1;
uint32_t wifi_rx_new_packet: 1;
uint32_t rd_retry: 1;
uint32_t bt_rx_new_packet: 1;
uint32_t reserved26: 6;
};
uint32_t val;
} slc1_int_raw;
union {
struct {
uint32_t tohost_bit0: 1;
uint32_t tohost_bit1: 1;
uint32_t tohost_bit2: 1;
uint32_t tohost_bit3: 1;
uint32_t tohost_bit4: 1;
uint32_t tohost_bit5: 1;
uint32_t tohost_bit6: 1;
uint32_t tohost_bit7: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t token0_0to1: 1;
uint32_t token1_0to1: 1;
uint32_t rx_sof: 1;
uint32_t rx_eof: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t rx_pf_valid: 1;
uint32_t ext_bit0: 1;
uint32_t ext_bit1: 1;
uint32_t ext_bit2: 1;
uint32_t ext_bit3: 1;
uint32_t rx_new_packet: 1;
uint32_t rd_retry: 1;
uint32_t gpio_sdio: 1;
uint32_t reserved26: 6;
};
uint32_t val;
} slc0_int_st;
union {
struct {
uint32_t tohost_bit0: 1;
uint32_t tohost_bit1: 1;
uint32_t tohost_bit2: 1;
uint32_t tohost_bit3: 1;
uint32_t tohost_bit4: 1;
uint32_t tohost_bit5: 1;
uint32_t tohost_bit6: 1;
uint32_t tohost_bit7: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t token0_0to1: 1;
uint32_t token1_0to1: 1;
uint32_t rx_sof: 1;
uint32_t rx_eof: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t rx_pf_valid: 1;
uint32_t ext_bit0: 1;
uint32_t ext_bit1: 1;
uint32_t ext_bit2: 1;
uint32_t ext_bit3: 1;
uint32_t wifi_rx_new_packet: 1;
uint32_t rd_retry: 1;
uint32_t bt_rx_new_packet: 1;
uint32_t reserved26: 6;
};
uint32_t val;
} slc1_int_st;
union {
struct {
uint32_t reg_slc0_len: 20;
uint32_t reg_slc0_len_check:12;
};
uint32_t val;
} pkt_len;
union {
struct {
uint32_t state0: 8;
uint32_t state1: 8;
uint32_t state2: 8;
uint32_t state3: 8;
};
uint32_t val;
} state_w0;
union {
struct {
uint32_t state4: 8;
uint32_t state5: 8;
uint32_t state6: 8;
uint32_t state7: 8;
};
uint32_t val;
} state_w1;
union {
struct {
uint32_t conf0: 8;
uint32_t conf1: 8;
uint32_t conf2: 8;
uint32_t conf3: 8;
};
uint32_t val;
} conf_w0;
union {
struct {
uint32_t conf4: 8;
uint32_t conf5: 8;
uint32_t conf6: 8;
uint32_t conf7: 8;
};
uint32_t val;
} conf_w1;
union {
struct {
uint32_t conf8: 8;
uint32_t conf9: 8;
uint32_t conf10: 8;
uint32_t conf11: 8;
};
uint32_t val;
} conf_w2;
union {
struct {
uint32_t conf12: 8;
uint32_t conf13: 8;
uint32_t conf14: 8;
uint32_t conf15: 8;
};
uint32_t val;
} conf_w3;
union {
struct {
uint32_t conf16: 8; /*SLC timeout value*/
uint32_t conf17: 8; /*SLC timeout enable*/
uint32_t conf18: 8;
uint32_t conf19: 8; /*Interrupt to target CPU*/
};
uint32_t val;
} conf_w4;
union {
struct {
uint32_t conf20: 8;
uint32_t conf21: 8;
uint32_t conf22: 8;
uint32_t conf23: 8;
};
uint32_t val;
} conf_w5;
uint32_t win_cmd; /**/
union {
struct {
uint32_t conf24: 8;
uint32_t conf25: 8;
uint32_t conf26: 8;
uint32_t conf27: 8;
};
uint32_t val;
} conf_w6;
union {
struct {
uint32_t conf28: 8;
uint32_t conf29: 8;
uint32_t conf30: 8;
uint32_t conf31: 8;
};
uint32_t val;
} conf_w7;
union {
struct {
uint32_t reg_slc0_len0:20;
uint32_t reserved20: 12;
};
uint32_t val;
} pkt_len0;
union {
struct {
uint32_t reg_slc0_len1:20;
uint32_t reserved20: 12;
};
uint32_t val;
} pkt_len1;
union {
struct {
uint32_t reg_slc0_len2:20;
uint32_t reserved20: 12;
};
uint32_t val;
} pkt_len2;
union {
struct {
uint32_t conf32: 8;
uint32_t conf33: 8;
uint32_t conf34: 8;
uint32_t conf35: 8;
};
uint32_t val;
} conf_w8;
union {
struct {
uint32_t conf36: 8;
uint32_t conf37: 8;
uint32_t conf38: 8;
uint32_t conf39: 8;
};
uint32_t val;
} conf_w9;
union {
struct {
uint32_t conf40: 8;
uint32_t conf41: 8;
uint32_t conf42: 8;
uint32_t conf43: 8;
};
uint32_t val;
} conf_w10;
union {
struct {
uint32_t conf44: 8;
uint32_t conf45: 8;
uint32_t conf46: 8;
uint32_t conf47: 8;
};
uint32_t val;
} conf_w11;
union {
struct {
uint32_t conf48: 8;
uint32_t conf49: 8;
uint32_t conf50: 8;
uint32_t conf51: 8;
};
uint32_t val;
} conf_w12;
union {
struct {
uint32_t conf52: 8;
uint32_t conf53: 8;
uint32_t conf54: 8;
uint32_t conf55: 8;
};
uint32_t val;
} conf_w13;
union {
struct {
uint32_t conf56: 8;
uint32_t conf57: 8;
uint32_t conf58: 8;
uint32_t conf59: 8;
};
uint32_t val;
} conf_w14;
union {
struct {
uint32_t conf60: 8;
uint32_t conf61: 8;
uint32_t conf62: 8;
uint32_t conf63: 8;
};
uint32_t val;
} conf_w15;
uint32_t check_sum0; /**/
uint32_t check_sum1; /**/
union {
struct {
uint32_t token0: 12;
uint32_t rx_pf_valid: 1;
uint32_t reserved13: 3;
uint32_t reg_token1: 12;
uint32_t rx_pf_eof: 4;
};
uint32_t val;
} slc1_token_rdata;
union {
struct {
uint32_t token0_wd: 12;
uint32_t reserved12: 4;
uint32_t token1_wd: 12;
uint32_t reserved28: 4;
};
uint32_t val;
} slc0_token_wdata;
union {
struct {
uint32_t token0_wd: 12;
uint32_t reserved12: 4;
uint32_t token1_wd: 12;
uint32_t reserved28: 4;
};
uint32_t val;
} slc1_token_wdata;
union {
struct {
uint32_t slc0_token0_dec: 1;
uint32_t slc0_token1_dec: 1;
uint32_t slc0_token0_wr: 1;
uint32_t slc0_token1_wr: 1;
uint32_t slc1_token0_dec: 1;
uint32_t slc1_token1_dec: 1;
uint32_t slc1_token0_wr: 1;
uint32_t slc1_token1_wr: 1;
uint32_t slc0_len_wr: 1;
uint32_t reserved9: 23;
};
uint32_t val;
} token_con;
union {
struct {
uint32_t tohost_bit0: 1;
uint32_t tohost_bit1: 1;
uint32_t tohost_bit2: 1;
uint32_t tohost_bit3: 1;
uint32_t tohost_bit4: 1;
uint32_t tohost_bit5: 1;
uint32_t tohost_bit6: 1;
uint32_t tohost_bit7: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t token0_0to1: 1;
uint32_t token1_0to1: 1;
uint32_t rx_sof: 1;
uint32_t rx_eof: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t rx_pf_valid: 1;
uint32_t ext_bit0: 1;
uint32_t ext_bit1: 1;
uint32_t ext_bit2: 1;
uint32_t ext_bit3: 1;
uint32_t rx_new_packet: 1;
uint32_t rd_retry: 1;
uint32_t gpio_sdio: 1;
uint32_t reserved26: 6;
};
uint32_t val;
} slc0_int_clr;
union {
struct {
uint32_t tohost_bit0: 1;
uint32_t tohost_bit1: 1;
uint32_t tohost_bit2: 1;
uint32_t tohost_bit3: 1;
uint32_t tohost_bit4: 1;
uint32_t tohost_bit5: 1;
uint32_t tohost_bit6: 1;
uint32_t tohost_bit7: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t token0_0to1: 1;
uint32_t token1_0to1: 1;
uint32_t rx_sof: 1;
uint32_t rx_eof: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t rx_pf_valid: 1;
uint32_t ext_bit0: 1;
uint32_t ext_bit1: 1;
uint32_t ext_bit2: 1;
uint32_t ext_bit3: 1;
uint32_t wifi_rx_new_packet: 1;
uint32_t rd_retry: 1;
uint32_t bt_rx_new_packet: 1;
uint32_t reserved26: 6;
};
uint32_t val;
} slc1_int_clr;
union {
struct {
uint32_t tohost_bit0: 1;
uint32_t tohost_bit1: 1;
uint32_t tohost_bit2: 1;
uint32_t tohost_bit3: 1;
uint32_t tohost_bit4: 1;
uint32_t tohost_bit5: 1;
uint32_t tohost_bit6: 1;
uint32_t tohost_bit7: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t token0_0to1: 1;
uint32_t token1_0to1: 1;
uint32_t rx_sof: 1;
uint32_t rx_eof: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t rx_pf_valid: 1;
uint32_t ext_bit0: 1;
uint32_t ext_bit1: 1;
uint32_t ext_bit2: 1;
uint32_t ext_bit3: 1;
uint32_t rx_new_packet: 1;
uint32_t rd_retry: 1;
uint32_t gpio_sdio: 1;
uint32_t reserved26: 6;
};
uint32_t val;
} slc0_func1_int_ena;
union {
struct {
uint32_t tohost_bit0: 1;
uint32_t tohost_bit1: 1;
uint32_t tohost_bit2: 1;
uint32_t tohost_bit3: 1;
uint32_t tohost_bit4: 1;
uint32_t tohost_bit5: 1;
uint32_t tohost_bit6: 1;
uint32_t tohost_bit7: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t token0_0to1: 1;
uint32_t token1_0to1: 1;
uint32_t rx_sof: 1;
uint32_t rx_eof: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t rx_pf_valid: 1;
uint32_t ext_bit0: 1;
uint32_t ext_bit1: 1;
uint32_t ext_bit2: 1;
uint32_t ext_bit3: 1;
uint32_t wifi_rx_new_packet: 1;
uint32_t rd_retry: 1;
uint32_t bt_rx_new_packet: 1;
uint32_t reserved26: 6;
};
uint32_t val;
} slc1_func1_int_ena;
union {
struct {
uint32_t tohost_bit0: 1;
uint32_t tohost_bit1: 1;
uint32_t tohost_bit2: 1;
uint32_t tohost_bit3: 1;
uint32_t tohost_bit4: 1;
uint32_t tohost_bit5: 1;
uint32_t tohost_bit6: 1;
uint32_t tohost_bit7: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t token0_0to1: 1;
uint32_t token1_0to1: 1;
uint32_t rx_sof: 1;
uint32_t rx_eof: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t rx_pf_valid: 1;
uint32_t ext_bit0: 1;
uint32_t ext_bit1: 1;
uint32_t ext_bit2: 1;
uint32_t ext_bit3: 1;
uint32_t rx_new_packet: 1;
uint32_t rd_retry: 1;
uint32_t gpio_sdio: 1;
uint32_t reserved26: 6;
};
uint32_t val;
} slc0_func2_int_ena;
union {
struct {
uint32_t tohost_bit0: 1;
uint32_t tohost_bit1: 1;
uint32_t tohost_bit2: 1;
uint32_t tohost_bit3: 1;
uint32_t tohost_bit4: 1;
uint32_t tohost_bit5: 1;
uint32_t tohost_bit6: 1;
uint32_t tohost_bit7: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t token0_0to1: 1;
uint32_t token1_0to1: 1;
uint32_t rx_sof: 1;
uint32_t rx_eof: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t rx_pf_valid: 1;
uint32_t ext_bit0: 1;
uint32_t ext_bit1: 1;
uint32_t ext_bit2: 1;
uint32_t ext_bit3: 1;
uint32_t wifi_rx_new_packet: 1;
uint32_t rd_retry: 1;
uint32_t bt_rx_new_packet: 1;
uint32_t reserved26: 6;
};
uint32_t val;
} slc1_func2_int_ena;
union {
struct {
uint32_t tohost_bit0: 1;
uint32_t tohost_bit1: 1;
uint32_t tohost_bit2: 1;
uint32_t tohost_bit3: 1;
uint32_t tohost_bit4: 1;
uint32_t tohost_bit5: 1;
uint32_t tohost_bit6: 1;
uint32_t tohost_bit7: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t token0_0to1: 1;
uint32_t token1_0to1: 1;
uint32_t rx_sof: 1;
uint32_t rx_eof: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t rx_pf_valid: 1;
uint32_t ext_bit0: 1;
uint32_t ext_bit1: 1;
uint32_t ext_bit2: 1;
uint32_t ext_bit3: 1;
uint32_t rx_new_packet: 1;
uint32_t rd_retry: 1;
uint32_t gpio_sdio: 1;
uint32_t reserved26: 6;
};
uint32_t val;
} slc0_int_ena;
union {
struct {
uint32_t tohost_bit0: 1;
uint32_t tohost_bit1: 1;
uint32_t tohost_bit2: 1;
uint32_t tohost_bit3: 1;
uint32_t tohost_bit4: 1;
uint32_t tohost_bit5: 1;
uint32_t tohost_bit6: 1;
uint32_t tohost_bit7: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t token0_0to1: 1;
uint32_t token1_0to1: 1;
uint32_t rx_sof: 1;
uint32_t rx_eof: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t rx_pf_valid: 1;
uint32_t ext_bit0: 1;
uint32_t ext_bit1: 1;
uint32_t ext_bit2: 1;
uint32_t ext_bit3: 1;
uint32_t wifi_rx_new_packet: 1;
uint32_t rd_retry: 1;
uint32_t bt_rx_new_packet: 1;
uint32_t reserved26: 6;
};
uint32_t val;
} slc1_int_ena;
union {
struct {
uint32_t infor: 20;
uint32_t reserved20: 12;
};
uint32_t val;
} slc0_rx_infor;
union {
struct {
uint32_t infor: 20;
uint32_t reserved20: 12;
};
uint32_t val;
} slc1_rx_infor;
uint32_t slc0_len_wd; /**/
uint32_t apbwin_wdata; /**/
union {
struct {
uint32_t addr: 28;
uint32_t wr: 1;
uint32_t start: 1;
uint32_t reserved30: 2;
};
uint32_t val;
} apbwin_conf;
uint32_t apbwin_rdata; /**/
union {
struct {
uint32_t bit7_clraddr: 9;
uint32_t bit6_clraddr: 9;
uint32_t reserved18: 14;
};
uint32_t val;
} slc0_rdclr;
union {
struct {
uint32_t bit7_clraddr: 9;
uint32_t bit6_clraddr: 9;
uint32_t reserved18: 14;
};
uint32_t val;
} slc1_rdclr;
union {
struct {
uint32_t tohost_bit01: 1;
uint32_t tohost_bit11: 1;
uint32_t tohost_bit21: 1;
uint32_t tohost_bit31: 1;
uint32_t tohost_bit41: 1;
uint32_t tohost_bit51: 1;
uint32_t tohost_bit61: 1;
uint32_t tohost_bit71: 1;
uint32_t token0_1to01: 1;
uint32_t token1_1to01: 1;
uint32_t token0_0to11: 1;
uint32_t token1_0to11: 1;
uint32_t rx_sof1: 1;
uint32_t rx_eof1: 1;
uint32_t rx_start1: 1;
uint32_t tx_start1: 1;
uint32_t rx_udf1: 1;
uint32_t tx_ovf1: 1;
uint32_t rx_pf_valid1: 1;
uint32_t ext_bit01: 1;
uint32_t ext_bit11: 1;
uint32_t ext_bit21: 1;
uint32_t ext_bit31: 1;
uint32_t rx_new_packet1: 1;
uint32_t rd_retry1: 1;
uint32_t gpio_sdio1: 1;
uint32_t reserved26: 6;
};
uint32_t val;
} slc0_int_ena1;
union {
struct {
uint32_t tohost_bit01: 1;
uint32_t tohost_bit11: 1;
uint32_t tohost_bit21: 1;
uint32_t tohost_bit31: 1;
uint32_t tohost_bit41: 1;
uint32_t tohost_bit51: 1;
uint32_t tohost_bit61: 1;
uint32_t tohost_bit71: 1;
uint32_t token0_1to01: 1;
uint32_t token1_1to01: 1;
uint32_t token0_0to11: 1;
uint32_t token1_0to11: 1;
uint32_t rx_sof1: 1;
uint32_t rx_eof1: 1;
uint32_t rx_start1: 1;
uint32_t tx_start1: 1;
uint32_t rx_udf1: 1;
uint32_t tx_ovf1: 1;
uint32_t rx_pf_valid1: 1;
uint32_t ext_bit01: 1;
uint32_t ext_bit11: 1;
uint32_t ext_bit21: 1;
uint32_t ext_bit31: 1;
uint32_t wifi_rx_new_packet1: 1;
uint32_t rd_retry1: 1;
uint32_t bt_rx_new_packet1: 1;
uint32_t reserved26: 6;
};
uint32_t val;
} slc1_int_ena1;
uint32_t reserved_11c;
uint32_t reserved_120;
uint32_t reserved_124;
uint32_t reserved_128;
uint32_t reserved_12c;
uint32_t reserved_130;
uint32_t reserved_134;
uint32_t reserved_138;
uint32_t reserved_13c;
uint32_t reserved_140;
uint32_t reserved_144;
uint32_t reserved_148;
uint32_t reserved_14c;
uint32_t reserved_150;
uint32_t reserved_154;
uint32_t reserved_158;
uint32_t reserved_15c;
uint32_t reserved_160;
uint32_t reserved_164;
uint32_t reserved_168;
uint32_t reserved_16c;
uint32_t reserved_170;
uint32_t reserved_174;
uint32_t date; /**/
uint32_t id; /**/
uint32_t reserved_180;
uint32_t reserved_184;
uint32_t reserved_188;
uint32_t reserved_18c;
uint32_t reserved_190;
uint32_t reserved_194;
uint32_t reserved_198;
uint32_t reserved_19c;
uint32_t reserved_1a0;
uint32_t reserved_1a4;
uint32_t reserved_1a8;
uint32_t reserved_1ac;
uint32_t reserved_1b0;
uint32_t reserved_1b4;
uint32_t reserved_1b8;
uint32_t reserved_1bc;
uint32_t reserved_1c0;
uint32_t reserved_1c4;
uint32_t reserved_1c8;
uint32_t reserved_1cc;
uint32_t reserved_1d0;
uint32_t reserved_1d4;
uint32_t reserved_1d8;
uint32_t reserved_1dc;
uint32_t reserved_1e0;
uint32_t reserved_1e4;
uint32_t reserved_1e8;
uint32_t reserved_1ec;
union {
struct {
uint32_t frc_sdio11: 5;
uint32_t frc_sdio20: 5;
uint32_t frc_neg_samp: 5;
uint32_t frc_pos_samp: 5;
uint32_t frc_quick_in: 5;
uint32_t sdio20_int_delay: 1;
uint32_t sdio_pad_pullup: 1;
uint32_t hspeed_con_en: 1;
uint32_t reserved28: 4;
};
uint32_t val;
} conf;
union {
struct {
uint32_t sdio20_mode: 5;
uint32_t sdio_neg_samp: 5;
uint32_t sdio_quick_in: 5;
uint32_t reserved15: 17;
};
uint32_t val;
} inf_st;
} host_dev_t;
extern host_dev_t HOST;
#ifdef __cplusplus
}
#endif
#endif /* _SOC_HOST_STRUCT_H_ */

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,858 @@
// Copyright 2015-2018 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#ifndef _SOC_SLC_STRUCT_H_
#define _SOC_SLC_STRUCT_H_
#ifdef __cplusplus
extern "C" {
#endif
typedef volatile struct {
union {
struct {
uint32_t slc0_tx_rst: 1;
uint32_t slc0_rx_rst: 1;
uint32_t ahbm_fifo_rst: 1;
uint32_t ahbm_rst: 1;
uint32_t slc0_tx_loop_test: 1;
uint32_t slc0_rx_loop_test: 1;
uint32_t slc0_rx_auto_wrback: 1;
uint32_t slc0_rx_no_restart_clr: 1;
uint32_t slc0_rxdscr_burst_en: 1;
uint32_t slc0_rxdata_burst_en: 1;
uint32_t slc0_rxlink_auto_ret: 1;
uint32_t slc0_txlink_auto_ret: 1;
uint32_t slc0_txdscr_burst_en: 1;
uint32_t slc0_txdata_burst_en: 1;
uint32_t slc0_token_auto_clr: 1;
uint32_t slc0_token_sel: 1;
uint32_t slc1_tx_rst: 1;
uint32_t slc1_rx_rst: 1;
uint32_t slc0_wr_retry_mask_en: 1;
uint32_t slc1_wr_retry_mask_en: 1;
uint32_t slc1_tx_loop_test: 1;
uint32_t slc1_rx_loop_test: 1;
uint32_t slc1_rx_auto_wrback: 1;
uint32_t slc1_rx_no_restart_clr: 1;
uint32_t slc1_rxdscr_burst_en: 1;
uint32_t slc1_rxdata_burst_en: 1;
uint32_t slc1_rxlink_auto_ret: 1;
uint32_t slc1_txlink_auto_ret: 1;
uint32_t slc1_txdscr_burst_en: 1;
uint32_t slc1_txdata_burst_en: 1;
uint32_t slc1_token_auto_clr: 1;
uint32_t slc1_token_sel: 1;
};
uint32_t val;
} conf0;
union {
struct {
uint32_t frhost_bit0: 1;
uint32_t frhost_bit1: 1;
uint32_t frhost_bit2: 1;
uint32_t frhost_bit3: 1;
uint32_t frhost_bit4: 1;
uint32_t frhost_bit5: 1;
uint32_t frhost_bit6: 1;
uint32_t frhost_bit7: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t tx_done: 1;
uint32_t tx_suc_eof: 1;
uint32_t rx_done: 1;
uint32_t rx_eof: 1;
uint32_t tohost: 1;
uint32_t tx_dscr_err: 1;
uint32_t rx_dscr_err: 1;
uint32_t tx_dscr_empty: 1;
uint32_t host_rd_ack: 1;
uint32_t wr_retry_done: 1;
uint32_t tx_err_eof: 1;
uint32_t cmd_dtc: 1;
uint32_t rx_quick_eof: 1;
uint32_t reserved27: 5;
};
uint32_t val;
} slc0_int_raw;
union {
struct {
uint32_t frhost_bit0: 1;
uint32_t frhost_bit1: 1;
uint32_t frhost_bit2: 1;
uint32_t frhost_bit3: 1;
uint32_t frhost_bit4: 1;
uint32_t frhost_bit5: 1;
uint32_t frhost_bit6: 1;
uint32_t frhost_bit7: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t tx_done: 1;
uint32_t tx_suc_eof: 1;
uint32_t rx_done: 1;
uint32_t rx_eof: 1;
uint32_t tohost: 1;
uint32_t tx_dscr_err: 1;
uint32_t rx_dscr_err: 1;
uint32_t tx_dscr_empty: 1;
uint32_t host_rd_ack: 1;
uint32_t wr_retry_done: 1;
uint32_t tx_err_eof: 1;
uint32_t cmd_dtc: 1;
uint32_t rx_quick_eof: 1;
uint32_t reserved27: 5;
};
uint32_t val;
} slc0_int_st;
union {
struct {
uint32_t frhost_bit0: 1;
uint32_t frhost_bit1: 1;
uint32_t frhost_bit2: 1;
uint32_t frhost_bit3: 1;
uint32_t frhost_bit4: 1;
uint32_t frhost_bit5: 1;
uint32_t frhost_bit6: 1;
uint32_t frhost_bit7: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t tx_done: 1;
uint32_t tx_suc_eof: 1;
uint32_t rx_done: 1;
uint32_t rx_eof: 1;
uint32_t tohost: 1;
uint32_t tx_dscr_err: 1;
uint32_t rx_dscr_err: 1;
uint32_t tx_dscr_empty: 1;
uint32_t host_rd_ack: 1;
uint32_t wr_retry_done: 1;
uint32_t tx_err_eof: 1;
uint32_t cmd_dtc: 1;
uint32_t rx_quick_eof: 1;
uint32_t reserved27: 5;
};
uint32_t val;
} slc0_int_ena;
union {
struct {
uint32_t frhost_bit0: 1;
uint32_t frhost_bit1: 1;
uint32_t frhost_bit2: 1;
uint32_t frhost_bit3: 1;
uint32_t frhost_bit4: 1;
uint32_t frhost_bit5: 1;
uint32_t frhost_bit6: 1;
uint32_t frhost_bit7: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t tx_done: 1;
uint32_t tx_suc_eof: 1;
uint32_t rx_done: 1;
uint32_t rx_eof: 1;
uint32_t tohost: 1;
uint32_t tx_dscr_err: 1;
uint32_t rx_dscr_err: 1;
uint32_t tx_dscr_empty: 1;
uint32_t host_rd_ack: 1;
uint32_t wr_retry_done: 1;
uint32_t tx_err_eof: 1;
uint32_t cmd_dtc: 1;
uint32_t rx_quick_eof: 1;
uint32_t reserved27: 5;
};
uint32_t val;
} slc0_int_clr;
union {
struct {
uint32_t frhost_bit8: 1;
uint32_t frhost_bit9: 1;
uint32_t frhost_bit10: 1;
uint32_t frhost_bit11: 1;
uint32_t frhost_bit12: 1;
uint32_t frhost_bit13: 1;
uint32_t frhost_bit14: 1;
uint32_t frhost_bit15: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t tx_done: 1;
uint32_t tx_suc_eof: 1;
uint32_t rx_done: 1;
uint32_t rx_eof: 1;
uint32_t tohost: 1;
uint32_t tx_dscr_err: 1;
uint32_t rx_dscr_err: 1;
uint32_t tx_dscr_empty: 1;
uint32_t host_rd_ack: 1;
uint32_t wr_retry_done: 1;
uint32_t tx_err_eof: 1;
uint32_t reserved25: 7;
};
uint32_t val;
} slc1_int_raw;
union {
struct {
uint32_t frhost_bit8: 1;
uint32_t frhost_bit9: 1;
uint32_t frhost_bit10: 1;
uint32_t frhost_bit11: 1;
uint32_t frhost_bit12: 1;
uint32_t frhost_bit13: 1;
uint32_t frhost_bit14: 1;
uint32_t frhost_bit15: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t tx_done: 1;
uint32_t tx_suc_eof: 1;
uint32_t rx_done: 1;
uint32_t rx_eof: 1;
uint32_t tohost: 1;
uint32_t tx_dscr_err: 1;
uint32_t rx_dscr_err: 1;
uint32_t tx_dscr_empty: 1;
uint32_t host_rd_ack: 1;
uint32_t wr_retry_done: 1;
uint32_t tx_err_eof: 1;
uint32_t reserved25: 7;
};
uint32_t val;
} slc1_int_st;
union {
struct {
uint32_t frhost_bit8: 1;
uint32_t frhost_bit9: 1;
uint32_t frhost_bit10: 1;
uint32_t frhost_bit11: 1;
uint32_t frhost_bit12: 1;
uint32_t frhost_bit13: 1;
uint32_t frhost_bit14: 1;
uint32_t frhost_bit15: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t tx_done: 1;
uint32_t tx_suc_eof: 1;
uint32_t rx_done: 1;
uint32_t rx_eof: 1;
uint32_t tohost: 1;
uint32_t tx_dscr_err: 1;
uint32_t rx_dscr_err: 1;
uint32_t tx_dscr_empty: 1;
uint32_t host_rd_ack: 1;
uint32_t wr_retry_done: 1;
uint32_t tx_err_eof: 1;
uint32_t reserved25: 7;
};
uint32_t val;
} slc1_int_ena;
union {
struct {
uint32_t frhost_bit8: 1;
uint32_t frhost_bit9: 1;
uint32_t frhost_bit10: 1;
uint32_t frhost_bit11: 1;
uint32_t frhost_bit12: 1;
uint32_t frhost_bit13: 1;
uint32_t frhost_bit14: 1;
uint32_t frhost_bit15: 1;
uint32_t rx_start: 1;
uint32_t tx_start: 1;
uint32_t rx_udf: 1;
uint32_t tx_ovf: 1;
uint32_t token0_1to0: 1;
uint32_t token1_1to0: 1;
uint32_t tx_done: 1;
uint32_t tx_suc_eof: 1;
uint32_t rx_done: 1;
uint32_t rx_eof: 1;
uint32_t tohost: 1;
uint32_t tx_dscr_err: 1;
uint32_t rx_dscr_err: 1;
uint32_t tx_dscr_empty: 1;
uint32_t host_rd_ack: 1;
uint32_t wr_retry_done: 1;
uint32_t tx_err_eof: 1;
uint32_t reserved25: 7;
};
uint32_t val;
} slc1_int_clr;
union {
struct {
uint32_t slc0_rx_full: 1;
uint32_t slc0_rx_empty: 1;
uint32_t reserved2: 14;
uint32_t slc1_rx_full: 1;
uint32_t slc1_rx_empty: 1;
uint32_t reserved18:14;
};
uint32_t val;
} rx_status;
union {
struct {
uint32_t rxfifo_wdata: 9;
uint32_t reserved9: 7;
uint32_t rxfifo_push: 1;
uint32_t reserved17: 15;
};
uint32_t val;
} slc0_rxfifo_push;
union {
struct {
uint32_t rxfifo_wdata: 9;
uint32_t reserved9: 7;
uint32_t rxfifo_push: 1;
uint32_t reserved17: 15;
};
uint32_t val;
} slc1_rxfifo_push;
union {
struct {
uint32_t slc0_tx_full: 1;
uint32_t slc0_tx_empty: 1;
uint32_t reserved2: 14;
uint32_t slc1_tx_full: 1;
uint32_t slc1_tx_empty: 1;
uint32_t reserved18:14;
};
uint32_t val;
} tx_status;
union {
struct {
uint32_t txfifo_rdata: 11;
uint32_t reserved11: 5;
uint32_t txfifo_pop: 1;
uint32_t reserved17: 15;
};
uint32_t val;
} slc0_txfifo_pop;
union {
struct {
uint32_t txfifo_rdata: 11;
uint32_t reserved11: 5;
uint32_t txfifo_pop: 1;
uint32_t reserved17: 15;
};
uint32_t val;
} slc1_txfifo_pop;
union {
struct {
uint32_t addr: 20;
uint32_t reserved20: 8;
uint32_t stop: 1;
uint32_t start: 1;
uint32_t restart: 1;
uint32_t park: 1;
};
uint32_t val;
} slc0_rx_link;
union {
struct {
uint32_t addr: 20;
uint32_t reserved20: 8;
uint32_t stop: 1;
uint32_t start: 1;
uint32_t restart: 1;
uint32_t park: 1;
};
uint32_t val;
} slc0_tx_link;
union {
struct {
uint32_t addr: 20;
uint32_t bt_packet: 1;
uint32_t reserved21: 7;
uint32_t stop: 1;
uint32_t start: 1;
uint32_t restart: 1;
uint32_t park: 1;
};
uint32_t val;
} slc1_rx_link;
union {
struct {
uint32_t addr: 20;
uint32_t reserved20: 8;
uint32_t stop: 1;
uint32_t start: 1;
uint32_t restart: 1;
uint32_t park: 1;
};
uint32_t val;
} slc1_tx_link;
union {
struct {
uint32_t slc0_intvec: 8;
uint32_t reserved8: 8;
uint32_t slc1_intvec: 8;
uint32_t reserved24: 8;
};
uint32_t val;
} intvec_tohost;
union {
struct {
uint32_t wdata: 12;
uint32_t wr: 1;
uint32_t inc: 1;
uint32_t inc_more: 1;
uint32_t reserved15: 1;
uint32_t token0: 12;
uint32_t reserved28: 4;
};
uint32_t val;
} slc0_token0;
union {
struct {
uint32_t wdata: 12;
uint32_t wr: 1;
uint32_t inc: 1;
uint32_t inc_more: 1;
uint32_t reserved15: 1;
uint32_t token1: 12;
uint32_t reserved28: 4;
};
uint32_t val;
} slc0_token1;
union {
struct {
uint32_t wdata: 12;
uint32_t wr: 1;
uint32_t inc: 1;
uint32_t inc_more: 1;
uint32_t reserved15: 1;
uint32_t token0: 12;
uint32_t reserved28: 4;
};
uint32_t val;
} slc1_token0;
union {
struct {
uint32_t wdata: 12;
uint32_t wr: 1;
uint32_t inc: 1;
uint32_t inc_more: 1;
uint32_t reserved15: 1;
uint32_t token1: 12;
uint32_t reserved28: 4;
};
uint32_t val;
} slc1_token1;
union {
struct {
uint32_t slc0_check_owner: 1;
uint32_t slc0_tx_check_sum_en: 1;
uint32_t slc0_rx_check_sum_en: 1;
uint32_t cmd_hold_en: 1;
uint32_t slc0_len_auto_clr: 1;
uint32_t slc0_tx_stitch_en: 1;
uint32_t slc0_rx_stitch_en: 1;
uint32_t reserved7: 9;
uint32_t slc1_check_owner: 1;
uint32_t slc1_tx_check_sum_en: 1;
uint32_t slc1_rx_check_sum_en: 1;
uint32_t host_int_level_sel: 1;
uint32_t slc1_tx_stitch_en: 1;
uint32_t slc1_rx_stitch_en: 1;
uint32_t clk_en: 1;
uint32_t reserved23: 9;
};
uint32_t val;
} conf1;
uint32_t slc0_state0; /**/
uint32_t slc0_state1; /**/
uint32_t slc1_state0; /**/
uint32_t slc1_state1; /**/
union {
struct {
uint32_t txeof_ena: 6;
uint32_t reserved6: 2;
uint32_t fifo_map_ena: 4;
uint32_t slc0_tx_dummy_mode: 1;
uint32_t hda_map_128k: 1;
uint32_t slc1_tx_dummy_mode: 1;
uint32_t reserved15: 1;
uint32_t tx_push_idle_num:16;
};
uint32_t val;
} bridge_conf;
uint32_t slc0_to_eof_des_addr; /**/
uint32_t slc0_tx_eof_des_addr; /**/
uint32_t slc0_to_eof_bfr_des_addr; /**/
uint32_t slc1_to_eof_des_addr; /**/
uint32_t slc1_tx_eof_des_addr; /**/
uint32_t slc1_to_eof_bfr_des_addr; /**/
union {
struct {
uint32_t mode: 3;
uint32_t reserved3: 1;
uint32_t addr: 2;
uint32_t reserved6: 26;
};
uint32_t val;
} ahb_test;
union {
struct {
uint32_t cmd_st: 3;
uint32_t reserved3: 1;
uint32_t func_st: 4;
uint32_t sdio_wakeup: 1;
uint32_t reserved9: 3;
uint32_t bus_st: 3;
uint32_t reserved15: 1;
uint32_t func1_acc_state: 5;
uint32_t reserved21: 3;
uint32_t func2_acc_state: 5;
uint32_t reserved29: 3;
};
uint32_t val;
} sdio_st;
union {
struct {
uint32_t slc0_token_no_replace: 1;
uint32_t slc0_infor_no_replace: 1;
uint32_t slc0_rx_fill_mode: 1;
uint32_t slc0_rx_eof_mode: 1;
uint32_t slc0_rx_fill_en: 1;
uint32_t slc0_rd_retry_threshold:11;
uint32_t slc1_token_no_replace: 1;
uint32_t slc1_infor_no_replace: 1;
uint32_t slc1_rx_fill_mode: 1;
uint32_t slc1_rx_eof_mode: 1;
uint32_t slc1_rx_fill_en: 1;
uint32_t slc1_rd_retry_threshold:11;
};
uint32_t val;
} rx_dscr_conf;
uint32_t slc0_txlink_dscr; /**/
uint32_t slc0_txlink_dscr_bf0; /**/
uint32_t slc0_txlink_dscr_bf1; /**/
uint32_t slc0_rxlink_dscr; /**/
uint32_t slc0_rxlink_dscr_bf0; /**/
uint32_t slc0_rxlink_dscr_bf1; /**/
uint32_t slc1_txlink_dscr; /**/
uint32_t slc1_txlink_dscr_bf0; /**/
uint32_t slc1_txlink_dscr_bf1; /**/
uint32_t slc1_rxlink_dscr; /**/
uint32_t slc1_rxlink_dscr_bf0; /**/
uint32_t slc1_rxlink_dscr_bf1; /**/
uint32_t slc0_tx_erreof_des_addr; /**/
uint32_t slc1_tx_erreof_des_addr; /**/
union {
struct {
uint32_t slc0_token:12;
uint32_t reserved12: 4;
uint32_t slc1_token:12;
uint32_t reserved28: 4;
};
uint32_t val;
} token_lat;
union {
struct {
uint32_t wr_retry_threshold:11;
uint32_t reserved11: 21;
};
uint32_t val;
} tx_dscr_conf;
uint32_t cmd_infor0; /**/
uint32_t cmd_infor1; /**/
union {
struct {
uint32_t len_wdata: 20;
uint32_t len_wr: 1;
uint32_t len_inc: 1;
uint32_t len_inc_more: 1;
uint32_t rx_packet_load_en: 1;
uint32_t tx_packet_load_en: 1;
uint32_t rx_get_used_dscr: 1;
uint32_t tx_get_used_dscr: 1;
uint32_t rx_new_pkt_ind: 1;
uint32_t tx_new_pkt_ind: 1;
uint32_t reserved29: 3;
};
uint32_t val;
} slc0_len_conf;
union {
struct {
uint32_t len: 20;
uint32_t reserved20:12;
};
uint32_t val;
} slc0_length;
uint32_t slc0_txpkt_h_dscr; /**/
uint32_t slc0_txpkt_e_dscr; /**/
uint32_t slc0_rxpkt_h_dscr; /**/
uint32_t slc0_rxpkt_e_dscr; /**/
uint32_t slc0_txpktu_h_dscr; /**/
uint32_t slc0_txpktu_e_dscr; /**/
uint32_t slc0_rxpktu_h_dscr; /**/
uint32_t slc0_rxpktu_e_dscr; /**/
uint32_t reserved_10c;
uint32_t reserved_110;
union {
struct {
uint32_t slc0_position: 8;
uint32_t slc1_position: 8;
uint32_t reserved16: 16;
};
uint32_t val;
} seq_position;
union {
struct {
uint32_t rx_dscr_rec_lim: 10;
uint32_t reserved10: 22;
};
uint32_t val;
} slc0_dscr_rec_conf;
union {
struct {
uint32_t dat0_crc_err_cnt: 8;
uint32_t dat1_crc_err_cnt: 8;
uint32_t dat2_crc_err_cnt: 8;
uint32_t dat3_crc_err_cnt: 8;
};
uint32_t val;
} sdio_crc_st0;
union {
struct {
uint32_t cmd_crc_err_cnt: 8;
uint32_t reserved8: 23;
uint32_t err_cnt_clr: 1;
};
uint32_t val;
} sdio_crc_st1;
uint32_t slc0_eof_start_des; /**/
uint32_t slc0_push_dscr_addr; /**/
uint32_t slc0_done_dscr_addr; /**/
uint32_t slc0_sub_start_des; /**/
union {
struct {
uint32_t rx_dscr_cnt_lat: 10;
uint32_t reserved10: 6;
uint32_t rx_get_eof_occ: 1;
uint32_t reserved17: 15;
};
uint32_t val;
} slc0_dscr_cnt;
union {
struct {
uint32_t len_lim: 20;
uint32_t reserved20:12;
};
uint32_t val;
} slc0_len_lim_conf;
union {
struct {
uint32_t frhost_bit01: 1;
uint32_t frhost_bit11: 1;
uint32_t frhost_bit21: 1;
uint32_t frhost_bit31: 1;
uint32_t frhost_bit41: 1;
uint32_t frhost_bit51: 1;
uint32_t frhost_bit61: 1;
uint32_t frhost_bit71: 1;
uint32_t rx_start1: 1;
uint32_t tx_start1: 1;
uint32_t rx_udf1: 1;
uint32_t tx_ovf1: 1;
uint32_t token0_1to01: 1;
uint32_t token1_1to01: 1;
uint32_t tx_done1: 1;
uint32_t tx_suc_eof1: 1;
uint32_t rx_done1: 1;
uint32_t rx_eof1: 1;
uint32_t tohost1: 1;
uint32_t tx_dscr_err1: 1;
uint32_t rx_dscr_err1: 1;
uint32_t tx_dscr_empty1: 1;
uint32_t host_rd_ack1: 1;
uint32_t wr_retry_done1: 1;
uint32_t tx_err_eof1: 1;
uint32_t cmd_dtc1: 1;
uint32_t rx_quick_eof1: 1;
uint32_t reserved27: 5;
};
uint32_t val;
} slc0_int_st1;
union {
struct {
uint32_t frhost_bit01: 1;
uint32_t frhost_bit11: 1;
uint32_t frhost_bit21: 1;
uint32_t frhost_bit31: 1;
uint32_t frhost_bit41: 1;
uint32_t frhost_bit51: 1;
uint32_t frhost_bit61: 1;
uint32_t frhost_bit71: 1;
uint32_t rx_start1: 1;
uint32_t tx_start1: 1;
uint32_t rx_udf1: 1;
uint32_t tx_ovf1: 1;
uint32_t token0_1to01: 1;
uint32_t token1_1to01: 1;
uint32_t tx_done1: 1;
uint32_t tx_suc_eof1: 1;
uint32_t rx_done1: 1;
uint32_t rx_eof1: 1;
uint32_t tohost1: 1;
uint32_t tx_dscr_err1: 1;
uint32_t rx_dscr_err1: 1;
uint32_t tx_dscr_empty1: 1;
uint32_t host_rd_ack1: 1;
uint32_t wr_retry_done1: 1;
uint32_t tx_err_eof1: 1;
uint32_t cmd_dtc1: 1;
uint32_t rx_quick_eof1: 1;
uint32_t reserved27: 5;
};
uint32_t val;
} slc0_int_ena1;
union {
struct {
uint32_t frhost_bit81: 1;
uint32_t frhost_bit91: 1;
uint32_t frhost_bit101: 1;
uint32_t frhost_bit111: 1;
uint32_t frhost_bit121: 1;
uint32_t frhost_bit131: 1;
uint32_t frhost_bit141: 1;
uint32_t frhost_bit151: 1;
uint32_t rx_start1: 1;
uint32_t tx_start1: 1;
uint32_t rx_udf1: 1;
uint32_t tx_ovf1: 1;
uint32_t token0_1to01: 1;
uint32_t token1_1to01: 1;
uint32_t tx_done1: 1;
uint32_t tx_suc_eof1: 1;
uint32_t rx_done1: 1;
uint32_t rx_eof1: 1;
uint32_t tohost1: 1;
uint32_t tx_dscr_err1: 1;
uint32_t rx_dscr_err1: 1;
uint32_t tx_dscr_empty1: 1;
uint32_t host_rd_ack1: 1;
uint32_t wr_retry_done1: 1;
uint32_t tx_err_eof1: 1;
uint32_t reserved25: 7;
};
uint32_t val;
} slc1_int_st1;
union {
struct {
uint32_t frhost_bit81: 1;
uint32_t frhost_bit91: 1;
uint32_t frhost_bit101: 1;
uint32_t frhost_bit111: 1;
uint32_t frhost_bit121: 1;
uint32_t frhost_bit131: 1;
uint32_t frhost_bit141: 1;
uint32_t frhost_bit151: 1;
uint32_t rx_start1: 1;
uint32_t tx_start1: 1;
uint32_t rx_udf1: 1;
uint32_t tx_ovf1: 1;
uint32_t token0_1to01: 1;
uint32_t token1_1to01: 1;
uint32_t tx_done1: 1;
uint32_t tx_suc_eof1: 1;
uint32_t rx_done1: 1;
uint32_t rx_eof1: 1;
uint32_t tohost1: 1;
uint32_t tx_dscr_err1: 1;
uint32_t rx_dscr_err1: 1;
uint32_t tx_dscr_empty1: 1;
uint32_t host_rd_ack1: 1;
uint32_t wr_retry_done1: 1;
uint32_t tx_err_eof1: 1;
uint32_t reserved25: 7;
};
uint32_t val;
} slc1_int_ena1;
uint32_t reserved_14c;
uint32_t reserved_150;
uint32_t reserved_154;
uint32_t reserved_158;
uint32_t reserved_15c;
uint32_t reserved_160;
uint32_t reserved_164;
uint32_t reserved_168;
uint32_t reserved_16c;
uint32_t reserved_170;
uint32_t reserved_174;
uint32_t reserved_178;
uint32_t reserved_17c;
uint32_t reserved_180;
uint32_t reserved_184;
uint32_t reserved_188;
uint32_t reserved_18c;
uint32_t reserved_190;
uint32_t reserved_194;
uint32_t reserved_198;
uint32_t reserved_19c;
uint32_t reserved_1a0;
uint32_t reserved_1a4;
uint32_t reserved_1a8;
uint32_t reserved_1ac;
uint32_t reserved_1b0;
uint32_t reserved_1b4;
uint32_t reserved_1b8;
uint32_t reserved_1bc;
uint32_t reserved_1c0;
uint32_t reserved_1c4;
uint32_t reserved_1c8;
uint32_t reserved_1cc;
uint32_t reserved_1d0;
uint32_t reserved_1d4;
uint32_t reserved_1d8;
uint32_t reserved_1dc;
uint32_t reserved_1e0;
uint32_t reserved_1e4;
uint32_t reserved_1e8;
uint32_t reserved_1ec;
uint32_t reserved_1f0;
uint32_t reserved_1f4;
uint32_t date; /**/
uint32_t id; /**/
} slc_dev_t;
extern slc_dev_t SLC;
#ifdef __cplusplus
}
#endif
#endif /* _SOC_SLC_STRUCT_H_ */

View File

@ -107,6 +107,8 @@ INPUT = \
../../components/driver/include/driver/sdmmc_host.h \
../../components/driver/include/driver/sdmmc_types.h \
../../components/driver/include/driver/sdspi_host.h \
## SDIO slave
../../components/driver/include/driver/sdio_slave.h \
## Non-Volatile Storage
../../components/nvs_flash/include/nvs.h \
../../components/nvs_flash/include/nvs_flash.h \

View File

@ -0,0 +1,85 @@
ESP SDIO slave protocol
=======================
The protocol is based on Function 1 access by CMD52 and CMD53, offering 3 services: (1) sending and receiving FIFO, (2) 52 8-bit R/W
register shared by host and slave, (3) 8 general purpose interrupt sources from host to slave and 8 in the oppsite direction.
The host should access the registers below as described to communicate with slave.
Slave register table
--------------------
32-bit
^^^^^^^
- 0x044 (TOKEN_RDATA): in which bit 27-16 holds the receiving buffer number.
- 0x058 (INT_ST): holds the interrupt source bits from slave to host.
- 0x060 (PKT_LEN): holds the accumulated length (by byte) to be sent from slave to host.
- 0x0D4 (INT_CLR): write 1 to clear interrupt bits corresponding to INT_ST.
- 0x0DC (INT_ENA): mask bits for interrupts from slave to host.
8-bit
^^^^^
Shared general purpose registers:
- 0x06C-0x077: R/W registers 0-11 shared by slave and host.
- 0x07A-0x07B: R/W registers 14-15 shared by slave and host.
- 0x07E-0x07F: R/W registers 18-19 shared by slave and host.
- 0x088-0x08B: R/W registers 24-27 shared by slave and host.
- 0x09C-0x0BB: R/W registers 32-63 shared by slave and host.
Interrupt Registers:
- 0x08D (SLAVE_INT): bits for host to interrupt slave. auto clear.
FIFO (sending and receiving)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^
0x090 - 0x1F7FF are reserved for FIFOs.
.. note:: This includes the CMD52 and CMD53 (block mode or byte mode).
The function number should be set to 1, OP Code should be set to 1 (for CMD53).
The slave will respond with the length according to the length field in CMD53 (1 of CMD52), with the data longer
than *requested length* filled with 0 (sending) or discard (receiving).
Interrupts
----------
For the host interrupts, the slave raise the interrupt by pulling DAT1 line down at a proper time (level sensitive).
The host detect this and read the INT_ST register to see the source. Then the host can clear it by writing the INT_CLR
register and do something with the interrupt. The host can also mask unneeded sources by clearing the bits in INT_ENA
register corresponding to the sources. If all the sources are cleared (or masked), the DAT1 line goes inactive.
``sdio_slave_hostint_t`` (:doc:`sdio_slave`) shows the bit definition corresponding to host interrupt sources.
For the slave interrupts, the host send transfers to write the SLAVE_INT register. Once a bit is written from 0 to 1,
the slave hardware and driver will detect it and inform the app.
Receiving FIFO
--------------
To write the receiving FIFO in the slave, host should work in the following steps:
1. Read the TOKEN1 field (bits 27-16) of TOKEN_RDATA (0x044) register. The buffer number remaining is TOKEN1 minus
the number of buffers used by host.
2. Make sure the buffer number is sufficient (*buffer_size* * *buffer_num* is greater than data to write, *buffer_size*
is pre-defined between the host and the slave before the communication starts). Or go back to step 1 until the buffer
is enough.
3. Write to the FIFO address with CMD53. Note that the *requested length* should not be larger than calculated in step 2,
and the FIFO address is related to *rquested length*.
4. Calculate used buffers, note that non-full buffer at the tail should be seen as one that is used.
Sending FIFO
------------
To read the sending FIFO in the slave, host should work in the following steps:
1. Wait for the interrupt line to be active (optional, low by default).
2. Read (poll) the interrupt bits in INT_ST register to see whether new packets exists.
3. If new packets are ready, reads the PKT_LEN reg. The data length to read from slave is PKT_LEN minuses the length
that has been read from the host. If the PKT_LEN is not larger than used, wait and poll until the slave is ready and
update the PKT_LEN.
4. Read from the FIFO with CMD53. Note that the *requested length* should not be larger than calculated in step3, and
the FIFO address is related to *requested length*.
5. Recored read length.

View File

@ -15,6 +15,7 @@ Peripherals API
Remote Control <rmt>
SDMMC Host <sdmmc_host>
SD SPI Host <sdspi_host>
SDIO Slave <sdio_slave>
Sigma-delta Modulation <sigmadelta>
SPI Master <spi_master>
SPI Slave <spi_slave>

View File

@ -0,0 +1,227 @@
SDIO Card Slave Driver
======================
Overview
--------
.. note:: At the moment, this code has been proven to work on the Wrover-Kit V3. Earlier versions of the Wrover-Kit
and other development kits are electrically incompatible with this code. Functionality on other devboards is untested.
The ESP32 SDIO Card peripherals (Host, Slave) shares two sets of pins as below table.
The first set is usually occupied by SPI0 bus which is responsible for the SPI flash holding the code to run.
This means SDIO slave driver can only runs on the second set of pins while SDIO host is not using it.
+----------+-------+-------+
| Pin Name | Slot1 | Slot2 |
+ +-------+-------+
| | GPIO Number |
+==========+=======+=======+
| CLK | 6 | 14 |
+----------+-------+-------+
| CMD | 11 | 15 |
+----------+-------+-------+
| DAT0 | 7 | 2 |
+----------+-------+-------+
| DAT1 | 8 | 4 |
+----------+-------+-------+
| DAT2 | 9 | 12 |
+----------+-------+-------+
| DAT3 | 10 | 13 |
+----------+-------+-------+
The SDIO slave can run under 3 modes: SPI, 1-bit SD and 4-bit SD modes, which is detected automatically by the
hardware. According to the SDIO specification, the host initialize the slave into SD mode by first sending CMD0 with
DAT3 pin high, while initialize the slave into SPI mode by sending CMD0 with CS pin (the same pin as DAT3) low. After the
initialization, the host can enable the 4-bit SD mode by writing CCCR register 0x07 by CMD52. All the bus detection
process are handled by the slave peripheral.
The host has to communicate with the slave by an ESP-slave-specific protocol. The slave driver offers 3 services over
Function 1 access by CMD52 and CMD53: (1) a sending FIFO and a receiving FIFO, (2) 52 8-bit R/W registers shared by
host and slave, (3) 16 interrupt sources (8 from host to slave, and 8 from slave to host).
Terminology
^^^^^^^^^^^
The SDIO slave driver uses the following terms:
- Transfer: a transfer is always started by a command token from the host, and may contain a reply and several data
blocks. ESP32 slave software is based on transfers.
- Sending: slave to host transfers.
- Receiving: host to slave transfers.
.. note:: Register names in ESP Rechnical Reference Manual are oriented from the point of view of the host, i.e. 'rx'
registers refer to sending, while 'tx' registers refer to receiving. We're not using `tx` or `rx` in the driver to
avoid ambiguities.
- FIFO: specific address in Function 1 that can be access by CMD53 to read/write large amount of data. The address is
related to the length requested to read from/write to the slave in a single transfer:
*requested length* = 0x1F800-address.
- Ownership: When the driver takes ownership of a buffer, it means the driver can randomly read/write the buffer
(mostly by the hardware). The application should not read/write the buffer until the ownership is returned to the
application. If the application reads from a buffer owned by a receiving driver, the data read can be random; if
the application writes to a buffer owned by a sending driver, the data sent may be corrupted.
- Requested length: The length requested in one transfer determined by the FIFO address.
- Transfer length: The length requested in one transfer determined by the CMD53 byte/block count field.
.. note:: Requested length is different from the transfer length. ESP32 slave DMA base on the *requested length* rather
than the *transfer length*. The *transfer length* should be no shorter than the *requested length*, and the rest
part will be filled with 0 (sending) or discard (receiving).
- Receiving buffer size: The buffer size is pre-defined between the host and the slave before communication starts.
Slave application has to set the buffer size during initialization by the ``recv_buffer_size`` member of
``sdio_slave_config_t``.
- Interrupts: the esp32 slave support interrupts in two directions: from host to slave (called slave interrupts below)
and from slave to host (called host interrupts below). See more in :ref:`interrupts`.
- Registers: specific address in Function 1 access by CMD52 or CMD53.
ESP SDIO Slave Protocol
^^^^^^^^^^^^^^^^^^^^^^^
The communication protocol slave used to communicate with the host is ESP32 specific, please refer to
:doc:`esp_slave_protocol`, or example :example:`peripherals/sdio` for designing a host.
.. toctree::
:hidden:
esp_slave_protocol
.. _interrupts:
Interrupts
^^^^^^^^^^
There are interrupts from host to slave, and from slave to host to help communicating conveniently.
Slave Interrupts
""""""""""""""""
The host can interrupt the slave by writing any one bit in the register 0x08D. Once any bit of the register is
set, an interrupt is raised and the SDIO slave driver calls the callback function defined in the ``slave_intr_cb`` member
in the ``sdio_slave_config_t`` structure.
.. note:: The callback function is called in the ISR, do not use any delay, loop or spinlock in the callback.
There's another set of functions can be used. You can call ``sdio_slave_wait_int`` to wait for an interrupt within a
certain time, or call ``sdio_slave_clear_int`` to clear interrupts from host. The callback function can work with the
wait functions perfectly.
Host Interrupts
"""""""""""""""
The slave can interrupt the host by an interrupt line (at certain time) which is level sensitive. When the host see the
interrupt line pulled down, it may read the slave interrupt status register, to see the interrupt source. Host can clear
interrupt bits, or choose to disable a interrupt source. The interrupt line will hold active until all the sources are
cleared or disabled.
There are several dedicated interrupt sources as well as general purpose sources. see ``sdio_slave_hostint_t`` for
more information.
Shared Registers
^^^^^^^^^^^^^^^^
There are 52 8-bit R/W shared registers to share information between host and slave. The slave can write or read the
registers at any time by ``sdio_slave_read_reg`` and ``sdio_slave_write_reg``. The host can access (R/W) the register by CMD52 or CMD53.
Receiving FIFO
^^^^^^^^^^^^^^
When the host is going to send the slave some packets, it has to check whether the slave is ready to receive by reading
the buffer number of slave.
To allow the host sending data to the slave, the application has to load buffers to the slave driver by the following steps:
1. Register the buffer by calling ``sdio_slave_recv_register_buf``, and get the handle of the registered buffer. The driver
will allocate memory for the linked-list descriptor needed to link the buffer onto the hardware.
2. Load buffers onto the driver by passing the buffer handle to ``sdio_slave_recv_load_buf``.
3. Call ``sdio_slave_recv`` to get the received data. If non-blocking call is needed, set ``wait=0``.
4. Pass the handle of processed buffer back to the driver by ``sdio_recv_load_buf`` again.
.. note:: To avoid overhead from copying data, the driver itself doesn't have any buffer inside, the application is
responsible to offer new buffers in time. The DMA will automatically store received data to the buffer.
Sending FIFO
^^^^^^^^^^^^
Each time the slave has data to send, it raises an interrupt and the host will request for the packet length. There are
two sending modes:
- Stream Mode: when a buffer is loaded to the driver, the buffer length will be counted into the packet length requested
by host in the incoming communications. Regardless previous packets are sent or not. This means the host can get data
of several buffers in one transfer.
- Packet Mode: the packet length is updated packet by packet, and only when previous packet is sent. This means that the
host can only get data of one buffer in one transfer.
.. note:: To avoid overhead from copying data, the driver itself doesn't have any buffer inside. Namely, the DMA takes
data directly from the buffer provided by the application. The application should not touch the buffer until the
sending is finished.
The sending mode can be set in the ``sending_mode`` member of ``sdio_slave_config_t``, and the buffer numbers can be
set in the ``send_queue_size``. All the buffers are restricted to be no larger than 4092 bytes. Though in the stream
mode several buffers can be sent in one transfer, each buffer is still counted as one in the queue.
The application can call ``sdio_slave_transmit`` to send packets. In this case the function returns when the transfer
is sucessfully done, so the queue is not fully used. When higher effeciency is required, the application can use the
following functions instead:
1. Pass buffer information (address, length, as well as an ``arg`` indicating the buffer) to ``sdio_slave_send_queue``.
If non-blocking call is needed, set ``wait=0``. If the ``wait`` is not ``portMAX_DELAY`` (wait until success),
application has to check the result to know whether the data is put in to the queue or discard.
2. Call ``sdio_slave_send_get_finished`` to get and deal with a finished transfer. A buffer should be keep unmodified
until returned from ``sdio_slave_send_get_finished``. This means the buffer is actually sent to the host, rather
than just staying in the queue.
There are several ways to use the ``arg`` in the queue parameter:
1. Directly point ``arg`` to a dynamic-allocated buffer, and use the ``arg`` to free it when transfer finished.
2. Wrap transfer informations in a transfer structure, and point ``arg`` to the structure. You can use the
structure to do more things like::
typedef struct {
uint8_t* buffer;
size_t size;
int id;
}sdio_transfer_t;
//and send as:
sdio_transfer_t trans = {
.buffer = ADDRESS_TO_SEND,
.size = 8,
.id = 3, //the 3rd transfer so far
};
sdio_slave_send_queue(trans.buffer, trans.size, &trans, portMAX_DELAY);
//... maybe more transfers are sent here
//and deal with finished transfer as:
sdio_transfer_t* arg = NULL;
sdio_slave_send_get_finished((void**)&arg, portMAX_DELAY);
ESP_LOGI("tag", "(%d) successfully send %d bytes of %p", arg->id, arg->size, arg->buffer);
some_post_callback(arg); //do more things
3. Working with the receiving part of this driver, point ``arg`` to the receive buffer handle of this buffer. So
that we can directly use the buffer to receive data when it's sent::
uint8_t buffer[256]={1,2,3,4,5,6,7,8};
sdio_slave_buf_handle_t handle = sdio_slave_recv_register_buf(buffer);
sdio_slave_send_queue(buffer, 8, handle, portMAX_DELAY);
//... maybe more transfers are sent here
//and load finished buffer to receive as
sdio_slave_buf_handle_t handle = NULL;
sdio_slave_send_get_finished((void**)&handle, portMAX_DELAY);
sdio_slave_recv_load_buf(handle);
More about this, see :example:`peripherals/sdio`.
Application Example
-------------------
Slave/master communication: :example:`peripherals/sdio`.
API Reference
-------------
.. include:: /_build/inc/sdio_slave.inc

View File

@ -0,0 +1 @@
.. include:: ../../../en/api-reference/peripherals/esp_slave_protocol.rst

View File

@ -0,0 +1 @@
.. include:: ../../../en/api-reference/peripherals/sdio_slave.rst