Use queue(9) instead of hand-crafted link lists for the global netatalk

address list.  Generally follow the style and convention of similar parts
in netinet.

MFC after:	6 weeks
This commit is contained in:
Robert Watson 2009-06-24 21:36:09 +00:00
parent 32187eb6d9
commit 2642bf60f7
Notes: svn2git 2020-12-20 02:59:44 +00:00
svn path=/head/; revision=194913
7 changed files with 41 additions and 60 deletions

View File

@ -154,7 +154,7 @@ at_ifawithnet_locked(struct sockaddr_at *sat)
AT_IFADDR_LOCK_ASSERT();
for (aa = at_ifaddr_list; aa != NULL; aa = aa->aa_next) {
TAILQ_FOREACH(aa, &at_ifaddrhead, aa_link) {
sat2 = &(aa->aa_addr);
if (sat2->sat_addr.s_net == sat->sat_addr.s_net)
break;

View File

@ -48,7 +48,7 @@ __FBSDID("$FreeBSD$");
#include <netatalk/at_extern.h>
struct rwlock at_ifaddr_rw;
struct at_ifaddr *at_ifaddr_list;
struct at_ifaddrhead at_ifaddrhead;
RW_SYSINIT(at_ifaddr_rw, &at_ifaddr_rw, "at_ifaddr_rw");
@ -79,9 +79,8 @@ at_control(struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp,
struct sockaddr_at *sat;
struct netrange *nr;
struct at_aliasreq *ifra = (struct at_aliasreq *)data;
struct at_ifaddr *aa_temp;
struct at_ifaddr *aa;
struct ifaddr *ifa, *ifa0;
struct ifaddr *ifa;
int error;
/*
@ -90,7 +89,7 @@ at_control(struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp,
aa = NULL;
AT_IFADDR_RLOCK();
if (ifp != NULL) {
for (aa = at_ifaddr_list; aa != NULL; aa = aa->aa_next) {
TAILQ_FOREACH(aa, &at_ifaddrhead, aa_link) {
if (aa->aa_ifp == ifp)
break;
}
@ -118,7 +117,7 @@ at_control(struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp,
struct at_ifaddr *oaa;
AT_IFADDR_RLOCK();
for (oaa = aa; aa; aa = aa->aa_next) {
for (oaa = aa; aa; aa = TAILQ_NEXT(aa, aa_link)) {
if (aa->aa_ifp == ifp &&
sateqaddr(&aa->aa_addr, &ifra->ifra_addr))
break;
@ -161,7 +160,7 @@ at_control(struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp,
* the NEXT interface!
*/
AT_IFADDR_RLOCK();
for (oaa = aa; aa; aa = aa->aa_next) {
for (oaa = aa; aa; aa = TAILQ_NEXT(aa, aa_link)) {
if (aa->aa_ifp == ifp &&
(aa->aa_flags & AFA_PHASE2) == 0)
break;
@ -180,7 +179,7 @@ at_control(struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp,
* the NEXT interface!
*/
AT_IFADDR_RLOCK();
for (oaa = aa; aa; aa = aa->aa_next) {
for (oaa = aa; aa; aa = TAILQ_NEXT(aa, aa_link)) {
if (aa->aa_ifp == ifp && (aa->aa_flags &
AFA_PHASE2))
break;
@ -228,9 +227,9 @@ at_control(struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp,
else
aa->aa_flags |= AFA_PHASE2;
ifa_ref(&aa->aa_ifa); /* at_ifaddr_list */
ifa_ref(&aa->aa_ifa); /* at_ifaddrhead */
AT_IFADDR_WLOCK();
if ((aa_temp = at_ifaddr_list) != NULL) {
if (!TAILQ_EMPTY(&at_ifaddrhead)) {
/*
* Don't let the loopback be first, since the
* first address is the machine's default
@ -238,18 +237,16 @@ at_control(struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp,
* ourself in front, otherwise go to the back
* of the list.
*/
if (at_ifaddr_list->aa_ifp->if_flags &
IFF_LOOPBACK) {
aa->aa_next = at_ifaddr_list;
at_ifaddr_list = aa;
} else {
for (; aa_temp->aa_next; aa_temp =
aa_temp->aa_next)
;
aa_temp->aa_next = aa;
}
if (TAILQ_FIRST(&at_ifaddrhead)->aa_ifp->
if_flags & IFF_LOOPBACK)
TAILQ_INSERT_HEAD(&at_ifaddrhead, aa,
aa_link);
else
TAILQ_INSERT_TAIL(&at_ifaddrhead, aa,
aa_link);
} else
at_ifaddr_list = aa;
TAILQ_INSERT_HEAD(&at_ifaddrhead, aa,
aa_link);
AT_IFADDR_WUNLOCK();
/*
@ -280,7 +277,7 @@ at_control(struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp,
* only look at a phase one address
*/
AT_IFADDR_RUNLOCK();
for (oaa = aa; aa; aa = aa->aa_next) {
for (oaa = aa; aa; aa = TAILQ_NEXT(aa, aa_link)) {
if (aa->aa_ifp == ifp &&
(aa->aa_flags & AFA_PHASE2) == 0)
break;
@ -297,7 +294,7 @@ at_control(struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp,
* default to phase 2
*/
AT_IFADDR_RLOCK();
for (oaa = aa; aa; aa = aa->aa_next) {
for (oaa = aa; aa; aa = TAILQ_NEXT(aa, aa_link)) {
if (aa->aa_ifp == ifp && (aa->aa_flags &
AFA_PHASE2))
break;
@ -359,11 +356,11 @@ at_control(struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp,
/*
* remove the ifaddr from the interface
*/
ifa0 = (struct ifaddr *)aa;
ifa = (struct ifaddr *)aa;
IF_ADDR_LOCK(ifp);
TAILQ_REMOVE(&ifp->if_addrhead, ifa0, ifa_link);
TAILQ_REMOVE(&ifp->if_addrhead, ifa, ifa_link);
IF_ADDR_UNLOCK(ifp);
ifa_free(ifa0); /* if_addrhead */
ifa_free(ifa); /* if_addrhead */
/*
* Now remove the at_ifaddr from the parallel structure
@ -371,24 +368,9 @@ at_control(struct socket *so, u_long cmd, caddr_t data, struct ifnet *ifp,
*/
AT_IFADDR_WLOCK();
if (aa == (aa_temp = at_ifaddr_list)) {
at_ifaddr_list = aa->aa_next;
} else {
while (aa_temp->aa_next && (aa_temp->aa_next != aa))
aa_temp = aa_temp->aa_next;
/*
* if we found it, remove it, otherwise we
* screwed up.
*/
if (aa_temp->aa_next)
aa_temp->aa_next = aa->aa_next;
else
panic("at_control");
}
TAILQ_REMOVE(&at_ifaddrhead, aa, aa_link);
AT_IFADDR_WUNLOCK();
ifa_free(ifa0); /* at_ifaddr_list */
aa = aa_temp;
ifa_free(ifa); /* at_ifaddrhead */
break;
default:
@ -760,7 +742,7 @@ at_broadcast(struct sockaddr_at *sat)
/*
* failing that, if the net is one we have, it's a broadcast as well.
*/
for (aa = at_ifaddr_list; aa != NULL; aa = aa->aa_next) {
TAILQ_FOREACH(aa, &at_ifaddrhead, aa_link) {
if ((aa->aa_ifp->if_flags & IFF_BROADCAST)
&& (ntohs(sat->sat_addr.s_net) >= ntohs(aa->aa_firstnet)
&& ntohs(sat->sat_addr.s_net) <= ntohs(aa->aa_lastnet)))

View File

@ -40,11 +40,13 @@ struct at_ifaddr {
u_short aa_lastnet;
int aa_probcnt;
struct callout aa_callout;
struct at_ifaddr *aa_next;
TAILQ_ENTRY(at_ifaddr) aa_link;
};
#define aa_ifp aa_ifa.ifa_ifp
#define aa_dstaddr aa_broadaddr;
TAILQ_HEAD(at_ifaddrhead, at_ifaddr);
struct at_aliasreq {
char ifra_name[IFNAMSIZ];
struct sockaddr_at ifra_addr;
@ -61,8 +63,8 @@ struct at_aliasreq {
#define AFA_PHASE2 0x0004
#ifdef _KERNEL
extern struct rwlock at_ifaddr_rw;
extern struct at_ifaddr *at_ifaddr_list;
extern struct rwlock at_ifaddr_rw;
extern struct at_ifaddrhead at_ifaddrhead;
#define AT_IFADDR_LOCK_INIT() rw_init(&at_ifaddr_rw, "at_ifaddr_rw")
#define AT_IFADDR_LOCK_ASSERT() rw_assert(&at_ifaddr_rw, RA_LOCKED)

View File

@ -162,7 +162,7 @@ ddp_input(struct mbuf *m, struct ifnet *ifp, struct elaphdr *elh, int phase)
* it's valid for this packet.
*/
AT_IFADDR_RLOCK();
for (aa = at_ifaddr_list; aa != NULL; aa = aa->aa_next) {
TAILQ_FOREACH(aa, &at_ifaddrhead, aa_link) {
if ((aa->aa_ifp == ifp)
&& ((aa->aa_flags & AFA_PHASE2) == 0)
&& ((to.sat_addr.s_node ==
@ -224,8 +224,7 @@ ddp_input(struct mbuf *m, struct ifnet *ifp, struct elaphdr *elh, int phase)
* what we want, but it's probably safe in 99.999% of
* cases.
*/
for (aa = at_ifaddr_list; aa != NULL;
aa = aa->aa_next) {
TAILQ_FOREACH(aa, &at_ifaddrhead, aa_link) {
if (phase == 1 && (aa->aa_flags &
AFA_PHASE2))
continue;
@ -244,8 +243,7 @@ ddp_input(struct mbuf *m, struct ifnet *ifp, struct elaphdr *elh, int phase)
* A destination network was given. We just try to
* find which ifaddr info matches it.
*/
for (aa = at_ifaddr_list; aa != NULL;
aa = aa->aa_next) {
TAILQ_FOREACH(aa, &at_ifaddrhead, aa_link) {
/*
* This is a kludge. Accept packets that are
* for any router on a local netrange.

View File

@ -143,7 +143,7 @@ ddp_route(struct mbuf *m, struct route *ro)
(ifp = ro->ro_rt->rt_ifa->ifa_ifp)) {
net = ntohs(satosat(ro->ro_rt->rt_gateway)->sat_addr.s_net);
AT_IFADDR_RLOCK();
for (aa = at_ifaddr_list; aa != NULL; aa = aa->aa_next) {
TAILQ_FOREACH(aa, &at_ifaddrhead, aa_link) {
if (((net == 0) || (aa->aa_ifp == ifp)) &&
net >= ntohs(aa->aa_firstnet) &&
net <= ntohs(aa->aa_lastnet))

View File

@ -113,8 +113,7 @@ at_pcbsetaddr(struct ddpcb *ddp, struct sockaddr *addr, struct thread *td)
if (sat->sat_addr.s_node != ATADDR_ANYNODE ||
sat->sat_addr.s_net != ATADDR_ANYNET) {
AT_IFADDR_RLOCK();
for (aa = at_ifaddr_list; aa != NULL;
aa = aa->aa_next) {
TAILQ_FOREACH(aa, &at_ifaddrhead, aa_link) {
if ((sat->sat_addr.s_net ==
AA_SAT(aa)->sat_addr.s_net) &&
(sat->sat_addr.s_node ==
@ -146,11 +145,11 @@ at_pcbsetaddr(struct ddpcb *ddp, struct sockaddr *addr, struct thread *td)
if (sat->sat_addr.s_node == ATADDR_ANYNODE &&
sat->sat_addr.s_net == ATADDR_ANYNET) {
AT_IFADDR_RLOCK();
if (at_ifaddr_list == NULL) {
if (TAILQ_EMPTY(&at_ifaddrhead)) {
AT_IFADDR_RUNLOCK();
return (EADDRNOTAVAIL);
}
sat->sat_addr = AA_SAT(at_ifaddr_list)->sat_addr;
sat->sat_addr = AA_SAT(TAILQ_FIRST(&at_ifaddrhead))->sat_addr;
AT_IFADDR_RUNLOCK();
}
ddp->ddp_lsat = *sat;
@ -229,8 +228,7 @@ at_pcbconnect(struct ddpcb *ddp, struct sockaddr *addr, struct thread *td)
aa = NULL;
AT_IFADDR_RLOCK();
if ((ifp = ro->ro_rt->rt_ifp) != NULL) {
for (aa = at_ifaddr_list; aa != NULL;
aa = aa->aa_next) {
TAILQ_FOREACH(aa, &at_ifaddrhead, aa_link) {
if (aa->aa_ifp == ifp &&
ntohs(net) >= ntohs(aa->aa_firstnet) &&
ntohs(net) <= ntohs(aa->aa_lastnet))
@ -268,7 +266,7 @@ at_pcbconnect(struct ddpcb *ddp, struct sockaddr *addr, struct thread *td)
aa = NULL;
if (ro->ro_rt && (ifp = ro->ro_rt->rt_ifp)) {
AT_IFADDR_RLOCK();
for (aa = at_ifaddr_list; aa != NULL; aa = aa->aa_next) {
TAILQ_FOREACH(aa, &at_ifaddrhead, aa_link) {
if (aa->aa_ifp == ifp)
break;
}

View File

@ -276,6 +276,7 @@ ddp_init(void)
{
DDP_LIST_LOCK_INIT();
TAILQ_INIT(&at_ifaddrhead);
netisr_register(&atalk1_nh);
netisr_register(&atalk2_nh);
netisr_register(&aarp_nh);