1666b2c10SAndrii Nakryiko // SPDX-License-Identifier: GPL-2.0
2666b2c10SAndrii Nakryiko // Copyright (c) 2019 Facebook
3666b2c10SAndrii Nakryiko 
4666b2c10SAndrii Nakryiko #include <linux/ptrace.h>
5666b2c10SAndrii Nakryiko #include <linux/bpf.h>
63e689141SToke Høiland-Jørgensen #include <bpf/bpf_helpers.h>
7666b2c10SAndrii Nakryiko 
8*256eab48SAndrii Nakryiko const struct {
9666b2c10SAndrii Nakryiko 	unsigned a[4];
10666b2c10SAndrii Nakryiko 	/*
11666b2c10SAndrii Nakryiko 	 * if the struct's size is multiple of 16, compiler will put it into
12666b2c10SAndrii Nakryiko 	 * .rodata.cst16 section, which is not recognized by libbpf; work
13666b2c10SAndrii Nakryiko 	 * around this by ensuring we don't have 16-aligned struct
14666b2c10SAndrii Nakryiko 	 */
15666b2c10SAndrii Nakryiko 	char _y;
16666b2c10SAndrii Nakryiko } rdonly_values = { .a = {2, 3, 4, 5} };
17666b2c10SAndrii Nakryiko 
18*256eab48SAndrii Nakryiko struct {
19666b2c10SAndrii Nakryiko 	unsigned did_run;
20666b2c10SAndrii Nakryiko 	unsigned iters;
21666b2c10SAndrii Nakryiko 	unsigned sum;
22*256eab48SAndrii Nakryiko } res = {};
23666b2c10SAndrii Nakryiko 
24666b2c10SAndrii Nakryiko SEC("raw_tracepoint/sys_enter:skip_loop")
skip_loop(struct pt_regs * ctx)25666b2c10SAndrii Nakryiko int skip_loop(struct pt_regs *ctx)
26666b2c10SAndrii Nakryiko {
27666b2c10SAndrii Nakryiko 	/* prevent compiler to optimize everything out */
28666b2c10SAndrii Nakryiko 	unsigned * volatile p = (void *)&rdonly_values.a;
29666b2c10SAndrii Nakryiko 	unsigned iters = 0, sum = 0;
30666b2c10SAndrii Nakryiko 
31666b2c10SAndrii Nakryiko 	/* we should never enter this loop */
32666b2c10SAndrii Nakryiko 	while (*p & 1) {
33666b2c10SAndrii Nakryiko 		iters++;
34666b2c10SAndrii Nakryiko 		sum += *p;
35666b2c10SAndrii Nakryiko 		p++;
36666b2c10SAndrii Nakryiko 	}
37666b2c10SAndrii Nakryiko 	res.did_run = 1;
38666b2c10SAndrii Nakryiko 	res.iters = iters;
39666b2c10SAndrii Nakryiko 	res.sum = sum;
40666b2c10SAndrii Nakryiko 	return 0;
41666b2c10SAndrii Nakryiko }
42666b2c10SAndrii Nakryiko 
43666b2c10SAndrii Nakryiko SEC("raw_tracepoint/sys_enter:part_loop")
part_loop(struct pt_regs * ctx)44666b2c10SAndrii Nakryiko int part_loop(struct pt_regs *ctx)
45666b2c10SAndrii Nakryiko {
46666b2c10SAndrii Nakryiko 	/* prevent compiler to optimize everything out */
47666b2c10SAndrii Nakryiko 	unsigned * volatile p = (void *)&rdonly_values.a;
48666b2c10SAndrii Nakryiko 	unsigned iters = 0, sum = 0;
49666b2c10SAndrii Nakryiko 
50666b2c10SAndrii Nakryiko 	/* validate verifier can derive loop termination */
51666b2c10SAndrii Nakryiko 	while (*p < 5) {
52666b2c10SAndrii Nakryiko 		iters++;
53666b2c10SAndrii Nakryiko 		sum += *p;
54666b2c10SAndrii Nakryiko 		p++;
55666b2c10SAndrii Nakryiko 	}
56666b2c10SAndrii Nakryiko 	res.did_run = 1;
57666b2c10SAndrii Nakryiko 	res.iters = iters;
58666b2c10SAndrii Nakryiko 	res.sum = sum;
59666b2c10SAndrii Nakryiko 	return 0;
60666b2c10SAndrii Nakryiko }
61666b2c10SAndrii Nakryiko 
62666b2c10SAndrii Nakryiko SEC("raw_tracepoint/sys_enter:full_loop")
full_loop(struct pt_regs * ctx)63666b2c10SAndrii Nakryiko int full_loop(struct pt_regs *ctx)
64666b2c10SAndrii Nakryiko {
65666b2c10SAndrii Nakryiko 	/* prevent compiler to optimize everything out */
66666b2c10SAndrii Nakryiko 	unsigned * volatile p = (void *)&rdonly_values.a;
67666b2c10SAndrii Nakryiko 	int i = sizeof(rdonly_values.a) / sizeof(rdonly_values.a[0]);
68666b2c10SAndrii Nakryiko 	unsigned iters = 0, sum = 0;
69666b2c10SAndrii Nakryiko 
70666b2c10SAndrii Nakryiko 	/* validate verifier can allow full loop as well */
71666b2c10SAndrii Nakryiko 	while (i > 0 ) {
72666b2c10SAndrii Nakryiko 		iters++;
73666b2c10SAndrii Nakryiko 		sum += *p;
74666b2c10SAndrii Nakryiko 		p++;
75666b2c10SAndrii Nakryiko 		i--;
76666b2c10SAndrii Nakryiko 	}
77666b2c10SAndrii Nakryiko 	res.did_run = 1;
78666b2c10SAndrii Nakryiko 	res.iters = iters;
79666b2c10SAndrii Nakryiko 	res.sum = sum;
80666b2c10SAndrii Nakryiko 	return 0;
81666b2c10SAndrii Nakryiko }
82666b2c10SAndrii Nakryiko 
83666b2c10SAndrii Nakryiko char _license[] SEC("license") = "GPL";
84