route.c: keep track of where cloned routes come from, and make sure to
delete them when the ``parent'' goes away route.h: add glue to track this to rtentry structure. WARNING WILL ROBINSON! This will be yet another incompatible change in your route-using binaries. I apologize, but this was the only way to do it. I took this opportunity to increase the size of the metrics to what I believe will be the final length for 2.1, so that when the T/TCP stuff is done, this won't happen again.
This commit is contained in:
parent
131128b25f
commit
265e9f859e
@ -31,7 +31,7 @@
|
|||||||
* SUCH DAMAGE.
|
* SUCH DAMAGE.
|
||||||
*
|
*
|
||||||
* @(#)route.c 8.2 (Berkeley) 11/15/93
|
* @(#)route.c 8.2 (Berkeley) 11/15/93
|
||||||
* $Id: route.c,v 1.11 1994/11/03 01:04:30 wollman Exp $
|
* $Id: route.c,v 1.13 1994/12/13 23:07:03 wollman Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <sys/param.h>
|
#include <sys/param.h>
|
||||||
@ -350,6 +350,8 @@ ifa_ifwithroute(flags, dst, gateway)
|
|||||||
|
|
||||||
#define ROUNDUP(a) (a>0 ? (1 + (((a) - 1) | (sizeof(long) - 1))) : sizeof(long))
|
#define ROUNDUP(a) (a>0 ? (1 + (((a) - 1) | (sizeof(long) - 1))) : sizeof(long))
|
||||||
|
|
||||||
|
static void rt_fixfamily(struct rtentry *rt);
|
||||||
|
|
||||||
int
|
int
|
||||||
rtrequest(req, dst, gateway, netmask, flags, ret_nrt)
|
rtrequest(req, dst, gateway, netmask, flags, ret_nrt)
|
||||||
int req, flags;
|
int req, flags;
|
||||||
@ -377,6 +379,7 @@ rtrequest(req, dst, gateway, netmask, flags, ret_nrt)
|
|||||||
panic ("rtrequest delete");
|
panic ("rtrequest delete");
|
||||||
rt = (struct rtentry *)rn;
|
rt = (struct rtentry *)rn;
|
||||||
rt->rt_flags &= ~RTF_UP;
|
rt->rt_flags &= ~RTF_UP;
|
||||||
|
rt_fixfamily(rt);
|
||||||
if (rt->rt_gwroute) {
|
if (rt->rt_gwroute) {
|
||||||
rt = rt->rt_gwroute; RTFREE(rt);
|
rt = rt->rt_gwroute; RTFREE(rt);
|
||||||
(rt = (struct rtentry *)rn)->rt_gwroute = 0;
|
(rt = (struct rtentry *)rn)->rt_gwroute = 0;
|
||||||
@ -443,6 +446,12 @@ rtrequest(req, dst, gateway, netmask, flags, ret_nrt)
|
|||||||
rt->rt_ifp = ifa->ifa_ifp;
|
rt->rt_ifp = ifa->ifa_ifp;
|
||||||
if (req == RTM_RESOLVE)
|
if (req == RTM_RESOLVE)
|
||||||
rt->rt_rmx = (*ret_nrt)->rt_rmx; /* copy metrics */
|
rt->rt_rmx = (*ret_nrt)->rt_rmx; /* copy metrics */
|
||||||
|
if ((req == RTM_RESOLVE)
|
||||||
|
&& ((*ret_nrt)->rt_flags & RTF_PRCLONING)) {
|
||||||
|
rt->rt_parent = (*ret_nrt);
|
||||||
|
rt->rt_nextchild = (*ret_nrt)->rt_nextchild;
|
||||||
|
(*ret_nrt)->rt_nextchild = rt;
|
||||||
|
}
|
||||||
if (ifa->ifa_rtrequest)
|
if (ifa->ifa_rtrequest)
|
||||||
ifa->ifa_rtrequest(req, rt, SA(ret_nrt ? *ret_nrt : 0));
|
ifa->ifa_rtrequest(req, rt, SA(ret_nrt ? *ret_nrt : 0));
|
||||||
if (ret_nrt) {
|
if (ret_nrt) {
|
||||||
@ -456,6 +465,50 @@ rtrequest(req, dst, gateway, netmask, flags, ret_nrt)
|
|||||||
return (error);
|
return (error);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Called from rtrequest(RTM_DELETE, ...) to fix up the route's ``family''
|
||||||
|
* (i.e., the routes related to it by the operation of cloning). This
|
||||||
|
* involves deleting the entire chain of descendants (in the case of a parent
|
||||||
|
* route being deleted), or removing this route from the chain (in the case
|
||||||
|
* of a child route being deleted).
|
||||||
|
*/
|
||||||
|
static void
|
||||||
|
rt_fixfamily(struct rtentry *rt0)
|
||||||
|
{
|
||||||
|
struct rtentry *rt, *lrt, *nrt;
|
||||||
|
|
||||||
|
if(rt = rt0->rt_parent) {
|
||||||
|
if(rt->rt_flags & RTF_CHAINDELETE)
|
||||||
|
return; /* relax, it will all be done for us */
|
||||||
|
|
||||||
|
/* So what if it takes linear time? */
|
||||||
|
do {
|
||||||
|
lrt = rt;
|
||||||
|
rt = rt->rt_nextchild;
|
||||||
|
} while(rt && rt != rt0);
|
||||||
|
lrt->rt_nextchild = rt0->rt_nextchild;
|
||||||
|
} else if((rt = rt0)->rt_nextchild) {
|
||||||
|
lrt = rt;
|
||||||
|
rt->rt_flags |= RTF_CHAINDELETE;
|
||||||
|
|
||||||
|
rt = rt->rt_nextchild;
|
||||||
|
|
||||||
|
while(rt) {
|
||||||
|
nrt = rt->rt_nextchild;
|
||||||
|
/*
|
||||||
|
* There might be some value to open-coding this
|
||||||
|
* rtrequest call, but I am not yet convinced of
|
||||||
|
* the value of this.
|
||||||
|
*/
|
||||||
|
rtrequest(RTM_DELETE, rt_key(rt),
|
||||||
|
(struct sockaddr *)0, rt_mask(rt),
|
||||||
|
rt->rt_flags, (struct rtentry **)0);
|
||||||
|
rt = nrt;
|
||||||
|
}
|
||||||
|
lrt->rt_flags &= ~RTF_CHAINDELETE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
rt_setgate(rt0, dst, gate)
|
rt_setgate(rt0, dst, gate)
|
||||||
struct rtentry *rt0;
|
struct rtentry *rt0;
|
||||||
@ -572,5 +625,4 @@ rtinit(ifa, cmd, flags)
|
|||||||
}
|
}
|
||||||
rt_newaddrmsg(cmd, ifa, error, nrt);
|
rt_newaddrmsg(cmd, ifa, error, nrt);
|
||||||
}
|
}
|
||||||
return (error);
|
return (e
|
||||||
}
|
|
@ -31,7 +31,7 @@
|
|||||||
* SUCH DAMAGE.
|
* SUCH DAMAGE.
|
||||||
*
|
*
|
||||||
* @(#)route.h 8.3 (Berkeley) 4/19/94
|
* @(#)route.h 8.3 (Berkeley) 4/19/94
|
||||||
* $Id: route.h,v 1.5 1994/11/03 01:04:32 wollman Exp $
|
* $Id: route.h,v 1.6 1994/12/13 22:31:48 wollman Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef _NET_ROUTE_H_
|
#ifndef _NET_ROUTE_H_
|
||||||
@ -69,8 +69,7 @@ struct rt_metrics {
|
|||||||
u_long rmx_rtt; /* estimated round trip time */
|
u_long rmx_rtt; /* estimated round trip time */
|
||||||
u_long rmx_rttvar; /* estimated rtt variance */
|
u_long rmx_rttvar; /* estimated rtt variance */
|
||||||
u_long rmx_pksent; /* packets sent using this route */
|
u_long rmx_pksent; /* packets sent using this route */
|
||||||
u_long rmx_ttcp_cc; /* cached last T/TCP CC option rcvd */
|
u_long rmx_filler[4]; /* will be used for T/TCP later */
|
||||||
u_long rmx_ttcp_ccsent; /* cached last T/TCP CC option sent */
|
|
||||||
};
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -107,7 +106,11 @@ struct rtentry {
|
|||||||
caddr_t rt_llinfo; /* pointer to link level info cache */
|
caddr_t rt_llinfo; /* pointer to link level info cache */
|
||||||
struct rt_metrics rt_rmx; /* metrics used by rx'ing protocols */
|
struct rt_metrics rt_rmx; /* metrics used by rx'ing protocols */
|
||||||
struct rtentry *rt_gwroute; /* implied entry for gatewayed routes */
|
struct rtentry *rt_gwroute; /* implied entry for gatewayed routes */
|
||||||
int (*rt_output) __P(()); /* output routine for this (rt,if) */
|
int (*rt_output) __P((struct rtentry *, struct mbuf *,
|
||||||
|
struct sockaddr *, int));
|
||||||
|
/* output routine for this (rt,if) */
|
||||||
|
struct rtentry *rt_parent; /* cloning parent of this route */
|
||||||
|
struct rtentry *rt_nextchild; /* next cloned child of this route */
|
||||||
};
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -145,7 +148,8 @@ struct ortentry {
|
|||||||
#define RTF_PRCLONING 0x10000 /* protocol requires cloning */
|
#define RTF_PRCLONING 0x10000 /* protocol requires cloning */
|
||||||
#define RTF_WASCLONED 0x20000 /* route generated through cloning */
|
#define RTF_WASCLONED 0x20000 /* route generated through cloning */
|
||||||
#define RTF_PROTO3 0x40000 /* protocol specific routing flag */
|
#define RTF_PROTO3 0x40000 /* protocol specific routing flag */
|
||||||
/* 0x80000 and up unassigned */
|
#define RTF_CHAINDELETE 0x80000 /* chain is being deleted (internal) */
|
||||||
|
/* 0x100000 and up unassigned */
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Routing statistics.
|
* Routing statistics.
|
||||||
@ -175,7 +179,7 @@ struct rt_msghdr {
|
|||||||
struct rt_metrics rtm_rmx; /* metrics themselves */
|
struct rt_metrics rtm_rmx; /* metrics themselves */
|
||||||
};
|
};
|
||||||
|
|
||||||
#define RTM_VERSION 4 /* Up the ante and ignore older versions */
|
#define RTM_VERSION 5 /* Up the ante and ignore older versions */
|
||||||
|
|
||||||
#define RTM_ADD 0x1 /* Add Route */
|
#define RTM_ADD 0x1 /* Add Route */
|
||||||
#define RTM_DELETE 0x2 /* Delete Route */
|
#define RTM_DELETE 0x2 /* Delete Route */
|
||||||
|
Loading…
Reference in New Issue
Block a user