2 * Copyright 2009, Colin Günther, coling@gmx.de.
3 * Copyright 2007-2009, Axel Dörfler, axeld@pinc-software.de.
4 * Copyright 2007, Hugo Santos. All Rights Reserved.
5 * Copyright 2004, Marcus Overhagen. All Rights Reserved.
7 * Distributed under the terms of the MIT License.
14 #include <net/if_types.h>
15 #include <sys/sockio.h>
17 #include <compat/sys/bus.h>
18 #include <compat/sys/kernel.h>
19 #include <compat/sys/taskqueue.h>
21 #include <compat/net/bpf.h>
22 #include <compat/net/ethernet.h>
23 #include <compat/net/if.h>
24 #include <compat/net/if_arp.h>
25 #include <compat/net/if_media.h>
26 #include <compat/net/if_var.h>
27 #include <compat/net/if_vlan_var.h>
28 #include <compat/sys/malloc.h>
32 int ifqmaxlen
= IFQ_MAXLEN
;
34 static void if_input_default(struct ifnet
*, struct mbuf
*);
35 static int if_requestencap_default(struct ifnet
*, struct if_encap_req
*);
39 #define IFNET_HOLD (void *)(uintptr_t)(-1)
43 insert_into_device_name_list(struct ifnet
* ifp
)
46 for (i
= 0; i
< MAX_DEVICES
; i
++) {
47 if (gDeviceNameList
[i
] == NULL
) {
48 gDeviceNameList
[i
] = ifp
->device_name
;
53 panic("too many devices");
58 remove_from_device_name_list(struct ifnet
* ifp
)
61 for (i
= 0; i
< MAX_DEVICES
; i
++) {
62 if (ifp
->device_name
== gDeviceNameList
[i
]) {
64 for (last
= i
+ 1; last
< MAX_DEVICES
; last
++) {
65 if (gDeviceNameList
[last
] == NULL
)
71 gDeviceNameList
[i
] = NULL
;
73 // switch positions with the last entry
74 gDeviceNameList
[i
] = gDeviceNameList
[last
];
75 gDeviceNameList
[last
] = NULL
;
84 ifnet_byindex(u_short idx
)
88 IFNET_RLOCK_NOSLEEP();
89 ifp
= ifnet_byindex_locked(idx
);
90 IFNET_RUNLOCK_NOSLEEP();
97 ifnet_byindex_locked(u_short idx
)
108 ifnet_setbyindex_locked(u_short idx
, struct ifnet
*ifp
)
115 ifnet_setbyindex(u_short idx
, struct ifnet
*ifp
)
118 ifnet_setbyindex_locked(idx
, ifp
);
124 ifindex_alloc_locked(u_short
*idxp
)
128 for (index
= 0; index
< MAX_DEVICES
; index
++) {
129 if (gDevices
[index
] == NULL
) {
134 if (index
== MAX_DEVICES
)
145 ifindex_free_locked(u_short idx
)
147 gDevices
[idx
] = NULL
;
153 if_alloc(u_char type
)
158 struct ifnet
*ifp
= _kernel_malloc(sizeof(struct ifnet
), M_ZERO
);
162 snprintf(semName
, sizeof(semName
), "%s receive", gDriverName
);
164 ifp
->receive_sem
= create_sem(0, semName
);
165 if (ifp
->receive_sem
< B_OK
)
171 ifp
->if_l2com
= _kernel_malloc(sizeof(struct arpcom
), M_ZERO
);
172 if (ifp
->if_l2com
== NULL
)
174 IFP2AC(ifp
)->ac_ifp
= ifp
;
179 if (wlan_if_l2com_alloc(ifp
) != B_OK
)
185 ifp
->link_state_sem
= -1;
189 ifq_init(&ifp
->receive_queue
, semName
);
191 ifp
->scan_done_sem
= -1;
192 // WLAN specific, doesn't hurt when initilized for other devices
194 // Search for the first free device slot, and use that one
196 if (ifindex_alloc_locked(&index
) != ENOERR
) {
198 panic("too many devices");
201 ifnet_setbyindex_locked(index
, IFNET_HOLD
);
204 ifp
->if_index
= index
;
205 ifnet_setbyindex(ifp
->if_index
, ifp
);
207 IF_ADDR_LOCK_INIT(ifp
);
214 _kernel_free(ifp
->if_l2com
);
219 delete_sem(ifp
->receive_sem
);
228 if_free(struct ifnet
*ifp
)
230 // IEEE80211 devices won't be in this list,
231 // so don't try to remove them.
232 if (ifp
->if_type
== IFT_ETHER
)
233 remove_from_device_name_list(ifp
);
236 ifindex_free_locked(ifp
->if_index
);
239 IF_ADDR_LOCK_DESTROY(ifp
);
240 switch (ifp
->if_type
) {
243 _kernel_free(ifp
->if_l2com
);
247 delete_sem(ifp
->receive_sem
);
248 ifq_uninit(&ifp
->receive_queue
);
255 if_initname(struct ifnet
*ifp
, const char *name
, int unit
)
257 dprintf("if_initname(%p, %s, %d)\n", ifp
, name
, unit
);
259 if (name
== NULL
|| name
[0] == '\0')
260 panic("interface goes unnamed");
262 ifp
->if_dname
= name
;
263 ifp
->if_dunit
= unit
;
265 strlcpy(ifp
->if_xname
, name
, sizeof(ifp
->if_xname
));
267 snprintf(ifp
->device_name
, sizeof(ifp
->device_name
), "net/%s/%i",
268 gDriverName
, ifp
->if_index
);
270 driver_printf("%s: /dev/%s\n", gDriverName
, ifp
->device_name
);
272 // For wlan devices we only want to see the cloned wlan device
274 // Remember: For each wlan device, there is a base device of type
275 // IFT_IEEE80211. On top of that a clone device is created of
277 // Haiku shall only see the cloned device as it is the one
278 // FreeBSD 8 uses for wireless i/o, too.
279 if (ifp
->if_type
== IFT_ETHER
)
280 insert_into_device_name_list(ifp
);
282 ifp
->root_device
= find_root_device(unit
);
287 ifq_init(struct ifqueue
*ifq
, const char *name
)
289 ifq
->ifq_head
= NULL
;
290 ifq
->ifq_tail
= NULL
;
292 ifq
->ifq_maxlen
= IFQ_MAXLEN
;
295 mtx_init(&ifq
->ifq_mtx
, name
, NULL
, MTX_DEF
);
300 ifq_uninit(struct ifqueue
*ifq
)
302 mtx_destroy(&ifq
->ifq_mtx
);
307 if_transmit(struct ifnet
*ifp
, struct mbuf
*m
)
311 IFQ_HANDOFF(ifp
, m
, error
);
317 if_input_default(struct ifnet
*ifp __unused
, struct mbuf
*m
)
325 * Flush an interface queue.
328 if_qflush(struct ifnet
*ifp
)
336 if (ALTQ_IS_ENABLED(ifq
))
340 while ((m
= n
) != NULL
) {
352 if_attach(struct ifnet
*ifp
)
354 unsigned socksize
, ifasize
;
355 int namelen
, masklen
;
356 struct sockaddr_dl
*sdl
;
359 TAILQ_INIT(&ifp
->if_addrhead
);
360 TAILQ_INIT(&ifp
->if_prefixhead
);
361 TAILQ_INIT(&ifp
->if_multiaddrs
);
363 IF_ADDR_LOCK_INIT(ifp
);
365 ifp
->if_lladdr
.sdl_family
= AF_LINK
;
367 ifq_init((struct ifqueue
*) &ifp
->if_snd
, ifp
->if_xname
);
369 if (ifp
->if_transmit
== NULL
) {
370 ifp
->if_transmit
= if_transmit
;
371 ifp
->if_qflush
= if_qflush
;
373 if (ifp
->if_input
== NULL
)
374 ifp
->if_input
= if_input_default
;
376 if (ifp
->if_requestencap
== NULL
)
377 ifp
->if_requestencap
= if_requestencap_default
;
380 * Create a Link Level name for this device.
382 namelen
= strlen(ifp
->if_xname
);
384 * Always save enough space for any possiable name so we
385 * can do a rename in place later.
387 masklen
= offsetof(struct sockaddr_dl
, sdl_data
[0]) + IFNAMSIZ
;
388 socksize
= masklen
+ ifp
->if_addrlen
;
389 if (socksize
< sizeof(*sdl
))
390 socksize
= sizeof(*sdl
);
391 socksize
= roundup2(socksize
, sizeof(long));
392 ifasize
= sizeof(*ifa
) + 2 * socksize
;
393 ifa
= ifa_alloc(ifasize
, M_WAITOK
);
394 sdl
= (struct sockaddr_dl
*)(ifa
+ 1);
395 sdl
->sdl_len
= socksize
;
396 sdl
->sdl_family
= AF_LINK
;
397 bcopy(ifp
->if_xname
, sdl
->sdl_data
, namelen
);
398 sdl
->sdl_nlen
= namelen
;
399 sdl
->sdl_index
= ifp
->if_index
;
400 sdl
->sdl_type
= ifp
->if_type
;
403 //ifa->ifa_rtrequest = link_rtrequest;
404 ifa
->ifa_addr
= (struct sockaddr
*)sdl
;
405 sdl
= (struct sockaddr_dl
*)(socksize
+ (caddr_t
)sdl
);
406 ifa
->ifa_netmask
= (struct sockaddr
*)sdl
;
407 sdl
->sdl_len
= masklen
;
409 sdl
->sdl_data
[--namelen
] = 0xff;
410 dprintf("if_attach %p\n", ifa
->ifa_addr
);
415 if_detach(struct ifnet
*ifp
)
417 if (HAIKU_DRIVER_REQUIRES(FBSD_SWI_TASKQUEUE
))
418 taskqueue_drain(taskqueue_swi
, &ifp
->if_linktask
);
420 IF_ADDR_LOCK_DESTROY(ifp
);
421 ifq_uninit((struct ifqueue
*) &ifp
->if_snd
);
426 if_start(struct ifnet
*ifp
)
428 #ifdef IFF_NEEDSGIANT
429 if (ifp
->if_flags
& IFF_NEEDSGIANT
)
430 panic("freebsd compat.: unsupported giant requirement");
437 if_printf(struct ifnet
*ifp
, const char *format
, ...)
441 va_start(vl
, format
);
442 vsnprintf(buf
, sizeof(buf
), format
, vl
);
445 dprintf("[%s] %s", ifp
->device_name
, buf
);
451 * Compat function for handling basic encapsulation requests.
452 * Not converted stacks (FDDI, IB, ..) supports traditional
453 * output model: ARP (and other similar L2 protocols) are handled
454 * inside output routine, arpresolve/nd6_resolve() returns MAC
455 * address instead of full prepend.
457 * This function creates calculated header==MAC for IPv4/IPv6 and
458 * returns EAFNOSUPPORT (which is then handled in ARP code) for other
462 if_requestencap_default(struct ifnet
*ifp
, struct if_encap_req
*req
)
465 if (req
->rtype
!= IFENCAP_LL
)
468 if (req
->bufsize
< req
->lladdr_len
)
471 switch (req
->family
) {
476 return (EAFNOSUPPORT
);
479 /* Copy lladdr to storage as is */
480 memmove(req
->buf
, req
->lladdr
, req
->lladdr_len
);
481 req
->bufsize
= req
->lladdr_len
;
489 if_link_state_change(struct ifnet
*ifp
, int linkState
)
491 if (ifp
->if_link_state
== linkState
)
494 ifp
->if_link_state
= linkState
;
495 release_sem_etc(ifp
->link_state_sem
, 1, B_DO_NOT_RESCHEDULE
);
498 static struct ifmultiaddr
*
499 if_findmulti(struct ifnet
*ifp
, struct sockaddr
*_address
)
501 struct sockaddr_dl
*address
= (struct sockaddr_dl
*) _address
;
502 struct ifmultiaddr
*ifma
;
504 TAILQ_FOREACH (ifma
, &ifp
->if_multiaddrs
, ifma_link
) {
505 if (memcmp(LLADDR(address
),
506 LLADDR((struct sockaddr_dl
*)ifma
->ifma_addr
), ETHER_ADDR_LEN
) == 0)
515 * if_freemulti: free ifmultiaddr structure and possibly attached related
516 * addresses. The caller is responsible for implementing reference
517 * counting, notifying the driver, handling routing messages, and releasing
518 * any dependent link layer state.
521 if_freemulti(struct ifmultiaddr
*ifma
)
524 KASSERT(ifma
->ifma_refcount
== 0, ("if_freemulti: refcount %d",
525 ifma
->ifma_refcount
));
526 KASSERT(ifma
->ifma_protospec
== NULL
,
527 ("if_freemulti: protospec not NULL"));
529 if (ifma
->ifma_lladdr
!= NULL
)
530 free(ifma
->ifma_lladdr
);
532 // Haiku note: We use a field in the ifmultiaddr struct (ifma_addr_storage)
533 // to store the address and let ifma_addr point to that. We therefore do not
534 // free it here, as it will be freed as part of freeing the if_multiaddr.
535 //free(ifma->ifma_addr);
541 static struct ifmultiaddr
*
542 _if_addmulti(struct ifnet
*ifp
, struct sockaddr
*address
)
544 struct ifmultiaddr
*addr
= if_findmulti(ifp
, address
);
547 addr
->ifma_refcount
++;
551 addr
= (struct ifmultiaddr
*) malloc(sizeof(struct ifmultiaddr
));
555 addr
->ifma_lladdr
= NULL
;
556 addr
->ifma_ifp
= ifp
;
557 addr
->ifma_protospec
= NULL
;
559 memcpy(&addr
->ifma_addr_storage
, address
, sizeof(struct sockaddr_dl
));
560 addr
->ifma_addr
= (struct sockaddr
*) &addr
->ifma_addr_storage
;
562 addr
->ifma_refcount
= 1;
564 TAILQ_INSERT_HEAD(&ifp
->if_multiaddrs
, addr
, ifma_link
);
571 if_addmulti(struct ifnet
*ifp
, struct sockaddr
*address
,
572 struct ifmultiaddr
**out
)
574 struct ifmultiaddr
*result
;
578 result
= _if_addmulti(ifp
, address
);
580 refcount
= result
->ifma_refcount
;
586 if (refcount
== 1 && ifp
->if_ioctl
!= NULL
)
587 ifp
->if_ioctl(ifp
, SIOCADDMULTI
, NULL
);
597 if_delmulti_locked(struct ifnet
*ifp
, struct ifmultiaddr
*ifma
, int detaching
)
599 struct ifmultiaddr
*ll_ifma
;
601 if (ifp
!= NULL
&& ifma
->ifma_ifp
!= NULL
) {
602 KASSERT(ifma
->ifma_ifp
== ifp
,
603 ("%s: inconsistent ifp %p", __func__
, ifp
));
604 IF_ADDR_LOCK_ASSERT(ifp
);
607 ifp
= ifma
->ifma_ifp
;
610 * If the ifnet is detaching, null out references to ifnet,
611 * so that upper protocol layers will notice, and not attempt
612 * to obtain locks for an ifnet which no longer exists. The
613 * routing socket announcement must happen before the ifnet
614 * instance is detached from the system.
618 printf("%s: detaching ifnet instance %p\n", __func__
, ifp
);
621 * ifp may already be nulled out if we are being reentered
622 * to delete the ll_ifma.
626 rt_newmaddrmsg(RTM_DELMADDR
, ifma
);
628 ifma
->ifma_ifp
= NULL
;
632 if (--ifma
->ifma_refcount
> 0)
637 * If this ifma is a network-layer ifma, a link-layer ifma may
638 * have been associated with it. Release it first if so.
640 ll_ifma
= ifma
->ifma_llifma
;
641 if (ll_ifma
!= NULL
) {
642 KASSERT(ifma
->ifma_lladdr
!= NULL
,
643 ("%s: llifma w/o lladdr", __func__
));
645 ll_ifma
->ifma_ifp
= NULL
; /* XXX */
646 if (--ll_ifma
->ifma_refcount
== 0) {
648 TAILQ_REMOVE(&ifp
->if_multiaddrs
, ll_ifma
,
651 if_freemulti(ll_ifma
);
657 TAILQ_REMOVE(&ifp
->if_multiaddrs
, ifma
, ifma_link
);
662 * The last reference to this instance of struct ifmultiaddr
663 * was released; the hardware should be notified of this change.
670 * Delete all multicast group membership for an interface.
671 * Should be used to quickly flush all multicast filters.
674 if_delallmulti(struct ifnet
*ifp
)
676 struct ifmultiaddr
*ifma
;
677 struct ifmultiaddr
*next
;
680 TAILQ_FOREACH_SAFE(ifma
, &ifp
->if_multiaddrs
, ifma_link
, next
)
681 if_delmulti_locked(ifp
, ifma
, 0);
687 if_delete_multiaddr(struct ifnet
*ifp
, struct ifmultiaddr
*ifma
)
689 TAILQ_REMOVE(&ifp
->if_multiaddrs
, ifma
, ifma_link
);
695 if_delmulti(struct ifnet
*ifp
, struct sockaddr
*sa
)
697 struct ifmultiaddr
*ifma
;
702 IFNET_RLOCK_NOSLEEP();
703 TAILQ_FOREACH(oifp
, &V_ifnet
, if_link
)
708 IFNET_RUNLOCK_NOSLEEP();
710 KASSERT(ifp
!= NULL
, ("%s: ifnet went away", __func__
));
717 ifma
= if_findmulti(ifp
, sa
);
719 lastref
= if_delmulti_locked(ifp
, ifma
, 0);
725 if (lastref
&& ifp
->if_ioctl
!= NULL
) {
726 (void)(*ifp
->if_ioctl
)(ifp
, SIOCDELMULTI
, 0);
734 if_purgemaddrs(struct ifnet
*ifp
)
736 struct ifmultiaddr
*ifma
;
737 struct ifmultiaddr
*next
;
740 TAILQ_FOREACH_SAFE(ifma
, &ifp
->if_multiaddrs
, ifma_link
, next
)
741 if_delmulti_locked(ifp
, ifma
, 1);
746 * Return counter values from counter(9)s stored in ifnet.
749 if_get_counter_default(struct ifnet
*ifp
, ift_counter cnt
)
752 KASSERT(cnt
< IFCOUNTERS
, ("%s: invalid cnt %d", __func__
, cnt
));
755 case IFCOUNTER_IPACKETS
:
756 return atomic_get64((int64
*)&ifp
->if_ipackets
);
757 case IFCOUNTER_IERRORS
:
758 return atomic_get64((int64
*)&ifp
->if_ierrors
);
759 case IFCOUNTER_OPACKETS
:
760 return atomic_get64((int64
*)&ifp
->if_opackets
);
761 case IFCOUNTER_OERRORS
:
762 return atomic_get64((int64
*)&ifp
->if_oerrors
);
763 case IFCOUNTER_COLLISIONS
:
764 return atomic_get64((int64
*)&ifp
->if_collisions
);
765 case IFCOUNTER_IBYTES
:
766 return atomic_get64((int64
*)&ifp
->if_ibytes
);
767 case IFCOUNTER_OBYTES
:
768 return atomic_get64((int64
*)&ifp
->if_obytes
);
769 case IFCOUNTER_IMCASTS
:
770 return atomic_get64((int64
*)&ifp
->if_imcasts
);
771 case IFCOUNTER_OMCASTS
:
772 return atomic_get64((int64
*)&ifp
->if_omcasts
);
773 case IFCOUNTER_IQDROPS
:
774 return atomic_get64((int64
*)&ifp
->if_iqdrops
);
775 case IFCOUNTER_OQDROPS
:
776 return atomic_get64((int64
*)&ifp
->if_oqdrops
);
777 case IFCOUNTER_NOPROTO
:
778 return atomic_get64((int64
*)&ifp
->if_noproto
);
780 KASSERT(cnt
< IFCOUNTERS
, ("%s: invalid cnt %d", __func__
, cnt
));
786 if_addr_rlock(struct ifnet
*ifp
)
793 if_addr_runlock(struct ifnet
*ifp
)
800 if_maddr_rlock(struct ifnet
*ifp
)
807 if_maddr_runlock(struct ifnet
*ifp
)
814 ether_output(struct ifnet
*ifp
, struct mbuf
*m
, struct sockaddr
*dst
,
818 IFQ_HANDOFF(ifp
, m
, error
);
823 static void ether_input(struct ifnet
*ifp
, struct mbuf
*m
)
825 IF_ENQUEUE(&ifp
->receive_queue
, m
);
826 release_sem_etc(ifp
->receive_sem
, 1, B_DO_NOT_RESCHEDULE
);
831 ether_ifattach(struct ifnet
*ifp
, const uint8_t *lla
)
834 struct sockaddr_dl
*sdl
;
836 ifp
->if_addrlen
= ETHER_ADDR_LEN
;
837 ifp
->if_hdrlen
= ETHER_HDR_LEN
;
839 ifp
->if_mtu
= ETHERMTU
;
840 ifp
->if_output
= ether_output
;
841 ifp
->if_input
= ether_input
;
842 ifp
->if_resolvemulti
= NULL
; // done in the stack
843 ifp
->if_broadcastaddr
= etherbroadcastaddr
;
846 sdl
= (struct sockaddr_dl
*)ifa
->ifa_addr
;
847 sdl
->sdl_type
= IFT_ETHER
;
848 sdl
->sdl_alen
= ifp
->if_addrlen
;
849 bcopy(lla
, LLADDR(sdl
), ifp
->if_addrlen
);
854 ether_ifdetach(struct ifnet
*ifp
)
861 ether_ioctl(struct ifnet
*ifp
, u_long command
, caddr_t data
)
863 struct ifreq
*ifr
= (struct ifreq
*) data
;
867 if (ifr
->ifr_mtu
> ETHERMTU
)
871 // need to fix our ifreq to work with C...
872 // ifp->ifr_mtu = ifr->ifr_mtu;
884 * Initialization, destruction and refcounting functions for ifaddrs.
887 ifa_alloc(size_t size
, int flags
)
891 KASSERT(size
>= sizeof(struct ifaddr
),
892 ("%s: invalid size %zu", __func__
, size
));
894 ifa
= _kernel_malloc(size
, M_ZERO
| flags
);
898 //refcount_init(&ifa->ifa_refcnt, 1);
903 /* free(NULL) is okay */
910 ifa_ref(struct ifaddr
*ifa
)
912 //refcount_acquire(&ifa->ifa_refcnt);
916 ifa_free(struct ifaddr
*ifa
)
919 //if (refcount_release(&ifa->ifa_refcnt)) {
925 if_inc_counter(struct ifnet
*ifp
, ift_counter cnt
, int64_t inc
)
928 case IFCOUNTER_IPACKETS
:
929 atomic_add64((int64
*)&ifp
->if_ipackets
, inc
);
931 case IFCOUNTER_IERRORS
:
932 atomic_add64((int64
*)&ifp
->if_ierrors
, inc
);
934 case IFCOUNTER_OPACKETS
:
935 atomic_add64((int64
*)&ifp
->if_opackets
, inc
);
937 case IFCOUNTER_OERRORS
:
938 atomic_add64((int64
*)&ifp
->if_oerrors
, inc
);
940 case IFCOUNTER_COLLISIONS
:
941 atomic_add64((int64
*)&ifp
->if_collisions
, inc
);
943 case IFCOUNTER_IBYTES
:
944 atomic_add64((int64
*)&ifp
->if_ibytes
, inc
);
946 case IFCOUNTER_OBYTES
:
947 atomic_add64((int64
*)&ifp
->if_obytes
, inc
);
949 case IFCOUNTER_IMCASTS
:
950 atomic_add64((int64
*)&ifp
->if_imcasts
, inc
);
952 case IFCOUNTER_OMCASTS
:
953 atomic_add64((int64
*)&ifp
->if_omcasts
, inc
);
955 case IFCOUNTER_IQDROPS
:
956 atomic_add64((int64
*)&ifp
->if_iqdrops
, inc
);
958 case IFCOUNTER_OQDROPS
:
959 atomic_add64((int64
*)&ifp
->if_oqdrops
, inc
);
961 case IFCOUNTER_NOPROTO
:
962 atomic_add64((int64
*)&ifp
->if_noproto
, inc
);
965 KASSERT(cnt
< IFCOUNTERS
, ("%s: invalid cnt %d", __func__
, cnt
));
970 /* API for driver access to network stack owned ifnet.*/
972 if_setbaudrate(struct ifnet
*ifp
, uint64_t baudrate
)
976 oldbrate
= ifp
->if_baudrate
;
977 ifp
->if_baudrate
= baudrate
;
982 if_getbaudrate(if_t ifp
)
985 return (((struct ifnet
*)ifp
)->if_baudrate
);
989 if_setcapabilities(if_t ifp
, int capabilities
)
991 ((struct ifnet
*)ifp
)->if_capabilities
= capabilities
;
996 if_setcapabilitiesbit(if_t ifp
, int setbit
, int clearbit
)
998 ((struct ifnet
*)ifp
)->if_capabilities
|= setbit
;
999 ((struct ifnet
*)ifp
)->if_capabilities
&= ~clearbit
;
1005 if_getcapabilities(if_t ifp
)
1007 return ((struct ifnet
*)ifp
)->if_capabilities
;
1011 if_setcapenable(if_t ifp
, int capabilities
)
1013 ((struct ifnet
*)ifp
)->if_capenable
= capabilities
;
1018 if_setcapenablebit(if_t ifp
, int setcap
, int clearcap
)
1021 ((struct ifnet
*)ifp
)->if_capenable
|= setcap
;
1023 ((struct ifnet
*)ifp
)->if_capenable
&= ~clearcap
;
1029 if_getdname(if_t ifp
)
1031 return ((struct ifnet
*)ifp
)->if_dname
;
1035 if_togglecapenable(if_t ifp
, int togglecap
)
1037 ((struct ifnet
*)ifp
)->if_capenable
^= togglecap
;
1042 if_getcapenable(if_t ifp
)
1044 return ((struct ifnet
*)ifp
)->if_capenable
;
1048 * This is largely undesirable because it ties ifnet to a device, but does
1049 * provide flexiblity for an embedded product vendor. Should be used with
1050 * the understanding that it violates the interface boundaries, and should be
1051 * a last resort only.
1054 if_setdev(if_t ifp
, void *dev
)
1060 if_setdrvflagbits(if_t ifp
, int set_flags
, int clear_flags
)
1062 ((struct ifnet
*)ifp
)->if_drv_flags
|= set_flags
;
1063 ((struct ifnet
*)ifp
)->if_drv_flags
&= ~clear_flags
;
1069 if_getdrvflags(if_t ifp
)
1071 return ((struct ifnet
*)ifp
)->if_drv_flags
;
1075 if_setdrvflags(if_t ifp
, int flags
)
1077 ((struct ifnet
*)ifp
)->if_drv_flags
= flags
;
1083 if_setflags(if_t ifp
, int flags
)
1085 ((struct ifnet
*)ifp
)->if_flags
= flags
;
1090 if_setflagbits(if_t ifp
, int set
, int clear
)
1092 ((struct ifnet
*)ifp
)->if_flags
|= set
;
1093 ((struct ifnet
*)ifp
)->if_flags
&= ~clear
;
1099 if_getflags(if_t ifp
)
1101 return ((struct ifnet
*)ifp
)->if_flags
;
1105 if_clearhwassist(if_t ifp
)
1107 ((struct ifnet
*)ifp
)->if_hwassist
= 0;
1112 if_sethwassistbits(if_t ifp
, int toset
, int toclear
)
1114 ((struct ifnet
*)ifp
)->if_hwassist
|= toset
;
1115 ((struct ifnet
*)ifp
)->if_hwassist
&= ~toclear
;
1121 if_sethwassist(if_t ifp
, int hwassist_bit
)
1123 ((struct ifnet
*)ifp
)->if_hwassist
= hwassist_bit
;
1128 if_gethwassist(if_t ifp
)
1130 return ((struct ifnet
*)ifp
)->if_hwassist
;
1134 if_setmtu(if_t ifp
, int mtu
)
1136 ((struct ifnet
*)ifp
)->if_mtu
= mtu
;
1143 return ((struct ifnet
*)ifp
)->if_mtu
;
1147 if_setsoftc(if_t ifp
, void *softc
)
1149 ((struct ifnet
*)ifp
)->if_softc
= softc
;
1154 if_getsoftc(if_t ifp
)
1156 return ((struct ifnet
*)ifp
)->if_softc
;
1160 if_setrcvif(struct mbuf
*m
, if_t ifp
)
1162 m
->m_pkthdr
.rcvif
= (struct ifnet
*)ifp
;
1166 if_setvtag(struct mbuf
*m
, uint16_t tag
)
1168 m
->m_pkthdr
.ether_vtag
= tag
;
1172 if_getvtag(struct mbuf
*m
)
1175 return (m
->m_pkthdr
.ether_vtag
);
1179 if_sendq_empty(if_t ifp
)
1181 return IFQ_DRV_IS_EMPTY(&((struct ifnet
*)ifp
)->if_snd
);
1185 if_getamcount(if_t ifp
)
1187 return ((struct ifnet
*)ifp
)->if_amcount
;
1192 if_setsendqready(if_t ifp
)
1194 IFQ_SET_READY(&((struct ifnet
*)ifp
)->if_snd
);
1199 if_setsendqlen(if_t ifp
, int tx_desc_count
)
1201 IFQ_SET_MAXLEN(&((struct ifnet
*)ifp
)->if_snd
, tx_desc_count
);
1202 ((struct ifnet
*)ifp
)->if_snd
.ifq_drv_maxlen
= tx_desc_count
;
1208 if_vlantrunkinuse(if_t ifp
)
1210 return ((struct ifnet
*)ifp
)->if_vlantrunk
!= NULL
?1:0;
1214 if_input(if_t ifp
, struct mbuf
* sendmp
)
1216 (*((struct ifnet
*)ifp
)->if_input
)((struct ifnet
*)ifp
, sendmp
);
1222 #ifndef ETH_ADDR_LEN
1223 #define ETH_ADDR_LEN 6
1227 if_setupmultiaddr(if_t ifp
, void *mta
, int *cnt
, int max
)
1229 struct ifmultiaddr
*ifma
;
1230 uint8_t *lmta
= (uint8_t *)mta
;
1233 TAILQ_FOREACH(ifma
, &((struct ifnet
*)ifp
)->if_multiaddrs
, ifma_link
) {
1234 if (ifma
->ifma_addr
->sa_family
!= AF_LINK
)
1240 bcopy(LLADDR((struct sockaddr_dl
*)ifma
->ifma_addr
),
1241 &lmta
[mcnt
* ETH_ADDR_LEN
], ETH_ADDR_LEN
);
1250 if_multiaddr_array(if_t ifp
, void *mta
, int *cnt
, int max
)
1254 if_maddr_rlock(ifp
);
1255 error
= if_setupmultiaddr(ifp
, mta
, cnt
, max
);
1256 if_maddr_runlock(ifp
);
1261 if_multiaddr_count(if_t ifp
, int max
)
1263 struct ifmultiaddr
*ifma
;
1267 if_maddr_rlock(ifp
);
1268 TAILQ_FOREACH(ifma
, &((struct ifnet
*)ifp
)->if_multiaddrs
, ifma_link
) {
1269 if (ifma
->ifma_addr
->sa_family
!= AF_LINK
)
1275 if_maddr_runlock(ifp
);
1280 if_dequeue(if_t ifp
)
1283 IFQ_DRV_DEQUEUE(&((struct ifnet
*)ifp
)->if_snd
, m
);
1289 if_sendq_prepend(if_t ifp
, struct mbuf
*m
)
1291 IFQ_DRV_PREPEND(&((struct ifnet
*)ifp
)->if_snd
, m
);
1296 if_setifheaderlen(if_t ifp
, int len
)
1298 ((struct ifnet
*)ifp
)->if_hdrlen
= len
;
1303 if_getlladdr(if_t ifp
)
1305 return (IF_LLADDR((struct ifnet
*)ifp
));
1309 if_gethandle(u_char type
)
1311 return (if_alloc(type
));
1315 if_bpfmtap(if_t ifh
, struct mbuf
*m
)
1317 struct ifnet
*ifp
= (struct ifnet
*)ifh
;
1323 if_etherbpfmtap(if_t ifh
, struct mbuf
*m
)
1325 struct ifnet
*ifp
= (struct ifnet
*)ifh
;
1327 ETHER_BPF_MTAP(ifp
, m
);
1331 if_vlancap(if_t ifh
)
1333 struct ifnet
*ifp
= (struct ifnet
*)ifh
;
1334 VLAN_CAPABILITIES(ifp
);
1338 if_setinitfn(if_t ifp
, void (*init_fn
)(void *))
1340 ((struct ifnet
*)ifp
)->if_init
= init_fn
;
1344 if_setioctlfn(if_t ifp
, int (*ioctl_fn
)(if_t
, u_long
, caddr_t
))
1346 ((struct ifnet
*)ifp
)->if_ioctl
= (void *)ioctl_fn
;
1350 if_setstartfn(if_t ifp
, void (*start_fn
)(if_t
))
1352 ((struct ifnet
*)ifp
)->if_start
= (void *)start_fn
;
1356 if_settransmitfn(if_t ifp
, if_transmit_fn_t start_fn
)
1358 ((struct ifnet
*)ifp
)->if_transmit
= start_fn
;
1361 void if_setqflushfn(if_t ifp
, if_qflush_fn_t flush_fn
)
1363 ((struct ifnet
*)ifp
)->if_qflush
= flush_fn
;
1367 if_setgetcounterfn(if_t ifp
, if_get_counter_t fn
)
1370 ifp
->if_get_counter
= fn
;