summaryrefslogtreecommitdiffstats
path: root/drivers/crypto
diff options
context:
space:
mode:
authorAtul Gupta <atul.gupta@chelsio.com>2019-02-18 05:04:37 -0500
committerHerbert Xu <herbert@gondor.apana.org.au>2019-02-28 01:17:58 -0500
commit8cd9d183731a8b54e7ca40de1c72e3c6bec40113 (patch)
tree794efc6f36284fc23a3e57c704f604274bfdfde2 /drivers/crypto
parentbf432e72c170f28c08bb8c0f45356a5a48a7cae2 (diff)
crypto: chelsio - Fixed Traffic Stall
Fixed Traffic Stall caused by - Subcommands except last should have more bit set - For esn case subcommand is required for linear skb only - Also Optimized is_eth_imm usage Signed-off-by: Atul Gupta <atul.gupta@chelsio.com> Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>
Diffstat (limited to 'drivers/crypto')
-rw-r--r--drivers/crypto/chelsio/chcr_ipsec.c33
1 files changed, 20 insertions, 13 deletions
diff --git a/drivers/crypto/chelsio/chcr_ipsec.c b/drivers/crypto/chelsio/chcr_ipsec.c
index 0c826d0e1bfc..2f60049361ef 100644
--- a/drivers/crypto/chelsio/chcr_ipsec.c
+++ b/drivers/crypto/chelsio/chcr_ipsec.c
@@ -336,7 +336,8 @@ static inline int is_eth_imm(const struct sk_buff *skb,
336} 336}
337 337
338static inline unsigned int calc_tx_sec_flits(const struct sk_buff *skb, 338static inline unsigned int calc_tx_sec_flits(const struct sk_buff *skb,
339 struct ipsec_sa_entry *sa_entry) 339 struct ipsec_sa_entry *sa_entry,
340 bool *immediate)
340{ 341{
341 unsigned int kctx_len; 342 unsigned int kctx_len;
342 unsigned int flits; 343 unsigned int flits;
@@ -354,8 +355,10 @@ static inline unsigned int calc_tx_sec_flits(const struct sk_buff *skb,
354 * TX Packet header plus the skb data in the Work Request. 355 * TX Packet header plus the skb data in the Work Request.
355 */ 356 */
356 357
357 if (hdrlen) 358 if (hdrlen) {
359 *immediate = true;
358 return DIV_ROUND_UP(skb->len + hdrlen, sizeof(__be64)); 360 return DIV_ROUND_UP(skb->len + hdrlen, sizeof(__be64));
361 }
359 362
360 flits = sgl_len(skb_shinfo(skb)->nr_frags + 1); 363 flits = sgl_len(skb_shinfo(skb)->nr_frags + 1);
361 364
@@ -418,7 +421,7 @@ inline void *copy_esn_pktxt(struct sk_buff *skb,
418 iv = skb_transport_header(skb) + sizeof(struct ip_esp_hdr); 421 iv = skb_transport_header(skb) + sizeof(struct ip_esp_hdr);
419 memcpy(aadiv->iv, iv, 8); 422 memcpy(aadiv->iv, iv, 8);
420 423
421 if (is_eth_imm(skb, sa_entry)) { 424 if (is_eth_imm(skb, sa_entry) && !skb_is_nonlinear(skb)) {
422 sc_imm = (struct ulptx_idata *)(pos + 425 sc_imm = (struct ulptx_idata *)(pos +
423 (DIV_ROUND_UP(sizeof(struct chcr_ipsec_aadiv), 426 (DIV_ROUND_UP(sizeof(struct chcr_ipsec_aadiv),
424 sizeof(__be64)) << 3)); 427 sizeof(__be64)) << 3));
@@ -531,15 +534,18 @@ inline void *chcr_crypto_wreq(struct sk_buff *skb,
531 struct adapter *adap = pi->adapter; 534 struct adapter *adap = pi->adapter;
532 unsigned int ivsize = GCM_ESP_IV_SIZE; 535 unsigned int ivsize = GCM_ESP_IV_SIZE;
533 struct chcr_ipsec_wr *wr; 536 struct chcr_ipsec_wr *wr;
537 bool immediate = false;
534 u16 immdatalen = 0; 538 u16 immdatalen = 0;
535 unsigned int flits; 539 unsigned int flits;
536 u32 ivinoffset; 540 u32 ivinoffset;
537 u32 aadstart; 541 u32 aadstart;
538 u32 aadstop; 542 u32 aadstop;
539 u32 ciphstart; 543 u32 ciphstart;
544 u16 sc_more = 0;
540 u32 ivdrop = 0; 545 u32 ivdrop = 0;
541 u32 esnlen = 0; 546 u32 esnlen = 0;
542 u32 wr_mid; 547 u32 wr_mid;
548 u16 ndesc;
543 int qidx = skb_get_queue_mapping(skb); 549 int qidx = skb_get_queue_mapping(skb);
544 struct sge_eth_txq *q = &adap->sge.ethtxq[qidx + pi->first_qset]; 550 struct sge_eth_txq *q = &adap->sge.ethtxq[qidx + pi->first_qset];
545 unsigned int kctx_len = sa_entry->kctx_len; 551 unsigned int kctx_len = sa_entry->kctx_len;
@@ -547,20 +553,24 @@ inline void *chcr_crypto_wreq(struct sk_buff *skb,
547 553
548 atomic_inc(&adap->chcr_stats.ipsec_cnt); 554 atomic_inc(&adap->chcr_stats.ipsec_cnt);
549 555
550 flits = calc_tx_sec_flits(skb, sa_entry); 556 flits = calc_tx_sec_flits(skb, sa_entry, &immediate);
557 ndesc = DIV_ROUND_UP(flits, 2);
551 if (sa_entry->esn) 558 if (sa_entry->esn)
552 ivdrop = 1; 559 ivdrop = 1;
553 560
554 if (is_eth_imm(skb, sa_entry)) 561 if (immediate)
555 immdatalen = skb->len; 562 immdatalen = skb->len;
556 563
557 if (sa_entry->esn) 564 if (sa_entry->esn) {
558 esnlen = sizeof(struct chcr_ipsec_aadiv); 565 esnlen = sizeof(struct chcr_ipsec_aadiv);
566 if (!skb_is_nonlinear(skb))
567 sc_more = 1;
568 }
559 569
560 /* WR Header */ 570 /* WR Header */
561 wr = (struct chcr_ipsec_wr *)pos; 571 wr = (struct chcr_ipsec_wr *)pos;
562 wr->wreq.op_to_compl = htonl(FW_WR_OP_V(FW_ULPTX_WR)); 572 wr->wreq.op_to_compl = htonl(FW_WR_OP_V(FW_ULPTX_WR));
563 wr_mid = FW_CRYPTO_LOOKASIDE_WR_LEN16_V(DIV_ROUND_UP(flits, 2)); 573 wr_mid = FW_CRYPTO_LOOKASIDE_WR_LEN16_V(ndesc);
564 574
565 if (unlikely(credits < ETHTXQ_STOP_THRES)) { 575 if (unlikely(credits < ETHTXQ_STOP_THRES)) {
566 netif_tx_stop_queue(q->txq); 576 netif_tx_stop_queue(q->txq);
@@ -572,10 +582,10 @@ inline void *chcr_crypto_wreq(struct sk_buff *skb,
572 582
573 /* ULPTX */ 583 /* ULPTX */
574 wr->req.ulptx.cmd_dest = FILL_ULPTX_CMD_DEST(pi->port_id, qid); 584 wr->req.ulptx.cmd_dest = FILL_ULPTX_CMD_DEST(pi->port_id, qid);
575 wr->req.ulptx.len = htonl(DIV_ROUND_UP(flits, 2) - 1); 585 wr->req.ulptx.len = htonl(ndesc - 1);
576 586
577 /* Sub-command */ 587 /* Sub-command */
578 wr->req.sc_imm.cmd_more = FILL_CMD_MORE(!immdatalen); 588 wr->req.sc_imm.cmd_more = FILL_CMD_MORE(!immdatalen || sc_more);
579 wr->req.sc_imm.len = cpu_to_be32(sizeof(struct cpl_tx_sec_pdu) + 589 wr->req.sc_imm.len = cpu_to_be32(sizeof(struct cpl_tx_sec_pdu) +
580 sizeof(wr->req.key_ctx) + 590 sizeof(wr->req.key_ctx) +
581 kctx_len + 591 kctx_len +
@@ -698,7 +708,7 @@ out_free: dev_kfree_skb_any(skb);
698 708
699 cxgb4_reclaim_completed_tx(adap, &q->q, true); 709 cxgb4_reclaim_completed_tx(adap, &q->q, true);
700 710
701 flits = calc_tx_sec_flits(skb, sa_entry); 711 flits = calc_tx_sec_flits(skb, sa_entry, &immediate);
702 ndesc = flits_to_desc(flits); 712 ndesc = flits_to_desc(flits);
703 credits = txq_avail(&q->q) - ndesc; 713 credits = txq_avail(&q->q) - ndesc;
704 714
@@ -711,9 +721,6 @@ out_free: dev_kfree_skb_any(skb);
711 return NETDEV_TX_BUSY; 721 return NETDEV_TX_BUSY;
712 } 722 }
713 723
714 if (is_eth_imm(skb, sa_entry))
715 immediate = true;
716
717 if (!immediate && 724 if (!immediate &&
718 unlikely(cxgb4_map_skb(adap->pdev_dev, skb, addr) < 0)) { 725 unlikely(cxgb4_map_skb(adap->pdev_dev, skb, addr) < 0)) {
719 q->mapping_err++; 726 q->mapping_err++;