emlxs_mbox.c (728bdc9b) | emlxs_mbox.c (291a2b48) |
---|---|
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 --- 6 unchanged lines hidden (view full) --- 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/* | 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 --- 6 unchanged lines hidden (view full) --- 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 2008 Emulex. All rights reserved. | 23 * Copyright 2009 Emulex. All rights reserved. |
24 * Use is subject to License terms. 25 */ 26 | 24 * Use is subject to License terms. 25 */ 26 |
27#include <emlxs.h> |
|
27 | 28 |
28#include "emlxs.h" 29 | |
30/* Required for EMLXS_CONTEXT in EMLXS_MSGF calls */ 31EMLXS_MSG_DEF(EMLXS_MBOX_C); 32 | 29/* Required for EMLXS_CONTEXT in EMLXS_MSGF calls */ 30EMLXS_MSG_DEF(EMLXS_MBOX_C); 31 |
33static void emlxs_mb_part_slim(emlxs_hba_t *hba, MAILBOX *mb, 34 uint32_t hbainit); 35static void emlxs_mb_set_mask(emlxs_hba_t *hba, MAILBOX *mb, uint32_t mask, 36 uint32_t ringno); 37static void emlxs_mb_set_debug(emlxs_hba_t *hba, MAILBOX *mb, uint32_t word0, 38 uint32_t word1, uint32_t word2); 39static int32_t emlxs_mb_handle_cmd(emlxs_hba_t *hba, MAILBOX *mb); 40static void emlxs_mb_write_nv(emlxs_hba_t *hba, MAILBOX *mb); | 32static void emlxs_mb_part_slim(emlxs_hba_t *hba, MAILBOX *mb, 33 uint32_t hbainit); 34static void emlxs_mb_set_mask(emlxs_hba_t *hba, MAILBOX *mb, uint32_t mask, 35 uint32_t ringno); 36static void emlxs_mb_set_debug(emlxs_hba_t *hba, MAILBOX *mb, 37 uint32_t word0, uint32_t word1, uint32_t word2); 38static int32_t emlxs_mb_handle_cmd(emlxs_hba_t *hba, MAILBOX *mb); 39static void emlxs_mb_write_nv(emlxs_hba_t *hba, MAILBOX *mb); |
41 | 40 |
42static void emlxs_mb_init(emlxs_hba_t *hba, MAILBOXQ *mbq, uint32_t flag, 43 uint32_t tmo); 44static void emlxs_mb_retry(emlxs_hba_t *hba, MAILBOX *mb); | |
45 | 41 |
46 47emlxs_table_t emlxs_mb_cmd_table[] = 48{ | 42emlxs_table_t emlxs_mb_cmd_table[] = { |
49 {MBX_SHUTDOWN, "SHUTDOWN"}, 50 {MBX_LOAD_SM, "LOAD_SM"}, 51 {MBX_READ_NV, "READ_NV"}, 52 {MBX_WRITE_NV, "WRITE_NV"}, 53 {MBX_RUN_BIU_DIAG, "RUN_BIU_DIAG"}, 54 {MBX_INIT_LINK, "INIT_LINK"}, 55 {MBX_DOWN_LINK, "DOWN_LINK"}, 56 {MBX_CONFIG_LINK, "CONFIG_LINK"}, --- 41 unchanged lines hidden (view full) --- 98 {MBX_BEACON, "BEACON"}, 99 {MBX_CONFIG_HBQ, "CONFIG_HBQ"}, /* SLI3 */ 100 {MBX_REG_VPI, "REG_VPI"}, /* NPIV */ 101 {MBX_ASYNC_EVENT, "ASYNC_EVENT"}, 102 {MBX_HEARTBEAT, "HEARTBEAT"}, 103 {MBX_READ_EVENT_LOG_STATUS, "READ_EVENT_LOG_STATUS"}, 104 {MBX_READ_EVENT_LOG, "READ_EVENT_LOG"}, 105 {MBX_WRITE_EVENT_LOG, "WRITE_EVENT_LOG"}, | 43 {MBX_SHUTDOWN, "SHUTDOWN"}, 44 {MBX_LOAD_SM, "LOAD_SM"}, 45 {MBX_READ_NV, "READ_NV"}, 46 {MBX_WRITE_NV, "WRITE_NV"}, 47 {MBX_RUN_BIU_DIAG, "RUN_BIU_DIAG"}, 48 {MBX_INIT_LINK, "INIT_LINK"}, 49 {MBX_DOWN_LINK, "DOWN_LINK"}, 50 {MBX_CONFIG_LINK, "CONFIG_LINK"}, --- 41 unchanged lines hidden (view full) --- 92 {MBX_BEACON, "BEACON"}, 93 {MBX_CONFIG_HBQ, "CONFIG_HBQ"}, /* SLI3 */ 94 {MBX_REG_VPI, "REG_VPI"}, /* NPIV */ 95 {MBX_ASYNC_EVENT, "ASYNC_EVENT"}, 96 {MBX_HEARTBEAT, "HEARTBEAT"}, 97 {MBX_READ_EVENT_LOG_STATUS, "READ_EVENT_LOG_STATUS"}, 98 {MBX_READ_EVENT_LOG, "READ_EVENT_LOG"}, 99 {MBX_WRITE_EVENT_LOG, "WRITE_EVENT_LOG"}, |
106 {MBX_NV_LOG, "NV_LOG"} 107 | 100 {MBX_NV_LOG, "NV_LOG"}, 101 {MBX_PORT_CAPABILITIES, "PORT_CAPABILITIES"}, 102 {MBX_IOV_CONTROL, "IOV_CONTROL"}, 103 {MBX_IOV_MBX, "IOV_MBX"} |
108}; /* emlxs_mb_cmd_table */ 109 110 | 104}; /* emlxs_mb_cmd_table */ 105 106 |
111/* ARGSUSED */ | 107/*ARGSUSED*/ |
112extern void 113emlxs_mb_async_event(emlxs_hba_t *hba, MAILBOX *mb) 114{ 115 bzero((void *) mb, MAILBOX_CMD_BSIZE); 116 117 mb->mbxCommand = MBX_ASYNC_EVENT; 118 mb->mbxOwner = OWN_HOST; 119 mb->un.varWords[0] = FC_ELS_RING; 120 121 return; 122 123} /* emlxs_mb_async_event() */ 124 125 | 108extern void 109emlxs_mb_async_event(emlxs_hba_t *hba, MAILBOX *mb) 110{ 111 bzero((void *) mb, MAILBOX_CMD_BSIZE); 112 113 mb->mbxCommand = MBX_ASYNC_EVENT; 114 mb->mbxOwner = OWN_HOST; 115 mb->un.varWords[0] = FC_ELS_RING; 116 117 return; 118 119} /* emlxs_mb_async_event() */ 120 121 |
126/* ARGSUSED */ | 122/*ARGSUSED*/ |
127extern void 128emlxs_mb_heartbeat(emlxs_hba_t *hba, MAILBOX *mb) 129{ 130 bzero((void *) mb, MAILBOX_CMD_BSIZE); 131 132 mb->mbxCommand = MBX_HEARTBEAT; 133 mb->mbxOwner = OWN_HOST; 134 135 return; 136 137} /* emlxs_mb_heartbeat() */ 138 139 140#ifdef MSI_SUPPORT 141 | 123extern void 124emlxs_mb_heartbeat(emlxs_hba_t *hba, MAILBOX *mb) 125{ 126 bzero((void *) mb, MAILBOX_CMD_BSIZE); 127 128 mb->mbxCommand = MBX_HEARTBEAT; 129 mb->mbxOwner = OWN_HOST; 130 131 return; 132 133} /* emlxs_mb_heartbeat() */ 134 135 136#ifdef MSI_SUPPORT 137 |
142/* ARGSUSED */ | 138/*ARGSUSED*/ |
143extern void 144emlxs_mb_config_msi(emlxs_hba_t *hba, MAILBOX *mb, uint32_t *intr_map, 145 uint32_t intr_count) 146{ 147 uint32_t i; 148 uint32_t mask; 149 | 139extern void 140emlxs_mb_config_msi(emlxs_hba_t *hba, MAILBOX *mb, uint32_t *intr_map, 141 uint32_t intr_count) 142{ 143 uint32_t i; 144 uint32_t mask; 145 |
150 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 146 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
151 152 mb->mbxCommand = MBX_CONFIG_MSI; 153 154 /* Set the default message id to zero */ 155 mb->un.varCfgMSI.defaultPresent = 1; 156 mb->un.varCfgMSI.defaultMessageNumber = 0; 157 158 for (i = 1; i < intr_count; i++) { --- 53 unchanged lines hidden (view full) --- 212 213 mb->mbxOwner = OWN_HOST; 214 215 return; 216 217} /* emlxs_mb_config_msi() */ 218 219 | 147 148 mb->mbxCommand = MBX_CONFIG_MSI; 149 150 /* Set the default message id to zero */ 151 mb->un.varCfgMSI.defaultPresent = 1; 152 mb->un.varCfgMSI.defaultMessageNumber = 0; 153 154 for (i = 1; i < intr_count; i++) { --- 53 unchanged lines hidden (view full) --- 208 209 mb->mbxOwner = OWN_HOST; 210 211 return; 212 213} /* emlxs_mb_config_msi() */ 214 215 |
220/* ARGSUSED */ | 216/*ARGSUSED*/ |
221extern void 222emlxs_mb_config_msix(emlxs_hba_t *hba, MAILBOX *mb, uint32_t *intr_map, 223 uint32_t intr_count) 224{ 225 uint32_t i; 226 uint32_t mask; 227 | 217extern void 218emlxs_mb_config_msix(emlxs_hba_t *hba, MAILBOX *mb, uint32_t *intr_map, 219 uint32_t intr_count) 220{ 221 uint32_t i; 222 uint32_t mask; 223 |
228 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 224 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
229 230 mb->mbxCommand = MBX_CONFIG_MSIX; 231 232 /* Set the default message id to zero */ 233 mb->un.varCfgMSIX.defaultPresent = 1; 234 mb->un.varCfgMSIX.defaultMessageNumber = 0; 235 236 for (i = 1; i < intr_count; i++) { --- 55 unchanged lines hidden (view full) --- 292 293 return; 294 295} /* emlxs_mb_config_msix() */ 296 297 298#endif /* MSI_SUPPORT */ 299 | 225 226 mb->mbxCommand = MBX_CONFIG_MSIX; 227 228 /* Set the default message id to zero */ 229 mb->un.varCfgMSIX.defaultPresent = 1; 230 mb->un.varCfgMSIX.defaultMessageNumber = 0; 231 232 for (i = 1; i < intr_count; i++) { --- 55 unchanged lines hidden (view full) --- 288 289 return; 290 291} /* emlxs_mb_config_msix() */ 292 293 294#endif /* MSI_SUPPORT */ 295 |
300/* ARGSUSED */ | 296 297/*ARGSUSED*/ |
301extern void 302emlxs_mb_reset_ring(emlxs_hba_t *hba, MAILBOX *mb, uint32_t ringno) 303{ | 298extern void 299emlxs_mb_reset_ring(emlxs_hba_t *hba, MAILBOX *mb, uint32_t ringno) 300{ |
304 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 301 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
305 306 mb->mbxCommand = MBX_RESET_RING; 307 mb->un.varRstRing.ring_no = ringno; 308 mb->mbxOwner = OWN_HOST; 309 310 return; 311 312} /* emlxs_mb_reset_ring() */ 313 314 315 316/* | 302 303 mb->mbxCommand = MBX_RESET_RING; 304 mb->un.varRstRing.ring_no = ringno; 305 mb->mbxOwner = OWN_HOST; 306 307 return; 308 309} /* emlxs_mb_reset_ring() */ 310 311 312 313/* |
317 * emlxs_mb_dump_vpd Issue a DUMP MEMORY 318 * mailbox command | 314 * emlxs_mb_dump_vpd Issue a DUMP MEMORY mailbox command |
319 */ | 315 */ |
320/* ARGSUSED */ | 316/*ARGSUSED*/ |
321extern void 322emlxs_mb_dump_vpd(emlxs_hba_t *hba, MAILBOX *mb, uint32_t offset) 323{ | 317extern void 318emlxs_mb_dump_vpd(emlxs_hba_t *hba, MAILBOX *mb, uint32_t offset) 319{ |
324 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 320 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
325 326 /* 327 * Setup to dump VPD region 328 */ 329 mb->mbxCommand = MBX_DUMP_MEMORY; 330 mb->un.varDmp.cv = 1; 331 mb->un.varDmp.type = DMP_NV_PARAMS; 332 mb->un.varDmp.entry_index = offset; 333 mb->un.varDmp.region_id = DMP_VPD_REGION; | 321 322 /* 323 * Setup to dump VPD region 324 */ 325 mb->mbxCommand = MBX_DUMP_MEMORY; 326 mb->un.varDmp.cv = 1; 327 mb->un.varDmp.type = DMP_NV_PARAMS; 328 mb->un.varDmp.entry_index = offset; 329 mb->un.varDmp.region_id = DMP_VPD_REGION; |
334 mb->un.varDmp.word_cnt = DMP_VPD_DUMP_WCOUNT; /* limited by */ 335 /* mailbox size */ | |
336 | 330 |
331 /* limited by mailbox size */ 332 mb->un.varDmp.word_cnt = DMP_VPD_DUMP_WCOUNT; 333 |
|
337 mb->un.varDmp.co = 0; 338 mb->un.varDmp.resp_offset = 0; 339 mb->mbxOwner = OWN_HOST; | 334 mb->un.varDmp.co = 0; 335 mb->un.varDmp.resp_offset = 0; 336 mb->mbxOwner = OWN_HOST; |
337 |
|
340} /* emlxs_mb_dump_vpd() */ 341 342 | 338} /* emlxs_mb_dump_vpd() */ 339 340 |
341/*ARGSUSED*/ 342extern void 343emlxs_mb_dump(emlxs_hba_t *hba, MAILBOX *mb, uint32_t offset, uint32_t words) 344{ 345 bzero((void *)mb, MAILBOX_CMD_BSIZE); 346 347 mb->mbxCommand = MBX_DUMP_MEMORY; 348 mb->un.varDmp.type = DMP_MEM_REG; 349 mb->un.varDmp.word_cnt = words; 350 mb->un.varDmp.base_adr = offset; 351 352 mb->un.varDmp.co = 0; 353 mb->un.varDmp.resp_offset = 0; 354 mb->mbxOwner = OWN_HOST; 355 356 return; 357 358} /* emlxs_mb_dump() */ 359 360 361 |
|
343/* | 362/* |
344 * emlxs_mb_read_nv Issue a READ NVPARAM 345 * mailbox command | 363 * emlxs_mb_read_nv Issue a READ NVPARAM mailbox command |
346 */ | 364 */ |
347/* ARGSUSED */ | 365/*ARGSUSED*/ |
348extern void 349emlxs_mb_read_nv(emlxs_hba_t *hba, MAILBOX *mb) 350{ | 366extern void 367emlxs_mb_read_nv(emlxs_hba_t *hba, MAILBOX *mb) 368{ |
351 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 369 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
352 353 mb->mbxCommand = MBX_READ_NV; 354 mb->mbxOwner = OWN_HOST; | 370 371 mb->mbxCommand = MBX_READ_NV; 372 mb->mbxOwner = OWN_HOST; |
355 | |
356} /* End emlxs_mb_read_nv */ 357 358 359/* | 373} /* End emlxs_mb_read_nv */ 374 375 376/* |
360 * emlxs_mb_read_rev Issue a READ REV 361 * mailbox command | 377 * emlxs_mb_read_rev Issue a READ REV mailbox command |
362 */ | 378 */ |
363/* ARGSUSED */ | 379/*ARGSUSED*/ |
364extern void 365emlxs_mb_read_rev(emlxs_hba_t *hba, MAILBOX *mb, uint32_t v3) 366{ | 380extern void 381emlxs_mb_read_rev(emlxs_hba_t *hba, MAILBOX *mb, uint32_t v3) 382{ |
367 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 383 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
368 369 mb->un.varRdRev.cv = 1; 370 371 if (v3) { 372 mb->un.varRdRev.cv3 = 1; 373 } 374 375 mb->mbxCommand = MBX_READ_REV; 376 mb->mbxOwner = OWN_HOST; | 384 385 mb->un.varRdRev.cv = 1; 386 387 if (v3) { 388 mb->un.varRdRev.cv3 = 1; 389 } 390 391 mb->mbxCommand = MBX_READ_REV; 392 mb->mbxOwner = OWN_HOST; |
377 | |
378} /* End emlxs_mb_read_rev */ 379 380 381/* | 393} /* End emlxs_mb_read_rev */ 394 395 396/* |
382 * emlxs_mb_run_biu_diag Issue a RUN_BIU_DIAG 383 * mailbox command | 397 * emlxs_mb_run_biu_diag Issue a RUN_BIU_DIAG mailbox command |
384 */ | 398 */ |
385/* ARGSUSED */ | 399/*ARGSUSED*/ |
386extern uint32_t 387emlxs_mb_run_biu_diag(emlxs_hba_t *hba, MAILBOX *mb, uint64_t out, 388 uint64_t in) 389{ | 400extern uint32_t 401emlxs_mb_run_biu_diag(emlxs_hba_t *hba, MAILBOX *mb, uint64_t out, 402 uint64_t in) 403{ |
390 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 404 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
391 392 mb->mbxCommand = MBX_RUN_BIU_DIAG64; 393 mb->un.varBIUdiag.un.s2.xmit_bde64.tus.f.bdeSize = MEM_ELSBUF_SIZE; | 405 406 mb->mbxCommand = MBX_RUN_BIU_DIAG64; 407 mb->un.varBIUdiag.un.s2.xmit_bde64.tus.f.bdeSize = MEM_ELSBUF_SIZE; |
394 mb->un.varBIUdiag.un.s2.xmit_bde64.addrHigh = 395 (uint32_t)putPaddrHigh(out); 396 mb->un.varBIUdiag.un.s2.xmit_bde64.addrLow = 397 (uint32_t)putPaddrLow(out); | 408 mb->un.varBIUdiag.un.s2.xmit_bde64.addrHigh = putPaddrHigh(out); 409 mb->un.varBIUdiag.un.s2.xmit_bde64.addrLow = putPaddrLow(out); |
398 mb->un.varBIUdiag.un.s2.rcv_bde64.tus.f.bdeSize = MEM_ELSBUF_SIZE; | 410 mb->un.varBIUdiag.un.s2.rcv_bde64.tus.f.bdeSize = MEM_ELSBUF_SIZE; |
399 mb->un.varBIUdiag.un.s2.rcv_bde64.addrHigh = 400 (uint32_t)putPaddrHigh(in); 401 mb->un.varBIUdiag.un.s2.rcv_bde64.addrLow = (uint32_t)putPaddrLow(in); | 411 mb->un.varBIUdiag.un.s2.rcv_bde64.addrHigh = putPaddrHigh(in); 412 mb->un.varBIUdiag.un.s2.rcv_bde64.addrLow = putPaddrLow(in); |
402 mb->mbxOwner = OWN_HOST; 403 404 return (0); | 413 mb->mbxOwner = OWN_HOST; 414 415 return (0); |
405 | |
406} /* End emlxs_mb_run_biu_diag */ 407 408 409/* | 416} /* End emlxs_mb_run_biu_diag */ 417 418 419/* |
410 * emlxs_mb_read_la Issue a READ LA 411 * mailbox command | 420 * emlxs_mb_read_la Issue a READ LA mailbox command |
412 */ 413extern uint32_t 414emlxs_mb_read_la(emlxs_hba_t *hba, MAILBOX *mb) 415{ 416 MATCHMAP *mp; 417 | 421 */ 422extern uint32_t 423emlxs_mb_read_la(emlxs_hba_t *hba, MAILBOX *mb) 424{ 425 MATCHMAP *mp; 426 |
418 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 427 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
419 | 428 |
420 if ((mp = (MATCHMAP *) emlxs_mem_get(hba, MEM_BUF)) == 0) { | 429 if ((mp = (MATCHMAP *)emlxs_mem_get(hba, MEM_BUF)) == 0) { |
421 mb->mbxCommand = MBX_READ_LA64; 422 423 return (1); 424 } | 430 mb->mbxCommand = MBX_READ_LA64; 431 432 return (1); 433 } |
434 |
|
425 mb->mbxCommand = MBX_READ_LA64; 426 mb->un.varReadLA.un.lilpBde64.tus.f.bdeSize = 128; | 435 mb->mbxCommand = MBX_READ_LA64; 436 mb->un.varReadLA.un.lilpBde64.tus.f.bdeSize = 128; |
427 mb->un.varReadLA.un.lilpBde64.addrHigh = 428 (uint32_t)putPaddrHigh(mp->phys); 429 mb->un.varReadLA.un.lilpBde64.addrLow = 430 (uint32_t)putPaddrLow(mp->phys); | 437 mb->un.varReadLA.un.lilpBde64.addrHigh = putPaddrHigh(mp->phys); 438 mb->un.varReadLA.un.lilpBde64.addrLow = putPaddrLow(mp->phys); |
431 mb->mbxOwner = OWN_HOST; 432 433 /* 434 * save address for completion 435 */ 436 ((MAILBOXQ *)mb)->bp = (uint8_t *)mp; 437 438 return (0); 439 440} /* emlxs_mb_read_la() */ 441 442 443/* | 439 mb->mbxOwner = OWN_HOST; 440 441 /* 442 * save address for completion 443 */ 444 ((MAILBOXQ *)mb)->bp = (uint8_t *)mp; 445 446 return (0); 447 448} /* emlxs_mb_read_la() */ 449 450 451/* |
444 * emlxs_mb_clear_la Issue a CLEAR LA 445 * mailbox command | 452 * emlxs_mb_clear_la Issue a CLEAR LA mailbox command |
446 */ 447extern void 448emlxs_mb_clear_la(emlxs_hba_t *hba, MAILBOX *mb) 449{ 450#ifdef FC_RPI_CHECK 451 emlxs_rpi_check(hba); 452#endif /* FC_RPI_CHECK */ 453 | 453 */ 454extern void 455emlxs_mb_clear_la(emlxs_hba_t *hba, MAILBOX *mb) 456{ 457#ifdef FC_RPI_CHECK 458 emlxs_rpi_check(hba); 459#endif /* FC_RPI_CHECK */ 460 |
454 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 461 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
455 456 mb->un.varClearLA.eventTag = hba->link_event_tag; 457 mb->mbxCommand = MBX_CLEAR_LA; 458 mb->mbxOwner = OWN_HOST; 459 460 return; 461 462} /* End emlxs_mb_clear_la */ 463 464 465/* | 462 463 mb->un.varClearLA.eventTag = hba->link_event_tag; 464 mb->mbxCommand = MBX_CLEAR_LA; 465 mb->mbxOwner = OWN_HOST; 466 467 return; 468 469} /* End emlxs_mb_clear_la */ 470 471 472/* |
466 * emlxs_mb_read_status Issue a READ STATUS 467 * mailbox command | 473 * emlxs_mb_read_status Issue a READ STATUS mailbox command |
468 */ | 474 */ |
469/* ARGSUSED */ | 475/*ARGSUSED*/ |
470extern void 471emlxs_mb_read_status(emlxs_hba_t *hba, MAILBOX *mb) 472{ | 476extern void 477emlxs_mb_read_status(emlxs_hba_t *hba, MAILBOX *mb) 478{ |
473 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 479 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
474 475 mb->mbxCommand = MBX_READ_STATUS; 476 mb->mbxOwner = OWN_HOST; | 480 481 mb->mbxCommand = MBX_READ_STATUS; 482 mb->mbxOwner = OWN_HOST; |
477 | |
478} /* End fc_read_status */ 479 | 483} /* End fc_read_status */ 484 |
480 | |
481/* | 485/* |
482 * emlxs_mb_read_lnk_stat Issue a LINK STATUS 483 * mailbox command | 486 * emlxs_mb_read_lnk_stat Issue a LINK STATUS mailbox command |
484 */ | 487 */ |
485/* ARGSUSED */ | 488/*ARGSUSED*/ |
486extern void 487emlxs_mb_read_lnk_stat(emlxs_hba_t *hba, MAILBOX *mb) 488{ | 489extern void 490emlxs_mb_read_lnk_stat(emlxs_hba_t *hba, MAILBOX *mb) 491{ |
489 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 492 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
490 491 mb->mbxCommand = MBX_READ_LNK_STAT; 492 mb->mbxOwner = OWN_HOST; | 493 494 mb->mbxCommand = MBX_READ_LNK_STAT; 495 mb->mbxOwner = OWN_HOST; |
493 | |
494} /* End emlxs_mb_read_lnk_stat */ 495 496 497/* | 496} /* End emlxs_mb_read_lnk_stat */ 497 498 499/* |
498 * emlxs_mb_write_nv Issue a WRITE NVPARAM 499 * mailbox command | 500 * emlxs_mb_write_nv Issue a WRITE NVPARAM mailbox command |
500 */ 501static void 502emlxs_emb_mb_write_nv(emlxs_hba_t *hba, MAILBOX *mb) 503{ | 501 */ 502static void 503emlxs_emb_mb_write_nv(emlxs_hba_t *hba, MAILBOX *mb) 504{ |
504 int32_t i; 505 emlxs_config_t *cfg = &CFG; | 505 int32_t i; 506 emlxs_config_t *cfg = &CFG; |
506 | 507 |
507 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 508 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
508 | 509 |
509 bcopy((void *) &hba->wwnn, 510 (void *) mb->un.varWTnvp.nodename, 511 sizeof (NAME_TYPE)); | 510 bcopy((void *)&hba->wwnn, 511 (void *)mb->un.varWTnvp.nodename, sizeof (NAME_TYPE)); |
512 | 512 |
513 bcopy((void *) &hba->wwpn, 514 (void *) mb->un.varWTnvp.portname, 515 sizeof (NAME_TYPE)); | 513 bcopy((void *)&hba->wwpn, 514 (void *)mb->un.varWTnvp.portname, sizeof (NAME_TYPE)); |
516 517 mb->un.varWTnvp.pref_DID = 0; 518 mb->un.varWTnvp.hardAL_PA = (uint8_t)cfg[CFG_ASSIGN_ALPA].current; 519 mb->un.varWTnvp.rsvd1[0] = 0xffffffff; 520 mb->un.varWTnvp.rsvd1[1] = 0xffffffff; 521 mb->un.varWTnvp.rsvd1[2] = 0xffffffff; 522 for (i = 0; i < 21; i++) { 523 mb->un.varWTnvp.rsvd3[i] = 0xffffffff; 524 } 525 526 mb->mbxCommand = MBX_WRITE_NV; 527 mb->mbxOwner = OWN_HOST; 528} /* End emlxs_mb_write_nv */ 529 530 531/* | 515 516 mb->un.varWTnvp.pref_DID = 0; 517 mb->un.varWTnvp.hardAL_PA = (uint8_t)cfg[CFG_ASSIGN_ALPA].current; 518 mb->un.varWTnvp.rsvd1[0] = 0xffffffff; 519 mb->un.varWTnvp.rsvd1[1] = 0xffffffff; 520 mb->un.varWTnvp.rsvd1[2] = 0xffffffff; 521 for (i = 0; i < 21; i++) { 522 mb->un.varWTnvp.rsvd3[i] = 0xffffffff; 523 } 524 525 mb->mbxCommand = MBX_WRITE_NV; 526 mb->mbxOwner = OWN_HOST; 527} /* End emlxs_mb_write_nv */ 528 529 530/* |
532 * emlxs_mb_part_slim Issue a PARTITION SLIM 533 * mailbox command | 531 * emlxs_mb_part_slim Issue a PARTITION SLIM mailbox command |
534 */ 535static void 536emlxs_mb_part_slim(emlxs_hba_t *hba, MAILBOX *mb, uint32_t hbainit) 537{ | 532 */ 533static void 534emlxs_mb_part_slim(emlxs_hba_t *hba, MAILBOX *mb, uint32_t hbainit) 535{ |
538 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 536 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
539 540 541 mb->un.varSlim.numRing = hba->ring_count; 542 mb->un.varSlim.hbainit = hbainit; 543 mb->mbxCommand = MBX_PART_SLIM; 544 mb->mbxOwner = OWN_HOST; | 537 538 539 mb->un.varSlim.numRing = hba->ring_count; 540 mb->un.varSlim.hbainit = hbainit; 541 mb->mbxCommand = MBX_PART_SLIM; 542 mb->mbxOwner = OWN_HOST; |
545 | |
546} /* End emlxs_mb_part_slim */ 547 548 549/* | 543} /* End emlxs_mb_part_slim */ 544 545 546/* |
550 * emlxs_mb_config_ring Issue a CONFIG RING 551 * mailbox command | 547 * emlxs_mb_config_ring Issue a CONFIG RING mailbox command |
552 */ 553extern void 554emlxs_mb_config_ring(emlxs_hba_t *hba, int32_t ring, MAILBOX *mb) 555{ 556 int32_t i; 557 int32_t j; 558 | 548 */ 549extern void 550emlxs_mb_config_ring(emlxs_hba_t *hba, int32_t ring, MAILBOX *mb) 551{ 552 int32_t i; 553 int32_t j; 554 |
559 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 555 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
560 561 j = 0; 562 for (i = 0; i < ring; i++) { 563 j += hba->ring_masks[i]; 564 } 565 566 for (i = 0; i < hba->ring_masks[ring]; i++) { 567 if ((j + i) >= 6) { 568 break; 569 } | 556 557 j = 0; 558 for (i = 0; i < ring; i++) { 559 j += hba->ring_masks[i]; 560 } 561 562 for (i = 0; i < hba->ring_masks[ring]; i++) { 563 if ((j + i) >= 6) { 564 break; 565 } |
570 mb->un.varCfgRing.rrRegs[i].rval = hba->ring_rval[j + i]; | 566 567 mb->un.varCfgRing.rrRegs[i].rval = hba->ring_rval[j + i]; |
571 mb->un.varCfgRing.rrRegs[i].rmask = hba->ring_rmask[j + i]; 572 | 568 mb->un.varCfgRing.rrRegs[i].rmask = hba->ring_rmask[j + i]; 569 |
573 mb->un.varCfgRing.rrRegs[i].tval = hba->ring_tval[j + i]; | 570 mb->un.varCfgRing.rrRegs[i].tval = hba->ring_tval[j + i]; |
574 mb->un.varCfgRing.rrRegs[i].tmask = hba->ring_tmask[j + i]; 575 } 576 577 mb->un.varCfgRing.ring = ring; 578 mb->un.varCfgRing.profile = 0; 579 mb->un.varCfgRing.maxOrigXchg = 0; 580 mb->un.varCfgRing.maxRespXchg = 0; 581 mb->un.varCfgRing.recvNotify = 1; 582 mb->un.varCfgRing.numMask = hba->ring_masks[ring]; 583 mb->mbxCommand = MBX_CONFIG_RING; 584 mb->mbxOwner = OWN_HOST; 585 586 return; 587 588} /* End emlxs_mb_config_ring */ 589 590 591/* | 571 mb->un.varCfgRing.rrRegs[i].tmask = hba->ring_tmask[j + i]; 572 } 573 574 mb->un.varCfgRing.ring = ring; 575 mb->un.varCfgRing.profile = 0; 576 mb->un.varCfgRing.maxOrigXchg = 0; 577 mb->un.varCfgRing.maxRespXchg = 0; 578 mb->un.varCfgRing.recvNotify = 1; 579 mb->un.varCfgRing.numMask = hba->ring_masks[ring]; 580 mb->mbxCommand = MBX_CONFIG_RING; 581 mb->mbxOwner = OWN_HOST; 582 583 return; 584 585} /* End emlxs_mb_config_ring */ 586 587 588/* |
592 * emlxs_mb_config_link Issue a CONFIG LINK 593 * mailbox command | 589 * emlxs_mb_config_link Issue a CONFIG LINK mailbox command |
594 */ 595extern void 596emlxs_mb_config_link(emlxs_hba_t *hba, MAILBOX *mb) 597{ | 590 */ 591extern void 592emlxs_mb_config_link(emlxs_hba_t *hba, MAILBOX *mb) 593{ |
598 emlxs_port_t *port = &PPORT; | 594 emlxs_port_t *port = &PPORT; |
599 emlxs_config_t *cfg = &CFG; 600 | 595 emlxs_config_t *cfg = &CFG; 596 |
601 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 597 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
602 603 /* 604 * NEW_FEATURE SLI-2, Coalescing Response Feature. 605 */ 606 if (cfg[CFG_CR_DELAY].current) { 607 mb->un.varCfgLnk.cr = 1; 608 mb->un.varCfgLnk.ci = 1; 609 mb->un.varCfgLnk.cr_delay = cfg[CFG_CR_DELAY].current; 610 mb->un.varCfgLnk.cr_count = cfg[CFG_CR_COUNT].current; 611 } | 598 599 /* 600 * NEW_FEATURE SLI-2, Coalescing Response Feature. 601 */ 602 if (cfg[CFG_CR_DELAY].current) { 603 mb->un.varCfgLnk.cr = 1; 604 mb->un.varCfgLnk.ci = 1; 605 mb->un.varCfgLnk.cr_delay = cfg[CFG_CR_DELAY].current; 606 mb->un.varCfgLnk.cr_count = cfg[CFG_CR_COUNT].current; 607 } |
608 |
|
612 if (cfg[CFG_ACK0].current) 613 mb->un.varCfgLnk.ack0_enable = 1; 614 615 mb->un.varCfgLnk.myId = port->did; 616 mb->un.varCfgLnk.edtov = hba->fc_edtov; 617 mb->un.varCfgLnk.arbtov = hba->fc_arbtov; 618 mb->un.varCfgLnk.ratov = hba->fc_ratov; 619 mb->un.varCfgLnk.rttov = hba->fc_rttov; --- 4 unchanged lines hidden (view full) --- 624 mb->mbxOwner = OWN_HOST; 625 626 return; 627 628} /* emlxs_mb_config_link() */ 629 630 631/* | 609 if (cfg[CFG_ACK0].current) 610 mb->un.varCfgLnk.ack0_enable = 1; 611 612 mb->un.varCfgLnk.myId = port->did; 613 mb->un.varCfgLnk.edtov = hba->fc_edtov; 614 mb->un.varCfgLnk.arbtov = hba->fc_arbtov; 615 mb->un.varCfgLnk.ratov = hba->fc_ratov; 616 mb->un.varCfgLnk.rttov = hba->fc_rttov; --- 4 unchanged lines hidden (view full) --- 621 mb->mbxOwner = OWN_HOST; 622 623 return; 624 625} /* emlxs_mb_config_link() */ 626 627 628/* |
632 * emlxs_mb_init_link Issue an INIT LINK 633 * mailbox command | 629 * emlxs_mb_init_link Issue an INIT LINK mailbox command |
634 */ 635extern void 636emlxs_mb_init_link(emlxs_hba_t *hba, MAILBOX *mb, uint32_t topology, 637 uint32_t linkspeed) 638{ | 630 */ 631extern void 632emlxs_mb_init_link(emlxs_hba_t *hba, MAILBOX *mb, uint32_t topology, 633 uint32_t linkspeed) 634{ |
639 emlxs_vpd_t *vpd = &VPD; 640 emlxs_config_t *cfg = &CFG; | 635 emlxs_vpd_t *vpd = &VPD; 636 emlxs_config_t *cfg = &CFG; |
641 | 637 |
642 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 638 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
643 644 switch (topology) { 645 case FLAGS_LOCAL_LB: 646 mb->un.varInitLnk.link_flags = FLAGS_TOPOLOGY_MODE_LOOP; 647 mb->un.varInitLnk.link_flags |= FLAGS_LOCAL_LB; 648 break; 649 case FLAGS_TOPOLOGY_MODE_LOOP_PT: 650 mb->un.varInitLnk.link_flags = FLAGS_TOPOLOGY_MODE_LOOP; --- 10 unchanged lines hidden (view full) --- 661 mb->un.varInitLnk.link_flags |= FLAGS_TOPOLOGY_FAILOVER; 662 break; 663 } 664 665 if (cfg[CFG_LILP_ENABLE].current == 0) { 666 /* Disable LIRP/LILP support */ 667 mb->un.varInitLnk.link_flags |= FLAGS_LIRP_LILP; 668 } | 639 640 switch (topology) { 641 case FLAGS_LOCAL_LB: 642 mb->un.varInitLnk.link_flags = FLAGS_TOPOLOGY_MODE_LOOP; 643 mb->un.varInitLnk.link_flags |= FLAGS_LOCAL_LB; 644 break; 645 case FLAGS_TOPOLOGY_MODE_LOOP_PT: 646 mb->un.varInitLnk.link_flags = FLAGS_TOPOLOGY_MODE_LOOP; --- 10 unchanged lines hidden (view full) --- 657 mb->un.varInitLnk.link_flags |= FLAGS_TOPOLOGY_FAILOVER; 658 break; 659 } 660 661 if (cfg[CFG_LILP_ENABLE].current == 0) { 662 /* Disable LIRP/LILP support */ 663 mb->un.varInitLnk.link_flags |= FLAGS_LIRP_LILP; 664 } |
665 |
|
669 /* 670 * Setting up the link speed 671 */ 672 switch (linkspeed) { 673 case 0: 674 break; 675 676 case 1: --- 31 unchanged lines hidden (view full) --- 708 break; 709 710 } 711 712 if ((linkspeed > 0) && (vpd->feaLevelHigh >= 0x02)) { 713 mb->un.varInitLnk.link_flags |= FLAGS_LINK_SPEED; 714 mb->un.varInitLnk.link_speed = linkspeed; 715 } | 666 /* 667 * Setting up the link speed 668 */ 669 switch (linkspeed) { 670 case 0: 671 break; 672 673 case 1: --- 31 unchanged lines hidden (view full) --- 705 break; 706 707 } 708 709 if ((linkspeed > 0) && (vpd->feaLevelHigh >= 0x02)) { 710 mb->un.varInitLnk.link_flags |= FLAGS_LINK_SPEED; 711 mb->un.varInitLnk.link_speed = linkspeed; 712 } |
713 |
|
716 mb->un.varInitLnk.link_flags |= FLAGS_PREABORT_RETURN; 717 | 714 mb->un.varInitLnk.link_flags |= FLAGS_PREABORT_RETURN; 715 |
718 mb->un.varInitLnk.fabric_AL_PA = (uint8_t)cfg[CFG_ASSIGN_ALPA].current; | 716 mb->un.varInitLnk.fabric_AL_PA = 717 (uint8_t)cfg[CFG_ASSIGN_ALPA].current; |
719 mb->mbxCommand = (volatile uint8_t) MBX_INIT_LINK; 720 mb->mbxOwner = OWN_HOST; 721 722 723 return; 724 725} /* emlxs_mb_init_link() */ 726 727 728/* | 718 mb->mbxCommand = (volatile uint8_t) MBX_INIT_LINK; 719 mb->mbxOwner = OWN_HOST; 720 721 722 return; 723 724} /* emlxs_mb_init_link() */ 725 726 727/* |
729 * emlxs_mb_down_link Issue a DOWN LINK 730 * mailbox command | 728 * emlxs_mb_down_link Issue a DOWN LINK mailbox command |
731 */ | 729 */ |
732/* ARGSUSED */ | 730/*ARGSUSED*/ |
733extern void 734emlxs_mb_down_link(emlxs_hba_t *hba, MAILBOX *mb) 735{ | 731extern void 732emlxs_mb_down_link(emlxs_hba_t *hba, MAILBOX *mb) 733{ |
736 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 734 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
737 738 mb->mbxCommand = MBX_DOWN_LINK; 739 mb->mbxOwner = OWN_HOST; 740 741 return; 742 743} /* emlxs_mb_down_link() */ 744 745 746/* | 735 736 mb->mbxCommand = MBX_DOWN_LINK; 737 mb->mbxOwner = OWN_HOST; 738 739 return; 740 741} /* emlxs_mb_down_link() */ 742 743 744/* |
747 * emlxs_mb_read_sparam Issue a READ SPARAM 748 * mailbox command | 745 * emlxs_mb_read_sparam Issue a READ SPARAM mailbox command |
749 */ 750extern uint32_t 751emlxs_mb_read_sparam(emlxs_hba_t *hba, MAILBOX *mb) 752{ 753 MATCHMAP *mp; 754 | 746 */ 747extern uint32_t 748emlxs_mb_read_sparam(emlxs_hba_t *hba, MAILBOX *mb) 749{ 750 MATCHMAP *mp; 751 |
755 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 752 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
756 | 753 |
757 if ((mp = (MATCHMAP *) emlxs_mem_get(hba, MEM_BUF)) == 0) { | 754 if ((mp = (MATCHMAP *)emlxs_mem_get(hba, MEM_BUF)) == 0) { |
758 mb->mbxCommand = MBX_READ_SPARM64; 759 760 return (1); 761 } | 755 mb->mbxCommand = MBX_READ_SPARM64; 756 757 return (1); 758 } |
759 |
|
762 mb->un.varRdSparm.un.sp64.tus.f.bdeSize = sizeof (SERV_PARM); | 760 mb->un.varRdSparm.un.sp64.tus.f.bdeSize = sizeof (SERV_PARM); |
763 mb->un.varRdSparm.un.sp64.addrHigh = (uint32_t)putPaddrHigh(mp->phys); 764 mb->un.varRdSparm.un.sp64.addrLow = (uint32_t)putPaddrLow(mp->phys); | 761 mb->un.varRdSparm.un.sp64.addrHigh = putPaddrHigh(mp->phys); 762 mb->un.varRdSparm.un.sp64.addrLow = putPaddrLow(mp->phys); |
765 mb->mbxCommand = MBX_READ_SPARM64; 766 mb->mbxOwner = OWN_HOST; 767 768 /* 769 * save address for completion 770 */ 771 ((MAILBOXQ *)mb)->bp = (uint8_t *)mp; 772 773 return (0); 774 775} /* emlxs_mb_read_sparam() */ 776 777 778/* | 763 mb->mbxCommand = MBX_READ_SPARM64; 764 mb->mbxOwner = OWN_HOST; 765 766 /* 767 * save address for completion 768 */ 769 ((MAILBOXQ *)mb)->bp = (uint8_t *)mp; 770 771 return (0); 772 773} /* emlxs_mb_read_sparam() */ 774 775 776/* |
779 * emlxs_mb_read_rpi Issue a READ RPI 780 * mailbox command | 777 * emlxs_mb_read_rpi Issue a READ RPI mailbox command |
781 */ | 778 */ |
782/* ARGSUSED */ | 779/*ARGSUSED*/ |
783extern uint32_t | 780extern uint32_t |
784emlxs_mb_read_rpi(emlxs_hba_t *hba, uint32_t rpi, MAILBOX *mb, uint32_t flag) | 781emlxs_mb_read_rpi(emlxs_hba_t *hba, uint32_t rpi, MAILBOX *mb, 782 uint32_t flag) |
785{ | 783{ |
786 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 784 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
787 788 /* 789 * Set flag to issue action on cmpl 790 */ 791 mb->un.varWords[30] = flag; 792 mb->un.varRdRPI.reqRpi = (volatile uint16_t) rpi; 793 mb->mbxCommand = MBX_READ_RPI64; 794 mb->mbxOwner = OWN_HOST; 795 796 return (0); | 785 786 /* 787 * Set flag to issue action on cmpl 788 */ 789 mb->un.varWords[30] = flag; 790 mb->un.varRdRPI.reqRpi = (volatile uint16_t) rpi; 791 mb->mbxCommand = MBX_READ_RPI64; 792 mb->mbxOwner = OWN_HOST; 793 794 return (0); |
797 | |
798} /* End emlxs_mb_read_rpi */ 799 800 801/* | 795} /* End emlxs_mb_read_rpi */ 796 797 798/* |
802 * emlxs_mb_read_xri Issue a READ XRI 803 * mailbox command | 799 * emlxs_mb_read_xri Issue a READ XRI mailbox command |
804 */ | 800 */ |
805/* ARGSUSED */ | 801/*ARGSUSED*/ |
806extern uint32_t | 802extern uint32_t |
807emlxs_mb_read_xri(emlxs_hba_t *hba, uint32_t xri, MAILBOX *mb, uint32_t flag) | 803emlxs_mb_read_xri(emlxs_hba_t *hba, uint32_t xri, MAILBOX *mb, 804 uint32_t flag) |
808{ | 805{ |
809 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 806 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
810 811 /* 812 * Set flag to issue action on cmpl 813 */ 814 mb->un.varWords[30] = flag; | 807 808 /* 809 * Set flag to issue action on cmpl 810 */ 811 mb->un.varWords[30] = flag; |
815 mb->un.varRdXRI.reqXri = (volatile uint16_t) xri; | 812 mb->un.varRdXRI.reqXri = (volatile uint16_t)xri; |
816 mb->mbxCommand = MBX_READ_XRI; 817 mb->mbxOwner = OWN_HOST; 818 819 return (0); | 813 mb->mbxCommand = MBX_READ_XRI; 814 mb->mbxOwner = OWN_HOST; 815 816 return (0); |
820 | |
821} /* End emlxs_mb_read_xri */ 822 823 | 817} /* End emlxs_mb_read_xri */ 818 819 |
824/* ARGSUSED */ | 820/*ARGSUSED*/ |
825extern int32_t 826emlxs_mb_check_sparm(emlxs_hba_t *hba, SERV_PARM *nsp) 827{ 828 uint32_t nsp_value; 829 uint32_t *iptr; 830 831 if (nsp->cmn.fPort) { 832 return (0); 833 } | 821extern int32_t 822emlxs_mb_check_sparm(emlxs_hba_t *hba, SERV_PARM *nsp) 823{ 824 uint32_t nsp_value; 825 uint32_t *iptr; 826 827 if (nsp->cmn.fPort) { 828 return (0); 829 } |
830 |
|
834 /* Validate the service parameters */ | 831 /* Validate the service parameters */ |
835 iptr = (uint32_t *)& nsp->portName; | 832 iptr = (uint32_t *)&nsp->portName; |
836 if (iptr[0] == 0 && iptr[1] == 0) { 837 return (1); 838 } | 833 if (iptr[0] == 0 && iptr[1] == 0) { 834 return (1); 835 } |
839 iptr = (uint32_t *)& nsp->nodeName; | 836 837 iptr = (uint32_t *)&nsp->nodeName; |
840 if (iptr[0] == 0 && iptr[1] == 0) { 841 return (2); 842 } | 838 if (iptr[0] == 0 && iptr[1] == 0) { 839 return (2); 840 } |
841 |
|
843 if (nsp->cls2.classValid) { | 842 if (nsp->cls2.classValid) { |
844 nsp_value = ((nsp->cls2.rcvDataSizeMsb & 0x0f) << 8) | 845 nsp->cls2.rcvDataSizeLsb; | 843 nsp_value = 844 ((nsp->cls2.rcvDataSizeMsb & 0x0f) << 8) | nsp->cls2. 845 rcvDataSizeLsb; |
846 | 846 |
847 /* 848 * If the receive data length is zero then set it to the CSP 849 * value 850 */ | 847 /* If the receive data length is zero then set it to */ 848 /* the CSP value */ |
851 if (!nsp_value) { 852 nsp->cls2.rcvDataSizeMsb = nsp->cmn.bbRcvSizeMsb; 853 nsp->cls2.rcvDataSizeLsb = nsp->cmn.bbRcvSizeLsb; 854 return (0); 855 } 856 } | 849 if (!nsp_value) { 850 nsp->cls2.rcvDataSizeMsb = nsp->cmn.bbRcvSizeMsb; 851 nsp->cls2.rcvDataSizeLsb = nsp->cmn.bbRcvSizeLsb; 852 return (0); 853 } 854 } |
855 |
|
857 if (nsp->cls3.classValid) { | 856 if (nsp->cls3.classValid) { |
858 nsp_value = ((nsp->cls3.rcvDataSizeMsb & 0x0f) << 8) | 859 nsp->cls3.rcvDataSizeLsb; | 857 nsp_value = 858 ((nsp->cls3.rcvDataSizeMsb & 0x0f) << 8) | nsp->cls3. 859 rcvDataSizeLsb; |
860 | 860 |
861 /* 862 * If the receive data length is zero then set it to the CSP 863 * value 864 */ 865 /* This prevents a Emulex adapter bug from occurring */ | 861 /* If the receive data length is zero then set it to */ 862 /* the CSP value */ |
866 if (!nsp_value) { 867 nsp->cls3.rcvDataSizeMsb = nsp->cmn.bbRcvSizeMsb; 868 nsp->cls3.rcvDataSizeLsb = nsp->cmn.bbRcvSizeLsb; 869 return (0); 870 } 871 } | 863 if (!nsp_value) { 864 nsp->cls3.rcvDataSizeMsb = nsp->cmn.bbRcvSizeMsb; 865 nsp->cls3.rcvDataSizeLsb = nsp->cmn.bbRcvSizeLsb; 866 return (0); 867 } 868 } |
869 |
|
872 return (0); 873 874} /* emlxs_mb_check_sparm() */ 875 876 877/* | 870 return (0); 871 872} /* emlxs_mb_check_sparm() */ 873 874 875/* |
878 * emlxs_mb_reg_did Issue a REG_LOGIN 879 * mailbox command | 876 * emlxs_mb_reg_did Issue a REG_LOGIN mailbox command |
880 */ 881extern uint32_t 882emlxs_mb_reg_did(emlxs_port_t *port, uint32_t did, SERV_PARM *param, 883 emlxs_buf_t *sbp, fc_unsol_buf_t *ubp, IOCBQ *iocbq) 884{ | 877 */ 878extern uint32_t 879emlxs_mb_reg_did(emlxs_port_t *port, uint32_t did, SERV_PARM *param, 880 emlxs_buf_t *sbp, fc_unsol_buf_t *ubp, IOCBQ *iocbq) 881{ |
885 emlxs_hba_t *hba = HBA; 886 MATCHMAP *mp; 887 MAILBOXQ *mbq; 888 MAILBOX *mb; 889 uint32_t rval; | 882 emlxs_hba_t *hba = HBA; 883 MATCHMAP *mp; 884 MAILBOXQ *mbq; 885 MAILBOX *mb; 886 uint32_t rval; |
890 891 /* Check for invalid node ids to register */ | 887 888 /* Check for invalid node ids to register */ |
892 if (did == 0 || (did & 0xff000000)) { | 889 if ((did == 0) && (!(hba->flag & FC_LOOPBACK_MODE))) { |
893 return (1); 894 } | 890 return (1); 891 } |
892 893 if (did & 0xff000000) { 894 return (1); 895 } 896 |
|
895 if ((rval = emlxs_mb_check_sparm(hba, param))) { 896 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_node_create_failed_msg, | 897 if ((rval = emlxs_mb_check_sparm(hba, param))) { 898 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_node_create_failed_msg, |
897 "Invalid service parameters. did=%06x rval=%d", did, rval); | 899 "Invalid service parameters. did=%06x rval=%d", did, 900 rval); |
898 899 return (1); 900 } | 901 902 return (1); 903 } |
904 |
|
901 /* Check if the node limit has been reached */ 902 if (port->node_count >= hba->max_nodes) { 903 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_node_create_failed_msg, | 905 /* Check if the node limit has been reached */ 906 if (port->node_count >= hba->max_nodes) { 907 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_node_create_failed_msg, |
904 "Limit reached. did=%06x count=%d", did, port->node_count); | 908 "Limit reached. did=%06x count=%d", did, 909 port->node_count); |
905 906 return (1); 907 } | 910 911 return (1); 912 } |
908 if (!(mbq = (MAILBOXQ *) emlxs_mem_get(hba, MEM_MBOX | MEM_PRI))) { | 913 914 if (!(mbq = (MAILBOXQ *)emlxs_mem_get(hba, MEM_MBOX | MEM_PRI))) { |
909 return (1); 910 } | 915 return (1); 916 } |
917 |
|
911 /* Build login request */ | 918 /* Build login request */ |
912 if ((mp = (MATCHMAP *) emlxs_mem_get(hba, MEM_BUF | MEM_PRI)) == 0) { | 919 if ((mp = (MATCHMAP *)emlxs_mem_get(hba, MEM_BUF | MEM_PRI)) == 0) { |
913 (void) emlxs_mem_put(hba, MEM_MBOX, (uint8_t *)mbq); 914 return (1); 915 } | 920 (void) emlxs_mem_put(hba, MEM_MBOX, (uint8_t *)mbq); 921 return (1); 922 } |
916 bcopy((void *) param, (void *) mp->virt, sizeof (SERV_PARM)); | |
917 | 923 |
918 mb = (MAILBOX *) mbq->mbox; | 924 bcopy((void *)param, (void *)mp->virt, sizeof (SERV_PARM)); 925 926 mb = (MAILBOX *)mbq->mbox; |
919 mb->un.varRegLogin.un.sp64.tus.f.bdeSize = sizeof (SERV_PARM); | 927 mb->un.varRegLogin.un.sp64.tus.f.bdeSize = sizeof (SERV_PARM); |
920 mb->un.varRegLogin.un.sp64.addrHigh = (uint32_t)putPaddrHigh(mp->phys); 921 mb->un.varRegLogin.un.sp64.addrLow = (uint32_t)putPaddrLow(mp->phys); | 928 mb->un.varRegLogin.un.sp64.addrHigh = putPaddrHigh(mp->phys); 929 mb->un.varRegLogin.un.sp64.addrLow = putPaddrLow(mp->phys); |
922 mb->un.varRegLogin.rpi = 0; 923 mb->un.varRegLogin.did = did; 924 mb->un.varWords[30] = 0; /* flags */ 925 mb->mbxCommand = MBX_REG_LOGIN64; 926 mb->mbxOwner = OWN_HOST; 927 928#ifdef SLI3_SUPPORT | 930 mb->un.varRegLogin.rpi = 0; 931 mb->un.varRegLogin.did = did; 932 mb->un.varWords[30] = 0; /* flags */ 933 mb->mbxCommand = MBX_REG_LOGIN64; 934 mb->mbxOwner = OWN_HOST; 935 936#ifdef SLI3_SUPPORT |
929 mb->un.varRegLogin.vpi = 930 port->vpi; | 937 mb->un.varRegLogin.vpi = port->vpi; |
931#endif /* SLI3_SUPPORT */ 932 933 mbq->sbp = (uint8_t *)sbp; 934 mbq->ubp = (uint8_t *)ubp; 935 mbq->iocbq = (uint8_t *)iocbq; 936 mbq->bp = (uint8_t *)mp; 937 | 938#endif /* SLI3_SUPPORT */ 939 940 mbq->sbp = (uint8_t *)sbp; 941 mbq->ubp = (uint8_t *)ubp; 942 mbq->iocbq = (uint8_t *)iocbq; 943 mbq->bp = (uint8_t *)mp; 944 |
938 if (emlxs_mb_issue_cmd(hba, mb, MBX_NOWAIT, 0) != MBX_BUSY) { | 945 if (emlxs_sli_issue_mbox_cmd(hba, mb, MBX_NOWAIT, 0) != MBX_BUSY) { |
939 (void) emlxs_mem_put(hba, MEM_MBOX, (uint8_t *)mbq); 940 } | 946 (void) emlxs_mem_put(hba, MEM_MBOX, (uint8_t *)mbq); 947 } |
948 |
|
941 return (0); 942 943} /* emlxs_mb_reg_did() */ 944 945/* | 949 return (0); 950 951} /* emlxs_mb_reg_did() */ 952 953/* |
946 * emlxs_mb_unreg_rpi Issue a UNREG_LOGIN 947 * mailbox command | 954 * emlxs_mb_unreg_rpi Issue a UNREG_LOGIN mailbox command |
948 */ 949extern uint32_t 950emlxs_mb_unreg_rpi(emlxs_port_t *port, uint32_t rpi, emlxs_buf_t *sbp, 951 fc_unsol_buf_t *ubp, IOCBQ *iocbq) 952{ | 955 */ 956extern uint32_t 957emlxs_mb_unreg_rpi(emlxs_port_t *port, uint32_t rpi, emlxs_buf_t *sbp, 958 fc_unsol_buf_t *ubp, IOCBQ *iocbq) 959{ |
953 emlxs_hba_t *hba = HBA; 954 MAILBOXQ *mbq; 955 MAILBOX *mb; 956 NODELIST *ndlp; | 960 emlxs_hba_t *hba = HBA; 961 MAILBOXQ *mbq; 962 MAILBOX *mb; 963 NODELIST *ndlp; |
957 958 if (rpi != 0xffff) { 959 /* Make sure the node does already exist */ 960 ndlp = emlxs_node_find_rpi(port, rpi); 961 962 963 if (ndlp) { 964 /* | 964 965 if (rpi != 0xffff) { 966 /* Make sure the node does already exist */ 967 ndlp = emlxs_node_find_rpi(port, rpi); 968 969 970 if (ndlp) { 971 /* |
965 * If we just unregistered the host node then clear 966 * the host DID | 972 * If we just unregistered the host node then 973 * clear the host DID |
967 */ 968 if (ndlp->nlp_DID == port->did) { 969 port->did = 0; 970 } | 974 */ 975 if (ndlp->nlp_DID == port->did) { 976 port->did = 0; 977 } |
978 |
|
971 /* remove it */ 972 emlxs_node_rm(port, ndlp); 973 974 } else { 975 return (1); 976 } 977 } else { /* Unreg all */ | 979 /* remove it */ 980 emlxs_node_rm(port, ndlp); 981 982 } else { 983 return (1); 984 } 985 } else { /* Unreg all */ |
986 |
|
978 emlxs_node_destroy_all(port); 979 } 980 | 987 emlxs_node_destroy_all(port); 988 } 989 |
981 if (!(mbq = (MAILBOXQ *) emlxs_mem_get(hba, MEM_MBOX | MEM_PRI))) { | 990 if (!(mbq = (MAILBOXQ *)emlxs_mem_get(hba, MEM_MBOX | MEM_PRI))) { |
982 return (1); 983 } | 991 return (1); 992 } |
984 mb = (MAILBOX *) mbq->mbox; | 993 994 mb = (MAILBOX *)mbq->mbox; |
985 mb->un.varUnregLogin.rpi = (uint16_t)rpi; 986 987#ifdef SLI3_SUPPORT 988 mb->un.varUnregLogin.vpi = port->vpi; | 995 mb->un.varUnregLogin.rpi = (uint16_t)rpi; 996 997#ifdef SLI3_SUPPORT 998 mb->un.varUnregLogin.vpi = port->vpi; |
989#endif /* SLI3_SUPPORT */ | 999#endif /* SLI3_SUPPORT */ |
990 991 mb->mbxCommand = MBX_UNREG_LOGIN; 992 mb->mbxOwner = OWN_HOST; 993 mbq->sbp = (uint8_t *)sbp; 994 mbq->ubp = (uint8_t *)ubp; 995 mbq->iocbq = (uint8_t *)iocbq; 996 | 1000 1001 mb->mbxCommand = MBX_UNREG_LOGIN; 1002 mb->mbxOwner = OWN_HOST; 1003 mbq->sbp = (uint8_t *)sbp; 1004 mbq->ubp = (uint8_t *)ubp; 1005 mbq->iocbq = (uint8_t *)iocbq; 1006 |
997 if (emlxs_mb_issue_cmd(hba, mb, MBX_NOWAIT, 0) != MBX_BUSY) { | 1007 if (emlxs_sli_issue_mbox_cmd(hba, mb, MBX_NOWAIT, 0) != MBX_BUSY) { |
998 (void) emlxs_mem_put(hba, MEM_MBOX, (uint8_t *)mbq); 999 } | 1008 (void) emlxs_mem_put(hba, MEM_MBOX, (uint8_t *)mbq); 1009 } |
1010 |
|
1000 return (0); 1001} /* emlxs_mb_unreg_rpi() */ 1002 1003/* | 1011 return (0); 1012} /* emlxs_mb_unreg_rpi() */ 1013 1014/* |
1004 * emlxs_mb_unreg_did Issue a UNREG_DID 1005 * mailbox command | 1015 * emlxs_mb_unreg_did Issue a UNREG_DID mailbox command |
1006 */ 1007extern uint32_t 1008emlxs_mb_unreg_did(emlxs_port_t *port, uint32_t did, emlxs_buf_t *sbp, 1009 fc_unsol_buf_t *ubp, IOCBQ *iocbq) 1010{ | 1016 */ 1017extern uint32_t 1018emlxs_mb_unreg_did(emlxs_port_t *port, uint32_t did, emlxs_buf_t *sbp, 1019 fc_unsol_buf_t *ubp, IOCBQ *iocbq) 1020{ |
1011 emlxs_hba_t *hba = HBA; 1012 NODELIST *ndlp; 1013 MAILBOXQ *mbq; 1014 MAILBOX *mb; | 1021 emlxs_hba_t *hba = HBA; 1022 NODELIST *ndlp; 1023 MAILBOXQ *mbq; 1024 MAILBOX *mb; |
1015 1016 /* 1017 * Unregister all default RPIs if did == 0xffffffff 1018 */ 1019 if (did != 0xffffffff) { 1020 /* Check for base node */ 1021 if (did == Bcast_DID) { 1022 /* just flush base node */ 1023 (void) emlxs_tx_node_flush(port, &port->node_base, 1024 0, 0, 0); | 1025 1026 /* 1027 * Unregister all default RPIs if did == 0xffffffff 1028 */ 1029 if (did != 0xffffffff) { 1030 /* Check for base node */ 1031 if (did == Bcast_DID) { 1032 /* just flush base node */ 1033 (void) emlxs_tx_node_flush(port, &port->node_base, 1034 0, 0, 0); |
1025 (void) emlxs_chipq_node_flush(port, 0, &port->node_base, 1026 0); | 1035 (void) emlxs_chipq_node_flush(port, 0, 1036 &port->node_base, 0); |
1027 1028 /* Return now */ 1029 return (1); 1030 } | 1037 1038 /* Return now */ 1039 return (1); 1040 } |
1041 1042 |
|
1031 /* 1032 * A zero DID means that we are trying to unreg the host node 1033 * after a link bounce 1034 */ 1035 1036 /* 1037 * If the prev_did == 0 then the adapter has been reset and 1038 * there is no need in unregistering 1039 */ 1040 1041 /* | 1043 /* 1044 * A zero DID means that we are trying to unreg the host node 1045 * after a link bounce 1046 */ 1047 1048 /* 1049 * If the prev_did == 0 then the adapter has been reset and 1050 * there is no need in unregistering 1051 */ 1052 1053 /* |
1042 * If the prev_did != 0 then we can look for the hosts last 1043 * known DID node | 1054 * If the prev_did != 0 then we can look for the hosts 1055 * last known DID node |
1044 */ 1045 1046 if (did == 0) { 1047 if (port->prev_did == 0) { 1048 return (1); 1049 } | 1056 */ 1057 1058 if (did == 0) { 1059 if (port->prev_did == 0) { 1060 return (1); 1061 } |
1062 |
|
1050 did = port->prev_did; 1051 } | 1063 did = port->prev_did; 1064 } |
1065 |
|
1052 /* Make sure the node does already exist */ 1053 ndlp = emlxs_node_find_did(port, did); 1054 1055 1056 if (ndlp) { 1057 /* remove it */ 1058 emlxs_node_rm(port, ndlp); 1059 1060 /* | 1066 /* Make sure the node does already exist */ 1067 ndlp = emlxs_node_find_did(port, did); 1068 1069 1070 if (ndlp) { 1071 /* remove it */ 1072 emlxs_node_rm(port, ndlp); 1073 1074 /* |
1061 * If we just unregistered the host node then clear 1062 * the host DID | 1075 * If we just unregistered the host node then 1076 * clear the host DID |
1063 */ 1064 if (did == port->did) { 1065 port->did = 0; 1066 } | 1077 */ 1078 if (did == port->did) { 1079 port->did = 0; 1080 } |
1081 |
|
1067 } else { 1068 return (1); 1069 } 1070 } | 1082 } else { 1083 return (1); 1084 } 1085 } |
1071 if (!(mbq = (MAILBOXQ *) emlxs_mem_get(hba, MEM_MBOX | MEM_PRI))) { | 1086 1087 if (!(mbq = (MAILBOXQ *)emlxs_mem_get(hba, MEM_MBOX | MEM_PRI))) { |
1072 return (1); 1073 } | 1088 return (1); 1089 } |
1074 mb = (MAILBOX *) mbq->mbox; | 1090 1091 mb = (MAILBOX *)mbq->mbox; |
1075 mb->un.varUnregDID.did = did; 1076 1077#ifdef SLI3_SUPPORT 1078 mb->un.varUnregDID.vpi = port->vpi; 1079#endif /* SLI3_SUPPORT */ 1080 1081 mb->mbxCommand = MBX_UNREG_D_ID; 1082 mb->mbxOwner = OWN_HOST; 1083 mbq->sbp = (uint8_t *)sbp; 1084 mbq->ubp = (uint8_t *)ubp; 1085 mbq->iocbq = (uint8_t *)iocbq; 1086 | 1092 mb->un.varUnregDID.did = did; 1093 1094#ifdef SLI3_SUPPORT 1095 mb->un.varUnregDID.vpi = port->vpi; 1096#endif /* SLI3_SUPPORT */ 1097 1098 mb->mbxCommand = MBX_UNREG_D_ID; 1099 mb->mbxOwner = OWN_HOST; 1100 mbq->sbp = (uint8_t *)sbp; 1101 mbq->ubp = (uint8_t *)ubp; 1102 mbq->iocbq = (uint8_t *)iocbq; 1103 |
1087 if (emlxs_mb_issue_cmd(hba, mb, MBX_NOWAIT, 0) != MBX_BUSY) { | 1104 if (emlxs_sli_issue_mbox_cmd(hba, mb, MBX_NOWAIT, 0) != MBX_BUSY) { |
1088 (void) emlxs_mem_put(hba, MEM_MBOX, (uint8_t *)mbq); 1089 } | 1105 (void) emlxs_mem_put(hba, MEM_MBOX, (uint8_t *)mbq); 1106 } |
1107 |
|
1090 return (0); 1091 1092} /* End emlxs_mb_unreg_did */ 1093 1094 1095/* | 1108 return (0); 1109 1110} /* End emlxs_mb_unreg_did */ 1111 1112 1113/* |
1096 * emlxs_mb_set_mask Issue a SET MASK 1097 * mailbox command | 1114 * emlxs_mb_set_mask Issue a SET MASK mailbox command |
1098 */ | 1115 */ |
1099/* ARGSUSED */ | 1116/*ARGSUSED*/ |
1100static void 1101emlxs_mb_set_mask(emlxs_hba_t *hba, MAILBOX *mb, uint32_t mask, 1102 uint32_t ringno) 1103{ | 1117static void 1118emlxs_mb_set_mask(emlxs_hba_t *hba, MAILBOX *mb, uint32_t mask, 1119 uint32_t ringno) 1120{ |
1104 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 1121 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
1105 1106 mb->un.varWords[0] = 0x11223344; /* set passwd */ 1107 mb->un.varWords[1] = mask; /* set mask */ 1108 mb->un.varWords[2] = ringno; /* set ringno */ 1109 mb->mbxCommand = MBX_SET_MASK; 1110 mb->mbxOwner = OWN_HOST; | 1122 1123 mb->un.varWords[0] = 0x11223344; /* set passwd */ 1124 mb->un.varWords[1] = mask; /* set mask */ 1125 mb->un.varWords[2] = ringno; /* set ringno */ 1126 mb->mbxCommand = MBX_SET_MASK; 1127 mb->mbxOwner = OWN_HOST; |
1111 | |
1112} /* End emlxs_mb_set_mask */ 1113 1114 1115/* | 1128} /* End emlxs_mb_set_mask */ 1129 1130 1131/* |
1116 * emlxs_mb_set_debug Issue a special debug 1117 * mailbox command | 1132 * emlxs_mb_set_debug Issue a special debug mailbox command |
1118 */ | 1133 */ |
1119/* ARGSUSED */ | 1134/*ARGSUSED*/ |
1120static void 1121emlxs_mb_set_debug(emlxs_hba_t *hba, MAILBOX *mb, uint32_t word0, 1122 uint32_t word1, uint32_t word2) 1123{ | 1135static void 1136emlxs_mb_set_debug(emlxs_hba_t *hba, MAILBOX *mb, uint32_t word0, 1137 uint32_t word1, uint32_t word2) 1138{ |
1124 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 1139 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
1125 1126 mb->un.varWords[0] = word0; 1127 mb->un.varWords[1] = word1; 1128 mb->un.varWords[2] = word2; 1129 mb->mbxCommand = MBX_SET_DEBUG; 1130 mb->mbxOwner = OWN_HOST; | 1140 1141 mb->un.varWords[0] = word0; 1142 mb->un.varWords[1] = word1; 1143 mb->un.varWords[2] = word2; 1144 mb->mbxCommand = MBX_SET_DEBUG; 1145 mb->mbxOwner = OWN_HOST; |
1131 | |
1132} /* End emlxs_mb_set_debug */ 1133 1134 1135/* | 1146} /* End emlxs_mb_set_debug */ 1147 1148 1149/* |
1136 * emlxs_mb_set_var Issue a special debug mbox 1137 * command to write slim | 1150 * emlxs_mb_set_var Issue a special debug mbox command to write slim |
1138 */ | 1151 */ |
1139/* ARGSUSED */ | 1152/*ARGSUSED*/ |
1140extern void | 1153extern void |
1141emlxs_mb_set_var(emlxs_hba_t *hba, MAILBOX *mb, uint32_t addr, uint32_t value) | 1154emlxs_mb_set_var(emlxs_hba_t *hba, MAILBOX *mb, uint32_t addr, 1155 uint32_t value) |
1142{ | 1156{ |
1143 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 1157 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
1144 1145 /* addr = 0x090597 is AUTO ABTS disable for ELS commands */ 1146 /* addr = 0x052198 is DELAYED ABTS enable for ELS commands */ 1147 /* addr = 0x100506 is for setting PCI MAX READ value */ 1148 1149 /* 1150 * Always turn on DELAYED ABTS for ELS timeouts 1151 */ 1152 if ((addr == 0x052198) && (value == 0)) { 1153 value = 1; 1154 } | 1158 1159 /* addr = 0x090597 is AUTO ABTS disable for ELS commands */ 1160 /* addr = 0x052198 is DELAYED ABTS enable for ELS commands */ 1161 /* addr = 0x100506 is for setting PCI MAX READ value */ 1162 1163 /* 1164 * Always turn on DELAYED ABTS for ELS timeouts 1165 */ 1166 if ((addr == 0x052198) && (value == 0)) { 1167 value = 1; 1168 } |
1169 |
|
1155 mb->un.varWords[0] = addr; 1156 mb->un.varWords[1] = value; 1157 mb->mbxCommand = MBX_SET_VARIABLE; 1158 mb->mbxOwner = OWN_HOST; | 1170 mb->un.varWords[0] = addr; 1171 mb->un.varWords[1] = value; 1172 mb->mbxCommand = MBX_SET_VARIABLE; 1173 mb->mbxOwner = OWN_HOST; |
1159 | |
1160} /* End emlxs_mb_set_var */ 1161 1162 1163/* 1164 * Disable Traffic Cop 1165 */ | 1174} /* End emlxs_mb_set_var */ 1175 1176 1177/* 1178 * Disable Traffic Cop 1179 */ |
1166/* ARGSUSED */ | 1180/*ARGSUSED*/ |
1167extern void 1168emlxs_disable_tc(emlxs_hba_t *hba, MAILBOX *mb) 1169{ | 1181extern void 1182emlxs_disable_tc(emlxs_hba_t *hba, MAILBOX *mb) 1183{ |
1170 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 1184 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
1171 1172 mb->un.varWords[0] = 0x50797; 1173 mb->un.varWords[1] = 0; 1174 mb->un.varWords[2] = 0xfffffffe; 1175 mb->mbxCommand = MBX_SET_VARIABLE; 1176 mb->mbxOwner = OWN_HOST; 1177 1178} /* End emlxs_disable_tc */ 1179 1180 | 1185 1186 mb->un.varWords[0] = 0x50797; 1187 mb->un.varWords[1] = 0; 1188 mb->un.varWords[2] = 0xfffffffe; 1189 mb->mbxCommand = MBX_SET_VARIABLE; 1190 mb->mbxOwner = OWN_HOST; 1191 1192} /* End emlxs_disable_tc */ 1193 1194 |
1181/* 1182 * emlxs_mb_config_port Issue a CONFIG_PORT 1183 * mailbox command 1184 */ 1185extern uint32_t 1186emlxs_mb_config_port(emlxs_hba_t *hba, MAILBOX *mb, uint32_t sli_mode, 1187 uint32_t hbainit) 1188{ 1189 emlxs_vpd_t *vpd = &VPD; 1190 emlxs_port_t *port = &PPORT; 1191 emlxs_config_t *cfg; 1192 RING *rp; 1193 uint64_t pcb; 1194 uint64_t mbx; 1195 uint64_t hgp; 1196 uint64_t pgp; 1197 uint64_t rgp; 1198 MAILBOX *mbox; 1199 SLIM2 *slim; 1200 SLI2_RDSC *rdsc; 1201 uint64_t offset; 1202 uint32_t Laddr; 1203 uint32_t i; | |
1204 | 1195 |
1205 cfg = &CFG; 1206 bzero((void *) mb, MAILBOX_CMD_BSIZE); 1207 mbox = NULL; 1208 slim = NULL; 1209 1210 mb->mbxCommand = MBX_CONFIG_PORT; 1211 mb->mbxOwner = OWN_HOST; 1212 1213 mb->un.varCfgPort.pcbLen = sizeof (PCB); 1214 | |
1215#ifdef SLI3_SUPPORT | 1196#ifdef SLI3_SUPPORT |
1216 mb->un.varCfgPort.hbainit[0] = hbainit; 1217#else /* SLI3_SUPPORT */ 1218 mb->un.varCfgPort.hbainit = hbainit; 1219#endif /* SLI3_SUPPORT */ 1220 1221 pcb = hba->slim2.phys + (uint64_t)(unsigned long)& (slim->pcb); 1222 mb->un.varCfgPort.pcbLow = (uint32_t)putPaddrLow(pcb); 1223 mb->un.varCfgPort.pcbHigh = (uint32_t)putPaddrHigh(pcb); 1224 1225 /* Set Host pointers in SLIM flag */ 1226 mb->un.varCfgPort.hps = 1; 1227 1228 /* Initialize hba structure for assumed default SLI2 mode */ 1229 /* If config port succeeds, then we will update it then */ 1230 hba->sli_mode = 2; 1231 hba->vpi_max = 1; 1232 hba->flag &= ~FC_NPIV_ENABLED; 1233 1234#ifdef SLI3_SUPPORT 1235 if (sli_mode >= 3) { 1236 mb->un.varCfgPort.sli_mode = 3; 1237 mb->un.varCfgPort.cerbm = 1; 1238 mb->un.varCfgPort.max_hbq = EMLXS_NUM_HBQ; 1239 1240#ifdef NPIV_SUPPORT 1241 if (cfg[CFG_NPIV_ENABLE].current) { 1242 if (vpd->feaLevelHigh >= 0x09) { 1243 if (hba->model_info.chip >= EMLXS_SATURN_CHIP) { 1244 mb->un.varCfgPort.vpi_max = 1245 MAX_VPORTS - 1; 1246 } else { 1247 mb->un.varCfgPort.vpi_max = 1248 MAX_VPORTS_LIMITED - 1; 1249 } 1250 1251 mb->un.varCfgPort.cmv = 1; 1252 } else { 1253 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_init_debug_msg, 1254 "CFGPORT: Firmware does not support NPIV. " 1255 "level=%d", vpd->feaLevelHigh); 1256 } 1257 1258 } 1259#endif /* NPIV_SUPPORT */ 1260 } 1261#endif /* SLI3_SUPPORT */ 1262 1263 /* 1264 * Now setup pcb 1265 */ 1266 ((SLIM2 *) hba->slim2.virt)->pcb.type = TYPE_NATIVE_SLI2; 1267 ((SLIM2 *) hba->slim2.virt)->pcb.feature = FEATURE_INITIAL_SLI2; 1268 ((SLIM2 *) hba->slim2.virt)->pcb.maxRing = (hba->ring_count - 1); 1269 ((SLIM2 *) hba->slim2.virt)->pcb.mailBoxSize = sizeof (MAILBOX) + 1270 MBOX_EXTENSION_SIZE; 1271 1272 mbx = hba->slim2.phys + (uint64_t)(unsigned long)& (slim->mbx); 1273 ((SLIM2 *)hba->slim2.virt)->pcb.mbAddrHigh = 1274 (uint32_t)putPaddrHigh(mbx); 1275 ((SLIM2 *)hba->slim2.virt)->pcb.mbAddrLow = (uint32_t)putPaddrLow(mbx); 1276 1277 1278 /* 1279 * Set up HGP - Port Memory 1280 * 1281 * CR0Put - SLI2(no HBQs) = 0xc0, With HBQs = 0x80 1282 * RR0Get 0xc4 0x84 1283 * CR1Put 0xc8 0x88 1284 * RR1Get 0xcc 0x8c 1285 * CR2Put 0xd0 0x90 1286 * RR2Get 0xd4 0x94 1287 * CR3Put 0xd8 0x98 1288 * RR3Get 0xdc 0x9c 1289 * 1290 * Reserved 0xa0-0xbf 1291 * 1292 * If HBQs configured: 1293 * HBQ 0 Put ptr 0xc0 1294 * HBQ 1 Put ptr 0xc4 1295 * HBQ 2 Put ptr 0xc8 1296 * ...... 1297 * HBQ(M-1)Put Pointer 0xc0+(M-1)*4 1298 */ 1299 1300#ifdef SLI3_SUPPORT 1301 if (sli_mode >= 3) { 1302 /* ERBM is enabled */ 1303 hba->hgp_ring_offset = 0x80; 1304 hba->hgp_hbq_offset = 0xC0; 1305 1306 hba->iocb_cmd_size = SLI3_IOCB_CMD_SIZE; 1307 hba->iocb_rsp_size = SLI3_IOCB_RSP_SIZE; 1308 1309 } else /* SLI2 */ 1310#endif /* SLI3_SUPPORT */ 1311 { 1312 /* ERBM is disabled */ 1313 hba->hgp_ring_offset = 0xC0; 1314 hba->hgp_hbq_offset = 0; 1315 1316 hba->iocb_cmd_size = SLI2_IOCB_CMD_SIZE; 1317 hba->iocb_rsp_size = SLI2_IOCB_RSP_SIZE; 1318 } 1319 1320 /* The Sbus card uses Host Memory. The PCI card uses SLIM POINTER */ 1321 if (hba->bus_type == SBUS_FC) { 1322 hgp = hba->slim2.phys + 1323 (uint64_t)(unsigned long)& (mbox->us.s2.host); 1324 ((SLIM2 *)hba->slim2.virt)->pcb.hgpAddrHigh = 1325 (uint32_t)putPaddrHigh(hgp); 1326 ((SLIM2 *)hba->slim2.virt)->pcb.hgpAddrLow = 1327 (uint32_t)putPaddrLow(hgp); 1328 } else { 1329 ((SLIM2 *)hba->slim2.virt)->pcb.hgpAddrHigh = 1330 (uint32_t)ddi_get32(hba->pci_acc_handle, 1331 (uint32_t *)(hba->pci_addr + PCI_BAR_1_REGISTER)); 1332 1333 Laddr = ddi_get32(hba->pci_acc_handle, 1334 (uint32_t *)(hba->pci_addr + PCI_BAR_0_REGISTER)); 1335 Laddr &= ~0x4; 1336 ((SLIM2 *)hba->slim2.virt)->pcb.hgpAddrLow = 1337 (uint32_t)(Laddr + hba->hgp_ring_offset); 1338 1339 } 1340 1341 pgp = hba->slim2.phys + (uint64_t)(unsigned long)& (mbox->us.s2.port); 1342 ((SLIM2 *)hba->slim2.virt)->pcb.pgpAddrHigh = 1343 (uint32_t)putPaddrHigh(pgp); 1344 ((SLIM2 *)hba->slim2.virt)->pcb.pgpAddrLow = (uint32_t)putPaddrLow(pgp); 1345 1346 offset = 0; 1347 for (i = 0; i < 4; i++) { 1348 rp = &hba->ring[i]; 1349 rdsc = &((SLIM2 *) hba->slim2.virt)->pcb.rdsc[i]; 1350 1351 /* Setup command ring */ 1352 rgp = hba->slim2.phys + 1353 (uint64_t)(unsigned long)& (slim->IOCBs[offset]); 1354 rdsc->cmdAddrHigh = (uint32_t)putPaddrHigh(rgp); 1355 rdsc->cmdAddrLow = (uint32_t)putPaddrLow(rgp); 1356 rdsc->cmdEntries = rp->fc_numCiocb; 1357 1358 rp->fc_cmdringaddr = (void *) &((SLIM2 *) hba->slim2.virt)-> 1359 IOCBs[offset]; 1360 offset += rdsc->cmdEntries * hba->iocb_cmd_size; 1361 1362 /* Setup response ring */ 1363 rgp = hba->slim2.phys + 1364 (uint64_t)(unsigned long)& (slim->IOCBs[offset]); 1365 rdsc->rspAddrHigh = (uint32_t)putPaddrHigh(rgp); 1366 rdsc->rspAddrLow = (uint32_t)putPaddrLow(rgp); 1367 rdsc->rspEntries = rp->fc_numRiocb; 1368 1369 rp->fc_rspringaddr = (void *) &((SLIM2 *) hba->slim2.virt)-> 1370 IOCBs[offset]; 1371 offset += rdsc->rspEntries * hba->iocb_rsp_size; 1372 } 1373 1374 emlxs_pcimem_bcopy((uint32_t *)(&((SLIM2 *) hba->slim2.virt)->pcb), 1375 (uint32_t *)(&((SLIM2 *) hba->slim2.virt)->pcb), sizeof (PCB)); 1376 1377 offset = 1378 ((uint64_t)(unsigned long)& (((SLIM2 *) hba->slim2.virt)->pcb) - 1379 (uint64_t)(unsigned long)hba->slim2.virt); 1380 emlxs_mpdata_sync(hba->slim2.dma_handle, (off_t)offset, sizeof (PCB), 1381 DDI_DMA_SYNC_FORDEV); 1382 1383 return (0); 1384 1385} /* emlxs_mb_config_port() */ 1386 1387 1388#ifdef SLI3_SUPPORT | |
1389extern void 1390emlxs_mb_config_hbq(emlxs_hba_t *hba, MAILBOX *mb, int hbq_id) 1391{ | 1197extern void 1198emlxs_mb_config_hbq(emlxs_hba_t *hba, MAILBOX *mb, int hbq_id) 1199{ |
1392 HBQ_INIT_t *hbq; 1393 int i; | 1200 HBQ_INIT_t *hbq; 1201 int i; |
1394 | 1202 |
1395 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 1203 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
1396 1397 hbq = &hba->hbq_table[hbq_id]; 1398 1399 mb->un.varCfgHbq.hbqId = hbq_id; 1400 mb->un.varCfgHbq.numEntries = hbq->HBQ_numEntries; 1401 mb->un.varCfgHbq.recvNotify = hbq->HBQ_recvNotify; 1402 mb->un.varCfgHbq.numMask = hbq->HBQ_num_mask; 1403 mb->un.varCfgHbq.profile = hbq->HBQ_profile; --- 7 unchanged lines hidden (view full) --- 1411 1412 /* Copy info for profiles 2,3,5. Other profiles this area is reserved */ 1413 if ((hbq->HBQ_profile == 2) || (hbq->HBQ_profile == 3) || 1414 (hbq->HBQ_profile == 5)) { 1415 bcopy(&hbq->profiles.allprofiles, 1416 &mb->un.varCfgHbq.profiles.allprofiles, 1417 sizeof (hbq->profiles)); 1418 } | 1204 1205 hbq = &hba->hbq_table[hbq_id]; 1206 1207 mb->un.varCfgHbq.hbqId = hbq_id; 1208 mb->un.varCfgHbq.numEntries = hbq->HBQ_numEntries; 1209 mb->un.varCfgHbq.recvNotify = hbq->HBQ_recvNotify; 1210 mb->un.varCfgHbq.numMask = hbq->HBQ_num_mask; 1211 mb->un.varCfgHbq.profile = hbq->HBQ_profile; --- 7 unchanged lines hidden (view full) --- 1219 1220 /* Copy info for profiles 2,3,5. Other profiles this area is reserved */ 1221 if ((hbq->HBQ_profile == 2) || (hbq->HBQ_profile == 3) || 1222 (hbq->HBQ_profile == 5)) { 1223 bcopy(&hbq->profiles.allprofiles, 1224 &mb->un.varCfgHbq.profiles.allprofiles, 1225 sizeof (hbq->profiles)); 1226 } |
1227 |
|
1419 /* Return if no rctl / type masks for this HBQ */ 1420 if (!hbq->HBQ_num_mask) { 1421 return; 1422 } | 1228 /* Return if no rctl / type masks for this HBQ */ 1229 if (!hbq->HBQ_num_mask) { 1230 return; 1231 } |
1232 |
|
1423 /* Otherwise we setup specific rctl / type masks for this HBQ */ 1424 for (i = 0; i < hbq->HBQ_num_mask; i++) { | 1233 /* Otherwise we setup specific rctl / type masks for this HBQ */ 1234 for (i = 0; i < hbq->HBQ_num_mask; i++) { |
1425 mb->un.varCfgHbq.hbqMasks[i].tmatch = hbq->HBQ_Masks[i].tmatch; | 1235 mb->un.varCfgHbq.hbqMasks[i].tmatch = 1236 hbq->HBQ_Masks[i].tmatch; |
1426 mb->un.varCfgHbq.hbqMasks[i].tmask = hbq->HBQ_Masks[i].tmask; 1427 mb->un.varCfgHbq.hbqMasks[i].rctlmatch = 1428 hbq->HBQ_Masks[i].rctlmatch; 1429 mb->un.varCfgHbq.hbqMasks[i].rctlmask = 1430 hbq->HBQ_Masks[i].rctlmask; 1431 } 1432 1433 return; 1434 1435} /* emlxs_mb_config_hbq() */ 1436 1437#endif /* SLI3_SUPPORT */ 1438 1439 1440extern uint32_t 1441emlxs_mb_reg_vpi(emlxs_port_t *port) 1442{ | 1237 mb->un.varCfgHbq.hbqMasks[i].tmask = hbq->HBQ_Masks[i].tmask; 1238 mb->un.varCfgHbq.hbqMasks[i].rctlmatch = 1239 hbq->HBQ_Masks[i].rctlmatch; 1240 mb->un.varCfgHbq.hbqMasks[i].rctlmask = 1241 hbq->HBQ_Masks[i].rctlmask; 1242 } 1243 1244 return; 1245 1246} /* emlxs_mb_config_hbq() */ 1247 1248#endif /* SLI3_SUPPORT */ 1249 1250 1251extern uint32_t 1252emlxs_mb_reg_vpi(emlxs_port_t *port) 1253{ |
1443 emlxs_hba_t *hba = HBA; 1444 MAILBOXQ *mbq; 1445 MAILBOX *mb; | 1254 emlxs_hba_t *hba = HBA; 1255 MAILBOXQ *mbq; 1256 MAILBOX *mb; |
1446 1447 if (!(hba->flag & FC_NPIV_ENABLED)) { 1448 return (0); 1449 } | 1257 1258 if (!(hba->flag & FC_NPIV_ENABLED)) { 1259 return (0); 1260 } |
1261 |
|
1450 mutex_enter(&EMLXS_PORT_LOCK); 1451 1452 /* Can't reg vpi until ClearLA is sent */ 1453 if (hba->state != FC_READY) { 1454 mutex_exit(&EMLXS_PORT_LOCK); 1455 1456 return (1); 1457 } | 1262 mutex_enter(&EMLXS_PORT_LOCK); 1263 1264 /* Can't reg vpi until ClearLA is sent */ 1265 if (hba->state != FC_READY) { 1266 mutex_exit(&EMLXS_PORT_LOCK); 1267 1268 return (1); 1269 } |
1270 |
|
1458 /* Must have port id */ 1459 if (!port->did) { 1460 mutex_exit(&EMLXS_PORT_LOCK); 1461 1462 return (1); 1463 } | 1271 /* Must have port id */ 1272 if (!port->did) { 1273 mutex_exit(&EMLXS_PORT_LOCK); 1274 1275 return (1); 1276 } |
1464 if (!(mbq = (MAILBOXQ *) emlxs_mem_get(hba, MEM_MBOX | MEM_PRI))) { | 1277 1278 if (!(mbq = (MAILBOXQ *)emlxs_mem_get(hba, MEM_MBOX | MEM_PRI))) { |
1465 mutex_exit(&EMLXS_PORT_LOCK); 1466 1467 return (1); 1468 } | 1279 mutex_exit(&EMLXS_PORT_LOCK); 1280 1281 return (1); 1282 } |
1283 |
|
1469 port->flag |= EMLXS_PORT_REGISTERED; 1470 1471 mutex_exit(&EMLXS_PORT_LOCK); 1472 | 1284 port->flag |= EMLXS_PORT_REGISTERED; 1285 1286 mutex_exit(&EMLXS_PORT_LOCK); 1287 |
1473 mb = (MAILBOX *) mbq->mbox; 1474 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 1288 mb = (MAILBOX *)mbq->mbox; 1289 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
1475 mb->un.varRegVpi.vpi = port->vpi; 1476 mb->un.varRegVpi.sid = port->did; 1477 mb->mbxCommand = MBX_REG_VPI; 1478 mb->mbxOwner = OWN_HOST; 1479 | 1290 mb->un.varRegVpi.vpi = port->vpi; 1291 mb->un.varRegVpi.sid = port->did; 1292 mb->mbxCommand = MBX_REG_VPI; 1293 mb->mbxOwner = OWN_HOST; 1294 |
1480 if (emlxs_mb_issue_cmd(hba, mb, MBX_NOWAIT, 0) != MBX_BUSY) { | 1295 if (emlxs_sli_issue_mbox_cmd(hba, mb, MBX_NOWAIT, 0) != MBX_BUSY) { |
1481 (void) emlxs_mem_put(hba, MEM_MBOX, (uint8_t *)mbq); 1482 } | 1296 (void) emlxs_mem_put(hba, MEM_MBOX, (uint8_t *)mbq); 1297 } |
1298 |
|
1483 return (0); 1484 1485} /* emlxs_mb_reg_vpi() */ 1486 1487 1488extern uint32_t 1489emlxs_mb_unreg_vpi(emlxs_port_t *port) 1490{ | 1299 return (0); 1300 1301} /* emlxs_mb_reg_vpi() */ 1302 1303 1304extern uint32_t 1305emlxs_mb_unreg_vpi(emlxs_port_t *port) 1306{ |
1491 emlxs_hba_t *hba = HBA; 1492 MAILBOXQ *mbq; 1493 MAILBOX *mb; | 1307 emlxs_hba_t *hba = HBA; 1308 MAILBOXQ *mbq; 1309 MAILBOX *mb; |
1494 1495 mutex_enter(&EMLXS_PORT_LOCK); 1496 1497 if (!(port->flag & EMLXS_PORT_REGISTERED)) { 1498 mutex_exit(&EMLXS_PORT_LOCK); 1499 1500 return (0); 1501 } | 1310 1311 mutex_enter(&EMLXS_PORT_LOCK); 1312 1313 if (!(port->flag & EMLXS_PORT_REGISTERED)) { 1314 mutex_exit(&EMLXS_PORT_LOCK); 1315 1316 return (0); 1317 } |
1502 if (!(mbq = (MAILBOXQ *) emlxs_mem_get(hba, MEM_MBOX | MEM_PRI))) { | 1318 1319 if (!(mbq = (MAILBOXQ *)emlxs_mem_get(hba, MEM_MBOX | MEM_PRI))) { |
1503 mutex_exit(&EMLXS_PORT_LOCK); 1504 1505 return (1); 1506 } | 1320 mutex_exit(&EMLXS_PORT_LOCK); 1321 1322 return (1); 1323 } |
1324 |
|
1507 port->flag &= ~EMLXS_PORT_REGISTERED; 1508 1509 mutex_exit(&EMLXS_PORT_LOCK); 1510 | 1325 port->flag &= ~EMLXS_PORT_REGISTERED; 1326 1327 mutex_exit(&EMLXS_PORT_LOCK); 1328 |
1511 mb = (MAILBOX *) mbq->mbox; 1512 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 1329 mb = (MAILBOX *)mbq->mbox; 1330 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
1513 mb->un.varUnregVpi.vpi = port->vpi; 1514 mb->mbxCommand = MBX_UNREG_VPI; 1515 mb->mbxOwner = OWN_HOST; 1516 | 1331 mb->un.varUnregVpi.vpi = port->vpi; 1332 mb->mbxCommand = MBX_UNREG_VPI; 1333 mb->mbxOwner = OWN_HOST; 1334 |
1517 if (emlxs_mb_issue_cmd(hba, mb, MBX_NOWAIT, 0) != MBX_BUSY) { | 1335 if (emlxs_sli_issue_mbox_cmd(hba, mb, MBX_NOWAIT, 0) != MBX_BUSY) { |
1518 (void) emlxs_mem_put(hba, MEM_MBOX, (uint8_t *)mbq); 1519 } | 1336 (void) emlxs_mem_put(hba, MEM_MBOX, (uint8_t *)mbq); 1337 } |
1338 |
|
1520 return (0); 1521 1522} /* emlxs_mb_unreg_vpi() */ 1523 1524 1525/* | 1339 return (0); 1340 1341} /* emlxs_mb_unreg_vpi() */ 1342 1343 1344/* |
1526 * emlxs_mb_config_farp Issue a CONFIG FARP 1527 * mailbox command | 1345 * emlxs_mb_config_farp Issue a CONFIG FARP mailbox command |
1528 */ 1529extern void 1530emlxs_mb_config_farp(emlxs_hba_t *hba, MAILBOX *mb) 1531{ | 1346 */ 1347extern void 1348emlxs_mb_config_farp(emlxs_hba_t *hba, MAILBOX *mb) 1349{ |
1532 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 1350 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
1533 | 1351 |
1534 bcopy((uint8_t *)& hba->wwpn, 1535 (uint8_t *)& mb->un.varCfgFarp.portname, 1536 sizeof (NAME_TYPE)); | 1352 bcopy((uint8_t *)&hba->wwpn, 1353 (uint8_t *)&mb->un.varCfgFarp.portname, sizeof (NAME_TYPE)); |
1537 | 1354 |
1538 bcopy((uint8_t *)& hba->wwpn, 1539 (uint8_t *)& mb->un.varCfgFarp.nodename, 1540 sizeof (NAME_TYPE)); | 1355 bcopy((uint8_t *)&hba->wwpn, 1356 (uint8_t *)&mb->un.varCfgFarp.nodename, sizeof (NAME_TYPE)); |
1541 1542 mb->un.varCfgFarp.filterEnable = 1; 1543 mb->un.varCfgFarp.portName = 1; 1544 mb->un.varCfgFarp.nodeName = 1; 1545 mb->mbxCommand = MBX_CONFIG_FARP; 1546 mb->mbxOwner = OWN_HOST; 1547} /* emlxs_mb_config_farp() */ 1548 1549 1550/* | 1357 1358 mb->un.varCfgFarp.filterEnable = 1; 1359 mb->un.varCfgFarp.portName = 1; 1360 mb->un.varCfgFarp.nodeName = 1; 1361 mb->mbxCommand = MBX_CONFIG_FARP; 1362 mb->mbxOwner = OWN_HOST; 1363} /* emlxs_mb_config_farp() */ 1364 1365 1366/* |
1551 * emlxs_mb_read_nv Issue a READ CONFIG 1552 * mailbox command | 1367 * emlxs_mb_read_nv Issue a READ CONFIG mailbox command |
1553 */ | 1368 */ |
1554/* ARGSUSED */ | 1369/*ARGSUSED*/ |
1555extern void 1556emlxs_mb_read_config(emlxs_hba_t *hba, MAILBOX *mb) 1557{ | 1370extern void 1371emlxs_mb_read_config(emlxs_hba_t *hba, MAILBOX *mb) 1372{ |
1558 bzero((void *) mb, MAILBOX_CMD_BSIZE); | 1373 bzero((void *)mb, MAILBOX_CMD_BSIZE); |
1559 1560 mb->mbxCommand = MBX_READ_CONFIG; 1561 mb->mbxOwner = OWN_HOST; | 1374 1375 mb->mbxCommand = MBX_READ_CONFIG; 1376 mb->mbxOwner = OWN_HOST; |
1562 | |
1563} /* emlxs_mb_read_config() */ 1564 1565 1566 1567/* 1568 * NAME: emlxs_mb_put 1569 * 1570 * FUNCTION: put mailbox cmd onto the mailbox queue. 1571 * 1572 * EXECUTION ENVIRONMENT: process and interrupt level. 1573 * 1574 * NOTES: 1575 * | 1377} /* emlxs_mb_read_config() */ 1378 1379 1380 1381/* 1382 * NAME: emlxs_mb_put 1383 * 1384 * FUNCTION: put mailbox cmd onto the mailbox queue. 1385 * 1386 * EXECUTION ENVIRONMENT: process and interrupt level. 1387 * 1388 * NOTES: 1389 * |
1576 * CALLED FROM: emlxs_mb_issue_cmd | 1390 * CALLED FROM: emlxs_sli_issue_mbox_cmd |
1577 * | 1391 * |
1578 * INPUT: hba - pointer to the device info area mbp 1579 * - pointer to mailbox queue entry of mailbox cmd | 1392 * INPUT: hba - pointer to the device info area 1393 * mbp - pointer to mailbox queue entry of mailbox cmd |
1580 * 1581 * RETURNS: NULL - command queued 1582 */ 1583extern void 1584emlxs_mb_put(emlxs_hba_t *hba, MAILBOXQ *mbq) 1585{ 1586 1587 mutex_enter(&EMLXS_MBOX_LOCK); 1588 1589 if (hba->mbox_queue.q_first) { 1590 1591 /* 1592 * queue command to end of list 1593 */ | 1394 * 1395 * RETURNS: NULL - command queued 1396 */ 1397extern void 1398emlxs_mb_put(emlxs_hba_t *hba, MAILBOXQ *mbq) 1399{ 1400 1401 mutex_enter(&EMLXS_MBOX_LOCK); 1402 1403 if (hba->mbox_queue.q_first) { 1404 1405 /* 1406 * queue command to end of list 1407 */ |
1594 ((MAILBOXQ *) hba->mbox_queue.q_last)->next = mbq; | 1408 ((MAILBOXQ *)hba->mbox_queue.q_last)->next = mbq; |
1595 hba->mbox_queue.q_last = (uint8_t *)mbq; 1596 hba->mbox_queue.q_cnt++; 1597 } else { 1598 1599 /* 1600 * add command to empty list 1601 */ 1602 hba->mbox_queue.q_first = (uint8_t *)mbq; --- 20 unchanged lines hidden (view full) --- 1623 * 1624 * INPUT: hba - pointer to the device info area 1625 * 1626 * RETURNS: NULL - no match found mb pointer - pointer to a mailbox command 1627 */ 1628extern MAILBOXQ * 1629emlxs_mb_get(emlxs_hba_t *hba) 1630{ | 1409 hba->mbox_queue.q_last = (uint8_t *)mbq; 1410 hba->mbox_queue.q_cnt++; 1411 } else { 1412 1413 /* 1414 * add command to empty list 1415 */ 1416 hba->mbox_queue.q_first = (uint8_t *)mbq; --- 20 unchanged lines hidden (view full) --- 1437 * 1438 * INPUT: hba - pointer to the device info area 1439 * 1440 * RETURNS: NULL - no match found mb pointer - pointer to a mailbox command 1441 */ 1442extern MAILBOXQ * 1443emlxs_mb_get(emlxs_hba_t *hba) 1444{ |
1631 MAILBOXQ *p_first = NULL; | 1445 MAILBOXQ *p_first = NULL; |
1632 1633 mutex_enter(&EMLXS_MBOX_LOCK); 1634 1635 if (hba->mbox_queue.q_first) { | 1446 1447 mutex_enter(&EMLXS_MBOX_LOCK); 1448 1449 if (hba->mbox_queue.q_first) { |
1636 p_first = (MAILBOXQ *) hba->mbox_queue.q_first; | 1450 p_first = (MAILBOXQ *)hba->mbox_queue.q_first; |
1637 hba->mbox_queue.q_first = (uint8_t *)p_first->next; 1638 1639 if (hba->mbox_queue.q_first == NULL) { 1640 hba->mbox_queue.q_last = NULL; 1641 hba->mbox_queue.q_cnt = 0; 1642 } else { 1643 hba->mbox_queue.q_cnt--; 1644 } 1645 1646 p_first->next = NULL; 1647 } | 1451 hba->mbox_queue.q_first = (uint8_t *)p_first->next; 1452 1453 if (hba->mbox_queue.q_first == NULL) { 1454 hba->mbox_queue.q_last = NULL; 1455 hba->mbox_queue.q_cnt = 0; 1456 } else { 1457 hba->mbox_queue.q_cnt--; 1458 } 1459 1460 p_first->next = NULL; 1461 } |
1462 |
|
1648 mutex_exit(&EMLXS_MBOX_LOCK); 1649 1650 return (p_first); 1651 1652} /* emlxs_mb_get() */ 1653 1654 1655 1656/* EMLXS_PORT_LOCK must be held when calling this */ | 1463 mutex_exit(&EMLXS_MBOX_LOCK); 1464 1465 return (p_first); 1466 1467} /* emlxs_mb_get() */ 1468 1469 1470 1471/* EMLXS_PORT_LOCK must be held when calling this */ |
1657static void | 1472void |
1658emlxs_mb_init(emlxs_hba_t *hba, MAILBOXQ *mbq, uint32_t flag, uint32_t tmo) 1659{ | 1473emlxs_mb_init(emlxs_hba_t *hba, MAILBOXQ *mbq, uint32_t flag, uint32_t tmo) 1474{ |
1660 MATCHMAP *mp; | 1475#ifdef FMA_SUPPORT 1476 emlxs_port_t *port = &PPORT; 1477#endif /* FMA_SUPPORT */ 1478 MATCHMAP *mp; |
1661 1662 HBASTATS.MboxIssued++; 1663 hba->mbox_queue_flag = flag; 1664 1665 /* Set the Mailbox timer */ 1666 hba->mbox_timer = hba->timer_tics + tmo; 1667 1668 /* Initialize mailbox */ --- 13 unchanged lines hidden (view full) --- 1682 if (mbq->bp) { 1683 mp = (MATCHMAP *) mbq->bp; 1684 emlxs_mpdata_sync(mp->dma_handle, 0, mp->size, 1685 DDI_DMA_SYNC_FORDEV); 1686 1687 hba->mbox_bp = mbq->bp; 1688 mbq->bp = 0; 1689 } | 1479 1480 HBASTATS.MboxIssued++; 1481 hba->mbox_queue_flag = flag; 1482 1483 /* Set the Mailbox timer */ 1484 hba->mbox_timer = hba->timer_tics + tmo; 1485 1486 /* Initialize mailbox */ --- 13 unchanged lines hidden (view full) --- 1500 if (mbq->bp) { 1501 mp = (MATCHMAP *) mbq->bp; 1502 emlxs_mpdata_sync(mp->dma_handle, 0, mp->size, 1503 DDI_DMA_SYNC_FORDEV); 1504 1505 hba->mbox_bp = mbq->bp; 1506 mbq->bp = 0; 1507 } |
1508 |
|
1690 if (mbq->sbp) { 1691 hba->mbox_sbp = mbq->sbp; 1692 mbq->sbp = 0; 1693 } | 1509 if (mbq->sbp) { 1510 hba->mbox_sbp = mbq->sbp; 1511 mbq->sbp = 0; 1512 } |
1513 |
|
1694 if (mbq->ubp) { 1695 hba->mbox_ubp = mbq->ubp; 1696 mbq->ubp = 0; 1697 } | 1514 if (mbq->ubp) { 1515 hba->mbox_ubp = mbq->ubp; 1516 mbq->ubp = 0; 1517 } |
1518 |
|
1698 if (mbq->iocbq) { 1699 hba->mbox_iocbq = mbq->iocbq; 1700 mbq->iocbq = 0; 1701 } 1702#ifdef MBOX_EXT_SUPPORT 1703 if (mbq->extbuf && mbq->extsize) { 1704 hba->mbox_ext = mbq->extbuf; 1705 hba->mbox_ext_size = mbq->extsize; 1706 } | 1519 if (mbq->iocbq) { 1520 hba->mbox_iocbq = mbq->iocbq; 1521 mbq->iocbq = 0; 1522 } 1523#ifdef MBOX_EXT_SUPPORT 1524 if (mbq->extbuf && mbq->extsize) { 1525 hba->mbox_ext = mbq->extbuf; 1526 hba->mbox_ext_size = mbq->extsize; 1527 } |
1707#endif /* MBOX_EXT_SUPPORT */ | 1528#endif /* MBOX_EXT_SUPPORT */ |
1708 1709 return; 1710 1711} /* emlxs_mb_init() */ 1712 1713 1714extern void 1715emlxs_mb_fini(emlxs_hba_t *hba, MAILBOX *mb, uint32_t mbxStatus) 1716{ | 1529 1530 return; 1531 1532} /* emlxs_mb_init() */ 1533 1534 1535extern void 1536emlxs_mb_fini(emlxs_hba_t *hba, MAILBOX *mb, uint32_t mbxStatus) 1537{ |
1717 emlxs_port_t *port = &PPORT; 1718 MATCHMAP *mbox_bp; 1719 emlxs_buf_t *mbox_sbp; 1720 fc_unsol_buf_t *mbox_ubp; 1721 IOCBQ *mbox_iocbq; 1722 MAILBOXQ *mbox_mbq; 1723 MAILBOX *mbox; 1724 uint32_t mbox_queue_flag; 1725 emlxs_ub_priv_t *ub_priv; | 1538 emlxs_port_t *port = &PPORT; 1539 MATCHMAP *mbox_bp; 1540 emlxs_buf_t *mbox_sbp; 1541 fc_unsol_buf_t *mbox_ubp; 1542 IOCBQ *mbox_iocbq; 1543 MAILBOXQ *mbox_mbq; 1544 MAILBOX *mbox; 1545 uint32_t mbox_queue_flag; 1546 emlxs_ub_priv_t *ub_priv; |
1726 1727 mutex_enter(&EMLXS_PORT_LOCK); 1728 1729 if (hba->mbox_queue_flag) { 1730 HBASTATS.MboxCompleted++; 1731 1732 if (mbxStatus != MBX_SUCCESS) { 1733 HBASTATS.MboxError++; 1734 } else { 1735 HBASTATS.MboxGood++; 1736 } 1737 } | 1547 1548 mutex_enter(&EMLXS_PORT_LOCK); 1549 1550 if (hba->mbox_queue_flag) { 1551 HBASTATS.MboxCompleted++; 1552 1553 if (mbxStatus != MBX_SUCCESS) { 1554 HBASTATS.MboxError++; 1555 } else { 1556 HBASTATS.MboxGood++; 1557 } 1558 } |
1738 mbox_bp = (MATCHMAP *) hba->mbox_bp; | 1559 1560 mbox_bp = (MATCHMAP *)hba->mbox_bp; |
1739 mbox_sbp = (emlxs_buf_t *)hba->mbox_sbp; 1740 mbox_ubp = (fc_unsol_buf_t *)hba->mbox_ubp; | 1561 mbox_sbp = (emlxs_buf_t *)hba->mbox_sbp; 1562 mbox_ubp = (fc_unsol_buf_t *)hba->mbox_ubp; |
1741 mbox_iocbq = (IOCBQ *) hba->mbox_iocbq; 1742 mbox_mbq = (MAILBOXQ *) hba->mbox_mbq; | 1563 mbox_iocbq = (IOCBQ *)hba->mbox_iocbq; 1564 mbox_mbq = (MAILBOXQ *)hba->mbox_mbq; |
1743 mbox_queue_flag = hba->mbox_queue_flag; 1744 1745#ifdef MBOX_EXT_SUPPORT 1746 hba->mbox_ext = 0; 1747 hba->mbox_ext_size = 0; | 1565 mbox_queue_flag = hba->mbox_queue_flag; 1566 1567#ifdef MBOX_EXT_SUPPORT 1568 hba->mbox_ext = 0; 1569 hba->mbox_ext_size = 0; |
1748#endif /* MBOX_EXT_SUPPORT */ | 1570#endif /* MBOX_EXT_SUPPORT */ |
1749 1750 hba->mbox_bp = 0; 1751 hba->mbox_sbp = 0; 1752 hba->mbox_ubp = 0; 1753 hba->mbox_iocbq = 0; 1754 hba->mbox_mbqflag = 0; 1755 hba->mbox_mbq = 0; 1756 hba->mbox_timer = 0; 1757 hba->mbox_queue_flag = 0; 1758 1759 mutex_exit(&EMLXS_PORT_LOCK); 1760 1761 if (mbox_mbq) { 1762 if (mb) { | 1571 1572 hba->mbox_bp = 0; 1573 hba->mbox_sbp = 0; 1574 hba->mbox_ubp = 0; 1575 hba->mbox_iocbq = 0; 1576 hba->mbox_mbqflag = 0; 1577 hba->mbox_mbq = 0; 1578 hba->mbox_timer = 0; 1579 hba->mbox_queue_flag = 0; 1580 1581 mutex_exit(&EMLXS_PORT_LOCK); 1582 1583 if (mbox_mbq) { 1584 if (mb) { |
1763 /* 1764 * Copy the local mailbox provided back into the 1765 * original mailbox 1766 */ | 1585 /* Copy the local mailbox provided back into */ 1586 /* the original mailbox */ |
1767 bcopy((uint32_t *)mb, (uint32_t *)mbox_mbq, 1768 MAILBOX_CMD_BSIZE); 1769 } | 1587 bcopy((uint32_t *)mb, (uint32_t *)mbox_mbq, 1588 MAILBOX_CMD_BSIZE); 1589 } |
1770 mbox = (MAILBOX *) mbox_mbq; | 1590 1591 mbox = (MAILBOX *)mbox_mbq; |
1771 mbox->mbxStatus = mbxStatus; 1772 1773 /* Mark mailbox complete */ 1774 mbox_mbq->flag |= MBQ_COMPLETED; 1775 1776 /* Wake up the sleeping thread */ 1777 if (mbox_queue_flag == MBX_SLEEP) { 1778 mutex_enter(&EMLXS_MBOX_LOCK); 1779 cv_broadcast(&EMLXS_MBOX_CV); 1780 mutex_exit(&EMLXS_MBOX_LOCK); 1781 } 1782 } | 1592 mbox->mbxStatus = mbxStatus; 1593 1594 /* Mark mailbox complete */ 1595 mbox_mbq->flag |= MBQ_COMPLETED; 1596 1597 /* Wake up the sleeping thread */ 1598 if (mbox_queue_flag == MBX_SLEEP) { 1599 mutex_enter(&EMLXS_MBOX_LOCK); 1600 cv_broadcast(&EMLXS_MBOX_CV); 1601 mutex_exit(&EMLXS_MBOX_LOCK); 1602 } 1603 } |
1604 |
|
1783 /* Check for deferred MBUF cleanup */ 1784 if (mbox_bp && (mbox_queue_flag == MBX_NOWAIT)) { 1785 (void) emlxs_mem_put(hba, MEM_BUF, (uint8_t *)mbox_bp); 1786 } 1787#ifdef SFCT_SUPPORT 1788 if (mbox_sbp && mbox_sbp->fct_cmd) { 1789 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_fct_detail_msg, 1790 "FCT mailbox: %s: status=%x", 1791 emlxs_mb_cmd_xlate(mb->mbxCommand), 1792 (uint32_t)mb->mbxStatus); 1793 } | 1605 /* Check for deferred MBUF cleanup */ 1606 if (mbox_bp && (mbox_queue_flag == MBX_NOWAIT)) { 1607 (void) emlxs_mem_put(hba, MEM_BUF, (uint8_t *)mbox_bp); 1608 } 1609#ifdef SFCT_SUPPORT 1610 if (mbox_sbp && mbox_sbp->fct_cmd) { 1611 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_fct_detail_msg, 1612 "FCT mailbox: %s: status=%x", 1613 emlxs_mb_cmd_xlate(mb->mbxCommand), 1614 (uint32_t)mb->mbxStatus); 1615 } |
1794#endif /* SFCT_SUPPORT */ | 1616#endif /* SFCT_SUPPORT */ |
1795 1796 /* Check for deferred pkt completion */ 1797 if (mbox_sbp) { 1798 if (mbxStatus != MBX_SUCCESS) { 1799 /* Set error status */ 1800 mbox_sbp->pkt_flags &= ~PACKET_STATE_VALID; 1801 emlxs_set_pkt_state(mbox_sbp, IOSTAT_LOCAL_REJECT, 1802 IOERR_NO_RESOURCES, 1); 1803 } | 1617 1618 /* Check for deferred pkt completion */ 1619 if (mbox_sbp) { 1620 if (mbxStatus != MBX_SUCCESS) { 1621 /* Set error status */ 1622 mbox_sbp->pkt_flags &= ~PACKET_STATE_VALID; 1623 emlxs_set_pkt_state(mbox_sbp, IOSTAT_LOCAL_REJECT, 1624 IOERR_NO_RESOURCES, 1); 1625 } |
1626 |
|
1804 emlxs_pkt_complete(mbox_sbp, -1, 0, 1); 1805 } | 1627 emlxs_pkt_complete(mbox_sbp, -1, 0, 1); 1628 } |
1629 |
|
1806 /* Check for deferred ub completion */ 1807 if (mbox_ubp) { 1808 ub_priv = mbox_ubp->ub_fca_private; 1809 port = ub_priv->port; 1810 1811 emlxs_ub_callback(port, mbox_ubp); 1812 } | 1630 /* Check for deferred ub completion */ 1631 if (mbox_ubp) { 1632 ub_priv = mbox_ubp->ub_fca_private; 1633 port = ub_priv->port; 1634 1635 emlxs_ub_callback(port, mbox_ubp); 1636 } |
1637 |
|
1813 /* Check for deferred iocb tx */ 1814 if (mbox_iocbq) { | 1638 /* Check for deferred iocb tx */ 1639 if (mbox_iocbq) { |
1815 emlxs_issue_iocb_cmd(hba, mbox_iocbq->ring, mbox_iocbq); | 1640 emlxs_sli_issue_iocb_cmd(hba, mbox_iocbq->ring, mbox_iocbq); |
1816 } | 1641 } |
1642 |
|
1817 return; 1818 1819} /* emlxs_mb_fini() */ 1820 1821 1822 1823/* This should only be called with active MBX_NOWAIT mailboxes */ | 1643 return; 1644 1645} /* emlxs_mb_fini() */ 1646 1647 1648 1649/* This should only be called with active MBX_NOWAIT mailboxes */ |
1824static void | 1650void |
1825emlxs_mb_retry(emlxs_hba_t *hba, MAILBOX *mb) 1826{ | 1651emlxs_mb_retry(emlxs_hba_t *hba, MAILBOX *mb) 1652{ |
1827 MAILBOXQ *mbq; | 1653 MAILBOXQ *mbq; |
1828 1829 mutex_enter(&EMLXS_PORT_LOCK); 1830 1831 HBASTATS.MboxCompleted++; 1832 1833 if (mb->mbxStatus != 0) { 1834 HBASTATS.MboxError++; 1835 } else { 1836 HBASTATS.MboxGood++; 1837 } 1838 | 1654 1655 mutex_enter(&EMLXS_PORT_LOCK); 1656 1657 HBASTATS.MboxCompleted++; 1658 1659 if (mb->mbxStatus != 0) { 1660 HBASTATS.MboxError++; 1661 } else { 1662 HBASTATS.MboxGood++; 1663 } 1664 |
1839 mbq = (MAILBOXQ *) mb; | 1665 mbq = (MAILBOXQ *)mb; |
1840 mbq->bp = (uint8_t *)hba->mbox_bp; 1841 mbq->sbp = (uint8_t *)hba->mbox_sbp; 1842 mbq->ubp = (uint8_t *)hba->mbox_ubp; 1843 mbq->iocbq = (uint8_t *)hba->mbox_iocbq; 1844 1845 hba->mbox_bp = 0; 1846 hba->mbox_sbp = 0; 1847 hba->mbox_ubp = 0; --- 4 unchanged lines hidden (view full) --- 1852 1853 mutex_exit(&EMLXS_PORT_LOCK); 1854 1855 return; 1856 1857} /* emlxs_mb_retry() */ 1858 1859 | 1666 mbq->bp = (uint8_t *)hba->mbox_bp; 1667 mbq->sbp = (uint8_t *)hba->mbox_sbp; 1668 mbq->ubp = (uint8_t *)hba->mbox_ubp; 1669 mbq->iocbq = (uint8_t *)hba->mbox_iocbq; 1670 1671 hba->mbox_bp = 0; 1672 hba->mbox_sbp = 0; 1673 hba->mbox_ubp = 0; --- 4 unchanged lines hidden (view full) --- 1678 1679 mutex_exit(&EMLXS_PORT_LOCK); 1680 1681 return; 1682 1683} /* emlxs_mb_retry() */ 1684 1685 |
1860 1861/* 1862 * emlxs_handle_mb_event 1863 * 1864 * Description: Process a Mailbox Attention. 1865 * Called from host_interrupt to process MBATT 1866 * 1867 * Returns: 1868 * 1869 */ 1870extern uint32_t 1871emlxs_handle_mb_event(emlxs_hba_t *hba) 1872{ 1873 emlxs_port_t *port = &PPORT; 1874 MAILBOX *mb; 1875 MAILBOX *swpmb; 1876 MAILBOX *mbox; 1877 MAILBOXQ *mbq; 1878 emlxs_config_t *cfg; 1879 uint32_t control; 1880 volatile uint32_t word0; 1881 MATCHMAP *mbox_bp; 1882 uint32_t la_enable; 1883 off_t offset; 1884 uint32_t i; 1885 MAILBOXQ mailbox; 1886 1887 cfg = &CFG; 1888 swpmb = (MAILBOX *) & word0; 1889 mb = (MAILBOX *) & mailbox; 1890 1891 switch (hba->mbox_queue_flag) { 1892 case 0: 1893 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_stray_mbox_intr_msg, 1894 "No mailbox active."); 1895 return (0); 1896 1897 case MBX_POLL: 1898 1899 /* 1900 * Mark mailbox complete, this should wake up any polling 1901 * threads 1902 */ 1903 /* 1904 * This can happen if interrupts are enabled while a polled 1905 * mailbox command is outstanding 1906 */ 1907 /* 1908 * If we don't set MBQ_COMPLETED here, the polling thread may 1909 * wait until timeout error occurs 1910 */ 1911 1912 mutex_enter(&EMLXS_MBOX_LOCK); 1913 mbq = (MAILBOXQ *) hba->mbox_mbq; 1914 if (mbq) { 1915 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_detail_msg, 1916 "Mailbox event. Completing Polled command."); 1917 mbq->flag |= MBQ_COMPLETED; 1918 } 1919 mutex_exit(&EMLXS_MBOX_LOCK); 1920 1921 return (0); 1922 1923 case MBX_SLEEP: 1924 case MBX_NOWAIT: 1925 break; 1926 1927 default: 1928 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_completion_error_msg, 1929 "Invalid Mailbox flag (%x)."); 1930 return (0); 1931 } 1932 1933 /* Get first word of mailbox */ 1934 if (hba->flag & FC_SLIM2_MODE) { 1935 mbox = FC_SLIM2_MAILBOX(hba); 1936 offset = (off_t)((uint64_t)(unsigned long)mbox - 1937 (uint64_t)(unsigned long)hba->slim2.virt); 1938 1939 emlxs_mpdata_sync(hba->slim2.dma_handle, offset, 1940 sizeof (uint32_t), DDI_DMA_SYNC_FORKERNEL); 1941 word0 = *((volatile uint32_t *) mbox); 1942 word0 = PCIMEM_LONG(word0); 1943 } else { 1944 mbox = FC_SLIM1_MAILBOX(hba); 1945 word0 = READ_SLIM_ADDR(hba, ((volatile uint32_t *) mbox)); 1946 } 1947 1948 i = 0; 1949 while (swpmb->mbxOwner == OWN_CHIP) { 1950 if (i++ > 10000) { 1951 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_stray_mbox_intr_msg, 1952 "OWN_CHIP: %s: status=%x", 1953 emlxs_mb_cmd_xlate(swpmb->mbxCommand), 1954 swpmb->mbxStatus); 1955 1956 return (1); 1957 } 1958 /* Get first word of mailbox */ 1959 if (hba->flag & FC_SLIM2_MODE) { 1960 emlxs_mpdata_sync(hba->slim2.dma_handle, offset, 1961 sizeof (uint32_t), DDI_DMA_SYNC_FORKERNEL); 1962 word0 = *((volatile uint32_t *) mbox); 1963 word0 = PCIMEM_LONG(word0); 1964 } else { 1965 word0 = READ_SLIM_ADDR(hba, 1966 ((volatile uint32_t *) mbox)); 1967 } 1968 } 1969 1970 /* Now that we are the owner, DMA Sync entire mailbox if needed */ 1971 if (hba->flag & FC_SLIM2_MODE) { 1972 emlxs_mpdata_sync(hba->slim2.dma_handle, offset, 1973 MAILBOX_CMD_BSIZE, DDI_DMA_SYNC_FORKERNEL); 1974 emlxs_pcimem_bcopy((uint32_t *)mbox, (uint32_t *)mb, 1975 MAILBOX_CMD_BSIZE); 1976 } else { 1977 READ_SLIM_COPY(hba, (uint32_t *)mb, (uint32_t *)mbox, 1978 MAILBOX_CMD_WSIZE); 1979 } 1980 1981#ifdef MBOX_EXT_SUPPORT 1982 if (hba->mbox_ext) { 1983 uint32_t *mbox_ext = (uint32_t *)((uint8_t *)mbox + 1984 MBOX_EXTENSION_OFFSET); 1985 off_t offset_ext = offset + MBOX_EXTENSION_OFFSET; 1986 1987 if (hba->flag & FC_SLIM2_MODE) { 1988 emlxs_mpdata_sync(hba->slim2.dma_handle, offset_ext, 1989 hba->mbox_ext_size, DDI_DMA_SYNC_FORKERNEL); 1990 emlxs_pcimem_bcopy(mbox_ext, (uint32_t *)hba->mbox_ext, 1991 hba->mbox_ext_size); 1992 } else { 1993 READ_SLIM_COPY(hba, (uint32_t *)hba->mbox_ext, mbox_ext, 1994 (hba->mbox_ext_size / 4)); 1995 } 1996 } 1997#endif /* MBOX_EXT_SUPPORT */ 1998 1999 /* Now sync the memory buffer if one was used */ 2000 if (hba->mbox_bp) { 2001 mbox_bp = (MATCHMAP *) hba->mbox_bp; 2002 emlxs_mpdata_sync(mbox_bp->dma_handle, 0, mbox_bp->size, 2003 DDI_DMA_SYNC_FORKERNEL); 2004 } 2005 /* Mailbox has been completely received at this point */ 2006 2007 if (mb->mbxCommand == MBX_HEARTBEAT) { 2008 hba->heartbeat_active = 0; 2009 goto done; 2010 } 2011 if (hba->mbox_queue_flag == MBX_SLEEP) { 2012 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_detail_msg, 2013 "Received. %s: status=%x Sleep.", 2014 emlxs_mb_cmd_xlate(swpmb->mbxCommand), swpmb->mbxStatus); 2015 } else { 2016 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_detail_msg, 2017 "Completed. %s: status=%x", 2018 emlxs_mb_cmd_xlate(swpmb->mbxCommand), swpmb->mbxStatus); 2019 } 2020 2021 /* Filter out passthru mailbox */ 2022 if (hba->mbox_mbqflag & MBQ_PASSTHRU) { 2023 goto done; 2024 } 2025 /* If succesful, process the result */ 2026 if (mb->mbxStatus == 0) { 2027 (void) emlxs_mb_handle_cmd(hba, mb); 2028 goto done; 2029 } 2030 /* ERROR RETURNED */ 2031 2032 /* Check for no resources */ 2033 if ((mb->mbxStatus == MBXERR_NO_RESOURCES) && 2034 (hba->mbox_queue_flag == MBX_NOWAIT)) { 2035 /* Retry only MBX_NOWAIT requests */ 2036 2037 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_event_msg, 2038 "Retrying. %s: status=%x", 2039 emlxs_mb_cmd_xlate(mb->mbxCommand), 2040 (uint32_t)mb->mbxStatus); 2041 2042 if ((mbox = (MAILBOX *) emlxs_mem_get(hba, MEM_MBOX))) { 2043 bcopy((uint8_t *)mb, (uint8_t *)mbox, 2044 MAILBOX_CMD_BSIZE); 2045 2046 switch (mbox->mbxCommand) { 2047 case MBX_READ_SPARM: 2048 control = mbox->un.varRdSparm.un.sp.bdeSize; 2049 if (control == 0) { 2050 (void) emlxs_mb_read_sparam(hba, mbox); 2051 } 2052 break; 2053 2054 case MBX_READ_SPARM64: 2055 control = mbox->un.varRdSparm.un.sp64.tus.f. 2056 bdeSize; 2057 if (control == 0) { 2058 (void) emlxs_mb_read_sparam(hba, mbox); 2059 } 2060 break; 2061 2062 case MBX_REG_LOGIN: 2063 control = mbox->un.varRegLogin.un.sp.bdeSize; 2064 if (control == 0) { 2065#ifdef NPIV_SUPPORT 2066 /* Special handle for vport PLOGI */ 2067 if (hba->mbox_iocbq == (uint8_t *)1) { 2068 hba->mbox_iocbq = NULL; 2069 } 2070#endif /* NPIV_SUPPORT */ 2071 goto done; 2072 } 2073 break; 2074 2075 case MBX_REG_LOGIN64: 2076 control = mbox->un.varRegLogin.un.sp64.tus.f. 2077 bdeSize; 2078 if (control == 0) { 2079#ifdef NPIV_SUPPORT 2080 /* Special handle for vport PLOGI */ 2081 if (hba->mbox_iocbq == (uint8_t *)1) { 2082 hba->mbox_iocbq = NULL; 2083 } 2084#endif /* NPIV_SUPPORT */ 2085 goto done; 2086 } 2087 break; 2088 2089 case MBX_READ_LA: 2090 control = mbox->un.varReadLA.un.lilpBde.bdeSize; 2091 if (control == 0) { 2092 (void) emlxs_mb_read_la(hba, mbox); 2093 } 2094 break; 2095 2096 case MBX_READ_LA64: 2097 control = mbox->un.varReadLA.un.lilpBde64.tus.f. 2098 bdeSize; 2099 if (control == 0) { 2100 (void) emlxs_mb_read_la(hba, mbox); 2101 } 2102 break; 2103 } 2104 2105 mbox->mbxOwner = OWN_HOST; 2106 mbox->mbxStatus = 0; 2107 2108 /* Refresh the mailbox area */ 2109 emlxs_mb_retry(hba, mbox); 2110 2111 if (emlxs_mb_issue_cmd(hba, mbox, MBX_NOWAIT, 0) != 2112 MBX_BUSY) { 2113 (void) emlxs_mem_put(hba, MEM_MBOX, 2114 (uint8_t *)mbox); 2115 } 2116 return (0); 2117 } 2118 } 2119 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_completion_error_msg, 2120 "%s: status=0x%x", emlxs_mb_cmd_xlate(mb->mbxCommand), 2121 (uint32_t)mb->mbxStatus); 2122 2123 /* 2124 * ERROR: process mailbox command error 2125 */ 2126 switch (mb->mbxCommand) { 2127 case MBX_REG_LOGIN: 2128 case MBX_REG_LOGIN64: 2129 2130 if (mb->mbxStatus == MBXERR_RPI_FULL) { 2131#ifdef SLI3_SUPPORT 2132 port = &VPORT(mb->un.varRegLogin.vpi); 2133#endif /* SLI3_SUPPORT */ 2134 2135 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_node_create_failed_msg, 2136 "Limit reached. count=%d", port->node_count); 2137 } 2138#ifdef NPIV_SUPPORT 2139 /* Special handle for vport PLOGI */ 2140 if (hba->mbox_iocbq == (uint8_t *)1) { 2141 hba->mbox_iocbq = NULL; 2142 } 2143#endif /* NPIV_SUPPORT */ 2144 break; 2145 2146 case MBX_READ_LA: 2147 case MBX_READ_LA64: 2148 2149 /* Enable Link Attention interrupts */ 2150 mutex_enter(&EMLXS_PORT_LOCK); 2151 2152 if (!(hba->hc_copy & HC_LAINT_ENA)) { 2153 /* 2154 * hba->hc_copy = READ_CSR_REG(hba, FC_HC_REG(hba, 2155 * hba->csr_addr)); 2156 */ 2157 hba->hc_copy |= HC_LAINT_ENA; 2158 WRITE_CSR_REG(hba, FC_HC_REG(hba, hba->csr_addr), 2159 hba->hc_copy); 2160 } 2161 mutex_exit(&EMLXS_PORT_LOCK); 2162 2163 break; 2164 2165 2166 case MBX_CLEAR_LA: 2167 2168 la_enable = 1; 2169 2170 if (mb->mbxStatus == 0x1601) { 2171 /* 2172 * Get a buffer which will be used for mailbox 2173 * commands 2174 */ 2175 if ((mbox = (MAILBOX *) emlxs_mem_get(hba, MEM_MBOX | 2176 MEM_PRI))) { 2177 /* Get link attention message */ 2178 if (emlxs_mb_read_la(hba, mbox) == 0) { 2179 if (emlxs_mb_issue_cmd(hba, mbox, 2180 MBX_NOWAIT, 0) != MBX_BUSY) { 2181 (void) emlxs_mem_put(hba, 2182 MEM_MBOX, (uint8_t *)mbox); 2183 } 2184 la_enable = 0; 2185 } else { 2186 (void) emlxs_mem_put(hba, MEM_MBOX, 2187 (uint8_t *)mbox); 2188 } 2189 } 2190 } 2191 mutex_enter(&EMLXS_PORT_LOCK); 2192 if (la_enable) { 2193 if (!(hba->hc_copy & HC_LAINT_ENA)) { 2194 /* Enable Link Attention interrupts */ 2195 /* 2196 * hba->hc_copy = READ_CSR_REG(hba, 2197 * FC_HC_REG(hba, hba->csr_addr)); 2198 */ 2199 hba->hc_copy |= HC_LAINT_ENA; 2200 WRITE_CSR_REG(hba, 2201 FC_HC_REG(hba, hba->csr_addr), 2202 hba->hc_copy); 2203 } 2204 } else { 2205 if (hba->hc_copy & HC_LAINT_ENA) { 2206 /* Disable Link Attention interrupts */ 2207 /* 2208 * hba->hc_copy = READ_CSR_REG(hba, 2209 * FC_HC_REG(hba, hba->csr_addr)); 2210 */ 2211 hba->hc_copy &= ~HC_LAINT_ENA; 2212 WRITE_CSR_REG(hba, 2213 FC_HC_REG(hba, hba->csr_addr), 2214 hba->hc_copy); 2215 } 2216 } 2217 mutex_exit(&EMLXS_PORT_LOCK); 2218 2219 break; 2220 2221 case MBX_INIT_LINK: 2222 if ((hba->flag & FC_SLIM2_MODE) && 2223 (hba->mbox_queue_flag == MBX_NOWAIT)) { 2224 /* Retry only MBX_NOWAIT requests */ 2225 2226 if ((cfg[CFG_LINK_SPEED].current > 0) && 2227 ((mb->mbxStatus == 0x0011) || 2228 (mb->mbxStatus == 0x0500))) { 2229 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_event_msg, 2230 "Retrying. %s: status=%x. Auto-speed set.", 2231 emlxs_mb_cmd_xlate(mb->mbxCommand), 2232 (uint32_t)mb->mbxStatus); 2233 2234 if ((mbox = (MAILBOX *) emlxs_mem_get(hba, 2235 MEM_MBOX))) { 2236 bcopy((uint8_t *)mb, (uint8_t *)mbox, 2237 MAILBOX_CMD_BSIZE); 2238 2239 mbox->un.varInitLnk.link_flags &= 2240 ~FLAGS_LINK_SPEED; 2241 mbox->un.varInitLnk.link_speed = 0; 2242 mbox->mbxOwner = OWN_HOST; 2243 mbox->mbxStatus = 0; 2244 2245 /* Refresh the mailbox area */ 2246 emlxs_mb_retry(hba, mbox); 2247 2248 if (emlxs_mb_issue_cmd(hba, mbox, 2249 MBX_NOWAIT, 0) != MBX_BUSY) { 2250 (void) emlxs_mem_put(hba, 2251 MEM_MBOX, (uint8_t *)mbox); 2252 } 2253 return (0); 2254 } 2255 } 2256 } 2257 break; 2258 } 2259 2260done: 2261 2262 /* Clean up the mailbox area */ 2263 emlxs_mb_fini(hba, mb, mb->mbxStatus); 2264 2265 /* Attempt to send pending mailboxes */ 2266 if ((mbox = (MAILBOX *) emlxs_mb_get(hba))) { 2267 if (emlxs_mb_issue_cmd(hba, mbox, MBX_NOWAIT, 0) != MBX_BUSY) { 2268 (void) emlxs_mem_put(hba, MEM_MBOX, (uint8_t *)mbox); 2269 } 2270 } 2271 return (0); 2272 2273} /* emlxs_handle_mb_event() */ 2274 2275 2276 2277/* 2278 * emlxs_mb_handle_cmd 2279 * 2280 * Description: Process a Mailbox Command. 2281 * Called from host_interrupt to process MBATT 2282 * 2283 * Returns: 2284 * 2285 */ 2286static int 2287emlxs_mb_handle_cmd(emlxs_hba_t *hba, MAILBOX *mb) 2288{ 2289 emlxs_port_t *port = &PPORT; 2290 emlxs_port_t *vport; 2291 MAILBOXQ *mbox; 2292 NODELIST *ndlp; 2293 volatile SERV_PARM *sp; 2294 int32_t i; 2295 uint32_t ldata; 2296 uint32_t ldid; 2297 uint16_t lrpi; 2298 uint16_t lvpi; 2299 MATCHMAP *mp; 2300 uint8_t *wwn; 2301 READ_LA_VAR la; 2302 2303 if (mb->mbxStatus != 0) { 2304 return (1); 2305 } 2306 mp = (MATCHMAP *) hba->mbox_bp; 2307 2308 /* 2309 * Mailbox command completed successfully, process completion 2310 */ 2311 switch (mb->mbxCommand) { 2312 case MBX_SHUTDOWN: 2313 case MBX_LOAD_SM: 2314 case MBX_READ_NV: 2315 case MBX_WRITE_NV: 2316 case MBX_RUN_BIU_DIAG: 2317 case MBX_RUN_BIU_DIAG64: 2318 case MBX_INIT_LINK: 2319 case MBX_DOWN_LINK: 2320 case MBX_CONFIG_LINK: 2321 case MBX_PART_SLIM: 2322 case MBX_CONFIG_RING: 2323 case MBX_RESET_RING: 2324 case MBX_READ_CONFIG: 2325 case MBX_READ_RCONFIG: 2326 case MBX_READ_STATUS: 2327 case MBX_READ_XRI: 2328 case MBX_READ_REV: 2329 case MBX_READ_LNK_STAT: 2330 case MBX_UNREG_LOGIN: 2331 case MBX_DUMP_MEMORY: 2332 case MBX_DUMP_CONTEXT: 2333 case MBX_RUN_DIAGS: 2334 case MBX_RESTART: 2335 case MBX_UPDATE_CFG: 2336 case MBX_DOWN_LOAD: 2337 case MBX_DEL_LD_ENTRY: 2338 case MBX_RUN_PROGRAM: 2339 case MBX_SET_MASK: 2340 case MBX_SET_VARIABLE: 2341 case MBX_UNREG_D_ID: 2342 case MBX_KILL_BOARD: 2343 case MBX_CONFIG_FARP: 2344 case MBX_LOAD_AREA: 2345 case MBX_CONFIG_PORT: 2346 case MBX_CONFIG_MSI: 2347 case MBX_FLASH_WR_ULA: 2348 case MBX_SET_DEBUG: 2349 case MBX_GET_DEBUG: 2350 case MBX_LOAD_EXP_ROM: 2351 case MBX_BEACON: 2352 case MBX_READ_RPI: 2353 case MBX_READ_RPI64: 2354 case MBX_REG_VPI: 2355 case MBX_UNREG_VPI: 2356 case MBX_CONFIG_HBQ: 2357 case MBX_ASYNC_EVENT: 2358 case MBX_HEARTBEAT: 2359 break; 2360 2361 case MBX_CONFIG_MSIX: 2362 break; 2363 2364 case MBX_READ_SPARM: /* a READ SPARAM command completed */ 2365 case MBX_READ_SPARM64: /* a READ SPARAM command completed */ 2366 { 2367 if (mp) { 2368 bcopy((caddr_t)mp->virt, (caddr_t)& hba->sparam, 2369 sizeof (SERV_PARM)); 2370 2371 bcopy((caddr_t)& hba->sparam.nodeName, 2372 (caddr_t)& hba->wwnn, 2373 sizeof (NAME_TYPE)); 2374 2375 bcopy((caddr_t)& hba->sparam.portName, 2376 (caddr_t)& hba->wwpn, 2377 sizeof (NAME_TYPE)); 2378 2379 /* Initialize the physical port */ 2380 bcopy((caddr_t)& hba->sparam, 2381 (caddr_t)& port->sparam, 2382 sizeof (SERV_PARM)); 2383 bcopy((caddr_t)& hba->wwpn, 2384 (caddr_t)& port->wwpn, sizeof (NAME_TYPE)); 2385 bcopy((caddr_t)& hba->wwnn, 2386 (caddr_t)& port->wwnn, sizeof (NAME_TYPE)); 2387 2388 /* Initialize the virtual ports */ 2389 for (i = 1; i < MAX_VPORTS; i++) { 2390 vport = &VPORT(i); 2391 if (vport->flag & EMLXS_PORT_BOUND) { 2392 continue; 2393 } 2394 bcopy((caddr_t)& hba->sparam, 2395 (caddr_t)& vport->sparam, 2396 sizeof (SERV_PARM)); 2397 2398 bcopy((caddr_t)& vport->wwnn, 2399 (caddr_t)& vport->sparam.nodeName, 2400 sizeof (NAME_TYPE)); 2401 2402 bcopy((caddr_t)& vport->wwpn, 2403 (caddr_t)& vport->sparam.portName, 2404 sizeof (NAME_TYPE)); 2405 } 2406 2407 } 2408 break; 2409 } 2410 2411 2412 case MBX_REG_LOGIN: 2413 case MBX_REG_LOGIN64: 2414 2415 if (!mp) { 2416 break; 2417 } 2418#ifdef SLI3_SUPPORT 2419 ldata = mb->un.varWords[5]; 2420 lvpi = ldata & 0xffff; 2421 port = &VPORT(lvpi); 2422#endif /* SLI3_SUPPORT */ 2423 2424 /* First copy command data */ 2425 ldata = mb->un.varWords[0]; /* get rpi */ 2426 lrpi = ldata & 0xffff; 2427 2428 ldata = mb->un.varWords[1]; /* get did */ 2429 ldid = ldata & Mask_DID; 2430 2431 sp = (volatile SERV_PARM *) mp->virt; 2432 ndlp = emlxs_node_find_did(port, ldid); 2433 2434 if (!ndlp) { 2435 /* Attempt to create a node */ 2436 if ((ndlp = (NODELIST *) emlxs_mem_get(hba, MEM_NLP))) { 2437 ndlp->nlp_Rpi = lrpi; 2438 ndlp->nlp_DID = ldid; 2439 2440 bcopy((uint8_t *)sp, 2441 (uint8_t *)& ndlp->sparm, 2442 sizeof (SERV_PARM)); 2443 2444 bcopy((uint8_t *)& sp->nodeName, 2445 (uint8_t *)& ndlp->nlp_nodename, 2446 sizeof (NAME_TYPE)); 2447 2448 bcopy((uint8_t *)& sp->portName, 2449 (uint8_t *)& ndlp->nlp_portname, 2450 sizeof (NAME_TYPE)); 2451 2452 ndlp->nlp_active = 1; 2453 ndlp->nlp_flag[FC_CT_RING] |= NLP_CLOSED; 2454 ndlp->nlp_flag[FC_ELS_RING] |= NLP_CLOSED; 2455 ndlp->nlp_flag[FC_FCP_RING] |= NLP_CLOSED; 2456 ndlp->nlp_flag[FC_IP_RING] |= NLP_CLOSED; 2457 2458 /* Add the node */ 2459 emlxs_node_add(port, ndlp); 2460 2461 /* Open the node */ 2462 emlxs_node_open(port, ndlp, FC_CT_RING); 2463 emlxs_node_open(port, ndlp, FC_ELS_RING); 2464 emlxs_node_open(port, ndlp, FC_IP_RING); 2465 emlxs_node_open(port, ndlp, FC_FCP_RING); 2466 } else { 2467 wwn = (uint8_t *)& sp->portName; 2468 EMLXS_MSGF(EMLXS_CONTEXT, 2469 &emlxs_node_create_failed_msg, 2470 "Unable to allocate node. did=%06x rpi=%x " 2471 "wwpn=%02x%02x%02x%02x%02x%02x%02x%02x", 2472 ldid, lrpi, wwn[0], wwn[1], wwn[2], wwn[3], 2473 wwn[4], wwn[5], wwn[6], wwn[7]); 2474 2475 break; 2476 } 2477 } else { 2478 mutex_enter(&EMLXS_PORT_LOCK); 2479 2480 ndlp->nlp_Rpi = lrpi; 2481 ndlp->nlp_DID = ldid; 2482 2483 bcopy((uint8_t *)sp, 2484 (uint8_t *)& ndlp->sparm, 2485 sizeof (SERV_PARM)); 2486 2487 bcopy((uint8_t *)& sp->nodeName, 2488 (uint8_t *)& ndlp->nlp_nodename, 2489 sizeof (NAME_TYPE)); 2490 2491 bcopy((uint8_t *)& sp->portName, 2492 (uint8_t *)& ndlp->nlp_portname, 2493 sizeof (NAME_TYPE)); 2494 2495 wwn = (uint8_t *)& ndlp->nlp_portname; 2496 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_node_update_msg, 2497 "node=%p did=%06x rpi=%x wwpn=" 2498 "%02x%02x%02x%02x%02x%02x%02x%02x", 2499 ndlp, ndlp->nlp_DID, ndlp->nlp_Rpi, wwn[0], wwn[1], 2500 wwn[2], wwn[3], wwn[4], wwn[5], wwn[6], wwn[7]); 2501 2502 mutex_exit(&EMLXS_PORT_LOCK); 2503 2504 /* Open the node */ 2505 emlxs_node_open(port, ndlp, FC_CT_RING); 2506 emlxs_node_open(port, ndlp, FC_ELS_RING); 2507 emlxs_node_open(port, ndlp, FC_IP_RING); 2508 emlxs_node_open(port, ndlp, FC_FCP_RING); 2509 } 2510 2511 /* If this was a fabric login */ 2512 if (ndlp->nlp_DID == Fabric_DID) { 2513 /* 2514 * If CLEAR_LA has been sent, then attempt to 2515 * register the vpi now 2516 */ 2517 if (hba->state == FC_READY) { 2518 (void) emlxs_mb_reg_vpi(port); 2519 } 2520#ifdef SLI3_SUPPORT 2521 /* 2522 * If NPIV Fabric support has just been established 2523 * on the physical port, then notify the vports of 2524 * the link up 2525 */ 2526 if ((lvpi == 0) && 2527 (hba->flag & FC_NPIV_ENABLED) && 2528 (hba->flag & FC_NPIV_SUPPORTED)) { 2529 /* Skip the physical port */ 2530 for (i = 1; i < MAX_VPORTS; i++) { 2531 vport = &VPORT(i); 2532 2533 if (!(vport->flag & EMLXS_PORT_BOUND) || 2534 !(vport->flag & 2535 EMLXS_PORT_ENABLE)) { 2536 continue; 2537 } 2538 emlxs_port_online(vport); 2539 } 2540 } 2541#endif /* SLI3_SUPPORT */ 2542 2543 } 2544#ifdef NPIV_SUPPORT 2545 if (hba->mbox_iocbq == (uint8_t *)1) { 2546 hba->mbox_iocbq = NULL; 2547 (void) emlxs_mb_unreg_did(port, ldid, NULL, NULL, NULL); 2548 } 2549#endif /* NPIV_SUPPORT */ 2550 2551#ifdef DHCHAP_SUPPORT 2552 if (hba->mbox_sbp || hba->mbox_ubp) { 2553 if (emlxs_dhc_auth_start(port, ndlp, hba->mbox_sbp, 2554 hba->mbox_ubp) == 0) { 2555 /* 2556 * Auth started - auth completion will handle 2557 * sbp and ubp now 2558 */ 2559 hba->mbox_sbp = NULL; 2560 hba->mbox_ubp = NULL; 2561 } 2562 } 2563#endif /* DHCHAP_SUPPORT */ 2564 2565#ifdef SFCT_SUPPORT 2566 if (hba->mbox_sbp && ((emlxs_buf_t *)hba->mbox_sbp)->fct_cmd) { 2567 emlxs_buf_t *cmd_sbp = (emlxs_buf_t *)hba->mbox_sbp; 2568 2569 if (cmd_sbp->fct_state == EMLXS_FCT_REG_PENDING) { 2570 hba->mbox_sbp = NULL; 2571 2572 mutex_enter(&EMLXS_PKT_LOCK); 2573 cmd_sbp->node = ndlp; 2574 cmd_sbp->fct_state = EMLXS_FCT_REG_COMPLETE; 2575 cv_broadcast(&EMLXS_PKT_CV); 2576 mutex_exit(&EMLXS_PKT_LOCK); 2577 } 2578 } 2579#endif /* SFCT_SUPPORT */ 2580 2581 break; 2582 2583 case MBX_READ_LA: 2584 case MBX_READ_LA64: 2585 bcopy((uint32_t *)((char *)mb + sizeof (uint32_t)), 2586 (uint32_t *)& la, sizeof (READ_LA_VAR)); 2587 2588 if (mp) { 2589 bcopy((caddr_t)mp->virt, 2590 (caddr_t)port->alpa_map, 128); 2591 } else { 2592 bzero((caddr_t)port->alpa_map, 128); 2593 } 2594 2595 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_link_atten_msg, 2596 "type=%s tag=%d -> %d ALPA=%x", 2597 ((la.attType == AT_LINK_UP) ? 2598 "LinkUp" : "LinkDown"), 2599 (uint32_t)hba->link_event_tag, 2600 (uint32_t)la.eventTag, (uint32_t)la.granted_AL_PA); 2601 2602 if (la.pb) { 2603 hba->flag |= FC_BYPASSED_MODE; 2604 } else { 2605 hba->flag &= ~FC_BYPASSED_MODE; 2606 } 2607 2608 if (hba->link_event_tag == la.eventTag) { 2609 HBASTATS.LinkMultiEvent++; 2610 } else if (hba->link_event_tag + 1 < la.eventTag) { 2611 HBASTATS.LinkMultiEvent++; 2612 2613 if (hba->state > FC_LINK_DOWN) { 2614 /* Declare link down here */ 2615 emlxs_linkdown(hba); 2616 } 2617 } 2618 hba->link_event_tag = la.eventTag; 2619 port->lip_type = 0; 2620 2621 /* If link not already up then declare it up now */ 2622 if ((la.attType == AT_LINK_UP) && 2623 (hba->state < FC_LINK_UP)) { 2624 2625 /* Save the linkspeed */ 2626 hba->linkspeed = la.UlnkSpeed; 2627 2628 /* 2629 * Check for old model adapters that only 2630 * supported 1Gb 2631 */ 2632 if ((hba->linkspeed == 0) && 2633 (hba->model_info.chip & 2634 EMLXS_DRAGONFLY_CHIP)) { 2635 hba->linkspeed = LA_1GHZ_LINK; 2636 } 2637 if ((hba->topology = la.topology) == 2638 TOPOLOGY_LOOP) { 2639 port->did = la.granted_AL_PA; 2640 port->lip_type = la.lipType; 2641 2642 if (hba->flag & FC_SLIM2_MODE) { 2643 i = la.un.lilpBde64.tus.f. 2644 bdeSize; 2645 } else { 2646 i = la.un.lilpBde.bdeSize; 2647 } 2648 2649 if (i == 0) { 2650 port->alpa_map[0] = 0; 2651 } else { 2652 uint8_t *alpa_map; 2653 uint32_t j; 2654 2655 /* 2656 * Check number of devices in 2657 * map 2658 */ 2659 if (port->alpa_map[0] > 127) { 2660 port->alpa_map[0] = 127; 2661 } 2662 alpa_map = (uint8_t *)port->alpa_map; 2663 2664 EMLXS_MSGF(EMLXS_CONTEXT, 2665 &emlxs_link_atten_msg, 2666 "alpa_map: %d device(s): %02x " 2667 "%02x %02x %02x %02x %02x %02x", 2668 alpa_map[0], alpa_map[1], 2669 alpa_map[2], alpa_map[3], 2670 alpa_map[4], alpa_map[5], 2671 alpa_map[6], alpa_map[7]); 2672 2673 for (j = 8; j <= alpa_map[0]; j += 8) { 2674 EMLXS_MSGF(EMLXS_CONTEXT, 2675 &emlxs_link_atten_msg, 2676 "alpa_map: %02x %02x %02x " 2677 "%02x %02x %02x %02x %02x", 2678 alpa_map[j], 2679 alpa_map[j + 1], 2680 alpa_map[j + 2], 2681 alpa_map[j + 3], 2682 alpa_map[j + 4], 2683 alpa_map[j + 5], 2684 alpa_map[j + 6], 2685 alpa_map[j + 7]); 2686 } 2687 } 2688 } 2689#ifdef MENLO_SUPPORT 2690 /* Check if Menlo maintenance mode is enabled */ 2691 if (hba->model_info.device_id == 2692 PCI_DEVICE_ID_LP21000_M) { 2693 if (la.mm == 1) { 2694 EMLXS_MSGF(EMLXS_CONTEXT, 2695 &emlxs_link_atten_msg, 2696 "Maintenance Mode enabled."); 2697 2698 mutex_enter(&EMLXS_PORT_LOCK); 2699 hba->flag |= FC_MENLO_MODE; 2700 mutex_exit(&EMLXS_PORT_LOCK); 2701 2702 mutex_enter(&EMLXS_LINKUP_LOCK); 2703 cv_broadcast(&EMLXS_LINKUP_CV); 2704 mutex_exit(&EMLXS_LINKUP_LOCK); 2705 } else { 2706 EMLXS_MSGF(EMLXS_CONTEXT, 2707 &emlxs_link_atten_msg, 2708 "Maintenance Mode disabled."); 2709 } 2710 2711 /* Check FCoE attention bit */ 2712 if (la.fa == 1) { 2713 (void) thread_create(NULL, 0, 2714 emlxs_fcoe_attention_thread, 2715 (char *)hba, 0, 2716 &p0, TS_RUN, 2717 v.v_maxsyspri - 2); 2718 } 2719 } 2720#endif /* MENLO_SUPPORT */ 2721 2722 if ((mbox = (MAILBOXQ *) emlxs_mem_get(hba, 2723 MEM_MBOX | MEM_PRI))) { 2724 /* 2725 * This should turn on DELAYED ABTS 2726 * for ELS timeouts 2727 */ 2728 emlxs_mb_set_var(hba, (MAILBOX *) mbox, 2729 0x00052198, 0x1); 2730 2731 emlxs_mb_put(hba, mbox); 2732 } 2733 if ((mbox = (MAILBOXQ *) emlxs_mem_get(hba, 2734 MEM_MBOX | MEM_PRI))) { 2735 /* 2736 * If link not already down then 2737 * declare it down now 2738 */ 2739 if (emlxs_mb_read_sparam(hba, 2740 (MAILBOX *) mbox) == 0) { 2741 emlxs_mb_put(hba, mbox); 2742 } else { 2743 (void) emlxs_mem_put(hba, MEM_MBOX, 2744 (uint8_t *)mbox); 2745 } 2746 } 2747 if ((mbox = (MAILBOXQ *) emlxs_mem_get(hba, 2748 MEM_MBOX | MEM_PRI))) { 2749 emlxs_mb_config_link(hba, 2750 (MAILBOX *) mbox); 2751 2752 emlxs_mb_put(hba, mbox); 2753 } 2754 /* Declare the linkup here */ 2755 emlxs_linkup(hba); 2756 } 2757 /* If link not already down then declare it down now */ 2758 else if ((la.attType == AT_LINK_DOWN) && 2759 (hba->state > FC_LINK_DOWN)) { 2760 /* Declare link down here */ 2761 emlxs_linkdown(hba); 2762 } 2763 /* Enable Link attention interrupt */ 2764 mutex_enter(&EMLXS_PORT_LOCK); 2765 2766 if (!(hba->hc_copy & HC_LAINT_ENA)) { 2767 /* 2768 * hba->hc_copy = READ_CSR_REG(hba, 2769 * FC_HC_REG(hba, hba->csr_addr)); 2770 */ 2771 hba->hc_copy |= HC_LAINT_ENA; 2772 WRITE_CSR_REG(hba, FC_HC_REG(hba, 2773 hba->csr_addr), hba->hc_copy); 2774 } 2775 mutex_exit(&EMLXS_PORT_LOCK); 2776 2777 /* Log the link event */ 2778 emlxs_log_link_event(port); 2779 2780 break; 2781 2782 case MBX_CLEAR_LA: 2783 /* Enable on Link Attention interrupts */ 2784 mutex_enter(&EMLXS_PORT_LOCK); 2785 2786 if (!(hba->hc_copy & HC_LAINT_ENA)) { 2787 /* 2788 * hba->hc_copy = READ_CSR_REG(hba, FC_HC_REG(hba, 2789 * hba->csr_addr)); 2790 */ 2791 hba->hc_copy |= HC_LAINT_ENA; 2792 WRITE_CSR_REG(hba, FC_HC_REG(hba, hba->csr_addr), 2793 hba->hc_copy); 2794 } 2795 if (hba->state >= FC_LINK_UP) { 2796 emlxs_ffstate_change_locked(hba, FC_READY); 2797 } 2798 mutex_exit(&EMLXS_PORT_LOCK); 2799 2800 /* Adapter is now ready for FCP traffic */ 2801 if (hba->state == FC_READY) { 2802 /* Register vpi's for all ports that have did's */ 2803 for (i = 0; i < MAX_VPORTS; i++) { 2804 vport = &VPORT(i); 2805 2806 if (!(vport->flag & EMLXS_PORT_BOUND) || 2807 !(vport->did)) { 2808 continue; 2809 } 2810 (void) emlxs_mb_reg_vpi(vport); 2811 } 2812 2813 /* Attempt to send any pending IO */ 2814 emlxs_issue_iocb_cmd(hba, &hba->ring[FC_FCP_RING], 0); 2815 } 2816 break; 2817 2818 default: 2819 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_completion_error_msg, 2820 "Unknown mailbox cmd: 0x%x", mb->mbxCommand); 2821 HBASTATS.MboxInvalid++; 2822 break; 2823 } 2824 2825 return (0); 2826 2827} /* emlxs_mb_handle_cmd() */ 2828 2829 2830/* MBX_NOWAIT - returns MBX_BUSY or MBX_SUCCESS or MBX_HARDWARE_ERROR */ 2831/* MBX_WAIT - returns MBX_TIMEOUT or mailbox_status */ 2832/* MBX_SLEEP - returns MBX_TIMEOUT or mailbox_status */ 2833/* MBX_POLL - returns MBX_TIMEOUT or mailbox_status */ 2834 2835extern uint32_t 2836emlxs_mb_issue_cmd(emlxs_hba_t *hba, MAILBOX *mb, int32_t flag, uint32_t tmo) 2837{ 2838 emlxs_port_t *port = &PPORT; 2839 MAILBOX *mbox; 2840 MAILBOXQ *mbq; 2841 volatile uint32_t word0; 2842 volatile uint32_t ldata; 2843 uint32_t ha_copy; 2844 off_t offset; 2845 MATCHMAP *mbox_bp; 2846 uint32_t tmo_local; 2847 MAILBOX *swpmb; 2848 2849 mbq = (MAILBOXQ *) mb; 2850 swpmb = (MAILBOX *) & word0; 2851 2852 mb->mbxStatus = MBX_SUCCESS; 2853 2854 /* Check for minimum timeouts */ 2855 switch (mb->mbxCommand) { 2856 /* Mailbox commands that erase/write flash */ 2857 case MBX_DOWN_LOAD: 2858 case MBX_UPDATE_CFG: 2859 case MBX_LOAD_AREA: 2860 case MBX_LOAD_EXP_ROM: 2861 case MBX_WRITE_NV: 2862 case MBX_FLASH_WR_ULA: 2863 case MBX_DEL_LD_ENTRY: 2864 case MBX_LOAD_SM: 2865 if (tmo < 300) { 2866 tmo = 300; 2867 } 2868 break; 2869 2870 default: 2871 if (tmo < 30) { 2872 tmo = 30; 2873 } 2874 break; 2875 } 2876 2877 /* Adjust wait flag */ 2878 if (flag != MBX_NOWAIT) { 2879 /* If interrupt is enabled, use sleep, otherwise poll */ 2880 if (hba->hc_copy & HC_MBINT_ENA) { 2881 flag = MBX_SLEEP; 2882 } else { 2883 flag = MBX_POLL; 2884 } 2885 } 2886 mutex_enter(&EMLXS_PORT_LOCK); 2887 2888 /* Check for hardware error */ 2889 if (hba->flag & FC_HARDWARE_ERROR) { 2890 mb->mbxStatus = (hba->flag & FC_OVERTEMP_EVENT) ? 2891 MBX_OVERTEMP_ERROR : MBX_HARDWARE_ERROR; 2892 2893 mutex_exit(&EMLXS_PORT_LOCK); 2894 2895 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_detail_msg, 2896 "Hardware error reported. %s failed. status=%x mb=%p", 2897 emlxs_mb_cmd_xlate(mb->mbxCommand), mb->mbxStatus, mb); 2898 2899 return (MBX_HARDWARE_ERROR); 2900 } 2901 if (hba->mbox_queue_flag) { 2902 /* If we are not polling, then queue it for later */ 2903 if (flag == MBX_NOWAIT) { 2904 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_detail_msg, 2905 "Busy. %s: mb=%p NoWait.", 2906 emlxs_mb_cmd_xlate(mb->mbxCommand), mb); 2907 2908 emlxs_mb_put(hba, mbq); 2909 2910 HBASTATS.MboxBusy++; 2911 2912 mutex_exit(&EMLXS_PORT_LOCK); 2913 2914 return (MBX_BUSY); 2915 } 2916 tmo_local = tmo * 20; /* Convert tmo seconds to 50 */ 2917 /* millisecond tics */ 2918 while (hba->mbox_queue_flag) { 2919 mutex_exit(&EMLXS_PORT_LOCK); 2920 2921 if (tmo_local-- == 0) { 2922 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_event_msg, 2923 "Timeout. %s: mb=%p tmo=%d Waiting.", 2924 emlxs_mb_cmd_xlate(mb->mbxCommand), mb, 2925 tmo); 2926 2927 /* Non-lethalStatus mailbox timeout */ 2928 /* Does not indicate a hardware error */ 2929 mb->mbxStatus = MBX_TIMEOUT; 2930 return (MBX_TIMEOUT); 2931 } 2932 DELAYMS(50); 2933 mutex_enter(&EMLXS_PORT_LOCK); 2934 } 2935 } 2936 /* Initialize mailbox area */ 2937 emlxs_mb_init(hba, mbq, flag, tmo); 2938 2939 switch (flag) { 2940 case MBX_NOWAIT: 2941 2942 if (mb->mbxCommand != MBX_HEARTBEAT) { 2943 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_detail_msg, 2944 "Sending. %s: mb=%p NoWait.", 2945 emlxs_mb_cmd_xlate(mb->mbxCommand), mb); 2946 } 2947 break; 2948 2949 case MBX_SLEEP: 2950 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_detail_msg, 2951 "Sending. %s: mb=%p Sleep.", 2952 emlxs_mb_cmd_xlate(mb->mbxCommand), mb); 2953 2954 break; 2955 2956 case MBX_POLL: 2957 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_detail_msg, 2958 "Sending. %s: mb=%p Polled.", 2959 emlxs_mb_cmd_xlate(mb->mbxCommand), mb); 2960 break; 2961 } 2962 2963 mb->mbxOwner = OWN_CHIP; 2964 2965 /* Clear the attention bit */ 2966 WRITE_CSR_REG(hba, FC_HA_REG(hba, hba->csr_addr), HA_MBATT); 2967 2968 if (hba->flag & FC_SLIM2_MODE) { 2969 /* First copy command data */ 2970 mbox = FC_SLIM2_MAILBOX(hba); 2971 offset = (off_t)((uint64_t)(unsigned long)mbox - 2972 (uint64_t)(unsigned long)hba->slim2.virt); 2973 2974#ifdef MBOX_EXT_SUPPORT 2975 if (hba->mbox_ext) { 2976 uint32_t *mbox_ext = (uint32_t *)((uint8_t *)mbox + 2977 MBOX_EXTENSION_OFFSET); 2978 off_t offset_ext = offset + MBOX_EXTENSION_OFFSET; 2979 2980 emlxs_pcimem_bcopy((uint32_t *)hba->mbox_ext, mbox_ext, 2981 hba->mbox_ext_size); 2982 emlxs_mpdata_sync(hba->slim2.dma_handle, offset_ext, 2983 hba->mbox_ext_size, DDI_DMA_SYNC_FORDEV); 2984 } 2985#endif /* MBOX_EXT_SUPPORT */ 2986 2987 emlxs_pcimem_bcopy((uint32_t *)mb, (uint32_t *)mbox, 2988 MAILBOX_CMD_BSIZE); 2989 emlxs_mpdata_sync(hba->slim2.dma_handle, offset, 2990 MAILBOX_CMD_BSIZE, DDI_DMA_SYNC_FORDEV); 2991 } 2992 /* Check for config port command */ 2993 else if (mb->mbxCommand == MBX_CONFIG_PORT) { 2994 /* copy command data into host mbox for cmpl */ 2995 mbox = FC_SLIM2_MAILBOX(hba); 2996 offset = (off_t)((uint64_t)(unsigned long)mbox - 2997 (uint64_t)(unsigned long)hba->slim2.virt); 2998 2999 emlxs_pcimem_bcopy((uint32_t *)mb, (uint32_t *)mbox, 3000 MAILBOX_CMD_BSIZE); 3001 emlxs_mpdata_sync(hba->slim2.dma_handle, offset, 3002 MAILBOX_CMD_BSIZE, DDI_DMA_SYNC_FORDEV); 3003 3004 /* First copy command data */ 3005 mbox = FC_SLIM1_MAILBOX(hba); 3006 WRITE_SLIM_COPY(hba, &mb->un.varWords, &mbox->un.varWords, 3007 (MAILBOX_CMD_WSIZE - 1)); 3008 3009 /* copy over last word, with mbxOwner set */ 3010 ldata = *((volatile uint32_t *) mb); 3011 WRITE_SLIM_ADDR(hba, ((volatile uint32_t *) mbox), ldata); 3012 3013 /* switch over to host mailbox */ 3014 /* 3015 * hba->mbox_queueaddr = (uint32_t *)&((SLIM2 *) 3016 * hba->slim2.virt)->mbx; 3017 */ 3018 hba->flag |= FC_SLIM2_MODE; 3019 } else { /* SLIM 1 */ 3020 mbox = FC_SLIM1_MAILBOX(hba); 3021 3022#ifdef MBOX_EXT_SUPPORT 3023 if (hba->mbox_ext) { 3024 uint32_t *mbox_ext = (uint32_t *)((uint8_t *)mbox + 3025 MBOX_EXTENSION_OFFSET); 3026 WRITE_SLIM_COPY(hba, (uint32_t *)hba->mbox_ext, 3027 mbox_ext, (hba->mbox_ext_size / 4)); 3028 } 3029#endif /* MBOX_EXT_SUPPORT */ 3030 3031 /* First copy command data */ 3032 WRITE_SLIM_COPY(hba, &mb->un.varWords, &mbox->un.varWords, 3033 (MAILBOX_CMD_WSIZE - 1)); 3034 3035 /* copy over last word, with mbxOwner set */ 3036 ldata = *((volatile uint32_t *) mb); 3037 WRITE_SLIM_ADDR(hba, ((volatile uint32_t *) mbox), ldata); 3038 } 3039 3040 /* Interrupt board to do it right away */ 3041 WRITE_CSR_REG(hba, FC_CA_REG(hba, hba->csr_addr), CA_MBATT); 3042 3043 mutex_exit(&EMLXS_PORT_LOCK); 3044 3045 switch (flag) { 3046 case MBX_NOWAIT: 3047 return (MBX_SUCCESS); 3048 3049 case MBX_SLEEP: 3050 3051 /* Wait for completion */ 3052 /* The driver clock is timing the mailbox. */ 3053 /* emlxs_mb_fini() will be called externally. */ 3054 3055 mutex_enter(&EMLXS_MBOX_LOCK); 3056 while (!(mbq->flag & MBQ_COMPLETED)) { 3057 cv_wait(&EMLXS_MBOX_CV, &EMLXS_MBOX_LOCK); 3058 } 3059 mutex_exit(&EMLXS_MBOX_LOCK); 3060 3061 if (mb->mbxStatus == MBX_TIMEOUT) { 3062 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_event_msg, 3063 "Timeout. %s: mb=%p tmo=%d. Sleep.", 3064 emlxs_mb_cmd_xlate(mb->mbxCommand), mb, tmo); 3065 } else { 3066 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_detail_msg, 3067 "Completed. %s: mb=%p status=%x Sleep.", 3068 emlxs_mb_cmd_xlate(mb->mbxCommand), mb, 3069 mb->mbxStatus); 3070 } 3071 3072 break; 3073 3074 case MBX_POLL: 3075 3076 tmo_local = tmo * 2000; /* Convert tmo seconds to 500 usec */ 3077 /* tics */ 3078 3079 if (hba->state >= FC_INIT_START) { 3080 ha_copy = READ_CSR_REG(hba, FC_HA_REG(hba, 3081 hba->csr_addr)); 3082 3083 /* Wait for command to complete */ 3084 while (!(ha_copy & HA_MBATT) && 3085 !(mbq->flag & MBQ_COMPLETED)) { 3086 if (!hba->timer_id && (tmo_local-- == 0)) { 3087 /* self time */ 3088 EMLXS_MSGF(EMLXS_CONTEXT, 3089 &emlxs_hardware_error_msg, 3090 "Mailbox Timeout: %s: mb=%p Polled", 3091 emlxs_mb_cmd_xlate(mb->mbxCommand), 3092 mb); 3093 3094 hba->flag |= FC_MBOX_TIMEOUT; 3095 emlxs_ffstate_change(hba, FC_ERROR); 3096 emlxs_mb_fini(hba, NULL, MBX_TIMEOUT); 3097 3098 break; 3099 } 3100 DELAYUS(500); 3101 ha_copy = READ_CSR_REG(hba, 3102 FC_HA_REG(hba, hba->csr_addr)); 3103 } 3104 3105 if (mb->mbxStatus == MBX_TIMEOUT) { 3106 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_event_msg, 3107 "Timeout. %s: mb=%p tmo=%d. Polled.", 3108 emlxs_mb_cmd_xlate(mb->mbxCommand), mb, 3109 tmo); 3110 3111 break; 3112 } 3113 } 3114 /* Get first word of mailbox */ 3115 if (hba->flag & FC_SLIM2_MODE) { 3116 mbox = FC_SLIM2_MAILBOX(hba); 3117 offset = (off_t)((uint64_t)(unsigned long)mbox - 3118 (uint64_t)(unsigned long)hba->slim2.virt); 3119 3120 emlxs_mpdata_sync(hba->slim2.dma_handle, offset, 3121 sizeof (uint32_t), DDI_DMA_SYNC_FORKERNEL); 3122 word0 = *((volatile uint32_t *) mbox); 3123 word0 = PCIMEM_LONG(word0); 3124 } else { 3125 mbox = FC_SLIM1_MAILBOX(hba); 3126 word0 = READ_SLIM_ADDR(hba, 3127 ((volatile uint32_t *) mbox)); 3128 } 3129 3130 /* Wait for command to complete */ 3131 while ((swpmb->mbxOwner == OWN_CHIP) && 3132 !(mbq->flag & MBQ_COMPLETED)) { 3133 if (!hba->timer_id && (tmo_local-- == 0)) { 3134 /* self time */ 3135 EMLXS_MSGF(EMLXS_CONTEXT, 3136 &emlxs_hardware_error_msg, 3137 "Mailbox Timeout: %s: mb=%p Polled.", 3138 emlxs_mb_cmd_xlate(mb->mbxCommand), mb); 3139 3140 hba->flag |= FC_MBOX_TIMEOUT; 3141 emlxs_ffstate_change(hba, FC_ERROR); 3142 emlxs_mb_fini(hba, NULL, MBX_TIMEOUT); 3143 3144 break; 3145 } 3146 DELAYUS(500); 3147 3148 /* Get first word of mailbox */ 3149 if (hba->flag & FC_SLIM2_MODE) { 3150 emlxs_mpdata_sync(hba->slim2.dma_handle, offset, 3151 sizeof (uint32_t), DDI_DMA_SYNC_FORKERNEL); 3152 word0 = *((volatile uint32_t *) mbox); 3153 word0 = PCIMEM_LONG(word0); 3154 } else { 3155 word0 = READ_SLIM_ADDR(hba, 3156 ((volatile uint32_t *) mbox)); 3157 } 3158 3159 } /* while */ 3160 3161 if (mb->mbxStatus == MBX_TIMEOUT) { 3162 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_event_msg, 3163 "Timeout. %s: mb=%p tmo=%d. Polled.", 3164 emlxs_mb_cmd_xlate(mb->mbxCommand), mb, tmo); 3165 3166 break; 3167 } 3168 /* copy results back to user */ 3169 if (hba->flag & FC_SLIM2_MODE) { 3170 emlxs_mpdata_sync(hba->slim2.dma_handle, offset, 3171 MAILBOX_CMD_BSIZE, DDI_DMA_SYNC_FORKERNEL); 3172 emlxs_pcimem_bcopy((uint32_t *)mbox, (uint32_t *)mb, 3173 MAILBOX_CMD_BSIZE); 3174 } else { 3175 READ_SLIM_COPY(hba, (uint32_t *)mb, (uint32_t *)mbox, 3176 MAILBOX_CMD_WSIZE); 3177 } 3178 3179#ifdef MBOX_EXT_SUPPORT 3180 if (hba->mbox_ext) { 3181 uint32_t *mbox_ext = (uint32_t *)((uint8_t *)mbox + 3182 MBOX_EXTENSION_OFFSET); 3183 off_t offset_ext = offset + MBOX_EXTENSION_OFFSET; 3184 3185 if (hba->flag & FC_SLIM2_MODE) { 3186 emlxs_mpdata_sync(hba->slim2.dma_handle, 3187 offset_ext, hba->mbox_ext_size, 3188 DDI_DMA_SYNC_FORKERNEL); 3189 emlxs_pcimem_bcopy(mbox_ext, 3190 (uint32_t *)hba->mbox_ext, 3191 hba->mbox_ext_size); 3192 } else { 3193 READ_SLIM_COPY(hba, (uint32_t *)hba->mbox_ext, 3194 mbox_ext, (hba->mbox_ext_size / 4)); 3195 } 3196 } 3197#endif /* MBOX_EXT_SUPPORT */ 3198 3199 /* Sync the memory buffer */ 3200 if (hba->mbox_bp) { 3201 mbox_bp = (MATCHMAP *) hba->mbox_bp; 3202 emlxs_mpdata_sync(mbox_bp->dma_handle, 0, mbox_bp->size, 3203 DDI_DMA_SYNC_FORKERNEL); 3204 } 3205 EMLXS_MSGF(EMLXS_CONTEXT, &emlxs_mbox_detail_msg, 3206 "Completed. %s: mb=%p status=%x Polled.", 3207 emlxs_mb_cmd_xlate(mb->mbxCommand), mb, mb->mbxStatus); 3208 3209 /* Process the result */ 3210 if (!(mbq->flag & MBQ_PASSTHRU)) { 3211 (void) emlxs_mb_handle_cmd(hba, mb); 3212 } 3213 /* Clear the attention bit */ 3214 WRITE_CSR_REG(hba, FC_HA_REG(hba, hba->csr_addr), HA_MBATT); 3215 3216 /* Clean up the mailbox area */ 3217 emlxs_mb_fini(hba, NULL, mb->mbxStatus); 3218 3219 break; 3220 3221 } /* switch (flag) */ 3222 3223 return (mb->mbxStatus); 3224 3225} /* emlxs_mb_issue_cmd() */ 3226 3227 3228 | |
3229extern char * 3230emlxs_mb_cmd_xlate(uint8_t cmd) 3231{ | 1686extern char * 1687emlxs_mb_cmd_xlate(uint8_t cmd) 1688{ |
3232 static char buffer[32]; 3233 uint32_t i; 3234 uint32_t count; | 1689 static char buffer[32]; 1690 uint32_t i; 1691 uint32_t count; |
3235 3236 count = sizeof (emlxs_mb_cmd_table) / sizeof (emlxs_table_t); 3237 for (i = 0; i < count; i++) { 3238 if (cmd == emlxs_mb_cmd_table[i].code) { 3239 return (emlxs_mb_cmd_table[i].string); 3240 } 3241 } 3242 3243 (void) sprintf(buffer, "Cmd=0x%x", cmd); 3244 return (buffer); 3245 3246} /* emlxs_mb_cmd_xlate() */ | 1692 1693 count = sizeof (emlxs_mb_cmd_table) / sizeof (emlxs_table_t); 1694 for (i = 0; i < count; i++) { 1695 if (cmd == emlxs_mb_cmd_table[i].code) { 1696 return (emlxs_mb_cmd_table[i].string); 1697 } 1698 } 1699 1700 (void) sprintf(buffer, "Cmd=0x%x", cmd); 1701 return (buffer); 1702 1703} /* emlxs_mb_cmd_xlate() */ |