Skip to content

Commit 0e1087f

Browse files
committed
natstacklat: Initialize the TAI-offset from user space
Make the user space loader calculate the TAI-offset at startup and set it as a constant for the eBPF programs. Split the open and loading stages of the eBPF programs apart to enable setting constants in the eBPF programs. Note that on some systems (e.g. most debian systems by default), the TAI offset may (incorrectly) be 0, so that CLOCK_TAI becomes identical to CLOCK_REALTIME. While this is principly incorrect, it does not pose an issue for netstacklat, as it only needs the TAI offset to translate CLOCK_TAI to CLOCK_REALTIME (which skb->tstamp is assumed to use as clock basis). Therefore, netstacklat will (from this commit) work correctly even if the TAI offset is not correctly set on the system. Limitation: The TAI offset is only set once the program is first loaded, and is not dynamically updated in case the TAI offset changes. So if the program is running while a leap second occurs, the recorded latencies may be off with one second. Furthermore, as the TAI offset is set from user space, it will not work when just using the eBPF portion together with ebpf-exporter. Signed-off-by: Simon Sundberg <[email protected]>
1 parent 7e178df commit 0e1087f

File tree

2 files changed

+21
-3
lines changed

2 files changed

+21
-3
lines changed

netstacklat/netstacklat.bpf.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@
1111

1212
char LICENSE[] SEC("license") = "GPL";
1313

14-
static volatile const u64 TAI_OFFSET = (37UL * NS_PER_S);
14+
volatile const signed long long TAI_OFFSET = (37LL * NS_PER_S);
1515

1616
/* Helpers in maps.bpf.h require any histogram key to be a struct with a bucket member */
1717
struct hist_key {

netstacklat/netstacklat.c

Lines changed: 20 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ static const char *__doc__ =
1414
#include <sys/timerfd.h>
1515
#include <sys/epoll.h>
1616
#include <sys/socket.h>
17+
#include <sys/timex.h>
1718

1819
#include <bpf/bpf.h>
1920
#include <bpf/libbpf.h>
@@ -445,6 +446,14 @@ static int enable_sw_rx_tstamps(void)
445446
return err;
446447
}
447448

449+
static long get_tai_offset(void)
450+
{
451+
struct ntptimeval ntpt;
452+
453+
ntp_gettimex(&ntpt);
454+
return ntpt.tai;
455+
}
456+
448457
static int init_signalfd(void)
449458
{
450459
sigset_t mask;
@@ -630,14 +639,23 @@ int main(int argc, char *argv[])
630639
return err;
631640
}
632641

633-
obj = netstacklat_bpf__open_and_load();
642+
obj = netstacklat_bpf__open();
634643
if (!obj) {
635644
err = libbpf_get_error(obj);
636645
libbpf_strerror(err, errmsg, sizeof(errmsg));
637-
fprintf(stderr, "Failed loading eBPF programs: %s\n", errmsg);
646+
fprintf(stderr, "Failed opening eBPF object file: %s\n", errmsg);
638647
goto exit_sockfd;
639648
}
640649

650+
obj->rodata->TAI_OFFSET = (signed long long)get_tai_offset() * NS_PER_S;
651+
652+
err = netstacklat_bpf__load(obj);
653+
if (err) {
654+
libbpf_strerror(err, errmsg, sizeof(errmsg));
655+
fprintf(stderr, "Failed loading eBPF programs: %s\n", errmsg);
656+
goto exit_destroy_bpf;
657+
}
658+
641659
err = netstacklat_bpf__attach(obj);
642660
if (err) {
643661
libbpf_strerror(err, errmsg, sizeof(errmsg));

0 commit comments

Comments
 (0)