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 2009 Sun Microsystems, Inc. All rights reserved. 24 * Use is subject to license terms. 25 */ 26 27 #ifndef _SYS_IB_ADAPTERS_HERMON_RSRC_H 28 #define _SYS_IB_ADAPTERS_HERMON_RSRC_H 29 30 /* 31 * hermon_rsrc.h 32 * Contains all of the prototypes, #defines, and structures necessary 33 * for the Hermon Resource Management routines. 34 * Specifically it contains the resource names, resource types, and 35 * structures used for enabling both init/fini and alloc/free operations. 36 */ 37 38 #include <sys/types.h> 39 #include <sys/conf.h> 40 #include <sys/ddi.h> 41 #include <sys/sunddi.h> 42 #include <sys/disp.h> 43 44 #ifdef __cplusplus 45 extern "C" { 46 #endif 47 48 /* 49 * The above extern and the following #defines and macro are used to determine 50 * the current context for purposes of setting the sleepflag. If the calling 51 * thread is running in the interrupt context, then macro will return 52 * HERMON_NOSLEEP (indicating that it is not appropriate to sleep in the current 53 * context. In all other cases, this macro will return HERMON_SLEEP. 54 * 55 * The HERMON_CMD_SLEEP_NOSPIN and HERMON_CMD_NOSLEEP_SPIN #defines from 56 * hermon_cmd.h are set to use and be compatible with the following SLEEP 57 * variables. It is important that these remain in sync so that the 58 * HERMON_SLEEPFLAG_FOR_CONTEXT() macro will work in all cases. 59 */ 60 #define HERMON_SLEEP 0 61 #define HERMON_NOSLEEP 1 62 #define HERMON_SLEEPFLAG_FOR_CONTEXT() \ 63 ((servicing_interrupt() || ddi_in_panic()) ? HERMON_NOSLEEP : \ 64 HERMON_SLEEP) 65 66 /* 67 * The following #defines are used as the names for various resource pools. 68 * They represent the kmem_cache and vmem_arena names, respectively. In 69 * order to provide for unique naming when multiple Hermon drivers are present, 70 * the HERMON_RSRC_NAME macro below is used to append the driver's instance 71 * number to the provided string. Note: resource names should not be longer 72 * than HERMON_RSRC_NAME_MAXLEN. 73 */ 74 75 76 #define HERMON_RSRC_CACHE "hermon_rsrc_cache" 77 #define HERMON_PDHDL_CACHE "hermon_pdhdl_cache" 78 #define HERMON_MRHDL_CACHE "hermon_mrhdl_cache" 79 #define HERMON_EQHDL_CACHE "hermon_eqhdl_cache" 80 #define HERMON_CQHDL_CACHE "hermon_cqhdl_cache" 81 #define HERMON_SRQHDL_CACHE "hermon_srqhdl_cache" 82 #define HERMON_AHHDL_CACHE "hermon_ahhdl_cache" 83 #define HERMON_QPHDL_CACHE "hermon_qphdl_cache" 84 #define HERMON_REFCNT_CACHE "hermon_refcnt_cache" 85 86 #define HERMON_ICM_VMEM "hermon_icm_vmem" 87 #define HERMON_INMBOX_VMEM "hermon_inmbox_vmem" 88 #define HERMON_OUTMBOX_VMEM "hermon_outmbox_vmem" 89 #define HERMON_INTR_INMBOX_VMEM "hermon_intr_inmbox_vmem" 90 #define HERMON_INTR_OUTMBOX_VMEM "hermon_intr_outmbox_vmem" 91 /* ICM based vmem */ 92 #define HERMON_CMPT_VMEM "hermon_cmpt_vmem" 93 #define HERMON_CMPT_QPC_VMEM "hermon_cmpt_qpc_vmem" 94 #define HERMON_CMPT_SRQ_VMEM "hermon_cmpt_srq_vmem" 95 #define HERMON_CMPT_CQC_VMEM "hermon_cmpt_cqc_vmem" 96 #define HERMON_CMPT_EQC_VMEM "hermon_cmpt_eqc_vmem" 97 #define HERMON_DMPT_VMEM "hermon_dmpt_vmem" 98 #define HERMON_MTT_VMEM "hermon_mtt_vmem" 99 #define HERMON_QPC_VMEM "hermon_qpc_vmem" 100 #define HERMON_SRQC_VMEM "hermon_srqc_vmem" 101 #define HERMON_RDB_VMEM "hermon_rdb_vmem" 102 #define HERMON_CQC_VMEM "hermon_cqc_vmem" 103 #define HERMON_ALTC_VMEM "hermon_altc_vmem" 104 #define HERMON_AUXC_VMEM "hermon_auxc_vmem" 105 #define HERMON_EQC_VMEM "hermon_eqc_vmem" 106 #define HERMON_MCG_VMEM "hermon_mcg_vmem" 107 /* Add'd vmem arenas */ 108 #define HERMON_UAR_PAGE_VMEM_ATTCH "hermon_uar_pg_vmem:a" 109 #define HERMON_UAR_PAGE_VMEM_RUNTM "hermon_uar_pg_vmem:r" 110 #define HERMON_BLUEFLAME_VMEM "hermon_blueflame_vmem" 111 #define HERMON_PDHDL_VMEM "hermon_pd_vmem" 112 113 /* Macro provided for building unique naming for multiple instance */ 114 #define HERMON_RSRC_NAME(rsrc_name, string) \ 115 (void) sprintf((rsrc_name), string"%08X", \ 116 state->hs_instance) 117 #define HERMON_RSRC_NAME_MAXLEN 0x80 118 119 /* various cMPT types - need to concatenate w/ index to find it in ICM */ 120 typedef enum { 121 HERMON_QP_CMPT = 0, 122 HERMON_SRQ_CMPT = 1, 123 HERMON_CQ_CMPT = 2, 124 HERMON_EQ_CMPT = 3, 125 HERMON_MPT_DMPT = 4 126 } hermon_mpt_rsrc_type_t; 127 128 129 /* 130 * The following enumerated type is used to capture all the various types 131 * of Hermon resources. Note the HERMON_NUM_RESOURCES type is used as a marker 132 * for the end of the resource types. No additional resources should be 133 * added after this. Note also that HERMON_NUM_ICM_RESOURCES is used similarly, 134 * indicating the number of ICM resource types. If additional ICM types are 135 * added, they should be added before MERMON_NUM_ICM_RESOURCES. 136 */ 137 138 typedef enum { 139 HERMON_CMPT, /* for sizing ICM space for control MPTs */ 140 HERMON_QPC, 141 HERMON_SRQC, 142 HERMON_CQC, 143 HERMON_EQC, 144 HERMON_DMPT, 145 HERMON_MTT, 146 HERMON_ALTC, /* for allocation of ICM backing memory */ 147 HERMON_AUXC, /* for allocation of ICM backing memory */ 148 HERMON_RDB, /* for allocation of ICM backing memory */ 149 HERMON_CMPT_QPC, /* for allocation of ICM backing memory */ 150 HERMON_CMPT_SRQC, /* for allocation of ICM backing memory */ 151 HERMON_CMPT_CQC, /* for allocation of ICM backing memory */ 152 HERMON_CMPT_EQC, /* for allocation of ICM backing memory */ 153 HERMON_MCG, /* type 0x0E */ 154 /* all types above are in ICM, all below are in non-ICM */ 155 HERMON_NUM_ICM_RESOURCES, 156 HERMON_IN_MBOX = HERMON_NUM_ICM_RESOURCES, 157 HERMON_OUT_MBOX, /* type 0x10 */ 158 HERMON_PDHDL, 159 HERMON_MRHDL, 160 HERMON_EQHDL, 161 HERMON_CQHDL, 162 HERMON_QPHDL, 163 HERMON_SRQHDL, 164 HERMON_AHHDL, 165 HERMON_REFCNT, 166 HERMON_UARPG, 167 HERMON_INTR_IN_MBOX, 168 HERMON_INTR_OUT_MBOX, /* type 0x1B */ 169 HERMON_NUM_RESOURCES 170 } hermon_rsrc_type_t; 171 172 /* 173 * The following enumerated type and structures are used during resource 174 * initialization. Note: The HERMON_RSRC_CLEANUP_ALL type is used as a marker 175 * for end of the cleanup steps. No cleanup steps should be added after 176 * HERMON_RSRC_CLEANUP_ALL. Any addition steps should be added before it. 177 */ 178 typedef enum { 179 HERMON_RSRC_CLEANUP_LEVEL0, 180 HERMON_RSRC_CLEANUP_LEVEL1, 181 HERMON_RSRC_CLEANUP_LEVEL2, 182 HERMON_RSRC_CLEANUP_LEVEL3, 183 HERMON_RSRC_CLEANUP_LEVEL4, 184 HERMON_RSRC_CLEANUP_LEVEL5, 185 HERMON_RSRC_CLEANUP_LEVEL6, 186 HERMON_RSRC_CLEANUP_LEVEL7, 187 HERMON_RSRC_CLEANUP_PHASE1_COMPLETE, 188 HERMON_RSRC_CLEANUP_LEVEL8, 189 HERMON_RSRC_CLEANUP_LEVEL9, 190 HERMON_RSRC_CLEANUP_LEVEL10, 191 HERMON_RSRC_CLEANUP_LEVEL10QP, 192 HERMON_RSRC_CLEANUP_LEVEL10SRQ, 193 HERMON_RSRC_CLEANUP_LEVEL10CQ, 194 HERMON_RSRC_CLEANUP_LEVEL10EQ, 195 HERMON_RSRC_CLEANUP_LEVEL11, 196 HERMON_RSRC_CLEANUP_LEVEL12, 197 HERMON_RSRC_CLEANUP_LEVEL13, 198 HERMON_RSRC_CLEANUP_LEVEL14, 199 HERMON_RSRC_CLEANUP_LEVEL15, 200 HERMON_RSRC_CLEANUP_LEVEL16, 201 HERMON_RSRC_CLEANUP_LEVEL17, 202 HERMON_RSRC_CLEANUP_LEVEL18, 203 HERMON_RSRC_CLEANUP_LEVEL19, 204 HERMON_RSRC_CLEANUP_LEVEL20, 205 HERMON_RSRC_CLEANUP_LEVEL21, 206 HERMON_RSRC_CLEANUP_LEVEL22, 207 HERMON_RSRC_CLEANUP_LEVEL23, 208 HERMON_RSRC_CLEANUP_LEVEL24, 209 HERMON_RSRC_CLEANUP_LEVEL25, 210 HERMON_RSRC_CLEANUP_LEVEL26, 211 HERMON_RSRC_CLEANUP_LEVEL27, 212 HERMON_RSRC_CLEANUP_LEVEL28, 213 HERMON_RSRC_CLEANUP_LEVEL29, 214 HERMON_RSRC_CLEANUP_LEVEL30, 215 HERMON_RSRC_CLEANUP_LEVEL31, 216 /* No more cleanup steps below this point! */ 217 HERMON_RSRC_CLEANUP_ALL 218 } hermon_rsrc_cleanup_level_t; 219 220 /* 221 * The hermon_rsrc_mbox_info_t structure is used when initializing the two 222 * Hermon mailbox types ("In" and "Out"). This structure contains the 223 * requested number and size of the mailboxes, and the resource pool from 224 * which the other relevant properties will come. 225 */ 226 typedef struct hermon_rsrc_mbox_info_s { 227 uint64_t mbi_num; 228 uint64_t mbi_size; 229 hermon_rsrc_pool_info_t *mbi_rsrcpool; 230 } hermon_rsrc_mbox_info_t; 231 232 /* 233 * The hermon_rsrc_hw_entry_info_t structure is used when initializing the 234 * Hermon HW entry types. This structure contains the requested number of 235 * entries for the resource. That value is compared against the maximum 236 * number (usually determined as a result of the Hermon QUERY_DEV_CAP command). 237 * In addition it contains a number of requested entries to be "pre-allocated" 238 * (this is generally because the Hermon hardware requires a certain number 239 * for its own purposes). Lastly the resource pool and resource name 240 * information. 241 */ 242 typedef struct hermon_rsrc_hw_entry_info_s { 243 uint64_t hwi_num; 244 uint64_t hwi_max; 245 uint64_t hwi_prealloc; 246 hermon_rsrc_pool_info_t *hwi_rsrcpool; 247 char *hwi_rsrcname; 248 } hermon_rsrc_hw_entry_info_t; 249 250 /* 251 * The hermon_rsrc_sw_hdl_info_t structure is used when initializing the 252 * Hermon software handle types. This structure also contains the requested 253 * number of handles for the resource. That value is compared against a 254 * maximum number passed in. Because many of the software handle resource 255 * types are managed through the use of kmem_cache, fields are provided for 256 * specifying cache constructor and destructor methods. Just like above, 257 * there is space for resource pool and resource name information. And, 258 * somewhat like above, there is space to provide information (size, type, 259 * pointer to table, etc). about any "pre-allocated" resources that need to 260 * be set aside. 261 * Note specifically that the "swi_flags" field may contain any of the flags 262 * #define'd below. The HERMON_SWHDL_KMEMCACHE_INIT flag indicates that the 263 * given resource should have a kmem_cache setup for it, and the 264 * HERMON_SWHDL_TABLE_INIT flag indicates that some preallocation (as defined 265 * by the "swi_num" and "swi_prealloc_sz" fields) should be done, with the 266 * resulting table pointer passed back in "swi_table_ptr". 267 */ 268 typedef struct hermon_rsrc_sw_hdl_info_s { 269 uint64_t swi_num; 270 uint64_t swi_max; 271 uint64_t swi_prealloc_sz; 272 hermon_rsrc_pool_info_t *swi_rsrcpool; 273 int (*swi_constructor)(void *, void *, int); 274 void (*swi_destructor)(void *, void *); 275 char *swi_rsrcname; 276 uint_t swi_flags; 277 void *swi_table_ptr; 278 } hermon_rsrc_sw_hdl_info_t; 279 #define HERMON_SWHDL_NOFLAGS 0 280 #define HERMON_SWHDL_KMEMCACHE_INIT (1 << 0) 281 #define HERMON_SWHDL_TABLE_INIT (1 << 1) 282 283 284 /* 285 * The following structure is used to specify (at init time) and to track 286 * (during allocation and freeing) all the useful information regarding a 287 * particular resource type. An array of these resources (indexed by 288 * resource type) is allocated at driver startup time. It is available 289 * through the driver's soft state structure. 290 * Each resource has an indication of its type and its location. Resources 291 * may be located in one of three possible places - in the Hermon ICM memory 292 * (device virtual, backed by system memory),in system memory, or in 293 * Hermon UAR memory (residing behind BAR2). 294 * Each resource pool also has properties associated with it and the object 295 * that make up the pool. These include the pool's size, the size of the 296 * individual objects (rsrc_quantum), any alignment restrictions placed on 297 * the pool of objects, and the shift size (log2) of each object. 298 * In addition (depending on object type) the "rsrc_ddr_offset" field may 299 * indicate where in DDR memory a given resource pool is located (e.g. a 300 * QP context table). It may have a pointer to a vmem_arena for that table 301 * and/or it may point to some other private information (rsrc_private) 302 * specific to the given object type. 303 * Always, though, the resource pool pointer provides a pointer back to the 304 * soft state structure of the Hermon driver instance with which it is 305 * associated. 306 */ 307 struct hermon_rsrc_pool_info_s { 308 hermon_rsrc_type_t rsrc_type; 309 uint_t rsrc_loc; 310 uint64_t rsrc_pool_size; /* table size (num x size) */ 311 uint64_t rsrc_align; 312 uint_t rsrc_shift; 313 uint_t rsrc_quantum; /* size of each content */ 314 void *rsrc_start; /* phys start addr of table */ 315 vmem_t *rsrc_vmp; /* vmem arena for table */ 316 hermon_state_t *rsrc_state; 317 void *rsrc_private; 318 }; 319 #define HERMON_IN_ICM 0x0 320 #define HERMON_IN_SYSMEM 0x1 321 #define HERMON_IN_UAR 0x2 322 323 /* 324 * The hermon_rsrc_priv_mbox_t structure is used to pass along additional 325 * information about the mailbox types. Specifically, by containing the 326 * DMA attributes, access handle, dev access handle, etc., it provides enough 327 * information that each mailbox can be later by bound/unbound/etc. for 328 * DMA access by the hardware. Note: we can also specify (using the 329 * "pmb_xfer_mode" field), whether a given mailbox type should be bound for 330 * DDI_DMA_STREAMING or DDI_DMA_CONSISTENT operations. 331 */ 332 typedef struct hermon_rsrc_priv_mbox_s { 333 dev_info_t *pmb_dip; 334 ddi_dma_attr_t pmb_dmaattr; 335 /* JBDB what is this handle for? */ 336 ddi_acc_handle_t pmb_acchdl; 337 ddi_device_acc_attr_t pmb_devaccattr; 338 uint_t pmb_xfer_mode; 339 } hermon_rsrc_priv_mbox_t; 340 341 /* 342 * The hermon_rsrc_t structure is the structure returned by the Hermon resource 343 * allocation routines. It contains all the necessary information about the 344 * allocated object. Specifically, it provides an address where the object 345 * can be accessed. It also provides the length and index (specifically, for 346 * those resources that are accessed from tables). In addition it can provide 347 * an access handles and DMA handle to be used when accessing or setting DMA 348 * to a specific object. Note: not all of this information is valid for all 349 * object types. See the consumers of each object for more explanation of 350 * which fields are used (and for what purpose). 351 */ 352 struct hermon_rsrc_s { 353 hermon_rsrc_type_t rsrc_type; 354 void *hr_addr; 355 uint32_t hr_len; 356 uint32_t hr_indx; 357 ddi_acc_handle_t hr_acchdl; 358 ddi_dma_handle_t hr_dmahdl; 359 }; 360 361 /* 362 * The following are the Hermon Resource Management routines that accessible 363 * externally (i.e. throughout the rest of the Hermon driver software). 364 * These include the alloc/free routines, the initialization routines, which 365 * are broken into two phases (see hermon_rsrc.c for further explanation), 366 * and the Hermon resource cleanup routines (which are used at driver detach() 367 * time. 368 */ 369 int hermon_rsrc_alloc(hermon_state_t *state, hermon_rsrc_type_t rsrc, 370 uint_t num, uint_t sleepflag, hermon_rsrc_t **hdl); 371 void hermon_rsrc_free(hermon_state_t *state, hermon_rsrc_t **hdl); 372 int hermon_rsrc_init_phase1(hermon_state_t *state); 373 int hermon_rsrc_init_phase2(hermon_state_t *state); 374 void hermon_rsrc_fini(hermon_state_t *state, 375 hermon_rsrc_cleanup_level_t clean); 376 377 378 #ifdef __cplusplus 379 } 380 #endif 381 382 #endif /* _SYS_IB_ADAPTERS_HERMON_RSRC_H */ 383