DPDK patches and discussions
 help / color / mirror / Atom feed
From: Cristian Dumitrescu <cristian.dumitrescu@intel.com>
To: dev@dpdk.org
Subject: [dpdk-dev] [PATCH] pipeline: add drop instruction to the SWX pipeline
Date: Fri, 26 Mar 2021 22:11:08 +0000
Message-ID: <20210326221108.17896-1-cristian.dumitrescu@intel.com> (raw)

Enabled the TX instruction to accept an immediate value for the output
port argument. The drop instruction is simply an alias to the TX
instruction for the last output port of the pipeline.

Signed-off-by: Cristian Dumitrescu <cristian.dumitrescu@intel.com>
---
 examples/pipeline/examples/vxlan.spec  |   3 +-
 lib/librte_pipeline/rte_swx_pipeline.c | 109 +++++++++++++++++++++----
 2 files changed, 96 insertions(+), 16 deletions(-)

diff --git a/examples/pipeline/examples/vxlan.spec b/examples/pipeline/examples/vxlan.spec
index b3f28630d..347dca29d 100644
--- a/examples/pipeline/examples/vxlan.spec
+++ b/examples/pipeline/examples/vxlan.spec
@@ -134,8 +134,7 @@ action vxlan_encap args instanceof vxlan_encap_args_t {
 }
 
 action drop args none {
-	mov m.port_out 4
-	tx m.port_out
+	drop
 }
 
 //
diff --git a/lib/librte_pipeline/rte_swx_pipeline.c b/lib/librte_pipeline/rte_swx_pipeline.c
index 6a19b1450..48ac250c1 100644
--- a/lib/librte_pipeline/rte_swx_pipeline.c
+++ b/lib/librte_pipeline/rte_swx_pipeline.c
@@ -281,8 +281,11 @@ enum instruction_type {
 	/* rx m.port_in */
 	INSTR_RX,
 
-	/* tx m.port_out */
-	INSTR_TX,
+	/* tx port_out
+	 * port_out = MI
+	 */
+	INSTR_TX,   /* port_out = M */
+	INSTR_TX_I, /* port_out = I */
 
 	/* extract h.header */
 	INSTR_HDR_EXTRACT,
@@ -582,9 +585,15 @@ struct instr_operand {
 
 struct instr_io {
 	struct {
-		uint8_t offset;
-		uint8_t n_bits;
-		uint8_t pad[2];
+		union {
+			struct {
+				uint8_t offset;
+				uint8_t n_bits;
+				uint8_t pad[2];
+			};
+
+			uint32_t val;
+		};
 	} io;
 
 	struct {
@@ -2490,6 +2499,19 @@ metadata_free(struct rte_swx_pipeline *p)
 /*
  * Instruction.
  */
+static int
+instruction_is_tx(enum instruction_type type)
+{
+	switch (type) {
+	case INSTR_TX:
+	case INSTR_TX_I:
+		return 1;
+
+	default:
+		return 0;
+	}
+}
+
 static int
 instruction_is_jmp(struct instruction *instr)
 {
@@ -2732,16 +2754,42 @@ instr_tx_translate(struct rte_swx_pipeline *p,
 		   struct instruction *instr,
 		   struct instruction_data *data __rte_unused)
 {
+	char *port = tokens[1];
 	struct field *f;
+	uint32_t port_val;
 
 	CHECK(n_tokens == 2, EINVAL);
 
-	f = metadata_field_parse(p, tokens[1]);
-	CHECK(f, EINVAL);
+	f = metadata_field_parse(p, port);
+	if (f) {
+		instr->type = INSTR_TX;
+		instr->io.io.offset = f->offset / 8;
+		instr->io.io.n_bits = f->n_bits;
+		return 0;
+	}
 
-	instr->type = INSTR_TX;
-	instr->io.io.offset = f->offset / 8;
-	instr->io.io.n_bits = f->n_bits;
+	/* TX_I. */
+	port_val = strtoul(port, &port, 0);
+	CHECK(!port[0], EINVAL);
+
+	instr->type = INSTR_TX_I;
+	instr->io.io.val = port_val;
+	return 0;
+}
+
+static int
+instr_drop_translate(struct rte_swx_pipeline *p,
+		     struct action *action __rte_unused,
+		     char **tokens __rte_unused,
+		     int n_tokens,
+		     struct instruction *instr,
+		     struct instruction_data *data __rte_unused)
+{
+	CHECK(n_tokens == 1, EINVAL);
+
+	/* TX_I. */
+	instr->type = INSTR_TX_I;
+	instr->io.io.val = p->n_ports_out - 1;
 	return 0;
 }
 
@@ -2829,6 +2877,30 @@ instr_tx_exec(struct rte_swx_pipeline *p)
 	instr_rx_exec(p);
 }
 
+static inline void
+instr_tx_i_exec(struct rte_swx_pipeline *p)
+{
+	struct thread *t = &p->threads[p->thread_id];
+	struct instruction *ip = t->ip;
+	uint64_t port_id = ip->io.io.val;
+	struct port_out_runtime *port = &p->out[port_id];
+	struct rte_swx_pkt *pkt = &t->pkt;
+
+	TRACE("[Thread %2u]: tx (i) 1 pkt to port %u\n",
+	      p->thread_id,
+	      (uint32_t)port_id);
+
+	/* Headers. */
+	emit_handler(t);
+
+	/* Packet. */
+	port->pkt_tx(port->obj, pkt);
+
+	/* Thread. */
+	thread_ip_reset(p, t);
+	instr_rx_exec(p);
+}
+
 /*
  * extract.
  */
@@ -7308,6 +7380,14 @@ instr_translate(struct rte_swx_pipeline *p,
 					  instr,
 					  data);
 
+	if (!strcmp(tokens[tpos], "drop"))
+		return instr_drop_translate(p,
+					    action,
+					    &tokens[tpos],
+					    n_tokens - tpos,
+					    instr,
+					    data);
+
 	if (!strcmp(tokens[tpos], "extract"))
 		return instr_hdr_extract_translate(p,
 						   action,
@@ -7694,7 +7774,7 @@ instr_verify(struct rte_swx_pipeline *p __rte_unused,
 		for (i = 0; i < n_instructions; i++) {
 			type = instr[i].type;
 
-			if (type == INSTR_TX)
+			if (instruction_is_tx(type))
 				break;
 		}
 		CHECK(i < n_instructions, EINVAL);
@@ -7703,7 +7783,7 @@ instr_verify(struct rte_swx_pipeline *p __rte_unused,
 		 * jump.
 		 */
 		type = instr[n_instructions - 1].type;
-		CHECK((type == INSTR_TX) || (type == INSTR_JMP), EINVAL);
+		CHECK(instruction_is_tx(type) || (type == INSTR_JMP), EINVAL);
 	}
 
 	if (a) {
@@ -7714,7 +7794,7 @@ instr_verify(struct rte_swx_pipeline *p __rte_unused,
 		for (i = 0; i < n_instructions; i++) {
 			type = instr[i].type;
 
-			if ((type == INSTR_RETURN) || (type == INSTR_TX))
+			if ((type == INSTR_RETURN) || instruction_is_tx(type))
 				break;
 		}
 		CHECK(i < n_instructions, EINVAL);
@@ -7794,7 +7874,7 @@ instr_pattern_emit_many_tx_detect(struct instruction *instr,
 	if (!i)
 		return 0;
 
-	if (instr[i].type != INSTR_TX)
+	if (!instruction_is_tx(instr[i].type))
 		return 0;
 
 	if (data[i].n_users)
@@ -8031,6 +8111,7 @@ typedef void (*instr_exec_t)(struct rte_swx_pipeline *);
 static instr_exec_t instruction_table[] = {
 	[INSTR_RX] = instr_rx_exec,
 	[INSTR_TX] = instr_tx_exec,
+	[INSTR_TX_I] = instr_tx_i_exec,
 
 	[INSTR_HDR_EXTRACT] = instr_hdr_extract_exec,
 	[INSTR_HDR_EXTRACT2] = instr_hdr_extract2_exec,
-- 
2.17.1


             reply	other threads:[~2021-03-26 22:11 UTC|newest]

Thread overview: 2+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2021-03-26 22:11 Cristian Dumitrescu [this message]
2021-04-20  0:22 ` Thomas Monjalon

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20210326221108.17896-1-cristian.dumitrescu@intel.com \
    --to=cristian.dumitrescu@intel.com \
    --cc=dev@dpdk.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link

DPDK patches and discussions

This inbox may be cloned and mirrored by anyone:

	git clone --mirror https://inbox.dpdk.org/dev/0 dev/git/0.git

	# If you have public-inbox 1.1+ installed, you may
	# initialize and index your mirror using the following commands:
	public-inbox-init -V2 dev dev/ https://inbox.dpdk.org/dev \
		dev@dpdk.org
	public-inbox-index dev

Example config snippet for mirrors.
Newsgroup available over NNTP:
	nntp://inbox.dpdk.org/inbox.dpdk.dev


AGPL code for this site: git clone https://public-inbox.org/public-inbox.git