Skip to content

Commit 068bae2

Browse files
olsajiriKernel Patches Daemon
authored andcommitted
libbpf: Add support to parse extra info in usdt note record
Adding support to parse extra info in usdt note record that indicates there's nop,nop5 emitted for probe. We detect this by checking extra zero byte placed in between args zero termination byte and desc data end. Please see [1] for more details. Together with uprobe syscall feature detection we can decide if we want to place the probe on top of nop or nop5. [1] https://github.com/libbpf/usdt Signed-off-by: Jiri Olsa <[email protected]>
1 parent 26a1cc7 commit 068bae2

File tree

1 file changed

+26
-1
lines changed

1 file changed

+26
-1
lines changed

tools/lib/bpf/usdt.c

Lines changed: 26 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -241,6 +241,7 @@ struct usdt_note {
241241
long loc_addr;
242242
long base_addr;
243243
long sema_addr;
244+
bool nop_combo;
244245
};
245246

246247
struct usdt_target {
@@ -262,6 +263,7 @@ struct usdt_manager {
262263
bool has_bpf_cookie;
263264
bool has_sema_refcnt;
264265
bool has_uprobe_multi;
266+
bool has_uprobe_syscall;
265267
};
266268

267269
struct usdt_manager *usdt_manager_new(struct bpf_object *obj)
@@ -301,6 +303,11 @@ struct usdt_manager *usdt_manager_new(struct bpf_object *obj)
301303
* usdt probes.
302304
*/
303305
man->has_uprobe_multi = kernel_supports(obj, FEAT_UPROBE_MULTI_LINK);
306+
307+
/*
308+
* Detect kernel support for uprobe syscall to be used to pick usdt attach point.
309+
*/
310+
man->has_uprobe_syscall = kernel_supports(obj, FEAT_UPROBE_SYSCALL);
304311
return man;
305312
}
306313

@@ -784,6 +791,15 @@ static int collect_usdt_targets(struct usdt_manager *man, Elf *elf, const char *
784791
target = &targets[target_cnt];
785792
memset(target, 0, sizeof(*target));
786793

794+
/*
795+
* We have usdt with nop,nop5 instruction and we detected uprobe syscall,
796+
* so we can place the uprobe directly on nop5 (+1) to get it optimized.
797+
*/
798+
if (note.nop_combo && man->has_uprobe_syscall) {
799+
usdt_abs_ip++;
800+
usdt_rel_ip++;
801+
}
802+
787803
target->abs_ip = usdt_abs_ip;
788804
target->rel_ip = usdt_rel_ip;
789805
target->sema_off = usdt_sema_off;
@@ -1144,7 +1160,7 @@ struct bpf_link *usdt_manager_attach_usdt(struct usdt_manager *man, const struct
11441160
static int parse_usdt_note(GElf_Nhdr *nhdr, const char *data, size_t name_off, size_t desc_off,
11451161
struct usdt_note *note)
11461162
{
1147-
const char *provider, *name, *args;
1163+
const char *provider, *name, *args, *end, *extra;
11481164
long addrs[3];
11491165
size_t len;
11501166

@@ -1182,6 +1198,15 @@ static int parse_usdt_note(GElf_Nhdr *nhdr, const char *data, size_t name_off, s
11821198
if (args >= data + len) /* missing arguments spec */
11831199
return -EINVAL;
11841200

1201+
extra = memchr(args, '\0', data + len - args);
1202+
if (!extra) /* non-zero-terminated args */
1203+
return -EINVAL;
1204+
++extra;
1205+
end = data + len;
1206+
1207+
/* check if we have one extra byte and if it's zero */
1208+
note->nop_combo = (extra + 1) == end && *extra == 0;
1209+
11851210
note->provider = provider;
11861211
note->name = name;
11871212
if (*args == '\0' || *args == ':')

0 commit comments

Comments
 (0)