Skip to content

Commit 25fb76d

Browse files
authored
Thread info and process visualization (#10)
* added multithread functionality and better readability * testing added, unit and e2e * refactor * e2e testing with multithread support * visualization with bar added and perfected * tests added * moved the pre-commit script * refactored the scripts folder to e2e testing * refactoring done with more helpers * thread state fixed * updated README
1 parent 59a224d commit 25fb76d

20 files changed

Lines changed: 1031 additions & 236 deletions

.devcontainer/devcontainer.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@
1313
"source=${localEnv:HOME}${localEnv:USERPROFILE}/.ssh,target=/home/ubuntu/.ssh,type=bind,consistency=cached"
1414
],
1515
"features": {},
16-
"postCreateCommand": "bash -c 'echo \"Setting up development environment...\" && make --version && gcc --version && clang-format --version && echo \"Installing Git hooks...\" && mkdir -p .git/hooks && if [ -f scripts/pre-commit.sh ]; then cp scripts/pre-commit.sh .git/hooks/pre-commit && chmod +x .git/hooks/pre-commit && echo \"✓ Git pre-commit hook installed\"; fi && echo \"✓ Dev environment ready!\"'",
16+
"postCreateCommand": "bash -c 'echo \"Setting up development environment...\" && make --version && gcc --version && clang-format --version && echo \"Installing Git hooks...\" && mkdir -p .git/hooks && if [ -f .github/pre-commit.sh ]; then cp .github/pre-commit.sh .git/hooks/pre-commit && chmod +x .git/hooks/pre-commit && echo \"✓ Git pre-commit hook installed\"; fi && echo \"✓ Dev environment ready!\"'",
1717
"customizations": {
1818
"vscode": {
1919
"extensions": [

.gitignore

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,7 @@ core.*
4949
*.backup
5050

5151
# QEMU testing environment
52-
scripts/qemu-env/
52+
e2e/qemu-env/
5353
*~
5454

5555
# Static analysis output

Makefile

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,13 @@ user:
3939
gcc -Wall -o $(BUILD_DIR)/$(USER_PROG) $(SRC_DIR)/$(USER_PROG).c
4040
@echo "User program built successfully!"
4141

42+
# Build multi-threaded test program (for E2E testing)
43+
test-multithread:
44+
@echo "Building multi-threaded test program..."
45+
@mkdir -p $(BUILD_DIR)
46+
gcc -Wall -pthread -o $(BUILD_DIR)/test_multithread $(SRC_DIR)/test_multithread.c
47+
@echo "Multi-threaded test program built successfully!"
48+
4249
# Function-level unit tests (user-space)
4350
unit:
4451
@echo "Building function-level unit tests..."
@@ -172,6 +179,7 @@ help:
172179
@echo " make all - Build both kernel module and user program (default)"
173180
@echo " make module - Build kernel module only"
174181
@echo " make user - Build user program only"
182+
@echo " make test-multithread - Build multi-threaded test program"
175183
@echo " make unit - Build and run function-level unit tests"
176184
@echo " make install - Install kernel module (requires root)"
177185
@echo " make uninstall - Remove kernel module (requires root)"

README.md

Lines changed: 99 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -4,17 +4,76 @@
44
[![Last Commit](https://img.shields.io/github/last-commit/navidpadid/process-info-kernel-module?style=for-the-badge&logo=git&logoColor=white)](https://github.com/navidpadid/process-info-kernel-module/commits/main)
55
[![License](https://img.shields.io/badge/License-Dual%20BSD%2FGPL-blue?style=for-the-badge)](LICENSE)
66

7-
> A Linux kernel module that extracts detailed process information including memory layout, CPU usage, and ELF sections via `/proc` filesystem.
7+
> A Linux kernel module that extracts detailed process and it's thread information including memory layout, CPU usage, and ELF sections via `/proc` filesystem.
88
99
## Features
1010

1111
- **Process Memory Layout**: Code, Data, BSS, Heap, and Stack addresses
12-
- **CPU Usage Tracking**: Real-time CPU percentage calculation
12+
- **Visual Memory Map**: Proportional bar chart visualization of memory regions
13+
- **Thread Information**: List all threads with TID, state, CPU usage, priority, and CPU affinity
14+
- **CPU Usage Tracking**: Real-time CPU percentage calculation per process and thread
1315
- **ELF Section Analysis**: Binary base address and section boundaries
1416
- **Proc Interface**: Easy access through `/proc/elf_det/`
1517
- **Comprehensive Testing**: Unit tests and QEMU-based E2E testing
1618
- **Code Quality**: Pre-configured static analysis (sparse, cppcheck, checkpatch)
1719

20+
### Example Output
21+
22+
```
23+
>> Enter process ID (or Ctrl+C to exit): 3115
24+
25+
================================================================================
26+
PROCESS INFORMATION
27+
================================================================================
28+
Command line: ./build/test_multithread
29+
Process ID: 3115
30+
Name: test_multithrea
31+
CPU Usage: 2.06%
32+
33+
Memory Layout:
34+
--------------------------------------------------------------------------------
35+
Code Section: 0x0000643f5b8f5000 - 0x0000643f5b8f5459
36+
Data Section: 0x0000643f5b8f7d78 - 0x0000643f5b8f8010
37+
BSS Section: 0x0000643f5b8f8010 - 0x0000643f87d3b000
38+
Heap: 0x0000643f87d3b000 - 0x0000643f87d5c000
39+
Stack: 0x00007ffcdf141220 - 0x00007ffcdf121000
40+
ELF Base: 0x0000643f5b8f4000
41+
42+
Memory Layout Visualization:
43+
--------------------------------------------------------------------------------
44+
Low: 0x0000643f5b8f5000
45+
46+
CODE (1 KB)
47+
[= ]
48+
49+
DATA (664 B)
50+
[= ]
51+
52+
BSS (708 MB)
53+
[================================================= ]
54+
55+
HEAP (132 KB)
56+
[= ]
57+
58+
STACK (128 KB)
59+
[= ]
60+
61+
High: 0x00007ffcdf141220
62+
--------------------------------------------------------------------------------
63+
64+
================================================================================
65+
THREAD INFORMATION
66+
================================================================================
67+
TID NAME CPU(%) STATE PRIORITY NICE CPU_AFFINITY
68+
----- --------------- ------- ----- -------- ---- ----------------
69+
3115 test_multithrea 2.06 S 0 0 0,1
70+
3117 test_multithrea 0.32 S 0 0 0,1
71+
3118 test_multithrea 0.29 S 0 0 0,1
72+
3119 test_multithrea 0.26 S 0 0 0,1
73+
3120 test_multithrea 0.14 S 0 0 0,1
74+
--------------------------------------------------------------------------------
75+
```
76+
1877
## Quick Start
1978

2079
### Prerequisites
@@ -38,42 +97,35 @@
3897
./build/proc_elf_ctrl
3998
```
4099

100+
### Uninstall the Module
101+
102+
```bash
103+
sudo make uninstall
104+
```
105+
41106
## Project Structure
42107

43108
```
44109
kernel_module/
45110
├── .devcontainer/ # Dev container config (Docker + VS Code setup)
46111
├── .github/ # CI/CD workflows (GitHub Actions)
47112
├── docs/ # Detailed documentation
48-
├── scripts/ # Testing scripts (QEMU setup, E2E testing automation)
113+
├── e2e/ # End-to-end testing scripts (QEMU setup, automation)
49114
├── src/ # Source code (kernel module, user program, tests, helpers)
50115
├── build/ # Build artifacts (generated by make)
51116
└── Makefile # Build system with quality checks
52117
```
53118

54-
The program will prompt you to enter a process ID (PID). You can find PIDs using:
119+
**Notes**:
120+
- **Memory Visualization**: Each region's bar length is proportional to its actual size
121+
- Sizes are automatically displayed in appropriate units (B, KB, or MB)
122+
- Low/High addresses show the memory address range of the process
123+
- BSS_START and BSS_END may be equal (zero-length BSS) in modern ELF binaries. This is normal.
124+
- Thread STATE: R=Running, S=Sleeping, D=Uninterruptible, T=Stopped, t=Traced, Z=Zombie, X=Dead
125+
- PRIORITY: Shown as nice value (-20 to 19, where lower is higher priority)
126+
- CPU_AFFINITY: Shows which CPUs the thread can run on
55127

56-
```bash
57-
ps aux | grep <process_name>
58-
```
59128

60-
### 3. Example Output
61-
62-
```
63-
************enter the process id: 1234
64-
65-
the process info is here:
66-
PID NAME CPU(%) START_CODE END_CODE START_DATA END_DATA BSS_START BSS_END HEAP_START HEAP_END STACK_START STACK_END ELF_BASE
67-
01234 bash 0.50 0x0000563a1234 0x0000563a5678 0x0000563a9abc 0x0000563adef0 0x0000563adef0 0x0000563adef0 0x0000563b0000 0x0000563b8000 0x00007ffd12345000 0x00007ffd12340000 0x0000563a1000
68-
```
69-
70-
**Note**: BSS_START and BSS_END may be equal (zero-length BSS) in modern ELF binaries. This is normal.
71-
72-
### 4. Uninstall the Module
73-
74-
```bash
75-
sudo make uninstall
76-
```
77129

78130
## Safe Testing with QEMU
79131

@@ -83,28 +135,36 @@ For maximum safety, test the kernel module in an isolated QEMU virtual machine t
83135

84136
```bash
85137
# One-time setup
86-
./scripts/qemu-setup.sh
138+
./e2e/qemu-setup.sh
87139

88140
# Start VM
89-
./scripts/qemu-run.sh
141+
./e2e/qemu-run.sh
90142

91143
# In another terminal, run automated tests
92-
./scripts/qemu-test.sh
144+
./e2e/qemu-test.sh
93145
```
94146

95147

96148
## Makefile Targets
97149

98150
```bash
99-
make all # Build kernel module and user program
100-
make install # Install kernel module (requires root)
101-
make uninstall # Remove kernel module
102-
make unit # Run unit tests (no kernel required)
103-
make test # Install module and run user program
104-
105-
make format # Format all source files
106-
make check # Run all static analysis
107-
make clean # Remove build artifacts
151+
make all # Build kernel module and user program
152+
make module # Build kernel module only
153+
make user # Build user program only
154+
make test-multithread # Build multi-threaded test program
155+
make install # Install kernel module (requires root)
156+
make uninstall # Remove kernel module
157+
make unit # Run unit tests (no kernel required)
158+
make test # Install module and run user program
159+
160+
make format # Format all source files
161+
make format-check # Check formatting (CI-friendly)
162+
make check # Run all static analysis
163+
make checkpatch # Check kernel coding style
164+
make sparse # Run sparse static analyzer
165+
make cppcheck # Run cppcheck static analyzer
166+
make clean # Remove build artifacts
167+
make help # Show help message
108168
```
109169

110170
## Testing
@@ -117,9 +177,9 @@ Runs pure function tests without kernel dependencies.
117177

118178
### QEMU Testing (Safe Kernel Testing)
119179
```bash
120-
./scripts/qemu-setup.sh # One-time setup
121-
./scripts/qemu-run.sh # Start VM
122-
./scripts/qemu-test.sh # Run automated tests
180+
./e2e/qemu-setup.sh # One-time setup
181+
./e2e/qemu-run.sh # Start VM
182+
./e2e/qemu-test.sh # Run automated tests
123183
```
124184

125185
See [docs/TESTING.md](docs/TESTING.md) for detailed testing documentation.

docs/SCRIPTS.md

Lines changed: 12 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -6,13 +6,13 @@ Scripts for testing the Linux Process Information Kernel Module in isolated QEMU
66

77
```bash
88
# QEMU Testing
9-
./scripts/qemu-setup.sh # One-time setup
10-
./scripts/qemu-run.sh # Start VM
11-
./scripts/qemu-test.sh # Automated tests (run from host in another terminal)
9+
./e2e/qemu-setup.sh # One-time setup
10+
./e2e/qemu-run.sh # Start VM
11+
./e2e/qemu-test.sh # Automated tests (run from host in another terminal)
1212

1313
# Other utilities
14-
./scripts/pre-commit.sh # Pre-commit hook (auto-installed in dev container)
15-
./scripts/quick-reference.sh # Display quick reference guide
14+
./.github/pre-commit.sh # Pre-commit hook (auto-installed in dev container)
15+
./e2e/quick-reference.sh # Display quick reference guide
1616
```
1717

1818
## Script Descriptions
@@ -69,15 +69,15 @@ Scripts for testing the Linux Process Information Kernel Module in isolated QEMU
6969
**Usage**:
7070
```bash
7171
# Start VM in one terminal
72-
./scripts/qemu-run.sh
72+
./e2e/qemu-run.sh
7373

7474
# Run tests from another terminal
75-
./scripts/qemu-test.sh
75+
./e2e/qemu-test.sh
7676
```
7777

7878
**Output**: Shows build process, module loading, test results, and kernel logs.
7979

80-
### `pre-commit.sh`
80+
### `.github/pre-commit.sh`
8181
**Purpose**: Git pre-commit hook for code quality
8282

8383
**What it does**:
@@ -105,7 +105,7 @@ git commit --no-verify -m "message"
105105

106106
**Usage**:
107107
```bash
108-
./scripts/quick-reference.sh
108+
./e2e/quick-reference.sh
109109
```
110110

111111
## QEMU VM Details
@@ -160,13 +160,13 @@ rsync -avz --exclude='.git' --exclude='build' \
160160

161161
### Remove QEMU Environment
162162
```bash
163-
rm -rf scripts/qemu-env/
163+
rm -rf e2e/qemu-env/
164164
```
165165

166166
### Reinstall Fresh VM
167167
```bash
168-
rm -rf scripts/qemu-env/
169-
./scripts/qemu-setup.sh
168+
rm -rf e2e/qemu-env/
169+
./e2e/qemu-setup.sh
170170
```
171171

172172
### Check VM Status

docs/TECHNICAL.md

Lines changed: 39 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -5,10 +5,12 @@
55
The kernel module creates entries in `/proc/elf_det/`:
66
- `/proc/elf_det/pid` - Write-only file to specify target PID
77
- `/proc/elf_det/det` - Read-only file to retrieve process information
8+
- `/proc/elf_det/threads` - Read-only file to retrieve thread information
89

910
### Key Functions
1011

1112
- `elfdet_show()` - Main function to gather and format process information
13+
- `elfdet_threads_show()` - Gathers thread information for all threads in a process
1214
- `find_stack_vma_end()` - Finds stack VMA lower boundary by iterating VMAs
1315
- `procfile_write()` - Handles PID input from user space
1416
- `procfile_read()` - Returns formatted process data
@@ -58,13 +60,13 @@ Simple C program that supports two modes:
5860
```bash
5961
./build/proc_elf_ctrl
6062
```
61-
Prompts for a PID, writes to `/proc/elf_det/pid`, then reads `/proc/elf_det/det` and prints output.
63+
Prompts for a PID, writes to `/proc/elf_det/pid`, then reads `/proc/elf_det/det` and `/proc/elf_det/threads` and prints output.
6264

6365
### Argument Mode
6466
```bash
6567
./build/proc_elf_ctrl <PID>
6668
```
67-
Non-interactive mode - write PID and print exactly two lines.
69+
Non-interactive mode - write PID and print both process and thread information.
6870

6971
### Environment Override
7072

@@ -78,21 +80,22 @@ Internally, path construction is handled via `build_proc_path()`.
7880

7981
## Helper Libraries
8082

81-
### `src/elf_helpers.h`
82-
Pure functions for CPU usage, BSS range, heap range, and address range checking:
83+
### `src/elf_det.h`
84+
Pure functions for CPU usage, BSS range, heap range, thread state, and address range checking:
8385
- `compute_usage_permyriad()` - CPU usage calculation
8486
- `compute_bss_range()` - BSS boundary validation
8587
- `compute_heap_range()` - Heap boundary validation
8688
- `is_address_in_range()` - Address containment check
8789

8890
Works in both kernel and user space contexts.
8991

90-
### `src/user_helpers.h`
92+
### `src/proc_elf_ctrl.h`
9193
Path building with environment override:
9294
- `build_proc_path()` - Constructs `/proc/elf_det/` paths with `ELF_DET_PROC_DIR` support
9395

9496
## Output Format
9597

98+
### Process Information (`/proc/elf_det/det`)
9699
```
97100
PID NAME CPU(%) START_CODE END_CODE START_DATA END_DATA
98101
BSS_START BSS_END HEAP_START HEAP_END STACK_START
@@ -106,4 +109,35 @@ Example:
106109
0x0000563b8000 0x00007ffd12345000 0x00007ffd12340000 0x0000563a1000
107110
```
108111

112+
### Thread Information (`/proc/elf_det/threads`)
113+
```
114+
TID NAME CPU(%) STATE PRIORITY NICE CPU_AFF
115+
```
116+
117+
Example:
118+
```
119+
01234 bash 0.50 S 0 0 0,1,2,3
120+
01235 worker 0.01 R 0 0 0,1
121+
122+
Total threads: 2
123+
```
124+
125+
#### Thread State Codes
126+
- **R** - Running or runnable (on run queue)
127+
- **S** - Interruptible sleep (waiting for an event)
128+
- **D** - Uninterruptible sleep (usually I/O)
129+
- **T** - Stopped (by job control signal)
130+
- **t** - Tracing stop (by debugger)
131+
- **Z** - Zombie (terminated but not reaped)
132+
- **X** - Dead (should never be seen)
133+
134+
#### Thread Fields
135+
- **TID** - Thread ID (same as PID for main thread)
136+
- **NAME** - Thread name (typically same as process name)
137+
- **CPU(%)** - Per-thread CPU usage since thread start
138+
- **STATE** - Current thread state (see codes above)
139+
- **PRIORITY** - Shown as nice value (-20 to 19, lower = higher priority)
140+
- **NICE** - Nice value for the thread
141+
- **CPU_AFF** - CPU affinity mask (which CPUs thread can run on)
142+
109143
**Note**: BSS_START and BSS_END may be equal (zero-length BSS) in modern ELF binaries. This is normal.

0 commit comments

Comments
 (0)