Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 5b823514 authored by Raghu Vatsavayi's avatar Raghu Vatsavayi Committed by David S. Miller
Browse files

liquidio: CN23XX octeon3 instruction



Adds support for data path related changes based
on octeon3 instruction header(ih3) for cn23xx.

Signed-off-by: default avatarDerek Chickles <derek.chickles@caviumnetworks.com>
Signed-off-by: default avatarSatanand Burla <satananda.burla@caviumnetworks.com>
Signed-off-by: default avatarFelix Manlunas <felix.manlunas@caviumnetworks.com>
Signed-off-by: default avatarRaghu Vatsavayi <raghu.vatsavayi@caviumnetworks.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 9bdd4609
Loading
Loading
Loading
Loading
+27 −10
Original line number Diff line number Diff line
@@ -1347,17 +1347,16 @@ static void octeon_destroy_resources(struct octeon_device *oct)
	case OCT_DEV_RESP_LIST_INIT_DONE:
		octeon_delete_response_list(oct);

		/* fallthrough */
	case OCT_DEV_SC_BUFF_POOL_INIT_DONE:
		octeon_free_sc_buffer_pool(oct);

		/* fallthrough */
	case OCT_DEV_INSTR_QUEUE_INIT_DONE:
		for (i = 0; i < MAX_OCTEON_INSTR_QUEUES(oct); i++) {
			if (!(oct->io_qmask.iq & (1ULL << i)))
			if (!(oct->io_qmask.iq & BIT_ULL(i)))
				continue;
			octeon_delete_instr_queue(oct, i);
		}
		/* fallthrough */
	case OCT_DEV_SC_BUFF_POOL_INIT_DONE:
		octeon_free_sc_buffer_pool(oct);

		/* fallthrough */
	case OCT_DEV_DISPATCH_INIT_DONE:
@@ -2929,9 +2928,15 @@ static inline int send_nic_timestamp_pkt(struct octeon_device *oct,
	sc->callback_arg = finfo->skb;
	sc->iq_no = ndata->q_no;

	len = (u32)((struct octeon_instr_ih2 *)(&sc->cmd.cmd2.ih2))->dlengsz;
	if (OCTEON_CN23XX_PF(oct))
		len = (u32)((struct octeon_instr_ih3 *)
			    (&sc->cmd.cmd3.ih3))->dlengsz;
	else
		len = (u32)((struct octeon_instr_ih2 *)
			    (&sc->cmd.cmd2.ih2))->dlengsz;

	ring_doorbell = 1;

	retval = octeon_send_command(oct, sc->iq_no, ring_doorbell, &sc->cmd,
				     sc, len, ndata->reqtype);

@@ -3063,6 +3068,9 @@ static int liquidio_xmit(struct sk_buff *skb, struct net_device *netdev)
			return NETDEV_TX_BUSY;
		}

		if (OCTEON_CN23XX_PF(oct))
			ndata.cmd.cmd3.dptr = dptr;
		else
			ndata.cmd.cmd2.dptr = dptr;
		finfo->dptr = dptr;
		ndata.reqtype = REQTYPE_NORESP_NET;
@@ -3138,6 +3146,9 @@ static int liquidio_xmit(struct sk_buff *skb, struct net_device *netdev)
					   g->sg_size, DMA_TO_DEVICE);
		dptr = g->sg_dma_ptr;

		if (OCTEON_CN23XX_PF(oct))
			ndata.cmd.cmd3.dptr = dptr;
		else
			ndata.cmd.cmd2.dptr = dptr;
		finfo->dptr = dptr;
		finfo->g = g;
@@ -3145,8 +3156,13 @@ static int liquidio_xmit(struct sk_buff *skb, struct net_device *netdev)
		ndata.reqtype = REQTYPE_NORESP_NET_SG;
	}

	if (OCTEON_CN23XX_PF(oct)) {
		irh = (struct octeon_instr_irh *)&ndata.cmd.cmd3.irh;
		tx_info = (union tx_info *)&ndata.cmd.cmd3.ossp[0];
	} else {
		irh = (struct octeon_instr_irh *)&ndata.cmd.cmd2.irh;
		tx_info = (union tx_info *)&ndata.cmd.cmd2.ossp[0];
	}

	if (skb_shinfo(skb)->gso_size) {
		tx_info->s.gso_size = skb_shinfo(skb)->gso_size;
@@ -3904,6 +3920,7 @@ static int liquidio_init_nic_module(struct octeon_device *oct)
	intrmod_cfg->tx_mincnt_trigger = LIO_INTRMOD_TXMINCNT_TRIGGER;
	intrmod_cfg->rx_frames = CFG_GET_OQ_INTR_PKT(octeon_get_conf(oct));
	intrmod_cfg->rx_usecs = CFG_GET_OQ_INTR_TIME(octeon_get_conf(oct));
	intrmod_cfg->tx_frames = CFG_GET_IQ_INTR_PKT(octeon_get_conf(oct));
	dev_dbg(&oct->pci_dev->dev, "Network interfaces ready\n");

	return retval;
+7 −0
Original line number Diff line number Diff line
@@ -310,6 +310,13 @@ union octnet_cmd {

#define   OCTNET_CMD_SIZE     (sizeof(union octnet_cmd))

/*pkiih3 + irh + ossp[0] + ossp[1] + rdp + rptr = 40 bytes */
#define LIO_SOFTCMDRESP_IH2       40
#define LIO_SOFTCMDRESP_IH3       (40 + 8)

#define LIO_PCICMD_O2             24
#define LIO_PCICMD_O3             (24 + 8)

/* Instruction Header(DPI) - for OCTEON-III models */
struct  octeon_instr_ih3 {
#ifdef __BIG_ENDIAN_BITFIELD
+19 −12
Original line number Diff line number Diff line
@@ -793,7 +793,6 @@ int octeon_setup_instr_queues(struct octeon_device *oct)
	union oct_txpciq txpciq;
	int numa_node = cpu_to_node(iq_no % num_online_cpus());

	/* this causes queue 0 to be default queue */
	if (OCTEON_CN6XXX(oct))
		num_descs =
			CFG_GET_NUM_DEF_TX_DESCS(CHIP_FIELD(oct, cn6xxx, conf));
@@ -816,6 +815,7 @@ int octeon_setup_instr_queues(struct octeon_device *oct)
	oct->instr_queue[0]->ifidx = 0;
	txpciq.u64 = 0;
	txpciq.s.q_no = iq_no;
	txpciq.s.pkind = oct->pfvf_hsword.pkind;
	txpciq.s.use_qpg = 0;
	txpciq.s.qpg = 0;
	if (octeon_init_instr_queue(oct, txpciq, num_descs)) {
@@ -835,7 +835,6 @@ int octeon_setup_output_queues(struct octeon_device *oct)
	u32 oq_no = 0;
	int numa_node = cpu_to_node(oq_no % num_online_cpus());

	/* this causes queue 0 to be default queue */
	if (OCTEON_CN6XXX(oct)) {
		num_descs =
			CFG_GET_NUM_DEF_RX_DESCS(CHIP_FIELD(oct, cn6xxx, conf));
@@ -863,11 +862,11 @@ int octeon_setup_output_queues(struct octeon_device *oct)

void octeon_set_io_queues_off(struct octeon_device *oct)
{
	/* Disable the i/p and o/p queues for this Octeon. */

	if (OCTEON_CN6XXX(oct)) {
		octeon_write_csr(oct, CN6XXX_SLI_PKT_INSTR_ENB, 0);
		octeon_write_csr(oct, CN6XXX_SLI_PKT_OUT_ENB, 0);
	}
}

void octeon_set_droq_pkt_op(struct octeon_device *oct,
			    u32 q_no,
@@ -876,6 +875,7 @@ void octeon_set_droq_pkt_op(struct octeon_device *oct,
	u32 reg_val = 0;

	/* Disable the i/p and o/p queues for this Octeon. */
	if (OCTEON_CN6XXX(oct)) {
		reg_val = octeon_read_csr(oct, CN6XXX_SLI_PKT_OUT_ENB);

		if (enable)
@@ -885,6 +885,7 @@ void octeon_set_droq_pkt_op(struct octeon_device *oct,

		octeon_write_csr(oct, CN6XXX_SLI_PKT_OUT_ENB, reg_val);
	}
}

int octeon_init_dispatch_list(struct octeon_device *oct)
{
@@ -1100,6 +1101,12 @@ int octeon_core_drv_init(struct octeon_recv_info *recv_info, void *buf)
	}
	oct->fw_info.app_cap_flags = recv_pkt->rh.r_core_drv_init.app_cap_flags;
	oct->fw_info.app_mode = (u32)recv_pkt->rh.r_core_drv_init.app_mode;
	oct->pfvf_hsword.app_mode = (u32)recv_pkt->rh.r_core_drv_init.app_mode;

	oct->pfvf_hsword.pkind = recv_pkt->rh.r_core_drv_init.pkind;

	for (i = 0; i < oct->num_iqs; i++)
		oct->instr_queue[i]->txpciq.s.pkind = oct->pfvf_hsword.pkind;

	atomic_set(&oct->status, OCT_DEV_CORE_OK);

+6 −0
Original line number Diff line number Diff line
@@ -31,6 +31,7 @@
#include "octeon_network.h"
#include "cn66xx_regs.h"
#include "cn66xx_device.h"
#include "cn23xx_pf_device.h"

#define     CVM_MIN(d1, d2)           (((d1) < (d2)) ? (d1) : (d2))
#define     CVM_MAX(d1, d2)           (((d1) > (d2)) ? (d1) : (d2))
@@ -262,6 +263,11 @@ int octeon_init_droq(struct octeon_device *oct,
		c_pkts_per_intr = (u32)CFG_GET_OQ_PKTS_PER_INTR(conf6x);
		c_refill_threshold =
			(u32)CFG_GET_OQ_REFILL_THRESHOLD(conf6x);
	} else if (OCTEON_CN23XX_PF(oct)) {
		struct octeon_config *conf23 = CHIP_FIELD(oct, cn23xx_pf, conf);

		c_pkts_per_intr = (u32)CFG_GET_OQ_PKTS_PER_INTR(conf23);
		c_refill_threshold = (u32)CFG_GET_OQ_REFILL_THRESHOLD(conf23);
	} else {
		return 1;
	}
+20 −7
Original line number Diff line number Diff line
@@ -35,6 +35,7 @@ octeon_alloc_soft_command_resp(struct octeon_device *oct,
			       u32		       rdatasize)
{
	struct octeon_soft_command *sc;
	struct octeon_instr_ih3  *ih3;
	struct octeon_instr_ih2  *ih2;
	struct octeon_instr_irh *irh;
	struct octeon_instr_rdp *rdp;
@@ -51,10 +52,19 @@ octeon_alloc_soft_command_resp(struct octeon_device *oct,
	/* Add in the response related fields. Opcode and Param are already
	 * there.
	 */
	if (OCTEON_CN23XX_PF(oct)) {
		ih3      = (struct octeon_instr_ih3 *)&sc->cmd.cmd3.ih3;
		rdp     = (struct octeon_instr_rdp *)&sc->cmd.cmd3.rdp;
		irh     = (struct octeon_instr_irh *)&sc->cmd.cmd3.irh;
		/*pkiih3 + irh + ossp[0] + ossp[1] + rdp + rptr = 40 bytes */
		ih3->fsz = LIO_SOFTCMDRESP_IH3;
	} else {
		ih2      = (struct octeon_instr_ih2 *)&sc->cmd.cmd2.ih2;
		rdp     = (struct octeon_instr_rdp *)&sc->cmd.cmd2.rdp;
		irh     = (struct octeon_instr_irh *)&sc->cmd.cmd2.irh;
	ih2->fsz = 40; /* irh + ossp[0] + ossp[1] + rdp + rptr = 40 bytes */
		/* irh + ossp[0] + ossp[1] + rdp + rptr = 40 bytes */
		ih2->fsz = LIO_SOFTCMDRESP_IH2;
	}

	irh->rflag = 1; /* a response is required */

@@ -63,6 +73,9 @@ octeon_alloc_soft_command_resp(struct octeon_device *oct,

	*sc->status_word = COMPLETION_WORD_INIT;

	if (OCTEON_CN23XX_PF(oct))
		sc->cmd.cmd3.rptr =  sc->dmarptr;
	else
		sc->cmd.cmd2.rptr =  sc->dmarptr;

	sc->wait_time = 1000;
@@ -179,8 +192,8 @@ octnet_send_nic_ctrl_pkt(struct octeon_device *oct,
	retval = octeon_send_soft_command(oct, sc);
	if (retval == IQ_SEND_FAILED) {
		octeon_free_soft_command(oct, sc);
		dev_err(&oct->pci_dev->dev, "%s soft command:%d send failed status: %x\n",
			__func__, nctrl->ncmd.s.cmd, retval);
		dev_err(&oct->pci_dev->dev, "%s pf_num:%d soft command:%d send failed status: %x\n",
			__func__, oct->pf_num, nctrl->ncmd.s.cmd, retval);
		spin_unlock_bh(&oct->cmd_resp_wqlock);
		return -1;
	}
Loading