Skip to content

Commit

Permalink
pim,yang: Implement AutoRP announcements
Browse files Browse the repository at this point in the history
Signed-off-by: Nathan Bahr <[email protected]>
  • Loading branch information
nabahr committed Aug 22, 2024
1 parent fbb3ccd commit 4eddfde
Show file tree
Hide file tree
Showing 10 changed files with 1,484 additions and 204 deletions.
862 changes: 695 additions & 167 deletions pimd/pim_autorp.c

Large diffs are not rendered by default.

83 changes: 73 additions & 10 deletions pimd/pim_autorp.h
Original file line number Diff line number Diff line change
Expand Up @@ -18,9 +18,13 @@
#define PIMV2 2
#define PIMV1_2 3

#define DEFAULT_ANNOUNCE_INTERVAL 60
#define DEFAULT_ANNOUNCE_SCOPE 31
#define DEFAULT_ANNOUNCE_HOLDTIME -1

PREDECL_SORTLIST_UNIQ(pim_autorp_rp);

struct __attribute__((__packed__)) autorp_pkt_grp {
struct autorp_pkt_grp {
#if __BYTE_ORDER == __LITTLE_ENDIAN
uint8_t negprefix : 1;
uint8_t reserved : 7;
Expand All @@ -32,9 +36,9 @@ struct __attribute__((__packed__)) autorp_pkt_grp {
#endif
uint8_t masklen;
uint32_t addr;
};
} __attribute__((__packed__));

struct __attribute__((__packed__)) autorp_pkt_rp {
struct autorp_pkt_rp {
uint32_t addr;
#if __BYTE_ORDER == __LITTLE_ENDIAN
uint8_t pimver : 2;
Expand All @@ -46,9 +50,9 @@ struct __attribute__((__packed__)) autorp_pkt_rp {
#error "Please fix <bits/endian.h>"
#endif
uint8_t grpcnt;
};
} __attribute__((__packed__));

struct __attribute__((__packed__)) autorp_pkt_hdr {
struct autorp_pkt_hdr {
#if __BYTE_ORDER == __LITTLE_ENDIAN
uint8_t type : 4;
uint8_t version : 4;
Expand All @@ -61,7 +65,11 @@ struct __attribute__((__packed__)) autorp_pkt_hdr {
uint8_t rpcnt;
uint16_t holdtime;
uint32_t reserved;
};
} __attribute__((__packed__));

#define MIN_AUTORP_PKT_SZ \
(sizeof(struct autorp_pkt_hdr) + sizeof(struct autorp_pkt_rp) + \
sizeof(struct autorp_pkt_grp))

struct pim_autorp_rp {
struct pim_autorp *autorp;
Expand All @@ -74,22 +82,77 @@ struct pim_autorp_rp {
};

struct pim_autorp {
/* backpointer to pim instance */
struct pim_instance *pim;

/* UDP socket bound to AutoRP port, used for sending and receiving all AutoRP packets */
int sock;
struct event *ev_msg;
bool enable;
struct pim_autorp_rp_head rplist;

/* Event for reading AutoRP packets */
struct event *read_event;

/* Event for sending announcement packets */
struct event *announce_timer;

/* Event for sending discovery packets*/
/* struct event *discovery_timer; */

/* Flag enabling reading discovery packets */
bool do_discovery;

/* Flag enabling mapping agent (reading announcements and sending discovery)*/
/* bool do_mapping; */

/* List of RP's in received discovery packets */
struct pim_autorp_rp_head discovery_rp_list;

/* List of configured candidate RP's to send in announcement packets */
struct pim_autorp_rp_head candidate_rp_list;

/* List of announced RP's to send in discovery packets */
/* struct pim_autorp_rp_head mapping_rp_list; */

/* Packet parameters for sending announcement packets */
uint8_t announce_scope;
uint16_t announce_interval;
int32_t announce_holdtime;

/* Pre-built announcement packet, only changes when configured RP's or packet parameters change */
uint8_t *annouce_pkt;
uint16_t annouce_pkt_sz;

/* Packet parameters for sending discovery packets */
/*
int discovery_scope;
int discovery_interval;
int discovery_holdtime;
*/
};

#define AUTORP_GRPLEN 6
#define AUTORP_RPLEN 6
#define AUTORP_HDRLEN 8

int pim_autorp_rm_candidate_rp(struct pim_instance *pim, pim_addr rpaddr);
int pim_autorp_add_candidate_rp_group(struct pim_instance *pim, pim_addr rpaddr,
struct prefix group);
int pim_autorp_rm_candidate_rp_group(struct pim_instance *pim, pim_addr rpaddr,
struct prefix group);
int pim_autorp_add_candidate_rp_plist(struct pim_instance *pim, pim_addr rpaddr,
const char *plist);
int pim_autorp_rm_candidate_rp_plist(struct pim_instance *pim, pim_addr rpaddr,
const char *plist);
int pim_autorp_announce_scope(struct pim_instance *pim, uint8_t scope);
int pim_autorp_announce_interval(struct pim_instance *pim, uint16_t interval);
int pim_autorp_announce_holdtime(struct pim_instance *pim, int32_t holdtime);
int pim_autorp_add_ifp(struct interface *ifp);
int pim_autorp_rm_ifp(struct interface *ifp);
int pim_autorp_start_discovery(struct pim_instance *pim);
int pim_autorp_stop_discovery(struct pim_instance *pim);
int pim_autorp_init(struct pim_instance *pim);
int pim_autorp_start(struct pim_instance *pim);
int pim_autorp_finish(struct pim_instance *pim);
int pim_autorp_config_write(struct pim_instance *pim, struct vty *vty);
void pim_autorp_show_autorp(struct vty *vty, struct pim_instance *pim,
json_object *json);

#endif
113 changes: 110 additions & 3 deletions pimd/pim_cmd.c
Original file line number Diff line number Diff line change
Expand Up @@ -2783,6 +2783,75 @@ DEFPY (show_ip_pim_rp_vrf_all,
(struct prefix *)group, !!json);
}

DEFPY (show_ip_pim_autorp,
show_ip_pim_autorp_cmd,
"show ip pim [vrf NAME] autorp [json$json]",
SHOW_STR
IP_STR
PIM_STR
VRF_CMD_HELP_STR
"PIM AutoRP information\n"
JSON_STR)
{
struct vrf *v;
json_object *json_parent = NULL;

v = vrf_lookup_by_name(vrf ? vrf : VRF_DEFAULT_NAME);
if (!v || !v->info) {
if (!json)
vty_out(vty, "%% Unable to find pim instance\n");
return CMD_WARNING;
}

if (json)
json_parent = json_object_new_object();

pim_autorp_show_autorp(vty, v->info, json_parent);

if (json)
vty_json(vty, json_parent);

return CMD_SUCCESS;
}

DEFPY (show_ip_pim_autorp_vrf_all,
show_ip_pim_autorp_vrf_all_cmd,
"show ip pim vrf all autorp [json$json]",
SHOW_STR
IP_STR
PIM_STR
VRF_CMD_HELP_STR
"PIM AutoRP information\n"
JSON_STR)
{
struct vrf *vrf;
json_object *json_parent = NULL;
json_object *json_vrf = NULL;

if (json)
json_parent = json_object_new_object();

RB_FOREACH (vrf, vrf_name_head, &vrfs_by_name) {
if (vrf->info) {
if (!json)
vty_out(vty, "VRF: %s\n", vrf->name);
else
json_vrf = json_object_new_object();

pim_autorp_show_autorp(vty, vrf->info, json_vrf);

if (json)
json_object_object_add(json_parent, vrf->name,
json_vrf);
}
}

if (json)
vty_json(vty, json_parent);

return CMD_SUCCESS;
}

DEFPY (show_ip_pim_rpf,
show_ip_pim_rpf_cmd,
"show ip pim [vrf NAME] rpf [json$json]",
Expand Down Expand Up @@ -4379,13 +4448,47 @@ DEFPY_ATTR(no_ip_pim_rp_prefix_list,
DEFPY (pim_autorp_discovery,
pim_autorp_discovery_cmd,
"[no] autorp discovery",
NO_STR
NO_STR
"AutoRP\n"
"Enable AutoRP discovery\n")
"Enable AutoRP discovery\n")
{
if (no)
return pim_process_no_autorp_cmd(vty);
return pim_process_autorp_cmd(vty);
else
return pim_process_autorp_cmd(vty);
}

DEFPY (pim_autorp_announce_rp,
pim_autorp_announce_rp_cmd,
"[no] autorp announce A.B.C.D$rpaddr ![A.B.C.D/M$grp|group-list PREFIX_LIST$plist]",
NO_STR
"AutoRP\n"
"AutoRP Candidate RP announcement\n"
"AutoRP Candidate RP address\n"
"Group prefix\n"
"Prefix list\n"
"List name\n")
{
return pim_process_autorp_candidate_rp_cmd(vty, no, rpaddr_str, grp,
plist);
}

DEFPY (pim_autorp_announce_scope_int,
pim_autorp_announce_scope_int_cmd,
"[no] autorp announce ![{scope (1-255) | interval (1-65535) | holdtime (0-65535)}]",
NO_STR
"AutoRP\n"
"AutoRP Candidate RP announcement\n"
"Packet scope (TTL)\n"
"TTL value\n"
"Announcement interval\n"
"Time in seconds\n"
"Announcement holdtime\n"
"Time in seconds\n")
{
return pim_process_autorp_announce_scope_int_cmd(vty, no, scope_str,
interval_str,
holdtime_str);
}

DEFPY (pim_ssm_prefix_list,
Expand Down Expand Up @@ -8542,6 +8645,8 @@ void pim_cmd_init(void)
install_element(PIM_NODE, &pim_rp_prefix_list_cmd);
install_element(PIM_NODE, &no_pim_rp_prefix_list_cmd);
install_element(PIM_NODE, &pim_autorp_discovery_cmd);
install_element(PIM_NODE, &pim_autorp_announce_rp_cmd);
install_element(PIM_NODE, &pim_autorp_announce_scope_int_cmd);
install_element(PIM_NODE, &no_pim_ssm_prefix_list_cmd);
install_element(PIM_NODE, &no_pim_ssm_prefix_list_name_cmd);
install_element(PIM_NODE, &pim_ssm_prefix_list_cmd);
Expand Down Expand Up @@ -8689,6 +8794,8 @@ void pim_cmd_init(void)
install_element(VIEW_NODE, &show_ip_pim_upstream_rpf_cmd);
install_element(VIEW_NODE, &show_ip_pim_rp_cmd);
install_element(VIEW_NODE, &show_ip_pim_rp_vrf_all_cmd);
install_element(VIEW_NODE, &show_ip_pim_autorp_cmd);
install_element(VIEW_NODE, &show_ip_pim_autorp_vrf_all_cmd);
install_element(VIEW_NODE, &show_ip_pim_bsr_cmd);
install_element(VIEW_NODE, &show_ip_multicast_cmd);
install_element(VIEW_NODE, &show_ip_multicast_vrf_all_cmd);
Expand Down
Loading

0 comments on commit 4eddfde

Please sign in to comment.