MacOS sandbox_init

This commit is contained in:
criyle 2020-05-13 20:43:58 -04:00
parent b64cc09c06
commit 3fd00038db
7 changed files with 140 additions and 3 deletions

2
go.mod
View File

@ -4,5 +4,5 @@ go 1.14
require (
github.com/seccomp/libseccomp-golang v0.9.1
golang.org/x/sys v0.0.0-20200509044756-6aff5f38e54f
golang.org/x/sys v0.0.0-20200513112337-417ce2331b5c
)

4
go.sum
View File

@ -1,4 +1,4 @@
github.com/seccomp/libseccomp-golang v0.9.1 h1:NJjM5DNFOs0s3kYE1WUOr6G8V97sdt46rlXTMfXGWBo=
github.com/seccomp/libseccomp-golang v0.9.1/go.mod h1:GbW5+tmTXfcxTToHLXlScSlAvWlF4P2Ca7zGrPiEpWo=
golang.org/x/sys v0.0.0-20200509044756-6aff5f38e54f h1:mOhmO9WsBaJCNmaZHPtHs9wOcdqdKCjF6OPJlmDM3KI=
golang.org/x/sys v0.0.0-20200509044756-6aff5f38e54f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20200513112337-417ce2331b5c h1:kISX68E8gSkNYAFRFiDU8rl5RIn1sJYKYb/r2vMLDrU=
golang.org/x/sys v0.0.0-20200513112337-417ce2331b5c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=

View File

@ -0,0 +1,36 @@
package darwin
import (
"io/ioutil"
"os"
"testing"
)
func TestWrite(t *testing.T) {
c, err := ioutil.ReadFile("test.sb")
if err != nil {
t.Error(err)
return
}
// before load profile, it is ok
f, err := os.OpenFile("/tmp/sandbox_test", os.O_CREATE|os.O_RDWR, 0777)
if err != nil {
t.Error(err)
return
}
f.Close()
if err = SandboxLoadProfile(string(c)); err != nil {
t.Error(err)
return
}
// after is not ok
f, err = os.OpenFile("/tmp/sandbox_test", os.O_CREATE|os.O_RDWR, 0777)
if !os.IsPermission(err) {
t.Error(err)
return
}
f.Close()
}

View File

@ -0,0 +1,35 @@
package darwin
import (
"errors"
"os"
"syscall"
"unsafe"
)
func goString(b *byte) string {
l := 0
sb := (*[1 << 20]byte)(unsafe.Pointer(b))
for sb[l] > 0 {
l++
}
return string(sb[: l-1 : l-1])
}
// SandboxLoadProfile loads profile by sandbox_init
func SandboxLoadProfile(profile string) (err error) {
var errBuf *byte
p, err := syscall.BytePtrFromString(profile)
if err != nil {
return
}
if err := SandboxInit(p, 0, &errBuf); err != nil {
defer SandboxFreeError(errBuf)
if errBuf != nil {
s := goString(errBuf)
return os.NewSyscallError("sandbox_init", errors.New(s))
}
return os.NewSyscallError("sandbox_init", err)
}
return
}

View File

@ -0,0 +1,39 @@
package darwin
import (
"syscall"
"unsafe"
)
// SandboxInit calls sandbox_init
func SandboxInit(profile *byte, flags uint64, errorBuf **byte) (err error) {
var r1 uintptr
r1, _, err = syscall3(funcPC(libc_sandbox_init_trampoline), uintptr(unsafe.Pointer(profile)), uintptr(flags), uintptr(unsafe.Pointer(errorBuf)))
if r1 != 0 {
err = syscall.EINVAL
} else {
err = nil
}
return
}
// SandboxFreeError calls sandbox_free_error
func SandboxFreeError(errorBuf *byte) {
syscall3(funcPC(libc_sandbox_free_error_trampoline), uintptr(unsafe.Pointer(errorBuf)), 0, 0)
}
func libc_sandbox_init_trampoline()
//go:linkname libc_sandbox_init libc_sandbox_init
//go:cgo_import_dynamic libc_sandbox_init sandbox_init "/usr/lib/libSystem.B.dylib"
func libc_sandbox_free_error_trampoline()
//go:linkname libc_sandbox_free_error libc_sandbox_free_error
//go:cgo_import_dynamic libc_sandbox_free_error sandbox_free_error "/usr/lib/libSystem.B.dylib"
//go:linkname syscall3 syscall.syscall
func syscall3(fn, a1, a2, a3 uintptr) (r1, r2 uintptr, err syscall.Errno)
//go:linkname funcPC syscall.funcPC
func funcPC(f func()) uintptr

21
pkg/darwin/test.sb Normal file
View File

@ -0,0 +1,21 @@
; Test Sandbox Profile
; No network / socket
; No system / sysctl
(version 1)
(deny default)
; allow posix ipc
(allow ipc-posix*)
; allow file access /
(allow file-read* (subpath "/usr/lib"))
; allow execve
(allow process-exec)
; allow fork
(allow process-fork)
; allow signal to self
(allow signal (target self))

View File

@ -0,0 +1,6 @@
#include "textflag.h"
TEXT ·libc_sandbox_init_trampoline(SB),NOSPLIT,$0-0
JMP libc_sandbox_init(SB)
TEXT ·libc_sandbox_free_error_trampoline(SB),NOSPLIT,$0-0
JMP libc_sandbox_free_error(SB)