Skip to content

Commit

Permalink
Revise python tutorial lesson 16 to make sure tutorial text and code …
Browse files Browse the repository at this point in the history
…match.
  • Loading branch information
freshdresch authored and yonghong-song committed May 29, 2019
1 parent a57dad4 commit 84ce85b
Show file tree
Hide file tree
Showing 3 changed files with 42 additions and 47 deletions.
44 changes: 20 additions & 24 deletions docs/tutorial_bcc_python_developer.md
Original file line number Diff line number Diff line change
Expand Up @@ -651,45 +651,41 @@ This is a slightly more complex tracing example than Hello World. This program
will be invoked for every task change in the kernel, and record in a BPF map
the new and old pids.

The C program below introduces two new concepts.
The first is the macro `BPF_TABLE`. This defines a table (type="hash"), with key
type `key_t` and leaf type `u64` (a single counter). The table name is `stats`,
containing 1024 entries maximum. One can `lookup`, `lookup_or_init`, `update`,
and `delete` entries from the table.
The second concept is the prev argument. This argument is treated specially by
the BCC frontend, such that accesses to this variable are read from the saved
context that is passed by the kprobe infrastructure. The prototype of the args
starting from position 1 should match the prototype of the kernel function being
kprobed. If done so, the program will have seamless access to the function
parameters.
The C program below introduces a new concept: the prev argument. This
argument is treated specially by the BCC frontend, such that accesses
to this variable are read from the saved context that is passed by the
kprobe infrastructure. The prototype of the args starting from
position 1 should match the prototype of the kernel function being
kprobed. If done so, the program will have seamless access to the
function parameters.

```c
#include <uapi/linux/ptrace.h>
#include <linux/sched.h>

struct key_t {
u32 prev_pid;
u32 curr_pid;
u32 prev_pid;
u32 curr_pid;
};
// map_type, key_type, leaf_type, table_name, num_entry

BPF_HASH(stats, struct key_t, u64, 1024);
int count_sched(struct pt_regs *ctx, struct task_struct *prev) {
struct key_t key = {};
u64 zero = 0, *val;
struct key_t key = {};
u64 zero = 0, *val;

key.curr_pid = bpf_get_current_pid_tgid();
key.prev_pid = prev->pid;
key.curr_pid = bpf_get_current_pid_tgid();
key.prev_pid = prev->pid;

// could also use `stats.increment(key);`
val = stats.lookup_or_init(&key, &zero);
(*val)++;
return 0;
// could also use `stats.increment(key);`
val = stats.lookup_or_init(&key, &zero);
(*val)++;
return 0;
}
```
The userspace component loads the file shown above, and attaches it to the
`finish_task_switch` kernel function.
The [] operator of the BPF object gives access to each BPF_TABLE in the
The `[]` operator of the BPF object gives access to each BPF_HASH in the
program, allowing pass-through access to the values residing in the kernel. Use
the object as you would any other python dict object: read, update, and deletes
are all allowed.
Expand All @@ -707,7 +703,7 @@ for k, v in b["stats"].items():
print("task_switch[%5d->%5d]=%u" % (k.prev_pid, k.curr_pid, v.value))
```

These programs have now been merged, and are both in [examples/tracing/task_switch.py](examples/tracing/task_switch.py).
These programs can be found in the files [examples/tracing/task_switch.c](../examples/tracing/task_switch.c) and [examples/tracing/task_switch.py](../examples/tracing/task_switch.py) respectively.

### Lesson 17. Further Study

Expand Down
21 changes: 21 additions & 0 deletions examples/tracing/task_switch.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
#include <uapi/linux/ptrace.h>
#include <linux/sched.h>

struct key_t {
u32 prev_pid;
u32 curr_pid;
};

BPF_HASH(stats, struct key_t, u64, 1024);
int count_sched(struct pt_regs *ctx, struct task_struct *prev) {
struct key_t key = {};
u64 zero = 0, *val;

key.curr_pid = bpf_get_current_pid_tgid();
key.prev_pid = prev->pid;

// could also use `stats.increment(key);`
val = stats.lookup_or_init(&key, &zero);
(*val)++;
return 0;
}
24 changes: 1 addition & 23 deletions examples/tracing/task_switch.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,29 +5,7 @@
from bcc import BPF
from time import sleep

b = BPF(text="""
#include <uapi/linux/ptrace.h>
#include <linux/sched.h>
struct key_t {
u32 prev_pid;
u32 curr_pid;
};
// map_type, key_type, leaf_type, table_name, num_entry
BPF_HASH(stats, struct key_t, u64, 1024);
int count_sched(struct pt_regs *ctx, struct task_struct *prev) {
struct key_t key = {};
u64 zero = 0, *val;
key.curr_pid = bpf_get_current_pid_tgid();
key.prev_pid = prev->pid;
// could also use `stats.increment(key);`
val = stats.lookup_or_init(&key, &zero);
(*val)++;
return 0;
}
""")
b = BPF(src_file="task_switch.c")
b.attach_kprobe(event="finish_task_switch", fn_name="count_sched")

# generate many schedule events
Expand Down

0 comments on commit 84ce85b

Please sign in to comment.