proxy_auto_config_library_unittest.cc 20 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587
  1. // Copyright 2018 The Chromium Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file.
  4. #include "services/network/proxy_auto_config_library.h"
  5. #include "net/base/address_list.h"
  6. #include "net/base/net_errors.h"
  7. #include "net/base/network_interfaces.h"
  8. #include "net/log/net_log_with_source.h"
  9. #include "net/socket/client_socket_factory.h"
  10. #include "net/socket/client_socket_handle.h"
  11. #include "net/socket/datagram_client_socket.h"
  12. #include "testing/gmock/include/gmock/gmock.h"
  13. #include "testing/gtest/include/gtest/gtest.h"
  14. namespace network {
  15. namespace {
  16. // Helper for verifying whether the address list returned by myIpAddress() /
  17. // myIpAddressEx() looks correct.
  18. void VerifyActualMyIpAddresses(const net::IPAddressList& test_list) {
  19. // Enumerate all of the IP addresses for the system (skipping loopback and
  20. // link-local ones). This is used as a reference implementation to check
  21. // whether |test_list| (which was obtained using a different strategy) looks
  22. // correct.
  23. std::set<net::IPAddress> candidates;
  24. net::NetworkInterfaceList networks;
  25. net::GetNetworkList(&networks, net::EXCLUDE_HOST_SCOPE_VIRTUAL_INTERFACES);
  26. for (const auto& network : networks) {
  27. if (network.address.IsLinkLocal() || network.address.IsLoopback())
  28. continue;
  29. candidates.insert(network.address);
  30. }
  31. // Ordinarily the machine running this test will have an IP address. However
  32. // for some bot configurations (notably Android) that may not be the case.
  33. EXPECT_EQ(candidates.empty(), test_list.empty());
  34. // |test_list| should be a subset of |candidates|.
  35. for (const auto& ip : test_list)
  36. EXPECT_EQ(1u, candidates.count(ip));
  37. }
  38. // Tests for PacMyIpAddress() and PacMyIpAddressEx().
  39. TEST(PacLibraryTest, ActualPacMyIpAddress) {
  40. auto my_ip_addresses = PacMyIpAddress();
  41. VerifyActualMyIpAddresses(my_ip_addresses);
  42. }
  43. TEST(PacLibraryTest, ActualPacMyIpAddressEx) {
  44. VerifyActualMyIpAddresses(PacMyIpAddressEx());
  45. }
  46. net::IPAddress CreateIPAddress(base::StringPiece literal) {
  47. net::IPAddress result;
  48. if (!result.AssignFromIPLiteral(literal)) {
  49. ADD_FAILURE() << "Failed parsing IP: " << literal;
  50. return net::IPAddress();
  51. }
  52. return result;
  53. }
  54. net::AddressList CreateAddressList(
  55. const std::vector<base::StringPiece>& ip_literals) {
  56. net::AddressList result;
  57. for (const auto& ip : ip_literals)
  58. result.push_back(net::IPEndPoint(CreateIPAddress(ip), 8080));
  59. return result;
  60. }
  61. class MockUDPSocket : public net::DatagramClientSocket {
  62. public:
  63. MockUDPSocket(const net::IPAddress& peer_ip,
  64. const net::IPAddress& local_ip,
  65. net::Error connect_error)
  66. : peer_ip_(peer_ip), local_ip_(local_ip), connect_error_(connect_error) {}
  67. MockUDPSocket(const MockUDPSocket&) = delete;
  68. MockUDPSocket& operator=(const MockUDPSocket&) = delete;
  69. ~MockUDPSocket() override = default;
  70. // Socket implementation.
  71. int Read(net::IOBuffer* buf,
  72. int buf_len,
  73. net::CompletionOnceCallback callback) override {
  74. ADD_FAILURE() << "Called Read()";
  75. return net::ERR_UNEXPECTED;
  76. }
  77. int Write(
  78. net::IOBuffer* buf,
  79. int buf_len,
  80. net::CompletionOnceCallback callback,
  81. const net::NetworkTrafficAnnotationTag& traffic_annotation) override {
  82. ADD_FAILURE() << "Called Read()";
  83. return net::ERR_UNEXPECTED;
  84. }
  85. int SetReceiveBufferSize(int32_t size) override {
  86. ADD_FAILURE() << "Called SetReceiveBufferSize()";
  87. return net::ERR_UNEXPECTED;
  88. }
  89. int SetSendBufferSize(int32_t size) override {
  90. ADD_FAILURE() << "Called SetSendBufferSize()";
  91. return net::ERR_UNEXPECTED;
  92. }
  93. // net::DatagramSocket implementation.
  94. void Close() override { ADD_FAILURE() << "Called Close()"; }
  95. int GetPeerAddress(net::IPEndPoint* address) const override {
  96. ADD_FAILURE() << "Called GetPeerAddress()";
  97. return net::ERR_UNEXPECTED;
  98. }
  99. int GetLocalAddress(net::IPEndPoint* address) const override {
  100. if (connect_error_ != net::OK)
  101. return connect_error_;
  102. *address = net::IPEndPoint(local_ip_, 8080);
  103. return net::OK;
  104. }
  105. void UseNonBlockingIO() override {
  106. ADD_FAILURE() << "Called UseNonBlockingIO()";
  107. }
  108. int SetDoNotFragment() override {
  109. ADD_FAILURE() << "Called SetDoNotFragment()";
  110. return net::ERR_UNEXPECTED;
  111. }
  112. void SetMsgConfirm(bool confirm) override {
  113. ADD_FAILURE() << "Called SetMsgConfirm()";
  114. }
  115. const net::NetLogWithSource& NetLog() const override {
  116. ADD_FAILURE() << "Called net::NetLog()";
  117. return net_log_;
  118. }
  119. // net::DatagramClientSocket implementation.
  120. int Connect(const net::IPEndPoint& address) override {
  121. EXPECT_EQ(peer_ip_.ToString(), address.address().ToString());
  122. return connect_error_;
  123. }
  124. int ConnectUsingNetwork(net::handles::NetworkHandle network,
  125. const net::IPEndPoint& address) override {
  126. ADD_FAILURE() << "Called ConnectUsingNetwork()";
  127. return net::ERR_UNEXPECTED;
  128. }
  129. int ConnectUsingDefaultNetwork(const net::IPEndPoint& address) override {
  130. ADD_FAILURE() << "Called ConnectUsingDefaultNetwork()";
  131. return net::ERR_UNEXPECTED;
  132. }
  133. net::handles::NetworkHandle GetBoundNetwork() const override {
  134. ADD_FAILURE() << "Called GetBoundNetwork()";
  135. return network_;
  136. }
  137. void ApplySocketTag(const net::SocketTag& tag) override {
  138. ADD_FAILURE() << "Called ApplySocketTag()";
  139. }
  140. int SetMulticastInterface(uint32_t interface_index) override {
  141. ADD_FAILURE() << "Called SetMulticastInterface()";
  142. return net::ERR_UNEXPECTED;
  143. }
  144. private:
  145. net::NetLogWithSource net_log_;
  146. net::handles::NetworkHandle network_;
  147. net::IPAddress peer_ip_;
  148. net::IPAddress local_ip_;
  149. net::Error connect_error_;
  150. };
  151. class MockSocketFactory : public net::ClientSocketFactory {
  152. public:
  153. MockSocketFactory() = default;
  154. void AddUDPConnectSuccess(base::StringPiece peer_ip_literal,
  155. base::StringPiece local_ip_literal) {
  156. auto peer_ip = CreateIPAddress(peer_ip_literal);
  157. auto local_ip = CreateIPAddress(local_ip_literal);
  158. // The address family of local and peer IP must match.
  159. ASSERT_EQ(peer_ip.size(), local_ip.size());
  160. udp_sockets_.push_back(
  161. std::make_unique<MockUDPSocket>(peer_ip, local_ip, net::OK));
  162. }
  163. void AddUDPConnectFailure(base::StringPiece peer_ip) {
  164. udp_sockets_.push_back(std::make_unique<MockUDPSocket>(
  165. CreateIPAddress(peer_ip), net::IPAddress(),
  166. net::ERR_ADDRESS_UNREACHABLE));
  167. }
  168. MockSocketFactory(const MockSocketFactory&) = delete;
  169. MockSocketFactory& operator=(const MockSocketFactory&) = delete;
  170. ~MockSocketFactory() override {
  171. EXPECT_EQ(0u, udp_sockets_.size())
  172. << "Not all of the mock sockets were consumed.";
  173. }
  174. // net::ClientSocketFactory
  175. std::unique_ptr<net::DatagramClientSocket> CreateDatagramClientSocket(
  176. net::DatagramSocket::BindType bind_type,
  177. net::NetLog* net_log,
  178. const net::NetLogSource& source) override {
  179. if (udp_sockets_.empty()) {
  180. ADD_FAILURE() << "Not enough mock UDP sockets";
  181. return nullptr;
  182. }
  183. auto result = std::move(udp_sockets_.front());
  184. udp_sockets_.erase(udp_sockets_.begin());
  185. return result;
  186. }
  187. std::unique_ptr<net::TransportClientSocket> CreateTransportClientSocket(
  188. const net::AddressList& addresses,
  189. std::unique_ptr<net::SocketPerformanceWatcher> socket_performance_watcher,
  190. net::NetworkQualityEstimator* network_quality_estimator,
  191. net::NetLog* net_log,
  192. const net::NetLogSource& source) override {
  193. ADD_FAILURE() << "Called CreateTransportClientSocket()";
  194. return nullptr;
  195. }
  196. std::unique_ptr<net::SSLClientSocket> CreateSSLClientSocket(
  197. net::SSLClientContext* context,
  198. std::unique_ptr<net::StreamSocket> stream_socket,
  199. const net::HostPortPair& host_and_port,
  200. const net::SSLConfig& ssl_config) override {
  201. ADD_FAILURE() << "Called CreateSSLClientSocket()";
  202. return nullptr;
  203. }
  204. private:
  205. std::vector<std::unique_ptr<MockUDPSocket>> udp_sockets_;
  206. };
  207. // Tests myIpAddress() when there is a route to 8.8.8.8.
  208. TEST(PacLibraryTest, PacMyIpAddress8888) {
  209. MockSocketFactory factory;
  210. factory.AddUDPConnectSuccess("8.8.8.8", "192.168.1.1");
  211. auto result = PacMyIpAddressForTest(&factory, {});
  212. ASSERT_EQ(1u, result.size());
  213. EXPECT_EQ("192.168.1.1", result.front().ToString());
  214. }
  215. // Tests myIpAddress() when there is no route to 8.8.8.8, but there is one to
  216. // 2001:4860:4860::8888.
  217. TEST(PacLibraryTest, PacMyIpAddress2001) {
  218. MockSocketFactory factory;
  219. factory.AddUDPConnectFailure("8.8.8.8");
  220. factory.AddUDPConnectSuccess("2001:4860:4860::8888", "2001::beef");
  221. net::AddressList dns_result;
  222. auto result = PacMyIpAddressForTest(&factory, dns_result);
  223. ASSERT_EQ(1u, result.size());
  224. EXPECT_EQ("2001::beef", result.front().ToString());
  225. }
  226. // Tests myIpAddress() when there is no route to 8.8.8.8, no route to
  227. // 2001:4860:4860::8888, however getaddrinfo(gethostname()) finds results. Most
  228. // of those results are skipped over, and the IPv4 one is favored.
  229. TEST(PacLibraryTest, PacMyIpAddressHostname) {
  230. MockSocketFactory factory;
  231. factory.AddUDPConnectFailure("8.8.8.8");
  232. factory.AddUDPConnectFailure("2001:4860:4860::8888");
  233. net::AddressList dns_result = CreateAddressList({
  234. "169.254.13.16",
  235. "127.0.0.1",
  236. "::1",
  237. "fe89::beef",
  238. "2001::f001",
  239. "178.1.99.3",
  240. "192.168.1.3",
  241. });
  242. auto result = PacMyIpAddressForTest(&factory, dns_result);
  243. ASSERT_EQ(1u, result.size());
  244. EXPECT_EQ("178.1.99.3", result.front().ToString());
  245. }
  246. // Tests myIpAddress() when there is no route to 8.8.8.8, no route to
  247. // 2001:4860:4860::8888, however getaddrinfo(gethostname()) finds multiple IPv6
  248. // results.
  249. TEST(PacLibraryTest, PacMyIpAddressHostnameAllIPv6) {
  250. MockSocketFactory factory;
  251. factory.AddUDPConnectFailure("8.8.8.8");
  252. factory.AddUDPConnectFailure("2001:4860:4860::8888");
  253. net::AddressList dns_result =
  254. CreateAddressList({"::1", "2001::f001", "2001::f00d", "169.254.0.6"});
  255. auto result = PacMyIpAddressForTest(&factory, dns_result);
  256. ASSERT_EQ(1u, result.size());
  257. EXPECT_EQ("2001::f001", result.front().ToString());
  258. }
  259. // Tests myIpAddress() when there is no route to 8.8.8.8, no route to
  260. // 2001:4860:4860::8888, no acceptable result in getaddrinfo(gethostname()),
  261. // however there is a route for private address.
  262. TEST(PacLibraryTest, PacMyIpAddressPrivateIPv4) {
  263. MockSocketFactory factory;
  264. factory.AddUDPConnectFailure("8.8.8.8");
  265. factory.AddUDPConnectFailure("2001:4860:4860::8888");
  266. net::AddressList dns_result = CreateAddressList({
  267. "169.254.13.16",
  268. "127.0.0.1",
  269. "::1",
  270. "fe89::beef",
  271. });
  272. factory.AddUDPConnectSuccess("10.0.0.0", "127.0.0.1");
  273. factory.AddUDPConnectFailure("172.16.0.0");
  274. factory.AddUDPConnectSuccess("192.168.0.0", "63.31.9.8");
  275. auto result = PacMyIpAddressForTest(&factory, dns_result);
  276. ASSERT_EQ(1u, result.size());
  277. EXPECT_EQ("63.31.9.8", result.front().ToString());
  278. }
  279. // Tests myIpAddress() when there is no route to 8.8.8.8, no route to
  280. // 2001:4860:4860::8888, no acceptable result in getaddrinfo(gethostname()),
  281. // however there is a route for private address.
  282. TEST(PacLibraryTest, PacMyIpAddressPrivateIPv6) {
  283. MockSocketFactory factory;
  284. factory.AddUDPConnectFailure("8.8.8.8");
  285. factory.AddUDPConnectFailure("2001:4860:4860::8888");
  286. net::AddressList dns_result;
  287. factory.AddUDPConnectSuccess("10.0.0.0", "127.0.0.1");
  288. factory.AddUDPConnectFailure("172.16.0.0");
  289. factory.AddUDPConnectFailure("192.168.0.0");
  290. factory.AddUDPConnectSuccess("FC00::", "2001::7777");
  291. auto result = PacMyIpAddressForTest(&factory, dns_result);
  292. ASSERT_EQ(1u, result.size());
  293. EXPECT_EQ("2001::7777", result.front().ToString());
  294. }
  295. // Tests myIpAddress() when there are no routes, and getaddrinfo(gethostname())
  296. // fails.
  297. TEST(PacLibraryTest, PacMyIpAddressAllFail) {
  298. MockSocketFactory factory;
  299. factory.AddUDPConnectFailure("8.8.8.8");
  300. factory.AddUDPConnectFailure("2001:4860:4860::8888");
  301. net::AddressList dns_result;
  302. factory.AddUDPConnectFailure("10.0.0.0");
  303. factory.AddUDPConnectFailure("172.16.0.0");
  304. factory.AddUDPConnectFailure("192.168.0.0");
  305. factory.AddUDPConnectFailure("FC00::");
  306. auto result = PacMyIpAddressForTest(&factory, dns_result);
  307. EXPECT_EQ(0u, result.size());
  308. }
  309. // Tests myIpAddress() when there are no routes, and
  310. // getaddrinfo(gethostname()) only returns loopback.
  311. TEST(PacLibraryTest, PacMyIpAddressAllFailOrLoopback) {
  312. MockSocketFactory factory;
  313. factory.AddUDPConnectFailure("8.8.8.8");
  314. factory.AddUDPConnectFailure("2001:4860:4860::8888");
  315. net::AddressList dns_result = CreateAddressList({"127.0.0.1", "::1"});
  316. factory.AddUDPConnectFailure("10.0.0.0");
  317. factory.AddUDPConnectFailure("172.16.0.0");
  318. factory.AddUDPConnectFailure("192.168.0.0");
  319. factory.AddUDPConnectFailure("FC00::");
  320. auto result = PacMyIpAddressForTest(&factory, dns_result);
  321. EXPECT_EQ(0u, result.size());
  322. }
  323. // Tests myIpAddress() when there is only an IPv6 link-local address.
  324. TEST(PacLibraryTest, PacMyIpAddressAllFailHasLinkLocal) {
  325. MockSocketFactory factory;
  326. factory.AddUDPConnectFailure("8.8.8.8");
  327. factory.AddUDPConnectFailure("2001:4860:4860::8888");
  328. net::AddressList dns_result =
  329. CreateAddressList({"127.0.0.1", "::1", "fe81::8881"});
  330. factory.AddUDPConnectFailure("10.0.0.0");
  331. factory.AddUDPConnectFailure("172.16.0.0");
  332. factory.AddUDPConnectFailure("192.168.0.0");
  333. factory.AddUDPConnectFailure("FC00::");
  334. auto result = PacMyIpAddressForTest(&factory, dns_result);
  335. ASSERT_EQ(1u, result.size());
  336. EXPECT_EQ("fe81::8881", result.front().ToString());
  337. }
  338. // Tests myIpAddress() when there are only link-local addresses. The IPv4
  339. // link-local address is favored.
  340. TEST(PacLibraryTest, PacMyIpAddressAllFailHasLinkLocalFavorIPv4) {
  341. MockSocketFactory factory;
  342. factory.AddUDPConnectFailure("8.8.8.8");
  343. factory.AddUDPConnectFailure("2001:4860:4860::8888");
  344. net::AddressList dns_result =
  345. CreateAddressList({"127.0.0.1", "::1", "fe81::8881", "169.254.89.133"});
  346. factory.AddUDPConnectFailure("10.0.0.0");
  347. factory.AddUDPConnectFailure("172.16.0.0");
  348. factory.AddUDPConnectFailure("192.168.0.0");
  349. factory.AddUDPConnectFailure("FC00::");
  350. auto result = PacMyIpAddressForTest(&factory, dns_result);
  351. ASSERT_EQ(1u, result.size());
  352. EXPECT_EQ("169.254.89.133", result.front().ToString());
  353. }
  354. // Tests myIpAddressEx() when there is a route to 8.8.8.8 but not one to
  355. // 2001:4860:4860::8888
  356. TEST(PacLibraryTest, PacMyIpAddressEx8888) {
  357. MockSocketFactory factory;
  358. factory.AddUDPConnectSuccess("8.8.8.8", "192.168.1.1");
  359. factory.AddUDPConnectFailure("2001:4860:4860::8888");
  360. auto result = PacMyIpAddressExForTest(&factory, {});
  361. ASSERT_EQ(1u, result.size());
  362. EXPECT_EQ("192.168.1.1", result.front().ToString());
  363. }
  364. // Tests myIpAddressEx() when there is a route to 2001:4860:4860::8888 but
  365. // not 8.8.8.8.
  366. TEST(PacLibraryTest, PacMyIpAddressEx2001) {
  367. MockSocketFactory factory;
  368. factory.AddUDPConnectFailure("8.8.8.8");
  369. factory.AddUDPConnectSuccess("2001:4860:4860::8888", "2001::3333");
  370. net::AddressList dns_result;
  371. auto result = PacMyIpAddressExForTest(&factory, dns_result);
  372. ASSERT_EQ(1u, result.size());
  373. EXPECT_EQ("2001::3333", result.front().ToString());
  374. }
  375. // Tests myIpAddressEx() when there is a route to both 8.8.8.8 and
  376. // 2001:4860:4860::8888.
  377. TEST(PacLibraryTest, PacMyIpAddressEx8888And2001) {
  378. MockSocketFactory factory;
  379. factory.AddUDPConnectSuccess("8.8.8.8", "192.168.17.8");
  380. factory.AddUDPConnectSuccess("2001:4860:4860::8888", "2001::8333");
  381. net::AddressList dns_result;
  382. auto result = PacMyIpAddressExForTest(&factory, dns_result);
  383. ASSERT_EQ(2u, result.size());
  384. EXPECT_EQ("192.168.17.8", result.front().ToString());
  385. EXPECT_EQ("2001::8333", result.back().ToString());
  386. }
  387. // Tests myIpAddressEx() when there is no route to 8.8.8.8, no route to
  388. // 2001:4860:4860::8888, however getaddrinfo(gethostname()) finds results. Some
  389. // of those results are skipped due to being link-local and loopback.
  390. TEST(PacLibraryTest, PacMyIpAddressExHostname) {
  391. MockSocketFactory factory;
  392. factory.AddUDPConnectFailure("8.8.8.8");
  393. factory.AddUDPConnectFailure("2001:4860:4860::8888");
  394. net::AddressList dns_result = CreateAddressList({
  395. "169.254.13.16",
  396. "::1",
  397. "fe89::beef",
  398. "2001::bebe",
  399. "178.1.99.3",
  400. "127.0.0.1",
  401. "192.168.1.3",
  402. });
  403. auto result = PacMyIpAddressExForTest(&factory, dns_result);
  404. ASSERT_EQ(3u, result.size());
  405. EXPECT_EQ("2001::bebe", result[0].ToString());
  406. EXPECT_EQ("178.1.99.3", result[1].ToString());
  407. EXPECT_EQ("192.168.1.3", result[2].ToString());
  408. }
  409. // Tests myIpAddressEx() when routes are found for private IP space.
  410. TEST(PacLibraryTest, PacMyIpAddressExPrivateDuplicates) {
  411. MockSocketFactory factory;
  412. factory.AddUDPConnectFailure("8.8.8.8");
  413. factory.AddUDPConnectFailure("2001:4860:4860::8888");
  414. net::AddressList dns_result;
  415. factory.AddUDPConnectSuccess("10.0.0.0", "192.168.3.3");
  416. factory.AddUDPConnectSuccess("172.16.0.0", "192.168.3.4");
  417. factory.AddUDPConnectSuccess("192.168.0.0", "192.168.3.3");
  418. factory.AddUDPConnectSuccess("FC00::", "2001::beef");
  419. auto result = PacMyIpAddressExForTest(&factory, dns_result);
  420. // Note that 192.168.3.3. was probed twice, but only added once to the final
  421. // result.
  422. ASSERT_EQ(3u, result.size());
  423. EXPECT_EQ("192.168.3.3", result[0].ToString());
  424. EXPECT_EQ("192.168.3.4", result[1].ToString());
  425. EXPECT_EQ("2001::beef", result[2].ToString());
  426. }
  427. // Tests myIpAddressEx() when there are no routes, and
  428. // getaddrinfo(gethostname()) fails.
  429. TEST(PacLibraryTest, PacMyIpAddressExAllFail) {
  430. MockSocketFactory factory;
  431. factory.AddUDPConnectFailure("8.8.8.8");
  432. factory.AddUDPConnectFailure("2001:4860:4860::8888");
  433. net::AddressList dns_result;
  434. factory.AddUDPConnectFailure("10.0.0.0");
  435. factory.AddUDPConnectFailure("172.16.0.0");
  436. factory.AddUDPConnectFailure("192.168.0.0");
  437. factory.AddUDPConnectFailure("FC00::");
  438. auto result = PacMyIpAddressExForTest(&factory, dns_result);
  439. EXPECT_EQ(0u, result.size());
  440. }
  441. // Tests myIpAddressEx() when there are only IPv6 link-local address.
  442. TEST(PacLibraryTest, PacMyIpAddressExAllFailHasLinkLocal) {
  443. MockSocketFactory factory;
  444. factory.AddUDPConnectFailure("8.8.8.8");
  445. factory.AddUDPConnectFailure("2001:4860:4860::8888");
  446. net::AddressList dns_result =
  447. CreateAddressList({"127.0.0.1", "::1", "fe81::8881", "fe80::8899"});
  448. factory.AddUDPConnectFailure("10.0.0.0");
  449. factory.AddUDPConnectFailure("172.16.0.0");
  450. factory.AddUDPConnectFailure("192.168.0.0");
  451. factory.AddUDPConnectSuccess("FC00::", "fe80::1");
  452. auto result = PacMyIpAddressExForTest(&factory, dns_result);
  453. // There were four link-local addresses found, but only the first one is
  454. // returned.
  455. ASSERT_EQ(1u, result.size());
  456. EXPECT_EQ("fe81::8881", result.front().ToString());
  457. }
  458. // Tests myIpAddressEx() when there are only link-local addresses. The IPv4
  459. // link-local address is favored.
  460. TEST(PacLibraryTest, PacMyIpAddressExAllFailHasLinkLocalFavorIPv4) {
  461. MockSocketFactory factory;
  462. factory.AddUDPConnectFailure("8.8.8.8");
  463. factory.AddUDPConnectFailure("2001:4860:4860::8888");
  464. net::AddressList dns_result =
  465. CreateAddressList({"127.0.0.1", "::1", "fe81::8881", "169.254.89.133"});
  466. factory.AddUDPConnectFailure("10.0.0.0");
  467. factory.AddUDPConnectFailure("172.16.0.0");
  468. factory.AddUDPConnectFailure("192.168.0.0");
  469. factory.AddUDPConnectFailure("FC00::");
  470. auto result = PacMyIpAddressExForTest(&factory, dns_result);
  471. ASSERT_EQ(1u, result.size());
  472. EXPECT_EQ("169.254.89.133", result.front().ToString());
  473. }
  474. // Tests myIpAddressEx() when there are no routes, and
  475. // getaddrinfo(gethostname()) only returns loopback.
  476. TEST(PacLibraryTest, PacMyIpAddressExAllFailOrLoopback) {
  477. MockSocketFactory factory;
  478. factory.AddUDPConnectFailure("8.8.8.8");
  479. factory.AddUDPConnectFailure("2001:4860:4860::8888");
  480. net::AddressList dns_result = CreateAddressList({"127.0.0.1", "::1"});
  481. factory.AddUDPConnectFailure("10.0.0.0");
  482. factory.AddUDPConnectFailure("172.16.0.0");
  483. factory.AddUDPConnectFailure("192.168.0.0");
  484. factory.AddUDPConnectFailure("FC00::");
  485. auto result = PacMyIpAddressExForTest(&factory, dns_result);
  486. EXPECT_EQ(0u, result.size());
  487. }
  488. } // namespace
  489. } // namespace network