Skip to content

Commit

Permalink
ipv6: split inet6_ehashfn to hash functions per compilation unit
Browse files Browse the repository at this point in the history
This patch splits the inet6_ehashfn into separate ones in
ipv6/inet6_hashtables.o and ipv6/udp.o to ease the introduction of
seperate secrets keys later.

Cc: Eric Dumazet <[email protected]>
Cc: "David S. Miller" <[email protected]>
Signed-off-by: Hannes Frederic Sowa <[email protected]>
Signed-off-by: David S. Miller <[email protected]>
  • Loading branch information
strssndktn authored and davem330 committed Oct 19, 2013
1 parent 65cd803 commit b50026b
Show file tree
Hide file tree
Showing 4 changed files with 49 additions and 27 deletions.
28 changes: 7 additions & 21 deletions include/net/inet6_hashtables.h
Original file line number Diff line number Diff line change
Expand Up @@ -28,28 +28,14 @@

struct inet_hashinfo;

static inline unsigned int inet6_ehashfn(struct net *net,
const struct in6_addr *laddr, const u16 lport,
const struct in6_addr *faddr, const __be16 fport)
static inline unsigned int __inet6_ehashfn(const u32 lhash,
const u16 lport,
const u32 fhash,
const __be16 fport,
const u32 initval)
{
u32 ports = (((u32)lport) << 16) | (__force u32)fport;

return jhash_3words((__force u32)laddr->s6_addr32[3],
ipv6_addr_jhash(faddr),
ports,
inet_ehash_secret + net_hash_mix(net));
}

static inline int inet6_sk_ehashfn(const struct sock *sk)
{
const struct inet_sock *inet = inet_sk(sk);
const struct in6_addr *laddr = &sk->sk_v6_rcv_saddr;
const struct in6_addr *faddr = &sk->sk_v6_daddr;
const __u16 lport = inet->inet_num;
const __be16 fport = inet->inet_dport;
struct net *net = sock_net(sk);

return inet6_ehashfn(net, laddr, lport, faddr, fport);
const u32 ports = (((u32)lport) << 16) | (__force u32)fport;
return jhash_3words(lhash, fhash, ports, initval);
}

int __inet6_hash(struct sock *sk, struct inet_timewait_sock *twp);
Expand Down
4 changes: 2 additions & 2 deletions include/net/ipv6.h
Original file line number Diff line number Diff line change
Expand Up @@ -539,14 +539,14 @@ static inline u32 ipv6_addr_hash(const struct in6_addr *a)
}

/* more secured version of ipv6_addr_hash() */
static inline u32 ipv6_addr_jhash(const struct in6_addr *a)
static inline u32 __ipv6_addr_jhash(const struct in6_addr *a, const u32 initval)
{
u32 v = (__force u32)a->s6_addr32[0] ^ (__force u32)a->s6_addr32[1];

return jhash_3words(v,
(__force u32)a->s6_addr32[2],
(__force u32)a->s6_addr32[3],
ipv6_hash_secret);
initval);
}

static inline bool ipv6_addr_loopback(const struct in6_addr *a)
Expand Down
24 changes: 24 additions & 0 deletions net/ipv6/inet6_hashtables.c
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,30 @@
#include <net/secure_seq.h>
#include <net/ip.h>

static unsigned int inet6_ehashfn(struct net *net,
const struct in6_addr *laddr,
const u16 lport,
const struct in6_addr *faddr,
const __be16 fport)
{
const u32 lhash = (__force u32)laddr->s6_addr32[3];
const u32 fhash = __ipv6_addr_jhash(faddr, ipv6_hash_secret);
return __inet6_ehashfn(lhash, lport, fhash, fport,
inet_ehash_secret + net_hash_mix(net));
}

static int inet6_sk_ehashfn(const struct sock *sk)
{
const struct inet_sock *inet = inet_sk(sk);
const struct in6_addr *laddr = &sk->sk_v6_rcv_saddr;
const struct in6_addr *faddr = &sk->sk_v6_daddr;
const __u16 lport = inet->inet_num;
const __be16 fport = inet->inet_dport;
struct net *net = sock_net(sk);

return inet6_ehashfn(net, laddr, lport, faddr, fport);
}

int __inet6_hash(struct sock *sk, struct inet_timewait_sock *tw)
{
struct inet_hashinfo *hashinfo = sk->sk_prot->h.hashinfo;
Expand Down
20 changes: 16 additions & 4 deletions net/ipv6/udp.c
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,18 @@
#include <trace/events/skb.h>
#include "udp_impl.h"

static unsigned int udp6_ehashfn(struct net *net,
const struct in6_addr *laddr,
const u16 lport,
const struct in6_addr *faddr,
const __be16 fport)
{
const u32 lhash = (__force u32)laddr->s6_addr32[3];
const u32 fhash = __ipv6_addr_jhash(faddr, ipv6_hash_secret);
return __inet6_ehashfn(lhash, lport, fhash, fport,
inet_ehash_secret + net_hash_mix(net));
}

int ipv6_rcv_saddr_equal(const struct sock *sk, const struct sock *sk2)
{
const struct in6_addr *sk2_rcv_saddr6 = inet6_rcv_saddr(sk2);
Expand Down Expand Up @@ -214,8 +226,8 @@ static struct sock *udp6_lib_lookup2(struct net *net,
badness = score;
reuseport = sk->sk_reuseport;
if (reuseport) {
hash = inet6_ehashfn(net, daddr, hnum,
saddr, sport);
hash = udp6_ehashfn(net, daddr, hnum,
saddr, sport);
matches = 1;
} else if (score == SCORE2_MAX)
goto exact_match;
Expand Down Expand Up @@ -295,8 +307,8 @@ struct sock *__udp6_lib_lookup(struct net *net,
badness = score;
reuseport = sk->sk_reuseport;
if (reuseport) {
hash = inet6_ehashfn(net, daddr, hnum,
saddr, sport);
hash = udp6_ehashfn(net, daddr, hnum,
saddr, sport);
matches = 1;
}
} else if (score == badness && reuseport) {
Expand Down

0 comments on commit b50026b

Please sign in to comment.