Просмотр исходного кода

gdma: support reset dma fifo at runtime

morris 4 лет назад
Родитель
Сommit
270ed70f3e
2 измененных файлов с 32 добавлено и 0 удалено
  1. 19 0
      components/driver/gdma.c
  2. 13 0
      components/driver/include/esp_private/gdma.h

+ 19 - 0
components/driver/gdma.c

@@ -412,6 +412,25 @@ err:
     return ret;
 }
 
+esp_err_t gdma_reset(gdma_channel_handle_t dma_chan)
+{
+    esp_err_t ret = ESP_OK;
+    gdma_pair_t *pair = NULL;
+    gdma_group_t *group = NULL;
+    ESP_GOTO_ON_FALSE(dma_chan, ESP_ERR_INVALID_ARG, err, TAG, "invalid argument");
+    pair = dma_chan->pair;
+    group = pair->group;
+
+    if (dma_chan->direction == GDMA_CHANNEL_DIRECTION_RX) {
+        gdma_ll_rx_reset_channel(group->hal.dev, pair->pair_id);
+    } else {
+        gdma_ll_tx_reset_channel(group->hal.dev, pair->pair_id);
+    }
+
+err:
+    return ret;
+}
+
 static void gdma_uninstall_group(gdma_group_t *group)
 {
     int group_id = group->group_id;

+ 13 - 0
components/driver/include/esp_private/gdma.h

@@ -155,6 +155,7 @@ esp_err_t gdma_new_channel(const gdma_channel_alloc_config_t *config, gdma_chann
  * @brief Connect GDMA channel to trigger peripheral
  *
  * @note Suggest to use helper macro `GDMA_MAKE_TRIGGER` to construct parameter `trig_periph`. e.g. GDMA_MAKE_TRIGGER(GDMA_TRIG_PERIPH_SHA,0)
+ * @note Connecting to a peripheral will also reset the DMA FIFO and FSM automatically
  *
  * @param[in] dma_chan GDMA channel handle, allocated by `gdma_new_channel`
  * @param[in] trig_periph GDMA trigger peripheral
@@ -279,6 +280,18 @@ esp_err_t gdma_stop(gdma_channel_handle_t dma_chan);
  */
 esp_err_t gdma_append(gdma_channel_handle_t dma_chan);
 
+/**
+ * @brief Reset DMA channel FIFO and internal finite state machine
+ * @note Resetting a DMA channel won't break the connection with the target peripheral
+ *
+ * @param[in] dma_chan GDMA channel handle, allocated by `gdma_new_channel`
+ * @return
+ *      - ESP_OK: DMA channel reset successfully
+ *      - ESP_ERR_INVALID_ARG: DMA channel reset failed due to invalid arguments
+ *      - ESP_FAIL: DMA channel reset failed due to other errors
+ */
+esp_err_t gdma_reset(gdma_channel_handle_t dma_chan);
+
 #ifdef __cplusplus
 }
 #endif