Date: Sat, 12 Jun 2010 22:33:04 +0000 (UTC) From: Navdeep Parhar <np@FreeBSD.org> To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r209116 - head/sys/dev/cxgb Message-ID: <201006122233.o5CMX4Fc032367@svn.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: np Date: Sat Jun 12 22:33:04 2010 New Revision: 209116 URL: http://svn.freebsd.org/changeset/base/209116 Log: cxgb(4): add knob to get packet timestamps from the hardware. The T3 ASIC can provide an incoming packet's timestamp instead of its RSS hash. The timestamp is just a counter running off the card's clock. With a 175MHz clock an increment represents ~5.7ns and the 32 bit value wraps around in ~25s. # sysctl -d dev.cxgbc.0.pkt_timestamp dev.cxgbc.0.pkt_timestamp: provide packet timestamp instead of connection hash # sysctl -d dev.cxgbc.0.core_clock dev.cxgbc.0.core_clock: core clock frequency (in KHz) # sysctl dev.cxgbc.0.core_clock dev.cxgbc.0.core_clock: 175000 Modified: head/sys/dev/cxgb/cxgb_adapter.h head/sys/dev/cxgb/cxgb_sge.c Modified: head/sys/dev/cxgb/cxgb_adapter.h ============================================================================== --- head/sys/dev/cxgb/cxgb_adapter.h Sat Jun 12 22:24:39 2010 (r209115) +++ head/sys/dev/cxgb/cxgb_adapter.h Sat Jun 12 22:33:04 2010 (r209116) @@ -388,6 +388,8 @@ struct adapter { char reglockbuf[ADAPTER_LOCK_NAME_LEN]; char mdiolockbuf[ADAPTER_LOCK_NAME_LEN]; char elmerlockbuf[ADAPTER_LOCK_NAME_LEN]; + + int timestamp; }; struct t3_rx_mode { Modified: head/sys/dev/cxgb/cxgb_sge.c ============================================================================== --- head/sys/dev/cxgb/cxgb_sge.c Sat Jun 12 22:24:39 2010 (r209115) +++ head/sys/dev/cxgb/cxgb_sge.c Sat Jun 12 22:33:04 2010 (r209116) @@ -2961,6 +2961,7 @@ process_responses(adapter_t *adap, struc struct lro_ctrl *lro_ctrl = &qs->lro.ctrl; struct mbuf *offload_mbufs[RX_BUNDLE_SIZE]; int ngathered = 0; + struct t3_mbuf_hdr *mh = &rspq->rspq_mh; #ifdef DEBUG static int last_holdoff = 0; if (cxgb_debug && rspq->holdoff_tmr != last_holdoff) { @@ -2984,9 +2985,9 @@ process_responses(adapter_t *adap, struc if (cxgb_debug) printf("async notification\n"); - if (rspq->rspq_mh.mh_head == NULL) { - rspq->rspq_mh.mh_head = m_gethdr(M_DONTWAIT, MT_DATA); - m = rspq->rspq_mh.mh_head; + if (mh->mh_head == NULL) { + mh->mh_head = m_gethdr(M_DONTWAIT, MT_DATA); + m = mh->mh_head; } else { m = m_gethdr(M_DONTWAIT, MT_DATA); } @@ -3005,27 +3006,28 @@ process_responses(adapter_t *adap, struc DPRINTF("IMM DATA VALID opcode=0x%x rspq->cidx=%d\n", r->rss_hdr.opcode, rspq->cidx); - if (rspq->rspq_mh.mh_head == NULL) - rspq->rspq_mh.mh_head = m_gethdr(M_DONTWAIT, MT_DATA); + if (mh->mh_head == NULL) + mh->mh_head = m_gethdr(M_DONTWAIT, MT_DATA); else m = m_gethdr(M_DONTWAIT, MT_DATA); - if (rspq->rspq_mh.mh_head == NULL && m == NULL) { + if (mh->mh_head == NULL && m == NULL) { no_mem: rspq->next_holdoff = NOMEM_INTR_DELAY; budget_left--; break; } - get_imm_packet(adap, r, rspq->rspq_mh.mh_head); + get_imm_packet(adap, r, mh->mh_head); eop = 1; rspq->imm_data++; } else if (r->len_cq) { int drop_thresh = eth ? SGE_RX_DROP_THRES : 0; - eop = get_packet(adap, drop_thresh, qs, &rspq->rspq_mh, r); + eop = get_packet(adap, drop_thresh, qs, mh, r); if (eop) { - rspq->rspq_mh.mh_head->m_flags |= M_FLOWID; - rspq->rspq_mh.mh_head->m_pkthdr.flowid = rss_hash; + if (r->rss_hdr.hash_type && !adap->timestamp) + mh->mh_head->m_flags |= M_FLOWID; + mh->mh_head->m_pkthdr.flowid = rss_hash; } ethpad = 2; @@ -3050,20 +3052,20 @@ process_responses(adapter_t *adap, struc rspq->credits = 0; } if (!eth && eop) { - rspq->rspq_mh.mh_head->m_pkthdr.csum_data = rss_csum; + mh->mh_head->m_pkthdr.csum_data = rss_csum; /* * XXX size mismatch */ - m_set_priority(rspq->rspq_mh.mh_head, rss_hash); + m_set_priority(mh->mh_head, rss_hash); ngathered = rx_offload(&adap->tdev, rspq, - rspq->rspq_mh.mh_head, offload_mbufs, ngathered); - rspq->rspq_mh.mh_head = NULL; + mh->mh_head, offload_mbufs, ngathered); + mh->mh_head = NULL; DPRINTF("received offload packet\n"); } else if (eth && eop) { - struct mbuf *m = rspq->rspq_mh.mh_head; + struct mbuf *m = mh->mh_head; t3_rx_eth(adap, rspq, m, ethpad); @@ -3092,7 +3094,7 @@ process_responses(adapter_t *adap, struc struct ifnet *ifp = m->m_pkthdr.rcvif; (*ifp->if_input)(ifp, m); } - rspq->rspq_mh.mh_head = NULL; + mh->mh_head = NULL; } __refill_fl_lt(adap, &qs->fl[0], 32); @@ -3459,6 +3461,29 @@ t3_set_coalesce_usecs(SYSCTL_HANDLER_ARG return (0); } +static int +t3_pkt_timestamp(SYSCTL_HANDLER_ARGS) +{ + adapter_t *sc = arg1; + int rc, timestamp; + + if ((sc->flags & FULL_INIT_DONE) == 0) + return (ENXIO); + + timestamp = sc->timestamp; + rc = sysctl_handle_int(oidp, ×tamp, arg2, req); + + if (rc != 0) + return (rc); + + if (timestamp != sc->timestamp) { + t3_set_reg_field(sc, A_TP_PC_CONFIG2, F_ENABLERXPKTTMSTPRSS, + timestamp ? F_ENABLERXPKTTMSTPRSS : 0); + sc->timestamp = timestamp; + } + + return (0); +} void t3_add_attach_sysctls(adapter_t *sc) @@ -3493,6 +3518,10 @@ t3_add_attach_sysctls(adapter_t *sc) "txq_overrun", CTLFLAG_RD, &txq_fills, 0, "#times txq overrun"); + SYSCTL_ADD_INT(ctx, children, OID_AUTO, + "core_clock", + CTLFLAG_RD, &sc->params.vpd.cclk, + 0, "core clock frequency (in KHz)"); } @@ -3537,6 +3566,12 @@ t3_add_configured_sysctls(adapter_t *sc) 0, t3_set_coalesce_usecs, "I", "interrupt coalescing timer (us)"); + SYSCTL_ADD_PROC(ctx, children, OID_AUTO, + "pkt_timestamp", + CTLTYPE_INT | CTLFLAG_RW, sc, + 0, t3_pkt_timestamp, + "I", "provide packet timestamp instead of connection hash"); + for (i = 0; i < sc->params.nports; i++) { struct port_info *pi = &sc->port[i]; struct sysctl_oid *poid;
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201006122233.o5CMX4Fc032367>