fortify/parse: accept config stream fd
All checks were successful
Tests / Go tests (push) Successful in 36s
Nix / NixOS tests (push) Successful in 3m29s

Signed-off-by: Ophestra <cat@gensokyo.uk>
This commit is contained in:
Ophestra 2024-12-23 20:09:07 +09:00
parent 70bffeaa1e
commit 9fc82d67b7
Signed by: cat
SSH Key Fingerprint: SHA256:gQ67O0enBZ7UdZypgtspB2FDM1g3GVw8nX0XSdcFw8Q

View File

@ -2,9 +2,12 @@ package main
import ( import (
"encoding/json" "encoding/json"
"errors"
"io" "io"
direct "os" direct "os"
"strconv"
"strings" "strings"
"syscall"
"git.gensokyo.uk/security/fortify/fst" "git.gensokyo.uk/security/fortify/fst"
"git.gensokyo.uk/security/fortify/internal/fmsg" "git.gensokyo.uk/security/fortify/internal/fmsg"
@ -16,12 +19,23 @@ func tryPath(name string) (config *fst.Config) {
config = new(fst.Config) config = new(fst.Config)
if name != "-" { if name != "-" {
if f, err := os.Open(name); err != nil { r = tryFd(name)
fmsg.Fatalf("cannot access configuration file %q: %s", name, err) if r == nil {
panic("unreachable") fmsg.VPrintln("load configuration from file")
if f, err := os.Open(name); err != nil {
fmsg.Fatalf("cannot access configuration file %q: %s", name, err)
panic("unreachable")
} else {
// finalizer closes f
r = f
}
} else { } else {
// finalizer closes f defer func() {
r = f if err := r.(io.ReadCloser).Close(); err != nil {
fmsg.Printf("cannot close config fd: %v", err)
}
}()
} }
} else { } else {
r = direct.Stdin r = direct.Stdin
@ -35,6 +49,22 @@ func tryPath(name string) (config *fst.Config) {
return return
} }
func tryFd(name string) io.ReadCloser {
if v, err := strconv.Atoi(name); err != nil {
fmsg.VPrintf("name cannot be interpreted as int64: %v", err)
return nil
} else {
fd := uintptr(v)
if _, _, errno := syscall.Syscall(syscall.SYS_FCNTL, fd, syscall.F_GETFD, 0); errno != 0 {
if errors.Is(errno, syscall.EBADF) {
return nil
}
fmsg.Fatalf("cannot get fd %d: %v", fd, errno)
}
return direct.NewFile(fd, strconv.Itoa(v))
}
}
func tryShort(name string) (config *fst.Config, instance *state.State) { func tryShort(name string) (config *fst.Config, instance *state.State) {
likePrefix := false likePrefix := false
if len(name) <= 32 { if len(name) <= 32 {