treewide: document linkname uses
All checks were successful
Test / Create distribution (push) Successful in 34s
Test / Sandbox (push) Successful in 2m17s
Test / Hakurei (push) Successful in 3m15s
Test / Hpkg (push) Successful in 4m6s
Test / Sandbox (race detector) (push) Successful in 4m12s
Test / Hakurei (race detector) (push) Successful in 5m2s
Test / Flake checks (push) Successful in 1m26s
All checks were successful
Test / Create distribution (push) Successful in 34s
Test / Sandbox (push) Successful in 2m17s
Test / Hakurei (push) Successful in 3m15s
Test / Hpkg (push) Successful in 4m6s
Test / Sandbox (race detector) (push) Successful in 4m12s
Test / Hakurei (race detector) (push) Successful in 5m2s
Test / Flake checks (push) Successful in 1m26s
These provide justification for each use of linkname. Poorly thought out uses of linkname are removed. Signed-off-by: Ophestra <cat@gensokyo.uk>
This commit is contained in:
parent
bf5d10743f
commit
abeb67964f
@ -11,7 +11,7 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
"sync"
|
"sync"
|
||||||
"time"
|
"time"
|
||||||
_ "unsafe"
|
_ "unsafe" // for go:linkname
|
||||||
|
|
||||||
"hakurei.app/command"
|
"hakurei.app/command"
|
||||||
"hakurei.app/container/check"
|
"hakurei.app/container/check"
|
||||||
@ -24,8 +24,11 @@ import (
|
|||||||
"hakurei.app/message"
|
"hakurei.app/message"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// optionalErrorUnwrap calls [errors.Unwrap] and returns the resulting value
|
||||||
|
// if it is not nil, or the original value if it is.
|
||||||
|
//
|
||||||
//go:linkname optionalErrorUnwrap hakurei.app/container.optionalErrorUnwrap
|
//go:linkname optionalErrorUnwrap hakurei.app/container.optionalErrorUnwrap
|
||||||
func optionalErrorUnwrap(_ error) error
|
func optionalErrorUnwrap(err error) error
|
||||||
|
|
||||||
func buildCommand(ctx context.Context, msg message.Msg, early *earlyHardeningErrs, out io.Writer) command.Command {
|
func buildCommand(ctx context.Context, msg message.Msg, early *earlyHardeningErrs, out io.Writer) command.Command {
|
||||||
var (
|
var (
|
||||||
|
|||||||
@ -1,18 +1,13 @@
|
|||||||
package main_test
|
package main
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"io"
|
|
||||||
"reflect"
|
"reflect"
|
||||||
"strings"
|
"strings"
|
||||||
"testing"
|
"testing"
|
||||||
_ "unsafe"
|
|
||||||
|
|
||||||
"hakurei.app/container/stub"
|
"hakurei.app/container/stub"
|
||||||
)
|
)
|
||||||
|
|
||||||
//go:linkname decodeJSON hakurei.app/cmd/hakurei.decodeJSON
|
|
||||||
func decodeJSON(fatal func(v ...any), op string, r io.Reader, v any)
|
|
||||||
|
|
||||||
func TestDecodeJSON(t *testing.T) {
|
func TestDecodeJSON(t *testing.T) {
|
||||||
t.Parallel()
|
t.Parallel()
|
||||||
|
|
||||||
@ -62,9 +57,6 @@ func TestDecodeJSON(t *testing.T) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
//go:linkname encodeJSON hakurei.app/cmd/hakurei.encodeJSON
|
|
||||||
func encodeJSON(fatal func(v ...any), output io.Writer, short bool, v any)
|
|
||||||
|
|
||||||
func TestEncodeJSON(t *testing.T) {
|
func TestEncodeJSON(t *testing.T) {
|
||||||
t.Parallel()
|
t.Parallel()
|
||||||
|
|
||||||
@ -74,7 +66,7 @@ func TestEncodeJSON(t *testing.T) {
|
|||||||
want string
|
want string
|
||||||
}{
|
}{
|
||||||
{"marshaler", errorJSONMarshaler{},
|
{"marshaler", errorJSONMarshaler{},
|
||||||
`cannot encode json for main_test.errorJSONMarshaler: unique error 3735928559 injected by the test suite`},
|
`cannot encode json for main.errorJSONMarshaler: unique error 3735928559 injected by the test suite`},
|
||||||
{"default", func() {},
|
{"default", func() {},
|
||||||
`cannot write json: json: unsupported type: func()`},
|
`cannot write json: json: unsupported type: func()`},
|
||||||
}
|
}
|
||||||
|
|||||||
@ -14,8 +14,10 @@ import (
|
|||||||
. "hakurei.app/container/check"
|
. "hakurei.app/container/check"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// unsafeAbs returns check.Absolute on any string value.
|
||||||
|
//
|
||||||
//go:linkname unsafeAbs hakurei.app/container/check.unsafeAbs
|
//go:linkname unsafeAbs hakurei.app/container/check.unsafeAbs
|
||||||
func unsafeAbs(_ string) *Absolute
|
func unsafeAbs(pathname string) *Absolute
|
||||||
|
|
||||||
func TestAbsoluteError(t *testing.T) {
|
func TestAbsoluteError(t *testing.T) {
|
||||||
t.Parallel()
|
t.Parallel()
|
||||||
|
|||||||
@ -8,8 +8,10 @@ import (
|
|||||||
|
|
||||||
/* constants in this file bypass abs check, be extremely careful when changing them! */
|
/* constants in this file bypass abs check, be extremely careful when changing them! */
|
||||||
|
|
||||||
|
// unsafeAbs returns check.Absolute on any string value.
|
||||||
|
//
|
||||||
//go:linkname unsafeAbs hakurei.app/container/check.unsafeAbs
|
//go:linkname unsafeAbs hakurei.app/container/check.unsafeAbs
|
||||||
func unsafeAbs(_ string) *check.Absolute
|
func unsafeAbs(pathname string) *check.Absolute
|
||||||
|
|
||||||
var (
|
var (
|
||||||
// AbsRoot is [Root] as [check.Absolute].
|
// AbsRoot is [Root] as [check.Absolute].
|
||||||
|
|||||||
@ -7,8 +7,10 @@ import (
|
|||||||
"hakurei.app/container/stub"
|
"hakurei.app/container/stub"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Made available here to check panic recovery behaviour.
|
||||||
|
//
|
||||||
//go:linkname handleExitNew hakurei.app/container/stub.handleExitNew
|
//go:linkname handleExitNew hakurei.app/container/stub.handleExitNew
|
||||||
func handleExitNew(_ testing.TB)
|
func handleExitNew(t testing.TB)
|
||||||
|
|
||||||
// overrideTFailNow overrides the Fail and FailNow method.
|
// overrideTFailNow overrides the Fail and FailNow method.
|
||||||
type overrideTFailNow struct {
|
type overrideTFailNow struct {
|
||||||
|
|||||||
@ -6,11 +6,13 @@ import (
|
|||||||
"reflect"
|
"reflect"
|
||||||
"testing"
|
"testing"
|
||||||
"time"
|
"time"
|
||||||
_ "unsafe"
|
_ "unsafe" // for go:linkname
|
||||||
|
|
||||||
"hakurei.app/hst"
|
"hakurei.app/hst"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Made available here to check time encoding behaviour of [hst.ID].
|
||||||
|
//
|
||||||
//go:linkname newInstanceID hakurei.app/hst.newInstanceID
|
//go:linkname newInstanceID hakurei.app/hst.newInstanceID
|
||||||
func newInstanceID(id *hst.ID, p uint64) error
|
func newInstanceID(id *hst.ID, p uint64) error
|
||||||
|
|
||||||
|
|||||||
@ -12,6 +12,8 @@ import (
|
|||||||
|
|
||||||
// IsPollDescriptor reports whether fd is the descriptor being used by the poller.
|
// IsPollDescriptor reports whether fd is the descriptor being used by the poller.
|
||||||
//
|
//
|
||||||
|
// Made available here to determine and reject impossible fd.
|
||||||
|
//
|
||||||
//go:linkname IsPollDescriptor internal/poll.IsPollDescriptor
|
//go:linkname IsPollDescriptor internal/poll.IsPollDescriptor
|
||||||
func IsPollDescriptor(fd uintptr) bool
|
func IsPollDescriptor(fd uintptr) bool
|
||||||
|
|
||||||
|
|||||||
@ -27,7 +27,7 @@ func TestEntryData(t *testing.T) {
|
|||||||
return buf.String()
|
return buf.String()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
templateStateGob := mustEncodeGob(newTemplateState())
|
templateStateGob := mustEncodeGob(NewTemplateState())
|
||||||
|
|
||||||
testCases := []struct {
|
testCases := []struct {
|
||||||
name string
|
name string
|
||||||
@ -45,11 +45,11 @@ func TestEntryData(t *testing.T) {
|
|||||||
Step: "validate configuration", Err: hst.ErrConfigNull,
|
Step: "validate configuration", Err: hst.ErrConfigNull,
|
||||||
Msg: "invalid configuration"}},
|
Msg: "invalid configuration"}},
|
||||||
|
|
||||||
{"inconsistent enablement", "\x00\xff\xca\xfe\x00\x00\xff\x00" + templateStateGob, newTemplateState(), &hst.AppError{
|
{"inconsistent enablement", "\x00\xff\xca\xfe\x00\x00\xff\x00" + templateStateGob, NewTemplateState(), &hst.AppError{
|
||||||
Step: "validate state enablement", Err: os.ErrInvalid,
|
Step: "validate state enablement", Err: os.ErrInvalid,
|
||||||
Msg: "state entry aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa has unexpected enablement byte 0xd, 0xff"}},
|
Msg: "state entry aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa has unexpected enablement byte 0xd, 0xff"}},
|
||||||
|
|
||||||
{"template", "\x00\xff\xca\xfe\x00\x00\x0d\xf2" + templateStateGob, newTemplateState(), nil},
|
{"template", "\x00\xff\xca\xfe\x00\x00\x0d\xf2" + templateStateGob, NewTemplateState(), nil},
|
||||||
}
|
}
|
||||||
for _, tc := range testCases {
|
for _, tc := range testCases {
|
||||||
t.Run(tc.name, func(t *testing.T) {
|
t.Run(tc.name, func(t *testing.T) {
|
||||||
@ -105,7 +105,7 @@ func TestEntryData(t *testing.T) {
|
|||||||
|
|
||||||
t.Run("encode fault", func(t *testing.T) {
|
t.Run("encode fault", func(t *testing.T) {
|
||||||
t.Parallel()
|
t.Parallel()
|
||||||
s := newTemplateState()
|
s := NewTemplateState()
|
||||||
|
|
||||||
t.Run("gob", func(t *testing.T) {
|
t.Run("gob", func(t *testing.T) {
|
||||||
var want = &hst.AppError{Step: "encode state body", Err: stub.UniqueError(0xcafe)}
|
var want = &hst.AppError{Step: "encode state body", Err: stub.UniqueError(0xcafe)}
|
||||||
@ -123,8 +123,8 @@ func TestEntryData(t *testing.T) {
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
// newTemplateState returns the address of a new template [hst.State] struct.
|
// NewTemplateState returns the address of a new template [hst.State] struct.
|
||||||
func newTemplateState() *hst.State {
|
func NewTemplateState() *hst.State {
|
||||||
return &hst.State{
|
return &hst.State{
|
||||||
ID: hst.ID(bytes.Repeat([]byte{0xaa}, len(hst.ID{}))),
|
ID: hst.ID(bytes.Repeat([]byte{0xaa}, len(hst.ID{}))),
|
||||||
PID: 0xcafe,
|
PID: 0xcafe,
|
||||||
|
|||||||
@ -10,7 +10,7 @@ import (
|
|||||||
"strings"
|
"strings"
|
||||||
"syscall"
|
"syscall"
|
||||||
"testing"
|
"testing"
|
||||||
_ "unsafe"
|
_ "unsafe" // for go:linkname
|
||||||
|
|
||||||
"hakurei.app/container/check"
|
"hakurei.app/container/check"
|
||||||
"hakurei.app/container/stub"
|
"hakurei.app/container/stub"
|
||||||
@ -18,18 +18,23 @@ import (
|
|||||||
"hakurei.app/internal/store"
|
"hakurei.app/internal/store"
|
||||||
)
|
)
|
||||||
|
|
||||||
//go:linkname newTemplateState hakurei.app/internal/store.newTemplateState
|
// Made available here for direct validation of state entry files.
|
||||||
func newTemplateState() *hst.State
|
//
|
||||||
|
|
||||||
//go:linkname entryDecode hakurei.app/internal/store.entryDecode
|
//go:linkname entryDecode hakurei.app/internal/store.entryDecode
|
||||||
func entryDecode(r io.Reader, p *hst.State) (hst.Enablement, error)
|
func entryDecode(r io.Reader, p *hst.State) (hst.Enablement, error)
|
||||||
|
|
||||||
|
// Made available here for direct access to known segment handles.
|
||||||
|
//
|
||||||
//go:linkname newHandle hakurei.app/internal/store.newHandle
|
//go:linkname newHandle hakurei.app/internal/store.newHandle
|
||||||
func newHandle(base *check.Absolute, identity int) *store.Handle
|
func newHandle(base *check.Absolute, identity int) *store.Handle
|
||||||
|
|
||||||
|
// Made available here to check open error handling behaviour.
|
||||||
|
//
|
||||||
//go:linkname open hakurei.app/internal/store.(*EntryHandle).open
|
//go:linkname open hakurei.app/internal/store.(*EntryHandle).open
|
||||||
func open(eh *store.EntryHandle, flag int, perm os.FileMode) (*os.File, error)
|
func open(eh *store.EntryHandle, flag int, perm os.FileMode) (*os.File, error)
|
||||||
|
|
||||||
|
// Made available here to check the saveload cycle.
|
||||||
|
//
|
||||||
//go:linkname save hakurei.app/internal/store.(*EntryHandle).save
|
//go:linkname save hakurei.app/internal/store.(*EntryHandle).save
|
||||||
func save(eh *store.EntryHandle, state *hst.State) error
|
func save(eh *store.EntryHandle, state *hst.State) error
|
||||||
|
|
||||||
@ -91,9 +96,9 @@ func TestStateEntryHandle(t *testing.T) {
|
|||||||
t.Run("saveload", func(t *testing.T) {
|
t.Run("saveload", func(t *testing.T) {
|
||||||
t.Parallel()
|
t.Parallel()
|
||||||
eh := store.EntryHandle{Pathname: check.MustAbs(t.TempDir()).Append("entry"),
|
eh := store.EntryHandle{Pathname: check.MustAbs(t.TempDir()).Append("entry"),
|
||||||
ID: newTemplateState().ID}
|
ID: store.NewTemplateState().ID}
|
||||||
|
|
||||||
if err := save(&eh, newTemplateState()); err != nil {
|
if err := save(&eh, store.NewTemplateState()); err != nil {
|
||||||
t.Fatalf("save: error = %v", err)
|
t.Fatalf("save: error = %v", err)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -112,7 +117,7 @@ func TestStateEntryHandle(t *testing.T) {
|
|||||||
t.Fatal(f.Close())
|
t.Fatal(f.Close())
|
||||||
}
|
}
|
||||||
|
|
||||||
if want := newTemplateState(); !reflect.DeepEqual(&got, want) {
|
if want := store.NewTemplateState(); !reflect.DeepEqual(&got, want) {
|
||||||
t.Errorf("entryDecode: %#v, want %#v", &got, want)
|
t.Errorf("entryDecode: %#v, want %#v", &got, want)
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
@ -122,7 +127,7 @@ func TestStateEntryHandle(t *testing.T) {
|
|||||||
|
|
||||||
if et, err := eh.Load(nil); err != nil {
|
if et, err := eh.Load(nil); err != nil {
|
||||||
t.Fatalf("load: error = %v", err)
|
t.Fatalf("load: error = %v", err)
|
||||||
} else if want := newTemplateState().Enablements.Unwrap(); et != want {
|
} else if want := store.NewTemplateState().Enablements.Unwrap(); et != want {
|
||||||
t.Errorf("load: et = %x, want %x", et, want)
|
t.Errorf("load: et = %x, want %x", et, want)
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
@ -133,7 +138,7 @@ func TestStateEntryHandle(t *testing.T) {
|
|||||||
var got hst.State
|
var got hst.State
|
||||||
if _, err := eh.Load(&got); err != nil {
|
if _, err := eh.Load(&got); err != nil {
|
||||||
t.Fatalf("load: error = %v", err)
|
t.Fatalf("load: error = %v", err)
|
||||||
} else if want := newTemplateState(); !reflect.DeepEqual(&got, want) {
|
} else if want := store.NewTemplateState(); !reflect.DeepEqual(&got, want) {
|
||||||
t.Errorf("load: %#v, want %#v", &got, want)
|
t.Errorf("load: %#v, want %#v", &got, want)
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
|||||||
@ -12,13 +12,15 @@ import (
|
|||||||
"syscall"
|
"syscall"
|
||||||
"testing"
|
"testing"
|
||||||
"time"
|
"time"
|
||||||
_ "unsafe"
|
_ "unsafe" // for go:linkname
|
||||||
|
|
||||||
"hakurei.app/container/check"
|
"hakurei.app/container/check"
|
||||||
"hakurei.app/hst"
|
"hakurei.app/hst"
|
||||||
"hakurei.app/internal/store"
|
"hakurei.app/internal/store"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Made available here to check bigLock error handling behaviour.
|
||||||
|
//
|
||||||
//go:linkname bigLock hakurei.app/internal/store.(*Store).bigLock
|
//go:linkname bigLock hakurei.app/internal/store.(*Store).bigLock
|
||||||
func bigLock(s *store.Store) (unlock func(), err error)
|
func bigLock(s *store.Store) (unlock func(), err error)
|
||||||
|
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user