Exemplo n.º 1
0
    def setUp(self):
        synced_data_struct_factory = PiCNSyncDataStructFactory()
        synced_data_struct_factory.register(
            'fib', ForwardingInformationBaseMemoryPrefix)
        synced_data_struct_factory.register('faceidtable', FaceIDDict)
        synced_data_struct_factory.create_manager()
        fib = synced_data_struct_factory.manager.fib()
        self.faceidtable: FaceIDDict = synced_data_struct_factory.manager.faceidtable(
        )
        # Create a face and an example route
        self.mock_interface = MockInterface(port=1337)
        self.linklayer = BasicLinkLayer([self.mock_interface],
                                        self.faceidtable)

        outfid = self.linklayer.faceidtable.get_or_create_faceid(
            AddressInfo(('127.13.37.42', 4242), 0))
        fib.add_fib_entry(Name('/global'), [outfid])
        # List of advertised prefixes
        self.prefixes: List[Tuple[Name, bool]] = [(Name('/test/repos'), False),
                                                  (Name('/home'), True)]
        self.autoconflayer = AutoconfigServerLayer(
            linklayer=self.linklayer,
            address='127.0.1.1',
            registration_prefixes=self.prefixes)
        self.autoconflayer.fib = fib
        self.autoconflayer.queue_to_higher = self.queue_to_higher = multiprocessing.Queue(
        )
        self.autoconflayer.queue_from_higher = self.queue_from_higher = multiprocessing.Queue(
        )
        self.autoconflayer.queue_to_lower = self.queue_to_lower = multiprocessing.Queue(
        )
        self.autoconflayer.queue_from_lower = self.queue_from_lower = multiprocessing.Queue(
        )
Exemplo n.º 2
0
    def setUp(self):
        synced_data_struct_factory = PiCNSyncDataStructFactory()
        synced_data_struct_factory.register('cs', ContentStoreMemoryExact)
        synced_data_struct_factory.register('pit',
                                            PendingInterstTableMemoryExact)
        synced_data_struct_factory.register(
            'fib', ForwardingInformationBaseMemoryPrefix)
        synced_data_struct_factory.register('faceidtable', FaceIDDict)
        synced_data_struct_factory.create_manager()
        # Set up forwarder
        cs = synced_data_struct_factory.manager.cs()
        pit = synced_data_struct_factory.manager.pit()
        fib = synced_data_struct_factory.manager.fib()
        prefixes = [(Name('/test/prefix/repos'), True)]
        # Auto-assign port
        forwarder_interface = UDP4Interface(0)
        forwarder_fidtable = synced_data_struct_factory.manager.faceidtable()
        forwarder_linklayer = BasicLinkLayer([forwarder_interface],
                                             forwarder_fidtable)
        forwarder_port = forwarder_interface.get_port()
        forwarder_encoder = NdnTlvEncoder()
        icnlayer = BasicICNLayer()
        icnlayer.cs = cs
        icnlayer.pit = pit
        icnlayer.fib = fib
        forwarder_autoconfiglayer = AutoconfigServerLayer(
            forwarder_linklayer, registration_prefixes=prefixes)
        forwarder_autoconfiglayer.fib = fib
        self.forwarder = LayerStack([
            icnlayer, forwarder_autoconfiglayer,
            BasicPacketEncodingLayer(forwarder_encoder), forwarder_linklayer
        ])

        # Set up repo
        repository = MockRepository(Name('/thisshouldbechanged'))
        repo_chunkifyer = SimpleContentChunkifyer()
        repo_chunklayer = BasicChunkLayer(repo_chunkifyer)
        repo_encoder = NdnTlvEncoder()
        # Auto-assign port
        repo_interface = UDP4Interface(0)
        repo_fidtable = synced_data_struct_factory.manager.faceidtable()
        repo_linklayer = BasicLinkLayer([repo_interface], repo_fidtable)
        repo_port = repo_interface.get_port()
        self.repo = LayerStack([
            BasicRepositoryLayer(repository), repo_chunklayer,
            AutoconfigRepoLayer('testrepo', repo_linklayer, repository,
                                '127.0.0.1', forwarder_port),
            BasicPacketEncodingLayer(repo_encoder), repo_linklayer
        ])

        # Set up fetch client
        client_chunkifyer = SimpleContentChunkifyer()
        client_chunklayer = BasicChunkLayer(client_chunkifyer)
        client_encoder = NdnTlvEncoder()
        client_interface = UDP4Interface(0)
        client_fidtable = synced_data_struct_factory.manager.faceidtable()
        client_linklayer = BasicLinkLayer([client_interface], client_fidtable)
        self.client = LayerStack([
            client_chunklayer,
            AutoconfigClientLayer(client_linklayer, bcport=forwarder_port),
            BasicPacketEncodingLayer(client_encoder), client_linklayer
        ])
Exemplo n.º 3
0
    def __init__(self,
                 port=9000,
                 log_level=255,
                 encoder: BasicEncoder = None,
                 routing: bool = False,
                 peers=None,
                 autoconfig: bool = False,
                 interfaces: List[BaseInterface] = None,
                 ageing_interval: int = 3,
                 node_name: str = None):
        # debug level
        logger = Logger("ICNForwarder",
                        log_level)  # FIXME: Why isn't this self.logger???
        self._node_name = node_name
        # packet encoder
        if encoder is None:
            self.encoder = SimpleStringEncoder(log_level=log_level)
        else:
            encoder.set_log_level(log_level=log_level)
            self.encoder = encoder

        # setup data structures
        synced_data_struct_factory = PiCNSyncDataStructFactory()
        synced_data_struct_factory.register("cs", ContentStoreMemoryExact)
        synced_data_struct_factory.register(
            "fib", ForwardingInformationBaseMemoryPrefix)
        synced_data_struct_factory.register("pit",
                                            PendingInterestTableMemoryExact)
        synced_data_struct_factory.register("rib", TreeRoutingInformationBase)
        synced_data_struct_factory.register("faceidtable", FaceIDDict)
        synced_data_struct_factory.create_manager()

        cs = synced_data_struct_factory.manager.cs()
        fib = synced_data_struct_factory.manager.fib()
        pit = synced_data_struct_factory.manager.pit()

        rib = None
        if routing:
            rib = synced_data_struct_factory.manager.rib()
        faceidtable = synced_data_struct_factory.manager.faceidtable()

        # default interface
        if interfaces is not None:
            self.interfaces = interfaces
            mgmt_port = port
        else:
            interfaces = [UDP4Interface(port)]
            mgmt_port = interfaces[0].get_port()

        # initialize layers
        self.linklayer = BasicLinkLayer(interfaces,
                                        faceidtable,
                                        log_level=log_level)
        self.packetencodinglayer = BasicPacketEncodingLayer(
            self.encoder, log_level=log_level)
        self.icnlayer = BasicICNLayer(log_level=log_level,
                                      ageing_interval=ageing_interval)

        self.lstack: LayerStack = LayerStack(
            [self.icnlayer, self.packetencodinglayer, self.linklayer])

        if autoconfig:
            self.autoconfiglayer: AutoconfigServerLayer = AutoconfigServerLayer(
                linklayer=self.linklayer,
                address='127.0.0.1',
                registration_prefixes=[(Name('/testnetwork/repos'), True)],
                log_level=log_level)
            self.lstack.insert(self.autoconfiglayer, below_of=self.icnlayer)

        if routing:
            self.routinglayer = BasicRoutingLayer(self.linklayer,
                                                  peers=peers,
                                                  log_level=log_level)
            self.lstack.insert(self.routinglayer, below_of=self.icnlayer)

        self.icnlayer.cs = cs
        self.icnlayer.fib = fib
        # ----- by Luc # FIXME: How to pass these parameters to __init__
        self.icnlayer.fib.logger = logger
        self.icnlayer.fib.node_name = self._node_name
        # ----- by Luc # FIXME: How to pass these parameters to __init__
        self.icnlayer.pit = pit
        self.icnlayer.pit.logger = logger
        self.icnlayer.pit.node_name = self._node_name
        # -----

        if autoconfig:
            self.autoconfiglayer.fib = fib
        if routing:
            self.routinglayer.rib = rib
            self.routinglayer.fib = fib

        # mgmt
        self.mgmt = Mgmt(cs,
                         fib,
                         pit,
                         self.linklayer,
                         mgmt_port,
                         self.stop_forwarder,
                         log_level=log_level)
Exemplo n.º 4
0
class test_AutoconfigServerLayer(unittest.TestCase):

    def setUp(self):
        synced_data_struct_factory = PiCNSyncDataStructFactory()
        synced_data_struct_factory.register('fib', ForwardingInformationBaseMemoryPrefix)
        synced_data_struct_factory.register('faceidtable', FaceIDDict)
        synced_data_struct_factory.create_manager()
        fib = synced_data_struct_factory.manager.fib()
        self.faceidtable: FaceIDDict = synced_data_struct_factory.manager.faceidtable()
        # Create a face and an example route
        self.mock_interface = MockInterface(port=1337)
        self.linklayer = BasicLinkLayer([self.mock_interface], self.faceidtable)

        outfid = self.linklayer.faceidtable.get_or_create_faceid(AddressInfo(('127.13.37.42', 4242), 0))
        fib.add_fib_entry(Name('/global'), outfid)
        # List of advertised prefixes
        self.prefixes: List[Tuple[Name, bool]] = [(Name('/test/repos'), False), (Name('/home'), True)]
        self.autoconflayer = AutoconfigServerLayer(linklayer=self.linklayer,
                                                   address='127.0.1.1',
                                                   registration_prefixes=self.prefixes)
        self.autoconflayer.fib = fib
        self.autoconflayer.queue_to_higher = self.queue_to_higher = multiprocessing.Queue()
        self.autoconflayer.queue_from_higher = self.queue_from_higher = multiprocessing.Queue()
        self.autoconflayer.queue_to_lower = self.queue_to_lower = multiprocessing.Queue()
        self.autoconflayer.queue_from_lower = self.queue_from_lower = multiprocessing.Queue()

    def tearDown(self):
        self.autoconflayer.stop_process()
        self.queue_to_higher.close()
        self.queue_from_higher.close()
        self.queue_to_lower.close()
        self.queue_from_lower.close()

    def test_broadcast_enabled(self):
        """Test that broadcasting was enabled on the UDP socket"""
        self.autoconflayer.start_process()
        self.mock_interface.sock.setsockopt.assert_called_once_with(socket.SOL_SOCKET, socket.SO_BROADCAST, 1)

    def test_pass_through(self):
        """Test that autoconfig-unrelated content is passed through unchanged"""
        self.autoconflayer.start_process()
        # Pass an interest object from below
        interest = Interest(Name('/foo/bar'))
        self.faceidtable.add(42, AddressInfo(('127.13.37.42', 4567), 0))
        self.queue_from_lower.put([42, interest])
        data = self.queue_to_higher.get()
        self.assertEqual(2, len(data))
        self.assertEqual(42, data[0])
        self.assertEqual(interest, data[1])
        # Pass a content object from above
        content = Content(Name('/foo/bar'), 'foo bar')
        self.queue_from_higher.put([1337, content])
        data = self.queue_to_lower.get()
        self.assertEqual(2, len(data))
        self.assertEqual(1337, data[0])
        self.assertEqual(content, data[1])

    def test_get_forwarder_advertisement(self):
        """Test simple retrieval of the forwarder advertisement"""
        self.autoconflayer.start_process()
        # Send forwarder solicitation
        name = Name('/autoconfig/forwarders')
        interest = Interest(name)
        self.faceidtable.add(42, AddressInfo(('127.13.37.42', 4567), 0))
        self.queue_from_lower.put([42, interest])
        # Receive forwarder advertisement
        fid, packet = self.queue_to_lower.get()
        self.assertEqual(42, fid)
        self.assertIsInstance(packet, Content)
        self.assertEqual(name, packet.name)
        lines: List[str] = [line for line in packet.content.split('\n') if len(line) > 0]
        self.assertEqual(4, len(lines))
        self.assertEqual('udp4://127.0.1.1:1337', lines[0])
        self.assertIn('r:/global', lines)
        self.assertIn('pg:/test/repos', lines)
        self.assertIn('pl:/home', lines)

    def test_register_service(self):
        """Test service registration and subsequent retrieval of the service list"""
        self.autoconflayer.start_process()
        # Send service registration
        rname = Name('/autoconfig/service')
        rname += 'udp4://127.42.42.42:1337'
        rname += 'test'
        rname += 'repos'
        rname += 'testrepo'
        rinterest = Interest(rname)
        self.faceidtable.add(42, AddressInfo(('127.13.37.42', 4567), 0))
        self.queue_from_lower.put([42, rinterest])
        # Receive service registration ACK
        fid, packet = self.queue_to_lower.get()
        self.assertEqual(42, fid)
        self.assertIsInstance(packet, Content)
        self.assertEqual(rname, packet.name)
        # Request known services list
        lname = Name('/autoconfig/services')
        linterest = Interest(lname)
        self.queue_from_lower.put([42, linterest])
        # Receive known services list
        fid, packet = self.queue_to_lower.get()
        self.assertEqual(42, fid)
        self.assertIsInstance(packet, Content)
        self.assertEqual(lname, packet.name)
        lines: List[str] = [line for line in packet.content.split('\n') if len(line) > 0]
        self.assertIn('/test/repos/testrepo', lines)

    def test_reregister_service(self):
        """Test re-registration of a service with matching name and address"""
        self.autoconflayer.start_process()
        rname = Name('/autoconfig/service')
        rname += 'udp4://127.42.42.42:1337'
        rname += 'test'
        rname += 'repos'
        rname += 'testrepo'
        rinterest = Interest(rname)
        for i in range(2):
            # Send service registration
            self.faceidtable.add(42, AddressInfo(('127.13.37.42', 4567), 0))
            self.queue_from_lower.put([42, rinterest])
            # Receive service registration, should be ACK both times
            fid, packet = self.queue_to_lower.get()
            self.assertEqual(42, fid)
            self.assertIsInstance(packet, Content)
            self.assertEqual(rname, packet.name)

    def test_register_service_twice_different_addr_nack(self):
        """Test registration of a second service with a different address under the same name; should be refused"""
        self.autoconflayer.start_process()
        # Send first service registration
        rname = Name('/autoconfig/service')
        rname += 'udp4://127.42.42.42:1337'
        rname += 'test'
        rname += 'repos'
        rname += 'testrepo'
        rinterest = Interest(rname)
        self.faceidtable.add(42, AddressInfo(('127.13.37.42', 4567), 0))
        self.queue_from_lower.put([42, rinterest])
        # Receive first service registration reply, should be ACK
        fid, packet = self.queue_to_lower.get()
        self.assertEqual(42, fid)
        self.assertIsInstance(packet, Content)
        self.assertEqual(rname, packet.name)
        # Send second service registration with different address
        fname = Name('/autoconfig/service')
        fname += 'udp4://127.0.0.42:1337'
        fname += 'test'
        fname += 'repos'
        fname += 'testrepo'
        finterest = Interest(fname)
        self.queue_from_lower.put([42, finterest])
        # Receive second service registration reply, should be NACK
        fid, packet = self.queue_to_lower.get()
        self.assertEqual(42, fid)
        self.assertIsInstance(packet, Nack)
        self.assertEqual(NackReason.DUPLICATE, packet.reason)
        self.assertEqual(fname, packet.name)

    def test_register_service_unavailable_prefix_nack(self):
        """Test registration of a service under a prefix that is not advertised by the forwarder; should be refused"""
        self.autoconflayer.start_process()
        # Send service registration with non-advertised name
        rname = Name('/autoconfig/service')
        rname += 'udp4://127.42.42.42:1337'
        rname += 'otherprefix'
        rname += 'testrepo'
        rinterest = Interest(rname)
        self.faceidtable.add(42, AddressInfo(('127.13.37.42', 4567), 0))
        self.queue_from_lower.put([42, rinterest])
        # Receive service registration reply, should be NACK
        fid, packet = self.queue_to_lower.get()
        self.assertEqual(42, fid)
        self.assertIsInstance(packet, Nack)
        self.assertEqual(rname, packet.name)
        self.assertEqual(packet.reason, NackReason.NO_ROUTE)