1 /* 2 * SPDX-FileCopyrightText: 2022-2024 Espressif Systems (Shanghai) CO LTD 3 * 4 * SPDX-License-Identifier: Apache-2.0 5 */ 6 7 #pragma once 8 9 #include <stdint.h> 10 #include <stdbool.h> 11 #include "esp_assert.h" 12 #include "esp_macros.h" 13 #include "esp_err.h" 14 #include "esp_bit_defs.h" 15 #include "soc/soc_caps.h" 16 17 #ifdef __cplusplus 18 extern "C" { 19 #endif 20 21 #if SOC_PAU_SUPPORTED 22 #include "hal/pau_types.h" 23 24 #define REGDMA_LINK_DBG 0 /* Enable REGDMA link info dump apis*/ 25 #define REGDMA_LINK_ENTRY_NUM (PAU_REGDMA_LINK_NUM) /* Maximum number of REG DMA linked list entries */ 26 27 #define ENTRY(n) (BIT(n)) 28 29 #define REGDMA_PHY_LINK(_pri) ((0x00 << 8) | _pri) 30 #define REGDMA_PCR_LINK(_pri) ((0x01 << 8) | _pri) 31 #define REGDMA_MODEMSYSCON_LINK(_pri) ((0x02 << 8) | _pri) 32 #define REGDMA_MODEMLPCON_LINK(_pri) ((0x03 << 8) | _pri) 33 34 #define REGDMA_INTMTX_LINK(_pri) ((0x0d << 8) | _pri) 35 #define REGDMA_HPSYS_LINK(_pri) ((0x0e << 8) | _pri) 36 #define REGDMA_TEEAPM_LINK(_pri) ((0x0f << 8) | _pri) 37 38 #define REGDMA_UART_LINK(_pri) ((0x10 << 8) | _pri) 39 #define REGDMA_TIMG_LINK(_pri) ((0x11 << 8) | _pri) 40 #define REGDMA_IOMUX_LINK(_pri) ((0x12 << 8) | _pri) 41 #define REGDMA_SPIMEM_LINK(_pri) ((0x13 << 8) | _pri) 42 #define REGDMA_SYSTIMER_LINK(_pri) ((0x14 << 8) | _pri) 43 #define REGDMA_BLE_MAC_LINK(_pri) ((0x15 << 8) | _pri) 44 #define REGDMA_MODEM_BT_BB_LINK(_pri) ((0x16 << 8) | _pri) 45 #define REGDMA_MODEM_IEEE802154_LINK(_pri) ((0x17 << 8) | _pri) 46 #define REGDMA_MODEM_GDMA_LINK(_pri) ((0x18 << 8) | _pri) 47 #define REGDMA_MODEM_FE_LINK(_pri) ((0xFF << 8) | _pri) 48 49 typedef enum { 50 REGDMA_LINK_PRI_0 = 0, 51 REGDMA_LINK_PRI_1, 52 REGDMA_LINK_PRI_2, 53 REGDMA_LINK_PRI_3, 54 REGDMA_LINK_PRI_4, 55 REGDMA_LINK_PRI_5, 56 REGDMA_LINK_PRI_6, 57 REGDMA_LINK_PRI_7, 58 } regdma_link_priority_t; 59 60 typedef pau_regdma_link_addr_t regdma_entry_buf_t; 61 62 typedef enum regdma_link_mode { 63 REGDMA_LINK_MODE_CONTINUOUS = 0, /*!< Link used to backup registers with consecutive addresses */ 64 REGDMA_LINK_MODE_ADDR_MAP, /*!< Link used to backup selected registers according to bitmap */ 65 REGDMA_LINK_MODE_WRITE, /*!< Link used to direct write to registers*/ 66 REGDMA_LINK_MODE_WAIT /*!< Link used to wait for register value to meet condition*/ 67 } regdma_link_mode_t; 68 69 70 #define REGDMA_LINK_PRI_SYS_CLK REGDMA_LINK_PRI_0 71 #define REGDMA_LINK_PRI_MODEM_CLK REGDMA_LINK_PRI_1 72 #define REGDMA_LINK_PRI_CRITICAL_TEE_APM REGDMA_LINK_PRI_2 73 #define REGDMA_LINK_PRI_WIFI_MAC_BB REGDMA_LINK_PRI_3 74 #define REGDMA_LINK_PRI_NON_CRITICAL_TEE_APM REGDMA_LINK_PRI_4 75 #define REGDMA_LINK_PRI_BT_MAC_BB REGDMA_LINK_PRI_5 76 #define REGDMA_LINK_PRI_SYS_PERIPH_HIGH REGDMA_LINK_PRI_5 // INT_MTX & HP_SYSTEM & Console UART 77 #define REGDMA_LINK_PRI_SYS_PERIPH_LOW REGDMA_LINK_PRI_6 // TG0 & IO MUX & SPI MEM & Systimer 78 #define REGDMA_LINK_PRI_IEEE802154 REGDMA_LINK_PRI_7 79 #define REGDMA_LINK_PRI_GDMA REGDMA_LINK_PRI_7 80 81 typedef struct regdma_link_head { 82 volatile uint32_t length: 10, /* total count of registers that need to be backup or restore, unit: 1 word = 4 bytes */ 83 reserve0: 6, 84 mode : 4, /* mode of current link */ 85 reserve1: 8, 86 branch : 1, /* branch link flag */ 87 skip_r : 1, /* skip the current linked node when restore the register */ 88 skip_b : 1, /* skip the current linked node when backup the register */ 89 eof : 1; /* end of link */ 90 } regdma_link_head_t; 91 92 /* Continuous type linked list node body type definition */ 93 typedef struct regdma_link_continuous_body { 94 volatile void *next; 95 volatile void *backup; 96 volatile void *restore; 97 volatile void *mem; 98 } regdma_link_continuous_body_t; 99 100 /* Address Map type linked list node body type definition */ 101 typedef struct regdma_link_addr_map_body { 102 volatile void *next; 103 volatile void *backup; 104 volatile void *restore; 105 volatile void *mem; 106 volatile uint32_t map[4]; 107 } regdma_link_addr_map_body_t; 108 109 /* Write/Wait type linked list node body type definition */ 110 typedef struct regdma_link_write_wait_body { 111 volatile void *next; 112 volatile void *backup; 113 volatile uint32_t value; 114 volatile uint32_t mask; 115 } regdma_link_write_wait_body_t; 116 117 /* Branch Continuous type linked list node body type definition */ 118 typedef struct regdma_link_branch_continuous_body { 119 regdma_entry_buf_t next; 120 volatile void *backup; 121 volatile void *restore; 122 volatile void *mem; 123 } regdma_link_branch_continuous_body_t; 124 125 /* Branch Address Map type linked list node body type definition */ 126 typedef struct regdma_link_branch_addr_map_body { 127 regdma_entry_buf_t next; 128 volatile void *backup; 129 volatile void *restore; 130 volatile void *mem; 131 volatile uint32_t map[4]; 132 } regdma_link_branch_addr_map_body_t; 133 134 /* Branch Write/Wait type linked list node body type definition */ 135 typedef struct regdma_link_branch_write_wait_body { 136 regdma_entry_buf_t next; 137 volatile void *backup; 138 volatile uint32_t value; 139 volatile uint32_t mask; 140 } regdma_link_branch_write_wait_body_t; 141 142 ESP_STATIC_ASSERT(REGDMA_LINK_ENTRY_NUM < 16, "regdma link entry number should less 16"); 143 typedef struct regdma_link_stats { 144 volatile uint32_t ref: REGDMA_LINK_ENTRY_NUM, /* a bitmap, identifies which entry has referenced the current link */ 145 reserve: 16-REGDMA_LINK_ENTRY_NUM, 146 id: 16; /* REGDMA linked list node unique identifier */ 147 volatile uint32_t module; /* a bitmap used to identify the module to which the current node belongs */ 148 } regdma_link_stats_t; 149 150 typedef struct regdma_link_continuous { 151 regdma_link_stats_t stat; 152 regdma_link_head_t head; 153 regdma_link_continuous_body_t body; 154 volatile uint32_t buff[0]; 155 } regdma_link_continuous_t; 156 157 typedef struct regdma_link_addr_map { 158 regdma_link_stats_t stat; 159 regdma_link_head_t head; 160 regdma_link_addr_map_body_t body; 161 volatile uint32_t buff[0]; 162 } regdma_link_addr_map_t; 163 164 typedef struct regdma_link_write_wait { 165 regdma_link_stats_t stat; 166 regdma_link_head_t head; 167 regdma_link_write_wait_body_t body; 168 } regdma_link_write_wait_t; 169 170 typedef struct regdma_link_branch_continuous { 171 regdma_link_stats_t stat; 172 regdma_link_head_t head; 173 regdma_link_branch_continuous_body_t body; 174 volatile uint32_t buff[0]; 175 } regdma_link_branch_continuous_t; 176 177 typedef struct regdma_link_branch_addr_map { 178 regdma_link_stats_t stat; 179 regdma_link_head_t head; 180 regdma_link_branch_addr_map_body_t body; 181 volatile uint32_t buff[0]; 182 } regdma_link_branch_addr_map_t; 183 184 typedef struct regdma_link_branch_write_wait { 185 regdma_link_stats_t stat; 186 regdma_link_head_t head; 187 regdma_link_branch_write_wait_body_t body; 188 } regdma_link_branch_write_wait_t; 189 190 typedef struct regdma_link_config { 191 regdma_link_head_t head; 192 union { 193 regdma_link_continuous_body_t continuous; 194 regdma_link_addr_map_body_t addr_map; 195 regdma_link_write_wait_body_t write_wait; 196 }; 197 int id; /* REGDMA linked list node unique identifier */ 198 } regdma_link_config_t; 199 200 #define REGDMA_LINK_HEAD(plink) (((regdma_link_config_t *)plink)->head) 201 202 #define REGDMA_LINK_HEAD_INIT(_l, _m, _b, _sr, _sb) \ 203 { \ 204 .length = (_l), \ 205 .mode = (_m), \ 206 .branch = (_b), \ 207 .skip_r = (_sr), \ 208 .skip_b = (_sb), \ 209 .eof = 0 \ 210 } 211 212 #define REGDMA_LINK_CONTINUOUS_INIT(_id, _backup, _restore, _len, _skip_b, _skip_r) \ 213 { \ 214 .head = REGDMA_LINK_HEAD_INIT( \ 215 _len, \ 216 REGDMA_LINK_MODE_CONTINUOUS,\ 217 0, \ 218 _skip_r, \ 219 _skip_b \ 220 ), \ 221 .continuous = { \ 222 .next = NULL, \ 223 .backup = (void *)_backup, \ 224 .restore = (void *)_restore, \ 225 .mem = NULL \ 226 }, \ 227 .id = (_id) \ 228 } 229 230 #define REGDMA_LINK_ADDR_MAP_INIT(_id, _backup, _restore, _len, _skip_b, _skip_r, ...) \ 231 { \ 232 .head = REGDMA_LINK_HEAD_INIT( \ 233 _len, \ 234 REGDMA_LINK_MODE_ADDR_MAP, \ 235 0, \ 236 _skip_r, \ 237 _skip_b \ 238 ), \ 239 .addr_map = { \ 240 .next = NULL, \ 241 .backup = (void *)_backup, \ 242 .restore = (void *)_restore, \ 243 .mem = NULL, \ 244 .map = {__VA_ARGS__} \ 245 }, \ 246 .id = (_id) \ 247 } 248 249 #define REGDMA_LINK_WRITE_INIT(_id, _backup, _val, _mask, _skip_b, _skip_r) \ 250 { \ 251 .head = REGDMA_LINK_HEAD_INIT( \ 252 0, \ 253 REGDMA_LINK_MODE_WRITE, \ 254 0, \ 255 _skip_r, \ 256 _skip_b \ 257 ), \ 258 .write_wait = { \ 259 .next = NULL, \ 260 .backup = (void *)_backup, \ 261 .value = (_val), \ 262 .mask = (_mask) \ 263 }, \ 264 .id = (_id) \ 265 } 266 267 #define REGDMA_LINK_WAIT_INIT(_id, _backup, _val, _mask, _skip_b, _skip_r) \ 268 { \ 269 .head = REGDMA_LINK_HEAD_INIT( \ 270 0, \ 271 REGDMA_LINK_MODE_WAIT, \ 272 0, \ 273 _skip_r, \ 274 _skip_b \ 275 ), \ 276 .write_wait = { \ 277 .next = NULL, \ 278 .backup = (void *)_backup, \ 279 .value = (_val), \ 280 .mask = (_mask) \ 281 }, \ 282 .id = (_id) \ 283 } 284 285 286 /** 287 * @brief Create a REGDMA continuous type linked list node without retention buffer and the retention buffer is passed in by the caller 288 * @param backup Register address to be backed up by REGDMA 289 * @param buff Retention buffer, it needs to be allocated by the caller and passed in by this argument 290 * @param len Number of registers to be backed up 291 * @param restore Register address to be restored by REGDMA 292 * @param next The next REGDMA linked list node 293 * @param skip_b Skip backup, True means that REGDMA skips the current node when executing the backup task 294 * @param skip_r Skip restore, True means that REGDMA skips the current node when executing the restore task 295 * @param id REGDMA linked list node unique identifier, the caller needs to ensure that the id of each node is unique 296 * @param module The module identifier of the current linked list node 297 * @return Created REGDMA linked list node pointer 298 */ 299 void *regdma_link_new_continuous(void *backup, void *buff, int len, void *restore, void *next, bool skip_b, bool skip_r, int id, uint32_t module); 300 301 /** 302 * @brief Create a REGDMA addr_map type linked list node without retention buffer and the retention buffer is passed in by the caller 303 * @param backup Register address to be backed up by REGDMA 304 * @param buff Retention buffer, it needs to be allocated by the caller and passed in by this argument 305 * @param bitmap The register bitmap that needs to be backed up and restored. when the bitmap corresponding to the 306 * register is 1, it needs to be backed up or restored, otherwise the corresponding register is skipped. 307 * @param len Number of registers to be backed up 308 * @param restore Register address to be restored by REGDMA 309 * @param next The next REGDMA linked list node 310 * @param skip_b Skip backup, True means that REGDMA skips the current node when executing the backup task 311 * @param skip_r Skip restore, True means that REGDMA skips the current node when executing the restore task 312 * @param id REGDMA linked list node unique identifier, the caller needs to ensure that the id of each node is unique 313 * @param module The module identifier of the current linked list node 314 * @return Created REGDMA linked list node pointer 315 */ 316 void *regdma_link_new_addr_map(void *backup, void *buff, uint32_t bitmap[4], int len, void *restore, void *next, bool skip_b, bool skip_r, int id, uint32_t module); 317 318 /** 319 * @brief Create a REGDMA write type linked list node without retention buffer and the retention buffer is passed in by the caller 320 * @param backup Register address to be backed up by REGDMA 321 * @param value The value to be written to the register 322 * @param mask The mask of value 323 * @param next The next REGDMA linked list node 324 * @param skip_b Skip backup, True means that REGDMA skips the current node when executing the backup task 325 * @param skip_r Skip restore, True means that REGDMA skips the current node when executing the restore task 326 * @param id REGDMA linked list node unique identifier, the caller needs to ensure that the id of each node is unique 327 * @param module The module identifier of the current linked list node 328 * @return Created REGDMA linked list node pointer 329 */ 330 void *regdma_link_new_write(void *backup, uint32_t value, uint32_t mask, void *next, bool skip_b, bool skip_r, int id, uint32_t module); 331 332 /** 333 * @brief Create a REGDMA write type linked list node without retention buffer and the retention buffer is passed in by the caller 334 * @param backup Register address to be backed up by REGDMA 335 * @param value The register value that needs to be waited for 336 * @param mask The mask of value 337 * @param next The next REGDMA linked list node 338 * @param skip_b Skip backup, True means that REGDMA skips the current node when executing the backup task 339 * @param skip_r Skip restore, True means that REGDMA skips the current node when executing the restore task 340 * @param id REGDMA linked list node unique identifier, the caller needs to ensure that the id of each node is unique 341 * @param module The module identifier of the current linked list node 342 * @return Created REGDMA linked list node pointer 343 */ 344 void *regdma_link_new_wait(void *backup, uint32_t value, uint32_t mask, void *next, bool skip_b, bool skip_r, int id, uint32_t module); 345 346 /** 347 * @brief Create a REGDMA continuouos branch list node without retention buffer and the retention buffer is passed in by the caller 348 * @param backup Register address to be backed up by REGDMA 349 * @param buff Retention buffer, it needs to be allocated by the caller and passed in by this argument 350 * @param len Number of registers to be backed up 351 * @param restore Register address to be restored by REGDMA 352 * @param next The next REGDMA linked list node (supports up to 4 next pointers) 353 * @param skip_b Skip backup, True means that REGDMA skips the current node when executing the backup task 354 * @param skip_r Skip restore, True means that REGDMA skips the current node when executing the restore task 355 * @param id REGDMA linked list node unique identifier, the caller needs to ensure that the id of each node is unique 356 * @param module The module identifier of the current linked list node 357 * @return Created REGDMA linked list node pointer 358 */ 359 void *regdma_link_new_branch_continuous(void *backup, void *buff, int len, void *restore, regdma_entry_buf_t *next, bool skip_b, bool skip_r, int id, uint32_t module); 360 361 /** 362 * @brief Create a REGDMA addr_map branch list node without retention buffer and the retention buffer is passed in by the caller 363 * @param backup Register address to be backed up by REGDMA 364 * @param buff Retention buffer, it needs to be allocated by the caller and passed in by this argument 365 * @param bitmap The register bitmap that needs to be backed up and restored. when the bitmap corresponding to the 366 * register is 1, it needs to be backed up or restored, otherwise the corresponding register is skipped. 367 * @param len Number of registers to be backed up 368 * @param restore Register address to be restored by REGDMA 369 * @param next The next REGDMA linked list node (supports up to 4 next pointers) 370 * @param skip_b Skip backup, True means that REGDMA skips the current node when executing the backup task 371 * @param skip_r Skip restore, True means that REGDMA skips the current node when executing the restore task 372 * @param id REGDMA linked list node unique identifier, the caller needs to ensure that the id of each node is unique 373 * @param module The module identifier of the current linked list node 374 * @return Created REGDMA linked list node pointer 375 */ 376 void *regdma_link_new_branch_addr_map(void *backup, void *buff, uint32_t bitmap[4], int len, void *restore, regdma_entry_buf_t *next, bool skip_b, bool skip_r, int id, uint32_t module); 377 378 /** 379 * @brief Create a REGDMA write branch list node without retention buffer and the retention buffer is passed in by the caller 380 * @param backup Register address to be backed up by REGDMA 381 * @param value The value to be written to the register 382 * @param mask The mask of value 383 * @param next The next REGDMA linked list node (supports up to 4 next pointers) 384 * @param skip_b Skip backup, True means that REGDMA skips the current node when executing the backup task 385 * @param skip_r Skip restore, True means that REGDMA skips the current node when executing the restore task 386 * @param id REGDMA linked list node unique identifier, the caller needs to ensure that the id of each node is unique 387 * @param module The module identifier of the current linked list node 388 * @return Created REGDMA linked list node pointer 389 */ 390 void *regdma_link_new_branch_write(void *backup, uint32_t value, uint32_t mask, regdma_entry_buf_t *next, bool skip_b, bool skip_r, int id, uint32_t module); 391 392 /** 393 * @brief Create a REGDMA wait branch list node without retention buffer and the retention buffer is passed in by the caller 394 * @param backup Register address to be backed up by REGDMA 395 * @param value The register value that needs to be waited for 396 * @param mask The mask of value 397 * @param next The next REGDMA linked list node (supports up to 4 next pointers) 398 * @param skip_b Skip backup, True means that REGDMA skips the current node when executing the backup task 399 * @param skip_r Skip restore, True means that REGDMA skips the current node when executing the restore task 400 * @param id REGDMA linked list node unique identifier, the caller needs to ensure that the id of each node is unique 401 * @param module The module identifier of the current linked list node 402 * @return Created REGDMA linked list node pointer 403 */ 404 void *regdma_link_new_branch_wait(void *backup, uint32_t value, uint32_t mask, regdma_entry_buf_t *next, bool skip_b, bool skip_r, int id, uint32_t module); 405 406 /** 407 * @brief Create a default REGDMA continuous type linked list node with retention buffer 408 * @param backup Register address to be backed up by REGDMA 409 * @param len Number of registers to be backed up 410 * @param restore Register address to be restored by REGDMA 411 * @param next The next REGDMA linked list node 412 * @param skip_b Skip backup, True means that REGDMA skips the current node when executing the backup task 413 * @param skip_r Skip restore, True means that REGDMA skips the current node when executing the restore task 414 * @param id REGDMA linked list node unique identifier, the caller needs to ensure that the id of each node is unique 415 * @param module The module identifier of the current linked list node 416 * @return Created REGDMA linked list node pointer 417 */ 418 void *regdma_link_new_continuous_default(void *backup, int len, void *restore, void *next, bool skip_b, bool skip_r, int id, uint32_t module); 419 420 /** 421 * @brief Create a default REGDMA addr_map type linked list node with retention buffer 422 * @param backup Register address to be backed up by REGDMA 423 * @param bitmap The register bitmap that needs to be backed up and restored. when the bitmap corresponding to the 424 * register is 1, it needs to be backed up or restored, otherwise the corresponding register is skipped. 425 * @param len Number of registers to be backed up 426 * @param restore Register address to be restored by REGDMA 427 * @param next The next REGDMA linked list node 428 * @param skip_b Skip backup, True means that REGDMA skips the current node when executing the backup task 429 * @param skip_r Skip restore, True means that REGDMA skips the current node when executing the restore task 430 * @param id REGDMA linked list node unique identifier, the caller needs to ensure that the id of each node is unique 431 * @param module The module identifier of the current linked list node 432 * @return Created REGDMA linked list node pointer 433 */ 434 void *regdma_link_new_addr_map_default(void *backup, uint32_t bitmap[4], int len, void *restore, void *next, bool skip_b, bool skip_r, int id, uint32_t module); 435 436 /** 437 * @brief Create a default REGDMA write type linked list node with retention buffer 438 * @param backup Register address to be backed up by REGDMA 439 * @param value The register value that needs to be waited for 440 * @param mask The mask of value 441 * @param next The next REGDMA linked list node 442 * @param skip_b Skip backup, True means that REGDMA skips the current node when executing the backup task 443 * @param skip_r Skip restore, True means that REGDMA skips the current node when executing the restore task 444 * @param id REGDMA linked list node unique identifier, the caller needs to ensure that the id of each node is unique 445 * @param module The module identifier of the current linked list node 446 * @return Created REGDMA linked list node pointer 447 */ 448 void *regdma_link_new_write_default(void *backup, uint32_t value, uint32_t mask, void *next, bool skip_b, bool skip_r, int id, uint32_t module); 449 450 /** 451 * @brief Create a default REGDMA wait type linked list node with retention buffer 452 * @param backup Register address to be backed up by REGDMA 453 * @param value The register value that needs to be waited for 454 * @param mask The mask of value 455 * @param next The next REGDMA linked list node 456 * @param skip_b Skip backup, True means that REGDMA skips the current node when executing the backup task 457 * @param skip_r Skip restore, True means that REGDMA skips the current node when executing the restore task 458 * @param id REGDMA linked list node unique identifier, the caller needs to ensure that the id of each node is unique 459 * @param module The module identifier of the current linked list node 460 * @return Created REGDMA linked list node pointer 461 */ 462 void *regdma_link_new_wait_default(void *backup, uint32_t value, uint32_t mask, void *next, bool skip_b, bool skip_r, int id, uint32_t module); 463 464 /** 465 * @brief Create a default REGDMA continuous branch list node with retention buffer 466 * @param backup Register address to be backed up by REGDMA 467 * @param len Number of registers to be backed up 468 * @param restore Register address to be restored by REGDMA 469 * @param next The next REGDMA linked list node (supports up to 4 next pointers) 470 * @param skip_b Skip backup, True means that REGDMA skips the current node when executing the backup task 471 * @param skip_r Skip restore, True means that REGDMA skips the current node when executing the restore task 472 * @param id REGDMA linked list node unique identifier, the caller needs to ensure that the id of each node is unique 473 * @param module The module identifier of the current linked list node 474 * @return Created REGDMA linked list node pointer 475 */ 476 void *regdma_link_new_branch_continuous_default(void *backup, int len, void *restore, regdma_entry_buf_t *next, bool skip_b, bool skip_r, int id, uint32_t module); 477 478 /** 479 * @brief Create a default REGDMA addr_map branch list node with retention buffer 480 * @param backup Register address to be backed up by REGDMA 481 * @param bitmap The register bitmap that needs to be backed up and restored. when the bitmap corresponding to the 482 * register is 1, it needs to be backed up or restored, otherwise the corresponding register is skipped. 483 * @param len Number of registers to be backed up 484 * @param restore Register address to be restored by REGDMA 485 * @param next The next REGDMA linked list node (supports up to 4 next pointers) 486 * @param skip_b Skip backup, True means that REGDMA skips the current node when executing the backup task 487 * @param skip_r Skip restore, True means that REGDMA skips the current node when executing the restore task 488 * @param id REGDMA linked list node unique identifier, the caller needs to ensure that the id of each node is unique 489 * @param module The module identifier of the current linked list node 490 * @return Created REGDMA linked list node pointer 491 */ 492 void *regdma_link_new_branch_addr_map_default(void *backup, uint32_t bitmap[4], int len, void *restore, regdma_entry_buf_t *next, bool skip_b, bool skip_r, int id, uint32_t module); 493 494 /** 495 * @brief Create a default REGDMA write branch list node with retention buffer 496 * @param backup Register address to be backed up by REGDMA 497 * @param value The value to be written to the register 498 * @param mask The mask of value 499 * @param next The next REGDMA linked list node (supports up to 4 next pointers) 500 * @param skip_b Skip backup, True means that REGDMA skips the current node when executing the backup task 501 * @param skip_r Skip restore, True means that REGDMA skips the current node when executing the restore task 502 * @param id REGDMA linked list node unique identifier, the caller needs to ensure that the id of each node is unique 503 * @param module The module identifier of the current linked list node 504 * @return Created REGDMA linked list node pointer 505 */ 506 void *regdma_link_new_branch_write_default(void *backup, uint32_t value, uint32_t mask, regdma_entry_buf_t *next, bool skip_b, bool skip_r, int id, uint32_t module); 507 508 /** 509 * @brief Create a default REGDMA wait branch list node with retention buffer 510 * @param backup Register address to be backed up by REGDMA 511 * @param value The register value that needs to be waited for 512 * @param mask The mask of value 513 * @param next The next REGDMA linked list node (supports up to 4 next pointers) 514 * @param skip_b Skip backup, True means that REGDMA skips the current node when executing the backup task 515 * @param skip_r Skip restore, True means that REGDMA skips the current node when executing the restore task 516 * @param id REGDMA linked list node unique identifier, the caller needs to ensure that the id of each node is unique 517 * @param module The module identifier of the current linked list node 518 * @return Created REGDMA linked list node pointer 519 */ 520 void *regdma_link_new_branch_wait_default(void *backup, uint32_t value, uint32_t mask, regdma_entry_buf_t *next, bool skip_b, bool skip_r, int id, uint32_t module); 521 522 /** 523 * @brief Create and initialize a REGDMA linked list node through configuration parameters 524 * @param config REGDMA linked node configuration parameters 525 * @param branch Is it a branch node 526 * @param module The module identifier of the current linked list node 527 * @param nentry The number of next pointers 528 * @param args next pointer, Since REGDMA supports 4 entries, it supports up to 4 variable parameter next pointers, and more will be ignored 529 * @return Initialized REGDMA linked list head node pointer 530 */ 531 void *regdma_link_init(const regdma_link_config_t *config, bool branch, uint32_t module, int nentry, ...); 532 533 /** 534 * @brief Get REGDMA linked list node mode through configuration parameters 535 * @param config REGDMA linked node configuration parameters 536 * @return REGDMA linked list node mode 537 */ 538 regdma_link_mode_t regdma_link_get_config_mode(const regdma_link_config_t *config); 539 540 /** 541 * @brief Recurse the REGDMA linked list and call the hook subroutine for each node 542 * @param link The REGDMA linkded list head pointer 543 * @param entry For nodes that support branching, use the branch specified by entry argument recursively 544 * @param hook Subroutines called during recursion, argument 1 is the pointer to the 545 * recursive node object, argument 2 is the entry to which the node belongs 546 * and the argument 3 is the position of the node in the current linked 547 * list (from head to tail, the position of the head node is 0) 548 * @return The REGDMA linked list node pointer indicated by the link argument 549 */ 550 void *regdma_link_recursive(void *link, int entry, void (*hook)(void *, int, int)); 551 552 /** 553 * @brief Find the linked list node object by node position 554 * @param link The REGDMA linkded list head pointer 555 * @param entry For nodes that support branching, use the branch specified by entry argument recursively 556 * @param pos Node position 557 * @return The linked list node object pointer or NULL 558 */ 559 void *regdma_find_link_by_pos(void *link, int entry, int pos); 560 561 /** 562 * @brief Find the linked list node object by node unique identifier 563 * @param link The REGDMA linkded list head pointer 564 * @param entry For nodes that support branching, use the branch specified by entry argument recursively 565 * @param id REGDMA linked list node unique identifier 566 * @return The linked list node object pointer or NULL 567 */ 568 void *regdma_find_link_by_id(void *link, int entry, int id); 569 570 /** 571 * @brief Destroy the REGDMA linked list indicated by the entry argument 572 * @param link The REGDMA linkded list head pointer 573 * @param entry For nodes that support branching, use the branch specified by entry argument recursively 574 */ 575 void regdma_link_destroy(void *link, int entry); 576 577 /** 578 * @brief Generate the statistics information of the REGDMA linked list indicated by the entry argument 579 * @param link The REGDMA linkded list head pointer 580 * @param entry For nodes that support branching, use the branch specified by entry argument recursively 581 */ 582 void regdma_link_stats(void *link, int entry); 583 584 /** 585 * @brief Set the value and mask of write or wait type REGDMA linked list node 586 * @param link Write or wait type REGDMA linked list node pointer 587 * @param value The value to be written to the register 588 * @param mask The mask of value 589 */ 590 void regdma_link_set_write_wait_content(void *link, uint32_t value, uint32_t mask); 591 592 /** 593 * @brief Dump all node information of the REGDMA linked list indicated by the entry argument 594 * @param link The REGDMA linkded list head pointer 595 * @param entry For nodes that support branching, use the branch specified by entry argument recursively 596 */ 597 void regdma_link_dump(FILE *out, void *link, int entry); 598 599 /** 600 * @brief Update REGDMA linked list node next pointers 601 * @param link The pointer of the REGDMA linked list node whose next field will be modified 602 * @param nentry The number of next pointers 603 */ 604 void regdma_link_update_next(void *link, int nentry, ...); 605 606 /** 607 * @brief Get all node entry reference bitmaps from the start of the link argument to the 608 * end of the tail argument in the REGDMA linked list indicated by the entry argument 609 * @param link The REGDMA linkded list head pointer 610 * @param tail The REGDMA linkded list tail pointer 611 * @param entry For nodes that support branching, use the branch specified by entry argument recursively 612 * @return The entry reference bitmap of all nodes starting from the link argument to the end of the tail argument 613 */ 614 uint32_t regdma_link_get_owner_bitmap(void *link, void *tail, int entry); 615 616 /** 617 * @brief Find the head node of the specified module in the REGDMA linked list indicated by the 618 * entry argument starting from the link argument to the end of the tail argument 619 * @param link The REGDMA linkded list head pointer 620 * @param tail The REGDMA linkded list tail pointer 621 * @param entry For nodes that support branching, use the branch specified by entry argument recursively 622 * @param module Module bitmap Identification 623 * @return The found head node pointer or NULL 624 */ 625 void *regdma_find_module_link_head(void *link, void *tail, int entry, uint32_t module); 626 627 /** 628 * @brief Find the tail node of the specified module in the REGDMA linked list indicated by the 629 * entry argument starting from the link argument to the end of the tail argument 630 * @param link The REGDMA linkded list head pointer 631 * @param tail The REGDMA linkded list tail pointer 632 * @param entry For nodes that support branching, use the branch specified by entry argument recursively 633 * @param module Module bitmap Identification 634 * @return The found tail node pointer or NULL 635 */ 636 void *regdma_find_module_link_tail(void *link, void *tail, int entry, uint32_t module); 637 638 /** 639 * @brief Find the tail node of the previous module of the specified module in the REGDMA linked list 640 * indicated by the entry argument starting from the link argument to the end of the tail argument 641 * @param link The REGDMA linkded list head pointer 642 * @param tail The REGDMA linkded list tail pointer 643 * @param entry For nodes that support branching, use the branch specified by entry argument recursively 644 * @param module Module bitmap Identification 645 * @return The found tail node pointer or NULL 646 */ 647 void *regdma_find_prev_module_link_tail(void *link, void *tail, int entry, uint32_t module); 648 649 /** 650 * @brief Find the head node of the next module of the specified module in the REGDMA linked list 651 * indicated by the entry argument starting from the link argument to the end of the tail argument 652 * @param link The REGDMA linkded list head pointer 653 * @param tail The REGDMA linkded list tail pointer 654 * @param entry For nodes that support branching, use the branch specified by entry argument recursively 655 * @param module Module bitmap Identification 656 * @return The found head node pointer or NULL 657 */ 658 void *regdma_find_next_module_link_head(void *link, void *tail, int entry, uint32_t module); 659 660 #define regdma_link_init_safe(pcfg, branch, module, ...) regdma_link_init((pcfg), (branch), (module), __VA_NARG__(__VA_ARGS__), ##__VA_ARGS__) 661 662 #define regdma_link_update_next_safe(link, ...) regdma_link_update_next((link), __VA_NARG__(__VA_ARGS__), ##__VA_ARGS__) 663 664 #endif // SOC_PAU_SUPPORTED 665 666 #ifdef __cplusplus 667 } 668 #endif 669