1221167Sgnn/*- 2221167Sgnn * Copyright(c) 2002-2011 Exar Corp. 3221167Sgnn * All rights reserved. 4221167Sgnn * 5221167Sgnn * Redistribution and use in source and binary forms, with or without 6221167Sgnn * modification are permitted provided the following conditions are met: 7221167Sgnn * 8221167Sgnn * 1. Redistributions of source code must retain the above copyright notice, 9221167Sgnn * this list of conditions and the following disclaimer. 10221167Sgnn * 11221167Sgnn * 2. Redistributions in binary form must reproduce the above copyright 12221167Sgnn * notice, this list of conditions and the following disclaimer in the 13221167Sgnn * documentation and/or other materials provided with the distribution. 14221167Sgnn * 15221167Sgnn * 3. Neither the name of the Exar Corporation nor the names of its 16221167Sgnn * contributors may be used to endorse or promote products derived from 17221167Sgnn * this software without specific prior written permission. 18221167Sgnn * 19221167Sgnn * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 20221167Sgnn * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 21221167Sgnn * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 22221167Sgnn * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE 23221167Sgnn * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 24221167Sgnn * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 25221167Sgnn * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 26221167Sgnn * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 27221167Sgnn * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 28221167Sgnn * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 29221167Sgnn * POSSIBILITY OF SUCH DAMAGE. 30221167Sgnn */ 31221167Sgnn/*$FreeBSD$*/ 32221167Sgnn 33221167Sgnn#include <dev/vxge/vxgehal/vxgehal.h> 34221167Sgnn 35221167Sgnn/* 36221167Sgnn * __hal_blockpool_create - Create block pool 37221167Sgnn * @devh: Pointer to HAL Device object. 38221167Sgnn * @blockpool: Block pool to be created. 39221167Sgnn * @pool_size: Number of blocks in the pool. 40221167Sgnn * @pool_incr: Number of blocks to be request from OS at a time 41221167Sgnn * @pool_min: Number of blocks below which new blocks to be requested. 42221167Sgnn * @pool_max: Number of blocks above which block to be freed. 43221167Sgnn * 44221167Sgnn * This function creates block pool 45221167Sgnn */ 46221167Sgnn 47221167Sgnnvxge_hal_status_e 48221167Sgnn__hal_blockpool_create(vxge_hal_device_h devh, 49221167Sgnn __hal_blockpool_t *blockpool, 50221167Sgnn u32 pool_size, 51221167Sgnn u32 pool_incr, 52221167Sgnn u32 pool_min, 53221167Sgnn u32 pool_max) 54221167Sgnn{ 55221167Sgnn u32 i; 56221167Sgnn __hal_device_t *hldev = (__hal_device_t *) devh; 57221167Sgnn __hal_blockpool_entry_t *entry; 58221167Sgnn void *memblock; 59221167Sgnn dma_addr_t dma_addr; 60221167Sgnn pci_dma_h dma_handle; 61221167Sgnn pci_dma_acc_h acc_handle; 62221167Sgnn vxge_hal_status_e status = VXGE_HAL_OK; 63221167Sgnn 64221167Sgnn vxge_assert(devh != NULL); 65221167Sgnn vxge_os_memzero(&dma_handle, sizeof(pci_dma_h)); 66221167Sgnn vxge_os_memzero(&acc_handle, sizeof(pci_dma_acc_h)); 67221167Sgnn 68221167Sgnn vxge_hal_trace_log_pool("==> %s:%s:%d", 69221167Sgnn __FILE__, __func__, __LINE__); 70221167Sgnn 71221167Sgnn vxge_hal_trace_log_pool("devh = 0x"VXGE_OS_STXFMT", " 72221167Sgnn "blockpool = 0x"VXGE_OS_STXFMT", pool_size = %d, pool_incr = %d, " 73221167Sgnn "pool_min = %d, pool_max = %d", (ptr_t) devh, (ptr_t) blockpool, 74221167Sgnn pool_size, pool_incr, pool_min, pool_max); 75221167Sgnn 76221167Sgnn if (blockpool == NULL) { 77221167Sgnn vxge_hal_err_log_pool( 78221167Sgnn "%s:%d null pointer passed. blockpool is null", 79221167Sgnn __FILE__, __LINE__); 80221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: %d", 81221167Sgnn __FILE__, __func__, __LINE__, VXGE_HAL_FAIL); 82221167Sgnn return (VXGE_HAL_FAIL); 83221167Sgnn } 84221167Sgnn 85221167Sgnn blockpool->hldev = devh; 86221167Sgnn blockpool->block_size = VXGE_OS_HOST_PAGE_SIZE; 87221167Sgnn blockpool->pool_size = 0; 88221167Sgnn blockpool->pool_incr = pool_incr; 89221167Sgnn blockpool->pool_min = pool_min; 90221167Sgnn blockpool->pool_max = pool_max; 91221167Sgnn blockpool->req_out = 0; 92221167Sgnn 93221167Sgnn#if defined(VXGE_HAL_DMA_CONSISTENT) 94221167Sgnn blockpool->dma_flags = VXGE_OS_DMA_CONSISTENT; 95221167Sgnn#else 96221167Sgnn blockpool->dma_flags = VXGE_OS_DMA_STREAMING; 97221167Sgnn#endif 98221167Sgnn 99221167Sgnn vxge_list_init(&blockpool->free_block_list); 100221167Sgnn 101221167Sgnn vxge_list_init(&blockpool->free_entry_list); 102221167Sgnn 103221167Sgnn#if defined(VXGE_HAL_BP_POST) 104221167Sgnn vxge_os_spin_lock_init(&blockpool->pool_lock, hldev->header.pdev); 105221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 106221167Sgnn vxge_os_spin_lock_init_irq(&blockpool->pool_lock, hldev->header.irqh); 107221167Sgnn#endif 108221167Sgnn 109221167Sgnn for (i = 0; i < pool_size + pool_max; i++) { 110221167Sgnn 111221167Sgnn entry = (__hal_blockpool_entry_t *) vxge_os_malloc( 112221167Sgnn hldev->header.pdev, 113221167Sgnn sizeof(__hal_blockpool_entry_t)); 114221167Sgnn if (entry == NULL) { 115221167Sgnn __hal_blockpool_destroy(blockpool); 116221167Sgnn 117221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: %d", 118221167Sgnn __FILE__, __func__, __LINE__, 119221167Sgnn VXGE_HAL_ERR_OUT_OF_MEMORY); 120221167Sgnn 121221167Sgnn return (VXGE_HAL_ERR_OUT_OF_MEMORY); 122221167Sgnn } 123221167Sgnn 124221167Sgnn vxge_list_insert(&entry->item, &blockpool->free_entry_list); 125221167Sgnn } 126221167Sgnn 127221167Sgnn for (i = 0; i < pool_size; i++) { 128221167Sgnn 129221167Sgnn memblock = vxge_os_dma_malloc( 130221167Sgnn hldev->header.pdev, 131221167Sgnn VXGE_OS_HOST_PAGE_SIZE, 132221167Sgnn blockpool->dma_flags, 133221167Sgnn &dma_handle, 134221167Sgnn &acc_handle); 135221167Sgnn 136221167Sgnn if (memblock == NULL) { 137221167Sgnn __hal_blockpool_destroy(blockpool); 138221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: %d", 139221167Sgnn __FILE__, __func__, __LINE__, 140221167Sgnn VXGE_HAL_ERR_OUT_OF_MEMORY); 141221167Sgnn 142221167Sgnn return (VXGE_HAL_ERR_OUT_OF_MEMORY); 143221167Sgnn } 144221167Sgnn 145221167Sgnn dma_addr = vxge_os_dma_map( 146221167Sgnn hldev->header.pdev, 147221167Sgnn dma_handle, 148221167Sgnn memblock, 149221167Sgnn VXGE_OS_HOST_PAGE_SIZE, 150221167Sgnn VXGE_OS_DMA_DIR_BIDIRECTIONAL, 151221167Sgnn blockpool->dma_flags); 152221167Sgnn 153221167Sgnn if (dma_addr == VXGE_OS_INVALID_DMA_ADDR) { 154221167Sgnn vxge_os_dma_free(hldev->header.pdev, 155221167Sgnn memblock, 156221167Sgnn VXGE_OS_HOST_PAGE_SIZE, 157221167Sgnn blockpool->dma_flags, 158221167Sgnn &dma_handle, 159221167Sgnn &acc_handle); 160221167Sgnn __hal_blockpool_destroy(blockpool); 161221167Sgnn 162221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: %d", 163221167Sgnn __FILE__, __func__, __LINE__, 164221167Sgnn VXGE_HAL_ERR_OUT_OF_MEMORY); 165221167Sgnn 166221167Sgnn return (VXGE_HAL_ERR_OUT_OF_MEMORY); 167221167Sgnn } 168221167Sgnn 169221167Sgnn entry = (__hal_blockpool_entry_t *) 170221167Sgnn vxge_list_first_get(&blockpool->free_entry_list); 171221167Sgnn 172221167Sgnn if (entry == NULL) { 173221167Sgnn entry = (__hal_blockpool_entry_t *) vxge_os_malloc( 174221167Sgnn hldev->header.pdev, 175221167Sgnn sizeof(__hal_blockpool_entry_t)); 176221167Sgnn } 177221167Sgnn 178221167Sgnn if (entry != NULL) { 179221167Sgnn vxge_list_remove(&entry->item); 180221167Sgnn entry->length = VXGE_OS_HOST_PAGE_SIZE; 181221167Sgnn entry->memblock = memblock; 182221167Sgnn entry->dma_addr = dma_addr; 183221167Sgnn entry->acc_handle = acc_handle; 184221167Sgnn entry->dma_handle = dma_handle; 185221167Sgnn vxge_list_insert(&entry->item, 186221167Sgnn &blockpool->free_block_list); 187221167Sgnn blockpool->pool_size++; 188221167Sgnn } else { 189221167Sgnn __hal_blockpool_destroy(blockpool); 190221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: %d", 191221167Sgnn __FILE__, __func__, __LINE__, 192221167Sgnn VXGE_HAL_ERR_OUT_OF_MEMORY); 193221167Sgnn 194221167Sgnn return (VXGE_HAL_ERR_OUT_OF_MEMORY); 195221167Sgnn } 196221167Sgnn } 197221167Sgnn 198221167Sgnn vxge_hal_info_log_pool( 199221167Sgnn "Blockpool block size:%d block pool size: %d", 200221167Sgnn blockpool->block_size, blockpool->pool_size); 201221167Sgnn 202221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: %d", 203221167Sgnn __FILE__, __func__, __LINE__, status); 204221167Sgnn 205221167Sgnn return (status); 206221167Sgnn} 207221167Sgnn 208221167Sgnn/* 209221167Sgnn * __hal_blockpool_destroy - Deallocates the block pool 210221167Sgnn * @blockpool: blockpool to be deallocated 211221167Sgnn * 212221167Sgnn * This function freeup the memory pool and removes the 213221167Sgnn * block pool. 214221167Sgnn */ 215221167Sgnn 216221167Sgnnvoid 217221167Sgnn__hal_blockpool_destroy( 218221167Sgnn __hal_blockpool_t *blockpool) 219221167Sgnn{ 220221167Sgnn __hal_device_t *hldev; 221221167Sgnn vxge_list_t *p, *n; 222221167Sgnn 223221167Sgnn vxge_assert(blockpool != NULL); 224221167Sgnn 225221167Sgnn hldev = (__hal_device_t *) blockpool->hldev; 226221167Sgnn 227221167Sgnn vxge_hal_trace_log_pool("==> %s:%s:%d", 228221167Sgnn __FILE__, __func__, __LINE__); 229221167Sgnn 230221167Sgnn vxge_hal_trace_log_pool("blockpool = 0x"VXGE_OS_STXFMT, 231221167Sgnn (ptr_t) blockpool); 232221167Sgnn 233221167Sgnn if (blockpool == NULL) { 234221167Sgnn vxge_hal_err_log_pool( 235221167Sgnn "%s:%d null pointer passed blockpool = null", 236221167Sgnn __FILE__, __LINE__); 237221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: 1", 238221167Sgnn __FILE__, __func__, __LINE__); 239221167Sgnn return; 240221167Sgnn } 241221167Sgnn 242221167Sgnn vxge_list_for_each_safe(p, n, &blockpool->free_block_list) { 243221167Sgnn 244221167Sgnn vxge_os_dma_unmap(hldev->header.pdev, 245221167Sgnn ((__hal_blockpool_entry_t *) p)->dma_handle, 246221167Sgnn ((__hal_blockpool_entry_t *) p)->dma_addr, 247221167Sgnn ((__hal_blockpool_entry_t *) p)->length, 248221167Sgnn VXGE_OS_DMA_DIR_BIDIRECTIONAL); 249221167Sgnn 250221167Sgnn vxge_os_dma_free(hldev->header.pdev, 251221167Sgnn ((__hal_blockpool_entry_t *) p)->memblock, 252221167Sgnn ((__hal_blockpool_entry_t *) p)->length, 253221167Sgnn blockpool->dma_flags, 254221167Sgnn &((__hal_blockpool_entry_t *) p)->dma_handle, 255221167Sgnn &((__hal_blockpool_entry_t *) p)->acc_handle); 256221167Sgnn 257221167Sgnn vxge_list_remove(&((__hal_blockpool_entry_t *) p)->item); 258221167Sgnn 259221167Sgnn vxge_os_free(hldev->header.pdev, 260221167Sgnn (void *)p, sizeof(__hal_blockpool_entry_t)); 261221167Sgnn 262221167Sgnn blockpool->pool_size--; 263221167Sgnn } 264221167Sgnn 265221167Sgnn vxge_list_for_each_safe(p, n, &blockpool->free_entry_list) { 266221167Sgnn 267221167Sgnn vxge_list_remove(&((__hal_blockpool_entry_t *) p)->item); 268221167Sgnn 269221167Sgnn vxge_os_free(hldev->header.pdev, 270221167Sgnn (void *)p, sizeof(__hal_blockpool_entry_t)); 271221167Sgnn 272221167Sgnn } 273221167Sgnn 274221167Sgnn#if defined(VXGE_HAL_BP_POST) 275221167Sgnn vxge_os_spin_lock_destroy(&blockpool->pool_lock, 276221167Sgnn hldev->header.pdev); 277221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 278221167Sgnn vxge_os_spin_lock_destroy_irq(&blockpool->pool_lock, 279221167Sgnn hldev->header.pdev); 280221167Sgnn#endif 281221167Sgnn 282221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: 0", 283221167Sgnn __FILE__, __func__, __LINE__); 284221167Sgnn} 285221167Sgnn 286221167Sgnn/* 287221167Sgnn * __hal_blockpool_blocks_add - Request additional blocks 288221167Sgnn * @blockpool: Block pool. 289221167Sgnn * 290221167Sgnn * Requests additional blocks to block pool 291221167Sgnn */ 292221167Sgnnstatic inline void 293221167Sgnn__hal_blockpool_blocks_add( 294221167Sgnn __hal_blockpool_t * blockpool) 295221167Sgnn{ 296221167Sgnn u32 nreq = 0, i; 297221167Sgnn __hal_device_t *hldev; 298221167Sgnn 299221167Sgnn vxge_assert(blockpool != NULL); 300221167Sgnn 301221167Sgnn hldev = (__hal_device_t *) blockpool->hldev; 302221167Sgnn 303221167Sgnn vxge_hal_trace_log_pool("==> %s:%s:%d", 304221167Sgnn __FILE__, __func__, __LINE__); 305221167Sgnn 306221167Sgnn vxge_hal_trace_log_pool("blockpool = 0x"VXGE_OS_STXFMT, 307221167Sgnn (ptr_t) blockpool); 308221167Sgnn 309221167Sgnn#if defined(VXGE_HAL_BP_POST) 310221167Sgnn vxge_os_spin_lock(&blockpool->pool_lock); 311221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 312221167Sgnn vxge_os_spin_lock_irq(&blockpool->pool_lock, flags); 313221167Sgnn#endif 314221167Sgnn if ((blockpool->pool_size + blockpool->req_out) < 315221167Sgnn blockpool->pool_min) { 316221167Sgnn nreq = blockpool->pool_incr; 317221167Sgnn blockpool->req_out += nreq; 318221167Sgnn } 319221167Sgnn 320221167Sgnn#if defined(VXGE_HAL_BP_POST) 321221167Sgnn vxge_os_spin_unlock(&blockpool->pool_lock); 322221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 323221167Sgnn vxge_os_spin_unlock_irq(&blockpool->pool_lock, flags); 324221167Sgnn#endif 325221167Sgnn 326221167Sgnn for (i = 0; i < nreq; i++) { 327221167Sgnn vxge_os_dma_malloc_async( 328221167Sgnn ((__hal_device_t *) blockpool->hldev)->header.pdev, 329221167Sgnn blockpool->hldev, 330221167Sgnn VXGE_OS_HOST_PAGE_SIZE, 331221167Sgnn blockpool->dma_flags); 332221167Sgnn } 333221167Sgnn 334221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: 0", 335221167Sgnn __FILE__, __func__, __LINE__); 336221167Sgnn} 337221167Sgnn 338221167Sgnn/* 339221167Sgnn * __hal_blockpool_blocks_remove - Free additional blocks 340221167Sgnn * @blockpool: Block pool. 341221167Sgnn * 342221167Sgnn * Frees additional blocks over maximum from the block pool 343221167Sgnn */ 344221167Sgnnstatic inline void 345221167Sgnn__hal_blockpool_blocks_remove( 346221167Sgnn __hal_blockpool_t * blockpool) 347221167Sgnn{ 348221167Sgnn vxge_list_t *p, *n; 349221167Sgnn __hal_device_t *hldev; 350221167Sgnn 351221167Sgnn vxge_assert(blockpool != NULL); 352221167Sgnn 353221167Sgnn hldev = (__hal_device_t *) blockpool->hldev; 354221167Sgnn 355221167Sgnn vxge_hal_trace_log_pool("==> %s:%s:%d", 356221167Sgnn __FILE__, __func__, __LINE__); 357221167Sgnn 358221167Sgnn vxge_hal_trace_log_pool("blockpool = 0x"VXGE_OS_STXFMT, 359221167Sgnn (ptr_t) blockpool); 360221167Sgnn 361221167Sgnn#if defined(VXGE_HAL_BP_POST) 362221167Sgnn vxge_os_spin_lock(&blockpool->pool_lock); 363221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 364221167Sgnn vxge_os_spin_lock_irq(&blockpool->pool_lock, flags); 365221167Sgnn#endif 366221167Sgnn vxge_list_for_each_safe(p, n, &blockpool->free_block_list) { 367221167Sgnn 368221167Sgnn if (blockpool->pool_size < blockpool->pool_max) 369221167Sgnn break; 370221167Sgnn 371221167Sgnn vxge_os_dma_unmap( 372221167Sgnn ((__hal_device_t *) blockpool->hldev)->header.pdev, 373221167Sgnn ((__hal_blockpool_entry_t *) p)->dma_handle, 374221167Sgnn ((__hal_blockpool_entry_t *) p)->dma_addr, 375221167Sgnn ((__hal_blockpool_entry_t *) p)->length, 376221167Sgnn VXGE_OS_DMA_DIR_BIDIRECTIONAL); 377221167Sgnn 378221167Sgnn vxge_os_dma_free( 379221167Sgnn ((__hal_device_t *) blockpool->hldev)->header.pdev, 380221167Sgnn ((__hal_blockpool_entry_t *) p)->memblock, 381221167Sgnn ((__hal_blockpool_entry_t *) p)->length, 382221167Sgnn blockpool->dma_flags, 383221167Sgnn &((__hal_blockpool_entry_t *) p)->dma_handle, 384221167Sgnn &((__hal_blockpool_entry_t *) p)->acc_handle); 385221167Sgnn 386221167Sgnn vxge_list_remove(&((__hal_blockpool_entry_t *) p)->item); 387221167Sgnn 388221167Sgnn vxge_list_insert(p, &blockpool->free_entry_list); 389221167Sgnn 390221167Sgnn blockpool->pool_size--; 391221167Sgnn 392221167Sgnn } 393221167Sgnn 394221167Sgnn#if defined(VXGE_HAL_BP_POST) 395221167Sgnn vxge_os_spin_unlock(&blockpool->pool_lock); 396221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 397221167Sgnn vxge_os_spin_unlock_irq(&blockpool->pool_lock, flags); 398221167Sgnn#endif 399221167Sgnn 400221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: 0", 401221167Sgnn __FILE__, __func__, __LINE__); 402221167Sgnn} 403221167Sgnn 404221167Sgnn/* 405221167Sgnn * vxge_hal_blockpool_block_add - callback for vxge_os_dma_malloc_async 406221167Sgnn * @devh: HAL device handle. 407221167Sgnn * @block_addr: Virtual address of the block 408221167Sgnn * @length: Length of the block. 409221167Sgnn * @p_dma_h: Physical address of the block 410221167Sgnn * @acc_handle: DMA acc handle 411221167Sgnn * 412221167Sgnn * Adds a block to block pool 413221167Sgnn */ 414221167Sgnnvoid 415221167Sgnnvxge_hal_blockpool_block_add( 416221167Sgnn vxge_hal_device_h devh, 417221167Sgnn void *block_addr, 418221167Sgnn u32 length, 419221167Sgnn pci_dma_h * dma_h, 420221167Sgnn pci_dma_acc_h * acc_handle) 421221167Sgnn{ 422221167Sgnn __hal_blockpool_t *blockpool; 423221167Sgnn __hal_blockpool_entry_t *entry; 424221167Sgnn __hal_device_t *hldev; 425221167Sgnn dma_addr_t dma_addr; 426221167Sgnn vxge_hal_status_e status; 427221167Sgnn u32 req_out; 428221167Sgnn 429221167Sgnn vxge_assert(devh != NULL); 430221167Sgnn 431221167Sgnn hldev = (__hal_device_t *) devh; 432221167Sgnn 433221167Sgnn vxge_hal_trace_log_pool("==> %s:%s:%d", 434221167Sgnn __FILE__, __func__, __LINE__); 435221167Sgnn 436221167Sgnn vxge_hal_trace_log_pool("devh = 0x"VXGE_OS_STXFMT", length = %d, " 437221167Sgnn "block_addr = 0x"VXGE_OS_STXFMT", dma_h = 0x"VXGE_OS_STXFMT", " 438221167Sgnn "acc_handle = 0x"VXGE_OS_STXFMT, (ptr_t) devh, length, 439221167Sgnn (ptr_t) block_addr, (ptr_t) dma_h, (ptr_t) acc_handle); 440221167Sgnn 441221167Sgnn blockpool = &hldev->block_pool; 442221167Sgnn 443221167Sgnn if (block_addr == NULL) { 444221167Sgnn#if defined(VXGE_HAL_BP_POST) 445221167Sgnn vxge_os_spin_lock(&blockpool->pool_lock); 446221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 447221167Sgnn vxge_os_spin_lock_irq(&blockpool->pool_lock, flags); 448221167Sgnn#endif 449221167Sgnn blockpool->req_out--; 450221167Sgnn 451221167Sgnn#if defined(VXGE_HAL_BP_POST) 452221167Sgnn vxge_os_spin_unlock(&blockpool->pool_lock); 453221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 454221167Sgnn vxge_os_spin_unlock_irq(&blockpool->pool_lock, flags); 455221167Sgnn#endif 456221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: 1", 457221167Sgnn __FILE__, __func__, __LINE__); 458221167Sgnn return; 459221167Sgnn } 460221167Sgnn 461221167Sgnn dma_addr = vxge_os_dma_map(hldev->header.pdev, 462221167Sgnn *dma_h, 463221167Sgnn block_addr, 464221167Sgnn length, 465221167Sgnn VXGE_OS_DMA_DIR_BIDIRECTIONAL, 466221167Sgnn blockpool->dma_flags); 467221167Sgnn 468221167Sgnn if (dma_addr == VXGE_OS_INVALID_DMA_ADDR) { 469221167Sgnn vxge_os_dma_free(hldev->header.pdev, 470221167Sgnn block_addr, 471221167Sgnn length, 472221167Sgnn blockpool->dma_flags, 473221167Sgnn dma_h, 474221167Sgnn acc_handle); 475221167Sgnn#if defined(VXGE_HAL_BP_POST) 476221167Sgnn vxge_os_spin_lock(&blockpool->pool_lock); 477221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 478221167Sgnn vxge_os_spin_lock_irq(&blockpool->pool_lock, flags); 479221167Sgnn#endif 480221167Sgnn blockpool->req_out--; 481221167Sgnn 482221167Sgnn#if defined(VXGE_HAL_BP_POST) 483221167Sgnn vxge_os_spin_unlock(&blockpool->pool_lock); 484221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 485221167Sgnn vxge_os_spin_unlock_irq(&blockpool->pool_lock, flags); 486221167Sgnn#endif 487221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: 1", 488221167Sgnn __FILE__, __func__, __LINE__); 489221167Sgnn return; 490221167Sgnn } 491221167Sgnn 492221167Sgnn#if defined(VXGE_HAL_BP_POST) 493221167Sgnn vxge_os_spin_lock(&blockpool->pool_lock); 494221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 495221167Sgnn vxge_os_spin_lock_irq(&blockpool->pool_lock, flags); 496221167Sgnn#endif 497221167Sgnn 498221167Sgnn entry = (__hal_blockpool_entry_t *) 499221167Sgnn vxge_list_first_get(&blockpool->free_entry_list); 500221167Sgnn 501221167Sgnn if (entry == NULL) { 502221167Sgnn entry = (__hal_blockpool_entry_t *) vxge_os_malloc( 503221167Sgnn hldev->header.pdev, 504221167Sgnn sizeof(__hal_blockpool_entry_t)); 505221167Sgnn } else { 506221167Sgnn vxge_list_remove(&entry->item); 507221167Sgnn } 508221167Sgnn 509221167Sgnn if (entry != NULL) { 510221167Sgnn entry->length = length; 511221167Sgnn entry->memblock = block_addr; 512221167Sgnn entry->dma_addr = dma_addr; 513221167Sgnn entry->acc_handle = *acc_handle; 514221167Sgnn entry->dma_handle = *dma_h; 515221167Sgnn vxge_list_insert(&entry->item, &blockpool->free_block_list); 516221167Sgnn blockpool->pool_size++; 517221167Sgnn status = VXGE_HAL_OK; 518221167Sgnn } else { 519221167Sgnn status = VXGE_HAL_ERR_OUT_OF_MEMORY; 520221167Sgnn } 521221167Sgnn 522221167Sgnn blockpool->req_out--; 523221167Sgnn 524221167Sgnn req_out = blockpool->req_out; 525221167Sgnn 526221167Sgnn#if defined(VXGE_HAL_BP_POST) 527221167Sgnn vxge_os_spin_unlock(&blockpool->pool_lock); 528221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 529221167Sgnn vxge_os_spin_unlock_irq(&blockpool->pool_lock, flags); 530221167Sgnn#endif 531221167Sgnn 532221167Sgnn if (req_out == 0) 533221167Sgnn __hal_channel_process_pending_list(devh); 534221167Sgnn 535221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: %d", 536221167Sgnn __FILE__, __func__, __LINE__, status); 537221167Sgnn} 538221167Sgnn 539221167Sgnn/* 540221167Sgnn * __hal_blockpool_malloc - Allocate a memory block from pool 541221167Sgnn * @devh: HAL device handle. 542221167Sgnn * @size: Length of the block. 543221167Sgnn * @dma_addr: Buffer to return DMA Address of the block. 544221167Sgnn * @dma_handle: Buffer to return DMA handle of the block. 545221167Sgnn * @acc_handle: Buffer to return DMA acc handle 546221167Sgnn * 547221167Sgnn * 548221167Sgnn * Allocates a block of memory of given size, either from block pool 549221167Sgnn * or by calling vxge_os_dma_malloc() 550221167Sgnn */ 551221167Sgnnvoid * 552221167Sgnn__hal_blockpool_malloc(vxge_hal_device_h devh, 553221167Sgnn u32 size, 554221167Sgnn dma_addr_t *dma_addr, 555221167Sgnn pci_dma_h *dma_handle, 556221167Sgnn pci_dma_acc_h *acc_handle) 557221167Sgnn{ 558221167Sgnn __hal_blockpool_entry_t *entry; 559221167Sgnn __hal_blockpool_t *blockpool; 560221167Sgnn __hal_device_t *hldev; 561221167Sgnn void *memblock = NULL; 562221167Sgnn 563221167Sgnn vxge_assert(devh != NULL); 564221167Sgnn 565221167Sgnn hldev = (__hal_device_t *) devh; 566221167Sgnn 567221167Sgnn vxge_hal_trace_log_pool("==> %s:%s:%d", 568221167Sgnn __FILE__, __func__, __LINE__); 569221167Sgnn 570221167Sgnn vxge_hal_trace_log_pool( 571221167Sgnn "devh = 0x"VXGE_OS_STXFMT", size = %d, " 572221167Sgnn "dma_addr = 0x"VXGE_OS_STXFMT", dma_handle = 0x"VXGE_OS_STXFMT", " 573221167Sgnn "acc_handle = 0x"VXGE_OS_STXFMT, (ptr_t) devh, size, 574221167Sgnn (ptr_t) dma_addr, (ptr_t) dma_handle, (ptr_t) acc_handle); 575221167Sgnn 576221167Sgnn blockpool = &((__hal_device_t *) devh)->block_pool; 577221167Sgnn 578221167Sgnn if (size != blockpool->block_size) { 579221167Sgnn 580221167Sgnn memblock = vxge_os_dma_malloc( 581221167Sgnn ((__hal_device_t *) devh)->header.pdev, 582221167Sgnn size, 583221167Sgnn blockpool->dma_flags | 584221167Sgnn VXGE_OS_DMA_CACHELINE_ALIGNED, 585221167Sgnn dma_handle, 586221167Sgnn acc_handle); 587221167Sgnn 588221167Sgnn if (memblock == NULL) { 589221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: %d", 590221167Sgnn __FILE__, __func__, __LINE__, 591221167Sgnn VXGE_HAL_ERR_OUT_OF_MEMORY); 592221167Sgnn return (NULL); 593221167Sgnn } 594221167Sgnn 595221167Sgnn *dma_addr = vxge_os_dma_map( 596221167Sgnn ((__hal_device_t *) devh)->header.pdev, 597221167Sgnn *dma_handle, 598221167Sgnn memblock, 599221167Sgnn size, 600221167Sgnn VXGE_OS_DMA_DIR_BIDIRECTIONAL, 601221167Sgnn blockpool->dma_flags); 602221167Sgnn 603221167Sgnn if (*dma_addr == VXGE_OS_INVALID_DMA_ADDR) { 604221167Sgnn vxge_os_dma_free(((__hal_device_t *) devh)->header.pdev, 605221167Sgnn memblock, 606221167Sgnn size, 607221167Sgnn blockpool->dma_flags | 608221167Sgnn VXGE_OS_DMA_CACHELINE_ALIGNED, 609221167Sgnn dma_handle, 610221167Sgnn acc_handle); 611221167Sgnn 612221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: %d", 613221167Sgnn __FILE__, __func__, __LINE__, 614221167Sgnn VXGE_HAL_ERR_OUT_OF_MEMORY); 615221167Sgnn 616221167Sgnn return (NULL); 617221167Sgnn } 618221167Sgnn 619221167Sgnn } else { 620221167Sgnn 621221167Sgnn#if defined(VXGE_HAL_BP_POST) 622221167Sgnn vxge_os_spin_lock(&blockpool->pool_lock); 623221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 624221167Sgnn vxge_os_spin_lock_irq(&blockpool->pool_lock, flags); 625221167Sgnn#endif 626221167Sgnn 627221167Sgnn entry = (__hal_blockpool_entry_t *) 628221167Sgnn vxge_list_first_get(&blockpool->free_block_list); 629221167Sgnn 630221167Sgnn if (entry != NULL) { 631221167Sgnn vxge_list_remove(&entry->item); 632221167Sgnn *dma_addr = entry->dma_addr; 633221167Sgnn *dma_handle = entry->dma_handle; 634221167Sgnn *acc_handle = entry->acc_handle; 635221167Sgnn memblock = entry->memblock; 636221167Sgnn 637221167Sgnn vxge_list_insert(&entry->item, 638221167Sgnn &blockpool->free_entry_list); 639221167Sgnn blockpool->pool_size--; 640221167Sgnn } 641221167Sgnn 642221167Sgnn#if defined(VXGE_HAL_BP_POST) 643221167Sgnn vxge_os_spin_unlock(&blockpool->pool_lock); 644221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 645221167Sgnn vxge_os_spin_unlock_irq(&blockpool->pool_lock, flags); 646221167Sgnn#endif 647221167Sgnn 648221167Sgnn if (memblock != NULL) 649221167Sgnn __hal_blockpool_blocks_add(blockpool); 650221167Sgnn 651221167Sgnn } 652221167Sgnn 653221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: %d", 654221167Sgnn __FILE__, __func__, __LINE__, !memblock); 655221167Sgnn 656221167Sgnn return (memblock); 657221167Sgnn 658221167Sgnn} 659221167Sgnn 660221167Sgnn/* 661221167Sgnn * __hal_blockpool_free - Frees the memory allcoated with __hal_blockpool_malloc 662221167Sgnn * @devh: HAL device handle. 663221167Sgnn * @memblock: Virtual address block 664221167Sgnn * @size: Length of the block. 665221167Sgnn * @dma_addr: DMA Address of the block. 666221167Sgnn * @dma_handle: DMA handle of the block. 667221167Sgnn * @acc_handle: DMA acc handle 668221167Sgnn * 669221167Sgnn * 670221167Sgnn * Frees the memory allocated with __hal_blockpool_malloc to blockpool or system 671221167Sgnn */ 672221167Sgnnvoid 673221167Sgnn__hal_blockpool_free(vxge_hal_device_h devh, 674221167Sgnn void *memblock, 675221167Sgnn u32 size, 676221167Sgnn dma_addr_t *dma_addr, 677221167Sgnn pci_dma_h *dma_handle, 678221167Sgnn pci_dma_acc_h *acc_handle) 679221167Sgnn{ 680221167Sgnn __hal_blockpool_entry_t *entry; 681221167Sgnn __hal_blockpool_t *blockpool; 682221167Sgnn __hal_device_t *hldev; 683221167Sgnn vxge_hal_status_e status = VXGE_HAL_OK; 684221167Sgnn 685221167Sgnn vxge_assert(devh != NULL); 686221167Sgnn 687221167Sgnn hldev = (__hal_device_t *) devh; 688221167Sgnn 689221167Sgnn vxge_hal_trace_log_pool("==> %s:%s:%d", 690221167Sgnn __FILE__, __func__, __LINE__); 691221167Sgnn 692221167Sgnn vxge_hal_trace_log_pool("devh = 0x"VXGE_OS_STXFMT", size = %d, " 693221167Sgnn "dma_addr = 0x"VXGE_OS_STXFMT", dma_handle = 0x"VXGE_OS_STXFMT", " 694221167Sgnn "acc_handle = 0x"VXGE_OS_STXFMT, (ptr_t) devh, size, 695221167Sgnn (ptr_t) dma_addr, (ptr_t) dma_handle, (ptr_t) acc_handle); 696221167Sgnn 697221167Sgnn blockpool = &((__hal_device_t *) devh)->block_pool; 698221167Sgnn 699221167Sgnn if (size != blockpool->block_size) { 700221167Sgnn 701221167Sgnn vxge_os_dma_unmap(((__hal_device_t *) devh)->header.pdev, 702221167Sgnn *dma_handle, 703221167Sgnn *dma_addr, 704221167Sgnn size, 705221167Sgnn VXGE_OS_DMA_DIR_BIDIRECTIONAL); 706221167Sgnn 707221167Sgnn vxge_os_dma_free(((__hal_device_t *) devh)->header.pdev, 708221167Sgnn memblock, 709221167Sgnn size, 710221167Sgnn blockpool->dma_flags | 711221167Sgnn VXGE_OS_DMA_CACHELINE_ALIGNED, 712221167Sgnn dma_handle, 713221167Sgnn acc_handle); 714221167Sgnn } else { 715221167Sgnn#if defined(VXGE_HAL_BP_POST) 716221167Sgnn vxge_os_spin_lock(&blockpool->pool_lock); 717221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 718221167Sgnn vxge_os_spin_lock_irq(&blockpool->pool_lock, flags); 719221167Sgnn#endif 720221167Sgnn 721221167Sgnn entry = (__hal_blockpool_entry_t *) 722221167Sgnn vxge_list_first_get(&blockpool->free_entry_list); 723221167Sgnn 724221167Sgnn if (entry == NULL) { 725221167Sgnn entry = (__hal_blockpool_entry_t *) vxge_os_malloc( 726221167Sgnn ((__hal_device_t *) devh)->header.pdev, 727221167Sgnn sizeof(__hal_blockpool_entry_t)); 728221167Sgnn } else { 729221167Sgnn vxge_list_remove(&entry->item); 730221167Sgnn } 731221167Sgnn 732221167Sgnn if (entry != NULL) { 733221167Sgnn entry->length = size; 734221167Sgnn entry->memblock = memblock; 735221167Sgnn entry->dma_addr = *dma_addr; 736221167Sgnn entry->acc_handle = *acc_handle; 737221167Sgnn entry->dma_handle = *dma_handle; 738221167Sgnn vxge_list_insert(&entry->item, 739221167Sgnn &blockpool->free_block_list); 740221167Sgnn blockpool->pool_size++; 741221167Sgnn status = VXGE_HAL_OK; 742221167Sgnn } else { 743221167Sgnn status = VXGE_HAL_ERR_OUT_OF_MEMORY; 744221167Sgnn } 745221167Sgnn 746221167Sgnn#if defined(VXGE_HAL_BP_POST) 747221167Sgnn vxge_os_spin_unlock(&blockpool->pool_lock); 748221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 749221167Sgnn vxge_os_spin_unlock_irq(&blockpool->pool_lock, flags); 750221167Sgnn#endif 751221167Sgnn if (status == VXGE_HAL_OK) 752221167Sgnn __hal_blockpool_blocks_remove(blockpool); 753221167Sgnn 754221167Sgnn } 755221167Sgnn 756221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: %d", 757221167Sgnn __FILE__, __func__, __LINE__, status); 758221167Sgnn} 759221167Sgnn 760221167Sgnn/* 761221167Sgnn * __hal_blockpool_block_allocate - Allocates a block from block pool 762221167Sgnn * @hldev: Hal device 763221167Sgnn * @size: Size of the block to be allocated 764221167Sgnn * 765221167Sgnn * This function allocates a block from block pool or from the system 766221167Sgnn */ 767221167Sgnn__hal_blockpool_entry_t * 768221167Sgnn__hal_blockpool_block_allocate(vxge_hal_device_h devh, 769221167Sgnn u32 size) 770221167Sgnn{ 771221167Sgnn __hal_blockpool_entry_t *entry = NULL; 772221167Sgnn __hal_device_t *hldev; 773221167Sgnn __hal_blockpool_t *blockpool; 774221167Sgnn 775221167Sgnn vxge_assert(devh != NULL); 776221167Sgnn 777221167Sgnn hldev = (__hal_device_t *) devh; 778221167Sgnn 779221167Sgnn vxge_hal_trace_log_pool("==> %s:%s:%d", 780221167Sgnn __FILE__, __func__, __LINE__); 781221167Sgnn 782221167Sgnn vxge_hal_trace_log_pool("devh = 0x"VXGE_OS_STXFMT", size = %d", 783221167Sgnn (ptr_t) devh, size); 784221167Sgnn 785221167Sgnn blockpool = &((__hal_device_t *) devh)->block_pool; 786221167Sgnn 787221167Sgnn if (size == blockpool->block_size) { 788221167Sgnn#if defined(VXGE_HAL_BP_POST) 789221167Sgnn vxge_os_spin_lock(&blockpool->pool_lock); 790221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 791221167Sgnn vxge_os_spin_lock_irq(&blockpool->pool_lock, flags); 792221167Sgnn#endif 793221167Sgnn 794221167Sgnn entry = (__hal_blockpool_entry_t *) 795221167Sgnn vxge_list_first_get(&blockpool->free_block_list); 796221167Sgnn 797221167Sgnn if (entry != NULL) { 798221167Sgnn vxge_list_remove(&entry->item); 799221167Sgnn blockpool->pool_size--; 800221167Sgnn } 801221167Sgnn 802221167Sgnn#if defined(VXGE_HAL_BP_POST) 803221167Sgnn vxge_os_spin_unlock(&blockpool->pool_lock); 804221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 805221167Sgnn vxge_os_spin_unlock_irq(&blockpool->pool_lock, flags); 806221167Sgnn#endif 807221167Sgnn } 808221167Sgnn 809221167Sgnn if (entry != NULL) 810221167Sgnn __hal_blockpool_blocks_add(blockpool); 811221167Sgnn 812221167Sgnn 813221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: %d", 814221167Sgnn __FILE__, __func__, __LINE__, !entry); 815221167Sgnn 816221167Sgnn return (entry); 817221167Sgnn} 818221167Sgnn 819221167Sgnn/* 820221167Sgnn * __hal_blockpool_block_free - Frees a block from block pool 821221167Sgnn * @devh: Hal device 822221167Sgnn * @entry: Entry of block to be freed 823221167Sgnn * 824221167Sgnn * This function frees a block from block pool 825221167Sgnn */ 826221167Sgnnvoid 827221167Sgnn__hal_blockpool_block_free(vxge_hal_device_h devh, 828221167Sgnn __hal_blockpool_entry_t *entry) 829221167Sgnn{ 830221167Sgnn __hal_device_t *hldev; 831221167Sgnn __hal_blockpool_t *blockpool; 832221167Sgnn 833221167Sgnn vxge_assert(devh != NULL); 834221167Sgnn 835221167Sgnn hldev = (__hal_device_t *) devh; 836221167Sgnn 837221167Sgnn vxge_hal_trace_log_pool("==> %s:%s:%d", 838221167Sgnn __FILE__, __func__, __LINE__); 839221167Sgnn 840221167Sgnn vxge_hal_trace_log_pool( 841221167Sgnn "devh = 0x"VXGE_OS_STXFMT", entry = 0x"VXGE_OS_STXFMT, 842221167Sgnn (ptr_t) devh, (ptr_t) entry); 843221167Sgnn 844221167Sgnn blockpool = &((__hal_device_t *) devh)->block_pool; 845221167Sgnn 846221167Sgnn if (entry->length == blockpool->block_size) { 847221167Sgnn#if defined(VXGE_HAL_BP_POST) 848221167Sgnn vxge_os_spin_lock(&blockpool->pool_lock); 849221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 850221167Sgnn vxge_os_spin_lock_irq(&blockpool->pool_lock, flags); 851221167Sgnn#endif 852221167Sgnn 853221167Sgnn vxge_list_insert(&entry->item, &blockpool->free_block_list); 854221167Sgnn blockpool->pool_size++; 855221167Sgnn 856221167Sgnn#if defined(VXGE_HAL_BP_POST) 857221167Sgnn vxge_os_spin_unlock(&blockpool->pool_lock); 858221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 859221167Sgnn vxge_os_spin_unlock_irq(&blockpool->pool_lock, flags); 860221167Sgnn#endif 861221167Sgnn } 862221167Sgnn 863221167Sgnn __hal_blockpool_blocks_remove(blockpool); 864221167Sgnn 865221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: 0", 866221167Sgnn __FILE__, __func__, __LINE__); 867221167Sgnn} 868221167Sgnn 869221167Sgnn 870221167Sgnn/* 871221167Sgnn * __hal_blockpool_list_allocate - Allocate blocks from block pool 872221167Sgnn * @devh: Hal device 873221167Sgnn * @blocklist: List into which the allocated blocks to be inserted 874221167Sgnn * @count: Number of blocks to be allocated 875221167Sgnn * 876221167Sgnn * This function allocates a register from the register pool 877221167Sgnn */ 878221167Sgnnvxge_hal_status_e 879221167Sgnn__hal_blockpool_list_allocate( 880221167Sgnn vxge_hal_device_h devh, 881221167Sgnn vxge_list_t *blocklist, 882221167Sgnn u32 count) 883221167Sgnn{ 884221167Sgnn u32 i; 885221167Sgnn __hal_device_t *hldev; 886221167Sgnn __hal_blockpool_t *blockpool; 887221167Sgnn __hal_blockpool_entry_t *block_entry; 888221167Sgnn vxge_hal_status_e status = VXGE_HAL_OK; 889221167Sgnn 890221167Sgnn vxge_assert(devh != NULL); 891221167Sgnn 892221167Sgnn hldev = (__hal_device_t *) devh; 893221167Sgnn 894221167Sgnn vxge_hal_trace_log_pool("==> %s:%s:%d", 895221167Sgnn __FILE__, __func__, __LINE__); 896221167Sgnn 897221167Sgnn vxge_hal_trace_log_pool("devh = 0x"VXGE_OS_STXFMT", blocklist = " 898221167Sgnn "0x"VXGE_OS_STXFMT", count = %d", (ptr_t) devh, 899221167Sgnn (ptr_t) blocklist, count); 900221167Sgnn 901221167Sgnn blockpool = &((__hal_device_t *) devh)->block_pool; 902221167Sgnn 903221167Sgnn if (blocklist == NULL) { 904221167Sgnn vxge_hal_err_log_pool( 905221167Sgnn "null pointer passed blockpool = 0x"VXGE_OS_STXFMT", " 906221167Sgnn "blocklist = 0x"VXGE_OS_STXFMT, (ptr_t) blockpool, 907221167Sgnn (ptr_t) blocklist); 908221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: 1", 909221167Sgnn __FILE__, __func__, __LINE__); 910221167Sgnn return (VXGE_HAL_FAIL); 911221167Sgnn } 912221167Sgnn 913221167Sgnn#if defined(VXGE_HAL_BP_POST) 914221167Sgnn vxge_os_spin_lock(&blockpool->pool_lock); 915221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 916221167Sgnn vxge_os_spin_lock_irq(&blockpool->pool_lock, flags); 917221167Sgnn#endif 918221167Sgnn 919221167Sgnn vxge_list_init(blocklist); 920221167Sgnn 921221167Sgnn for (i = 0; i < count; i++) { 922221167Sgnn 923221167Sgnn block_entry = (__hal_blockpool_entry_t *) 924221167Sgnn vxge_list_first_get(&blockpool->free_block_list); 925221167Sgnn 926221167Sgnn if (block_entry == NULL) 927221167Sgnn break; 928221167Sgnn 929221167Sgnn vxge_list_remove(&block_entry->item); 930221167Sgnn 931221167Sgnn vxge_os_memzero(block_entry->memblock, blockpool->block_size); 932221167Sgnn 933221167Sgnn vxge_list_insert(&block_entry->item, blocklist); 934221167Sgnn 935221167Sgnn blockpool->pool_size++; 936221167Sgnn } 937221167Sgnn 938221167Sgnn#if defined(VXGE_HAL_BP_POST) 939221167Sgnn vxge_os_spin_unlock(&blockpool->pool_lock); 940221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 941221167Sgnn vxge_os_spin_unlock_irq(&blockpool->pool_lock, flags); 942221167Sgnn#endif 943221167Sgnn 944221167Sgnn if (i < count) { 945221167Sgnn 946221167Sgnn vxge_hal_err_log_pool("%s:%d Blockpool out of blocks", 947221167Sgnn __FILE__, __LINE__); 948221167Sgnn 949221167Sgnn vxge_assert(FALSE); 950221167Sgnn 951221167Sgnn __hal_blockpool_list_free(blockpool, blocklist); 952221167Sgnn 953221167Sgnn status = VXGE_HAL_ERR_OUT_OF_MEMORY; 954221167Sgnn 955221167Sgnn } 956221167Sgnn 957221167Sgnn __hal_blockpool_blocks_add(blockpool); 958221167Sgnn 959221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: %d", 960221167Sgnn __FILE__, __func__, __LINE__, status); 961221167Sgnn 962221167Sgnn return (status); 963221167Sgnn} 964221167Sgnn 965221167Sgnn/* 966221167Sgnn * __hal_blockpool_list_free - Free a list of blocks from block pool 967221167Sgnn * @devh: Hal device 968221167Sgnn * @blocklist: List of blocks to be freed 969221167Sgnn * 970221167Sgnn * This function frees a list of blocks to the block pool 971221167Sgnn */ 972221167Sgnnvoid 973221167Sgnn__hal_blockpool_list_free( 974221167Sgnn vxge_hal_device_h devh, 975221167Sgnn vxge_list_t *blocklist) 976221167Sgnn{ 977221167Sgnn __hal_device_t *hldev; 978221167Sgnn __hal_blockpool_t *blockpool; 979221167Sgnn __hal_blockpool_entry_t *block_entry; 980221167Sgnn 981221167Sgnn vxge_assert(devh != NULL); 982221167Sgnn 983221167Sgnn hldev = (__hal_device_t *) devh; 984221167Sgnn 985221167Sgnn vxge_hal_trace_log_pool("==> %s:%s:%d", 986221167Sgnn __FILE__, __func__, __LINE__); 987221167Sgnn 988221167Sgnn vxge_hal_trace_log_pool( 989221167Sgnn "devh = 0x"VXGE_OS_STXFMT", blocklist = 0x"VXGE_OS_STXFMT, 990221167Sgnn (ptr_t) devh, (ptr_t) blocklist); 991221167Sgnn 992221167Sgnn blockpool = &((__hal_device_t *) devh)->block_pool; 993221167Sgnn 994221167Sgnn if (blocklist == NULL) { 995221167Sgnn vxge_hal_err_log_pool( 996221167Sgnn "null pointer passed blockpool = 0x"VXGE_OS_STXFMT", " 997221167Sgnn "blocklist = 0x"VXGE_OS_STXFMT, (ptr_t) blockpool, 998221167Sgnn (ptr_t) blocklist); 999221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: 1", 1000221167Sgnn __FILE__, __func__, __LINE__); 1001221167Sgnn return; 1002221167Sgnn } 1003221167Sgnn 1004221167Sgnn#if defined(VXGE_HAL_BP_POST) 1005221167Sgnn vxge_os_spin_lock(&blockpool->pool_lock); 1006221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 1007221167Sgnn vxge_os_spin_lock_irq(&blockpool->pool_lock, flags); 1008221167Sgnn#endif 1009221167Sgnn 1010221167Sgnn while ((block_entry = (__hal_blockpool_entry_t *) 1011221167Sgnn vxge_list_first_get(blocklist)) != NULL) { 1012221167Sgnn 1013221167Sgnn vxge_list_remove(&block_entry->item); 1014221167Sgnn 1015221167Sgnn vxge_list_insert(&block_entry->item, 1016221167Sgnn &blockpool->free_block_list); 1017221167Sgnn 1018221167Sgnn blockpool->pool_size++; 1019221167Sgnn } 1020221167Sgnn 1021221167Sgnn#if defined(VXGE_HAL_BP_POST) 1022221167Sgnn vxge_os_spin_unlock(&blockpool->pool_lock); 1023221167Sgnn#elif defined(VXGE_HAL_BP_POST_IRQ) 1024221167Sgnn vxge_os_spin_unlock_irq(&blockpool->pool_lock, flags); 1025221167Sgnn#endif 1026221167Sgnn 1027221167Sgnn __hal_blockpool_blocks_remove(blockpool); 1028221167Sgnn 1029221167Sgnn vxge_hal_trace_log_pool("<== %s:%s:%d Result: 0", 1030221167Sgnn __FILE__, __func__, __LINE__); 1031221167Sgnn} 1032