Commit aea7427f authored by Shan Wei's avatar Shan Wei Committed by David S. Miller

ipv6: Remove options header when setsockopt's optlen is 0

Remove the sticky Hop-by-Hop options header by calling setsockopt()
for IPV6_HOPOPTS with a zero option length, per RFC3542.

Routing header and Destination options header does the same as
Hop-by-Hop options header.
Signed-off-by: default avatarShan Wei <shanwei@cn.fujitsu.com>
Acked-by: default avatarYOSHIFUJI Hideaki <yoshfuji@linux-ipv6.org>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent ef3a62d2
...@@ -345,18 +345,21 @@ static int do_ipv6_setsockopt(struct sock *sk, int level, int optname, ...@@ -345,18 +345,21 @@ static int do_ipv6_setsockopt(struct sock *sk, int level, int optname,
case IPV6_DSTOPTS: case IPV6_DSTOPTS:
{ {
struct ipv6_txoptions *opt; struct ipv6_txoptions *opt;
/* remove any sticky options header with a zero option
* length, per RFC3542.
*/
if (optlen == 0) if (optlen == 0)
optval = NULL; optval = NULL;
else if (optlen < sizeof(struct ipv6_opt_hdr) ||
optlen & 0x7 || optlen > 8 * 255)
goto e_inval;
/* hop-by-hop / destination options are privileged option */ /* hop-by-hop / destination options are privileged option */
retv = -EPERM; retv = -EPERM;
if (optname != IPV6_RTHDR && !capable(CAP_NET_RAW)) if (optname != IPV6_RTHDR && !capable(CAP_NET_RAW))
break; break;
if (optlen < sizeof(struct ipv6_opt_hdr) ||
optlen & 0x7 || optlen > 8 * 255)
goto e_inval;
opt = ipv6_renew_options(sk, np->opt, optname, opt = ipv6_renew_options(sk, np->opt, optname,
(struct ipv6_opt_hdr __user *)optval, (struct ipv6_opt_hdr __user *)optval,
optlen); optlen);
......
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