Skip to content

Commit bd4d627

Browse files
lxindavem330
authored andcommitted
sctp: implement ulpevent_data for sctp_stream_interleave
ulpevent_data is added as a member of sctp_stream_interleave, used to do the most process in ulpq, including to convert data or idata chunk to event, reasm them in reasm queue and put them in lobby queue in right order, and deliver them up to user sk rx queue. This procedure is described in section 2.2.3 of RFC8260. It adds most functions for idata here to do the similar process as the old functions for data. But since the details are very different between them, the old functions can not be reused for idata. event->ssn and event->ppid settings are moved to ulpevent_data from sctp_ulpevent_make_rcvmsg, so that sctp_ulpevent_make_rcvmsg could work for both data and idata. Note that mid is added in sctp_ulpevent for idata, __packed has to be used for defining sctp_ulpevent, or it would exceeds the skb cb that saves a sctp_ulpevent variable for ulp layer process. Signed-off-by: Xin Long <lucien.xin@gmail.com> Acked-by: Marcelo Ricardo Leitner <marcelo.leitner@gmail.com> Acked-by: Neil Horman <nhorman@tuxdriver.com> Signed-off-by: David S. Miller <davem@davemloft.net>
1 parent 9d4ceaf commit bd4d627

File tree

7 files changed

+451
-11
lines changed

7 files changed

+451
-11
lines changed

include/net/sctp/stream_interleave.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,8 @@ struct sctp_stream_interleave {
3939
int len, __u8 flags, gfp_t gfp);
4040
void (*assign_number)(struct sctp_chunk *chunk);
4141
bool (*validate_data)(struct sctp_chunk *chunk);
42+
int (*ulpevent_data)(struct sctp_ulpq *ulpq,
43+
struct sctp_chunk *chunk, gfp_t gfp);
4244
};
4345

4446
void sctp_stream_interleave_init(struct sctp_stream *stream);

include/net/sctp/structs.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -411,6 +411,8 @@ void sctp_stream_update(struct sctp_stream *stream, struct sctp_stream *new);
411411
#define sctp_mid_skip(stream, type, sid, mid) \
412412
((stream)->type[sid].mid = mid + 1)
413413

414+
#define sctp_stream_in(asoc, sid) (&(asoc)->stream.in[sid])
415+
414416
/*
415417
* Pointers to address related SCTP functions.
416418
* (i.e. things that depend on the address family.)
@@ -1387,6 +1389,7 @@ struct sctp_stream_in {
13871389
__u16 ssn;
13881390
};
13891391
__u32 fsn;
1392+
char pd_mode;
13901393
};
13911394

13921395
struct sctp_stream {

include/net/sctp/ulpevent.h

Lines changed: 17 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -45,19 +45,29 @@
4545
/* A structure to carry information to the ULP (e.g. Sockets API) */
4646
/* Warning: This sits inside an skb.cb[] area. Be very careful of
4747
* growing this structure as it is at the maximum limit now.
48+
*
49+
* sctp_ulpevent is saved in sk->cb(48 bytes), whose last 4 bytes
50+
* have been taken by sock_skb_cb, So here it has to use 'packed'
51+
* to make sctp_ulpevent fit into the rest 44 bytes.
4852
*/
4953
struct sctp_ulpevent {
5054
struct sctp_association *asoc;
5155
struct sctp_chunk *chunk;
5256
unsigned int rmem_len;
53-
__u32 ppid;
57+
union {
58+
__u32 mid;
59+
__u16 ssn;
60+
};
61+
union {
62+
__u32 ppid;
63+
__u32 fsn;
64+
};
5465
__u32 tsn;
5566
__u32 cumtsn;
5667
__u16 stream;
57-
__u16 ssn;
5868
__u16 flags;
5969
__u16 msg_flags;
60-
};
70+
} __packed;
6171

6272
/* Retrieve the skb this event sits inside of. */
6373
static inline struct sk_buff *sctp_event2skb(const struct sctp_ulpevent *ev)
@@ -140,6 +150,10 @@ struct sctp_ulpevent *sctp_ulpevent_make_stream_change_event(
140150
const struct sctp_association *asoc, __u16 flags,
141151
__u32 strchange_instrms, __u32 strchange_outstrms, gfp_t gfp);
142152

153+
struct sctp_ulpevent *sctp_make_reassembled_event(
154+
struct net *net, struct sk_buff_head *queue,
155+
struct sk_buff *f_frag, struct sk_buff *l_frag);
156+
143157
void sctp_ulpevent_read_sndrcvinfo(const struct sctp_ulpevent *event,
144158
struct msghdr *);
145159
void sctp_ulpevent_read_rcvinfo(const struct sctp_ulpevent *event,

net/sctp/sm_sideeffect.c

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1483,8 +1483,9 @@ static int sctp_cmd_interpreter(enum sctp_event event_type,
14831483
pr_debug("%s: sm_sideff: chunk_up:%p, ulpq:%p\n",
14841484
__func__, cmd->obj.chunk, &asoc->ulpq);
14851485

1486-
sctp_ulpq_tail_data(&asoc->ulpq, cmd->obj.chunk,
1487-
GFP_ATOMIC);
1486+
asoc->stream.si->ulpevent_data(&asoc->ulpq,
1487+
cmd->obj.chunk,
1488+
GFP_ATOMIC);
14881489
break;
14891490

14901491
case SCTP_CMD_EVENT_ULP:

0 commit comments

Comments
 (0)