Introduce an interface announcement message for the routing

socket so that routing daemons and other interested parties
know when an interface is attached/detached.

PR:		kern/33747
Obtained from:	NetBSD
MFC after:	2 weeks
This commit is contained in:
Ruslan Ermilov 2002-01-18 14:33:04 +00:00
parent 98bf25aae1
commit 7b6edd044b
Notes: svn2git 2020-12-20 02:59:44 +00:00
svn path=/head/; revision=89498
6 changed files with 96 additions and 3 deletions

View File

@ -1335,6 +1335,7 @@ char *msgtypes[] = {
"RTM_IFINFO: iface status change",
"RTM_NEWMADDR: new multicast group membership on iface",
"RTM_DELMADDR: multicast group membership removed from iface",
"RTM_IFANNOUNCE: interface arrival/departure",
0,
};
@ -1363,6 +1364,7 @@ print_rtmsg(rtm, msglen)
#ifdef RTM_NEWMADDR
struct ifma_msghdr *ifmam;
#endif
struct if_announcemsghdr *ifan;
if (verbose == 0)
return;
@ -1371,7 +1373,11 @@ print_rtmsg(rtm, msglen)
rtm->rtm_version);
return;
}
(void)printf("%s: len %d, ", msgtypes[rtm->rtm_type], rtm->rtm_msglen);
if (msgtypes[rtm->rtm_type] != NULL)
(void)printf("%s: ", msgtypes[rtm->rtm_type]);
else
(void)printf("#%d: ", rtm->rtm_type);
(void)printf("len %d, ", rtm->rtm_msglen);
switch (rtm->rtm_type) {
case RTM_IFINFO:
ifm = (struct if_msghdr *)rtm;
@ -1393,6 +1399,23 @@ print_rtmsg(rtm, msglen)
pmsg_addrs((char *)(ifmam + 1), ifmam->ifmam_addrs);
break;
#endif
case RTM_IFANNOUNCE:
ifan = (struct if_announcemsghdr *)rtm;
(void) printf("if# %d, what: ", ifan->ifan_index);
switch (ifan->ifan_what) {
case IFAN_ARRIVAL:
printf("arrival");
break;
case IFAN_DEPARTURE:
printf("departure");
break;
default:
printf("#%d", ifan->ifan_what);
break;
}
printf("\n");
break;
default:
(void) printf("pid: %ld, seq %d, errno %d, flags:",
(long)rtm->rtm_pid, rtm->rtm_seq, rtm->rtm_errno);

View File

@ -32,7 +32,7 @@
.\" From: @(#)route.4 8.6 (Berkeley) 4/19/94
.\" $FreeBSD$
.\"
.Dd October 8, 1996
.Dd January 18, 2002
.Dt ROUTE 4
.Os
.Sh NAME
@ -198,6 +198,7 @@ Messages include:
#define RTM_IFINFO 0xe /* iface going up/down etc. */
#define RTM_NEWMADDR 0xf /* mcast group membership being added to if */
#define RTM_DELMADDR 0x10 /* mcast group membership being deleted */
#define RTM_IFANNOUNCE 0x11 /* iface arrival/departure */
.Ed
.Pp
A message header consists of one of the following:
@ -245,6 +246,15 @@ struct ifma_msghdr {
int ifmam_flags; /* value of ifa_flags */
u_short ifmam_index; /* index for associated ifp */
};
struct if_announcemsghdr {
u_short ifan_msglen; /* to skip over non-understood messages */
u_char ifan_version; /* future binary compatibility */
u_char ifan_type; /* message type */
u_short ifan_index; /* index for associated ifp */
char ifan_name[IFNAMSIZ]; /* if name, e.g. "en0" */
u_short ifan_what; /* what type of announcement */
};
.Ed
.Pp
The
@ -262,7 +272,12 @@ header, the
and
.Dv RTM_DELMADDR
messages use a
.Ar ifma_msghdr ,
.Vt ifma_msghdr
header, the
.Dv RTM_IFANNOUNCE
message uses a
.Vt if_announcemsghdr
header,
and all other messages use the
.Ar rt_msghdr
header.

View File

@ -430,6 +430,9 @@ if_attach(ifp)
TAILQ_INSERT_HEAD(&ifp->if_addrhead, ifa, ifa_link);
}
ifp->if_broadcastaddr = 0; /* reliably crash if used uninitialized */
/* Announce the interface. */
rt_ifannouncemsg(ifp, IFAN_ARRIVAL);
}
/*
@ -511,6 +514,9 @@ if_detach(ifp)
(void) rnh->rnh_walktree(rnh, if_rtdel, ifp);
}
/* Announce that the interface is gone. */
rt_ifannouncemsg(ifp, IFAN_DEPARTURE);
KNOTE(&ifp->if_klist, NOTE_EXIT);
TAILQ_REMOVE(&ifnet, ifp, if_link);
mtx_destroy(&ifp->if_snd.ifq_mtx);

View File

@ -196,6 +196,21 @@ struct ifma_msghdr {
u_short ifmam_index; /* index for associated ifp */
};
/*
* Message format announcing the arrival or departure of a network interface.
*/
struct if_announcemsghdr {
u_short ifan_msglen; /* to skip over non-understood messages */
u_char ifan_version; /* future binary compatibility */
u_char ifan_type; /* message type */
u_short ifan_index; /* index for associated ifp */
char ifan_name[IFNAMSIZ]; /* if name, e.g. "en0" */
u_short ifan_what; /* what type of announcement */
};
#define IFAN_ARRIVAL 0 /* interface arrival */
#define IFAN_DEPARTURE 1 /* interface departure */
/*
* Interface request structure used for socket
* ioctl's. All interface ioctl's must have parameter

View File

@ -207,6 +207,7 @@ struct rt_msghdr {
#define RTM_IFINFO 0xe /* iface going up/down etc. */
#define RTM_NEWMADDR 0xf /* mcast group membership being added to if */
#define RTM_DELMADDR 0x10 /* mcast group membership being deleted */
#define RTM_IFANNOUNCE 0x11 /* iface arrival/departure */
/*
* Bitmask values for rtm_inits and rmx_locks.
@ -277,6 +278,7 @@ struct ifmultiaddr;
void route_init __P((void));
int rt_getifa __P((struct rt_addrinfo *));
void rt_ifannouncemsg __P((struct ifnet *, int));
void rt_ifmsg __P((struct ifnet *));
void rt_missmsg __P((int, struct rt_addrinfo *, int, int));
void rt_newaddrmsg __P((int, struct ifaddr *, int, struct rtentry *));

View File

@ -595,6 +595,10 @@ rt_msg1(type, rtinfo)
len = sizeof(struct if_msghdr);
break;
case RTM_IFANNOUNCE:
len = sizeof(struct if_announcemsghdr);
break;
default:
len = sizeof(struct rt_msghdr);
}
@ -860,6 +864,34 @@ rt_newmaddrmsg(cmd, ifma)
raw_input(m, &route_proto, &route_src, &route_dst);
}
/*
* This is called to generate routing socket messages indicating
* network interface arrival and departure.
*/
void
rt_ifannouncemsg(ifp, what)
struct ifnet *ifp;
int what;
{
struct if_announcemsghdr *ifan;
struct mbuf *m;
struct rt_addrinfo info;
if (route_cb.any_count == 0)
return;
bzero((caddr_t)&info, sizeof(info));
m = rt_msg1(RTM_IFANNOUNCE, &info);
if (m == NULL)
return;
ifan = mtod(m, struct if_announcemsghdr *);
ifan->ifan_index = ifp->if_index;
snprintf(ifan->ifan_name, sizeof(ifan->ifan_name),
"%s%d", ifp->if_name, ifp->if_unit);
ifan->ifan_what = what;
route_proto.sp_protocol = 0;
raw_input(m, &route_proto, &route_src, &route_dst);
}
/*
* This is used in dumping the kernel table via sysctl().
*/