Convert network timestamps to be y2038 safe
Subsystems (5)
v2 cover Convert network timestamps to be y2038 safe
Introduction:
The series is aimed at transitioning network timestamps to being y2038 safe.
All patches can be reviewed and merged independently.
Socket timestamps and ioctl calls will be handled separately.
Thanks to Arnd Bergmann for discussing solution options with me.
Solution:
Data type struct timespec is not y2038 safe. Replace timespec with struct timespec64 which is y2038 safe.
Changes v1 -> v2:
Move and rename inet_current_time() as discussed Squash patches 1 and 2
Reword commit text for patch 2/3
Carry over review tags
Deepa Dinamani (3):
net: ipv4: Convert IP network timestamps to be y2038 safe
net: ipv4: tcp_probe: Replace timespec with timespec64
net: sctp: Convert log timestamps to be y2038 safe
include/net/ip.h | 2 ++ net/ipv4/af_inet.c | 26 ++++++++++++++++++++++++++ net/ipv4/icmp.c | 5 +---- net/ipv4/ip_options.c | 14 ++++++-------- net/ipv4/tcp_probe.c | 8 ++++---- net/sctp/probe.c | 10 +++++----- 6 files changed, 44 insertions(+), 21 deletions(-)
Signature · 10 lines
1.9.1 Cc: Vlad Yasevich <[email protected]> Cc: Neil Horman <[email protected]> Cc: "David S. Miller" <[email protected]> Cc: Alexey Kuznetsov <[email protected]> Cc: James Morris <[email protected]> Cc: Hideaki YOSHIFUJI <[email protected]> Cc: Patrick McHardy <[email protected]> Cc: [email protected]
PATCH v2 1/3 net: ipv4: Convert IP network timestamps to be y2038 safe
ICMP timestamp messages and IP source route options require timestamps to be in milliseconds modulo 24 hours from midnight UT format.
Add inet_current_timestamp() function to support this. The function returns the required timestamp in network byte order.
Timestamp calculation is also changed to call ktime_get_real_ts64() which uses struct timespec64. struct timespec64 is y2038 safe. Previously it called getnstimeofday() which uses struct timespec. struct timespec is not y2038 safe.
--- include/net/ip.h | 2 ++ net/ipv4/af_inet.c | 26 ++++++++++++++++++++++++++ net/ipv4/icmp.c | 5 +---- net/ipv4/ip_options.c | 14 ++++++-------- 4 files changed, 35 insertions(+), 12 deletions(-)
include/net/ip.h +2 -0
@@ -240,6 +240,8 @@ static inline int inet_is_local_reserved_port(struct net *net, int port) }#endif +__be32 inet_current_timestamp (void ); +/* From inetpeer.c */ extern int inet_peer_threshold;extern int inet_peer_minttl;
net/ipv4/af_inet.c +26 -0
@@ -1386,6 +1386,32 @@ out:return pp; } +#define SECONDS_PER_DAY 86400 + +/* inet_current_timestamp - Return IP network timestamp +* +* Return milliseconds since midnight in network byte order. +*/ +__be32 inet_current_timestamp (void ) +{ +u32 secs; +u32 msecs; +struct timespec64 ts; + +ktime_get_real_ts64 (&ts); + +/* Get secs since midnight. */ + (void )div_u64_rem (ts.tv_sec,SECONDS_PER_DAY , &secs); +/* Convert to msecs. */ + msecs = secs *MSEC_PER_SEC ; +/* Convert nsec to msec. */ + msecs += (u32 )ts.tv_nsec /NSEC_PER_MSEC ; + +/* Convert to network byte order. */ +return htons (msecs); +} +EXPORT_SYMBOL (inet_current_timestamp); +int inet_recv_error (struct sock *sk,struct msghdr *msg,int len,int *addr_len) {if (sk->sk_family ==AF_INET )
net/ipv4/icmp.c +1 -4
@@ -931,7 +931,6 @@ static bool icmp_echo(struct sk_buff *skb)*/ static bool icmp_timestamp (struct sk_buff *skb) { -struct timespec tv;struct icmp_bxm icmp_param;/* * Too short.
@@ -942,9 +941,7 @@ static bool icmp_timestamp(struct sk_buff *skb)/* * Fill in the current time as ms since midnight UT: */ -getnstimeofday (&tv); - icmp_param.data.times[1 ] =htonl ((tv.tv_sec %86400 ) *MSEC_PER_SEC + - tv.tv_nsec /NSEC_PER_MSEC ); + icmp_param.data.times[1 ] =inet_current_timestamp (); icmp_param.data.times[2 ] = icmp_param.data.times[1 ];if (skb_copy_bits (skb,0 , &icmp_param.data.times[0 ],4 ))BUG ();
net/ipv4/ip_options.c +6 -8
@@ -58,10 +58,9 @@ void ip_options_build(struct sk_buff *skb, struct ip_options *opt,if (opt->ts_needaddr)ip_rt_get_source (iph+opt->ts+iph[opt->ts+2 ]-9 , skb, rt);if (opt->ts_needtime) { -struct timespec tv;__be32 midtime; -getnstimeofday (&tv); - midtime =htonl ((tv.tv_sec %86400 ) *MSEC_PER_SEC + tv.tv_nsec /NSEC_PER_MSEC ); + + midtime =inet_current_timestamp ();memcpy (iph+opt->ts+iph[opt->ts+2 ]-5 , &midtime,4 ); }return ;
@@ -415,11 +414,10 @@ int ip_options_compile(struct net *net,break ; }if (timeptr) { -struct timespec tv; -u32 midtime; -getnstimeofday (&tv); - midtime = (tv.tv_sec %86400 ) *MSEC_PER_SEC + tv.tv_nsec /NSEC_PER_MSEC ; -put_unaligned_be32 (midtime, timeptr); +__be32 midtime; + + midtime =inet_current_timestamp (); +memcpy (timeptr, &midtime,4 ); opt->is_changed =1 ; } }else if ((optptr[3 ]&0xF ) !=IPOPT_TS_PRESPEC ) {
Signature · 1 line
1.9.1
Re: [PATCH v2 1/3] net: ipv4: Convert IP network timestamps to be y2038 safe
Quoted 7 lines · Deepa Dinamani
ICMP timestamp messages and IP source route options require timestamps to be in milliseconds modulo 24 hours from midnight UT format.
Add
inet_current_timestamp()function to support this. The function returns the required timestamp in network byte order.
Quoted 6 lines
Timestamp calculation is also changed to call
ktime_get_real_ts64()which uses struct timespec64. struct timespec64 is y2038 safe. Previously it calledgetnstimeofday()which uses struct timespec. struct timespec is not y2038 safe.Signed-off-by Deepa Dinamani <[email protected]>
--yoshfuji
Quoted 119 lines
Cc "David S. Miller" <[email protected]>Cc Alexey Kuznetsov <[email protected]>Cc Hideaki YOSHIFUJI <[email protected]>Cc James Morris <[email protected]>Cc Patrick McHardy <[email protected]>--- include/net/ip.h | 2 ++ net/ipv4/af_inet.c | 26 ++++++++++++++++++++++++++ net/ipv4/icmp.c | 5 +---- net/ipv4/ip_options.c | 14 ++++++-------- 4 files changed, 35 insertions(+), 12 deletions(-)include/net/ip.h +2
-0@@ -240,6 +240,8 @@ static inline int inet_is_local_reserved_port(struct net *net, int port) }#endif +__be32 inet_current_timestamp (void ); +/* From inetpeer.c */ extern int inet_peer_threshold;extern int inet_peer_minttl;net/ipv4/af_inet.c +26
-0@@ -1386,6 +1386,32 @@ out:return pp; } +#define SECONDS_PER_DAY 86400 + +/* inet_current_timestamp - Return IP network timestamp +* +* Return milliseconds since midnight in network byte order. +*/ +__be32 inet_current_timestamp (void ) +{ +u32 secs; +u32 msecs; +struct timespec64 ts; + +ktime_get_real_ts64 (&ts); + +/* Get secs since midnight. */ + (void )div_u64_rem (ts.tv_sec,SECONDS_PER_DAY , &secs); +/* Convert to msecs. */ + msecs = secs *MSEC_PER_SEC ; +/* Convert nsec to msec. */ + msecs += (u32 )ts.tv_nsec /NSEC_PER_MSEC ; + +/* Convert to network byte order. */ +return htons (msecs); +} +EXPORT_SYMBOL (inet_current_timestamp); +int inet_recv_error (struct sock *sk,struct msghdr *msg,int len,int *addr_len) {if (sk->sk_family ==AF_INET )net/ipv4/icmp.c +1
-4@@ -931,7 +931,6 @@ static bool icmp_echo(struct sk_buff *skb)*/ static bool icmp_timestamp (struct sk_buff *skb) { -struct timespec tv;struct icmp_bxm icmp_param;/* * Too short. @@ -942,9 +941,7 @@ static bool icmp_timestamp(struct sk_buff *skb)/* * Fill in the current time as ms since midnight UT: */ -getnstimeofday (&tv); - icmp_param.data.times[1 ] =htonl ((tv.tv_sec %86400 ) *MSEC_PER_SEC + - tv.tv_nsec /NSEC_PER_MSEC ); + icmp_param.data.times[1 ] =inet_current_timestamp (); icmp_param.data.times[2 ] = icmp_param.data.times[1 ];if (skb_copy_bits (skb,0 , &icmp_param.data.times[0 ],4 ))BUG ();net/ipv4/ip_options.c +6
-8@@ -58,10 +58,9 @@ void ip_options_build(struct sk_buff *skb, struct ip_options *opt,if (opt->ts_needaddr)ip_rt_get_source (iph+opt->ts+iph[opt->ts+2 ]-9 , skb, rt);if (opt->ts_needtime) { -struct timespec tv;__be32 midtime; -getnstimeofday (&tv); - midtime =htonl ((tv.tv_sec %86400 ) *MSEC_PER_SEC + tv.tv_nsec /NSEC_PER_MSEC ); + + midtime =inet_current_timestamp ();memcpy (iph+opt->ts+iph[opt->ts+2 ]-5 , &midtime,4 ); }return ;@@ -415,11 +414,10 @@ int ip_options_compile(struct net *net,break ; }if (timeptr) { -struct timespec tv; -u32 midtime; -getnstimeofday (&tv); - midtime = (tv.tv_sec %86400 ) *MSEC_PER_SEC + tv.tv_nsec /NSEC_PER_MSEC ; -put_unaligned_be32 (midtime, timeptr); +__be32 midtime; + + midtime =inet_current_timestamp (); +memcpy (timeptr, &midtime,4 ); opt->is_changed =1 ; } }else if ((optptr[3 ]&0xF ) !=IPOPT_TS_PRESPEC ) {
Signature · 2 lines
Hideaki Yoshifuji <[email protected]> Technical Division, MIRACLE LINUX CORPORATION
Re: [PATCH v2 1/3] net: ipv4: Convert IP network timestamps to be y2038 safe
In reply to Deepa DinamaniQuoted 12 lines · On Saturday 27 February 2016 00:32:15 Deepa Dinamani wrote:
ICMP timestamp messages and IP source route options require timestamps to be in milliseconds modulo 24 hours from midnight UT format.
Add
inet_current_timestamp()function to support this. The function returns the required timestamp in network byte order.Timestamp calculation is also changed to call
ktime_get_real_ts64()which uses struct timespec64. struct timespec64 is y2038 safe. Previously it calledgetnstimeofday()which uses struct timespec. struct timespec is not y2038 safe.
Quoted 7 lines
Signed-off-by Deepa Dinamani <[email protected]>Cc "David S. Miller" <[email protected]>Cc Alexey Kuznetsov <[email protected]>Cc Hideaki YOSHIFUJI <[email protected]>Cc James Morris <[email protected]>Cc Patrick McHardy <[email protected]>
_______________________________________________
Y2038 mailing list
[email protected]
https://lists.linaro.org/mailman/listinfo/y2038
PATCH v2 2/3 net: ipv4: tcp_probe: Replace timespec with timespec64
In reply to Deepa DinamaniTCP probe log timestamps use struct timespec which is not y2038 safe. Even though timespec might be good enough here as it is used to represent delta time, the plan is to get rid of all uses of timespec in the kernel.
Replace with struct timespec64 which is y2038 safe.
Prints still use unsigned long format and type.
--- net/ipv4/tcp_probe.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-)
net/ipv4/tcp_probe.c +4 -4
@@ -187,13 +187,13 @@ static int tcpprobe_sprint(char *tbuf, int n) {const struct tcp_log *p = tcp_probe.log + tcp_probe.tail; -struct timespec tv - =ktime_to_timespec (ktime_sub (p->tstamp, tcp_probe.start)); +struct timespec64 ts + =ktime_to_timespec64 (ktime_sub (p->tstamp, tcp_probe.start));return scnprintf (tbuf, n,"%lu.%09lu %pISpc %pISpc %d %#x %#x %u %u %u %u %u\n" , - (unsigned long )tv.tv_sec, - (unsigned long )tv.tv_nsec, + (unsigned long )ts.tv_sec, + (unsigned long )ts.tv_nsec, &p->src, &p->dst, p->length, p->snd_nxt, p->snd_una, p->snd_cwnd, p->ssthresh, p->snd_wnd, p->srtt, p->rcv_wnd); }
Signature · 1 line
1.9.1
Re: [PATCH v2 2/3] net: ipv4: tcp_probe: Replace timespec with timespec64
Quoted 9 lines · Deepa Dinamani
TCP probe log timestamps use struct timespec which is not y2038 safe. Even though timespec might be good enough here as it is used to represent delta time, the plan is to get rid of all uses of timespec in the kernel.
Replace with struct timespec64 which is y2038 safe.Prints still use unsigned long format and type.
Signed-off-by Deepa Dinamani <[email protected]>
Quoted 33 lines
Reviewed-by Arnd Bergmann <[email protected]>Cc "David S. Miller" <[email protected]>Cc Alexey Kuznetsov <[email protected]>Cc James Morris <[email protected]>Cc Hideaki YOSHIFUJI <[email protected]>Cc Patrick McHardy <[email protected]>--- net/ipv4/tcp_probe.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-)net/ipv4/tcp_probe.c +4
-4@@ -187,13 +187,13 @@ static int tcpprobe_sprint(char *tbuf, int n) {const struct tcp_log *p = tcp_probe.log + tcp_probe.tail; -struct timespec tv - =ktime_to_timespec (ktime_sub (p->tstamp, tcp_probe.start)); +struct timespec64 ts + =ktime_to_timespec64 (ktime_sub (p->tstamp, tcp_probe.start));return scnprintf (tbuf, n,"%lu.%09lu %pISpc %pISpc %d %#x %#x %u %u %u %u %u\n" , - (unsigned long )tv.tv_sec, - (unsigned long )tv.tv_nsec, + (unsigned long )ts.tv_sec, + (unsigned long )ts.tv_nsec, &p->src, &p->dst, p->length, p->snd_nxt, p->snd_una, p->snd_cwnd, p->ssthresh, p->snd_wnd, p->srtt, p->rcv_wnd); }
Signature · 2 lines
Hideaki Yoshifuji <[email protected]> Technical Division, MIRACLE LINUX CORPORATION
PATCH v2 3/3 net: sctp: Convert log timestamps to be y2038 safe
In reply to Deepa DinamaniSCTP probe log timestamps use struct timespec which is not y2038 safe.
Use struct timespec64 which is 2038 safe instead.
Use monotonic time instead of real time as only time differences are logged.
--- net/sctp/probe.c | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-)
net/sctp/probe.c +5 -5
@@ -65,7 +65,7 @@ static struct {struct kfifo fifo;spinlock_t lock;wait_queue_head_t wait; -struct timespec tstart; +struct timespec64 tstart; } sctpw; static __printf(1, 2) void printl(const char *fmt, ...)
@@ -85,7 +85,7 @@ static __printf(1, 2) void printl(const char *fmt, ...)static int sctpprobe_open (struct inode *inode,struct file *file) {kfifo_reset (&sctpw.fifo); -getnstimeofday (&sctpw.tstart); +ktime_get_ts64 (&sctpw.tstart);return 0 ; }
@@ -138,7 +138,7 @@ static sctp_disposition_t jsctp_sf_eat_sack(struct net *net,struct sk_buff *skb = chunk->skb;struct sctp_transport *sp;static __u32 lcwnd =0 ; -struct timespec now; +struct timespec64 now; sp = asoc->peer.primary_path;
@@ -149,8 +149,8 @@ static sctp_disposition_t jsctp_sf_eat_sack(struct net *net, (full || sp->cwnd != lcwnd)) { lcwnd = sp->cwnd; -getnstimeofday (&now); - now =timespec_sub (now, sctpw.tstart); +ktime_get_ts64 (&now); + now =timespec64_sub (now, sctpw.tstart);printl ("%lu.%06lu " , (unsigned long ) now.tv_sec, (unsigned long ) now.tv_nsec /NSEC_PER_USEC );
Signature · 1 line
1.9.1
David Miller
maintainerFrom: Deepa Dinamani <[email protected]>
Date: Sat, 27 Feb 2016 00:32:14 -0800
Quoted 12 lines
Introduction:
The series is aimed at transitioning network timestamps to being y2038 safe.
All patches can be reviewed and merged independently.Socket timestamps and ioctl calls will be handled separately.
Thanks to Arnd Bergmann for discussing solution options with me.
Solution:
Quoted 8 lines
Data type struct timespec is not y2038 safe. Replace timespec with struct timespec64 which is y2038 safe.
Changes v1 -> v2:
Move and renameinet_current_time()as discussed Squash patches 1 and 2
Reword commit text for patch 2/3
Carry over review tags
Series applied to net-next, thanks.