summaryrefslogtreecommitdiff
path: root/usr.sbin/ospfd
diff options
context:
space:
mode:
authorClaudio Jeker <claudio@cvs.openbsd.org>2005-03-07 10:28:15 +0000
committerClaudio Jeker <claudio@cvs.openbsd.org>2005-03-07 10:28:15 +0000
commit56b4dcaaffe518f3956a530758aecfc2eb6452e0 (patch)
tree377e6f256d847fe32b5aa3875df9791a0425a891 /usr.sbin/ospfd
parente23ab2df47790640b5ecc7f7452866c06177328d (diff)
Track interface state (up/down) and media status. Simplify the code a bit
by using the kif/kroute info while allocating interfaces.
Diffstat (limited to 'usr.sbin/ospfd')
-rw-r--r--usr.sbin/ospfd/interface.c62
-rw-r--r--usr.sbin/ospfd/kroute.c41
-rw-r--r--usr.sbin/ospfd/ospfd.c5
-rw-r--r--usr.sbin/ospfd/ospfd.h35
-rw-r--r--usr.sbin/ospfd/ospfe.c13
-rw-r--r--usr.sbin/ospfd/ospfe.h5
-rw-r--r--usr.sbin/ospfd/parse.y18
7 files changed, 102 insertions, 77 deletions
diff --git a/usr.sbin/ospfd/interface.c b/usr.sbin/ospfd/interface.c
index 0e2c29c7358..b5591c8a456 100644
--- a/usr.sbin/ospfd/interface.c
+++ b/usr.sbin/ospfd/interface.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: interface.c,v 1.9 2005/02/16 15:23:33 norby Exp $ */
+/* $OpenBSD: interface.c,v 1.10 2005/03/07 10:28:14 claudio Exp $ */
/*
* Copyright (c) 2005 Claudio Jeker <claudio@openbsd.org>
@@ -109,7 +109,7 @@ if_fsm(struct iface *iface, enum iface_event event)
/* XXX event outside of the defined fsm, ignore it. */
log_debug("fsm_if: interface %s, "
"event %s not expected in state %s", iface->name,
- nbr_event_name(event), if_state_name(old_state));
+ if_event_name(event), if_state_name(old_state));
return (0);
}
@@ -150,15 +150,15 @@ if_fsm(struct iface *iface, enum iface_event event)
}
struct iface *
-if_new(char *name, unsigned int idx)
+if_new(struct kif *kif)
{
struct sockaddr_in *sain;
- struct iface *iface = NULL;
+ struct iface *iface;
struct ifreq *ifr;
int s;
if ((iface = calloc(1, sizeof(*iface))) == NULL)
- errx(1, "if_new: calloc");
+ err(1, "if_new: calloc");
iface->state = IF_STA_DOWN;
iface->passive = true;
@@ -168,55 +168,50 @@ if_new(char *name, unsigned int idx)
evtimer_set(&iface->lsack_tx_timer, ls_ack_tx_timer, iface);
- strlcpy(iface->name, name, sizeof(iface->name));
+ strlcpy(iface->name, kif->ifname, sizeof(iface->name));
if ((ifr = calloc(1, sizeof(*ifr))) == NULL)
- errx(1, "if_new: calloc");
+ err(1, "if_new: calloc");
/* set up ifreq */
- strlcpy(ifr->ifr_name, name, sizeof(ifr->ifr_name));
+ strlcpy(ifr->ifr_name, kif->ifname, sizeof(ifr->ifr_name));
if ((s = socket(AF_INET, SOCK_DGRAM, 0)) < 0)
- errx(1, "if_new: socket");
+ err(1, "if_new: socket");
+
/* get type */
- if (ioctl(s, SIOCGIFFLAGS, (caddr_t)ifr) < 0)
- errx(1, "if_new: cannot get type");
- if ((ifr->ifr_flags & IFF_POINTOPOINT))
+ if ((kif->flags & IFF_POINTOPOINT))
iface->type = IF_TYPE_POINTOPOINT;
-
- if ((ifr->ifr_flags & IFF_BROADCAST) &&
- (ifr->ifr_flags & IFF_MULTICAST))
+ if ((kif->flags & IFF_BROADCAST) &&
+ (kif->flags & IFF_MULTICAST))
iface->type = IF_TYPE_BROADCAST;
- iface->flags = ifr->ifr_flags;
+ /* get mtu, index and flags */
+ iface->mtu = kif->mtu;
+ iface->ifindex = kif->ifindex;
+ iface->flags = kif->flags;
+ iface->linkstate = kif->link_state;
/* get address */
if (ioctl(s, SIOCGIFADDR, (caddr_t)ifr) < 0)
- errx(1, "if_new: cannot get address");
+ err(1, "if_new: cannot get address");
sain = (struct sockaddr_in *) &ifr->ifr_addr;
iface->addr = sain->sin_addr;
/* get mask */
if (ioctl(s, SIOCGIFNETMASK, (caddr_t)ifr) < 0)
- errx(1, "if_new: cannot get mask");
+ err(1, "if_new: cannot get mask");
sain = (struct sockaddr_in *) &ifr->ifr_addr;
iface->mask = sain->sin_addr;
/* get p2p dst address */
if (iface->type == IF_TYPE_POINTOPOINT) {
if (ioctl(s, SIOCGIFDSTADDR, (caddr_t)ifr) < 0)
- errx(1, "if_new: cannot get dst addr");
+ err(1, "if_new: cannot get dst addr");
sain = (struct sockaddr_in *) &ifr->ifr_addr;
iface->dst = sain->sin_addr;
}
- /* get mtu */
- if (ioctl(s, SIOCGIFMTU, (caddr_t)ifr) < 0)
- errx(1, "if_new: cannot get mtu");
-
- iface->mtu = ifr->ifr_mtu;
- iface->ifindex = idx;
-
/* set event handlers for interface */
evtimer_set(&iface->hello_timer, if_hello_timer, iface);
evtimer_set(&iface->wait_timer, if_wait_timer, iface);
@@ -374,8 +369,16 @@ if_act_start(struct iface *iface)
return (-1);
}
+ if (!((iface->flags & IFF_UP) &&
+ (iface->linkstate != LINK_STATE_DOWN))) {
+ log_debug("if_act_start: interface %s link down",
+ iface->name);
+ return (0);
+ }
+
/* init the dummy local neighbor */
- iface->self = nbr_new(ospfe_router_id(), iface, 1);
+ if (iface->self == NULL)
+ iface->self = nbr_new(ospfe_router_id(), iface, 1);
/* up interface */
/* ... */
@@ -600,11 +603,6 @@ if_act_reset(struct iface *iface)
}
}
- while ((nbr = LIST_FIRST(&iface->nbr_list))) {
- LIST_REMOVE(nbr, entry);
- nbr_del(nbr);
- }
-
iface->dr = NULL;
iface->bdr = NULL;
diff --git a/usr.sbin/ospfd/kroute.c b/usr.sbin/ospfd/kroute.c
index 8ec07d10260..ceb25605f9c 100644
--- a/usr.sbin/ospfd/kroute.c
+++ b/usr.sbin/ospfd/kroute.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: kroute.c,v 1.4 2005/02/24 16:28:43 claudio Exp $ */
+/* $OpenBSD: kroute.c,v 1.5 2005/03/07 10:28:14 claudio Exp $ */
/*
* Copyright (c) 2004 Esben Norby <norby@openbsd.org>
@@ -99,15 +99,26 @@ int dispatch_rtmsg(void);
int fetchtable(void);
int fetchifs(int);
-RB_HEAD(kroute_tree, kroute_node) kroute_tree, krt;
+RB_HEAD(kroute_tree, kroute_node) krt;
RB_PROTOTYPE(kroute_tree, kroute_node, entry, kroute_compare)
RB_GENERATE(kroute_tree, kroute_node, entry, kroute_compare)
-RB_HEAD(kif_tree, kif_node) kif_tree, kit;
+RB_HEAD(kif_tree, kif_node) kit;
RB_PROTOTYPE(kif_tree, kif_node, entry, kif_compare)
RB_GENERATE(kif_tree, kif_node, entry, kif_compare)
int
+kif_init(void)
+{
+ RB_INIT(&kit);
+
+ if (fetchifs(0) == -1)
+ return (-1);
+
+ return (0);
+}
+
+int
kr_init(int fs)
{
int opt;
@@ -128,10 +139,6 @@ kr_init(int fs)
kr_state.rtseq = 1;
RB_INIT(&krt);
- RB_INIT(&kit);
-
- if (fetchifs(0) == -1)
- return (-1);
if (fetchtable() == -1)
return (-1);
@@ -139,7 +146,8 @@ kr_init(int fs)
if (protect_lo() == -1)
return (-1);
- event_set(&kr_state.ev, kr_state.fd, EV_READ, kr_dispatch_msg, NULL);
+ event_set(&kr_state.ev, kr_state.fd, EV_READ | EV_PERSIST,
+ kr_dispatch_msg, NULL);
event_add(&kr_state.ev, NULL);
return (0);
@@ -377,6 +385,18 @@ kif_find(int ifindex)
return (RB_FIND(kif_tree, &kit, &s));
}
+struct kif *
+kif_findname(char *ifname)
+{
+ struct kif_node *kif;
+
+ RB_FOREACH(kif, kif_tree, &kit)
+ if (!strcmp(ifname, kif->k.ifname))
+ return (&kif->k);
+
+ return (NULL);
+}
+
int
kif_insert(struct kif_node *kif)
{
@@ -588,13 +608,12 @@ if_change(u_short ifindex, int flags, struct if_data *ifd)
kif->k.media_type = ifd->ifi_type;
kif->k.baudrate = ifd->ifi_baudrate;
- main_imsg_compose_ospfe(IMSG_IFINFO, 0, &kif->k, sizeof(kif->k));
-
if ((reachable = (flags & IFF_UP) &&
(ifd->ifi_link_state != LINK_STATE_DOWN)) == kif->k.nh_reachable)
return; /* nothing changed wrt nexthop validity */
kif->k.nh_reachable = reachable;
+ main_imsg_compose_ospfe(IMSG_IFINFO, 0, &kif->k, sizeof(kif->k));
LIST_FOREACH(kkr, &kif->kroute_l, entry) {
/*
@@ -851,9 +870,9 @@ fetchifs(int ifindex)
kif->k.link_state = ifm.ifm_data.ifi_link_state;
kif->k.media_type = ifm.ifm_data.ifi_type;
kif->k.baudrate = ifm.ifm_data.ifi_baudrate;
+ kif->k.mtu = ifm.ifm_data.ifi_mtu;
kif->k.nh_reachable = (kif->k.flags & IFF_UP) &&
(ifm.ifm_data.ifi_link_state != LINK_STATE_DOWN);
-
if ((sa = rti_info[RTAX_IFP]) != NULL)
if (sa->sa_family == AF_LINK) {
sdl = (struct sockaddr_dl *)sa;
diff --git a/usr.sbin/ospfd/ospfd.c b/usr.sbin/ospfd/ospfd.c
index 165f859ee27..b135c55cf55 100644
--- a/usr.sbin/ospfd/ospfd.c
+++ b/usr.sbin/ospfd/ospfd.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ospfd.c,v 1.6 2005/02/27 08:21:15 norby Exp $ */
+/* $OpenBSD: ospfd.c,v 1.7 2005/03/07 10:28:14 claudio Exp $ */
/*
* Copyright (c) 2005 Claudio Jeker <claudio@openbsd.org>
@@ -141,6 +141,9 @@ main(int argc, char *argv[])
log_init(debug);
+ /* fetch interfaces early */
+ kif_init();
+
/* parse config file */
if ((conf = parse_config(conffile, OSPFD_OPT_VERBOSE)) == NULL )
exit(1);
diff --git a/usr.sbin/ospfd/ospfd.h b/usr.sbin/ospfd/ospfd.h
index 1c338dcd448..f449f8513e3 100644
--- a/usr.sbin/ospfd/ospfd.h
+++ b/usr.sbin/ospfd/ospfd.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: ospfd.h,v 1.11 2005/02/27 08:21:15 norby Exp $ */
+/* $OpenBSD: ospfd.h,v 1.12 2005/03/07 10:28:14 claudio Exp $ */
/*
* Copyright (c) 2004 Esben Norby <norby@openbsd.org>
@@ -310,19 +310,20 @@ struct ospfd_conf {
/* kroute */
struct kroute {
struct in_addr prefix;
- u_int8_t prefixlen;
struct in_addr nexthop;
u_int16_t flags;
u_short ifindex;
+ u_int8_t prefixlen;
};
struct kif {
- u_short ifindex;
- int flags;
char ifname[IF_NAMESIZE];
+ u_long baudrate;
+ int flags;
+ int mtu;
+ u_short ifindex;
u_int8_t media_type;
u_int8_t link_state;
- u_long baudrate;
u_int8_t nh_reachable; /* for nexthop verification */
};
@@ -421,16 +422,18 @@ int in_cksum(void *, int);
u_int16_t iso_cksum(void *, u_int16_t, u_int16_t);
/* kroute.c */
-int kr_init(int);
-int kr_change(struct kroute *);
-int kr_delete(struct kroute *);
-void kr_shutdown(void);
-void kr_fib_couple(void);
-void kr_fib_decouple(void);
-void kr_dispatch_msg(int, short, void *);
-int kr_nexthop_add(struct in_addr);
-void kr_nexthop_delete(struct in_addr);
-void kr_show_route(struct imsg *);
-void kr_ifinfo(char *);
+int kif_init(void);
+int kr_init(int);
+int kr_change(struct kroute *);
+int kr_delete(struct kroute *);
+void kr_shutdown(void);
+void kr_fib_couple(void);
+void kr_fib_decouple(void);
+void kr_dispatch_msg(int, short, void *);
+int kr_nexthop_add(struct in_addr);
+void kr_nexthop_delete(struct in_addr);
+void kr_show_route(struct imsg *);
+void kr_ifinfo(char *);
+struct kif *kif_findname(char *);
#endif /* _OSPFD_H_ */
diff --git a/usr.sbin/ospfd/ospfe.c b/usr.sbin/ospfd/ospfe.c
index a1ba93f5311..c42206230e0 100644
--- a/usr.sbin/ospfd/ospfe.c
+++ b/usr.sbin/ospfd/ospfe.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ospfe.c,v 1.8 2005/02/27 08:21:15 norby Exp $ */
+/* $OpenBSD: ospfe.c,v 1.9 2005/03/07 10:28:14 claudio Exp $ */
/*
* Copyright (c) 2005 Claudio Jeker <claudio@openbsd.org>
@@ -250,13 +250,15 @@ ospfe_dispatch_main(int fd, short event, void *bula)
fatalx("IFINFO imsg with wrong len");
kif = imsg.data;
- log_debug("ospfe_dispatch_main: ifindex %d changed",
- kif->ifindex);
-
LIST_FOREACH(area, &oeconf->area_list, entry) {
LIST_FOREACH(iface, &area->iface_list, entry) {
if (kif->ifindex == iface->ifindex) {
- if (kif->flags & IFF_UP) {
+ iface->flags = kif->flags;
+ iface->linkstate =
+ kif->link_state;
+ if ((kif->flags & IFF_UP) &&
+ (kif->link_state !=
+ LINK_STATE_DOWN)) {
if_fsm(iface,
IF_EVT_UP);
} else {
@@ -266,7 +268,6 @@ ospfe_dispatch_main(int fd, short event, void *bula)
}
}
}
-
break;
case IMSG_CTL_END:
log_debug("ospfe_dispatch_main: IMSG_CTL_END");
diff --git a/usr.sbin/ospfd/ospfe.h b/usr.sbin/ospfd/ospfe.h
index 9ee7500a488..9daa6e9ac0c 100644
--- a/usr.sbin/ospfd/ospfe.h
+++ b/usr.sbin/ospfd/ospfe.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: ospfe.h,v 1.6 2005/02/10 14:05:48 claudio Exp $ */
+/* $OpenBSD: ospfe.h,v 1.7 2005/03/07 10:28:14 claudio Exp $ */
/*
* Copyright (c) 2004, 2005 Esben Norby <norby@openbsd.org>
@@ -134,6 +134,7 @@ struct nbr {
u_int32_t ls_req_cnt;
int state;
+ u_int8_t link_state;
u_int8_t priority;
u_int8_t options;
u_int8_t last_rx_options;
@@ -177,7 +178,7 @@ void orig_net_lsa(struct iface *);
/* interface.c */
int if_fsm(struct iface *, enum iface_event);
-struct iface *if_new(char *, unsigned int);
+struct iface *if_new(struct kif *);
int if_del(struct iface *);
int if_init(struct ospfd_conf *);
int if_shutdown(struct ospfd_conf *);
diff --git a/usr.sbin/ospfd/parse.y b/usr.sbin/ospfd/parse.y
index fca2dd01d5f..e90dbad962b 100644
--- a/usr.sbin/ospfd/parse.y
+++ b/usr.sbin/ospfd/parse.y
@@ -1,4 +1,4 @@
-/* $OpenBSD: parse.y,v 1.5 2005/02/27 08:21:15 norby Exp $ */
+/* $OpenBSD: parse.y,v 1.6 2005/03/07 10:28:14 claudio Exp $ */
/*
* Copyright (c) 2004, 2005 Esben Norby <norby@openbsd.org>
@@ -85,7 +85,7 @@ int symset(const char *, const char *, int);
char *symget(const char *);
int atoul(char *, u_long *);
struct area *conf_get_area(struct in_addr);
-struct iface *conf_get_if(char *, unsigned int);
+struct iface *conf_get_if(struct kif *);
typedef struct {
union {
@@ -358,15 +358,15 @@ areaoptsl : interface nl
;
interface : INTERFACE STRING {
- unsigned int idx;
+ struct kif *kif;
- if ((idx = if_nametoindex($2)) == 0 ) {
+ if ((kif = kif_findname($2)) == NULL) {
yyerror("unknown interface %s", $2);
free($2);
YYERROR;
}
- iface = conf_get_if($2, idx);
free($2);
+ iface = conf_get_if(kif);
if (iface == NULL)
YYERROR;
iface->area = area;
@@ -870,20 +870,20 @@ conf_get_area(struct in_addr id)
}
struct iface *
-conf_get_if(char *name, unsigned int idx)
+conf_get_if(struct kif *kif)
{
struct area *a;
struct iface *i;
LIST_FOREACH(a, &conf->area_list, entry)
LIST_FOREACH(i, &a->iface_list, entry)
- if (i->ifindex == idx) {
+ if (i->ifindex == kif->ifindex) {
yyerror("interface %s already configured",
- name);
+ kif->ifname);
return (NULL);
}
- i = if_new(name, idx);
+ i = if_new(kif);
i->dead_interval = area->dead_interval;
i->transfer_delay = area->transfer_delay;
i->hello_interval = area->hello_interval;