diff options
author | Jason A. Donenfeld <Jason@zx2c4.com> | 2020-04-22 02:13:42 -0600 |
---|---|---|
committer | Jason A. Donenfeld <Jason@zx2c4.com> | 2020-04-22 02:13:42 -0600 |
commit | 0181fa1ec0cfd002b49480c116ca3d7a59ddd99a (patch) | |
tree | 33c8375f00bfd38e7b648535b26c6493c2474b38 /drivers/net/wireguard/symmetric.c | |
parent | 71a7269d778f9a131d1cecbfdb3cd00c248131a8 (diff) | |
download | wireguard-linux-trimmed-jd/unified-crypt-queue.tar.gz wireguard-linux-trimmed-jd/unified-crypt-queue.zip |
wireguard: unify encryption and decryption workersjd/unified-crypt-queue
By unifying encryption and decryption workers into a single worker, this
ensures that encryption and decryption happening at the same time does
not result in workqueues stepping on each other and creating
unnecessary work for the scheduler.
Signed-off-by: Jason A. Donenfeld <Jason@zx2c4.com>
Diffstat (limited to 'drivers/net/wireguard/symmetric.c')
-rw-r--r-- | drivers/net/wireguard/symmetric.c | 51 |
1 files changed, 24 insertions, 27 deletions
diff --git a/drivers/net/wireguard/symmetric.c b/drivers/net/wireguard/symmetric.c index 6e16fec..a1fd394 100644 --- a/drivers/net/wireguard/symmetric.c +++ b/drivers/net/wireguard/symmetric.c @@ -134,40 +134,37 @@ static bool decrypt_packet(struct sk_buff *skb, struct noise_symmetric_key *key) return true; } -void wg_packet_encrypt_worker(struct work_struct *work) +void wg_packet_crypt_worker(struct work_struct *work) { struct crypt_queue *queue = container_of(work, struct multicore_worker, work)->ptr; struct sk_buff *first, *skb, *next; while ((first = ptr_ring_consume_bh(&queue->ring)) != NULL) { - enum packet_state state = PACKET_STATE_ENCRYPTED; - - skb_list_walk_safe(first, skb, next) { - if (likely(encrypt_packet(skb, - PACKET_CB(first)->keypair))) { - wg_reset_packet(skb); - } else { - state = PACKET_STATE_DEAD; - break; + switch (atomic_read_acquire(&PACKET_CB(first)->state)) { + case PACKET_STATE_NOT_ENCRYPTED: { + enum packet_state state = PACKET_STATE_ENCRYPTED; + + skb_list_walk_safe(first, skb, next) { + if (likely(encrypt_packet(skb, + PACKET_CB(first)->keypair))) { + wg_reset_packet(skb); + } else { + state = PACKET_STATE_DEAD; + break; + } } + wg_queue_enqueue_per_peer(&PACKET_PEER(first)->tx_queue, + first, state); + break; + } + case PACKET_STATE_NOT_DECRYPTED: { + enum packet_state state = likely(decrypt_packet(first, + &PACKET_CB(first)->keypair->receiving)) ? + PACKET_STATE_DECRYPTED : PACKET_STATE_DEAD; + wg_queue_enqueue_per_peer_napi(first, state); + break; + } } - wg_queue_enqueue_per_peer(&PACKET_PEER(first)->tx_queue, first, - state); - } -} - -void wg_packet_decrypt_worker(struct work_struct *work) -{ - struct crypt_queue *queue = container_of(work, struct multicore_worker, - work)->ptr; - struct sk_buff *skb; - - while ((skb = ptr_ring_consume_bh(&queue->ring)) != NULL) { - enum packet_state state = likely(decrypt_packet(skb, - &PACKET_CB(skb)->keypair->receiving)) ? - PACKET_STATE_DECRYPTED : PACKET_STATE_DEAD; - wg_queue_enqueue_per_peer_napi(skb, state); } } - |