sctputil.h revision 267723
116Salm/*- 216Salm * Copyright (c) 2001-2007, by Cisco Systems, Inc. All rights reserved. 31057Salm * Copyright (c) 2008-2012, by Randall Stewart. All rights reserved. 416Salm * Copyright (c) 2008-2012, by Michael Tuexen. All rights reserved. 516Salm * 61057Salm * Redistribution and use in source and binary forms, with or without 71057Salm * modification, are permitted provided that the following conditions are met: 816Salm * 916Salm * a) Redistributions of source code must retain the above copyright notice, 1016Salm * this list of conditions and the following disclaimer. 1116Salm * 1216Salm * b) Redistributions in binary form must reproduce the above copyright 1316Salm * notice, this list of conditions and the following disclaimer in 1416Salm * the documentation and/or other materials provided with the distribution. 1516Salm * 1616Salm * c) Neither the name of Cisco Systems, Inc. nor the names of its 1716Salm * contributors may be used to endorse or promote products derived 1816Salm * from this software without specific prior written permission. 1916Salm * 2016Salm * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 2116Salm * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, 2216Salm * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 2316Salm * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE 2416Salm * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 2516Salm * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 2616Salm * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 2716Salm * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 2816Salm * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 2916Salm * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF 3016Salm * THE POSSIBILITY OF SUCH DAMAGE. 3116Salm */ 3216Salm 3316Salm#include <sys/cdefs.h> 3416Salm__FBSDID("$FreeBSD: stable/10/sys/netinet/sctputil.h 267723 2014-06-22 16:28:52Z tuexen $"); 3516Salm 361057Salm#ifndef _NETINET_SCTP_UTIL_H_ 371057Salm#define _NETINET_SCTP_UTIL_H_ 3816Salm 3916Salm#if defined(_KERNEL) || defined(__Userspace__) 4016Salm 4127963Ssteve#define SCTP_READ_LOCK_HELD 1 4220420Ssteve#define SCTP_READ_LOCK_NOT_HELD 0 4327963Ssteve 4427963Ssteve#ifdef SCTP_ASOCLOG_OF_TSNS 4550471Spetervoid sctp_print_out_track_log(struct sctp_tcb *stcb); 4627963Ssteve 4716Salm#endif 4816Salm 491057Salm#ifdef SCTP_MBUF_LOGGING 5016Salmstruct mbuf *sctp_m_free(struct mbuf *m); 5116Salmvoid sctp_m_freem(struct mbuf *m); 5227963Ssteve 5327963Ssteve#else 5427963Ssteve#define sctp_m_free m_free 5516Salm#define sctp_m_freem m_freem 5616Salm#endif 5716Salm 581057Salm#if defined(SCTP_LOCAL_TRACE_BUF) || defined(__APPLE__) 5916Salmvoid 6016Salm sctp_log_trace(uint32_t fr, const char *str SCTP_UNUSED, uint32_t a, uint32_t b, uint32_t c, uint32_t d, uint32_t e, uint32_t f); 6116Salm 6216Salm#endif 6316Salm 6416Salm#define sctp_get_associd(stcb) ((sctp_assoc_t)stcb->asoc.assoc_id) 6516Salm 6616Salm 671057Salm/* 6816Salm * Function prototypes 6916Salm */ 7016Salmuint32_t 7116Salmsctp_get_ifa_hash_val(struct sockaddr *addr); 7216Salm 7316Salmstruct sctp_ifa * 7416Salm sctp_find_ifa_in_ep(struct sctp_inpcb *inp, struct sockaddr *addr, int hold_lock); 751057Salm 7616Salmstruct sctp_ifa * 7716Salm sctp_find_ifa_by_addr(struct sockaddr *addr, uint32_t vrf_id, int holds_lock); 781057Salm 7916Salmuint32_t sctp_select_initial_TSN(struct sctp_pcb *); 8016Salm 8116Salmuint32_t sctp_select_a_tag(struct sctp_inpcb *, uint16_t lport, uint16_t rport, int); 8216Salm 8316Salmint sctp_init_asoc(struct sctp_inpcb *, struct sctp_tcb *, uint32_t, uint32_t); 8416Salm 8516Salmvoid sctp_fill_random_store(struct sctp_pcb *); 8616Salm 8716Salmvoid 8816Salmsctp_notify_stream_reset_add(struct sctp_tcb *stcb, uint16_t numberin, 8916Salm uint16_t numberout, int flag); 9016Salmvoid 9116Salm sctp_notify_stream_reset_tsn(struct sctp_tcb *stcb, uint32_t sending_tsn, uint32_t recv_tsn, int flag); 9216Salm 9316Salmvoid 9416Salmsctp_timer_start(int, struct sctp_inpcb *, struct sctp_tcb *, 9516Salm struct sctp_nets *); 9616Salm 9716Salmvoid 9816Salmsctp_timer_stop(int, struct sctp_inpcb *, struct sctp_tcb *, 9916Salm struct sctp_nets *, uint32_t); 10016Salm 10116Salmint 10216Salm sctp_dynamic_set_primary(struct sockaddr *sa, uint32_t vrf_id); 10316Salm 10416Salmvoid 10516Salm sctp_mtu_size_reset(struct sctp_inpcb *, struct sctp_association *, uint32_t); 10616Salm 10716Salmvoid 10816Salmsctp_add_to_readq(struct sctp_inpcb *inp, 10916Salm struct sctp_tcb *stcb, 1101057Salm struct sctp_queued_to_read *control, 1111057Salm struct sockbuf *sb, 1121057Salm int end, 11316Salm int inpread_locked, 11416Salm int so_locked 1151057Salm#if !defined(__APPLE__) && !defined(SCTP_SO_LOCK_TESTING) 11616Salm SCTP_UNUSED 1171057Salm#endif 11816Salm); 11916Salm 12016Salmint 12116Salmsctp_append_to_readq(struct sctp_inpcb *inp, 12216Salm struct sctp_tcb *stcb, 12316Salm struct sctp_queued_to_read *control, 1247165Sjoerg struct mbuf *m, 12516Salm int end, 12616Salm int new_cumack, 12746684Skris struct sockbuf *sb); 12816Salm 12916Salm 13016Salmvoid sctp_iterator_worker(void); 13116Salm 13216Salmuint32_t sctp_get_prev_mtu(uint32_t); 13316Salmuint32_t sctp_get_next_mtu(uint32_t); 13416Salm 1351057Salmvoid 1361057Salm sctp_timeout_handler(void *); 1371057Salm 13816Salmuint32_t 13916Salmsctp_calculate_rto(struct sctp_tcb *, struct sctp_association *, 14016Salm struct sctp_nets *, struct timeval *, int, int); 14116Salm 14216Salmuint32_t sctp_calculate_len(struct mbuf *); 1431057Salm 14416Salmcaddr_t sctp_m_getptr(struct mbuf *, int, int, uint8_t *); 14516Salm 1467165Sjoergstruct sctp_paramhdr * 1477165Sjoergsctp_get_next_param(struct mbuf *, int, 14816Salm struct sctp_paramhdr *, int); 14916Salm 15016Salmint sctp_add_pad_tombuf(struct mbuf *, int); 15116Salm 1521057Salmint sctp_pad_lastmbuf(struct mbuf *, int, struct mbuf *); 1531057Salm 1541057Salmvoid 15516Salmsctp_ulp_notify(uint32_t, struct sctp_tcb *, uint32_t, void *, int 15616Salm#if !defined(__APPLE__) && !defined(SCTP_SO_LOCK_TESTING) 15716Salm SCTP_UNUSED 15816Salm#endif 15916Salm); 1601057Salm 16116Salmvoid 16216Salmsctp_pull_off_control_to_new_inp(struct sctp_inpcb *old_inp, 16316Salm struct sctp_inpcb *new_inp, 1647165Sjoerg struct sctp_tcb *stcb, int waitflags); 1657165Sjoerg 16616Salm 16716Salmvoid sctp_stop_timers_for_shutdown(struct sctp_tcb *); 16816Salm 16916Salmvoid 1701057Salmsctp_report_all_outbound(struct sctp_tcb *, uint16_t, int, int 1711057Salm#if !defined(__APPLE__) && !defined(SCTP_SO_LOCK_TESTING) 1721057Salm SCTP_UNUSED 17316Salm#endif 17416Salm); 17516Salm 17616Salmint sctp_expand_mapping_array(struct sctp_association *, uint32_t); 1771057Salm 17816Salmvoid 17916Salmsctp_abort_notification(struct sctp_tcb *, uint8_t, uint16_t, 1801057Salm struct sctp_abort_chunk *, int 1817165Sjoerg#if !defined(__APPLE__) && !defined(SCTP_SO_LOCK_TESTING) 1827165Sjoerg SCTP_UNUSED 18316Salm#endif 18416Salm); 18516Salm 18616Salm/* We abort responding to an IP packet for some reason */ 18716Salmvoid 18816Salmsctp_abort_association(struct sctp_inpcb *, struct sctp_tcb *, struct mbuf *, 18916Salm int, struct sockaddr *, struct sockaddr *, 1901057Salm struct sctphdr *, struct mbuf *, 1911057Salm uint8_t, uint32_t, 19216Salm uint32_t, uint16_t); 19316Salm 19416Salm 19516Salm/* We choose to abort via user input */ 19616Salmvoid 19716Salmsctp_abort_an_association(struct sctp_inpcb *, struct sctp_tcb *, 19816Salm struct mbuf *, int 19916Salm#if !defined(__APPLE__) && !defined(SCTP_SO_LOCK_TESTING) 20016Salm SCTP_UNUSED 20116Salm#endif 20216Salm); 20316Salm 2041057Salmvoid 20516Salmsctp_handle_ootb(struct mbuf *, int, int, 2061057Salm struct sockaddr *, struct sockaddr *, 20716Salm struct sctphdr *, struct sctp_inpcb *, 20816Salm struct mbuf *, 20916Salm uint8_t, uint32_t, 21016Salm uint32_t, uint16_t); 21116Salm 21216Salmint 21316Salmsctp_connectx_helper_add(struct sctp_tcb *stcb, struct sockaddr *addr, 21416Salm int totaddr, int *error); 21516Salm 21616Salmstruct sctp_tcb * 21716Salmsctp_connectx_helper_find(struct sctp_inpcb *inp, struct sockaddr *addr, 2181057Salm int *totaddr, int *num_v4, int *num_v6, int *error, int limit, int *bad_addr); 21916Salm 22016Salmint sctp_is_there_an_abort_here(struct mbuf *, int, uint32_t *); 22116Salm 22216Salm#ifdef INET6 22316Salmuint32_t sctp_is_same_scope(struct sockaddr_in6 *, struct sockaddr_in6 *); 22416Salm 22516Salmstruct sockaddr_in6 * 22616Salm sctp_recover_scope(struct sockaddr_in6 *, struct sockaddr_in6 *); 2271057Salm 2281057Salm#define sctp_recover_scope_mac(addr, store) do { \ 22916Salm if ((addr->sin6_family == AF_INET6) && \ 23016Salm (IN6_IS_SCOPE_LINKLOCAL(&addr->sin6_addr))) { \ 23116Salm *store = *addr; \ 23216Salm if (addr->sin6_scope_id == 0) { \ 23316Salm if (!sa6_recoverscope(store)) { \ 23416Salm addr = store; \ 23516Salm } \ 23616Salm } else { \ 23716Salm in6_clearscope(&addr->sin6_addr); \ 23816Salm addr = store; \ 23916Salm } \ 24016Salm } \ 24116Salm} while (0) 24216Salm#endif 24316Salm 24416Salmint sctp_cmpaddr(struct sockaddr *, struct sockaddr *); 24516Salm 24616Salmvoid sctp_print_address(struct sockaddr *); 24716Salm 24816Salmint 24916Salmsctp_release_pr_sctp_chunk(struct sctp_tcb *, struct sctp_tmit_chunk *, 25016Salm uint8_t, int 25116Salm#if !defined(__APPLE__) && !defined(SCTP_SO_LOCK_TESTING) 25216Salm SCTP_UNUSED 25316Salm#endif 25416Salm); 25516Salm 25616Salmstruct mbuf *sctp_generate_cause(uint16_t, char *); 25716Salm 25816Salmvoid 25916Salmsctp_bindx_add_address(struct socket *so, struct sctp_inpcb *inp, 2601057Salm struct sockaddr *sa, sctp_assoc_t assoc_id, 26116Salm uint32_t vrf_id, int *error, void *p); 26216Salmvoid 26316Salmsctp_bindx_delete_address(struct sctp_inpcb *inp, 26416Salm struct sockaddr *sa, sctp_assoc_t assoc_id, 26516Salm uint32_t vrf_id, int *error); 26616Salm 26716Salmint sctp_local_addr_count(struct sctp_tcb *stcb); 26816Salm 26916Salm#ifdef SCTP_MBCNT_LOGGING 27016Salmvoid 27116Salmsctp_free_bufspace(struct sctp_tcb *, struct sctp_association *, 27216Salm struct sctp_tmit_chunk *, int); 27316Salm 27416Salm#else 27516Salm#define sctp_free_bufspace(stcb, asoc, tp1, chk_cnt) \ 2761057Salmdo { \ 2771057Salm if (tp1->data != NULL) { \ 27816Salm atomic_subtract_int(&((asoc)->chunks_on_out_queue), chk_cnt); \ 27916Salm if ((asoc)->total_output_queue_size >= tp1->book_size) { \ 28016Salm atomic_subtract_int(&((asoc)->total_output_queue_size), tp1->book_size); \ 28116Salm } else { \ 28216Salm (asoc)->total_output_queue_size = 0; \ 28316Salm } \ 28416Salm if (stcb->sctp_socket && ((stcb->sctp_ep->sctp_flags & SCTP_PCB_FLAGS_TCPTYPE) || \ 28516Salm (stcb->sctp_ep->sctp_flags & SCTP_PCB_FLAGS_IN_TCPPOOL))) { \ 28616Salm if (stcb->sctp_socket->so_snd.sb_cc >= tp1->book_size) { \ 28716Salm atomic_subtract_int(&((stcb)->sctp_socket->so_snd.sb_cc), tp1->book_size); \ 28816Salm } else { \ 28916Salm stcb->sctp_socket->so_snd.sb_cc = 0; \ 29016Salm } \ 29116Salm } \ 29216Salm } \ 29316Salm} while (0) 29416Salm 29516Salm#endif 2961057Salm 2971057Salm#define sctp_free_spbufspace(stcb, asoc, sp) \ 29816Salmdo { \ 29916Salm if (sp->data != NULL) { \ 30016Salm if ((asoc)->total_output_queue_size >= sp->length) { \ 30116Salm atomic_subtract_int(&(asoc)->total_output_queue_size, sp->length); \ 30216Salm } else { \ 30316Salm (asoc)->total_output_queue_size = 0; \ 30416Salm } \ 30516Salm if (stcb->sctp_socket && ((stcb->sctp_ep->sctp_flags & SCTP_PCB_FLAGS_TCPTYPE) || \ 30616Salm (stcb->sctp_ep->sctp_flags & SCTP_PCB_FLAGS_IN_TCPPOOL))) { \ 30716Salm if (stcb->sctp_socket->so_snd.sb_cc >= sp->length) { \ 30816Salm atomic_subtract_int(&stcb->sctp_socket->so_snd.sb_cc,sp->length); \ 30916Salm } else { \ 31016Salm stcb->sctp_socket->so_snd.sb_cc = 0; \ 31116Salm } \ 31216Salm } \ 31316Salm } \ 31416Salm} while (0) 31516Salm 31616Salm#define sctp_snd_sb_alloc(stcb, sz) \ 31716Salmdo { \ 31816Salm atomic_add_int(&stcb->asoc.total_output_queue_size,sz); \ 31916Salm if ((stcb->sctp_socket != NULL) && \ 32016Salm ((stcb->sctp_ep->sctp_flags & SCTP_PCB_FLAGS_TCPTYPE) || \ 32116Salm (stcb->sctp_ep->sctp_flags & SCTP_PCB_FLAGS_IN_TCPPOOL))) { \ 32216Salm atomic_add_int(&stcb->sctp_socket->so_snd.sb_cc,sz); \ 32316Salm } \ 32416Salm} while (0) 32516Salm 32616Salm/* functions to start/stop udp tunneling */ 32716Salmvoid sctp_over_udp_stop(void); 3281057Salmint sctp_over_udp_start(void); 32916Salm 33016Salmint 33116Salmsctp_soreceive(struct socket *so, struct sockaddr **psa, 33216Salm struct uio *uio, 33316Salm struct mbuf **mp0, 33416Salm struct mbuf **controlp, 33516Salm int *flagsp); 33616Salm 33716Salmvoid 33816Salm sctp_misc_ints(uint8_t from, uint32_t a, uint32_t b, uint32_t c, uint32_t d); 33916Salm 34016Salmvoid 34116Salmsctp_wakeup_log(struct sctp_tcb *stcb, 34216Salm uint32_t wake_cnt, int from); 34316Salm 34416Salmvoid sctp_log_strm_del_alt(struct sctp_tcb *stcb, uint32_t, uint16_t, uint16_t, int); 34516Salm 34616Salmvoid sctp_log_nagle_event(struct sctp_tcb *stcb, int action); 34716Salm 34816Salm 34916Salmvoid 35016Salm sctp_log_mb(struct mbuf *m, int from); 35116Salm 35216Salmvoid 35316Salmsctp_sblog(struct sockbuf *sb, 35416Salm struct sctp_tcb *stcb, int from, int incr); 35516Salm 35616Salmvoid 3571057Salmsctp_log_strm_del(struct sctp_queued_to_read *control, 3581057Salm struct sctp_queued_to_read *poschk, 35916Salm int from); 36016Salmvoid sctp_log_cwnd(struct sctp_tcb *stcb, struct sctp_nets *, int, uint8_t); 36116Salmvoid rto_logging(struct sctp_nets *net, int from); 36216Salm 36316Salmvoid sctp_log_closing(struct sctp_inpcb *inp, struct sctp_tcb *stcb, int16_t loc); 36416Salm 36516Salmvoid sctp_log_lock(struct sctp_inpcb *inp, struct sctp_tcb *stcb, uint8_t from); 36616Salmvoid sctp_log_maxburst(struct sctp_tcb *stcb, struct sctp_nets *, int, int, uint8_t); 36716Salmvoid sctp_log_block(uint8_t, struct sctp_association *, int); 36816Salmvoid sctp_log_rwnd(uint8_t, uint32_t, uint32_t, uint32_t); 36916Salmvoid sctp_log_mbcnt(uint8_t, uint32_t, uint32_t, uint32_t, uint32_t); 37016Salmvoid sctp_log_rwnd_set(uint8_t, uint32_t, uint32_t, uint32_t, uint32_t); 37116Salmint sctp_fill_stat_log(void *, size_t *); 37216Salmvoid sctp_log_fr(uint32_t, uint32_t, uint32_t, int); 37316Salmvoid sctp_log_sack(uint32_t, uint32_t, uint32_t, uint16_t, uint16_t, int); 37416Salmvoid sctp_log_map(uint32_t, uint32_t, uint32_t, int); 37516Salmvoid sctp_print_mapping_array(struct sctp_association *asoc); 37616Salmvoid sctp_clr_stat_log(void); 37716Salm 37816Salm 37916Salm#ifdef SCTP_AUDITING_ENABLED 38016Salmvoid 38116Salmsctp_auditing(int, struct sctp_inpcb *, struct sctp_tcb *, 38216Salm struct sctp_nets *); 38316Salmvoid sctp_audit_log(uint8_t, uint8_t); 38416Salm 38516Salm#endif 38616Salm#endif /* _KERNEL */ 38716Salm#endif 38816Salm