SCTP Application Guide

Download as doc, pdf, or txt
Download as doc, pdf, or txt
You are on page 1of 52

DOCUMENTTYPE 1 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

SCTP Application Guide

Document type: User’s Guide


Creator: Zhao Kai
Reviewer: Huang Hui
Approver:
Date approved: 2002-12-6
Function:

Version History

Version Date Handled by Version history


1.0 2002-12-16 Zhao kai Skeleton
1.1 2002-12-16 Zhao kai 3, 4
1.2 2002-12-17 Zhao kai 2.5
1.21. 2002-12-20 Nie Sen 2.2-2.4
Shijinyang/ 2.6-2.8
Moltchanov
Vladimir
1.3 2002-12-30 WangLan Change 2.3,2.4,2.7 as appendix
2.3, 2.4 is new
give explainings and examples in 2.5, 2.6, 2.7
complete part 2.8
give function table of socket options in 2.9
complete part 2.10
give an compared integrated examples in 5
1.4 18.8.2004 J Leppänen Added Chapter 6.
DOCUMENTTYPE 2 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

Table of Contents

1. INTRODUCTION........................................................................................................................... 4
1.1 Purpose.................................................................................................................................. 4
1.2 Scope..................................................................................................................................... 4
1.3 Glossary................................................................................................................................. 4
1.3.1 Abbreviations................................................................................................................... 4
2. Socket API.................................................................................................................................... 4
2.1 Objectives............................................................................................................................... 4
2.1.1 Maintain consistency with existing sockets APIs:.............................................................4
2.1.2 Support a one to many style interface.............................................................................4
2.1.3 Support a one to one style interface................................................................................4
2.2 Data Types............................................................................................................................. 5
2.3 How to program...................................................................................................................... 5
2.4 Basic socket functions............................................................................................................ 6
2.4.1 introduction...................................................................................................................... 6
2.4.2 socket address................................................................................................................ 6
2.4.3 byte-order........................................................................................................................ 6
2.4.4 socket operations............................................................................................................ 7
2.4.5 Non-blocking mode........................................................................................................10
2.5 Header data structures and event data structures................................................................10
2.5.1 The msghdr and cmsghdr Structures.............................................................................10
2.5.2 SCTP msg_control Structures.......................................................................................11
2.5.3 SCTP Events and Notifications in /include/net/sctp/sctp_user.h....................................12
2.6 Super socket operations for Both Styles...............................................................................14
2.6.1 send(), recv(), sendto(), recvfrom()................................................................................14
2.6.2 sendmsg() and recvmsg()..............................................................................................15
2.6.3 read() and wirte()........................................................................................................... 16
2.6.4 getsockname()...............................................................................................................16
2.6.5 setsockopt(), getsockopt().............................................................................................17
2.7 The function of event and how to use...................................................................................17
2.8 Ancillary Data Considerations and Semantics......................................................................19
2.8.1 Multiple Items and Ordering...........................................................................................19
2.8.2 Accessing and Manipulating Ancillary Data...................................................................19
2.8.3 Control Message Buffer Sizing......................................................................................20
2.8.4 How to use data structures when programming.............................................................20
2.9 Socket Options..................................................................................................................... 20
2.9.1 table of socket options’ functions...................................................................................21
2.10 New Interfaces..................................................................................................................22
2.10.1 sctp_bindx()............................................................................................................... 22
2.10.2 sctp_peeloff().............................................................................................................23
2.10.3 sctp_getpaddrs()........................................................................................................23
2.10.4 sctp_freepaddrs().......................................................................................................24
2.10.5 sctp_getladdrs()......................................................................................................... 24
2.10.6 sctp_freeladdrs()........................................................................................................25
2.10.7 sctp_sendmsg().........................................................................................................25
2.10.8 sctp_recvmsg().......................................................................................................... 25
3. Installation Guide........................................................................................................................ 26
3.1 account in isource.nokia.com................................................................................................26
3.2 Create the source tree (based on Linux Kernel 2.4.18).........................................................26
3.3 File list.................................................................................................................................. 27
3.4 Compile................................................................................................................................ 27
3.4.1 Compile lksctp in kernel.................................................................................................27
DOCUMENTTYPE 3 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

3.4.2 Compile lksctp as a kernel.............................................................................................28


4. Refference.................................................................................................................................. 28
5. Examples.................................................................................................................................... 28
5.1 Server................................................................................................................................... 28
5.2 Client.................................................................................................................................... 30
6. SCTP in FlexiServer.................................................................................................................... 35
6.1 Configuration, Installation and Storage.................................................................................35
6.2 The SCTP Header................................................................................................................35
6.3 The SCTP Library................................................................................................................. 35
6.4 LBSCTP Sockets..................................................................................................................36
APPENDIX A.................................................................................................................................... 38
A.1 UDP-style Interface...................................................................................................................38
A.1.1 Basic Operation................................................................................................................. 38
A.1.2 Implicit Association Setup..................................................................................................39
A.1.3 Non-blocking mode............................................................................................................ 39
A.2 TCP-style Interface................................................................................................................... 39
A.2.1 Basic Operation................................................................................................................. 39
APPENDIX B...................................................................................................................................... 43
B.1 Read / Write Options................................................................................................................43
B.1.1 Retransmission Timeout Parameters (SCTP_RTOINFO).................................................43
B.1.2 Association Parameters (SCTP_ASSOCINFO)................................................................43
B.1.3 Initialization Parameters (SCTP_INITMSG)......................................................................44
B.1.4 SO_LINGER...................................................................................................................... 45
B.1.5 SO_NODELAY.................................................................................................................. 45
B.1.6 SO_RCVBUF..................................................................................................................... 46
B.1.7 SO_SNDBUF..................................................................................................................... 46
B.1.8 Automatic close of associations (SCTP_AUTOCLOSE)....................................................46
B.1.9 Set Primary Address (SCTP_SET_PRIMARY_ADDR)......................................................46
B.1.10 Set Peer Primary Address (SCTP_SET_PEER_PRIMARY_ADDR)................................46
B.1.11 Set Adaption Layer Indicator (SCTP_SET_ADAPTION_LAYER)...................................47
B.1.12 Set default message time outs (SCTP_SET_STREAM_TIMEOUTS)..............................47
B.1.13 Enable/Disable message fragmentation(SCTP_DISABLE_FRAGMENTS)......................47
B.1.14 Peer Address Parameters (SCTP_SET_PEER_ADDR_PARAMS).................................48
B.1.15 Set default send parameters (SET_DEFAULT_SEND_PARAM).....................................48
B.1.16 Set notification and ancillary events (SCTP_SET_EVENTS)...........................................50
B.2 Read only options..................................................................................................................... 50
B.2.1 Association Status (SCTP_STATUS).................................................................................50
B.2.2 Peer Address Information (SCTP_GET_PEER_ADDR_INFO)..........................................51
DOCUMENTTYPE 4 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

1. INTRODUCTION

1.1 Purpose

This document is the application guide for Nokia Linux kernel SCTP implementation. The
instructions herein are meant for the developers of SCTP user applications in. This
document was originally written by members of the noklksctp team at NRC Beijing.

1.2 Scope

This document has 3 parts: including SCTP socket API description and LKSCTP
installation and configuration guide. The third part is Chapter 6 SCTP in FlexiServer, which
contains FlexiServer-specific SCTP information.

1.3 Glossary

1.3.1 Abbreviations

SCTP Stream Control Transmission Protocol

LKSCTP Linux Kernel SCTP

2. SOCKET API

2.1 Objectives

Defines a method to map the existing sockets API for use with SCTP, providing both a
base for access to new features and compatibility so that most existing TCP applications
can be migrated to SCTP with few (if any) changes.

There are three basic design objectives:

2.1.1 Maintain consistency with existing sockets APIs:

We define a sockets mapping for SCTP that is consistent with other sockets API protocol
mappings (for instance, UDP, TCP, IPv4, and IPv6).

2.1.2 Support a one to many style interface

This set of semantics is similar to that defined for connectionless protocols, such as UDP.
It is more efficient than a TCP-like connection-oriented interface in terms of exploring the
new features of SCTP.

Note that SCTP is connection-oriented in nature, and it does not support broadcast or
multicast communications, as UDP does.

2.1.3 Support a one to one style interface

This interface supports the same basic semantics as sockets for connection-oriented
protocols, such as TCP.
DOCUMENTTYPE 5 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

The purpose of defining this interface is to allow existing applications built on connection-
oriented protocols be ported to use SCTP with very little effort, and developers familiar with
those semantics can easily adapt to SCTP.

Extensions will be added to this mapping to provide mechanisms to exploit new features of
SCTP.

Goals 2 and 3 are not compatible, so in this document we define two modes of mapping,
namely the one to many style(UDP style) mapping and the one to one style(TCP-style)
mapping. These two modes share some common data structures and operations, but will
require the use of two different application programming models.

A mechanism is defined to convert a UDP-style SCTP association into a TCP-style socket.

Some of the SCTP mechanisms cannot be adequately mapped to existing socket interface.
In some cases, it is more desirable to have new interface instead of using existing socket
calls. This document also describes those new interface.

2.2 Data Types

Whenever possible, data types from Draft 6.6 (March 1997) of POSIX 1003.1g are used:
uintN_t means an unsigned integer of exactly N bits (e.g., uint16_t). We also assume the
argument data types from 1003.1g when possible (e.g., the final argument to setsockopt()
is a size_t value). Whenever buffer sizes are specified, the POSIX 1003.1 size_t data type
is used.

2.3 How to program

When a programmer begins his/her programming, he/she has one step which must be
done before programming. That is he/she should copy some files provided by us to his/her
own directory or to the place according to necessary. Now, we put those files in
noklksctp/test/libc/include/netinet/. E.g., we put data structures and event structures in
sctp.h. Users clould named his/her directory if only the directory include these files.

Why files are included:

The data structures of events and socket options which are already included in linux kernel.
While linux operating system will only auto read files in <sys/>, therefore, for the users’
program, it could not find those SCTP data structures although they are already belong to
linux kernel.

Library functions:

Nokia linux kernel support some lirary functions according to draft api, such as
sctp_bindx(); sctp_sendmsg(); sctp_recvmsg() and so on. Their aim is to provide
convenience to the user. Each function is elaborately described in section 2.10. Now, all
these library fuctions are included in /noklksctp/test/sctp_lib.c. Since our c program are all
in the same directory, it is no use to point at the directrory in makefile. However, if users
want to put sctp_lib.c in his/her directory, he/her must point at the directory.

User could use makefile to include the directory which include those files.
DOCUMENTTYPE 6 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

2.4 Basic socket functions

2.4.1 introduction

Linux provide socket mechanism to access network protocol of lower layer. The following
firstly introduce address format and byte-orders which are used by socket functions. Then
discuss basic socket functions. More elaborately functions will be described in attachment.

2.4.2 socket address

Socket of linux operating system is a universal network programming interface. It support


several protocols. Each protocol used different socket address format. In order to keep
parameters’ consistency when calling socket functions, linux has defined a common socket
address in <linux/socket.h>.

struct sockaddr
{
unsigned short sa_family; /* type of address, AF_**** */
char sa_data[14]; /*address */
};

e.g. we use AF_INET and AF_INET6 for TCP/IP protocol cluster.

SCTP/IP uses the address of TCP/IP protocol cluster. It is:

struct sockaddr_in {
short int sin_family; /* type of address. */
unsigned shot int sin_port; /* port */
struct in_addr; sin_addr; /* internet address */
unsigned char pad; /* pad, in order to compatible with
BSD. */
}

note:

(1) <linux/socket.h> and <linux/in.h> is head files which specially owned by linux. In order
to keep code could be transplanted, we should not include these two files, while should
include <sys/socket.h> and <netinet/in.h> which have no relationship with platform.

(2) port and address in struct sockaddr_in are all stored in host byte-order. They should be
converted to network byte-order when programming.

2.4.3 byte-order

there are four libaray functions to provide change or byte-order.


#include <netinet/in.h>
unsigned short in htons(unsigned short int hostshort);
unsigned long in htonl(unsigned long int hostlong);
unsigned short in ntohs(unsigned short int hostshort);
unsigned long in ntohl(unsigned long int hostlong);

note: (1) h---host; n---network; s---short; l---long;


DOCUMENTTYPE 7 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

(2) when programming, it had better use these functions while not depending on
special machines.

2.4.4 socket operations

The following table compares the socket operations of UDP style and TCP style.

Under the table, we state the functions and difference of UDP and TCP styles simply.

Elaberation of the fuction and parameters list in the appendix, whose index number is
written down in the table.

We alse have some examples in the attachment for each socket operation.

socket()

Style Description Elaberation

UDP socket(PF_INET,SEQ_PACKET,IPPROTO_SCTP)

TCP socket(PF_INET,STREAM,IPPROTO_SCTP)

Function: creating a socket descriptor, that is to say, to create a data struct of sock, which
use to communicate with peer.

Difference: only the second parameter in the bracket has difference. That parameter is
used to mark the style of the socket.

bind()

Style Description Elaberation

UDP bind(int sd, struct sockaddr *addr, socklen_t addrlen)

TCP bind(int sd, struct sockaddr *addr, socklen_t addrlen)

Function: binding a socket descriptor with a port. I.e., if a socket descriptor is a telephone,
then a socket descriptor with port is a telephone with line.

Note:
Use wild-card is need to use parameters INADDR_ANY. It has some difference with TCP
protocol. In SCTP, using this parameter means that host will choose multiple address for
communication, whereas in TCP protocol, this parameter has two meanings. In TCP
protocol, when a server use INADDR_ANY for binding address, it means the server will
accept any connection whatever the clients’ address are. When a client use this address, it
means local host.
DOCUMENTTYPE 8 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

Difference: although they seems same in style, while UDP can build association without call
bind(). It means that UDP socket support auto bind whereas TCP can’t.

listen()

Style Description Elaberation

UDP listen(int socket, int backlog)

TCP listen(int socket, int backlog)

Function: the operation is only used in server. Firstly, to create a corresponding socket to
the client to prepare communicate. Secondly, it will monitor whether it could accept an
other client’s connection.

Difference: although they seems same in style, while the parameter----backlog is not
supported by UDP. It means the second parameter in listen() is “false”.

connect()

Style Description Elaberation

UDP connect(int sd, const struct sockaddr *nam, socklen_t len) 2.4.1.6

TCP connect(int sd, const struct sockaddr *nam, socklen_t len) 2.5.1.5

Function: it belongs to clients action which to apply a connection.

Difference: although there is no defference in form for the two style, while in practice UDP
style seldom use connect(). UDP socket always use sendmsg() or sendto() to establish
association.

accept()

Style Description Elaberation

UDP --- ----

TCP accept(int sd, const struct sockaddr *addr, socklen_t addrlen) 2.5.1.4

Function: it is to move the socket from the listen socket so as to build one-to-one style
communication mechanism.
DOCUMENTTYPE 9 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

Difference: It is clear that UDP do not support accept(), while it has similar operation which
is named peel off().

close()

Style Description Elaberation

UDP close(int sd) 2.4.1.5

TCP close(int sd) 2.5.1.6

Function: close() will decrease the counter of socket descriptor. If it is decresed to zero,
descriptor will be free, otherwise it means there is some other course using the descriptor,
then close() will return normally. Until there is no any course using the descriptor, the
descriptor will be freed.

No difference between TCP and UDP.

shutdown()

Style Description Elaberation

UDP ----- ----

TCP shutdown(int socket, int how) 2.4.1.7

Fuction: gracefully shutdown when necessary. It could be called whenever the program
want. While close() always be called after finishing of communication.

Difference: only used by TCP style.


TCP style in SCTP has some different points with TCP, which are described in appendix A.

getsockname() & getpeername()

Style Description Elaberation

UDP getsockname(int socket, struct sockaddr *address, socklen_t *len);

TCP getpeername(int socket, struct sockaddr *address, socklen_t *len);

getsockname(int socket, struct sockaddr *address, socklen_t *len);


DOCUMENTTYPE 10 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

Function: (1)after the client calls connect(), getsockname() may get the address and port of
local host.(2) After connected, getpeername() used by server, after calling this, server may
get the address and port of remote host.

Difference :getpeername() is TCP only.

2.4.5 Non-blocking mode

Some SCTP users might want to avoid blocking when they call socket interface function.
Whenever the user which want to avoid blocking must call select() before calling

Sendmsg()/sendto() and recvmsg()/recvfrom(), and check the socket status is writable or


readable.

If the socket status is not writable sendmsg() and sendto() return EAGAIN and do not
transmit the message. Similarly, if the status is not readable, recvmsg() and recvfrom()
return EAGAIN.

Once all bind() calls are complete on a one-to-many style socket, the application must set
the non-blocking option by a fcntl() (such as O_NONBLOCK). After which the sendmsg()
function returns immediately, and the success or failure of the data message (and possible
SCTP_INITMSG parameters) will be signaled by the SCTP_ASSOC_CHANGE event with
SCTP_COMM_UP or CANT_START_ASSOC. If user data could not be sent (due to a
CANT_START_ASSOC), the sender will also receive a SCTP_SEND_FAILED event.
Those event(s) can be received by the user calling of recvmsg(). A server (having called
listen()) is also notified of an association up event by the reception of a
SCTP_ASSOC_CHANGE with SCTP_COMM_UP via the calling of recvmsg() and possibly
the reception of the first data message.

In order to shutdown the association gracefully, the user must call sendmsg() with no data
and with the MSG_EOF flag set. The function returns immediately, and completion of the
graceful shutdown is indicated by an SCTP_ASSOC_CHANGE notification of type
SHUTDOWN_COMPLET.

2.5 Header data structures and event data structures

In this part, we introduce message header structure, control message header structure and
some event structures. And in the following two parts, we introduce the functions and
usage of these two kinds of structure. Firstly, we use socket interface sendmsg()(2.5.1) to
show how msghdr and cmsghdr is used, then we inscribe a table to list each event(2.6.1)
and explain how these events work.

2.5.1 The msghdr and cmsghdr Structures

2.5.1.1 struct msghdr in /include/linux/socket.h

struct msghdr {
void *msg_name; /* Socket name*/
int msg_namelen; /* Length of name*/
struct iovec * msg_iov; /* Data blocks
*/
DOCUMENTTYPE 11 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

__kernel_size_t msg_iovlen; /* Number of blocks*/


void *msg_control; /* Per protocol magic
(eg BSD file descriptor passing) */
__kernel_size_t msg_controllen; /* Length of cmsg list */
unsigned msg_flags;
};

struct iovec {
void iov_base; /* beginning address of buffer. */
size_t iov_len; /* the size of the buffer. */
}

2.5.1.2 struct cmsghdr in /include/linux/socket.h

struct cmsghdr {
__kernel_size_t cmsg_len; /* data byte count, including hdr */
int cmsg_level; /* originating protocol */
int cmsg_type; /* protocol-specific type */
};

The use of the above two structures is same with TCP/UDP protocol.

2.5.1.3 struct SCTP_cmsghdr in /include/net/sctp/sctp_user.h

struct SCTP_cmsghdr {
size_t cmsg_len; /* #bytes, including this header */
int cmsg_level; /* originating protocol */
sctp_cmsg_t cmsg_type; /* protocol-specific type */
sctp_cmsg_data_t cmsg_data;
};

This structure provides classification of control message header. cmsg_level is


IPPROTO_SCTP in SCTP protocol; cmsg_type has two options, one is SCTP_INIT,
sctp_cmsg_data_t corresponding to sctp_sctp_initmsg strucure; the other is
SCTP_SNDRCV, sctp_cmsg_data_t corresponding to sctp_sndrcvinfo structure.
Programmers use it according to situation.

2.5.2 SCTP msg_control Structures

Defined in struct msghdr (2.5.1.1)

2.5.2.1 SCTP Initiation Structure (SCTP_INIT) in /include/net/sctp/sctp_user.h

/ * cmsg_level cmsg_type cmsg_data[]


* ------------ ------------ ----------------------
* IPPROTO_SCTP SCTP_INIT struct sctp_initmsg
*/
struct sctp_initmsg {
uint16_t sinit_num_ostreams;
uint16_t sinit_max_instreams;
uint16_t sinit_max_attempts;
DOCUMENTTYPE 12 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

uint16_t sinit_max_init_timeo;
};

This cmsghdr structure provides information for initializing new SCTP associations with
sendmsg(). The SCTP_INITMSG socket option used this same data structure. This
structure is not used for recvmsg().

2.5.2.2 Header Information Structure (SCTP_SNDRCV) in /include/net/sctp/sctp_user.h

/* cmsg_level cmsg_type cmsg_data[]


* ------------ ------------ ----------------------
* IPPROTO_SCTP SCTP_SNDRCV struct sctp_sndrcvinfo
*/
struct sctp_sndrcvinfo {
uint16_t sinfo_stream; uint16_t sinfo_ssn;
uint16_t sinfo_flags;
uint32_t sinfo_ppid;
uint32_t sinfo_context;
uint32_t sinfo_timetolive;
uint32_t sinfo_tsn;
uint32_t sinfo_cumtsn;
sctp_assoc_t sinfo_assoc_id;
};

This cmsghdr structure specifies SCTP options for sendmsg() and describes SCTP header
information about a received message through recvmsg().

2.5.3 SCTP Events and Notifications in /include/net/sctp/sctp_user.h

enum sctp_sn_type {
SCTP_SN_TYPE_BASE = (1<<15),
SCTP_ASSOC_CHANGE,
SCTP_PEER_ADDR_CHANGE,
SCTP_SEND_FAILED,
SCTP_REMOTE_ERROR,
SCTP_SHUTDOWN_EVENT,
SCTP_PARTIAL_DELIVERY_EVENT,
SCTP_ADAPTION_INDICATION,
};

This structure is notification to the user, let ULP know which event has happened.

2.5.3.1 SCTP_ASSOC_CHANGE

struct sctp_assoc_change {
uint16_t sac_type;
uint16_t sac_flags;
uint32_t sac_length;
uint16_t sac_state;
uint16_t sac_error;
uint16_t sac_outbound_streams;
DOCUMENTTYPE 13 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

uint16_t sac_inbound_streams;
sctp_assoc_t sac_assoc_id;
uint8_t sac_info[0];
};

Communication notifications inform ULP that SCTP association has either begun or ended.

2.5.3.2 SCTP_PEER_ADDR_CHANGE

struct sctp_paddr_change{
uint16_t spc_type;
uint16_t spc_flags;
uint32_t spc_length;
struct sockaddr_storage spc_aaddr;
int spc_state;
int spc_error;
sctp_assoc_t spc_assoc_id;
};

When a destination address on a multi-homed peer encounters a change an interface


details enent is sent by this structure.

2.5.3.3 SCTP_REMOTE_ERROR

struct sctp_remote_error {
uint16_t sre_type;
uint16_t sre_flags;
uint32_t sre_length;
uint16_t sre_error;
sctp_assoc_t sre_assoc_id;
uint8_t sre_data[0];
};

When peer encounter an operational error, it will send the error by this structure.

2.5.3.4 SCTP_SEND_FAILED

struct sctp_send_failed {
uint16_t ssf_type;
uint16_t ssf_flags;
uint32_t ssf_length;
uint32_t ssf_error;
struct sctp_sndrcvinfo ssf_info;
sctp_assoc_t ssf_assoc_id;
uint8_t ssf_data[0];
};

If a host can not deliver a message to peer, it will notify ULP with SCTP_SEND_FAILED
event by this structure. Of course attached data in this structure can not be delivered to
peer.
DOCUMENTTYPE 14 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

2.5.3.5 SCTP_SHUTDOWN_EVENT

struct sctp_shutdown_event {
uint16_t sse_type;
uint16_t sse_flags;
uint32_t sse_length;
sctp_assoc_t sse_assoc_id;
};

2.5.3.6 SCTP_ADAPTION_INDICATION

struct sctp_adaption_event {
uint16_t sai_type;
uint16_t sai_flags;
uint32_t sai_length;
uint32_t sai_adaptation_ind;
sctp_assoc_t sse_assoc_id;
};

When a peer sends a Adaption Layer Indication parameter , SCTP delivers this notification
to inform the application that of the peers requested adaption layer.

2.5.3.7 SCTP_PARTIAL_DELIVERY_EVENT

struct sctp_rcv_pdapi_event {
uint16_t pdapi_type;
uint16_t pdapi_flags;
uint32_t pdapi_length;
uint32_t pdapi_indication;
sctp_assoc_t pdapi_assoc_id;
};

When a receiver is engaged in a partial delivery of a message this notification will be used
to indicate various events.

2.6 Super socket operations for Both Styles

2.6.1 send(), recv(), sendto(), recvfrom()

Applications can use send() and sendto() to transmit data to the peer of an SCTP endpoint.
recv() and recvfrom() can be used to receive data from the peer.

The syntax is:

ssize_t send(int sd, connst void *msg, size_t len, int flags);
ssize_t sendto(int sd, const void *msg, size_t len, int flags,
const struct sockaddr *to, int tolen);
ssize_t recv(int sd, void *buf, size_t len, int flags);
ssize_t recvfrom(int sd, void *buf, size_t len, int flags,
struct sockaddr *from, int *fromlen);

sd - the socket descriptor of an SCTP endpoint.


DOCUMENTTYPE 15 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

msg - the message to be sent.


len - the size of the message or the size of buffer.
to - one of the peer addresses of the association to be
used to send the message.
tolen - the size of the address.
buf - the buffer to store a received message.
from - the buffer to store the peer address used to send the
received message.
fromlen - the size of the from address
flags - (described below).

These calls give access to only basic SCTP protocol features. If either peer in the
association uses multiple streams, or sends unordered data these calls will usually be
inadequate, and may deliver the data in unpredictable ways.

SCTP has the concept of multiple streams in one association. The above calls do not allow
the caller to specify on which stream a message should be sent. The system uses stream
0 as the default stream for send() and sendto(). recv() and recvfrom() return data from any
stream, but the caller can not distinguish the different streams. This may result in data
seeming to arrive out of order. Similarly, if a data chunk is sent unordered, recv() and
recvfrom() provide no indication.

SCTP is message based. The msg buffer above in send() and sendto() is considered to be
a single message. This means that if the caller wants to send a message which is
composed by several buffers, the caller needs to combine them before calling send() or
sendto(). Alternately, the caller can use sendmsg() to do that without combining them.
recv() and recvfrom() cannot distinguish message boundaries.

In receiving, if the buffer supplied is not large enough to hold a complete message, the
receive call acts like a stream socket and returns as much data as will fit in the buffer.

Note, the send and recv calls, when used in the UDP-style model, may only be used with
branched off socket descriptors (see Section 2.8.2).

Note, if an application calls a send function with no user data and no ancillary data the
SCTP implementation should reject the request with an appropriate error message. An
implementation is NOT allowed to send a Data chunk with no user data.

2.6.2 sendmsg() and recvmsg()

ssize_t sendmsg(int socket, const struct msghdr *message, int flags);

ssize_t recvmsg(int socket, struct msghdr *message, int flags);

socket - the socket descriptor of the endpoint

message - pointer to the msghdr structure which contains a single user


message and possibly some ancillary data.

flags - No new flags are defined for SCTP at this level.

These two functions encapsulate most parameters in struct msghdr, flags has the same
meaning of flags in send(). We have introduced the structure of msghdr in 2.5.1.1. . When
DOCUMENTTYPE 16 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

programming, msg_name and msg_namelen record the address of peer. In fact,


msg_name is a pointer which point at a variable of struct sockaddr, msg_namelen is the
length of the address. Recvmsg() store the address of receiver in these two fields. The
following is an example:

struct msghdr hdr;


struct sockaddr_in addr;
……
addr.sin_family = AF_INET;
……
hdr.msg_name = (struct sockaddr *)&addr;
hdr.msg_namelen = sizeof(addr);
……
sendmsg(sockfd, &hdr, 0);

2.6.3 read() and wirte()

Applications can use read() and write() to send and receive data to and from peer. They
have the same semantics as send() and recv() except that the flags parameter cannot be
used.

Note, these calls, when used in the one to many style model, may only be used with
branched off socket descriptors .

2.6.4 getsockname()

Applications use getsockname() to retrieve the locally-bound socket address of the


specified socket. This is especially useful if the caller let SCTP chose a local port. This call
is for where the endpoint is not multi-homed. It does not work well with multi-homed
sockets. See Section 8.5 for a multi-homed version of the call.

The syntax is:

int getsockname(int socket, struct sockaddr *address,


socklen_t *len);

sd - the socket descriptor to be queried.

address - On return, one locally bound address (chosen by the SCTP stack) is stored in
this buffer. If the socket is an IPv4 socket, the address will be IPv4. If the
socket is an IPv6 socket, the address will be either an IPv6 or IPv4 address.

len - The caller should set the length of address here. On return, this is set to the
length of the returned address.

If the actual length of the address is greater than the length of the supplied sockaddr
structure, the stored address will be truncated.

If the socket has not been bound to a local name, the value stored in the object pointed to
by address is unspecified.
DOCUMENTTYPE 17 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

2.6.5 setsockopt(), getsockopt()

Applications use setsockopt() and getsockopt() to set or retrieve socket options. Socket
options are used to change the default behavior of sockets calls. They are described in
Section 2.7.

The syntax is:

ret = getsockopt(int sd, int level, int optname, void *optval,


size_t *optlen);
ret = setsockopt(int sd, int level, int optname, const void *optval,
size_t optlen);

sd - the socket descript.


level - set to SOL_SCTP for all SCTP options.
optname - the option name.
optval - the buffer to store the value of the option.
optlen - the size of the buffer (or the length of the option returned).

2.7 The function of event and how to use

Applications can receive per-message ancillary information and notifications of certain


SCTP events with recvmsg().

The following optional information is available to the application:

1. SCTP_SNDRCV (sctp_data_io_event): Per-message information (i.e.stream number,


TSN, SSN, etc. described in Section 2.5.2.2).

2. SCTP_ASSOC_CHANGE (sctp_association_event): (described in Section 2.5.3.1)

3. SCTP_PEER_ADDR_CHANGE (sctp_address_event): (described in Section 2.5.3.2)

4. SCTP_SEND_FAILED (sctp_send_failure_event): (described in Section 2.5.3.4)

5. SCTP_REMOTE_ERROR (sctp_peer_error_event): (described in Section 2.5.3.3)

6. SCTP_SHUTDOWN_EVENT (sctp_shtudown_event): (described in Section2.5.3.5)

7. SCTP_PARTIAL_DELIVERY_EVENT (sctp_partial_delivery_event):

(described in Section 2.5.3.7)

8. SCTP_ADAPTION_INDICATION (sctp_adaption_layer_event):

(described in section 2.3.5.6).

To receive any ancillary data or notifications, first the application registers it's interest by
calling the SCTP_EVENTS setsockopt() with the following structure.

struct sctp_event_subscribe{
u_int8_t sctp_data_io_event;
u_int8_t sctp_association_event;
DOCUMENTTYPE 18 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

u_int8_t sctp_address_event;
u_int8_t sctp_send_failure_event;
u_int8_t sctp_peer_error_event;
u_int8_t sctp_shutdown_event;
u_int8_t sctp_partial_delivery_event;
u_int8_t sctp_adaption_layer_event;
};

sctp_data_io_event - Setting this flag to 1 will cause the reception of SCTP_SNDRCV


information on a per message basis. The application will need to use the recvmsg()
interface so that it can receive the event information contained in the msg_control field.
Setting the flag to 0 will disable reception of the message control information.

sctp_association_event - Setting this flag to 1 will enable the reception of association event
notifications. Setting the flag to 0 will disable association event notifications.

sctp_address_event - Setting this flag to 1 will enable the reception of address event
notifications. Setting the flag to 0 will disable address event notifications.

sctp_send_failure_event - Setting this flag to 1 will enable the reception of send failure
event notifications. Setting the flag to 0 will disable send failure event notifications.

sctp_peer_error_event - Setting this flag to 1 will enable the reception of peer error event
notifications. Setting the flag to 0 will disable peer error event notifications.

sctp_shutdown_event - Setting this flag to 1 will enable the reception of shutdown event
notifications. Setting the flag to 0 will disable shutdown event notifications.

sctp_partial_delivery_event - Setting this flag to 1 will enable the reception of partial


delivery notifications. Setting the flag to 0 will disable partial delivery event notifications.

sctp_adaption_layer_event - Setting this flag to 1 will enable the reception of adaption layer
notifications. Setting the flag to 0 will disable adaption layer event notifications.

The following is an example.

struct sctp_event_subscribe event;

memset(&event,0,sizeof(event));

event.sctp_data_io_event = 1;

setsockopt (fd, IPPROTO_SCTP, SCTP_EVENT, &event, sizeof(event));

……

error = recvmsg(fd, &inmessage, MSG_WAITALL);

/* this will receive a notification. */

test_check_message(&inmessage, CMSG_SPACE(sizeof(struce sctp_sndrcvinfo)),

SCTP_SNDRCV);

……
DOCUMENTTYPE 19 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

note: function test_check_message() will be included in another file which could be


written like the following.
int
test_check_message(struct msghdr *msg, int controllen,
sctp_cmsg_t event)
{

if (msg->msg_controllen != controllen) {
printf("Got control structure of length %d, not %d\n",
msg->msg_controllen, controllen);
DUMP_CORE;
}
if (controllen > 0 && event != CMSG_FIRSTHDR(msg)->cmsg_type) {
printf("Wrong kind of event: %d, not %d\n",
CMSG_FIRSTHDR(msg)->cmsg_type, event);
DUMP_CORE;
}

return 1;

} /* test_check_message() */

All those test functions we have examples in /noklksctp/test/funutil.c. Users clould use it as
a guide.

2.8 Ancillary Data Considerations and Semantics

Programming with ancillary socket data contains some subtleties and pitfalls, which are
discussed below.

2.8.1 Multiple Items and Ordering

Multiple ancillary data items may be included in any call to sendmsg() or recvmsg(); these
may include multiple SCTP or non-SCTP items, or both. The ordering of ancillary data
items (either by SCTP or another protocol) is not significant and is implementation-
dependent, so applications must not depend on any ordering.

SCTP_SNDRCV items must always correspond to the data in the msghdr's msg_iov
member. There can be only a single SCTP_SNDRCV info for each sendmsg() or
recvmsg() call.

2.8.2 Accessing and Manipulating Ancillary Data

Applications can infer the presence of data or ancillary data by examining the msg_iovlen
and msg_controllen msghdr members, respectively. Implementations may have different
padding quirements for ancillary data, so portable applications should make use of the
macros CMSG_FIRSTHDR, CMSG_NXTHDR, CMSG_DATA, CMSG_SPACE, and
DOCUMENTTYPE 20 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

CMSG_LEN. See RFC2292 and your SCTP implementation's documentation for more
information. Following is an example, from RFC2292, demonstrating the use of these
macros to access ancillary data:

struct msghdr msg; /* fill in msg */


struct cmsghdr *cmsgptr; /* call recvmsg() */
for (cmsgptr = CMSG_FIRSTHDR(&msg); cmsgptr != NULL;
cmsgptr = CMSG_NXTHDR(&msg, cmsgptr)) {
if (cmsgptr->cmsg_level == ... && cmsgptr->cmsg_type == ... ) {
u_char *ptr;
ptr = CMSG_DATA(cmsgptr); /* process data pointed to by ptr */
}
}

2.8.3 Control Message Buffer Sizing

The information conveyed via SCTP_SNDRCV events will often be fundamental to the
correct and sane operation of the sockets application. This is particularly true of the one-to-
many semantics, but also of the one-ton-one semantics. For example, if an application
needs to send and receive data on different SCTP streams, SCTP_SNDRCV events are
indispensable.

Given that some ancillary data is critical, and that multiple ancillary data items may appear
in any order, applications should be carefully written to always provide a large enough
buffer to contain all possible ancillary data that can be presented by recvmsg(). If the buffer
is too small, and crucial data is truncated, it may pose a fatal error condition.

2.8.4 How to use data structures when programming

Although lksctp has data structures in linux kernel, all the data structures should be
included in a .h file, the files name could be named by the programmer, while the .h file
must be clearly indicated its directory in the makefile.

2.9 Socket Options

The implementation supplies various SCTP level socket options that are common to both
models. SCTP associations can be multi-homed. Therefore, certain option parameters
include a sockaddr_storage structure to select which peer address the option should be
applied to.

For the one to many style sockets, an sctp_assoc_t structure (association ID) is used to
identify the the association instance that the operation affects. So it must be set when
using this model.

For the one to one style sockets and branched off one to one style sockets (see Section
2.8) this association ID parameter is ignored. In the cases noted below where the
parameter is ignored, an application can pass to the system a corresponding option
structure similar to those described below but without the association ID parameter, which
should be the last field of the option structure. This can make the option setting/getting
operation more efficient. If an application does this, it should also specify an appropriate
optlen value (i.e. sizeof (option parameter) - sizeof (struct sctp_assoc_t)).
DOCUMENTTYPE 21 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

Note that socket or IP level options is set or retrieved per socket. This means that for one to
one style sockets, those options will be applied to all associations belonging to the socket.
And for TCP-style model, those options will be applied to all peer addresses of the
association controlled by the socket. Applications should be very careful in setting those
options.

2.9.1 table of socket options’ functions

Corresponding
Option event Option function
structure
Modifiy and examine
SCTP_RTOINFO sctp_rtoinfo retransmission timeout
parameters
Modify and examine
SCTP_ASSOCINFO sctp_associnfo association and endpoint
parameters
Modify and examine
SCTP_INITMSG sctp_initmsg
initialization parameters
Perform SCTP ABORT
SO_LINGER(TCP only) Linger
primitive
(no corresponding
Turn on/off any nagle-like
SCTP_NODELAY structure only a
algorithm
parameter)
(no corresponding
SO_RCVBUF structure only a Sets receive buffer size
parameter)
(no corresponding
SO_SNDBUF structure only a Sets send buffer size
parameter)
(no corresponding Perform wether the
SCTP_AUTOCLOSE(UDP only) structure only a association could auto
parameter) close.
Requests that the peer mark
SCTP_SET_PEER_PRIMARY Sctp_setpeerprim the enclosed address as the
association primary.
Requests that the local
SCTP stack use the enclosed
SCTP_PRIMARY_ADDR sctp_setprim
peer address as
the association primary.
Requests that the local
endpoint set the specified
Adaption Layer
SCTP_ADAPTION_LAYER sctp_setadaption
Indication parameter for
all future INIT and INIT-
ACK exchanges.
(no corresponding
Turn on/off fragments of a
SCTP_DISABLE_FRAGMENTS structure only a
message
parameter)
SCTP_PEER_ADDR_PARAM sctp_paddrparams enable or disable
heartbeats for any peer
address of an association,
modify an address's
heartbeat interval, force a
heartbeat to be sent
immediately, and adjust the
address's maximum
number of
DOCUMENTTYPE 22 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

retransmissions
specify a default set of
SCTP_DEFAULT_SEND_PARAM sctp_sndrcvinfo
parameters
specify various
Each event
notifications and
SCTP_EVENTS correspond a data
ancillary data the user
structure
wishes to receive.
(no corresponding Turn on/off whether v4
SCTP_I_WANT_MAPPED_V4_ADDR structure only a address can be mapped v6
parameter) address
(no corresponding specifies the maximum size
SCTP_MAXSEG structure only a to put in any outgoing
parameter) SCTP DATA chunk.
etrieve current status
SCTP_STATUS(read only) sctp_status
information
retrieve information about
SCTP_GET_PEER_ADDR_INFO sctp_paddrinfo a specific peer address
of an association

2.10 New Interfaces

2.10.1 sctp_bindx()

The syntax of sctp_bindx() is,

int sctp_bindx(int sd, struct sockaddr_storage *addrs, int addrcnt,


int flags);

If sd is an IPv4 socket, the addresses passed must be IPv4 addresses. If the sd is an IPv6
socket, the addresses passed can either be IPv4 or IPv6 addresses.

A single address may be specified as INADDR_ANY or IN6ADDR_ANY, see Section


2.3.1.2 for this usage.

addrs is a pointer to an array of one or more socket addresses. Each address is contained
in a struct sockaddr_storage, so each address is a fixed length. The caller specifies the
number of addresses in the array with addrcnt.

On success, sctp_bindx() returns 0. On failure, sctp_bindx() returns -1, and sets errno to
the appropriate error code.

For SCTP, the port given in each socket address must be the same, or sctp_bindx() will fail,
setting errno to EINVAL.

The flags parameter is formed from the bitwise OR of zero or more of the following currently
defined flags:

SCTP_BINDX_ADD_ADDR

SCTP_BINDX_REM_ADDR
DOCUMENTTYPE 23 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

SCTP_BINDX_ADD_ADDR directs SCTP to add the given addresses to the association,


and SCTP_BINDX_REM_ADDR directs SCTP to remove the given addresses from the
association. The two flags are mutually exclusive; if both are given, sctp_bindx() will fail
with EINVAL. A caller may not remove all addresses from an association; sctp_bindx() will
reject such an attempt with EINVAL.

An application can use sctp_bindx(SCTP_BINDX_ADD_ADDR) to associate additional


addresses with an endpoint after calling bind(). Or use
sctp_bindx(SCTP_BINDX_REM_ADDR) to remove some addresses a listening socket is
associated with so that no new association accepted will be associated with those
addresses. If the endpoint supports dynamic address a SCTP_BINDX_REM_ADDR or
SCTP_BINDX_ADD_ADDR may cause a endpoint to send the appropriate message to the
peer to change the peers address lists.

This interface is implemented as a system call.

2.10.2 sctp_peeloff()

After an association is established on a UDP-style socket, the application may wish to


branch off the association into a separate socket/file descriptor.

This is particularly desirable when, for instance, the application wishes to have a number of
sporadic message senders/receivers remain under the original UDP-style socket but branch
off those associations carrying high volume data traffic into their own separate socket
descriptors.

The application uses sctp_peeloff() call to branch off an association into a separate socket
(Note the semantics are somewhat changed from the traditional TCP-style accept() call).

The syntax is:

new_sd = sctp_peeloff(int sd, sctp_assoc_t *assoc_id);

the new socket descriptor representing the branched-off association.

the original UDP-style socket descriptor returned from the socket() system call (see Section
3.1.1).

the specified identifier of the association that is to be branched off to a separate file
descriptor (Note, in a traditional TCP-style accept() call, this would be an out parameter, but
for the UDP-style call, this is an in parameter).

This interface is implemented as a system call.

2.10.3 sctp_getpaddrs()

sctp_getpaddrs() returns all peer addresses in an association. The syntax is,

int sctp_getpaddrs(int sd, sctp_assoc_t id,


struct sockaddr_storage **addrs);
DOCUMENTTYPE 24 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

On return, addrs will point to a dynamically allocated array of struct sockaddr_storages, one
for each peer address. The caller should use sctp_freepaddrs() to free the memory. addrs
must not be NULL.

If sd is an IPv4 socket, the addresses returned will be all IPv4 addresses. If sd is an IPv6
socket, the addresses returned can be a mix of IPv4 or IPv6 addresses.

For UDP-style sockets, id specifies the association to query. For TCP-style sockets, id is
ignored.

On success, sctp_getpaddrs() returns the number of peer addresses in the association. If


there is no association on this socket, sctp_getpaddrs() returns 0, and the value of *addrs is
undefined. If an error occurs, sctp_getpaddrs() returns -1, and the value of *addrs is
undefined.

This interface is implemented as a library function.

2.10.4 sctp_freepaddrs()

sctp_freepaddrs() frees all resources allocated by


sctp_getpaddrs(). Its syntax is,

void sctp_freepaddrs(struct sockaddr_storage *addrs);

addrs is the array of peer addresses returned by sctp_getpaddrs().

This interface is implemented as a library function.

2.10.5 sctp_getladdrs()

sctp_getladdrs() returns all locally bound address on a socket. The syntax is,

int sctp_getladdrs(int sock, sctp_assoc_t id,


struct sockaddr_storage **ss);

On return, addrs will point to a dynamically allocated array of struct sockaddr_storages, one
for each local address. The caller should use sctp_freeladdrs() to free the memory. addrs
must not be NULL.

If sd is an IPv4 socket, the addresses returned will be all IPv4 addresses. If sd is an IPv6
socket, the addresses returned can be a mix of IPv4 or IPv6 addresses.

For UDP-style sockets, id specifies the association to query. For TCP-style sockets, id is
ignored.

If the id field is set to the value '0' then the locally bound addresses are returned without
regard to any particular association.

On success, sctp_getladdrs() returns the number of local addresses bound to the socket. If
the socket is unbound, sctp_getladdrs() returns 0, and the value of *addrs is undefined. If
an error occurs, sctp_getladdrs() returns -1, and the value of *addrs is undefined.

This interface is implemented as a library function.


DOCUMENTTYPE 25 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

2.10.6 sctp_freeladdrs()

sctp_freeladdrs() frees all resources allocated by sctp_getladdrs(). Its syntax is,

void sctp_freeladdrs(struct sockaddr_storage *addrs);

addrs is the array of peer addresses returned by sctp_getladdrs().

2.10.7 sctp_sendmsg()

sctp_sendmsg(). Its syntax is,

ssize_t sctp_sendmsg(int s,
const void *msg,
size_t len,
struct sockaddr *to,
socklen_t tolen,
uint32_t ppid,
uint32_t flags,
uint16_t stream_no,
uint32_t timetolive,
uint32_t context)

s - is the socket descriptor


msg - is the message to be sent.
len - is the length of the message.
to - is the destination address of the message.
tolen - is the length of the destination address.
ppid - is the same as sinfo_ppid
flags - is the same as sinfo_flags
stream_no - is the same as sinfo_stream
timetolive - is the same as sinfo_timetolive
context - is the same as sinfo_context

2.10.8 sctp_recvmsg()

sctp_recvmsg(). Its syntax is,

ssize_t sctp_recvmsg(int s,
void *msg,
size_t *len,
struct sockaddr *from,
socklen_t *fromlen
struct sctp_sndrcvinfo *sinfo
int *msg_flags)

s - is the socket descriptor


msg - is a message buffer to be filled.
DOCUMENTTYPE 26 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

len - is the length of the message buffer.


from - is a pointer to a address to be filled with
the sender of this messages address.
fromlen - is the from length.
sinfo - A pointer to a sctp_sndrcvinfo structure
to be filled upon receipt of the message.
msg_flags - A pointer to a integer to be filled with
any message flags (e.g. MSG_NOTIFICATION).

Notes: The four interfaces getpaddrs(),freepaddrs(), getladdrs(),freeladdrs() are non-system call API.
These APIs of the sctp are not part of the standard set of system calls in linux kernel. For
that reason, these functions are plemented with the use of other system calls to interface
kernel back-end from the user-level front-end. So any application that is to make use of
these functions has to have sctpulib.c source file as its part. Header file is sctpulib.h.

These files:
sctpulib.c
sctpulib.h

3. INSTALLATION GUIDE

3.1 account in isource.nokia.com

Reference http://www.sourceforge.net/

Create a account for yourself in http://isource.nokia.com/ ,

Give the userid to project manager and add you to noklksctp developer list.

3.2 Create the source tree (based on Linux Kernel 2.4.18)

$ tar xvfz noklksctp.tgz

$ cvs [email protected]:/isource/cvsroot/noklksctp co noklksctp


[email protected]'s password:
cvs server: Updating noklksctp
U noklksctp/CHANGES
cvs server: Updating noklksctp/docs
cvs server: Updating noklksctp/docs/withdrawn
cvs server: Updating noklksctp/sctp_cvs
cvs server: Updating noklksctp/sctp_cvs/include
cvs server: Updating noklksctp/sctp_cvs/include/linux
cvs server: Updating noklksctp/sctp_cvs/include/net
cvs server: Updating noklksctp/sctp_cvs/include/net/sctp
……

$ cd noklksctp

$ mkdir linux_sctp

$ cd tools

$ ./mklinux_sctp.sh
DOCUMENTTYPE 27 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

$ ./updatelinux_sctp.sh

3.3 File list

COPYING If you haven't seen this, you probably want to start


with some other program...
README README file. Read this before developing.
ANNOUNCEMENT The original announcement of the Developers' Release.
BUGS An empty file :-). These are bugs not documented in
the code itself.
CHANGES What has changed since the last release?
STORIES This is the current set of XP stories we've identified.

sctp_cvs/ This directory hierarchy contains the bulk of our code


including the modified files from the stock linux kernel
source tree.
sctp_cvs/include/net/sctp/ All the SCTP-specific headers.
sctp_cvs/net/sctp All the SCTP-specific source files.

docs/ All the relevant Internet Drafts and RFC's.


docs/states.txt This is a detailed state table for SCTP. It makes a
pretty good index for RFC2960 too...
test/ Find the functional tests, the unit tests, and the
user space test frame here. Use the Makefile in this
directory to run all the automated tests.
test/linux/include This include heirarchy includes special versions of
kernel include files needed by the user-space test
frame.
test/libc/include This include hierarchy contains header files needed by
the user-space SCTP test programs.
tools/mklinux_sctp.sh This script creates linux_sctp directory formed by
merging stock 2.4.18 kernel from linux directory
and the SCTP specific files from sctp_cvs directory.
tools/updatesctp_cvs.sh This script pulls the modified SCTP specific files from
linux_sctp and updates the corresponding files in sctp_cvs.
tools/updatelinux_sctp.sh This script pushes the modified SCTP specific files from
sctp_cvs to linux_sctp.
tools/mklinks.sh This script creates links from linux into the linux_sctp
directory and is called by the above mklinux_sctp.sh.
3.4 Compile

3.4.1 Compile lksctp in kernel

$ cd test;make chicken;cd ../linux_sctp


$ make xconfig
Code Maturity->Development->Yes,
Networking->IP:
Enable SCTP->Yes.
make dep
make bzImage;
su -
cp arch/i386/boot/bzImage /boot/vmlinuz-sctp
vi /etc/grub.conf
DOCUMENTTYPE 28 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

title Red Hat Linux (sctp)


root (hd0,0)
kernel /boot/vmlinuz-sctp ro root=/dev/hda1
reboot

3.4.2 Compile lksctp as a kernel

cd linux_sctp
make xconfig
code materity -> yes
Networking -> IPv6 -> Module
Networking -> SCTP -> Module
make dep
make bzImage;
su -
cp arch/i386/boot/bzImage /boot/vmlinuz-sctp
vi /etc/grub.conf
title Red Hat Linux (sctp)
root (hd0,0)
kernel /boot/vmlinuz-sctp ro root=/dev/hda1
reboot
make modules; make modules_install
insmod ipv6
insmod sctp

4. REFFERENCE

1. rfc2960.txt

2. draft-ietf-tsvwg-sctpsocket-05.txt

3. project webpage

http://www.china.nokia.com/nokia/www/cnrdait.nsf/document/BE045C55X4?OpenDocument

5. EXAMPLES

5.1 Server

In this TCP style example, server finish the function of socket(), bind(), listen(), accept() and
close().
#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/socket.h> /* needed by linux/sctp.h */
#include <sys/uio.h>
#include <netinet/in.h> /* for sockaddr_in */
#include <sys/errno.h>
#include <errno.h>
#include <sctp.h>

int
main(void)
{
DOCUMENTTYPE 29 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

int sk;
int pf_class;
sockaddr_storage_t loopSer;

int newsk;
struct sockaddr newAddr;

int len, notAccepted;


int error = 0;
#if TEST_V6
pf_class = PF_INET6;
loopSer.v6.sin_family = AF_INET6;
loopSer.v6.sin_port = htons(S_PORT);
inet_aton(SERVER, &loopSer.v6.sin_addr);
#else
pf_class = PF_INET;
loopSer.v4.sin_family = AF_INET;
loopSer.v4.sin_port = htons(S_PORT);
inet_aton(SERVER, &loopSer.v4.sin_addr);
#endif

sk = socket(pf_class, SOCK_STREAM, IPPROTO_SCTP);


if (sk == -1) {
printf("Can not creat a socket!\n");
exit(1);
}

error = bind(sk, (struct sockaddr *)&loopSer.sa, sizeof(loopSer));


if (0 != error) {
printf("\n\n\t\tFailure: %s.\n\n\n", sys_errlist[errno]);
exit(1);
}

error = listen(sk, 1);


if (0 != error) {
printf("\n\n\t\tFailure: %s.\n\n\n", sys_errlist[errno]);
exit(1);
}

printf("Listening ...\n");

notAccepted = 1;
while(notAccepted) {
newsk = accept(sk, (struct sockaddr *)&newAddr, &len);
notAccepted = 0;

if (0 >= newsk) {
printf("Can not open as new socket...\n");
exit(1);
}

printf("Socket is opened.\n");
}

sleep (3);

if (0 != close(sk) ||
0 != close(newsk)) {
DOCUMENTTYPE 30 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

printf("Can not close connections ...\n");


return -1;
}else{
printf("Socket is closed.\n");
}

return 0;

5.2 Client

Note: in this TCP style example(which corresponding to the above, it shows the function of socket(),
bind(), connect(), setsockopt(), getsockopt(). )
#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/socket.h> /* needed by linux/sctp.h */
#include <sys/uio.h>
#include <netinet/in.h> /* for sockaddr_in */
#include <sys/errno.h>
#include <errno.h>
#include <sctp.h>

int
main(void)
{
int sk;
int pf_class;
sockaddr_storage_t loopClt, loopSer;
struct sctp_assocparams asocparam,setparam;
struct sctp_initmsg initmsg, reinitmsg;

int error;
int optlen;
int nodelay = 0 , renodelay = 0;
int sbuf, resbuf;

#if TEST_V6
pf_class = PF_INET6;
loopClt.v6.sin_family = AF_INET6;
loopClt.v6.sin_port = htons(C_PORT);
loopSer.v6.sin_family = AF_INET6;
loopSer.v6.sin_port = htons(S_PORT);
inet_aton(SERVER, &loopSer.v6.sin_addr);
inet_aton(CLIENT, &loopClt.v6.sin_addr);
#else
pf_class = PF_INET;
loopClt.v4.sin_family = AF_INET;
loopClt.v4.sin_port = htons(C_PORT);
loopSer.v4.sin_family = AF_INET;
loopSer.v4.sin_port = htons(S_PORT);
inet_aton(SERVER, &loopSer.v4.sin_addr);
inet_aton(CLIENT, &loopClt.v4.sin_addr);
#endif

sk = socket(pf_class, SOCK_STREAM, IPPROTO_SCTP);


DOCUMENTTYPE 31 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

if (sk == -1) {
printf("Can not creat a socket\n");
exit(-1);
}

error = bind(sk, (struct sockaddr *)&loopClt.sa, sizeof(loopClt));


if (0 != error) {
printf("bind to port %d error\n",3000);
exit(-1);
}

printf("Connecting ...\n");

error = connect(sk, &loopSer.sa, sizeof(loopSer));


if (error != 0) {
printf("Error connecting!\n");
printf("%s\n", sys_errlist[errno]);
printf("error is: %d\n",error);
exit(1);
}

// test case 11.2


/* TEST #7.1.2: SCTP_ASSOCINFO socket option. */
memset(&asocparam, 0x00, sizeof(struct sctp_assocparams));
asocparam.sasoc_assoc_id = 0;
optlen = sizeof(struct sctp_assocparams);
error = getsockopt(sk, SOL_SCTP, SCTP_ASSOCINFO,
(char *)&asocparam, &optlen);
if (error != 0) {
printf("set socket option error!\n");
exit(1);
}

/* check the option value.*/


printf("This is default value!\n The endpoint:
uint16_t sasoc_asocmaxrxt:%d\n
uint16_t sasoc_number_peer_destinations:%d\n
uint32_t sasoc_peer_rwnd:%d\n
uint32_t sasoc_local_rwnd:%d\n
uint32_t sasoc_cookie_life:%d milliseconds\n\n",
asocparam.sasoc_asocmaxrxt,/* 10? for ep*/
asocparam.sasoc_number_peer_destinations,/*0? for ep */
asocparam.sasoc_peer_rwnd,/* nothing for ep*/
asocparam.sasoc_local_rwnd,/* DEFAULT_MAX_WINDOW? for ep*/
asocparam.sasoc_cookie_life);/* DEFAULT? for ep */

/* We change the endpoint default AsocRtxInfo parameters.*/


/* The asocmaxrtx should be less than 5,
*which is Summation of path.max.retrans
*/
setparam.sasoc_assoc_id = 0;/* ignored */
setparam.sasoc_asocmaxrxt = 4; /* another */
setparam.sasoc_number_peer_destinations = 0;/* ignored*/
setparam.sasoc_peer_rwnd = 0;/* ignored*/
setparam.sasoc_local_rwnd = 0;/* ignored*/
setparam.sasoc_cookie_life = 1000000;/* 1 second */
error = setsockopt(sk, SOL_SCTP, SCTP_ASSOCINFO, (char *)&setparam,
sizeof(struct sctp_assocparams));
DOCUMENTTYPE 32 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

if (error != 0) {
printf("set socket option error!\n");
printf("errno is :%s\n", sys_errlist[errno]);
exit(1);
}else{
printf("set socket option asocmaxrtx = 4.\n");
printf("set socket option cookie_life = 1000000.\n");
}

/*== We check the association AsocRtxInfo parameters.*/


memset(&asocparam, 0x00, sizeof(struct sctp_assocparams));
asocparam.sasoc_assoc_id = 0;
optlen = sizeof(struct sctp_assocparams);
error = getsockopt(sk, SOL_SCTP, SCTP_ASSOCINFO,
(char *)&asocparam, &optlen);
if (error != 0) {
printf("get socket option error!\n");
exit(1);
}

/* check the option value.*/


printf("\n The association 1:
uint16_t sasoc_asocmaxrxt:%d\n
uint16_t sasoc_number_peer_destinations:%d\n
uint32_t sasoc_peer_rwnd:%d\n
uint32_t sasoc_local_rwnd:%d\n
uint32_t sasoc_cookie_life:%d milliseconds\n\n",
asocparam.sasoc_asocmaxrxt,/* 8? */
asocparam.sasoc_number_peer_destinations,/*1? */
asocparam.sasoc_peer_rwnd,/* ? */
asocparam.sasoc_local_rwnd,/* DEFAULT_MAX_WINDOW? */
asocparam.sasoc_cookie_life);/* 1000000? */

printf("Test case 11.2 for SCTP_ASSOCINFO passes!\n\n\n");

/* test case 11.3 */


/* draft socket api 7.1.3 */
memset(&reinitmsg, 0x00, sizeof(struct sctp_initmsg));
optlen = sizeof(struct sctp_initmsg);
error = getsockopt(sk, SOL_SCTP, SCTP_INITMSG,
(char *)&reinitmsg, &optlen);
if (error != 0) {
printf("get socket option error!");
exit(-1);
}

/* Set socket option*/


memset(&initmsg, 0x00, sizeof(struct sctp_initmsg));
initmsg.sinit_num_ostreams = 9;
initmsg.sinit_max_instreams = 9;
initmsg.sinit_max_attempts = 4;
initmsg.sinit_max_init_timeo = 100;
error = setsockopt(sk, SOL_SCTP, SCTP_INITMSG,
(char *)&initmsg, sizeof(struct sctp_initmsg));
if (error != 0) {
printf("get socket option error!");
exit(-1);
DOCUMENTTYPE 33 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

/* Get the parameters*/


memset(&reinitmsg, 0x00, sizeof(struct sctp_initmsg));
optlen = sizeof(struct sctp_initmsg);
error = getsockopt(sk, SOL_SCTP, SCTP_INITMSG,
(char *)&reinitmsg, &optlen);
if (error != 0) {
printf("get socket option error!");
exit(-1);
}

if ((initmsg.sinit_num_ostreams != reinitmsg.sinit_num_ostreams)||
(initmsg.sinit_max_instreams != initmsg.sinit_max_instreams)||
(initmsg.sinit_max_attempts != initmsg.sinit_max_attempts )||
(initmsg.sinit_max_init_timeo !=initmsg.sinit_max_init_timeo))
{
printf("Test case 11.2 for SCTP_INITMSG Fail.\n\n");
exit(-1);
}else{
printf("Test case 11.2 for SCTP_INITMSG passes!\n\n");
}
/* End of TEST case 11.3: SCTP_INITMSG socket option.*/

/* TEST case 11.5: SCTP_NODELAY socket option. */


/* Get the parameters of nodelay*/
renodelay = 1;
optlen = sizeof(int);
error = getsockopt(sk, SOL_SCTP, SCTP_NODELAY,
(char *)&renodelay, &optlen);
if (error != 0) {
printf("get socket option error.\n");
exit(-1);
}

printf("\nSCTP_NODELAY is set to be %d by default.\n",renodelay);


/* Set socket option */
nodelay = 1;
error = setsockopt(sk, SOL_SCTP, SCTP_NODELAY,
(char *)&nodelay, sizeof(int));
if (error != 0) {
printf("get socket option error.\n");
exit(-1);
}

/* Get the parameters of nodelay*/


renodelay = 0;
optlen = sizeof(int);
error = getsockopt(sk, SOL_SCTP, SCTP_NODELAY,
(char *)&renodelay, &optlen);
if (error != 0) {
printf("set socket option error.\n");
exit(-1);
}

printf("SCTP_NODELAY is set to be %d now.\n",renodelay);


DOCUMENTTYPE 34 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

if (renodelay == nodelay){
printf("Test case 11.5 for SCTP_NODELAY passes!\n\n\n");
}else{
printf("Test case 11.5 for SCTP_NODELAY Fail.\n\n\n");
}

/* TEST case 11.7: SO_SNDBUF socket option. ---*/


/* test draft socket api 7.1.6 */
resbuf = 0;
optlen = sizeof(uint32_t);
error = getsockopt(sk, SOL_SCTP, SO_SNDBUF,
(char *)&resbuf, &optlen);
sbuf = resbuf * 2;
error = setsockopt(sk, SOL_SCTP, SO_SNDBUF, (char *)&sbuf,
sizeof(uint32_t));
if (error != 0) {
printf("set socket option Fail.\n");
exit(-1);
}
resbuf = 0;
optlen = sizeof(uint32_t);
/* Get the skn's rcvbuf and check */
error = getsockopt(sk, SOL_SCTP, SO_SNDBUF,
(char *)&resbuf, &optlen);
if (error != 0) {
printf("get socket option Fail.\n");
exit(-1);
}
if (resbuf != sbuf){
printf("\n\n\t\tSO_SNDBUF Fail.\n\n");
exit(-1);
}else{
printf("SO_SNDBUF is %d!\n",sbuf);
printf("Test case 11.6 passes!\n\n");
}

if (0 != close(sk)) {
printf("Error closing ...\n");
return -1;
}

return 0;

}
DOCUMENTTYPE 35 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

6. SCTP IN FLEXISERVER

6.1 Configuration, Installation and Storage

There are no user or operator configurable parameters in SCTP. The implementation is an


integral part of the FlexiOS kernel and it is statically linked in the kernel. The source code is
part of the kernel source code and resides in net/sctp/ directory in the kernel source tree. If
you're running FlexiOS, you have SCTP support.

6.2 The SCTP Header

The general instructions in the previous chapters apply. In case of any conflicts, the
instructions in this chapter override the instructions elsewhere in this document.

netinet/sctp.h is included in source modules normally. However, in order to get the correct
version of sctp.h, $(SCTP_INC) must be added to include paths in makefile. Note that it
should be the first include path in the list in order to override other sctp.h files found in any
other include paths.

Example:
INCFLAGS = \
-I$(SCTP_INC) \
-I$(SRCDIR) \
-I$(TTEN_HOME)/include

Or if INCFLAGS doesn't place SCTP_INC sufficiently close to the start of the compiler
command, just put it in CXXLOCALOPTS:
CXXLOCALOPTS = -I$(SCTP_INC) -O3 -Wall

6.3 The SCTP Library

The SCTP Library, libsctp, provides the following functions for the SCTP user:
unsigned long bindx(int fd, struct sockaddr_storage *bindx_addr,
int addrcnt, int flags);
int sctp_peeloff(int fd, sctp_assoc_t *associd);

int sctp_sendmsg(int s,
const void *msg,
int len,
struct sockaddr *to,
int tolen,
uint32_t ppid,
uint32_t flags,
uint32_t stream_no,
uint32_t timetolive,
uint32_t context);

int sctp_recvmsg(int s,
void *msg,
int *len,
struct sockaddr *from,
int *from_len,
DOCUMENTTYPE 36 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

struct sctp_sndrcvinfo *sinfo,


int *msg_flags);

int sctp_getpaddrs(int sd, sctp_assoc_t id,


struct sockaddr_storage **addrs);
int sctp_freepaddrs(struct sockaddr_storage *addrs);
int sctp_getladdrs(int sd, sctp_assoc_t id,
struct sockaddr_storage **addrs);
int sctp_freeladdrs(struct sockaddr_storage *addrs);

These are documented in the SCTP Sockets API Draft (IETF), and also in this document,
Section 2.10.

libsctp is a static library that resides in SS_LibSS7Stack/sctp. The library is not related to
SS_LibSS7Stack as such, the subsystem acts simply as a storage place for libsctp. libsctp
is used like any other library in FlexiServer. Source modules that use any of the functions
listed above, must include sctp_lib.h. The following settings must be added in makefile in
order to compile and link with libsctp:
INCFLAGS = -I$(DIR_SS_LIBSS7STACK)/sctp/src/
LIBRARIES = $(DIR_SS_LIBSS7STACK)/sctp/build/libsctp.a
APPLIBS = -L$(DIR_SS_LIBSS7STACK)/sctp/build -lsctp

6.4 LBSCTP Sockets

An LBSCTP (Load Balancer SCTP) socket is a special kind of SCTP socket specific to the
FlexiServer IPD kernel. LBSCTP sockets are used in the IPD for handling multiplexed
associations to internal nodes. For load balancing purposes, FlexiServer Recovery Groups
have virtual IPs, that is, all Recovery Units of an Recovery Group in all nodes are
addressed with the same IP. Hence, in order to address a specific node, the node's MAC
address is required in addition to the IP. LBSCTP sockets are used exactly like normal
SCTP sockets, with the exceptions explained below.

The user code must define the following: AF_INET6 and SOCK_STREAM are also valid
with LBSCTP sockets just like they are valid with normal SCTP sockets.
#ifndef IPPROTO2LB
#define IPPROTO2LB(arg) ((arg) | 0x100)
#define LB2IPPROTO(arg) ((arg) & ~0x100)
#define IPPROTO_LBSCTP IPPROTO2LB(IPPROTO_SCTP)
#endif /* !IPPROTO2LB */

#ifndef AF_LBHWADDR
#define AF_LBHWADDR 30
#define PF_LBHWADDR AF_LBHWADDR
#endif /* !AF_LBHWADDR */

An LBSCTP socket is created with the socket() call, using IPPROTO_LBSCTP:


fd = socket(AF_INET, SOCK_SEQPACKET, IPPROTO_LBSCTP)
DOCUMENTTYPE 37 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

All calls involving the peer address (the address of an internal node) must include the MAC
address in addition to the virtual IP address. For this purpose, the user code should define
an address structure:
struct
{
struct sockaddr mac_addr; /* MAC */
struct sockaddr_in ip_addr; /* virtual IP (in this case IPv4) */
} address;

Fill the address structure:


address.mac_addr.sa_family = AF_LBHWADDR;
memcpy(&address.mac_addr.sa_data, mac_addr, 6); /* 6 bytes */
address.ip_addr.sin_family = AF_INET;
memcpy(&address.ip_addr.sin_addr, ip_addr, sizeof(*ip_addr));
address.ip_addr.sin_port = port;

After the address structure is filled, it can be used in any calls requiring the peer address,
such as connect() and sendmsg(). recvmsg() works similarly, the address structure is of
course filled by the recvmsg() call. Prior to the recvmsg() call the address structure must be
filled with zeroes. An example connect() call:
connect(fd, &address, sizeof(address));

The size of the address structure must include the MAC as well as the IP. Hence,
sizeof(address) instead of just sizeof(sockaddr_in).

All of the above is valid for IPv6 also, with sockaddr_in6 instead of sockaddr_in and
AF_INET6 instead of AF_INET.

An LBSCTP socket can also be used as a server socket in IPD, listening to connections
from the internal nodes. Such a server socket must be bound to IPADDR_ANY and a given
port. The server socket will then accept connections from the internal nodes to any IP
address, as long as the connection is made using the given port and the client socket in the
internal node is bound to a virtual IP. The idea is that an application in an internal node
attempts to form an SCTP association to an external peer. Regardless of the external
peer's IP address, the association is in fact formed to a server process in IPD. Effectively,
the association is "hijacked" by a loadbalancer process in IPD and the IPD poses as the
external peer for the application in the internal node. After a new association has been
formed using an LBSCTP server socket, an sctp_getladdr() call for that association will
return the IP to which the association was being formed to from the internal node. In other
words, the IP address of the external peer. For one-to-one LBSCTP sockets in IPD,
getpeername() returns struct address (including MAC and IP) containing the address of the
internal node. There is no parameter in getpeername() to specify an association in a one-
to-many socket, so getpeername() does not support one-to-many sockets. Since recvmsg()
returns the address of the peer in msg_name member of struct msghdr, the server process
in IPD can get the internal node's address from the COMM_UP notification when the
association is formed. This is what the SS7 Load Balancer does.
DOCUMENTTYPE 38 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

APPENDIX A

A.1 UDP-style Interface

The UDP-style interface has the following characteristics:


A) Outbound association setup is implicit.
B) Messages are delivered in complete messages (with one notable exception).
C) There is a 1 to MANY relationship between socket and association.

A.1.1 Basic Operation

A.1.1.1 socket() - UDP Style Syntax

sd = socket(PF_INET, SOCK_SEQPACKET, IPPROTO_SCTP);


or,
sd = socket(PF_INET6, SOCK_SEQPACKET, IPPROTO_SCTP);

PF_INET only support Ipv4 address, while PF_INET6 can support both IPv4 and IPv6
address. SCTP allow a mapped IPv6 address communicate with a host which has IPv4
address.

A.1.1.2 bind() - UDP Style Syntax

ret = bind(int sd, struct sockaddr *addr, int addrlen);

sd - the socket descriptor returned by socket().


addr - the address structure (struct sockaddr_in or struct sockaddr_in6 [RFC 2553]),
addrlen - the size of the address structure.

A.1.1.3 listen() - UDP Style Syntax

int listen(int socket, int backlog);

socket - the socket descriptor of the endpoint.

backlog - ignored for UDP-style sockets.

A.1.1.4 sendmsg() and recvmsg() - UDP Style Syntax

ssize_t sendmsg(int socket, const struct msghdr *message, int flag s);

ssize_t recvmsg(int socket, struct msghdr *message, int flags);

socket - the socket descriptor of the endpoint

message - pointer to the msghdr structure which contains a single user


message and possibly some ancillary data.

flags - No new flags are defined for SCTP at this level.

A.1.1.5 close() - UDP Style Syntax

ret = close(int sd);


DOCUMENTTYPE 39 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

sd - the socket descriptor of the associations to be closed.

A.1.1.6 connect() - UDP Style Syntax

ret = connect(int sd, const struct sockaddr *nam, int len);

sd - the socket descriptor to have a new association added to.

nam - the address structure (either struct sockaddr_in or struct sockaddr_in6 defined in
[RFC 2553]).

len - the size of the address.

A.1.2 Implicit Association Setup

1.using bind()

Once all bind() calls are complete on a UDP-style socket, the application can begin sending
and receiving data using the sendmsg()/recvmsg() or sendto()/recvfrom() calls, without
going through any explicit association setup procedures (i.e., no connect() calls required).

2. without bind()

Whenever sendmsg() or sendto() is called and the SCTP stack at the sender finds that
there is no association existing between the sender and the intended receiver (identified by
the address passed either in the msg_name field of msghdr structure in the sendmsg() call
or the dest_addr field in the sendto() call), the SCTP stack will automatically setup an
association to the intended receiver.

A.1.3 Non-blocking mode

Some SCTP users might want to avoid blocking when they call socket interface function.
Whenever the user which want to avoid blocking must call select() before calling
sendmsg()/sendto() and recvmsg()/recvfrom(), and check the socket status is writable or
readable. Once all bind() calls are complete on a UDP-style socket, the application must
set the non-blocking option by a fcntl() (such as O_NONBLOCK). In order to shutdown the
association gracefully, the user must call sendmsg() with no data and with the MSG_EOF
flag set.

A.2 TCP-style Interface

This model enables existing applications using connection oriented protocols to be ported
to SCTP with very little effort. Note that some new SCTP features and some new SCTP
socket options can only be utilized through the use of sendmsg() and recvmsg() calls.

A.2.1 Basic Operation

A.2.1.1 socket() - TCP Style Syntax

int socket(PF_INET, SOCK_STREAM, IPPROTO_SCTP);


or,
int socket(PF_INET6, SOCK_STREAM, IPPROTO_SCTP);
DOCUMENTTYPE 40 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

PF_INET only support Ipv4 address, while PF_INET6 can support both IPv4 and IPv6
address. SCTP allow a mapped IPv6 address communicate with a host which has IPv4
address.

A.2.1.2 bind() - TCP Style Syntax

int bind(int sd, struct sockaddr *addr, int addrlen);

sd - the socket descriptor returned by socket() call.


addr - the address structure (either struct sockaddr_in or struct sockaddr_in6 defined in
[RFC 2553]).
addrlen - the size of the address structure.

A.2.1.3 listen() - TCP Style Syntax

int listen(int sd, int backlog);

sd - the socket descriptor of the SCTP endpoint.

backlog - this specifies the max number of outstanding associations allowed in the socket's
accept queue. These are the associations that have finished the four-way initiation
handshake (see Section 5 of [SCTP]) and are in the ESTABLISHED state. Note, a backlog
of '0' indicates that the caller no longer wishes to receive new.

A.2.1.4 accept() - TCP Style Syntax

new_sd = accept(int sd, struct sockaddr *addr, socklen_t *addrlen);

new_sd - the socket descriptor for the newly formed association.


sd - the listening socket descriptor.
addr - on return, will contain the primary address of the peer endpoint.
addrlen - on return, will contain the size of addr.

A.2.1.5 connect() - TCP Style Syntax

int connect(int sd, const struct sockaddr *addr, int addrlen);

sd - the socket descriptor of the endpoint.


addr - the peer's address.
addrlen - the size of the address.

A.2.1.6 close() - TCP Style Syntax

int close(int sd);

sd - the socket descriptor of the association to be closed.

A.2.1.7 shutdown() - TCP Style Syntax

int shutdown(int socket, int how);

sd - the socket descriptor of the association to be closed.


how - Specifies the type of shutdown. The values are as follows:

SHUT_RD
DOCUMENTTYPE 41 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

Disables further receive operations. No SCTP protocol action is taken.

Note:

Socket who calls the shutdown(sd, SHUT_RD): it could not receive messages
and datas any more even the peer continuously sends messages and datas,
while it could sends messages and datas. After call shutdown(sd, SHUT_RD),
each time the socket call recv, 0 will be returned indicating EOF.

Socket who receive the shutdown signal: nothing else will be different with the
socket.

SHUT_WR

Disables further send operations, and initiates the SCTP shutdown sequence.

Note:

Socket who calls the shutdown(sd, SHUT_WR): it still could receive


messages or datas from the peer until it receives shutdown ack signal, but it
could not send any messages or datas.

Socket who receives the shutdown ack: if it receives shutdown signal, call
recv() on the socket will not return error, instead it will return 0 indicating EOF.

SHUT_RDWR

Disables further send and receive operations and initiates the SCTP
shutdown sequence.

Note:

Neither of the sockets could send messages or datas; neither of them could
receive any messages and datas. If recv() is called, 0 will be returned; if
send() or sendto() will be called, an error will returnd.

A.2.1.8 sendmsg() and recvmsg() - TCP Style Syntax

The semantics is similar to those used in the UDP-style model (section 2.3.1.4), with the
following differences:

1) When sending, the msg_name field in the msghdr is not used to specify the intended
receiver, rather it is used to indicate a different peer address if the sender does not want to
send the message over the primary address of the receiver. If the transport address given
is not part of the current association, the data will not be sent and a SCTP_SEND_FAILED
event will be delivered to the application if send failure events are enabled. When receiving,
if a message is not received from the primary address, the SCTP stack will fill in the
msg_name field on return so that the application can retrieve the source address
information of the received message.

2) An application must use close() to gracefully shutdown an association, or use


SO_LINGER option with close() to abort an association(2.7.1.4). It must not use the
DOCUMENTTYPE 42 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

MSG_ABORT or MSG_EOF flag in sendmsg(). The system returns an error if an


application tries to do so.

A.2.1.9 getpeername()

int getpeername(int socket, struct sockaddr *address, socklen_t *len);

sd - the socket descriptor to be queried.

address - On return, the peer primary address is stored in this buffer. If the socket is an
IPv4 socket, the address will be IPv4. If the socket is an IPv6 socket, the address will be
either an IPv6 or mapped IPv4 address.

len - The caller should set the length of address here. On return, this is set to the length
of the returned address.
DOCUMENTTYPE 43 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

APPENDIX B

B.1 Read / Write Options

B.1.1 Retransmission Timeout Parameters (SCTP_RTOINFO)

The protocol parameters used to initialize and bound retransmission timeout (RTO) are
tunable. The peer address parameter is ignored for TCP style socket.

The following structure is used to access and modify these parameters:

struct sctp_rtoinfo {
sctp_assoc_t srto_assoc_id;
uint32_t srto_initial;
uint32_t srto_max;
uint32_t srto_min;
};

srto_initial - This contains the initial RTO value.


srto_max and srto_min - These contain the maximum and minimum bounds for all
RTOs.
srto_assoc_id - (UDP style socket) This is filled in the application, and identifies the
association for this query. If this parameter is missing (on a UDP style
socket), then the change effects the entire endpoint.

All parameters are time values, in milliseconds. A value of 0, when modifying the
parameters, indicates that the current value should not be changed.

To access or modify these parameters, the application should call getsockopt or


setsockopt() respectively with the option name SCTP_RTOINFO.

B.1.2 Association Parameters (SCTP_ASSOCINFO)

This option is used to both examine and set various association and endpoint parameters.
The peer address parameter is ignored for TCP style socket.

The following structure is used to access and modify this parameters:

struct sctp_assocparams {
sctp_assoc_t sasoc_assoc_id;
uint16_t sasoc_asocmaxrxt;
uint16_t sasoc_number_peer_destinations;
uint32_t sasoc_peer_rwnd;
uint32_t sasoc_local_rwnd;
uint32_t sasoc_cookie_life;
};
sasoc_asocmaxrxt - This contains the maximum retransmission attempts
to make for the association.

sasoc_number_peer_destinations - This is the number of destination address that the


peer considers valid.
sasoc_peer_rwnd - This holds the current value of the peers rwnd (reported in the last
SACK) minus any outstanding data (i.e. data inflight).
DOCUMENTTYPE 44 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

sasoc_local_rwnd - This holds the last reported rwnd that was sent to the peer.
sasoc_cookie_life - This is the associations cookie life value used when issuing cookies.
sasoc_assoc_id - (UDP style socket) This is filled in the application, and identifies the
association for this query.

This information may be examined for either the endpoint or a specific association. To
examine a endpoints default parameters the association id (sasoc_assoc_id) should must
be set to the value '0'. The values of the sasoc_peer_rwnd is meaningless when examining
endpoint information.

The values of the sasoc_asocmaxrxt and sasoc_cookie_life may be set on either an


endpoint or association basis. The rwnd and destination counts
(sasoc_number_peer_destinations, sasoc_peer_rwnd,sasoc_local_rwnd) are NOT settable
and any value placed in these is ignored.

To access or modify these parameters, the application should call getsockopt or


setsockopt() respectively with the option name

SCTP_ASSOCRTXINFO.

The maximum number of retransmissions before an address is considered unreachable is


also tunable, but is address-specific, so it is covered in a separate option. If an application
attempts to set the value of the association maximum retransmission parameter to more
than the sum of all maximum retransmission parameters, setsockopt() shall return an error.

Note: When configuring the SCTP endpoint, the user should avoid having the value of
'Association.Max.Retrans' larger than the summation of the 'Path.Max.Retrans' of all the
destination addresses for the remote endpoint. Otherwise, all the destination
addressesmay become inactive while the endpoint still considers the peer endpoint
reachable.

B.1.3 Initialization Parameters (SCTP_INITMSG)

Applications can specify protocol parameters for the default association initialization. The
structure used to access and modify these parameters is defined in Section 2.5.2.1). The
option name argument to setsockopt() and getsockopt() is SCTP_INITMSG.

struct sctp_initmsg {
uint16_t sinit_num_ostreams;
uint16_t sinit_max_instreams;
uint16_t sinit_max_attempts;
uint16_t sinit_max_init_timeo;
};

sinit_num_ostreams: 16 bits (unsigned integer)

This is an integer number representing the number of streams that the application wishes to
be able to send to. This number is confirmed in the SCTP_COMM_UP notification and
must be verified since it is a negotiated number with the remote endpoint. The default
value of 0 indicates to use the endpoint default value.

sinit_max_instreams: 16 bits (unsigned integer)


DOCUMENTTYPE 45 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

This value represents the maximum number of inbound streams the application is prepared
to support. This value is bounded by the actual implementation. In other words the user
MAY be able to support more streams than the Operating System. In such a case, the
Operating System limit overrides the value requested by the user. The default value of 0
indicates to use the endpoint's default value.

sinit_max_attempts: 16 bits (unsigned integer)

This integer specifies how many attempts the SCTP endpoint should make at resending the
INIT. This value overrides the system SCTP 'Max.Init.Retransmits' value. The default
value of 0 indicates to use the endpoint's default value. This is normally set to the system's
default 'Max.Init.Retransmit' value.

sinit_max_init_timeo: 16 bits (unsigned integer)

This value represents the largest Time-Out or RTO value to use in attempting a INIT.
Normally the 'RTO.Max' is used to limit the doubling of the RTO upon timeout. For the INIT
message this value MAY override 'RTO.Max'. This value MUST NOT influence 'RTO.Max'
during data transmission and is only used to bound the initial setup time. A default value of
0 indicates to use the endpoint's default value. This is normally set to the system's TO.Max'
value (60 seconds).

Setting initialization parameters is effective only on an unconnected socket (for UDP-style


sockets only future associations are effected by the change). With TCP-style sockets, this
option is inherited by sockets derived from a listener socket.

B.1.4 SO_LINGER

An application using the TCP-style socket can use this option to perform the SCTP ABORT
primitive. The linger option structure is:

struct linger {
int l_onoff; /* option on/off */
int l_linger; /* linger time */
};

To enable the option, set l_onoff to 1. If the l_linger value is set to 0, calling close() is the
same as the ABORT primitive. If the value is set to a negative value, the setsockopt() call
will return an error. If the value is set to a positive value linger_time, the close() can be
blocked for at most linger_time ms. If the graceful shutdown phase does not finish during
this period, close() will return but the graceful shutdown phase continues in the system.

B.1.5 SO_NODELAY

Turn on/off any Nagle-like algorithm. This means that packets are generally sent as soon
as possible and no unnecessary delays are introduced, at the cost of more packets in the
network.

Expects an integer boolean flag.

Note that all the current SCTP implementations still have no Nagle like algorithm, including
our Linux Kernel SCTP. It is need to be extended later.
DOCUMENTTYPE 46 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

The option name argument to setsockopt() and getsockopt() is SO_NODELAY.

B.1.6 SO_RCVBUF

Sets receive buffer size. For SCTP TCP-style sockets, this controls the receiver window
size. For UDP-style sockets, this controls the receiver window size for all associations
bound to the socket descriptor used in the setsockopt() or getsockopt() call. The option
applies to each association's window size separately. Expects an integer or uint32_t.

B.1.7 SO_SNDBUF

Sets send buffer size. For SCTP TCP-style sockets, this controls the amount of data SCTP
may have waiting in internal buffers to be sent. This option therefore bounds the maximum
size of data that can be sent in a single send call. For UDP-style sockets, the effect is the
same, except that it applies to all associations bound to the socket descriptor used in the
setsockopt() or getsockopt() call. The option applies to each association's window size
separately. Expects an integer or uint32_t.

B.1.8 Automatic close of associations (SCTP_AUTOCLOSE)

This socket option is applicable to the UDP-style socket only. When set it will cause
associations that are idle for more than the specified number of seconds to automatically
close. An association being idle is defined an association that has NOT sent or received
user data. The special value of '0' indicates that no automatic close of any associations
should be performed. The option expects an integer defining the number of seconds of idle
time before an association is closed.

B.1.9 Set Primary Address (SCTP_SET_PRIMARY_ADDR)

Requests that the peer mark the enclosed address as the association primary. The
enclosed address must be one of the association's locally bound addresses. The following
structure is used to make a set primary request:

struct sctp_setprim {
sctp_assoc_t ssp_assoc_id;
struct sockaddr_storage ssp_addr;
};
ssp_addr The address to set as primary
ssp_assoc_id (UDP style socket) This is filled in by the application, and identifies
the association for this request.

This functionality is optional, within the extension. In our implementation, it is a set-only


option, the getsockopt operation is not supported. The option name argument to
setsockopt() is SCTP_SET_PRIMARY_ADDR.

B.1.10 Set Peer Primary Address (SCTP_SET_PEER_PRIMARY_ADDR)

Requests that the local SCTP stack use the enclosed peer address as the association
primary. The enclosed address must be one of the association peer's addresses. The
following structure is used to make a set peer primary request:

struct sctp_setpeerprim {
DOCUMENTTYPE 47 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

sctp_assoc_t sspp_assoc_id;
struct sockaddr_storage sspp_addr;
};

sspp_addr The address to set as primary


sspp_assoc_id (UDP style socket) This is filled in by the application, and identifies
the association for this request.

B.1.11 Set Adaption Layer Indicator (SCTP_SET_ADAPTION_LAYER)

Requests that the local endpoint set the specified Adaption Layer Indication parameter for
all future INIT and INIT-ACK exchanges.

struct sctp_setadaption {
u_int32_t ssb_adaption_ind;
};

ssb_adaption_ind The adaption layer indicator that will be included in any outgoing
Adaption Layer Indication parameter.

B.1.12 Set default message time outs (SCTP_SET_STREAM_TIMEOUTS)

This option requests that the requested stream apply a default time-out for messages in
queue. The default value is used when the application does not specify a timeout in the
sendrcvinfo structure (sinfo_timetolive element see Section 2.5.2.2).

struct sctp_setstrm_timeout {
sctp_assoc_t ssto_assoc_id;
u_int32_t ssto_timeout;
u_int16_t ssto_streamid_start;
u_int16_t ssto_streamid_end;
};

ssto_assoc_id (UDP style socket) This is filled in by the application, and identifies
the association for this request.
ssto_timeout The maximum time in milliseconds that messages should be held
inqueue before failure.
ssto_streamid_start The beginning stream identifier to apply this default against.
ssto_streamid_end The ending stream identifier to apply this default against.

Note that the current SCTP implementations still don`t support the time-out for messages in
queue. It is within the PR-SCTP extension, and need to be extended later.

The option name argument to setsockopt() and getsockopt() is


SCTP_SET_STREAM_TIMEOUTS.

B.1.13 Enable/Disable message fragmentation(SCTP_DISABLE_FRAGMENTS)

This option is an on/off flag. If enabled no SCTP message fragmentation will be performed.
Instead if a message being sent exceeds the current PMTU size, the message will NOT be
sent and instead a error will be indicated to the user.
DOCUMENTTYPE 48 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

B.1.14 Peer Address Parameters (SCTP_SET_PEER_ADDR_PARAMS)

Applications can enable or disable heartbeats for any peer address of an association,
modify an address's heartbeat interval, force a heartbeat to be sent immediately, and adjust
the address's maximum number of retransmissions sent before an address is considered
unreachable. The following structure is used to access and modify an address's
parameters:

struct sctp_paddrparams {
sctp_assoc_t spp_assoc_id;
struct sockaddr_storage spp_address;
uint32_t spp_hbinterval;
uint16_t spp_pathmaxrxt;
};

spp_assoc_id - (UDP style socket) This is filled in the application, and identifies the
association for this query.
spp_address - This specifies which address is of interest.
spp_hbinterval - This contains the value of the heartbeat interval, in milliseconds. A
value of 0, when modifying the parameter, specifies that the heartbeat
on this address should be disabled. A value of UINT32_MAX
(4294967295), when modifying the parameter, specifies that a
heartbeat should be sent immediately to the peer address, and the
current interval should remain unchanged.
spp_pathmaxrxt - This contains the maximum number of retransmissions before this
address shall be considered unreachable.

B.1.15 Set default send parameters (SET_DEFAULT_SEND_PARAM)

Applications that wish to use the sendto() system call may wish to specify a default set of
parameters that would normally be supplied through the inclusion of ancillary data. This
socket option allows such an application to set the default sctp_sndrcvinfo structure. The
application that wishes to use this socket option simply passes in to this call the
sctp_sndrcvinfo structure defined in Section 2.5.2.2) The input parameters accepted by this
call include sinfo_stream, sinfo_flags, sinfo_ppid, sinfo_context, sinfo_timetolive.

struct sctp_sndrcvinfo {
uint16_t sinfo_stream;
uint16_t sinfo_ssn;
uint16_t sinfo_flags;
uint32_t sinfo_ppid;
uint32_t sinfo_context;
uint32_t sinfo_timetolive;
uint32_t sinfo_tsn;
uint32_t sinfo_cumtsn;
sctp_assoc_t sinfo_assoc_id;
};

sinfo_stream: 16 bits (unsigned integer)


DOCUMENTTYPE 49 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

For sendmsg() this value holds the stream number that the application wishes to send this
message to. If a sender specifies an invalid stream number an error indication is returned
and the call fails.

sinfo_ssn: 16 bits (unsigned integer)

This parameter is ignored.

sinfo_ppid: 32 bits (unsigned integer)

This value in sendmsg() is an opaque unsigned value that is passed to the remote end in
each user message. Please note that byte order issues are NOT accounted for and this
information is passed opaquely by the SCTP stack from one end to the other.

sinfo_context: 32 bits (unsigned integer)

This value is an opaque 32 bit context datum that is used in the sendmsg() function. This
value is passed back to the upper layer if a error occurs on the send of a message and is
retrieved with each undelivered message (Note: if a endpoint has done multiple sends, all
of which fail, multiple different sinfo_context values will be returned. One with each user
data message).

sinfo_flags: 16 bits (unsigned integer)

This field may contain any of the following flags and is composed of a bitwise OR of these
values.
sendmsg() flags:

MSG_UNORDERED - This flag requests the un-ordered delivery of the message. If


this flag is clear the datagram is considered an ordered send.

MSG_ADDR_OVER - This flag, in the UDP model, requests the SCTP stack to
override the primary destination address with the address found
with the sendto/sendmsg call.

MSG_ABORT - Setting this flag causes the specified association to abort by


sending an ABORT message to the peer (UDP-style only). The
ABORT chunk will contain an error cause 'User Initiated Abort'
with cause code 12. The cause specific information of this error
cause is provided in msg_iov.

MSG_EOF - Setting this flag invokes the SCTP graceful shutdown procedures on
the specified association. Graceful shutdown assures that all
data enqueued by both endpoints is successfully transmitted
before closing the association (UDP-style only).

sinfo_timetolive: 32 bit (unsigned integer)

For the sending side, this field contains the message time to live in milliseconds. The
sending side will expire the message within the specified time period if the message as not
been sent to the peer within this time period. This value will override any default value set
using any socket option. Also note that the value of 0 is special in that it indicates no
timeout should occur on this message.
DOCUMENTTYPE 50 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

sinfo_tsn: 32 bit (unsigned integer)

This parameter is ignored.

sinfo_cumtsn: 32 bit (unsigned integer)

This parameter is ignored.

sinfo_assoc_id: sizeof (sctp_assoc_t)

The association handle field, sinfo_assoc_id, holds the identifier for the association
announced in the SCTP_COMM_UP notification. All notifications for a given association
have the same identifier. Ignored for TCP-style sockets.

The user must provide the sinfo_assoc_id field in to this call if the caller is using the UDP
model.

B.1.16 Set notification and ancillary events (SCTP_SET_EVENTS)

This socket option is used to specify various notifications and ancillary data the user wishes
to receive.

struct sctp_event_subscribe{
u_int8_t sctp_data_io_event;
u_int8_t sctp_association_event;
u_int8_t sctp_address_event;
u_int8_t sctp_send_failure_event;
u_int8_t sctp_peer_error_event;
u_int8_t sctp_shutdown_event;
u_int8_t sctp_partial_delivery_event;
u_int8_t sctp_adaption_layer_event;
};

Please see Section 2.7.3 for a full description of this option and its usage.

B.2 Read only options

B.2.1 Association Status (SCTP_STATUS)

Applications can retrieve current status information about an association, including


association state, peer receiver window size, number of unacked data chunks, and number
of data chunks pending receipt. This information is read-only. The following structure is
used to access this information:

struct sctp_status {
sctp_assoc_t sstat_assoc_id;
int32_t sstat_state;
uint32_t sstat_rwnd;
uint16_t sstat_unackdata;
uint16_t sstat_penddata;
uint16_t sstat_instrms;
DOCUMENTTYPE 51 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

uint16_t sstat_outstrms;
uint32_t sstat_fragmentation_point;
struct sctp_paddrinfo sstat_primary;
};

sstat_state - This contains the association's current state one of the following values:

SCTP_CLOSED
SCTP_BOUND
SCTP_LISTEN
SCTP_COOKIE_WAIT
SCTP_COOKIE_ECHOED
SCTP_ESTABLISHED
SCTP_SHUTDOWN_PENDING
SCTP_SHUTDOWN_SENT
SCTP_SHUTDOWN_RECEIVED
SCTP_SHUTDOWN_ACK_SENT

sstat_rwnd - This contains the association peer's current receiver window size.
sstat_unackdata - This is the number of unacked data chunks.
sstat_penddata - This is the number of data chunks pending receipt.
sstat_primary - This is information on the current primary peer address.
sstat_assoc_id - (UDP style socket) This holds the an identifier for the association. All
notifications for a given association have the same association
identifier.

sstat_instrms - The number of streams that the peer will be using inbound.

sstat_outstrms - The number of streams that the endpoint is allowed to use outbound.

sstat_fragmentation_point - The size at which SCTP fragmentation will occur.

To access these status values, the application calls getsockopt() with the option name
SCTP_STATUS. The sstat_assoc_id parameter is ignored for TCP style socket.

B.2.2 Peer Address Information (SCTP_GET_PEER_ADDR_INFO)

Applications can retrieve information about a specific peer address of an association,


including its reachability state, congestion window, and retransmission timer values. This
information is read-only. The following structure is used to access this information:

struct sctp_paddrinfo {
sctp_assoc_t spinfo_assoc_id;
struct sockaddr_storage spinfo_address;
int32_t spinfo_state;
uint32_t spinfo_cwnd;
uint32_t spinfo_srtt;
uint32_t spinfo_rto;
uint32_t spinfo_mtu;
};
DOCUMENTTYPE 52 (52)

TypeUnitOrDepartmentHere
TypeYourNameHere TypeDateHere

spinfo_address - This is filled in the application, and contains the peer address of
interest.

On return from getsockopt():

spinfo_state - This contains the peer addresses's state (either SCTP_ACTIVE or


SCTP_INACTIVE).
spinfo_cwnd - This contains the peer addresses's current congestion window.
spinfo_srtt - This contains the peer addresses's current smoothed round-trip time
calculation in milliseconds.
spinfo_rto - This contains the peer addresses's current retransmission timeout value
in milliseconds.
spinfo_mtu - The current P-MTU of this address.
spinfo_assoc_id - (UDP style socket) This is filled in the application, and identifies the
association for this query.

You might also like