Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
L
linux
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
Kirill Smelkov
linux
Commits
f8dfb3b0
Commit
f8dfb3b0
authored
Nov 08, 2002
by
Jon Grimm
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
[SCTP] Addr family cleanup part 2. (jgrimm)
Splitting out yet more code. New af and pf specific functions.
parent
d9a91e70
Changes
7
Hide whitespace changes
Inline
Side-by-side
Showing
7 changed files
with
195 additions
and
208 deletions
+195
-208
include/net/sctp/structs.h
include/net/sctp/structs.h
+7
-4
net/sctp/bind_addr.c
net/sctp/bind_addr.c
+8
-107
net/sctp/input.c
net/sctp/input.c
+2
-2
net/sctp/ipv6.c
net/sctp/ipv6.c
+74
-5
net/sctp/protocol.c
net/sctp/protocol.c
+82
-27
net/sctp/sm_make_chunk.c
net/sctp/sm_make_chunk.c
+4
-40
net/sctp/socket.c
net/sctp/socket.c
+18
-23
No files found.
include/net/sctp/structs.h
View file @
f8dfb3b0
...
@@ -2,7 +2,7 @@
...
@@ -2,7 +2,7 @@
* Copyright (c) 1999-2000 Cisco, Inc.
* Copyright (c) 1999-2000 Cisco, Inc.
* Copyright (c) 1999-2001 Motorola, Inc.
* Copyright (c) 1999-2001 Motorola, Inc.
* Copyright (c) 2001 Intel Corp.
* Copyright (c) 2001 Intel Corp.
* Copyright (c) 2001 International Business Machines Corp.
* Copyright (c) 2001
-2002
International Business Machines Corp.
*
*
* This file is part of the SCTP kernel reference Implementation
* This file is part of the SCTP kernel reference Implementation
*
*
...
@@ -257,6 +257,8 @@ typedef struct sctp_func {
...
@@ -257,6 +257,8 @@ typedef struct sctp_func {
void
(
*
from_skb
)
(
union
sctp_addr
*
,
void
(
*
from_skb
)
(
union
sctp_addr
*
,
struct
sk_buff
*
skb
,
struct
sk_buff
*
skb
,
int
saddr
);
int
saddr
);
int
(
*
addr_valid
)
(
union
sctp_addr
*
);
sctp_scope_t
(
*
scope
)
(
union
sctp_addr
*
);
__u16
net_header_len
;
__u16
net_header_len
;
int
sockaddr_len
;
int
sockaddr_len
;
sa_family_t
sa_family
;
sa_family_t
sa_family
;
...
@@ -269,13 +271,14 @@ sctp_func_t *sctp_get_af_specific(sa_family_t);
...
@@ -269,13 +271,14 @@ sctp_func_t *sctp_get_af_specific(sa_family_t);
typedef
struct
sctp_pf
{
typedef
struct
sctp_pf
{
void
(
*
event_msgname
)(
sctp_ulpevent_t
*
,
char
*
,
int
*
);
void
(
*
event_msgname
)(
sctp_ulpevent_t
*
,
char
*
,
int
*
);
void
(
*
skb_msgname
)(
struct
sk_buff
*
,
char
*
,
int
*
);
void
(
*
skb_msgname
)(
struct
sk_buff
*
,
char
*
,
int
*
);
int
(
*
af_supported
)(
sa_family_t
);
}
sctp_pf_t
;
}
sctp_pf_t
;
/* SCTP Socket type: UDP or TCP style. */
/* SCTP Socket type: UDP or TCP style. */
typedef
enum
{
typedef
enum
{
SCTP_SOCKET_UDP
=
0
,
SCTP_SOCKET_UDP
=
0
,
SCTP_SOCKET_UDP_HIGH_BANDWIDTH
,
SCTP_SOCKET_UDP_HIGH_BANDWIDTH
,
SCTP_SOCKET_TCP
SCTP_SOCKET_TCP
}
sctp_socket_type_t
;
}
sctp_socket_type_t
;
/* Per socket SCTP information. */
/* Per socket SCTP information. */
...
@@ -505,7 +508,7 @@ void *sctp_addto_chunk(sctp_chunk_t *chunk, int len, const void *data);
...
@@ -505,7 +508,7 @@ void *sctp_addto_chunk(sctp_chunk_t *chunk, int len, const void *data);
int
sctp_user_addto_chunk
(
sctp_chunk_t
*
chunk
,
int
len
,
struct
iovec
*
data
);
int
sctp_user_addto_chunk
(
sctp_chunk_t
*
chunk
,
int
len
,
struct
iovec
*
data
);
sctp_chunk_t
*
sctp_chunkify
(
struct
sk_buff
*
,
const
sctp_association_t
*
,
sctp_chunk_t
*
sctp_chunkify
(
struct
sk_buff
*
,
const
sctp_association_t
*
,
struct
sock
*
);
struct
sock
*
);
void
sctp_init_addrs
(
sctp_chunk_t
*
chunk
);
void
sctp_init_addrs
(
sctp_chunk_t
*
,
union
sctp_addr
*
,
union
sctp_addr
*
);
const
union
sctp_addr
*
sctp_source
(
const
sctp_chunk_t
*
chunk
);
const
union
sctp_addr
*
sctp_source
(
const
sctp_chunk_t
*
chunk
);
/* This is a structure for holding either an IPv6 or an IPv4 address. */
/* This is a structure for holding either an IPv6 or an IPv4 address. */
...
...
net/sctp/bind_addr.c
View file @
f8dfb3b0
/* SCTP kernel reference Implementation
/* SCTP kernel reference Implementation
* Copyright (c) Cisco 1999,2000
* Copyright (c) Cisco 1999,2000
* Copyright (c) Motorola 1999,2000,2001
* Copyright (c) Motorola 1999,2000,2001
* Copyright (c) International Business Machines Corp., 2001
* Copyright (c) International Business Machines Corp., 2001
,2002
* Copyright (c) La Monte H.P. Yarroll 2001
* Copyright (c) La Monte H.P. Yarroll 2001
*
*
* This file is part of the SCTP kernel reference implementation.
* This file is part of the SCTP kernel reference implementation.
...
@@ -196,7 +196,7 @@ int sctp_del_bind_addr(sctp_bind_addr_t *bp, union sctp_addr *del_addr)
...
@@ -196,7 +196,7 @@ int sctp_del_bind_addr(sctp_bind_addr_t *bp, union sctp_addr *del_addr)
*
*
* The second argument is the return value for the length.
* The second argument is the return value for the length.
*/
*/
union
sctp_params
sctp_bind_addrs_to_raw
(
const
sctp_bind_addr_t
*
bp
,
union
sctp_params
sctp_bind_addrs_to_raw
(
const
sctp_bind_addr_t
*
bp
,
int
*
addrs_len
,
int
priority
)
int
*
addrs_len
,
int
priority
)
{
{
union
sctp_params
addrparms
;
union
sctp_params
addrparms
;
...
@@ -252,7 +252,7 @@ int sctp_raw_to_bind_addrs(sctp_bind_addr_t *bp, __u8 *raw_addr_list,
...
@@ -252,7 +252,7 @@ int sctp_raw_to_bind_addrs(sctp_bind_addr_t *bp, __u8 *raw_addr_list,
rawaddr
=
(
sctp_addr_param_t
*
)
raw_addr_list
;
rawaddr
=
(
sctp_addr_param_t
*
)
raw_addr_list
;
switch
(
param
->
type
)
{
switch
(
param
->
type
)
{
case
SCTP_PARAM_IPV4_ADDRESS
:
case
SCTP_PARAM_IPV4_ADDRESS
:
case
SCTP_PARAM_IPV6_ADDRESS
:
case
SCTP_PARAM_IPV6_ADDRESS
:
sctp_param2sockaddr
(
&
addr
,
rawaddr
,
port
);
sctp_param2sockaddr
(
&
addr
,
rawaddr
,
port
);
retval
=
sctp_add_bind_addr
(
bp
,
&
addr
,
priority
);
retval
=
sctp_add_bind_addr
(
bp
,
&
addr
,
priority
);
...
@@ -422,110 +422,11 @@ int sctp_in_scope(const union sctp_addr *addr, sctp_scope_t scope)
...
@@ -422,110 +422,11 @@ int sctp_in_scope(const union sctp_addr *addr, sctp_scope_t scope)
/* What is the scope of 'addr'? */
/* What is the scope of 'addr'? */
sctp_scope_t
sctp_scope
(
const
union
sctp_addr
*
addr
)
sctp_scope_t
sctp_scope
(
const
union
sctp_addr
*
addr
)
{
{
s
ctp_scope_t
retval
=
SCTP_SCOPE_GLOBAL
;
s
truct
sctp_func
*
af
;
switch
(
addr
->
sa
.
sa_family
)
{
af
=
sctp_get_af_specific
(
addr
->
sa
.
sa_family
);
case
AF_INET
:
if
(
!
af
)
/* We are checking the loopback, private and other address
return
SCTP_SCOPE_UNUSABLE
;
* scopes as defined in RFC 1918.
* The IPv4 scoping is based on the draft for SCTP IPv4
* scoping <draft-stewart-tsvwg-sctp-ipv4-00.txt>.
* The set of SCTP address scope hopefully can cover both
* types of addresses.
*/
/* Should IPv4 scoping be a sysctl configurable option
* so users can turn it off (default on) for certain
* unconventional networking environments?
*/
/* Check for unusable SCTP addresses. */
if
(
IS_IPV4_UNUSABLE_ADDRESS
(
&
addr
->
v4
.
sin_addr
.
s_addr
))
{
retval
=
SCTP_SCOPE_UNUSABLE
;
}
else
if
(
LOOPBACK
(
addr
->
v4
.
sin_addr
.
s_addr
))
{
retval
=
SCTP_SCOPE_LOOPBACK
;
}
else
if
(
IS_IPV4_LINK_ADDRESS
(
&
addr
->
v4
.
sin_addr
.
s_addr
))
{
retval
=
SCTP_SCOPE_LINK
;
}
else
if
(
IS_IPV4_PRIVATE_ADDRESS
(
&
addr
->
v4
.
sin_addr
.
s_addr
))
{
retval
=
SCTP_SCOPE_PRIVATE
;
}
else
{
retval
=
SCTP_SCOPE_GLOBAL
;
}
break
;
case
AF_INET6
:
{
SCTP_V6
(
int
v6scope
;
v6scope
=
ipv6_addr_scope
((
struct
in6_addr
*
)
&
addr
->
v6
.
sin6_addr
);
/* The IPv6 scope is really a set of bit
* fields. See IFA_* in <net/if_inet6.h>.
* Mapping them to the generic SCTP scope
* set is an attempt to have code
* consistencies with the IPv4 scoping.
*/
switch
(
v6scope
)
{
case
IFA_HOST
:
retval
=
SCTP_SCOPE_LOOPBACK
;
break
;
case
IFA_LINK
:
retval
=
SCTP_SCOPE_LINK
;
break
;
case
IFA_SITE
:
retval
=
SCTP_SCOPE_PRIVATE
;
break
;
default:
retval
=
SCTP_SCOPE_GLOBAL
;
break
;
};
);
break
;
}
default:
retval
=
SCTP_SCOPE_GLOBAL
;
break
;
};
return
retval
;
}
/* This function checks if the address is a valid address to be used for
* SCTP.
*
* Output:
* Return 0 - If the address is a non-unicast or an illegal address.
* Return 1 - If the address is a unicast.
*/
int
sctp_addr_is_valid
(
const
union
sctp_addr
*
addr
)
{
unsigned
short
sa_family
=
addr
->
sa
.
sa_family
;
switch
(
sa_family
)
{
case
AF_INET
:
/* Is this a non-unicast address or a unusable SCTP address? */
if
(
IS_IPV4_UNUSABLE_ADDRESS
(
&
addr
->
v4
.
sin_addr
.
s_addr
))
return
0
;
break
;
case
AF_INET6
:
SCTP_V6
(
{
int
ret
=
sctp_ipv6_addr_type
(
&
addr
->
v6
.
sin6_addr
);
/* Is this a non-unicast address */
if
(
!
(
ret
&
IPV6_ADDR_UNICAST
))
return
0
;
break
;
});
default:
return
0
;
};
return
1
;
return
af
->
scope
((
union
sctp_addr
*
)
addr
)
;
}
}
net/sctp/input.c
View file @
f8dfb3b0
...
@@ -132,7 +132,7 @@ int sctp_rcv(struct sk_buff *skb)
...
@@ -132,7 +132,7 @@ int sctp_rcv(struct sk_buff *skb)
* IP broadcast addresses cannot be used in an SCTP transport
* IP broadcast addresses cannot be used in an SCTP transport
* address."
* address."
*/
*/
if
(
!
sctp_addr_is_valid
(
&
src
)
||
!
sctp_addr_is
_valid
(
&
dest
))
if
(
!
af
->
addr_valid
(
&
src
)
||
!
af
->
addr
_valid
(
&
dest
))
goto
discard_it
;
goto
discard_it
;
asoc
=
__sctp_rcv_lookup
(
skb
,
&
src
,
&
dest
,
&
transport
);
asoc
=
__sctp_rcv_lookup
(
skb
,
&
src
,
&
dest
,
&
transport
);
...
@@ -172,7 +172,7 @@ int sctp_rcv(struct sk_buff *skb)
...
@@ -172,7 +172,7 @@ int sctp_rcv(struct sk_buff *skb)
chunk
->
sctp_hdr
=
sh
;
chunk
->
sctp_hdr
=
sh
;
/* Set the source and destination addresses of the incoming chunk. */
/* Set the source and destination addresses of the incoming chunk. */
sctp_init_addrs
(
chunk
);
sctp_init_addrs
(
chunk
,
&
src
,
&
dest
);
/* Remember where we came from. */
/* Remember where we came from. */
chunk
->
transport
=
transport
;
chunk
->
transport
=
transport
;
...
...
net/sctp/ipv6.c
View file @
f8dfb3b0
...
@@ -181,7 +181,7 @@ struct dst_entry *sctp_v6_get_dst(union sctp_addr *daddr,
...
@@ -181,7 +181,7 @@ struct dst_entry *sctp_v6_get_dst(union sctp_addr *daddr,
SCTP_DEBUG_PRINTK
(
"%s: DST=%04x:%04x:%04x:%04x:%04x:%04x:%04x:%04x "
,
SCTP_DEBUG_PRINTK
(
"%s: DST=%04x:%04x:%04x:%04x:%04x:%04x:%04x:%04x "
,
__FUNCTION__
,
NIP6
(
fl
.
fl6_dst
));
__FUNCTION__
,
NIP6
(
fl
.
fl6_dst
));
if
(
saddr
)
{
if
(
saddr
)
{
fl
.
fl6_src
=
&
saddr
->
v6
.
sin6_addr
;
fl
.
fl6_src
=
&
saddr
->
v6
.
sin6_addr
;
...
@@ -249,7 +249,7 @@ static void sctp_v6_from_skb(union sctp_addr *addr,struct sk_buff *skb,
...
@@ -249,7 +249,7 @@ static void sctp_v6_from_skb(union sctp_addr *addr,struct sk_buff *skb,
addr
->
v6
.
sin6_family
=
AF_INET6
;
addr
->
v6
.
sin6_family
=
AF_INET6
;
addr
->
v6
.
sin6_flowinfo
=
0
;
/* FIXME */
addr
->
v6
.
sin6_flowinfo
=
0
;
/* FIXME */
addr
->
v6
.
sin6_scope_id
=
0
;
/* FIXME */
addr
->
v6
.
sin6_scope_id
=
0
;
/* FIXME */
sh
=
(
struct
sctphdr
*
)
skb
->
h
.
raw
;
sh
=
(
struct
sctphdr
*
)
skb
->
h
.
raw
;
if
(
is_saddr
)
{
if
(
is_saddr
)
{
*
port
=
ntohs
(
sh
->
source
);
*
port
=
ntohs
(
sh
->
source
);
...
@@ -262,11 +262,60 @@ static void sctp_v6_from_skb(union sctp_addr *addr,struct sk_buff *skb,
...
@@ -262,11 +262,60 @@ static void sctp_v6_from_skb(union sctp_addr *addr,struct sk_buff *skb,
}
}
/* Check if the dst entry's source addr matches the given source addr. */
/* Check if the dst entry's source addr matches the given source addr. */
int
sctp_v6_cmp_saddr
(
struct
dst_entry
*
dst
,
union
sctp_addr
*
saddr
)
static
int
sctp_v6_cmp_saddr
(
struct
dst_entry
*
dst
,
union
sctp_addr
*
saddr
)
{
{
struct
rt6_info
*
rt
=
(
struct
rt6_info
*
)
dst
;
struct
rt6_info
*
rt
=
(
struct
rt6_info
*
)
dst
;
return
ipv6_addr_cmp
(
&
rt
->
rt6i_src
.
addr
,
&
saddr
->
v6
.
sin6_addr
);
return
ipv6_addr_cmp
(
&
rt
->
rt6i_src
.
addr
,
&
saddr
->
v6
.
sin6_addr
);
}
/* This function checks if the address is a valid address to be used for
* SCTP.
*
* Output:
* Return 0 - If the address is a non-unicast or an illegal address.
* Return 1 - If the address is a unicast.
*/
static
int
sctp_v6_addr_valid
(
union
sctp_addr
*
addr
)
{
int
ret
=
sctp_ipv6_addr_type
(
&
addr
->
v6
.
sin6_addr
);
/* FIXME: v4-mapped-v6 address support. */
/* Is this a non-unicast address */
if
(
!
(
ret
&
IPV6_ADDR_UNICAST
))
return
0
;
return
1
;
}
/* What is the scope of 'addr'? */
static
sctp_scope_t
sctp_v6_scope
(
union
sctp_addr
*
addr
)
{
int
v6scope
;
sctp_scope_t
retval
;
/* The IPv6 scope is really a set of bit fields.
* See IFA_* in <net/if_inet6.h>. Map to a generic SCTP scope.
*/
v6scope
=
ipv6_addr_scope
(
&
addr
->
v6
.
sin6_addr
);
switch
(
v6scope
)
{
case
IFA_HOST
:
retval
=
SCTP_SCOPE_LOOPBACK
;
break
;
case
IFA_LINK
:
retval
=
SCTP_SCOPE_LINK
;
break
;
case
IFA_SITE
:
retval
=
SCTP_SCOPE_PRIVATE
;
break
;
default:
retval
=
SCTP_SCOPE_GLOBAL
;
break
;
};
return
retval
;
}
}
/* Initialize a PF_INET6 socket msg_name. */
/* Initialize a PF_INET6 socket msg_name. */
...
@@ -282,7 +331,7 @@ static void sctp_inet6_msgname(char *msgname, int *addr_len)
...
@@ -282,7 +331,7 @@ static void sctp_inet6_msgname(char *msgname, int *addr_len)
}
}
/* Initialize a PF_INET msgname from a ulpevent. */
/* Initialize a PF_INET msgname from a ulpevent. */
static
void
sctp_inet6_event_msgname
(
sctp_ulpevent_t
*
event
,
char
*
msgname
,
static
void
sctp_inet6_event_msgname
(
sctp_ulpevent_t
*
event
,
char
*
msgname
,
int
*
addrlen
)
int
*
addrlen
)
{
{
struct
sockaddr_in6
*
sin6
,
*
sin6from
;
struct
sockaddr_in6
*
sin6
,
*
sin6from
;
...
@@ -344,6 +393,23 @@ static void sctp_inet6_skb_msgname(struct sk_buff *skb, char *msgname,
...
@@ -344,6 +393,23 @@ static void sctp_inet6_skb_msgname(struct sk_buff *skb, char *msgname,
}
}
}
}
/* Do we support this AF? */
static
int
sctp_inet6_af_supported
(
sa_family_t
family
)
{
/* FIXME: v4-mapped-v6 addresses. The I-D is still waffling
* on what to do with sockaddr formats for PF_INET6 sockets.
* For now assume we'll support both.
*/
switch
(
family
)
{
case
AF_INET6
:
case
AF_INET
:
return
1
;
default:
return
0
;
}
}
static
struct
proto_ops
inet6_seqpacket_ops
=
{
static
struct
proto_ops
inet6_seqpacket_ops
=
{
.
family
=
PF_INET6
,
.
family
=
PF_INET6
,
.
release
=
inet6_release
,
.
release
=
inet6_release
,
...
@@ -386,6 +452,8 @@ static sctp_func_t sctp_ipv6_specific = {
...
@@ -386,6 +452,8 @@ static sctp_func_t sctp_ipv6_specific = {
.
copy_addrlist
=
sctp_v6_copy_addrlist
,
.
copy_addrlist
=
sctp_v6_copy_addrlist
,
.
from_skb
=
sctp_v6_from_skb
,
.
from_skb
=
sctp_v6_from_skb
,
.
cmp_saddr
=
sctp_v6_cmp_saddr
,
.
cmp_saddr
=
sctp_v6_cmp_saddr
,
.
scope
=
sctp_v6_scope
,
.
addr_valid
=
sctp_v6_addr_valid
,
.
net_header_len
=
sizeof
(
struct
ipv6hdr
),
.
net_header_len
=
sizeof
(
struct
ipv6hdr
),
.
sockaddr_len
=
sizeof
(
struct
sockaddr_in6
),
.
sockaddr_len
=
sizeof
(
struct
sockaddr_in6
),
.
sa_family
=
AF_INET6
,
.
sa_family
=
AF_INET6
,
...
@@ -394,6 +462,7 @@ static sctp_func_t sctp_ipv6_specific = {
...
@@ -394,6 +462,7 @@ static sctp_func_t sctp_ipv6_specific = {
static
sctp_pf_t
sctp_pf_inet6_specific
=
{
static
sctp_pf_t
sctp_pf_inet6_specific
=
{
.
event_msgname
=
sctp_inet6_event_msgname
,
.
event_msgname
=
sctp_inet6_event_msgname
,
.
skb_msgname
=
sctp_inet6_skb_msgname
,
.
skb_msgname
=
sctp_inet6_skb_msgname
,
.
af_supported
=
sctp_inet6_af_supported
,
};
};
/* Initialize IPv6 support and register with inet6 stack. */
/* Initialize IPv6 support and register with inet6 stack. */
...
...
net/sctp/protocol.c
View file @
f8dfb3b0
...
@@ -5,42 +5,42 @@
...
@@ -5,42 +5,42 @@
* Copyright (c) 2001 Intel Corp.
* Copyright (c) 2001 Intel Corp.
* Copyright (c) 2001 Nokia, Inc.
* Copyright (c) 2001 Nokia, Inc.
* Copyright (c) 2001 La Monte H.P. Yarroll
* Copyright (c) 2001 La Monte H.P. Yarroll
*
*
* This file is part of the SCTP kernel reference Implementation
* This file is part of the SCTP kernel reference Implementation
*
*
* Initialization/cleanup for SCTP protocol support.
* Initialization/cleanup for SCTP protocol support.
*
*
* The SCTP reference implementation is free software;
* The SCTP reference implementation is free software;
* you can redistribute it and/or modify it under the terms of
* you can redistribute it and/or modify it under the terms of
* the GNU General Public License as published by
* the GNU General Public License as published by
* the Free Software Foundation; either version 2, or (at your option)
* the Free Software Foundation; either version 2, or (at your option)
* any later version.
* any later version.
*
*
* The SCTP reference implementation is distributed in the hope that it
* The SCTP reference implementation is distributed in the hope that it
* will be useful, but WITHOUT ANY WARRANTY; without even the implied
* will be useful, but WITHOUT ANY WARRANTY; without even the implied
* ************************
* ************************
* warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU General Public License for more details.
* See the GNU General Public License for more details.
*
*
* You should have received a copy of the GNU General Public License
* You should have received a copy of the GNU General Public License
* along with GNU CC; see the file COPYING. If not, write to
* along with GNU CC; see the file COPYING. If not, write to
* the Free Software Foundation, 59 Temple Place - Suite 330,
* the Free Software Foundation, 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
* Boston, MA 02111-1307, USA.
*
*
* Please send any bug reports or fixes you make to the
* Please send any bug reports or fixes you make to the
* email address(es):
* email address(es):
* lksctp developers <lksctp-developers@lists.sourceforge.net>
* lksctp developers <lksctp-developers@lists.sourceforge.net>
*
*
* Or submit a bug report through the following website:
* Or submit a bug report through the following website:
* http://www.sf.net/projects/lksctp
* http://www.sf.net/projects/lksctp
*
*
* Written or modified by:
* Written or modified by:
* La Monte H.P. Yarroll <piggy@acm.org>
* La Monte H.P. Yarroll <piggy@acm.org>
* Karl Knutson <karl@athena.chicago.il.us>
* Karl Knutson <karl@athena.chicago.il.us>
* Jon Grimm <jgrimm@us.ibm.com>
* Jon Grimm <jgrimm@us.ibm.com>
* Sridhar Samudrala <sri@us.ibm.com>
* Sridhar Samudrala <sri@us.ibm.com>
* Daisy Chang <daisyc@us.ibm.com>
* Daisy Chang <daisyc@us.ibm.com>
*
*
* Any bugs reported given to us we will try to fix... any fixes shared will
* Any bugs reported given to us we will try to fix... any fixes shared will
* be incorporated into the next SCTP release.
* be incorporated into the next SCTP release.
*/
*/
...
@@ -103,7 +103,7 @@ void sctp_proc_exit(void)
...
@@ -103,7 +103,7 @@ void sctp_proc_exit(void)
/* Private helper to extract ipv4 address and stash them in
/* Private helper to extract ipv4 address and stash them in
* the protocol structure.
* the protocol structure.
*/
*/
static
void
sctp_v4_copy_addrlist
(
struct
list_head
*
addrlist
,
static
void
sctp_v4_copy_addrlist
(
struct
list_head
*
addrlist
,
struct
net_device
*
dev
)
struct
net_device
*
dev
)
{
{
struct
in_device
*
in_dev
;
struct
in_device
*
in_dev
;
...
@@ -227,10 +227,10 @@ struct dst_entry *sctp_v4_get_dst(union sctp_addr *daddr,
...
@@ -227,10 +227,10 @@ struct dst_entry *sctp_v4_get_dst(union sctp_addr *daddr,
union
sctp_addr
*
saddr
)
union
sctp_addr
*
saddr
)
{
{
struct
rtable
*
rt
;
struct
rtable
*
rt
;
struct
flowi
fl
=
{
struct
flowi
fl
=
{
.
nl_u
=
{
.
nl_u
=
{
.
ip4_u
=
{
.
daddr
=
.
ip4_u
=
{
.
daddr
=
daddr
->
v4
.
sin_addr
.
s_addr
,
}},
daddr
->
v4
.
sin_addr
.
s_addr
,
}},
.
proto
=
IPPROTO_SCTP
,
.
proto
=
IPPROTO_SCTP
,
};
};
...
@@ -280,7 +280,52 @@ int sctp_v4_cmp_saddr(struct dst_entry *dst, union sctp_addr *saddr)
...
@@ -280,7 +280,52 @@ int sctp_v4_cmp_saddr(struct dst_entry *dst, union sctp_addr *saddr)
{
{
struct
rtable
*
rt
=
(
struct
rtable
*
)
dst
;
struct
rtable
*
rt
=
(
struct
rtable
*
)
dst
;
return
(
rt
->
rt_src
==
saddr
->
v4
.
sin_addr
.
s_addr
);
return
(
rt
->
rt_src
==
saddr
->
v4
.
sin_addr
.
s_addr
);
}
/* This function checks if the address is a valid address to be used for
* SCTP.
*
* Output:
* Return 0 - If the address is a non-unicast or an illegal address.
* Return 1 - If the address is a unicast.
*/
static
int
sctp_v4_addr_valid
(
union
sctp_addr
*
addr
)
{
/* Is this a non-unicast address or a unusable SCTP address? */
if
(
IS_IPV4_UNUSABLE_ADDRESS
(
&
addr
->
v4
.
sin_addr
.
s_addr
))
return
0
;
return
1
;
}
/* Checking the loopback, private and other address scopes as defined in
* RFC 1918. The IPv4 scoping is based on the draft for SCTP IPv4
* scoping <draft-stewart-tsvwg-sctp-ipv4-00.txt>.
*/
static
sctp_scope_t
sctp_v4_scope
(
union
sctp_addr
*
addr
)
{
sctp_scope_t
retval
;
/* Should IPv4 scoping be a sysctl configurable option
* so users can turn it off (default on) for certain
* unconventional networking environments?
*/
/* Check for unusable SCTP addresses. */
if
(
IS_IPV4_UNUSABLE_ADDRESS
(
&
addr
->
v4
.
sin_addr
.
s_addr
))
{
retval
=
SCTP_SCOPE_UNUSABLE
;
}
else
if
(
LOOPBACK
(
addr
->
v4
.
sin_addr
.
s_addr
))
{
retval
=
SCTP_SCOPE_LOOPBACK
;
}
else
if
(
IS_IPV4_LINK_ADDRESS
(
&
addr
->
v4
.
sin_addr
.
s_addr
))
{
retval
=
SCTP_SCOPE_LINK
;
}
else
if
(
IS_IPV4_PRIVATE_ADDRESS
(
&
addr
->
v4
.
sin_addr
.
s_addr
))
{
retval
=
SCTP_SCOPE_PRIVATE
;
}
else
{
retval
=
SCTP_SCOPE_GLOBAL
;
}
return
retval
;
}
}
/* Event handler for inet device events.
/* Event handler for inet device events.
...
@@ -352,13 +397,13 @@ sctp_func_t *sctp_get_af_specific(sa_family_t family)
...
@@ -352,13 +397,13 @@ sctp_func_t *sctp_get_af_specific(sa_family_t family)
static
void
sctp_inet_msgname
(
char
*
msgname
,
int
*
addr_len
)
static
void
sctp_inet_msgname
(
char
*
msgname
,
int
*
addr_len
)
{
{
struct
sockaddr_in
*
sin
;
struct
sockaddr_in
*
sin
;
sin
=
(
struct
sockaddr_in
*
)
msgname
;
sin
=
(
struct
sockaddr_in
*
)
msgname
;
*
addr_len
=
sizeof
(
struct
sockaddr_in
);
*
addr_len
=
sizeof
(
struct
sockaddr_in
);
sin
->
sin_family
=
AF_INET
;
sin
->
sin_family
=
AF_INET
;
memset
(
sin
->
sin_zero
,
0
,
sizeof
(
sin
->
sin_zero
));
memset
(
sin
->
sin_zero
,
0
,
sizeof
(
sin
->
sin_zero
));
}
}
/* Copy the primary address of the peer primary address as the msg_name. */
/* Copy the primary address of the peer primary address as the msg_name. */
static
void
sctp_inet_event_msgname
(
sctp_ulpevent_t
*
event
,
char
*
msgname
,
int
*
addr_len
)
static
void
sctp_inet_event_msgname
(
sctp_ulpevent_t
*
event
,
char
*
msgname
,
int
*
addr_len
)
{
{
...
@@ -371,26 +416,34 @@ static void sctp_inet_event_msgname(sctp_ulpevent_t *event, char *msgname, int *
...
@@ -371,26 +416,34 @@ static void sctp_inet_event_msgname(sctp_ulpevent_t *event, char *msgname, int *
sin
->
sin_port
=
htons
(
event
->
asoc
->
peer
.
port
);
sin
->
sin_port
=
htons
(
event
->
asoc
->
peer
.
port
);
sin
->
sin_addr
.
s_addr
=
sinfrom
->
sin_addr
.
s_addr
;
sin
->
sin_addr
.
s_addr
=
sinfrom
->
sin_addr
.
s_addr
;
}
}
}
}
/* Initialize and copy out a msgname from an inbound skb. */
/* Initialize and copy out a msgname from an inbound skb. */
static
void
sctp_inet_skb_msgname
(
struct
sk_buff
*
skb
,
char
*
msgname
,
int
*
addr_
len
)
static
void
sctp_inet_skb_msgname
(
struct
sk_buff
*
skb
,
char
*
msgname
,
int
*
len
)
{
{
struct
sctphdr
*
sh
;
struct
sctphdr
*
sh
;
struct
sockaddr_in
*
sin
;
struct
sockaddr_in
*
sin
;
if
(
msgname
)
{
if
(
msgname
)
{
sctp_inet_msgname
(
msgname
,
addr_
len
);
sctp_inet_msgname
(
msgname
,
len
);
sin
=
(
struct
sockaddr_in
*
)
msgname
;
sin
=
(
struct
sockaddr_in
*
)
msgname
;
sh
=
(
struct
sctphdr
*
)
skb
->
h
.
raw
;
sh
=
(
struct
sctphdr
*
)
skb
->
h
.
raw
;
sin
->
sin_port
=
sh
->
source
;
sin
->
sin_port
=
sh
->
source
;
sin
->
sin_addr
.
s_addr
=
skb
->
nh
.
iph
->
saddr
;
sin
->
sin_addr
.
s_addr
=
skb
->
nh
.
iph
->
saddr
;
}
}
}
}
/* Do we support this AF? */
static
int
sctp_inet_af_supported
(
sa_family_t
family
)
{
/* PF_INET only supports AF_INET addresses. */
return
(
AF_INET
==
family
);
}
static
sctp_pf_t
sctp_pf_inet
=
{
static
sctp_pf_t
sctp_pf_inet
=
{
.
event_msgname
=
sctp_inet_event_msgname
,
.
event_msgname
=
sctp_inet_event_msgname
,
.
skb_msgname
=
sctp_inet_skb_msgname
,
.
skb_msgname
=
sctp_inet_skb_msgname
,
.
af_supported
=
sctp_inet_af_supported
,
};
};
...
@@ -446,6 +499,8 @@ struct sctp_func sctp_ipv4_specific = {
...
@@ -446,6 +499,8 @@ struct sctp_func sctp_ipv4_specific = {
.
copy_addrlist
=
sctp_v4_copy_addrlist
,
.
copy_addrlist
=
sctp_v4_copy_addrlist
,
.
from_skb
=
sctp_v4_from_skb
,
.
from_skb
=
sctp_v4_from_skb
,
.
cmp_saddr
=
sctp_v4_cmp_saddr
,
.
cmp_saddr
=
sctp_v4_cmp_saddr
,
.
addr_valid
=
sctp_v4_addr_valid
,
.
scope
=
sctp_v4_scope
,
.
net_header_len
=
sizeof
(
struct
iphdr
),
.
net_header_len
=
sizeof
(
struct
iphdr
),
.
sockaddr_len
=
sizeof
(
struct
sockaddr_in
),
.
sockaddr_len
=
sizeof
(
struct
sockaddr_in
),
.
sa_family
=
AF_INET
,
.
sa_family
=
AF_INET
,
...
...
net/sctp/sm_make_chunk.c
View file @
f8dfb3b0
...
@@ -1031,47 +1031,11 @@ sctp_chunk_t *sctp_chunkify(struct sk_buff *skb, const sctp_association_t *asoc,
...
@@ -1031,47 +1031,11 @@ sctp_chunk_t *sctp_chunkify(struct sk_buff *skb, const sctp_association_t *asoc,
}
}
/* Set chunk->source and dest based on the IP header in chunk->skb. */
/* Set chunk->source and dest based on the IP header in chunk->skb. */
void
sctp_init_addrs
(
sctp_chunk_t
*
chunk
)
void
sctp_init_addrs
(
sctp_chunk_t
*
chunk
,
union
sctp_addr
*
src
,
union
sctp_addr
*
dest
)
{
{
union
sctp_addr
*
source
,
*
dest
;
memcpy
(
&
chunk
->
source
,
src
,
sizeof
(
union
sctp_addr
));
struct
sk_buff
*
skb
;
memcpy
(
&
chunk
->
dest
,
dest
,
sizeof
(
union
sctp_addr
));
struct
sctphdr
*
sh
;
struct
iphdr
*
ih4
;
struct
ipv6hdr
*
ih6
;
source
=
&
chunk
->
source
;
dest
=
&
chunk
->
dest
;
skb
=
chunk
->
skb
;
ih4
=
skb
->
nh
.
iph
;
ih6
=
skb
->
nh
.
ipv6h
;
sh
=
chunk
->
sctp_hdr
;
switch
(
ih4
->
version
)
{
case
4
:
source
->
v4
.
sin_family
=
AF_INET
;
source
->
v4
.
sin_port
=
ntohs
(
sh
->
source
);
source
->
v4
.
sin_addr
.
s_addr
=
ih4
->
saddr
;
dest
->
v4
.
sin_family
=
AF_INET
;
dest
->
v4
.
sin_port
=
ntohs
(
sh
->
dest
);
dest
->
v4
.
sin_addr
.
s_addr
=
ih4
->
daddr
;
break
;
case
6
:
SCTP_V6
(
source
->
v6
.
sin6_family
=
AF_INET6
;
source
->
v6
.
sin6_port
=
ntohs
(
sh
->
source
);
source
->
v6
.
sin6_addr
=
ih6
->
saddr
;
dest
->
v6
.
sin6_family
=
AF_INET6
;
dest
->
v6
.
sin6_port
=
ntohs
(
sh
->
dest
);
dest
->
v6
.
sin6_addr
=
ih6
->
daddr
;
/* FIXME: What do we do with scope, etc. ? */
break
;
)
default:
/* This is a bogus address type, just bail. */
break
;
};
}
}
/* Extract the source address from a chunk. */
/* Extract the source address from a chunk. */
...
...
net/sctp/socket.c
View file @
f8dfb3b0
...
@@ -2691,38 +2691,33 @@ static struct sk_buff *sctp_skb_recv_datagram(struct sock *sk, int flags, int no
...
@@ -2691,38 +2691,33 @@ static struct sk_buff *sctp_skb_recv_datagram(struct sock *sk, int flags, int no
return
NULL
;
return
NULL
;
}
}
static
inline
int
sctp_verify_addr
(
struct
sock
*
sk
,
struct
sockaddr
*
addr
,
int
addrlen
)
/* Verify that this is a valid address. */
static
int
sctp_verify_addr
(
struct
sock
*
sk
,
struct
sockaddr
*
addr
,
int
len
)
{
{
union
sctp_addr
*
sa
;
struct
sctp_func
*
af
;
if
(
addrlen
<
sizeof
(
struct
sockaddr
))
/* Check minimum size. */
if
(
len
<
sizeof
(
struct
sockaddr
))
return
-
EINVAL
;
return
-
EINVAL
;
sa
=
(
union
sctp_addr
*
)
addr
;
/* Do we support this address family in general? */
switch
(
sa
->
sa
.
sa_family
)
{
af
=
sctp_get_af_specific
(
addr
->
sa_family
);
case
AF_INET
:
if
(
!
af
)
if
(
addrlen
<
sizeof
(
struct
sockaddr_in
))
return
-
EINVAL
;
return
-
EINVAL
;
break
;
case
AF_INET6
:
if
(
PF_INET
==
sk
->
family
)
return
-
EINVAL
;
SCTP_V6
(
if
(
addrlen
<
sizeof
(
struct
sockaddr_in6
))
return
-
EINVAL
;
break
;
);
default:
/* Does this PF support this AF? */
if
(
!
sctp_sk
(
sk
)
->
pf
->
af_supported
(
addr
->
sa_family
))
return
-
EINVAL
;
/* Verify the minimum for this AF sockaddr. */
if
(
len
<
af
->
sockaddr_len
)
return
-
EINVAL
;
return
-
EINVAL
;
};
/*
Disallow any illegal addresses to be used as destinations.
*/
/*
Is this a valid SCTP address?
*/
if
(
!
sctp_addr_is_valid
(
sa
))
if
(
!
af
->
addr_valid
((
union
sctp_addr
*
)
addr
))
return
-
EINVAL
;
return
-
EINVAL
;
return
0
;
return
0
;
}
}
/* Get the sndbuf space available at the time on the association. */
/* Get the sndbuf space available at the time on the association. */
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment