11package sandbox
22
33import (
4+ "context"
45 "fmt"
56 "sync"
67
@@ -13,21 +14,22 @@ type Manager struct {
1314 sandboxes map [string ]* Sandbox
1415 allocatedRanges map [string ]int
1516
16- allocator * allocator.Allocator
17+ allocator * allocator.Allocator
18+ maxConcurrency int
1719
18- mu sync.Mutex
20+ mu sync.Mutex
21+ sem chan struct {}
1922}
2023
21- func NewManager () error {
22- alloc , err := allocator .NewAllocator ()
23- if err != nil {
24- return err
25- }
24+ func NewManager (maxConcurrency int ) error {
25+ alloc := allocator .NewAllocator ()
2626
2727 m = & Manager {
2828 sandboxes : make (map [string ]* Sandbox ),
2929 allocatedRanges : make (map [string ]int ),
3030 allocator : alloc ,
31+ maxConcurrency : maxConcurrency ,
32+ sem : make (chan struct {}, maxConcurrency ),
3133 }
3234 return nil
3335}
@@ -36,17 +38,17 @@ func GetManager() *Manager {
3638 return m
3739}
3840
39- func (m * Manager ) NewSandbox (id string , cfg * Config ) ( * Sandbox , error ) {
41+ func (m * Manager ) NewSandbox (id string , cfg * Config ) error {
4042 m .mu .Lock ()
4143 defer m .mu .Unlock ()
4244
4345 if _ , exists := m .sandboxes [id ]; exists {
44- return nil , fmt .Errorf ("sandbox with id %q already exists" , id )
46+ return fmt .Errorf ("sandbox with id %q already exists" , id )
4547 }
4648
4749 idx , rng := m .allocator .Allocate ()
4850 if idx == - 1 {
49- return nil , fmt .Errorf ("no available uid/gid ranges" )
51+ return fmt .Errorf ("no available uid/gid ranges" )
5052 }
5153
5254 cfg .UserNamespace = & UserNamespaceConfig {
@@ -66,7 +68,27 @@ func (m *Manager) NewSandbox(id string, cfg *Config) (*Sandbox, error) {
6668 m .sandboxes [id ] = sandbox
6769 m .allocatedRanges [id ] = idx
6870
69- return sandbox , nil
71+ return nil
72+ }
73+
74+ func (m * Manager ) RunSandbox (ctx context.Context , id string ) (Report , error ) {
75+ m .sem <- struct {}{}
76+ defer func () { <- m .sem }()
77+
78+ m .mu .Lock ()
79+ sandbox , exists := m .sandboxes [id ]
80+ m .mu .Unlock ()
81+
82+ if ! exists {
83+ return Report {}, fmt .Errorf ("sandbox with id %q does not exist" , id )
84+ }
85+
86+ report , err := sandbox .Run (ctx )
87+ if err != nil {
88+ return Report {}, fmt .Errorf ("error running sandbox %q: %w" , id , err )
89+ }
90+
91+ return report , nil
7092}
7193
7294func (m * Manager ) DestroySandbox (id string ) error {
0 commit comments