util: add syspolicy package (#9550)

Add a more generalized package for getting policies.
Updates tailcale/corp#10967

Signed-off-by: Claire Wang <claire@tailscale.com>
Co-authored-by: Adrian Dewhurst <adrian@tailscale.com>
This commit is contained in:
Claire Wang
2023-09-29 13:40:35 -04:00
committed by GitHub
parent d71184d674
commit 32c0156311
6 changed files with 685 additions and 0 deletions

52
util/syspolicy/handler.go Normal file
View File

@@ -0,0 +1,52 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
package syspolicy
import (
"errors"
"sync/atomic"
)
var (
handlerUsed atomic.Bool
handler Handler = defaultHandler{}
)
// Handler reads system policies from OS-specific storage.
type Handler interface {
// ReadString reads the policy settings value string given the key.
ReadString(key string) (string, error)
// ReadUInt64 reads the policy settings uint64 value given the key.
ReadUInt64(key string) (uint64, error)
}
// ErrNoSuchKey is returned when the specified key does not have a value set.
var ErrNoSuchKey = errors.New("no such key")
// defaultHandler is the catch all syspolicy type for anything that isn't windows or apple.
type defaultHandler struct{}
func (defaultHandler) ReadString(_ string) (string, error) {
return "", ErrNoSuchKey
}
func (defaultHandler) ReadUInt64(_ string) (uint64, error) {
return 0, ErrNoSuchKey
}
// markHandlerInUse is called before handler methods are called.
func markHandlerInUse() {
handlerUsed.Store(true)
}
// RegisterHandler initializes the policy handler and ensures registration will happen once.
func RegisterHandler(h Handler) {
// Technically this assignment is not concurrency safe, but in the
// event that there was any risk of a data race, we will panic due to
// the CompareAndSwap failing.
handler = h
if !handlerUsed.CompareAndSwap(false, true) {
panic("handler was already used before registration")
}
}