diff options
author | Eric Dumazet <edumazet@google.com> | 2014-10-10 07:48:17 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2014-10-10 15:37:28 -0400 |
commit | 98226208c8a1fe5834e92d827a2a1e8051a17943 (patch) | |
tree | 09bc0b1ebf516dcba2d21b93d98dc0e3d2bc3181 /drivers/net/ethernet/mellanox | |
parent | ec91698360b3818ff426488a1529811f7a7ab87f (diff) |
mlx4: fix race accessing page->_count
This is illegal to use atomic_set(&page->_count, ...) even if we 'own'
the page. Other entities in the kernel need to use get_page_unless_zero()
to get a reference to the page before testing page properties, so we could
loose a refcount increment.
Signed-off-by: Eric Dumazet <edumazet@google.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/ethernet/mellanox')
-rw-r--r-- | drivers/net/ethernet/mellanox/mlx4/en_rx.c | 6 |
1 files changed, 3 insertions, 3 deletions
diff --git a/drivers/net/ethernet/mellanox/mlx4/en_rx.c b/drivers/net/ethernet/mellanox/mlx4/en_rx.c index a33048ee9621..01660c595f5c 100644 --- a/drivers/net/ethernet/mellanox/mlx4/en_rx.c +++ b/drivers/net/ethernet/mellanox/mlx4/en_rx.c | |||
@@ -76,10 +76,10 @@ static int mlx4_alloc_pages(struct mlx4_en_priv *priv, | |||
76 | page_alloc->dma = dma; | 76 | page_alloc->dma = dma; |
77 | page_alloc->page_offset = frag_info->frag_align; | 77 | page_alloc->page_offset = frag_info->frag_align; |
78 | /* Not doing get_page() for each frag is a big win | 78 | /* Not doing get_page() for each frag is a big win |
79 | * on asymetric workloads. | 79 | * on asymetric workloads. Note we can not use atomic_set(). |
80 | */ | 80 | */ |
81 | atomic_set(&page->_count, | 81 | atomic_add(page_alloc->page_size / frag_info->frag_stride - 1, |
82 | page_alloc->page_size / frag_info->frag_stride); | 82 | &page->_count); |
83 | return 0; | 83 | return 0; |
84 | } | 84 | } |
85 | 85 | ||