diff options
| author | Eric Dumazet <eric.dumazet@gmail.com> | 2010-08-26 02:02:17 -0400 |
|---|---|---|
| committer | David S. Miller <davem@davemloft.net> | 2010-08-26 02:02:17 -0400 |
| commit | c5ed63d66f24fd4f7089b5a6e087b0ce7202aa8e (patch) | |
| tree | 140df25fef28c94f9ec1e5c29b4a8d0876da2fe8 | |
| parent | ad1af0fedba14f82b240a03fe20eb9b2fdbd0357 (diff) | |
tcp: fix three tcp sysctls tuning
As discovered by Anton Blanchard, current code to autotune
tcp_death_row.sysctl_max_tw_buckets, sysctl_tcp_max_orphans and
sysctl_max_syn_backlog makes little sense.
The bigger a page is, the less tcp_max_orphans is : 4096 on a 512GB
machine in Anton's case.
(tcp_hashinfo.bhash_size * sizeof(struct inet_bind_hashbucket))
is much bigger if spinlock debugging is on. Its wrong to select bigger
limits in this case (where kernel structures are also bigger)
bhash_size max is 65536, and we get this value even for small machines.
A better ground is to use size of ehash table, this also makes code
shorter and more obvious.
Based on a patch from Anton, and another from David.
Reported-and-tested-by: Anton Blanchard <anton@samba.org>
Signed-off-by: Eric Dumazet <eric.dumazet@gmail.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
| -rw-r--r-- | net/ipv4/tcp.c | 24 |
1 files changed, 7 insertions, 17 deletions
diff --git a/net/ipv4/tcp.c b/net/ipv4/tcp.c index 197b9b77fa3e..e2add5ff9cb1 100644 --- a/net/ipv4/tcp.c +++ b/net/ipv4/tcp.c | |||
| @@ -3209,7 +3209,7 @@ void __init tcp_init(void) | |||
| 3209 | { | 3209 | { |
| 3210 | struct sk_buff *skb = NULL; | 3210 | struct sk_buff *skb = NULL; |
| 3211 | unsigned long nr_pages, limit; | 3211 | unsigned long nr_pages, limit; |
| 3212 | int order, i, max_share; | 3212 | int i, max_share, cnt; |
| 3213 | unsigned long jiffy = jiffies; | 3213 | unsigned long jiffy = jiffies; |
| 3214 | 3214 | ||
| 3215 | BUILD_BUG_ON(sizeof(struct tcp_skb_cb) > sizeof(skb->cb)); | 3215 | BUILD_BUG_ON(sizeof(struct tcp_skb_cb) > sizeof(skb->cb)); |
| @@ -3258,22 +3258,12 @@ void __init tcp_init(void) | |||
| 3258 | INIT_HLIST_HEAD(&tcp_hashinfo.bhash[i].chain); | 3258 | INIT_HLIST_HEAD(&tcp_hashinfo.bhash[i].chain); |
| 3259 | } | 3259 | } |
| 3260 | 3260 | ||
| 3261 | /* Try to be a bit smarter and adjust defaults depending | 3261 | |
| 3262 | * on available memory. | 3262 | cnt = tcp_hashinfo.ehash_mask + 1; |
| 3263 | */ | 3263 | |
| 3264 | for (order = 0; ((1 << order) << PAGE_SHIFT) < | 3264 | tcp_death_row.sysctl_max_tw_buckets = cnt / 2; |
| 3265 | (tcp_hashinfo.bhash_size * sizeof(struct inet_bind_hashbucket)); | 3265 | sysctl_tcp_max_orphans = cnt / 2; |
| 3266 | order++) | 3266 | sysctl_max_syn_backlog = max(128, cnt / 256); |
| 3267 | ; | ||
| 3268 | if (order >= 4) { | ||
| 3269 | tcp_death_row.sysctl_max_tw_buckets = 180000; | ||
| 3270 | sysctl_tcp_max_orphans = 4096 << (order - 4); | ||
| 3271 | sysctl_max_syn_backlog = 1024; | ||
| 3272 | } else if (order < 3) { | ||
| 3273 | tcp_death_row.sysctl_max_tw_buckets >>= (3 - order); | ||
| 3274 | sysctl_tcp_max_orphans >>= (3 - order); | ||
| 3275 | sysctl_max_syn_backlog = 128; | ||
| 3276 | } | ||
| 3277 | 3267 | ||
| 3278 | /* Set the pressure threshold to be a fraction of global memory that | 3268 | /* Set the pressure threshold to be a fraction of global memory that |
| 3279 | * is up to 1/2 at 256 MB, decreasing toward zero with the amount of | 3269 | * is up to 1/2 at 256 MB, decreasing toward zero with the amount of |
