OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2009 The WebRTC Project Authors. All rights reserved. | 2 * Copyright 2009 The WebRTC Project Authors. All rights reserved. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license | 4 * Use of this source code is governed by a BSD-style license |
5 * that can be found in the LICENSE file in the root of the source | 5 * that can be found in the LICENSE file in the root of the source |
6 * tree. An additional intellectual property rights grant can be found | 6 * tree. An additional intellectual property rights grant can be found |
7 * in the file PATENTS. All contributing project authors may | 7 * in the file PATENTS. All contributing project authors may |
8 * be found in the AUTHORS file in the root of the source tree. | 8 * be found in the AUTHORS file in the root of the source tree. |
9 */ | 9 */ |
10 | 10 |
(...skipping 1732 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1743 ch.OnCandidate(CreateCandidate("1.1.1.1", 1, 1)); | 1743 ch.OnCandidate(CreateCandidate("1.1.1.1", 1, 1)); |
1744 cricket::Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1); | 1744 cricket::Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1); |
1745 ASSERT_TRUE(conn1 != nullptr); | 1745 ASSERT_TRUE(conn1 != nullptr); |
1746 | 1746 |
1747 conn1->ReceivedPing(); | 1747 conn1->ReceivedPing(); |
1748 conn1->OnReadPacket("ABC", 3, rtc::CreatePacketTime(0)); | 1748 conn1->OnReadPacket("ABC", 3, rtc::CreatePacketTime(0)); |
1749 EXPECT_TRUE_WAIT(ch.best_connection() != nullptr, 1000) | 1749 EXPECT_TRUE_WAIT(ch.best_connection() != nullptr, 1000) |
1750 EXPECT_TRUE_WAIT(ch.receiving(), 1000); | 1750 EXPECT_TRUE_WAIT(ch.receiving(), 1000); |
1751 EXPECT_TRUE_WAIT(!ch.receiving(), 1000); | 1751 EXPECT_TRUE_WAIT(!ch.receiving(), 1000); |
1752 } | 1752 } |
| 1753 |
| 1754 // The controlled side will select a connection as the "best connection" based |
| 1755 // on priority until the controlling side nominates a connection, at which |
| 1756 // point the controlled side will select that connection as the |
| 1757 // "best connection". |
| 1758 TEST_F(P2PTransportChannelPingTest, TestSelectConnectionBeforeNomination) { |
| 1759 cricket::FakePortAllocator pa(rtc::Thread::Current(), nullptr); |
| 1760 cricket::P2PTransportChannel ch("receiving state change", 1, nullptr, &pa); |
| 1761 PrepareChannel(&ch); |
| 1762 ch.SetIceRole(cricket::ICEROLE_CONTROLLED); |
| 1763 ch.Connect(); |
| 1764 ch.OnCandidate(CreateCandidate("1.1.1.1", 1, 1)); |
| 1765 cricket::Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1); |
| 1766 ASSERT_TRUE(conn1 != nullptr); |
| 1767 EXPECT_EQ(conn1, ch.best_connection()); |
| 1768 |
| 1769 // When a higher priority candidate comes in, the new connection is chosen |
| 1770 // as the best connection. |
| 1771 ch.OnCandidate(CreateCandidate("2.2.2.2", 2, 10)); |
| 1772 cricket::Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2); |
| 1773 ASSERT_TRUE(conn1 != nullptr); |
| 1774 EXPECT_EQ(conn2, ch.best_connection()); |
| 1775 |
| 1776 // If a stun request with use-candidate attribute arrives, the receiving |
| 1777 // connection will be set as the best connection, even though |
| 1778 // its priority is lower. |
| 1779 ch.OnCandidate(CreateCandidate("3.3.3.3", 3, 1)); |
| 1780 cricket::Connection* conn3 = WaitForConnectionTo(&ch, "3.3.3.3", 3); |
| 1781 ASSERT_TRUE(conn3 != nullptr); |
| 1782 // Because it has a lower priority, the best connection is still conn2. |
| 1783 EXPECT_EQ(conn2, ch.best_connection()); |
| 1784 conn3->ReceivedPingResponse(); // Become writable. |
| 1785 // But if it is nominated via use_candidate, it is chosen as the best |
| 1786 // connection. |
| 1787 conn3->set_nominated(true); |
| 1788 conn3->SignalNominated(conn3); |
| 1789 EXPECT_EQ(conn3, ch.best_connection()); |
| 1790 |
| 1791 // Even if another higher priority candidate arrives, |
| 1792 // it will not be set as the best connection because the best connection |
| 1793 // is nominated by the controlling side. |
| 1794 ch.OnCandidate(CreateCandidate("4.4.4.4", 4, 100)); |
| 1795 cricket::Connection* conn4 = WaitForConnectionTo(&ch, "4.4.4.4", 4); |
| 1796 ASSERT_TRUE(conn4 != nullptr); |
| 1797 EXPECT_EQ(conn3, ch.best_connection()); |
| 1798 // But if it is nominated via use_candidate and writable, it will be set as |
| 1799 // the best connection. |
| 1800 conn4->set_nominated(true); |
| 1801 conn4->SignalNominated(conn4); |
| 1802 // Not switched yet because conn4 is not writable. |
| 1803 EXPECT_EQ(conn3, ch.best_connection()); |
| 1804 // The best connection switches after conn4 becomes writable. |
| 1805 conn4->ReceivedPingResponse(); |
| 1806 EXPECT_EQ(conn4, ch.best_connection()); |
| 1807 } |
| 1808 |
| 1809 // The controlled side will select a connection as the "best connection" based |
| 1810 // on requests from an unknown address before the controlling side nominates |
| 1811 // a connection, and will nominate a connection from an unknown address if the |
| 1812 // request contains the use_candidate attribute. |
| 1813 TEST_F(P2PTransportChannelPingTest, TestSelectConnectionFromUnknownAddress) { |
| 1814 cricket::FakePortAllocator pa(rtc::Thread::Current(), nullptr); |
| 1815 cricket::P2PTransportChannel ch("receiving state change", 1, nullptr, &pa); |
| 1816 PrepareChannel(&ch); |
| 1817 ch.SetIceRole(cricket::ICEROLE_CONTROLLED); |
| 1818 ch.Connect(); |
| 1819 // A minimal STUN message with prflx priority. |
| 1820 cricket::IceMessage request; |
| 1821 request.SetType(cricket::STUN_BINDING_REQUEST); |
| 1822 request.AddAttribute(new cricket::StunByteStringAttribute( |
| 1823 cricket::STUN_ATTR_USERNAME, kIceUfrag[1])); |
| 1824 uint32 prflx_priority = cricket::ICE_TYPE_PREFERENCE_PRFLX << 24; |
| 1825 request.AddAttribute(new cricket::StunUInt32Attribute( |
| 1826 cricket::STUN_ATTR_PRIORITY, prflx_priority)); |
| 1827 cricket::Port* port = GetPort(&ch); |
| 1828 port->SignalUnknownAddress(port, rtc::SocketAddress("1.1.1.1", 1), |
| 1829 cricket::PROTO_UDP, &request, kIceUfrag[1], false); |
| 1830 cricket::Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1); |
| 1831 ASSERT_TRUE(conn1 != nullptr); |
| 1832 EXPECT_EQ(conn1, ch.best_connection()); |
| 1833 conn1->ReceivedPingResponse(); |
| 1834 EXPECT_EQ(conn1, ch.best_connection()); |
| 1835 |
| 1836 // Another connection is nominated via use_candidate. |
| 1837 ch.OnCandidate(CreateCandidate("2.2.2.2", 2, 1)); |
| 1838 cricket::Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2); |
| 1839 ASSERT_TRUE(conn2 != nullptr); |
| 1840 // Because it has a lower priority, the best connection is still conn1. |
| 1841 EXPECT_EQ(conn1, ch.best_connection()); |
| 1842 // When it is nominated via use_candidate and writable, it is chosen as the |
| 1843 // best connection. |
| 1844 conn2->ReceivedPingResponse(); // Become writable. |
| 1845 conn2->set_nominated(true); |
| 1846 conn2->SignalNominated(conn2); |
| 1847 EXPECT_EQ(conn2, ch.best_connection()); |
| 1848 |
| 1849 // Another request with unknown address, it will not be set as the best |
| 1850 // connection because the best connection was nominated by the controlling |
| 1851 // side. |
| 1852 port->SignalUnknownAddress(port, rtc::SocketAddress("3.3.3.3", 3), |
| 1853 cricket::PROTO_UDP, &request, kIceUfrag[1], false); |
| 1854 cricket::Connection* conn3 = WaitForConnectionTo(&ch, "3.3.3.3", 3); |
| 1855 ASSERT_TRUE(conn3 != nullptr); |
| 1856 conn3->ReceivedPingResponse(); // Become writable. |
| 1857 EXPECT_EQ(conn2, ch.best_connection()); |
| 1858 |
| 1859 // However if the request contains use_candidate attribute, it will be |
| 1860 // selected as the best connection. |
| 1861 request.AddAttribute( |
| 1862 new cricket::StunByteStringAttribute(cricket::STUN_ATTR_USE_CANDIDATE)); |
| 1863 port->SignalUnknownAddress(port, rtc::SocketAddress("4.4.4.4", 4), |
| 1864 cricket::PROTO_UDP, &request, kIceUfrag[1], false); |
| 1865 cricket::Connection* conn4 = WaitForConnectionTo(&ch, "4.4.4.4", 4); |
| 1866 ASSERT_TRUE(conn4 != nullptr); |
| 1867 // conn4 is not the best connection yet because it is not writable. |
| 1868 EXPECT_EQ(conn2, ch.best_connection()); |
| 1869 conn4->ReceivedPingResponse(); // Become writable. |
| 1870 EXPECT_EQ(conn4, ch.best_connection()); |
| 1871 } |
| 1872 |
| 1873 // The controlled side will select a connection as the "best connection" |
| 1874 // based on media received until the controlling side nominates a connection, |
| 1875 // at which point the controlled side will select that connection as |
| 1876 // the "best connection". |
| 1877 TEST_F(P2PTransportChannelPingTest, TestSelectConnectionBasedOnMediaReceived) { |
| 1878 cricket::FakePortAllocator pa(rtc::Thread::Current(), nullptr); |
| 1879 cricket::P2PTransportChannel ch("receiving state change", 1, nullptr, &pa); |
| 1880 PrepareChannel(&ch); |
| 1881 ch.SetIceRole(cricket::ICEROLE_CONTROLLED); |
| 1882 ch.Connect(); |
| 1883 ch.OnCandidate(CreateCandidate("1.1.1.1", 1, 10)); |
| 1884 cricket::Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1); |
| 1885 ASSERT_TRUE(conn1 != nullptr); |
| 1886 EXPECT_EQ(conn1, ch.best_connection()); |
| 1887 |
| 1888 // If a data packet is received on conn2, the best connection should |
| 1889 // switch to conn2 because the controlled side must mirror the media path |
| 1890 // chosen by the controlling side. |
| 1891 ch.OnCandidate(CreateCandidate("2.2.2.2", 2, 1)); |
| 1892 cricket::Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2); |
| 1893 ASSERT_TRUE(conn2 != nullptr); |
| 1894 conn2->ReceivedPing(); // Become readable. |
| 1895 // Do not switch because it is not writable. |
| 1896 conn2->OnReadPacket("ABC", 3, rtc::CreatePacketTime(0)); |
| 1897 EXPECT_EQ(conn1, ch.best_connection()); |
| 1898 |
| 1899 conn2->ReceivedPingResponse(); // Become writable. |
| 1900 // Switch because it is writable. |
| 1901 conn2->OnReadPacket("DEF", 3, rtc::CreatePacketTime(0)); |
| 1902 EXPECT_EQ(conn2, ch.best_connection()); |
| 1903 |
| 1904 // Now another STUN message with an unknown address and use_candidate will |
| 1905 // nominate the best connection. |
| 1906 cricket::IceMessage request; |
| 1907 request.SetType(cricket::STUN_BINDING_REQUEST); |
| 1908 request.AddAttribute(new cricket::StunByteStringAttribute( |
| 1909 cricket::STUN_ATTR_USERNAME, kIceUfrag[1])); |
| 1910 uint32 prflx_priority = cricket::ICE_TYPE_PREFERENCE_PRFLX << 24; |
| 1911 request.AddAttribute(new cricket::StunUInt32Attribute( |
| 1912 cricket::STUN_ATTR_PRIORITY, prflx_priority)); |
| 1913 request.AddAttribute( |
| 1914 new cricket::StunByteStringAttribute(cricket::STUN_ATTR_USE_CANDIDATE)); |
| 1915 cricket::Port* port = GetPort(&ch); |
| 1916 port->SignalUnknownAddress(port, rtc::SocketAddress("3.3.3.3", 3), |
| 1917 cricket::PROTO_UDP, &request, kIceUfrag[1], false); |
| 1918 cricket::Connection* conn3 = WaitForConnectionTo(&ch, "3.3.3.3", 3); |
| 1919 ASSERT_TRUE(conn3 != nullptr); |
| 1920 EXPECT_EQ(conn2, ch.best_connection()); // Not writable yet. |
| 1921 conn3->ReceivedPingResponse(); // Become writable. |
| 1922 EXPECT_EQ(conn3, ch.best_connection()); |
| 1923 |
| 1924 // Now another data packet will not switch the best connection because the |
| 1925 // best connection was nominated by the controlling side. |
| 1926 conn2->ReceivedPing(); |
| 1927 conn2->ReceivedPingResponse(); |
| 1928 conn2->OnReadPacket("XYZ", 3, rtc::CreatePacketTime(0)); |
| 1929 EXPECT_EQ(conn3, ch.best_connection()); |
| 1930 } |
OLD | NEW |