diff options
author | David S. Miller <davem@davemloft.net> | 2013-02-14 15:57:38 -0500 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2013-02-14 15:57:38 -0500 |
commit | 9754e293491e3a4e6c1ac020d25140b1ed3d9cd2 (patch) | |
tree | 72273ca8e34846ac586a520b792c147bd95cd498 /net/core | |
parent | ba7797119b486bb5992beda74bdb26be9a291b46 (diff) |
net: Don't write to current task flags on every packet received.
Even for non-pfmalloc SKBs, __netif_receive_skb() will do a
tsk_restore_flags() on current unconditionally.
Make __netif_receive_skb() a shim around the existing code, renamed to
__netif_receive_skb_core(). Let __netif_receive_skb() wrap the
__netif_receive_skb_core() call with the task flag modifications, if
necessary.
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/core')
-rw-r--r-- | net/core/dev.c | 46 |
1 files changed, 28 insertions, 18 deletions
diff --git a/net/core/dev.c b/net/core/dev.c index 2f31bf97ba65..f44473696b8b 100644 --- a/net/core/dev.c +++ b/net/core/dev.c | |||
@@ -3457,7 +3457,7 @@ static bool skb_pfmemalloc_protocol(struct sk_buff *skb) | |||
3457 | } | 3457 | } |
3458 | } | 3458 | } |
3459 | 3459 | ||
3460 | static int __netif_receive_skb(struct sk_buff *skb) | 3460 | static int __netif_receive_skb_core(struct sk_buff *skb, bool pfmemalloc) |
3461 | { | 3461 | { |
3462 | struct packet_type *ptype, *pt_prev; | 3462 | struct packet_type *ptype, *pt_prev; |
3463 | rx_handler_func_t *rx_handler; | 3463 | rx_handler_func_t *rx_handler; |
@@ -3466,24 +3466,11 @@ static int __netif_receive_skb(struct sk_buff *skb) | |||
3466 | bool deliver_exact = false; | 3466 | bool deliver_exact = false; |
3467 | int ret = NET_RX_DROP; | 3467 | int ret = NET_RX_DROP; |
3468 | __be16 type; | 3468 | __be16 type; |
3469 | unsigned long pflags = current->flags; | ||
3470 | 3469 | ||
3471 | net_timestamp_check(!netdev_tstamp_prequeue, skb); | 3470 | net_timestamp_check(!netdev_tstamp_prequeue, skb); |
3472 | 3471 | ||
3473 | trace_netif_receive_skb(skb); | 3472 | trace_netif_receive_skb(skb); |
3474 | 3473 | ||
3475 | /* | ||
3476 | * PFMEMALLOC skbs are special, they should | ||
3477 | * - be delivered to SOCK_MEMALLOC sockets only | ||
3478 | * - stay away from userspace | ||
3479 | * - have bounded memory usage | ||
3480 | * | ||
3481 | * Use PF_MEMALLOC as this saves us from propagating the allocation | ||
3482 | * context down to all allocation sites. | ||
3483 | */ | ||
3484 | if (sk_memalloc_socks() && skb_pfmemalloc(skb)) | ||
3485 | current->flags |= PF_MEMALLOC; | ||
3486 | |||
3487 | /* if we've gotten here through NAPI, check netpoll */ | 3474 | /* if we've gotten here through NAPI, check netpoll */ |
3488 | if (netpoll_receive_skb(skb)) | 3475 | if (netpoll_receive_skb(skb)) |
3489 | goto out; | 3476 | goto out; |
@@ -3517,7 +3504,7 @@ another_round: | |||
3517 | } | 3504 | } |
3518 | #endif | 3505 | #endif |
3519 | 3506 | ||
3520 | if (sk_memalloc_socks() && skb_pfmemalloc(skb)) | 3507 | if (pfmemalloc) |
3521 | goto skip_taps; | 3508 | goto skip_taps; |
3522 | 3509 | ||
3523 | list_for_each_entry_rcu(ptype, &ptype_all, list) { | 3510 | list_for_each_entry_rcu(ptype, &ptype_all, list) { |
@@ -3536,8 +3523,7 @@ skip_taps: | |||
3536 | ncls: | 3523 | ncls: |
3537 | #endif | 3524 | #endif |
3538 | 3525 | ||
3539 | if (sk_memalloc_socks() && skb_pfmemalloc(skb) | 3526 | if (pfmemalloc && !skb_pfmemalloc_protocol(skb)) |
3540 | && !skb_pfmemalloc_protocol(skb)) | ||
3541 | goto drop; | 3527 | goto drop; |
3542 | 3528 | ||
3543 | if (vlan_tx_tag_present(skb)) { | 3529 | if (vlan_tx_tag_present(skb)) { |
@@ -3607,7 +3593,31 @@ drop: | |||
3607 | unlock: | 3593 | unlock: |
3608 | rcu_read_unlock(); | 3594 | rcu_read_unlock(); |
3609 | out: | 3595 | out: |
3610 | tsk_restore_flags(current, pflags, PF_MEMALLOC); | 3596 | return ret; |
3597 | } | ||
3598 | |||
3599 | static int __netif_receive_skb(struct sk_buff *skb) | ||
3600 | { | ||
3601 | int ret; | ||
3602 | |||
3603 | if (sk_memalloc_socks() && skb_pfmemalloc(skb)) { | ||
3604 | unsigned long pflags = current->flags; | ||
3605 | |||
3606 | /* | ||
3607 | * PFMEMALLOC skbs are special, they should | ||
3608 | * - be delivered to SOCK_MEMALLOC sockets only | ||
3609 | * - stay away from userspace | ||
3610 | * - have bounded memory usage | ||
3611 | * | ||
3612 | * Use PF_MEMALLOC as this saves us from propagating the allocation | ||
3613 | * context down to all allocation sites. | ||
3614 | */ | ||
3615 | current->flags |= PF_MEMALLOC; | ||
3616 | ret = __netif_receive_skb_core(skb, true); | ||
3617 | tsk_restore_flags(current, pflags, PF_MEMALLOC); | ||
3618 | } else | ||
3619 | ret = __netif_receive_skb_core(skb, false); | ||
3620 | |||
3611 | return ret; | 3621 | return ret; |
3612 | } | 3622 | } |
3613 | 3623 | ||