Skip to content
This repository has been archived by the owner on Jun 18, 2024. It is now read-only.

Commit

Permalink
scx: Add new macros to compat.h
Browse files Browse the repository at this point in the history
Now that we have the hotplug sequence number, schedulers can set the
sequence number when opening the skeleton to detect hotplug events. In
order to provide backwards compatibility and avoid excess boilerplate,
let's add a new SCX_OPS_OPEN() macro that encapsulates this for the
caller.

In addition, we add an SCX_HOTPLUG_SQN() macro that can be used to read
the current global sequence number from
/sys/kernel/sched_ext/hotplug_sqn. This is called by SCX_OPS_OPEN() when
running on a kernel with hotplug sqn support.

Signed-off-by: David Vernet <[email protected]>
  • Loading branch information
Byte-Lab committed Apr 11, 2024
1 parent 084287e commit b0e0f90
Showing 1 changed file with 44 additions and 3 deletions.
47 changes: 44 additions & 3 deletions tools/sched_ext/include/scx/compat.h
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,9 @@
#define __SCX_COMPAT_H

#include <bpf/btf.h>
#include <fcntl.h>
#include <stdlib.h>
#include <unistd.h>

struct btf *__COMPAT_vmlinux_btf __attribute__((weak));

Expand Down Expand Up @@ -106,16 +109,54 @@ static inline bool __COMPAT_struct_has_field(const char *type, const char *field
#define __COMPAT_SCX_OPS_SWITCH_PARTIAL \
__COMPAT_ENUM_OR_ZERO("scx_ops_flags", "SCX_OPS_SWITCH_PARTIAL")

#define SCX_HOTPLUG_SQN() ({ \
int __fd, __errno; \
char __buf[32]; \
ssize_t __len; \
long __val; \
\
__fd = open("/sys/kernel/sched_ext/hotplug_sqn", O_RDONLY); \
SCX_BUG_ON(__fd < 0, "invalid fd %d", __fd); \
\
__len = read(__fd, __buf, sizeof(__buf) - 1); \
SCX_BUG_ON(__len <= 0, "read failed (%ld)", __len); \
__buf[__len] = 0; \
close(__fd); \
\
__errno = errno; \
__val = strtoul(__buf, NULL, 10); \
SCX_BUG_ON(errno != __errno, "invalid buf %s", __buf); \
\
__val; \
})

/*
* struct sched_ext_ops can change over time. If compat.bpf.h::SCX_OPS_DEFINE()
* is used to define ops and compat.h::SCX_OPS_LOAD/ATTACH() are used to load
* and attach it, backward compatibility is automatically maintained where
* reasonable.
*
* - sched_ext_ops.exit_dump_len was added later. On kernels which don't support
* it, the value is ignored and a warning is triggered if the value is
* requested to be non-zero.
* The following values were added in newer kernels:
*
* - sched_ext_ops.exit_dump_len
* o If nonzero and running on an older kernel, the value is set to zero
* and a warning is emitted
*
* - sched_ext_ops.hotplug_sqn
* o If nonzero and running on an older kernel, the scheduler will fail to
* load
*/
#define SCX_OPS_OPEN(__ops_name, __scx_name) ({ \
struct __scx_name *__skel; \
\
__skel = __scx_name##__open(); \
SCX_BUG_ON(!__skel, "Could not open " #__scx_name); \
\
if (__COMPAT_struct_has_field("sched_ext_ops", "hotplug_sqn")) \
__skel->struct_ops.__ops_name->hotplug_sqn = SCX_HOTPLUG_SQN(); \
__skel; \
})

#define SCX_OPS_LOAD(__skel, __ops_name, __scx_name, __uei_name) ({ \
UEI_SET_SIZE(__skel, __ops_name, __uei_name); \
if (__COMPAT_struct_has_field("sched_ext_ops", "exit_dump_len") && \
Expand Down

0 comments on commit b0e0f90

Please sign in to comment.