Linux Audio

Check our new training course

Loading...
v3.5.6
 
   1/*
   2 *	DCCP over IPv6
   3 *	Linux INET6 implementation
   4 *
   5 *	Based on net/dccp6/ipv6.c
   6 *
   7 *	Arnaldo Carvalho de Melo <acme@ghostprotocols.net>
   8 *
   9 *	This program is free software; you can redistribute it and/or
  10 *      modify it under the terms of the GNU General Public License
  11 *      as published by the Free Software Foundation; either version
  12 *      2 of the License, or (at your option) any later version.
  13 */
  14
  15#include <linux/module.h>
  16#include <linux/random.h>
  17#include <linux/slab.h>
  18#include <linux/xfrm.h>
 
  19
  20#include <net/addrconf.h>
  21#include <net/inet_common.h>
  22#include <net/inet_hashtables.h>
  23#include <net/inet_sock.h>
  24#include <net/inet6_connection_sock.h>
  25#include <net/inet6_hashtables.h>
  26#include <net/ip6_route.h>
  27#include <net/ipv6.h>
  28#include <net/protocol.h>
  29#include <net/transp_v6.h>
  30#include <net/ip6_checksum.h>
  31#include <net/xfrm.h>
  32#include <net/secure_seq.h>
 
 
  33
  34#include "dccp.h"
  35#include "ipv6.h"
  36#include "feat.h"
  37
  38/* The per-net dccp.v6_ctl_sk is used for sending RSTs and ACKs */
 
 
 
 
 
 
  39
  40static const struct inet_connection_sock_af_ops dccp_ipv6_mapped;
  41static const struct inet_connection_sock_af_ops dccp_ipv6_af_ops;
  42
  43static void dccp_v6_hash(struct sock *sk)
  44{
  45	if (sk->sk_state != DCCP_CLOSED) {
  46		if (inet_csk(sk)->icsk_af_ops == &dccp_ipv6_mapped) {
  47			inet_hash(sk);
  48			return;
  49		}
  50		local_bh_disable();
  51		__inet6_hash(sk, NULL);
  52		local_bh_enable();
  53	}
  54}
  55
  56/* add pseudo-header to DCCP checksum stored in skb->csum */
  57static inline __sum16 dccp_v6_csum_finish(struct sk_buff *skb,
  58				      const struct in6_addr *saddr,
  59				      const struct in6_addr *daddr)
  60{
  61	return csum_ipv6_magic(saddr, daddr, skb->len, IPPROTO_DCCP, skb->csum);
  62}
  63
  64static inline void dccp_v6_send_check(struct sock *sk, struct sk_buff *skb)
  65{
  66	struct ipv6_pinfo *np = inet6_sk(sk);
  67	struct dccp_hdr *dh = dccp_hdr(skb);
  68
  69	dccp_csum_outgoing(skb);
  70	dh->dccph_checksum = dccp_v6_csum_finish(skb, &np->saddr, &np->daddr);
  71}
  72
  73static inline __u64 dccp_v6_init_sequence(struct sk_buff *skb)
  74{
  75	return secure_dccpv6_sequence_number(ipv6_hdr(skb)->daddr.s6_addr32,
  76					     ipv6_hdr(skb)->saddr.s6_addr32,
  77					     dccp_hdr(skb)->dccph_dport,
  78					     dccp_hdr(skb)->dccph_sport     );
  79
  80}
  81
  82static void dccp_v6_err(struct sk_buff *skb, struct inet6_skb_parm *opt,
  83			u8 type, u8 code, int offset, __be32 info)
  84{
  85	const struct ipv6hdr *hdr = (const struct ipv6hdr *)skb->data;
  86	const struct dccp_hdr *dh = (struct dccp_hdr *)(skb->data + offset);
  87	struct dccp_sock *dp;
  88	struct ipv6_pinfo *np;
  89	struct sock *sk;
  90	int err;
  91	__u64 seq;
  92	struct net *net = dev_net(skb->dev);
  93
  94	if (skb->len < offset + sizeof(*dh) ||
  95	    skb->len < offset + __dccp_basic_hdr_len(dh)) {
  96		ICMP6_INC_STATS_BH(net, __in6_dev_get(skb->dev),
  97				   ICMP6_MIB_INERRORS);
  98		return;
  99	}
 
 100
 101	sk = inet6_lookup(net, &dccp_hashinfo,
 102			&hdr->daddr, dh->dccph_dport,
 103			&hdr->saddr, dh->dccph_sport, inet6_iif(skb));
 104
 105	if (sk == NULL) {
 106		ICMP6_INC_STATS_BH(net, __in6_dev_get(skb->dev),
 107				   ICMP6_MIB_INERRORS);
 108		return;
 
 109	}
 110
 111	if (sk->sk_state == DCCP_TIME_WAIT) {
 112		inet_twsk_put(inet_twsk(sk));
 113		return;
 
 
 
 
 
 114	}
 115
 116	bh_lock_sock(sk);
 117	if (sock_owned_by_user(sk))
 118		NET_INC_STATS_BH(net, LINUX_MIB_LOCKDROPPEDICMPS);
 119
 120	if (sk->sk_state == DCCP_CLOSED)
 121		goto out;
 122
 123	dp = dccp_sk(sk);
 124	seq = dccp_hdr_seq(dh);
 125	if ((1 << sk->sk_state) & ~(DCCPF_REQUESTING | DCCPF_LISTEN) &&
 126	    !between48(seq, dp->dccps_awl, dp->dccps_awh)) {
 127		NET_INC_STATS_BH(net, LINUX_MIB_OUTOFWINDOWICMPS);
 128		goto out;
 129	}
 130
 131	np = inet6_sk(sk);
 132
 
 
 
 
 
 
 
 
 
 
 133	if (type == ICMPV6_PKT_TOOBIG) {
 134		struct dst_entry *dst = NULL;
 135
 
 
 
 136		if (sock_owned_by_user(sk))
 137			goto out;
 138		if ((1 << sk->sk_state) & (DCCPF_LISTEN | DCCPF_CLOSED))
 139			goto out;
 140
 141		/* icmp should have updated the destination cache entry */
 142		dst = __sk_dst_check(sk, np->dst_cookie);
 143		if (dst == NULL) {
 144			struct inet_sock *inet = inet_sk(sk);
 145			struct flowi6 fl6;
 146
 147			/* BUGGG_FUTURE: Again, it is not clear how
 148			   to handle rthdr case. Ignore this complexity
 149			   for now.
 150			 */
 151			memset(&fl6, 0, sizeof(fl6));
 152			fl6.flowi6_proto = IPPROTO_DCCP;
 153			fl6.daddr = np->daddr;
 154			fl6.saddr = np->saddr;
 155			fl6.flowi6_oif = sk->sk_bound_dev_if;
 156			fl6.fl6_dport = inet->inet_dport;
 157			fl6.fl6_sport = inet->inet_sport;
 158			security_sk_classify_flow(sk, flowi6_to_flowi(&fl6));
 159
 160			dst = ip6_dst_lookup_flow(sk, &fl6, NULL, false);
 161			if (IS_ERR(dst)) {
 162				sk->sk_err_soft = -PTR_ERR(dst);
 163				goto out;
 164			}
 165		} else
 166			dst_hold(dst);
 167
 168		if (inet_csk(sk)->icsk_pmtu_cookie > dst_mtu(dst)) {
 169			dccp_sync_mss(sk, dst_mtu(dst));
 170		} /* else let the usual retransmit timer handle it */
 171		dst_release(dst);
 172		goto out;
 173	}
 174
 175	icmpv6_err_convert(type, code, &err);
 176
 177	/* Might be for an request_sock */
 178	switch (sk->sk_state) {
 179		struct request_sock *req, **prev;
 180	case DCCP_LISTEN:
 181		if (sock_owned_by_user(sk))
 182			goto out;
 183
 184		req = inet6_csk_search_req(sk, &prev, dh->dccph_dport,
 185					   &hdr->daddr, &hdr->saddr,
 186					   inet6_iif(skb));
 187		if (req == NULL)
 188			goto out;
 189
 190		/*
 191		 * ICMPs are not backlogged, hence we cannot get an established
 192		 * socket here.
 193		 */
 194		WARN_ON(req->sk != NULL);
 195
 196		if (!between48(seq, dccp_rsk(req)->dreq_iss,
 197				    dccp_rsk(req)->dreq_gss)) {
 198			NET_INC_STATS_BH(net, LINUX_MIB_OUTOFWINDOWICMPS);
 199			goto out;
 200		}
 201
 202		inet_csk_reqsk_queue_drop(sk, req, prev);
 203		goto out;
 204
 205	case DCCP_REQUESTING:
 206	case DCCP_RESPOND:  /* Cannot happen.
 207			       It can, it SYNs are crossed. --ANK */
 208		if (!sock_owned_by_user(sk)) {
 209			DCCP_INC_STATS_BH(DCCP_MIB_ATTEMPTFAILS);
 210			sk->sk_err = err;
 211			/*
 212			 * Wake people up to see the error
 213			 * (see connect in sock.c)
 214			 */
 215			sk->sk_error_report(sk);
 216			dccp_done(sk);
 217		} else
 218			sk->sk_err_soft = err;
 
 219		goto out;
 220	}
 221
 222	if (!sock_owned_by_user(sk) && np->recverr) {
 223		sk->sk_err = err;
 224		sk->sk_error_report(sk);
 225	} else
 226		sk->sk_err_soft = err;
 227
 228out:
 229	bh_unlock_sock(sk);
 230	sock_put(sk);
 
 231}
 232
 233
 234static int dccp_v6_send_response(struct sock *sk, struct request_sock *req,
 235				 struct request_values *rv_unused)
 236{
 237	struct inet6_request_sock *ireq6 = inet6_rsk(req);
 238	struct ipv6_pinfo *np = inet6_sk(sk);
 239	struct sk_buff *skb;
 240	struct ipv6_txoptions *opt = NULL;
 241	struct in6_addr *final_p, final;
 242	struct flowi6 fl6;
 243	int err = -1;
 244	struct dst_entry *dst;
 245
 246	memset(&fl6, 0, sizeof(fl6));
 247	fl6.flowi6_proto = IPPROTO_DCCP;
 248	fl6.daddr = ireq6->rmt_addr;
 249	fl6.saddr = ireq6->loc_addr;
 250	fl6.flowlabel = 0;
 251	fl6.flowi6_oif = ireq6->iif;
 252	fl6.fl6_dport = inet_rsk(req)->rmt_port;
 253	fl6.fl6_sport = inet_rsk(req)->loc_port;
 254	security_req_classify_flow(req, flowi6_to_flowi(&fl6));
 255
 256	opt = np->opt;
 257
 258	final_p = fl6_update_dst(&fl6, opt, &final);
 
 
 259
 260	dst = ip6_dst_lookup_flow(sk, &fl6, final_p, false);
 261	if (IS_ERR(dst)) {
 262		err = PTR_ERR(dst);
 263		dst = NULL;
 264		goto done;
 265	}
 266
 267	skb = dccp_make_response(sk, dst, req);
 268	if (skb != NULL) {
 269		struct dccp_hdr *dh = dccp_hdr(skb);
 
 270
 271		dh->dccph_checksum = dccp_v6_csum_finish(skb,
 272							 &ireq6->loc_addr,
 273							 &ireq6->rmt_addr);
 274		fl6.daddr = ireq6->rmt_addr;
 275		err = ip6_xmit(sk, skb, &fl6, opt, np->tclass);
 
 
 
 
 
 
 276		err = net_xmit_eval(err);
 277	}
 278
 279done:
 280	if (opt != NULL && opt != np->opt)
 281		sock_kfree_s(sk, opt, opt->tot_len);
 282	dst_release(dst);
 283	return err;
 284}
 285
 286static void dccp_v6_reqsk_destructor(struct request_sock *req)
 287{
 288	dccp_feat_list_purge(&dccp_rsk(req)->dreq_featneg);
 289	if (inet6_rsk(req)->pktopts != NULL)
 290		kfree_skb(inet6_rsk(req)->pktopts);
 291}
 292
 293static void dccp_v6_ctl_send_reset(struct sock *sk, struct sk_buff *rxskb)
 294{
 295	const struct ipv6hdr *rxip6h;
 296	struct sk_buff *skb;
 297	struct flowi6 fl6;
 298	struct net *net = dev_net(skb_dst(rxskb)->dev);
 299	struct sock *ctl_sk = net->dccp.v6_ctl_sk;
 
 300	struct dst_entry *dst;
 301
 302	if (dccp_hdr(rxskb)->dccph_type == DCCP_PKT_RESET)
 303		return;
 304
 305	if (!ipv6_unicast_destination(rxskb))
 306		return;
 307
 
 
 308	skb = dccp_ctl_make_reset(ctl_sk, rxskb);
 309	if (skb == NULL)
 310		return;
 311
 312	rxip6h = ipv6_hdr(rxskb);
 313	dccp_hdr(skb)->dccph_checksum = dccp_v6_csum_finish(skb, &rxip6h->saddr,
 314							    &rxip6h->daddr);
 315
 316	memset(&fl6, 0, sizeof(fl6));
 317	fl6.daddr = rxip6h->saddr;
 318	fl6.saddr = rxip6h->daddr;
 319
 320	fl6.flowi6_proto = IPPROTO_DCCP;
 321	fl6.flowi6_oif = inet6_iif(rxskb);
 322	fl6.fl6_dport = dccp_hdr(skb)->dccph_dport;
 323	fl6.fl6_sport = dccp_hdr(skb)->dccph_sport;
 324	security_skb_classify_flow(rxskb, flowi6_to_flowi(&fl6));
 325
 326	/* sk = NULL, but it is safe for now. RST socket required. */
 327	dst = ip6_dst_lookup_flow(ctl_sk, &fl6, NULL, false);
 328	if (!IS_ERR(dst)) {
 329		skb_dst_set(skb, dst);
 330		ip6_xmit(ctl_sk, skb, &fl6, NULL, 0);
 331		DCCP_INC_STATS_BH(DCCP_MIB_OUTSEGS);
 332		DCCP_INC_STATS_BH(DCCP_MIB_OUTRSTS);
 333		return;
 334	}
 335
 336	kfree_skb(skb);
 337}
 338
 339static struct request_sock_ops dccp6_request_sock_ops = {
 340	.family		= AF_INET6,
 341	.obj_size	= sizeof(struct dccp6_request_sock),
 342	.rtx_syn_ack	= dccp_v6_send_response,
 343	.send_ack	= dccp_reqsk_send_ack,
 344	.destructor	= dccp_v6_reqsk_destructor,
 345	.send_reset	= dccp_v6_ctl_send_reset,
 346	.syn_ack_timeout = dccp_syn_ack_timeout,
 347};
 348
 349static struct sock *dccp_v6_hnd_req(struct sock *sk,struct sk_buff *skb)
 350{
 351	const struct dccp_hdr *dh = dccp_hdr(skb);
 352	const struct ipv6hdr *iph = ipv6_hdr(skb);
 353	struct sock *nsk;
 354	struct request_sock **prev;
 355	/* Find possible connection requests. */
 356	struct request_sock *req = inet6_csk_search_req(sk, &prev,
 357							dh->dccph_sport,
 358							&iph->saddr,
 359							&iph->daddr,
 360							inet6_iif(skb));
 361	if (req != NULL)
 362		return dccp_check_req(sk, skb, req, prev);
 363
 364	nsk = __inet6_lookup_established(sock_net(sk), &dccp_hashinfo,
 365					 &iph->saddr, dh->dccph_sport,
 366					 &iph->daddr, ntohs(dh->dccph_dport),
 367					 inet6_iif(skb));
 368	if (nsk != NULL) {
 369		if (nsk->sk_state != DCCP_TIME_WAIT) {
 370			bh_lock_sock(nsk);
 371			return nsk;
 372		}
 373		inet_twsk_put(inet_twsk(nsk));
 374		return NULL;
 375	}
 376
 377	return sk;
 378}
 379
 380static int dccp_v6_conn_request(struct sock *sk, struct sk_buff *skb)
 381{
 382	struct request_sock *req;
 383	struct dccp_request_sock *dreq;
 384	struct inet6_request_sock *ireq6;
 385	struct ipv6_pinfo *np = inet6_sk(sk);
 386	const __be32 service = dccp_hdr_request(skb)->dccph_req_service;
 387	struct dccp_skb_cb *dcb = DCCP_SKB_CB(skb);
 388
 389	if (skb->protocol == htons(ETH_P_IP))
 390		return dccp_v4_conn_request(sk, skb);
 391
 392	if (!ipv6_unicast_destination(skb))
 393		return 0;	/* discard, don't send a reset here */
 394
 
 
 
 
 
 395	if (dccp_bad_service_code(sk, service)) {
 396		dcb->dccpd_reset_code = DCCP_RESET_CODE_BAD_SERVICE_CODE;
 397		goto drop;
 398	}
 399	/*
 400	 * There are no SYN attacks on IPv6, yet...
 401	 */
 402	dcb->dccpd_reset_code = DCCP_RESET_CODE_TOO_BUSY;
 403	if (inet_csk_reqsk_queue_is_full(sk))
 404		goto drop;
 405
 406	if (sk_acceptq_is_full(sk) && inet_csk_reqsk_queue_young(sk) > 1)
 407		goto drop;
 408
 409	req = inet6_reqsk_alloc(&dccp6_request_sock_ops);
 410	if (req == NULL)
 411		goto drop;
 412
 413	if (dccp_reqsk_init(req, dccp_sk(sk), skb))
 414		goto drop_and_free;
 415
 416	dreq = dccp_rsk(req);
 417	if (dccp_parse_options(sk, dreq, skb))
 418		goto drop_and_free;
 419
 
 
 
 
 
 
 420	if (security_inet_conn_request(sk, skb, req))
 421		goto drop_and_free;
 422
 423	ireq6 = inet6_rsk(req);
 424	ireq6->rmt_addr = ipv6_hdr(skb)->saddr;
 425	ireq6->loc_addr = ipv6_hdr(skb)->daddr;
 426
 427	if (ipv6_opt_accepted(sk, skb) ||
 428	    np->rxopt.bits.rxinfo || np->rxopt.bits.rxoinfo ||
 429	    np->rxopt.bits.rxhlim || np->rxopt.bits.rxohlim) {
 430		atomic_inc(&skb->users);
 431		ireq6->pktopts = skb;
 432	}
 433	ireq6->iif = sk->sk_bound_dev_if;
 434
 435	/* So that link locals have meaning */
 436	if (!sk->sk_bound_dev_if &&
 437	    ipv6_addr_type(&ireq6->rmt_addr) & IPV6_ADDR_LINKLOCAL)
 438		ireq6->iif = inet6_iif(skb);
 439
 440	/*
 441	 * Step 3: Process LISTEN state
 442	 *
 443	 *   Set S.ISR, S.GSR, S.SWL, S.SWH from packet or Init Cookie
 444	 *
 445	 * Setting S.SWL/S.SWH to is deferred to dccp_create_openreq_child().
 446	 */
 447	dreq->dreq_isr	   = dcb->dccpd_seq;
 448	dreq->dreq_gsr     = dreq->dreq_isr;
 449	dreq->dreq_iss	   = dccp_v6_init_sequence(skb);
 450	dreq->dreq_gss     = dreq->dreq_iss;
 451	dreq->dreq_service = service;
 452
 453	if (dccp_v6_send_response(sk, req, NULL))
 454		goto drop_and_free;
 455
 456	inet6_csk_reqsk_queue_hash_add(sk, req, DCCP_TIMEOUT_INIT);
 
 457	return 0;
 458
 459drop_and_free:
 460	reqsk_free(req);
 461drop:
 462	DCCP_INC_STATS_BH(DCCP_MIB_ATTEMPTFAILS);
 463	return -1;
 464}
 465
 466static struct sock *dccp_v6_request_recv_sock(struct sock *sk,
 467					      struct sk_buff *skb,
 468					      struct request_sock *req,
 469					      struct dst_entry *dst)
 
 
 470{
 471	struct inet6_request_sock *ireq6 = inet6_rsk(req);
 472	struct ipv6_pinfo *newnp, *np = inet6_sk(sk);
 
 
 473	struct inet_sock *newinet;
 474	struct dccp6_sock *newdp6;
 475	struct sock *newsk;
 476	struct ipv6_txoptions *opt;
 477
 478	if (skb->protocol == htons(ETH_P_IP)) {
 479		/*
 480		 *	v6 mapped
 481		 */
 482		newsk = dccp_v4_request_recv_sock(sk, skb, req, dst);
 
 483		if (newsk == NULL)
 484			return NULL;
 485
 486		newdp6 = (struct dccp6_sock *)newsk;
 487		newinet = inet_sk(newsk);
 488		newinet->pinet6 = &newdp6->inet6;
 489		newnp = inet6_sk(newsk);
 490
 491		memcpy(newnp, np, sizeof(struct ipv6_pinfo));
 492
 493		ipv6_addr_set_v4mapped(newinet->inet_daddr, &newnp->daddr);
 494
 495		ipv6_addr_set_v4mapped(newinet->inet_saddr, &newnp->saddr);
 496
 497		newnp->rcv_saddr = newnp->saddr;
 498
 499		inet_csk(newsk)->icsk_af_ops = &dccp_ipv6_mapped;
 500		newsk->sk_backlog_rcv = dccp_v4_do_rcv;
 501		newnp->pktoptions  = NULL;
 502		newnp->opt	   = NULL;
 503		newnp->mcast_oif   = inet6_iif(skb);
 504		newnp->mcast_hops  = ipv6_hdr(skb)->hop_limit;
 
 
 
 505
 506		/*
 507		 * No need to charge this sock to the relevant IPv6 refcnt debug socks count
 508		 * here, dccp_create_openreq_child now does this for us, see the comment in
 509		 * that function for the gory details. -acme
 510		 */
 511
 512		/* It is tricky place. Until this moment IPv4 tcp
 513		   worked with IPv6 icsk.icsk_af_ops.
 514		   Sync it now.
 515		 */
 516		dccp_sync_mss(newsk, inet_csk(newsk)->icsk_pmtu_cookie);
 517
 518		return newsk;
 519	}
 520
 521	opt = np->opt;
 522
 523	if (sk_acceptq_is_full(sk))
 524		goto out_overflow;
 525
 526	if (dst == NULL) {
 527		struct in6_addr *final_p, final;
 528		struct flowi6 fl6;
 529
 530		memset(&fl6, 0, sizeof(fl6));
 531		fl6.flowi6_proto = IPPROTO_DCCP;
 532		fl6.daddr = ireq6->rmt_addr;
 533		final_p = fl6_update_dst(&fl6, opt, &final);
 534		fl6.saddr = ireq6->loc_addr;
 535		fl6.flowi6_oif = sk->sk_bound_dev_if;
 536		fl6.fl6_dport = inet_rsk(req)->rmt_port;
 537		fl6.fl6_sport = inet_rsk(req)->loc_port;
 538		security_sk_classify_flow(sk, flowi6_to_flowi(&fl6));
 539
 540		dst = ip6_dst_lookup_flow(sk, &fl6, final_p, false);
 541		if (IS_ERR(dst))
 542			goto out;
 543	}
 544
 545	newsk = dccp_create_openreq_child(sk, req, skb);
 546	if (newsk == NULL)
 547		goto out_nonewsk;
 548
 549	/*
 550	 * No need to charge this sock to the relevant IPv6 refcnt debug socks
 551	 * count here, dccp_create_openreq_child now does this for us, see the
 552	 * comment in that function for the gory details. -acme
 553	 */
 554
 555	__ip6_dst_store(newsk, dst, NULL, NULL);
 556	newsk->sk_route_caps = dst->dev->features & ~(NETIF_F_IP_CSUM |
 557						      NETIF_F_TSO);
 558	newdp6 = (struct dccp6_sock *)newsk;
 559	newinet = inet_sk(newsk);
 560	newinet->pinet6 = &newdp6->inet6;
 561	newnp = inet6_sk(newsk);
 562
 563	memcpy(newnp, np, sizeof(struct ipv6_pinfo));
 564
 565	newnp->daddr = ireq6->rmt_addr;
 566	newnp->saddr = ireq6->loc_addr;
 567	newnp->rcv_saddr = ireq6->loc_addr;
 568	newsk->sk_bound_dev_if = ireq6->iif;
 569
 570	/* Now IPv6 options...
 571
 572	   First: no IPv4 options.
 573	 */
 574	newinet->inet_opt = NULL;
 575
 576	/* Clone RX bits */
 577	newnp->rxopt.all = np->rxopt.all;
 578
 579	/* Clone pktoptions received with SYN */
 
 
 580	newnp->pktoptions = NULL;
 581	if (ireq6->pktopts != NULL) {
 582		newnp->pktoptions = skb_clone(ireq6->pktopts, GFP_ATOMIC);
 583		consume_skb(ireq6->pktopts);
 584		ireq6->pktopts = NULL;
 585		if (newnp->pktoptions)
 586			skb_set_owner_r(newnp->pktoptions, newsk);
 587	}
 588	newnp->opt	  = NULL;
 589	newnp->mcast_oif  = inet6_iif(skb);
 590	newnp->mcast_hops = ipv6_hdr(skb)->hop_limit;
 591
 592	/*
 593	 * Clone native IPv6 options from listening socket (if any)
 594	 *
 595	 * Yes, keeping reference count would be much more clever, but we make
 596	 * one more one thing there: reattach optmem to newsk.
 597	 */
 598	if (opt != NULL) {
 599		newnp->opt = ipv6_dup_options(newsk, opt);
 600		if (opt != np->opt)
 601			sock_kfree_s(sk, opt, opt->tot_len);
 
 
 602	}
 603
 604	inet_csk(newsk)->icsk_ext_hdr_len = 0;
 605	if (newnp->opt != NULL)
 606		inet_csk(newsk)->icsk_ext_hdr_len = (newnp->opt->opt_nflen +
 607						     newnp->opt->opt_flen);
 608
 609	dccp_sync_mss(newsk, dst_mtu(dst));
 610
 611	newinet->inet_daddr = newinet->inet_saddr = LOOPBACK4_IPV6;
 612	newinet->inet_rcv_saddr = LOOPBACK4_IPV6;
 613
 614	if (__inet_inherit_port(sk, newsk) < 0) {
 615		sock_put(newsk);
 
 616		goto out;
 617	}
 618	__inet6_hash(newsk, NULL);
 
 
 
 
 
 
 619
 620	return newsk;
 621
 622out_overflow:
 623	NET_INC_STATS_BH(sock_net(sk), LINUX_MIB_LISTENOVERFLOWS);
 624out_nonewsk:
 625	dst_release(dst);
 626out:
 627	NET_INC_STATS_BH(sock_net(sk), LINUX_MIB_LISTENDROPS);
 628	if (opt != NULL && opt != np->opt)
 629		sock_kfree_s(sk, opt, opt->tot_len);
 630	return NULL;
 631}
 632
 633/* The socket must have it's spinlock held when we get
 634 * here.
 635 *
 636 * We have a potential double-lock case here, so even when
 637 * doing backlog processing we use the BH locking scheme.
 638 * This is because we cannot sleep with the original spinlock
 639 * held.
 640 */
 641static int dccp_v6_do_rcv(struct sock *sk, struct sk_buff *skb)
 642{
 643	struct ipv6_pinfo *np = inet6_sk(sk);
 644	struct sk_buff *opt_skb = NULL;
 645
 646	/* Imagine: socket is IPv6. IPv4 packet arrives,
 647	   goes to IPv4 receive handler and backlogged.
 648	   From backlog it always goes here. Kerboom...
 649	   Fortunately, dccp_rcv_established and rcv_established
 650	   handle them correctly, but it is not case with
 651	   dccp_v6_hnd_req and dccp_v6_ctl_send_reset().   --ANK
 652	 */
 653
 654	if (skb->protocol == htons(ETH_P_IP))
 655		return dccp_v4_do_rcv(sk, skb);
 656
 657	if (sk_filter(sk, skb))
 658		goto discard;
 659
 660	/*
 661	 * socket locking is here for SMP purposes as backlog rcv is currently
 662	 * called with bh processing disabled.
 663	 */
 664
 665	/* Do Stevens' IPV6_PKTOPTIONS.
 666
 667	   Yes, guys, it is the only place in our code, where we
 668	   may make it not affecting IPv4.
 669	   The rest of code is protocol independent,
 670	   and I do not like idea to uglify IPv4.
 671
 672	   Actually, all the idea behind IPV6_PKTOPTIONS
 673	   looks not very well thought. For now we latch
 674	   options, received in the last packet, enqueued
 675	   by tcp. Feel free to propose better solution.
 676					       --ANK (980728)
 677	 */
 678	if (np->rxopt.all)
 679	/*
 680	 * FIXME: Add handling of IPV6_PKTOPTIONS skb. See the comments below
 681	 *        (wrt ipv6_pktopions) and net/ipv6/tcp_ipv6.c for an example.
 682	 */
 683		opt_skb = skb_clone(skb, GFP_ATOMIC);
 684
 685	if (sk->sk_state == DCCP_OPEN) { /* Fast path */
 686		if (dccp_rcv_established(sk, skb, dccp_hdr(skb), skb->len))
 687			goto reset;
 688		if (opt_skb) {
 689			/* XXX This is where we would goto ipv6_pktoptions. */
 690			__kfree_skb(opt_skb);
 691		}
 692		return 0;
 693	}
 694
 695	/*
 696	 *  Step 3: Process LISTEN state
 697	 *     If S.state == LISTEN,
 698	 *	 If P.type == Request or P contains a valid Init Cookie option,
 699	 *	      (* Must scan the packet's options to check for Init
 700	 *		 Cookies.  Only Init Cookies are processed here,
 701	 *		 however; other options are processed in Step 8.  This
 702	 *		 scan need only be performed if the endpoint uses Init
 703	 *		 Cookies *)
 704	 *	      (* Generate a new socket and switch to that socket *)
 705	 *	      Set S := new socket for this port pair
 706	 *	      S.state = RESPOND
 707	 *	      Choose S.ISS (initial seqno) or set from Init Cookies
 708	 *	      Initialize S.GAR := S.ISS
 709	 *	      Set S.ISR, S.GSR, S.SWL, S.SWH from packet or Init Cookies
 710	 *	      Continue with S.state == RESPOND
 711	 *	      (* A Response packet will be generated in Step 11 *)
 712	 *	 Otherwise,
 713	 *	      Generate Reset(No Connection) unless P.type == Reset
 714	 *	      Drop packet and return
 715	 *
 716	 * NOTE: the check for the packet types is done in
 717	 *	 dccp_rcv_state_process
 718	 */
 719	if (sk->sk_state == DCCP_LISTEN) {
 720		struct sock *nsk = dccp_v6_hnd_req(sk, skb);
 721
 722		if (nsk == NULL)
 723			goto discard;
 724		/*
 725		 * Queue it on the new socket if the new socket is active,
 726		 * otherwise we just shortcircuit this and continue with
 727		 * the new socket..
 728		 */
 729		if (nsk != sk) {
 730			if (dccp_child_process(sk, nsk, skb))
 731				goto reset;
 732			if (opt_skb != NULL)
 733				__kfree_skb(opt_skb);
 734			return 0;
 735		}
 736	}
 737
 738	if (dccp_rcv_state_process(sk, skb, dccp_hdr(skb), skb->len))
 739		goto reset;
 740	if (opt_skb) {
 741		/* XXX This is where we would goto ipv6_pktoptions. */
 742		__kfree_skb(opt_skb);
 743	}
 744	return 0;
 745
 746reset:
 747	dccp_v6_ctl_send_reset(sk, skb);
 748discard:
 749	if (opt_skb != NULL)
 750		__kfree_skb(opt_skb);
 751	kfree_skb(skb);
 752	return 0;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 753}
 754
 755static int dccp_v6_rcv(struct sk_buff *skb)
 756{
 757	const struct dccp_hdr *dh;
 
 758	struct sock *sk;
 759	int min_cov;
 760
 761	/* Step 1: Check header basics */
 762
 763	if (dccp_invalid_packet(skb))
 764		goto discard_it;
 765
 766	/* Step 1: If header checksum is incorrect, drop packet and return. */
 767	if (dccp_v6_csum_finish(skb, &ipv6_hdr(skb)->saddr,
 768				     &ipv6_hdr(skb)->daddr)) {
 769		DCCP_WARN("dropped packet with invalid checksum\n");
 770		goto discard_it;
 771	}
 772
 773	dh = dccp_hdr(skb);
 774
 775	DCCP_SKB_CB(skb)->dccpd_seq  = dccp_hdr_seq(dh);
 776	DCCP_SKB_CB(skb)->dccpd_type = dh->dccph_type;
 777
 778	if (dccp_packet_without_ack(skb))
 779		DCCP_SKB_CB(skb)->dccpd_ack_seq = DCCP_PKT_WITHOUT_ACK_SEQ;
 780	else
 781		DCCP_SKB_CB(skb)->dccpd_ack_seq = dccp_hdr_ack_seq(skb);
 782
 783	/* Step 2:
 784	 *	Look up flow ID in table and get corresponding socket */
 785	sk = __inet6_lookup_skb(&dccp_hashinfo, skb,
 786			        dh->dccph_sport, dh->dccph_dport);
 787	/*
 788	 * Step 2:
 789	 *	If no socket ...
 790	 */
 791	if (sk == NULL) {
 792		dccp_pr_debug("failed to look up flow ID in table and "
 793			      "get corresponding socket\n");
 794		goto no_dccp_socket;
 795	}
 796
 797	/*
 798	 * Step 2:
 799	 *	... or S.state == TIMEWAIT,
 800	 *		Generate Reset(No Connection) unless P.type == Reset
 801	 *		Drop packet and return
 802	 */
 803	if (sk->sk_state == DCCP_TIME_WAIT) {
 804		dccp_pr_debug("sk->sk_state == DCCP_TIME_WAIT: do_time_wait\n");
 805		inet_twsk_put(inet_twsk(sk));
 806		goto no_dccp_socket;
 807	}
 808
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 809	/*
 810	 * RFC 4340, sec. 9.2.1: Minimum Checksum Coverage
 811	 *	o if MinCsCov = 0, only packets with CsCov = 0 are accepted
 812	 *	o if MinCsCov > 0, also accept packets with CsCov >= MinCsCov
 813	 */
 814	min_cov = dccp_sk(sk)->dccps_pcrlen;
 815	if (dh->dccph_cscov  &&  (min_cov == 0 || dh->dccph_cscov < min_cov))  {
 816		dccp_pr_debug("Packet CsCov %d does not satisfy MinCsCov %d\n",
 817			      dh->dccph_cscov, min_cov);
 818		/* FIXME: send Data Dropped option (see also dccp_v4_rcv) */
 819		goto discard_and_relse;
 820	}
 821
 822	if (!xfrm6_policy_check(sk, XFRM_POLICY_IN, skb))
 823		goto discard_and_relse;
 
 824
 825	return sk_receive_skb(sk, skb, 1) ? -1 : 0;
 
 826
 827no_dccp_socket:
 828	if (!xfrm6_policy_check(NULL, XFRM_POLICY_IN, skb))
 829		goto discard_it;
 830	/*
 831	 * Step 2:
 832	 *	If no socket ...
 833	 *		Generate Reset(No Connection) unless P.type == Reset
 834	 *		Drop packet and return
 835	 */
 836	if (dh->dccph_type != DCCP_PKT_RESET) {
 837		DCCP_SKB_CB(skb)->dccpd_reset_code =
 838					DCCP_RESET_CODE_NO_CONNECTION;
 839		dccp_v6_ctl_send_reset(sk, skb);
 840	}
 841
 842discard_it:
 843	kfree_skb(skb);
 844	return 0;
 845
 846discard_and_relse:
 847	sock_put(sk);
 
 848	goto discard_it;
 849}
 850
 851static int dccp_v6_connect(struct sock *sk, struct sockaddr *uaddr,
 852			   int addr_len)
 853{
 854	struct sockaddr_in6 *usin = (struct sockaddr_in6 *)uaddr;
 855	struct inet_connection_sock *icsk = inet_csk(sk);
 856	struct inet_sock *inet = inet_sk(sk);
 857	struct ipv6_pinfo *np = inet6_sk(sk);
 858	struct dccp_sock *dp = dccp_sk(sk);
 859	struct in6_addr *saddr = NULL, *final_p, final;
 
 860	struct flowi6 fl6;
 861	struct dst_entry *dst;
 862	int addr_type;
 863	int err;
 864
 865	dp->dccps_role = DCCP_ROLE_CLIENT;
 866
 867	if (addr_len < SIN6_LEN_RFC2133)
 868		return -EINVAL;
 869
 870	if (usin->sin6_family != AF_INET6)
 871		return -EAFNOSUPPORT;
 872
 873	memset(&fl6, 0, sizeof(fl6));
 874
 875	if (np->sndflow) {
 876		fl6.flowlabel = usin->sin6_flowinfo & IPV6_FLOWINFO_MASK;
 877		IP6_ECN_flow_init(fl6.flowlabel);
 878		if (fl6.flowlabel & IPV6_FLOWLABEL_MASK) {
 879			struct ip6_flowlabel *flowlabel;
 880			flowlabel = fl6_sock_lookup(sk, fl6.flowlabel);
 881			if (flowlabel == NULL)
 882				return -EINVAL;
 883			usin->sin6_addr = flowlabel->dst;
 884			fl6_sock_release(flowlabel);
 885		}
 886	}
 887	/*
 888	 * connect() to INADDR_ANY means loopback (BSD'ism).
 889	 */
 890	if (ipv6_addr_any(&usin->sin6_addr))
 891		usin->sin6_addr.s6_addr[15] = 1;
 892
 893	addr_type = ipv6_addr_type(&usin->sin6_addr);
 894
 895	if (addr_type & IPV6_ADDR_MULTICAST)
 896		return -ENETUNREACH;
 897
 898	if (addr_type & IPV6_ADDR_LINKLOCAL) {
 899		if (addr_len >= sizeof(struct sockaddr_in6) &&
 900		    usin->sin6_scope_id) {
 901			/* If interface is set while binding, indices
 902			 * must coincide.
 903			 */
 904			if (sk->sk_bound_dev_if &&
 905			    sk->sk_bound_dev_if != usin->sin6_scope_id)
 906				return -EINVAL;
 907
 908			sk->sk_bound_dev_if = usin->sin6_scope_id;
 909		}
 910
 911		/* Connect to link-local address requires an interface */
 912		if (!sk->sk_bound_dev_if)
 913			return -EINVAL;
 914	}
 915
 916	np->daddr = usin->sin6_addr;
 917	np->flow_label = fl6.flowlabel;
 918
 919	/*
 920	 * DCCP over IPv4
 921	 */
 922	if (addr_type == IPV6_ADDR_MAPPED) {
 923		u32 exthdrlen = icsk->icsk_ext_hdr_len;
 924		struct sockaddr_in sin;
 925
 926		SOCK_DEBUG(sk, "connect: ipv4 mapped\n");
 927
 928		if (__ipv6_only_sock(sk))
 929			return -ENETUNREACH;
 930
 931		sin.sin_family = AF_INET;
 932		sin.sin_port = usin->sin6_port;
 933		sin.sin_addr.s_addr = usin->sin6_addr.s6_addr32[3];
 934
 935		icsk->icsk_af_ops = &dccp_ipv6_mapped;
 936		sk->sk_backlog_rcv = dccp_v4_do_rcv;
 937
 938		err = dccp_v4_connect(sk, (struct sockaddr *)&sin, sizeof(sin));
 939		if (err) {
 940			icsk->icsk_ext_hdr_len = exthdrlen;
 941			icsk->icsk_af_ops = &dccp_ipv6_af_ops;
 942			sk->sk_backlog_rcv = dccp_v6_do_rcv;
 943			goto failure;
 944		}
 945		ipv6_addr_set_v4mapped(inet->inet_saddr, &np->saddr);
 946		ipv6_addr_set_v4mapped(inet->inet_rcv_saddr, &np->rcv_saddr);
 947
 948		return err;
 949	}
 950
 951	if (!ipv6_addr_any(&np->rcv_saddr))
 952		saddr = &np->rcv_saddr;
 953
 954	fl6.flowi6_proto = IPPROTO_DCCP;
 955	fl6.daddr = np->daddr;
 956	fl6.saddr = saddr ? *saddr : np->saddr;
 957	fl6.flowi6_oif = sk->sk_bound_dev_if;
 958	fl6.fl6_dport = usin->sin6_port;
 959	fl6.fl6_sport = inet->inet_sport;
 960	security_sk_classify_flow(sk, flowi6_to_flowi(&fl6));
 961
 962	final_p = fl6_update_dst(&fl6, np->opt, &final);
 
 963
 964	dst = ip6_dst_lookup_flow(sk, &fl6, final_p, true);
 965	if (IS_ERR(dst)) {
 966		err = PTR_ERR(dst);
 967		goto failure;
 968	}
 969
 970	if (saddr == NULL) {
 971		saddr = &fl6.saddr;
 972		np->rcv_saddr = *saddr;
 
 
 
 973	}
 974
 975	/* set the source address */
 976	np->saddr = *saddr;
 977	inet->inet_rcv_saddr = LOOPBACK4_IPV6;
 978
 979	__ip6_dst_store(sk, dst, NULL, NULL);
 980
 981	icsk->icsk_ext_hdr_len = 0;
 982	if (np->opt != NULL)
 983		icsk->icsk_ext_hdr_len = (np->opt->opt_flen +
 984					  np->opt->opt_nflen);
 985
 986	inet->inet_dport = usin->sin6_port;
 987
 988	dccp_set_state(sk, DCCP_REQUESTING);
 989	err = inet6_hash_connect(&dccp_death_row, sk);
 990	if (err)
 991		goto late_failure;
 992
 993	dp->dccps_iss = secure_dccpv6_sequence_number(np->saddr.s6_addr32,
 994						      np->daddr.s6_addr32,
 995						      inet->inet_sport,
 996						      inet->inet_dport);
 997	err = dccp_connect(sk);
 998	if (err)
 999		goto late_failure;
1000
1001	return 0;
1002
1003late_failure:
1004	dccp_set_state(sk, DCCP_CLOSED);
 
1005	__sk_dst_reset(sk);
1006failure:
1007	inet->inet_dport = 0;
1008	sk->sk_route_caps = 0;
1009	return err;
1010}
1011
1012static const struct inet_connection_sock_af_ops dccp_ipv6_af_ops = {
1013	.queue_xmit	   = inet6_csk_xmit,
1014	.send_check	   = dccp_v6_send_check,
1015	.rebuild_header	   = inet6_sk_rebuild_header,
1016	.conn_request	   = dccp_v6_conn_request,
1017	.syn_recv_sock	   = dccp_v6_request_recv_sock,
1018	.net_header_len	   = sizeof(struct ipv6hdr),
1019	.setsockopt	   = ipv6_setsockopt,
1020	.getsockopt	   = ipv6_getsockopt,
1021	.addr2sockaddr	   = inet6_csk_addr2sockaddr,
1022	.sockaddr_len	   = sizeof(struct sockaddr_in6),
1023	.bind_conflict	   = inet6_csk_bind_conflict,
1024#ifdef CONFIG_COMPAT
1025	.compat_setsockopt = compat_ipv6_setsockopt,
1026	.compat_getsockopt = compat_ipv6_getsockopt,
1027#endif
1028};
1029
1030/*
1031 *	DCCP over IPv4 via INET6 API
1032 */
1033static const struct inet_connection_sock_af_ops dccp_ipv6_mapped = {
1034	.queue_xmit	   = ip_queue_xmit,
1035	.send_check	   = dccp_v4_send_check,
1036	.rebuild_header	   = inet_sk_rebuild_header,
1037	.conn_request	   = dccp_v6_conn_request,
1038	.syn_recv_sock	   = dccp_v6_request_recv_sock,
1039	.net_header_len	   = sizeof(struct iphdr),
1040	.setsockopt	   = ipv6_setsockopt,
1041	.getsockopt	   = ipv6_getsockopt,
1042	.addr2sockaddr	   = inet6_csk_addr2sockaddr,
1043	.sockaddr_len	   = sizeof(struct sockaddr_in6),
1044#ifdef CONFIG_COMPAT
1045	.compat_setsockopt = compat_ipv6_setsockopt,
1046	.compat_getsockopt = compat_ipv6_getsockopt,
1047#endif
1048};
1049
 
 
 
 
 
 
1050/* NOTE: A lot of things set to zero explicitly by call to
1051 *       sk_alloc() so need not be done here.
1052 */
1053static int dccp_v6_init_sock(struct sock *sk)
1054{
1055	static __u8 dccp_v6_ctl_sock_initialized;
1056	int err = dccp_init_sock(sk, dccp_v6_ctl_sock_initialized);
1057
1058	if (err == 0) {
1059		if (unlikely(!dccp_v6_ctl_sock_initialized))
1060			dccp_v6_ctl_sock_initialized = 1;
1061		inet_csk(sk)->icsk_af_ops = &dccp_ipv6_af_ops;
 
1062	}
1063
1064	return err;
1065}
1066
1067static void dccp_v6_destroy_sock(struct sock *sk)
1068{
1069	dccp_destroy_sock(sk);
1070	inet6_destroy_sock(sk);
1071}
1072
1073static struct timewait_sock_ops dccp6_timewait_sock_ops = {
1074	.twsk_obj_size	= sizeof(struct dccp6_timewait_sock),
1075};
1076
1077static struct proto dccp_v6_prot = {
1078	.name		   = "DCCPv6",
1079	.owner		   = THIS_MODULE,
1080	.close		   = dccp_close,
1081	.connect	   = dccp_v6_connect,
1082	.disconnect	   = dccp_disconnect,
1083	.ioctl		   = dccp_ioctl,
1084	.init		   = dccp_v6_init_sock,
1085	.setsockopt	   = dccp_setsockopt,
1086	.getsockopt	   = dccp_getsockopt,
1087	.sendmsg	   = dccp_sendmsg,
1088	.recvmsg	   = dccp_recvmsg,
1089	.backlog_rcv	   = dccp_v6_do_rcv,
1090	.hash		   = dccp_v6_hash,
1091	.unhash		   = inet_unhash,
1092	.accept		   = inet_csk_accept,
1093	.get_port	   = inet_csk_get_port,
1094	.shutdown	   = dccp_shutdown,
1095	.destroy	   = dccp_v6_destroy_sock,
1096	.orphan_count	   = &dccp_orphan_count,
1097	.max_header	   = MAX_DCCP_HEADER,
1098	.obj_size	   = sizeof(struct dccp6_sock),
1099	.slab_flags	   = SLAB_DESTROY_BY_RCU,
 
1100	.rsk_prot	   = &dccp6_request_sock_ops,
1101	.twsk_prot	   = &dccp6_timewait_sock_ops,
1102	.h.hashinfo	   = &dccp_hashinfo,
1103#ifdef CONFIG_COMPAT
1104	.compat_setsockopt = compat_dccp_setsockopt,
1105	.compat_getsockopt = compat_dccp_getsockopt,
1106#endif
1107};
1108
1109static const struct inet6_protocol dccp_v6_protocol = {
1110	.handler	= dccp_v6_rcv,
1111	.err_handler	= dccp_v6_err,
1112	.flags		= INET6_PROTO_NOPOLICY | INET6_PROTO_FINAL,
1113};
1114
1115static const struct proto_ops inet6_dccp_ops = {
1116	.family		   = PF_INET6,
1117	.owner		   = THIS_MODULE,
1118	.release	   = inet6_release,
1119	.bind		   = inet6_bind,
1120	.connect	   = inet_stream_connect,
1121	.socketpair	   = sock_no_socketpair,
1122	.accept		   = inet_accept,
1123	.getname	   = inet6_getname,
1124	.poll		   = dccp_poll,
1125	.ioctl		   = inet6_ioctl,
 
1126	.listen		   = inet_dccp_listen,
1127	.shutdown	   = inet_shutdown,
1128	.setsockopt	   = sock_common_setsockopt,
1129	.getsockopt	   = sock_common_getsockopt,
1130	.sendmsg	   = inet_sendmsg,
1131	.recvmsg	   = sock_common_recvmsg,
1132	.mmap		   = sock_no_mmap,
1133	.sendpage	   = sock_no_sendpage,
1134#ifdef CONFIG_COMPAT
1135	.compat_setsockopt = compat_sock_common_setsockopt,
1136	.compat_getsockopt = compat_sock_common_getsockopt,
1137#endif
1138};
1139
1140static struct inet_protosw dccp_v6_protosw = {
1141	.type		= SOCK_DCCP,
1142	.protocol	= IPPROTO_DCCP,
1143	.prot		= &dccp_v6_prot,
1144	.ops		= &inet6_dccp_ops,
1145	.flags		= INET_PROTOSW_ICSK,
1146};
1147
1148static int __net_init dccp_v6_init_net(struct net *net)
1149{
 
 
1150	if (dccp_hashinfo.bhash == NULL)
1151		return -ESOCKTNOSUPPORT;
1152
1153	return inet_ctl_sock_create(&net->dccp.v6_ctl_sk, PF_INET6,
1154				    SOCK_DCCP, IPPROTO_DCCP, net);
1155}
1156
1157static void __net_exit dccp_v6_exit_net(struct net *net)
1158{
1159	inet_ctl_sock_destroy(net->dccp.v6_ctl_sk);
 
 
 
 
 
 
 
1160}
1161
1162static struct pernet_operations dccp_v6_ops = {
1163	.init   = dccp_v6_init_net,
1164	.exit   = dccp_v6_exit_net,
 
 
 
1165};
1166
1167static int __init dccp_v6_init(void)
1168{
1169	int err = proto_register(&dccp_v6_prot, 1);
1170
1171	if (err != 0)
1172		goto out;
1173
1174	err = inet6_add_protocol(&dccp_v6_protocol, IPPROTO_DCCP);
1175	if (err != 0)
1176		goto out_unregister_proto;
1177
1178	inet6_register_protosw(&dccp_v6_protosw);
1179
1180	err = register_pernet_subsys(&dccp_v6_ops);
1181	if (err != 0)
1182		goto out_destroy_ctl_sock;
 
 
 
 
 
1183out:
1184	return err;
1185
 
1186out_destroy_ctl_sock:
1187	inet6_del_protocol(&dccp_v6_protocol, IPPROTO_DCCP);
1188	inet6_unregister_protosw(&dccp_v6_protosw);
1189out_unregister_proto:
1190	proto_unregister(&dccp_v6_prot);
1191	goto out;
1192}
1193
1194static void __exit dccp_v6_exit(void)
1195{
1196	unregister_pernet_subsys(&dccp_v6_ops);
1197	inet6_del_protocol(&dccp_v6_protocol, IPPROTO_DCCP);
 
1198	inet6_unregister_protosw(&dccp_v6_protosw);
1199	proto_unregister(&dccp_v6_prot);
1200}
1201
1202module_init(dccp_v6_init);
1203module_exit(dccp_v6_exit);
1204
1205/*
1206 * __stringify doesn't likes enums, so use SOCK_DCCP (6) and IPPROTO_DCCP (33)
1207 * values directly, Also cover the case where the protocol is not specified,
1208 * i.e. net-pf-PF_INET6-proto-0-type-SOCK_DCCP
1209 */
1210MODULE_ALIAS_NET_PF_PROTO_TYPE(PF_INET6, 33, 6);
1211MODULE_ALIAS_NET_PF_PROTO_TYPE(PF_INET6, 0, 6);
1212MODULE_LICENSE("GPL");
1213MODULE_AUTHOR("Arnaldo Carvalho de Melo <acme@mandriva.com>");
1214MODULE_DESCRIPTION("DCCPv6 - Datagram Congestion Controlled Protocol");
v6.8
   1// SPDX-License-Identifier: GPL-2.0-or-later
   2/*
   3 *	DCCP over IPv6
   4 *	Linux INET6 implementation
   5 *
   6 *	Based on net/dccp6/ipv6.c
   7 *
   8 *	Arnaldo Carvalho de Melo <acme@ghostprotocols.net>
 
 
 
 
 
   9 */
  10
  11#include <linux/module.h>
  12#include <linux/random.h>
  13#include <linux/slab.h>
  14#include <linux/xfrm.h>
  15#include <linux/string.h>
  16
  17#include <net/addrconf.h>
  18#include <net/inet_common.h>
  19#include <net/inet_hashtables.h>
  20#include <net/inet_sock.h>
  21#include <net/inet6_connection_sock.h>
  22#include <net/inet6_hashtables.h>
  23#include <net/ip6_route.h>
  24#include <net/ipv6.h>
  25#include <net/protocol.h>
  26#include <net/transp_v6.h>
  27#include <net/ip6_checksum.h>
  28#include <net/xfrm.h>
  29#include <net/secure_seq.h>
  30#include <net/netns/generic.h>
  31#include <net/sock.h>
  32
  33#include "dccp.h"
  34#include "ipv6.h"
  35#include "feat.h"
  36
  37struct dccp_v6_pernet {
  38	struct sock *v6_ctl_sk;
  39};
  40
  41static unsigned int dccp_v6_pernet_id __read_mostly;
  42
  43/* The per-net v6_ctl_sk is used for sending RSTs and ACKs */
  44
  45static const struct inet_connection_sock_af_ops dccp_ipv6_mapped;
  46static const struct inet_connection_sock_af_ops dccp_ipv6_af_ops;
  47
 
 
 
 
 
 
 
 
 
 
 
 
 
  48/* add pseudo-header to DCCP checksum stored in skb->csum */
  49static inline __sum16 dccp_v6_csum_finish(struct sk_buff *skb,
  50				      const struct in6_addr *saddr,
  51				      const struct in6_addr *daddr)
  52{
  53	return csum_ipv6_magic(saddr, daddr, skb->len, IPPROTO_DCCP, skb->csum);
  54}
  55
  56static inline void dccp_v6_send_check(struct sock *sk, struct sk_buff *skb)
  57{
  58	struct ipv6_pinfo *np = inet6_sk(sk);
  59	struct dccp_hdr *dh = dccp_hdr(skb);
  60
  61	dccp_csum_outgoing(skb);
  62	dh->dccph_checksum = dccp_v6_csum_finish(skb, &np->saddr, &sk->sk_v6_daddr);
  63}
  64
  65static inline __u64 dccp_v6_init_sequence(struct sk_buff *skb)
  66{
  67	return secure_dccpv6_sequence_number(ipv6_hdr(skb)->daddr.s6_addr32,
  68					     ipv6_hdr(skb)->saddr.s6_addr32,
  69					     dccp_hdr(skb)->dccph_dport,
  70					     dccp_hdr(skb)->dccph_sport     );
  71
  72}
  73
  74static int dccp_v6_err(struct sk_buff *skb, struct inet6_skb_parm *opt,
  75			u8 type, u8 code, int offset, __be32 info)
  76{
  77	const struct ipv6hdr *hdr;
  78	const struct dccp_hdr *dh;
  79	struct dccp_sock *dp;
  80	struct ipv6_pinfo *np;
  81	struct sock *sk;
  82	int err;
  83	__u64 seq;
  84	struct net *net = dev_net(skb->dev);
  85
  86	if (!pskb_may_pull(skb, offset + sizeof(*dh)))
  87		return -EINVAL;
  88	dh = (struct dccp_hdr *)(skb->data + offset);
  89	if (!pskb_may_pull(skb, offset + __dccp_basic_hdr_len(dh)))
  90		return -EINVAL;
  91	hdr = (const struct ipv6hdr *)skb->data;
  92	dh = (struct dccp_hdr *)(skb->data + offset);
  93
  94	sk = __inet6_lookup_established(net, &dccp_hashinfo,
  95					&hdr->daddr, dh->dccph_dport,
  96					&hdr->saddr, ntohs(dh->dccph_sport),
  97					inet6_iif(skb), 0);
  98
  99	if (!sk) {
 100		__ICMP6_INC_STATS(net, __in6_dev_get(skb->dev),
 101				  ICMP6_MIB_INERRORS);
 102		return -ENOENT;
 103	}
 104
 105	if (sk->sk_state == DCCP_TIME_WAIT) {
 106		inet_twsk_put(inet_twsk(sk));
 107		return 0;
 108	}
 109	seq = dccp_hdr_seq(dh);
 110	if (sk->sk_state == DCCP_NEW_SYN_RECV) {
 111		dccp_req_err(sk, seq);
 112		return 0;
 113	}
 114
 115	bh_lock_sock(sk);
 116	if (sock_owned_by_user(sk))
 117		__NET_INC_STATS(net, LINUX_MIB_LOCKDROPPEDICMPS);
 118
 119	if (sk->sk_state == DCCP_CLOSED)
 120		goto out;
 121
 122	dp = dccp_sk(sk);
 
 123	if ((1 << sk->sk_state) & ~(DCCPF_REQUESTING | DCCPF_LISTEN) &&
 124	    !between48(seq, dp->dccps_awl, dp->dccps_awh)) {
 125		__NET_INC_STATS(net, LINUX_MIB_OUTOFWINDOWICMPS);
 126		goto out;
 127	}
 128
 129	np = inet6_sk(sk);
 130
 131	if (type == NDISC_REDIRECT) {
 132		if (!sock_owned_by_user(sk)) {
 133			struct dst_entry *dst = __sk_dst_check(sk, np->dst_cookie);
 134
 135			if (dst)
 136				dst->ops->redirect(dst, sk, skb);
 137		}
 138		goto out;
 139	}
 140
 141	if (type == ICMPV6_PKT_TOOBIG) {
 142		struct dst_entry *dst = NULL;
 143
 144		if (!ip6_sk_accept_pmtu(sk))
 145			goto out;
 146
 147		if (sock_owned_by_user(sk))
 148			goto out;
 149		if ((1 << sk->sk_state) & (DCCPF_LISTEN | DCCPF_CLOSED))
 150			goto out;
 151
 152		dst = inet6_csk_update_pmtu(sk, ntohl(info));
 153		if (!dst)
 154			goto out;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 155
 156		if (inet_csk(sk)->icsk_pmtu_cookie > dst_mtu(dst))
 157			dccp_sync_mss(sk, dst_mtu(dst));
 
 
 158		goto out;
 159	}
 160
 161	icmpv6_err_convert(type, code, &err);
 162
 163	/* Might be for an request_sock */
 164	switch (sk->sk_state) {
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 165	case DCCP_REQUESTING:
 166	case DCCP_RESPOND:  /* Cannot happen.
 167			       It can, it SYNs are crossed. --ANK */
 168		if (!sock_owned_by_user(sk)) {
 169			__DCCP_INC_STATS(DCCP_MIB_ATTEMPTFAILS);
 170			sk->sk_err = err;
 171			/*
 172			 * Wake people up to see the error
 173			 * (see connect in sock.c)
 174			 */
 175			sk_error_report(sk);
 176			dccp_done(sk);
 177		} else {
 178			WRITE_ONCE(sk->sk_err_soft, err);
 179		}
 180		goto out;
 181	}
 182
 183	if (!sock_owned_by_user(sk) && inet6_test_bit(RECVERR6, sk)) {
 184		sk->sk_err = err;
 185		sk_error_report(sk);
 186	} else {
 187		WRITE_ONCE(sk->sk_err_soft, err);
 188	}
 189out:
 190	bh_unlock_sock(sk);
 191	sock_put(sk);
 192	return 0;
 193}
 194
 195
 196static int dccp_v6_send_response(const struct sock *sk, struct request_sock *req)
 
 197{
 198	struct inet_request_sock *ireq = inet_rsk(req);
 199	struct ipv6_pinfo *np = inet6_sk(sk);
 200	struct sk_buff *skb;
 
 201	struct in6_addr *final_p, final;
 202	struct flowi6 fl6;
 203	int err = -1;
 204	struct dst_entry *dst;
 205
 206	memset(&fl6, 0, sizeof(fl6));
 207	fl6.flowi6_proto = IPPROTO_DCCP;
 208	fl6.daddr = ireq->ir_v6_rmt_addr;
 209	fl6.saddr = ireq->ir_v6_loc_addr;
 210	fl6.flowlabel = 0;
 211	fl6.flowi6_oif = ireq->ir_iif;
 212	fl6.fl6_dport = ireq->ir_rmt_port;
 213	fl6.fl6_sport = htons(ireq->ir_num);
 214	security_req_classify_flow(req, flowi6_to_flowi_common(&fl6));
 215
 
 216
 217	rcu_read_lock();
 218	final_p = fl6_update_dst(&fl6, rcu_dereference(np->opt), &final);
 219	rcu_read_unlock();
 220
 221	dst = ip6_dst_lookup_flow(sock_net(sk), sk, &fl6, final_p);
 222	if (IS_ERR(dst)) {
 223		err = PTR_ERR(dst);
 224		dst = NULL;
 225		goto done;
 226	}
 227
 228	skb = dccp_make_response(sk, dst, req);
 229	if (skb != NULL) {
 230		struct dccp_hdr *dh = dccp_hdr(skb);
 231		struct ipv6_txoptions *opt;
 232
 233		dh->dccph_checksum = dccp_v6_csum_finish(skb,
 234							 &ireq->ir_v6_loc_addr,
 235							 &ireq->ir_v6_rmt_addr);
 236		fl6.daddr = ireq->ir_v6_rmt_addr;
 237		rcu_read_lock();
 238		opt = ireq->ipv6_opt;
 239		if (!opt)
 240			opt = rcu_dereference(np->opt);
 241		err = ip6_xmit(sk, skb, &fl6, READ_ONCE(sk->sk_mark), opt,
 242			       np->tclass, READ_ONCE(sk->sk_priority));
 243		rcu_read_unlock();
 244		err = net_xmit_eval(err);
 245	}
 246
 247done:
 
 
 248	dst_release(dst);
 249	return err;
 250}
 251
 252static void dccp_v6_reqsk_destructor(struct request_sock *req)
 253{
 254	dccp_feat_list_purge(&dccp_rsk(req)->dreq_featneg);
 255	kfree(inet_rsk(req)->ipv6_opt);
 256	kfree_skb(inet_rsk(req)->pktopts);
 257}
 258
 259static void dccp_v6_ctl_send_reset(const struct sock *sk, struct sk_buff *rxskb)
 260{
 261	const struct ipv6hdr *rxip6h;
 262	struct sk_buff *skb;
 263	struct flowi6 fl6;
 264	struct net *net = dev_net(skb_dst(rxskb)->dev);
 265	struct dccp_v6_pernet *pn;
 266	struct sock *ctl_sk;
 267	struct dst_entry *dst;
 268
 269	if (dccp_hdr(rxskb)->dccph_type == DCCP_PKT_RESET)
 270		return;
 271
 272	if (!ipv6_unicast_destination(rxskb))
 273		return;
 274
 275	pn = net_generic(net, dccp_v6_pernet_id);
 276	ctl_sk = pn->v6_ctl_sk;
 277	skb = dccp_ctl_make_reset(ctl_sk, rxskb);
 278	if (skb == NULL)
 279		return;
 280
 281	rxip6h = ipv6_hdr(rxskb);
 282	dccp_hdr(skb)->dccph_checksum = dccp_v6_csum_finish(skb, &rxip6h->saddr,
 283							    &rxip6h->daddr);
 284
 285	memset(&fl6, 0, sizeof(fl6));
 286	fl6.daddr = rxip6h->saddr;
 287	fl6.saddr = rxip6h->daddr;
 288
 289	fl6.flowi6_proto = IPPROTO_DCCP;
 290	fl6.flowi6_oif = inet6_iif(rxskb);
 291	fl6.fl6_dport = dccp_hdr(skb)->dccph_dport;
 292	fl6.fl6_sport = dccp_hdr(skb)->dccph_sport;
 293	security_skb_classify_flow(rxskb, flowi6_to_flowi_common(&fl6));
 294
 295	/* sk = NULL, but it is safe for now. RST socket required. */
 296	dst = ip6_dst_lookup_flow(sock_net(ctl_sk), ctl_sk, &fl6, NULL);
 297	if (!IS_ERR(dst)) {
 298		skb_dst_set(skb, dst);
 299		ip6_xmit(ctl_sk, skb, &fl6, 0, NULL, 0, 0);
 300		DCCP_INC_STATS(DCCP_MIB_OUTSEGS);
 301		DCCP_INC_STATS(DCCP_MIB_OUTRSTS);
 302		return;
 303	}
 304
 305	kfree_skb(skb);
 306}
 307
 308static struct request_sock_ops dccp6_request_sock_ops = {
 309	.family		= AF_INET6,
 310	.obj_size	= sizeof(struct dccp6_request_sock),
 311	.rtx_syn_ack	= dccp_v6_send_response,
 312	.send_ack	= dccp_reqsk_send_ack,
 313	.destructor	= dccp_v6_reqsk_destructor,
 314	.send_reset	= dccp_v6_ctl_send_reset,
 315	.syn_ack_timeout = dccp_syn_ack_timeout,
 316};
 317
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 318static int dccp_v6_conn_request(struct sock *sk, struct sk_buff *skb)
 319{
 320	struct request_sock *req;
 321	struct dccp_request_sock *dreq;
 322	struct inet_request_sock *ireq;
 323	struct ipv6_pinfo *np = inet6_sk(sk);
 324	const __be32 service = dccp_hdr_request(skb)->dccph_req_service;
 325	struct dccp_skb_cb *dcb = DCCP_SKB_CB(skb);
 326
 327	if (skb->protocol == htons(ETH_P_IP))
 328		return dccp_v4_conn_request(sk, skb);
 329
 330	if (!ipv6_unicast_destination(skb))
 331		return 0;	/* discard, don't send a reset here */
 332
 333	if (ipv6_addr_v4mapped(&ipv6_hdr(skb)->saddr)) {
 334		__IP6_INC_STATS(sock_net(sk), NULL, IPSTATS_MIB_INHDRERRORS);
 335		return 0;
 336	}
 337
 338	if (dccp_bad_service_code(sk, service)) {
 339		dcb->dccpd_reset_code = DCCP_RESET_CODE_BAD_SERVICE_CODE;
 340		goto drop;
 341	}
 342	/*
 343	 * There are no SYN attacks on IPv6, yet...
 344	 */
 345	dcb->dccpd_reset_code = DCCP_RESET_CODE_TOO_BUSY;
 346	if (inet_csk_reqsk_queue_is_full(sk))
 347		goto drop;
 348
 349	if (sk_acceptq_is_full(sk))
 350		goto drop;
 351
 352	req = inet_reqsk_alloc(&dccp6_request_sock_ops, sk, true);
 353	if (req == NULL)
 354		goto drop;
 355
 356	if (dccp_reqsk_init(req, dccp_sk(sk), skb))
 357		goto drop_and_free;
 358
 359	dreq = dccp_rsk(req);
 360	if (dccp_parse_options(sk, dreq, skb))
 361		goto drop_and_free;
 362
 363	ireq = inet_rsk(req);
 364	ireq->ir_v6_rmt_addr = ipv6_hdr(skb)->saddr;
 365	ireq->ir_v6_loc_addr = ipv6_hdr(skb)->daddr;
 366	ireq->ireq_family = AF_INET6;
 367	ireq->ir_mark = inet_request_mark(sk, skb);
 368
 369	if (security_inet_conn_request(sk, skb, req))
 370		goto drop_and_free;
 371
 372	if (ipv6_opt_accepted(sk, skb, IP6CB(skb)) ||
 
 
 
 
 373	    np->rxopt.bits.rxinfo || np->rxopt.bits.rxoinfo ||
 374	    np->rxopt.bits.rxhlim || np->rxopt.bits.rxohlim) {
 375		refcount_inc(&skb->users);
 376		ireq->pktopts = skb;
 377	}
 378	ireq->ir_iif = READ_ONCE(sk->sk_bound_dev_if);
 379
 380	/* So that link locals have meaning */
 381	if (!ireq->ir_iif &&
 382	    ipv6_addr_type(&ireq->ir_v6_rmt_addr) & IPV6_ADDR_LINKLOCAL)
 383		ireq->ir_iif = inet6_iif(skb);
 384
 385	/*
 386	 * Step 3: Process LISTEN state
 387	 *
 388	 *   Set S.ISR, S.GSR, S.SWL, S.SWH from packet or Init Cookie
 389	 *
 390	 * Setting S.SWL/S.SWH to is deferred to dccp_create_openreq_child().
 391	 */
 392	dreq->dreq_isr	   = dcb->dccpd_seq;
 393	dreq->dreq_gsr     = dreq->dreq_isr;
 394	dreq->dreq_iss	   = dccp_v6_init_sequence(skb);
 395	dreq->dreq_gss     = dreq->dreq_iss;
 396	dreq->dreq_service = service;
 397
 398	if (dccp_v6_send_response(sk, req))
 399		goto drop_and_free;
 400
 401	inet_csk_reqsk_queue_hash_add(sk, req, DCCP_TIMEOUT_INIT);
 402	reqsk_put(req);
 403	return 0;
 404
 405drop_and_free:
 406	reqsk_free(req);
 407drop:
 408	__DCCP_INC_STATS(DCCP_MIB_ATTEMPTFAILS);
 409	return -1;
 410}
 411
 412static struct sock *dccp_v6_request_recv_sock(const struct sock *sk,
 413					      struct sk_buff *skb,
 414					      struct request_sock *req,
 415					      struct dst_entry *dst,
 416					      struct request_sock *req_unhash,
 417					      bool *own_req)
 418{
 419	struct inet_request_sock *ireq = inet_rsk(req);
 420	struct ipv6_pinfo *newnp;
 421	const struct ipv6_pinfo *np = inet6_sk(sk);
 422	struct ipv6_txoptions *opt;
 423	struct inet_sock *newinet;
 424	struct dccp6_sock *newdp6;
 425	struct sock *newsk;
 
 426
 427	if (skb->protocol == htons(ETH_P_IP)) {
 428		/*
 429		 *	v6 mapped
 430		 */
 431		newsk = dccp_v4_request_recv_sock(sk, skb, req, dst,
 432						  req_unhash, own_req);
 433		if (newsk == NULL)
 434			return NULL;
 435
 436		newdp6 = (struct dccp6_sock *)newsk;
 437		newinet = inet_sk(newsk);
 438		newinet->pinet6 = &newdp6->inet6;
 439		newnp = inet6_sk(newsk);
 440
 441		memcpy(newnp, np, sizeof(struct ipv6_pinfo));
 442
 443		newnp->saddr = newsk->sk_v6_rcv_saddr;
 
 
 
 
 444
 445		inet_csk(newsk)->icsk_af_ops = &dccp_ipv6_mapped;
 446		newsk->sk_backlog_rcv = dccp_v4_do_rcv;
 447		newnp->pktoptions  = NULL;
 448		newnp->opt	   = NULL;
 449		newnp->ipv6_mc_list = NULL;
 450		newnp->ipv6_ac_list = NULL;
 451		newnp->ipv6_fl_list = NULL;
 452		newnp->mcast_oif   = inet_iif(skb);
 453		newnp->mcast_hops  = ip_hdr(skb)->ttl;
 454
 455		/*
 456		 * No need to charge this sock to the relevant IPv6 refcnt debug socks count
 457		 * here, dccp_create_openreq_child now does this for us, see the comment in
 458		 * that function for the gory details. -acme
 459		 */
 460
 461		/* It is tricky place. Until this moment IPv4 tcp
 462		   worked with IPv6 icsk.icsk_af_ops.
 463		   Sync it now.
 464		 */
 465		dccp_sync_mss(newsk, inet_csk(newsk)->icsk_pmtu_cookie);
 466
 467		return newsk;
 468	}
 469
 
 470
 471	if (sk_acceptq_is_full(sk))
 472		goto out_overflow;
 473
 474	if (!dst) {
 
 475		struct flowi6 fl6;
 476
 477		dst = inet6_csk_route_req(sk, &fl6, req, IPPROTO_DCCP);
 478		if (!dst)
 
 
 
 
 
 
 
 
 
 
 479			goto out;
 480	}
 481
 482	newsk = dccp_create_openreq_child(sk, req, skb);
 483	if (newsk == NULL)
 484		goto out_nonewsk;
 485
 486	/*
 487	 * No need to charge this sock to the relevant IPv6 refcnt debug socks
 488	 * count here, dccp_create_openreq_child now does this for us, see the
 489	 * comment in that function for the gory details. -acme
 490	 */
 491
 492	ip6_dst_store(newsk, dst, NULL, NULL);
 493	newsk->sk_route_caps = dst->dev->features & ~(NETIF_F_IP_CSUM |
 494						      NETIF_F_TSO);
 495	newdp6 = (struct dccp6_sock *)newsk;
 496	newinet = inet_sk(newsk);
 497	newinet->pinet6 = &newdp6->inet6;
 498	newnp = inet6_sk(newsk);
 499
 500	memcpy(newnp, np, sizeof(struct ipv6_pinfo));
 501
 502	newsk->sk_v6_daddr	= ireq->ir_v6_rmt_addr;
 503	newnp->saddr		= ireq->ir_v6_loc_addr;
 504	newsk->sk_v6_rcv_saddr	= ireq->ir_v6_loc_addr;
 505	newsk->sk_bound_dev_if	= ireq->ir_iif;
 506
 507	/* Now IPv6 options...
 508
 509	   First: no IPv4 options.
 510	 */
 511	newinet->inet_opt = NULL;
 512
 513	/* Clone RX bits */
 514	newnp->rxopt.all = np->rxopt.all;
 515
 516	newnp->ipv6_mc_list = NULL;
 517	newnp->ipv6_ac_list = NULL;
 518	newnp->ipv6_fl_list = NULL;
 519	newnp->pktoptions = NULL;
 
 
 
 
 
 
 
 520	newnp->opt	  = NULL;
 521	newnp->mcast_oif  = inet6_iif(skb);
 522	newnp->mcast_hops = ipv6_hdr(skb)->hop_limit;
 523
 524	/*
 525	 * Clone native IPv6 options from listening socket (if any)
 526	 *
 527	 * Yes, keeping reference count would be much more clever, but we make
 528	 * one more one thing there: reattach optmem to newsk.
 529	 */
 530	opt = ireq->ipv6_opt;
 531	if (!opt)
 532		opt = rcu_dereference(np->opt);
 533	if (opt) {
 534		opt = ipv6_dup_options(newsk, opt);
 535		RCU_INIT_POINTER(newnp->opt, opt);
 536	}
 
 537	inet_csk(newsk)->icsk_ext_hdr_len = 0;
 538	if (opt)
 539		inet_csk(newsk)->icsk_ext_hdr_len = opt->opt_nflen +
 540						    opt->opt_flen;
 541
 542	dccp_sync_mss(newsk, dst_mtu(dst));
 543
 544	newinet->inet_daddr = newinet->inet_saddr = LOOPBACK4_IPV6;
 545	newinet->inet_rcv_saddr = LOOPBACK4_IPV6;
 546
 547	if (__inet_inherit_port(sk, newsk) < 0) {
 548		inet_csk_prepare_forced_close(newsk);
 549		dccp_done(newsk);
 550		goto out;
 551	}
 552	*own_req = inet_ehash_nolisten(newsk, req_to_sk(req_unhash), NULL);
 553	/* Clone pktoptions received with SYN, if we own the req */
 554	if (*own_req && ireq->pktopts) {
 555		newnp->pktoptions = skb_clone_and_charge_r(ireq->pktopts, newsk);
 556		consume_skb(ireq->pktopts);
 557		ireq->pktopts = NULL;
 558	}
 559
 560	return newsk;
 561
 562out_overflow:
 563	__NET_INC_STATS(sock_net(sk), LINUX_MIB_LISTENOVERFLOWS);
 564out_nonewsk:
 565	dst_release(dst);
 566out:
 567	__NET_INC_STATS(sock_net(sk), LINUX_MIB_LISTENDROPS);
 
 
 568	return NULL;
 569}
 570
 571/* The socket must have it's spinlock held when we get
 572 * here.
 573 *
 574 * We have a potential double-lock case here, so even when
 575 * doing backlog processing we use the BH locking scheme.
 576 * This is because we cannot sleep with the original spinlock
 577 * held.
 578 */
 579static int dccp_v6_do_rcv(struct sock *sk, struct sk_buff *skb)
 580{
 581	struct ipv6_pinfo *np = inet6_sk(sk);
 582	struct sk_buff *opt_skb = NULL;
 583
 584	/* Imagine: socket is IPv6. IPv4 packet arrives,
 585	   goes to IPv4 receive handler and backlogged.
 586	   From backlog it always goes here. Kerboom...
 587	   Fortunately, dccp_rcv_established and rcv_established
 588	   handle them correctly, but it is not case with
 589	   dccp_v6_hnd_req and dccp_v6_ctl_send_reset().   --ANK
 590	 */
 591
 592	if (skb->protocol == htons(ETH_P_IP))
 593		return dccp_v4_do_rcv(sk, skb);
 594
 595	if (sk_filter(sk, skb))
 596		goto discard;
 597
 598	/*
 599	 * socket locking is here for SMP purposes as backlog rcv is currently
 600	 * called with bh processing disabled.
 601	 */
 602
 603	/* Do Stevens' IPV6_PKTOPTIONS.
 604
 605	   Yes, guys, it is the only place in our code, where we
 606	   may make it not affecting IPv4.
 607	   The rest of code is protocol independent,
 608	   and I do not like idea to uglify IPv4.
 609
 610	   Actually, all the idea behind IPV6_PKTOPTIONS
 611	   looks not very well thought. For now we latch
 612	   options, received in the last packet, enqueued
 613	   by tcp. Feel free to propose better solution.
 614					       --ANK (980728)
 615	 */
 616	if (np->rxopt.all)
 617		opt_skb = skb_clone_and_charge_r(skb, sk);
 
 
 
 
 618
 619	if (sk->sk_state == DCCP_OPEN) { /* Fast path */
 620		if (dccp_rcv_established(sk, skb, dccp_hdr(skb), skb->len))
 621			goto reset;
 622		if (opt_skb)
 623			goto ipv6_pktoptions;
 
 
 624		return 0;
 625	}
 626
 627	/*
 628	 *  Step 3: Process LISTEN state
 629	 *     If S.state == LISTEN,
 630	 *	 If P.type == Request or P contains a valid Init Cookie option,
 631	 *	      (* Must scan the packet's options to check for Init
 632	 *		 Cookies.  Only Init Cookies are processed here,
 633	 *		 however; other options are processed in Step 8.  This
 634	 *		 scan need only be performed if the endpoint uses Init
 635	 *		 Cookies *)
 636	 *	      (* Generate a new socket and switch to that socket *)
 637	 *	      Set S := new socket for this port pair
 638	 *	      S.state = RESPOND
 639	 *	      Choose S.ISS (initial seqno) or set from Init Cookies
 640	 *	      Initialize S.GAR := S.ISS
 641	 *	      Set S.ISR, S.GSR, S.SWL, S.SWH from packet or Init Cookies
 642	 *	      Continue with S.state == RESPOND
 643	 *	      (* A Response packet will be generated in Step 11 *)
 644	 *	 Otherwise,
 645	 *	      Generate Reset(No Connection) unless P.type == Reset
 646	 *	      Drop packet and return
 647	 *
 648	 * NOTE: the check for the packet types is done in
 649	 *	 dccp_rcv_state_process
 650	 */
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 651
 652	if (dccp_rcv_state_process(sk, skb, dccp_hdr(skb), skb->len))
 653		goto reset;
 654	if (opt_skb)
 655		goto ipv6_pktoptions;
 
 
 656	return 0;
 657
 658reset:
 659	dccp_v6_ctl_send_reset(sk, skb);
 660discard:
 661	if (opt_skb != NULL)
 662		__kfree_skb(opt_skb);
 663	kfree_skb(skb);
 664	return 0;
 665
 666/* Handling IPV6_PKTOPTIONS skb the similar
 667 * way it's done for net/ipv6/tcp_ipv6.c
 668 */
 669ipv6_pktoptions:
 670	if (!((1 << sk->sk_state) & (DCCPF_CLOSED | DCCPF_LISTEN))) {
 671		if (np->rxopt.bits.rxinfo || np->rxopt.bits.rxoinfo)
 672			WRITE_ONCE(np->mcast_oif, inet6_iif(opt_skb));
 673		if (np->rxopt.bits.rxhlim || np->rxopt.bits.rxohlim)
 674			WRITE_ONCE(np->mcast_hops, ipv6_hdr(opt_skb)->hop_limit);
 675		if (np->rxopt.bits.rxflow || np->rxopt.bits.rxtclass)
 676			np->rcv_flowinfo = ip6_flowinfo(ipv6_hdr(opt_skb));
 677		if (inet6_test_bit(REPFLOW, sk))
 678			np->flow_label = ip6_flowlabel(ipv6_hdr(opt_skb));
 679		if (ipv6_opt_accepted(sk, opt_skb,
 680				      &DCCP_SKB_CB(opt_skb)->header.h6)) {
 681			memmove(IP6CB(opt_skb),
 682				&DCCP_SKB_CB(opt_skb)->header.h6,
 683				sizeof(struct inet6_skb_parm));
 684			opt_skb = xchg(&np->pktoptions, opt_skb);
 685		} else {
 686			__kfree_skb(opt_skb);
 687			opt_skb = xchg(&np->pktoptions, NULL);
 688		}
 689	}
 690
 691	kfree_skb(opt_skb);
 692	return 0;
 693}
 694
 695static int dccp_v6_rcv(struct sk_buff *skb)
 696{
 697	const struct dccp_hdr *dh;
 698	bool refcounted;
 699	struct sock *sk;
 700	int min_cov;
 701
 702	/* Step 1: Check header basics */
 703
 704	if (dccp_invalid_packet(skb))
 705		goto discard_it;
 706
 707	/* Step 1: If header checksum is incorrect, drop packet and return. */
 708	if (dccp_v6_csum_finish(skb, &ipv6_hdr(skb)->saddr,
 709				     &ipv6_hdr(skb)->daddr)) {
 710		DCCP_WARN("dropped packet with invalid checksum\n");
 711		goto discard_it;
 712	}
 713
 714	dh = dccp_hdr(skb);
 715
 716	DCCP_SKB_CB(skb)->dccpd_seq  = dccp_hdr_seq(dh);
 717	DCCP_SKB_CB(skb)->dccpd_type = dh->dccph_type;
 718
 719	if (dccp_packet_without_ack(skb))
 720		DCCP_SKB_CB(skb)->dccpd_ack_seq = DCCP_PKT_WITHOUT_ACK_SEQ;
 721	else
 722		DCCP_SKB_CB(skb)->dccpd_ack_seq = dccp_hdr_ack_seq(skb);
 723
 724lookup:
 725	sk = __inet6_lookup_skb(&dccp_hashinfo, skb, __dccp_hdr_len(dh),
 726			        dh->dccph_sport, dh->dccph_dport,
 727				inet6_iif(skb), 0, &refcounted);
 728	if (!sk) {
 
 
 
 
 729		dccp_pr_debug("failed to look up flow ID in table and "
 730			      "get corresponding socket\n");
 731		goto no_dccp_socket;
 732	}
 733
 734	/*
 735	 * Step 2:
 736	 *	... or S.state == TIMEWAIT,
 737	 *		Generate Reset(No Connection) unless P.type == Reset
 738	 *		Drop packet and return
 739	 */
 740	if (sk->sk_state == DCCP_TIME_WAIT) {
 741		dccp_pr_debug("sk->sk_state == DCCP_TIME_WAIT: do_time_wait\n");
 742		inet_twsk_put(inet_twsk(sk));
 743		goto no_dccp_socket;
 744	}
 745
 746	if (sk->sk_state == DCCP_NEW_SYN_RECV) {
 747		struct request_sock *req = inet_reqsk(sk);
 748		struct sock *nsk;
 749
 750		sk = req->rsk_listener;
 751		if (unlikely(sk->sk_state != DCCP_LISTEN)) {
 752			inet_csk_reqsk_queue_drop_and_put(sk, req);
 753			goto lookup;
 754		}
 755		sock_hold(sk);
 756		refcounted = true;
 757		nsk = dccp_check_req(sk, skb, req);
 758		if (!nsk) {
 759			reqsk_put(req);
 760			goto discard_and_relse;
 761		}
 762		if (nsk == sk) {
 763			reqsk_put(req);
 764		} else if (dccp_child_process(sk, nsk, skb)) {
 765			dccp_v6_ctl_send_reset(sk, skb);
 766			goto discard_and_relse;
 767		} else {
 768			sock_put(sk);
 769			return 0;
 770		}
 771	}
 772	/*
 773	 * RFC 4340, sec. 9.2.1: Minimum Checksum Coverage
 774	 *	o if MinCsCov = 0, only packets with CsCov = 0 are accepted
 775	 *	o if MinCsCov > 0, also accept packets with CsCov >= MinCsCov
 776	 */
 777	min_cov = dccp_sk(sk)->dccps_pcrlen;
 778	if (dh->dccph_cscov  &&  (min_cov == 0 || dh->dccph_cscov < min_cov))  {
 779		dccp_pr_debug("Packet CsCov %d does not satisfy MinCsCov %d\n",
 780			      dh->dccph_cscov, min_cov);
 781		/* FIXME: send Data Dropped option (see also dccp_v4_rcv) */
 782		goto discard_and_relse;
 783	}
 784
 785	if (!xfrm6_policy_check(sk, XFRM_POLICY_IN, skb))
 786		goto discard_and_relse;
 787	nf_reset_ct(skb);
 788
 789	return __sk_receive_skb(sk, skb, 1, dh->dccph_doff * 4,
 790				refcounted) ? -1 : 0;
 791
 792no_dccp_socket:
 793	if (!xfrm6_policy_check(NULL, XFRM_POLICY_IN, skb))
 794		goto discard_it;
 795	/*
 796	 * Step 2:
 797	 *	If no socket ...
 798	 *		Generate Reset(No Connection) unless P.type == Reset
 799	 *		Drop packet and return
 800	 */
 801	if (dh->dccph_type != DCCP_PKT_RESET) {
 802		DCCP_SKB_CB(skb)->dccpd_reset_code =
 803					DCCP_RESET_CODE_NO_CONNECTION;
 804		dccp_v6_ctl_send_reset(sk, skb);
 805	}
 806
 807discard_it:
 808	kfree_skb(skb);
 809	return 0;
 810
 811discard_and_relse:
 812	if (refcounted)
 813		sock_put(sk);
 814	goto discard_it;
 815}
 816
 817static int dccp_v6_connect(struct sock *sk, struct sockaddr *uaddr,
 818			   int addr_len)
 819{
 820	struct sockaddr_in6 *usin = (struct sockaddr_in6 *)uaddr;
 821	struct inet_connection_sock *icsk = inet_csk(sk);
 822	struct inet_sock *inet = inet_sk(sk);
 823	struct ipv6_pinfo *np = inet6_sk(sk);
 824	struct dccp_sock *dp = dccp_sk(sk);
 825	struct in6_addr *saddr = NULL, *final_p, final;
 826	struct ipv6_txoptions *opt;
 827	struct flowi6 fl6;
 828	struct dst_entry *dst;
 829	int addr_type;
 830	int err;
 831
 832	dp->dccps_role = DCCP_ROLE_CLIENT;
 833
 834	if (addr_len < SIN6_LEN_RFC2133)
 835		return -EINVAL;
 836
 837	if (usin->sin6_family != AF_INET6)
 838		return -EAFNOSUPPORT;
 839
 840	memset(&fl6, 0, sizeof(fl6));
 841
 842	if (inet6_test_bit(SNDFLOW, sk)) {
 843		fl6.flowlabel = usin->sin6_flowinfo & IPV6_FLOWINFO_MASK;
 844		IP6_ECN_flow_init(fl6.flowlabel);
 845		if (fl6.flowlabel & IPV6_FLOWLABEL_MASK) {
 846			struct ip6_flowlabel *flowlabel;
 847			flowlabel = fl6_sock_lookup(sk, fl6.flowlabel);
 848			if (IS_ERR(flowlabel))
 849				return -EINVAL;
 
 850			fl6_sock_release(flowlabel);
 851		}
 852	}
 853	/*
 854	 * connect() to INADDR_ANY means loopback (BSD'ism).
 855	 */
 856	if (ipv6_addr_any(&usin->sin6_addr))
 857		usin->sin6_addr.s6_addr[15] = 1;
 858
 859	addr_type = ipv6_addr_type(&usin->sin6_addr);
 860
 861	if (addr_type & IPV6_ADDR_MULTICAST)
 862		return -ENETUNREACH;
 863
 864	if (addr_type & IPV6_ADDR_LINKLOCAL) {
 865		if (addr_len >= sizeof(struct sockaddr_in6) &&
 866		    usin->sin6_scope_id) {
 867			/* If interface is set while binding, indices
 868			 * must coincide.
 869			 */
 870			if (sk->sk_bound_dev_if &&
 871			    sk->sk_bound_dev_if != usin->sin6_scope_id)
 872				return -EINVAL;
 873
 874			sk->sk_bound_dev_if = usin->sin6_scope_id;
 875		}
 876
 877		/* Connect to link-local address requires an interface */
 878		if (!sk->sk_bound_dev_if)
 879			return -EINVAL;
 880	}
 881
 882	sk->sk_v6_daddr = usin->sin6_addr;
 883	np->flow_label = fl6.flowlabel;
 884
 885	/*
 886	 * DCCP over IPv4
 887	 */
 888	if (addr_type == IPV6_ADDR_MAPPED) {
 889		u32 exthdrlen = icsk->icsk_ext_hdr_len;
 890		struct sockaddr_in sin;
 891
 892		net_dbg_ratelimited("connect: ipv4 mapped\n");
 893
 894		if (ipv6_only_sock(sk))
 895			return -ENETUNREACH;
 896
 897		sin.sin_family = AF_INET;
 898		sin.sin_port = usin->sin6_port;
 899		sin.sin_addr.s_addr = usin->sin6_addr.s6_addr32[3];
 900
 901		icsk->icsk_af_ops = &dccp_ipv6_mapped;
 902		sk->sk_backlog_rcv = dccp_v4_do_rcv;
 903
 904		err = dccp_v4_connect(sk, (struct sockaddr *)&sin, sizeof(sin));
 905		if (err) {
 906			icsk->icsk_ext_hdr_len = exthdrlen;
 907			icsk->icsk_af_ops = &dccp_ipv6_af_ops;
 908			sk->sk_backlog_rcv = dccp_v6_do_rcv;
 909			goto failure;
 910		}
 911		np->saddr = sk->sk_v6_rcv_saddr;
 
 
 912		return err;
 913	}
 914
 915	if (!ipv6_addr_any(&sk->sk_v6_rcv_saddr))
 916		saddr = &sk->sk_v6_rcv_saddr;
 917
 918	fl6.flowi6_proto = IPPROTO_DCCP;
 919	fl6.daddr = sk->sk_v6_daddr;
 920	fl6.saddr = saddr ? *saddr : np->saddr;
 921	fl6.flowi6_oif = sk->sk_bound_dev_if;
 922	fl6.fl6_dport = usin->sin6_port;
 923	fl6.fl6_sport = inet->inet_sport;
 924	security_sk_classify_flow(sk, flowi6_to_flowi_common(&fl6));
 925
 926	opt = rcu_dereference_protected(np->opt, lockdep_sock_is_held(sk));
 927	final_p = fl6_update_dst(&fl6, opt, &final);
 928
 929	dst = ip6_dst_lookup_flow(sock_net(sk), sk, &fl6, final_p);
 930	if (IS_ERR(dst)) {
 931		err = PTR_ERR(dst);
 932		goto failure;
 933	}
 934
 935	if (saddr == NULL) {
 936		saddr = &fl6.saddr;
 937
 938		err = inet_bhash2_update_saddr(sk, saddr, AF_INET6);
 939		if (err)
 940			goto failure;
 941	}
 942
 943	/* set the source address */
 944	np->saddr = *saddr;
 945	inet->inet_rcv_saddr = LOOPBACK4_IPV6;
 946
 947	ip6_dst_store(sk, dst, NULL, NULL);
 948
 949	icsk->icsk_ext_hdr_len = 0;
 950	if (opt)
 951		icsk->icsk_ext_hdr_len = opt->opt_flen + opt->opt_nflen;
 
 952
 953	inet->inet_dport = usin->sin6_port;
 954
 955	dccp_set_state(sk, DCCP_REQUESTING);
 956	err = inet6_hash_connect(&dccp_death_row, sk);
 957	if (err)
 958		goto late_failure;
 959
 960	dp->dccps_iss = secure_dccpv6_sequence_number(np->saddr.s6_addr32,
 961						      sk->sk_v6_daddr.s6_addr32,
 962						      inet->inet_sport,
 963						      inet->inet_dport);
 964	err = dccp_connect(sk);
 965	if (err)
 966		goto late_failure;
 967
 968	return 0;
 969
 970late_failure:
 971	dccp_set_state(sk, DCCP_CLOSED);
 972	inet_bhash2_reset_saddr(sk);
 973	__sk_dst_reset(sk);
 974failure:
 975	inet->inet_dport = 0;
 976	sk->sk_route_caps = 0;
 977	return err;
 978}
 979
 980static const struct inet_connection_sock_af_ops dccp_ipv6_af_ops = {
 981	.queue_xmit	   = inet6_csk_xmit,
 982	.send_check	   = dccp_v6_send_check,
 983	.rebuild_header	   = inet6_sk_rebuild_header,
 984	.conn_request	   = dccp_v6_conn_request,
 985	.syn_recv_sock	   = dccp_v6_request_recv_sock,
 986	.net_header_len	   = sizeof(struct ipv6hdr),
 987	.setsockopt	   = ipv6_setsockopt,
 988	.getsockopt	   = ipv6_getsockopt,
 989	.addr2sockaddr	   = inet6_csk_addr2sockaddr,
 990	.sockaddr_len	   = sizeof(struct sockaddr_in6),
 
 
 
 
 
 991};
 992
 993/*
 994 *	DCCP over IPv4 via INET6 API
 995 */
 996static const struct inet_connection_sock_af_ops dccp_ipv6_mapped = {
 997	.queue_xmit	   = ip_queue_xmit,
 998	.send_check	   = dccp_v4_send_check,
 999	.rebuild_header	   = inet_sk_rebuild_header,
1000	.conn_request	   = dccp_v6_conn_request,
1001	.syn_recv_sock	   = dccp_v6_request_recv_sock,
1002	.net_header_len	   = sizeof(struct iphdr),
1003	.setsockopt	   = ipv6_setsockopt,
1004	.getsockopt	   = ipv6_getsockopt,
1005	.addr2sockaddr	   = inet6_csk_addr2sockaddr,
1006	.sockaddr_len	   = sizeof(struct sockaddr_in6),
 
 
 
 
1007};
1008
1009static void dccp_v6_sk_destruct(struct sock *sk)
1010{
1011	dccp_destruct_common(sk);
1012	inet6_sock_destruct(sk);
1013}
1014
1015/* NOTE: A lot of things set to zero explicitly by call to
1016 *       sk_alloc() so need not be done here.
1017 */
1018static int dccp_v6_init_sock(struct sock *sk)
1019{
1020	static __u8 dccp_v6_ctl_sock_initialized;
1021	int err = dccp_init_sock(sk, dccp_v6_ctl_sock_initialized);
1022
1023	if (err == 0) {
1024		if (unlikely(!dccp_v6_ctl_sock_initialized))
1025			dccp_v6_ctl_sock_initialized = 1;
1026		inet_csk(sk)->icsk_af_ops = &dccp_ipv6_af_ops;
1027		sk->sk_destruct = dccp_v6_sk_destruct;
1028	}
1029
1030	return err;
1031}
1032
 
 
 
 
 
 
1033static struct timewait_sock_ops dccp6_timewait_sock_ops = {
1034	.twsk_obj_size	= sizeof(struct dccp6_timewait_sock),
1035};
1036
1037static struct proto dccp_v6_prot = {
1038	.name		   = "DCCPv6",
1039	.owner		   = THIS_MODULE,
1040	.close		   = dccp_close,
1041	.connect	   = dccp_v6_connect,
1042	.disconnect	   = dccp_disconnect,
1043	.ioctl		   = dccp_ioctl,
1044	.init		   = dccp_v6_init_sock,
1045	.setsockopt	   = dccp_setsockopt,
1046	.getsockopt	   = dccp_getsockopt,
1047	.sendmsg	   = dccp_sendmsg,
1048	.recvmsg	   = dccp_recvmsg,
1049	.backlog_rcv	   = dccp_v6_do_rcv,
1050	.hash		   = inet6_hash,
1051	.unhash		   = inet_unhash,
1052	.accept		   = inet_csk_accept,
1053	.get_port	   = inet_csk_get_port,
1054	.shutdown	   = dccp_shutdown,
1055	.destroy	   = dccp_destroy_sock,
1056	.orphan_count	   = &dccp_orphan_count,
1057	.max_header	   = MAX_DCCP_HEADER,
1058	.obj_size	   = sizeof(struct dccp6_sock),
1059	.ipv6_pinfo_offset = offsetof(struct dccp6_sock, inet6),
1060	.slab_flags	   = SLAB_TYPESAFE_BY_RCU,
1061	.rsk_prot	   = &dccp6_request_sock_ops,
1062	.twsk_prot	   = &dccp6_timewait_sock_ops,
1063	.h.hashinfo	   = &dccp_hashinfo,
 
 
 
 
1064};
1065
1066static const struct inet6_protocol dccp_v6_protocol = {
1067	.handler	= dccp_v6_rcv,
1068	.err_handler	= dccp_v6_err,
1069	.flags		= INET6_PROTO_NOPOLICY | INET6_PROTO_FINAL,
1070};
1071
1072static const struct proto_ops inet6_dccp_ops = {
1073	.family		   = PF_INET6,
1074	.owner		   = THIS_MODULE,
1075	.release	   = inet6_release,
1076	.bind		   = inet6_bind,
1077	.connect	   = inet_stream_connect,
1078	.socketpair	   = sock_no_socketpair,
1079	.accept		   = inet_accept,
1080	.getname	   = inet6_getname,
1081	.poll		   = dccp_poll,
1082	.ioctl		   = inet6_ioctl,
1083	.gettstamp	   = sock_gettstamp,
1084	.listen		   = inet_dccp_listen,
1085	.shutdown	   = inet_shutdown,
1086	.setsockopt	   = sock_common_setsockopt,
1087	.getsockopt	   = sock_common_getsockopt,
1088	.sendmsg	   = inet_sendmsg,
1089	.recvmsg	   = sock_common_recvmsg,
1090	.mmap		   = sock_no_mmap,
 
1091#ifdef CONFIG_COMPAT
1092	.compat_ioctl	   = inet6_compat_ioctl,
 
1093#endif
1094};
1095
1096static struct inet_protosw dccp_v6_protosw = {
1097	.type		= SOCK_DCCP,
1098	.protocol	= IPPROTO_DCCP,
1099	.prot		= &dccp_v6_prot,
1100	.ops		= &inet6_dccp_ops,
1101	.flags		= INET_PROTOSW_ICSK,
1102};
1103
1104static int __net_init dccp_v6_init_net(struct net *net)
1105{
1106	struct dccp_v6_pernet *pn = net_generic(net, dccp_v6_pernet_id);
1107
1108	if (dccp_hashinfo.bhash == NULL)
1109		return -ESOCKTNOSUPPORT;
1110
1111	return inet_ctl_sock_create(&pn->v6_ctl_sk, PF_INET6,
1112				    SOCK_DCCP, IPPROTO_DCCP, net);
1113}
1114
1115static void __net_exit dccp_v6_exit_net(struct net *net)
1116{
1117	struct dccp_v6_pernet *pn = net_generic(net, dccp_v6_pernet_id);
1118
1119	inet_ctl_sock_destroy(pn->v6_ctl_sk);
1120}
1121
1122static void __net_exit dccp_v6_exit_batch(struct list_head *net_exit_list)
1123{
1124	inet_twsk_purge(&dccp_hashinfo, AF_INET6);
1125}
1126
1127static struct pernet_operations dccp_v6_ops = {
1128	.init   = dccp_v6_init_net,
1129	.exit   = dccp_v6_exit_net,
1130	.exit_batch = dccp_v6_exit_batch,
1131	.id	= &dccp_v6_pernet_id,
1132	.size   = sizeof(struct dccp_v6_pernet),
1133};
1134
1135static int __init dccp_v6_init(void)
1136{
1137	int err = proto_register(&dccp_v6_prot, 1);
1138
1139	if (err)
1140		goto out;
1141
 
 
 
 
1142	inet6_register_protosw(&dccp_v6_protosw);
1143
1144	err = register_pernet_subsys(&dccp_v6_ops);
1145	if (err)
1146		goto out_destroy_ctl_sock;
1147
1148	err = inet6_add_protocol(&dccp_v6_protocol, IPPROTO_DCCP);
1149	if (err)
1150		goto out_unregister_proto;
1151
1152out:
1153	return err;
1154out_unregister_proto:
1155	unregister_pernet_subsys(&dccp_v6_ops);
1156out_destroy_ctl_sock:
 
1157	inet6_unregister_protosw(&dccp_v6_protosw);
 
1158	proto_unregister(&dccp_v6_prot);
1159	goto out;
1160}
1161
1162static void __exit dccp_v6_exit(void)
1163{
 
1164	inet6_del_protocol(&dccp_v6_protocol, IPPROTO_DCCP);
1165	unregister_pernet_subsys(&dccp_v6_ops);
1166	inet6_unregister_protosw(&dccp_v6_protosw);
1167	proto_unregister(&dccp_v6_prot);
1168}
1169
1170module_init(dccp_v6_init);
1171module_exit(dccp_v6_exit);
1172
1173/*
1174 * __stringify doesn't likes enums, so use SOCK_DCCP (6) and IPPROTO_DCCP (33)
1175 * values directly, Also cover the case where the protocol is not specified,
1176 * i.e. net-pf-PF_INET6-proto-0-type-SOCK_DCCP
1177 */
1178MODULE_ALIAS_NET_PF_PROTO_TYPE(PF_INET6, 33, 6);
1179MODULE_ALIAS_NET_PF_PROTO_TYPE(PF_INET6, 0, 6);
1180MODULE_LICENSE("GPL");
1181MODULE_AUTHOR("Arnaldo Carvalho de Melo <acme@mandriva.com>");
1182MODULE_DESCRIPTION("DCCPv6 - Datagram Congestion Controlled Protocol");