def test_deny_rule_install(self):
        """
        Adds a policy to a subscriber. Verifies that flows are properly
        installed in enforcement and enforcement stats.
        Assert:
            Policy classification flows installed in enforcement
            Policy match flows installed in enforcement_stats
        """
        fake_controller_setup(self.enforcement_controller,
                              self.enforcement_stats_controller)
        imsi = 'IMSI001010000000014'
        sub_ip = '192.16.15.7'
        num_pkt_unmatched = 4096

        flow_list = [
            FlowDescription(match=FlowMatch(
                ip_dst=convert_ipv4_str_to_ip_proto('1.1.0.0/24'),
                direction=FlowMatch.UPLINK),
                            action=FlowDescription.DENY)
        ]
        policy = PolicyRule(id='rule1', priority=3, flow_list=flow_list)
        self.service_manager.session_rule_version_mapper.update_version(
            imsi, convert_ipv4_str_to_ip_proto(sub_ip), 'rule1')
        """ Setup subscriber, setup table_isolation to fwd pkts """
        sub_context = RyuDirectSubscriberContext(
            imsi, sub_ip, self.enforcement_controller, self._main_tbl_num,
            self.enforcement_stats_controller).add_dynamic_rule(policy)

        isolator = RyuDirectTableIsolator(
            RyuForwardFlowArgsBuilder.from_subscriber(
                sub_context.cfg).build_requests(), self.testing_controller)

        pkt_sender = ScapyPacketInjector(self.IFACE)
        packet = IPPacketBuilder() \
            .set_ip_layer('45.10.0.0/20', sub_ip) \
            .set_ether_layer(self.MAC_DEST, "00:00:00:00:00:00") \
            .build()

        # =========================== Verification ===========================

        # Verifies that 1 flow is installed in enforcement and 2 flows are
        # installed in enforcement stats, one for uplink and one for downlink.
        snapshot_verifier = SnapshotVerifier(self, self.BRIDGE,
                                             self.service_manager)

        with isolator, sub_context, snapshot_verifier:
            pkt_sender.send(packet)

        enf_stat_name = imsi + '|' + self.DEFAULT_DROP_FLOW_NAME + '|' + sub_ip
        wait_for_enforcement_stats(self.enforcement_stats_controller,
                                   [enf_stat_name])
        stats = get_enforcement_stats(
            self.enforcement_stats_controller._report_usage.call_args_list)

        self.assertEqual(stats[enf_stat_name].sid, imsi)
        self.assertEqual(stats[enf_stat_name].rule_id,
                         self.DEFAULT_DROP_FLOW_NAME)
        self.assertEqual(stats[enf_stat_name].dropped_rx, 0)
        self.assertEqual(stats[enf_stat_name].dropped_tx,
                         num_pkt_unmatched * len(packet))
Exemple #2
0
def activate_flows(client, args):
    request = ActivateFlowsRequest(
        sid=SIDUtils.to_pb(args.imsi),
        ip_addr=args.ipv4,
        policies=[
            VersionedPolicy(
                rule=PolicyRule(
                    id=args.rule_id,
                    priority=args.priority,
                    hard_timeout=args.hard_timeout,
                    flow_list=[
                        FlowDescription(
                            match=FlowMatch(
                                ip_dst=convert_ipv4_str_to_ip_proto(args.ipv4_dst),
                                direction=FlowMatch.UPLINK,
                            ),
                        ),
                        FlowDescription(
                            match=FlowMatch(
                                ip_src=convert_ipv4_str_to_ip_proto(args.ipv4_dst),
                                direction=FlowMatch.DOWNLINK,
                            ),
                        ),
                    ],
                ),
                version=1,
            ),
        ],
        request_origin=RequestOriginType(type=RequestOriginType.GX),
        shard_id=args.shard_id,
    )
    response = client.ActivateFlows(request)
    _print_rule_mod_results(response.policy_results)
Exemple #3
0
def add_rule(args):
    rule_id = args.rule_id
    policy_dict = PolicyRuleDict()
    arg_list = {
        'ip_proto':
        args.ip_proto,
        'ip_dst':
        IPAddress(version=IPAddress.IPV4,
                  address=args.ipv4_dst.encode('utf-8')),
        'ip_src':
        IPAddress(version=IPAddress.IPV4,
                  address=args.ipv4_src.encode('utf-8')),
        'tcp_dst':
        args.tcp_dst,
        'tcp_src':
        args.tcp_src,
        'udp_dst':
        args.udp_dst,
        'udp_src':
        args.udp_src,
        'direction':
        args.direction
    }
    match = FlowMatch(**arg_list)
    flow = FlowDescription(match=match, action=args.action)
    rule = policy_dict.get(rule_id)
    if not rule or args.overwrite:
        action = 'add'
        rule = PolicyRule(id=rule_id, flow_list=[flow])
    else:
        action = 'edit'
        rule.flow_list.extend([flow])
    policy_dict[rule_id] = rule
    print("Rule '%s' successfully %sed!" % (rule_id, action))
Exemple #4
0
def create_uplink_rule(id,
                       rating_group,
                       ip_dest,
                       m_key=None,
                       priority=10,
                       tracking=PolicyRule.ONLY_OCS,
                       action=FlowDescription.PERMIT):
    """
    Create a rule with a single uplink IP flow, useful for testing
    Args:
        id (string): rule id
        rating_group (int): charging key
        ip_dest (string): IP destination for rule flow
        m_key (optional string): monitoring key, if the rule is tracked by PCRF
        priority (int): priority of flow, the greater the higher the priority
        tracking (PolicyRule.TrackingType): enum to dictate whether OCS or PCRF
            or both is tracking the credit
        action: permit or deny
    Returns:
        PolicyRule with single uplink IP flow
    """
    return PolicyRule(
        id=id,
        priority=priority,
        flow_list=[
            FlowDescription(match=FlowMatch(ipv4_dst=ip_dest,
                                            direction=FlowMatch.UPLINK),
                            action=action)
        ],
        tracking_type=tracking,
        rating_group=rating_group,
        monitoring_key=m_key,
    )
Exemple #5
0
    def test_invalid_subscriber(self):
        """
        Try to apply an invalid policy to a subscriber, should log and error

        Assert:
            Only 1 flow gets added to the table (drop flow)
        """
        fake_controller_setup(self.enforcement_controller)
        imsi = 'IMSI000000000000001'
        sub_ip = '192.168.128.45'
        flow_list = [
            FlowDescription(match=FlowMatch(
                ip_src=convert_ipv4_str_to_ip_proto('9999.0.0.0/24')),
                            action=FlowDescription.DENY)
        ]
        policy = PolicyRule(id='invalid', priority=2, flow_list=flow_list)
        invalid_sub_context = RyuDirectSubscriberContext(
            imsi, sub_ip, self.enforcement_controller,
            self._tbl_num).add_dynamic_rule(policy)
        isolator = RyuDirectTableIsolator(
            RyuForwardFlowArgsBuilder.from_subscriber(
                invalid_sub_context.cfg).build_requests(),
            self.testing_controller)
        flow_query = FlowQuery(self._tbl_num, self.testing_controller)
        num_flows_start = len(flow_query.lookup())
        snapshot_verifier = SnapshotVerifier(self, self.BRIDGE,
                                             self.service_manager)

        with isolator, invalid_sub_context, snapshot_verifier:
            wait_after_send(self.testing_controller)
            num_flows_final = len(flow_query.lookup())

        self.assertEqual(num_flows_final - num_flows_start, 0)
Exemple #6
0
    def test_rule_install(self):
        """
        Adds a policy to a subscriber. Verifies that flows are properly
        installed in enforcement and enforcement stats.

        Assert:
            Policy classification flows installed in enforcement
            Policy match flows installed in enforcement_stats
        """
        fake_controller_setup(self.enforcement_controller,
                              self.enforcement_stats_controller)
        imsi = 'IMSI001010000000013'
        sub_ip = '192.168.128.74'

        flow_list = [
            FlowDescription(match=FlowMatch(ipv4_dst='45.10.0.0/25',
                                            direction=FlowMatch.UPLINK),
                            action=FlowDescription.PERMIT)
        ]
        policy = PolicyRule(id='rule1', priority=3, flow_list=flow_list)
        self.service_manager.session_rule_version_mapper.update_version(
            imsi, 'rule1')
        version = \
            self.service_manager.session_rule_version_mapper.get_version(
                imsi, 'rule1')
        """ Setup subscriber, setup table_isolation to fwd pkts """
        self._static_rule_dict[policy.id] = policy
        sub_context = RyuDirectSubscriberContext(
            imsi, sub_ip, self.enforcement_controller, self._main_tbl_num,
            self.enforcement_stats_controller).add_static_rule(policy.id)

        # =========================== Verification ===========================
        rule_num = self.enforcement_stats_controller._rule_mapper \
            .get_or_create_rule_num(policy.id)
        enf_query = FlowQuery(self._main_tbl_num,
                              self.testing_controller,
                              match=flow_match_to_magma_match(
                                  FlowMatch(ipv4_dst='45.10.0.0/25',
                                            direction=FlowMatch.UPLINK)),
                              cookie=rule_num)
        es_query = FlowQuery(self._scratch_tbl_num,
                             self.testing_controller,
                             match=MagmaMatch(imsi=encode_imsi(imsi),
                                              reg2=rule_num,
                                              rule_version=version),
                             cookie=rule_num)

        # Verifies that 1 flow is installed in enforcement and 2 flows are
        # installed in enforcement stats, one for uplink and one for downlink.
        flow_verifier = FlowVerifier([
            FlowTest(enf_query, 0, flow_count=1),
            FlowTest(es_query, 0, flow_count=2),
        ], lambda: None)
        snapshot_verifier = SnapshotVerifier(self, self.BRIDGE,
                                             self.service_manager)

        with sub_context, flow_verifier, snapshot_verifier:
            pass

        flow_verifier.verify()
Exemple #7
0
 def create_bearer(self, imsi, lbi):
     """
     Sends a CreateBearer Request to SPGW service
     """
     print('Sending CreateBearer request to spgw service')
     req = CreateBearerRequest(
         sid=SIDUtils.to_pb(imsi),
         link_bearer_id=lbi,
         policy_rules=[
             PolicyRule(
                 qos=FlowQos(
                     qci=1,
                     gbr_ul=10000000,
                     gbr_dl=10000000,
                     max_req_bw_ul=10000000,
                     max_req_bw_dl=10000000,
                     arp=QosArp(
                         priority_level=1,
                         pre_capability=1,
                         pre_vulnerability=0,
                     )
                 )
             )
         ]
     )
     self._stub.CreateBearer(req)
Exemple #8
0
    def test_redirect_policy(self):
        """
        Add a redirect policy, verifies that EnforcementStatsController reports
        correct stats to sessiond

        Assert:
            1 Packet is matched and reported
        """
        fake_controller_setup(self.enforcement_controller,
                              self.enforcement_stats_controller)
        redirect_ips = ["185.128.101.5", "185.128.121.4"]
        self.enforcement_controller._redirect_manager._dns_cache.get(
            "about.sha.ddih.org", lambda: redirect_ips, max_age=42)
        imsi = 'IMSI010000000088888'
        sub_ip = '192.168.128.74'
        flow_list = [FlowDescription(match=FlowMatch())]
        policy = PolicyRule(id='redir_test',
                            priority=3,
                            flow_list=flow_list,
                            redirect=RedirectInformation(
                                support=1,
                                address_type=2,
                                server_address="http://about.sha.ddih.org/"))
        stat_name = imsi + '|redir_test' + '|' + sub_ip
        self.service_manager.session_rule_version_mapper.update_version(
            imsi, convert_ipv4_str_to_ip_proto(sub_ip), 'redir_test')
        """ Setup subscriber, setup table_isolation to fwd pkts """
        self._static_rule_dict[policy.id] = policy
        sub_context = RyuDirectSubscriberContext(
            imsi, sub_ip, self.enforcement_controller, self._main_tbl_num,
            self.enforcement_stats_controller).add_dynamic_rule(policy)
        isolator = RyuDirectTableIsolator(
            RyuForwardFlowArgsBuilder.from_subscriber(
                sub_context.cfg).build_requests(), self.testing_controller)
        pkt_sender = ScapyPacketInjector(self.IFACE)
        packet = TCPPacketBuilder() \
            .set_tcp_layer(42132, 80, 321) \
            .set_tcp_flags("S") \
            .set_ip_layer('151.42.41.122', sub_ip) \
            .set_ether_layer(self.MAC_DEST, "00:00:00:00:00:00") \
            .build()

        # =========================== Verification ===========================
        snapshot_verifier = SnapshotVerifier(self, self.BRIDGE,
                                             self.service_manager)
        """ Send packet, wait until pkts are received by ovs and enf stats """
        with isolator, sub_context, snapshot_verifier:
            self.enforcement_stats_controller._report_usage.reset_mock()
            pkt_sender.send(packet)

        wait_for_enforcement_stats(self.enforcement_stats_controller,
                                   [stat_name])
        """ Send packets, wait until pkts are received by ovs and enf stats """
        stats = get_enforcement_stats(
            self.enforcement_stats_controller._report_usage.call_args_list)

        self.assertEqual(stats[stat_name].sid, imsi)
        self.assertEqual(stats[stat_name].rule_id, "redir_test")
        self.assertEqual(stats[stat_name].bytes_rx, 0)
        self.assertEqual(stats[stat_name].bytes_tx, len(packet))
Exemple #9
0
    def test_subscriber_restrict_policy(self):
        """
        Add restrict policy to subscriber, send 4096 packets

        Assert:
            Packets are properly matched with the 'restrict_match' policy
            Send /20 (4096) packets, match /16 (256) packets
        """
        fake_controller_setup(self.gy_controller)
        imsi = 'IMSI010000000088888'
        sub_ip = '192.168.128.74'
        flow_list1 = [
            FlowDescription(match=FlowMatch(
                ip_dst=convert_ipv4_str_to_ip_proto('8.8.8.0/24'),
                direction=FlowMatch.UPLINK),
                            action=FlowDescription.PERMIT)
        ]
        policies = [
            VersionedPolicy(
                rule=PolicyRule(id='restrict_match',
                                priority=2,
                                flow_list=flow_list1),
                version=1,
            )
        ]
        pkts_matched = 256
        pkts_sent = 4096

        # ============================ Subscriber ============================
        sub_context = RyuDirectSubscriberContext(
            imsi, sub_ip, self.gy_controller,
            self._tbl_num).add_policy(policies[0])
        isolator = RyuDirectTableIsolator(
            RyuForwardFlowArgsBuilder.from_subscriber(
                sub_context.cfg).build_requests(), self.testing_controller)
        pkt_sender = ScapyPacketInjector(self.IFACE)
        packet = IPPacketBuilder()\
            .set_ip_layer('8.8.8.8', sub_ip)\
            .set_ether_layer(self.MAC_DEST, "00:00:00:00:00:00")\
            .build()
        flow_query = FlowQuery(self._tbl_num,
                               self.testing_controller,
                               match=flow_match_to_magma_match(
                                   flow_list1[0].match))

        # =========================== Verification ===========================
        # Verify aggregate table stats, subscriber 1 'simple_match' pkt count
        flow_verifier = FlowVerifier([
            FlowTest(FlowQuery(self._tbl_num, self.testing_controller),
                     pkts_sent),
            FlowTest(flow_query, pkts_matched)
        ], lambda: wait_after_send(self.testing_controller))
        snapshot_verifier = SnapshotVerifier(self,
                                             self.BRIDGE,
                                             self.service_manager,
                                             include_stats=False)

        with isolator, sub_context, flow_verifier, snapshot_verifier:
            pkt_sender.send(packet)
Exemple #10
0
    def test_cookie_poll(self):
        """
        Add a subscriber policy, verify flows are properly installed
        Assert:
        Query with RULE_NUM 1 returns proper values
        """
        original = self.enforcement_stats_controller._poll_stats
        self.enforcement_stats_controller._poll_stats = MagicMock()
        self.enforcement_stats_controller.init_finished = False
        self.enforcement_controller.init_finished = True

        imsi = 'IMSI001010000000013'
        sub_ip = '192.168.128.74'

        flow_list = [
            FlowDescription(
                match=FlowMatch(
                    ip_dst=convert_ipv4_str_to_ip_proto('45.10.0.0/25'),
                    direction=FlowMatch.UPLINK,
                ),
                action=FlowDescription.PERMIT,
            ),
        ]

        policy = VersionedPolicy(
            rule=PolicyRule(id='rule1', priority=3, flow_list=flow_list),
            version=1,
        )
        enf_stat_name = imsi + '|' + 'rule1' + '|' + sub_ip + '|' + "1"
        """ Setup subscriber, setup table_isolation to fwd pkts """
        sub_context = RyuDirectSubscriberContext(
            imsi, sub_ip, self.enforcement_controller,
            self._main_tbl_num, self.enforcement_stats_controller,
        ).add_policy(policy)

        snapshot_verifier = SnapshotVerifier(
            self, self.BRIDGE,
            self.service_manager,
        )

        self.enforcement_stats_controller._report_usage.reset_mock()
        with sub_context, snapshot_verifier:
            self.enforcement_stats_controller.init_finished = True
            flows.send_stats_request(
                self.enforcement_stats_controller._datapath,
                self.enforcement_stats_controller.tbl_num,
                0,
                flows.OVS_COOKIE_MATCH_ALL,
            )
            wait_for_enforcement_stats(
                self.enforcement_stats_controller,
                [enf_stat_name],
            )
        stats = get_enforcement_stats(
            self.enforcement_stats_controller._report_usage.call_args_list,
        )
        self.assertEqual(stats[enf_stat_name].rule_id, 'rule1')
        self.enforcement_stats_controller._poll_stats = original
        self.assertEqual(len(stats), 2)
Exemple #11
0
    def test_subscriber_ipv6_policy(self):
        """
        Add policy to subscriber, send 4096 packets

        Assert:
            Packets are properly matched with the 'simple_match' policy
            Send /20 (4096) packets, match /16 (256) packets
        """
        fake_controller_setup(self.enforcement_controller)
        imsi = 'IMSI010000000088888'
        sub_ip = 'de34:431d:1bc::'
        flow_list1 = [
            FlowDescription(
                match=FlowMatch(
                    ip_dst=convert_ipv6_bytes_to_ip_proto(
                        'f333:432::dbca'.encode('utf-8'), ),
                    direction=FlowMatch.UPLINK,
                ),
                action=FlowDescription.PERMIT,
            ),
        ]
        policies = [
            VersionedPolicy(
                rule=PolicyRule(id='simple_match',
                                priority=2,
                                flow_list=flow_list1),
                version=1,
            ),
        ]

        # ============================ Subscriber ============================
        sub_context = RyuDirectSubscriberContext(
            imsi,
            sub_ip,
            self.enforcement_controller,
            self._tbl_num,
        ).add_policy(policies[0])
        isolator = RyuDirectTableIsolator(
            RyuForwardFlowArgsBuilder.from_subscriber(
                sub_context.cfg).build_requests(),
            self.testing_controller,
        )
        pkt_sender = ScapyPacketInjector(self.IFACE)
        packet = IPv6PacketBuilder() \
            .set_ip_layer('f333:432::dbca', sub_ip) \
            .set_ether_layer(self.MAC_DEST, "00:00:00:00:00:00") \
            .build()

        # =========================== Verification ===========================
        snapshot_verifier = SnapshotVerifier(
            self,
            self.BRIDGE,
            self.service_manager,
        )

        with isolator, sub_context, snapshot_verifier:
            pkt_sender.send(packet)
Exemple #12
0
    def test_poll(self):
        """
        Unit test to help verify stats polling using cookie and cookie_mask
        """
        fake_controller_setup(
            self.enforcement_controller,
            self.enforcement_stats_controller,
        )
        imsi = 'IMSI001010000000013'
        sub_ip = '192.168.128.74'

        flow_list = [
            FlowDescription(
                match=FlowMatch(
                    ip_dst=convert_ipv4_str_to_ip_proto('45.10.0.0/25'),
                    direction=FlowMatch.UPLINK,
                ),
                action=FlowDescription.PERMIT,
            ),
        ]
        policy = VersionedPolicy(
            rule=PolicyRule(id='rule1', priority=3, flow_list=flow_list),
            version=1,
        )
        self.service_manager.session_rule_version_mapper.save_version(
            imsi, convert_ipv4_str_to_ip_proto(sub_ip), 'rule1', 1,
        )

        """ Setup subscriber, setup table_isolation to fwd pkts """
        sub_context = RyuDirectSubscriberContext(
            imsi, sub_ip, self.enforcement_controller,
            self._main_tbl_num, self.enforcement_stats_controller,
        ).add_policy(policy)

        snapshot_verifier = SnapshotVerifier(
            self, self.BRIDGE,
            self.service_manager,
        )
        with sub_context, snapshot_verifier:
            rule_map = self.enforcement_stats_controller.get_stats()
            if (rule_map.records[0].rule_id == self.DEFAULT_DROP_FLOW_NAME):
                rule_record = rule_map.records[1]
            else:
                rule_record = rule_map.records[0]
            self.assertEqual(rule_record.sid, imsi)
            self.assertEqual(rule_record.rule_id, "rule1")
            self.assertEqual(rule_record.bytes_tx, 0)
            self.assertEqual(rule_record.bytes_rx, 0)
            rule_map_cookie = self.enforcement_stats_controller.get_stats(1, 0)
            if (rule_map_cookie.records[0].rule_id == self.DEFAULT_DROP_FLOW_NAME):
                rule_record_cookie = rule_map_cookie.records[1]
            else:
                rule_record_cookie = rule_map_cookie.records[0]
            self.assertEqual(rule_record_cookie.sid, imsi)
            self.assertEqual(rule_record_cookie.rule_id, "rule1")
            self.assertEqual(rule_record_cookie.bytes_tx, 0)
            self.assertEqual(rule_record_cookie.bytes_rx, 0)
Exemple #13
0
    def CreateAddQERinPDR(
        qos_enforce_rule: QoSEnforceRuleEntry,
        ue_ip_addr: str,
        apn_ambr: AggregatedMaximumBitrate,
    ) -> ActivateFlowsRequest:

        if qos_enforce_rule.allow == 'YES':
            allow = FlowDescription.PERMIT
        else:
            allow = FlowDescription.DENY

        ip_dst = None
        ip_src = None

        if qos_enforce_rule.ipv4_dst:
            ip_dst = convert_ipv4_str_to_ip_proto(qos_enforce_rule.ipv4_dst)
            ip_src = convert_ipv4_str_to_ip_proto(qos_enforce_rule.ipv4_dst)

        if qos_enforce_rule.direction == FlowMatch.UPLINK:
            flow_list = [
                FlowDescription(
                    match=FlowMatch(
                        ip_dst=ip_dst,
                        direction=qos_enforce_rule.direction,
                    ),
                    action=allow,
                ),
            ]
        else:
            flow_list = [
                FlowDescription(
                    match=FlowMatch(
                        ip_src=ip_src,
                        direction=qos_enforce_rule.direction,
                    ),
                    action=allow,
                ),
            ]
        qos_enforce_rule = ActivateFlowsRequest(
            sid=SIDUtils.to_pb(qos_enforce_rule.imsi),
            ip_addr=ue_ip_addr,
            policies=[
                VersionedPolicy(
                    rule=PolicyRule(
                        id=qos_enforce_rule.rule_id,
                        priority=qos_enforce_rule.priority,
                        hard_timeout=qos_enforce_rule.hard_timeout,
                        flow_list=flow_list,
                    ),
                    version=1,
                ),
            ],
            request_origin=RequestOriginType(type=RequestOriginType.N4),
            apn_ambr=apn_ambr,
        )
        return qos_enforce_rule
    def test_rule_install(self):
        """
        Adds a policy to a subscriber. Verifies that flows are properly
        installed in enforcement and enforcement stats.

        Assert:
            Policy classification flows installed in enforcement
            Policy match flows installed in enforcement_stats
        """
        fake_controller_setup(
            self.enforcement_controller,
            self.enforcement_stats_controller,
        )
        imsi = 'IMSI001010000000013'
        sub_ip = '192.168.128.74'

        flow_list = [
            FlowDescription(
                match=FlowMatch(
                    ip_dst=convert_ipv4_str_to_ip_proto('45.10.0.0/25'),
                    direction=FlowMatch.UPLINK,
                ),
                action=FlowDescription.PERMIT,
            ),
        ]
        policy = VersionedPolicy(
            rule=PolicyRule(id='rule1', priority=3, flow_list=flow_list),
            version=1,
        )
        self.service_manager.session_rule_version_mapper.save_version(
            imsi,
            convert_ipv4_str_to_ip_proto(sub_ip),
            'rule1',
            1,
        )
        """ Setup subscriber, setup table_isolation to fwd pkts """
        sub_context = RyuDirectSubscriberContext(
            imsi,
            sub_ip,
            self.enforcement_controller,
            self._main_tbl_num,
            self.enforcement_stats_controller,
        ).add_policy(policy)

        # =========================== Verification ===========================

        # Verifies that 1 flow is installed in enforcement and 2 flows are
        # installed in enforcement stats, one for uplink and one for downlink.
        snapshot_verifier = SnapshotVerifier(
            self,
            self.BRIDGE,
            self.service_manager,
        )

        with sub_context, snapshot_verifier:
            pass
    def test_ipv6_rule_install(self):
        """
        Adds a ipv6 policy to a subscriber. Verifies that flows are properly
        installed in enforcement and enforcement stats.

        Assert:
            Policy classification flows installed in enforcement
            Policy match flows installed in enforcement_stats
        """
        fake_controller_setup(
            self.enforcement_controller,
            self.enforcement_stats_controller,
        )

        imsi = 'IMSI001010000000013'
        sub_ip = 'de34:431d:1bc::'

        flow_list = [
            FlowDescription(
                match=FlowMatch(
                    ip_dst=convert_ipv6_bytes_to_ip_proto(
                        'f333:432::dbca'.encode('utf-8'), ),
                    direction=FlowMatch.UPLINK,
                ),
                action=FlowDescription.PERMIT,
            ),
        ]
        policy = VersionedPolicy(
            rule=PolicyRule(id='rule1', priority=3, flow_list=flow_list),
            version=1,
        )
        self.service_manager.session_rule_version_mapper.save_version(
            imsi,
            convert_ipv4_str_to_ip_proto(sub_ip),
            'rule1',
            1,
        )
        """ Setup subscriber, setup table_isolation to fwd pkts """
        sub_context = RyuDirectSubscriberContext(
            imsi,
            sub_ip,
            self.enforcement_controller,
            self._main_tbl_num,
            self.enforcement_stats_controller,
        ).add_policy(policy)

        # =========================== Verification ===========================
        snapshot_verifier = SnapshotVerifier(
            self,
            self.BRIDGE,
            self.service_manager,
        )

        with sub_context, snapshot_verifier:
            pass
Exemple #16
0
    def test_activate_flows_req(self):
        rule = PolicyRule(id="rule1", priority=100, flow_list=[])
        policies = [VersionedPolicy(rule=rule, version=1)]
        req = ActivateFlowsRequest(
            sid=SubscriberID(id="imsi12345"),
            ip_addr="1.2.3.4",
            msisdn=b'magma',
            uplink_tunnel=0x1,
            downlink_tunnel=0x2,
            policies=policies,
        )
        ip_addr = IPAddress(
            version=IPAddress.IPV4,
            address=req.ip_addr.encode('utf-8'),
        )

        self.pipelined_srv.ActivateFlows(req, MagicMock())
        # Not using assert_called_with because protos comparison

        assert self._enforcement_stats.activate_rules.call_args.args[
            0] == req.sid.id
        assert self._enforcement_stats.activate_rules.call_args.args[
            1] == req.msisdn
        assert self._enforcement_stats.activate_rules.call_args.args[
            2] == req.uplink_tunnel
        assert self._enforcement_stats.activate_rules.call_args.args[
            3].version == ip_addr.version
        assert self._enforcement_stats.activate_rules.call_args.args[
            3].address == ip_addr.address
        assert self._enforcement_stats.activate_rules.call_args.args[
            4] == req.apn_ambr
        assert self._enforcement_stats.activate_rules.call_args.args[5][
            0].version == policies[0].version
        assert self._enforcement_stats.activate_rules.call_args.args[
            6] == req.shard_id
        assert self._enforcement_stats.activate_rules.call_args.args[7] == 0

        assert self._enforcer_app.activate_rules.call_args.args[
            0] == req.sid.id
        assert self._enforcer_app.activate_rules.call_args.args[
            1] == req.msisdn
        assert self._enforcer_app.activate_rules.call_args.args[
            2] == req.uplink_tunnel
        assert self._enforcer_app.activate_rules.call_args.args[
            3].version == ip_addr.version
        assert self._enforcer_app.activate_rules.call_args.args[
            3].address == ip_addr.address
        assert self._enforcer_app.activate_rules.call_args.args[
            4] == req.apn_ambr
        assert self._enforcer_app.activate_rules.call_args.args[5][
            0].version == policies[0].version
        assert self._enforcer_app.activate_rules.call_args.args[
            6] == req.shard_id
        assert self._enforcer_app.activate_rules.call_args.args[7] == 0
Exemple #17
0
 def _get_redirect_policies(self):
     """ Policy to redirect traffic to the captive portal """
     redirect_info = RedirectInformation(
         support=RedirectInformation.ENABLED,
         address_type=RedirectInformation.URL,
         server_address=self._captive_portal_address)
     return [
         PolicyRule(id='redirect',
                    priority=self.REDIRECT_PRIORITY,
                    redirect=redirect_info)
     ]
Exemple #18
0
    def test_subscriber_policy(self):
        """
        Add policy to subscriber, send 4096 packets

        Assert:
            Packets are properly matched with the 'simple_match' policy
            Send /20 (4096) packets, match /16 (256) packets
        """
        imsi = 'IMSI010000000088888'
        sub_ip = '192.168.128.74'
        flow_list1 = [FlowDescription(
            match=FlowMatch(
                ipv4_dst='45.10.0.0/24', direction=FlowMatch.UPLINK),
            action=FlowDescription.PERMIT)
        ]
        policies = [
            PolicyRule(id='simple_match', priority=2, flow_list=flow_list1)
        ]
        pkts_matched = 256
        pkts_sent = 4096

        self._static_rule_dict[policies[0].id] = policies[0]

        # ============================ Subscriber ============================
        sub_context = RyuDirectSubscriberContext(
            imsi, sub_ip, self.enforcement_controller, self._tbl_num
        ).add_static_rule(policies[0].id)
        isolator = RyuDirectTableIsolator(
            RyuForwardFlowArgsBuilder.from_subscriber(sub_context.cfg)
                                     .build_requests(),
            self.testing_controller
        )
        pkt_sender = ScapyPacketInjector(self.IFACE)
        packet = IPPacketBuilder()\
            .set_ip_layer('45.10.0.0/20', sub_ip)\
            .set_ether_layer(self.MAC_DEST, "00:00:00:00:00:00")\
            .build()
        flow_query = FlowQuery(
            self._tbl_num, self.testing_controller,
            match=flow_match_to_magma_match(flow_list1[0].match)
        )

        # =========================== Verification ===========================
        # Verify aggregate table stats, subscriber 1 'simple_match' pkt count
        flow_verifier = FlowVerifier([
            FlowTest(FlowQuery(self._tbl_num, self.testing_controller),
                     pkts_sent),
            FlowTest(flow_query, pkts_matched)
        ], lambda: wait_after_send(self.testing_controller))

        with isolator, sub_context, flow_verifier:
            pkt_sender.send(packet)

        flow_verifier.verify()
Exemple #19
0
    def test_subscriber_redirect_policy(self):
        """
        Add redirect policy to subscriber, send 4096 packets

        Assert:
            Packets are properly matched with the 'simple_match' policy
            Send /20 (4096) packets, match /16 (256) packets
        """
        fake_controller_setup(self.gy_controller)
        imsi = 'IMSI010000000088888'
        sub_ip = '192.168.128.74'
        redirect_ips = ["185.128.101.5", "185.128.121.4"]
        self.gy_controller._redirect_manager._dns_cache.get(
            "about.sha.ddih.org", lambda: redirect_ips, max_age=42,
        )
        flow_list = [FlowDescription(match=FlowMatch())]
        policy = VersionedPolicy(
            rule=PolicyRule(
                id='redir_test', priority=3, flow_list=flow_list,
                redirect=RedirectInformation(
                    support=1,
                    address_type=2,
                    server_address="http://about.sha.ddih.org/",
                ),
            ),
            version=1,
        )

        # ============================ Subscriber ============================
        sub_context = RyuDirectSubscriberContext(
            imsi, sub_ip, self.gy_controller, self._tbl_num,
        ).add_policy(policy)
        isolator = RyuDirectTableIsolator(
            RyuForwardFlowArgsBuilder.from_subscriber(sub_context.cfg)
                                     .build_requests(),
            self.testing_controller,
        )
        pkt_sender = ScapyPacketInjector(self.IFACE)
        packet = TCPPacketBuilder()\
            .set_tcp_layer(42132, 80, 2)\
            .set_tcp_flags("S")\
            .set_ip_layer('151.42.41.122', sub_ip)\
            .set_ether_layer(self.MAC_DEST, "01:20:10:20:aa:bb")\
            .build()

        snapshot_verifier = SnapshotVerifier(
            self, self.BRIDGE,
            self.service_manager,
            include_stats=False,
        )

        with isolator, sub_context, snapshot_verifier:
            pkt_sender.send(packet)
    def test_enforcemnet_rules(self):
        """
        Add QOS policy to enforcement table into OVS. 
        """
        fake_controller_setup(self.enforcement_controller)
        imsi = 'IMSI001010000000013'
        sub_ip = '192.168.128.30'
        flow_list1 = [
            FlowDescription(
                match=FlowMatch(direction=FlowMatch.UPLINK, ),
                action=FlowDescription.PERMIT,
            ),
            FlowDescription(
                match=FlowMatch(
                    ip_dst=convert_ipv4_str_to_ip_proto("192.168.0.0/24"),
                    direction=FlowMatch.DOWNLINK,
                ),
                action=FlowDescription.PERMIT,
            ),
        ]
        self.service_manager.session_rule_version_mapper.save_version(
            imsi,
            convert_ipv4_str_to_ip_proto(sub_ip),
            "rule1",
            1,
        )
        self.enforcement_controller.activate_rules(
            imsi,
            None,
            0,
            convert_ipv4_str_to_ip_proto(sub_ip),
            None,
            policies=[
                VersionedPolicy(
                    rule=PolicyRule(id='rule1',
                                    priority=65530,
                                    flow_list=flow_list1),
                    version=1,
                ),
            ],
            shard_id=0,
            local_f_teid_ng=100,
        )

        snapshot_verifier = SnapshotVerifier(
            self,
            self.BRIDGE,
            self.service_manager,
        )

        with snapshot_verifier:
            pass
Exemple #21
0
    def test_subscriber_policy_with_he(self):
        """
        Add policy to subscriber with HE config

        """
        cls = self.__class__

        fake_controller_setup(self.enforcement_controller)

        imsi = 'IMSI010000000088888'
        sub_ip = '192.168.128.74'
        flow_list1 = [
            FlowDescription(
                match=FlowMatch(
                    ip_dst=convert_ipv4_str_to_ip_proto('45.10.0.0/24'),
                    direction=FlowMatch.UPLINK,
                ),
                action=FlowDescription.PERMIT,
            ),
        ]
        he = HeaderEnrichment(urls=['abc.com'])
        policies = [
            VersionedPolicy(
                rule=PolicyRule(id='simple_match',
                                priority=2,
                                flow_list=flow_list1,
                                he=he),
                version=1,
            ),
        ]

        # ============================ Subscriber ============================
        sub_context = RyuDirectSubscriberContext(
            imsi,
            sub_ip,
            self.enforcement_controller,
            self._tbl_num,
        ).add_policy(policies[0])

        isolator = RyuDirectTableIsolator(
            RyuForwardFlowArgsBuilder.from_subscriber(
                sub_context.cfg).build_requests(),
            self.testing_controller,
        )
        snapshot_verifier = SnapshotVerifier(
            self,
            self.BRIDGE,
            self.service_manager,
        )
        with isolator, sub_context, snapshot_verifier:
            pass
Exemple #22
0
 def _get_allow_all_traffic_policies(self):
     """ Policy to allow all traffic to the internet """
     return [
         PolicyRule(
             id='allow_all_traffic',
             priority=self.ALLOW_ALL_PRIORITY,
             flow_list=[
                 FlowDescription(match=FlowMatch(
                     direction=FlowMatch.UPLINK)),
                 FlowDescription(match=FlowMatch(
                     direction=FlowMatch.DOWNLINK)),
             ],
         )
     ]
Exemple #23
0
def activate_dynamic_rule(client, args):
    request = ActivateFlowsRequest(
        sid=SIDUtils.to_pb(args.imsi),
        dynamic_rules=[PolicyRule(
            id=args.rule_id,
            priority=args.priority,
            hard_timeout=args.hard_timeout,
            flow_list=[
                FlowDescription(match=FlowMatch(
                    ipv4_dst=args.ipv4_dst, direction=FlowMatch.UPLINK)),
                FlowDescription(match=FlowMatch(
                    ipv4_src=args.ipv4_dst, direction=FlowMatch.DOWNLINK)),
            ],
        )])
    client.ActivateFlows(request)
Exemple #24
0
 def process_update(self, stream_name, updates, resync):
     logging.info("Processing %d policy updates (resync=%s)", len(updates),
                  resync)
     if resync:
         policy_ids = set()
         for update in updates:
             policy = PolicyRule()
             policy.ParseFromString(update.value)
             self._store_policy_rule(policy)
             policy_ids.add(policy.id)
         logging.debug("Resync with policies: %s", ','.join(policy_ids))
         self._remove_old_policies(policy_ids)
         self._policy_dict.send_update_notification()
     else:
         pass
Exemple #25
0
 def _get_whitelist_policy_rule(
     self,
     policy_id: str,
     ip: str,
     port: int,
 ) -> PolicyRule:
     return PolicyRule(
         # Don't set the rating group
         # Don't set the monitoring key
         # Don't set the hard timeout
         id=policy_id,
         priority=100,
         qos=self._get_default_qos(),
         flow_list=self._get_whitelist_flows(ip, port),
         tracking_type=PolicyRule.TrackingType.Value("NO_TRACKING"),
     )
def activate_gy_redirect(client, args):
    request = ActivateFlowsRequest(
        sid=SIDUtils.to_pb(args.imsi),
        ip_addr=args.ipv4,
        dynamic_rules=[
            PolicyRule(id=args.rule_id,
                       priority=999,
                       flow_list=[],
                       redirect=RedirectInformation(
                           support=1,
                           address_type=2,
                           server_address=args.redirect_addr))
        ],
        request_origin=RequestOriginType(type=RequestOriginType.GY))
    response = client.ActivateFlows(request)
    _print_rule_mod_results(response.dynamic_rule_results)
Exemple #27
0
def create_bearer(client, args):
    req = CreateBearerRequest(
        sid=SIDUtils.to_pb(args.imsi),
        link_bearer_id=args.lbi,
        policy_rules=[
            PolicyRule(qos=FlowQos(qci=args.qci,
                                   gbr_ul=args.gbr_ul,
                                   gbr_dl=args.gbr_dl,
                                   max_req_bw_ul=args.mbr_ul,
                                   max_req_bw_dl=args.mbr_dl,
                                   arp=QosArp(priority_level=args.priority,
                                              pre_capability=args.pre_cap,
                                              pre_vulnerability=args.pre_vul)))
        ])
    print("Creating dedicated bearer for : ", args.imsi)
    client.CreateBearer(req)
 def __init__(self):
     self._set_session = SetSMSessionContext(
         common_context=CommonSessionContext(
             sid=SubscriberID(id="IMSI12345"),
             ue_ipv4="192.168.128.11",
             apn=bytes("BLR", 'utf-8'),
             rat_type=RATType.Name(2),
             sm_session_state=SMSessionFSMState.Name(2),
             sm_session_version=1,
         ),
         rat_specific_context=RatSpecificContext(
             m5gsm_session_context=M5GSMSessionContext(
                 pdu_session_id=1,
                 request_type=RequestType.Name(
                     1,
                 ),
                 gnode_endpoint=TeidSet(
                     teid=10000,
                     end_ipv4_addr="192.168.60.141",
                 ),
                 pdu_session_type=PduSessionType.Name(0),
                 ssc_mode=SscMode.Name(2),
                 qos_policy=[
                     QosPolicy(
                         policy_state=0,
                         policy_action=1,
                         version=2,
                         qos=PolicyRule(
                             id="ims-voice",
                             priority=10,
                             flow_list=[],
                             qos=FlowQos(
                                 qci=int(5),
                                 max_req_bw_ul=100000,
                                 max_req_bw_dl=100000,
                                 arp=QosArp(
                                     priority_level=1,
                                     pre_capability=1,
                                     pre_vulnerability=0,
                                 ),
                             ),
                         ),
                     ),
                 ],
             ),
         ),
     )
Exemple #29
0
 def _get_allow_all_policy_rule(
     self,
     policy_id: str,
 ) -> PolicyRule:
     """
     This builds a PolicyRule used as a default to allow traffic
     for an attached subscriber.
     """
     return PolicyRule(
         # Don't set the rating group
         # Don't set the monitoring key
         # Don't set the hard timeout
         id=policy_id,
         priority=2,
         flow_list=self._get_allow_all_flows(),
         tracking_type=PolicyRule.TrackingType.Value("NO_TRACKING"),
     )
Exemple #30
0
def _build_activate_flows_data(ue_dict, disable_qos):
    activate_flow_reqs = []

    if disable_qos:
        print("QOS Disabled")
        apn_ambr = None
    else:
        print("QOS Enabled")
        apn_ambr = AggregatedMaximumBitrate(
            max_bandwidth_ul=1000000000,
            max_bandwidth_dl=1000000000,
        )
    for ue in ue_dict:
        request = ActivateFlowsRequest(
            sid=SIDUtils.to_pb(ue.imsi_str),
            ip_addr=ue.ipv4_src,
            policies=[
                VersionedPolicy(
                    rule=PolicyRule(
                        id=ue.rule_id,
                        priority=10,
                        flow_list=[
                            FlowDescription(match=FlowMatch(
                                ip_dst=convert_ipv4_str_to_ip_proto(
                                    ue.ipv4_src),
                                direction=FlowMatch.UPLINK,
                            ), ),
                            FlowDescription(match=FlowMatch(
                                ip_src=convert_ipv4_str_to_ip_proto(
                                    ue.ipv4_dst),
                                direction=FlowMatch.DOWNLINK,
                            ), ),
                        ],
                    ),
                    version=1,
                ),
            ],
            request_origin=RequestOriginType(type=RequestOriginType.GX),
            apn_ambr=apn_ambr,
        )
        request_dict = json_format.MessageToDict(request)
        # Dumping ActivateFlows request into json
        activate_flow_reqs.append(request_dict)
    with open('activate_flows.json', 'w') as file:
        json.dump(activate_flow_reqs, file, separators=(',', ':'))