1 /*- 2 * Copyright (c) 2010-2016 Solarflare Communications Inc. 3 * All rights reserved. 4 * 5 * This software was developed in part by Philip Paeps under contract for 6 * Solarflare Communications, Inc. 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted provided that the following conditions are met: 10 * 11 * 1. Redistributions of source code must retain the above copyright notice, 12 * this list of conditions and the following disclaimer. 13 * 2. Redistributions in binary form must reproduce the above copyright notice, 14 * this list of conditions and the following disclaimer in the documentation 15 * and/or other materials provided with the distribution. 16 * 17 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 18 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, 19 * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 20 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR 21 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 22 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 23 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; 24 * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 25 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR 26 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, 27 * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 28 * 29 * The views and conclusions contained in the software and documentation are 30 * those of the authors and should not be interpreted as representing official 31 * policies, either expressed or implied, of the FreeBSD Project. 32 */ 33 34 #include <sys/cdefs.h> 35 __FBSDID("$FreeBSD$"); 36 37 #include <sys/param.h> 38 #include <sys/kernel.h> 39 #include <sys/malloc.h> 40 #include <sys/param.h> 41 #include <sys/queue.h> 42 #include <sys/systm.h> 43 #include <sys/taskqueue.h> 44 45 #include "common/efx.h" 46 47 #include "sfxge.h" 48 49 static void 50 sfxge_ev_qcomplete(struct sfxge_evq *evq, boolean_t eop) 51 { 52 struct sfxge_softc *sc; 53 unsigned int index; 54 struct sfxge_rxq *rxq; 55 struct sfxge_txq *txq; 56 57 SFXGE_EVQ_LOCK_ASSERT_OWNED(evq); 58 59 sc = evq->sc; 60 index = evq->index; 61 rxq = sc->rxq[index]; 62 63 if ((txq = evq->txq) != NULL) { 64 evq->txq = NULL; 65 evq->txqs = &(evq->txq); 66 67 do { 68 struct sfxge_txq *next; 69 70 next = txq->next; 71 txq->next = NULL; 72 73 KASSERT(txq->evq_index == index, 74 ("txq->evq_index != index")); 75 76 if (txq->pending != txq->completed) 77 sfxge_tx_qcomplete(txq, evq); 78 79 txq = next; 80 } while (txq != NULL); 81 } 82 83 if (rxq->pending != rxq->completed) 84 sfxge_rx_qcomplete(rxq, eop); 85 } 86 87 static struct sfxge_rxq * 88 sfxge_get_rxq_by_label(struct sfxge_evq *evq, uint32_t label) 89 { 90 struct sfxge_rxq *rxq; 91 92 KASSERT(label == 0, ("unexpected rxq label != 0")); 93 94 rxq = evq->sc->rxq[evq->index]; 95 96 KASSERT(rxq != NULL, ("rxq == NULL")); 97 KASSERT(evq->index == rxq->index, ("evq->index != rxq->index")); 98 99 return (rxq); 100 } 101 102 static boolean_t 103 sfxge_ev_rx(void *arg, uint32_t label, uint32_t id, uint32_t size, 104 uint16_t flags) 105 { 106 struct sfxge_evq *evq; 107 struct sfxge_softc *sc; 108 struct sfxge_rxq *rxq; 109 unsigned int stop; 110 unsigned int delta; 111 struct sfxge_rx_sw_desc *rx_desc; 112 113 evq = arg; 114 SFXGE_EVQ_LOCK_ASSERT_OWNED(evq); 115 116 sc = evq->sc; 117 118 if (evq->exception) 119 goto done; 120 121 rxq = sfxge_get_rxq_by_label(evq, label); 122 if (__predict_false(rxq->init_state != SFXGE_RXQ_STARTED)) 123 goto done; 124 125 stop = (id + 1) & rxq->ptr_mask; 126 id = rxq->pending & rxq->ptr_mask; 127 delta = (stop >= id) ? (stop - id) : (rxq->entries - id + stop); 128 rxq->pending += delta; 129 130 if (delta != 1) { 131 if ((delta <= 0) || 132 (delta > efx_nic_cfg_get(sc->enp)->enc_rx_batch_max)) { 133 evq->exception = B_TRUE; 134 135 device_printf(sc->dev, "RX completion out of order" 136 " (id=%#x delta=%u flags=%#x); resetting\n", 137 id, delta, flags); 138 sfxge_schedule_reset(sc); 139 140 goto done; 141 } 142 } 143 144 rx_desc = &rxq->queue[id]; 145 146 prefetch_read_many(rx_desc->mbuf); 147 148 for (; id != stop; id = (id + 1) & rxq->ptr_mask) { 149 rx_desc = &rxq->queue[id]; 150 KASSERT(rx_desc->flags == EFX_DISCARD, 151 ("rx_desc->flags != EFX_DISCARD")); 152 rx_desc->flags = flags; 153 154 KASSERT(size < (1 << 16), ("size > (1 << 16)")); 155 rx_desc->size = (uint16_t)size; 156 } 157 158 evq->rx_done++; 159 160 if (rxq->pending - rxq->completed >= SFXGE_RX_BATCH) 161 sfxge_ev_qcomplete(evq, B_FALSE); 162 163 done: 164 return (evq->rx_done >= SFXGE_EV_BATCH); 165 } 166 167 static boolean_t 168 sfxge_ev_exception(void *arg, uint32_t code, uint32_t data) 169 { 170 struct sfxge_evq *evq; 171 struct sfxge_softc *sc; 172 173 evq = (struct sfxge_evq *)arg; 174 SFXGE_EVQ_LOCK_ASSERT_OWNED(evq); 175 176 sc = evq->sc; 177 178 DBGPRINT(sc->dev, "[%d] %s", evq->index, 179 (code == EFX_EXCEPTION_RX_RECOVERY) ? "RX_RECOVERY" : 180 (code == EFX_EXCEPTION_RX_DSC_ERROR) ? "RX_DSC_ERROR" : 181 (code == EFX_EXCEPTION_TX_DSC_ERROR) ? "TX_DSC_ERROR" : 182 (code == EFX_EXCEPTION_UNKNOWN_SENSOREVT) ? "UNKNOWN_SENSOREVT" : 183 (code == EFX_EXCEPTION_FWALERT_SRAM) ? "FWALERT_SRAM" : 184 (code == EFX_EXCEPTION_UNKNOWN_FWALERT) ? "UNKNOWN_FWALERT" : 185 (code == EFX_EXCEPTION_RX_ERROR) ? "RX_ERROR" : 186 (code == EFX_EXCEPTION_TX_ERROR) ? "TX_ERROR" : 187 (code == EFX_EXCEPTION_EV_ERROR) ? "EV_ERROR" : 188 "UNKNOWN"); 189 190 evq->exception = B_TRUE; 191 192 if (code != EFX_EXCEPTION_UNKNOWN_SENSOREVT) { 193 device_printf(sc->dev, 194 "hardware exception (code=%u); resetting\n", 195 code); 196 sfxge_schedule_reset(sc); 197 } 198 199 return (B_FALSE); 200 } 201 202 static boolean_t 203 sfxge_ev_rxq_flush_done(void *arg, uint32_t rxq_index) 204 { 205 struct sfxge_evq *evq; 206 struct sfxge_softc *sc; 207 struct sfxge_rxq *rxq; 208 unsigned int index; 209 uint16_t magic; 210 211 evq = (struct sfxge_evq *)arg; 212 SFXGE_EVQ_LOCK_ASSERT_OWNED(evq); 213 214 sc = evq->sc; 215 rxq = sc->rxq[rxq_index]; 216 217 KASSERT(rxq != NULL, ("rxq == NULL")); 218 219 /* Resend a software event on the correct queue */ 220 index = rxq->index; 221 if (index == evq->index) { 222 sfxge_rx_qflush_done(rxq); 223 return (B_FALSE); 224 } 225 226 evq = sc->evq[index]; 227 magic = sfxge_sw_ev_rxq_magic(SFXGE_SW_EV_RX_QFLUSH_DONE, rxq); 228 229 KASSERT(evq->init_state == SFXGE_EVQ_STARTED, 230 ("evq not started")); 231 efx_ev_qpost(evq->common, magic); 232 233 return (B_FALSE); 234 } 235 236 static boolean_t 237 sfxge_ev_rxq_flush_failed(void *arg, uint32_t rxq_index) 238 { 239 struct sfxge_evq *evq; 240 struct sfxge_softc *sc; 241 struct sfxge_rxq *rxq; 242 unsigned int index; 243 uint16_t magic; 244 245 evq = (struct sfxge_evq *)arg; 246 SFXGE_EVQ_LOCK_ASSERT_OWNED(evq); 247 248 sc = evq->sc; 249 rxq = sc->rxq[rxq_index]; 250 251 KASSERT(rxq != NULL, ("rxq == NULL")); 252 253 /* Resend a software event on the correct queue */ 254 index = rxq->index; 255 evq = sc->evq[index]; 256 magic = sfxge_sw_ev_rxq_magic(SFXGE_SW_EV_RX_QFLUSH_FAILED, rxq); 257 258 KASSERT(evq->init_state == SFXGE_EVQ_STARTED, 259 ("evq not started")); 260 efx_ev_qpost(evq->common, magic); 261 262 return (B_FALSE); 263 } 264 265 static struct sfxge_txq * 266 sfxge_get_txq_by_label(struct sfxge_evq *evq, enum sfxge_txq_type label) 267 { 268 unsigned int index; 269 270 KASSERT((evq->index == 0 && label < SFXGE_TXQ_NTYPES) || 271 (label == SFXGE_TXQ_IP_TCP_UDP_CKSUM), ("unexpected txq label")); 272 index = (evq->index == 0) ? label : (evq->index - 1 + SFXGE_TXQ_NTYPES); 273 return (evq->sc->txq[index]); 274 } 275 276 static boolean_t 277 sfxge_ev_tx(void *arg, uint32_t label, uint32_t id) 278 { 279 struct sfxge_evq *evq; 280 struct sfxge_txq *txq; 281 unsigned int stop; 282 unsigned int delta; 283 284 evq = (struct sfxge_evq *)arg; 285 SFXGE_EVQ_LOCK_ASSERT_OWNED(evq); 286 287 txq = sfxge_get_txq_by_label(evq, label); 288 289 KASSERT(txq != NULL, ("txq == NULL")); 290 KASSERT(evq->index == txq->evq_index, 291 ("evq->index != txq->evq_index")); 292 293 if (__predict_false(txq->init_state != SFXGE_TXQ_STARTED)) 294 goto done; 295 296 stop = (id + 1) & txq->ptr_mask; 297 id = txq->pending & txq->ptr_mask; 298 299 delta = (stop >= id) ? (stop - id) : (txq->entries - id + stop); 300 txq->pending += delta; 301 302 evq->tx_done++; 303 304 if (txq->next == NULL && 305 evq->txqs != &(txq->next)) { 306 *(evq->txqs) = txq; 307 evq->txqs = &(txq->next); 308 } 309 310 if (txq->pending - txq->completed >= SFXGE_TX_BATCH) 311 sfxge_tx_qcomplete(txq, evq); 312 313 done: 314 return (evq->tx_done >= SFXGE_EV_BATCH); 315 } 316 317 static boolean_t 318 sfxge_ev_txq_flush_done(void *arg, uint32_t txq_index) 319 { 320 struct sfxge_evq *evq; 321 struct sfxge_softc *sc; 322 struct sfxge_txq *txq; 323 uint16_t magic; 324 325 evq = (struct sfxge_evq *)arg; 326 SFXGE_EVQ_LOCK_ASSERT_OWNED(evq); 327 328 sc = evq->sc; 329 txq = sc->txq[txq_index]; 330 331 KASSERT(txq != NULL, ("txq == NULL")); 332 KASSERT(txq->init_state == SFXGE_TXQ_INITIALIZED, 333 ("txq not initialized")); 334 335 if (txq->evq_index == evq->index) { 336 sfxge_tx_qflush_done(txq); 337 return (B_FALSE); 338 } 339 340 /* Resend a software event on the correct queue */ 341 evq = sc->evq[txq->evq_index]; 342 magic = sfxge_sw_ev_txq_magic(SFXGE_SW_EV_TX_QFLUSH_DONE, txq); 343 344 KASSERT(evq->init_state == SFXGE_EVQ_STARTED, 345 ("evq not started")); 346 efx_ev_qpost(evq->common, magic); 347 348 return (B_FALSE); 349 } 350 351 static boolean_t 352 sfxge_ev_software(void *arg, uint16_t magic) 353 { 354 struct sfxge_evq *evq; 355 struct sfxge_softc *sc; 356 unsigned int label; 357 358 evq = (struct sfxge_evq *)arg; 359 SFXGE_EVQ_LOCK_ASSERT_OWNED(evq); 360 361 sc = evq->sc; 362 363 label = magic & SFXGE_MAGIC_DMAQ_LABEL_MASK; 364 magic &= ~SFXGE_MAGIC_DMAQ_LABEL_MASK; 365 366 switch (magic) { 367 case SFXGE_SW_EV_MAGIC(SFXGE_SW_EV_RX_QFLUSH_DONE): 368 sfxge_rx_qflush_done(sfxge_get_rxq_by_label(evq, label)); 369 break; 370 371 case SFXGE_SW_EV_MAGIC(SFXGE_SW_EV_RX_QFLUSH_FAILED): 372 sfxge_rx_qflush_failed(sfxge_get_rxq_by_label(evq, label)); 373 break; 374 375 case SFXGE_SW_EV_MAGIC(SFXGE_SW_EV_RX_QREFILL): 376 sfxge_rx_qrefill(sfxge_get_rxq_by_label(evq, label)); 377 break; 378 379 case SFXGE_SW_EV_MAGIC(SFXGE_SW_EV_TX_QFLUSH_DONE): { 380 struct sfxge_txq *txq = sfxge_get_txq_by_label(evq, label); 381 382 KASSERT(txq != NULL, ("txq == NULL")); 383 KASSERT(evq->index == txq->evq_index, 384 ("evq->index != txq->evq_index")); 385 386 sfxge_tx_qflush_done(txq); 387 break; 388 } 389 default: 390 break; 391 } 392 393 return (B_FALSE); 394 } 395 396 static boolean_t 397 sfxge_ev_sram(void *arg, uint32_t code) 398 { 399 (void)arg; 400 (void)code; 401 402 switch (code) { 403 case EFX_SRAM_UPDATE: 404 EFSYS_PROBE(sram_update); 405 break; 406 407 case EFX_SRAM_CLEAR: 408 EFSYS_PROBE(sram_clear); 409 break; 410 411 case EFX_SRAM_ILLEGAL_CLEAR: 412 EFSYS_PROBE(sram_illegal_clear); 413 break; 414 415 default: 416 KASSERT(B_FALSE, ("Impossible SRAM event")); 417 break; 418 } 419 420 return (B_FALSE); 421 } 422 423 static boolean_t 424 sfxge_ev_timer(void *arg, uint32_t index) 425 { 426 (void)arg; 427 (void)index; 428 429 return (B_FALSE); 430 } 431 432 static boolean_t 433 sfxge_ev_wake_up(void *arg, uint32_t index) 434 { 435 (void)arg; 436 (void)index; 437 438 return (B_FALSE); 439 } 440 441 #if EFSYS_OPT_QSTATS 442 443 static void 444 sfxge_ev_stat_update(struct sfxge_softc *sc) 445 { 446 struct sfxge_evq *evq; 447 unsigned int index; 448 clock_t now; 449 450 SFXGE_ADAPTER_LOCK(sc); 451 452 if (__predict_false(sc->evq[0]->init_state != SFXGE_EVQ_STARTED)) 453 goto out; 454 455 now = ticks; 456 if ((unsigned int)(now - sc->ev_stats_update_time) < (unsigned int)hz) 457 goto out; 458 459 sc->ev_stats_update_time = now; 460 461 /* Add event counts from each event queue in turn */ 462 for (index = 0; index < sc->evq_count; index++) { 463 evq = sc->evq[index]; 464 SFXGE_EVQ_LOCK(evq); 465 efx_ev_qstats_update(evq->common, sc->ev_stats); 466 SFXGE_EVQ_UNLOCK(evq); 467 } 468 out: 469 SFXGE_ADAPTER_UNLOCK(sc); 470 } 471 472 static int 473 sfxge_ev_stat_handler(SYSCTL_HANDLER_ARGS) 474 { 475 struct sfxge_softc *sc = arg1; 476 unsigned int id = arg2; 477 478 sfxge_ev_stat_update(sc); 479 480 return (SYSCTL_OUT(req, &sc->ev_stats[id], sizeof(sc->ev_stats[id]))); 481 } 482 483 static void 484 sfxge_ev_stat_init(struct sfxge_softc *sc) 485 { 486 struct sysctl_ctx_list *ctx = device_get_sysctl_ctx(sc->dev); 487 struct sysctl_oid_list *stat_list; 488 unsigned int id; 489 char name[40]; 490 491 stat_list = SYSCTL_CHILDREN(sc->stats_node); 492 493 for (id = 0; id < EV_NQSTATS; id++) { 494 snprintf(name, sizeof(name), "ev_%s", 495 efx_ev_qstat_name(sc->enp, id)); 496 SYSCTL_ADD_PROC( 497 ctx, stat_list, 498 OID_AUTO, name, CTLTYPE_U64|CTLFLAG_RD, 499 sc, id, sfxge_ev_stat_handler, "Q", 500 ""); 501 } 502 } 503 504 #endif /* EFSYS_OPT_QSTATS */ 505 506 static void 507 sfxge_ev_qmoderate(struct sfxge_softc *sc, unsigned int idx, unsigned int us) 508 { 509 struct sfxge_evq *evq; 510 efx_evq_t *eep; 511 512 evq = sc->evq[idx]; 513 eep = evq->common; 514 515 KASSERT(evq->init_state == SFXGE_EVQ_STARTED, 516 ("evq->init_state != SFXGE_EVQ_STARTED")); 517 518 (void)efx_ev_qmoderate(eep, us); 519 } 520 521 static int 522 sfxge_int_mod_handler(SYSCTL_HANDLER_ARGS) 523 { 524 struct sfxge_softc *sc = arg1; 525 struct sfxge_intr *intr = &sc->intr; 526 unsigned int moderation; 527 int error; 528 unsigned int index; 529 530 SFXGE_ADAPTER_LOCK(sc); 531 532 if (req->newptr != NULL) { 533 if ((error = SYSCTL_IN(req, &moderation, sizeof(moderation))) 534 != 0) 535 goto out; 536 537 /* We may not be calling efx_ev_qmoderate() now, 538 * so we have to range-check the value ourselves. 539 */ 540 if (moderation > 541 efx_nic_cfg_get(sc->enp)->enc_evq_timer_max_us) { 542 error = EINVAL; 543 goto out; 544 } 545 546 sc->ev_moderation = moderation; 547 if (intr->state == SFXGE_INTR_STARTED) { 548 for (index = 0; index < sc->evq_count; index++) 549 sfxge_ev_qmoderate(sc, index, moderation); 550 } 551 } else { 552 error = SYSCTL_OUT(req, &sc->ev_moderation, 553 sizeof(sc->ev_moderation)); 554 } 555 556 out: 557 SFXGE_ADAPTER_UNLOCK(sc); 558 559 return (error); 560 } 561 562 static boolean_t 563 sfxge_ev_initialized(void *arg) 564 { 565 struct sfxge_evq *evq; 566 567 evq = (struct sfxge_evq *)arg; 568 SFXGE_EVQ_LOCK_ASSERT_OWNED(evq); 569 570 /* Init done events may be duplicated on 7xxx */ 571 KASSERT(evq->init_state == SFXGE_EVQ_STARTING || 572 evq->init_state == SFXGE_EVQ_STARTED, 573 ("evq not starting")); 574 575 evq->init_state = SFXGE_EVQ_STARTED; 576 577 return (0); 578 } 579 580 static boolean_t 581 sfxge_ev_link_change(void *arg, efx_link_mode_t link_mode) 582 { 583 struct sfxge_evq *evq; 584 struct sfxge_softc *sc; 585 586 evq = (struct sfxge_evq *)arg; 587 SFXGE_EVQ_LOCK_ASSERT_OWNED(evq); 588 589 sc = evq->sc; 590 591 sfxge_mac_link_update(sc, link_mode); 592 593 return (0); 594 } 595 596 static const efx_ev_callbacks_t sfxge_ev_callbacks = { 597 .eec_initialized = sfxge_ev_initialized, 598 .eec_rx = sfxge_ev_rx, 599 .eec_tx = sfxge_ev_tx, 600 .eec_exception = sfxge_ev_exception, 601 .eec_rxq_flush_done = sfxge_ev_rxq_flush_done, 602 .eec_rxq_flush_failed = sfxge_ev_rxq_flush_failed, 603 .eec_txq_flush_done = sfxge_ev_txq_flush_done, 604 .eec_software = sfxge_ev_software, 605 .eec_sram = sfxge_ev_sram, 606 .eec_wake_up = sfxge_ev_wake_up, 607 .eec_timer = sfxge_ev_timer, 608 .eec_link_change = sfxge_ev_link_change, 609 }; 610 611 612 int 613 sfxge_ev_qpoll(struct sfxge_evq *evq) 614 { 615 int rc; 616 617 SFXGE_EVQ_LOCK(evq); 618 619 if (__predict_false(evq->init_state != SFXGE_EVQ_STARTING && 620 evq->init_state != SFXGE_EVQ_STARTED)) { 621 rc = EINVAL; 622 goto fail; 623 } 624 625 /* Synchronize the DMA memory for reading */ 626 bus_dmamap_sync(evq->mem.esm_tag, evq->mem.esm_map, 627 BUS_DMASYNC_POSTREAD); 628 629 KASSERT(evq->rx_done == 0, ("evq->rx_done != 0")); 630 KASSERT(evq->tx_done == 0, ("evq->tx_done != 0")); 631 KASSERT(evq->txq == NULL, ("evq->txq != NULL")); 632 KASSERT(evq->txqs == &evq->txq, ("evq->txqs != &evq->txq")); 633 634 /* Poll the queue */ 635 efx_ev_qpoll(evq->common, &evq->read_ptr, &sfxge_ev_callbacks, evq); 636 637 evq->rx_done = 0; 638 evq->tx_done = 0; 639 640 /* Perform any pending completion processing */ 641 sfxge_ev_qcomplete(evq, B_TRUE); 642 643 /* Re-prime the event queue for interrupts */ 644 if ((rc = efx_ev_qprime(evq->common, evq->read_ptr)) != 0) 645 goto fail; 646 647 SFXGE_EVQ_UNLOCK(evq); 648 649 return (0); 650 651 fail: 652 SFXGE_EVQ_UNLOCK(evq); 653 return (rc); 654 } 655 656 static void 657 sfxge_ev_qstop(struct sfxge_softc *sc, unsigned int index) 658 { 659 struct sfxge_evq *evq; 660 661 evq = sc->evq[index]; 662 663 KASSERT(evq->init_state == SFXGE_EVQ_STARTED, 664 ("evq->init_state != SFXGE_EVQ_STARTED")); 665 666 SFXGE_EVQ_LOCK(evq); 667 evq->init_state = SFXGE_EVQ_INITIALIZED; 668 evq->read_ptr = 0; 669 evq->exception = B_FALSE; 670 671 #if EFSYS_OPT_QSTATS 672 /* Add event counts before discarding the common evq state */ 673 efx_ev_qstats_update(evq->common, sc->ev_stats); 674 #endif 675 676 efx_ev_qdestroy(evq->common); 677 efx_sram_buf_tbl_clear(sc->enp, evq->buf_base_id, 678 EFX_EVQ_NBUFS(evq->entries)); 679 SFXGE_EVQ_UNLOCK(evq); 680 } 681 682 static int 683 sfxge_ev_qstart(struct sfxge_softc *sc, unsigned int index) 684 { 685 struct sfxge_evq *evq; 686 efsys_mem_t *esmp; 687 int count; 688 int rc; 689 690 evq = sc->evq[index]; 691 esmp = &evq->mem; 692 693 KASSERT(evq->init_state == SFXGE_EVQ_INITIALIZED, 694 ("evq->init_state != SFXGE_EVQ_INITIALIZED")); 695 696 /* Clear all events. */ 697 (void)memset(esmp->esm_base, 0xff, EFX_EVQ_SIZE(evq->entries)); 698 699 /* Program the buffer table. */ 700 if ((rc = efx_sram_buf_tbl_set(sc->enp, evq->buf_base_id, esmp, 701 EFX_EVQ_NBUFS(evq->entries))) != 0) 702 return (rc); 703 704 /* Create the common code event queue. */ 705 if ((rc = efx_ev_qcreate(sc->enp, index, esmp, evq->entries, 706 evq->buf_base_id, sc->ev_moderation, &evq->common)) != 0) 707 goto fail; 708 709 SFXGE_EVQ_LOCK(evq); 710 711 /* Prime the event queue for interrupts */ 712 if ((rc = efx_ev_qprime(evq->common, evq->read_ptr)) != 0) 713 goto fail2; 714 715 evq->init_state = SFXGE_EVQ_STARTING; 716 717 SFXGE_EVQ_UNLOCK(evq); 718 719 /* Wait for the initialization event */ 720 count = 0; 721 do { 722 /* Pause for 100 ms */ 723 pause("sfxge evq init", hz / 10); 724 725 /* Check to see if the test event has been processed */ 726 if (evq->init_state == SFXGE_EVQ_STARTED) 727 goto done; 728 729 } while (++count < 20); 730 731 rc = ETIMEDOUT; 732 goto fail3; 733 734 done: 735 return (0); 736 737 fail3: 738 SFXGE_EVQ_LOCK(evq); 739 evq->init_state = SFXGE_EVQ_INITIALIZED; 740 fail2: 741 SFXGE_EVQ_UNLOCK(evq); 742 efx_ev_qdestroy(evq->common); 743 fail: 744 efx_sram_buf_tbl_clear(sc->enp, evq->buf_base_id, 745 EFX_EVQ_NBUFS(evq->entries)); 746 747 return (rc); 748 } 749 750 void 751 sfxge_ev_stop(struct sfxge_softc *sc) 752 { 753 struct sfxge_intr *intr; 754 efx_nic_t *enp; 755 int index; 756 757 intr = &sc->intr; 758 enp = sc->enp; 759 760 KASSERT(intr->state == SFXGE_INTR_STARTED, 761 ("Interrupts not started")); 762 763 /* Stop the event queue(s) */ 764 index = sc->evq_count; 765 while (--index >= 0) 766 sfxge_ev_qstop(sc, index); 767 768 /* Tear down the event module */ 769 efx_ev_fini(enp); 770 } 771 772 int 773 sfxge_ev_start(struct sfxge_softc *sc) 774 { 775 struct sfxge_intr *intr; 776 int index; 777 int rc; 778 779 intr = &sc->intr; 780 781 KASSERT(intr->state == SFXGE_INTR_STARTED, 782 ("intr->state != SFXGE_INTR_STARTED")); 783 784 /* Initialize the event module */ 785 if ((rc = efx_ev_init(sc->enp)) != 0) 786 return (rc); 787 788 /* Start the event queues */ 789 for (index = 0; index < sc->evq_count; index++) { 790 if ((rc = sfxge_ev_qstart(sc, index)) != 0) 791 goto fail; 792 } 793 794 return (0); 795 796 fail: 797 /* Stop the event queue(s) */ 798 while (--index >= 0) 799 sfxge_ev_qstop(sc, index); 800 801 /* Tear down the event module */ 802 efx_ev_fini(sc->enp); 803 804 return (rc); 805 } 806 807 static void 808 sfxge_ev_qfini(struct sfxge_softc *sc, unsigned int index) 809 { 810 struct sfxge_evq *evq; 811 812 evq = sc->evq[index]; 813 814 KASSERT(evq->init_state == SFXGE_EVQ_INITIALIZED, 815 ("evq->init_state != SFXGE_EVQ_INITIALIZED")); 816 KASSERT(evq->txqs == &evq->txq, ("evq->txqs != &evq->txq")); 817 818 sfxge_dma_free(&evq->mem); 819 820 sc->evq[index] = NULL; 821 822 SFXGE_EVQ_LOCK_DESTROY(evq); 823 824 free(evq, M_SFXGE); 825 } 826 827 static int 828 sfxge_ev_qinit(struct sfxge_softc *sc, unsigned int index) 829 { 830 struct sfxge_evq *evq; 831 efsys_mem_t *esmp; 832 int rc; 833 834 KASSERT(index < SFXGE_RX_SCALE_MAX, ("index >= SFXGE_RX_SCALE_MAX")); 835 836 evq = malloc(sizeof(struct sfxge_evq), M_SFXGE, M_ZERO | M_WAITOK); 837 evq->sc = sc; 838 evq->index = index; 839 sc->evq[index] = evq; 840 esmp = &evq->mem; 841 842 /* Build an event queue with room for one event per tx and rx buffer, 843 * plus some extra for link state events and MCDI completions. 844 * There are three tx queues in the first event queue and one in 845 * other. 846 */ 847 if (index == 0) 848 evq->entries = 849 ROUNDUP_POW_OF_TWO(sc->rxq_entries + 850 3 * sc->txq_entries + 851 128); 852 else 853 evq->entries = 854 ROUNDUP_POW_OF_TWO(sc->rxq_entries + 855 sc->txq_entries + 856 128); 857 858 /* Initialise TX completion list */ 859 evq->txqs = &evq->txq; 860 861 /* Allocate DMA space. */ 862 if ((rc = sfxge_dma_alloc(sc, EFX_EVQ_SIZE(evq->entries), esmp)) != 0) 863 return (rc); 864 865 /* Allocate buffer table entries. */ 866 sfxge_sram_buf_tbl_alloc(sc, EFX_EVQ_NBUFS(evq->entries), 867 &evq->buf_base_id); 868 869 SFXGE_EVQ_LOCK_INIT(evq, device_get_nameunit(sc->dev), index); 870 871 evq->init_state = SFXGE_EVQ_INITIALIZED; 872 873 return (0); 874 } 875 876 void 877 sfxge_ev_fini(struct sfxge_softc *sc) 878 { 879 struct sfxge_intr *intr; 880 int index; 881 882 intr = &sc->intr; 883 884 KASSERT(intr->state == SFXGE_INTR_INITIALIZED, 885 ("intr->state != SFXGE_INTR_INITIALIZED")); 886 887 sc->ev_moderation = 0; 888 889 /* Tear down the event queue(s). */ 890 index = sc->evq_count; 891 while (--index >= 0) 892 sfxge_ev_qfini(sc, index); 893 894 sc->evq_count = 0; 895 } 896 897 int 898 sfxge_ev_init(struct sfxge_softc *sc) 899 { 900 struct sysctl_ctx_list *sysctl_ctx = device_get_sysctl_ctx(sc->dev); 901 struct sysctl_oid *sysctl_tree = device_get_sysctl_tree(sc->dev); 902 struct sfxge_intr *intr; 903 int index; 904 int rc; 905 906 intr = &sc->intr; 907 908 sc->evq_count = intr->n_alloc; 909 910 KASSERT(intr->state == SFXGE_INTR_INITIALIZED, 911 ("intr->state != SFXGE_INTR_INITIALIZED")); 912 913 /* Set default interrupt moderation; add a sysctl to 914 * read and change it. 915 */ 916 sc->ev_moderation = SFXGE_MODERATION; 917 SYSCTL_ADD_PROC(sysctl_ctx, SYSCTL_CHILDREN(sysctl_tree), 918 OID_AUTO, "int_mod", CTLTYPE_UINT|CTLFLAG_RW, 919 sc, 0, sfxge_int_mod_handler, "IU", 920 "sfxge interrupt moderation (us)"); 921 922 /* 923 * Initialize the event queue(s) - one per interrupt. 924 */ 925 for (index = 0; index < sc->evq_count; index++) { 926 if ((rc = sfxge_ev_qinit(sc, index)) != 0) 927 goto fail; 928 } 929 930 #if EFSYS_OPT_QSTATS 931 sfxge_ev_stat_init(sc); 932 #endif 933 934 return (0); 935 936 fail: 937 while (--index >= 0) 938 sfxge_ev_qfini(sc, index); 939 940 sc->evq_count = 0; 941 return (rc); 942 } 943