Commit 3ff547c0 authored by Xin Long's avatar Xin Long Committed by David S. Miller

sctp: add support for SCTP AUTH Information for sendmsg

This patch is to add support for SCTP AUTH Information for sendmsg,
as described in section 5.3.8 of RFC6458.

With this option, you can provide shared key identifier used for
sending the user message.

It's also a necessary send info for sctp_sendv.

Note that it reuses sinfo->sinfo_tsn to indicate if this option is
set and sinfo->sinfo_ssn to save the shkey ID which can be 0.
Signed-off-by: default avatarXin Long <lucien.xin@gmail.com>
Acked-by: default avatarMarcelo Ricardo Leitner <marcelo.leitner@gmail.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 1b1e0bc9
...@@ -2118,6 +2118,7 @@ struct sctp_cmsgs { ...@@ -2118,6 +2118,7 @@ struct sctp_cmsgs {
struct sctp_sndrcvinfo *srinfo; struct sctp_sndrcvinfo *srinfo;
struct sctp_sndinfo *sinfo; struct sctp_sndinfo *sinfo;
struct sctp_prinfo *prinfo; struct sctp_prinfo *prinfo;
struct sctp_authinfo *authinfo;
struct msghdr *addrs_msg; struct msghdr *addrs_msg;
}; };
......
...@@ -273,6 +273,18 @@ struct sctp_prinfo { ...@@ -273,6 +273,18 @@ struct sctp_prinfo {
__u32 pr_value; __u32 pr_value;
}; };
/* 5.3.8 SCTP AUTH Information Structure (SCTP_AUTHINFO)
*
* This cmsghdr structure specifies SCTP options for sendmsg().
*
* cmsg_level cmsg_type cmsg_data[]
* ------------ ------------ -------------------
* IPPROTO_SCTP SCTP_AUTHINFO struct sctp_authinfo
*/
struct sctp_authinfo {
__u16 auth_keynumber;
};
/* /*
* sinfo_flags: 16 bits (unsigned integer) * sinfo_flags: 16 bits (unsigned integer)
* *
...@@ -310,7 +322,7 @@ typedef enum sctp_cmsg_type { ...@@ -310,7 +322,7 @@ typedef enum sctp_cmsg_type {
#define SCTP_NXTINFO SCTP_NXTINFO #define SCTP_NXTINFO SCTP_NXTINFO
SCTP_PRINFO, /* 5.3.7 SCTP PR-SCTP Information Structure */ SCTP_PRINFO, /* 5.3.7 SCTP PR-SCTP Information Structure */
#define SCTP_PRINFO SCTP_PRINFO #define SCTP_PRINFO SCTP_PRINFO
SCTP_AUTHINFO, /* 5.3.8 SCTP AUTH Information Structure (RESERVED) */ SCTP_AUTHINFO, /* 5.3.8 SCTP AUTH Information Structure */
#define SCTP_AUTHINFO SCTP_AUTHINFO #define SCTP_AUTHINFO SCTP_AUTHINFO
SCTP_DSTADDRV4, /* 5.3.9 SCTP Destination IPv4 Address Structure */ SCTP_DSTADDRV4, /* 5.3.9 SCTP Destination IPv4 Address Structure */
#define SCTP_DSTADDRV4 SCTP_DSTADDRV4 #define SCTP_DSTADDRV4 SCTP_DSTADDRV4
......
...@@ -206,8 +206,17 @@ struct sctp_datamsg *sctp_datamsg_from_user(struct sctp_association *asoc, ...@@ -206,8 +206,17 @@ struct sctp_datamsg *sctp_datamsg_from_user(struct sctp_association *asoc,
max_data -= SCTP_PAD4(sizeof(struct sctp_auth_chunk) + max_data -= SCTP_PAD4(sizeof(struct sctp_auth_chunk) +
hmac_desc->hmac_len); hmac_desc->hmac_len);
if (sinfo->sinfo_tsn &&
sinfo->sinfo_ssn != asoc->active_key_id) {
shkey = sctp_auth_get_shkey(asoc, sinfo->sinfo_ssn);
if (!shkey) {
err = -EINVAL;
goto errout;
}
} else {
shkey = asoc->shkey; shkey = asoc->shkey;
} }
}
/* Check what's our max considering the above */ /* Check what's our max considering the above */
max_data = min_t(size_t, max_data, asoc->frag_point); max_data = min_t(size_t, max_data, asoc->frag_point);
......
...@@ -1987,6 +1987,14 @@ static void sctp_sendmsg_update_sinfo(struct sctp_association *asoc, ...@@ -1987,6 +1987,14 @@ static void sctp_sendmsg_update_sinfo(struct sctp_association *asoc,
if (!cmsgs->srinfo && !cmsgs->prinfo) if (!cmsgs->srinfo && !cmsgs->prinfo)
sinfo->sinfo_timetolive = asoc->default_timetolive; sinfo->sinfo_timetolive = asoc->default_timetolive;
if (cmsgs->authinfo) {
/* Reuse sinfo_tsn to indicate that authinfo was set and
* sinfo_ssn to save the keyid on tx path.
*/
sinfo->sinfo_tsn = 1;
sinfo->sinfo_ssn = cmsgs->authinfo->auth_keynumber;
}
} }
static int sctp_sendmsg(struct sock *sk, struct msghdr *msg, size_t msg_len) static int sctp_sendmsg(struct sock *sk, struct msghdr *msg, size_t msg_len)
...@@ -7874,6 +7882,21 @@ static int sctp_msghdr_parse(const struct msghdr *msg, struct sctp_cmsgs *cmsgs) ...@@ -7874,6 +7882,21 @@ static int sctp_msghdr_parse(const struct msghdr *msg, struct sctp_cmsgs *cmsgs)
if (cmsgs->prinfo->pr_policy == SCTP_PR_SCTP_NONE) if (cmsgs->prinfo->pr_policy == SCTP_PR_SCTP_NONE)
cmsgs->prinfo->pr_value = 0; cmsgs->prinfo->pr_value = 0;
break; break;
case SCTP_AUTHINFO:
/* SCTP Socket API Extension
* 5.3.8 SCTP AUTH Information Structure (SCTP_AUTHINFO)
*
* This cmsghdr structure specifies SCTP options for sendmsg().
*
* cmsg_level cmsg_type cmsg_data[]
* ------------ ------------ ---------------------
* IPPROTO_SCTP SCTP_AUTHINFO struct sctp_authinfo
*/
if (cmsg->cmsg_len != CMSG_LEN(sizeof(struct sctp_authinfo)))
return -EINVAL;
cmsgs->authinfo = CMSG_DATA(cmsg);
break;
case SCTP_DSTADDRV4: case SCTP_DSTADDRV4:
case SCTP_DSTADDRV6: case SCTP_DSTADDRV6:
/* SCTP Socket API Extension /* SCTP Socket API Extension
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment