]> git.proxmox.com Git - mirror_frr.git/commitdiff
pimd: mtrace only IGMP sockets
authorMladen Sablic <mladen.sablic@gmail.com>
Tue, 27 Feb 2018 22:16:45 +0000 (23:16 +0100)
committerMladen Sablic <mladen.sablic@gmail.com>
Thu, 8 Mar 2018 08:40:48 +0000 (09:40 +0100)
Feature of mtrace only IGMP sockets on pim sm and pim
ssm interfaces. Modifed IGMP socket creation and show
igmp interface command output.

Signed-off-by: Mladen Sablic <mladen.sablic@gmail.com>
pimd/pim_cmd.c
pimd/pim_iface.c
pimd/pim_igmp.c
pimd/pim_igmp.h
pimd/pim_igmpv2.c
pimd/pim_igmpv3.c

index 60027946587dae86fd32977dd081e2bffb452606..803e7bb01325c586553d62f47e3dcd1c9174f979 100644 (file)
@@ -604,11 +604,18 @@ static void igmp_show_interfaces(struct pim_instance *pim, struct vty *vty,
                                json_object_object_add(json, ifp->name,
                                                       json_row);
 
+                               if (igmp->mtrace_only) {
+                                       json_object_boolean_true_add(
+                                               json_row, "mtraceOnly");
+                               }
                        } else {
                                vty_out(vty,
                                        "%-9s  %5s  %15s  %d  %7s  %11s  %8s\n",
                                        ifp->name,
-                                       if_is_up(ifp) ? "up" : "down",
+                                       if_is_up(ifp)
+                                               ? (igmp->mtrace_only ? "mtrc"
+                                                                    : "up")
+                                               : "down",
                                        inet_ntoa(igmp->ifaddr),
                                        pim_ifp->igmp_version,
                                        igmp->t_igmp_query_timer ? "local"
@@ -758,10 +765,17 @@ static void igmp_show_interfaces_single(struct pim_instance *pim,
                                json_object_object_add(json, ifp->name,
                                                       json_row);
 
+                               if (igmp->mtrace_only) {
+                                       json_object_boolean_true_add(
+                                               json_row, "mtraceOnly");
+                               }
                        } else {
                                vty_out(vty, "Interface : %s\n", ifp->name);
                                vty_out(vty, "State     : %s\n",
-                                       if_is_up(ifp) ? "up" : "down");
+                                       if_is_up(ifp)
+                                               ? (igmp->mtrace_only ? "mtrace"
+                                                                    : "up")
+                                               : "down");
                                vty_out(vty, "Address   : %s\n",
                                        inet_ntoa(pim_ifp->primary_address));
                                vty_out(vty, "Uptime    : %s\n", uptime);
index 998f8fc2caa6082407a70a54b5d6d87c15bda99b..ff7238ae97bec4339edfbef81db2413354f81543 100644 (file)
@@ -574,7 +574,11 @@ void pim_if_addr_add(struct connected *ifc)
                        /* if addr new, add IGMP socket */
                        if (ifc->address->family == AF_INET)
                                pim_igmp_sock_add(pim_ifp->igmp_socket_list,
-                                                 ifaddr, ifp);
+                                                 ifaddr, ifp, false);
+               } else if (igmp->mtrace_only) {
+                       igmp_sock_delete(igmp);
+                       pim_igmp_sock_add(pim_ifp->igmp_socket_list, ifaddr,
+                                         ifp, false);
                }
 
                /* Replay Static IGMP groups */
@@ -611,6 +615,20 @@ void pim_if_addr_add(struct connected *ifc)
                        }
                }
        } /* igmp */
+       else {
+               struct igmp_sock *igmp;
+
+               /* lookup IGMP socket */
+               igmp = pim_igmp_sock_lookup_ifaddr(pim_ifp->igmp_socket_list,
+                                                  ifaddr);
+               if (ifc->address->family == AF_INET) {
+                       if (igmp)
+                               igmp_sock_delete(igmp);
+                       /* if addr new, add IGMP socket */
+                       pim_igmp_sock_add(pim_ifp->igmp_socket_list, ifaddr,
+                                         ifp, true);
+               }
+       } /* igmp mtrace only */
 
        if (PIM_IF_TEST_PIM(pim_ifp->options)) {
 
index c0a58516d993ec24c61135639acbe2e2e5fd1204..5e1aecc3a389cec533e495815141c8bd545ad022 100644 (file)
@@ -281,6 +281,9 @@ static int igmp_recv_query(struct igmp_sock *igmp, int query_version,
        uint16_t recv_checksum;
        uint16_t checksum;
 
+       if (igmp->mtrace_only)
+               return 0;
+
        memcpy(&group_addr, igmp_msg + 4, sizeof(struct in_addr));
 
        ifp = igmp->interface;
@@ -387,6 +390,9 @@ static int igmp_v1_recv_report(struct igmp_sock *igmp, struct in_addr from,
 
        on_trace(__PRETTY_FUNCTION__, igmp->interface, from);
 
+       if (igmp->mtrace_only)
+               return 0;
+
        if (igmp_msg_len != IGMP_V12_MSG_SIZE) {
                zlog_warn(
                        "Recv IGMP report v1 from %s on %s: size=%d other than correct=%d",
@@ -510,7 +516,6 @@ int pim_igmp_packet(struct igmp_sock *igmp, char *buf, size_t len)
                return igmp_mtrace_recv_response(igmp, ip_hdr, ip_hdr->ip_src,
                                                 from_str, igmp_msg,
                                                 igmp_msg_len);
-               break;
        case PIM_IGMP_MTRACE_QUERY_REQUEST:
                return igmp_mtrace_recv_qry_req(igmp, ip_hdr, ip_hdr->ip_src,
                                                from_str, igmp_msg,
@@ -819,7 +824,7 @@ static int igmp_group_hash_equal(const void *arg1, const void *arg2)
 }
 
 static struct igmp_sock *igmp_sock_new(int fd, struct in_addr ifaddr,
-                                      struct interface *ifp)
+                                      struct interface *ifp, int mtrace_only)
 {
        struct pim_interface *pim_ifp;
        struct igmp_sock *igmp;
@@ -862,6 +867,13 @@ static struct igmp_sock *igmp_sock_new(int fd, struct in_addr ifaddr,
                pim_ifp->igmp_default_robustness_variable;
        igmp->sock_creation = pim_time_monotonic_sec();
 
+       if (mtrace_only) {
+               igmp->mtrace_only = mtrace_only;
+               return igmp;
+       }
+
+       igmp->mtrace_only = false;
+
        /*
          igmp_startup_mode_on() will reset QQI:
 
@@ -919,7 +931,8 @@ static void igmp_read_on(struct igmp_sock *igmp)
 
 struct igmp_sock *pim_igmp_sock_add(struct list *igmp_sock_list,
                                    struct in_addr ifaddr,
-                                   struct interface *ifp)
+                                   struct interface *ifp,
+                                   bool mtrace_only)
 {
        struct pim_interface *pim_ifp;
        struct igmp_sock *igmp;
@@ -934,7 +947,7 @@ struct igmp_sock *pim_igmp_sock_add(struct list *igmp_sock_list,
                return 0;
        }
 
-       igmp = igmp_sock_new(fd, ifaddr, ifp);
+       igmp = igmp_sock_new(fd, ifaddr, ifp, mtrace_only);
        if (!igmp) {
                zlog_err("%s %s: igmp_sock_new() failure", __FILE__,
                         __PRETTY_FUNCTION__);
index 962c50e76a66eb0f2d75d84d5c6f36d001d45762..561a127d0f1dcc963d3082675c4c96c08aac432f 100644 (file)
@@ -90,6 +90,8 @@ struct igmp_sock {
        int querier_robustness_variable; /* QRV */
        int startup_query_count;
 
+       bool mtrace_only;
+
        struct list *igmp_group_list; /* list of struct igmp_group */
        struct hash *igmp_group_hash;
 };
@@ -99,7 +101,8 @@ struct igmp_sock *pim_igmp_sock_lookup_ifaddr(struct list *igmp_sock_list,
 struct igmp_sock *igmp_sock_lookup_by_fd(struct list *igmp_sock_list, int fd);
 struct igmp_sock *pim_igmp_sock_add(struct list *igmp_sock_list,
                                    struct in_addr ifaddr,
-                                   struct interface *ifp);
+                                   struct interface *ifp,
+                                   bool mtrace_only);
 void igmp_sock_delete(struct igmp_sock *igmp);
 void igmp_sock_free(struct igmp_sock *igmp);
 void igmp_sock_delete_all(struct interface *ifp);
index efa36e618fa6530c8a5426a73c64e92cfb829783..dbbe83a9658842a3679cc71824969723423b1bd0 100644 (file)
@@ -111,6 +111,9 @@ int igmp_v2_recv_report(struct igmp_sock *igmp, struct in_addr from,
 
        on_trace(__PRETTY_FUNCTION__, igmp->interface, from);
 
+       if (igmp->mtrace_only)
+               return 0;
+
        if (igmp_msg_len != IGMP_V12_MSG_SIZE) {
                zlog_warn(
                        "Recv IGMPv2 REPORT from %s on %s: size=%d other than correct=%d",
@@ -154,6 +157,9 @@ int igmp_v2_recv_leave(struct igmp_sock *igmp, struct in_addr from,
 
        on_trace(__PRETTY_FUNCTION__, igmp->interface, from);
 
+       if (igmp->mtrace_only)
+               return 0;
+
        if (igmp_msg_len != IGMP_V12_MSG_SIZE) {
                zlog_warn(
                        "Recv IGMPv2 LEAVE from %s on %s: size=%d other than correct=%d",
index ecde546c06a431ae75a0228cb8e1b72e39905cc8..3360e36b4aaff8816f35c304701c569d320706ba 100644 (file)
@@ -1874,6 +1874,9 @@ int igmp_v3_recv_report(struct igmp_sock *igmp, struct in_addr from,
        int local_ncb = 0;
        struct pim_interface *pim_ifp;
 
+       if (igmp->mtrace_only)
+               return 0;
+
        pim_ifp = igmp->interface->info;
 
        if (igmp_msg_len < IGMP_V3_MSG_MIN_SIZE) {