1 /* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License (the "License"). 6 * You may not use this file except in compliance with the License. 7 * 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9 * or http://www.opensolaris.org/os/licensing. 10 * See the License for the specific language governing permissions 11 * and limitations under the License. 12 * 13 * When distributing Covered Code, include this CDDL HEADER in each 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15 * If applicable, add the following below this CDDL HEADER, with the 16 * fields enclosed by brackets "[]" replaced with your own identifying 17 * information: Portions Copyright [yyyy] [name of copyright owner] 18 * 19 * CDDL HEADER END 20 */ 21 22 /* 23 * Copyright 2010 Emulex. All rights reserved. 24 * Use is subject to license terms. 25 */ 26 27 /* 28 * Header file defining the driver buffer management interface 29 */ 30 31 #ifndef _OCE_BUF_H_ 32 #define _OCE_BUF_H_ 33 34 #ifdef __cplusplus 35 extern "C" { 36 #endif 37 38 #include <sys/ddidmareq.h> 39 #include <oce_io.h> 40 #include <oce_utils.h> 41 42 #define GET_Q_NEXT(_START, _STEP, _END) \ 43 (((_START) + (_STEP)) < (_END) ? ((_START) + (_STEP)) \ 44 : (((_START) + (_STEP)) - (_END))) 45 46 #define OCE_MAX_TX_HDL 8 47 #define OCE_MAX_TXDMA_COOKIES 16 48 #define OCE_TXMAP_ALIGN 1 49 #define OCE_TX_MAX_FRAGS (OCE_MAX_TX_HDL * OCE_MAX_TXDMA_COOKIES) 50 #define OCE_TX_LO_WM OCE_TX_MAX_FRAGS 51 52 /* helper structure to access OS addresses */ 53 typedef union oce_addr_s { 54 uint64_t addr64; 55 struct { 56 #ifdef _BIG_ENDIAN 57 uint32_t addr_hi; 58 uint32_t addr_lo; 59 #else 60 uint32_t addr_lo; 61 uint32_t addr_hi; 62 #endif 63 }dw; 64 }oce_addr64_t; 65 66 typedef struct oce_dma_buf_s { 67 caddr_t base; 68 uint64_t addr; 69 ddi_acc_handle_t acc_handle; 70 ddi_dma_handle_t dma_handle; 71 /* size of the memory */ 72 size_t size; 73 size_t off; 74 size_t len; 75 uint32_t num_pages; 76 }oce_dma_buf_t; 77 78 #define DBUF_PA(obj) (((oce_dma_buf_t *)(obj))->addr) 79 #define DBUF_VA(obj) (((oce_dma_buf_t *)(obj))->base) 80 #define DBUF_DHDL(obj) (((oce_dma_buf_t *)(obj))->dma_handle) 81 #define DBUF_AHDL(obj) (((oce_dma_buf_t *)obj))->acc_handle) 82 #define DBUF_SYNC(obj, flags) ddi_dma_sync(DBUF_DHDL(obj), 0,\ 83 ((oce_dma_buf_t *)obj)->len, (flags)) 84 85 typedef struct oce_ring_buffer_s { 86 uint16_t cidx; /* Get ptr */ 87 uint16_t pidx; /* Put Ptr */ 88 size_t item_size; /* Size */ 89 size_t num_items; /* count */ 90 uint32_t num_used; 91 oce_dma_buf_t *dbuf; /* dma buffer */ 92 }oce_ring_buffer_t; 93 94 typedef struct oce_rq_bdesc_s { 95 OCE_LIST_NODE_T link; 96 oce_dma_buf_t *rqb; 97 struct oce_rq *rq; 98 oce_addr64_t frag_addr; 99 mblk_t *mp; 100 frtn_t fr_rtn; 101 }oce_rq_bdesc_t; 102 103 typedef struct oce_wq_bdesc_s { 104 OCE_LIST_NODE_T link; 105 oce_dma_buf_t *wqb; 106 oce_addr64_t frag_addr; 107 } oce_wq_bdesc_t; 108 109 typedef struct oce_wq_mdesc_s { 110 OCE_LIST_NODE_T link; 111 ddi_dma_handle_t dma_handle; 112 } oce_wq_mdesc_t; 113 114 enum entry_type { 115 HEADER_WQE = 0x1, /* arbitrary value */ 116 MAPPED_WQE, 117 COPY_WQE, 118 DUMMY_WQE 119 }; 120 121 typedef struct _oce_handle_s { 122 void *hdl; /* opaque handle */ 123 }oce_handle_t; 124 125 typedef struct _oce_wqe_desc_s { 126 OCE_LIST_NODE_T link; 127 oce_handle_t hdesc[OCE_MAX_TX_HDL]; 128 struct oce_nic_frag_wqe frag[OCE_TX_MAX_FRAGS]; 129 struct oce_wq *wq; 130 mblk_t *mp; 131 enum entry_type type; 132 uint16_t wq_start_idx; 133 uint16_t wq_end_idx; 134 uint16_t wqe_cnt; 135 uint16_t pkt_len; /* 64K MAX */ 136 uint32_t frag_cnt; 137 uint32_t nhdl; 138 }oce_wqe_desc_t; 139 140 #pragma pack(1) 141 /* Always keep it 2 mod 4 */ 142 typedef struct _oce_rq_buf_hdr_s { 143 void *datap; 144 uint8_t pad[18]; 145 /* ether_vlan_header_t vhdr; */ 146 } oce_rq_buf_hdr_t; 147 #pragma pack() 148 149 #define OCE_RQE_BUF_HEADROOM sizeof (oce_rq_buf_hdr_t) 150 #define MAX_POOL_NAME 32 151 152 #define RING_NUM_PENDING(ring) ring->num_used 153 154 #define RING_NUM_FREE(ring) \ 155 (uint32_t)(ring->num_items - ring->num_used) 156 157 #define RING_FULL(ring) (ring->num_used == ring->num_items) 158 159 #define RING_EMPTY(ring) (ring->num_used == 0) 160 161 #define RING_GET(ring, n) \ 162 ring->cidx = GET_Q_NEXT(ring->cidx, n, ring->num_items) 163 164 #define RING_PUT(ring, n) \ 165 ring->pidx = GET_Q_NEXT(ring->pidx, n, ring->num_items) 166 167 #define RING_GET_CONSUMER_ITEM_VA(ring, type) \ 168 (void*)(((type *)DBUF_VA(ring->dbuf)) + ring->cidx) 169 170 #define RING_GET_CONSUMER_ITEM_PA(ring, type) \ 171 (uint64_t)(((type *)DBUF_PA(ring->dbuf)) + ring->cidx) 172 173 #define RING_GET_PRODUCER_ITEM_VA(ring, type) \ 174 (void *)(((type *)DBUF_VA(ring->dbuf)) + ring->pidx) 175 176 #define RING_GET_PRODUCER_ITEM_PA(ring, type) \ 177 (uint64_t)(((type *)DBUF_PA(ring->dbuf)) + ring->pidx) 178 179 /* Rq cache */ 180 int oce_rqb_cache_create(struct oce_rq *rq, size_t buf_size); 181 void oce_rqb_cache_destroy(struct oce_rq *rq); 182 183 /* Wq Cache */ 184 int oce_wqe_desc_ctor(void *buf, void *arg, int kmflags); 185 void oce_wqe_desc_dtor(void *buf, void *arg); 186 187 int oce_wqb_cache_create(struct oce_wq *wq, size_t buf_size); 188 void oce_wqb_cache_destroy(struct oce_wq *wq); 189 190 void oce_wqm_cache_destroy(struct oce_wq *wq); 191 int oce_wqm_cache_create(struct oce_wq *wq); 192 193 void oce_page_list(oce_dma_buf_t *dbuf, 194 struct phys_addr *pa_list, int list_size); 195 196 197 #ifdef __cplusplus 198 } 199 #endif 200 201 #endif /* _OCE_BUF_H_ */ 202