@@ -90,6 +90,17 @@ static struct tcp_md5sig_key *tcp_v6_md5_do_lookup(const struct sock *sk,
9090}
9191#endif
9292
93+ /* Helper returning the inet6 address from a given tcp socket.
94+ * It can be used in TCP stack instead of inet6_sk(sk).
95+ * This avoids a dereference and allow compiler optimizations.
96+ */
97+ static struct ipv6_pinfo * tcp_inet6_sk (const struct sock * sk )
98+ {
99+ struct tcp6_sock * tcp6 = container_of (tcp_sk (sk ), struct tcp6_sock , tcp );
100+
101+ return & tcp6 -> inet6 ;
102+ }
103+
93104static void inet6_sk_rx_dst_set (struct sock * sk , const struct sk_buff * skb )
94105{
95106 struct dst_entry * dst = skb_dst (skb );
@@ -99,7 +110,7 @@ static void inet6_sk_rx_dst_set(struct sock *sk, const struct sk_buff *skb)
99110
100111 sk -> sk_rx_dst = dst ;
101112 inet_sk (sk )-> rx_dst_ifindex = skb -> skb_iif ;
102- inet6_sk (sk )-> rx_dst_cookie = rt6_get_cookie (rt );
113+ tcp_inet6_sk (sk )-> rx_dst_cookie = rt6_get_cookie (rt );
103114 }
104115}
105116
@@ -138,7 +149,7 @@ static int tcp_v6_connect(struct sock *sk, struct sockaddr *uaddr,
138149 struct sockaddr_in6 * usin = (struct sockaddr_in6 * ) uaddr ;
139150 struct inet_sock * inet = inet_sk (sk );
140151 struct inet_connection_sock * icsk = inet_csk (sk );
141- struct ipv6_pinfo * np = inet6_sk (sk );
152+ struct ipv6_pinfo * np = tcp_inet6_sk (sk );
142153 struct tcp_sock * tp = tcp_sk (sk );
143154 struct in6_addr * saddr = NULL , * final_p , final ;
144155 struct ipv6_txoptions * opt ;
@@ -390,7 +401,7 @@ static int tcp_v6_err(struct sk_buff *skb, struct inet6_skb_parm *opt,
390401 if (sk -> sk_state == TCP_CLOSE )
391402 goto out ;
392403
393- if (ipv6_hdr (skb )-> hop_limit < inet6_sk (sk )-> min_hopcount ) {
404+ if (ipv6_hdr (skb )-> hop_limit < tcp_inet6_sk (sk )-> min_hopcount ) {
394405 __NET_INC_STATS (net , LINUX_MIB_TCPMINTTLDROP );
395406 goto out ;
396407 }
@@ -405,7 +416,7 @@ static int tcp_v6_err(struct sk_buff *skb, struct inet6_skb_parm *opt,
405416 goto out ;
406417 }
407418
408- np = inet6_sk (sk );
419+ np = tcp_inet6_sk (sk );
409420
410421 if (type == NDISC_REDIRECT ) {
411422 if (!sock_owned_by_user (sk )) {
@@ -478,7 +489,7 @@ static int tcp_v6_send_synack(const struct sock *sk, struct dst_entry *dst,
478489 enum tcp_synack_type synack_type )
479490{
480491 struct inet_request_sock * ireq = inet_rsk (req );
481- struct ipv6_pinfo * np = inet6_sk (sk );
492+ struct ipv6_pinfo * np = tcp_inet6_sk (sk );
482493 struct ipv6_txoptions * opt ;
483494 struct flowi6 * fl6 = & fl -> u .ip6 ;
484495 struct sk_buff * skb ;
@@ -737,7 +748,7 @@ static void tcp_v6_init_req(struct request_sock *req,
737748{
738749 bool l3_slave = ipv6_l3mdev_skb (TCP_SKB_CB (skb )-> header .h6 .flags );
739750 struct inet_request_sock * ireq = inet_rsk (req );
740- const struct ipv6_pinfo * np = inet6_sk (sk_listener );
751+ const struct ipv6_pinfo * np = tcp_inet6_sk (sk_listener );
741752
742753 ireq -> ir_v6_rmt_addr = ipv6_hdr (skb )-> saddr ;
743754 ireq -> ir_v6_loc_addr = ipv6_hdr (skb )-> daddr ;
@@ -1066,9 +1077,8 @@ static struct sock *tcp_v6_syn_recv_sock(const struct sock *sk, struct sk_buff *
10661077{
10671078 struct inet_request_sock * ireq ;
10681079 struct ipv6_pinfo * newnp ;
1069- const struct ipv6_pinfo * np = inet6_sk (sk );
1080+ const struct ipv6_pinfo * np = tcp_inet6_sk (sk );
10701081 struct ipv6_txoptions * opt ;
1071- struct tcp6_sock * newtcp6sk ;
10721082 struct inet_sock * newinet ;
10731083 struct tcp_sock * newtp ;
10741084 struct sock * newsk ;
@@ -1088,11 +1098,10 @@ static struct sock *tcp_v6_syn_recv_sock(const struct sock *sk, struct sk_buff *
10881098 if (!newsk )
10891099 return NULL ;
10901100
1091- newtcp6sk = (struct tcp6_sock * )newsk ;
1092- inet_sk (newsk )-> pinet6 = & newtcp6sk -> inet6 ;
1101+ inet_sk (newsk )-> pinet6 = tcp_inet6_sk (newsk );
10931102
10941103 newinet = inet_sk (newsk );
1095- newnp = inet6_sk (newsk );
1104+ newnp = tcp_inet6_sk (newsk );
10961105 newtp = tcp_sk (newsk );
10971106
10981107 memcpy (newnp , np , sizeof (struct ipv6_pinfo ));
@@ -1156,12 +1165,11 @@ static struct sock *tcp_v6_syn_recv_sock(const struct sock *sk, struct sk_buff *
11561165 ip6_dst_store (newsk , dst , NULL , NULL );
11571166 inet6_sk_rx_dst_set (newsk , skb );
11581167
1159- newtcp6sk = (struct tcp6_sock * )newsk ;
1160- inet_sk (newsk )-> pinet6 = & newtcp6sk -> inet6 ;
1168+ inet_sk (newsk )-> pinet6 = tcp_inet6_sk (newsk );
11611169
11621170 newtp = tcp_sk (newsk );
11631171 newinet = inet_sk (newsk );
1164- newnp = inet6_sk (newsk );
1172+ newnp = tcp_inet6_sk (newsk );
11651173
11661174 memcpy (newnp , np , sizeof (struct ipv6_pinfo ));
11671175
@@ -1276,9 +1284,9 @@ static struct sock *tcp_v6_syn_recv_sock(const struct sock *sk, struct sk_buff *
12761284 */
12771285static int tcp_v6_do_rcv (struct sock * sk , struct sk_buff * skb )
12781286{
1279- struct ipv6_pinfo * np = inet6_sk (sk );
1280- struct tcp_sock * tp ;
1287+ struct ipv6_pinfo * np = tcp_inet6_sk (sk );
12811288 struct sk_buff * opt_skb = NULL ;
1289+ struct tcp_sock * tp ;
12821290
12831291 /* Imagine: socket is IPv6. IPv4 packet arrives,
12841292 goes to IPv4 receive handler and backlogged.
@@ -1524,7 +1532,7 @@ static int tcp_v6_rcv(struct sk_buff *skb)
15241532 return 0 ;
15251533 }
15261534 }
1527- if (hdr -> hop_limit < inet6_sk (sk )-> min_hopcount ) {
1535+ if (hdr -> hop_limit < tcp_inet6_sk (sk )-> min_hopcount ) {
15281536 __NET_INC_STATS (net , LINUX_MIB_TCPMINTTLDROP );
15291537 goto discard_and_relse ;
15301538 }
@@ -1669,7 +1677,7 @@ static void tcp_v6_early_demux(struct sk_buff *skb)
16691677 struct dst_entry * dst = READ_ONCE (sk -> sk_rx_dst );
16701678
16711679 if (dst )
1672- dst = dst_check (dst , inet6_sk (sk )-> rx_dst_cookie );
1680+ dst = dst_check (dst , tcp_inet6_sk (sk )-> rx_dst_cookie );
16731681 if (dst &&
16741682 inet_sk (sk )-> rx_dst_ifindex == skb -> skb_iif )
16751683 skb_dst_set_noref (skb , dst );
0 commit comments