This solution utilizes PWM to trigger ADC sampling at specific moments . Simultaneously triggers HDMA to operate the SPI controller at another specific time within the PWM cycle.
Using the HDMA (High-Speed Direct Memory Access) chain mode and implementing it as a circular linked list, the HDMA autonomously executes SPI (Serial Peripheral Interface) read and write tasks. The data read is stored in the designated memory without the need for CPU involvement.
Users can directly utilize the ADC sampling results and SPI encoder information within the ADC completion interrupt to implement subsequent closed-loop algorithms.
Chain transfer with DMA typically reduces the latency of data transfers, which is crucial for real-time systems and applications requiring rapid response.
{
dma_channel_config_t dma_ch_config;
static uint8_t dummy_cmd = 0xff;
static uint8_t dummy_buff1 = 0xff, dummy_buff2 = 0xff;
dma_default_channel_config(HPM_HDMA, &dma_ch_config);
dma_ch_config.size_in_byte = 4;
dma_ch_config.src_addr = core_local_mem_to_sys_address(HPM_CORE0, (uint32_t)&
spi_transctrl[0]);
dma_ch_config.dst_addr = core_local_mem_to_sys_address(HPM_CORE0, (uint32_t)&BOARD_APP_SPI_BASE->TRANSCTRL);
dma_ch_config.src_width = DMA_TRANSFER_WIDTH_WORD;
dma_ch_config.dst_width = DMA_TRANSFER_WIDTH_WORD;
dma_ch_config.src_burst_size = DMA_NUM_TRANSFER_PER_BURST_1T;
dma_ch_config.src_mode = DMA_HANDSHAKE_MODE_HANDSHAKE;
dma_ch_config.dst_mode = DMA_HANDSHAKE_MODE_HANDSHAKE;
dma_ch_config.src_addr_ctrl = DMA_ADDRESS_CONTROL_FIXED;
dma_ch_config.dst_addr_ctrl = DMA_ADDRESS_CONTROL_FIXED;
dma_ch_config.linked_ptr = core_local_mem_to_sys_address(HPM_CORE0, (uint32_t)&
adc_descriptors1[1]);
dma_config_linked_descriptor(HPM_HDMA, &
adc_descriptors1[0], 0, &dma_ch_config);
dma_ch_config.size_in_byte = 1;
dma_ch_config.src_addr = core_local_mem_to_sys_address(HPM_CORE0, (uint32_t)&dummy_cmd);
dma_ch_config.dst_addr = core_local_mem_to_sys_address(HPM_CORE0, (uint32_t)&BOARD_APP_SPI_BASE->CMD);
dma_ch_config.src_width = DMA_TRANSFER_WIDTH_BYTE;
dma_ch_config.dst_width = DMA_TRANSFER_WIDTH_BYTE;
dma_ch_config.src_burst_size = DMA_NUM_TRANSFER_PER_BURST_1T;
dma_ch_config.src_mode = DMA_HANDSHAKE_MODE_NORMAL;
dma_ch_config.dst_mode = DMA_HANDSHAKE_MODE_NORMAL;
dma_ch_config.src_addr_ctrl = DMA_ADDRESS_CONTROL_FIXED;
dma_ch_config.dst_addr_ctrl = DMA_ADDRESS_CONTROL_FIXED;
dma_ch_config.linked_ptr = core_local_mem_to_sys_address(HPM_CORE0, (uint32_t)&
adc_descriptors1[2]);
dma_config_linked_descriptor(HPM_HDMA, &
adc_descriptors1[1], 0, &dma_ch_config);
dma_ch_config.size_in_byte =
sizeof(
sendbuff);
dma_ch_config.src_addr = core_local_mem_to_sys_address(HPM_CORE0, (uint32_t)&
sendbuff);
dma_ch_config.dst_addr = core_local_mem_to_sys_address(HPM_CORE0, (uint32_t)&BOARD_APP_SPI_BASE->DATA);
dma_ch_config.src_width = DMA_TRANSFER_WIDTH_BYTE;
dma_ch_config.dst_width = DMA_TRANSFER_WIDTH_BYTE;
dma_ch_config.src_burst_size = DMA_NUM_TRANSFER_PER_BURST_1T;
dma_ch_config.src_mode = DMA_HANDSHAKE_MODE_NORMAL;
dma_ch_config.dst_mode = DMA_HANDSHAKE_MODE_NORMAL;
dma_ch_config.src_addr_ctrl = DMA_ADDRESS_CONTROL_INCREMENT;
dma_ch_config.dst_addr_ctrl = DMA_ADDRESS_CONTROL_FIXED;
dma_ch_config.linked_ptr = core_local_mem_to_sys_address(HPM_CORE0, (uint32_t)&
adc_descriptors1[3]);
dma_config_linked_descriptor(HPM_HDMA, &
adc_descriptors1[2], 0, &dma_ch_config);
dma_ch_config.size_in_byte = 64;
dma_ch_config.src_addr = core_local_mem_to_sys_address(HPM_CORE0, (uint32_t)&dummy_buff1);
dma_ch_config.dst_addr = core_local_mem_to_sys_address(HPM_CORE0, (uint32_t)&dummy_buff2);
dma_ch_config.src_width = DMA_TRANSFER_WIDTH_BYTE;
dma_ch_config.dst_width = DMA_TRANSFER_WIDTH_BYTE;
dma_ch_config.src_burst_size = DMA_NUM_TRANSFER_PER_BURST_1T;
dma_ch_config.src_mode = DMA_HANDSHAKE_MODE_NORMAL;
dma_ch_config.dst_mode = DMA_HANDSHAKE_MODE_NORMAL;
dma_ch_config.src_addr_ctrl = DMA_ADDRESS_CONTROL_FIXED;
dma_ch_config.dst_addr_ctrl = DMA_ADDRESS_CONTROL_FIXED;
dma_ch_config.linked_ptr = core_local_mem_to_sys_address(HPM_CORE0, (uint32_t)&
adc_descriptors1[4]);
dma_config_linked_descriptor(HPM_HDMA, &
adc_descriptors1[3], 0, &dma_ch_config);
dma_ch_config.size_in_byte =
sizeof(
spi_buf);
dma_ch_config.src_addr = core_local_mem_to_sys_address(HPM_CORE0, (uint32_t)&BOARD_APP_SPI_BASE->DATA);
dma_ch_config.dst_addr = core_local_mem_to_sys_address(HPM_CORE0, (uint32_t)&
spi_buf);
dma_ch_config.src_width = DMA_TRANSFER_WIDTH_BYTE;
dma_ch_config.dst_width = DMA_TRANSFER_WIDTH_BYTE;
dma_ch_config.src_burst_size = DMA_NUM_TRANSFER_PER_BURST_1T;
dma_ch_config.src_mode = DMA_HANDSHAKE_MODE_NORMAL;
dma_ch_config.dst_mode = DMA_HANDSHAKE_MODE_NORMAL;
dma_ch_config.src_addr_ctrl = DMA_ADDRESS_CONTROL_FIXED;
dma_ch_config.dst_addr_ctrl = DMA_ADDRESS_CONTROL_INCREMENT;
dma_ch_config.linked_ptr = core_local_mem_to_sys_address(HPM_CORE0, (uint32_t)&
adc_descriptors1[0]);
dma_config_linked_descriptor(HPM_HDMA, &
adc_descriptors1[4], 0, &dma_ch_config);
}
uint8_t spi_buf[4]
Definition: adc16.c:75
static uint32_t spi_transctrl[5]
Definition: adc16.c:84
uint8_t sendbuff[2]
Definition: adc16.c:73
dma_linked_descriptor_t adc_descriptors1[6]
Definition: adc16.c:82
void hdma_spi_tx_chain_config(void)
HDMA chain transmission configuration;HDMA链式传输配置 task 1:SPI->TRANSCTRL configuration; ;SPI数据格式配置 task...
Definition: adc16.c:238
#define PWM_FREQUENCY (20000)
#define PWM_RELOAD (clock_get_frequency(clock_mot0) / PWM_FREQUENCY - 1)
{
pwm_cmp_config_t pwm_cmp_cfg;
pwm_cmp_config_t pwm_cmp_cfg_spi[2];
pwm_output_channel_t pwm_output_ch_cfg;
memset(&pwm_cmp_cfg, 0x00, sizeof(pwm_cmp_config_t));
pwm_cmp_cfg.enable_ex_cmp = false;
pwm_cmp_cfg.mode = pwm_cmp_mode_output_compare;
pwm_cmp_cfg.update_trigger = pwm_shadow_register_update_on_shlk;
pwm_cmp_cfg.cmp = 2999;
pwm_cmp_cfg_spi[0].enable_ex_cmp = false;
pwm_cmp_cfg_spi[0].mode = pwm_cmp_mode_output_compare;
pwm_cmp_cfg_spi[0].update_trigger = pwm_shadow_register_update_on_shlk;
pwm_cmp_cfg_spi[0].cmp = 4999;
pwm_enable_dma_request(HPM_PWM0, PWM_IRQ_CMP(9));
pwm_output_ch_cfg.invert_output = false;
pwm_start_counter(ptr);
}
#define APP_ADC16_PMT_PWM_REFCH_A
Definition: adc16.c:51
#define PWM_RELOAD
Definition: adc16.c:180
#define APP_ADC16_PMT_PWM
Definition: adc16.c:52
void init_trigger_source(PWM_Type *ptr)
Initialize trigger source ;初始化触发源PWM.
Definition: adc16.c:183