static int sge_qinfo_show()

in ethernet/chelsio/cxgb4/cxgb4_debugfs.c [2650:3151]


static int sge_qinfo_show(struct seq_file *seq, void *v)
{
	int eth_entries, ctrl_entries, eohw_entries = 0, eosw_entries = 0;
	int uld_rxq_entries[CXGB4_ULD_MAX] = { 0 };
	int uld_ciq_entries[CXGB4_ULD_MAX] = { 0 };
	int uld_txq_entries[CXGB4_TX_MAX] = { 0 };
	const struct sge_uld_txq_info *utxq_info;
	const struct sge_uld_rxq_info *urxq_info;
	struct cxgb4_tc_port_mqprio *port_mqprio;
	struct adapter *adap = seq->private;
	int i, j, n, r = (uintptr_t)v - 1;
	struct sge *s = &adap->sge;

	eth_entries = DIV_ROUND_UP(adap->sge.ethqsets, 4);
	ctrl_entries = DIV_ROUND_UP(MAX_CTRL_QUEUES, 4);

	if (r)
		seq_putc(seq, '\n');

#define S3(fmt_spec, s, v) \
do { \
	seq_printf(seq, "%-12s", s); \
	for (i = 0; i < n; ++i) \
		seq_printf(seq, " %16" fmt_spec, v); \
	seq_putc(seq, '\n'); \
} while (0)
#define S(s, v) S3("s", s, v)
#define T3(fmt_spec, s, v) S3(fmt_spec, s, tx[i].v)
#define T(s, v) S3("u", s, tx[i].v)
#define TL(s, v) T3("lu", s, v)
#define R3(fmt_spec, s, v) S3(fmt_spec, s, rx[i].v)
#define R(s, v) S3("u", s, rx[i].v)
#define RL(s, v) R3("lu", s, v)

	if (r < eth_entries) {
		int base_qset = r * 4;
		const struct sge_eth_rxq *rx = &s->ethrxq[base_qset];
		const struct sge_eth_txq *tx = &s->ethtxq[base_qset];

		n = min(4, s->ethqsets - 4 * r);

		S("QType:", "Ethernet");
		S("Interface:",
		  rx[i].rspq.netdev ? rx[i].rspq.netdev->name : "N/A");
		T("TxQ ID:", q.cntxt_id);
		T("TxQ size:", q.size);
		T("TxQ inuse:", q.in_use);
		T("TxQ CIDX:", q.cidx);
		T("TxQ PIDX:", q.pidx);
#ifdef CONFIG_CHELSIO_T4_DCB
		T("DCB Prio:", dcb_prio);
		S3("u", "DCB PGID:",
		   (ethqset2pinfo(adap, base_qset + i)->dcb.pgid >>
		    4*(7-tx[i].dcb_prio)) & 0xf);
		S3("u", "DCB PFC:",
		   (ethqset2pinfo(adap, base_qset + i)->dcb.pfcen >>
		    1*(7-tx[i].dcb_prio)) & 0x1);
#endif
		R("RspQ ID:", rspq.abs_id);
		R("RspQ size:", rspq.size);
		R("RspQE size:", rspq.iqe_len);
		R("RspQ CIDX:", rspq.cidx);
		R("RspQ Gen:", rspq.gen);
		S3("u", "Intr delay:", qtimer_val(adap, &rx[i].rspq));
		S3("u", "Intr pktcnt:", s->counter_val[rx[i].rspq.pktcnt_idx]);
		R("FL ID:", fl.cntxt_id);
		R("FL size:", fl.size - 8);
		R("FL pend:", fl.pend_cred);
		R("FL avail:", fl.avail);
		R("FL PIDX:", fl.pidx);
		R("FL CIDX:", fl.cidx);
		RL("RxPackets:", stats.pkts);
		RL("RxCSO:", stats.rx_cso);
		RL("VLANxtract:", stats.vlan_ex);
		RL("LROmerged:", stats.lro_merged);
		RL("LROpackets:", stats.lro_pkts);
		RL("RxDrops:", stats.rx_drops);
		RL("RxBadPkts:", stats.bad_rx_pkts);
		TL("TSO:", tso);
		TL("USO:", uso);
		TL("TxCSO:", tx_cso);
		TL("VLANins:", vlan_ins);
		TL("TxQFull:", q.stops);
		TL("TxQRestarts:", q.restarts);
		TL("TxMapErr:", mapping_err);
		RL("FLAllocErr:", fl.alloc_failed);
		RL("FLLrgAlcErr:", fl.large_alloc_failed);
		RL("FLMapErr:", fl.mapping_err);
		RL("FLLow:", fl.low);
		RL("FLStarving:", fl.starving);

		goto out;
	}

	r -= eth_entries;
	for_each_port(adap, j) {
		struct port_info *pi = adap2pinfo(adap, j);
		const struct sge_eth_rxq *rx;

		mutex_lock(&pi->vi_mirror_mutex);
		if (!pi->vi_mirror_count) {
			mutex_unlock(&pi->vi_mirror_mutex);
			continue;
		}

		if (r >= DIV_ROUND_UP(pi->nmirrorqsets, 4)) {
			r -= DIV_ROUND_UP(pi->nmirrorqsets, 4);
			mutex_unlock(&pi->vi_mirror_mutex);
			continue;
		}

		rx = &s->mirror_rxq[j][r * 4];
		n = min(4, pi->nmirrorqsets - 4 * r);

		S("QType:", "Mirror-Rxq");
		S("Interface:",
		  rx[i].rspq.netdev ? rx[i].rspq.netdev->name : "N/A");
		R("RspQ ID:", rspq.abs_id);
		R("RspQ size:", rspq.size);
		R("RspQE size:", rspq.iqe_len);
		R("RspQ CIDX:", rspq.cidx);
		R("RspQ Gen:", rspq.gen);
		S3("u", "Intr delay:", qtimer_val(adap, &rx[i].rspq));
		S3("u", "Intr pktcnt:", s->counter_val[rx[i].rspq.pktcnt_idx]);
		R("FL ID:", fl.cntxt_id);
		R("FL size:", fl.size - 8);
		R("FL pend:", fl.pend_cred);
		R("FL avail:", fl.avail);
		R("FL PIDX:", fl.pidx);
		R("FL CIDX:", fl.cidx);
		RL("RxPackets:", stats.pkts);
		RL("RxCSO:", stats.rx_cso);
		RL("VLANxtract:", stats.vlan_ex);
		RL("LROmerged:", stats.lro_merged);
		RL("LROpackets:", stats.lro_pkts);
		RL("RxDrops:", stats.rx_drops);
		RL("RxBadPkts:", stats.bad_rx_pkts);
		RL("FLAllocErr:", fl.alloc_failed);
		RL("FLLrgAlcErr:", fl.large_alloc_failed);
		RL("FLMapErr:", fl.mapping_err);
		RL("FLLow:", fl.low);
		RL("FLStarving:", fl.starving);

		mutex_unlock(&pi->vi_mirror_mutex);
		goto out;
	}

	if (!adap->tc_mqprio)
		goto skip_mqprio;

	mutex_lock(&adap->tc_mqprio->mqprio_mutex);
	if (!refcount_read(&adap->tc_mqprio->refcnt)) {
		mutex_unlock(&adap->tc_mqprio->mqprio_mutex);
		goto skip_mqprio;
	}

	eohw_entries = DIV_ROUND_UP(adap->sge.eoqsets, 4);
	if (r < eohw_entries) {
		int base_qset = r * 4;
		const struct sge_ofld_rxq *rx = &s->eohw_rxq[base_qset];
		const struct sge_eohw_txq *tx = &s->eohw_txq[base_qset];

		n = min(4, s->eoqsets - 4 * r);

		S("QType:", "ETHOFLD");
		S("Interface:",
		  rx[i].rspq.netdev ? rx[i].rspq.netdev->name : "N/A");
		T("TxQ ID:", q.cntxt_id);
		T("TxQ size:", q.size);
		T("TxQ inuse:", q.in_use);
		T("TxQ CIDX:", q.cidx);
		T("TxQ PIDX:", q.pidx);
		R("RspQ ID:", rspq.abs_id);
		R("RspQ size:", rspq.size);
		R("RspQE size:", rspq.iqe_len);
		R("RspQ CIDX:", rspq.cidx);
		R("RspQ Gen:", rspq.gen);
		S3("u", "Intr delay:", qtimer_val(adap, &rx[i].rspq));
		S3("u", "Intr pktcnt:", s->counter_val[rx[i].rspq.pktcnt_idx]);
		R("FL ID:", fl.cntxt_id);
		S3("u", "FL size:", rx->fl.size ? rx->fl.size - 8 : 0);
		R("FL pend:", fl.pend_cred);
		R("FL avail:", fl.avail);
		R("FL PIDX:", fl.pidx);
		R("FL CIDX:", fl.cidx);
		RL("RxPackets:", stats.pkts);
		RL("RxImm:", stats.imm);
		RL("RxAN", stats.an);
		RL("RxNoMem", stats.nomem);
		TL("TSO:", tso);
		TL("USO:", uso);
		TL("TxCSO:", tx_cso);
		TL("VLANins:", vlan_ins);
		TL("TxQFull:", q.stops);
		TL("TxQRestarts:", q.restarts);
		TL("TxMapErr:", mapping_err);
		RL("FLAllocErr:", fl.alloc_failed);
		RL("FLLrgAlcErr:", fl.large_alloc_failed);
		RL("FLMapErr:", fl.mapping_err);
		RL("FLLow:", fl.low);
		RL("FLStarving:", fl.starving);

		mutex_unlock(&adap->tc_mqprio->mqprio_mutex);
		goto out;
	}

	r -= eohw_entries;
	for (j = 0; j < adap->params.nports; j++) {
		int entries;
		u8 tc;

		port_mqprio = &adap->tc_mqprio->port_mqprio[j];
		entries = 0;
		for (tc = 0; tc < port_mqprio->mqprio.qopt.num_tc; tc++)
			entries += port_mqprio->mqprio.qopt.count[tc];

		if (!entries)
			continue;

		eosw_entries = DIV_ROUND_UP(entries, 4);
		if (r < eosw_entries) {
			const struct sge_eosw_txq *tx;

			n = min(4, entries - 4 * r);
			tx = &port_mqprio->eosw_txq[4 * r];

			S("QType:", "EOSW-TXQ");
			S("Interface:",
			  adap->port[j] ? adap->port[j]->name : "N/A");
			T("EOTID:", hwtid);
			T("HWQID:", hwqid);
			T("State:", state);
			T("Size:", ndesc);
			T("In-Use:", inuse);
			T("Credits:", cred);
			T("Compl:", ncompl);
			T("Last-Compl:", last_compl);
			T("PIDX:", pidx);
			T("Last-PIDX:", last_pidx);
			T("CIDX:", cidx);
			T("Last-CIDX:", last_cidx);
			T("FLOWC-IDX:", flowc_idx);

			mutex_unlock(&adap->tc_mqprio->mqprio_mutex);
			goto out;
		}

		r -= eosw_entries;
	}
	mutex_unlock(&adap->tc_mqprio->mqprio_mutex);

skip_mqprio:
	if (!is_uld(adap))
		goto skip_uld;

	mutex_lock(&uld_mutex);
	if (s->uld_txq_info)
		for (i = 0; i < ARRAY_SIZE(uld_txq_entries); i++)
			uld_txq_entries[i] = sge_qinfo_uld_txq_entries(adap, i);

	if (s->uld_rxq_info) {
		for (i = 0; i < ARRAY_SIZE(uld_rxq_entries); i++) {
			uld_rxq_entries[i] = sge_qinfo_uld_rxq_entries(adap, i);
			uld_ciq_entries[i] = sge_qinfo_uld_ciq_entries(adap, i);
		}
	}

	if (r < uld_txq_entries[CXGB4_TX_OFLD]) {
		const struct sge_uld_txq *tx;

		utxq_info = s->uld_txq_info[CXGB4_TX_OFLD];
		tx = &utxq_info->uldtxq[r * 4];
		n = min(4, utxq_info->ntxq - 4 * r);

		S("QType:", "OFLD-TXQ");
		T("TxQ ID:", q.cntxt_id);
		T("TxQ size:", q.size);
		T("TxQ inuse:", q.in_use);
		T("TxQ CIDX:", q.cidx);
		T("TxQ PIDX:", q.pidx);

		goto unlock;
	}

	r -= uld_txq_entries[CXGB4_TX_OFLD];
	if (r < uld_rxq_entries[CXGB4_ULD_RDMA]) {
		const struct sge_ofld_rxq *rx;

		urxq_info = s->uld_rxq_info[CXGB4_ULD_RDMA];
		rx = &urxq_info->uldrxq[r * 4];
		n = min(4, urxq_info->nrxq - 4 * r);

		S("QType:", "RDMA-CPL");
		S("Interface:",
		  rx[i].rspq.netdev ? rx[i].rspq.netdev->name : "N/A");
		R("RspQ ID:", rspq.abs_id);
		R("RspQ size:", rspq.size);
		R("RspQE size:", rspq.iqe_len);
		R("RspQ CIDX:", rspq.cidx);
		R("RspQ Gen:", rspq.gen);
		S3("u", "Intr delay:", qtimer_val(adap, &rx[i].rspq));
		S3("u", "Intr pktcnt:",	s->counter_val[rx[i].rspq.pktcnt_idx]);
		R("FL ID:", fl.cntxt_id);
		R("FL size:", fl.size - 8);
		R("FL pend:", fl.pend_cred);
		R("FL avail:", fl.avail);
		R("FL PIDX:", fl.pidx);
		R("FL CIDX:", fl.cidx);

		goto unlock;
	}

	r -= uld_rxq_entries[CXGB4_ULD_RDMA];
	if (r < uld_ciq_entries[CXGB4_ULD_RDMA]) {
		const struct sge_ofld_rxq *rx;
		int ciq_idx = 0;

		urxq_info = s->uld_rxq_info[CXGB4_ULD_RDMA];
		ciq_idx = urxq_info->nrxq + (r * 4);
		rx = &urxq_info->uldrxq[ciq_idx];
		n = min(4, urxq_info->nciq - 4 * r);

		S("QType:", "RDMA-CIQ");
		S("Interface:",
		  rx[i].rspq.netdev ? rx[i].rspq.netdev->name : "N/A");
		R("RspQ ID:", rspq.abs_id);
		R("RspQ size:", rspq.size);
		R("RspQE size:", rspq.iqe_len);
		R("RspQ CIDX:", rspq.cidx);
		R("RspQ Gen:", rspq.gen);
		S3("u", "Intr delay:", qtimer_val(adap, &rx[i].rspq));
		S3("u", "Intr pktcnt:",	s->counter_val[rx[i].rspq.pktcnt_idx]);

		goto unlock;
	}

	r -= uld_ciq_entries[CXGB4_ULD_RDMA];
	if (r < uld_rxq_entries[CXGB4_ULD_ISCSI]) {
		const struct sge_ofld_rxq *rx;

		urxq_info = s->uld_rxq_info[CXGB4_ULD_ISCSI];
		rx = &urxq_info->uldrxq[r * 4];
		n = min(4, urxq_info->nrxq - 4 * r);

		S("QType:", "iSCSI");
		R("RspQ ID:", rspq.abs_id);
		R("RspQ size:", rspq.size);
		R("RspQE size:", rspq.iqe_len);
		R("RspQ CIDX:", rspq.cidx);
		R("RspQ Gen:", rspq.gen);
		S3("u", "Intr delay:", qtimer_val(adap, &rx[i].rspq));
		S3("u", "Intr pktcnt:",	s->counter_val[rx[i].rspq.pktcnt_idx]);
		R("FL ID:", fl.cntxt_id);
		R("FL size:", fl.size - 8);
		R("FL pend:", fl.pend_cred);
		R("FL avail:", fl.avail);
		R("FL PIDX:", fl.pidx);
		R("FL CIDX:", fl.cidx);

		goto unlock;
	}

	r -= uld_rxq_entries[CXGB4_ULD_ISCSI];
	if (r < uld_rxq_entries[CXGB4_ULD_ISCSIT]) {
		const struct sge_ofld_rxq *rx;

		urxq_info = s->uld_rxq_info[CXGB4_ULD_ISCSIT];
		rx = &urxq_info->uldrxq[r * 4];
		n = min(4, urxq_info->nrxq - 4 * r);

		S("QType:", "iSCSIT");
		R("RspQ ID:", rspq.abs_id);
		R("RspQ size:", rspq.size);
		R("RspQE size:", rspq.iqe_len);
		R("RspQ CIDX:", rspq.cidx);
		R("RspQ Gen:", rspq.gen);
		S3("u", "Intr delay:", qtimer_val(adap, &rx[i].rspq));
		S3("u", "Intr pktcnt:",	s->counter_val[rx[i].rspq.pktcnt_idx]);
		R("FL ID:", fl.cntxt_id);
		R("FL size:", fl.size - 8);
		R("FL pend:", fl.pend_cred);
		R("FL avail:", fl.avail);
		R("FL PIDX:", fl.pidx);
		R("FL CIDX:", fl.cidx);

		goto unlock;
	}

	r -= uld_rxq_entries[CXGB4_ULD_ISCSIT];
	if (r < uld_rxq_entries[CXGB4_ULD_TLS]) {
		const struct sge_ofld_rxq *rx;

		urxq_info = s->uld_rxq_info[CXGB4_ULD_TLS];
		rx = &urxq_info->uldrxq[r * 4];
		n = min(4, urxq_info->nrxq - 4 * r);

		S("QType:", "TLS");
		R("RspQ ID:", rspq.abs_id);
		R("RspQ size:", rspq.size);
		R("RspQE size:", rspq.iqe_len);
		R("RspQ CIDX:", rspq.cidx);
		R("RspQ Gen:", rspq.gen);
		S3("u", "Intr delay:", qtimer_val(adap, &rx[i].rspq));
		S3("u", "Intr pktcnt:",	s->counter_val[rx[i].rspq.pktcnt_idx]);
		R("FL ID:", fl.cntxt_id);
		R("FL size:", fl.size - 8);
		R("FL pend:", fl.pend_cred);
		R("FL avail:", fl.avail);
		R("FL PIDX:", fl.pidx);
		R("FL CIDX:", fl.cidx);

		goto unlock;
	}

	r -= uld_rxq_entries[CXGB4_ULD_TLS];
	if (r < uld_txq_entries[CXGB4_TX_CRYPTO]) {
		const struct sge_ofld_rxq *rx;
		const struct sge_uld_txq *tx;

		utxq_info = s->uld_txq_info[CXGB4_TX_CRYPTO];
		urxq_info = s->uld_rxq_info[CXGB4_ULD_CRYPTO];
		tx = &utxq_info->uldtxq[r * 4];
		rx = &urxq_info->uldrxq[r * 4];
		n = min(4, utxq_info->ntxq - 4 * r);

		S("QType:", "Crypto");
		T("TxQ ID:", q.cntxt_id);
		T("TxQ size:", q.size);
		T("TxQ inuse:", q.in_use);
		T("TxQ CIDX:", q.cidx);
		T("TxQ PIDX:", q.pidx);
		R("RspQ ID:", rspq.abs_id);
		R("RspQ size:", rspq.size);
		R("RspQE size:", rspq.iqe_len);
		R("RspQ CIDX:", rspq.cidx);
		R("RspQ Gen:", rspq.gen);
		S3("u", "Intr delay:", qtimer_val(adap, &rx[i].rspq));
		S3("u", "Intr pktcnt:",	s->counter_val[rx[i].rspq.pktcnt_idx]);
		R("FL ID:", fl.cntxt_id);
		R("FL size:", fl.size - 8);
		R("FL pend:", fl.pend_cred);
		R("FL avail:", fl.avail);
		R("FL PIDX:", fl.pidx);
		R("FL CIDX:", fl.cidx);

		goto unlock;
	}

	r -= uld_txq_entries[CXGB4_TX_CRYPTO];
	mutex_unlock(&uld_mutex);

skip_uld:
	if (r < ctrl_entries) {
		const struct sge_ctrl_txq *tx = &s->ctrlq[r * 4];

		n = min(4, adap->params.nports - 4 * r);

		S("QType:", "Control");
		T("TxQ ID:", q.cntxt_id);
		T("TxQ size:", q.size);
		T("TxQ inuse:", q.in_use);
		T("TxQ CIDX:", q.cidx);
		T("TxQ PIDX:", q.pidx);
		TL("TxQFull:", q.stops);
		TL("TxQRestarts:", q.restarts);

		goto out;
	}

	r -= ctrl_entries;
	if (r < 1) {
		const struct sge_rspq *evtq = &s->fw_evtq;

		seq_printf(seq, "%-12s %16s\n", "QType:", "FW event queue");
		seq_printf(seq, "%-12s %16u\n", "RspQ ID:", evtq->abs_id);
		seq_printf(seq, "%-12s %16u\n", "RspQ size:", evtq->size);
		seq_printf(seq, "%-12s %16u\n", "RspQE size:", evtq->iqe_len);
		seq_printf(seq, "%-12s %16u\n", "RspQ CIDX:", evtq->cidx);
		seq_printf(seq, "%-12s %16u\n", "RspQ Gen:", evtq->gen);
		seq_printf(seq, "%-12s %16u\n", "Intr delay:",
			   qtimer_val(adap, evtq));
		seq_printf(seq, "%-12s %16u\n", "Intr pktcnt:",
			   s->counter_val[evtq->pktcnt_idx]);

		goto out;
	}

#undef R
#undef RL
#undef T
#undef TL
#undef S
#undef R3
#undef T3
#undef S3
out:
	return 0;

unlock:
	mutex_unlock(&uld_mutex);
	return 0;
}