As defined per RFC Draft ndata Section 4.3.3, named as SCTP_STREAM_SCHEDULER_VALUE.
Unified · Split
| @@ -123,6 +123,7 @@ typedef __s32 sctp_assoc_t; · 122 unmodified lines | ||
| 123 | 123 | #define SCTP_ADD_STREAMS 121 |
| 124 | 124 | #define SCTP_SOCKOPT_PEELOFF_FLAGS 122 |
| 125 | 125 | #define SCTP_STREAM_SCHEDULER 123 |
| 126 | +#define SCTP_STREAM_SCHEDULER_VALUE 124 | |
| 126 | 127 | |
| 127 | 128 | /* PR-SCTP policies */ |
| 128 | 129 | #define SCTP_PR_SCTP_NONE 0x0000 |
| @@ -815,6 +816,12 @@ struct sctp_assoc_value { · 686 unmodified lines | ||
| 815 | 816 | uint32_t assoc_value; |
| 816 | 817 | }; |
| 817 | 818 | |
| 819 | +struct sctp_stream_value { | |
| 820 | + sctp_assoc_t assoc_id; | |
| 821 | + uint16_t stream_id; | |
| 822 | + uint16_t stream_value; | |
| 823 | +}; | |
| 824 | + | |
| 818 | 825 | /* |
| 819 | 826 | * 7.2.2 Peer Address Information |
| 820 | 827 | * |
| @@ -3945,6 +3945,34 @@ out: · 3944 unmodified lines | ||
| 3945 | 3945 | return retval; |
| 3946 | 3946 | } |
| 3947 | 3947 | |
| 3948 | +static int sctp_setsockopt_scheduler_value(struct sock *sk, | |
| 3949 | + char __user *optval, | |
| 3950 | + unsigned int optlen) | |
| 3951 | +{ | |
| 3952 | + struct sctp_association *asoc; | |
| 3953 | + struct sctp_stream_value params; | |
| 3954 | + int retval = -EINVAL; | |
| 3955 | + | |
| 3956 | + if (optlen < sizeof(params)) | |
| 3957 | + goto out; | |
| 3958 | + | |
| 3959 | + optlen = sizeof(params); | |
| 3960 | + if (copy_from_user(¶ms, optval, optlen)) { | |
| 3961 | + retval = -EFAULT; | |
| 3962 | + goto out; | |
| 3963 | + } | |
| 3964 | + | |
| 3965 | + asoc = sctp_id2assoc(sk, params.assoc_id); | |
| 3966 | + if (!asoc) | |
| 3967 | + goto out; | |
| 3968 | + | |
| 3969 | + retval = sctp_sched_set_value(asoc, params.stream_id, | |
| 3970 | + params.stream_value, GFP_KERNEL); | |
| 3971 | + | |
| 3972 | +out: | |
| 3973 | + return retval; | |
| 3974 | +} | |
| 3975 | + | |
| 3948 | 3976 | /* API 6.2 setsockopt(), getsockopt() |
| 3949 | 3977 | * |
| 3950 | 3978 | * Applications use setsockopt() and getsockopt() to set or retrieve |
| @@ -4129,6 +4157,9 @@ static int sctp_setsockopt(struct sock *sk, int level, int optname, · 178 unmodified lines | ||
| 4129 | 4157 | case SCTP_STREAM_SCHEDULER: |
| 4130 | 4158 | retval = sctp_setsockopt_scheduler(sk, optval, optlen); |
| 4131 | 4159 | break; |
| 4160 | + case SCTP_STREAM_SCHEDULER_VALUE: | |
| 4161 | + retval = sctp_setsockopt_scheduler_value(sk, optval, optlen); | |
| 4162 | + break; | |
| 4132 | 4163 | default: |
| 4133 | 4164 | retval = -ENOPROTOOPT; |
| 4134 | 4165 | break; |
| @@ -6864,6 +6895,48 @@ out: · 2729 unmodified lines | ||
| 6864 | 6895 | return retval; |
| 6865 | 6896 | } |
| 6866 | 6897 | |
| 6898 | +static int sctp_getsockopt_scheduler_value(struct sock *sk, int len, | |
| 6899 | + char __user *optval, | |
| 6900 | + int __user *optlen) | |
| 6901 | +{ | |
| 6902 | + struct sctp_stream_value params; | |
| 6903 | + struct sctp_association *asoc; | |
| 6904 | + int retval = -EFAULT; | |
| 6905 | + | |
| 6906 | + if (len < sizeof(params)) { | |
| 6907 | + retval = -EINVAL; | |
| 6908 | + goto out; | |
| 6909 | + } | |
| 6910 | + | |
| 6911 | + len = sizeof(params); | |
| 6912 | + if (copy_from_user(¶ms, optval, len)) | |
| 6913 | + goto out; | |
| 6914 | + | |
| 6915 | + asoc = sctp_id2assoc(sk, params.assoc_id); | |
| 6916 | + if (!asoc) { | |
| 6917 | + retval = -EINVAL; | |
| 6918 | + goto out; | |
| 6919 | + } | |
| 6920 | + | |
| 6921 | + retval = sctp_sched_get_value(asoc, params.stream_id, | |
| 6922 | + ¶ms.stream_value); | |
| 6923 | + if (retval) | |
| 6924 | + goto out; | |
| 6925 | + | |
| 6926 | + if (put_user(len, optlen)) { | |
| 6927 | + retval = -EFAULT; | |
| 6928 | + goto out; | |
| 6929 | + } | |
| 6930 | + | |
| 6931 | + if (copy_to_user(optval, ¶ms, len)) { | |
| 6932 | + retval = -EFAULT; | |
| 6933 | + goto out; | |
| 6934 | + } | |
| 6935 | + | |
| 6936 | +out: | |
| 6937 | + return retval; | |
| 6938 | +} | |
| 6939 | + | |
| 6867 | 6940 | static int sctp_getsockopt(struct sock *sk, int level, int optname, |
| 6868 | 6941 | char __user *optval, int __user *optlen) |
| 6869 | 6942 | { |
| @@ -7050,6 +7123,10 @@ static int sctp_getsockopt(struct sock *sk, int level, int optname, · 180 unmodified lines | ||
| 7050 | 7123 | retval = sctp_getsockopt_scheduler(sk, len, optval, |
| 7051 | 7124 | optlen); |
| 7052 | 7125 | break; |
| 7126 | + case SCTP_STREAM_SCHEDULER_VALUE: | |
| 7127 | + retval = sctp_getsockopt_scheduler_value(sk, len, optval, | |
| 7128 | + optlen); | |
| 7129 | + break; | |
| 7053 | 7130 | default: |
| 7054 | 7131 | retval = -ENOPROTOOPT; |
| 7055 | 7132 | break; |