Lines Matching +full:timer +full:- +full:cannot +full:- +full:wake +full:- +full:cpu

1 /*-
2 * SPDX-License-Identifier: BSD-3-Clause
4 * Copyright (c) 2001-2008, by Cisco Systems, Inc. All rights reserved.
5 * Copyright (c) 2008-2012, by Randall Stewart. All rights reserved.
6 * Copyright (c) 2008-2012, by Michael Tuexen. All rights reserved.
85 spcb->ep_count = SCTP_BASE_INFO(ipi_count_ep); in sctp_fill_pcbinfo()
86 spcb->asoc_count = SCTP_BASE_INFO(ipi_count_asoc); in sctp_fill_pcbinfo()
87 spcb->laddr_count = SCTP_BASE_INFO(ipi_count_laddr); in sctp_fill_pcbinfo()
88 spcb->raddr_count = SCTP_BASE_INFO(ipi_count_raddr); in sctp_fill_pcbinfo()
89 spcb->chk_count = SCTP_BASE_INFO(ipi_count_chunk); in sctp_fill_pcbinfo()
90 spcb->readq_count = SCTP_BASE_INFO(ipi_count_readq); in sctp_fill_pcbinfo()
91 spcb->stream_oque = SCTP_BASE_INFO(ipi_count_strmoq); in sctp_fill_pcbinfo()
92 spcb->free_chunks = SCTP_BASE_INFO(ipi_free_chunks); in sctp_fill_pcbinfo()
96 /*-
106 * hash-vrf-table
107 * vrf-> ifn-> ifn -> ifn
109 * ... +--ifa-> ifa -> ifa
126 * - An endpoint can be in multiple VRF's
127 * - An association lives within a VRF and only one VRF.
128 * - Any incoming packet we can deduce the VRF for by
130 * - Any downward send call or connect call must supply the
134 * - An endpoint may add multiple VRF's to it.
135 * - Listening sockets can accept associations in any
164 vrf->vrf_id = vrf_id; in sctp_allocate_vrf()
165 LIST_INIT(&vrf->ifnlist); in sctp_allocate_vrf()
166 vrf->total_ifa_count = 0; in sctp_allocate_vrf()
167 vrf->refcount = 0; in sctp_allocate_vrf()
171 vrf->vrf_addr_hash = SCTP_HASH_INIT(SCTP_VRF_ADDR_HASH_SIZE, in sctp_allocate_vrf()
172 &vrf->vrf_addr_hashmark); in sctp_allocate_vrf()
173 if (vrf->vrf_addr_hash == NULL) { in sctp_allocate_vrf()
199 if (sctp_ifnp->ifn_index == ifn_index && in sctp_find_ifn()
200 sctp_ifnp->ifn_p == ifn) { in sctp_find_ifn()
215 if (vrf_id == liste->vrf_id) { in sctp_find_vrf()
225 if (SCTP_DECREMENT_AND_CHECK_REFCOUNT(&vrf->refcount)) { in sctp_free_vrf()
226 if (vrf->vrf_addr_hash) { in sctp_free_vrf()
227 SCTP_HASH_FREE(vrf->vrf_addr_hash, vrf->vrf_addr_hashmark); in sctp_free_vrf()
228 vrf->vrf_addr_hash = NULL; in sctp_free_vrf()
240 if (SCTP_DECREMENT_AND_CHECK_REFCOUNT(&sctp_ifnp->refcount)) { in sctp_free_ifn()
242 if (sctp_ifnp->vrf) { in sctp_free_ifn()
243 sctp_free_vrf(sctp_ifnp->vrf); in sctp_free_ifn()
253 if (SCTP_DECREMENT_AND_CHECK_REFCOUNT(&sctp_ifap->refcount)) { in sctp_free_ifa()
255 if (sctp_ifap->ifn_p) { in sctp_free_ifa()
256 sctp_free_ifn(sctp_ifap->ifn_p); in sctp_free_ifa()
268 if (sctp_find_ifn(sctp_ifnp->ifn_p, sctp_ifnp->ifn_index) == NULL) { in sctp_delete_ifn()
278 /*-
288 LIST_INSERT_HEAD(&sctp_ifnp->ifalist, sctp_ifap, next_ifa); in sctp_add_ifa_to_ifn()
289 sctp_ifap->ifn_p = sctp_ifnp; in sctp_add_ifa_to_ifn()
290 atomic_add_int(&sctp_ifap->ifn_p->refcount, 1); in sctp_add_ifa_to_ifn()
292 sctp_ifnp->ifa_count++; in sctp_add_ifa_to_ifn()
293 ifa_af = sctp_ifap->address.sa.sa_family; in sctp_add_ifa_to_ifn()
297 sctp_ifnp->num_v4++; in sctp_add_ifa_to_ifn()
302 sctp_ifnp->num_v6++; in sctp_add_ifa_to_ifn()
308 if (sctp_ifnp->ifa_count == 1) { in sctp_add_ifa_to_ifn()
310 sctp_ifnp->registered_af = ifa_af; in sctp_add_ifa_to_ifn()
314 /*-
316 * If no more addresses exist, remove the ifn too. Otherwise, re-register
324 if (sctp_ifap->ifn_p) { in sctp_remove_ifa_from_ifn()
326 sctp_ifap->ifn_p->ifa_count--; in sctp_remove_ifa_from_ifn()
327 switch (sctp_ifap->address.sa.sa_family) { in sctp_remove_ifa_from_ifn()
330 sctp_ifap->ifn_p->num_v4--; in sctp_remove_ifa_from_ifn()
335 sctp_ifap->ifn_p->num_v6--; in sctp_remove_ifa_from_ifn()
342 if (LIST_EMPTY(&sctp_ifap->ifn_p->ifalist)) { in sctp_remove_ifa_from_ifn()
344 sctp_delete_ifn(sctp_ifap->ifn_p); in sctp_remove_ifa_from_ifn()
346 /* re-register address family type, if needed */ in sctp_remove_ifa_from_ifn()
347 if ((sctp_ifap->ifn_p->num_v6 == 0) && in sctp_remove_ifa_from_ifn()
348 (sctp_ifap->ifn_p->registered_af == AF_INET6)) { in sctp_remove_ifa_from_ifn()
349 sctp_ifap->ifn_p->registered_af = AF_INET; in sctp_remove_ifa_from_ifn()
350 } else if ((sctp_ifap->ifn_p->num_v4 == 0) && in sctp_remove_ifa_from_ifn()
351 (sctp_ifap->ifn_p->registered_af == AF_INET)) { in sctp_remove_ifa_from_ifn()
352 sctp_ifap->ifn_p->registered_af = AF_INET6; in sctp_remove_ifa_from_ifn()
355 sctp_free_ifn(sctp_ifap->ifn_p); in sctp_remove_ifa_from_ifn()
357 sctp_ifap->ifn_p = NULL; in sctp_remove_ifa_from_ifn()
398 vrf = sctp_ifnp->vrf; in sctp_add_addr_to_vrf()
419 sctp_ifnp->ifn_index = ifn_index; in sctp_add_addr_to_vrf()
420 sctp_ifnp->ifn_p = ifn; in sctp_add_addr_to_vrf()
421 sctp_ifnp->ifn_type = ifn_type; in sctp_add_addr_to_vrf()
422 sctp_ifnp->refcount = 0; in sctp_add_addr_to_vrf()
423 sctp_ifnp->vrf = vrf; in sctp_add_addr_to_vrf()
424 atomic_add_int(&vrf->refcount, 1); in sctp_add_addr_to_vrf()
425 sctp_ifnp->ifn_mtu = SCTP_GATHER_MTU_FROM_IFN_INFO(ifn, ifn_index); in sctp_add_addr_to_vrf()
427 SCTP_SNPRINTF(sctp_ifnp->ifn_name, SCTP_IFNAMSIZ, "%s", if_name); in sctp_add_addr_to_vrf()
429 SCTP_SNPRINTF(sctp_ifnp->ifn_name, SCTP_IFNAMSIZ, "%s", "unknown"); in sctp_add_addr_to_vrf()
432 LIST_INIT(&sctp_ifnp->ifalist); in sctp_add_addr_to_vrf()
434 LIST_INSERT_HEAD(&vrf->ifnlist, sctp_ifnp, next_ifn); in sctp_add_addr_to_vrf()
437 sctp_ifap = sctp_find_ifa_by_addr(addr, vrf->vrf_id, SCTP_ADDR_LOCKED); in sctp_add_addr_to_vrf()
440 if (sctp_ifap->ifn_p != NULL) { in sctp_add_addr_to_vrf()
441 if (sctp_ifap->ifn_p->ifn_index == ifn_index && in sctp_add_addr_to_vrf()
442 sctp_ifap->ifn_p->ifn_p == ifn) { in sctp_add_addr_to_vrf()
445 sctp_ifap->ifn_p->ifn_name, ifn_index, in sctp_add_addr_to_vrf()
451 if (sctp_ifap->localifa_flags & SCTP_BEING_DELETED) { in sctp_add_addr_to_vrf()
455 sctp_ifap->localifa_flags = SCTP_ADDR_VALID; in sctp_add_addr_to_vrf()
456 sctp_ifap->ifn_p = sctp_ifnp; in sctp_add_addr_to_vrf()
457 atomic_add_int(&sctp_ifap->ifn_p->refcount, 1); in sctp_add_addr_to_vrf()
467 sctp_ifap->ifn_p->ifn_name, in sctp_add_addr_to_vrf()
468 sctp_ifap->ifn_p->ifn_index, if_name, in sctp_add_addr_to_vrf()
477 sctp_ifap->localifa_flags = SCTP_ADDR_VALID; in sctp_add_addr_to_vrf()
496 sctp_ifap->ifn_p = sctp_ifnp; in sctp_add_addr_to_vrf()
497 atomic_add_int(&sctp_ifnp->refcount, 1); in sctp_add_addr_to_vrf()
498 sctp_ifap->vrf_id = vrf_id; in sctp_add_addr_to_vrf()
499 sctp_ifap->ifa = ifa; in sctp_add_addr_to_vrf()
500 memcpy(&sctp_ifap->address, addr, addr->sa_len); in sctp_add_addr_to_vrf()
501 sctp_ifap->localifa_flags = SCTP_ADDR_VALID | SCTP_ADDR_DEFER_USE; in sctp_add_addr_to_vrf()
502 sctp_ifap->flags = ifa_flags; in sctp_add_addr_to_vrf()
504 switch (sctp_ifap->address.sa.sa_family) { in sctp_add_addr_to_vrf()
510 sin = &sctp_ifap->address.sin; in sctp_add_addr_to_vrf()
511 if (SCTP_IFN_IS_IFT_LOOP(sctp_ifap->ifn_p) || in sctp_add_addr_to_vrf()
512 (IN4_ISLOOPBACK_ADDRESS(&sin->sin_addr))) { in sctp_add_addr_to_vrf()
513 sctp_ifap->src_is_loop = 1; in sctp_add_addr_to_vrf()
515 if ((IN4_ISPRIVATE_ADDRESS(&sin->sin_addr))) { in sctp_add_addr_to_vrf()
516 sctp_ifap->src_is_priv = 1; in sctp_add_addr_to_vrf()
518 sctp_ifnp->num_v4++; in sctp_add_addr_to_vrf()
520 sctp_ifnp->registered_af = AF_INET; in sctp_add_addr_to_vrf()
530 sin6 = &sctp_ifap->address.sin6; in sctp_add_addr_to_vrf()
531 if (SCTP_IFN_IS_IFT_LOOP(sctp_ifap->ifn_p) || in sctp_add_addr_to_vrf()
532 (IN6_IS_ADDR_LOOPBACK(&sin6->sin6_addr))) { in sctp_add_addr_to_vrf()
533 sctp_ifap->src_is_loop = 1; in sctp_add_addr_to_vrf()
535 if (IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr)) { in sctp_add_addr_to_vrf()
536 sctp_ifap->src_is_priv = 1; in sctp_add_addr_to_vrf()
538 sctp_ifnp->num_v6++; in sctp_add_addr_to_vrf()
540 sctp_ifnp->registered_af = AF_INET6; in sctp_add_addr_to_vrf()
547 hash_of_addr = sctp_get_ifa_hash_val(&sctp_ifap->address.sa); in sctp_add_addr_to_vrf()
549 if ((sctp_ifap->src_is_priv == 0) && in sctp_add_addr_to_vrf()
550 (sctp_ifap->src_is_loop == 0)) { in sctp_add_addr_to_vrf()
551 sctp_ifap->src_is_glob = 1; in sctp_add_addr_to_vrf()
553 hash_addr_head = &vrf->vrf_addr_hash[(hash_of_addr & vrf->vrf_addr_hashmark)]; in sctp_add_addr_to_vrf()
555 sctp_ifap->refcount = 1; in sctp_add_addr_to_vrf()
556 LIST_INSERT_HEAD(&sctp_ifnp->ifalist, sctp_ifap, next_ifa); in sctp_add_addr_to_vrf()
557 sctp_ifnp->ifa_count++; in sctp_add_addr_to_vrf()
558 vrf->total_ifa_count++; in sctp_add_addr_to_vrf()
567 * Bump up the refcount so that when the timer completes it in sctp_add_addr_to_vrf()
572 atomic_add_int(&sctp_ifap->refcount, 1); in sctp_add_addr_to_vrf()
586 (void)SCTP_GETTIME_TIMEVAL(&wi->start_time); in sctp_add_addr_to_vrf()
587 wi->ifa = sctp_ifap; in sctp_add_addr_to_vrf()
588 wi->action = SCTP_ADD_IP_ADDRESS; in sctp_add_addr_to_vrf()
599 sctp_ifap->localifa_flags &= ~SCTP_ADDR_DEFER_USE; in sctp_add_addr_to_vrf()
623 sctp_ifap = sctp_find_ifa_by_addr(addr, vrf->vrf_id, SCTP_ADDR_LOCKED); in sctp_del_addr_from_vrf()
626 if (sctp_ifap->ifn_p) { in sctp_del_addr_from_vrf()
627 if (ifn_index != sctp_ifap->ifn_p->ifn_index || in sctp_del_addr_from_vrf()
628 ifn != sctp_ifap->ifn_p->ifn_p) { in sctp_del_addr_from_vrf()
629 SCTPDBG(SCTP_DEBUG_PCB4, "ifn:%d (%p) ifname:%s - ignoring delete\n", in sctp_del_addr_from_vrf()
630 sctp_ifap->ifn_p->ifn_index, in sctp_del_addr_from_vrf()
631 sctp_ifap->ifn_p->ifn_p, in sctp_del_addr_from_vrf()
632 sctp_ifap->ifn_p->ifn_name); in sctp_del_addr_from_vrf()
638 sctp_ifap->localifa_flags &= SCTP_ADDR_VALID; in sctp_del_addr_from_vrf()
646 /* sctp_ifap->localifa_flags |= SCTP_BEING_DELETED; */ in sctp_del_addr_from_vrf()
647 vrf->total_ifa_count--; in sctp_del_addr_from_vrf()
653 SCTPDBG(SCTP_DEBUG_PCB4, "Del Addr-ifn:%d Could not find address:", in sctp_del_addr_from_vrf()
677 (void)SCTP_GETTIME_TIMEVAL(&wi->start_time); in sctp_del_addr_from_vrf()
678 wi->ifa = sctp_ifap; in sctp_del_addr_from_vrf()
679 wi->action = SCTP_DEL_IP_ADDRESS; in sctp_del_addr_from_vrf()
683 * the newest first :-0 in sctp_del_addr_from_vrf()
709 loopback_scope = stcb->asoc.scope.loopback_scope; in sctp_does_stcb_own_this_addr()
711 ipv4_local_scope = stcb->asoc.scope.ipv4_local_scope; in sctp_does_stcb_own_this_addr()
712 ipv4_addr_legal = stcb->asoc.scope.ipv4_addr_legal; in sctp_does_stcb_own_this_addr()
715 local_scope = stcb->asoc.scope.local_scope; in sctp_does_stcb_own_this_addr()
716 site_scope = stcb->asoc.scope.site_scope; in sctp_does_stcb_own_this_addr()
717 ipv6_addr_legal = stcb->asoc.scope.ipv6_addr_legal; in sctp_does_stcb_own_this_addr()
721 vrf = sctp_find_vrf(stcb->asoc.vrf_id); in sctp_does_stcb_own_this_addr()
728 if (stcb->sctp_ep->sctp_flags & SCTP_PCB_FLAGS_BOUNDALL) { in sctp_does_stcb_own_this_addr()
729 LIST_FOREACH(sctp_ifn, &vrf->ifnlist, next_ifn) { in sctp_does_stcb_own_this_addr()
734 LIST_FOREACH(sctp_ifa, &sctp_ifn->ifalist, next_ifa) { in sctp_does_stcb_own_this_addr()
739 * we have sent an asconf-add to be in sctp_does_stcb_own_this_addr()
744 if (sctp_ifa->address.sa.sa_family != to->sa_family) { in sctp_does_stcb_own_this_addr()
747 switch (sctp_ifa->address.sa.sa_family) { in sctp_does_stcb_own_this_addr()
754 sin = &sctp_ifa->address.sin; in sctp_does_stcb_own_this_addr()
757 IN4_ISPRIVATE_ADDRESS(&sin->sin_addr)) { in sctp_does_stcb_own_this_addr()
760 if (prison_check_ip4(stcb->sctp_ep->ip_inp.inp.inp_cred, in sctp_does_stcb_own_this_addr()
761 &sin->sin_addr) != 0) { in sctp_does_stcb_own_this_addr()
764 if (sin->sin_addr.s_addr == rsin->sin_addr.s_addr) { in sctp_does_stcb_own_this_addr()
777 sin6 = &sctp_ifa->address.sin6; in sctp_does_stcb_own_this_addr()
779 if (prison_check_ip6(stcb->sctp_ep->ip_inp.inp.inp_cred, in sctp_does_stcb_own_this_addr()
780 &sin6->sin6_addr) != 0) { in sctp_does_stcb_own_this_addr()
783 if (IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr)) { in sctp_does_stcb_own_this_addr()
786 if (sin6->sin6_scope_id == 0) { in sctp_does_stcb_own_this_addr()
792 (IN6_IS_ADDR_SITELOCAL(&sin6->sin6_addr))) { in sctp_does_stcb_own_this_addr()
811 LIST_FOREACH(laddr, &stcb->sctp_ep->sctp_addr_list, sctp_nxt_addr) { in sctp_does_stcb_own_this_addr()
812 if (laddr->ifa->localifa_flags & SCTP_BEING_DELETED) { in sctp_does_stcb_own_this_addr()
816 if (sctp_is_addr_restricted(stcb, laddr->ifa) && in sctp_does_stcb_own_this_addr()
817 (!sctp_is_addr_pending(stcb, laddr->ifa))) { in sctp_does_stcb_own_this_addr()
820 * sent an asconf-add to be considered in sctp_does_stcb_own_this_addr()
825 if (laddr->ifa->address.sa.sa_family != to->sa_family) { in sctp_does_stcb_own_this_addr()
828 switch (to->sa_family) { in sctp_does_stcb_own_this_addr()
834 sin = &laddr->ifa->address.sin; in sctp_does_stcb_own_this_addr()
836 if (sin->sin_addr.s_addr == rsin->sin_addr.s_addr) { in sctp_does_stcb_own_this_addr()
848 sin6 = &laddr->ifa->address.sin6; in sctp_does_stcb_own_this_addr()
888 switch (to->sa_family) { in sctp_tcb_special_locate()
891 if (from->sa_family == AF_INET) { in sctp_tcb_special_locate()
892 lport = ((struct sockaddr_in *)to)->sin_port; in sctp_tcb_special_locate()
893 rport = ((struct sockaddr_in *)from)->sin_port; in sctp_tcb_special_locate()
901 if (from->sa_family == AF_INET6) { in sctp_tcb_special_locate()
902 lport = ((struct sockaddr_in6 *)to)->sin6_port; in sctp_tcb_special_locate()
903 rport = ((struct sockaddr_in6 *)from)->sin6_port; in sctp_tcb_special_locate()
915 * - Does the remote port match. - Does there single association's in sctp_tcb_special_locate()
921 if (inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_ALLGONE) { in sctp_tcb_special_locate()
925 if (lport != inp->sctp_lport) { in sctp_tcb_special_locate()
929 switch (to->sa_family) { in sctp_tcb_special_locate()
936 if (prison_check_ip4(inp->ip_inp.inp.inp_cred, in sctp_tcb_special_locate()
937 &sin->sin_addr) != 0) { in sctp_tcb_special_locate()
950 if (prison_check_ip6(inp->ip_inp.inp.inp_cred, in sctp_tcb_special_locate()
951 &sin6->sin6_addr) != 0) { in sctp_tcb_special_locate()
962 if (inp->def_vrf_id != vrf_id) { in sctp_tcb_special_locate()
967 if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUNDALL) == 0) { in sctp_tcb_special_locate()
971 LIST_FOREACH(laddr, &inp->sctp_addr_list, sctp_nxt_addr) { in sctp_tcb_special_locate()
972 if (laddr->ifa == NULL) { in sctp_tcb_special_locate()
976 if (laddr->ifa->localifa_flags & SCTP_BEING_DELETED) { in sctp_tcb_special_locate()
980 if (laddr->ifa->address.sa.sa_family == in sctp_tcb_special_locate()
981 to->sa_family) { in sctp_tcb_special_locate()
984 if (from->sa_family == AF_INET) { in sctp_tcb_special_locate()
988 intf_addr = &laddr->ifa->address.sin; in sctp_tcb_special_locate()
990 if (sin->sin_addr.s_addr == in sctp_tcb_special_locate()
991 intf_addr->sin_addr.s_addr) { in sctp_tcb_special_locate()
998 if (from->sa_family == AF_INET6) { in sctp_tcb_special_locate()
1004 intf_addr6 = &laddr->ifa->address.sin6; in sctp_tcb_special_locate()
1026 stcb = LIST_FIRST(&inp->sctp_asoc_list); in sctp_tcb_special_locate()
1037 if (stcb->rport != rport) { in sctp_tcb_special_locate()
1043 if (stcb->asoc.state & SCTP_STATE_ABOUT_TO_BE_FREED) { in sctp_tcb_special_locate()
1054 TAILQ_FOREACH(net, &stcb->asoc.nets, sctp_next) { in sctp_tcb_special_locate()
1055 if (net->ro._l_addr.sa.sa_family != from->sa_family) { in sctp_tcb_special_locate()
1059 switch (from->sa_family) { in sctp_tcb_special_locate()
1065 sin = (struct sockaddr_in *)&net->ro._l_addr; in sctp_tcb_special_locate()
1067 if (sin->sin_addr.s_addr == in sctp_tcb_special_locate()
1068 rsin->sin_addr.s_addr) { in sctp_tcb_special_locate()
1089 sin6 = (struct sockaddr_in6 *)&net->ro._l_addr; in sctp_tcb_special_locate()
1139 switch (remote->sa_family) { in sctp_findassociation_ep_addr()
1142 rport = (((struct sockaddr_in *)remote)->sin_port); in sctp_findassociation_ep_addr()
1147 rport = (((struct sockaddr_in6 *)remote)->sin6_port); in sctp_findassociation_ep_addr()
1155 * UN-lock so we can do proper locking here this occurs when in sctp_findassociation_ep_addr()
1158 atomic_add_int(&locked_tcb->asoc.refcnt, 1); in sctp_findassociation_ep_addr()
1162 if ((inp->sctp_flags & SCTP_PCB_FLAGS_TCPTYPE) || in sctp_findassociation_ep_addr()
1163 (inp->sctp_flags & SCTP_PCB_FLAGS_IN_TCPPOOL)) { in sctp_findassociation_ep_addr()
1164 /*- in sctp_findassociation_ep_addr()
1171 if ((inp->sctp_socket) && SCTP_IS_LISTENING(inp)) { in sctp_findassociation_ep_addr()
1174 netp, inp->def_vrf_id); in sctp_findassociation_ep_addr()
1180 SCTP_INP_RLOCK(locked_tcb->sctp_ep); in sctp_findassociation_ep_addr()
1182 atomic_subtract_int(&locked_tcb->asoc.refcnt, 1); in sctp_findassociation_ep_addr()
1183 SCTP_INP_RUNLOCK(locked_tcb->sctp_ep); in sctp_findassociation_ep_addr()
1189 if (inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_ALLGONE) { in sctp_findassociation_ep_addr()
1192 stcb = LIST_FIRST(&inp->sctp_asoc_list); in sctp_findassociation_ep_addr()
1198 if (stcb->rport != rport) { in sctp_findassociation_ep_addr()
1203 if (stcb->asoc.state & SCTP_STATE_ABOUT_TO_BE_FREED) { in sctp_findassociation_ep_addr()
1212 TAILQ_FOREACH(net, &stcb->asoc.nets, sctp_next) { in sctp_findassociation_ep_addr()
1218 if (net->ro._l_addr.sa.sa_family != in sctp_findassociation_ep_addr()
1219 remote->sa_family) { in sctp_findassociation_ep_addr()
1223 switch (remote->sa_family) { in sctp_findassociation_ep_addr()
1231 &net->ro._l_addr; in sctp_findassociation_ep_addr()
1233 if (sin->sin_addr.s_addr == in sctp_findassociation_ep_addr()
1234 rsin->sin_addr.s_addr) { in sctp_findassociation_ep_addr()
1245 atomic_subtract_int(&locked_tcb->asoc.refcnt, 1); in sctp_findassociation_ep_addr()
1261 sin6 = (struct sockaddr_in6 *)&net->ro._l_addr; in sctp_findassociation_ep_addr()
1275 atomic_subtract_int(&locked_tcb->asoc.refcnt, 1); in sctp_findassociation_ep_addr()
1293 if (inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_ALLGONE) { in sctp_findassociation_ep_addr()
1296 head = &inp->sctp_tcbhash[SCTP_PCBHASH_ALLADDR(rport, in sctp_findassociation_ep_addr()
1297 inp->sctp_hashmark)]; in sctp_findassociation_ep_addr()
1299 if (stcb->rport != rport) { in sctp_findassociation_ep_addr()
1304 if (stcb->asoc.state & SCTP_STATE_ABOUT_TO_BE_FREED) { in sctp_findassociation_ep_addr()
1313 TAILQ_FOREACH(net, &stcb->asoc.nets, sctp_next) { in sctp_findassociation_ep_addr()
1319 if (net->ro._l_addr.sa.sa_family != in sctp_findassociation_ep_addr()
1320 remote->sa_family) { in sctp_findassociation_ep_addr()
1324 switch (remote->sa_family) { in sctp_findassociation_ep_addr()
1332 &net->ro._l_addr; in sctp_findassociation_ep_addr()
1334 if (sin->sin_addr.s_addr == in sctp_findassociation_ep_addr()
1335 rsin->sin_addr.s_addr) { in sctp_findassociation_ep_addr()
1346 atomic_subtract_int(&locked_tcb->asoc.refcnt, 1); in sctp_findassociation_ep_addr()
1362 &net->ro._l_addr; in sctp_findassociation_ep_addr()
1376 atomic_subtract_int(&locked_tcb->asoc.refcnt, 1); in sctp_findassociation_ep_addr()
1397 atomic_subtract_int(&locked_tcb->asoc.refcnt, 1); in sctp_findassociation_ep_addr()
1419 if (inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_ALLGONE) { in sctp_findasoc_ep_asocid_locked()
1424 head = &inp->sctp_asocidhash[SCTP_PCBHASH_ASOC(id, inp->hashasocidmark)]; in sctp_findasoc_ep_asocid_locked()
1431 if (stcb->asoc.assoc_id == id) { in sctp_findasoc_ep_asocid_locked()
1432 if (inp != stcb->sctp_ep) { in sctp_findasoc_ep_asocid_locked()
1440 if (stcb->asoc.state & SCTP_STATE_ABOUT_TO_BE_FREED) { in sctp_findasoc_ep_asocid_locked()
1487 switch (nam->sa_family) { in sctp_endpoint_probe()
1508 if (inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_ALLGONE) { in sctp_endpoint_probe()
1512 if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUNDALL) && in sctp_endpoint_probe()
1513 (inp->sctp_lport == lport)) { in sctp_endpoint_probe()
1515 switch (nam->sa_family) { in sctp_endpoint_probe()
1518 if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) && in sctp_endpoint_probe()
1527 if (prison_check_ip4(inp->ip_inp.inp.inp_cred, in sctp_endpoint_probe()
1528 &sin->sin_addr) != 0) { in sctp_endpoint_probe()
1540 if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) == 0) { in sctp_endpoint_probe()
1544 if (prison_check_ip6(inp->ip_inp.inp.inp_cred, in sctp_endpoint_probe()
1545 &sin6->sin6_addr) != 0) { in sctp_endpoint_probe()
1556 if (inp->def_vrf_id == vrf_id) in sctp_endpoint_probe()
1566 switch (nam->sa_family) { in sctp_endpoint_probe()
1569 if (sin->sin_addr.s_addr == INADDR_ANY) { in sctp_endpoint_probe()
1577 if (IN6_IS_ADDR_UNSPECIFIED(&sin6->sin6_addr)) { in sctp_endpoint_probe()
1592 if (inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_ALLGONE) { in sctp_endpoint_probe()
1596 if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUNDALL)) { in sctp_endpoint_probe()
1604 if (inp->sctp_lport != lport) { in sctp_endpoint_probe()
1610 if (inp->def_vrf_id == vrf_id) in sctp_endpoint_probe()
1617 LIST_FOREACH(laddr, &inp->sctp_addr_list, sctp_nxt_addr) { in sctp_endpoint_probe()
1618 if (laddr->ifa == NULL) { in sctp_endpoint_probe()
1623 SCTPDBG(SCTP_DEBUG_PCB1, "Ok laddr->ifa:%p is possible, ", in sctp_endpoint_probe()
1624 (void *)laddr->ifa); in sctp_endpoint_probe()
1625 if (laddr->ifa->localifa_flags & SCTP_BEING_DELETED) { in sctp_endpoint_probe()
1629 if (laddr->ifa->address.sa.sa_family == nam->sa_family) { in sctp_endpoint_probe()
1631 switch (nam->sa_family) { in sctp_endpoint_probe()
1634 if (sin->sin_addr.s_addr == in sctp_endpoint_probe()
1635 laddr->ifa->address.sin.sin_addr.s_addr) { in sctp_endpoint_probe()
1643 intf_addr6 = &laddr->ifa->address.sin6; in sctp_endpoint_probe()
1669 if (t_inp->sctp_lport != lport) { in sctp_isport_inuse()
1674 if (t_inp->def_vrf_id == vrf_id) in sctp_isport_inuse()
1681 if ((t_inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) && in sctp_isport_inuse()
1683 if (inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) { in sctp_isport_inuse()
1690 } else if (t_inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) { in sctp_isport_inuse()
1695 if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) && in sctp_isport_inuse()
1710 /* For 1-2-1 with port reuse */ in sctp_swap_inpcb_for_listen()
1719 return (-1); in sctp_swap_inpcb_for_listen()
1721 if ((inp->sctp_flags & SCTP_PCB_FLAGS_IN_TCPPOOL) == 0) { in sctp_swap_inpcb_for_listen()
1725 head = &SCTP_BASE_INFO(sctp_ephash)[SCTP_PCBHASH_ALLADDR(inp->sctp_lport, in sctp_swap_inpcb_for_listen()
1727 /* Kick out all non-listeners to the TCP hash */ in sctp_swap_inpcb_for_listen()
1729 if (tinp->sctp_lport != inp->sctp_lport) { in sctp_swap_inpcb_for_listen()
1732 if (tinp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_ALLGONE) { in sctp_swap_inpcb_for_listen()
1735 if (tinp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_GONE) { in sctp_swap_inpcb_for_listen()
1743 …head = &SCTP_BASE_INFO(sctp_tcpephash)[SCTP_PCBHASH_ALLADDR(tinp->sctp_lport, SCTP_BASE_INFO(hasht… in sctp_swap_inpcb_for_listen()
1744 tinp->sctp_flags |= SCTP_PCB_FLAGS_IN_TCPPOOL; in sctp_swap_inpcb_for_listen()
1751 inp->sctp_flags &= ~SCTP_PCB_FLAGS_IN_TCPPOOL; in sctp_swap_inpcb_for_listen()
1752 …head = &SCTP_BASE_INFO(sctp_ephash)[SCTP_PCBHASH_ALLADDR(inp->sctp_lport, SCTP_BASE_INFO(hashmark)… in sctp_swap_inpcb_for_listen()
1776 switch (nam->sa_family) { in sctp_pcb_findep()
1780 lport = sin->sin_port; in sctp_pcb_findep()
1786 lport = sin6->sin6_port; in sctp_pcb_findep()
1885 * This routine will grub through the mbuf that is a INIT or INIT-ACK and
1911 sin4.sin_port = sh->src_port; in sctp_findassociation_special_addr()
1917 sin6.sin6_port = sh->src_port; in sctp_findassociation_special_addr()
1926 ptype = ntohs(phdr->param_type); in sctp_findassociation_special_addr()
1928 plen = ntohs(phdr->param_length); in sctp_findassociation_special_addr()
1944 memcpy(&sin4.sin_addr, &p4->addr, sizeof(p4->addr)); in sctp_findassociation_special_addr()
1965 memcpy(&sin6.sin6_addr, &p6->addr, sizeof(p6->addr)); in sctp_findassociation_special_addr()
1999 SCTP_INP_RLOCK(stcb->sctp_ep); in sctp_findassoc_by_vtag()
2000 if (stcb->sctp_ep->sctp_flags & SCTP_PCB_FLAGS_SOCKET_ALLGONE) { in sctp_findassoc_by_vtag()
2001 SCTP_INP_RUNLOCK(stcb->sctp_ep); in sctp_findassoc_by_vtag()
2004 if (stcb->sctp_ep->def_vrf_id != vrf_id) { in sctp_findassoc_by_vtag()
2005 SCTP_INP_RUNLOCK(stcb->sctp_ep); in sctp_findassoc_by_vtag()
2009 SCTP_INP_RUNLOCK(stcb->sctp_ep); in sctp_findassoc_by_vtag()
2010 if (stcb->asoc.my_vtag == vtag) { in sctp_findassoc_by_vtag()
2012 if (stcb->rport != rport) { in sctp_findassoc_by_vtag()
2016 if (stcb->sctp_ep->sctp_lport != lport) { in sctp_findassoc_by_vtag()
2020 if (stcb->asoc.state & SCTP_STATE_ABOUT_TO_BE_FREED) { in sctp_findassoc_by_vtag()
2035 if (stcb->asoc.peer_vtag == remote_tag) { in sctp_findassoc_by_vtag()
2052 *inp_p = stcb->sctp_ep; in sctp_findassoc_by_vtag()
2061 *inp_p = stcb->sctp_ep; in sctp_findassoc_by_vtag()
2091 if (sh->v_tag) { in sctp_findassociation_addr()
2092 /* we only go down this path if vtag is non-zero */ in sctp_findassociation_addr()
2093 stcb = sctp_findassoc_by_vtag(src, dst, ntohl(sh->v_tag), in sctp_findassociation_addr()
2094 inp_p, netp, sh->src_port, sh->dest_port, 0, vrf_id, 0); in sctp_findassociation_addr()
2111 if ((ch->chunk_type == SCTP_INITIATION) || in sctp_findassociation_addr()
2112 (ch->chunk_type == SCTP_INITIATION_ACK)) { in sctp_findassociation_addr()
2113 /*- in sctp_findassociation_addr()
2121 if (inp->sctp_flags & SCTP_PCB_FLAGS_IN_TCPPOOL) { in sctp_findassociation_addr()
2167 ptype = (int)((uint32_t)ntohs(phdr->param_type)); in sctp_findassociation_ep_asconf()
2176 if (ntohs(phdr->param_length) != sizeof(struct sctp_ipv6addr_param)) { in sctp_findassociation_ep_asconf()
2188 sin6->sin6_family = AF_INET6; in sctp_findassociation_ep_asconf()
2189 sin6->sin6_len = sizeof(*sin6); in sctp_findassociation_ep_asconf()
2190 sin6->sin6_port = sh->src_port; in sctp_findassociation_ep_asconf()
2191 memcpy(&sin6->sin6_addr, &p6->addr, sizeof(struct in6_addr)); in sctp_findassociation_ep_asconf()
2192 if (IN6_IS_ADDR_UNSPECIFIED(&sin6->sin6_addr)) in sctp_findassociation_ep_asconf()
2203 if (ntohs(phdr->param_length) != sizeof(struct sctp_ipv4addr_param)) { in sctp_findassociation_ep_asconf()
2215 sin->sin_family = AF_INET; in sctp_findassociation_ep_asconf()
2216 sin->sin_len = sizeof(*sin); in sctp_findassociation_ep_asconf()
2217 sin->sin_port = sh->src_port; in sctp_findassociation_ep_asconf()
2218 memcpy(&sin->sin_addr, &p4->addr, sizeof(struct in_addr)); in sctp_findassociation_ep_asconf()
2219 if (sin->sin_addr.s_addr == INADDR_ANY) in sctp_findassociation_ep_asconf()
2230 stcb = sctp_findassoc_by_vtag(NULL, dst, ntohl(sh->v_tag), inp_p, in sctp_findassociation_ep_asconf()
2231 netp, sh->src_port, sh->dest_port, 1, vrf_id, 0); in sctp_findassociation_ep_asconf()
2270 SCTP_PRINTF("Out of SCTP-INPCB structures - no resources\n"); in sctp_inpcb_alloc()
2280 inp->sctp_socket = so; in sctp_inpcb_alloc()
2281 inp->ip_inp.inp.inp_socket = so; in sctp_inpcb_alloc()
2282 inp->ip_inp.inp.inp_cred = crhold(so->so_cred); in sctp_inpcb_alloc()
2286 inp->ip_inp.inp.inp_flags |= IN6P_AUTOFLOWLABEL; in sctp_inpcb_alloc()
2289 inp->ip_inp.inp.inp_flags |= IN6P_IPV6_V6ONLY; in sctp_inpcb_alloc()
2293 inp->sctp_associd_counter = 1; in sctp_inpcb_alloc()
2294 inp->partial_delivery_point = SCTP_SB_LIMIT_RCV(so) >> SCTP_PARTIAL_DELIVERY_SHIFT; in sctp_inpcb_alloc()
2295 inp->sctp_frag_point = 0; in sctp_inpcb_alloc()
2296 inp->max_cwnd = 0; in sctp_inpcb_alloc()
2297 inp->sctp_cmt_on_off = SCTP_BASE_SYSCTL(sctp_cmt_on_off); in sctp_inpcb_alloc()
2298 inp->ecn_supported = (uint8_t)SCTP_BASE_SYSCTL(sctp_ecn_enable); in sctp_inpcb_alloc()
2299 inp->prsctp_supported = (uint8_t)SCTP_BASE_SYSCTL(sctp_pr_enable); in sctp_inpcb_alloc()
2300 inp->auth_supported = (uint8_t)SCTP_BASE_SYSCTL(sctp_auth_enable); in sctp_inpcb_alloc()
2301 inp->asconf_supported = (uint8_t)SCTP_BASE_SYSCTL(sctp_asconf_enable); in sctp_inpcb_alloc()
2302 inp->reconfig_supported = (uint8_t)SCTP_BASE_SYSCTL(sctp_reconfig_enable); in sctp_inpcb_alloc()
2303 inp->nrsack_supported = (uint8_t)SCTP_BASE_SYSCTL(sctp_nrsack_enable); in sctp_inpcb_alloc()
2304 inp->pktdrop_supported = (uint8_t)SCTP_BASE_SYSCTL(sctp_pktdrop_enable); in sctp_inpcb_alloc()
2305 inp->idata_supported = 0; in sctp_inpcb_alloc()
2306 inp->rcv_edmid = SCTP_EDMID_NONE; in sctp_inpcb_alloc()
2308 inp->fibnum = so->so_fibnum; in sctp_inpcb_alloc()
2309 /* init the small hash table we use to track asocid <-> tcb */ in sctp_inpcb_alloc()
2310 inp->sctp_asocidhash = SCTP_HASH_INIT(SCTP_STACK_VTAG_HASH_SIZE, &inp->hashasocidmark); in sctp_inpcb_alloc()
2311 if (inp->sctp_asocidhash == NULL) { in sctp_inpcb_alloc()
2312 crfree(inp->ip_inp.inp.inp_cred); in sctp_inpcb_alloc()
2318 inp->ip_inp.inp.inp_ip_ttl = MODULE_GLOBAL(ip_defttl); in sctp_inpcb_alloc()
2321 so->so_pcb = (caddr_t)inp; in sctp_inpcb_alloc()
2325 inp->sctp_flags = (SCTP_PCB_FLAGS_UDPTYPE | in sctp_inpcb_alloc()
2327 /* Be sure it is NON-BLOCKING IO for UDP */ in sctp_inpcb_alloc()
2331 inp->sctp_flags = (SCTP_PCB_FLAGS_TCPTYPE | in sctp_inpcb_alloc()
2339 * unsupported socket type (RAW, etc)- in case we missed it in sctp_inpcb_alloc()
2343 so->so_pcb = NULL; in sctp_inpcb_alloc()
2344 crfree(inp->ip_inp.inp.inp_cred); in sctp_inpcb_alloc()
2358 inp->sctp_tcbhash = SCTP_HASH_INIT(SCTP_BASE_SYSCTL(sctp_pcbtblsize), in sctp_inpcb_alloc()
2359 &inp->sctp_hashmark); in sctp_inpcb_alloc()
2360 if (inp->sctp_tcbhash == NULL) { in sctp_inpcb_alloc()
2361 SCTP_PRINTF("Out of SCTP-INPCB->hashinit - no resources\n"); in sctp_inpcb_alloc()
2363 so->so_pcb = NULL; in sctp_inpcb_alloc()
2364 crfree(inp->ip_inp.inp.inp_cred); in sctp_inpcb_alloc()
2368 inp->def_vrf_id = vrf_id; in sctp_inpcb_alloc()
2372 rw_init_flags(&inp->ip_inp.inp.inp_lock, "sctpinp", in sctp_inpcb_alloc()
2383 TAILQ_INIT(&inp->read_queue); in sctp_inpcb_alloc()
2384 LIST_INIT(&inp->sctp_addr_list); in sctp_inpcb_alloc()
2386 LIST_INIT(&inp->sctp_asoc_list); in sctp_inpcb_alloc()
2390 LIST_INIT(&inp->sctp_asoc_free_list); in sctp_inpcb_alloc()
2392 /* Init the timer structure for signature change */ in sctp_inpcb_alloc()
2393 SCTP_OS_TIMER_INIT(&inp->sctp_ep.signature_change.timer); in sctp_inpcb_alloc()
2394 inp->sctp_ep.signature_change.type = SCTP_TIMER_TYPE_NEWCOOKIE; in sctp_inpcb_alloc()
2397 m = &inp->sctp_ep; in sctp_inpcb_alloc()
2400 m->sctp_timeoutticks[SCTP_TIMER_SEND] = sctp_secs_to_ticks(SCTP_SEND_SEC); /* needed ? */ in sctp_inpcb_alloc()
2401 m->sctp_timeoutticks[SCTP_TIMER_INIT] = sctp_secs_to_ticks(SCTP_INIT_SEC); /* needed ? */ in sctp_inpcb_alloc()
2402 …m->sctp_timeoutticks[SCTP_TIMER_RECV] = sctp_msecs_to_ticks(SCTP_BASE_SYSCTL(sctp_delayed_sack_tim… in sctp_inpcb_alloc()
2403 …m->sctp_timeoutticks[SCTP_TIMER_HEARTBEAT] = sctp_msecs_to_ticks(SCTP_BASE_SYSCTL(sctp_heartbeat_i… in sctp_inpcb_alloc()
2404 …m->sctp_timeoutticks[SCTP_TIMER_PMTU] = sctp_secs_to_ticks(SCTP_BASE_SYSCTL(sctp_pmtu_raise_time_d… in sctp_inpcb_alloc()
2405 …m->sctp_timeoutticks[SCTP_TIMER_MAXSHUTDOWN] = sctp_secs_to_ticks(SCTP_BASE_SYSCTL(sctp_shutdown_g… in sctp_inpcb_alloc()
2406 …m->sctp_timeoutticks[SCTP_TIMER_SIGNATURE] = sctp_secs_to_ticks(SCTP_BASE_SYSCTL(sctp_secret_lifet… in sctp_inpcb_alloc()
2408 m->sctp_maxrto = SCTP_BASE_SYSCTL(sctp_rto_max_default); in sctp_inpcb_alloc()
2409 m->sctp_minrto = SCTP_BASE_SYSCTL(sctp_rto_min_default); in sctp_inpcb_alloc()
2410 m->initial_rto = SCTP_BASE_SYSCTL(sctp_rto_initial_default); in sctp_inpcb_alloc()
2411 m->initial_init_rto_max = SCTP_BASE_SYSCTL(sctp_init_rto_max_default); in sctp_inpcb_alloc()
2412 m->sctp_sack_freq = SCTP_BASE_SYSCTL(sctp_sack_freq_default); in sctp_inpcb_alloc()
2413 m->max_init_times = SCTP_BASE_SYSCTL(sctp_init_rtx_max_default); in sctp_inpcb_alloc()
2414 m->max_send_times = SCTP_BASE_SYSCTL(sctp_assoc_rtx_max_default); in sctp_inpcb_alloc()
2415 m->def_net_failure = SCTP_BASE_SYSCTL(sctp_path_rtx_max_default); in sctp_inpcb_alloc()
2416 m->def_net_pf_threshold = SCTP_BASE_SYSCTL(sctp_path_pf_threshold); in sctp_inpcb_alloc()
2417 m->sctp_sws_sender = SCTP_SWS_SENDER_DEF; in sctp_inpcb_alloc()
2418 m->sctp_sws_receiver = SCTP_SWS_RECEIVER_DEF; in sctp_inpcb_alloc()
2419 m->max_burst = SCTP_BASE_SYSCTL(sctp_max_burst_default); in sctp_inpcb_alloc()
2420 m->fr_max_burst = SCTP_BASE_SYSCTL(sctp_fr_max_burst_default); in sctp_inpcb_alloc()
2422 m->sctp_default_cc_module = SCTP_BASE_SYSCTL(sctp_default_cc_module); in sctp_inpcb_alloc()
2423 m->sctp_default_ss_module = SCTP_BASE_SYSCTL(sctp_default_ss_module); in sctp_inpcb_alloc()
2424 m->max_open_streams_intome = SCTP_BASE_SYSCTL(sctp_nr_incoming_streams_default); in sctp_inpcb_alloc()
2425 /* number of streams to pre-open on a association */ in sctp_inpcb_alloc()
2426 m->pre_open_stream_count = SCTP_BASE_SYSCTL(sctp_nr_outgoing_streams_default); in sctp_inpcb_alloc()
2428 m->default_mtu = 0; in sctp_inpcb_alloc()
2430 m->adaptation_layer_indicator = 0; in sctp_inpcb_alloc()
2431 m->adaptation_layer_indicator_provided = 0; in sctp_inpcb_alloc()
2434 m->random_counter = 1; in sctp_inpcb_alloc()
2435 m->store_at = SCTP_SIGNATURE_SIZE; in sctp_inpcb_alloc()
2436 SCTP_READ_RANDOM(m->random_numbers, sizeof(m->random_numbers)); in sctp_inpcb_alloc()
2440 m->size_of_a_cookie = (sizeof(struct sctp_init_msg) * 2) + in sctp_inpcb_alloc()
2442 m->size_of_a_cookie += SCTP_SIGNATURE_SIZE; in sctp_inpcb_alloc()
2446 m->time_of_secret_change = time.tv_sec; in sctp_inpcb_alloc()
2449 m->secret_key[0][i] = sctp_select_initial_TSN(m); in sctp_inpcb_alloc()
2454 m->def_cookie_life = sctp_msecs_to_ticks(SCTP_BASE_SYSCTL(sctp_valid_cookie_life_default)); in sctp_inpcb_alloc()
2458 m->local_hmacs = sctp_default_supported_hmaclist(); in sctp_inpcb_alloc()
2459 m->local_auth_chunks = sctp_alloc_chunklist(); in sctp_inpcb_alloc()
2460 if (inp->asconf_supported) { in sctp_inpcb_alloc()
2461 sctp_auth_add_chunk(SCTP_ASCONF, m->local_auth_chunks); in sctp_inpcb_alloc()
2462 sctp_auth_add_chunk(SCTP_ASCONF_ACK, m->local_auth_chunks); in sctp_inpcb_alloc()
2464 m->default_dscp = 0; in sctp_inpcb_alloc()
2466 m->default_flowlabel = 0; in sctp_inpcb_alloc()
2468 m->port = 0; /* encapsulation disabled by default */ in sctp_inpcb_alloc()
2469 LIST_INIT(&m->shared_keys); in sctp_inpcb_alloc()
2472 sctp_insert_sharedkey(&m->shared_keys, null_key); in sctp_inpcb_alloc()
2489 atomic_add_int(&stcb->asoc.refcnt, 1); in sctp_move_pcb_and_assoc()
2495 atomic_subtract_int(&stcb->asoc.refcnt, 1); in sctp_move_pcb_and_assoc()
2498 if (old_inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) { in sctp_move_pcb_and_assoc()
2499 new_inp->ip_inp.inp.inp_flags |= old_inp->ip_inp.inp.inp_flags & INP_CONTROLOPTS; in sctp_move_pcb_and_assoc()
2500 if (old_inp->ip_inp.inp.in6p_outputopts) { in sctp_move_pcb_and_assoc()
2501 …new_inp->ip_inp.inp.in6p_outputopts = ip6_copypktopts(old_inp->ip_inp.inp.in6p_outputopts, M_NOWAI… in sctp_move_pcb_and_assoc()
2510 new_inp->ip_inp.inp.inp_ip_tos = old_inp->ip_inp.inp.inp_ip_tos; in sctp_move_pcb_and_assoc()
2511 new_inp->ip_inp.inp.inp_ip_ttl = old_inp->ip_inp.inp.inp_ip_ttl; in sctp_move_pcb_and_assoc()
2514 new_inp->sctp_ep.time_of_secret_change = in sctp_move_pcb_and_assoc()
2515 old_inp->sctp_ep.time_of_secret_change; in sctp_move_pcb_and_assoc()
2516 memcpy(new_inp->sctp_ep.secret_key, old_inp->sctp_ep.secret_key, in sctp_move_pcb_and_assoc()
2517 sizeof(old_inp->sctp_ep.secret_key)); in sctp_move_pcb_and_assoc()
2518 new_inp->sctp_ep.current_secret_number = in sctp_move_pcb_and_assoc()
2519 old_inp->sctp_ep.current_secret_number; in sctp_move_pcb_and_assoc()
2520 new_inp->sctp_ep.last_secret_number = in sctp_move_pcb_and_assoc()
2521 old_inp->sctp_ep.last_secret_number; in sctp_move_pcb_and_assoc()
2522 new_inp->sctp_ep.size_of_a_cookie = old_inp->sctp_ep.size_of_a_cookie; in sctp_move_pcb_and_assoc()
2525 stcb->sctp_socket = new_inp->sctp_socket; in sctp_move_pcb_and_assoc()
2526 stcb->sctp_ep = new_inp; in sctp_move_pcb_and_assoc()
2529 lport = new_inp->sctp_lport = old_inp->sctp_lport; in sctp_move_pcb_and_assoc()
2530 rport = stcb->rport; in sctp_move_pcb_and_assoc()
2534 if (stcb->asoc.in_asocid_hash) { in sctp_move_pcb_and_assoc()
2542 new_inp->sctp_flags &= ~SCTP_PCB_FLAGS_UNBOUND; in sctp_move_pcb_and_assoc()
2545 LIST_INSERT_HEAD(&new_inp->sctp_asoc_list, stcb, sctp_tcblist); in sctp_move_pcb_and_assoc()
2547 * Question, do we even need to worry about the ep-hash since we in sctp_move_pcb_and_assoc()
2551 if (stcb->asoc.in_asocid_hash) { in sctp_move_pcb_and_assoc()
2554 lhd = &new_inp->sctp_asocidhash[SCTP_PCBHASH_ASOC(stcb->asoc.assoc_id, in sctp_move_pcb_and_assoc()
2555 new_inp->hashasocidmark)]; in sctp_move_pcb_and_assoc()
2558 /* Ok. Let's restart timer. */ in sctp_move_pcb_and_assoc()
2559 TAILQ_FOREACH(net, &stcb->asoc.nets, sctp_next) { in sctp_move_pcb_and_assoc()
2565 if (new_inp->sctp_tcbhash != NULL) { in sctp_move_pcb_and_assoc()
2566 SCTP_HASH_FREE(new_inp->sctp_tcbhash, new_inp->sctp_hashmark); in sctp_move_pcb_and_assoc()
2567 new_inp->sctp_tcbhash = NULL; in sctp_move_pcb_and_assoc()
2569 if ((new_inp->sctp_flags & SCTP_PCB_FLAGS_BOUNDALL) == 0) { in sctp_move_pcb_and_assoc()
2571 LIST_FOREACH(oladdr, &old_inp->sctp_addr_list, sctp_nxt_addr) { in sctp_move_pcb_and_assoc()
2584 (void)SCTP_GETTIME_TIMEVAL(&laddr->start_time); in sctp_move_pcb_and_assoc()
2585 laddr->ifa = oladdr->ifa; in sctp_move_pcb_and_assoc()
2586 atomic_add_int(&laddr->ifa->refcount, 1); in sctp_move_pcb_and_assoc()
2587 LIST_INSERT_HEAD(&new_inp->sctp_addr_list, laddr, in sctp_move_pcb_and_assoc()
2589 new_inp->laddr_count++; in sctp_move_pcb_and_assoc()
2590 if (oladdr == stcb->asoc.last_used_address) { in sctp_move_pcb_and_assoc()
2591 stcb->asoc.last_used_address = laddr; in sctp_move_pcb_and_assoc()
2596 if (stcb->asoc.dack_timer.ep == old_inp) { in sctp_move_pcb_and_assoc()
2598 stcb->asoc.dack_timer.ep = new_inp; in sctp_move_pcb_and_assoc()
2601 if (stcb->asoc.asconf_timer.ep == old_inp) { in sctp_move_pcb_and_assoc()
2603 stcb->asoc.asconf_timer.ep = new_inp; in sctp_move_pcb_and_assoc()
2606 if (stcb->asoc.strreset_timer.ep == old_inp) { in sctp_move_pcb_and_assoc()
2608 stcb->asoc.strreset_timer.ep = new_inp; in sctp_move_pcb_and_assoc()
2611 if (stcb->asoc.shut_guard_timer.ep == old_inp) { in sctp_move_pcb_and_assoc()
2613 stcb->asoc.shut_guard_timer.ep = new_inp; in sctp_move_pcb_and_assoc()
2616 if (stcb->asoc.autoclose_timer.ep == old_inp) { in sctp_move_pcb_and_assoc()
2618 stcb->asoc.autoclose_timer.ep = new_inp; in sctp_move_pcb_and_assoc()
2621 if (stcb->asoc.delete_prim_timer.ep == old_inp) { in sctp_move_pcb_and_assoc()
2623 stcb->asoc.delete_prim_timer.ep = new_inp; in sctp_move_pcb_and_assoc()
2627 TAILQ_FOREACH(net, &stcb->asoc.nets, sctp_next) { in sctp_move_pcb_and_assoc()
2628 if (net->pmtu_timer.ep == old_inp) { in sctp_move_pcb_and_assoc()
2630 net->pmtu_timer.ep = new_inp; in sctp_move_pcb_and_assoc()
2633 if (net->hb_timer.ep == old_inp) { in sctp_move_pcb_and_assoc()
2635 net->hb_timer.ep = new_inp; in sctp_move_pcb_and_assoc()
2638 if (net->rxt_timer.ep == old_inp) { in sctp_move_pcb_and_assoc()
2640 net->rxt_timer.ep = new_inp; in sctp_move_pcb_and_assoc()
2664 (void)SCTP_GETTIME_TIMEVAL(&laddr->start_time); in sctp_insert_laddr()
2665 laddr->ifa = ifa; in sctp_insert_laddr()
2666 laddr->action = act; in sctp_insert_laddr()
2667 atomic_add_int(&ifa->refcount, 1); in sctp_insert_laddr()
2683 sctp_free_ifa(laddr->ifa); in sctp_remove_laddr()
2690 * socket address is specified, the PCB lock may be dropped and re-acquired.
2713 ip_inp = &inp->ip_inp.inp; in sctp_inpcb_bind_locked()
2721 ntohs(((struct sockaddr_in *)addr)->sin_port)); in sctp_inpcb_bind_locked()
2726 if ((inp->sctp_flags & SCTP_PCB_FLAGS_UNBOUND) == 0) { in sctp_inpcb_bind_locked()
2733 switch (addr->sa_family) { in sctp_inpcb_bind_locked()
2745 if (addr->sa_len != sizeof(*sin)) { in sctp_inpcb_bind_locked()
2752 lport = sin->sin_port; in sctp_inpcb_bind_locked()
2758 if ((error = prison_local_ip4(td->td_ucred, &sin->sin_addr)) != 0) { in sctp_inpcb_bind_locked()
2762 if (sin->sin_addr.s_addr != INADDR_ANY) { in sctp_inpcb_bind_locked()
2778 if (addr->sa_len != sizeof(*sin6)) { in sctp_inpcb_bind_locked()
2783 lport = sin6->sin6_port; in sctp_inpcb_bind_locked()
2789 if ((error = prison_local_ip6(td->td_ucred, &sin6->sin6_addr, in sctp_inpcb_bind_locked()
2794 if (!IN6_IS_ADDR_UNSPECIFIED(&sin6->sin6_addr)) { in sctp_inpcb_bind_locked()
2804 sin6->sin6_scope_id = 0; in sctp_inpcb_bind_locked()
2814 /* Setup a vrf_id to be the default for the non-bind-all case. */ in sctp_inpcb_bind_locked()
2815 vrf_id = inp->def_vrf_id; in sctp_inpcb_bind_locked()
2830 vrf_id = inp->def_vrf_id; in sctp_inpcb_bind_locked()
2845 * Ok, must be one-2-one and in sctp_inpcb_bind_locked()
2846 * allowing port re-use in sctp_inpcb_bind_locked()
2872 * Ok, must be one-2-one and in sctp_inpcb_bind_locked()
2873 * allowing port re-use in sctp_inpcb_bind_locked()
2907 if (ip_inp->inp_flags & INP_HIGHPORT) { in sctp_inpcb_bind_locked()
2910 } else if (ip_inp->inp_flags & INP_LOWPORT) { in sctp_inpcb_bind_locked()
2928 count = last - first + 1; /* number of candidates */ in sctp_inpcb_bind_locked()
2929 candidate = first + sctp_select_initial_TSN(&inp->sctp_ep) % (count); in sctp_inpcb_bind_locked()
2932 if (sctp_isport_inuse(inp, htons(candidate), inp->def_vrf_id) == NULL) { in sctp_inpcb_bind_locked()
2936 if (--count == 0) { in sctp_inpcb_bind_locked()
2947 if (inp->sctp_flags & (SCTP_PCB_FLAGS_SOCKET_GONE | in sctp_inpcb_bind_locked()
2950 * this really should not happen. The guy did a non-blocking in sctp_inpcb_bind_locked()
2960 inp->sctp_flags |= SCTP_PCB_FLAGS_BOUNDALL; in sctp_inpcb_bind_locked()
3011 switch (addr->sa_family) { in sctp_inpcb_bind_locked()
3049 if (addr->sa_family == AF_INET6) { in sctp_inpcb_bind_locked()
3051 if (ifa->localifa_flags & SCTP_ADDR_IFA_UNUSEABLE) { in sctp_inpcb_bind_locked()
3052 /* Can't bind a non-existent addr. */ in sctp_inpcb_bind_locked()
3060 inp->sctp_flags &= ~SCTP_PCB_FLAGS_BOUNDALL; in sctp_inpcb_bind_locked()
3067 error = sctp_insert_laddr(&inp->sctp_addr_list, ifa, 0); in sctp_inpcb_bind_locked()
3070 inp->laddr_count++; in sctp_inpcb_bind_locked()
3074 /* Put it into tcp 1-2-1 hash */ in sctp_inpcb_bind_locked()
3076 inp->sctp_flags |= SCTP_PCB_FLAGS_IN_TCPPOOL; in sctp_inpcb_bind_locked()
3082 SCTPDBG(SCTP_DEBUG_PCB1, "Main hash to bind at head:%p, bound port:%d - in tcp_pool=%d\n", in sctp_inpcb_bind_locked()
3085 inp->sctp_lport = lport; in sctp_inpcb_bind_locked()
3088 KASSERT((inp->sctp_flags & SCTP_PCB_FLAGS_UNBOUND) != 0, in sctp_inpcb_bind_locked()
3090 inp->sctp_flags &= ~SCTP_PCB_FLAGS_UNBOUND; in sctp_inpcb_bind_locked()
3102 inp = so->so_pcb; in sctp_inpcb_bind()
3121 if (it && (it->vn != curvnet)) { in sctp_iterator_inp_being_freed()
3125 if (it && (it->inp == inp)) { in sctp_iterator_inp_being_freed()
3139 if (it->iterator_flags & SCTP_ITERATOR_DO_SINGLE_INP) { in sctp_iterator_inp_being_freed()
3151 if (it->vn != curvnet) { in sctp_iterator_inp_being_freed()
3154 if (it->inp == inp) { in sctp_iterator_inp_being_freed()
3156 if (it->iterator_flags & SCTP_ITERATOR_DO_SINGLE_INP) { in sctp_iterator_inp_being_freed()
3160 if (it->function_atend != NULL) { in sctp_iterator_inp_being_freed()
3161 (*it->function_atend) (it->pointer, it->val); in sctp_iterator_inp_being_freed()
3165 it->inp = LIST_NEXT(it->inp, sctp_list); in sctp_iterator_inp_being_freed()
3166 if (it->inp) { in sctp_iterator_inp_being_freed()
3167 SCTP_INP_INCR_REF(it->inp); in sctp_iterator_inp_being_freed()
3188 * complete then any timer has to be stopped. Then start the actual in sctp_inpcb_free()
3212 so = inp->sctp_socket; in sctp_inpcb_free()
3213 KASSERT((inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_GONE) != 0, in sctp_inpcb_free()
3215 KASSERT((inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_ALLGONE) == 0, in sctp_inpcb_free()
3218 inp->sctp_flags &= ~SCTP_PCB_FLAGS_CLOSE_IP; in sctp_inpcb_free()
3220 inp->sctp_flags |= SCTP_PCB_FLAGS_DONT_WAKE; in sctp_inpcb_free()
3221 inp->sctp_flags &= ~SCTP_PCB_FLAGS_WAKEINPUT; in sctp_inpcb_free()
3222 inp->sctp_flags &= ~SCTP_PCB_FLAGS_WAKEOUTPUT; in sctp_inpcb_free()
3228 if (inp->control) { in sctp_inpcb_free()
3229 sctp_m_freem(inp->control); in sctp_inpcb_free()
3230 inp->control = NULL; in sctp_inpcb_free()
3232 if (inp->pkt) { in sctp_inpcb_free()
3233 sctp_m_freem(inp->pkt); in sctp_inpcb_free()
3234 inp->pkt = NULL; in sctp_inpcb_free()
3236 ip_pcb = &inp->ip_inp.inp; /* we could just cast the main pointer in sctp_inpcb_free()
3243 LIST_FOREACH_SAFE(stcb, &inp->sctp_asoc_list, sctp_tcblist, nstcb) { in sctp_inpcb_free()
3246 stcb->sctp_socket = NULL; in sctp_inpcb_free()
3248 if (stcb->asoc.state & SCTP_STATE_ABOUT_TO_BE_FREED) { in sctp_inpcb_free()
3251 if (stcb->asoc.state & SCTP_STATE_IN_ACCEPT_QUEUE) { in sctp_inpcb_free()
3253 * Special case - we did not start a in sctp_inpcb_free()
3254 * kill timer on the asoc due to it in sctp_inpcb_free()
3266 (stcb->asoc.total_output_queue_size == 0)) { in sctp_inpcb_free()
3280 if ((stcb->asoc.size_on_reasm_queue > 0) || in sctp_inpcb_free()
3281 (stcb->asoc.size_on_all_streams > 0) || in sctp_inpcb_free()
3282 ((so != NULL) && (SCTP_SBAVAIL(&so->so_rcv) > 0))) { in sctp_inpcb_free()
3287 stcb->sctp_ep->last_abort_code = SCTP_FROM_SCTP_PCB + SCTP_LOC_3; in sctp_inpcb_free()
3299 } else if (TAILQ_EMPTY(&stcb->asoc.send_queue) && in sctp_inpcb_free()
3300 TAILQ_EMPTY(&stcb->asoc.sent_queue) && in sctp_inpcb_free()
3301 (stcb->asoc.stream_queue_cnt == 0)) { in sctp_inpcb_free()
3302 if ((*stcb->asoc.ss_functions.sctp_ss_is_user_msgs_incomplete) (stcb, &stcb->asoc)) { in sctp_inpcb_free()
3319 if (stcb->asoc.alternate) { in sctp_inpcb_free()
3320 netp = stcb->asoc.alternate; in sctp_inpcb_free()
3322 netp = stcb->asoc.primary_destination; in sctp_inpcb_free()
3325 sctp_timer_start(SCTP_TIMER_TYPE_SHUTDOWN, stcb->sctp_ep, stcb, in sctp_inpcb_free()
3327 sctp_timer_start(SCTP_TIMER_TYPE_SHUTDOWNGUARD, stcb->sctp_ep, stcb, NULL); in sctp_inpcb_free()
3333 if ((*stcb->asoc.ss_functions.sctp_ss_is_user_msgs_incomplete) (stcb, &stcb->asoc)) { in sctp_inpcb_free()
3336 if (TAILQ_EMPTY(&stcb->asoc.send_queue) && in sctp_inpcb_free()
3337 TAILQ_EMPTY(&stcb->asoc.sent_queue) && in sctp_inpcb_free()
3338 (stcb->asoc.state & SCTP_STATE_PARTIAL_MSG_LEFT)) { in sctp_inpcb_free()
3343 stcb->sctp_ep->last_abort_code = SCTP_FROM_SCTP_PCB + SCTP_LOC_5; in sctp_inpcb_free()
3368 inp->sctp_socket = NULL; in sctp_inpcb_free()
3375 inp->sctp_socket = NULL; in sctp_inpcb_free()
3376 if ((inp->sctp_flags & SCTP_PCB_FLAGS_UNBOUND) == 0) { in sctp_inpcb_free()
3382 inp->sctp_flags |= SCTP_PCB_FLAGS_UNBOUND; in sctp_inpcb_free()
3386 * If there is a timer running to kill us, forget it, since it may in sctp_inpcb_free()
3390 LIST_FOREACH_SAFE(stcb, &inp->sctp_asoc_list, sctp_tcblist, nstcb) { in sctp_inpcb_free()
3394 stcb->sctp_socket = NULL; in sctp_inpcb_free()
3397 if (stcb->asoc.state & SCTP_STATE_ABOUT_TO_BE_FREED) { in sctp_inpcb_free()
3398 if (stcb->asoc.state & SCTP_STATE_IN_ACCEPT_QUEUE) { in sctp_inpcb_free()
3408 ((stcb->asoc.state & SCTP_STATE_ABOUT_TO_BE_FREED) == 0)) { in sctp_inpcb_free()
3412 stcb->sctp_ep->last_abort_code = SCTP_FROM_SCTP_PCB + SCTP_LOC_7; in sctp_inpcb_free()
3415 } else if (stcb->asoc.state & SCTP_STATE_ABOUT_TO_BE_FREED) { in sctp_inpcb_free()
3446 if ((inp->refcount) || in sctp_inpcb_free()
3448 (inp->sctp_flags & SCTP_PCB_FLAGS_CLOSE_IP)) { in sctp_inpcb_free()
3458 inp->sctp_ep.signature_change.type = 0; in sctp_inpcb_free()
3459 inp->sctp_flags |= SCTP_PCB_FLAGS_SOCKET_ALLGONE; in sctp_inpcb_free()
3471 if ((inp->sctp_asocidhash) != NULL) { in sctp_inpcb_free()
3472 SCTP_HASH_FREE(inp->sctp_asocidhash, inp->hashasocidmark); in sctp_inpcb_free()
3473 inp->sctp_asocidhash = NULL; in sctp_inpcb_free()
3476 TAILQ_FOREACH_SAFE(sq, &inp->read_queue, next, nsq) { in sctp_inpcb_free()
3478 if (sq->length) in sctp_inpcb_free()
3481 TAILQ_REMOVE(&inp->read_queue, sq, next); in sctp_inpcb_free()
3482 sctp_free_remote_addr(sq->whoFrom); in sctp_inpcb_free()
3484 SCTP_SB_DECR(&so->so_rcv, sq->length); in sctp_inpcb_free()
3485 if (sq->data) { in sctp_inpcb_free()
3486 sctp_m_freem(sq->data); in sctp_inpcb_free()
3487 sq->data = NULL; in sctp_inpcb_free()
3501 if (ip_pcb->inp_options) { in sctp_inpcb_free()
3502 (void)sctp_m_free(ip_pcb->inp_options); in sctp_inpcb_free()
3503 ip_pcb->inp_options = 0; in sctp_inpcb_free()
3506 if (ip_pcb->inp_vflag & INP_IPV6) { in sctp_inpcb_free()
3507 ip6_freepcbopts(ip_pcb->in6p_outputopts); in sctp_inpcb_free()
3510 ip_pcb->inp_vflag = 0; in sctp_inpcb_free()
3512 if (inp->sctp_ep.local_auth_chunks != NULL) in sctp_inpcb_free()
3513 sctp_free_chunklist(inp->sctp_ep.local_auth_chunks); in sctp_inpcb_free()
3514 if (inp->sctp_ep.local_hmacs != NULL) in sctp_inpcb_free()
3515 sctp_free_hmaclist(inp->sctp_ep.local_hmacs); in sctp_inpcb_free()
3517 LIST_FOREACH_SAFE(shared_key, &inp->sctp_ep.shared_keys, next, nshared_key) { in sctp_inpcb_free()
3528 LIST_FOREACH_SAFE(laddr, &inp->sctp_addr_list, sctp_nxt_addr, nladdr) { in sctp_inpcb_free()
3534 LIST_FOREACH_SAFE(stcb, &inp->sctp_asoc_free_list, sctp_tcblist, nstcb) { in sctp_inpcb_free()
3542 if (inp->sctp_tcbhash != NULL) { in sctp_inpcb_free()
3543 SCTP_HASH_FREE(inp->sctp_tcbhash, inp->sctp_hashmark); in sctp_inpcb_free()
3544 inp->sctp_tcbhash = NULL; in sctp_inpcb_free()
3547 crfree(inp->ip_inp.inp.inp_cred); in sctp_inpcb_free()
3548 INP_LOCK_DESTROY(&inp->ip_inp.inp); in sctp_inpcb_free()
3562 TAILQ_FOREACH(net, &stcb->asoc.nets, sctp_next) { in sctp_findnet()
3563 if (sctp_cmpaddr(addr, (struct sockaddr *)&net->ro._l_addr)) in sctp_findnet()
3583 * add's a remote endpoint address, done with the INIT/INIT-ACK as well as
3615 if (netfirst->dest_state & SCTP_ADDR_UNCONFIRMED) { in sctp_add_remote_addr()
3616 netfirst->dest_state = (SCTP_ADDR_REACHABLE | in sctp_add_remote_addr()
3619 netfirst->dest_state = SCTP_ADDR_REACHABLE; in sctp_add_remote_addr()
3625 switch (newaddr->sa_family) { in sctp_add_remote_addr()
3632 if (sin->sin_addr.s_addr == 0) { in sctp_add_remote_addr()
3634 return (-1); in sctp_add_remote_addr()
3637 memset(&sin->sin_zero, 0, sizeof(sin->sin_zero)); in sctp_add_remote_addr()
3640 sin->sin_len = sizeof(struct sockaddr_in); in sctp_add_remote_addr()
3642 if (IN4_ISPRIVATE_ADDRESS(&sin->sin_addr)) { in sctp_add_remote_addr()
3643 stcb->asoc.scope.ipv4_local_scope = 1; in sctp_add_remote_addr()
3647 if ((IN4_ISPRIVATE_ADDRESS(&sin->sin_addr)) && in sctp_add_remote_addr()
3648 (stcb->asoc.scope.ipv4_local_scope == 0)) { in sctp_add_remote_addr()
3661 if (IN6_IS_ADDR_UNSPECIFIED(&sin6->sin6_addr)) { in sctp_add_remote_addr()
3663 return (-1); in sctp_add_remote_addr()
3666 sin6->sin6_len = sizeof(struct sockaddr_in6); in sctp_add_remote_addr()
3668 if (sctp_is_address_on_local_host(newaddr, stcb->asoc.vrf_id)) { in sctp_add_remote_addr()
3669 stcb->asoc.scope.loopback_scope = 1; in sctp_add_remote_addr()
3670 stcb->asoc.scope.local_scope = 0; in sctp_add_remote_addr()
3671 stcb->asoc.scope.ipv4_local_scope = 1; in sctp_add_remote_addr()
3672 stcb->asoc.scope.site_scope = 1; in sctp_add_remote_addr()
3673 } else if (IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr)) { in sctp_add_remote_addr()
3684 stcb->asoc.scope.ipv4_local_scope = 1; in sctp_add_remote_addr()
3685 stcb->asoc.scope.site_scope = 1; in sctp_add_remote_addr()
3686 } else if (IN6_IS_ADDR_SITELOCAL(&sin6->sin6_addr)) { in sctp_add_remote_addr()
3692 stcb->asoc.scope.site_scope = 1; in sctp_add_remote_addr()
3696 if (IN6_IS_ADDR_LOOPBACK(&sin6->sin6_addr) && in sctp_add_remote_addr()
3697 (stcb->asoc.scope.loopback_scope == 0)) { in sctp_add_remote_addr()
3699 } else if (IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr) && in sctp_add_remote_addr()
3700 (stcb->asoc.scope.local_scope == 0)) { in sctp_add_remote_addr()
3702 } else if (IN6_IS_ADDR_SITELOCAL(&sin6->sin6_addr) && in sctp_add_remote_addr()
3703 (stcb->asoc.scope.site_scope == 0)) { in sctp_add_remote_addr()
3712 return (-1); in sctp_add_remote_addr()
3716 return (-1); in sctp_add_remote_addr()
3720 (void)SCTP_GETTIME_TIMEVAL(&net->start_time); in sctp_add_remote_addr()
3721 memcpy(&net->ro._l_addr, newaddr, newaddr->sa_len); in sctp_add_remote_addr()
3722 switch (newaddr->sa_family) { in sctp_add_remote_addr()
3725 ((struct sockaddr_in *)&net->ro._l_addr)->sin_port = stcb->rport; in sctp_add_remote_addr()
3730 ((struct sockaddr_in6 *)&net->ro._l_addr)->sin6_port = stcb->rport; in sctp_add_remote_addr()
3736 net->addr_is_local = sctp_is_address_on_local_host(newaddr, stcb->asoc.vrf_id); in sctp_add_remote_addr()
3737 if (net->addr_is_local && ((set_scope || (from == SCTP_ADDR_IS_CONFIRMED)))) { in sctp_add_remote_addr()
3738 stcb->asoc.scope.loopback_scope = 1; in sctp_add_remote_addr()
3739 stcb->asoc.scope.ipv4_local_scope = 1; in sctp_add_remote_addr()
3740 stcb->asoc.scope.local_scope = 0; in sctp_add_remote_addr()
3741 stcb->asoc.scope.site_scope = 1; in sctp_add_remote_addr()
3744 net->failure_threshold = stcb->asoc.def_net_failure; in sctp_add_remote_addr()
3745 net->pf_threshold = stcb->asoc.def_net_pf_threshold; in sctp_add_remote_addr()
3747 net->dest_state = (SCTP_ADDR_REACHABLE | in sctp_add_remote_addr()
3752 net->dest_state = SCTP_ADDR_REACHABLE; in sctp_add_remote_addr()
3754 net->dest_state = SCTP_ADDR_REACHABLE | in sctp_add_remote_addr()
3758 * We set this to 0, the timer code knows that this means its an in sctp_add_remote_addr()
3761 net->rto_needed = 1; in sctp_add_remote_addr()
3762 net->RTO = 0; in sctp_add_remote_addr()
3763 net->RTO_measured = 0; in sctp_add_remote_addr()
3764 stcb->asoc.numnets++; in sctp_add_remote_addr()
3765 net->ref_count = 1; in sctp_add_remote_addr()
3766 net->cwr_window_tsn = net->last_cwr_tsn = stcb->asoc.sending_seq - 1; in sctp_add_remote_addr()
3767 net->port = port; in sctp_add_remote_addr()
3768 net->dscp = stcb->asoc.default_dscp; in sctp_add_remote_addr()
3770 net->flowlabel = stcb->asoc.default_flowlabel; in sctp_add_remote_addr()
3772 if (sctp_stcb_is_feature_on(stcb->sctp_ep, stcb, SCTP_PCB_FLAGS_DONOT_HEARTBEAT)) { in sctp_add_remote_addr()
3773 net->dest_state |= SCTP_ADDR_NOHB; in sctp_add_remote_addr()
3775 net->dest_state &= ~SCTP_ADDR_NOHB; in sctp_add_remote_addr()
3777 if (sctp_stcb_is_feature_on(stcb->sctp_ep, stcb, SCTP_PCB_FLAGS_DO_NOT_PMTUD)) { in sctp_add_remote_addr()
3778 net->dest_state |= SCTP_ADDR_NO_PMTUD; in sctp_add_remote_addr()
3780 net->dest_state &= ~SCTP_ADDR_NO_PMTUD; in sctp_add_remote_addr()
3782 net->heart_beat_delay = stcb->asoc.heart_beat_delay; in sctp_add_remote_addr()
3783 /* Init the timer structure */ in sctp_add_remote_addr()
3784 SCTP_OS_TIMER_INIT(&net->rxt_timer.timer); in sctp_add_remote_addr()
3785 SCTP_OS_TIMER_INIT(&net->pmtu_timer.timer); in sctp_add_remote_addr()
3786 SCTP_OS_TIMER_INIT(&net->hb_timer.timer); in sctp_add_remote_addr()
3791 if (newaddr->sa_family == AF_INET6) { in sctp_add_remote_addr()
3794 sin6 = (struct sockaddr_in6 *)&net->ro._l_addr; in sctp_add_remote_addr()
3796 sin6->sin6_scope_id = 0; in sctp_add_remote_addr()
3799 SCTP_RTALLOC((sctp_route_t *)&net->ro, in sctp_add_remote_addr()
3800 stcb->asoc.vrf_id, in sctp_add_remote_addr()
3801 stcb->sctp_ep->fibnum); in sctp_add_remote_addr()
3803 net->src_addr_selected = 0; in sctp_add_remote_addr()
3804 if (SCTP_ROUTE_HAS_VALID_IFN(&net->ro)) { in sctp_add_remote_addr()
3806 net->ro._s_addr = sctp_source_address_selection(stcb->sctp_ep, in sctp_add_remote_addr()
3808 (sctp_route_t *)&net->ro, in sctp_add_remote_addr()
3811 stcb->asoc.vrf_id); in sctp_add_remote_addr()
3812 if (stcb->asoc.default_mtu > 0) { in sctp_add_remote_addr()
3813 net->mtu = stcb->asoc.default_mtu; in sctp_add_remote_addr()
3814 switch (net->ro._l_addr.sa.sa_family) { in sctp_add_remote_addr()
3817 net->mtu += SCTP_MIN_V4_OVERHEAD; in sctp_add_remote_addr()
3822 net->mtu += SCTP_MIN_OVERHEAD; in sctp_add_remote_addr()
3829 if (net->port) { in sctp_add_remote_addr()
3830 net->mtu += (uint32_t)sizeof(struct udphdr); in sctp_add_remote_addr()
3833 } else if (net->ro._s_addr != NULL) { in sctp_add_remote_addr()
3836 net->src_addr_selected = 1; in sctp_add_remote_addr()
3838 if (net->ro._s_addr->ifn_p != NULL) { in sctp_add_remote_addr()
3841 * net->ro._s_addr->ifn_p->ifn_mtu in sctp_add_remote_addr()
3843 imtu = SCTP_GATHER_MTU_FROM_IFN_INFO(net->ro._s_addr->ifn_p->ifn_p, in sctp_add_remote_addr()
3844 net->ro._s_addr->ifn_p->ifn_index); in sctp_add_remote_addr()
3848 rmtu = SCTP_GATHER_MTU_FROM_ROUTE(net->ro._s_addr, &net->ro._l_addr.sa, net->ro.ro_nh); in sctp_add_remote_addr()
3849 hcmtu = sctp_hc_get_mtu(&net->ro._l_addr, stcb->sctp_ep->fibnum); in sctp_add_remote_addr()
3850 net->mtu = sctp_min_mtu(hcmtu, rmtu, imtu); in sctp_add_remote_addr()
3853 if (net->mtu == 0) { in sctp_add_remote_addr()
3854 if (stcb->asoc.default_mtu > 0) { in sctp_add_remote_addr()
3855 net->mtu = stcb->asoc.default_mtu; in sctp_add_remote_addr()
3856 switch (net->ro._l_addr.sa.sa_family) { in sctp_add_remote_addr()
3859 net->mtu += SCTP_MIN_V4_OVERHEAD; in sctp_add_remote_addr()
3864 net->mtu += SCTP_MIN_OVERHEAD; in sctp_add_remote_addr()
3871 if (net->port) { in sctp_add_remote_addr()
3872 net->mtu += (uint32_t)sizeof(struct udphdr); in sctp_add_remote_addr()
3876 switch (newaddr->sa_family) { in sctp_add_remote_addr()
3879 net->mtu = SCTP_DEFAULT_MTU; in sctp_add_remote_addr()
3884 net->mtu = 1280; in sctp_add_remote_addr()
3893 if (net->port) { in sctp_add_remote_addr()
3894 net->mtu -= (uint32_t)sizeof(struct udphdr); in sctp_add_remote_addr()
3898 stcb->asoc.smallest_mtu = net->mtu; in sctp_add_remote_addr()
3900 if (stcb->asoc.smallest_mtu > net->mtu) { in sctp_add_remote_addr()
3901 sctp_pathmtu_adjustment(stcb, net->mtu, true); in sctp_add_remote_addr()
3904 if (newaddr->sa_family == AF_INET6) { in sctp_add_remote_addr()
3907 sin6 = (struct sockaddr_in6 *)&net->ro._l_addr; in sctp_add_remote_addr()
3912 /* JRS - Use the congestion control given in the CC module */ in sctp_add_remote_addr()
3913 if (stcb->asoc.cc_functions.sctp_set_initial_cc_param != NULL) in sctp_add_remote_addr()
3914 (*stcb->asoc.cc_functions.sctp_set_initial_cc_param) (stcb, net); in sctp_add_remote_addr()
3917 * CMT: CUC algo - set find_pseudo_cumack to TRUE (1) at beginning in sctp_add_remote_addr()
3920 net->find_pseudo_cumack = 1; in sctp_add_remote_addr()
3921 net->find_rtx_pseudo_cumack = 1; in sctp_add_remote_addr()
3923 net->flowid = stcb->asoc.my_vtag ^ in sctp_add_remote_addr()
3924 ntohs(stcb->rport) ^ in sctp_add_remote_addr()
3925 ntohs(stcb->sctp_ep->sctp_lport); in sctp_add_remote_addr()
3926 net->flowtype = M_HASHTYPE_OPAQUE_HASH; in sctp_add_remote_addr()
3930 netfirst = TAILQ_FIRST(&stcb->asoc.nets); in sctp_add_remote_addr()
3931 if (net->ro.ro_nh == NULL) { in sctp_add_remote_addr()
3933 TAILQ_INSERT_TAIL(&stcb->asoc.nets, net, sctp_next); in sctp_add_remote_addr()
3936 TAILQ_INSERT_HEAD(&stcb->asoc.nets, net, sctp_next); in sctp_add_remote_addr()
3937 } else if (netfirst->ro.ro_nh == NULL) { in sctp_add_remote_addr()
3942 TAILQ_INSERT_HEAD(&stcb->asoc.nets, net, sctp_next); in sctp_add_remote_addr()
3943 } else if (net->ro.ro_nh->nh_ifp != netfirst->ro.ro_nh->nh_ifp) { in sctp_add_remote_addr()
3948 TAILQ_INSERT_HEAD(&stcb->asoc.nets, net, sctp_next); in sctp_add_remote_addr()
3962 TAILQ_INSERT_TAIL(&stcb->asoc.nets, net, sctp_next); in sctp_add_remote_addr()
3964 } else if (netlook->ro.ro_nh == NULL) { in sctp_add_remote_addr()
3968 } else if (netlook->ro.ro_nh->nh_ifp != net->ro.ro_nh->nh_ifp) { in sctp_add_remote_addr()
3969 TAILQ_INSERT_AFTER(&stcb->asoc.nets, netlook, in sctp_add_remote_addr()
3979 if (stcb->asoc.primary_destination == 0) { in sctp_add_remote_addr()
3980 stcb->asoc.primary_destination = net; in sctp_add_remote_addr()
3981 } else if ((stcb->asoc.primary_destination->ro.ro_nh == NULL) && in sctp_add_remote_addr()
3982 (net->ro.ro_nh) && in sctp_add_remote_addr()
3983 ((net->dest_state & SCTP_ADDR_UNCONFIRMED) == 0)) { in sctp_add_remote_addr()
3985 stcb->asoc.primary_destination = net; in sctp_add_remote_addr()
3988 net = TAILQ_FIRST(&stcb->asoc.nets); in sctp_add_remote_addr()
3989 if ((net != stcb->asoc.primary_destination) && in sctp_add_remote_addr()
3990 (stcb->asoc.primary_destination)) { in sctp_add_remote_addr()
3996 TAILQ_REMOVE(&stcb->asoc.nets, in sctp_add_remote_addr()
3997 stcb->asoc.primary_destination, sctp_next); in sctp_add_remote_addr()
3998 TAILQ_INSERT_HEAD(&stcb->asoc.nets, in sctp_add_remote_addr()
3999 stcb->asoc.primary_destination, sctp_next); in sctp_add_remote_addr()
4012 if (inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_ALLGONE) { in sctp_aloc_a_assoc_id()
4020 if (inp->sctp_associd_counter <= SCTP_ALL_ASSOC) { in sctp_aloc_a_assoc_id()
4021 inp->sctp_associd_counter = SCTP_ALL_ASSOC + 1; in sctp_aloc_a_assoc_id()
4023 id = inp->sctp_associd_counter; in sctp_aloc_a_assoc_id()
4024 inp->sctp_associd_counter++; in sctp_aloc_a_assoc_id()
4029 head = &inp->sctp_asocidhash[SCTP_PCBHASH_ASOC(id, inp->hashasocidmark)]; in sctp_aloc_a_assoc_id()
4031 stcb->asoc.in_asocid_hash = 1; in sctp_aloc_a_assoc_id()
4074 if (inp->sctp_flags & (SCTP_PCB_FLAGS_SOCKET_GONE | SCTP_PCB_FLAGS_SOCKET_ALLGONE)) { in sctp_aloc_assoc_locked()
4079 if ((inp->sctp_flags & SCTP_PCB_FLAGS_IN_TCPPOOL) && in sctp_aloc_assoc_locked()
4081 (inp->sctp_flags & SCTP_PCB_FLAGS_CONNECTED))) { in sctp_aloc_assoc_locked()
4085 * sctp_aloc_assoc.. or the one-2-many socket. If a peeled in sctp_aloc_assoc_locked()
4092 if ((inp->sctp_flags & SCTP_PCB_FLAGS_IN_TCPPOOL) || in sctp_aloc_assoc_locked()
4093 (inp->sctp_flags & SCTP_PCB_FLAGS_TCPTYPE)) { in sctp_aloc_assoc_locked()
4094 if ((inp->sctp_flags & SCTP_PCB_FLAGS_WAS_CONNECTED) || in sctp_aloc_assoc_locked()
4095 (inp->sctp_flags & SCTP_PCB_FLAGS_WAS_ABORTED)) { in sctp_aloc_assoc_locked()
4105 switch (firstaddr->sa_family) { in sctp_aloc_assoc_locked()
4109 ntohs(((struct sockaddr_in *)firstaddr)->sin_port)); in sctp_aloc_assoc_locked()
4115 ntohs(((struct sockaddr_in6 *)firstaddr)->sin6_port)); in sctp_aloc_assoc_locked()
4125 switch (firstaddr->sa_family) { in sctp_aloc_assoc_locked()
4132 if ((ntohs(sin->sin_port) == 0) || in sctp_aloc_assoc_locked()
4133 (sin->sin_addr.s_addr == INADDR_ANY) || in sctp_aloc_assoc_locked()
4134 (sin->sin_addr.s_addr == INADDR_BROADCAST) || in sctp_aloc_assoc_locked()
4135 IN_MULTICAST(ntohl(sin->sin_addr.s_addr)) || in sctp_aloc_assoc_locked()
4136 ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) && in sctp_aloc_assoc_locked()
4143 rport = sin->sin_port; in sctp_aloc_assoc_locked()
4153 if ((ntohs(sin6->sin6_port) == 0) || in sctp_aloc_assoc_locked()
4154 IN6_IS_ADDR_UNSPECIFIED(&sin6->sin6_addr) || in sctp_aloc_assoc_locked()
4155 IN6_IS_ADDR_MULTICAST(&sin6->sin6_addr) || in sctp_aloc_assoc_locked()
4156 ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) == 0)) { in sctp_aloc_assoc_locked()
4162 rport = sin6->sin6_port; in sctp_aloc_assoc_locked()
4172 if (inp->sctp_flags & SCTP_PCB_FLAGS_UNBOUND) { in sctp_aloc_assoc_locked()
4193 asoc = &stcb->asoc; in sctp_aloc_assoc_locked()
4196 stcb->rport = rport; in sctp_aloc_assoc_locked()
4198 stcb->sctp_ep = inp; in sctp_aloc_assoc_locked()
4199 stcb->sctp_socket = inp->sctp_socket; in sctp_aloc_assoc_locked()
4210 asoc->assoc_id = sctp_aloc_a_assoc_id(inp, stcb); in sctp_aloc_assoc_locked()
4212 …head = &SCTP_BASE_INFO(sctp_asochash)[SCTP_PCBHASH_ASOC(stcb->asoc.my_vtag, SCTP_BASE_INFO(hashaso… in sctp_aloc_assoc_locked()
4218 if (asoc->strmout) { in sctp_aloc_assoc_locked()
4219 SCTP_FREE(asoc->strmout, SCTP_M_STRMO); in sctp_aloc_assoc_locked()
4220 asoc->strmout = NULL; in sctp_aloc_assoc_locked()
4222 if (asoc->mapping_array) { in sctp_aloc_assoc_locked()
4223 SCTP_FREE(asoc->mapping_array, SCTP_M_MAP); in sctp_aloc_assoc_locked()
4224 asoc->mapping_array = NULL; in sctp_aloc_assoc_locked()
4226 if (asoc->nr_mapping_array) { in sctp_aloc_assoc_locked()
4227 SCTP_FREE(asoc->nr_mapping_array, SCTP_M_MAP); in sctp_aloc_assoc_locked()
4228 asoc->nr_mapping_array = NULL; in sctp_aloc_assoc_locked()
4242 SCTP_OS_TIMER_INIT(&asoc->dack_timer.timer); in sctp_aloc_assoc_locked()
4243 SCTP_OS_TIMER_INIT(&asoc->strreset_timer.timer); in sctp_aloc_assoc_locked()
4244 SCTP_OS_TIMER_INIT(&asoc->asconf_timer.timer); in sctp_aloc_assoc_locked()
4245 SCTP_OS_TIMER_INIT(&asoc->shut_guard_timer.timer); in sctp_aloc_assoc_locked()
4246 SCTP_OS_TIMER_INIT(&asoc->autoclose_timer.timer); in sctp_aloc_assoc_locked()
4247 SCTP_OS_TIMER_INIT(&asoc->delete_prim_timer.timer); in sctp_aloc_assoc_locked()
4249 LIST_INSERT_HEAD(&inp->sctp_asoc_list, stcb, sctp_tcblist); in sctp_aloc_assoc_locked()
4251 if (inp->sctp_tcbhash != NULL) { in sctp_aloc_assoc_locked()
4252 head = &inp->sctp_tcbhash[SCTP_PCBHASH_ALLADDR(stcb->rport, in sctp_aloc_assoc_locked()
4253 inp->sctp_hashmark)]; in sctp_aloc_assoc_locked()
4292 if ((inp->sctp_flags & SCTP_PCB_FLAGS_TCPTYPE) && in sctp_aloc_assoc_connected()
4302 if (stcb != NULL && (inp->sctp_flags & SCTP_PCB_FLAGS_TCPTYPE)) { in sctp_aloc_assoc_connected()
4303 inp->sctp_flags |= SCTP_PCB_FLAGS_CONNECTED; in sctp_aloc_assoc_connected()
4304 soisconnecting(inp->sctp_socket); in sctp_aloc_assoc_connected()
4316 inp = stcb->sctp_ep; in sctp_remove_net()
4317 asoc = &stcb->asoc; in sctp_remove_net()
4318 asoc->numnets--; in sctp_remove_net()
4319 TAILQ_REMOVE(&asoc->nets, net, sctp_next); in sctp_remove_net()
4320 if (net == asoc->primary_destination) { in sctp_remove_net()
4324 lnet = TAILQ_FIRST(&asoc->nets); in sctp_remove_net()
4330 if (sctp_is_mobility_feature_on(stcb->sctp_ep, in sctp_remove_net()
4332 sctp_is_mobility_feature_on(stcb->sctp_ep, in sctp_remove_net()
4335 if (asoc->deleted_primary != NULL) { in sctp_remove_net()
4339 asoc->deleted_primary = net; in sctp_remove_net()
4340 atomic_add_int(&net->ref_count, 1); in sctp_remove_net()
4341 memset(&net->lastsa, 0, sizeof(net->lastsa)); in sctp_remove_net()
4342 memset(&net->lastsv, 0, sizeof(net->lastsv)); in sctp_remove_net()
4343 sctp_mobility_feature_on(stcb->sctp_ep, in sctp_remove_net()
4346 stcb->sctp_ep, stcb, NULL); in sctp_remove_net()
4350 asoc->primary_destination = sctp_find_alternate_net(stcb, lnet, 0); in sctp_remove_net()
4352 if (net == asoc->last_data_chunk_from) { in sctp_remove_net()
4354 asoc->last_data_chunk_from = TAILQ_FIRST(&asoc->nets); in sctp_remove_net()
4356 if (net == asoc->last_control_chunk_from) { in sctp_remove_net()
4358 asoc->last_control_chunk_from = NULL; in sctp_remove_net()
4360 if (net == asoc->last_net_cmt_send_started) { in sctp_remove_net()
4362 asoc->last_net_cmt_send_started = NULL; in sctp_remove_net()
4364 if (net == stcb->asoc.alternate) { in sctp_remove_net()
4365 sctp_free_remote_addr(stcb->asoc.alternate); in sctp_remove_net()
4366 stcb->asoc.alternate = NULL; in sctp_remove_net()
4372 net->dest_state |= SCTP_ADDR_BEING_DELETED; in sctp_remove_net()
4386 * (tasoc->asoc.nets) and then if it is there, we do a LIST_REMOVE in sctp_del_remote_addr()
4393 asoc = &stcb->asoc; in sctp_del_remote_addr()
4396 TAILQ_FOREACH_SAFE(net, &asoc->nets, sctp_next, nnet) { in sctp_del_remote_addr()
4397 if (net->ro._l_addr.sa.sa_family != remaddr->sa_family) { in sctp_del_remote_addr()
4400 if (sctp_cmpaddr((struct sockaddr *)&net->ro._l_addr, in sctp_del_remote_addr()
4403 if (asoc->numnets < 2) { in sctp_del_remote_addr()
4405 return (-1); in sctp_del_remote_addr()
4413 return (-2); in sctp_del_remote_addr()
4427 if ((twait_block->vtag_block[i].tv_sec_at_expire >= now) && in sctp_is_in_timewait()
4428 (twait_block->vtag_block[i].v_tag == tag) && in sctp_is_in_timewait()
4429 (twait_block->vtag_block[i].lport == lport) && in sctp_is_in_timewait()
4430 (twait_block->vtag_block[i].rport == rport)) { in sctp_is_in_timewait()
4442 vtag_block->tv_sec_at_expire = time; in sctp_set_vtag_block()
4443 vtag_block->v_tag = tag; in sctp_set_vtag_block()
4444 vtag_block->lport = lport; in sctp_set_vtag_block()
4445 vtag_block->rport = rport; in sctp_set_vtag_block()
4466 if ((twait_block->vtag_block[i].v_tag == 0) && !set) { in sctp_add_vtag_to_timewait()
4467 sctp_set_vtag_block(twait_block->vtag_block + i, time, tag, lport, rport); in sctp_add_vtag_to_timewait()
4471 if ((twait_block->vtag_block[i].v_tag != 0) && in sctp_add_vtag_to_timewait()
4472 (twait_block->vtag_block[i].tv_sec_at_expire < now.tv_sec)) { in sctp_add_vtag_to_timewait()
4475 sctp_set_vtag_block(twait_block->vtag_block + i, 0, 0, 0, 0); in sctp_add_vtag_to_timewait()
4478 sctp_set_vtag_block(twait_block->vtag_block + i, time, tag, lport, rport); in sctp_add_vtag_to_timewait()
4500 sctp_set_vtag_block(twait_block->vtag_block, time, tag, lport, rport); in sctp_add_vtag_to_timewait()
4512 control->on_strm_q = 0; in sctp_clean_up_stream()
4513 if (control->on_read_q == 0) { in sctp_clean_up_stream()
4514 sctp_free_remote_addr(control->whoFrom); in sctp_clean_up_stream()
4515 if (control->data) { in sctp_clean_up_stream()
4516 sctp_m_freem(control->data); in sctp_clean_up_stream()
4517 control->data = NULL; in sctp_clean_up_stream()
4521 TAILQ_FOREACH_SAFE(chk, &control->reasm, sctp_next, nchk) { in sctp_clean_up_stream()
4522 TAILQ_REMOVE(&control->reasm, chk, sctp_next); in sctp_clean_up_stream()
4523 if (chk->data) { in sctp_clean_up_stream()
4524 sctp_m_freem(chk->data); in sctp_clean_up_stream()
4525 chk->data = NULL; in sctp_clean_up_stream()
4527 if (chk->holds_key_ref) in sctp_clean_up_stream()
4528 sctp_auth_key_release(stcb, chk->auth_keyid, SCTP_SO_LOCKED); in sctp_clean_up_stream()
4529 sctp_free_remote_addr(chk->whoTo); in sctp_clean_up_stream()
4538 if (control->on_read_q == 0) { in sctp_clean_up_stream()
4544 /*-
4545 * Free the association after un-hashing the remote port. This
4549 * it unlocks it. It will return NON-zero if it either destroyed the
4574 if (stcb->asoc.state == 0) { in sctp_free_assoc()
4578 /* there is no asoc, really TSNH :-0 */ in sctp_free_assoc()
4581 if (stcb->asoc.alternate) { in sctp_free_assoc()
4582 sctp_free_remote_addr(stcb->asoc.alternate); in sctp_free_assoc()
4583 stcb->asoc.alternate = NULL; in sctp_free_assoc()
4586 if (stcb->freed_from_where == 0) { in sctp_free_assoc()
4588 stcb->freed_from_where = from_location; in sctp_free_assoc()
4592 asoc = &stcb->asoc; in sctp_free_assoc()
4593 if ((inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_ALLGONE) || in sctp_free_assoc()
4594 (inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_GONE)) in sctp_free_assoc()
4598 so = inp->sctp_socket; in sctp_free_assoc()
4601 * We used timer based freeing if a reader or writer is in the way. in sctp_free_assoc()
4602 * So we first check if we are actually being called from a timer, in sctp_free_assoc()
4605 if ((stcb->asoc.state & SCTP_STATE_ABOUT_TO_BE_FREED) && in sctp_free_assoc()
4608 * is it the timer driving us? if so are the reader/writers in sctp_free_assoc()
4611 if (stcb->asoc.refcnt) { in sctp_free_assoc()
4625 if ((stcb->asoc.state & SCTP_STATE_ABOUT_TO_BE_FREED) == 0) { in sctp_free_assoc()
4628 TAILQ_FOREACH(sq, &inp->read_queue, next) { in sctp_free_assoc()
4629 if (sq->stcb == stcb) { in sctp_free_assoc()
4630 sq->do_not_ref_stcb = 1; in sctp_free_assoc()
4631 sq->sinfo_cumtsn = stcb->asoc.cumulative_tsn; in sctp_free_assoc()
4636 if (sq->end_added == 0) { in sctp_free_assoc()
4637 /* Held for PD-API, clear that. */ in sctp_free_assoc()
4638 sq->pdapi_aborted = 1; in sctp_free_assoc()
4639 sq->held_length = 0; in sctp_free_assoc()
4647 /* Add an end to wake them */ in sctp_free_assoc()
4648 sq->end_added = 1; in sctp_free_assoc()
4653 if (stcb->block_entry) { in sctp_free_assoc()
4655 stcb->block_entry->error = ECONNRESET; in sctp_free_assoc()
4656 stcb->block_entry = NULL; in sctp_free_assoc()
4659 if ((stcb->asoc.refcnt) || (stcb->asoc.state & SCTP_STATE_IN_ACCEPT_QUEUE)) { in sctp_free_assoc()
4664 if ((stcb->asoc.refcnt) || in sctp_free_assoc()
4665 (inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_ALLGONE) || in sctp_free_assoc()
4666 (inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_GONE)) { in sctp_free_assoc()
4670 if ((inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_ALLGONE) || in sctp_free_assoc()
4671 (inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_GONE)) in sctp_free_assoc()
4675 /* Wake any reader/writers */ in sctp_free_assoc()
4695 * timer and blow out above thus assuring us that we hold exclusive in sctp_free_assoc()
4698 * timer a passing stranger may have started :-S in sctp_free_assoc()
4701 atomic_add_int(&stcb->asoc.refcnt, 1); in sctp_free_assoc()
4709 if ((inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_ALLGONE) || in sctp_free_assoc()
4710 (inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_GONE)) in sctp_free_assoc()
4714 if ((inp->sctp_flags & SCTP_PCB_FLAGS_TCPTYPE) || in sctp_free_assoc()
4715 (inp->sctp_flags & SCTP_PCB_FLAGS_IN_TCPPOOL)) { in sctp_free_assoc()
4720 if (inp->sctp_flags & SCTP_PCB_FLAGS_CONNECTED) { in sctp_free_assoc()
4721 inp->sctp_flags &= ~SCTP_PCB_FLAGS_CONNECTED; in sctp_free_assoc()
4722 inp->sctp_flags |= SCTP_PCB_FLAGS_WAS_CONNECTED; in sctp_free_assoc()
4724 SOCKBUF_LOCK(&so->so_rcv); in sctp_free_assoc()
4725 so->so_state &= ~(SS_ISCONNECTING | in sctp_free_assoc()
4728 so->so_state |= SS_ISDISCONNECTED; in sctp_free_assoc()
4742 /* re-increment the lock */ in sctp_free_assoc()
4744 atomic_subtract_int(&stcb->asoc.refcnt, 1); in sctp_free_assoc()
4746 if (stcb->asoc.refcnt) { in sctp_free_assoc()
4756 asoc->state = 0; in sctp_free_assoc()
4757 if (inp->sctp_tcbhash) { in sctp_free_assoc()
4760 if (stcb->asoc.in_asocid_hash) { in sctp_free_assoc()
4763 if (inp->sctp_socket == NULL) { in sctp_free_assoc()
4764 stcb->sctp_socket = NULL; in sctp_free_assoc()
4774 sctp_add_vtag_to_timewait(asoc->my_vtag, inp->sctp_lport, stcb->rport); in sctp_free_assoc()
4786 for (i = 0; i < asoc->streamoutcnt; i++) { in sctp_free_assoc()
4789 outs = &asoc->strmout[i]; in sctp_free_assoc()
4791 TAILQ_FOREACH_SAFE(sp, &outs->outqueue, next, nsp) { in sctp_free_assoc()
4792 atomic_subtract_int(&asoc->stream_queue_cnt, 1); in sctp_free_assoc()
4793 TAILQ_REMOVE(&outs->outqueue, sp, next); in sctp_free_assoc()
4794 stcb->asoc.ss_functions.sctp_ss_remove_from_stream(stcb, asoc, outs, sp); in sctp_free_assoc()
4796 if (sp->data) { in sctp_free_assoc()
4798 /* Still an open socket - report */ in sctp_free_assoc()
4802 if (sp->data) { in sctp_free_assoc()
4803 sctp_m_freem(sp->data); in sctp_free_assoc()
4804 sp->data = NULL; in sctp_free_assoc()
4805 sp->tail_mbuf = NULL; in sctp_free_assoc()
4806 sp->length = 0; in sctp_free_assoc()
4809 if (sp->net) { in sctp_free_assoc()
4810 sctp_free_remote_addr(sp->net); in sctp_free_assoc()
4811 sp->net = NULL; in sctp_free_assoc()
4817 TAILQ_FOREACH_SAFE(strrst, &asoc->resetHead, next_resp, nstrrst) { in sctp_free_assoc()
4818 TAILQ_REMOVE(&asoc->resetHead, strrst, next_resp); in sctp_free_assoc()
4821 TAILQ_FOREACH_SAFE(sq, &asoc->pending_reply_queue, next, nsq) { in sctp_free_assoc()
4822 TAILQ_REMOVE(&asoc->pending_reply_queue, sq, next); in sctp_free_assoc()
4823 if (sq->data) { in sctp_free_assoc()
4824 sctp_m_freem(sq->data); in sctp_free_assoc()
4825 sq->data = NULL; in sctp_free_assoc()
4827 sctp_free_remote_addr(sq->whoFrom); in sctp_free_assoc()
4828 sq->whoFrom = NULL; in sctp_free_assoc()
4829 sq->stcb = NULL; in sctp_free_assoc()
4834 TAILQ_FOREACH_SAFE(chk, &asoc->free_chunks, sctp_next, nchk) { in sctp_free_assoc()
4835 TAILQ_REMOVE(&asoc->free_chunks, chk, sctp_next); in sctp_free_assoc()
4836 if (chk->data) { in sctp_free_assoc()
4837 sctp_m_freem(chk->data); in sctp_free_assoc()
4838 chk->data = NULL; in sctp_free_assoc()
4840 if (chk->holds_key_ref) in sctp_free_assoc()
4841 sctp_auth_key_release(stcb, chk->auth_keyid, SCTP_SO_LOCKED); in sctp_free_assoc()
4845 asoc->free_chunk_cnt--; in sctp_free_assoc()
4849 TAILQ_FOREACH_SAFE(chk, &asoc->send_queue, sctp_next, nchk) { in sctp_free_assoc()
4850 if (asoc->strmout[chk->rec.data.sid].chunks_on_queues > 0) { in sctp_free_assoc()
4851 asoc->strmout[chk->rec.data.sid].chunks_on_queues--; in sctp_free_assoc()
4854 panic("No chunks on the queues for sid %u.", chk->rec.data.sid); in sctp_free_assoc()
4857 TAILQ_REMOVE(&asoc->send_queue, chk, sctp_next); in sctp_free_assoc()
4858 if (chk->data) { in sctp_free_assoc()
4864 if (chk->data) { in sctp_free_assoc()
4865 sctp_m_freem(chk->data); in sctp_free_assoc()
4866 chk->data = NULL; in sctp_free_assoc()
4869 if (chk->holds_key_ref) in sctp_free_assoc()
4870 sctp_auth_key_release(stcb, chk->auth_keyid, SCTP_SO_LOCKED); in sctp_free_assoc()
4871 if (chk->whoTo) { in sctp_free_assoc()
4872 sctp_free_remote_addr(chk->whoTo); in sctp_free_assoc()
4873 chk->whoTo = NULL; in sctp_free_assoc()
4880 TAILQ_FOREACH_SAFE(chk, &asoc->sent_queue, sctp_next, nchk) { in sctp_free_assoc()
4881 if (chk->sent != SCTP_DATAGRAM_NR_ACKED) { in sctp_free_assoc()
4882 if (asoc->strmout[chk->rec.data.sid].chunks_on_queues > 0) { in sctp_free_assoc()
4883 asoc->strmout[chk->rec.data.sid].chunks_on_queues--; in sctp_free_assoc()
4886 panic("No chunks on the queues for sid %u.", chk->rec.data.sid); in sctp_free_assoc()
4890 TAILQ_REMOVE(&asoc->sent_queue, chk, sctp_next); in sctp_free_assoc()
4891 if (chk->data) { in sctp_free_assoc()
4897 if (chk->data) { in sctp_free_assoc()
4898 sctp_m_freem(chk->data); in sctp_free_assoc()
4899 chk->data = NULL; in sctp_free_assoc()
4902 if (chk->holds_key_ref) in sctp_free_assoc()
4903 sctp_auth_key_release(stcb, chk->auth_keyid, SCTP_SO_LOCKED); in sctp_free_assoc()
4904 sctp_free_remote_addr(chk->whoTo); in sctp_free_assoc()
4910 for (i = 0; i < stcb->asoc.streamoutcnt; i++) { in sctp_free_assoc()
4911 if (stcb->asoc.strmout[i].chunks_on_queues > 0) { in sctp_free_assoc()
4912 panic("%u chunks left for stream %u.", stcb->asoc.strmout[i].chunks_on_queues, i); in sctp_free_assoc()
4917 TAILQ_FOREACH_SAFE(chk, &asoc->control_send_queue, sctp_next, nchk) { in sctp_free_assoc()
4918 TAILQ_REMOVE(&asoc->control_send_queue, chk, sctp_next); in sctp_free_assoc()
4919 if (chk->data) { in sctp_free_assoc()
4920 sctp_m_freem(chk->data); in sctp_free_assoc()
4921 chk->data = NULL; in sctp_free_assoc()
4923 if (chk->holds_key_ref) in sctp_free_assoc()
4924 sctp_auth_key_release(stcb, chk->auth_keyid, SCTP_SO_LOCKED); in sctp_free_assoc()
4925 sctp_free_remote_addr(chk->whoTo); in sctp_free_assoc()
4931 TAILQ_FOREACH_SAFE(chk, &asoc->asconf_send_queue, sctp_next, nchk) { in sctp_free_assoc()
4932 TAILQ_REMOVE(&asoc->asconf_send_queue, chk, sctp_next); in sctp_free_assoc()
4933 if (chk->data) { in sctp_free_assoc()
4934 sctp_m_freem(chk->data); in sctp_free_assoc()
4935 chk->data = NULL; in sctp_free_assoc()
4937 if (chk->holds_key_ref) in sctp_free_assoc()
4938 sctp_auth_key_release(stcb, chk->auth_keyid, SCTP_SO_LOCKED); in sctp_free_assoc()
4939 sctp_free_remote_addr(chk->whoTo); in sctp_free_assoc()
4944 if (asoc->mapping_array) { in sctp_free_assoc()
4945 SCTP_FREE(asoc->mapping_array, SCTP_M_MAP); in sctp_free_assoc()
4946 asoc->mapping_array = NULL; in sctp_free_assoc()
4948 if (asoc->nr_mapping_array) { in sctp_free_assoc()
4949 SCTP_FREE(asoc->nr_mapping_array, SCTP_M_MAP); in sctp_free_assoc()
4950 asoc->nr_mapping_array = NULL; in sctp_free_assoc()
4953 if (asoc->strmout) { in sctp_free_assoc()
4954 SCTP_FREE(asoc->strmout, SCTP_M_STRMO); in sctp_free_assoc()
4955 asoc->strmout = NULL; in sctp_free_assoc()
4957 asoc->strm_realoutsize = asoc->streamoutcnt = 0; in sctp_free_assoc()
4958 if (asoc->strmin) { in sctp_free_assoc()
4959 for (i = 0; i < asoc->streamincnt; i++) { in sctp_free_assoc()
4960 sctp_clean_up_stream(stcb, &asoc->strmin[i].inqueue); in sctp_free_assoc()
4961 sctp_clean_up_stream(stcb, &asoc->strmin[i].uno_inqueue); in sctp_free_assoc()
4963 SCTP_FREE(asoc->strmin, SCTP_M_STRMI); in sctp_free_assoc()
4964 asoc->strmin = NULL; in sctp_free_assoc()
4966 asoc->streamincnt = 0; in sctp_free_assoc()
4967 TAILQ_FOREACH_SAFE(net, &asoc->nets, sctp_next, nnet) { in sctp_free_assoc()
4973 TAILQ_REMOVE(&asoc->nets, net, sctp_next); in sctp_free_assoc()
4976 LIST_FOREACH_SAFE(laddr, &asoc->sctp_restricted_addrs, sctp_nxt_addr, naddr) { in sctp_free_assoc()
4982 TAILQ_FOREACH_SAFE(aparam, &asoc->asconf_queue, next, naparam) { in sctp_free_assoc()
4984 TAILQ_REMOVE(&asoc->asconf_queue, aparam, next); in sctp_free_assoc()
4987 TAILQ_FOREACH_SAFE(aack, &asoc->asconf_ack_sent, next, naack) { in sctp_free_assoc()
4989 TAILQ_REMOVE(&asoc->asconf_ack_sent, aack, next); in sctp_free_assoc()
4990 if (aack->data != NULL) { in sctp_free_assoc()
4991 sctp_m_freem(aack->data); in sctp_free_assoc()
4996 if (asoc->local_hmacs) in sctp_free_assoc()
4997 sctp_free_hmaclist(asoc->local_hmacs); in sctp_free_assoc()
4998 if (asoc->peer_hmacs) in sctp_free_assoc()
4999 sctp_free_hmaclist(asoc->peer_hmacs); in sctp_free_assoc()
5001 if (asoc->local_auth_chunks) in sctp_free_assoc()
5002 sctp_free_chunklist(asoc->local_auth_chunks); in sctp_free_assoc()
5003 if (asoc->peer_auth_chunks) in sctp_free_assoc()
5004 sctp_free_chunklist(asoc->peer_auth_chunks); in sctp_free_assoc()
5006 sctp_free_authinfo(&asoc->authinfo); in sctp_free_assoc()
5008 LIST_FOREACH_SAFE(shared_key, &asoc->shared_keys, next, nshared_key) { in sctp_free_assoc()
5024 if (inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_GONE) { in sctp_free_assoc()
5029 LIST_INSERT_HEAD(&inp->sctp_asoc_free_list, stcb, sctp_tcblist); in sctp_free_assoc()
5036 if (inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_GONE) { in sctp_free_assoc()
5043 * This will start the kill timer (if we are the in sctp_free_assoc()
5071 * FIX: if we allow assoc-level bindx(), then this needs to be fixed to use
5087 * only want to read the sctp_flags, which is either bound-all or in sctp_destination_is_reachable()
5091 inp = stcb->sctp_ep; in sctp_destination_is_reachable()
5092 if (inp->sctp_flags & SCTP_PCB_FLAGS_BOUNDALL) { in sctp_destination_is_reachable()
5096 * are bound-all you still might need to obey the V4--V6 in sctp_destination_is_reachable()
5097 * flags??? IMO this bound-all stuff needs to be removed! in sctp_destination_is_reachable()
5102 switch (destaddr->sa_family) { in sctp_destination_is_reachable()
5105 answer = inp->ip_inp.inp.inp_vflag & INP_IPV6; in sctp_destination_is_reachable()
5110 answer = inp->ip_inp.inp.inp_vflag & INP_IPV4; in sctp_destination_is_reachable()
5130 inp->ip_inp.inp.inp_vflag = 0; in sctp_update_ep_vflag()
5132 LIST_FOREACH(laddr, &inp->sctp_addr_list, sctp_nxt_addr) { in sctp_update_ep_vflag()
5133 if (laddr->ifa == NULL) { in sctp_update_ep_vflag()
5139 if (laddr->ifa->localifa_flags & SCTP_BEING_DELETED) { in sctp_update_ep_vflag()
5142 switch (laddr->ifa->address.sa.sa_family) { in sctp_update_ep_vflag()
5145 inp->ip_inp.inp.inp_vflag |= INP_IPV6; in sctp_update_ep_vflag()
5150 inp->ip_inp.inp.inp_vflag |= INP_IPV4; in sctp_update_ep_vflag()
5172 if (inp->sctp_flags & SCTP_PCB_FLAGS_BOUNDALL) { in sctp_add_local_addr_ep()
5177 if (ifa->address.sa.sa_family == AF_INET6) { in sctp_add_local_addr_ep()
5178 if (ifa->localifa_flags & SCTP_ADDR_IFA_UNUSEABLE) { in sctp_add_local_addr_ep()
5179 /* Can't bind a non-useable addr. */ in sctp_add_local_addr_ep()
5185 LIST_FOREACH(laddr, &inp->sctp_addr_list, sctp_nxt_addr) { in sctp_add_local_addr_ep()
5186 if (laddr->ifa == ifa) { in sctp_add_local_addr_ep()
5194 error = sctp_insert_laddr(&inp->sctp_addr_list, ifa, action); in sctp_add_local_addr_ep()
5197 inp->laddr_count++; in sctp_add_local_addr_ep()
5199 switch (ifa->address.sa.sa_family) { in sctp_add_local_addr_ep()
5202 inp->ip_inp.inp.inp_vflag |= INP_IPV6; in sctp_add_local_addr_ep()
5207 inp->ip_inp.inp.inp_vflag |= INP_IPV4; in sctp_add_local_addr_ep()
5213 LIST_FOREACH(stcb, &inp->sctp_asoc_list, sctp_tcblist) { in sctp_add_local_addr_ep()
5230 TAILQ_FOREACH(net, &stcb->asoc.nets, sctp_next) { in sctp_select_primary_destination()
5232 if (net->dest_state & SCTP_ADDR_UNCONFIRMED) in sctp_select_primary_destination()
5235 (struct sockaddr *)&net->ro._l_addr)) { in sctp_select_primary_destination()
5237 stcb->asoc.primary_destination = net; in sctp_select_primary_destination()
5254 if (inp->sctp_flags & SCTP_PCB_FLAGS_BOUNDALL) { in sctp_del_local_addr_ep()
5258 LIST_FOREACH(laddr, &inp->sctp_addr_list, sctp_nxt_addr) { in sctp_del_local_addr_ep()
5259 if (laddr->ifa == ifa) { in sctp_del_local_addr_ep()
5264 if (fnd && (inp->laddr_count < 2)) { in sctp_del_local_addr_ep()
5278 if (inp->next_addr_touse == laddr) in sctp_del_local_addr_ep()
5280 inp->next_addr_touse = NULL; in sctp_del_local_addr_ep()
5283 LIST_FOREACH(stcb, &inp->sctp_asoc_list, sctp_tcblist) { in sctp_del_local_addr_ep()
5287 if (stcb->asoc.last_used_address == laddr) in sctp_del_local_addr_ep()
5289 stcb->asoc.last_used_address = NULL; in sctp_del_local_addr_ep()
5294 TAILQ_FOREACH(net, &stcb->asoc.nets, sctp_next) { in sctp_del_local_addr_ep()
5295 if (net->ro._s_addr == laddr->ifa) { in sctp_del_local_addr_ep()
5297 RO_NHFREE(&net->ro); in sctp_del_local_addr_ep()
5298 sctp_free_ifa(net->ro._s_addr); in sctp_del_local_addr_ep()
5299 net->ro._s_addr = NULL; in sctp_del_local_addr_ep()
5300 net->src_addr_selected = 0; in sctp_del_local_addr_ep()
5307 inp->laddr_count--; in sctp_del_local_addr_ep()
5317 * ASCONF-ACK response) and cannot be used as a valid source address.
5329 list = &stcb->asoc.sctp_restricted_addrs; in sctp_add_local_addr_restricted()
5332 if (ifa->address.sa.sa_family == AF_INET6) { in sctp_add_local_addr_restricted()
5333 if (ifa->localifa_flags & SCTP_ADDR_IFA_UNUSEABLE) { in sctp_add_local_addr_restricted()
5334 /* Can't bind a non-existent addr. */ in sctp_add_local_addr_restricted()
5341 if (laddr->ifa == ifa) { in sctp_add_local_addr_restricted()
5367 * up is changing :-D in sctp_del_local_addr_restricted()
5370 inp = stcb->sctp_ep; in sctp_del_local_addr_restricted()
5372 if (((inp->sctp_flags & SCTP_PCB_FLAGS_BOUNDALL) == 0) && in sctp_del_local_addr_restricted()
5374 if (stcb->sctp_ep->laddr_count < 2) { in sctp_del_local_addr_restricted()
5379 LIST_FOREACH(laddr, &stcb->asoc.sctp_restricted_addrs, sctp_nxt_addr) { in sctp_del_local_addr_restricted()
5381 if (laddr->ifa == NULL) in sctp_del_local_addr_restricted()
5383 if (laddr->ifa == ifa) { in sctp_del_local_addr_restricted()
5422 qent->vn = curvnet; in sctp_queue_to_mcore()
5423 qent->m = m; in sctp_queue_to_mcore()
5424 qent->off = off; in sctp_queue_to_mcore()
5425 qent->v6 = 0; in sctp_queue_to_mcore()
5429 TAILQ_INSERT_TAIL(&wkq->que, qent, next); in sctp_queue_to_mcore()
5430 if (wkq->running == 0) { in sctp_queue_to_mcore()
5435 wakeup(&wkq->running); in sctp_queue_to_mcore()
5452 wkq->running = 0; in sctp_mcore_thread()
5453 msleep(&wkq->running, in sctp_mcore_thread()
5454 &wkq->core_mtx, in sctp_mcore_thread()
5458 /* Bind to our cpu */ in sctp_mcore_thread()
5460 sched_bind(curthread, wkq->cpuid); in sctp_mcore_thread()
5469 wkq->running = 1; in sctp_mcore_thread()
5470 qent = TAILQ_FIRST(&wkq->que); in sctp_mcore_thread()
5472 TAILQ_REMOVE(&wkq->que, qent, next); in sctp_mcore_thread()
5474 CURVNET_SET(qent->vn); in sctp_mcore_thread()
5475 m = qent->m; in sctp_mcore_thread()
5476 off = qent->off; in sctp_mcore_thread()
5477 v6 = qent->v6; in sctp_mcore_thread()
5488 wkq->running = 0; in sctp_mcore_thread()
5489 if (!TAILQ_EMPTY(&wkq->que)) { in sctp_mcore_thread()
5493 msleep(&wkq->running, in sctp_mcore_thread()
5494 &wkq->core_mtx, in sctp_mcore_thread()
5502 int i, cpu; in sctp_startup_mcore_threads() local
5534 CPU_FOREACH(cpu) { in sctp_startup_mcore_threads()
5535 sctp_cpuarry[i] = cpu; in sctp_startup_mcore_threads()
5540 CPU_FOREACH(cpu) { in sctp_startup_mcore_threads()
5542 (void *)&sctp_mcore_workers[cpu], in sctp_startup_mcore_threads()
5543 &sctp_mcore_workers[cpu].thread_proc, in sctp_startup_mcore_threads()
5683 SCTP_OS_TIMER_INIT(&SCTP_BASE_INFO(addr_wq_timer.timer)); in sctp_pcb_init()
5736 * wait to re-acquire the lock. in sctp_pcb_finish()
5746 if (it->vn != curvnet) { in sctp_pcb_finish()
5750 if (it->function_atend != NULL) { in sctp_pcb_finish()
5751 (*it->function_atend) (it->pointer, it->val); in sctp_pcb_finish()
5758 (sctp_it_ctl.cur_it->vn == curvnet)) { in sctp_pcb_finish()
5762 SCTP_OS_TIMER_STOP_DRAIN(&SCTP_BASE_INFO(addr_wq_timer.timer)); in sctp_pcb_finish()
5767 if (wi->action == SCTP_DEL_IP_ADDRESS) { in sctp_pcb_finish()
5768 SCTP_FREE(wi->ifa, SCTP_M_IFA); in sctp_pcb_finish()
5781 LIST_FOREACH_SAFE(ifn, &vrf->ifnlist, next_ifn, nifn) { in sctp_pcb_finish()
5782 LIST_FOREACH_SAFE(ifa, &ifn->ifalist, next_ifa, nifa) { in sctp_pcb_finish()
5793 SCTP_HASH_FREE(vrf->vrf_addr_hash, vrf->vrf_addr_hashmark); in sctp_pcb_finish()
5863 * with either INIT or INIT-ACK's as long as the m points to the IP in sctp_load_addresses_from_init()
5907 sin.sin_port = stcb->rport; in sctp_load_addresses_from_init()
5913 sin6.sin6_port = stcb->rport; in sctp_load_addresses_from_init()
5929 TAILQ_FOREACH(net, &stcb->asoc.nets, sctp_next) { in sctp_load_addresses_from_init()
5931 net->dest_state |= SCTP_ADDR_NOT_IN_ASSOC; in sctp_load_addresses_from_init()
5934 inp = stcb->sctp_ep; in sctp_load_addresses_from_init()
5935 atomic_add_int(&stcb->asoc.refcnt, 1); in sctp_load_addresses_from_init()
5937 atomic_subtract_int(&stcb->asoc.refcnt, 1); in sctp_load_addresses_from_init()
5939 if ((stcb_tmp == NULL && inp == stcb->sctp_ep) || inp == NULL) { in sctp_load_addresses_from_init()
5942 switch (sa->sa_family) { in sctp_load_addresses_from_init()
5945 if (stcb->asoc.scope.ipv4_addr_legal) { in sctp_load_addresses_from_init()
5947 return (-1); in sctp_load_addresses_from_init()
5954 if (stcb->asoc.scope.ipv6_addr_legal) { in sctp_load_addresses_from_init()
5956 return (-2); in sctp_load_addresses_from_init()
5966 net_tmp->dest_state &= ~SCTP_ADDR_NOT_IN_ASSOC; in sctp_load_addresses_from_init()
5971 return (-3); in sctp_load_addresses_from_init()
5974 if (stcb->asoc.state == 0) { in sctp_load_addresses_from_init()
5976 return (-4); in sctp_load_addresses_from_init()
5981 ptype = ntohs(phdr->param_type); in sctp_load_addresses_from_init()
5982 plen = ntohs(phdr->param_length); in sctp_load_addresses_from_init()
5995 if (stcb->asoc.scope.ipv4_addr_legal) { in sctp_load_addresses_from_init()
6004 return (-5); in sctp_load_addresses_from_init()
6007 sin.sin_addr.s_addr = p4->addr; in sctp_load_addresses_from_init()
6009 /* Skip multi-cast addresses */ in sctp_load_addresses_from_init()
6017 inp = stcb->sctp_ep; in sctp_load_addresses_from_init()
6018 atomic_add_int(&stcb->asoc.refcnt, 1); in sctp_load_addresses_from_init()
6021 atomic_subtract_int(&stcb->asoc.refcnt, 1); in sctp_load_addresses_from_init()
6023 if ((stcb_tmp == NULL && inp == stcb->sctp_ep) || in sctp_load_addresses_from_init()
6036 if (stcb->asoc.state == 0) { in sctp_load_addresses_from_init()
6038 return (-7); in sctp_load_addresses_from_init()
6041 return (-8); in sctp_load_addresses_from_init()
6044 if (stcb->asoc.state == 0) { in sctp_load_addresses_from_init()
6046 return (-10); in sctp_load_addresses_from_init()
6050 net->dest_state &= in sctp_load_addresses_from_init()
6071 sctp_abort_an_association(stcb_tmp->sctp_ep, in sctp_load_addresses_from_init()
6079 if (stcb->asoc.state == 0) { in sctp_load_addresses_from_init()
6081 return (-12); in sctp_load_addresses_from_init()
6083 return (-13); in sctp_load_addresses_from_init()
6090 if (stcb->asoc.scope.ipv6_addr_legal) { in sctp_load_addresses_from_init()
6099 return (-14); in sctp_load_addresses_from_init()
6102 memcpy((caddr_t)&sin6.sin6_addr, p6->addr, in sctp_load_addresses_from_init()
6103 sizeof(p6->addr)); in sctp_load_addresses_from_init()
6105 /* Skip multi-cast addresses */ in sctp_load_addresses_from_init()
6116 inp = stcb->sctp_ep; in sctp_load_addresses_from_init()
6117 atomic_add_int(&stcb->asoc.refcnt, 1); in sctp_load_addresses_from_init()
6120 atomic_subtract_int(&stcb->asoc.refcnt, 1); in sctp_load_addresses_from_init()
6122 (inp == stcb->sctp_ep || inp == NULL)) { in sctp_load_addresses_from_init()
6128 if (stcb->asoc.state == 0) { in sctp_load_addresses_from_init()
6130 return (-16); in sctp_load_addresses_from_init()
6137 return (-17); in sctp_load_addresses_from_init()
6144 if (stcb->asoc.state == 0) { in sctp_load_addresses_from_init()
6146 return (-19); in sctp_load_addresses_from_init()
6150 net->dest_state &= in sctp_load_addresses_from_init()
6171 sctp_abort_an_association(stcb_tmp->sctp_ep, in sctp_load_addresses_from_init()
6178 if (stcb->asoc.state == 0) { in sctp_load_addresses_from_init()
6180 return (-21); in sctp_load_addresses_from_init()
6182 return (-22); in sctp_load_addresses_from_init()
6190 if (stcb->asoc.state != SCTP_STATE_OPEN) { in sctp_load_addresses_from_init()
6198 stcb->asoc.peers_adaptation = ntohl(aip->indication); in sctp_load_addresses_from_init()
6199 stcb->asoc.adaptation_needed = 1; in sctp_load_addresses_from_init()
6210 if (stcb->asoc.asconf_supported == 0) { in sctp_load_addresses_from_init()
6211 return (-100); in sctp_load_addresses_from_init()
6214 return (-23); in sctp_load_addresses_from_init()
6217 return (-101); in sctp_load_addresses_from_init()
6223 return (-24); in sctp_load_addresses_from_init()
6226 lptype = ntohs(fee->addrp.ph.param_type); in sctp_load_addresses_from_init()
6232 SCTP_PRINTF("Sizeof setprim in init/init ack not %d but %d - ignored\n", in sctp_load_addresses_from_init()
6237 sin.sin_addr.s_addr = fii->addrp.addr; in sctp_load_addresses_from_init()
6246 SCTP_PRINTF("Sizeof setprim (v6) in init/init ack not %d but %d - ignored\n", in sctp_load_addresses_from_init()
6251 fee->addrp.addr, in sctp_load_addresses_from_init()
6252 sizeof(fee->addrp.addr)); in sctp_load_addresses_from_init()
6264 stcb->asoc.peer_supports_nat = 1; in sctp_load_addresses_from_init()
6266 /* Peer supports pr-sctp */ in sctp_load_addresses_from_init()
6282 if ((ntohl(zero_chksum_p->edmid) != SCTP_EDMID_NONE) && in sctp_load_addresses_from_init()
6283 (ntohl(zero_chksum_p->edmid) == stcb->asoc.rcv_edmid)) { in sctp_load_addresses_from_init()
6284 stcb->asoc.snd_edmid = stcb->asoc.rcv_edmid; in sctp_load_addresses_from_init()
6294 return (-35); in sctp_load_addresses_from_init()
6299 return (-25); in sctp_load_addresses_from_init()
6302 num_ent = plen - sizeof(struct sctp_paramhdr); in sctp_load_addresses_from_init()
6304 switch (pr_supported->chunk_types[i]) { in sctp_load_addresses_from_init()
6345 return (-26); in sctp_load_addresses_from_init()
6347 random_len = plen - sizeof(*p_random); in sctp_load_addresses_from_init()
6351 return (-27); in sctp_load_addresses_from_init()
6368 return (-28); in sctp_load_addresses_from_init()
6370 hmacs_len = plen - sizeof(*hmacs); in sctp_load_addresses_from_init()
6371 num_hmacs = hmacs_len / sizeof(hmacs->hmac_ids[0]); in sctp_load_addresses_from_init()
6374 return (-29); in sctp_load_addresses_from_init()
6376 if (stcb->asoc.peer_hmacs != NULL) in sctp_load_addresses_from_init()
6377 sctp_free_hmaclist(stcb->asoc.peer_hmacs); in sctp_load_addresses_from_init()
6378 stcb->asoc.peer_hmacs = sctp_alloc_hmaclist(num_hmacs); in sctp_load_addresses_from_init()
6379 if (stcb->asoc.peer_hmacs != NULL) { in sctp_load_addresses_from_init()
6381 (void)sctp_auth_add_hmacid(stcb->asoc.peer_hmacs, in sctp_load_addresses_from_init()
6382 ntohs(hmacs->hmac_ids[i])); in sctp_load_addresses_from_init()
6399 return (-30); in sctp_load_addresses_from_init()
6401 num_chunks = plen - sizeof(*chunks); in sctp_load_addresses_from_init()
6402 if (stcb->asoc.peer_auth_chunks != NULL) in sctp_load_addresses_from_init()
6403 sctp_clear_chunklist(stcb->asoc.peer_auth_chunks); in sctp_load_addresses_from_init()
6405 stcb->asoc.peer_auth_chunks = sctp_alloc_chunklist(); in sctp_load_addresses_from_init()
6407 (void)sctp_auth_add_chunk(chunks->chunk_types[i], in sctp_load_addresses_from_init()
6408 stcb->asoc.peer_auth_chunks); in sctp_load_addresses_from_init()
6409 /* record asconf/asconf-ack if listed */ in sctp_load_addresses_from_init()
6410 if (chunks->chunk_types[i] == SCTP_ASCONF) in sctp_load_addresses_from_init()
6412 if (chunks->chunk_types[i] == SCTP_ASCONF_ACK) in sctp_load_addresses_from_init()
6433 * when the INIT or INIT-ACK was first seen. in sctp_load_addresses_from_init()
6448 TAILQ_FOREACH_SAFE(net, &stcb->asoc.nets, sctp_next, nnet) { in sctp_load_addresses_from_init()
6449 if ((net->dest_state & SCTP_ADDR_NOT_IN_ASSOC) == in sctp_load_addresses_from_init()
6453 stcb->asoc.numnets--; in sctp_load_addresses_from_init()
6454 TAILQ_REMOVE(&stcb->asoc.nets, net, sctp_next); in sctp_load_addresses_from_init()
6455 if (net == stcb->asoc.alternate) { in sctp_load_addresses_from_init()
6456 sctp_free_remote_addr(stcb->asoc.alternate); in sctp_load_addresses_from_init()
6457 stcb->asoc.alternate = NULL; in sctp_load_addresses_from_init()
6459 if (net == stcb->asoc.primary_destination) { in sctp_load_addresses_from_init()
6460 stcb->asoc.primary_destination = NULL; in sctp_load_addresses_from_init()
6466 if ((stcb->asoc.ecn_supported == 1) && in sctp_load_addresses_from_init()
6468 stcb->asoc.ecn_supported = 0; in sctp_load_addresses_from_init()
6470 if ((stcb->asoc.prsctp_supported == 1) && in sctp_load_addresses_from_init()
6472 stcb->asoc.prsctp_supported = 0; in sctp_load_addresses_from_init()
6474 if ((stcb->asoc.auth_supported == 1) && in sctp_load_addresses_from_init()
6477 stcb->asoc.auth_supported = 0; in sctp_load_addresses_from_init()
6479 if ((stcb->asoc.asconf_supported == 1) && in sctp_load_addresses_from_init()
6481 (stcb->asoc.auth_supported == 0) || in sctp_load_addresses_from_init()
6483 stcb->asoc.asconf_supported = 0; in sctp_load_addresses_from_init()
6485 if ((stcb->asoc.reconfig_supported == 1) && in sctp_load_addresses_from_init()
6487 stcb->asoc.reconfig_supported = 0; in sctp_load_addresses_from_init()
6489 if ((stcb->asoc.idata_supported == 1) && in sctp_load_addresses_from_init()
6491 stcb->asoc.idata_supported = 0; in sctp_load_addresses_from_init()
6493 if ((stcb->asoc.nrsack_supported == 1) && in sctp_load_addresses_from_init()
6495 stcb->asoc.nrsack_supported = 0; in sctp_load_addresses_from_init()
6497 if ((stcb->asoc.pktdrop_supported == 1) && in sctp_load_addresses_from_init()
6499 stcb->asoc.pktdrop_supported = 0; in sctp_load_addresses_from_init()
6504 return (-31); in sctp_load_addresses_from_init()
6508 return (-32); in sctp_load_addresses_from_init()
6512 return (-33); in sctp_load_addresses_from_init()
6524 memcpy(new_key->key, p_random, keylen); in sctp_load_addresses_from_init()
6530 memcpy(new_key->key + keylen, chunks, in sctp_load_addresses_from_init()
6536 memcpy(new_key->key + keylen, hmacs, in sctp_load_addresses_from_init()
6541 return (-34); in sctp_load_addresses_from_init()
6543 if (stcb->asoc.authinfo.peer_random != NULL) in sctp_load_addresses_from_init()
6544 sctp_free_key(stcb->asoc.authinfo.peer_random); in sctp_load_addresses_from_init()
6545 stcb->asoc.authinfo.peer_random = new_key; in sctp_load_addresses_from_init()
6546 sctp_clear_cachedkeys(stcb, stcb->asoc.authinfo.assoc_keyid); in sctp_load_addresses_from_init()
6547 sctp_clear_cachedkeys(stcb, stcb->asoc.authinfo.recv_keyid); in sctp_load_addresses_from_init()
6562 return (-1); in sctp_set_primary_addr()
6565 if (net->dest_state & SCTP_ADDR_UNCONFIRMED) { in sctp_set_primary_addr()
6567 net->dest_state |= SCTP_ADDR_REQ_PRIMARY; in sctp_set_primary_addr()
6570 stcb->asoc.primary_destination = net; in sctp_set_primary_addr()
6571 if (((net->dest_state & SCTP_ADDR_PF) == 0) && in sctp_set_primary_addr()
6572 (stcb->asoc.alternate != NULL)) { in sctp_set_primary_addr()
6573 sctp_free_remote_addr(stcb->asoc.alternate); in sctp_set_primary_addr()
6574 stcb->asoc.alternate = NULL; in sctp_set_primary_addr()
6576 net = TAILQ_FIRST(&stcb->asoc.nets); in sctp_set_primary_addr()
6577 if (net != stcb->asoc.primary_destination) { in sctp_set_primary_addr()
6583 TAILQ_REMOVE(&stcb->asoc.nets, stcb->asoc.primary_destination, sctp_next); in sctp_set_primary_addr()
6584 TAILQ_INSERT_HEAD(&stcb->asoc.nets, stcb->asoc.primary_destination, sctp_next); in sctp_set_primary_addr()
6604 * this assumption, but we will go with it for now :-) in sctp_is_vtag_good()
6606 if (stcb->sctp_ep->sctp_flags & SCTP_PCB_FLAGS_SOCKET_ALLGONE) { in sctp_is_vtag_good()
6609 if (stcb->asoc.my_vtag == tag) { in sctp_is_vtag_good()
6611 if (stcb->rport != rport) { in sctp_is_vtag_good()
6614 if (stcb->sctp_ep->sctp_lport != lport) { in sctp_is_vtag_good()
6621 return (!sctp_is_in_timewait(tag, lport, rport, now->tv_sec)); in sctp_is_vtag_good()
6639 /* We look for anything larger than the cum-ack + 1 */ in sctp_drain_mbufs()
6641 asoc = &stcb->asoc; in sctp_drain_mbufs()
6642 if (asoc->cumulative_tsn == asoc->highest_tsn_inside_map) { in sctp_drain_mbufs()
6647 cumulative_tsn_p1 = asoc->cumulative_tsn + 1; in sctp_drain_mbufs()
6650 for (strmat = 0; strmat < asoc->streamincnt; strmat++) { in sctp_drain_mbufs()
6651 TAILQ_FOREACH_SAFE(control, &asoc->strmin[strmat].inqueue, next_instrm, ncontrol) { in sctp_drain_mbufs()
6653 if (control->on_strm_q != SCTP_ON_ORDERED) { in sctp_drain_mbufs()
6654 panic("Huh control: %p on_q: %d -- not ordered?", in sctp_drain_mbufs()
6655 control, control->on_strm_q); in sctp_drain_mbufs()
6658 if (SCTP_TSN_GT(control->sinfo_tsn, cumulative_tsn_p1)) { in sctp_drain_mbufs()
6659 /* Yep it is above cum-ack */ in sctp_drain_mbufs()
6661 SCTP_CALC_TSN_TO_GAP(gap, control->sinfo_tsn, asoc->mapping_array_base_tsn); in sctp_drain_mbufs()
6662 KASSERT(control->length > 0, ("control has zero length")); in sctp_drain_mbufs()
6663 if (asoc->size_on_all_streams >= control->length) { in sctp_drain_mbufs()
6664 asoc->size_on_all_streams -= control->length; in sctp_drain_mbufs()
6667 …ize_on_all_streams = %u smaller than control length %u", asoc->size_on_all_streams, control->lengt… in sctp_drain_mbufs()
6669 asoc->size_on_all_streams = 0; in sctp_drain_mbufs()
6672 sctp_ucount_decr(asoc->cnt_on_all_streams); in sctp_drain_mbufs()
6673 SCTP_UNSET_TSN_PRESENT(asoc->mapping_array, gap); in sctp_drain_mbufs()
6674 if (control->on_read_q) { in sctp_drain_mbufs()
6675 TAILQ_REMOVE(&stcb->sctp_ep->read_queue, control, next); in sctp_drain_mbufs()
6676 control->on_read_q = 0; in sctp_drain_mbufs()
6678 TAILQ_REMOVE(&asoc->strmin[strmat].inqueue, control, next_instrm); in sctp_drain_mbufs()
6679 control->on_strm_q = 0; in sctp_drain_mbufs()
6680 if (control->data) { in sctp_drain_mbufs()
6681 sctp_m_freem(control->data); in sctp_drain_mbufs()
6682 control->data = NULL; in sctp_drain_mbufs()
6684 sctp_free_remote_addr(control->whoFrom); in sctp_drain_mbufs()
6686 TAILQ_FOREACH_SAFE(chk, &control->reasm, sctp_next, nchk) { in sctp_drain_mbufs()
6688 SCTP_CALC_TSN_TO_GAP(gap, chk->rec.data.tsn, asoc->mapping_array_base_tsn); in sctp_drain_mbufs()
6689 KASSERT(chk->send_size > 0, ("chunk has zero length")); in sctp_drain_mbufs()
6690 if (asoc->size_on_reasm_queue >= chk->send_size) { in sctp_drain_mbufs()
6691 asoc->size_on_reasm_queue -= chk->send_size; in sctp_drain_mbufs()
6694 …c("size_on_reasm_queue = %u smaller than chunk length %u", asoc->size_on_reasm_queue, chk->send_si… in sctp_drain_mbufs()
6696 asoc->size_on_reasm_queue = 0; in sctp_drain_mbufs()
6699 sctp_ucount_decr(asoc->cnt_on_reasm_queue); in sctp_drain_mbufs()
6700 SCTP_UNSET_TSN_PRESENT(asoc->mapping_array, gap); in sctp_drain_mbufs()
6701 TAILQ_REMOVE(&control->reasm, chk, sctp_next); in sctp_drain_mbufs()
6702 if (chk->data) { in sctp_drain_mbufs()
6703 sctp_m_freem(chk->data); in sctp_drain_mbufs()
6704 chk->data = NULL; in sctp_drain_mbufs()
6711 TAILQ_FOREACH_SAFE(control, &asoc->strmin[strmat].uno_inqueue, next_instrm, ncontrol) { in sctp_drain_mbufs()
6713 if (control->on_strm_q != SCTP_ON_UNORDERED) { in sctp_drain_mbufs()
6714 panic("Huh control: %p on_q: %d -- not unordered?", in sctp_drain_mbufs()
6715 control, control->on_strm_q); in sctp_drain_mbufs()
6718 if (SCTP_TSN_GT(control->sinfo_tsn, cumulative_tsn_p1)) { in sctp_drain_mbufs()
6719 /* Yep it is above cum-ack */ in sctp_drain_mbufs()
6721 SCTP_CALC_TSN_TO_GAP(gap, control->sinfo_tsn, asoc->mapping_array_base_tsn); in sctp_drain_mbufs()
6722 KASSERT(control->length > 0, ("control has zero length")); in sctp_drain_mbufs()
6723 if (asoc->size_on_all_streams >= control->length) { in sctp_drain_mbufs()
6724 asoc->size_on_all_streams -= control->length; in sctp_drain_mbufs()
6727 …ize_on_all_streams = %u smaller than control length %u", asoc->size_on_all_streams, control->lengt… in sctp_drain_mbufs()
6729 asoc->size_on_all_streams = 0; in sctp_drain_mbufs()
6732 sctp_ucount_decr(asoc->cnt_on_all_streams); in sctp_drain_mbufs()
6733 SCTP_UNSET_TSN_PRESENT(asoc->mapping_array, gap); in sctp_drain_mbufs()
6734 if (control->on_read_q) { in sctp_drain_mbufs()
6735 TAILQ_REMOVE(&stcb->sctp_ep->read_queue, control, next); in sctp_drain_mbufs()
6736 control->on_read_q = 0; in sctp_drain_mbufs()
6738 TAILQ_REMOVE(&asoc->strmin[strmat].uno_inqueue, control, next_instrm); in sctp_drain_mbufs()
6739 control->on_strm_q = 0; in sctp_drain_mbufs()
6740 if (control->data) { in sctp_drain_mbufs()
6741 sctp_m_freem(control->data); in sctp_drain_mbufs()
6742 control->data = NULL; in sctp_drain_mbufs()
6744 sctp_free_remote_addr(control->whoFrom); in sctp_drain_mbufs()
6746 TAILQ_FOREACH_SAFE(chk, &control->reasm, sctp_next, nchk) { in sctp_drain_mbufs()
6748 SCTP_CALC_TSN_TO_GAP(gap, chk->rec.data.tsn, asoc->mapping_array_base_tsn); in sctp_drain_mbufs()
6749 KASSERT(chk->send_size > 0, ("chunk has zero length")); in sctp_drain_mbufs()
6750 if (asoc->size_on_reasm_queue >= chk->send_size) { in sctp_drain_mbufs()
6751 asoc->size_on_reasm_queue -= chk->send_size; in sctp_drain_mbufs()
6754 …c("size_on_reasm_queue = %u smaller than chunk length %u", asoc->size_on_reasm_queue, chk->send_si… in sctp_drain_mbufs()
6756 asoc->size_on_reasm_queue = 0; in sctp_drain_mbufs()
6759 sctp_ucount_decr(asoc->cnt_on_reasm_queue); in sctp_drain_mbufs()
6760 SCTP_UNSET_TSN_PRESENT(asoc->mapping_array, gap); in sctp_drain_mbufs()
6761 TAILQ_REMOVE(&control->reasm, chk, sctp_next); in sctp_drain_mbufs()
6762 if (chk->data) { in sctp_drain_mbufs()
6763 sctp_m_freem(chk->data); in sctp_drain_mbufs()
6764 chk->data = NULL; in sctp_drain_mbufs()
6774 for (i = asoc->highest_tsn_inside_map; SCTP_TSN_GE(i, asoc->mapping_array_base_tsn); i--) { in sctp_drain_mbufs()
6775 SCTP_CALC_TSN_TO_GAP(gap, i, asoc->mapping_array_base_tsn); in sctp_drain_mbufs()
6776 if (SCTP_IS_TSN_PRESENT(asoc->mapping_array, gap)) { in sctp_drain_mbufs()
6777 asoc->highest_tsn_inside_map = i; in sctp_drain_mbufs()
6783 asoc->highest_tsn_inside_map = asoc->mapping_array_base_tsn - 1; in sctp_drain_mbufs()
6789 * a p-d-api up. An attacker COULD send enough in to in sctp_drain_mbufs()
6790 * initiate the PD-API and then send a bunch of stuff to in sctp_drain_mbufs()
6793 * to do this I then have to back-track and un-deliver in sctp_drain_mbufs()
6794 * sequence numbers in streams.. el-yucko. I think for now in sctp_drain_mbufs()
6797 * abort the P-D-API with a notification and then deliver in sctp_drain_mbufs()
6807 * asoc->highest_tsn_inside_map? in sctp_drain_mbufs()
6809 asoc->last_revoke_count = cnt; in sctp_drain_mbufs()
6810 sctp_timer_stop(SCTP_TIMER_TYPE_RECV, stcb->sctp_ep, stcb, NULL, in sctp_drain_mbufs()
6814 sctp_chunk_output(stcb->sctp_ep, stcb, SCTP_OUTPUT_FROM_DRAIN, SCTP_SO_NOT_LOCKED); in sctp_drain_mbufs()
6817 * Another issue, in un-setting the TSN's in the mapping array we in sctp_drain_mbufs()
6822 * we will recover once we get our cum-ack above and all this stuff in sctp_drain_mbufs()
6859 LIST_FOREACH(stcb, &inp->sctp_asoc_list, sctp_tcblist) { in sctp_drain()
6902 return (-1); in sctp_initiate_iterator()
6907 return (-1); in sctp_initiate_iterator()
6913 return (-1); in sctp_initiate_iterator()
6916 it->function_assoc = af; in sctp_initiate_iterator()
6917 it->function_inp = inpf; in sctp_initiate_iterator()
6919 it->done_current_ep = 0; in sctp_initiate_iterator()
6921 it->done_current_ep = 1; in sctp_initiate_iterator()
6922 it->function_atend = ef; in sctp_initiate_iterator()
6923 it->pointer = argp; in sctp_initiate_iterator()
6924 it->val = argi; in sctp_initiate_iterator()
6925 it->pcb_flags = pcb_state; in sctp_initiate_iterator()
6926 it->pcb_features = pcb_features; in sctp_initiate_iterator()
6927 it->asoc_state = asoc_state; in sctp_initiate_iterator()
6928 it->function_inp_end = inpe; in sctp_initiate_iterator()
6929 it->no_chunk_output = chunk_output_off; in sctp_initiate_iterator()
6930 it->vn = curvnet; in sctp_initiate_iterator()
6933 it->inp = s_inp; in sctp_initiate_iterator()
6934 SCTP_INP_INCR_REF(it->inp); in sctp_initiate_iterator()
6935 it->iterator_flags = SCTP_ITERATOR_DO_SINGLE_INP; in sctp_initiate_iterator()
6938 it->inp = LIST_FIRST(&SCTP_BASE_INFO(listhead)); in sctp_initiate_iterator()
6939 if (it->inp) { in sctp_initiate_iterator()
6940 SCTP_INP_INCR_REF(it->inp); in sctp_initiate_iterator()
6943 it->iterator_flags = SCTP_ITERATOR_DO_ALL_INP; in sctp_initiate_iterator()
6951 return (-1); in sctp_initiate_iterator()
6972 old_flags = inp->sctp_flags; in sctp_pcb_add_flags()
6974 } while (atomic_cmpset_int(&inp->sctp_flags, old_flags, new_flags) == 0); in sctp_pcb_add_flags()