Skip to content

Commit 0483f86

Browse files
authored
Merge pull request #836 from devlights/add-unix-forkjoin-example
2 parents 316b83d + 8a1b336 commit 0483f86

File tree

3 files changed

+115
-0
lines changed

3 files changed

+115
-0
lines changed
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
app
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
# https://taskfile.dev
2+
3+
version: '3'
4+
5+
vars:
6+
APP_NAME: app
7+
8+
tasks:
9+
default:
10+
cmds:
11+
- task: run
12+
build:
13+
cmds:
14+
- go build -o {{.APP_NAME}}{{.exeExt}}
15+
run:
16+
deps: [ build ]
17+
cmds:
18+
- ./{{.APP_NAME}}{{.exeExt}}
Lines changed: 96 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,96 @@
1+
//go:build linux
2+
3+
package main
4+
5+
import (
6+
"fmt"
7+
"log"
8+
"os"
9+
"time"
10+
11+
"golang.org/x/sys/unix"
12+
)
13+
14+
var (
15+
gi int
16+
)
17+
18+
func init() {
19+
log.SetFlags(0)
20+
}
21+
22+
func main() {
23+
if err := run(); err != nil {
24+
log.Fatal(err)
25+
}
26+
}
27+
28+
func run() error {
29+
os.Stdout.Sync()
30+
os.Stderr.Sync()
31+
32+
var li int
33+
34+
//
35+
// Fork
36+
//
37+
pid, _, errno := unix.RawSyscall(unix.SYS_FORK, 0, 0, 0)
38+
if errno != 0 {
39+
return fmt.Errorf("fork failed: %d", errno)
40+
}
41+
42+
var err error
43+
switch pid {
44+
case 0:
45+
err = child(pid, &li)
46+
default:
47+
err = parent(pid)
48+
}
49+
50+
if err != nil {
51+
return err
52+
}
53+
54+
log.Printf("[%5d] li = %d, gi = %d", pid, li, gi)
55+
56+
return nil
57+
}
58+
59+
func child(pid uintptr, i *int) error {
60+
log.Printf("[%5d] This is the child process.", pid)
61+
62+
for range 3 {
63+
log.Printf("[%5d] child processing...", pid)
64+
*i++
65+
gi++
66+
time.Sleep(time.Second)
67+
}
68+
69+
return nil
70+
}
71+
72+
func parent(pid uintptr) error {
73+
log.Printf("[%5d] This is the parent process.", pid)
74+
75+
//
76+
// Join
77+
//
78+
log.Printf("[%5d] parent process WAIT started.", pid)
79+
defer log.Printf("[%5d] parent process WAIT done.", pid)
80+
81+
var status unix.WaitStatus
82+
if _, err := unix.Wait4(int(pid), &status, 0, nil); err != nil {
83+
return fmt.Errorf("wait() failed: %w", err)
84+
}
85+
86+
//
87+
// WIFEXITED(status) と等価
88+
//
89+
if status.Exited() {
90+
log.Printf("[%5d] Child process exited with status: %d", pid, status.ExitStatus())
91+
} else {
92+
log.Printf("[%5d] Child process did not exit normally: %d", pid, status.ExitStatus())
93+
}
94+
95+
return nil
96+
}

0 commit comments

Comments
 (0)