From: "David S. Miller" <davem@redhat.com>
To: toml@us.ibm.com
Cc: netdev@oss.sgi.com, kuznet@ms2.inr.ac.ru
Subject: Re: IPSec: IPv6 random failures
Date: Thu, 22 May 2003 17:43:17 -0700 (PDT) [thread overview]
Message-ID: <20030522.174317.21915853.davem@redhat.com> (raw)
In-Reply-To: <20030522.155408.85396915.davem@redhat.com>
From: "David S. Miller" <davem@redhat.com>
Date: Thu, 22 May 2003 15:54:08 -0700 (PDT)
I'll see how much work it is to change all of ipv6 to store
addresses directly into the flowi's instead of via pointers.
Whoa, what a rats nest area of the ipv6 stack :-(((
Ok, this cleaned up a LOT of crap. Silly kmalloc's of in6_addr
objects and all sorts of junk like that (especially ip6_dst_lookup()).
The rt0_hdr handling was a little tricky, but I think I got it all
sorted out.
Can someone review and stress test out this patch for me?
One thing to look out for are not-fully initialized flowi
structures. Ie. there are only two valid ways to setup
such objects:
struct flowi fl = { .foo = x, .bar = y, ... };
and
struct flowi fl;
memset(&fl, 0, sizeof(fl));
fl.foo = x;
fl.bar = y;
...
So if there are any cases left that don't do this correctly
please let me know.
--- ./include/net/flow.h.~1~ Thu May 22 15:58:19 2003
+++ ./include/net/flow.h Thu May 22 17:25:11 2003
@@ -7,6 +7,8 @@
#ifndef _NET_FLOW_H
#define _NET_FLOW_H
+#include <linux/in6.h>
+
struct flowi {
int oif;
int iif;
@@ -21,8 +23,8 @@ struct flowi {
} ip4_u;
struct {
- struct in6_addr * daddr;
- struct in6_addr * saddr;
+ struct in6_addr daddr;
+ struct in6_addr saddr;
__u32 flowlabel;
} ip6_u;
--- ./include/net/xfrm.h.~1~ Thu May 22 16:00:14 2003
+++ ./include/net/xfrm.h Thu May 22 16:00:49 2003
@@ -315,14 +315,14 @@ static inline u32 __flow_hash4(struct fl
static inline u32 __flow_hash6(struct flowi *fl)
{
- u32 hash = fl->fl6_src->s6_addr32[2] ^
- fl->fl6_src->s6_addr32[3] ^
+ u32 hash = fl->fl6_src.s6_addr32[2] ^
+ fl->fl6_src.s6_addr32[3] ^
fl->fl_ip_sport;
hash = ((hash & 0xF0F0F0F0) >> 4) | ((hash & 0x0F0F0F0F) << 4);
- hash ^= fl->fl6_dst->s6_addr32[2] ^
- fl->fl6_dst->s6_addr32[3] ^
+ hash ^= fl->fl6_dst.s6_addr32[2] ^
+ fl->fl6_dst.s6_addr32[3] ^
fl->fl_ip_dport;
hash ^= (hash >> 10);
hash ^= (hash >> 20);
@@ -471,8 +471,8 @@ __xfrm4_selector_match(struct xfrm_selec
static inline int
__xfrm6_selector_match(struct xfrm_selector *sel, struct flowi *fl)
{
- return addr_match(fl->fl6_dst, &sel->daddr, sel->prefixlen_d) &&
- addr_match(fl->fl6_src, &sel->saddr, sel->prefixlen_s) &&
+ return addr_match(&fl->fl6_dst, &sel->daddr, sel->prefixlen_d) &&
+ addr_match(&fl->fl6_src, &sel->saddr, sel->prefixlen_s) &&
!((fl->fl_ip_dport^sel->dport)&sel->dport_mask) &&
!((fl->fl_ip_sport^sel->sport)&sel->sport_mask) &&
(fl->proto == sel->proto || !sel->proto) &&
@@ -654,7 +654,7 @@ xfrm_address_t *xfrm_flowi_daddr(struct
case AF_INET:
return (xfrm_address_t *)&fl->fl4_dst;
case AF_INET6:
- return (xfrm_address_t *)fl->fl6_dst;
+ return (xfrm_address_t *)&fl->fl6_dst;
}
return NULL;
}
@@ -666,7 +666,7 @@ xfrm_address_t *xfrm_flowi_saddr(struct
case AF_INET:
return (xfrm_address_t *)&fl->fl4_src;
case AF_INET6:
- return (xfrm_address_t *)fl->fl6_src;
+ return (xfrm_address_t *)&fl->fl6_src;
}
return NULL;
}
--- ./include/net/ipv6.h.~1~ Thu May 22 16:40:49 2003
+++ ./include/net/ipv6.h Thu May 22 16:41:00 2003
@@ -334,8 +334,7 @@ extern void ip6_flush_pending_frames(s
extern int ip6_dst_lookup(struct sock *sk,
struct dst_entry **dst,
- struct flowi *fl,
- struct in6_addr **saddr);
+ struct flowi *fl);
/*
* skb processing functions
--- ./net/ipv6/datagram.c.~1~ Thu May 22 16:00:14 2003
+++ ./net/ipv6/datagram.c Thu May 22 16:01:17 2003
@@ -80,7 +80,7 @@ void ipv6_local_error(struct sock *sk, i
iph = (struct ipv6hdr*)skb_put(skb, sizeof(struct ipv6hdr));
skb->nh.ipv6h = iph;
- ipv6_addr_copy(&iph->daddr, fl->fl6_dst);
+ ipv6_addr_copy(&iph->daddr, &fl->fl6_dst);
serr = SKB_EXT_ERR(skb);
serr->ee.ee_errno = err;
@@ -297,7 +297,8 @@ int datagram_send_ctl(struct msghdr *msg
goto exit_f;
}
- fl->fl6_src = &src_info->ipi6_addr;
+ ipv6_addr_copy(&fl->fl6_src,
+ &src_info->ipi6_addr);
}
break;
--- ./net/ipv6/icmp.c.~1~ Thu May 22 16:00:14 2003
+++ ./net/ipv6/icmp.c Thu May 22 17:36:53 2003
@@ -223,9 +223,10 @@ int icmpv6_push_pending_frames(struct so
if (skb_queue_len(&sk->write_queue) == 1) {
skb->csum = csum_partial((char *)icmp6h,
sizeof(struct icmp6hdr), skb->csum);
- icmp6h->icmp6_cksum = csum_ipv6_magic(fl->fl6_src,
- fl->fl6_dst,
- len, fl->proto, skb->csum);
+ icmp6h->icmp6_cksum = csum_ipv6_magic(&fl->fl6_src,
+ &fl->fl6_dst,
+ len, fl->proto,
+ skb->csum);
} else {
u32 tmp_csum = 0;
@@ -235,8 +236,8 @@ int icmpv6_push_pending_frames(struct so
tmp_csum = csum_partial((char *)icmp6h,
sizeof(struct icmp6hdr), tmp_csum);
- tmp_csum = csum_ipv6_magic(fl->fl6_src,
- fl->fl6_dst,
+ tmp_csum = csum_ipv6_magic(&fl->fl6_src,
+ &fl->fl6_dst,
len, fl->proto, tmp_csum);
icmp6h->icmp6_cksum = tmp_csum;
}
@@ -266,7 +267,7 @@ void icmpv6_send(struct sk_buff *skb, in
struct ipv6hdr *hdr = skb->nh.ipv6h;
struct sock *sk = icmpv6_socket->sk;
struct ipv6_pinfo *np = inet6_sk(sk);
- struct in6_addr *saddr = NULL, *tmp_saddr = NULL;
+ struct in6_addr *saddr = NULL;
struct dst_entry *dst;
struct icmp6hdr tmp_hdr;
struct flowi fl;
@@ -332,11 +333,12 @@ void icmpv6_send(struct sk_buff *skb, in
return;
}
+ memset(&fl, 0, sizeof(fl));
fl.proto = IPPROTO_ICMPV6;
- fl.fl6_dst = &hdr->saddr;
- fl.fl6_src = saddr;
+ ipv6_addr_copy(&fl.fl6_dst, &hdr->saddr);
+ if (saddr)
+ ipv6_addr_copy(&fl.fl6_src, saddr);
fl.oif = iif;
- fl.fl6_flowlabel = 0;
fl.fl_icmp_type = type;
fl.fl_icmp_code = code;
@@ -350,14 +352,14 @@ void icmpv6_send(struct sk_buff *skb, in
tmp_hdr.icmp6_cksum = 0;
tmp_hdr.icmp6_pointer = htonl(info);
- if (!fl.oif && ipv6_addr_is_multicast(fl.fl6_dst))
+ if (!fl.oif && ipv6_addr_is_multicast(&fl.fl6_dst))
fl.oif = np->mcast_oif;
- err = ip6_dst_lookup(sk, &dst, &fl, &tmp_saddr);
+ err = ip6_dst_lookup(sk, &dst, &fl);
if (err) goto out;
if (hlimit < 0) {
- if (ipv6_addr_is_multicast(fl.fl6_dst))
+ if (ipv6_addr_is_multicast(&fl.fl6_dst))
hlimit = np->mcast_hops;
else
hlimit = np->hop_limit;
@@ -394,7 +396,6 @@ void icmpv6_send(struct sk_buff *skb, in
if (likely(idev != NULL))
in6_dev_put(idev);
out:
- if (tmp_saddr) kfree(tmp_saddr);
icmpv6_xmit_unlock();
}
@@ -403,7 +404,7 @@ static void icmpv6_echo_reply(struct sk_
struct sock *sk = icmpv6_socket->sk;
struct inet6_dev *idev;
struct ipv6_pinfo *np = inet6_sk(sk);
- struct in6_addr *saddr = NULL, *tmp_saddr = NULL;
+ struct in6_addr *saddr = NULL;
struct icmp6hdr *icmph = (struct icmp6hdr *) skb->h.raw;
struct icmp6hdr tmp_hdr;
struct flowi fl;
@@ -420,25 +421,25 @@ static void icmpv6_echo_reply(struct sk_
memcpy(&tmp_hdr, icmph, sizeof(tmp_hdr));
tmp_hdr.icmp6_type = ICMPV6_ECHO_REPLY;
+ memset(&fl, 0, sizeof(fl));
fl.proto = IPPROTO_ICMPV6;
- fl.fl6_dst = &skb->nh.ipv6h->saddr;
- fl.fl6_src = saddr;
+ ipv6_addr_copy(&fl.fl6_dst, &skb->nh.ipv6h->saddr);
+ if (saddr)
+ ipv6_addr_copy(&fl.fl6_src, saddr);
fl.oif = skb->dev->ifindex;
- fl.fl6_flowlabel = 0;
fl.fl_icmp_type = ICMPV6_ECHO_REPLY;
- fl.fl_icmp_code = 0;
icmpv6_xmit_lock();
- if (!fl.oif && ipv6_addr_is_multicast(fl.nl_u.ip6_u.daddr))
+ if (!fl.oif && ipv6_addr_is_multicast(&fl.fl6_dst))
fl.oif = np->mcast_oif;
- err = ip6_dst_lookup(sk, &dst, &fl, &tmp_saddr);
+ err = ip6_dst_lookup(sk, &dst, &fl);
if (err) goto out;
if (hlimit < 0) {
- if (ipv6_addr_is_multicast(fl.fl6_dst))
+ if (ipv6_addr_is_multicast(&fl.fl6_dst))
hlimit = np->mcast_hops;
else
hlimit = np->hop_limit;
@@ -464,7 +465,6 @@ static void icmpv6_echo_reply(struct sk_
if (likely(idev != NULL))
in6_dev_put(idev);
out:
- if (tmp_saddr) kfree(tmp_saddr);
icmpv6_xmit_unlock();
}
--- ./net/ipv6/ip6_output.c.~1~ Thu May 22 16:00:14 2003
+++ ./net/ipv6/ip6_output.c Thu May 22 17:27:35 2003
@@ -152,15 +152,14 @@ int ip6_route_me_harder(struct sk_buff *
{
struct ipv6hdr *iph = skb->nh.ipv6h;
struct dst_entry *dst;
- struct flowi fl;
-
- fl.proto = iph->nexthdr;
- fl.fl6_dst = &iph->daddr;
- fl.fl6_src = &iph->saddr;
- fl.oif = skb->sk ? skb->sk->bound_dev_if : 0;
- fl.fl6_flowlabel = 0;
- fl.fl_ip_dport = 0;
- fl.fl_ip_sport = 0;
+ struct flowi fl = {
+ .oif = skb->sk ? skb->sk->bound_dev_if : 0,
+ .nl_u =
+ { .ip6_u =
+ { .daddr = iph->daddr,
+ .saddr = iph->saddr, } },
+ .proto = iph->nexthdr,
+ };
dst = ip6_route_output(skb->sk, &fl);
@@ -200,7 +199,7 @@ int ip6_xmit(struct sock *sk, struct sk_
struct ipv6_txoptions *opt)
{
struct ipv6_pinfo *np = sk ? inet6_sk(sk) : NULL;
- struct in6_addr *first_hop = fl->fl6_dst;
+ struct in6_addr *first_hop = &fl->fl6_dst;
struct dst_entry *dst = skb->dst;
struct ipv6hdr *hdr;
u8 proto = fl->proto;
@@ -255,7 +254,7 @@ int ip6_xmit(struct sock *sk, struct sk_
hdr->nexthdr = proto;
hdr->hop_limit = hlimit;
- ipv6_addr_copy(&hdr->saddr, fl->fl6_src);
+ ipv6_addr_copy(&hdr->saddr, &fl->fl6_src);
ipv6_addr_copy(&hdr->daddr, first_hop);
mtu = dst_pmtu(dst);
@@ -320,8 +319,8 @@ static struct ipv6hdr * ip6_bld_1(struct
hdr->hop_limit = hlimit;
hdr->nexthdr = fl->proto;
- ipv6_addr_copy(&hdr->saddr, fl->fl6_src);
- ipv6_addr_copy(&hdr->daddr, fl->fl6_dst);
+ ipv6_addr_copy(&hdr->saddr, &fl->fl6_src);
+ ipv6_addr_copy(&hdr->daddr, &fl->fl6_dst);
return hdr;
}
@@ -526,19 +525,19 @@ int ip6_build_xmit(struct sock *sk, inet
{
struct inet_opt *inet = inet_sk(sk);
struct ipv6_pinfo *np = inet6_sk(sk);
- struct in6_addr *final_dst = NULL;
+ struct in6_addr final_dst_buf, *final_dst = NULL;
struct dst_entry *dst;
int err = 0;
unsigned int pktlength, jumbolen, mtu;
- struct in6_addr saddr;
if (opt && opt->srcrt) {
struct rt0_hdr *rt0 = (struct rt0_hdr *) opt->srcrt;
- final_dst = fl->fl6_dst;
- fl->fl6_dst = rt0->addr;
+ ipv6_addr_copy(&final_dst_buf, &fl->fl6_dst);
+ final_dst = &final_dst_buf;
+ ipv6_addr_copy(&fl->fl6_dst, rt0->addr);
}
- if (!fl->oif && ipv6_addr_is_multicast(fl->fl6_dst))
+ if (!fl->oif && ipv6_addr_is_multicast(&fl->fl6_dst))
fl->oif = np->mcast_oif;
dst = __sk_dst_check(sk, np->dst_cookie);
@@ -564,9 +563,9 @@ int ip6_build_xmit(struct sock *sk, inet
*/
if (((rt->rt6i_dst.plen != 128 ||
- ipv6_addr_cmp(fl->fl6_dst, &rt->rt6i_dst.addr))
+ ipv6_addr_cmp(&fl->fl6_dst, &rt->rt6i_dst.addr))
&& (np->daddr_cache == NULL ||
- ipv6_addr_cmp(fl->fl6_dst, np->daddr_cache)))
+ ipv6_addr_cmp(&fl->fl6_dst, np->daddr_cache)))
|| (fl->oif && fl->oif != dst->dev->ifindex)) {
dst = NULL;
} else
@@ -582,8 +581,8 @@ int ip6_build_xmit(struct sock *sk, inet
return -ENETUNREACH;
}
- if (fl->fl6_src == NULL) {
- err = ipv6_get_saddr(dst, fl->fl6_dst, &saddr);
+ if (ipv6_addr_any(&fl->fl6_src)) {
+ err = ipv6_get_saddr(dst, &fl->fl6_dst, &fl->fl6_src);
if (err) {
#if IP6_DEBUG >= 2
@@ -592,7 +591,6 @@ int ip6_build_xmit(struct sock *sk, inet
#endif
goto out;
}
- fl->fl6_src = &saddr;
}
pktlength = length;
@@ -604,7 +602,7 @@ int ip6_build_xmit(struct sock *sk, inet
}
if (hlimit < 0) {
- if (ipv6_addr_is_multicast(fl->fl6_dst))
+ if (ipv6_addr_is_multicast(&fl->fl6_dst))
hlimit = np->mcast_hops;
else
hlimit = np->hop_limit;
@@ -715,7 +713,9 @@ int ip6_build_xmit(struct sock *sk, inet
* cleanup
*/
out:
- ip6_dst_store(sk, dst, fl->fl6_dst == &np->daddr ? &np->daddr : NULL);
+ ip6_dst_store(sk, dst,
+ !ipv6_addr_cmp(&fl->fl6_dst, &np->daddr) ?
+ &np->daddr : NULL);
if (err > 0)
err = np->recverr ? net_xmit_errno(err) : 0;
return err;
@@ -1135,7 +1135,7 @@ fail:
return err;
}
-int ip6_dst_lookup(struct sock *sk, struct dst_entry **dst, struct flowi *fl, struct in6_addr **saddr)
+int ip6_dst_lookup(struct sock *sk, struct dst_entry **dst, struct flowi *fl)
{
struct ipv6_pinfo *np = inet6_sk(sk);
int err = 0;
@@ -1163,9 +1163,9 @@ int ip6_dst_lookup(struct sock *sk, stru
*/
if (((rt->rt6i_dst.plen != 128 ||
- ipv6_addr_cmp(fl->fl6_dst, &rt->rt6i_dst.addr))
+ ipv6_addr_cmp(&fl->fl6_dst, &rt->rt6i_dst.addr))
&& (np->daddr_cache == NULL ||
- ipv6_addr_cmp(fl->fl6_dst, np->daddr_cache)))
+ ipv6_addr_cmp(&fl->fl6_dst, np->daddr_cache)))
|| (fl->oif && fl->oif != (*dst)->dev->ifindex)) {
*dst = NULL;
} else
@@ -1181,9 +1181,8 @@ int ip6_dst_lookup(struct sock *sk, stru
return -ENETUNREACH;
}
- if (fl->fl6_src == NULL) {
- *saddr = kmalloc(sizeof(struct in6_addr), GFP_ATOMIC);
- err = ipv6_get_saddr(*dst, fl->fl6_dst, *saddr);
+ if (ipv6_addr_any(&fl->fl6_src)) {
+ err = ipv6_get_saddr(*dst, &fl->fl6_dst, &fl->fl6_src);
if (err) {
#if IP6_DEBUG >= 2
@@ -1192,7 +1191,6 @@ int ip6_dst_lookup(struct sock *sk, stru
#endif
return err;
}
- fl->fl6_src = *saddr;
}
if (*dst) {
@@ -1415,7 +1413,7 @@ int ip6_push_pending_frames(struct sock
{
struct sk_buff *skb, *tmp_skb;
struct sk_buff **tail_skb;
- struct in6_addr *final_dst = NULL;
+ struct in6_addr final_dst_buf, *final_dst = &final_dst_buf;
struct inet_opt *inet = inet_sk(sk);
struct ipv6_pinfo *np = inet6_sk(sk);
struct ipv6hdr *hdr;
@@ -1446,7 +1444,7 @@ int ip6_push_pending_frames(struct sock
#endif
}
- final_dst = fl->fl6_dst;
+ ipv6_addr_copy(final_dst, &fl->fl6_dst);
__skb_pull(skb, skb->h.raw - skb->nh.raw);
if (opt && opt->opt_flen)
ipv6_push_frag_opts(skb, opt, &proto);
@@ -1463,7 +1461,7 @@ int ip6_push_pending_frames(struct sock
hdr->payload_len = 0;
hdr->hop_limit = np->hop_limit;
hdr->nexthdr = proto;
- ipv6_addr_copy(&hdr->saddr, fl->fl6_src);
+ ipv6_addr_copy(&hdr->saddr, &fl->fl6_src);
ipv6_addr_copy(&hdr->daddr, final_dst);
skb->dst = dst_clone(&rt->u.dst);
--- ./net/ipv6/raw.c.~1~ Thu May 22 16:00:14 2003
+++ ./net/ipv6/raw.c Thu May 22 16:57:18 2003
@@ -461,9 +461,9 @@ static int rawv6_push_pending_frames(str
* Only one fragment on the socket.
*/
/* should be check HW csum miyazawa */
- *csum = csum_ipv6_magic(fl->fl6_src,
- fl->fl6_dst,
- len, fl->proto, skb->csum);
+ *csum = csum_ipv6_magic(&fl->fl6_src,
+ &fl->fl6_dst,
+ len, fl->proto, skb->csum);
} else {
u32 tmp_csum = 0;
@@ -471,9 +471,9 @@ static int rawv6_push_pending_frames(str
tmp_csum = csum_add(tmp_csum, skb->csum);
}
- tmp_csum = csum_ipv6_magic(fl->fl6_src,
- fl->fl6_dst,
- len, fl->proto, tmp_csum);
+ tmp_csum = csum_ipv6_magic(&fl->fl6_src,
+ &fl->fl6_dst,
+ len, fl->proto, tmp_csum);
*csum = tmp_csum;
}
if (*csum == 0)
@@ -540,7 +540,7 @@ static int rawv6_sendmsg(struct kiocb *i
{
struct ipv6_txoptions opt_space;
struct sockaddr_in6 * sin6 = (struct sockaddr_in6 *) msg->msg_name;
- struct in6_addr *daddr, *saddr = NULL;
+ struct in6_addr *daddr;
struct inet_opt *inet = inet_sk(sk);
struct ipv6_pinfo *np = inet6_sk(sk);
struct raw6_opt *raw_opt = raw6_sk(sk);
@@ -566,9 +566,7 @@ static int rawv6_sendmsg(struct kiocb *i
/*
* Get and verify the address.
*/
-
- fl.fl6_flowlabel = 0;
- fl.oif = 0;
+ memset(&fl, 0, sizeof(fl));
if (sin6) {
if (addr_len < SIN6_LEN_RFC2133)
@@ -628,7 +626,6 @@ static int rawv6_sendmsg(struct kiocb *i
if (fl.oif == 0)
fl.oif = sk->bound_dev_if;
- fl.fl6_src = NULL;
if (msg->msg_controllen) {
opt = &opt_space;
@@ -653,26 +650,25 @@ static int rawv6_sendmsg(struct kiocb *i
opt = fl6_merge_options(&opt_space, flowlabel, opt);
fl.proto = proto;
- fl.fl6_dst = daddr;
- if (fl.fl6_src == NULL && !ipv6_addr_any(&np->saddr))
- fl.fl6_src = &np->saddr;
- fl.fl_icmp_type = 0;
- fl.fl_icmp_code = 0;
+ ipv6_addr_copy(&fl.fl6_dst, daddr);
+ if (ipv6_addr_any(&fl.fl6_src) && !ipv6_addr_any(&np->saddr))
+ ipv6_addr_copy(&fl.fl6_src, &np->saddr);
/* merge ip6_build_xmit from ip6_output */
if (opt && opt->srcrt) {
struct rt0_hdr *rt0 = (struct rt0_hdr *) opt->srcrt;
- fl.fl6_dst = rt0->addr;
+ ipv6_addr_copy(&fl.fl6_dst, rt0->addr);
}
- if (!fl.oif && ipv6_addr_is_multicast(fl.nl_u.ip6_u.daddr))
+ if (!fl.oif && ipv6_addr_is_multicast(&fl.fl6_dst))
fl.oif = np->mcast_oif;
- err = ip6_dst_lookup(sk, &dst, &fl, &saddr);
- if (err) goto out;
+ err = ip6_dst_lookup(sk, &dst, &fl);
+ if (err)
+ goto out;
if (hlimit < 0) {
- if (ipv6_addr_is_multicast(fl.fl6_dst))
+ if (ipv6_addr_is_multicast(&fl.fl6_dst))
hlimit = np->mcast_hops;
else
hlimit = np->hop_limit;
@@ -702,14 +698,15 @@ back_from_confirm:
}
}
done:
- ip6_dst_store(sk, dst, fl.nl_u.ip6_u.daddr == &np->daddr ? &np->daddr : NULL);
+ ip6_dst_store(sk, dst,
+ !ipv6_addr_cmp(&fl.fl6_dst, &np->daddr) ?
+ &np->daddr : NULL);
if (err > 0)
err = np->recverr ? net_xmit_errno(err) : 0;
release_sock(sk);
out:
fl6_sock_release(flowlabel);
- if (saddr) kfree(saddr);
return err<0?err:len;
do_confirm:
dst_confirm(dst);
--- ./net/ipv6/udp.c.~1~ Thu May 22 16:00:14 2003
+++ ./net/ipv6/udp.c Thu May 22 17:15:56 2003
@@ -270,7 +270,7 @@ int udpv6_connect(struct sock *sk, struc
if (usin->sin6_family != AF_INET6)
return -EAFNOSUPPORT;
- fl.fl6_flowlabel = 0;
+ memset(&fl, 0, sizeof(fl));
if (np->sndflow) {
fl.fl6_flowlabel = usin->sin6_flowinfo&IPV6_FLOWINFO_MASK;
if (fl.fl6_flowlabel&IPV6_FLOWLABEL_MASK) {
@@ -350,8 +350,8 @@ ipv4_connected:
*/
fl.proto = IPPROTO_UDP;
- fl.fl6_dst = &np->daddr;
- fl.fl6_src = &saddr;
+ ipv6_addr_copy(&fl.fl6_dst, &np->daddr);
+ ipv6_addr_copy(&fl.fl6_src, &saddr);
fl.oif = sk->bound_dev_if;
fl.fl_ip_dport = inet->dport;
fl.fl_ip_sport = inet->sport;
@@ -362,11 +362,11 @@ ipv4_connected:
if (flowlabel) {
if (flowlabel->opt && flowlabel->opt->srcrt) {
struct rt0_hdr *rt0 = (struct rt0_hdr *) flowlabel->opt->srcrt;
- fl.fl6_dst = rt0->addr;
+ ipv6_addr_copy(&fl.fl6_dst, rt0->addr);
}
} else if (np->opt && np->opt->srcrt) {
struct rt0_hdr *rt0 = (struct rt0_hdr *)np->opt->srcrt;
- fl.fl6_dst = rt0->addr;
+ ipv6_addr_copy(&fl.fl6_dst, rt0->addr);
}
dst = ip6_route_output(sk, &fl);
@@ -377,7 +377,7 @@ ipv4_connected:
return err;
}
- ip6_dst_store(sk, dst, fl.fl6_dst);
+ ip6_dst_store(sk, dst, &fl.fl6_dst);
/* get the source address used in the appropriate device */
@@ -784,8 +784,8 @@ static int udp_v6_push_pending_frames(st
if (skb_queue_len(&sk->write_queue) == 1) {
skb->csum = csum_partial((char *)uh,
sizeof(struct udphdr), skb->csum);
- uh->check = csum_ipv6_magic(fl->fl6_src,
- fl->fl6_dst,
+ uh->check = csum_ipv6_magic(&fl->fl6_src,
+ &fl->fl6_dst,
up->len, fl->proto, skb->csum);
} else {
u32 tmp_csum = 0;
@@ -795,8 +795,8 @@ static int udp_v6_push_pending_frames(st
}
tmp_csum = csum_partial((char *)uh,
sizeof(struct udphdr), tmp_csum);
- tmp_csum = csum_ipv6_magic(fl->fl6_src,
- fl->fl6_dst,
+ tmp_csum = csum_ipv6_magic(&fl->fl6_src,
+ &fl->fl6_dst,
up->len, fl->proto, tmp_csum);
uh->check = tmp_csum;
@@ -819,7 +819,7 @@ static int udpv6_sendmsg(struct kiocb *i
struct inet_opt *inet = inet_sk(sk);
struct ipv6_pinfo *np = inet6_sk(sk);
struct sockaddr_in6 *sin6 = (struct sockaddr_in6 *) msg->msg_name;
- struct in6_addr *daddr, *saddr = NULL;
+ struct in6_addr *daddr;
struct ipv6_txoptions *opt = NULL;
struct ip6_flowlabel *flowlabel = NULL;
struct flowi fl;
@@ -849,8 +849,7 @@ static int udpv6_sendmsg(struct kiocb *i
}
ulen += sizeof(struct udphdr);
- fl.fl6_flowlabel = 0;
- fl.oif = 0;
+ memset(&fl, 0, sizeof(fl));
if (sin6) {
if (sin6->sin6_family == AF_INET) {
@@ -919,7 +918,6 @@ static int udpv6_sendmsg(struct kiocb *i
if (!fl.oif)
fl.oif = sk->bound_dev_if;
- fl.fl6_src = NULL;
if (msg->msg_controllen) {
opt = &opt_space;
@@ -944,26 +942,27 @@ static int udpv6_sendmsg(struct kiocb *i
opt = fl6_merge_options(&opt_space, flowlabel, opt);
fl.proto = IPPROTO_UDP;
- fl.fl6_dst = daddr;
- if (fl.fl6_src == NULL && !ipv6_addr_any(&np->saddr))
- fl.fl6_src = &np->saddr;
+ ipv6_addr_copy(&fl.fl6_dst, daddr);
+ if (ipv6_addr_any(&fl.fl6_src) && !ipv6_addr_any(&np->saddr))
+ ipv6_addr_copy(&fl.fl6_src, &np->saddr);
fl.fl_ip_dport = up->dport;
fl.fl_ip_sport = inet->sport;
/* merge ip6_build_xmit from ip6_output */
if (opt && opt->srcrt) {
struct rt0_hdr *rt0 = (struct rt0_hdr *) opt->srcrt;
- fl.fl6_dst = rt0->addr;
+ ipv6_addr_copy(&fl.fl6_dst, rt0->addr);
}
- if (!fl.oif && ipv6_addr_is_multicast(fl.nl_u.ip6_u.daddr))
+ if (!fl.oif && ipv6_addr_is_multicast(&fl.fl6_dst))
fl.oif = np->mcast_oif;
- err = ip6_dst_lookup(sk, &dst, &fl, &saddr);
- if (err) goto out;
+ err = ip6_dst_lookup(sk, &dst, &fl);
+ if (err)
+ goto out;
if (hlimit < 0) {
- if (ipv6_addr_is_multicast(fl.fl6_dst))
+ if (ipv6_addr_is_multicast(&fl.fl6_dst))
hlimit = np->mcast_hops;
else
hlimit = np->hop_limit;
@@ -998,13 +997,14 @@ do_append_data:
else if (!corkreq)
err = udp_v6_push_pending_frames(sk, up);
- ip6_dst_store(sk, dst, fl.nl_u.ip6_u.daddr == &np->daddr ? &np->daddr : NULL);
+ ip6_dst_store(sk, dst,
+ !ipv6_addr_cmp(&fl.fl6_dst, &np->daddr) ?
+ &np->daddr : NULL);
if (err > 0)
err = np->recverr ? net_xmit_errno(err) : 0;
release_sock(sk);
out:
fl6_sock_release(flowlabel);
- if (saddr) kfree(saddr);
if (!err) {
UDP6_INC_STATS_USER(UdpOutDatagrams);
return len;
--- ./net/ipv6/ndisc.c.~1~ Thu May 22 16:00:14 2003
+++ ./net/ipv6/ndisc.c Thu May 22 16:51:55 2003
@@ -405,8 +405,8 @@ static inline void ndisc_flow_init(struc
struct in6_addr *saddr, struct in6_addr *daddr)
{
memset(fl, 0, sizeof(*fl));
- fl->fl6_src = saddr;
- fl->fl6_dst = daddr;
+ ipv6_addr_copy(&fl->fl6_src, saddr);
+ ipv6_addr_copy(&fl->fl6_dst, daddr);
fl->proto = IPPROTO_ICMPV6;
fl->fl_icmp_type = type;
fl->fl_icmp_code = 0;
--- ./net/ipv6/route.c.~1~ Thu May 22 16:00:14 2003
+++ ./net/ipv6/route.c Thu May 22 16:58:35 2003
@@ -454,12 +454,12 @@ struct dst_entry * ip6_route_output(stru
int strict;
int attempts = 3;
- strict = ipv6_addr_type(fl->fl6_dst) & (IPV6_ADDR_MULTICAST|IPV6_ADDR_LINKLOCAL);
+ strict = ipv6_addr_type(&fl->fl6_dst) & (IPV6_ADDR_MULTICAST|IPV6_ADDR_LINKLOCAL);
relookup:
read_lock_bh(&rt6_lock);
- fn = fib6_lookup(&ip6_routing_table, fl->fl6_dst, fl->fl6_src);
+ fn = fib6_lookup(&ip6_routing_table, &fl->fl6_dst, &fl->fl6_src);
restart:
rt = fn->leaf;
@@ -481,7 +481,7 @@ restart:
if (!rt->rt6i_nexthop && !(rt->rt6i_flags & RTF_NONEXTHOP)) {
read_unlock_bh(&rt6_lock);
- rt = rt6_cow(rt, fl->fl6_dst, fl->fl6_src);
+ rt = rt6_cow(rt, &fl->fl6_dst, &fl->fl6_src);
if (rt->u.dst.error != -EEXIST || --attempts <= 0)
goto out2;
@@ -1616,9 +1616,11 @@ int inet6_rtm_getroute(struct sk_buff *i
memset(&fl, 0, sizeof(fl));
if (rta[RTA_SRC-1])
- fl.fl6_src = (struct in6_addr*)RTA_DATA(rta[RTA_SRC-1]);
+ ipv6_addr_copy(&fl.fl6_src,
+ (struct in6_addr*)RTA_DATA(rta[RTA_SRC-1]));
if (rta[RTA_DST-1])
- fl.fl6_dst = (struct in6_addr*)RTA_DATA(rta[RTA_DST-1]);
+ ipv6_addr_copy(&fl.fl6_dst,
+ (struct in6_addr*)RTA_DATA(rta[RTA_DST-1]));
if (rta[RTA_IIF-1])
memcpy(&iif, RTA_DATA(rta[RTA_IIF-1]), sizeof(int));
@@ -1642,7 +1644,7 @@ int inet6_rtm_getroute(struct sk_buff *i
NETLINK_CB(skb).dst_pid = NETLINK_CB(in_skb).pid;
err = rt6_fill_node(skb, rt,
- fl.fl6_dst, fl.fl6_src,
+ &fl.fl6_dst, &fl.fl6_src,
iif,
RTM_NEWROUTE, NETLINK_CB(in_skb).pid,
nlh->nlmsg_seq, nlh);
--- ./net/ipv6/tcp_ipv6.c.~1~ Thu May 22 16:00:14 2003
+++ ./net/ipv6/tcp_ipv6.c Thu May 22 17:11:38 2003
@@ -571,7 +571,8 @@ static int tcp_v6_connect(struct sock *s
if (usin->sin6_family != AF_INET6)
return(-EAFNOSUPPORT);
- fl.fl6_flowlabel = 0;
+ memset(&fl, 0, sizeof(fl));
+
if (np->sndflow) {
fl.fl6_flowlabel = usin->sin6_flowinfo&IPV6_FLOWINFO_MASK;
IP6_ECN_flow_init(fl.fl6_flowlabel);
@@ -666,20 +667,18 @@ static int tcp_v6_connect(struct sock *s
saddr = &np->rcv_saddr;
fl.proto = IPPROTO_TCP;
- fl.fl6_dst = &np->daddr;
- fl.fl6_src = saddr;
+ ipv6_addr_copy(&fl.fl6_dst, &np->daddr);
+ ipv6_addr_copy(&fl.fl6_src,
+ (saddr ? saddr : &np->saddr));
fl.oif = sk->bound_dev_if;
fl.fl_ip_dport = usin->sin6_port;
fl.fl_ip_sport = inet->sport;
if (np->opt && np->opt->srcrt) {
struct rt0_hdr *rt0 = (struct rt0_hdr *)np->opt->srcrt;
- fl.fl6_dst = rt0->addr;
+ ipv6_addr_copy(&fl.fl6_dst, rt0->addr);
}
- if (!fl.fl6_src)
- fl.fl6_src = &np->saddr;
-
dst = ip6_route_output(sk, &fl);
if ((err = dst->error) != 0) {
@@ -794,9 +793,10 @@ static void tcp_v6_err(struct sk_buff *s
to handle rthdr case. Ignore this complexity
for now.
*/
+ memset(&fl, 0, sizeof(fl));
fl.proto = IPPROTO_TCP;
- fl.fl6_dst = &np->daddr;
- fl.fl6_src = &np->saddr;
+ ipv6_addr_copy(&fl.fl6_dst, &np->daddr);
+ ipv6_addr_copy(&fl.fl6_src, &np->saddr);
fl.oif = sk->bound_dev_if;
fl.fl_ip_dport = inet->dport;
fl.fl_ip_sport = inet->sport;
@@ -879,9 +879,10 @@ static int tcp_v6_send_synack(struct soc
struct flowi fl;
int err = -1;
+ memset(&fl, 0, sizeof(fl));
fl.proto = IPPROTO_TCP;
- fl.fl6_dst = &req->af.v6_req.rmt_addr;
- fl.fl6_src = &req->af.v6_req.loc_addr;
+ ipv6_addr_copy(&fl.fl6_dst, &req->af.v6_req.rmt_addr);
+ ipv6_addr_copy(&fl.fl6_src, &req->af.v6_req.loc_addr);
fl.fl6_flowlabel = 0;
fl.oif = req->af.v6_req.iif;
fl.fl_ip_dport = req->rmt_port;
@@ -900,7 +901,7 @@ static int tcp_v6_send_synack(struct soc
if (opt && opt->srcrt) {
struct rt0_hdr *rt0 = (struct rt0_hdr *) opt->srcrt;
- fl.fl6_dst = rt0->addr;
+ ipv6_addr_copy(&fl.fl6_dst, rt0->addr);
}
dst = ip6_route_output(sk, &fl);
@@ -916,7 +917,7 @@ static int tcp_v6_send_synack(struct soc
&req->af.v6_req.loc_addr, &req->af.v6_req.rmt_addr,
csum_partial((char *)th, skb->len, skb->csum));
- fl.fl6_dst = &req->af.v6_req.rmt_addr;
+ ipv6_addr_copy(&fl.fl6_dst, &req->af.v6_req.rmt_addr);
err = ip6_xmit(sk, skb, &fl, opt);
if (err == NET_XMIT_CN)
err = 0;
@@ -1018,11 +1019,11 @@ static void tcp_v6_send_reset(struct sk_
buff->csum = csum_partial((char *)t1, sizeof(*t1), 0);
- fl.fl6_dst = &skb->nh.ipv6h->saddr;
- fl.fl6_src = &skb->nh.ipv6h->daddr;
- fl.fl6_flowlabel = 0;
+ memset(&fl, 0, sizeof(fl));
+ ipv6_addr_copy(&fl.fl6_dst, &skb->nh.ipv6h->saddr);
+ ipv6_addr_copy(&fl.fl6_src, &skb->nh.ipv6h->daddr);
- t1->check = csum_ipv6_magic(fl.fl6_src, fl.fl6_dst,
+ t1->check = csum_ipv6_magic(&fl.fl6_src, &fl.fl6_dst,
sizeof(*t1), IPPROTO_TCP,
buff->csum);
@@ -1082,11 +1083,11 @@ static void tcp_v6_send_ack(struct sk_bu
buff->csum = csum_partial((char *)t1, tot_len, 0);
- fl.fl6_dst = &skb->nh.ipv6h->saddr;
- fl.fl6_src = &skb->nh.ipv6h->daddr;
- fl.fl6_flowlabel = 0;
+ memset(&fl, 0, sizeof(fl));
+ ipv6_addr_copy(&fl.fl6_dst, &skb->nh.ipv6h->saddr);
+ ipv6_addr_copy(&fl.fl6_src, &skb->nh.ipv6h->daddr);
- t1->check = csum_ipv6_magic(fl.fl6_src, fl.fl6_dst,
+ t1->check = csum_ipv6_magic(&fl.fl6_src, &fl.fl6_dst,
tot_len, IPPROTO_TCP,
buff->csum);
@@ -1261,7 +1262,6 @@ static struct sock * tcp_v6_syn_recv_soc
{
struct ipv6_pinfo *newnp, *np = inet6_sk(sk);
struct tcp6_sock *newtcp6sk;
- struct flowi fl;
struct inet_opt *newinet;
struct tcp_opt *newtp;
struct sock *newsk;
@@ -1330,14 +1330,16 @@ static struct sock * tcp_v6_syn_recv_soc
}
if (dst == NULL) {
+ struct flowi fl;
+
+ memset(&fl, 0, sizeof(fl));
fl.proto = IPPROTO_TCP;
- fl.fl6_dst = &req->af.v6_req.rmt_addr;
+ ipv6_addr_copy(&fl.fl6_dst, &req->af.v6_req.rmt_addr);
if (opt && opt->srcrt) {
struct rt0_hdr *rt0 = (struct rt0_hdr *) opt->srcrt;
- fl.fl6_dst = rt0->addr;
+ ipv6_addr_copy(&fl.fl6_dst, rt0->addr);
}
- fl.fl6_src = &req->af.v6_req.loc_addr;
- fl.fl6_flowlabel = 0;
+ ipv6_addr_copy(&fl.fl6_src, &req->af.v6_req.loc_addr);
fl.oif = sk->bound_dev_if;
fl.fl_ip_dport = req->rmt_port;
fl.fl_ip_sport = inet_sk(sk)->sport;
@@ -1725,9 +1727,10 @@ static int tcp_v6_rebuild_header(struct
struct inet_opt *inet = inet_sk(sk);
struct flowi fl;
+ memset(&fl, 0, sizeof(fl));
fl.proto = IPPROTO_TCP;
- fl.fl6_dst = &np->daddr;
- fl.fl6_src = &np->saddr;
+ ipv6_addr_copy(&fl.fl6_dst, &np->daddr);
+ ipv6_addr_copy(&fl.fl6_src, &np->saddr);
fl.fl6_flowlabel = np->flow_label;
fl.oif = sk->bound_dev_if;
fl.fl_ip_dport = inet->dport;
@@ -1735,7 +1738,7 @@ static int tcp_v6_rebuild_header(struct
if (np->opt && np->opt->srcrt) {
struct rt0_hdr *rt0 = (struct rt0_hdr *) np->opt->srcrt;
- fl.fl6_dst = rt0->addr;
+ ipv6_addr_copy(&fl.fl6_dst, rt0->addr);
}
dst = ip6_route_output(sk, &fl);
@@ -1762,9 +1765,10 @@ static int tcp_v6_xmit(struct sk_buff *s
struct flowi fl;
struct dst_entry *dst;
+ memset(&fl, 0, sizeof(fl));
fl.proto = IPPROTO_TCP;
- fl.fl6_dst = &np->daddr;
- fl.fl6_src = &np->saddr;
+ ipv6_addr_copy(&fl.fl6_dst, &np->daddr);
+ ipv6_addr_copy(&fl.fl6_src, &np->saddr);
fl.fl6_flowlabel = np->flow_label;
IP6_ECN_flow_xmit(sk, fl.fl6_flowlabel);
fl.oif = sk->bound_dev_if;
@@ -1773,7 +1777,7 @@ static int tcp_v6_xmit(struct sk_buff *s
if (np->opt && np->opt->srcrt) {
struct rt0_hdr *rt0 = (struct rt0_hdr *) np->opt->srcrt;
- fl.fl6_dst = rt0->addr;
+ ipv6_addr_copy(&fl.fl6_dst, rt0->addr);
}
dst = __sk_dst_check(sk, np->dst_cookie);
@@ -1793,7 +1797,7 @@ static int tcp_v6_xmit(struct sk_buff *s
skb->dst = dst_clone(dst);
/* Restore final destination back after routing done */
- fl.fl6_dst = &np->daddr;
+ ipv6_addr_copy(&fl.fl6_dst, &np->daddr);
return ip6_xmit(sk, skb, &fl, np->opt);
}
--- ./net/ipv6/xfrm6_policy.c.~1~ Thu May 22 16:00:14 2003
+++ ./net/ipv6/xfrm6_policy.c Thu May 22 17:17:59 2003
@@ -60,8 +60,8 @@ __xfrm6_find_bundle(struct flowi *fl, st
read_lock_bh(&policy->lock);
for (dst = policy->bundles; dst; dst = dst->next) {
struct xfrm_dst *xdst = (struct xfrm_dst*)dst;
- if (!ipv6_addr_cmp(&xdst->u.rt6.rt6i_dst.addr, fl->fl6_dst) &&
- !ipv6_addr_cmp(&xdst->u.rt6.rt6i_src.addr, fl->fl6_src) &&
+ if (!ipv6_addr_cmp(&xdst->u.rt6.rt6i_dst.addr, &fl->fl6_dst) &&
+ !ipv6_addr_cmp(&xdst->u.rt6.rt6i_src.addr, &fl->fl6_src) &&
__xfrm6_bundle_ok(xdst, fl)) {
dst_clone(dst);
break;
@@ -82,8 +82,8 @@ __xfrm6_bundle_create(struct xfrm_policy
struct dst_entry *dst, *dst_prev;
struct rt6_info *rt0 = (struct rt6_info*)(*dst_p);
struct rt6_info *rt = rt0;
- struct in6_addr *remote = fl->fl6_dst;
- struct in6_addr *local = fl->fl6_src;
+ struct in6_addr *remote = &fl->fl6_dst;
+ struct in6_addr *local = &fl->fl6_src;
int i;
int err = 0;
int header_len = 0;
@@ -116,13 +116,15 @@ __xfrm6_bundle_create(struct xfrm_policy
trailer_len += xfrm[i]->props.trailer_len;
}
- if (ipv6_addr_cmp(remote, fl->fl6_dst)) {
- struct flowi fl_tunnel = { .nl_u = { .ip6_u =
- { .daddr = remote,
- .saddr = local }
- }
- };
- err = xfrm_dst_lookup((struct xfrm_dst**)&rt, &fl_tunnel, AF_INET6);
+ if (ipv6_addr_cmp(remote, &fl->fl6_dst)) {
+ struct flowi fl_tunnel;
+
+ memset(&fl_tunnel, 0, sizeof(fl_tunnel));
+ ipv6_addr_copy(&fl_tunnel.fl6_dst, remote);
+ ipv6_addr_copy(&fl_tunnel.fl6_src, local);
+
+ err = xfrm_dst_lookup((struct xfrm_dst **) &rt,
+ &fl_tunnel, AF_INET6);
if (err)
goto error;
} else {
@@ -175,8 +177,8 @@ _decode_session6(struct sk_buff *skb, st
struct ipv6_opt_hdr *exthdr = (struct ipv6_opt_hdr*)(skb->nh.raw + offset);
u8 nexthdr = skb->nh.ipv6h->nexthdr;
- fl->fl6_dst = &hdr->daddr;
- fl->fl6_src = &hdr->saddr;
+ ipv6_addr_copy(&fl->fl6_dst, &hdr->daddr);
+ ipv6_addr_copy(&fl->fl6_src, &hdr->saddr);
while (pskb_may_pull(skb, skb->nh.raw + offset + 1 - skb->data)) {
switch (nexthdr) {
--- ./net/ipv6/xfrm6_state.c.~1~ Thu May 22 16:00:14 2003
+++ ./net/ipv6/xfrm6_state.c Thu May 22 17:18:24 2003
@@ -25,8 +25,8 @@ __xfrm6_init_tempsel(struct xfrm_state *
{
/* Initialize temporary selector matching only
* to current session. */
- ipv6_addr_copy((struct in6_addr *)&x->sel.daddr, fl->fl6_dst);
- ipv6_addr_copy((struct in6_addr *)&x->sel.saddr, fl->fl6_src);
+ ipv6_addr_copy((struct in6_addr *)&x->sel.daddr, &fl->fl6_dst);
+ ipv6_addr_copy((struct in6_addr *)&x->sel.saddr, &fl->fl6_src);
x->sel.dport = fl->fl_ip_dport;
x->sel.dport_mask = ~0;
x->sel.sport = fl->fl_ip_sport;
--- ./net/sctp/ipv6.c.~1~ Thu May 22 16:00:14 2003
+++ ./net/sctp/ipv6.c Thu May 22 17:29:21 2003
@@ -144,17 +144,19 @@ static int sctp_v6_xmit(struct sk_buff *
struct ipv6_pinfo *np = inet6_sk(sk);
struct flowi fl;
+ memset(&fl, 0, sizeof(fl));
+
fl.proto = sk->protocol;
/* Fill in the dest address from the route entry passed with the skb
* and the source address from the transport.
*/
- fl.fl6_dst = &transport->ipaddr.v6.sin6_addr;
- fl.fl6_src = &transport->saddr.v6.sin6_addr;
+ ipv6_addr_copy(&fl.fl6_dst, &transport->ipaddr.v6.sin6_addr);
+ ipv6_addr_copy(&fl.fl6_src, &transport->saddr.v6.sin6_addr);
fl.fl6_flowlabel = np->flow_label;
IP6_ECN_flow_xmit(sk, fl.fl6_flowlabel);
- if (ipv6_addr_type(fl.fl6_src) & IPV6_ADDR_LINKLOCAL)
+ if (ipv6_addr_type(&fl.fl6_src) & IPV6_ADDR_LINKLOCAL)
fl.oif = transport->saddr.v6.sin6_scope_id;
else
fl.oif = sk->bound_dev_if;
@@ -163,14 +165,14 @@ static int sctp_v6_xmit(struct sk_buff *
if (np->opt && np->opt->srcrt) {
struct rt0_hdr *rt0 = (struct rt0_hdr *) np->opt->srcrt;
- fl.nl_u.ip6_u.daddr = rt0->addr;
+ ipv6_addr_copy(&fl.fl6_dst, rt0->addr);
}
SCTP_DEBUG_PRINTK("%s: skb:%p, len:%d, "
"src:%04x:%04x:%04x:%04x:%04x:%04x:%04x:%04x "
"dst:%04x:%04x:%04x:%04x:%04x:%04x:%04x:%04x\n",
__FUNCTION__, skb, skb->len,
- NIP6(*fl.fl6_src), NIP6(*fl.fl6_dst));
+ NIP6(fl.fl6_src), NIP6(fl.fl6_dst));
SCTP_INC_STATS(SctpOutSCTPPacks);
@@ -185,17 +187,19 @@ struct dst_entry *sctp_v6_get_dst(struct
union sctp_addr *saddr)
{
struct dst_entry *dst;
- struct flowi fl = {
- .nl_u = { .ip6_u = { .daddr = &daddr->v6.sin6_addr, } } };
+ struct flowi fl;
+
+ memset(&fl, 0, sizeof(fl));
+ ipv6_addr_copy(&fl.fl6_dst, &daddr->v6.sin6_addr);
SCTP_DEBUG_PRINTK("%s: DST=%04x:%04x:%04x:%04x:%04x:%04x:%04x:%04x ",
- __FUNCTION__, NIP6(*fl.fl6_dst));
+ __FUNCTION__, NIP6(fl.fl6_dst));
if (saddr) {
- fl.fl6_src = &saddr->v6.sin6_addr;
+ ipv6_addr_copy(&fl.fl6_src, &saddr->v6.sin6_addr);
SCTP_DEBUG_PRINTK(
"SRC=%04x:%04x:%04x:%04x:%04x:%04x:%04x:%04x - ",
- NIP6(*fl.fl6_src));
+ NIP6(fl.fl6_src));
}
dst = ip6_route_output(NULL, &fl);
next prev parent reply other threads:[~2003-05-23 0:43 UTC|newest]
Thread overview: 5+ messages / expand[flat|nested] mbox.gz Atom feed top
2003-05-22 18:15 IPSec: IPv6 random failures Tom Lendacky
2003-05-22 22:54 ` David S. Miller
2003-05-23 0:43 ` David S. Miller [this message]
-- strict thread matches above, loose matches on Subject: below --
2003-05-23 15:42 Tom Lendacky
2003-05-23 20:50 ` David S. Miller
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20030522.174317.21915853.davem@redhat.com \
--to=davem@redhat.com \
--cc=kuznet@ms2.inr.ac.ru \
--cc=netdev@oss.sgi.com \
--cc=toml@us.ibm.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).