Move files from gst-plugins-bad into the "subprojects/gst-plugins-bad/" subdir
[platform/upstream/gstreamer.git] / subprojects / gst-plugins-bad / ext / sctp / usrsctp / usrsctplib / netinet / sctp_asconf.c
1 /*-
2  * SPDX-License-Identifier: BSD-3-Clause
3  *
4  * Copyright (c) 2001-2007, 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.
7  *
8  * Redistribution and use in source and binary forms, with or without
9  * modification, are permitted provided that the following conditions are met:
10  *
11  * a) Redistributions of source code must retain the above copyright notice,
12  *    this list of conditions and the following disclaimer.
13  *
14  * b) Redistributions in binary form must reproduce the above copyright
15  *    notice, this list of conditions and the following disclaimer in
16  *    the documentation and/or other materials provided with the distribution.
17  *
18  * c) Neither the name of Cisco Systems, Inc. nor the names of its
19  *    contributors may be used to endorse or promote products derived
20  *    from this software without specific prior written permission.
21  *
22  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
23  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
24  * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
25  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
26  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
27  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
28  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
29  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
30  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
31  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
32  * THE POSSIBILITY OF SUCH DAMAGE.
33  */
34
35 #if defined(__FreeBSD__) && !defined(__Userspace__)
36 #include <sys/cdefs.h>
37 __FBSDID("$FreeBSD: head/sys/netinet/sctp_asconf.c 363194 2020-07-14 20:32:50Z tuexen $");
38 #endif
39
40 #include <netinet/sctp_os.h>
41 #include <netinet/sctp_var.h>
42 #include <netinet/sctp_sysctl.h>
43 #include <netinet/sctp_pcb.h>
44 #include <netinet/sctp_header.h>
45 #include <netinet/sctputil.h>
46 #include <netinet/sctp_output.h>
47 #include <netinet/sctp_asconf.h>
48 #include <netinet/sctp_timer.h>
49
50 /*
51  * debug flags:
52  * SCTP_DEBUG_ASCONF1: protocol info, general info and errors
53  * SCTP_DEBUG_ASCONF2: detailed info
54  */
55
56 /*
57  * RFC 5061
58  *
59  * An ASCONF parameter queue exists per asoc which holds the pending address
60  * operations.  Lists are updated upon receipt of ASCONF-ACK.
61  *
62  * A restricted_addrs list exists per assoc to hold local addresses that are
63  * not (yet) usable by the assoc as a source address.  These addresses are
64  * either pending an ASCONF operation (and exist on the ASCONF parameter
65  * queue), or they are permanently restricted (the peer has returned an
66  * ERROR indication to an ASCONF(ADD), or the peer does not support ASCONF).
67  *
68  * Deleted addresses are always immediately removed from the lists as they will
69  * (shortly) no longer exist in the kernel.  We send ASCONFs as a courtesy,
70  * only if allowed.
71  */
72
73 /*
74  * ASCONF parameter processing.
75  * response_required: set if a reply is required (eg. SUCCESS_REPORT).
76  * returns a mbuf to an "error" response parameter or NULL/"success" if ok.
77  * FIX: allocating this many mbufs on the fly is pretty inefficient...
78  */
79 static struct mbuf *
80 sctp_asconf_success_response(uint32_t id)
81 {
82         struct mbuf *m_reply = NULL;
83         struct sctp_asconf_paramhdr *aph;
84
85         m_reply = sctp_get_mbuf_for_msg(sizeof(struct sctp_asconf_paramhdr),
86                                         0, M_NOWAIT, 1, MT_DATA);
87         if (m_reply == NULL) {
88                 SCTPDBG(SCTP_DEBUG_ASCONF1,
89                         "asconf_success_response: couldn't get mbuf!\n");
90                 return (NULL);
91         }
92         aph = mtod(m_reply, struct sctp_asconf_paramhdr *);
93         aph->correlation_id = id;
94         aph->ph.param_type = htons(SCTP_SUCCESS_REPORT);
95         aph->ph.param_length = sizeof(struct sctp_asconf_paramhdr);
96         SCTP_BUF_LEN(m_reply) = aph->ph.param_length;
97         aph->ph.param_length = htons(aph->ph.param_length);
98
99         return (m_reply);
100 }
101
102 static struct mbuf *
103 sctp_asconf_error_response(uint32_t id, uint16_t cause, uint8_t *error_tlv,
104                            uint16_t tlv_length)
105 {
106         struct mbuf *m_reply = NULL;
107         struct sctp_asconf_paramhdr *aph;
108         struct sctp_error_cause *error;
109         uint32_t buf_len;
110         uint16_t i, param_length, cause_length, padding_length;
111         uint8_t *tlv;
112
113         if (error_tlv == NULL) {
114                 tlv_length = 0;
115         }
116         cause_length = sizeof(struct sctp_error_cause) + tlv_length;
117         param_length = sizeof(struct sctp_asconf_paramhdr) + cause_length;
118         padding_length = tlv_length % 4;
119         if (padding_length != 0) {
120                 padding_length = 4 - padding_length;
121         }
122         buf_len = param_length + padding_length;
123         if (buf_len > MLEN) {
124                 SCTPDBG(SCTP_DEBUG_ASCONF1,
125                         "asconf_error_response: tlv_length (%xh) too big\n",
126                         tlv_length);
127                 return (NULL);
128         }
129         m_reply = sctp_get_mbuf_for_msg(buf_len, 0, M_NOWAIT, 1, MT_DATA);
130         if (m_reply == NULL) {
131                 SCTPDBG(SCTP_DEBUG_ASCONF1,
132                         "asconf_error_response: couldn't get mbuf!\n");
133                 return (NULL);
134         }
135         aph = mtod(m_reply, struct sctp_asconf_paramhdr *);
136         aph->ph.param_type = htons(SCTP_ERROR_CAUSE_IND);
137         aph->ph.param_length = htons(param_length);
138         aph->correlation_id = id;
139         error = (struct sctp_error_cause *)(aph + 1);
140         error->code = htons(cause);
141         error->length = htons(cause_length);
142         if (error_tlv != NULL) {
143                 tlv = (uint8_t *) (error + 1);
144                 memcpy(tlv, error_tlv, tlv_length);
145                 for (i = 0; i < padding_length; i++) {
146                         tlv[tlv_length + i] = 0;
147                 }
148         }
149         SCTP_BUF_LEN(m_reply) = buf_len;
150         return (m_reply);
151 }
152
153 static struct mbuf *
154 sctp_process_asconf_add_ip(struct sockaddr *src, struct sctp_asconf_paramhdr *aph,
155                            struct sctp_tcb *stcb, int send_hb, int response_required)
156 {
157         struct sctp_nets *net;
158         struct mbuf *m_reply = NULL;
159         union sctp_sockstore store;
160         struct sctp_paramhdr *ph;
161         uint16_t param_type, aparam_length;
162 #if defined(INET) || defined(INET6)
163         uint16_t param_length;
164 #endif
165         struct sockaddr *sa;
166         int zero_address = 0;
167         int bad_address = 0;
168 #ifdef INET
169         struct sockaddr_in *sin;
170         struct sctp_ipv4addr_param *v4addr;
171 #endif
172 #ifdef INET6
173         struct sockaddr_in6 *sin6;
174         struct sctp_ipv6addr_param *v6addr;
175 #endif
176
177         aparam_length = ntohs(aph->ph.param_length);
178         if (aparam_length < sizeof(struct sctp_asconf_paramhdr) + sizeof(struct sctp_paramhdr)) {
179                 return (NULL);
180         }
181         ph = (struct sctp_paramhdr *)(aph + 1);
182         param_type = ntohs(ph->param_type);
183 #if defined(INET) || defined(INET6)
184         param_length = ntohs(ph->param_length);
185         if (param_length + sizeof(struct sctp_asconf_paramhdr) != aparam_length) {
186                 return (NULL);
187         }
188 #endif
189         sa = &store.sa;
190         switch (param_type) {
191 #ifdef INET
192         case SCTP_IPV4_ADDRESS:
193                 if (param_length != sizeof(struct sctp_ipv4addr_param)) {
194                         /* invalid param size */
195                         return (NULL);
196                 }
197                 v4addr = (struct sctp_ipv4addr_param *)ph;
198                 sin = &store.sin;
199                 memset(sin, 0, sizeof(*sin));
200                 sin->sin_family = AF_INET;
201 #ifdef HAVE_SIN_LEN
202                 sin->sin_len = sizeof(struct sockaddr_in);
203 #endif
204                 sin->sin_port = stcb->rport;
205                 sin->sin_addr.s_addr = v4addr->addr;
206                 if ((sin->sin_addr.s_addr == INADDR_BROADCAST) ||
207                     IN_MULTICAST(ntohl(sin->sin_addr.s_addr))) {
208                         bad_address = 1;
209                 }
210                 if (sin->sin_addr.s_addr == INADDR_ANY)
211                         zero_address = 1;
212                 SCTPDBG(SCTP_DEBUG_ASCONF1, "process_asconf_add_ip: adding ");
213                 SCTPDBG_ADDR(SCTP_DEBUG_ASCONF1, sa);
214                 break;
215 #endif
216 #ifdef INET6
217         case SCTP_IPV6_ADDRESS:
218                 if (param_length != sizeof(struct sctp_ipv6addr_param)) {
219                         /* invalid param size */
220                         return (NULL);
221                 }
222                 v6addr = (struct sctp_ipv6addr_param *)ph;
223                 sin6 = &store.sin6;
224                 memset(sin6, 0, sizeof(*sin6));
225                 sin6->sin6_family = AF_INET6;
226 #ifdef HAVE_SIN6_LEN
227                 sin6->sin6_len = sizeof(struct sockaddr_in6);
228 #endif
229                 sin6->sin6_port = stcb->rport;
230                 memcpy((caddr_t)&sin6->sin6_addr, v6addr->addr,
231                     sizeof(struct in6_addr));
232                 if (IN6_IS_ADDR_MULTICAST(&sin6->sin6_addr)) {
233                         bad_address = 1;
234                 }
235                 if (IN6_IS_ADDR_UNSPECIFIED(&sin6->sin6_addr))
236                         zero_address = 1;
237                 SCTPDBG(SCTP_DEBUG_ASCONF1, "process_asconf_add_ip: adding ");
238                 SCTPDBG_ADDR(SCTP_DEBUG_ASCONF1, sa);
239                 break;
240 #endif
241         default:
242                 m_reply = sctp_asconf_error_response(aph->correlation_id,
243                     SCTP_CAUSE_INVALID_PARAM, (uint8_t *) aph,
244                     aparam_length);
245                 return (m_reply);
246         }                       /* end switch */
247
248         /* if 0.0.0.0/::0, add the source address instead */
249         if (zero_address && SCTP_BASE_SYSCTL(sctp_nat_friendly)) {
250                 sa = src;
251                 SCTPDBG(SCTP_DEBUG_ASCONF1,
252                         "process_asconf_add_ip: using source addr ");
253                 SCTPDBG_ADDR(SCTP_DEBUG_ASCONF1, src);
254         }
255         net = NULL;
256         /* add the address */
257         if (bad_address) {
258                 m_reply = sctp_asconf_error_response(aph->correlation_id,
259                     SCTP_CAUSE_INVALID_PARAM, (uint8_t *) aph,
260                     aparam_length);
261         } else if (sctp_add_remote_addr(stcb, sa, &net, stcb->asoc.port,
262                                         SCTP_DONOT_SETSCOPE,
263                                         SCTP_ADDR_DYNAMIC_ADDED) != 0) {
264                 SCTPDBG(SCTP_DEBUG_ASCONF1,
265                         "process_asconf_add_ip: error adding address\n");
266                 m_reply = sctp_asconf_error_response(aph->correlation_id,
267                     SCTP_CAUSE_RESOURCE_SHORTAGE, (uint8_t *) aph,
268                     aparam_length);
269         } else {
270                 if (response_required) {
271                         m_reply =
272                             sctp_asconf_success_response(aph->correlation_id);
273                 }
274                 if (net != NULL) {
275                         /* notify upper layer */
276                         sctp_ulp_notify(SCTP_NOTIFY_ASCONF_ADD_IP, stcb, 0, sa, SCTP_SO_NOT_LOCKED);
277                         sctp_timer_start(SCTP_TIMER_TYPE_PATHMTURAISE, stcb->sctp_ep, stcb, net);
278                         sctp_timer_start(SCTP_TIMER_TYPE_HEARTBEAT, stcb->sctp_ep,
279                                          stcb, net);
280                         if (send_hb) {
281                                 sctp_send_hb(stcb, net, SCTP_SO_NOT_LOCKED);
282                         }
283                 }
284         }
285         return (m_reply);
286 }
287
288 static int
289 sctp_asconf_del_remote_addrs_except(struct sctp_tcb *stcb, struct sockaddr *src)
290 {
291         struct sctp_nets *src_net, *net, *nnet;
292
293         /* make sure the source address exists as a destination net */
294         src_net = sctp_findnet(stcb, src);
295         if (src_net == NULL) {
296                 /* not found */
297                 return (-1);
298         }
299
300         /* delete all destination addresses except the source */
301         TAILQ_FOREACH_SAFE(net, &stcb->asoc.nets, sctp_next, nnet) {
302                 if (net != src_net) {
303                         /* delete this address */
304                         SCTPDBG(SCTP_DEBUG_ASCONF1,
305                                 "asconf_del_remote_addrs_except: deleting ");
306                         SCTPDBG_ADDR(SCTP_DEBUG_ASCONF1,
307                                      (struct sockaddr *)&net->ro._l_addr);
308                         /* notify upper layer */
309                         sctp_ulp_notify(SCTP_NOTIFY_ASCONF_DELETE_IP, stcb, 0,
310                             (struct sockaddr *)&net->ro._l_addr, SCTP_SO_NOT_LOCKED);
311                         sctp_remove_net(stcb, net);
312                 }
313         }
314         return (0);
315 }
316
317 static struct mbuf *
318 sctp_process_asconf_delete_ip(struct sockaddr *src,
319                               struct sctp_asconf_paramhdr *aph,
320                               struct sctp_tcb *stcb, int response_required)
321 {
322         struct mbuf *m_reply = NULL;
323         union sctp_sockstore store;
324         struct sctp_paramhdr *ph;
325         uint16_t param_type, aparam_length;
326 #if defined(INET) || defined(INET6)
327         uint16_t param_length;
328 #endif
329         struct sockaddr *sa;
330         int zero_address = 0;
331         int result;
332 #ifdef INET
333         struct sockaddr_in *sin;
334         struct sctp_ipv4addr_param *v4addr;
335 #endif
336 #ifdef INET6
337         struct sockaddr_in6 *sin6;
338         struct sctp_ipv6addr_param *v6addr;
339 #endif
340
341         aparam_length = ntohs(aph->ph.param_length);
342         if (aparam_length < sizeof(struct sctp_asconf_paramhdr) + sizeof(struct sctp_paramhdr)) {
343                 return (NULL);
344         }
345         ph = (struct sctp_paramhdr *)(aph + 1);
346         param_type = ntohs(ph->param_type);
347 #if defined(INET) || defined(INET6)
348         param_length = ntohs(ph->param_length);
349         if (param_length + sizeof(struct sctp_asconf_paramhdr) != aparam_length) {
350                 return (NULL);
351         }
352 #endif
353         sa = &store.sa;
354         switch (param_type) {
355 #ifdef INET
356         case SCTP_IPV4_ADDRESS:
357                 if (param_length != sizeof(struct sctp_ipv4addr_param)) {
358                         /* invalid param size */
359                         return (NULL);
360                 }
361                 v4addr = (struct sctp_ipv4addr_param *)ph;
362                 sin = &store.sin;
363                 memset(sin, 0, sizeof(*sin));
364                 sin->sin_family = AF_INET;
365 #ifdef HAVE_SIN_LEN
366                 sin->sin_len = sizeof(struct sockaddr_in);
367 #endif
368                 sin->sin_port = stcb->rport;
369                 sin->sin_addr.s_addr = v4addr->addr;
370                 if (sin->sin_addr.s_addr == INADDR_ANY)
371                         zero_address = 1;
372                 SCTPDBG(SCTP_DEBUG_ASCONF1,
373                         "process_asconf_delete_ip: deleting ");
374                 SCTPDBG_ADDR(SCTP_DEBUG_ASCONF1, sa);
375                 break;
376 #endif
377 #ifdef INET6
378         case SCTP_IPV6_ADDRESS:
379                 if (param_length != sizeof(struct sctp_ipv6addr_param)) {
380                         /* invalid param size */
381                         return (NULL);
382                 }
383                 v6addr = (struct sctp_ipv6addr_param *)ph;
384                 sin6 = &store.sin6;
385                 memset(sin6, 0, sizeof(*sin6));
386                 sin6->sin6_family = AF_INET6;
387 #ifdef HAVE_SIN6_LEN
388                 sin6->sin6_len = sizeof(struct sockaddr_in6);
389 #endif
390                 sin6->sin6_port = stcb->rport;
391                 memcpy(&sin6->sin6_addr, v6addr->addr,
392                     sizeof(struct in6_addr));
393                 if (IN6_IS_ADDR_UNSPECIFIED(&sin6->sin6_addr))
394                         zero_address = 1;
395                 SCTPDBG(SCTP_DEBUG_ASCONF1,
396                         "process_asconf_delete_ip: deleting ");
397                 SCTPDBG_ADDR(SCTP_DEBUG_ASCONF1, sa);
398                 break;
399 #endif
400         default:
401                 m_reply = sctp_asconf_error_response(aph->correlation_id,
402                     SCTP_CAUSE_UNRESOLVABLE_ADDR, (uint8_t *) aph,
403                     aparam_length);
404                 return (m_reply);
405         }
406
407         /* make sure the source address is not being deleted */
408         if (sctp_cmpaddr(sa, src)) {
409                 /* trying to delete the source address! */
410                 SCTPDBG(SCTP_DEBUG_ASCONF1, "process_asconf_delete_ip: tried to delete source addr\n");
411                 m_reply = sctp_asconf_error_response(aph->correlation_id,
412                     SCTP_CAUSE_DELETING_SRC_ADDR, (uint8_t *) aph,
413                     aparam_length);
414                 return (m_reply);
415         }
416
417         /* if deleting 0.0.0.0/::0, delete all addresses except src addr */
418         if (zero_address && SCTP_BASE_SYSCTL(sctp_nat_friendly)) {
419                 result = sctp_asconf_del_remote_addrs_except(stcb, src);
420
421                 if (result) {
422                         /* src address did not exist? */
423                         SCTPDBG(SCTP_DEBUG_ASCONF1, "process_asconf_delete_ip: src addr does not exist?\n");
424                         /* what error to reply with?? */
425                         m_reply =
426                             sctp_asconf_error_response(aph->correlation_id,
427                             SCTP_CAUSE_REQUEST_REFUSED, (uint8_t *) aph,
428                             aparam_length);
429                 } else if (response_required) {
430                         m_reply =
431                             sctp_asconf_success_response(aph->correlation_id);
432                 }
433                 return (m_reply);
434         }
435
436         /* delete the address */
437         result = sctp_del_remote_addr(stcb, sa);
438         /*
439          * note if result == -2, the address doesn't exist in the asoc but
440          * since it's being deleted anyways, we just ack the delete -- but
441          * this probably means something has already gone awry
442          */
443         if (result == -1) {
444                 /* only one address in the asoc */
445                 SCTPDBG(SCTP_DEBUG_ASCONF1, "process_asconf_delete_ip: tried to delete last IP addr!\n");
446                 m_reply = sctp_asconf_error_response(aph->correlation_id,
447                     SCTP_CAUSE_DELETING_LAST_ADDR, (uint8_t *) aph,
448                     aparam_length);
449         } else {
450                 if (response_required) {
451                         m_reply = sctp_asconf_success_response(aph->correlation_id);
452                 }
453                 /* notify upper layer */
454                 sctp_ulp_notify(SCTP_NOTIFY_ASCONF_DELETE_IP, stcb, 0, sa, SCTP_SO_NOT_LOCKED);
455         }
456         return (m_reply);
457 }
458
459 static struct mbuf *
460 sctp_process_asconf_set_primary(struct sockaddr *src,
461                                 struct sctp_asconf_paramhdr *aph,
462                                 struct sctp_tcb *stcb, int response_required)
463 {
464         struct mbuf *m_reply = NULL;
465         union sctp_sockstore store;
466         struct sctp_paramhdr *ph;
467         uint16_t param_type, aparam_length;
468 #if defined(INET) || defined(INET6)
469         uint16_t param_length;
470 #endif
471         struct sockaddr *sa;
472         int zero_address = 0;
473 #ifdef INET
474         struct sockaddr_in *sin;
475         struct sctp_ipv4addr_param *v4addr;
476 #endif
477 #ifdef INET6
478         struct sockaddr_in6 *sin6;
479         struct sctp_ipv6addr_param *v6addr;
480 #endif
481
482         aparam_length = ntohs(aph->ph.param_length);
483         if (aparam_length < sizeof(struct sctp_asconf_paramhdr) + sizeof(struct sctp_paramhdr)) {
484                 return (NULL);
485         }
486         ph = (struct sctp_paramhdr *)(aph + 1);
487         param_type = ntohs(ph->param_type);
488 #if defined(INET) || defined(INET6)
489         param_length = ntohs(ph->param_length);
490         if (param_length + sizeof(struct sctp_asconf_paramhdr) != aparam_length) {
491                 return (NULL);
492         }
493 #endif
494         sa = &store.sa;
495         switch (param_type) {
496 #ifdef INET
497         case SCTP_IPV4_ADDRESS:
498                 if (param_length != sizeof(struct sctp_ipv4addr_param)) {
499                         /* invalid param size */
500                         return (NULL);
501                 }
502                 v4addr = (struct sctp_ipv4addr_param *)ph;
503                 sin = &store.sin;
504                 memset(sin, 0, sizeof(*sin));
505                 sin->sin_family = AF_INET;
506 #ifdef HAVE_SIN_LEN
507                 sin->sin_len = sizeof(struct sockaddr_in);
508 #endif
509                 sin->sin_addr.s_addr = v4addr->addr;
510                 if (sin->sin_addr.s_addr == INADDR_ANY)
511                         zero_address = 1;
512                 SCTPDBG(SCTP_DEBUG_ASCONF1, "process_asconf_set_primary: ");
513                 SCTPDBG_ADDR(SCTP_DEBUG_ASCONF1, sa);
514                 break;
515 #endif
516 #ifdef INET6
517         case SCTP_IPV6_ADDRESS:
518                 if (param_length != sizeof(struct sctp_ipv6addr_param)) {
519                         /* invalid param size */
520                         return (NULL);
521                 }
522                 v6addr = (struct sctp_ipv6addr_param *)ph;
523                 sin6 = &store.sin6;
524                 memset(sin6, 0, sizeof(*sin6));
525                 sin6->sin6_family = AF_INET6;
526 #ifdef HAVE_SIN6_LEN
527                 sin6->sin6_len = sizeof(struct sockaddr_in6);
528 #endif
529                 memcpy((caddr_t)&sin6->sin6_addr, v6addr->addr,
530                     sizeof(struct in6_addr));
531                 if (IN6_IS_ADDR_UNSPECIFIED(&sin6->sin6_addr))
532                         zero_address = 1;
533                 SCTPDBG(SCTP_DEBUG_ASCONF1, "process_asconf_set_primary: ");
534                 SCTPDBG_ADDR(SCTP_DEBUG_ASCONF1, sa);
535                 break;
536 #endif
537         default:
538                 m_reply = sctp_asconf_error_response(aph->correlation_id,
539                     SCTP_CAUSE_UNRESOLVABLE_ADDR, (uint8_t *) aph,
540                     aparam_length);
541                 return (m_reply);
542         }
543
544         /* if 0.0.0.0/::0, use the source address instead */
545         if (zero_address && SCTP_BASE_SYSCTL(sctp_nat_friendly)) {
546                 sa = src;
547                 SCTPDBG(SCTP_DEBUG_ASCONF1,
548                         "process_asconf_set_primary: using source addr ");
549                 SCTPDBG_ADDR(SCTP_DEBUG_ASCONF1, src);
550         }
551         /* set the primary address */
552         if (sctp_set_primary_addr(stcb, sa, NULL) == 0) {
553                 SCTPDBG(SCTP_DEBUG_ASCONF1,
554                         "process_asconf_set_primary: primary address set\n");
555                 /* notify upper layer */
556                 sctp_ulp_notify(SCTP_NOTIFY_ASCONF_SET_PRIMARY, stcb, 0, sa, SCTP_SO_NOT_LOCKED);
557                 if ((stcb->asoc.primary_destination->dest_state & SCTP_ADDR_REACHABLE) &&
558                     (!(stcb->asoc.primary_destination->dest_state & SCTP_ADDR_PF)) &&
559                     (stcb->asoc.alternate)) {
560                         sctp_free_remote_addr(stcb->asoc.alternate);
561                         stcb->asoc.alternate = NULL;
562                 }
563                 if (response_required) {
564                         m_reply = sctp_asconf_success_response(aph->correlation_id);
565                 }
566                 /* Mobility adaptation.
567                    Ideally, when the reception of SET PRIMARY with DELETE IP
568                    ADDRESS of the previous primary destination, unacknowledged
569                    DATA are retransmitted immediately to the new primary
570                    destination for seamless handover.
571                    If the destination is UNCONFIRMED and marked to REQ_PRIM,
572                    The retransmission occur when reception of the
573                    HEARTBEAT-ACK.  (See sctp_handle_heartbeat_ack in
574                    sctp_input.c)
575                    Also, when change of the primary destination, it is better
576                    that all subsequent new DATA containing already queued DATA
577                    are transmitted to the new primary destination. (by micchie)
578                  */
579                 if ((sctp_is_mobility_feature_on(stcb->sctp_ep,
580                                                  SCTP_MOBILITY_BASE) ||
581                     sctp_is_mobility_feature_on(stcb->sctp_ep,
582                                                 SCTP_MOBILITY_FASTHANDOFF)) &&
583                     sctp_is_mobility_feature_on(stcb->sctp_ep,
584                                                 SCTP_MOBILITY_PRIM_DELETED) &&
585                     (stcb->asoc.primary_destination->dest_state &
586                      SCTP_ADDR_UNCONFIRMED) == 0) {
587
588                         sctp_timer_stop(SCTP_TIMER_TYPE_PRIM_DELETED,
589                                         stcb->sctp_ep, stcb, NULL,
590                                         SCTP_FROM_SCTP_ASCONF + SCTP_LOC_1);
591                         if (sctp_is_mobility_feature_on(stcb->sctp_ep,
592                                         SCTP_MOBILITY_FASTHANDOFF)) {
593                                 sctp_assoc_immediate_retrans(stcb,
594                                                 stcb->asoc.primary_destination);
595                         }
596                         if (sctp_is_mobility_feature_on(stcb->sctp_ep,
597                                         SCTP_MOBILITY_BASE)) {
598                                 sctp_move_chunks_from_net(stcb,
599                                                 stcb->asoc.deleted_primary);
600                         }
601                         sctp_delete_prim_timer(stcb->sctp_ep, stcb);
602                 }
603         } else {
604                 /* couldn't set the requested primary address! */
605                 SCTPDBG(SCTP_DEBUG_ASCONF1,
606                         "process_asconf_set_primary: set primary failed!\n");
607                 /* must have been an invalid address, so report */
608                 m_reply = sctp_asconf_error_response(aph->correlation_id,
609                     SCTP_CAUSE_UNRESOLVABLE_ADDR, (uint8_t *) aph,
610                     aparam_length);
611         }
612
613         return (m_reply);
614 }
615
616 /*
617  * handles an ASCONF chunk.
618  * if all parameters are processed ok, send a plain (empty) ASCONF-ACK
619  */
620 void
621 sctp_handle_asconf(struct mbuf *m, unsigned int offset,
622                    struct sockaddr *src,
623                    struct sctp_asconf_chunk *cp, struct sctp_tcb *stcb,
624                    int first)
625 {
626         struct sctp_association *asoc;
627         uint32_t serial_num;
628         struct mbuf *n, *m_ack, *m_result, *m_tail;
629         struct sctp_asconf_ack_chunk *ack_cp;
630         struct sctp_asconf_paramhdr *aph;
631         struct sctp_ipv6addr_param *p_addr;
632         unsigned int asconf_limit, cnt;
633         int error = 0;          /* did an error occur? */
634
635         /* asconf param buffer */
636         uint8_t aparam_buf[SCTP_PARAM_BUFFER_SIZE];
637         struct sctp_asconf_ack *ack, *ack_next;
638
639         /* verify minimum length */
640         if (ntohs(cp->ch.chunk_length) < sizeof(struct sctp_asconf_chunk)) {
641                 SCTPDBG(SCTP_DEBUG_ASCONF1,
642                         "handle_asconf: chunk too small = %xh\n",
643                         ntohs(cp->ch.chunk_length));
644                 return;
645         }
646         asoc = &stcb->asoc;
647         serial_num = ntohl(cp->serial_number);
648
649         if (SCTP_TSN_GE(asoc->asconf_seq_in, serial_num)) {
650                 /* got a duplicate ASCONF */
651                 SCTPDBG(SCTP_DEBUG_ASCONF1,
652                         "handle_asconf: got duplicate serial number = %xh\n",
653                         serial_num);
654                 return;
655         } else if (serial_num != (asoc->asconf_seq_in + 1)) {
656                 SCTPDBG(SCTP_DEBUG_ASCONF1, "handle_asconf: incorrect serial number = %xh (expected next = %xh)\n",
657                         serial_num, asoc->asconf_seq_in + 1);
658                 return;
659         }
660
661         /* it's the expected "next" sequence number, so process it */
662         asoc->asconf_seq_in = serial_num;       /* update sequence */
663         /* get length of all the param's in the ASCONF */
664         asconf_limit = offset + ntohs(cp->ch.chunk_length);
665         SCTPDBG(SCTP_DEBUG_ASCONF1,
666                 "handle_asconf: asconf_limit=%u, sequence=%xh\n",
667                 asconf_limit, serial_num);
668
669         if (first) {
670                 /* delete old cache */
671                 SCTPDBG(SCTP_DEBUG_ASCONF1,"handle_asconf: Now processing first ASCONF. Try to delete old cache\n");
672
673                 TAILQ_FOREACH_SAFE(ack, &asoc->asconf_ack_sent, next, ack_next) {
674                         if (ack->serial_number == serial_num)
675                                 break;
676                         SCTPDBG(SCTP_DEBUG_ASCONF1,"handle_asconf: delete old(%u) < first(%u)\n",
677                             ack->serial_number, serial_num);
678                         TAILQ_REMOVE(&asoc->asconf_ack_sent, ack, next);
679                         if (ack->data != NULL) {
680                                 sctp_m_freem(ack->data);
681                         }
682                         SCTP_ZONE_FREE(SCTP_BASE_INFO(ipi_zone_asconf_ack), ack);
683                 }
684         }
685
686         m_ack = sctp_get_mbuf_for_msg(sizeof(struct sctp_asconf_ack_chunk), 0,
687                                       M_NOWAIT, 1, MT_DATA);
688         if (m_ack == NULL) {
689                 SCTPDBG(SCTP_DEBUG_ASCONF1,
690                         "handle_asconf: couldn't get mbuf!\n");
691                 return;
692         }
693         m_tail = m_ack;         /* current reply chain's tail */
694
695         /* fill in ASCONF-ACK header */
696         ack_cp = mtod(m_ack, struct sctp_asconf_ack_chunk *);
697         ack_cp->ch.chunk_type = SCTP_ASCONF_ACK;
698         ack_cp->ch.chunk_flags = 0;
699         ack_cp->serial_number = htonl(serial_num);
700         /* set initial lengths (eg. just an ASCONF-ACK), ntohx at the end! */
701         SCTP_BUF_LEN(m_ack) = sizeof(struct sctp_asconf_ack_chunk);
702         ack_cp->ch.chunk_length = sizeof(struct sctp_asconf_ack_chunk);
703
704         /* skip the lookup address parameter */
705         offset += sizeof(struct sctp_asconf_chunk);
706         p_addr = (struct sctp_ipv6addr_param *)sctp_m_getptr(m, offset, sizeof(struct sctp_paramhdr), (uint8_t *)&aparam_buf);
707         if (p_addr == NULL) {
708                 SCTPDBG(SCTP_DEBUG_ASCONF1,
709                         "handle_asconf: couldn't get lookup addr!\n");
710                 /* respond with a missing/invalid mandatory parameter error */
711                 sctp_m_freem(m_ack);
712                 return;
713         }
714         /* skip lookup addr */
715         offset += SCTP_SIZE32(ntohs(p_addr->ph.param_length));
716         /* get pointer to first asconf param in ASCONF */
717         aph = (struct sctp_asconf_paramhdr *)sctp_m_getptr(m, offset, sizeof(struct sctp_asconf_paramhdr), (uint8_t *)&aparam_buf);
718         if (aph == NULL) {
719                 SCTPDBG(SCTP_DEBUG_ASCONF1, "Empty ASCONF received?\n");
720                 goto send_reply;
721         }
722         /* process through all parameters */
723         cnt = 0;
724         while (aph != NULL) {
725                 unsigned int param_length, param_type;
726
727                 param_type = ntohs(aph->ph.param_type);
728                 param_length = ntohs(aph->ph.param_length);
729                 if (offset + param_length > asconf_limit) {
730                         /* parameter goes beyond end of chunk! */
731                         sctp_m_freem(m_ack);
732                         return;
733                 }
734                 m_result = NULL;
735
736                 if (param_length > sizeof(aparam_buf)) {
737                         SCTPDBG(SCTP_DEBUG_ASCONF1, "handle_asconf: param length (%u) larger than buffer size!\n", param_length);
738                         sctp_m_freem(m_ack);
739                         return;
740                 }
741                 if (param_length <= sizeof(struct sctp_paramhdr)) {
742                         SCTPDBG(SCTP_DEBUG_ASCONF1, "handle_asconf: param length (%u) too short\n", param_length);
743                         sctp_m_freem(m_ack);
744                         return;
745                 }
746                 /* get the entire parameter */
747                 aph = (struct sctp_asconf_paramhdr *)sctp_m_getptr(m, offset, param_length, aparam_buf);
748                 if (aph == NULL) {
749                         SCTPDBG(SCTP_DEBUG_ASCONF1, "handle_asconf: couldn't get entire param\n");
750                         sctp_m_freem(m_ack);
751                         return;
752                 }
753                 switch (param_type) {
754                 case SCTP_ADD_IP_ADDRESS:
755                         m_result = sctp_process_asconf_add_ip(src, aph, stcb,
756                             (cnt < SCTP_BASE_SYSCTL(sctp_hb_maxburst)), error);
757                         cnt++;
758                         break;
759                 case SCTP_DEL_IP_ADDRESS:
760                         m_result = sctp_process_asconf_delete_ip(src, aph, stcb,
761                             error);
762                         break;
763                 case SCTP_ERROR_CAUSE_IND:
764                         /* not valid in an ASCONF chunk */
765                         break;
766                 case SCTP_SET_PRIM_ADDR:
767                         m_result = sctp_process_asconf_set_primary(src, aph,
768                             stcb, error);
769                         break;
770                 case SCTP_NAT_VTAGS:
771                         SCTPDBG(SCTP_DEBUG_ASCONF1, "handle_asconf: sees a NAT VTAG state parameter\n");
772                         break;
773                 case SCTP_SUCCESS_REPORT:
774                         /* not valid in an ASCONF chunk */
775                         break;
776                 case SCTP_ULP_ADAPTATION:
777                         /* FIX */
778                         break;
779                 default:
780                         if ((param_type & 0x8000) == 0) {
781                                 /* Been told to STOP at this param */
782                                 asconf_limit = offset;
783                                 /*
784                                  * FIX FIX - We need to call
785                                  * sctp_arethere_unrecognized_parameters()
786                                  * to get a operr and send it for any
787                                  * param's with the 0x4000 bit set OR do it
788                                  * here ourselves... note we still must STOP
789                                  * if the 0x8000 bit is clear.
790                                  */
791                         }
792                         /* unknown/invalid param type */
793                         break;
794                 } /* switch */
795
796                 /* add any (error) result to the reply mbuf chain */
797                 if (m_result != NULL) {
798                         SCTP_BUF_NEXT(m_tail) = m_result;
799                         m_tail = m_result;
800                         ack_cp->ch.chunk_length += SCTP_BUF_LEN(m_result);
801                         /* set flag to force success reports */
802                         error = 1;
803                 }
804                 offset += SCTP_SIZE32(param_length);
805                 /* update remaining ASCONF message length to process */
806                 if (offset >= asconf_limit) {
807                         /* no more data in the mbuf chain */
808                         break;
809                 }
810                 /* get pointer to next asconf param */
811                 aph = (struct sctp_asconf_paramhdr *)sctp_m_getptr(m, offset,
812                     sizeof(struct sctp_asconf_paramhdr),
813                     (uint8_t *)&aparam_buf);
814                 if (aph == NULL) {
815                         /* can't get an asconf paramhdr */
816                         SCTPDBG(SCTP_DEBUG_ASCONF1, "handle_asconf: can't get asconf param hdr!\n");
817                         /* FIX ME - add error here... */
818                 }
819         }
820
821  send_reply:
822         ack_cp->ch.chunk_length = htons(ack_cp->ch.chunk_length);
823         /* save the ASCONF-ACK reply */
824         ack = SCTP_ZONE_GET(SCTP_BASE_INFO(ipi_zone_asconf_ack),
825             struct sctp_asconf_ack);
826         if (ack == NULL) {
827                 sctp_m_freem(m_ack);
828                 return;
829         }
830         ack->serial_number = serial_num;
831         ack->last_sent_to = NULL;
832         ack->data = m_ack;
833         ack->len = 0;
834         for (n = m_ack; n != NULL; n = SCTP_BUF_NEXT(n)) {
835                 ack->len += SCTP_BUF_LEN(n);
836         }
837         TAILQ_INSERT_TAIL(&stcb->asoc.asconf_ack_sent, ack, next);
838
839         /* see if last_control_chunk_from is set properly (use IP src addr) */
840         if (stcb->asoc.last_control_chunk_from == NULL) {
841                 /*
842                  * this could happen if the source address was just newly
843                  * added
844                  */
845                 SCTPDBG(SCTP_DEBUG_ASCONF1, "handle_asconf: looking up net for IP source address\n");
846                 SCTPDBG(SCTP_DEBUG_ASCONF1, "Looking for IP source: ");
847                 SCTPDBG_ADDR(SCTP_DEBUG_ASCONF1, src);
848                 /* look up the from address */
849                 stcb->asoc.last_control_chunk_from = sctp_findnet(stcb, src);
850 #ifdef SCTP_DEBUG
851                 if (stcb->asoc.last_control_chunk_from == NULL) {
852                         SCTPDBG(SCTP_DEBUG_ASCONF1, "handle_asconf: IP source address not found?!\n");
853                 }
854 #endif
855         }
856 }
857
858 /*
859  * does the address match? returns 0 if not, 1 if so
860  */
861 static uint32_t
862 sctp_asconf_addr_match(struct sctp_asconf_addr *aa, struct sockaddr *sa)
863 {
864         switch (sa->sa_family) {
865 #ifdef INET6
866         case AF_INET6:
867         {
868                 /* XXX scopeid */
869                 struct sockaddr_in6 *sin6 = (struct sockaddr_in6 *)sa;
870
871                 if ((aa->ap.addrp.ph.param_type == SCTP_IPV6_ADDRESS) &&
872                     (memcmp(&aa->ap.addrp.addr, &sin6->sin6_addr,
873                     sizeof(struct in6_addr)) == 0)) {
874                         return (1);
875                 }
876                 break;
877         }
878 #endif
879 #ifdef INET
880         case AF_INET:
881         {
882                 struct sockaddr_in *sin = (struct sockaddr_in *)sa;
883
884                 if ((aa->ap.addrp.ph.param_type == SCTP_IPV4_ADDRESS) &&
885                     (memcmp(&aa->ap.addrp.addr, &sin->sin_addr,
886                     sizeof(struct in_addr)) == 0)) {
887                         return (1);
888                 }
889                 break;
890         }
891 #endif
892         default:
893                 break;
894         }
895         return (0);
896 }
897
898 /*
899  * does the address match? returns 0 if not, 1 if so
900  */
901 static uint32_t
902 sctp_addr_match(struct sctp_paramhdr *ph, struct sockaddr *sa)
903 {
904 #if defined(INET) || defined(INET6)
905         uint16_t param_type, param_length;
906
907         param_type = ntohs(ph->param_type);
908         param_length = ntohs(ph->param_length);
909 #endif
910         switch (sa->sa_family) {
911 #ifdef INET6
912         case AF_INET6:
913         {
914                 /* XXX scopeid */
915                 struct sockaddr_in6 *sin6 = (struct sockaddr_in6 *)sa;
916                 struct sctp_ipv6addr_param *v6addr;
917
918                 v6addr = (struct sctp_ipv6addr_param *)ph;
919                 if ((param_type == SCTP_IPV6_ADDRESS) &&
920                     (param_length == sizeof(struct sctp_ipv6addr_param)) &&
921                     (memcmp(&v6addr->addr, &sin6->sin6_addr,
922                     sizeof(struct in6_addr)) == 0)) {
923                         return (1);
924                 }
925                 break;
926         }
927 #endif
928 #ifdef INET
929         case AF_INET:
930         {
931                 struct sockaddr_in *sin = (struct sockaddr_in *)sa;
932                 struct sctp_ipv4addr_param *v4addr;
933
934                 v4addr = (struct sctp_ipv4addr_param *)ph;
935                 if ((param_type == SCTP_IPV4_ADDRESS) &&
936                     (param_length == sizeof(struct sctp_ipv4addr_param)) &&
937                     (memcmp(&v4addr->addr, &sin->sin_addr,
938                     sizeof(struct in_addr)) == 0)) {
939                         return (1);
940                 }
941                 break;
942         }
943 #endif
944         default:
945                 break;
946         }
947         return (0);
948 }
949 /*
950  * Cleanup for non-responded/OP ERR'd ASCONF
951  */
952 void
953 sctp_asconf_cleanup(struct sctp_tcb *stcb)
954 {
955         /*
956          * clear out any existing asconfs going out
957          */
958         sctp_timer_stop(SCTP_TIMER_TYPE_ASCONF, stcb->sctp_ep, stcb, NULL,
959                         SCTP_FROM_SCTP_ASCONF + SCTP_LOC_2);
960         stcb->asoc.asconf_seq_out_acked = stcb->asoc.asconf_seq_out;
961         /* remove the old ASCONF on our outbound queue */
962         sctp_toss_old_asconf(stcb);
963 }
964
965 /*
966  * cleanup any cached source addresses that may be topologically
967  * incorrect after a new address has been added to this interface.
968  */
969 static void
970 sctp_asconf_nets_cleanup(struct sctp_tcb *stcb, struct sctp_ifn *ifn)
971 {
972         struct sctp_nets *net;
973
974         /*
975          * Ideally, we want to only clear cached routes and source addresses
976          * that are topologically incorrect.  But since there is no easy way
977          * to know whether the newly added address on the ifn would cause a
978          * routing change (i.e. a new egress interface would be chosen)
979          * without doing a new routing lookup and source address selection,
980          * we will (for now) just flush any cached route using a different
981          * ifn (and cached source addrs) and let output re-choose them during
982          * the next send on that net.
983          */
984         TAILQ_FOREACH(net, &stcb->asoc.nets, sctp_next) {
985                 /*
986                  * clear any cached route (and cached source address) if the
987                  * route's interface is NOT the same as the address change.
988                  * If it's the same interface, just clear the cached source
989                  * address.
990                  */
991                 if (SCTP_ROUTE_HAS_VALID_IFN(&net->ro) &&
992                     ((ifn == NULL) ||
993                      (SCTP_GET_IF_INDEX_FROM_ROUTE(&net->ro) != ifn->ifn_index))) {
994                         /* clear any cached route */
995 #if defined(__FreeBSD__) && !defined(__Userspace__)
996                         RO_NHFREE(&net->ro);
997 #else
998                         RTFREE(net->ro.ro_rt);
999                         net->ro.ro_rt = NULL;
1000 #endif
1001                 }
1002                 /* clear any cached source address */
1003                 if (net->src_addr_selected) {
1004                         sctp_free_ifa(net->ro._s_addr);
1005                         net->ro._s_addr = NULL;
1006                         net->src_addr_selected = 0;
1007                 }
1008         }
1009 }
1010
1011
1012 void
1013 sctp_assoc_immediate_retrans(struct sctp_tcb *stcb, struct sctp_nets *dstnet)
1014 {
1015         int error;
1016
1017         if (dstnet->dest_state & SCTP_ADDR_UNCONFIRMED) {
1018                 return;
1019         }
1020         if (stcb->asoc.deleted_primary == NULL) {
1021                 return;
1022         }
1023
1024         if (!TAILQ_EMPTY(&stcb->asoc.sent_queue)) {
1025                 SCTPDBG(SCTP_DEBUG_ASCONF1, "assoc_immediate_retrans: Deleted primary is ");
1026                 SCTPDBG_ADDR(SCTP_DEBUG_ASCONF1, &stcb->asoc.deleted_primary->ro._l_addr.sa);
1027                 SCTPDBG(SCTP_DEBUG_ASCONF1, "Current Primary is ");
1028                 SCTPDBG_ADDR(SCTP_DEBUG_ASCONF1, &stcb->asoc.primary_destination->ro._l_addr.sa);
1029                 sctp_timer_stop(SCTP_TIMER_TYPE_SEND, stcb->sctp_ep, stcb,
1030                                 stcb->asoc.deleted_primary,
1031                                 SCTP_FROM_SCTP_ASCONF + SCTP_LOC_3);
1032                 stcb->asoc.num_send_timers_up--;
1033                 if (stcb->asoc.num_send_timers_up < 0) {
1034                         stcb->asoc.num_send_timers_up = 0;
1035                 }
1036                 SCTP_TCB_LOCK_ASSERT(stcb);
1037                 error = sctp_t3rxt_timer(stcb->sctp_ep, stcb,
1038                                         stcb->asoc.deleted_primary);
1039                 if (error) {
1040                         SCTP_INP_DECR_REF(stcb->sctp_ep);
1041                         return;
1042                 }
1043                 SCTP_TCB_LOCK_ASSERT(stcb);
1044 #ifdef SCTP_AUDITING_ENABLED
1045                 sctp_auditing(4, stcb->sctp_ep, stcb, stcb->asoc.deleted_primary);
1046 #endif
1047                 sctp_chunk_output(stcb->sctp_ep, stcb, SCTP_OUTPUT_FROM_T3, SCTP_SO_NOT_LOCKED);
1048                 if ((stcb->asoc.num_send_timers_up == 0) &&
1049                     (stcb->asoc.sent_queue_cnt > 0)) {
1050                         struct sctp_tmit_chunk *chk;
1051
1052                         TAILQ_FOREACH(chk, &stcb->asoc.sent_queue, sctp_next) {
1053                                 if (chk->whoTo != NULL) {
1054                                         break;
1055                                 }
1056                         }
1057                         if (chk != NULL) {
1058                                 sctp_timer_start(SCTP_TIMER_TYPE_SEND, stcb->sctp_ep, stcb, chk->whoTo);
1059                         }
1060                 }
1061         }
1062         return;
1063 }
1064
1065 #if defined(__FreeBSD__) || defined(__APPLE__) || defined(__Userspace__)
1066 static int
1067 sctp_asconf_queue_mgmt(struct sctp_tcb *, struct sctp_ifa *, uint16_t);
1068
1069 void
1070 sctp_net_immediate_retrans(struct sctp_tcb *stcb, struct sctp_nets *net)
1071 {
1072         struct sctp_tmit_chunk *chk;
1073
1074         SCTPDBG(SCTP_DEBUG_ASCONF1, "net_immediate_retrans: RTO is %d\n", net->RTO);
1075         sctp_timer_stop(SCTP_TIMER_TYPE_SEND, stcb->sctp_ep, stcb, net,
1076                         SCTP_FROM_SCTP_ASCONF + SCTP_LOC_4);
1077         stcb->asoc.cc_functions.sctp_set_initial_cc_param(stcb, net);
1078         net->error_count = 0;
1079         TAILQ_FOREACH(chk, &stcb->asoc.sent_queue, sctp_next) {
1080                 if (chk->whoTo == net) {
1081                         if (chk->sent < SCTP_DATAGRAM_RESEND) {
1082                                 chk->sent = SCTP_DATAGRAM_RESEND;
1083                                 sctp_ucount_incr(stcb->asoc.sent_queue_retran_cnt);
1084                                 sctp_flight_size_decrease(chk);
1085                                 sctp_total_flight_decrease(stcb, chk);
1086                                 net->marked_retrans++;
1087                                 stcb->asoc.marked_retrans++;
1088                         }
1089                 }
1090         }
1091         if (net->marked_retrans) {
1092                 sctp_chunk_output(stcb->sctp_ep, stcb, SCTP_OUTPUT_FROM_T3, SCTP_SO_NOT_LOCKED);
1093         }
1094 }
1095
1096 static void
1097 sctp_path_check_and_react(struct sctp_tcb *stcb, struct sctp_ifa *newifa)
1098 {
1099         struct sctp_nets *net;
1100         int addrnum, changed;
1101
1102         /*   If number of local valid addresses is 1, the valid address is
1103              probably newly added address.
1104              Several valid addresses in this association.  A source address
1105              may not be changed.  Additionally, they can be configured on a
1106              same interface as "alias" addresses.  (by micchie)
1107          */
1108         addrnum = sctp_local_addr_count(stcb);
1109         SCTPDBG(SCTP_DEBUG_ASCONF1, "p_check_react(): %d local addresses\n",
1110                 addrnum);
1111         if (addrnum == 1) {
1112                 TAILQ_FOREACH(net, &stcb->asoc.nets, sctp_next) {
1113                         /* clear any cached route and source address */
1114 #if defined(__FreeBSD__) && !defined(__Userspace__)
1115                         RO_NHFREE(&net->ro);
1116 #else
1117                         if (net->ro.ro_rt) {
1118                                 RTFREE(net->ro.ro_rt);
1119                                 net->ro.ro_rt = NULL;
1120                         }
1121 #endif
1122                         if (net->src_addr_selected) {
1123                                 sctp_free_ifa(net->ro._s_addr);
1124                                 net->ro._s_addr = NULL;
1125                                 net->src_addr_selected = 0;
1126                         }
1127                         /* Retransmit unacknowledged DATA chunks immediately */
1128                         if (sctp_is_mobility_feature_on(stcb->sctp_ep,
1129                                                         SCTP_MOBILITY_FASTHANDOFF)) {
1130                                 sctp_net_immediate_retrans(stcb, net);
1131                         }
1132                         /* also, SET PRIMARY is maybe already sent */
1133                 }
1134                 return;
1135         }
1136
1137         /* Multiple local addresses exsist in the association.  */
1138         TAILQ_FOREACH(net, &stcb->asoc.nets, sctp_next) {
1139                 /* clear any cached route and source address */
1140 #if defined(__FreeBSD__) && !defined(__Userspace__)
1141                 RO_NHFREE(&net->ro);
1142 #else
1143                 if (net->ro.ro_rt) {
1144                         RTFREE(net->ro.ro_rt);
1145                         net->ro.ro_rt = NULL;
1146                 }
1147 #endif
1148                 if (net->src_addr_selected) {
1149                         sctp_free_ifa(net->ro._s_addr);
1150                         net->ro._s_addr = NULL;
1151                         net->src_addr_selected = 0;
1152                 }
1153                 /* Check if the nexthop is corresponding to the new address.
1154                    If the new address is corresponding to the current nexthop,
1155                    the path will be changed.
1156                    If the new address is NOT corresponding to the current
1157                    nexthop, the path will not be changed.
1158                  */
1159                 SCTP_RTALLOC((sctp_route_t *)&net->ro,
1160                              stcb->sctp_ep->def_vrf_id,
1161                              stcb->sctp_ep->fibnum);
1162 #if defined(__FreeBSD__) && !defined(__Userspace__)
1163                 if (net->ro.ro_nh == NULL)
1164 #else
1165                 if (net->ro.ro_rt == NULL)
1166 #endif
1167                         continue;
1168
1169                 changed = 0;
1170                 switch (net->ro._l_addr.sa.sa_family) {
1171 #ifdef INET
1172                 case AF_INET:
1173                         if (sctp_v4src_match_nexthop(newifa, (sctp_route_t *)&net->ro)) {
1174                                 changed = 1;
1175                         }
1176                         break;
1177 #endif
1178 #ifdef INET6
1179                 case AF_INET6:
1180                         if (sctp_v6src_match_nexthop(
1181                             &newifa->address.sin6, (sctp_route_t *)&net->ro)) {
1182                                 changed = 1;
1183                         }
1184                         break;
1185 #endif
1186                 default:
1187                         break;
1188                 }
1189                 /* if the newly added address does not relate routing
1190                    information, we skip.
1191                  */
1192                 if (changed == 0)
1193                         continue;
1194                 /* Retransmit unacknowledged DATA chunks immediately */
1195                 if (sctp_is_mobility_feature_on(stcb->sctp_ep,
1196                                                 SCTP_MOBILITY_FASTHANDOFF)) {
1197                         sctp_net_immediate_retrans(stcb, net);
1198                 }
1199                 /* Send SET PRIMARY for this new address */
1200                 if (net == stcb->asoc.primary_destination) {
1201                         (void)sctp_asconf_queue_mgmt(stcb, newifa,
1202                                                      SCTP_SET_PRIM_ADDR);
1203                 }
1204         }
1205 }
1206 #endif
1207
1208 /*
1209  * process an ADD/DELETE IP ack from peer.
1210  * addr: corresponding sctp_ifa to the address being added/deleted.
1211  * type: SCTP_ADD_IP_ADDRESS or SCTP_DEL_IP_ADDRESS.
1212  * flag: 1=success, 0=failure.
1213  */
1214 static void
1215 sctp_asconf_addr_mgmt_ack(struct sctp_tcb *stcb, struct sctp_ifa *addr, uint32_t flag)
1216 {
1217         /*
1218          * do the necessary asoc list work- if we get a failure indication,
1219          * leave the address on the assoc's restricted list.  If we get a
1220          * success indication, remove the address from the restricted list.
1221          */
1222         /*
1223          * Note: this will only occur for ADD_IP_ADDRESS, since
1224          * DEL_IP_ADDRESS is never actually added to the list...
1225          */
1226         if (flag) {
1227                 /* success case, so remove from the restricted list */
1228                 sctp_del_local_addr_restricted(stcb, addr);
1229
1230 #if defined(__FreeBSD__) || defined(__APPLE__) || defined(__Userspace__)
1231                 if (sctp_is_mobility_feature_on(stcb->sctp_ep,
1232                                                 SCTP_MOBILITY_BASE) ||
1233                     sctp_is_mobility_feature_on(stcb->sctp_ep,
1234                                                 SCTP_MOBILITY_FASTHANDOFF)) {
1235                         sctp_path_check_and_react(stcb, addr);
1236                         return;
1237                 }
1238 #endif
1239                 /* clear any cached/topologically incorrect source addresses */
1240                 sctp_asconf_nets_cleanup(stcb, addr->ifn_p);
1241         }
1242         /* else, leave it on the list */
1243 }
1244
1245 /*
1246  * add an asconf add/delete/set primary IP address parameter to the queue.
1247  * type = SCTP_ADD_IP_ADDRESS, SCTP_DEL_IP_ADDRESS, SCTP_SET_PRIM_ADDR.
1248  * returns 0 if queued, -1 if not queued/removed.
1249  * NOTE: if adding, but a delete for the same address is already scheduled
1250  * (and not yet sent out), simply remove it from queue.  Same for deleting
1251  * an address already scheduled for add.  If a duplicate operation is found,
1252  * ignore the new one.
1253  */
1254 static int
1255 sctp_asconf_queue_mgmt(struct sctp_tcb *stcb, struct sctp_ifa *ifa,
1256                        uint16_t type)
1257 {
1258         struct sctp_asconf_addr *aa, *aa_next;
1259
1260         /* make sure the request isn't already in the queue */
1261         TAILQ_FOREACH_SAFE(aa, &stcb->asoc.asconf_queue, next, aa_next) {
1262                 /* address match? */
1263                 if (sctp_asconf_addr_match(aa, &ifa->address.sa) == 0)
1264                         continue;
1265                 /* is the request already in queue but not sent?
1266                  * pass the request already sent in order to resolve the following case:
1267                  *  1. arrival of ADD, then sent
1268                  *  2. arrival of DEL. we can't remove the ADD request already sent
1269                  *  3. arrival of ADD
1270                  */
1271                 if (aa->ap.aph.ph.param_type == type && aa->sent == 0) {
1272                         return (-1);
1273                 }
1274                 /* is the negative request already in queue, and not sent */
1275                 if ((aa->sent == 0) && (type == SCTP_ADD_IP_ADDRESS) &&
1276                     (aa->ap.aph.ph.param_type == SCTP_DEL_IP_ADDRESS)) {
1277                         /* add requested, delete already queued */
1278                         TAILQ_REMOVE(&stcb->asoc.asconf_queue, aa, next);
1279                         /* remove the ifa from the restricted list */
1280                         sctp_del_local_addr_restricted(stcb, ifa);
1281                         /* free the asconf param */
1282                         SCTP_FREE(aa, SCTP_M_ASC_ADDR);
1283                         SCTPDBG(SCTP_DEBUG_ASCONF2, "asconf_queue_mgmt: add removes queued entry\n");
1284                         return (-1);
1285                 }
1286                 if ((aa->sent == 0) && (type == SCTP_DEL_IP_ADDRESS) &&
1287                     (aa->ap.aph.ph.param_type == SCTP_ADD_IP_ADDRESS)) {
1288                         /* delete requested, add already queued */
1289                         TAILQ_REMOVE(&stcb->asoc.asconf_queue, aa, next);
1290                         /* remove the aa->ifa from the restricted list */
1291                         sctp_del_local_addr_restricted(stcb, aa->ifa);
1292                         /* free the asconf param */
1293                         SCTP_FREE(aa, SCTP_M_ASC_ADDR);
1294                         SCTPDBG(SCTP_DEBUG_ASCONF2, "asconf_queue_mgmt: delete removes queued entry\n");
1295                         return (-1);
1296                 }
1297         } /* for each aa */
1298
1299         /* adding new request to the queue */
1300         SCTP_MALLOC(aa, struct sctp_asconf_addr *, sizeof(*aa),
1301                     SCTP_M_ASC_ADDR);
1302         if (aa == NULL) {
1303                 /* didn't get memory */
1304                 SCTPDBG(SCTP_DEBUG_ASCONF1, "asconf_queue_mgmt: failed to get memory!\n");
1305                 return (-1);
1306         }
1307         aa->special_del = 0;
1308         /* fill in asconf address parameter fields */
1309         /* top level elements are "networked" during send */
1310         aa->ap.aph.ph.param_type = type;
1311         aa->ifa = ifa;
1312         atomic_add_int(&ifa->refcount, 1);
1313         /* correlation_id filled in during send routine later... */
1314         switch (ifa->address.sa.sa_family) {
1315 #ifdef INET6
1316         case AF_INET6:
1317         {
1318                 struct sockaddr_in6 *sin6;
1319
1320                 sin6 = &ifa->address.sin6;
1321                 aa->ap.addrp.ph.param_type = SCTP_IPV6_ADDRESS;
1322                 aa->ap.addrp.ph.param_length = (sizeof(struct sctp_ipv6addr_param));
1323                 aa->ap.aph.ph.param_length = sizeof(struct sctp_asconf_paramhdr) +
1324                     sizeof(struct sctp_ipv6addr_param);
1325                 memcpy(&aa->ap.addrp.addr, &sin6->sin6_addr,
1326                        sizeof(struct in6_addr));
1327                 break;
1328         }
1329 #endif
1330 #ifdef INET
1331         case AF_INET:
1332         {
1333                 struct sockaddr_in *sin;
1334
1335                 sin = &ifa->address.sin;
1336                 aa->ap.addrp.ph.param_type = SCTP_IPV4_ADDRESS;
1337                 aa->ap.addrp.ph.param_length = (sizeof(struct sctp_ipv4addr_param));
1338                 aa->ap.aph.ph.param_length = sizeof(struct sctp_asconf_paramhdr) +
1339                     sizeof(struct sctp_ipv4addr_param);
1340                 memcpy(&aa->ap.addrp.addr, &sin->sin_addr,
1341                        sizeof(struct in_addr));
1342                 break;
1343         }
1344 #endif
1345         default:
1346                 /* invalid family! */
1347                 SCTP_FREE(aa, SCTP_M_ASC_ADDR);
1348                 sctp_free_ifa(ifa);
1349                 return (-1);
1350         }
1351         aa->sent = 0;           /* clear sent flag */
1352
1353         TAILQ_INSERT_TAIL(&stcb->asoc.asconf_queue, aa, next);
1354 #ifdef SCTP_DEBUG
1355         if (SCTP_BASE_SYSCTL(sctp_debug_on) & SCTP_DEBUG_ASCONF2) {
1356                 if (type == SCTP_ADD_IP_ADDRESS) {
1357                         SCTP_PRINTF("asconf_queue_mgmt: inserted asconf ADD_IP_ADDRESS: ");
1358                         SCTPDBG_ADDR(SCTP_DEBUG_ASCONF2, &ifa->address.sa);
1359                 } else if (type == SCTP_DEL_IP_ADDRESS) {
1360                         SCTP_PRINTF("asconf_queue_mgmt: appended asconf DEL_IP_ADDRESS: ");
1361                         SCTPDBG_ADDR(SCTP_DEBUG_ASCONF2, &ifa->address.sa);
1362                 } else {
1363                         SCTP_PRINTF("asconf_queue_mgmt: appended asconf SET_PRIM_ADDR: ");
1364                         SCTPDBG_ADDR(SCTP_DEBUG_ASCONF2, &ifa->address.sa);
1365                 }
1366         }
1367 #endif
1368
1369         return (0);
1370 }
1371
1372
1373 /*
1374  * add an asconf operation for the given ifa and type.
1375  * type = SCTP_ADD_IP_ADDRESS, SCTP_DEL_IP_ADDRESS, SCTP_SET_PRIM_ADDR.
1376  * returns 0 if completed, -1 if not completed, 1 if immediate send is
1377  * advisable.
1378  */
1379 static int
1380 sctp_asconf_queue_add(struct sctp_tcb *stcb, struct sctp_ifa *ifa,
1381                       uint16_t type)
1382 {
1383         uint32_t status;
1384         int pending_delete_queued = 0;
1385         int last;
1386
1387         /* see if peer supports ASCONF */
1388         if (stcb->asoc.asconf_supported == 0) {
1389                 return (-1);
1390         }
1391
1392         /*
1393          * if this is deleting the last address from the assoc, mark it as
1394          * pending.
1395          */
1396         if ((type == SCTP_DEL_IP_ADDRESS) && !stcb->asoc.asconf_del_pending) {
1397                 if (stcb->sctp_ep->sctp_flags & SCTP_PCB_FLAGS_BOUNDALL) {
1398                         last = (sctp_local_addr_count(stcb) == 0);
1399                 } else {
1400                         last = (sctp_local_addr_count(stcb) == 1);
1401                 }
1402                 if (last) {
1403                         /* set the pending delete info only */
1404                         stcb->asoc.asconf_del_pending = 1;
1405                         stcb->asoc.asconf_addr_del_pending = ifa;
1406                         atomic_add_int(&ifa->refcount, 1);
1407                         SCTPDBG(SCTP_DEBUG_ASCONF2,
1408                                 "asconf_queue_add: mark delete last address pending\n");
1409                         return (-1);
1410                 }
1411         }
1412
1413         /* queue an asconf parameter */
1414         status = sctp_asconf_queue_mgmt(stcb, ifa, type);
1415
1416         /*
1417          * if this is an add, and there is a delete also pending (i.e. the
1418          * last local address is being changed), queue the pending delete too.
1419          */
1420         if ((type == SCTP_ADD_IP_ADDRESS) && stcb->asoc.asconf_del_pending && (status == 0)) {
1421                 /* queue in the pending delete */
1422                 if (sctp_asconf_queue_mgmt(stcb,
1423                                            stcb->asoc.asconf_addr_del_pending,
1424                                            SCTP_DEL_IP_ADDRESS) == 0) {
1425                         SCTPDBG(SCTP_DEBUG_ASCONF2, "asconf_queue_add: queuing pending delete\n");
1426                         pending_delete_queued = 1;
1427                         /* clear out the pending delete info */
1428                         stcb->asoc.asconf_del_pending = 0;
1429                         sctp_free_ifa(stcb->asoc.asconf_addr_del_pending);
1430                         stcb->asoc.asconf_addr_del_pending = NULL;
1431                 }
1432         }
1433
1434         if (pending_delete_queued) {
1435                 struct sctp_nets *net;
1436                 /*
1437                  * since we know that the only/last address is now being
1438                  * changed in this case, reset the cwnd/rto on all nets to
1439                  * start as a new address and path.  Also clear the error
1440                  * counts to give the assoc the best chance to complete the
1441                  * address change.
1442                  */
1443                 TAILQ_FOREACH(net, &stcb->asoc.nets, sctp_next) {
1444                         stcb->asoc.cc_functions.sctp_set_initial_cc_param(stcb,
1445                                                                           net);
1446                         net->RTO = 0;
1447                         net->error_count = 0;
1448                 }
1449                 stcb->asoc.overall_error_count = 0;
1450                 if (SCTP_BASE_SYSCTL(sctp_logging_level) & SCTP_THRESHOLD_LOGGING) {
1451                         sctp_misc_ints(SCTP_THRESHOLD_CLEAR,
1452                                        stcb->asoc.overall_error_count,
1453                                        0,
1454                                        SCTP_FROM_SCTP_ASCONF,
1455                                        __LINE__);
1456                 }
1457
1458                 /* queue in an advisory set primary too */
1459                 (void)sctp_asconf_queue_mgmt(stcb, ifa, SCTP_SET_PRIM_ADDR);
1460                 /* let caller know we should send this out immediately */
1461                 status = 1;
1462         }
1463         return (status);
1464 }
1465
1466 /*-
1467  * add an asconf delete IP address parameter to the queue by sockaddr and
1468  * possibly with no sctp_ifa available.  This is only called by the routine
1469  * that checks the addresses in an INIT-ACK against the current address list.
1470  * returns 0 if completed, non-zero if not completed.
1471  * NOTE: if an add is already scheduled (and not yet sent out), simply
1472  * remove it from queue.  If a duplicate operation is found, ignore the
1473  * new one.
1474  */
1475 static int
1476 sctp_asconf_queue_sa_delete(struct sctp_tcb *stcb, struct sockaddr *sa)
1477 {
1478         struct sctp_ifa *ifa;
1479         struct sctp_asconf_addr *aa, *aa_next;
1480
1481         if (stcb == NULL) {
1482                 return (-1);
1483         }
1484         /* see if peer supports ASCONF */
1485         if (stcb->asoc.asconf_supported == 0) {
1486                 return (-1);
1487         }
1488         /* make sure the request isn't already in the queue */
1489         TAILQ_FOREACH_SAFE(aa, &stcb->asoc.asconf_queue, next, aa_next) {
1490                 /* address match? */
1491                 if (sctp_asconf_addr_match(aa, sa) == 0)
1492                         continue;
1493                 /* is the request already in queue (sent or not) */
1494                 if (aa->ap.aph.ph.param_type == SCTP_DEL_IP_ADDRESS) {
1495                         return (-1);
1496                 }
1497                 /* is the negative request already in queue, and not sent */
1498                 if (aa->sent == 1)
1499                         continue;
1500                 if (aa->ap.aph.ph.param_type == SCTP_ADD_IP_ADDRESS) {
1501                         /* add already queued, so remove existing entry */
1502                         TAILQ_REMOVE(&stcb->asoc.asconf_queue, aa, next);
1503                         sctp_del_local_addr_restricted(stcb, aa->ifa);
1504                         /* free the entry */
1505                         SCTP_FREE(aa, SCTP_M_ASC_ADDR);
1506                         return (-1);
1507                 }
1508         } /* for each aa */
1509
1510         /* find any existing ifa-- NOTE ifa CAN be allowed to be NULL */
1511         ifa = sctp_find_ifa_by_addr(sa, stcb->asoc.vrf_id, SCTP_ADDR_NOT_LOCKED);
1512
1513         /* adding new request to the queue */
1514         SCTP_MALLOC(aa, struct sctp_asconf_addr *, sizeof(*aa),
1515                     SCTP_M_ASC_ADDR);
1516         if (aa == NULL) {
1517                 /* didn't get memory */
1518                 SCTPDBG(SCTP_DEBUG_ASCONF1,
1519                         "sctp_asconf_queue_sa_delete: failed to get memory!\n");
1520                 return (-1);
1521         }
1522         aa->special_del = 0;
1523         /* fill in asconf address parameter fields */
1524         /* top level elements are "networked" during send */
1525         aa->ap.aph.ph.param_type = SCTP_DEL_IP_ADDRESS;
1526         aa->ifa = ifa;
1527         if (ifa)
1528                 atomic_add_int(&ifa->refcount, 1);
1529         /* correlation_id filled in during send routine later... */
1530         switch (sa->sa_family) {
1531 #ifdef INET6
1532         case AF_INET6:
1533         {
1534                 /* IPv6 address */
1535                 struct sockaddr_in6 *sin6;
1536
1537                 sin6 = (struct sockaddr_in6 *)sa;
1538                 aa->ap.addrp.ph.param_type = SCTP_IPV6_ADDRESS;
1539                 aa->ap.addrp.ph.param_length = (sizeof(struct sctp_ipv6addr_param));
1540                 aa->ap.aph.ph.param_length = sizeof(struct sctp_asconf_paramhdr) + sizeof(struct sctp_ipv6addr_param);
1541                 memcpy(&aa->ap.addrp.addr, &sin6->sin6_addr,
1542                     sizeof(struct in6_addr));
1543                 break;
1544         }
1545 #endif
1546 #ifdef INET
1547         case AF_INET:
1548         {
1549                 /* IPv4 address */
1550                 struct sockaddr_in *sin = (struct sockaddr_in *)sa;
1551
1552                 aa->ap.addrp.ph.param_type = SCTP_IPV4_ADDRESS;
1553                 aa->ap.addrp.ph.param_length = (sizeof(struct sctp_ipv4addr_param));
1554                 aa->ap.aph.ph.param_length = sizeof(struct sctp_asconf_paramhdr) + sizeof(struct sctp_ipv4addr_param);
1555                 memcpy(&aa->ap.addrp.addr, &sin->sin_addr,
1556                     sizeof(struct in_addr));
1557                 break;
1558         }
1559 #endif
1560         default:
1561                 /* invalid family! */
1562                 SCTP_FREE(aa, SCTP_M_ASC_ADDR);
1563                 if (ifa)
1564                         sctp_free_ifa(ifa);
1565                 return (-1);
1566         }
1567         aa->sent = 0;           /* clear sent flag */
1568
1569         /* delete goes to the back of the queue */
1570         TAILQ_INSERT_TAIL(&stcb->asoc.asconf_queue, aa, next);
1571
1572         /* sa_ignore MEMLEAK {memory is put on the tailq} */
1573         return (0);
1574 }
1575
1576 /*
1577  * find a specific asconf param on our "sent" queue
1578  */
1579 static struct sctp_asconf_addr *
1580 sctp_asconf_find_param(struct sctp_tcb *stcb, uint32_t correlation_id)
1581 {
1582         struct sctp_asconf_addr *aa;
1583
1584         TAILQ_FOREACH(aa, &stcb->asoc.asconf_queue, next) {
1585                 if (aa->ap.aph.correlation_id == correlation_id &&
1586                     aa->sent == 1) {
1587                         /* found it */
1588                         return (aa);
1589                 }
1590         }
1591         /* didn't find it */
1592         return (NULL);
1593 }
1594
1595 /*
1596  * process an SCTP_ERROR_CAUSE_IND for a ASCONF-ACK parameter and do
1597  * notifications based on the error response
1598  */
1599 static void
1600 sctp_asconf_process_error(struct sctp_tcb *stcb SCTP_UNUSED,
1601                           struct sctp_asconf_paramhdr *aph)
1602 {
1603         struct sctp_error_cause *eh;
1604         struct sctp_paramhdr *ph;
1605         uint16_t param_type;
1606         uint16_t error_code;
1607
1608         eh = (struct sctp_error_cause *)(aph + 1);
1609         ph = (struct sctp_paramhdr *)(eh + 1);
1610         /* validate lengths */
1611         if (htons(eh->length) + sizeof(struct sctp_error_cause) >
1612             htons(aph->ph.param_length)) {
1613                 /* invalid error cause length */
1614                 SCTPDBG(SCTP_DEBUG_ASCONF1,
1615                         "asconf_process_error: cause element too long\n");
1616                 return;
1617         }
1618         if (htons(ph->param_length) + sizeof(struct sctp_paramhdr) >
1619             htons(eh->length)) {
1620                 /* invalid included TLV length */
1621                 SCTPDBG(SCTP_DEBUG_ASCONF1,
1622                         "asconf_process_error: included TLV too long\n");
1623                 return;
1624         }
1625         /* which error code ? */
1626         error_code = ntohs(eh->code);
1627         param_type = ntohs(aph->ph.param_type);
1628         /* FIX: this should go back up the REMOTE_ERROR ULP notify */
1629         switch (error_code) {
1630         case SCTP_CAUSE_RESOURCE_SHORTAGE:
1631                 /* we allow ourselves to "try again" for this error */
1632                 break;
1633         default:
1634                 /* peer can't handle it... */
1635                 switch (param_type) {
1636                 case SCTP_ADD_IP_ADDRESS:
1637                 case SCTP_DEL_IP_ADDRESS:
1638                 case SCTP_SET_PRIM_ADDR:
1639                         break;
1640                 default:
1641                         break;
1642                 }
1643         }
1644 }
1645
1646 /*
1647  * process an asconf queue param.
1648  * aparam: parameter to process, will be removed from the queue.
1649  * flag: 1=success case, 0=failure case
1650  */
1651 static void
1652 sctp_asconf_process_param_ack(struct sctp_tcb *stcb,
1653                               struct sctp_asconf_addr *aparam, uint32_t flag)
1654 {
1655         uint16_t param_type;
1656
1657         /* process this param */
1658         param_type = aparam->ap.aph.ph.param_type;
1659         switch (param_type) {
1660         case SCTP_ADD_IP_ADDRESS:
1661                 SCTPDBG(SCTP_DEBUG_ASCONF1,
1662                         "process_param_ack: added IP address\n");
1663                 sctp_asconf_addr_mgmt_ack(stcb, aparam->ifa, flag);
1664                 break;
1665         case SCTP_DEL_IP_ADDRESS:
1666                 SCTPDBG(SCTP_DEBUG_ASCONF1,
1667                         "process_param_ack: deleted IP address\n");
1668                 /* nothing really to do... lists already updated */
1669                 break;
1670         case SCTP_SET_PRIM_ADDR:
1671                 SCTPDBG(SCTP_DEBUG_ASCONF1,
1672                         "process_param_ack: set primary IP address\n");
1673                 /* nothing to do... peer may start using this addr */
1674                 break;
1675         default:
1676                 /* should NEVER happen */
1677                 break;
1678         }
1679
1680         /* remove the param and free it */
1681         TAILQ_REMOVE(&stcb->asoc.asconf_queue, aparam, next);
1682         if (aparam->ifa)
1683                 sctp_free_ifa(aparam->ifa);
1684         SCTP_FREE(aparam, SCTP_M_ASC_ADDR);
1685 }
1686
1687 /*
1688  * cleanup from a bad asconf ack parameter
1689  */
1690 static void
1691 sctp_asconf_ack_clear(struct sctp_tcb *stcb SCTP_UNUSED)
1692 {
1693         /* assume peer doesn't really know how to do asconfs */
1694         /* XXX we could free the pending queue here */
1695
1696 }
1697
1698 void
1699 sctp_handle_asconf_ack(struct mbuf *m, int offset,
1700                        struct sctp_asconf_ack_chunk *cp, struct sctp_tcb *stcb,
1701                        struct sctp_nets *net, int *abort_no_unlock)
1702 {
1703         struct sctp_association *asoc;
1704         uint32_t serial_num;
1705         uint16_t ack_length;
1706         struct sctp_asconf_paramhdr *aph;
1707         struct sctp_asconf_addr *aa, *aa_next;
1708         uint32_t last_error_id = 0;     /* last error correlation id */
1709         uint32_t id;
1710         struct sctp_asconf_addr *ap;
1711
1712         /* asconf param buffer */
1713         uint8_t aparam_buf[SCTP_PARAM_BUFFER_SIZE];
1714
1715         /* verify minimum length */
1716         if (ntohs(cp->ch.chunk_length) < sizeof(struct sctp_asconf_ack_chunk)) {
1717                 SCTPDBG(SCTP_DEBUG_ASCONF1,
1718                         "handle_asconf_ack: chunk too small = %xh\n",
1719                         ntohs(cp->ch.chunk_length));
1720                 return;
1721         }
1722         asoc = &stcb->asoc;
1723         serial_num = ntohl(cp->serial_number);
1724
1725         /*
1726          * NOTE: we may want to handle this differently- currently, we will
1727          * abort when we get an ack for the expected serial number + 1 (eg.
1728          * we didn't send it), process an ack normally if it is the expected
1729          * serial number, and re-send the previous ack for *ALL* other
1730          * serial numbers
1731          */
1732
1733         /*
1734          * if the serial number is the next expected, but I didn't send it,
1735          * abort the asoc, since someone probably just hijacked us...
1736          */
1737         if (serial_num == (asoc->asconf_seq_out + 1)) {
1738                 struct mbuf *op_err;
1739                 char msg[SCTP_DIAG_INFO_LEN];
1740
1741                 SCTPDBG(SCTP_DEBUG_ASCONF1, "handle_asconf_ack: got unexpected next serial number! Aborting asoc!\n");
1742                 SCTP_SNPRINTF(msg, sizeof(msg), "Never sent serial number %8.8x", serial_num);
1743                 op_err = sctp_generate_cause(SCTP_CAUSE_PROTOCOL_VIOLATION, msg);
1744                 sctp_abort_an_association(stcb->sctp_ep, stcb, op_err, SCTP_SO_NOT_LOCKED);
1745                 *abort_no_unlock = 1;
1746                 return;
1747         }
1748         if (serial_num != asoc->asconf_seq_out_acked + 1) {
1749                 /* got a duplicate/unexpected ASCONF-ACK */
1750                 SCTPDBG(SCTP_DEBUG_ASCONF1, "handle_asconf_ack: got duplicate/unexpected serial number = %xh (expected = %xh)\n",
1751                         serial_num, asoc->asconf_seq_out_acked + 1);
1752                 return;
1753         }
1754
1755         if (serial_num == asoc->asconf_seq_out - 1) {
1756                 /* stop our timer */
1757                 sctp_timer_stop(SCTP_TIMER_TYPE_ASCONF, stcb->sctp_ep, stcb, NULL,
1758                                 SCTP_FROM_SCTP_ASCONF + SCTP_LOC_5);
1759         }
1760
1761         /* process the ASCONF-ACK contents */
1762         ack_length = ntohs(cp->ch.chunk_length) -
1763             sizeof(struct sctp_asconf_ack_chunk);
1764         offset += sizeof(struct sctp_asconf_ack_chunk);
1765         /* process through all parameters */
1766         while (ack_length >= sizeof(struct sctp_asconf_paramhdr)) {
1767                 unsigned int param_length, param_type;
1768
1769                 /* get pointer to next asconf parameter */
1770                 aph = (struct sctp_asconf_paramhdr *)sctp_m_getptr(m, offset,
1771                     sizeof(struct sctp_asconf_paramhdr), aparam_buf);
1772                 if (aph == NULL) {
1773                         /* can't get an asconf paramhdr */
1774                         sctp_asconf_ack_clear(stcb);
1775                         return;
1776                 }
1777                 param_type = ntohs(aph->ph.param_type);
1778                 param_length = ntohs(aph->ph.param_length);
1779                 if (param_length > ack_length) {
1780                         sctp_asconf_ack_clear(stcb);
1781                         return;
1782                 }
1783                 if (param_length < sizeof(struct sctp_paramhdr)) {
1784                         sctp_asconf_ack_clear(stcb);
1785                         return;
1786                 }
1787                 /* get the complete parameter... */
1788                 if (param_length > sizeof(aparam_buf)) {
1789                         SCTPDBG(SCTP_DEBUG_ASCONF1,
1790                                 "param length (%u) larger than buffer size!\n", param_length);
1791                         sctp_asconf_ack_clear(stcb);
1792                         return;
1793                 }
1794                 aph = (struct sctp_asconf_paramhdr *)sctp_m_getptr(m, offset, param_length, aparam_buf);
1795                 if (aph == NULL) {
1796                         sctp_asconf_ack_clear(stcb);
1797                         return;
1798                 }
1799                 /* correlation_id is transparent to peer, no ntohl needed */
1800                 id = aph->correlation_id;
1801
1802                 switch (param_type) {
1803                 case SCTP_ERROR_CAUSE_IND:
1804                         last_error_id = id;
1805                         /* find the corresponding asconf param in our queue */
1806                         ap = sctp_asconf_find_param(stcb, id);
1807                         if (ap == NULL) {
1808                                 /* hmm... can't find this in our queue! */
1809                                 break;
1810                         }
1811                         /* process the parameter, failed flag */
1812                         sctp_asconf_process_param_ack(stcb, ap, 0);
1813                         /* process the error response */
1814                         sctp_asconf_process_error(stcb, aph);
1815                         break;
1816                 case SCTP_SUCCESS_REPORT:
1817                         /* find the corresponding asconf param in our queue */
1818                         ap = sctp_asconf_find_param(stcb, id);
1819                         if (ap == NULL) {
1820                                 /* hmm... can't find this in our queue! */
1821                                 break;
1822                         }
1823                         /* process the parameter, success flag */
1824                         sctp_asconf_process_param_ack(stcb, ap, 1);
1825                         break;
1826                 default:
1827                         break;
1828                 }               /* switch */
1829
1830                 /* update remaining ASCONF-ACK message length to process */
1831                 if (ack_length > SCTP_SIZE32(param_length)) {
1832                         ack_length -= SCTP_SIZE32(param_length);
1833                 } else {
1834                         break;
1835                 }
1836                 offset += SCTP_SIZE32(param_length);
1837         } /* while */
1838
1839         /*
1840          * if there are any "sent" params still on the queue, these are
1841          * implicitly "success", or "failed" (if we got an error back) ...
1842          * so process these appropriately
1843          *
1844          * we assume that the correlation_id's are monotonically increasing
1845          * beginning from 1 and that we don't have *that* many outstanding
1846          * at any given time
1847          */
1848         if (last_error_id == 0)
1849                 last_error_id--;        /* set to "max" value */
1850         TAILQ_FOREACH_SAFE(aa, &stcb->asoc.asconf_queue, next, aa_next) {
1851                 if (aa->sent == 1) {
1852                         /*
1853                          * implicitly successful or failed if correlation_id
1854                          * < last_error_id, then success else, failure
1855                          */
1856                         if (aa->ap.aph.correlation_id < last_error_id)
1857                                 sctp_asconf_process_param_ack(stcb, aa, 1);
1858                         else
1859                                 sctp_asconf_process_param_ack(stcb, aa, 0);
1860                 } else {
1861                         /*
1862                          * since we always process in order (FIFO queue) if
1863                          * we reach one that hasn't been sent, the rest
1864                          * should not have been sent either. so, we're
1865                          * done...
1866                          */
1867                         break;
1868                 }
1869         }
1870
1871         /* update the next sequence number to use */
1872         asoc->asconf_seq_out_acked++;
1873         /* remove the old ASCONF on our outbound queue */
1874         sctp_toss_old_asconf(stcb);
1875         if (!TAILQ_EMPTY(&stcb->asoc.asconf_queue)) {
1876 #ifdef SCTP_TIMER_BASED_ASCONF
1877                 /* we have more params, so restart our timer */
1878                 sctp_timer_start(SCTP_TIMER_TYPE_ASCONF, stcb->sctp_ep,
1879                                  stcb, net);
1880 #else
1881                 /* we have more params, so send out more */
1882                 sctp_send_asconf(stcb, net, SCTP_ADDR_NOT_LOCKED);
1883 #endif
1884         }
1885 }
1886
1887 #ifdef INET6
1888 static uint32_t
1889 sctp_is_scopeid_in_nets(struct sctp_tcb *stcb, struct sockaddr *sa)
1890 {
1891         struct sockaddr_in6 *sin6, *net6;
1892         struct sctp_nets *net;
1893
1894         if (sa->sa_family != AF_INET6) {
1895                 /* wrong family */
1896                 return (0);
1897         }
1898         sin6 = (struct sockaddr_in6 *)sa;
1899         if (IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr) == 0) {
1900                 /* not link local address */
1901                 return (0);
1902         }
1903         /* hunt through our destination nets list for this scope_id */
1904         TAILQ_FOREACH(net, &stcb->asoc.nets, sctp_next) {
1905                 if (((struct sockaddr *)(&net->ro._l_addr))->sa_family !=
1906                     AF_INET6)
1907                         continue;
1908                 net6 = (struct sockaddr_in6 *)&net->ro._l_addr;
1909                 if (IN6_IS_ADDR_LINKLOCAL(&net6->sin6_addr) == 0)
1910                         continue;
1911                 if (sctp_is_same_scope(sin6, net6)) {
1912                         /* found one */
1913                         return (1);
1914                 }
1915         }
1916         /* didn't find one */
1917         return (0);
1918 }
1919 #endif
1920
1921 /*
1922  * address management functions
1923  */
1924 static void
1925 sctp_addr_mgmt_assoc(struct sctp_inpcb *inp, struct sctp_tcb *stcb,
1926                      struct sctp_ifa *ifa, uint16_t type, int addr_locked)
1927 {
1928         int status;
1929
1930         if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUNDALL) == 0 ||
1931             sctp_is_feature_off(inp, SCTP_PCB_FLAGS_DO_ASCONF)) {
1932                 /* subset bound, no ASCONF allowed case, so ignore */
1933                 return;
1934         }
1935         /*
1936          * note: we know this is not the subset bound, no ASCONF case eg.
1937          * this is boundall or subset bound w/ASCONF allowed
1938          */
1939
1940         /* first, make sure that the address is IPv4 or IPv6 and not jailed */
1941         switch (ifa->address.sa.sa_family) {
1942 #ifdef INET6
1943         case AF_INET6:
1944 #if defined(__FreeBSD__) && !defined(__Userspace__)
1945                 if (prison_check_ip6(inp->ip_inp.inp.inp_cred,
1946                                      &ifa->address.sin6.sin6_addr) != 0) {
1947                         return;
1948                 }
1949 #endif
1950                 break;
1951 #endif
1952 #ifdef INET
1953         case AF_INET:
1954 #if defined(__FreeBSD__) && !defined(__Userspace__)
1955                 if (prison_check_ip4(inp->ip_inp.inp.inp_cred,
1956                                      &ifa->address.sin.sin_addr) != 0) {
1957                         return;
1958                 }
1959 #endif
1960                 break;
1961 #endif
1962         default:
1963                 return;
1964         }
1965 #ifdef INET6
1966         /* make sure we're "allowed" to add this type of addr */
1967         if (ifa->address.sa.sa_family == AF_INET6) {
1968                 /* invalid if we're not a v6 endpoint */
1969                 if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) == 0)
1970                         return;
1971                 /* is the v6 addr really valid ? */
1972                 if (ifa->localifa_flags & SCTP_ADDR_IFA_UNUSEABLE) {
1973                         return;
1974                 }
1975         }
1976 #endif
1977         /* put this address on the "pending/do not use yet" list */
1978         sctp_add_local_addr_restricted(stcb, ifa);
1979         /*
1980          * check address scope if address is out of scope, don't queue
1981          * anything... note: this would leave the address on both inp and
1982          * asoc lists
1983          */
1984         switch (ifa->address.sa.sa_family) {
1985 #ifdef INET6
1986         case AF_INET6:
1987         {
1988                 struct sockaddr_in6 *sin6;
1989
1990                 sin6 = &ifa->address.sin6;
1991                 if (IN6_IS_ADDR_UNSPECIFIED(&sin6->sin6_addr)) {
1992                         /* we skip unspecifed addresses */
1993                         return;
1994                 }
1995                 if (IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr)) {
1996                         if (stcb->asoc.scope.local_scope == 0) {
1997                                 return;
1998                         }
1999                         /* is it the right link local scope? */
2000                         if (sctp_is_scopeid_in_nets(stcb, &ifa->address.sa) == 0) {
2001                                 return;
2002                         }
2003                 }
2004                 if (stcb->asoc.scope.site_scope == 0 &&
2005                     IN6_IS_ADDR_SITELOCAL(&sin6->sin6_addr)) {
2006                         return;
2007                 }
2008                 break;
2009         }
2010 #endif
2011 #ifdef INET
2012         case AF_INET:
2013         {
2014                 struct sockaddr_in *sin;
2015
2016                 /* invalid if we are a v6 only endpoint */
2017                 if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) &&
2018                     SCTP_IPV6_V6ONLY(inp))
2019                         return;
2020
2021                 sin = &ifa->address.sin;
2022                 if (sin->sin_addr.s_addr == 0) {
2023                         /* we skip unspecifed addresses */
2024                         return;
2025                 }
2026                 if (stcb->asoc.scope.ipv4_local_scope == 0 &&
2027                     IN4_ISPRIVATE_ADDRESS(&sin->sin_addr)) {
2028                         return;
2029                 }
2030                 break;
2031         }
2032 #endif
2033         default:
2034                 /* else, not AF_INET or AF_INET6, so skip */
2035                 return;
2036         }
2037
2038         /* queue an asconf for this address add/delete */
2039         if (sctp_is_feature_on(inp, SCTP_PCB_FLAGS_DO_ASCONF)) {
2040                 /* does the peer do asconf? */
2041                 if (stcb->asoc.asconf_supported) {
2042                         /* queue an asconf for this addr */
2043                         status = sctp_asconf_queue_add(stcb, ifa, type);
2044
2045                         /*
2046                          * if queued ok, and in the open state, send out the
2047                          * ASCONF.  If in the non-open state, these will be
2048                          * sent when the state goes open.
2049                          */
2050                         if (status == 0 &&
2051                             ((SCTP_GET_STATE(stcb) == SCTP_STATE_OPEN) ||
2052                              (SCTP_GET_STATE(stcb) == SCTP_STATE_SHUTDOWN_RECEIVED))) {
2053 #ifdef SCTP_TIMER_BASED_ASCONF
2054                                 sctp_timer_start(SCTP_TIMER_TYPE_ASCONF, inp,
2055                                     stcb, stcb->asoc.primary_destination);
2056 #else
2057                                 sctp_send_asconf(stcb, NULL, addr_locked);
2058 #endif
2059                         }
2060                 }
2061         }
2062 }
2063
2064
2065 int
2066 sctp_asconf_iterator_ep(struct sctp_inpcb *inp, void *ptr, uint32_t val SCTP_UNUSED)
2067 {
2068         struct sctp_asconf_iterator *asc;
2069         struct sctp_ifa *ifa;
2070         struct sctp_laddr *l;
2071         int cnt_invalid = 0;
2072
2073         asc = (struct sctp_asconf_iterator *)ptr;
2074         LIST_FOREACH(l, &asc->list_of_work, sctp_nxt_addr) {
2075                 ifa = l->ifa;
2076                 switch (ifa->address.sa.sa_family) {
2077 #ifdef INET6
2078                 case AF_INET6:
2079                         /* invalid if we're not a v6 endpoint */
2080                         if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) == 0) {
2081                                 cnt_invalid++;
2082                                 if (asc->cnt == cnt_invalid)
2083                                         return (1);
2084                         }
2085                         break;
2086 #endif
2087 #ifdef INET
2088                 case AF_INET:
2089                 {
2090                         /* invalid if we are a v6 only endpoint */
2091                         if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) &&
2092                             SCTP_IPV6_V6ONLY(inp)) {
2093                                 cnt_invalid++;
2094                                 if (asc->cnt == cnt_invalid)
2095                                         return (1);
2096                         }
2097                         break;
2098                 }
2099 #endif
2100                 default:
2101                         /* invalid address family */
2102                         cnt_invalid++;
2103                         if (asc->cnt == cnt_invalid)
2104                                 return (1);
2105                 }
2106         }
2107         return (0);
2108 }
2109
2110 static int
2111 sctp_asconf_iterator_ep_end(struct sctp_inpcb *inp, void *ptr, uint32_t val SCTP_UNUSED)
2112 {
2113         struct sctp_ifa *ifa;
2114         struct sctp_asconf_iterator *asc;
2115         struct sctp_laddr *laddr, *nladdr, *l;
2116
2117         /* Only for specific case not bound all */
2118         asc = (struct sctp_asconf_iterator *)ptr;
2119         LIST_FOREACH(l, &asc->list_of_work, sctp_nxt_addr) {
2120                 ifa = l->ifa;
2121                 if (l->action == SCTP_ADD_IP_ADDRESS) {
2122                         LIST_FOREACH(laddr, &inp->sctp_addr_list,
2123                                      sctp_nxt_addr) {
2124                                 if (laddr->ifa == ifa) {
2125                                         laddr->action = 0;
2126                                         break;
2127                                 }
2128
2129                         }
2130                 } else if (l->action == SCTP_DEL_IP_ADDRESS) {
2131                         LIST_FOREACH_SAFE(laddr, &inp->sctp_addr_list, sctp_nxt_addr, nladdr) {
2132                                 /* remove only after all guys are done */
2133                                 if (laddr->ifa == ifa) {
2134                                         sctp_del_local_addr_ep(inp, ifa);
2135                                 }
2136                         }
2137                 }
2138         }
2139         return (0);
2140 }
2141
2142 void
2143 sctp_asconf_iterator_stcb(struct sctp_inpcb *inp, struct sctp_tcb *stcb,
2144                           void *ptr, uint32_t val SCTP_UNUSED)
2145 {
2146         struct sctp_asconf_iterator *asc;
2147         struct sctp_ifa *ifa;
2148         struct sctp_laddr *l;
2149         int cnt_invalid = 0;
2150         int type, status;
2151         int num_queued = 0;
2152
2153         asc = (struct sctp_asconf_iterator *)ptr;
2154         LIST_FOREACH(l, &asc->list_of_work, sctp_nxt_addr) {
2155                 ifa = l->ifa;
2156                 type = l->action;
2157
2158                 /* address's vrf_id must be the vrf_id of the assoc */
2159                 if (ifa->vrf_id != stcb->asoc.vrf_id) {
2160                         continue;
2161                 }
2162
2163                 /* Same checks again for assoc */
2164                 switch (ifa->address.sa.sa_family) {
2165 #ifdef INET6
2166                 case AF_INET6:
2167                 {
2168                         /* invalid if we're not a v6 endpoint */
2169                         struct sockaddr_in6 *sin6;
2170
2171                         if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) == 0) {
2172                                 cnt_invalid++;
2173                                 if (asc->cnt == cnt_invalid)
2174                                         return;
2175                                 else
2176                                         continue;
2177                         }
2178                         sin6 = &ifa->address.sin6;
2179                         if (IN6_IS_ADDR_UNSPECIFIED(&sin6->sin6_addr)) {
2180                                 /* we skip unspecifed addresses */
2181                                 continue;
2182                         }
2183 #if defined(__FreeBSD__) && !defined(__Userspace__)
2184                         if (prison_check_ip6(inp->ip_inp.inp.inp_cred,
2185                                              &sin6->sin6_addr) != 0) {
2186                                 continue;
2187                         }
2188 #endif
2189                         if (IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr)) {
2190                                 if (stcb->asoc.scope.local_scope == 0) {
2191                                         continue;
2192                                 }
2193                                 /* is it the right link local scope? */
2194                                 if (sctp_is_scopeid_in_nets(stcb, &ifa->address.sa) == 0) {
2195                                         continue;
2196                                 }
2197                         }
2198                         break;
2199                 }
2200 #endif
2201 #ifdef INET
2202                 case AF_INET:
2203                 {
2204                         /* invalid if we are a v6 only endpoint */
2205                         struct sockaddr_in *sin;
2206
2207                         /* invalid if we are a v6 only endpoint */
2208                         if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) &&
2209                             SCTP_IPV6_V6ONLY(inp))
2210                                 continue;
2211
2212                         sin = &ifa->address.sin;
2213                         if (sin->sin_addr.s_addr == 0) {
2214                                 /* we skip unspecifed addresses */
2215                                 continue;
2216                         }
2217 #if defined(__FreeBSD__) && !defined(__Userspace__)
2218                         if (prison_check_ip4(inp->ip_inp.inp.inp_cred,
2219                                              &sin->sin_addr) != 0) {
2220                                 continue;
2221                         }
2222 #endif
2223                         if (stcb->asoc.scope.ipv4_local_scope == 0 &&
2224                             IN4_ISPRIVATE_ADDRESS(&sin->sin_addr)) {
2225                                 continue;
2226                         }
2227                         if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) &&
2228                             SCTP_IPV6_V6ONLY(inp)) {
2229                                 cnt_invalid++;
2230                                 if (asc->cnt == cnt_invalid)
2231                                         return;
2232                                 else
2233                                         continue;
2234                         }
2235                         break;
2236                 }
2237 #endif
2238                 default:
2239                         /* invalid address family */
2240                         cnt_invalid++;
2241                         if (asc->cnt == cnt_invalid)
2242                                 return;
2243                         else
2244                                 continue;
2245                         break;
2246                 }
2247
2248                 if (type == SCTP_ADD_IP_ADDRESS) {
2249                         /* prevent this address from being used as a source */
2250                         sctp_add_local_addr_restricted(stcb, ifa);
2251                 } else if (type == SCTP_DEL_IP_ADDRESS) {
2252                         struct sctp_nets *net;
2253                         TAILQ_FOREACH(net, &stcb->asoc.nets, sctp_next) {
2254                                 /* delete this address if cached */
2255                                 if (net->ro._s_addr == ifa) {
2256                                         sctp_free_ifa(net->ro._s_addr);
2257                                         net->ro._s_addr = NULL;
2258                                         net->src_addr_selected = 0;
2259 #if defined(__FreeBSD__) && !defined(__Userspace__)
2260                                         RO_NHFREE(&net->ro);
2261 #else
2262                                         if (net->ro.ro_rt) {
2263                                                 RTFREE(net->ro.ro_rt);
2264                                                 net->ro.ro_rt = NULL;
2265                                         }
2266 #endif
2267                                         /*
2268                                          * Now we deleted our src address,
2269                                          * should we not also now reset the
2270                                          * cwnd/rto to start as if its a new
2271                                          * address?
2272                                          */
2273                                         stcb->asoc.cc_functions.sctp_set_initial_cc_param(stcb, net);
2274                                         net->RTO = 0;
2275
2276                                 }
2277                         }
2278                 } else if (type == SCTP_SET_PRIM_ADDR) {
2279                         if ((stcb->sctp_ep->sctp_flags & SCTP_PCB_FLAGS_BOUNDALL) == 0) {
2280                                 /* must validate the ifa is in the ep */
2281                                 if (sctp_is_addr_in_ep(stcb->sctp_ep, ifa) == 0) {
2282                                         continue;
2283                                 }
2284                         } else {
2285                                 /* Need to check scopes for this guy */
2286                                 if (sctp_is_address_in_scope(ifa, &stcb->asoc.scope, 0) == 0) {
2287                                         continue;
2288                                 }
2289                         }
2290                 }
2291                 /* queue an asconf for this address add/delete */
2292                 if (sctp_is_feature_on(inp, SCTP_PCB_FLAGS_DO_ASCONF) &&
2293                     stcb->asoc.asconf_supported == 1) {
2294                         /* queue an asconf for this addr */
2295                         status = sctp_asconf_queue_add(stcb, ifa, type);
2296                         /*
2297                          * if queued ok, and in the open state, update the
2298                          * count of queued params.  If in the non-open state,
2299                          * these get sent when the assoc goes open.
2300                          */
2301                         if ((SCTP_GET_STATE(stcb) == SCTP_STATE_OPEN) ||
2302                             (SCTP_GET_STATE(stcb) == SCTP_STATE_SHUTDOWN_RECEIVED)) {
2303                                 if (status >= 0) {
2304                                         num_queued++;
2305                                 }
2306                         }
2307                 }
2308         }
2309         /*
2310          * If we have queued params in the open state, send out an ASCONF.
2311          */
2312         if (num_queued > 0) {
2313                 sctp_send_asconf(stcb, NULL, SCTP_ADDR_NOT_LOCKED);
2314         }
2315 }
2316
2317 void
2318 sctp_asconf_iterator_end(void *ptr, uint32_t val SCTP_UNUSED)
2319 {
2320         struct sctp_asconf_iterator *asc;
2321         struct sctp_ifa *ifa;
2322         struct sctp_laddr *l, *nl;
2323
2324         asc = (struct sctp_asconf_iterator *)ptr;
2325         LIST_FOREACH_SAFE(l, &asc->list_of_work, sctp_nxt_addr, nl) {
2326                 ifa = l->ifa;
2327                 if (l->action == SCTP_ADD_IP_ADDRESS) {
2328                         /* Clear the defer use flag */
2329                         ifa->localifa_flags &= ~SCTP_ADDR_DEFER_USE;
2330                 }
2331                 sctp_free_ifa(ifa);
2332                 SCTP_ZONE_FREE(SCTP_BASE_INFO(ipi_zone_laddr), l);
2333                 SCTP_DECR_LADDR_COUNT();
2334         }
2335         SCTP_FREE(asc, SCTP_M_ASC_IT);
2336 }
2337
2338 /*
2339  * sa is the sockaddr to ask the peer to set primary to.
2340  * returns: 0 = completed, -1 = error
2341  */
2342 int32_t
2343 sctp_set_primary_ip_address_sa(struct sctp_tcb *stcb, struct sockaddr *sa)
2344 {
2345         uint32_t vrf_id;
2346         struct sctp_ifa *ifa;
2347
2348         /* find the ifa for the desired set primary */
2349         vrf_id = stcb->asoc.vrf_id;
2350         ifa = sctp_find_ifa_by_addr(sa, vrf_id, SCTP_ADDR_NOT_LOCKED);
2351         if (ifa == NULL) {
2352                 /* Invalid address */
2353                 return (-1);
2354         }
2355
2356         /* queue an ASCONF:SET_PRIM_ADDR to be sent */
2357         if (!sctp_asconf_queue_add(stcb, ifa, SCTP_SET_PRIM_ADDR)) {
2358                 /* set primary queuing succeeded */
2359                 SCTPDBG(SCTP_DEBUG_ASCONF1,
2360                         "set_primary_ip_address_sa: queued on tcb=%p, ",
2361                         (void *)stcb);
2362                 SCTPDBG_ADDR(SCTP_DEBUG_ASCONF1, sa);
2363                 if ((SCTP_GET_STATE(stcb) == SCTP_STATE_OPEN) ||
2364                     (SCTP_GET_STATE(stcb) == SCTP_STATE_SHUTDOWN_RECEIVED)) {
2365 #ifdef SCTP_TIMER_BASED_ASCONF
2366                         sctp_timer_start(SCTP_TIMER_TYPE_ASCONF,
2367                                          stcb->sctp_ep, stcb,
2368                                          stcb->asoc.primary_destination);
2369 #else
2370                         sctp_send_asconf(stcb, NULL, SCTP_ADDR_NOT_LOCKED);
2371 #endif
2372                 }
2373         } else {
2374                 SCTPDBG(SCTP_DEBUG_ASCONF1, "set_primary_ip_address_sa: failed to add to queue on tcb=%p, ",
2375                         (void *)stcb);
2376                 SCTPDBG_ADDR(SCTP_DEBUG_ASCONF1, sa);
2377                 return (-1);
2378         }
2379         return (0);
2380 }
2381
2382 int
2383 sctp_is_addr_pending(struct sctp_tcb *stcb, struct sctp_ifa *sctp_ifa)
2384 {
2385         struct sctp_tmit_chunk *chk, *nchk;
2386         unsigned int offset, asconf_limit;
2387         struct sctp_asconf_chunk *acp;
2388         struct sctp_asconf_paramhdr *aph;
2389         uint8_t aparam_buf[SCTP_PARAM_BUFFER_SIZE];
2390         struct sctp_paramhdr *ph;
2391         int add_cnt, del_cnt;
2392         uint16_t last_param_type;
2393
2394         add_cnt = del_cnt = 0;
2395         last_param_type = 0;
2396         TAILQ_FOREACH_SAFE(chk, &stcb->asoc.asconf_send_queue, sctp_next, nchk) {
2397                 if (chk->data == NULL) {
2398                         SCTPDBG(SCTP_DEBUG_ASCONF1, "is_addr_pending: No mbuf data?\n");
2399                         continue;
2400                 }
2401                 offset = 0;
2402                 acp = mtod(chk->data, struct sctp_asconf_chunk *);
2403                 offset += sizeof(struct sctp_asconf_chunk);
2404                 asconf_limit = ntohs(acp->ch.chunk_length);
2405                 ph = (struct sctp_paramhdr *)sctp_m_getptr(chk->data, offset, sizeof(struct sctp_paramhdr), aparam_buf);
2406                 if (ph == NULL) {
2407                         SCTPDBG(SCTP_DEBUG_ASCONF1, "is_addr_pending: couldn't get lookup addr!\n");
2408                         continue;
2409                 }
2410                 offset += ntohs(ph->param_length);
2411
2412                 aph = (struct sctp_asconf_paramhdr *)sctp_m_getptr(chk->data, offset, sizeof(struct sctp_asconf_paramhdr), aparam_buf);
2413                 if (aph == NULL) {
2414                         SCTPDBG(SCTP_DEBUG_ASCONF1, "is_addr_pending: Empty ASCONF will be sent?\n");
2415                         continue;
2416                 }
2417                 while (aph != NULL) {
2418                         unsigned int param_length, param_type;
2419
2420                         param_type = ntohs(aph->ph.param_type);
2421                         param_length = ntohs(aph->ph.param_length);
2422                         if (offset + param_length > asconf_limit) {
2423                                 /* parameter goes beyond end of chunk! */
2424                                 break;
2425                         }
2426                         if (param_length > sizeof(aparam_buf)) {
2427                                 SCTPDBG(SCTP_DEBUG_ASCONF1, "is_addr_pending: param length (%u) larger than buffer size!\n", param_length);
2428                                 break;
2429                         }
2430                         if (param_length <= sizeof(struct sctp_paramhdr)) {
2431                                 SCTPDBG(SCTP_DEBUG_ASCONF1, "is_addr_pending: param length(%u) too short\n", param_length);
2432                                 break;
2433                         }
2434
2435                         aph = (struct sctp_asconf_paramhdr *)sctp_m_getptr(chk->data, offset, param_length, aparam_buf);
2436                         if (aph == NULL) {
2437                                 SCTPDBG(SCTP_DEBUG_ASCONF1, "is_addr_pending: couldn't get entire param\n");
2438                                 break;
2439                         }
2440
2441                         ph = (struct sctp_paramhdr *)(aph + 1);
2442                         if (sctp_addr_match(ph, &sctp_ifa->address.sa) != 0) {
2443                                 switch (param_type) {
2444                                 case SCTP_ADD_IP_ADDRESS:
2445                                         add_cnt++;
2446                                         break;
2447                                 case SCTP_DEL_IP_ADDRESS:
2448                                         del_cnt++;
2449                                         break;
2450                                 default:
2451                                         break;
2452                                 }
2453                                 last_param_type = param_type;
2454                         }
2455
2456                         offset += SCTP_SIZE32(param_length);
2457                         if (offset >= asconf_limit) {
2458                                 /* no more data in the mbuf chain */
2459                                 break;
2460                         }
2461                         /* get pointer to next asconf param */
2462                         aph = (struct sctp_asconf_paramhdr *)sctp_m_getptr(chk->data, offset, sizeof(struct sctp_asconf_paramhdr), aparam_buf);
2463                 }
2464         }
2465
2466         /* we want to find the sequences which consist of ADD -> DEL -> ADD or DEL -> ADD */
2467         if (add_cnt > del_cnt ||
2468             (add_cnt == del_cnt && last_param_type == SCTP_ADD_IP_ADDRESS)) {
2469                 return (1);
2470         }
2471         return (0);
2472 }
2473
2474 static struct sockaddr *
2475 sctp_find_valid_localaddr(struct sctp_tcb *stcb, int addr_locked)
2476 {
2477         struct sctp_vrf *vrf = NULL;
2478         struct sctp_ifn *sctp_ifn;
2479         struct sctp_ifa *sctp_ifa;
2480
2481         if (addr_locked == SCTP_ADDR_NOT_LOCKED)
2482                 SCTP_IPI_ADDR_RLOCK();
2483         vrf = sctp_find_vrf(stcb->asoc.vrf_id);
2484         if (vrf == NULL) {
2485                 if (addr_locked == SCTP_ADDR_NOT_LOCKED)
2486                         SCTP_IPI_ADDR_RUNLOCK();
2487                 return (NULL);
2488         }
2489         LIST_FOREACH(sctp_ifn, &vrf->ifnlist, next_ifn) {
2490                 if (stcb->asoc.scope.loopback_scope == 0 &&
2491                     SCTP_IFN_IS_IFT_LOOP(sctp_ifn)) {
2492                         /* Skip if loopback_scope not set */
2493                         continue;
2494                 }
2495                 LIST_FOREACH(sctp_ifa, &sctp_ifn->ifalist, next_ifa) {
2496                         switch (sctp_ifa->address.sa.sa_family) {
2497 #ifdef INET
2498                         case AF_INET:
2499                                 if (stcb->asoc.scope.ipv4_addr_legal) {
2500                                         struct sockaddr_in *sin;
2501
2502                                         sin = &sctp_ifa->address.sin;
2503                                         if (sin->sin_addr.s_addr == 0) {
2504                                                 /* skip unspecifed addresses */
2505                                                 continue;
2506                                         }
2507 #if defined(__FreeBSD__) && !defined(__Userspace__)
2508                                         if (prison_check_ip4(stcb->sctp_ep->ip_inp.inp.inp_cred,
2509                                                              &sin->sin_addr) != 0) {
2510                                                 continue;
2511                                         }
2512 #endif
2513                                         if (stcb->asoc.scope.ipv4_local_scope == 0 &&
2514                                             IN4_ISPRIVATE_ADDRESS(&sin->sin_addr))
2515                                                 continue;
2516
2517                                         if (sctp_is_addr_restricted(stcb, sctp_ifa) &&
2518                                             (!sctp_is_addr_pending(stcb, sctp_ifa)))
2519                                                 continue;
2520                                         /* found a valid local v4 address to use */
2521                                         if (addr_locked == SCTP_ADDR_NOT_LOCKED)
2522                                                 SCTP_IPI_ADDR_RUNLOCK();
2523                                         return (&sctp_ifa->address.sa);
2524                                 }
2525                                 break;
2526 #endif
2527 #ifdef INET6
2528                         case AF_INET6:
2529                                 if (stcb->asoc.scope.ipv6_addr_legal) {
2530                                         struct sockaddr_in6 *sin6;
2531
2532                                         if (sctp_ifa->localifa_flags & SCTP_ADDR_IFA_UNUSEABLE) {
2533                                                 continue;
2534                                         }
2535
2536                                         sin6 = &sctp_ifa->address.sin6;
2537                                         if (IN6_IS_ADDR_UNSPECIFIED(&sin6->sin6_addr)) {
2538                                                 /* we skip unspecifed addresses */
2539                                                 continue;
2540                                         }
2541 #if defined(__FreeBSD__) && !defined(__Userspace__)
2542                                         if (prison_check_ip6(stcb->sctp_ep->ip_inp.inp.inp_cred,
2543                                                              &sin6->sin6_addr) != 0) {
2544                                                 continue;
2545                                         }
2546 #endif
2547                                         if (stcb->asoc.scope.local_scope == 0 &&
2548                                             IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr))
2549                                                 continue;
2550                                         if (stcb->asoc.scope.site_scope == 0 &&
2551                                             IN6_IS_ADDR_SITELOCAL(&sin6->sin6_addr))
2552                                                 continue;
2553
2554                                         if (sctp_is_addr_restricted(stcb, sctp_ifa) &&
2555                                             (!sctp_is_addr_pending(stcb, sctp_ifa)))
2556                                                 continue;
2557                                         /* found a valid local v6 address to use */
2558                                         if (addr_locked == SCTP_ADDR_NOT_LOCKED)
2559                                                 SCTP_IPI_ADDR_RUNLOCK();
2560                                         return (&sctp_ifa->address.sa);
2561                                 }
2562                                 break;
2563 #endif
2564                         default:
2565                                 break;
2566                         }
2567                 }
2568         }
2569         /* no valid addresses found */
2570         if (addr_locked == SCTP_ADDR_NOT_LOCKED)
2571                 SCTP_IPI_ADDR_RUNLOCK();
2572         return (NULL);
2573 }
2574
2575 static struct sockaddr *
2576 sctp_find_valid_localaddr_ep(struct sctp_tcb *stcb)
2577 {
2578         struct sctp_laddr *laddr;
2579
2580         LIST_FOREACH(laddr, &stcb->sctp_ep->sctp_addr_list, sctp_nxt_addr) {
2581                 if (laddr->ifa == NULL) {
2582                         continue;
2583                 }
2584                 /* is the address restricted ? */
2585                 if (sctp_is_addr_restricted(stcb, laddr->ifa) &&
2586                     (!sctp_is_addr_pending(stcb, laddr->ifa)))
2587                         continue;
2588
2589                 /* found a valid local address to use */
2590                 return (&laddr->ifa->address.sa);
2591         }
2592         /* no valid addresses found */
2593         return (NULL);
2594 }
2595
2596 /*
2597  * builds an ASCONF chunk from queued ASCONF params.
2598  * returns NULL on error (no mbuf, no ASCONF params queued, etc).
2599  */
2600 struct mbuf *
2601 sctp_compose_asconf(struct sctp_tcb *stcb, int *retlen, int addr_locked)
2602 {
2603         struct mbuf *m_asconf, *m_asconf_chk;
2604         struct sctp_asconf_addr *aa;
2605         struct sctp_asconf_chunk *acp;
2606         struct sctp_asconf_paramhdr *aph;
2607         struct sctp_asconf_addr_param *aap;
2608         uint32_t p_length;
2609         uint32_t correlation_id = 1;    /* 0 is reserved... */
2610         caddr_t ptr, lookup_ptr;
2611         uint8_t lookup_used = 0;
2612
2613         /* are there any asconf params to send? */
2614         TAILQ_FOREACH(aa, &stcb->asoc.asconf_queue, next) {
2615                 if (aa->sent == 0)
2616                         break;
2617         }
2618         if (aa == NULL)
2619                 return (NULL);
2620
2621         /*
2622          * get a chunk header mbuf and a cluster for the asconf params since
2623          * it's simpler to fill in the asconf chunk header lookup address on
2624          * the fly
2625          */
2626         m_asconf_chk = sctp_get_mbuf_for_msg(sizeof(struct sctp_asconf_chunk), 0, M_NOWAIT, 1, MT_DATA);
2627         if (m_asconf_chk == NULL) {
2628                 /* no mbuf's */
2629                 SCTPDBG(SCTP_DEBUG_ASCONF1,
2630                         "sctp_compose_asconf: couldn't get chunk mbuf!\n");
2631                 return (NULL);
2632         }
2633         m_asconf = sctp_get_mbuf_for_msg(MCLBYTES, 0, M_NOWAIT, 1, MT_DATA);
2634         if (m_asconf == NULL) {
2635                 /* no mbuf's */
2636                 SCTPDBG(SCTP_DEBUG_ASCONF1,
2637                         "sctp_compose_asconf: couldn't get mbuf!\n");
2638                 sctp_m_freem(m_asconf_chk);
2639                 return (NULL);
2640         }
2641         SCTP_BUF_LEN(m_asconf_chk) = sizeof(struct sctp_asconf_chunk);
2642         SCTP_BUF_LEN(m_asconf) = 0;
2643         acp = mtod(m_asconf_chk, struct sctp_asconf_chunk *);
2644         memset(acp, 0, sizeof(struct sctp_asconf_chunk));
2645         /* save pointers to lookup address and asconf params */
2646         lookup_ptr = (caddr_t)(acp + 1);        /* after the header */
2647         ptr = mtod(m_asconf, caddr_t);  /* beginning of cluster */
2648
2649         /* fill in chunk header info */
2650         acp->ch.chunk_type = SCTP_ASCONF;
2651         acp->ch.chunk_flags = 0;
2652         acp->serial_number = htonl(stcb->asoc.asconf_seq_out);
2653         stcb->asoc.asconf_seq_out++;
2654
2655         /* add parameters... up to smallest MTU allowed */
2656         TAILQ_FOREACH(aa, &stcb->asoc.asconf_queue, next) {
2657                 if (aa->sent)
2658                         continue;
2659                 /* get the parameter length */
2660                 p_length = SCTP_SIZE32(aa->ap.aph.ph.param_length);
2661                 /* will it fit in current chunk? */
2662                 if ((SCTP_BUF_LEN(m_asconf) + p_length > stcb->asoc.smallest_mtu) ||
2663                     (SCTP_BUF_LEN(m_asconf) + p_length > MCLBYTES)) {
2664                         /* won't fit, so we're done with this chunk */
2665                         break;
2666                 }
2667                 /* assign (and store) a correlation id */
2668                 aa->ap.aph.correlation_id = correlation_id++;
2669
2670                 /*
2671                  * fill in address if we're doing a delete this is a simple
2672                  * way for us to fill in the correlation address, which
2673                  * should only be used by the peer if we're deleting our
2674                  * source address and adding a new address (e.g. renumbering
2675                  * case)
2676                  */
2677                 if (lookup_used == 0 &&
2678                     (aa->special_del == 0) &&
2679                     aa->ap.aph.ph.param_type == SCTP_DEL_IP_ADDRESS) {
2680                         struct sctp_ipv6addr_param *lookup;
2681                         uint16_t p_size, addr_size;
2682
2683                         lookup = (struct sctp_ipv6addr_param *)lookup_ptr;
2684                         lookup->ph.param_type =
2685                             htons(aa->ap.addrp.ph.param_type);
2686                         if (aa->ap.addrp.ph.param_type == SCTP_IPV6_ADDRESS) {
2687                                 /* copy IPv6 address */
2688                                 p_size = sizeof(struct sctp_ipv6addr_param);
2689                                 addr_size = sizeof(struct in6_addr);
2690                         } else {
2691                                 /* copy IPv4 address */
2692                                 p_size = sizeof(struct sctp_ipv4addr_param);
2693                                 addr_size = sizeof(struct in_addr);
2694                         }
2695                         lookup->ph.param_length = htons(SCTP_SIZE32(p_size));
2696                         memcpy(lookup->addr, &aa->ap.addrp.addr, addr_size);
2697                         SCTP_BUF_LEN(m_asconf_chk) += SCTP_SIZE32(p_size);
2698                         lookup_used = 1;
2699                 }
2700                 /* copy into current space */
2701                 memcpy(ptr, &aa->ap, p_length);
2702
2703                 /* network elements and update lengths */
2704                 aph = (struct sctp_asconf_paramhdr *)ptr;
2705                 aap = (struct sctp_asconf_addr_param *)ptr;
2706                 /* correlation_id is transparent to peer, no htonl needed */
2707                 aph->ph.param_type = htons(aph->ph.param_type);
2708                 aph->ph.param_length = htons(aph->ph.param_length);
2709                 aap->addrp.ph.param_type = htons(aap->addrp.ph.param_type);
2710                 aap->addrp.ph.param_length = htons(aap->addrp.ph.param_length);
2711
2712                 SCTP_BUF_LEN(m_asconf) += SCTP_SIZE32(p_length);
2713                 ptr += SCTP_SIZE32(p_length);
2714
2715                 /*
2716                  * these params are removed off the pending list upon
2717                  * getting an ASCONF-ACK back from the peer, just set flag
2718                  */
2719                 aa->sent = 1;
2720         }
2721         /* check to see if the lookup addr has been populated yet */
2722         if (lookup_used == 0) {
2723                 /* NOTE: if the address param is optional, can skip this... */
2724                 /* add any valid (existing) address... */
2725                 struct sctp_ipv6addr_param *lookup;
2726                 uint16_t p_size, addr_size;
2727                 struct sockaddr *found_addr;
2728                 caddr_t addr_ptr;
2729
2730                 if (stcb->sctp_ep->sctp_flags & SCTP_PCB_FLAGS_BOUNDALL)
2731                         found_addr = sctp_find_valid_localaddr(stcb,
2732                                                                addr_locked);
2733                 else
2734                         found_addr = sctp_find_valid_localaddr_ep(stcb);
2735
2736                 lookup = (struct sctp_ipv6addr_param *)lookup_ptr;
2737                 if (found_addr != NULL) {
2738                         switch (found_addr->sa_family) {
2739 #ifdef INET6
2740                         case AF_INET6:
2741                                 /* copy IPv6 address */
2742                                 lookup->ph.param_type =
2743                                     htons(SCTP_IPV6_ADDRESS);
2744                                 p_size = sizeof(struct sctp_ipv6addr_param);
2745                                 addr_size = sizeof(struct in6_addr);
2746                                 addr_ptr = (caddr_t)&((struct sockaddr_in6 *)
2747                                     found_addr)->sin6_addr;
2748                                 break;
2749 #endif
2750 #ifdef INET
2751                         case AF_INET:
2752                                 /* copy IPv4 address */
2753                                 lookup->ph.param_type =
2754                                     htons(SCTP_IPV4_ADDRESS);
2755                                 p_size = sizeof(struct sctp_ipv4addr_param);
2756                                 addr_size = sizeof(struct in_addr);
2757                                 addr_ptr = (caddr_t)&((struct sockaddr_in *)
2758                                     found_addr)->sin_addr;
2759                                 break;
2760 #endif
2761                         default:
2762                                 SCTPDBG(SCTP_DEBUG_ASCONF1,
2763                                         "sctp_compose_asconf: no usable lookup addr (family = %d)!\n",
2764                                         found_addr->sa_family);
2765                                 sctp_m_freem(m_asconf_chk);
2766                                 sctp_m_freem(m_asconf);
2767                                 return (NULL);
2768                         }
2769                         lookup->ph.param_length = htons(SCTP_SIZE32(p_size));
2770                         memcpy(lookup->addr, addr_ptr, addr_size);
2771                         SCTP_BUF_LEN(m_asconf_chk) += SCTP_SIZE32(p_size);
2772                 } else {
2773                         /* uh oh... don't have any address?? */
2774                         SCTPDBG(SCTP_DEBUG_ASCONF1,
2775                                 "sctp_compose_asconf: no lookup addr!\n");
2776                         sctp_m_freem(m_asconf_chk);
2777                         sctp_m_freem(m_asconf);
2778                         return (NULL);
2779                 }
2780         }
2781         /* chain it all together */
2782         SCTP_BUF_NEXT(m_asconf_chk) = m_asconf;
2783         *retlen = SCTP_BUF_LEN(m_asconf_chk) + SCTP_BUF_LEN(m_asconf);
2784         acp->ch.chunk_length = htons(*retlen);
2785
2786         return (m_asconf_chk);
2787 }
2788
2789 /*
2790  * section to handle address changes before an association is up eg. changes
2791  * during INIT/INIT-ACK/COOKIE-ECHO handshake
2792  */
2793
2794 /*
2795  * processes the (local) addresses in the INIT-ACK chunk
2796  */
2797 static void
2798 sctp_process_initack_addresses(struct sctp_tcb *stcb, struct mbuf *m,
2799     unsigned int offset, unsigned int length)
2800 {
2801         struct sctp_paramhdr tmp_param, *ph;
2802         uint16_t plen, ptype;
2803         struct sctp_ifa *sctp_ifa;
2804         union sctp_sockstore store;
2805 #ifdef INET6
2806         struct sctp_ipv6addr_param addr6_store;
2807 #endif
2808 #ifdef INET
2809         struct sctp_ipv4addr_param addr4_store;
2810 #endif
2811
2812         SCTPDBG(SCTP_DEBUG_ASCONF2, "processing init-ack addresses\n");
2813         if (stcb == NULL) /* Un-needed check for SA */
2814                 return;
2815
2816         /* convert to upper bound */
2817         length += offset;
2818
2819         if ((offset + sizeof(struct sctp_paramhdr)) > length) {
2820                 return;
2821         }
2822         /* go through the addresses in the init-ack */
2823         ph = (struct sctp_paramhdr *)
2824              sctp_m_getptr(m, offset, sizeof(struct sctp_paramhdr),
2825                            (uint8_t *)&tmp_param);
2826         while (ph != NULL) {
2827                 ptype = ntohs(ph->param_type);
2828                 plen = ntohs(ph->param_length);
2829                 switch (ptype) {
2830 #ifdef INET6
2831                 case SCTP_IPV6_ADDRESS:
2832                 {
2833                         struct sctp_ipv6addr_param *a6p;
2834
2835                         /* get the entire IPv6 address param */
2836                         a6p = (struct sctp_ipv6addr_param *)
2837                             sctp_m_getptr(m, offset,
2838                             sizeof(struct sctp_ipv6addr_param),
2839                             (uint8_t *)&addr6_store);
2840                         if (plen != sizeof(struct sctp_ipv6addr_param) ||
2841                             a6p == NULL) {
2842                                 return;
2843                         }
2844                         memset(&store, 0, sizeof(union sctp_sockstore));
2845                         store.sin6.sin6_family = AF_INET6;
2846 #ifdef HAVE_SIN6_LEN
2847                         store.sin6.sin6_len = sizeof(struct sockaddr_in6);
2848 #endif
2849                         store.sin6.sin6_port = stcb->rport;
2850                         memcpy(&store.sin6.sin6_addr, a6p->addr, sizeof(struct in6_addr));
2851                         break;
2852                 }
2853 #endif
2854 #ifdef INET
2855                 case SCTP_IPV4_ADDRESS:
2856                 {
2857                         struct sctp_ipv4addr_param *a4p;
2858
2859                         /* get the entire IPv4 address param */
2860                         a4p = (struct sctp_ipv4addr_param *)sctp_m_getptr(m, offset,
2861                                                                           sizeof(struct sctp_ipv4addr_param),
2862                                                                           (uint8_t *)&addr4_store);
2863                         if (plen != sizeof(struct sctp_ipv4addr_param) ||
2864                             a4p == NULL) {
2865                                 return;
2866                         }
2867                         memset(&store, 0, sizeof(union sctp_sockstore));
2868                         store.sin.sin_family = AF_INET;
2869 #ifdef HAVE_SIN_LEN
2870                         store.sin.sin_len = sizeof(struct sockaddr_in);
2871 #endif
2872                         store.sin.sin_port = stcb->rport;
2873                         store.sin.sin_addr.s_addr = a4p->addr;
2874                         break;
2875                 }
2876 #endif
2877                 default:
2878                         goto next_addr;
2879                 }
2880
2881                 /* see if this address really (still) exists */
2882                 sctp_ifa = sctp_find_ifa_by_addr(&store.sa, stcb->asoc.vrf_id,
2883                                                  SCTP_ADDR_NOT_LOCKED);
2884                 if (sctp_ifa == NULL) {
2885                         /* address doesn't exist anymore */
2886                         int status;
2887
2888                         /* are ASCONFs allowed ? */
2889                         if ((sctp_is_feature_on(stcb->sctp_ep,
2890                             SCTP_PCB_FLAGS_DO_ASCONF)) &&
2891                             stcb->asoc.asconf_supported) {
2892                                 /* queue an ASCONF DEL_IP_ADDRESS */
2893                                 status = sctp_asconf_queue_sa_delete(stcb, &store.sa);
2894                                 /*
2895                                  * if queued ok, and in correct state, send
2896                                  * out the ASCONF.
2897                                  */
2898                                 if (status == 0 &&
2899                                     SCTP_GET_STATE(stcb) == SCTP_STATE_OPEN) {
2900 #ifdef SCTP_TIMER_BASED_ASCONF
2901                                         sctp_timer_start(SCTP_TIMER_TYPE_ASCONF,
2902                                                          stcb->sctp_ep, stcb,
2903                                                          stcb->asoc.primary_destination);
2904 #else
2905                                         sctp_send_asconf(stcb, NULL, SCTP_ADDR_NOT_LOCKED);
2906 #endif
2907                                 }
2908                         }
2909                 }
2910
2911 next_addr:
2912                 /*
2913                  * Sanity check:  Make sure the length isn't 0, otherwise
2914                  * we'll be stuck in this loop for a long time...
2915                  */
2916                 if (SCTP_SIZE32(plen) == 0) {
2917                         SCTP_PRINTF("process_initack_addrs: bad len (%d) type=%xh\n",
2918                                     plen, ptype);
2919                         return;
2920                 }
2921                 /* get next parameter */
2922                 offset += SCTP_SIZE32(plen);
2923                 if ((offset + sizeof(struct sctp_paramhdr)) > length)
2924                         return;
2925                 ph = (struct sctp_paramhdr *)sctp_m_getptr(m, offset,
2926                     sizeof(struct sctp_paramhdr), (uint8_t *)&tmp_param);
2927         } /* while */
2928 }
2929
2930 /* FIX ME: need to verify return result for v6 address type if v6 disabled */
2931 /*
2932  * checks to see if a specific address is in the initack address list returns
2933  * 1 if found, 0 if not
2934  */
2935 static uint32_t
2936 sctp_addr_in_initack(struct mbuf *m, uint32_t offset, uint32_t length, struct sockaddr *sa)
2937 {
2938         struct sctp_paramhdr tmp_param, *ph;
2939         uint16_t plen, ptype;
2940 #ifdef INET
2941         struct sockaddr_in *sin;
2942         struct sctp_ipv4addr_param *a4p;
2943         struct sctp_ipv6addr_param addr4_store;
2944 #endif
2945 #ifdef INET6
2946         struct sockaddr_in6 *sin6;
2947         struct sctp_ipv6addr_param *a6p;
2948         struct sctp_ipv6addr_param addr6_store;
2949 #ifdef SCTP_EMBEDDED_V6_SCOPE
2950         struct sockaddr_in6 sin6_tmp;
2951 #endif
2952 #endif
2953
2954         switch (sa->sa_family) {
2955 #ifdef INET
2956         case AF_INET:
2957                 break;
2958 #endif
2959 #ifdef INET6
2960         case AF_INET6:
2961                 break;
2962 #endif
2963         default:
2964                 return (0);
2965         }
2966
2967         SCTPDBG(SCTP_DEBUG_ASCONF2, "find_initack_addr: starting search for ");
2968         SCTPDBG_ADDR(SCTP_DEBUG_ASCONF2, sa);
2969         /* convert to upper bound */
2970         length += offset;
2971
2972         if ((offset + sizeof(struct sctp_paramhdr)) > length) {
2973                 SCTPDBG(SCTP_DEBUG_ASCONF1,
2974                         "find_initack_addr: invalid offset?\n");
2975                 return (0);
2976         }
2977         /* go through the addresses in the init-ack */
2978         ph = (struct sctp_paramhdr *)sctp_m_getptr(m, offset,
2979             sizeof(struct sctp_paramhdr), (uint8_t *) & tmp_param);
2980         while (ph != NULL) {
2981                 ptype = ntohs(ph->param_type);
2982                 plen = ntohs(ph->param_length);
2983                 switch (ptype) {
2984 #ifdef INET6
2985                 case SCTP_IPV6_ADDRESS:
2986                         if (sa->sa_family == AF_INET6) {
2987                                 /* get the entire IPv6 address param */
2988                                 if (plen != sizeof(struct sctp_ipv6addr_param)) {
2989                                         break;
2990                                 }
2991                                 /* get the entire IPv6 address param */
2992                                 a6p = (struct sctp_ipv6addr_param *)
2993                                       sctp_m_getptr(m, offset,
2994                                                     sizeof(struct sctp_ipv6addr_param),
2995                                                     (uint8_t *)&addr6_store);
2996                                 if (a6p == NULL) {
2997                                         return (0);
2998                                 }
2999                                 sin6 = (struct sockaddr_in6 *)sa;
3000 #ifdef SCTP_EMBEDDED_V6_SCOPE
3001                                 if (IN6_IS_SCOPE_LINKLOCAL(&sin6->sin6_addr)) {
3002                                         /* create a copy and clear scope */
3003                                         memcpy(&sin6_tmp, sin6,
3004                                                sizeof(struct sockaddr_in6));
3005                                         sin6 = &sin6_tmp;
3006                                         in6_clearscope(&sin6->sin6_addr);
3007                                 }
3008 #endif /* SCTP_EMBEDDED_V6_SCOPE */
3009                                 if (memcmp(&sin6->sin6_addr, a6p->addr,
3010                                            sizeof(struct in6_addr)) == 0) {
3011                                         /* found it */
3012                                         return (1);
3013                                 }
3014                         }
3015                         break;
3016 #endif /* INET6 */
3017 #ifdef INET
3018                 case SCTP_IPV4_ADDRESS:
3019                         if (sa->sa_family == AF_INET) {
3020                                 if (plen != sizeof(struct sctp_ipv4addr_param)) {
3021                                         break;
3022                                 }
3023                                 /* get the entire IPv4 address param */
3024                                 a4p = (struct sctp_ipv4addr_param *)
3025                                       sctp_m_getptr(m, offset,
3026                                                     sizeof(struct sctp_ipv4addr_param),
3027                                                     (uint8_t *)&addr4_store);
3028                                 if (a4p == NULL) {
3029                                         return (0);
3030                                 }
3031                                 sin = (struct sockaddr_in *)sa;
3032                                 if (sin->sin_addr.s_addr == a4p->addr) {
3033                                         /* found it */
3034                                         return (1);
3035                                 }
3036                         }
3037                         break;
3038 #endif
3039                 default:
3040                         break;
3041                 }
3042                 /* get next parameter */
3043                 offset += SCTP_SIZE32(plen);
3044                 if (offset + sizeof(struct sctp_paramhdr) > length) {
3045                         return (0);
3046                 }
3047                 ph = (struct sctp_paramhdr *)
3048                     sctp_m_getptr(m, offset, sizeof(struct sctp_paramhdr),
3049                     (uint8_t *) & tmp_param);
3050         } /* while */
3051         /* not found! */
3052         return (0);
3053 }
3054
3055 /*
3056  * makes sure that the current endpoint local addr list is consistent with
3057  * the new association (eg. subset bound, asconf allowed) adds addresses as
3058  * necessary
3059  */
3060 static void
3061 sctp_check_address_list_ep(struct sctp_tcb *stcb, struct mbuf *m, int offset,
3062     int length, struct sockaddr *init_addr)
3063 {
3064         struct sctp_laddr *laddr;
3065
3066         /* go through the endpoint list */
3067         LIST_FOREACH(laddr, &stcb->sctp_ep->sctp_addr_list, sctp_nxt_addr) {
3068                 /* be paranoid and validate the laddr */
3069                 if (laddr->ifa == NULL) {
3070                         SCTPDBG(SCTP_DEBUG_ASCONF1,
3071                                 "check_addr_list_ep: laddr->ifa is NULL");
3072                         continue;
3073                 }
3074                 /* do i have it implicitly? */
3075                 if (sctp_cmpaddr(&laddr->ifa->address.sa, init_addr)) {
3076                         continue;
3077                 }
3078                 /* check to see if in the init-ack */
3079                 if (!sctp_addr_in_initack(m, offset, length, &laddr->ifa->address.sa)) {
3080                         /* try to add it */
3081                         sctp_addr_mgmt_assoc(stcb->sctp_ep, stcb, laddr->ifa,
3082                             SCTP_ADD_IP_ADDRESS, SCTP_ADDR_NOT_LOCKED);
3083                 }
3084         }
3085 }
3086
3087 /*
3088  * makes sure that the current kernel address list is consistent with the new
3089  * association (with all addrs bound) adds addresses as necessary
3090  */
3091 static void
3092 sctp_check_address_list_all(struct sctp_tcb *stcb, struct mbuf *m, int offset,
3093     int length, struct sockaddr *init_addr,
3094     uint16_t local_scope, uint16_t site_scope,
3095     uint16_t ipv4_scope, uint16_t loopback_scope)
3096 {
3097         struct sctp_vrf *vrf = NULL;
3098         struct sctp_ifn *sctp_ifn;
3099         struct sctp_ifa *sctp_ifa;
3100         uint32_t vrf_id;
3101 #ifdef INET
3102         struct sockaddr_in *sin;
3103 #endif
3104 #ifdef INET6
3105         struct sockaddr_in6 *sin6;
3106 #endif
3107
3108         if (stcb) {
3109                 vrf_id = stcb->asoc.vrf_id;
3110         } else {
3111                 return;
3112         }
3113         SCTP_IPI_ADDR_RLOCK();
3114         vrf = sctp_find_vrf(vrf_id);
3115         if (vrf == NULL) {
3116                 SCTP_IPI_ADDR_RUNLOCK();
3117                 return;
3118         }
3119         /* go through all our known interfaces */
3120         LIST_FOREACH(sctp_ifn, &vrf->ifnlist, next_ifn) {
3121                 if (loopback_scope == 0 && SCTP_IFN_IS_IFT_LOOP(sctp_ifn)) {
3122                         /* skip loopback interface */
3123                         continue;
3124                 }
3125                 /* go through each interface address */
3126                 LIST_FOREACH(sctp_ifa, &sctp_ifn->ifalist, next_ifa) {
3127                         /* do i have it implicitly? */
3128                         if (sctp_cmpaddr(&sctp_ifa->address.sa, init_addr)) {
3129                                 continue;
3130                         }
3131                         switch (sctp_ifa->address.sa.sa_family) {
3132 #ifdef INET
3133                         case AF_INET:
3134                                 sin = &sctp_ifa->address.sin;
3135 #if defined(__FreeBSD__) && !defined(__Userspace__)
3136                                 if (prison_check_ip4(stcb->sctp_ep->ip_inp.inp.inp_cred,
3137                                                      &sin->sin_addr) != 0) {
3138                                         continue;
3139                                 }
3140 #endif
3141                                 if ((ipv4_scope == 0) &&
3142                                     (IN4_ISPRIVATE_ADDRESS(&sin->sin_addr))) {
3143                                         /* private address not in scope */
3144                                         continue;
3145                                 }
3146                                 break;
3147 #endif
3148 #ifdef INET6
3149                         case AF_INET6:
3150                                 sin6 = &sctp_ifa->address.sin6;
3151 #if defined(__FreeBSD__) && !defined(__Userspace__)
3152                                 if (prison_check_ip6(stcb->sctp_ep->ip_inp.inp.inp_cred,
3153                                                      &sin6->sin6_addr) != 0) {
3154                                         continue;
3155                                 }
3156 #endif
3157                                 if ((local_scope == 0) &&
3158                                     (IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr))) {
3159                                         continue;
3160                                 }
3161                                 if ((site_scope == 0) &&
3162                                     (IN6_IS_ADDR_SITELOCAL(&sin6->sin6_addr))) {
3163                                         continue;
3164                                 }
3165                                 break;
3166 #endif
3167                         default:
3168                                 break;
3169                         }
3170                         /* check to see if in the init-ack */
3171                         if (!sctp_addr_in_initack(m, offset, length, &sctp_ifa->address.sa)) {
3172                                 /* try to add it */
3173                                 sctp_addr_mgmt_assoc(stcb->sctp_ep, stcb,
3174                                     sctp_ifa, SCTP_ADD_IP_ADDRESS,
3175                                     SCTP_ADDR_LOCKED);
3176                         }
3177                 } /* end foreach ifa */
3178         } /* end foreach ifn */
3179         SCTP_IPI_ADDR_RUNLOCK();
3180 }
3181
3182 /*
3183  * validates an init-ack chunk (from a cookie-echo) with current addresses
3184  * adds addresses from the init-ack into our local address list, if needed
3185  * queues asconf adds/deletes addresses as needed and makes appropriate list
3186  * changes for source address selection m, offset: points to the start of the
3187  * address list in an init-ack chunk length: total length of the address
3188  * params only init_addr: address where my INIT-ACK was sent from
3189  */
3190 void
3191 sctp_check_address_list(struct sctp_tcb *stcb, struct mbuf *m, int offset,
3192     int length, struct sockaddr *init_addr,
3193     uint16_t local_scope, uint16_t site_scope,
3194     uint16_t ipv4_scope, uint16_t loopback_scope)
3195 {
3196         /* process the local addresses in the initack */
3197         sctp_process_initack_addresses(stcb, m, offset, length);
3198
3199         if (stcb->sctp_ep->sctp_flags & SCTP_PCB_FLAGS_BOUNDALL) {
3200                 /* bound all case */
3201                 sctp_check_address_list_all(stcb, m, offset, length, init_addr,
3202                     local_scope, site_scope, ipv4_scope, loopback_scope);
3203         } else {
3204                 /* subset bound case */
3205                 if (sctp_is_feature_on(stcb->sctp_ep,
3206                     SCTP_PCB_FLAGS_DO_ASCONF)) {
3207                         /* asconf's allowed */
3208                         sctp_check_address_list_ep(stcb, m, offset, length,
3209                             init_addr);
3210                 }
3211                 /* else, no asconfs allowed, so what we sent is what we get */
3212         }
3213 }
3214
3215 /*
3216  * sctp_bindx() support
3217  */
3218 uint32_t
3219 sctp_addr_mgmt_ep_sa(struct sctp_inpcb *inp, struct sockaddr *sa,
3220                      uint32_t type, uint32_t vrf_id)
3221 {
3222         struct sctp_ifa *ifa;
3223         struct sctp_laddr *laddr, *nladdr;
3224
3225 #ifdef HAVE_SA_LEN
3226         if (sa->sa_len == 0) {
3227                 SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTP_ASCONF, EINVAL);
3228                 return (EINVAL);
3229         }
3230 #endif
3231         if (type == SCTP_ADD_IP_ADDRESS) {
3232                 /* For an add the address MUST be on the system */
3233                 ifa = sctp_find_ifa_by_addr(sa, vrf_id, SCTP_ADDR_NOT_LOCKED);
3234         } else if (type == SCTP_DEL_IP_ADDRESS) {
3235                 /* For a delete we need to find it in the inp */
3236                 ifa = sctp_find_ifa_in_ep(inp, sa, SCTP_ADDR_NOT_LOCKED);
3237         } else {
3238                 ifa = NULL;
3239         }
3240         if (ifa != NULL) {
3241                 if (type == SCTP_ADD_IP_ADDRESS) {
3242                         sctp_add_local_addr_ep(inp, ifa, type);
3243                 } else if (type == SCTP_DEL_IP_ADDRESS) {
3244                         if (inp->laddr_count < 2) {
3245                                 /* can't delete the last local address */
3246                                 SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTP_ASCONF, EINVAL);
3247                                 return (EINVAL);
3248                         }
3249                         LIST_FOREACH(laddr, &inp->sctp_addr_list,
3250                                      sctp_nxt_addr) {
3251                                 if (ifa == laddr->ifa) {
3252                                         /* Mark in the delete */
3253                                         laddr->action = type;
3254                                 }
3255                         }
3256                 }
3257                 if (LIST_EMPTY(&inp->sctp_asoc_list)) {
3258                         /*
3259                          * There is no need to start the iterator if
3260                          * the inp has no associations.
3261                          */
3262                         if (type == SCTP_DEL_IP_ADDRESS) {
3263                                 LIST_FOREACH_SAFE(laddr, &inp->sctp_addr_list, sctp_nxt_addr, nladdr) {
3264                                         if (laddr->ifa == ifa) {
3265                                                 sctp_del_local_addr_ep(inp, ifa);
3266                                         }
3267                                 }
3268                         }
3269                 } else {
3270                         struct sctp_asconf_iterator *asc;
3271                         struct sctp_laddr *wi;
3272                         int ret;
3273
3274                         SCTP_MALLOC(asc, struct sctp_asconf_iterator *,
3275                                     sizeof(struct sctp_asconf_iterator),
3276                                     SCTP_M_ASC_IT);
3277                         if (asc == NULL) {
3278                                 SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTP_ASCONF, ENOMEM);
3279                                 return (ENOMEM);
3280                         }
3281                         wi = SCTP_ZONE_GET(SCTP_BASE_INFO(ipi_zone_laddr), struct sctp_laddr);
3282                         if (wi == NULL) {
3283                                 SCTP_FREE(asc, SCTP_M_ASC_IT);
3284                                 SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTP_ASCONF, ENOMEM);
3285                                 return (ENOMEM);
3286                         }
3287                         LIST_INIT(&asc->list_of_work);
3288                         asc->cnt = 1;
3289                         SCTP_INCR_LADDR_COUNT();
3290                         wi->ifa = ifa;
3291                         wi->action = type;
3292                         atomic_add_int(&ifa->refcount, 1);
3293                         LIST_INSERT_HEAD(&asc->list_of_work, wi, sctp_nxt_addr);
3294                         ret = sctp_initiate_iterator(sctp_asconf_iterator_ep,
3295                                                      sctp_asconf_iterator_stcb,
3296                                                      sctp_asconf_iterator_ep_end,
3297                                                      SCTP_PCB_ANY_FLAGS,
3298                                                      SCTP_PCB_ANY_FEATURES,
3299                                                      SCTP_ASOC_ANY_STATE,
3300                                                      (void *)asc, 0,
3301                                                      sctp_asconf_iterator_end, inp, 0);
3302                         if (ret) {
3303                                 SCTP_PRINTF("Failed to initiate iterator for addr_mgmt_ep_sa\n");
3304                                 SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTP_ASCONF, EFAULT);
3305                                                     sctp_asconf_iterator_end(asc, 0);
3306                                 return (EFAULT);
3307                         }
3308                 }
3309                 return (0);
3310         } else {
3311                 /* invalid address! */
3312                 SCTP_LTRACE_ERR_RET(NULL, NULL, NULL, SCTP_FROM_SCTP_ASCONF, EADDRNOTAVAIL);
3313                 return (EADDRNOTAVAIL);
3314         }
3315 }
3316
3317 void
3318 sctp_asconf_send_nat_state_update(struct sctp_tcb *stcb, struct sctp_nets *net)
3319 {
3320         struct sctp_asconf_addr *aa_vtag, *aa_add, *aa_del;
3321         struct sctp_ifa *sctp_ifap;
3322         struct sctp_asconf_tag_param *vtag;
3323 #ifdef INET
3324         struct sockaddr_in *to;
3325 #endif
3326 #ifdef INET6
3327         struct sockaddr_in6 *to6;
3328 #endif
3329
3330         if (net == NULL) {
3331                 SCTPDBG(SCTP_DEBUG_ASCONF1, "sctp_asconf_send_nat_state_update: Missing net\n");
3332                 return;
3333         }
3334         if (stcb == NULL) {
3335                 SCTPDBG(SCTP_DEBUG_ASCONF1, "sctp_asconf_send_nat_state_update: Missing stcb\n");
3336                 return;
3337         }
3338         /* Need to have in the ASCONF:
3339          * - VTAG(my_vtag/peer_vtag)
3340          * - ADD(wildcard)
3341          * - DEL(wildcard)
3342          * - ADD(Any global addresses)
3343          */
3344         SCTP_MALLOC(aa_vtag, struct sctp_asconf_addr *, sizeof(struct sctp_asconf_addr), SCTP_M_ASC_ADDR);
3345         SCTP_MALLOC(aa_add, struct sctp_asconf_addr *, sizeof(struct sctp_asconf_addr), SCTP_M_ASC_ADDR);
3346         SCTP_MALLOC(aa_del, struct sctp_asconf_addr *, sizeof(struct sctp_asconf_addr), SCTP_M_ASC_ADDR);
3347
3348         if ((aa_vtag == NULL) || (aa_add == NULL) || (aa_del == NULL)) {
3349                 /* Didn't get memory */
3350                 SCTPDBG(SCTP_DEBUG_ASCONF1, "sctp_asconf_send_nat_state_update: failed to get memory!\n");
3351 out:
3352                 if (aa_vtag != NULL) {
3353                         SCTP_FREE(aa_vtag, SCTP_M_ASC_ADDR);
3354                 }
3355                 if (aa_add != NULL) {
3356                         SCTP_FREE(aa_add, SCTP_M_ASC_ADDR);
3357                 }
3358                 if (aa_del != NULL) {
3359                         SCTP_FREE(aa_del, SCTP_M_ASC_ADDR);
3360                 }
3361                 return;
3362         }
3363         memset(aa_vtag, 0, sizeof(struct sctp_asconf_addr));
3364         aa_vtag->special_del = 0;
3365         /* Fill in ASCONF address parameter fields. */
3366         /* Top level elements are "networked" during send. */
3367         aa_vtag->ifa = NULL;
3368         aa_vtag->sent = 0;              /* clear sent flag */
3369         vtag = (struct sctp_asconf_tag_param *)&aa_vtag->ap.aph;
3370         vtag->aph.ph.param_type = SCTP_NAT_VTAGS;
3371         vtag->aph.ph.param_length = sizeof(struct sctp_asconf_tag_param);
3372         vtag->local_vtag = htonl(stcb->asoc.my_vtag);
3373         vtag->remote_vtag = htonl(stcb->asoc.peer_vtag);
3374
3375         memset(aa_add, 0, sizeof(struct sctp_asconf_addr));
3376         memset(aa_del, 0, sizeof(struct sctp_asconf_addr));
3377         switch (net->ro._l_addr.sa.sa_family) {
3378 #ifdef INET
3379         case AF_INET:
3380                 aa_add->ap.aph.ph.param_type = SCTP_ADD_IP_ADDRESS;
3381                 aa_add->ap.aph.ph.param_length = sizeof(struct sctp_asconf_addrv4_param);
3382                 aa_add->ap.addrp.ph.param_type = SCTP_IPV4_ADDRESS;
3383                 aa_add->ap.addrp.ph.param_length = sizeof (struct sctp_ipv4addr_param);
3384                 /* No need to fill the address, we are using 0.0.0.0 */
3385                 aa_del->ap.aph.ph.param_type = SCTP_ADD_IP_ADDRESS;
3386                 aa_del->ap.aph.ph.param_length = sizeof(struct sctp_asconf_addrv4_param);
3387                 aa_del->ap.addrp.ph.param_type = SCTP_IPV4_ADDRESS;
3388                 aa_del->ap.addrp.ph.param_length = sizeof (struct sctp_ipv4addr_param);
3389                 /* No need to fill the address, we are using 0.0.0.0 */
3390                 break;
3391 #endif
3392 #ifdef INET6
3393         case AF_INET6:
3394                 aa_add->ap.aph.ph.param_type = SCTP_ADD_IP_ADDRESS;
3395                 aa_add->ap.aph.ph.param_length = sizeof(struct sctp_asconf_addr_param);
3396                 aa_add->ap.addrp.ph.param_type = SCTP_IPV6_ADDRESS;
3397                 aa_add->ap.addrp.ph.param_length = sizeof (struct sctp_ipv6addr_param);
3398                 /* No need to fill the address, we are using ::0 */
3399                 aa_del->ap.aph.ph.param_type = SCTP_DEL_IP_ADDRESS;
3400                 aa_del->ap.aph.ph.param_length = sizeof(struct sctp_asconf_addr_param);
3401                 aa_del->ap.addrp.ph.param_type = SCTP_IPV6_ADDRESS;
3402                 aa_del->ap.addrp.ph.param_length = sizeof (struct sctp_ipv6addr_param);
3403                 /* No need to fill the address, we are using ::0 */
3404                 break;
3405 #endif
3406         default:
3407                 SCTPDBG(SCTP_DEBUG_ASCONF1,
3408                         "sctp_asconf_send_nat_state_update: unknown address family %d\n",
3409                         net->ro._l_addr.sa.sa_family);
3410                 goto out;
3411         }
3412         TAILQ_INSERT_TAIL(&stcb->asoc.asconf_queue, aa_vtag, next);
3413         TAILQ_INSERT_TAIL(&stcb->asoc.asconf_queue, aa_add, next);
3414         TAILQ_INSERT_TAIL(&stcb->asoc.asconf_queue, aa_del, next);
3415
3416         /* Now we must hunt the addresses and add all global addresses */
3417         if (stcb->sctp_ep->sctp_flags & SCTP_PCB_FLAGS_BOUNDALL) {
3418                 struct sctp_vrf *vrf = NULL;
3419                 struct sctp_ifn *sctp_ifnp;
3420                 uint32_t vrf_id;
3421
3422                 vrf_id = stcb->sctp_ep->def_vrf_id;
3423                 vrf = sctp_find_vrf(vrf_id);
3424                 if (vrf == NULL) {
3425                         goto skip_rest;
3426                 }
3427
3428                 SCTP_IPI_ADDR_RLOCK();
3429                 LIST_FOREACH(sctp_ifnp, &vrf->ifnlist, next_ifn) {
3430                         LIST_FOREACH(sctp_ifap, &sctp_ifnp->ifalist, next_ifa) {
3431                                 switch (sctp_ifap->address.sa.sa_family) {
3432 #ifdef INET
3433                                 case AF_INET:
3434                                         to = &sctp_ifap->address.sin;
3435 #if defined(__FreeBSD__) && !defined(__Userspace__)
3436                                         if (prison_check_ip4(stcb->sctp_ep->ip_inp.inp.inp_cred,
3437                                                              &to->sin_addr) != 0) {
3438                                                 continue;
3439                                         }
3440 #endif
3441                                         if (IN4_ISPRIVATE_ADDRESS(&to->sin_addr)) {
3442                                                 continue;
3443                                         }
3444                                         if (IN4_ISLOOPBACK_ADDRESS(&to->sin_addr)) {
3445                                                 continue;
3446                                         }
3447                                         break;
3448 #endif
3449 #ifdef INET6
3450                                 case AF_INET6:
3451                                         to6 = &sctp_ifap->address.sin6;
3452 #if defined(__FreeBSD__) && !defined(__Userspace__)
3453                                         if (prison_check_ip6(stcb->sctp_ep->ip_inp.inp.inp_cred,
3454                                                              &to6->sin6_addr) != 0) {
3455                                                 continue;
3456                                         }
3457 #endif
3458                                         if (IN6_IS_ADDR_LOOPBACK(&to6->sin6_addr)) {
3459                                                 continue;
3460                                         }
3461                                         if (IN6_IS_ADDR_LINKLOCAL(&to6->sin6_addr)) {
3462                                                 continue;
3463                                         }
3464                                         break;
3465 #endif
3466                                 default:
3467                                         continue;
3468                                 }
3469                                 sctp_asconf_queue_mgmt(stcb, sctp_ifap, SCTP_ADD_IP_ADDRESS);
3470                         }
3471                 }
3472                 SCTP_IPI_ADDR_RUNLOCK();
3473         } else {
3474                 struct sctp_laddr *laddr;
3475
3476                 LIST_FOREACH(laddr, &stcb->sctp_ep->sctp_addr_list, sctp_nxt_addr) {
3477                         if (laddr->ifa == NULL) {
3478                                 continue;
3479                         }
3480                         if (laddr->ifa->localifa_flags & SCTP_BEING_DELETED)
3481                                 /* Address being deleted by the system, dont
3482                                  * list.
3483                                  */
3484                                 continue;
3485                         if (laddr->action == SCTP_DEL_IP_ADDRESS) {
3486                                 /* Address being deleted on this ep
3487                                  * don't list.
3488                                  */
3489                                 continue;
3490                         }
3491                         sctp_ifap = laddr->ifa;
3492                         switch (sctp_ifap->address.sa.sa_family) {
3493 #ifdef INET
3494                         case AF_INET:
3495                                 to = &sctp_ifap->address.sin;
3496                                 if (IN4_ISPRIVATE_ADDRESS(&to->sin_addr)) {
3497                                         continue;
3498                                 }
3499                                 if (IN4_ISLOOPBACK_ADDRESS(&to->sin_addr)) {
3500                                         continue;
3501                                 }
3502                                 break;
3503 #endif
3504 #ifdef INET6
3505                         case AF_INET6:
3506                                 to6 = &sctp_ifap->address.sin6;
3507                                 if (IN6_IS_ADDR_LOOPBACK(&to6->sin6_addr)) {
3508                                         continue;
3509                                 }
3510                                 if (IN6_IS_ADDR_LINKLOCAL(&to6->sin6_addr)) {
3511                                         continue;
3512                                 }
3513                                 break;
3514 #endif
3515                         default:
3516                                 continue;
3517                         }
3518                         sctp_asconf_queue_mgmt(stcb, sctp_ifap, SCTP_ADD_IP_ADDRESS);
3519                 }
3520         }
3521  skip_rest:
3522         /* Now we must send the asconf into the queue */
3523         sctp_send_asconf(stcb, net, SCTP_ADDR_NOT_LOCKED);
3524 }