if_stf.c (142352) | if_stf.c (147256) |
---|---|
1/* $FreeBSD: head/sys/net/if_stf.c 142352 2005-02-24 01:34:01Z sam $ */ | 1/* $FreeBSD: head/sys/net/if_stf.c 147256 2005-06-10 16:49:24Z brooks $ */ |
2/* $KAME: if_stf.c,v 1.73 2001/12/03 11:08:30 keiichi Exp $ */ 3 4/*- 5 * Copyright (C) 2000 WIDE Project. 6 * All rights reserved. 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted provided that the following conditions --- 116 unchanged lines hidden (view full) --- 126 127/* 128 * XXX: Return a pointer with 16-bit aligned. Don't cast it to 129 * struct in_addr *; use bcopy() instead. 130 */ 131#define GET_V4(x) ((caddr_t)(&(x)->s6_addr16[1])) 132 133struct stf_softc { | 2/* $KAME: if_stf.c,v 1.73 2001/12/03 11:08:30 keiichi Exp $ */ 3 4/*- 5 * Copyright (C) 2000 WIDE Project. 6 * All rights reserved. 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted provided that the following conditions --- 116 unchanged lines hidden (view full) --- 126 127/* 128 * XXX: Return a pointer with 16-bit aligned. Don't cast it to 129 * struct in_addr *; use bcopy() instead. 130 */ 131#define GET_V4(x) ((caddr_t)(&(x)->s6_addr16[1])) 132 133struct stf_softc { |
134 struct ifnet sc_if; /* common area */ | 134 struct ifnet *sc_ifp; |
135 union { 136 struct route __sc_ro4; 137 struct route_in6 __sc_ro6; /* just for safety */ 138 } __sc_ro46; 139#define sc_ro __sc_ro46.__sc_ro4 140 const struct encaptab *encap_cookie; 141 LIST_ENTRY(stf_softc) sc_list; /* all stf's are linked */ 142}; | 135 union { 136 struct route __sc_ro4; 137 struct route_in6 __sc_ro6; /* just for safety */ 138 } __sc_ro46; 139#define sc_ro __sc_ro46.__sc_ro4 140 const struct encaptab *encap_cookie; 141 LIST_ENTRY(stf_softc) sc_list; /* all stf's are linked */ 142}; |
143#define STF2IFP(sc) ((sc)->sc_ifp) |
|
143 144/* 145 * All mutable global variables in if_stf.c are protected by stf_mtx. 146 * XXXRW: Note that mutable fields in the softc are not currently locked: 147 * in particular, sc_ro needs to be protected from concurrent entrance 148 * of stf_output(). 149 */ 150static struct mtx stf_mtx; --- 58 unchanged lines hidden (view full) --- 209 * interfaces. 210 */ 211 unit = STFUNIT; 212 err = ifc_alloc_unit(ifc, &unit); 213 if (err != 0) 214 return (err); 215 216 sc = malloc(sizeof(struct stf_softc), M_STF, M_WAITOK | M_ZERO); | 144 145/* 146 * All mutable global variables in if_stf.c are protected by stf_mtx. 147 * XXXRW: Note that mutable fields in the softc are not currently locked: 148 * in particular, sc_ro needs to be protected from concurrent entrance 149 * of stf_output(). 150 */ 151static struct mtx stf_mtx; --- 58 unchanged lines hidden (view full) --- 210 * interfaces. 211 */ 212 unit = STFUNIT; 213 err = ifc_alloc_unit(ifc, &unit); 214 if (err != 0) 215 return (err); 216 217 sc = malloc(sizeof(struct stf_softc), M_STF, M_WAITOK | M_ZERO); |
217 ifp = &sc->sc_if; | 218 ifp = sc->sc_ifp = if_alloc(IFT_STF); 219 if (ifp == NULL) { 220 free(sc, M_STF); 221 ifc_free_unit(ifc, unit); 222 return (ENOSPC); 223 } |
218 /* 219 * Set the name manually rather then using if_initname because 220 * we don't conform to the default naming convention for interfaces. 221 */ 222 strlcpy(ifp->if_xname, name, IFNAMSIZ); 223 ifp->if_dname = ifc->ifc_name; 224 ifp->if_dunit = IF_DUNIT_NONE; 225 --- 4 unchanged lines hidden (view full) --- 230 free(sc, M_STF); 231 ifc_free_unit(ifc, unit); 232 return (ENOMEM); 233 } 234 235 ifp->if_mtu = IPV6_MMTU; 236 ifp->if_ioctl = stf_ioctl; 237 ifp->if_output = stf_output; | 224 /* 225 * Set the name manually rather then using if_initname because 226 * we don't conform to the default naming convention for interfaces. 227 */ 228 strlcpy(ifp->if_xname, name, IFNAMSIZ); 229 ifp->if_dname = ifc->ifc_name; 230 ifp->if_dunit = IF_DUNIT_NONE; 231 --- 4 unchanged lines hidden (view full) --- 236 free(sc, M_STF); 237 ifc_free_unit(ifc, unit); 238 return (ENOMEM); 239 } 240 241 ifp->if_mtu = IPV6_MMTU; 242 ifp->if_ioctl = stf_ioctl; 243 ifp->if_output = stf_output; |
238 ifp->if_type = IFT_STF; | |
239 ifp->if_snd.ifq_maxlen = IFQ_MAXLEN; 240 if_attach(ifp); 241 bpfattach(ifp, DLT_NULL, sizeof(u_int)); 242 mtx_lock(&stf_mtx); 243 LIST_INSERT_HEAD(&stf_softc_list, sc, sc_list); 244 mtx_unlock(&stf_mtx); 245 return (0); 246} 247 248static void 249stf_destroy(struct stf_softc *sc) 250{ 251 int err; 252 253 err = encap_detach(sc->encap_cookie); 254 KASSERT(err == 0, ("Unexpected error detaching encap_cookie")); | 244 ifp->if_snd.ifq_maxlen = IFQ_MAXLEN; 245 if_attach(ifp); 246 bpfattach(ifp, DLT_NULL, sizeof(u_int)); 247 mtx_lock(&stf_mtx); 248 LIST_INSERT_HEAD(&stf_softc_list, sc, sc_list); 249 mtx_unlock(&stf_mtx); 250 return (0); 251} 252 253static void 254stf_destroy(struct stf_softc *sc) 255{ 256 int err; 257 258 err = encap_detach(sc->encap_cookie); 259 KASSERT(err == 0, ("Unexpected error detaching encap_cookie")); |
255 bpfdetach(&sc->sc_if); 256 if_detach(&sc->sc_if); | 260 bpfdetach(STF2IFP(sc)); 261 if_detach(STF2IFP(sc)); 262 if_free(STF2IFP(sc)); |
257 258 free(sc, M_STF); 259} 260 261static int 262stf_clone_destroy(struct if_clone *ifc, struct ifnet *ifp) 263{ | 263 264 free(sc, M_STF); 265} 266 267static int 268stf_clone_destroy(struct if_clone *ifc, struct ifnet *ifp) 269{ |
264 struct stf_softc *sc = (void *) ifp; | 270 struct stf_softc *sc = ifp->if_softc; |
265 266 mtx_lock(&stf_mtx); 267 LIST_REMOVE(sc, sc_list); 268 mtx_unlock(&stf_mtx); 269 270 stf_destroy(sc); 271 ifc_free_unit(ifc, STFUNIT); 272 --- 54 unchanged lines hidden (view full) --- 327 struct in6_ifaddr *ia6; 328 struct stf_softc *sc; 329 struct in_addr a, b, mask; 330 331 sc = (struct stf_softc *)arg; 332 if (sc == NULL) 333 return 0; 334 | 271 272 mtx_lock(&stf_mtx); 273 LIST_REMOVE(sc, sc_list); 274 mtx_unlock(&stf_mtx); 275 276 stf_destroy(sc); 277 ifc_free_unit(ifc, STFUNIT); 278 --- 54 unchanged lines hidden (view full) --- 333 struct in6_ifaddr *ia6; 334 struct stf_softc *sc; 335 struct in_addr a, b, mask; 336 337 sc = (struct stf_softc *)arg; 338 if (sc == NULL) 339 return 0; 340 |
335 if ((sc->sc_if.if_flags & IFF_UP) == 0) | 341 if ((STF2IFP(sc)->if_flags & IFF_UP) == 0) |
336 return 0; 337 338 /* IFF_LINK0 means "no decapsulation" */ | 342 return 0; 343 344 /* IFF_LINK0 means "no decapsulation" */ |
339 if ((sc->sc_if.if_flags & IFF_LINK0) != 0) | 345 if ((STF2IFP(sc)->if_flags & IFF_LINK0) != 0) |
340 return 0; 341 342 if (proto != IPPROTO_IPV6) 343 return 0; 344 345 /* LINTED const cast */ 346 m_copydata((struct mbuf *)(uintptr_t)m, 0, sizeof(ip), (caddr_t)&ip); 347 348 if (ip.ip_v != 4) 349 return 0; 350 | 346 return 0; 347 348 if (proto != IPPROTO_IPV6) 349 return 0; 350 351 /* LINTED const cast */ 352 m_copydata((struct mbuf *)(uintptr_t)m, 0, sizeof(ip), (caddr_t)&ip); 353 354 if (ip.ip_v != 4) 355 return 0; 356 |
351 ia6 = stf_getsrcifa6(&sc->sc_if); | 357 ia6 = stf_getsrcifa6(STF2IFP(sc)); |
352 if (ia6 == NULL) 353 return 0; 354 355 /* 356 * check if IPv4 dst matches the IPv4 address derived from the 357 * local 6to4 address. 358 * success on: dst = 10.1.1.1, ia6->ia_addr = 2002:0a01:0101:... 359 */ --- 75 unchanged lines hidden (view full) --- 435 436 error = mac_check_ifnet_transmit(ifp, m); 437 if (error) { 438 m_freem(m); 439 return (error); 440 } 441#endif 442 | 358 if (ia6 == NULL) 359 return 0; 360 361 /* 362 * check if IPv4 dst matches the IPv4 address derived from the 363 * local 6to4 address. 364 * success on: dst = 10.1.1.1, ia6->ia_addr = 2002:0a01:0101:... 365 */ --- 75 unchanged lines hidden (view full) --- 441 442 error = mac_check_ifnet_transmit(ifp, m); 443 if (error) { 444 m_freem(m); 445 return (error); 446 } 447#endif 448 |
443 sc = (struct stf_softc*)ifp; | 449 sc = ifp->if_softc; |
444 dst6 = (struct sockaddr_in6 *)dst; 445 446 /* just in case */ 447 if ((ifp->if_flags & IFF_UP) == 0) { 448 m_freem(m); 449 ifp->if_oerrors++; 450 return ENETDOWN; 451 } --- 152 unchanged lines hidden (view full) --- 604 continue; 605 if (in->s_addr == ia4->ia_broadaddr.sin_addr.s_addr) 606 return -1; 607 } 608 609 /* 610 * perform ingress filter 611 */ | 450 dst6 = (struct sockaddr_in6 *)dst; 451 452 /* just in case */ 453 if ((ifp->if_flags & IFF_UP) == 0) { 454 m_freem(m); 455 ifp->if_oerrors++; 456 return ENETDOWN; 457 } --- 152 unchanged lines hidden (view full) --- 610 continue; 611 if (in->s_addr == ia4->ia_broadaddr.sin_addr.s_addr) 612 return -1; 613 } 614 615 /* 616 * perform ingress filter 617 */ |
612 if (sc && (sc->sc_if.if_flags & IFF_LINK2) == 0 && inifp) { | 618 if (sc && (STF2IFP(sc)->if_flags & IFF_LINK2) == 0 && inifp) { |
613 struct sockaddr_in sin; 614 struct rtentry *rt; 615 616 bzero(&sin, sizeof(sin)); 617 sin.sin_family = AF_INET; 618 sin.sin_len = sizeof(struct sockaddr_in); 619 sin.sin_addr = *in; 620 rt = rtalloc1((struct sockaddr *)&sin, 0, 0UL); 621 if (!rt || rt->rt_ifp != inifp) { 622#if 0 623 log(LOG_WARNING, "%s: packet from 0x%x dropped " | 619 struct sockaddr_in sin; 620 struct rtentry *rt; 621 622 bzero(&sin, sizeof(sin)); 623 sin.sin_family = AF_INET; 624 sin.sin_len = sizeof(struct sockaddr_in); 625 sin.sin_addr = *in; 626 rt = rtalloc1((struct sockaddr *)&sin, 0, 0UL); 627 if (!rt || rt->rt_ifp != inifp) { 628#if 0 629 log(LOG_WARNING, "%s: packet from 0x%x dropped " |
624 "due to ingress filter\n", if_name(&sc->sc_if), | 630 "due to ingress filter\n", if_name(STF2IFP(sc)), |
625 (u_int32_t)ntohl(sin.sin_addr.s_addr)); 626#endif 627 if (rt) 628 rtfree(rt); 629 return -1; 630 } 631 rtfree(rt); 632 } --- 46 unchanged lines hidden (view full) --- 679 m_freem(m); 680 return; 681 } 682 683 ip = mtod(m, struct ip *); 684 685 sc = (struct stf_softc *)encap_getarg(m); 686 | 631 (u_int32_t)ntohl(sin.sin_addr.s_addr)); 632#endif 633 if (rt) 634 rtfree(rt); 635 return -1; 636 } 637 rtfree(rt); 638 } --- 46 unchanged lines hidden (view full) --- 685 m_freem(m); 686 return; 687 } 688 689 ip = mtod(m, struct ip *); 690 691 sc = (struct stf_softc *)encap_getarg(m); 692 |
687 if (sc == NULL || (sc->sc_if.if_flags & IFF_UP) == 0) { | 693 if (sc == NULL || (STF2IFP(sc)->if_flags & IFF_UP) == 0) { |
688 m_freem(m); 689 return; 690 } 691 | 694 m_freem(m); 695 return; 696 } 697 |
692 ifp = &sc->sc_if; | 698 ifp = STF2IFP(sc); |
693 694#ifdef MAC 695 mac_create_mbuf_from_ifnet(ifp, m); 696#endif 697 698 /* 699 * perform sanity check against outer src/dst. 700 * for source, perform ingress filter as well. --- 122 unchanged lines hidden --- | 699 700#ifdef MAC 701 mac_create_mbuf_from_ifnet(ifp, m); 702#endif 703 704 /* 705 * perform sanity check against outer src/dst. 706 * for source, perform ingress filter as well. --- 122 unchanged lines hidden --- |