Skip to content

Commit 581269e

Browse files
committed
docs: Fix user-guide/compilation
1 parent 8bfd998 commit 581269e

File tree

1 file changed

+13
-110
lines changed

1 file changed

+13
-110
lines changed

docs/user-guide/compilation.md

Lines changed: 13 additions & 110 deletions
Original file line numberDiff line numberDiff line change
@@ -6,10 +6,9 @@ PythonBPF provides several functions and classes for compiling Python code into
66

77
The compilation process transforms Python code into executable BPF programs:
88

9-
1. **Python Source** → AST parsing
10-
2. **AST** → LLVM IR generation (using llvmlite)
11-
3. **LLVM IR** → BPF bytecode (using llc)
12-
4. **BPF Object** → Kernel loading (using libbpf)
9+
1. **Python AST** → LLVM IR generation (using llvmlite)
10+
2. **LLVM IR** → BPF bytecode (using llc)
11+
3. **BPF Object** → Kernel loading (using libbpf)
1312

1413
## Compilation Functions
1514

@@ -20,14 +19,14 @@ Compile Python source to LLVM Intermediate Representation.
2019
#### Signature
2120

2221
```python
23-
def compile_to_ir(filename: str, output: str, loglevel=logging.INFO)
22+
def compile_to_ir(filename: str, output: str, loglevel=logging.WARNING)
2423
```
2524

2625
#### Parameters
2726

2827
* `filename` - Path to the Python source file to compile
2928
* `output` - Path where the LLVM IR file (.ll) should be written
30-
* `loglevel` - Logging level (default: `logging.INFO`)
29+
* `loglevel` - Logging level (default: `logging.WARNING`)
3130

3231
#### Usage
3332

@@ -49,22 +48,6 @@ This function generates an `.ll` file containing LLVM IR, which is human-readabl
4948

5049
* Debugging compilation issues
5150
* Understanding code generation
52-
* Manual optimization
53-
* Educational purposes
54-
55-
#### Example IR Output
56-
57-
```llvm
58-
; ModuleID = 'bpf_module'
59-
source_filename = "bpf_module"
60-
target triple = "bpf"
61-
62-
define i64 @hello_world(i8* %ctx) {
63-
entry:
64-
; BPF code here
65-
ret i64 0
66-
}
67-
```
6851

6952
### compile()
7053

@@ -73,14 +56,14 @@ Compile Python source to BPF object file.
7356
#### Signature
7457

7558
```python
76-
def compile(filename: str = None, output: str = None, loglevel=logging.INFO)
59+
def compile(filename: str = None, output: str = None, loglevel=logging.WARNING)
7760
```
7861

7962
#### Parameters
8063

8164
* `filename` - Path to the Python source file (default: calling file)
8265
* `output` - Path for the output object file (default: same name with `.o` extension)
83-
* `loglevel` - Logging level (default: `logging.INFO`)
66+
* `loglevel` - Logging level (default: `logging.WARNING`)
8467

8568
#### Usage
8669

@@ -107,17 +90,6 @@ This function generates a `.o` file containing BPF bytecode that can be:
10790
* Verified with the BPF verifier
10891
* Distributed as a compiled binary
10992

110-
#### Compilation Steps
111-
112-
The `compile()` function performs these steps:
113-
114-
1. Parse Python source to AST
115-
2. Process decorators and find BPF functions
116-
3. Generate LLVM IR
117-
4. Write IR to temporary `.ll` file
118-
5. Invoke `llc` to compile to BPF object
119-
6. Write final `.o` file
120-
12193
### BPF Class
12294

12395
The `BPF` class provides a high-level interface to compile, load, and attach BPF programs.
@@ -126,7 +98,7 @@ The `BPF` class provides a high-level interface to compile, load, and attach BPF
12698

12799
```python
128100
class BPF:
129-
def __init__(self, filename: str = None, loglevel=logging.INFO)
101+
def __init__(self, filename: str = None, loglevel=logging.WARNING)
130102
def load(self)
131103
def attach_all(self)
132104
def load_and_attach(self)
@@ -135,7 +107,7 @@ class BPF:
135107
#### Parameters
136108

137109
* `filename` - Path to Python source file (default: calling file)
138-
* `loglevel` - Logging level (default: `logging.INFO`)
110+
* `loglevel` - Logging level (default: `logging.WARNING`)
139111

140112
#### Methods
141113

@@ -212,7 +184,7 @@ from ctypes import c_void_p, c_int64
212184
@section("tracepoint/syscalls/sys_enter_execve")
213185
def trace_exec(ctx: c_void_p) -> c_int64:
214186
print("Process started")
215-
return c_int64(0)
187+
return 0
216188

217189
@bpf
218190
@bpfglobal
@@ -224,13 +196,13 @@ if __name__ == "__main__":
224196
b = BPF()
225197
b.load_and_attach()
226198
trace_pipe()
227-
199+
228200
# Method 2: Step-by-step
229201
# b = BPF()
230202
# b.load()
231203
# b.attach_all()
232204
# trace_pipe()
233-
205+
234206
# Method 3: Manual compilation
235207
# from pythonbpf import compile
236208
# compile(filename="my_program.py", output="my_program.o")
@@ -285,11 +257,6 @@ The LLVM IR is compiled to BPF bytecode using `llc`:
285257
llc -march=bpf -filetype=obj input.ll -o output.o
286258
```
287259

288-
Compiler flags:
289-
* `-march=bpf` - Target BPF architecture
290-
* `-filetype=obj` - Generate object file
291-
* `-O2` - Optimization level (sometimes used)
292-
293260
### Kernel Loading
294261

295262
The compiled object is loaded using `pylibbpf`:
@@ -301,13 +268,6 @@ obj = BpfObject(path="program.o")
301268
obj.load()
302269
```
303270

304-
The kernel verifier checks:
305-
* Memory access patterns
306-
* Pointer usage
307-
* Loop bounds
308-
* Instruction count
309-
* Helper function calls
310-
311271
## Debugging Compilation
312272

313273
### Logging
@@ -364,24 +324,11 @@ bpftool map dump id <ID>
364324

365325
If the kernel verifier rejects your program:
366326

367-
1. Check `dmesg` for detailed error messages:
327+
* Check `dmesg` for detailed error messages:
368328
```bash
369329
sudo dmesg | tail -50
370330
```
371331

372-
2. Common issues:
373-
* Unbounded loops
374-
* Invalid pointer arithmetic
375-
* Exceeding instruction limit
376-
* Invalid helper calls
377-
* License incompatibility
378-
379-
3. Solutions:
380-
* Simplify logic
381-
* Use bounded loops
382-
* Check pointer operations
383-
* Verify GPL license
384-
385332
## Compilation Options
386333

387334
### Optimization Levels
@@ -395,20 +342,11 @@ While PythonBPF doesn't expose optimization flags directly, you can:
395342

396343
2. Modify the compilation pipeline in your code
397344

398-
### Target Options
399-
400-
BPF compilation targets the BPF architecture:
401-
402-
* **Architecture**: `bpf`
403-
* **Endianness**: Typically little-endian
404-
* **Pointer size**: 64-bit
405-
406345
### Debug Information
407346

408347
PythonBPF automatically generates debug information (DWARF) for:
409348

410349
* Function names
411-
* Line numbers
412350
* Variable names
413351
* Type information
414352

@@ -461,41 +399,6 @@ BPF objects are generally compatible across kernel versions, but:
461399
* Helper functions may not be available on older kernels
462400
* BTF (BPF Type Format) requirements vary
463401

464-
## Best Practices
465-
466-
1. **Keep compilation separate from runtime**
467-
```python
468-
if __name__ == "__main__":
469-
b = BPF()
470-
b.load_and_attach()
471-
# Runtime code
472-
```
473-
474-
2. **Handle compilation errors gracefully**
475-
```python
476-
try:
477-
b = BPF()
478-
b.load()
479-
except Exception as e:
480-
print(f"Failed to load BPF program: {e}")
481-
exit(1)
482-
```
483-
484-
3. **Use appropriate logging levels**
485-
* `DEBUG` for development
486-
* `INFO` for production
487-
* `ERROR` for critical issues
488-
489-
4. **Cache compiled objects**
490-
* Compile once, load many times
491-
* Store `.o` files for reuse
492-
* Version your compiled objects
493-
494-
5. **Test incrementally**
495-
* Compile after each change
496-
* Verify programs load successfully
497-
* Test attachment before full deployment
498-
499402
## Troubleshooting
500403

501404
### Compilation Fails

0 commit comments

Comments
 (0)