ipsec: fix async buffer leak
[vpp.git] / src / vnet / ipsec / esp_decrypt.c
index b700f2c..905b13a 100644 (file)
@@ -748,10 +748,11 @@ out:
 }
 
 static_always_inline void
-esp_decrypt_post_crypto (vlib_main_t * vm, vlib_node_runtime_t * node,
-                        esp_decrypt_packet_data_t * pd,
-                        esp_decrypt_packet_data2_t * pd2, vlib_buffer_t * b,
-                        u16 * next, int is_ip6, int is_tun, int is_async)
+esp_decrypt_post_crypto (vlib_main_t *vm, const vlib_node_runtime_t *node,
+                        const esp_decrypt_packet_data_t *pd,
+                        const esp_decrypt_packet_data2_t *pd2,
+                        vlib_buffer_t *b, u16 *next, int is_ip6, int is_tun,
+                        int is_async)
 {
   ipsec_sa_t *sa0 = ipsec_sa_get (pd->sa_index);
   vlib_buffer_t *lb = b;
@@ -790,7 +791,11 @@ esp_decrypt_post_crypto (vlib_main_t * vm, vlib_node_runtime_t * node,
       return;
     }
 
-  ipsec_sa_anti_replay_advance (sa0, pd->seq, pd->seq_hi);
+  u64 n_lost =
+    ipsec_sa_anti_replay_advance (sa0, vm->thread_index, pd->seq, pd->seq_hi);
+
+  vlib_prefetch_simple_counter (&ipsec_sa_lost_counters, vm->thread_index,
+                               pd->sa_index);
 
   if (pd->is_chain)
     {
@@ -1011,6 +1016,10 @@ esp_decrypt_post_crypto (vlib_main_t * vm, vlib_node_runtime_t * node,
            }
        }
     }
+
+  if (PREDICT_FALSE (n_lost))
+    vlib_increment_simple_counter (&ipsec_sa_lost_counters, vm->thread_index,
+                                  pd->sa_index, n_lost);
 }
 
 always_inline uword
@@ -1068,9 +1077,9 @@ esp_decrypt_inline (vlib_main_t *vm, vlib_node_runtime_t *node,
          u8 *p;
          vlib_prefetch_buffer_header (b[2], LOAD);
          p = vlib_buffer_get_current (b[1]);
-         CLIB_PREFETCH (p, CLIB_CACHE_LINE_BYTES, LOAD);
+         clib_prefetch_load (p);
          p -= CLIB_CACHE_LINE_BYTES;
-         CLIB_PREFETCH (p, CLIB_CACHE_LINE_BYTES, LOAD);
+         clib_prefetch_load (p);
        }
 
       u32 n_bufs = vlib_buffer_chain_linearize (vm, b[0]);
@@ -1095,7 +1104,7 @@ esp_decrypt_inline (vlib_main_t *vm, vlib_node_runtime_t *node,
          sa0 = ipsec_sa_get (current_sa_index);
 
          /* fetch the second cacheline ASAP */
-         CLIB_PREFETCH (sa0->cacheline1, CLIB_CACHE_LINE_BYTES, LOAD);
+         clib_prefetch_load (sa0->cacheline1);
          cpd.icv_sz = sa0->integ_icv_size;
          cpd.iv_sz = sa0->crypto_iv_size;
          cpd.flags = sa0->flags;
@@ -1245,7 +1254,7 @@ esp_decrypt_inline (vlib_main_t *vm, vlib_node_runtime_t *node,
        {
          n_noop += esp_async_recycle_failed_submit (
            vm, *async_frame, node, ESP_DECRYPT_ERROR_CRYPTO_ENGINE_ERROR,
-           n_sync, noop_bi, noop_nexts, ESP_DECRYPT_NEXT_DROP);
+           n_noop, noop_bi, noop_nexts, ESP_DECRYPT_NEXT_DROP);
          vnet_crypto_async_reset_frame (*async_frame);
          vnet_crypto_async_free_frame (vm, *async_frame);
        }