rrtrace 0.1.0 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.github/dependabot.yml +36 -0
- data/.github/workflows/ci.yml +94 -0
- data/.github/workflows/release.yml +4 -4
- data/Cargo.lock +26 -30
- data/Cargo.toml +8 -4
- data/README.md +77 -16
- data/exe/rrtrace +16 -0
- data/ext/rrtrace/process_manager_posix.h +18 -2
- data/ext/rrtrace/process_manager_windows.h +14 -0
- data/ext/rrtrace/rrtrace.c +153 -44
- data/ext/rrtrace/rrtrace_event.h +6 -15
- data/ext/rrtrace/rrtrace_event_ringbuffer.h +2 -2
- data/ext/rrtrace/shared_memory_posix.h +57 -5
- data/ext/rrtrace/shared_memory_windows.h +38 -3
- data/ext/rrtrace/time_posix.h +29 -0
- data/ext/rrtrace/time_windows.h +33 -0
- data/lib/rrtrace/run.rb +5 -0
- data/lib/rrtrace/version.rb +1 -1
- data/lib/rrtrace.rb +31 -3
- data/libexec/rrtrace +0 -0
- data/mise.toml +5 -2
- data/sig/rrtrace.rbs +3 -0
- data/src/main.rs +114 -32
- data/src/object_scatter.rs +110 -0
- data/src/oneshot_channel.rs +74 -0
- data/src/renderer/vertex_arena.rs +17 -13
- data/src/renderer.rs +268 -37
- data/src/ringbuffer.rs +2 -2
- data/src/shader.wgsl +160 -115
- data/src/trace_state.rs +500 -119
- data/src/universal_notifier.rs +31 -0
- data/taplo.toml +4 -0
- metadata +14 -3
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 4770d1ed4c3dfd4e968190d28c300e613b4fe660407a481f85a567a74139c2b6
|
|
4
|
+
data.tar.gz: b867a6b6d82c1069b0c3a5892a4020a17594d1711094d2880fc3b4e268a37461
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: f94c33853d5c3bd8c145659cee3248f36d874d5abb36b483c0d4a3b760edf8ac387a174e3624e055fe93db18fd41bb91beb7a2ba160c9959add8fcc4165daa20
|
|
7
|
+
data.tar.gz: e87f11308160e5b2ab3c7effc25dbb5958ba537f79521c3e1d8cd16ff30f95ba02f4db6e06c90fbc1eb0c4c6afd6d75be6f5f31c4e7561462bc09ff9c4d17107
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
version: 2
|
|
2
|
+
updates:
|
|
3
|
+
- package-ecosystem: "cargo"
|
|
4
|
+
directory: "/"
|
|
5
|
+
schedule:
|
|
6
|
+
interval: "daily"
|
|
7
|
+
cooldown:
|
|
8
|
+
default-days: 3
|
|
9
|
+
groups:
|
|
10
|
+
semver-compatible:
|
|
11
|
+
applies-to: version-updates
|
|
12
|
+
update-types:
|
|
13
|
+
- "minor"
|
|
14
|
+
- "patch"
|
|
15
|
+
- package-ecosystem: "bundler"
|
|
16
|
+
directory: "/"
|
|
17
|
+
schedule:
|
|
18
|
+
interval: "daily"
|
|
19
|
+
cooldown:
|
|
20
|
+
default-days: 3
|
|
21
|
+
groups:
|
|
22
|
+
semver-compatible:
|
|
23
|
+
applies-to: version-updates
|
|
24
|
+
update-types:
|
|
25
|
+
- "minor"
|
|
26
|
+
- "patch"
|
|
27
|
+
- package-ecosystem: "github-actions"
|
|
28
|
+
directory: "/"
|
|
29
|
+
schedule:
|
|
30
|
+
interval: "daily"
|
|
31
|
+
cooldown:
|
|
32
|
+
default-days: 3
|
|
33
|
+
groups:
|
|
34
|
+
default:
|
|
35
|
+
patterns:
|
|
36
|
+
- "*"
|
|
@@ -0,0 +1,94 @@
|
|
|
1
|
+
name: CI
|
|
2
|
+
|
|
3
|
+
on: push
|
|
4
|
+
|
|
5
|
+
jobs:
|
|
6
|
+
rustfmt:
|
|
7
|
+
runs-on: ubuntu-latest
|
|
8
|
+
steps:
|
|
9
|
+
- uses: actions/checkout@v6
|
|
10
|
+
|
|
11
|
+
- uses: dtolnay/rust-toolchain@stable
|
|
12
|
+
|
|
13
|
+
- run: cargo fmt --all --check
|
|
14
|
+
|
|
15
|
+
clippy:
|
|
16
|
+
runs-on: ubuntu-latest
|
|
17
|
+
steps:
|
|
18
|
+
- uses: actions/checkout@v6
|
|
19
|
+
|
|
20
|
+
- uses: dtolnay/rust-toolchain@stable
|
|
21
|
+
with:
|
|
22
|
+
components: clippy
|
|
23
|
+
|
|
24
|
+
- uses: actions/cache@v5
|
|
25
|
+
with:
|
|
26
|
+
path: |
|
|
27
|
+
~/.cargo/bin/
|
|
28
|
+
~/.cargo/registry/index/
|
|
29
|
+
~/.cargo/registry/cache/
|
|
30
|
+
~/.cargo/git/db/
|
|
31
|
+
key: ${{ runner.os }}-cargo-${{ hashFiles('Cargo.lock') }}
|
|
32
|
+
restore-keys: ${{ github.ref_name != github.event.repository.default_branch && format('{0}-cargo-', runner.os) }}
|
|
33
|
+
|
|
34
|
+
- uses: actions/cache@v5
|
|
35
|
+
with:
|
|
36
|
+
path: target
|
|
37
|
+
key: ${{ runner.os }}-cargo-clippy-${{ hashFiles('Cargo.lock') }}
|
|
38
|
+
restore-keys: ${{ github.ref_name != github.event.repository.default_branch && format('{0}-cargo-clippy-', runner.os) }}
|
|
39
|
+
|
|
40
|
+
- run: cargo fetch --locked
|
|
41
|
+
|
|
42
|
+
- run: cargo clippy --tests -- -D warnings
|
|
43
|
+
|
|
44
|
+
test:
|
|
45
|
+
runs-on: ubuntu-latest
|
|
46
|
+
steps:
|
|
47
|
+
- uses: actions/checkout@v6
|
|
48
|
+
|
|
49
|
+
- uses: dtolnay/rust-toolchain@stable
|
|
50
|
+
|
|
51
|
+
- uses: actions/cache@v5
|
|
52
|
+
with:
|
|
53
|
+
path: |
|
|
54
|
+
~/.cargo/bin/
|
|
55
|
+
~/.cargo/registry/index/
|
|
56
|
+
~/.cargo/registry/cache/
|
|
57
|
+
~/.cargo/git/db/
|
|
58
|
+
key: ${{ runner.os }}-cargo-${{ hashFiles('Cargo.lock') }}
|
|
59
|
+
restore-keys: ${{ github.ref_name != github.event.repository.default_branch && format('{0}-cargo-', runner.os) }}
|
|
60
|
+
|
|
61
|
+
- uses: actions/cache@v5
|
|
62
|
+
with:
|
|
63
|
+
path: target
|
|
64
|
+
key: ${{ runner.os }}-cargo-test-${{ hashFiles('Cargo.lock') }}
|
|
65
|
+
restore-keys: ${{ github.ref_name != github.event.repository.default_branch && format('{0}-cargo-test-', runner.os) }}
|
|
66
|
+
|
|
67
|
+
- run: cargo fetch --locked
|
|
68
|
+
|
|
69
|
+
- run: cargo test --locked
|
|
70
|
+
|
|
71
|
+
taplo:
|
|
72
|
+
runs-on: ubuntu-latest
|
|
73
|
+
steps:
|
|
74
|
+
- uses: actions/checkout@v6
|
|
75
|
+
|
|
76
|
+
- id: latest-taplo-version
|
|
77
|
+
run: |
|
|
78
|
+
V=$(curl https://index.crates.io/ta/pl/taplo-cli | jq -r 'select(.yanked == false) | .vers' | grep --extended-regexp '^[0-9]+\.[0-9]+\.[0-9]+$' | sort --reverse --version-sort | head --lines=1)
|
|
79
|
+
echo "Latest version of taplo-cli: $V"
|
|
80
|
+
echo "version=$V" >> $GITHUB_OUTPUT
|
|
81
|
+
|
|
82
|
+
- id: taplo-bin-cache
|
|
83
|
+
uses: actions/cache@v5
|
|
84
|
+
with:
|
|
85
|
+
path: ~/.cargo/bin/taplo
|
|
86
|
+
key: ${{ runner.os }}-taplo-cli-${{ steps.latest-taplo-version.outputs.version }}
|
|
87
|
+
|
|
88
|
+
- if: steps.taplo-bin-cache.outputs.cache-hit != 'true'
|
|
89
|
+
uses: dtolnay/rust-toolchain@stable
|
|
90
|
+
|
|
91
|
+
- if: steps.taplo-bin-cache.outputs.cache-hit != 'true'
|
|
92
|
+
run: cargo install taplo-cli@${{ steps.latest-taplo-version.outputs.version }} --locked
|
|
93
|
+
|
|
94
|
+
- run: ~/.cargo/bin/taplo fmt --check
|
|
@@ -12,7 +12,7 @@ jobs:
|
|
|
12
12
|
os: [ ubuntu-latest, macos-latest, windows-latest ]
|
|
13
13
|
|
|
14
14
|
steps:
|
|
15
|
-
- uses: actions/checkout@
|
|
15
|
+
- uses: actions/checkout@v6
|
|
16
16
|
|
|
17
17
|
- name: Set up Ruby
|
|
18
18
|
uses: ruby/setup-ruby@v1
|
|
@@ -46,7 +46,7 @@ jobs:
|
|
|
46
46
|
mv rrtrace-${{ steps.get_version.outputs.version }}.gem pkg/
|
|
47
47
|
|
|
48
48
|
- name: Upload artifacts
|
|
49
|
-
uses: actions/upload-artifact@
|
|
49
|
+
uses: actions/upload-artifact@v7
|
|
50
50
|
with:
|
|
51
51
|
name: gems-${{ matrix.os }}
|
|
52
52
|
path: pkg/*.gem
|
|
@@ -60,7 +60,7 @@ jobs:
|
|
|
60
60
|
id-token: write
|
|
61
61
|
contents: write
|
|
62
62
|
steps:
|
|
63
|
-
- uses: actions/checkout@
|
|
63
|
+
- uses: actions/checkout@v6
|
|
64
64
|
|
|
65
65
|
- name: Set up Ruby
|
|
66
66
|
uses: ruby/setup-ruby@v1
|
|
@@ -69,7 +69,7 @@ jobs:
|
|
|
69
69
|
bundler-cache: true
|
|
70
70
|
|
|
71
71
|
- name: Download artifacts
|
|
72
|
-
uses: actions/download-artifact@
|
|
72
|
+
uses: actions/download-artifact@v8
|
|
73
73
|
with:
|
|
74
74
|
path: pkg
|
|
75
75
|
merge-multiple: true
|
data/Cargo.lock
CHANGED
|
@@ -100,6 +100,16 @@ dependencies = [
|
|
|
100
100
|
"libloading",
|
|
101
101
|
]
|
|
102
102
|
|
|
103
|
+
[[package]]
|
|
104
|
+
name = "atomic-wait"
|
|
105
|
+
version = "1.1.0"
|
|
106
|
+
source = "registry+https://github.com/rust-lang/crates.io-index"
|
|
107
|
+
checksum = "a55b94919229f2c42292fd71ffa4b75e83193bffdd77b1e858cd55fd2d0b0ea8"
|
|
108
|
+
dependencies = [
|
|
109
|
+
"libc",
|
|
110
|
+
"windows-sys 0.42.0",
|
|
111
|
+
]
|
|
112
|
+
|
|
103
113
|
[[package]]
|
|
104
114
|
name = "atomic-waker"
|
|
105
115
|
version = "1.1.2"
|
|
@@ -333,25 +343,6 @@ dependencies = [
|
|
|
333
343
|
"libc",
|
|
334
344
|
]
|
|
335
345
|
|
|
336
|
-
[[package]]
|
|
337
|
-
name = "crossbeam-deque"
|
|
338
|
-
version = "0.8.6"
|
|
339
|
-
source = "registry+https://github.com/rust-lang/crates.io-index"
|
|
340
|
-
checksum = "9dd111b7b7f7d55b72c0a6ae361660ee5853c9af73f70c3c2ef6858b950e2e51"
|
|
341
|
-
dependencies = [
|
|
342
|
-
"crossbeam-epoch",
|
|
343
|
-
"crossbeam-utils",
|
|
344
|
-
]
|
|
345
|
-
|
|
346
|
-
[[package]]
|
|
347
|
-
name = "crossbeam-epoch"
|
|
348
|
-
version = "0.9.18"
|
|
349
|
-
source = "registry+https://github.com/rust-lang/crates.io-index"
|
|
350
|
-
checksum = "5b82ac4a3c2ca9c3460964f020e1402edd5753411d7737aa39c3714ad1b5420e"
|
|
351
|
-
dependencies = [
|
|
352
|
-
"crossbeam-utils",
|
|
353
|
-
]
|
|
354
|
-
|
|
355
346
|
[[package]]
|
|
356
347
|
name = "crossbeam-queue"
|
|
357
348
|
version = "0.3.12"
|
|
@@ -1290,16 +1281,6 @@ version = "0.6.2"
|
|
|
1290
1281
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
|
1291
1282
|
checksum = "20675572f6f24e9e76ef639bc5552774ed45f1c30e2951e1e99c59888861c539"
|
|
1292
1283
|
|
|
1293
|
-
[[package]]
|
|
1294
|
-
name = "rayon-core"
|
|
1295
|
-
version = "1.13.0"
|
|
1296
|
-
source = "registry+https://github.com/rust-lang/crates.io-index"
|
|
1297
|
-
checksum = "22e18b0f0062d30d4230b2e85ff77fdfe4326feb054b9783a3460d8435c8ab91"
|
|
1298
|
-
dependencies = [
|
|
1299
|
-
"crossbeam-deque",
|
|
1300
|
-
"crossbeam-utils",
|
|
1301
|
-
]
|
|
1302
|
-
|
|
1303
1284
|
[[package]]
|
|
1304
1285
|
name = "redox_syscall"
|
|
1305
1286
|
version = "0.4.1"
|
|
@@ -1337,12 +1318,12 @@ checksum = "19b30a45b0cd0bcca8037f3d0dc3421eaf95327a17cad11964fb8179b4fc4832"
|
|
|
1337
1318
|
name = "rrtrace"
|
|
1338
1319
|
version = "0.1.0"
|
|
1339
1320
|
dependencies = [
|
|
1321
|
+
"atomic-wait",
|
|
1340
1322
|
"bytemuck",
|
|
1341
1323
|
"crossbeam-queue",
|
|
1342
1324
|
"glam",
|
|
1343
1325
|
"libc",
|
|
1344
1326
|
"pollster",
|
|
1345
|
-
"rayon-core",
|
|
1346
1327
|
"smallvec",
|
|
1347
1328
|
"wgpu",
|
|
1348
1329
|
"windows-sys 0.61.2",
|
|
@@ -2160,6 +2141,21 @@ dependencies = [
|
|
|
2160
2141
|
"windows-link",
|
|
2161
2142
|
]
|
|
2162
2143
|
|
|
2144
|
+
[[package]]
|
|
2145
|
+
name = "windows-sys"
|
|
2146
|
+
version = "0.42.0"
|
|
2147
|
+
source = "registry+https://github.com/rust-lang/crates.io-index"
|
|
2148
|
+
checksum = "5a3e1820f08b8513f676f7ab6c1f99ff312fb97b553d30ff4dd86f9f15728aa7"
|
|
2149
|
+
dependencies = [
|
|
2150
|
+
"windows_aarch64_gnullvm 0.42.2",
|
|
2151
|
+
"windows_aarch64_msvc 0.42.2",
|
|
2152
|
+
"windows_i686_gnu 0.42.2",
|
|
2153
|
+
"windows_i686_msvc 0.42.2",
|
|
2154
|
+
"windows_x86_64_gnu 0.42.2",
|
|
2155
|
+
"windows_x86_64_gnullvm 0.42.2",
|
|
2156
|
+
"windows_x86_64_msvc 0.42.2",
|
|
2157
|
+
]
|
|
2158
|
+
|
|
2163
2159
|
[[package]]
|
|
2164
2160
|
name = "windows-sys"
|
|
2165
2161
|
version = "0.45.0"
|
data/Cargo.toml
CHANGED
|
@@ -1,17 +1,17 @@
|
|
|
1
1
|
[package]
|
|
2
|
+
edition = "2024"
|
|
2
3
|
name = "rrtrace"
|
|
3
4
|
version = "0.1.0"
|
|
4
|
-
edition = "2024"
|
|
5
5
|
|
|
6
6
|
[profile.release]
|
|
7
7
|
overflow-checks = true
|
|
8
8
|
|
|
9
9
|
[dependencies]
|
|
10
|
-
|
|
10
|
+
atomic-wait = "1.1.0"
|
|
11
|
+
bytemuck = { features = ["derive"], version = "1.24.0" }
|
|
11
12
|
crossbeam-queue = "0.3.12"
|
|
12
13
|
glam = "0.30.9"
|
|
13
14
|
pollster = "0.4.0"
|
|
14
|
-
rayon-core = "1.13.0"
|
|
15
15
|
smallvec = "1.15.1"
|
|
16
16
|
wgpu = "28.0.0"
|
|
17
17
|
winit = "0.30.12"
|
|
@@ -20,4 +20,8 @@ winit = "0.30.12"
|
|
|
20
20
|
libc = "0.2.178"
|
|
21
21
|
|
|
22
22
|
[target.'cfg(windows)'.dependencies]
|
|
23
|
-
windows-sys = {
|
|
23
|
+
windows-sys = { features = [
|
|
24
|
+
"Win32_Foundation",
|
|
25
|
+
"Win32_System_Diagnostics_Debug",
|
|
26
|
+
"Win32_System_Memory",
|
|
27
|
+
], version = "0.61.2" }
|
data/README.md
CHANGED
|
@@ -1,39 +1,100 @@
|
|
|
1
|
-
#
|
|
1
|
+
# rrtrace
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
`rrtrace` is a Ruby tracing tool with a Rust-based visualizer.
|
|
4
|
+
It records Ruby method calls, returns, GC transitions, and thread lifecycle events, then streams them to a separate GPU renderer process for real-time visualization.
|
|
4
5
|
|
|
5
|
-
|
|
6
|
+
## Features
|
|
6
7
|
|
|
7
|
-
|
|
8
|
+
- Trace Ruby `call` / `return` and C-level `c_call` / `c_return` events
|
|
9
|
+
- Capture GC enter / exit events
|
|
10
|
+
- Capture thread start / ready / suspend / resume / exit events
|
|
11
|
+
- Stream events through shared memory to a separate visualizer process
|
|
12
|
+
- Render the trace with a native Rust application built on `wgpu` and `winit`
|
|
8
13
|
|
|
9
|
-
|
|
14
|
+
## How It Works
|
|
10
15
|
|
|
11
|
-
|
|
16
|
+
`rrtrace` consists of two parts:
|
|
17
|
+
|
|
18
|
+
1. A Ruby native extension written in C
|
|
19
|
+
- Installs Ruby tracepoints and internal thread event hooks
|
|
20
|
+
- Writes trace events into a shared-memory ring buffer
|
|
21
|
+
- Launches the visualizer process
|
|
22
|
+
2. A Rust visualizer
|
|
23
|
+
- Reads events from shared memory
|
|
24
|
+
- Builds trace state in background threads
|
|
25
|
+
- Renders the result in a desktop window using the GPU
|
|
26
|
+
|
|
27
|
+
At a high level, the data flow is:
|
|
28
|
+
|
|
29
|
+
`Ruby VM` -> `C extension hooks` -> `shared-memory ring buffer` -> `Rust visualizer` -> `window`
|
|
30
|
+
|
|
31
|
+
## Usage
|
|
32
|
+
|
|
33
|
+
### CLI
|
|
34
|
+
|
|
35
|
+
Run a Ruby script under `rrtrace`:
|
|
12
36
|
|
|
13
37
|
```bash
|
|
14
|
-
|
|
38
|
+
rrtrace path/to/script.rb
|
|
15
39
|
```
|
|
16
40
|
|
|
17
|
-
|
|
41
|
+
You can also use the repository executable directly during development:
|
|
18
42
|
|
|
19
43
|
```bash
|
|
20
|
-
|
|
44
|
+
bundle exec exe/rrtrace path/to/script.rb
|
|
21
45
|
```
|
|
22
46
|
|
|
23
|
-
|
|
47
|
+
The command starts the visualizer process, opens a window, loads the target Ruby file, and stops tracing when the program exits.
|
|
48
|
+
|
|
49
|
+
### Ruby API
|
|
50
|
+
|
|
51
|
+
For manual control:
|
|
52
|
+
|
|
53
|
+
```ruby
|
|
54
|
+
require "rrtrace"
|
|
55
|
+
|
|
56
|
+
Rrtrace.start
|
|
57
|
+
|
|
58
|
+
# your Ruby code here
|
|
24
59
|
|
|
25
|
-
|
|
60
|
+
Rrtrace.stop
|
|
61
|
+
```
|
|
62
|
+
|
|
63
|
+
Available methods:
|
|
64
|
+
|
|
65
|
+
- `Rrtrace.start`
|
|
66
|
+
- `Rrtrace.stop`
|
|
67
|
+
- `Rrtrace.started?`
|
|
68
|
+
- `Rrtrace.visualizer_path`
|
|
69
|
+
|
|
70
|
+
`Rrtrace.stop` is also registered with `at_exit`, so tracing is cleaned up automatically when the process exits normally.
|
|
26
71
|
|
|
27
72
|
## Development
|
|
28
73
|
|
|
29
|
-
|
|
74
|
+
Install dependencies:
|
|
75
|
+
|
|
76
|
+
```bash
|
|
77
|
+
bin/setup
|
|
78
|
+
```
|
|
30
79
|
|
|
31
|
-
|
|
80
|
+
Build the extension and visualizer:
|
|
32
81
|
|
|
33
|
-
|
|
82
|
+
```bash
|
|
83
|
+
bundle exec rake build
|
|
84
|
+
```
|
|
85
|
+
|
|
86
|
+
Useful commands:
|
|
87
|
+
|
|
88
|
+
```bash
|
|
89
|
+
bundle exec rake compile
|
|
90
|
+
bundle exec rake standard
|
|
91
|
+
cargo test --locked
|
|
92
|
+
cargo fmt --all
|
|
93
|
+
cargo clippy --tests -- -D warnings
|
|
94
|
+
```
|
|
34
95
|
|
|
35
|
-
|
|
96
|
+
The Rust visualizer built during extension compilation is copied to `libexec/rrtrace` (or `libexec/rrtrace.exe` on Windows).
|
|
36
97
|
|
|
37
98
|
## License
|
|
38
99
|
|
|
39
|
-
|
|
100
|
+
This project is licensed under the MIT License. See [LICENSE.txt](LICENSE.txt).
|
data/exe/rrtrace
ADDED
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
#!/usr/bin/env ruby
|
|
2
|
+
# frozen_string_literal: true
|
|
3
|
+
|
|
4
|
+
require "rrtrace"
|
|
5
|
+
|
|
6
|
+
if ARGV.empty?
|
|
7
|
+
$stderr.puts "Usage: rrtrace <executable.rb> [args...]"
|
|
8
|
+
exit 1
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
executable = ARGV.shift
|
|
12
|
+
|
|
13
|
+
$0 = executable
|
|
14
|
+
Rrtrace.start
|
|
15
|
+
load executable
|
|
16
|
+
Rrtrace.stop
|
|
@@ -4,9 +4,14 @@
|
|
|
4
4
|
#include <sys/types.h>
|
|
5
5
|
#include <sys/wait.h>
|
|
6
6
|
#include <spawn.h>
|
|
7
|
+
#include <signal.h>
|
|
7
8
|
|
|
8
9
|
typedef pid_t process_id;
|
|
9
10
|
|
|
11
|
+
static inline process_id invalid_process_id(void) {
|
|
12
|
+
return 0;
|
|
13
|
+
}
|
|
14
|
+
|
|
10
15
|
extern char **environ;
|
|
11
16
|
|
|
12
17
|
static inline process_id spawn_process(const char *cmd, char * const* restrict argv) {
|
|
@@ -17,9 +22,20 @@ static inline process_id spawn_process(const char *cmd, char * const* restrict a
|
|
|
17
22
|
}
|
|
18
23
|
|
|
19
24
|
static inline int is_process_running(process_id pid) {
|
|
25
|
+
if (pid == 0) return 0;
|
|
20
26
|
int status;
|
|
21
|
-
waitpid(pid, &status, WNOHANG);
|
|
22
|
-
return
|
|
27
|
+
pid_t result = waitpid(pid, &status, WNOHANG);
|
|
28
|
+
return result == 0;
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
static inline void terminate_process(process_id pid) {
|
|
32
|
+
if (pid == 0) return;
|
|
33
|
+
kill(pid, SIGTERM);
|
|
34
|
+
waitpid(pid, NULL, 0);
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
static inline void close_process(process_id pid) {
|
|
38
|
+
(void)pid;
|
|
23
39
|
}
|
|
24
40
|
|
|
25
41
|
#endif /* PROCESS_MANAGER_POSIX_H */
|
|
@@ -6,6 +6,10 @@
|
|
|
6
6
|
|
|
7
7
|
typedef HANDLE process_id;
|
|
8
8
|
|
|
9
|
+
static inline process_id invalid_process_id(void) {
|
|
10
|
+
return NULL;
|
|
11
|
+
}
|
|
12
|
+
|
|
9
13
|
static inline process_id spawn_process(const char *cmd, char * const* argv) {
|
|
10
14
|
STARTUPINFOA si;
|
|
11
15
|
PROCESS_INFORMATION pi;
|
|
@@ -37,4 +41,14 @@ static inline int is_process_running(process_id pid) {
|
|
|
37
41
|
return 0;
|
|
38
42
|
}
|
|
39
43
|
|
|
44
|
+
static inline void terminate_process(process_id pid) {
|
|
45
|
+
if (pid == NULL) return;
|
|
46
|
+
TerminateProcess(pid, 1);
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
static inline void close_process(process_id pid) {
|
|
50
|
+
if (pid == NULL) return;
|
|
51
|
+
CloseHandle(pid);
|
|
52
|
+
}
|
|
53
|
+
|
|
40
54
|
#endif /* PROCESS_MANAGER_WIN_H */
|