예제 #1
0
    def test_HTTPSDistributor_getBridges_with_BridgeRingParameters(self):
        param = BridgeRingParameters(needPorts=[(443, 1)])
        dist = distributor.HTTPSDistributor(3,
                                            self.key,
                                            answerParameters=param)

        bridges = self.bridges[:32]
        for b in self.bridges:
            b.orPort = 443

        [dist.insert(bridge) for bridge in bridges]
        [dist.insert(bridge) for bridge in self.bridges[:250]]

        for _ in range(32):
            bridgeRequest = self.randomClientRequest()
            answer = dist.getBridges(bridgeRequest, 1)
            count = 0
            fingerprints = {}
            for bridge in answer:
                fingerprints[bridge.identity] = 1
                if bridge.orPort == 443:
                    count += 1
            self.assertEquals(len(fingerprints), len(answer))
            self.assertGreater(len(fingerprints), 0)
            self.assertTrue(count >= 1)
예제 #2
0
    def test_HTTPSDistributor_getBridges_with_some_blocked_bridges(self):
        dist = distributor.HTTPSDistributor(1, self.key)
        bridges = self.bridges[:]

        blockedCN = []
        blockedIR = []

        for bridge in bridges:
            if self.coinFlip():
                bridge.setBlockedIn('cn')
                blockedCN.append(bridge.fingerprint)

            if self.coinFlip():
                bridge.setBlockedIn('ir')
                blockedIR.append(bridge.fingerprint)

        [dist.insert(bridge) for bridge in bridges]

        for _ in range(5):
            clientRequest1 = self.randomClientRequestForNotBlockedIn('cn')
            bridges = dist.getBridges(clientRequest1, 1)
            for b in bridges:
                self.assertFalse(b.isBlockedIn('cn'))
                self.assertNotIn(b.fingerprint, blockedCN)
            # The client *should* have gotten some bridges still.
            self.assertGreater(len(bridges), 0)

            clientRequest2 = self.randomClientRequestForNotBlockedIn('ir')
            bridges = dist.getBridges(clientRequest2, 1)
            for b in bridges:
                self.assertFalse(b.isBlockedIn('ir'))
                self.assertNotIn(b.fingerprint, blockedIR)
            self.assertGreater(len(bridges), 0)
예제 #3
0
    def test_HTTPSDistributor_getBridges_probing_vulnerable(self):
        dist = distributor.HTTPSDistributor(1, self.key)
        bridges = self.bridges[:]
        [dist.insert(bridge) for bridge in bridges]

        def requestTransports(bridges, transport, vulnerable):
            for _ in range(len(bridges)):
                request = HTTPSBridgeRequest(addClientCountryCode=False)
                request.client = randomValidIPv4String()
                request.isValid(True)
                if transport is not None:
                    request.transports.append(transport)
                request.generateFilters()

                obtained_bridges = dist.getBridges(request, 1)
                for bridge in obtained_bridges:
                    if vulnerable:
                        self.assertFalse(bridge.hasProbingResistantPT())
                        for t in bridge.transports:
                            self.assertTrue(t.methodname != 'obfs4'
                                            and t.methodname != 'scramblesuit')
                    else:
                        self.assertTrue(bridge.hasProbingResistantPT())

        requestTransports(bridges, None, True)
        requestTransports(bridges, 'obfs2', True)
        requestTransports(bridges, 'obfs3', True)
        requestTransports(bridges, 'obfs4', False)
예제 #4
0
    def test_HTTPSDistributor_getBridges_with_proxy_and_nonproxy_users(self):
        """An HTTPSDistributor should give separate bridges to proxy users."""
        proxies = ProxySet(
            ['.'.join(['1.1.1', str(x)]) for x in range(1, 256)])
        dist = distributor.HTTPSDistributor(3, self.key, proxies)
        [dist.insert(bridge) for bridge in self.bridges]

        for _ in range(10):
            bridgeRequest1 = self.randomClientRequest()
            bridgeRequest1.client = '.'.join(
                ['1.1.1', str(random.randrange(1, 255))])

            bridgeRequest2 = self.randomClientRequest()
            bridgeRequest2.client = '.'.join(
                ['9.9.9', str(random.randrange(1, 255))])

            n1 = dist.getBridges(bridgeRequest1, 1)
            n2 = dist.getBridges(bridgeRequest2, 1)

            self.assertGreater(len(n1), 0)
            self.assertGreater(len(n2), 0)

            for b in n1:
                self.assertNotIn(b, n2)
            for b in n2:
                self.assertNotIn(b, n1)
예제 #5
0
 def test_HTTPSDistributor_prepopulateRings_with_proxies(self):
     """An HTTPSDistributor with proxies should prepopulate two extra
     subhashrings (one for each of HTTP-Proxy-IPv4 and HTTP-Proxy-IPv6).
     """
     dist = distributor.HTTPSDistributor(3, self.key, ProxySet(['1.1.1.1', '2.2.2.2']))
     [dist.insert(bridge) for bridge in self.bridges]
     dist.prepopulateRings()
     self.assertEqual(len(dist.hashring.filterRings), 8)
예제 #6
0
 def test_HTTPSDistributor_mapSubnetToSubring_usingProxy(self):
     """HTTPSDistributor.mapSubnetToSubring() when the client was using a
     proxy should map the client to the proxy subhashring.
     """
     dist = distributor.HTTPSDistributor(3, self.key, ProxySet(['1.1.1.1', '2.2.2.2']))
     subnet = 'proxy-group-3'
     subring = dist.mapSubnetToSubring(subnet, usingProxy=True)
     self.assertEqual(subring, dist.proxySubring)
예제 #7
0
 def test_HTTPSDistributor_init_with_proxies(self):
     """The HTTPSDistributor, when initialised with proxies, should add an
     extra hashring for proxy users.
     """
     dist = distributor.HTTPSDistributor(3, self.key, ProxySet(['1.1.1.1', '2.2.2.2']))
     self.assertIsNotNone(dist.proxies)
     self.assertGreater(dist.proxySubring, 0)
     self.assertEqual(dist.proxySubring, 4)
     self.assertEqual(dist.totalSubrings, 4)
예제 #8
0
 def test_HTTPSDistributor_mapSubnetToSubring_with_proxies(self):
     """HTTPSDistributor.mapSubnetToSubring() when the client wasn't using
     a proxy, but the distributor does have some known proxies and a
     proxySubring, should not map the client to the proxy subhashring.
     """
     dist = distributor.HTTPSDistributor(3, self.key, ProxySet(['1.1.1.1', '2.2.2.2']))
     # Note that if they were actually from a proxy, their subnet would be
     # something like "proxy-group-3".
     subnet = '15.1.0.0/16'
     subring = dist.mapSubnetToSubring(subnet, usingProxy=False)
     self.assertNotEqual(subring, dist.proxySubring)
예제 #9
0
    def test_HTTPSDistributor_getBridges_same_bridges_to_same_client(self):
        """The same client asking for bridges from the HTTPSDistributor
        multiple times in a row should get the same bridges in response each
        time.
        """
        dist = distributor.HTTPSDistributor(3, self.key)
        [dist.insert(bridge) for bridge in self.bridges[:250]]

        bridgeRequest = self.randomClientRequest()
        responses = {}
        for i in range(5):
            responses[i] = dist.getBridges(bridgeRequest, 1)
        for i in range(4):
            self.assertItemsEqual(responses[i], responses[i+1])
예제 #10
0
    def test_HTTPSDistributor_getBridges_with_blocked_bridges(self):
        dist = distributor.HTTPSDistributor(1, self.key)
        bridges = self.bridges[:]

        for bridge in bridges:
            bridge.setBlockedIn('cn')

        [dist.insert(bridge) for bridge in bridges]

        for _ in range(5):
            clientRequest1 = self.randomClientRequestForNotBlockedIn('cn')
            b = dist.getBridges(clientRequest1, 1)
            self.assertEqual(len(b), 0)

            clientRequest2 = self.randomClientRequestForNotBlockedIn('ir')
            b = dist.getBridges(clientRequest2, 1)
            self.assertEqual(len(b), 3)
예제 #11
0
    def test_HTTPSDistributor_getBridges_ipv4(self):
        """A request for IPv4 bridges should return IPv4 bridges."""
        dist = distributor.HTTPSDistributor(1, self.key)
        [dist.insert(bridge) for bridge in self.bridges[:250]]

        for i in xrange(500):
            bridgeRequest = self.randomClientRequest()
            bridgeRequest.generateFilters()

            bridges = dist.getBridges(bridgeRequest, "faketimestamp")
            self.assertTrue(type(bridges) is list)
            self.assertGreater(len(bridges), 0)

            bridge = random.choice(bridges)
            bridgeLine = bridge.getBridgeLine(bridgeRequest)
            addrport, fingerprint = bridgeLine.split()
            address, port = addrport.rsplit(':', 1)
            self.assertIsInstance(ipaddr.IPAddress(address), ipaddr.IPv4Address)
            self.assertIsNotNone(byIPv4(random.choice(bridges)))
예제 #12
0
    def test_HTTPSDistributor_prepopulateRings_without_proxies(self):
        """An HTTPSDistributor without proxies should prepopulate
        totalSubrings * 2 subrings.
        """
        dist = distributor.HTTPSDistributor(3, self.key)
        [dist.insert(bridge) for bridge in self.bridges]
        dist.prepopulateRings()
        self.assertEqual(len(dist.hashring.filterRings), 6)

        ipv4subrings = []
        ipv6subrings = []

        for subringName, (filters, subring) in dist.hashring.filterRings.items():
            if 'IPv4' in subringName:
                ipv6subrings.append(subring)
            if 'IPv6' in subringName:
                ipv6subrings.append(subring)

        self.assertEqual(len(ipv4subrings), len(ipv6subrings))
예제 #13
0
    def test_HTTPSDistributor_getBridges_ipv6_ipv4(self):
        """Asking for bridge addresses which are simultaneously IPv6 and IPv4
        (in that order) should return IPv6 bridges.
        """
        dist = distributor.HTTPSDistributor(1, self.key)
        [dist.insert(bridge) for bridge in self.bridges[:250]]

        bridgeRequest = self.randomClientRequest()
        bridgeRequest.withIPv6()
        bridgeRequest.generateFilters()
        bridgeRequest.filters.append(byIPv4)

        bridges = dist.getBridges(bridgeRequest, 1)
        self.assertEqual(len(bridges), 3)

        bridge = random.choice(bridges)
        bridgeLine = bridge.getBridgeLine(bridgeRequest)
        addrport, fingerprint = bridgeLine.split()
        address, port = addrport.rsplit(':', 1)
        address = address.strip('[]')
        self.assertIsInstance(ipaddr.IPAddress(address), ipaddr.IPv6Address)
        self.assertIsNotNone(byIPv6(random.choice(bridges)))
예제 #14
0
    def test_HTTPSDistributor_getBridges_with_varied_blocked_bridges(self):
        dist = distributor.HTTPSDistributor(1, self.key)
        bridges = self.bridges[:]

        for bridge in bridges:
            # Pretend that China blocks all vanilla bridges:
            bridge.setBlockedIn('cn', methodname='vanilla')
            # Pretend that China blocks all obfs2:
            bridge.setBlockedIn('cn', methodname='obfs2')
            # Pretend that China blocks some obfs3:
            if self.coinFlip():
                bridge.setBlockedIn('cn', methodname='obfs3')

        [dist.insert(bridge) for bridge in bridges]

        for i in xrange(5):
            bridgeRequest1 = self.randomClientRequestForNotBlockedIn('cn')
            bridgeRequest1.transports.append('obfs2')
            bridgeRequest1.generateFilters()
            # We shouldn't get any obfs2 bridges, since they're all blocked in
            # China:
            bridges = dist.getBridges(bridgeRequest1, "faketimestamp")
            self.assertEqual(len(bridges), 0)

            bridgeRequest2 = self.randomClientRequestForNotBlockedIn('cn')
            bridgeRequest2.transports.append('obfs3')
            bridgeRequest2.generateFilters()
            # We probably will get at least one bridge back!  It's pretty
            # unlikely to lose a coin flip 500 times in a row.
            bridges = dist.getBridges(bridgeRequest2, "faketimestamp")
            self.assertGreater(len(bridges), 0)

            bridgeRequest3 = self.randomClientRequestForNotBlockedIn('nl')
            bridgeRequest3.transports.append('obfs3')
            bridgeRequest3.generateFilters()
            # We should get bridges, since obfs3 isn't blocked in netherlands:
            bridges = dist.getBridges(bridgeRequest3, "faketimestamp")
            self.assertGreater(len(bridges), 0)
예제 #15
0
 def test_HTTPSDistributor_bridgesPerResponse_100_max_5(self):
     dist = distributor.HTTPSDistributor(3, self.key)
     dist._bridgesPerResponseMax = 5
     [dist.insert(bridge) for bridge in self.bridges[:100]]
     self.assertEqual(dist.bridgesPerResponse(), 5)
예제 #16
0
 def test_HTTPSDistributor_bridgesPerResponse_15(self):
     dist = distributor.HTTPSDistributor(3, self.key)
     [dist.insert(bridge) for bridge in self.bridges[:15]]
     self.assertEqual(dist.bridgesPerResponse(), 1)
예제 #17
0
 def test_HTTPSDistributor_bridgesPerResponse_100(self):
     dist = distributor.HTTPSDistributor(3, self.key)
     [dist.hashring.insert(bridge) for bridge in self.bridges[:100]]
     self.assertEqual(dist.bridgesPerResponse(), 3)