| 393 | } |
| 394 | |
| 395 | int |
| 396 | rte_malloc_heap_memory_add(const char *heap_name, void *va_addr, size_t len, |
| 397 | rte_iova_t iova_addrs[], unsigned int n_pages, size_t page_sz) |
| 398 | { |
| 399 | struct malloc_heap *heap = NULL; |
| 400 | struct rte_memseg_list *msl; |
| 401 | unsigned int n; |
| 402 | int ret; |
| 403 | |
| 404 | if (heap_name == NULL || va_addr == NULL || |
| 405 | page_sz == 0 || !rte_is_power_of_2(page_sz) || |
| 406 | RTE_ALIGN(len, page_sz) != len || |
| 407 | !rte_is_aligned(va_addr, page_sz) || |
| 408 | ((len / page_sz) != n_pages && iova_addrs != NULL) || |
| 409 | strnlen(heap_name, RTE_HEAP_NAME_MAX_LEN) == 0 || |
| 410 | strnlen(heap_name, RTE_HEAP_NAME_MAX_LEN) == |
| 411 | RTE_HEAP_NAME_MAX_LEN) { |
| 412 | rte_errno = EINVAL; |
| 413 | return -1; |
| 414 | } |
| 415 | rte_mcfg_mem_write_lock(); |
| 416 | |
| 417 | /* find our heap */ |
| 418 | heap = find_named_heap(heap_name); |
| 419 | if (heap == NULL) { |
| 420 | rte_errno = ENOENT; |
| 421 | ret = -1; |
| 422 | goto unlock; |
| 423 | } |
| 424 | if (heap->socket_id < RTE_MAX_NUMA_NODES) { |
| 425 | /* cannot add memory to internal heaps */ |
| 426 | rte_errno = EPERM; |
| 427 | ret = -1; |
| 428 | goto unlock; |
| 429 | } |
| 430 | n = len / page_sz; |
| 431 | |
| 432 | msl = malloc_heap_create_external_seg(va_addr, iova_addrs, n, page_sz, |
| 433 | heap_name, heap->socket_id); |
| 434 | if (msl == NULL) { |
| 435 | ret = -1; |
| 436 | goto unlock; |
| 437 | } |
| 438 | |
| 439 | rte_spinlock_lock(&heap->lock); |
| 440 | ret = malloc_heap_add_external_memory(heap, msl); |
| 441 | msl->heap = 1; /* mark it as heap segment */ |
| 442 | rte_spinlock_unlock(&heap->lock); |
| 443 | |
| 444 | unlock: |
| 445 | rte_mcfg_mem_write_unlock(); |
| 446 | |
| 447 | return ret; |
| 448 | } |
| 449 | |
| 450 | int |
| 451 | rte_malloc_heap_memory_remove(const char *heap_name, void *va_addr, size_t len) |