Skip to content

Commit e3390b3

Browse files
edumazetdavem330
authored andcommitted
net: annotate data-races around sk->sk_tsflags
sk->sk_tsflags can be read locklessly, add corresponding annotations. Fixes: b9f40e2 ("net-timestamp: move timestamp flags out of sk_flags") Signed-off-by: Eric Dumazet <[email protected]> Cc: Willem de Bruijn <[email protected]> Signed-off-by: David S. Miller <[email protected]>
1 parent 9531e4a commit e3390b3

File tree

13 files changed

+40
-32
lines changed

13 files changed

+40
-32
lines changed

include/net/ip.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -94,7 +94,7 @@ static inline void ipcm_init_sk(struct ipcm_cookie *ipcm,
9494
ipcm_init(ipcm);
9595

9696
ipcm->sockc.mark = READ_ONCE(inet->sk.sk_mark);
97-
ipcm->sockc.tsflags = inet->sk.sk_tsflags;
97+
ipcm->sockc.tsflags = READ_ONCE(inet->sk.sk_tsflags);
9898
ipcm->oif = READ_ONCE(inet->sk.sk_bound_dev_if);
9999
ipcm->addr = inet->inet_saddr;
100100
ipcm->protocol = inet->inet_num;

include/net/sock.h

Lines changed: 10 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1906,7 +1906,9 @@ struct sockcm_cookie {
19061906
static inline void sockcm_init(struct sockcm_cookie *sockc,
19071907
const struct sock *sk)
19081908
{
1909-
*sockc = (struct sockcm_cookie) { .tsflags = sk->sk_tsflags };
1909+
*sockc = (struct sockcm_cookie) {
1910+
.tsflags = READ_ONCE(sk->sk_tsflags)
1911+
};
19101912
}
19111913

19121914
int __sock_cmsg_send(struct sock *sk, struct cmsghdr *cmsg,
@@ -2701,20 +2703,20 @@ void __sock_recv_wifi_status(struct msghdr *msg, struct sock *sk,
27012703
static inline void
27022704
sock_recv_timestamp(struct msghdr *msg, struct sock *sk, struct sk_buff *skb)
27032705
{
2704-
ktime_t kt = skb->tstamp;
27052706
struct skb_shared_hwtstamps *hwtstamps = skb_hwtstamps(skb);
2706-
2707+
u32 tsflags = READ_ONCE(sk->sk_tsflags);
2708+
ktime_t kt = skb->tstamp;
27072709
/*
27082710
* generate control messages if
27092711
* - receive time stamping in software requested
27102712
* - software time stamp available and wanted
27112713
* - hardware time stamps available and wanted
27122714
*/
27132715
if (sock_flag(sk, SOCK_RCVTSTAMP) ||
2714-
(sk->sk_tsflags & SOF_TIMESTAMPING_RX_SOFTWARE) ||
2715-
(kt && sk->sk_tsflags & SOF_TIMESTAMPING_SOFTWARE) ||
2716+
(tsflags & SOF_TIMESTAMPING_RX_SOFTWARE) ||
2717+
(kt && tsflags & SOF_TIMESTAMPING_SOFTWARE) ||
27162718
(hwtstamps->hwtstamp &&
2717-
(sk->sk_tsflags & SOF_TIMESTAMPING_RAW_HARDWARE)))
2719+
(tsflags & SOF_TIMESTAMPING_RAW_HARDWARE)))
27182720
__sock_recv_timestamp(msg, sk, skb);
27192721
else
27202722
sock_write_timestamp(sk, kt);
@@ -2736,7 +2738,8 @@ static inline void sock_recv_cmsgs(struct msghdr *msg, struct sock *sk,
27362738
#define TSFLAGS_ANY (SOF_TIMESTAMPING_SOFTWARE | \
27372739
SOF_TIMESTAMPING_RAW_HARDWARE)
27382740

2739-
if (sk->sk_flags & FLAGS_RECV_CMSGS || sk->sk_tsflags & TSFLAGS_ANY)
2741+
if (sk->sk_flags & FLAGS_RECV_CMSGS ||
2742+
READ_ONCE(sk->sk_tsflags) & TSFLAGS_ANY)
27402743
__sock_recv_cmsgs(msg, sk, skb);
27412744
else if (unlikely(sock_flag(sk, SOCK_TIMESTAMP)))
27422745
sock_write_timestamp(sk, skb->tstamp);

net/can/j1939/socket.c

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -974,20 +974,22 @@ static void __j1939_sk_errqueue(struct j1939_session *session, struct sock *sk,
974974
struct sock_exterr_skb *serr;
975975
struct sk_buff *skb;
976976
char *state = "UNK";
977+
u32 tsflags;
977978
int err;
978979

979980
jsk = j1939_sk(sk);
980981

981982
if (!(jsk->state & J1939_SOCK_ERRQUEUE))
982983
return;
983984

985+
tsflags = READ_ONCE(sk->sk_tsflags);
984986
switch (type) {
985987
case J1939_ERRQUEUE_TX_ACK:
986-
if (!(sk->sk_tsflags & SOF_TIMESTAMPING_TX_ACK))
988+
if (!(tsflags & SOF_TIMESTAMPING_TX_ACK))
987989
return;
988990
break;
989991
case J1939_ERRQUEUE_TX_SCHED:
990-
if (!(sk->sk_tsflags & SOF_TIMESTAMPING_TX_SCHED))
992+
if (!(tsflags & SOF_TIMESTAMPING_TX_SCHED))
991993
return;
992994
break;
993995
case J1939_ERRQUEUE_TX_ABORT:
@@ -997,7 +999,7 @@ static void __j1939_sk_errqueue(struct j1939_session *session, struct sock *sk,
997999
case J1939_ERRQUEUE_RX_DPO:
9981000
fallthrough;
9991001
case J1939_ERRQUEUE_RX_ABORT:
1000-
if (!(sk->sk_tsflags & SOF_TIMESTAMPING_RX_SOFTWARE))
1002+
if (!(tsflags & SOF_TIMESTAMPING_RX_SOFTWARE))
10011003
return;
10021004
break;
10031005
default:
@@ -1054,7 +1056,7 @@ static void __j1939_sk_errqueue(struct j1939_session *session, struct sock *sk,
10541056
}
10551057

10561058
serr->opt_stats = true;
1057-
if (sk->sk_tsflags & SOF_TIMESTAMPING_OPT_ID)
1059+
if (tsflags & SOF_TIMESTAMPING_OPT_ID)
10581060
serr->ee.ee_data = session->tskey;
10591061

10601062
netdev_dbg(session->priv->ndev, "%s: 0x%p tskey: %i, state: %s\n",

net/core/skbuff.c

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -5207,7 +5207,7 @@ static void __skb_complete_tx_timestamp(struct sk_buff *skb,
52075207
serr->ee.ee_info = tstype;
52085208
serr->opt_stats = opt_stats;
52095209
serr->header.h4.iif = skb->dev ? skb->dev->ifindex : 0;
5210-
if (sk->sk_tsflags & SOF_TIMESTAMPING_OPT_ID) {
5210+
if (READ_ONCE(sk->sk_tsflags) & SOF_TIMESTAMPING_OPT_ID) {
52115211
serr->ee.ee_data = skb_shinfo(skb)->tskey;
52125212
if (sk_is_tcp(sk))
52135213
serr->ee.ee_data -= atomic_read(&sk->sk_tskey);
@@ -5263,21 +5263,23 @@ void __skb_tstamp_tx(struct sk_buff *orig_skb,
52635263
{
52645264
struct sk_buff *skb;
52655265
bool tsonly, opt_stats = false;
5266+
u32 tsflags;
52665267

52675268
if (!sk)
52685269
return;
52695270

5270-
if (!hwtstamps && !(sk->sk_tsflags & SOF_TIMESTAMPING_OPT_TX_SWHW) &&
5271+
tsflags = READ_ONCE(sk->sk_tsflags);
5272+
if (!hwtstamps && !(tsflags & SOF_TIMESTAMPING_OPT_TX_SWHW) &&
52715273
skb_shinfo(orig_skb)->tx_flags & SKBTX_IN_PROGRESS)
52725274
return;
52735275

5274-
tsonly = sk->sk_tsflags & SOF_TIMESTAMPING_OPT_TSONLY;
5276+
tsonly = tsflags & SOF_TIMESTAMPING_OPT_TSONLY;
52755277
if (!skb_may_tx_timestamp(sk, tsonly))
52765278
return;
52775279

52785280
if (tsonly) {
52795281
#ifdef CONFIG_INET
5280-
if ((sk->sk_tsflags & SOF_TIMESTAMPING_OPT_STATS) &&
5282+
if ((tsflags & SOF_TIMESTAMPING_OPT_STATS) &&
52815283
sk_is_tcp(sk)) {
52825284
skb = tcp_get_timestamping_opt_stats(sk, orig_skb,
52835285
ack_skb);

net/core/sock.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -937,7 +937,7 @@ int sock_set_timestamping(struct sock *sk, int optname,
937937
return ret;
938938
}
939939

940-
sk->sk_tsflags = val;
940+
WRITE_ONCE(sk->sk_tsflags, val);
941941
sock_valbool_flag(sk, SOCK_TSTAMP_NEW, optname == SO_TIMESTAMPING_NEW);
942942

943943
if (val & SOF_TIMESTAMPING_RX_SOFTWARE)
@@ -1719,7 +1719,7 @@ int sk_getsockopt(struct sock *sk, int level, int optname,
17191719

17201720
case SO_TIMESTAMPING_OLD:
17211721
lv = sizeof(v.timestamping);
1722-
v.timestamping.flags = sk->sk_tsflags;
1722+
v.timestamping.flags = READ_ONCE(sk->sk_tsflags);
17231723
v.timestamping.bind_phc = sk->sk_bind_phc;
17241724
break;
17251725

net/ipv4/ip_output.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -981,7 +981,7 @@ static int __ip_append_data(struct sock *sk,
981981
paged = !!cork->gso_size;
982982

983983
if (cork->tx_flags & SKBTX_ANY_TSTAMP &&
984-
sk->sk_tsflags & SOF_TIMESTAMPING_OPT_ID)
984+
READ_ONCE(sk->sk_tsflags) & SOF_TIMESTAMPING_OPT_ID)
985985
tskey = atomic_inc_return(&sk->sk_tskey) - 1;
986986

987987
hh_len = LL_RESERVED_SPACE(rt->dst.dev);

net/ipv4/ip_sockglue.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -511,7 +511,7 @@ static bool ipv4_datagram_support_cmsg(const struct sock *sk,
511511
* or without payload (SOF_TIMESTAMPING_OPT_TSONLY).
512512
*/
513513
info = PKTINFO_SKB_CB(skb);
514-
if (!(sk->sk_tsflags & SOF_TIMESTAMPING_OPT_CMSG) ||
514+
if (!(READ_ONCE(sk->sk_tsflags) & SOF_TIMESTAMPING_OPT_CMSG) ||
515515
!info->ipi_ifindex)
516516
return false;
517517

net/ipv4/tcp.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2259,14 +2259,14 @@ void tcp_recv_timestamp(struct msghdr *msg, const struct sock *sk,
22592259
}
22602260
}
22612261

2262-
if (sk->sk_tsflags & SOF_TIMESTAMPING_SOFTWARE)
2262+
if (READ_ONCE(sk->sk_tsflags) & SOF_TIMESTAMPING_SOFTWARE)
22632263
has_timestamping = true;
22642264
else
22652265
tss->ts[0] = (struct timespec64) {0};
22662266
}
22672267

22682268
if (tss->ts[2].tv_sec || tss->ts[2].tv_nsec) {
2269-
if (sk->sk_tsflags & SOF_TIMESTAMPING_RAW_HARDWARE)
2269+
if (READ_ONCE(sk->sk_tsflags) & SOF_TIMESTAMPING_RAW_HARDWARE)
22702270
has_timestamping = true;
22712271
else
22722272
tss->ts[2] = (struct timespec64) {0};

net/ipv6/ip6_output.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1501,7 +1501,7 @@ static int __ip6_append_data(struct sock *sk,
15011501
orig_mtu = mtu;
15021502

15031503
if (cork->tx_flags & SKBTX_ANY_TSTAMP &&
1504-
sk->sk_tsflags & SOF_TIMESTAMPING_OPT_ID)
1504+
READ_ONCE(sk->sk_tsflags) & SOF_TIMESTAMPING_OPT_ID)
15051505
tskey = atomic_inc_return(&sk->sk_tskey) - 1;
15061506

15071507
hh_len = LL_RESERVED_SPACE(rt->dst.dev);

net/ipv6/ping.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -119,7 +119,7 @@ static int ping_v6_sendmsg(struct sock *sk, struct msghdr *msg, size_t len)
119119
return -EINVAL;
120120

121121
ipcm6_init_sk(&ipc6, np);
122-
ipc6.sockc.tsflags = sk->sk_tsflags;
122+
ipc6.sockc.tsflags = READ_ONCE(sk->sk_tsflags);
123123
ipc6.sockc.mark = READ_ONCE(sk->sk_mark);
124124

125125
fl6.flowi6_oif = oif;

0 commit comments

Comments
 (0)