aboutsummaryrefslogtreecommitdiffstats
path: root/net/sctp/socket.c
diff options
context:
space:
mode:
Diffstat (limited to 'net/sctp/socket.c')
-rw-r--r--net/sctp/socket.c206
1 files changed, 173 insertions, 33 deletions
diff --git a/net/sctp/socket.c b/net/sctp/socket.c
index a1b904529d5e..b14a8f33e42d 100644
--- a/net/sctp/socket.c
+++ b/net/sctp/socket.c
@@ -114,7 +114,7 @@ extern int sysctl_sctp_wmem[3];
114 114
115static int sctp_memory_pressure; 115static int sctp_memory_pressure;
116static atomic_t sctp_memory_allocated; 116static atomic_t sctp_memory_allocated;
117static atomic_t sctp_sockets_allocated; 117struct percpu_counter sctp_sockets_allocated;
118 118
119static void sctp_enter_memory_pressure(struct sock *sk) 119static void sctp_enter_memory_pressure(struct sock *sk)
120{ 120{
@@ -2404,9 +2404,9 @@ static int sctp_setsockopt_delayed_ack(struct sock *sk,
2404 if (params.sack_delay == 0 && params.sack_freq == 0) 2404 if (params.sack_delay == 0 && params.sack_freq == 0)
2405 return 0; 2405 return 0;
2406 } else if (optlen == sizeof(struct sctp_assoc_value)) { 2406 } else if (optlen == sizeof(struct sctp_assoc_value)) {
2407 printk(KERN_WARNING "SCTP: Use of struct sctp_sack_info " 2407 printk(KERN_WARNING "SCTP: Use of struct sctp_assoc_value "
2408 "in delayed_ack socket option deprecated\n"); 2408 "in delayed_ack socket option deprecated\n");
2409 printk(KERN_WARNING "SCTP: struct sctp_sack_info instead\n"); 2409 printk(KERN_WARNING "SCTP: Use struct sctp_sack_info instead\n");
2410 if (copy_from_user(&params, optval, optlen)) 2410 if (copy_from_user(&params, optval, optlen))
2411 return -EFAULT; 2411 return -EFAULT;
2412 2412
@@ -2778,32 +2778,77 @@ static int sctp_setsockopt_mappedv4(struct sock *sk, char __user *optval, int op
2778} 2778}
2779 2779
2780/* 2780/*
2781 * 7.1.17 Set the maximum fragrmentation size (SCTP_MAXSEG) 2781 * 8.1.16. Get or Set the Maximum Fragmentation Size (SCTP_MAXSEG)
2782 * 2782 * This option will get or set the maximum size to put in any outgoing
2783 * This socket option specifies the maximum size to put in any outgoing 2783 * SCTP DATA chunk. If a message is larger than this size it will be
2784 * SCTP chunk. If a message is larger than this size it will be
2785 * fragmented by SCTP into the specified size. Note that the underlying 2784 * fragmented by SCTP into the specified size. Note that the underlying
2786 * SCTP implementation may fragment into smaller sized chunks when the 2785 * SCTP implementation may fragment into smaller sized chunks when the
2787 * PMTU of the underlying association is smaller than the value set by 2786 * PMTU of the underlying association is smaller than the value set by
2788 * the user. 2787 * the user. The default value for this option is '0' which indicates
2788 * the user is NOT limiting fragmentation and only the PMTU will effect
2789 * SCTP's choice of DATA chunk size. Note also that values set larger
2790 * than the maximum size of an IP datagram will effectively let SCTP
2791 * control fragmentation (i.e. the same as setting this option to 0).
2792 *
2793 * The following structure is used to access and modify this parameter:
2794 *
2795 * struct sctp_assoc_value {
2796 * sctp_assoc_t assoc_id;
2797 * uint32_t assoc_value;
2798 * };
2799 *
2800 * assoc_id: This parameter is ignored for one-to-one style sockets.
2801 * For one-to-many style sockets this parameter indicates which
2802 * association the user is performing an action upon. Note that if
2803 * this field's value is zero then the endpoints default value is
2804 * changed (effecting future associations only).
2805 * assoc_value: This parameter specifies the maximum size in bytes.
2789 */ 2806 */
2790static int sctp_setsockopt_maxseg(struct sock *sk, char __user *optval, int optlen) 2807static int sctp_setsockopt_maxseg(struct sock *sk, char __user *optval, int optlen)
2791{ 2808{
2809 struct sctp_assoc_value params;
2792 struct sctp_association *asoc; 2810 struct sctp_association *asoc;
2793 struct sctp_sock *sp = sctp_sk(sk); 2811 struct sctp_sock *sp = sctp_sk(sk);
2794 int val; 2812 int val;
2795 2813
2796 if (optlen < sizeof(int)) 2814 if (optlen == sizeof(int)) {
2815 printk(KERN_WARNING
2816 "SCTP: Use of int in maxseg socket option deprecated\n");
2817 printk(KERN_WARNING
2818 "SCTP: Use struct sctp_assoc_value instead\n");
2819 if (copy_from_user(&val, optval, optlen))
2820 return -EFAULT;
2821 params.assoc_id = 0;
2822 } else if (optlen == sizeof(struct sctp_assoc_value)) {
2823 if (copy_from_user(&params, optval, optlen))
2824 return -EFAULT;
2825 val = params.assoc_value;
2826 } else
2797 return -EINVAL; 2827 return -EINVAL;
2798 if (get_user(val, (int __user *)optval)) 2828
2799 return -EFAULT;
2800 if ((val != 0) && ((val < 8) || (val > SCTP_MAX_CHUNK_LEN))) 2829 if ((val != 0) && ((val < 8) || (val > SCTP_MAX_CHUNK_LEN)))
2801 return -EINVAL; 2830 return -EINVAL;
2802 sp->user_frag = val;
2803 2831
2804 /* Update the frag_point of the existing associations. */ 2832 asoc = sctp_id2assoc(sk, params.assoc_id);
2805 list_for_each_entry(asoc, &(sp->ep->asocs), asocs) { 2833 if (!asoc && params.assoc_id && sctp_style(sk, UDP))
2806 asoc->frag_point = sctp_frag_point(sp, asoc->pathmtu); 2834 return -EINVAL;
2835
2836 if (asoc) {
2837 if (val == 0) {
2838 val = asoc->pathmtu;
2839 val -= sp->pf->af->net_header_len;
2840 val -= sizeof(struct sctphdr) +
2841 sizeof(struct sctp_data_chunk);
2842 }
2843
2844 asoc->frag_point = val;
2845 } else {
2846 sp->user_frag = val;
2847
2848 /* Update the frag_point of the existing associations. */
2849 list_for_each_entry(asoc, &(sp->ep->asocs), asocs) {
2850 asoc->frag_point = sctp_frag_point(sp, asoc->pathmtu);
2851 }
2807 } 2852 }
2808 2853
2809 return 0; 2854 return 0;
@@ -2965,14 +3010,21 @@ static int sctp_setsockopt_fragment_interleave(struct sock *sk,
2965} 3010}
2966 3011
2967/* 3012/*
2968 * 7.1.25. Set or Get the sctp partial delivery point 3013 * 8.1.21. Set or Get the SCTP Partial Delivery Point
2969 * (SCTP_PARTIAL_DELIVERY_POINT) 3014 * (SCTP_PARTIAL_DELIVERY_POINT)
3015 *
2970 * This option will set or get the SCTP partial delivery point. This 3016 * This option will set or get the SCTP partial delivery point. This
2971 * point is the size of a message where the partial delivery API will be 3017 * point is the size of a message where the partial delivery API will be
2972 * invoked to help free up rwnd space for the peer. Setting this to a 3018 * invoked to help free up rwnd space for the peer. Setting this to a
2973 * lower value will cause partial delivery's to happen more often. The 3019 * lower value will cause partial deliveries to happen more often. The
2974 * calls argument is an integer that sets or gets the partial delivery 3020 * calls argument is an integer that sets or gets the partial delivery
2975 * point. 3021 * point. Note also that the call will fail if the user attempts to set
3022 * this value larger than the socket receive buffer size.
3023 *
3024 * Note that any single message having a length smaller than or equal to
3025 * the SCTP partial delivery point will be delivered in one single read
3026 * call as long as the user provided buffer is large enough to hold the
3027 * message.
2976 */ 3028 */
2977static int sctp_setsockopt_partial_delivery_point(struct sock *sk, 3029static int sctp_setsockopt_partial_delivery_point(struct sock *sk,
2978 char __user *optval, 3030 char __user *optval,
@@ -2985,6 +3037,12 @@ static int sctp_setsockopt_partial_delivery_point(struct sock *sk,
2985 if (get_user(val, (int __user *)optval)) 3037 if (get_user(val, (int __user *)optval))
2986 return -EFAULT; 3038 return -EFAULT;
2987 3039
3040 /* Note: We double the receive buffer from what the user sets
3041 * it to be, also initial rwnd is based on rcvbuf/2.
3042 */
3043 if (val > (sk->sk_rcvbuf >> 1))
3044 return -EINVAL;
3045
2988 sctp_sk(sk)->pd_point = val; 3046 sctp_sk(sk)->pd_point = val;
2989 3047
2990 return 0; /* is this the right error code? */ 3048 return 0; /* is this the right error code? */
@@ -3613,7 +3671,12 @@ SCTP_STATIC int sctp_init_sock(struct sock *sk)
3613 sp->hmac = NULL; 3671 sp->hmac = NULL;
3614 3672
3615 SCTP_DBG_OBJCNT_INC(sock); 3673 SCTP_DBG_OBJCNT_INC(sock);
3616 atomic_inc(&sctp_sockets_allocated); 3674 percpu_counter_inc(&sctp_sockets_allocated);
3675
3676 local_bh_disable();
3677 sock_prot_inuse_add(sock_net(sk), sk->sk_prot, 1);
3678 local_bh_enable();
3679
3617 return 0; 3680 return 0;
3618} 3681}
3619 3682
@@ -3627,7 +3690,10 @@ SCTP_STATIC void sctp_destroy_sock(struct sock *sk)
3627 /* Release our hold on the endpoint. */ 3690 /* Release our hold on the endpoint. */
3628 ep = sctp_sk(sk)->ep; 3691 ep = sctp_sk(sk)->ep;
3629 sctp_endpoint_free(ep); 3692 sctp_endpoint_free(ep);
3630 atomic_dec(&sctp_sockets_allocated); 3693 percpu_counter_dec(&sctp_sockets_allocated);
3694 local_bh_disable();
3695 sock_prot_inuse_add(sock_net(sk), sk->sk_prot, -1);
3696 local_bh_enable();
3631} 3697}
3632 3698
3633/* API 4.1.7 shutdown() - TCP Style Syntax 3699/* API 4.1.7 shutdown() - TCP Style Syntax
@@ -4168,9 +4234,9 @@ static int sctp_getsockopt_delayed_ack(struct sock *sk, int len,
4168 if (copy_from_user(&params, optval, len)) 4234 if (copy_from_user(&params, optval, len))
4169 return -EFAULT; 4235 return -EFAULT;
4170 } else if (len == sizeof(struct sctp_assoc_value)) { 4236 } else if (len == sizeof(struct sctp_assoc_value)) {
4171 printk(KERN_WARNING "SCTP: Use of struct sctp_sack_info " 4237 printk(KERN_WARNING "SCTP: Use of struct sctp_assoc_value "
4172 "in delayed_ack socket option deprecated\n"); 4238 "in delayed_ack socket option deprecated\n");
4173 printk(KERN_WARNING "SCTP: struct sctp_sack_info instead\n"); 4239 printk(KERN_WARNING "SCTP: Use struct sctp_sack_info instead\n");
4174 if (copy_from_user(&params, optval, len)) 4240 if (copy_from_user(&params, optval, len))
4175 return -EFAULT; 4241 return -EFAULT;
4176 } else 4242 } else
@@ -5092,30 +5158,69 @@ static int sctp_getsockopt_context(struct sock *sk, int len,
5092} 5158}
5093 5159
5094/* 5160/*
5095 * 7.1.17 Set the maximum fragrmentation size (SCTP_MAXSEG) 5161 * 8.1.16. Get or Set the Maximum Fragmentation Size (SCTP_MAXSEG)
5096 * 5162 * This option will get or set the maximum size to put in any outgoing
5097 * This socket option specifies the maximum size to put in any outgoing 5163 * SCTP DATA chunk. If a message is larger than this size it will be
5098 * SCTP chunk. If a message is larger than this size it will be
5099 * fragmented by SCTP into the specified size. Note that the underlying 5164 * fragmented by SCTP into the specified size. Note that the underlying
5100 * SCTP implementation may fragment into smaller sized chunks when the 5165 * SCTP implementation may fragment into smaller sized chunks when the
5101 * PMTU of the underlying association is smaller than the value set by 5166 * PMTU of the underlying association is smaller than the value set by
5102 * the user. 5167 * the user. The default value for this option is '0' which indicates
5168 * the user is NOT limiting fragmentation and only the PMTU will effect
5169 * SCTP's choice of DATA chunk size. Note also that values set larger
5170 * than the maximum size of an IP datagram will effectively let SCTP
5171 * control fragmentation (i.e. the same as setting this option to 0).
5172 *
5173 * The following structure is used to access and modify this parameter:
5174 *
5175 * struct sctp_assoc_value {
5176 * sctp_assoc_t assoc_id;
5177 * uint32_t assoc_value;
5178 * };
5179 *
5180 * assoc_id: This parameter is ignored for one-to-one style sockets.
5181 * For one-to-many style sockets this parameter indicates which
5182 * association the user is performing an action upon. Note that if
5183 * this field's value is zero then the endpoints default value is
5184 * changed (effecting future associations only).
5185 * assoc_value: This parameter specifies the maximum size in bytes.
5103 */ 5186 */
5104static int sctp_getsockopt_maxseg(struct sock *sk, int len, 5187static int sctp_getsockopt_maxseg(struct sock *sk, int len,
5105 char __user *optval, int __user *optlen) 5188 char __user *optval, int __user *optlen)
5106{ 5189{
5107 int val; 5190 struct sctp_assoc_value params;
5191 struct sctp_association *asoc;
5108 5192
5109 if (len < sizeof(int)) 5193 if (len == sizeof(int)) {
5194 printk(KERN_WARNING
5195 "SCTP: Use of int in maxseg socket option deprecated\n");
5196 printk(KERN_WARNING
5197 "SCTP: Use struct sctp_assoc_value instead\n");
5198 params.assoc_id = 0;
5199 } else if (len >= sizeof(struct sctp_assoc_value)) {
5200 len = sizeof(struct sctp_assoc_value);
5201 if (copy_from_user(&params, optval, sizeof(params)))
5202 return -EFAULT;
5203 } else
5110 return -EINVAL; 5204 return -EINVAL;
5111 5205
5112 len = sizeof(int); 5206 asoc = sctp_id2assoc(sk, params.assoc_id);
5207 if (!asoc && params.assoc_id && sctp_style(sk, UDP))
5208 return -EINVAL;
5209
5210 if (asoc)
5211 params.assoc_value = asoc->frag_point;
5212 else
5213 params.assoc_value = sctp_sk(sk)->user_frag;
5113 5214
5114 val = sctp_sk(sk)->user_frag;
5115 if (put_user(len, optlen)) 5215 if (put_user(len, optlen))
5116 return -EFAULT; 5216 return -EFAULT;
5117 if (copy_to_user(optval, &val, len)) 5217 if (len == sizeof(int)) {
5118 return -EFAULT; 5218 if (copy_to_user(optval, &params.assoc_value, len))
5219 return -EFAULT;
5220 } else {
5221 if (copy_to_user(optval, &params, len))
5222 return -EFAULT;
5223 }
5119 5224
5120 return 0; 5225 return 0;
5121} 5226}
@@ -5368,6 +5473,38 @@ num:
5368 return 0; 5473 return 0;
5369} 5474}
5370 5475
5476/*
5477 * 8.2.5. Get the Current Number of Associations (SCTP_GET_ASSOC_NUMBER)
5478 * This option gets the current number of associations that are attached
5479 * to a one-to-many style socket. The option value is an uint32_t.
5480 */
5481static int sctp_getsockopt_assoc_number(struct sock *sk, int len,
5482 char __user *optval, int __user *optlen)
5483{
5484 struct sctp_sock *sp = sctp_sk(sk);
5485 struct sctp_association *asoc;
5486 u32 val = 0;
5487
5488 if (sctp_style(sk, TCP))
5489 return -EOPNOTSUPP;
5490
5491 if (len < sizeof(u32))
5492 return -EINVAL;
5493
5494 len = sizeof(u32);
5495
5496 list_for_each_entry(asoc, &(sp->ep->asocs), asocs) {
5497 val++;
5498 }
5499
5500 if (put_user(len, optlen))
5501 return -EFAULT;
5502 if (copy_to_user(optval, &val, len))
5503 return -EFAULT;
5504
5505 return 0;
5506}
5507
5371SCTP_STATIC int sctp_getsockopt(struct sock *sk, int level, int optname, 5508SCTP_STATIC int sctp_getsockopt(struct sock *sk, int level, int optname,
5372 char __user *optval, int __user *optlen) 5509 char __user *optval, int __user *optlen)
5373{ 5510{
@@ -5510,6 +5647,9 @@ SCTP_STATIC int sctp_getsockopt(struct sock *sk, int level, int optname,
5510 retval = sctp_getsockopt_local_auth_chunks(sk, len, optval, 5647 retval = sctp_getsockopt_local_auth_chunks(sk, len, optval,
5511 optlen); 5648 optlen);
5512 break; 5649 break;
5650 case SCTP_GET_ASSOC_NUMBER:
5651 retval = sctp_getsockopt_assoc_number(sk, len, optval, optlen);
5652 break;
5513 default: 5653 default:
5514 retval = -ENOPROTOOPT; 5654 retval = -ENOPROTOOPT;
5515 break; 5655 break;