diff options
-rw-r--r-- | net/dccp/feat.h | 14 | ||||
-rw-r--r-- | net/dccp/options.c | 21 |
2 files changed, 28 insertions, 7 deletions
diff --git a/net/dccp/feat.h b/net/dccp/feat.h index 093af1610d11..a8ab9e1e8b17 100644 --- a/net/dccp/feat.h +++ b/net/dccp/feat.h | |||
@@ -125,4 +125,18 @@ extern int dccp_feat_clone(struct sock *oldsk, struct sock *newsk); | |||
125 | extern int dccp_feat_clone_list(struct list_head const *, struct list_head *); | 125 | extern int dccp_feat_clone_list(struct list_head const *, struct list_head *); |
126 | extern int dccp_feat_init(struct sock *sk); | 126 | extern int dccp_feat_init(struct sock *sk); |
127 | 127 | ||
128 | /* | ||
129 | * Encoding variable-length options and their maximum length. | ||
130 | * | ||
131 | * This affects NN options (SP options are all u8) and other variable-length | ||
132 | * options (see table 3 in RFC 4340). The limit is currently given the Sequence | ||
133 | * Window NN value (sec. 7.5.2) and the NDP count (sec. 7.7) option, all other | ||
134 | * options consume less than 6 bytes (timestamps are 4 bytes). | ||
135 | * When updating this constant (e.g. due to new internet drafts / RFCs), make | ||
136 | * sure that you also update all code which refers to it. | ||
137 | */ | ||
138 | #define DCCP_OPTVAL_MAXLEN 6 | ||
139 | |||
140 | extern void dccp_encode_value_var(const u64 value, u8 *to, const u8 len); | ||
141 | extern u64 dccp_decode_value_var(const u8 *bf, const u8 len); | ||
128 | #endif /* _DCCP_FEAT_H */ | 142 | #endif /* _DCCP_FEAT_H */ |
diff --git a/net/dccp/options.c b/net/dccp/options.c index 515ad45013ad..9cb0ff894052 100644 --- a/net/dccp/options.c +++ b/net/dccp/options.c | |||
@@ -29,16 +29,20 @@ int sysctl_dccp_feat_tx_ccid = DCCPF_INITIAL_CCID; | |||
29 | int sysctl_dccp_feat_send_ack_vector = DCCPF_INITIAL_SEND_ACK_VECTOR; | 29 | int sysctl_dccp_feat_send_ack_vector = DCCPF_INITIAL_SEND_ACK_VECTOR; |
30 | int sysctl_dccp_feat_send_ndp_count = DCCPF_INITIAL_SEND_NDP_COUNT; | 30 | int sysctl_dccp_feat_send_ndp_count = DCCPF_INITIAL_SEND_NDP_COUNT; |
31 | 31 | ||
32 | static u32 dccp_decode_value_var(const unsigned char *bf, const u8 len) | 32 | u64 dccp_decode_value_var(const u8 *bf, const u8 len) |
33 | { | 33 | { |
34 | u32 value = 0; | 34 | u64 value = 0; |
35 | 35 | ||
36 | if (len >= DCCP_OPTVAL_MAXLEN) | ||
37 | value += ((u64)*bf++) << 40; | ||
38 | if (len > 4) | ||
39 | value += ((u64)*bf++) << 32; | ||
36 | if (len > 3) | 40 | if (len > 3) |
37 | value += *bf++ << 24; | 41 | value += ((u64)*bf++) << 24; |
38 | if (len > 2) | 42 | if (len > 2) |
39 | value += *bf++ << 16; | 43 | value += ((u64)*bf++) << 16; |
40 | if (len > 1) | 44 | if (len > 1) |
41 | value += *bf++ << 8; | 45 | value += ((u64)*bf++) << 8; |
42 | if (len > 0) | 46 | if (len > 0) |
43 | value += *bf; | 47 | value += *bf; |
44 | 48 | ||
@@ -298,9 +302,12 @@ out_invalid_option: | |||
298 | 302 | ||
299 | EXPORT_SYMBOL_GPL(dccp_parse_options); | 303 | EXPORT_SYMBOL_GPL(dccp_parse_options); |
300 | 304 | ||
301 | static void dccp_encode_value_var(const u32 value, unsigned char *to, | 305 | void dccp_encode_value_var(const u64 value, u8 *to, const u8 len) |
302 | const unsigned int len) | ||
303 | { | 306 | { |
307 | if (len >= DCCP_OPTVAL_MAXLEN) | ||
308 | *to++ = (value & 0xFF0000000000ull) >> 40; | ||
309 | if (len > 4) | ||
310 | *to++ = (value & 0xFF00000000ull) >> 32; | ||
304 | if (len > 3) | 311 | if (len > 3) |
305 | *to++ = (value & 0xFF000000) >> 24; | 312 | *to++ = (value & 0xFF000000) >> 24; |
306 | if (len > 2) | 313 | if (len > 2) |