OLD | NEW |
---|---|
1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2013 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "net/socket/tcp_socket.h" | 5 #include "net/socket/tcp_socket.h" |
6 | 6 |
7 #include "base/file_util.h" | 7 #include "base/file_util.h" |
8 #include "base/files/file_path.h" | 8 #include "base/files/file_path.h" |
9 #include "base/location.h" | 9 #include "base/location.h" |
10 #include "base/memory/ref_counted.h" | 10 #include "base/memory/ref_counted.h" |
11 #include "base/threading/worker_pool.h" | 11 #include "base/threading/worker_pool.h" |
12 | 12 |
13 namespace net { | 13 namespace net { |
14 | 14 |
15 namespace { | 15 namespace { |
16 | 16 |
17 // True if OS supports TCP FastOpen. | |
18 bool g_tcp_fastopen_supported = false; | |
19 // True if OS supports TCP FastOpen and is turned on for all connections. | |
17 bool g_tcp_fastopen_enabled = false; | 20 bool g_tcp_fastopen_enabled = false; |
mmenke
2014/08/12 15:25:15
Do we really need globals for TCP FastOpen? May t
Jana
2014/08/13 07:33:40
I'll see how this might be done. Given that this c
mmenke
2014/08/13 15:36:49
Fine with a TODO, for now, though I suspect that m
| |
18 | 21 |
19 #if defined(OS_LINUX) || defined(OS_ANDROID) | 22 #if defined(OS_LINUX) || defined(OS_ANDROID) |
20 | 23 |
21 typedef base::RefCountedData<bool> SharedBoolean; | 24 typedef base::RefCountedData<bool> SharedBoolean; |
22 | 25 |
23 // Checks to see if the system supports TCP FastOpen. Notably, it requires | 26 // Checks if the kernel supports TCP FastOpen. |
24 // kernel support. Additionally, this checks system configuration to ensure that | 27 void SystemSupportsTCPFastOpen(scoped_refptr<SharedBoolean> system_supported) { |
25 // it's enabled. | 28 system_supported->data = false; |
26 void SystemSupportsTCPFastOpen(scoped_refptr<SharedBoolean> supported) { | |
27 supported->data = false; | |
28 static const base::FilePath::CharType kTCPFastOpenProcFilePath[] = | 29 static const base::FilePath::CharType kTCPFastOpenProcFilePath[] = |
29 "/proc/sys/net/ipv4/tcp_fastopen"; | 30 "/proc/sys/net/ipv4/tcp_fastopen"; |
30 std::string system_enabled_tcp_fastopen; | 31 std::string system_supports_tcp_fastopen; |
31 if (!base::ReadFileToString(base::FilePath(kTCPFastOpenProcFilePath), | 32 if (!base::ReadFileToString(base::FilePath(kTCPFastOpenProcFilePath), |
32 &system_enabled_tcp_fastopen)) { | 33 &system_supports_tcp_fastopen)) { |
33 return; | 34 return; |
34 } | 35 } |
35 | 36 // The read from /proc should return '1' if TCP FastOpen is enabled in the OS. |
36 // As per http://lxr.linux.no/linux+v3.7.7/include/net/tcp.h#L225 | 37 if (system_supports_tcp_fastopen.empty() || |
37 // TFO_CLIENT_ENABLE is the LSB | 38 (system_supports_tcp_fastopen[0] != '1')) { |
38 if (system_enabled_tcp_fastopen.empty() || | |
39 (system_enabled_tcp_fastopen[0] & 0x1) == 0) { | |
40 return; | 39 return; |
41 } | 40 } |
42 | 41 system_supported->data = true; |
43 supported->data = true; | |
44 } | 42 } |
45 | 43 |
46 void EnableCallback(scoped_refptr<SharedBoolean> supported) { | 44 void CallbackForTCPFastOpenCheck(scoped_refptr<SharedBoolean> system_supported, |
47 g_tcp_fastopen_enabled = supported->data; | 45 bool user_enabled) { |
48 } | 46 g_tcp_fastopen_supported = system_supported->data; |
49 | 47 if (user_enabled) { |
50 // This is asynchronous because it needs to do file IO, and it isn't allowed to | 48 g_tcp_fastopen_enabled = system_supported->data; |
51 // do that on the IO thread. | 49 } |
52 void EnableFastOpenIfSupported() { | |
53 scoped_refptr<SharedBoolean> supported = new SharedBoolean; | |
54 base::WorkerPool::PostTaskAndReply( | |
55 FROM_HERE, | |
56 base::Bind(SystemSupportsTCPFastOpen, supported), | |
57 base::Bind(EnableCallback, supported), | |
58 false); | |
59 } | 50 } |
60 | 51 |
61 #else | 52 #else |
62 | 53 |
63 void EnableFastOpenIfSupported() { | 54 void CheckSupportAndMaybeEnableTCPFastOpen(bool user_enabled) {} |
64 g_tcp_fastopen_enabled = false; | |
65 } | |
66 | 55 |
67 #endif | 56 #endif |
68 | 57 |
69 } // namespace | 58 } // namespace |
70 | 59 |
71 void SetTCPFastOpenEnabled(bool value) { | 60 // This is asynchronous because it needs to do file IO, and it isn't allowed to |
72 if (value) { | 61 // do that on the IO thread. |
73 EnableFastOpenIfSupported(); | 62 void CheckSupportAndMaybeEnableTCPFastOpen(bool user_enabled) { |
74 } else { | 63 scoped_refptr<SharedBoolean> system_supported = new SharedBoolean; |
mmenke
2014/08/12 15:25:15
Using a shared boolean seems unnecessary to me. Y
Jana
2014/08/13 07:33:40
Done.
| |
75 g_tcp_fastopen_enabled = false; | 64 base::WorkerPool::PostTaskAndReply( |
76 } | 65 FROM_HERE, |
66 base::Bind(SystemSupportsTCPFastOpen, system_supported), | |
67 base::Bind(CallbackForTCPFastOpenCheck, system_supported, user_enabled), | |
68 false); | |
69 } | |
70 | |
71 bool IsTCPFastOpenSupported() { | |
72 return g_tcp_fastopen_supported; | |
77 } | 73 } |
78 | 74 |
79 bool IsTCPFastOpenEnabled() { | 75 bool IsTCPFastOpenEnabled() { |
80 return g_tcp_fastopen_enabled; | 76 return g_tcp_fastopen_enabled; |
81 } | 77 } |
82 | 78 |
83 } // namespace net | 79 } // namespace net |
OLD | NEW |