static inline bool
vr_my_pkt(unsigned char *pkt_mac, struct vr_interface *vif)
{
    /*
     * Packet is destined to us if:
     * 1) IF destination MAC is our Mac
     * 2) If VIF is service interface
     */
    if (VR_MAC_CMP(pkt_mac, vif->vif_mac) || vif_is_service(vif))
        return true;

    return false;
}
/*
 * vr_interface_input() is invoked if a packet ingresses an interface.
 * This function demultiplexes the packet to right input
 * function depending on the protocols enabled on the VIF
 */
unsigned int
vr_virtual_input(unsigned short vrf, struct vr_interface *vif,
                 struct vr_packet *pkt, unsigned short vlan_id)
{
    struct vr_forwarding_md fmd;

    vr_init_forwarding_md(&fmd);
    fmd.fmd_vlan = vlan_id;
    fmd.fmd_dvrf = vrf;

    if (vif->vif_flags & VIF_FLAG_MIRROR_RX) {
        fmd.fmd_dvrf = vif->vif_vrf;
        vr_mirror(vif->vif_router, vif->vif_mirror_id, pkt, &fmd);
    }

    if (vr_pkt_type(pkt, 0, &fmd) < 0) {
        vif_drop_pkt(vif, pkt, 1);
        return 0;
    }

    /*
     * we really do not allow any broadcast packets from interfaces
     * that are part of transparent service chain, since transparent
     * service chain bridges packets across vrf (and hence loops can
     * happen)
     */
    if ((pkt->vp_flags & VP_FLAG_MULTICAST) &&
            (vif_is_service(vif))) {
        vif_drop_pkt(vif, pkt, 1);
        return 0;
    }

    if (!vr_flow_forward(pkt->vp_if->vif_router, pkt, &fmd))
        return 0;

    vr_bridge_input(vif->vif_router, pkt, &fmd);
    return 0;

}
Beispiel #3
0
static inline void
vr_get_flow_key(struct vr_flow_key *key, uint16_t vlan, struct vr_packet *pkt,
        unsigned int sip, unsigned int dip, unsigned char proto,
        unsigned short sport, unsigned short dport)
{
    unsigned short nh_id;

    /* copy both source and destinations */
    key->key_src_ip = sip;
    key->key_dest_ip = dip;
    key->key_proto = proto;
    key->key_zero = 0;

    if (vif_is_fabric(pkt->vp_if) && pkt->vp_nh) {
        nh_id = pkt->vp_nh->nh_id;
    } else if (vif_is_service(pkt->vp_if)) {
        nh_id = vif_vrf_table_get_nh(pkt->vp_if, vlan);
    } else {
        nh_id = pkt->vp_if->vif_nh_id;
    }

    key->key_nh_id = nh_id;

    switch (proto) {
    case VR_IP_PROTO_TCP:
    case VR_IP_PROTO_UDP:
    case VR_IP_PROTO_ICMP:
        key->key_src_port = sport;
        key->key_dst_port = dport;
        break;

    default:
        key->key_src_port = key->key_dst_port = 0;
        break;
    }

    return;
}