Skip to content

Commit a75eab4

Browse files
committed
Merge branch 'change/bs_cmake_cleanup_v5.4' into 'release/v5.4'
feat(gdma): added help function to count the bytes in the receive buffer (v5.4) See merge request espressif/esp-idf!36375
2 parents bd5c6b0 + 2d6bc67 commit a75eab4

File tree

2 files changed

+60
-17
lines changed

2 files changed

+60
-17
lines changed

components/esp_hw_support/dma/gdma_link.c

Lines changed: 48 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* SPDX-FileCopyrightText: 2023-2024 Espressif Systems (Shanghai) CO LTD
2+
* SPDX-FileCopyrightText: 2023-2025 Espressif Systems (Shanghai) CO LTD
33
*
44
* SPDX-License-Identifier: Apache-2.0
55
*/
@@ -141,21 +141,22 @@ esp_err_t gdma_del_link_list(gdma_link_list_handle_t list)
141141
return ESP_OK;
142142
}
143143

144-
esp_err_t gdma_link_mount_buffers(gdma_link_list_handle_t list, uint32_t start_item_index, const gdma_buffer_mount_config_t *buf_config_array, size_t num_buf, uint32_t *end_item_index)
144+
esp_err_t gdma_link_mount_buffers(gdma_link_list_handle_t list, int start_item_index, const gdma_buffer_mount_config_t *buf_config_array, size_t num_buf, int *end_item_index)
145145
{
146146
ESP_RETURN_ON_FALSE(list && buf_config_array && num_buf, ESP_ERR_INVALID_ARG, TAG, "invalid argument");
147-
ESP_RETURN_ON_FALSE(start_item_index < list->num_items, ESP_ERR_INVALID_ARG, TAG, "invalid start item index");
148147
size_t buffer_alignment = list->buffer_alignment;
149148
size_t item_size = list->item_size;
150149
uint32_t list_item_capacity = list->num_items;
150+
// ensure the start_item_index is between 0 and `list_item_capacity - 1`
151+
start_item_index = (start_item_index % list_item_capacity + list_item_capacity) % list_item_capacity;
151152
size_t max_buffer_mount_length = ALIGN_DOWN(GDMA_MAX_BUFFER_SIZE_PER_LINK_ITEM, buffer_alignment);
152153
uint32_t begin_item_idx = start_item_index;
153154
gdma_link_list_item_t *lli_nc = NULL;
154155

155156
uint32_t num_items_avail = 0;
156157
// if the link list is responsible for checking the ownership, we need to skip the items that are owned by the DMA
157158
if (list->flags.check_owner) {
158-
for (uint32_t i = 0; i < list_item_capacity; i++) {
159+
for (int i = 0; i < list_item_capacity; i++) {
159160
lli_nc = (gdma_link_list_item_t *)(list->items_nc + (i + start_item_index) % list_item_capacity * item_size);
160161
if (lli_nc->dw0.owner == GDMA_LLI_OWNER_CPU) {
161162
num_items_avail++;
@@ -166,8 +167,8 @@ esp_err_t gdma_link_mount_buffers(gdma_link_list_handle_t list, uint32_t start_i
166167
}
167168

168169
// check alignment and length for each buffer
169-
for (size_t i = 0; i < num_buf; i++) {
170-
const gdma_buffer_mount_config_t *config = &buf_config_array[i];
170+
for (size_t bi = 0; bi < num_buf; bi++) {
171+
const gdma_buffer_mount_config_t *config = &buf_config_array[bi];
171172
uint8_t *buf = (uint8_t *)config->buffer;
172173
size_t len = config->length;
173174
// check the buffer alignment
@@ -183,8 +184,8 @@ esp_err_t gdma_link_mount_buffers(gdma_link_list_handle_t list, uint32_t start_i
183184
lli_nc->next = (gdma_link_list_item_t *)(list->items + start_item_index * item_size);
184185

185186
begin_item_idx = start_item_index;
186-
for (size_t i = 0; i < num_buf; i++) {
187-
const gdma_buffer_mount_config_t *config = &buf_config_array[i];
187+
for (size_t bi = 0; bi < num_buf; bi++) {
188+
const gdma_buffer_mount_config_t *config = &buf_config_array[bi];
188189
uint8_t *buf = (uint8_t *)config->buffer;
189190
size_t len = config->length;
190191
// skip zero-length buffer
@@ -193,7 +194,7 @@ esp_err_t gdma_link_mount_buffers(gdma_link_list_handle_t list, uint32_t start_i
193194
}
194195
uint32_t num_items_need = (len + max_buffer_mount_length - 1) / max_buffer_mount_length;
195196
// mount the buffer to the link list
196-
for (uint32_t i = 0; i < num_items_need; i++) {
197+
for (int i = 0; i < num_items_need; i++) {
197198
lli_nc = (gdma_link_list_item_t *)(list->items_nc + (i + begin_item_idx) % list_item_capacity * item_size);
198199
lli_nc->buffer = buf;
199200
lli_nc->dw0.length = len > max_buffer_mount_length ? max_buffer_mount_length : len;
@@ -232,25 +233,57 @@ esp_err_t gdma_link_concat(gdma_link_list_handle_t first_link, int first_link_it
232233
{
233234
ESP_RETURN_ON_FALSE(first_link && second_link, ESP_ERR_INVALID_ARG, TAG, "invalid argument");
234235
gdma_link_list_item_t *lli_nc = NULL;
235-
lli_nc = (gdma_link_list_item_t *)(first_link->items_nc + (first_link->num_items + first_link_item_index) % first_link->num_items * first_link->item_size);
236-
lli_nc->next = (gdma_link_list_item_t *)(second_link->items + (second_link->num_items + second_link_item_index) % second_link->num_items * second_link->item_size);
236+
// ensure the first_link_item_index is between 0 and `num_items - 1`
237+
int num_items = first_link->num_items;
238+
first_link_item_index = (first_link_item_index % num_items + num_items) % num_items;
239+
lli_nc = (gdma_link_list_item_t *)(first_link->items_nc + first_link_item_index * first_link->item_size);
240+
// ensure the second_link_item_index is between 0 and `num_items - 1`
241+
num_items = second_link->num_items;
242+
second_link_item_index = (second_link_item_index % num_items + num_items) % num_items;
243+
// concatenate the two link lists
244+
lli_nc->next = (gdma_link_list_item_t *)(second_link->items + second_link_item_index * second_link->item_size);
237245
return ESP_OK;
238246
}
239247

240248
esp_err_t gdma_link_set_owner(gdma_link_list_handle_t list, int item_index, gdma_lli_owner_t owner)
241249
{
242250
ESP_RETURN_ON_FALSE_ISR(list, ESP_ERR_INVALID_ARG, TAG, "invalid argument");
243-
ESP_RETURN_ON_FALSE_ISR(item_index < list->num_items, ESP_ERR_INVALID_ARG, TAG, "invalid item index");
244-
gdma_link_list_item_t *lli = (gdma_link_list_item_t *)(list->items_nc + (list->num_items + item_index) % list->num_items * list->item_size);
251+
int num_items = list->num_items;
252+
// ensure the item_index is between 0 and `num_items - 1`
253+
item_index = (item_index % num_items + num_items) % num_items;
254+
gdma_link_list_item_t *lli = (gdma_link_list_item_t *)(list->items_nc + item_index * list->item_size);
245255
lli->dw0.owner = owner;
246256
return ESP_OK;
247257
}
248258

249259
esp_err_t gdma_link_get_owner(gdma_link_list_handle_t list, int item_index, gdma_lli_owner_t *owner)
250260
{
251261
ESP_RETURN_ON_FALSE_ISR(list && owner, ESP_ERR_INVALID_ARG, TAG, "invalid argument");
252-
ESP_RETURN_ON_FALSE_ISR(item_index < list->num_items, ESP_ERR_INVALID_ARG, TAG, "invalid item index");
253-
gdma_link_list_item_t *lli = (gdma_link_list_item_t *)(list->items_nc + (list->num_items + item_index) % list->num_items * list->item_size);
262+
int num_items = list->num_items;
263+
// ensure the item_index is between 0 and `num_items - 1`
264+
item_index = (item_index % num_items + num_items) % num_items;
265+
gdma_link_list_item_t *lli = (gdma_link_list_item_t *)(list->items_nc + item_index * list->item_size);
254266
*owner = lli->dw0.owner;
255267
return ESP_OK;
256268
}
269+
270+
size_t gdma_link_count_buffer_size_till_eof(gdma_link_list_handle_t list, int start_item_index)
271+
{
272+
if (!list) {
273+
return 0;
274+
}
275+
int num_items = list->num_items;
276+
// ensure the start_item_index is between 0 and `num_items - 1`
277+
start_item_index = (start_item_index % num_items + num_items) % num_items;
278+
size_t buf_size = 0;
279+
gdma_link_list_item_t *lli_nc = NULL;
280+
for (int i = 0; i < num_items; i++) {
281+
lli_nc = (gdma_link_list_item_t *)(list->items_nc + (start_item_index + i) % num_items * list->item_size);
282+
buf_size += lli_nc->dw0.length;
283+
// break if the current item is the last one or the EOF item
284+
if (lli_nc->dw0.suc_eof || lli_nc->next == NULL) {
285+
break;
286+
}
287+
}
288+
return buf_size;
289+
}

components/esp_hw_support/dma/include/esp_private/gdma_link.h

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* SPDX-FileCopyrightText: 2023-2024 Espressif Systems (Shanghai) CO LTD
2+
* SPDX-FileCopyrightText: 2023-2025 Espressif Systems (Shanghai) CO LTD
33
*
44
* SPDX-License-Identifier: Apache-2.0
55
*/
@@ -91,7 +91,7 @@ typedef struct {
9191
* - ESP_ERR_INVALID_ARG: Mount the buffer failed because of invalid argument
9292
* - ESP_FAIL: Mount the buffer failed because of other error
9393
*/
94-
esp_err_t gdma_link_mount_buffers(gdma_link_list_handle_t list, uint32_t start_item_index, const gdma_buffer_mount_config_t *buf_config_array, size_t num_buf, uint32_t *end_item_index);
94+
esp_err_t gdma_link_mount_buffers(gdma_link_list_handle_t list, int start_item_index, const gdma_buffer_mount_config_t *buf_config_array, size_t num_buf, int *end_item_index);
9595

9696
/**
9797
* @brief Get the address of the head item in the link list
@@ -164,6 +164,16 @@ esp_err_t gdma_link_set_owner(gdma_link_list_handle_t list, int item_index, gdma
164164
*/
165165
esp_err_t gdma_link_get_owner(gdma_link_list_handle_t list, int item_index, gdma_lli_owner_t *owner);
166166

167+
/**
168+
* @brief Get the size of the buffer that is mounted to the link list until the eof item (inclusive)
169+
*
170+
* @param[in] list Link list handle, allocated by `gdma_new_link_list`
171+
* @param[in] start_item_index Index of the first item in the link list to be calculated
172+
* @return Size of the buffer that is mounted to the link list until the eof item (inclusive).
173+
* If the link list is empty or invalid, return 0.
174+
*/
175+
size_t gdma_link_count_buffer_size_till_eof(gdma_link_list_handle_t list, int start_item_index);
176+
167177
#ifdef __cplusplus
168178
}
169179
#endif

0 commit comments

Comments
 (0)