167306f84SDaniel Xu // SPDX-License-Identifier: GPL-2.0
267306f84SDaniel Xu // Copyright (c) 2019 Facebook
367306f84SDaniel Xu 
467306f84SDaniel Xu #include <stddef.h>
567306f84SDaniel Xu #include <linux/ptrace.h>
667306f84SDaniel Xu #include <linux/bpf.h>
767306f84SDaniel Xu #include <bpf/bpf_helpers.h>
8df8ff353SAndrii Nakryiko #include <bpf/bpf_tracing.h>
967306f84SDaniel Xu 
1067306f84SDaniel Xu int valid = 0;
1167306f84SDaniel Xu int required_size_out = 0;
1267306f84SDaniel Xu int written_stack_out = 0;
1367306f84SDaniel Xu int written_global_out = 0;
1467306f84SDaniel Xu 
1567306f84SDaniel Xu struct {
1667306f84SDaniel Xu 	__u64 _a;
1767306f84SDaniel Xu 	__u64 _b;
1867306f84SDaniel Xu 	__u64 _c;
1967306f84SDaniel Xu } fpbe[30] = {0};
2067306f84SDaniel Xu 
2167306f84SDaniel Xu SEC("perf_event")
perf_branches(void * ctx)2267306f84SDaniel Xu int perf_branches(void *ctx)
2367306f84SDaniel Xu {
2467306f84SDaniel Xu 	__u64 entries[4 * 3] = {0};
2567306f84SDaniel Xu 	int required_size, written_stack, written_global;
2667306f84SDaniel Xu 
2767306f84SDaniel Xu 	/* write to stack */
2867306f84SDaniel Xu 	written_stack = bpf_read_branch_records(ctx, entries, sizeof(entries), 0);
2967306f84SDaniel Xu 	/* ignore spurious events */
3067306f84SDaniel Xu 	if (!written_stack)
3167306f84SDaniel Xu 		return 1;
3267306f84SDaniel Xu 
3367306f84SDaniel Xu 	/* get required size */
3467306f84SDaniel Xu 	required_size = bpf_read_branch_records(ctx, NULL, 0,
3567306f84SDaniel Xu 						BPF_F_GET_BRANCH_RECORDS_SIZE);
3667306f84SDaniel Xu 
3767306f84SDaniel Xu 	written_global = bpf_read_branch_records(ctx, fpbe, sizeof(fpbe), 0);
3867306f84SDaniel Xu 	/* ignore spurious events */
3967306f84SDaniel Xu 	if (!written_global)
4067306f84SDaniel Xu 		return 1;
4167306f84SDaniel Xu 
4267306f84SDaniel Xu 	required_size_out = required_size;
4367306f84SDaniel Xu 	written_stack_out = written_stack;
4467306f84SDaniel Xu 	written_global_out = written_global;
4567306f84SDaniel Xu 	valid = 1;
4667306f84SDaniel Xu 
4767306f84SDaniel Xu 	return 0;
4867306f84SDaniel Xu }
4967306f84SDaniel Xu 
5067306f84SDaniel Xu char _license[] SEC("license") = "GPL";
51