sys/syz-extract: switch to consolidated target info in sys package

This commit is contained in:
Dmitry Vyukov 2017-09-14 12:14:52 +02:00
parent 487aa0d537
commit 75ddf7ab90
4 changed files with 49 additions and 50 deletions

View File

@ -8,10 +8,13 @@ import (
)
type Target struct {
OS string
Arch string
PtrSize uint64
CArch []string
CFlags []string
CCompiler string
CrossCFlags []string
CCompilerPrefix string
KernelArch string
KernelHeaderArch string
KernelCrossCompile string
@ -23,7 +26,7 @@ var Targets = map[string]map[string]*Target{
PtrSize: 8,
CArch: []string{"__x86_64__"},
CFlags: []string{"-m64"},
CCompiler: "x86_64-linux-gnu-",
CCompilerPrefix: "x86_64-linux-gnu-",
KernelArch: "x86_64",
KernelHeaderArch: "x86",
},
@ -31,23 +34,23 @@ var Targets = map[string]map[string]*Target{
PtrSize: 4,
CArch: []string{"__i386__"},
CFlags: []string{"-m32"},
CCompiler: "x86_64-linux-gnu-",
CCompilerPrefix: "x86_64-linux-gnu-",
KernelArch: "i386",
KernelHeaderArch: "x86",
},
"arm64": {
PtrSize: 8,
CArch: []string{"__aarch64__"},
CFlags: []string{},
CCompiler: "aarch64-linux-gnu-",
CCompilerPrefix: "aarch64-linux-gnu-",
KernelArch: "arm64",
KernelHeaderArch: "arm64",
},
"arm": {
PtrSize: 4,
CArch: []string{"__arm__"},
CFlags: []string{"-D__LINUX_ARM_ARCH__=6", "-march=armv6t2", "-m32"},
CCompiler: "arm-linux-gnueabihf-",
CFlags: []string{"-D__LINUX_ARM_ARCH__=6", "-m32"},
CrossCFlags: []string{"-march=armv6t2"},
CCompilerPrefix: "arm-linux-gnueabihf-",
KernelArch: "arm",
KernelHeaderArch: "arm",
},
@ -55,9 +58,18 @@ var Targets = map[string]map[string]*Target{
PtrSize: 8,
CArch: []string{"__ppc64__", "__PPC64__", "__powerpc64__"},
CFlags: []string{"-D__powerpc64__"},
CCompiler: "powerpc64le-linux-gnu-",
CCompilerPrefix: "powerpc64le-linux-gnu-",
KernelArch: "powerpc",
KernelHeaderArch: "powerpc",
},
},
}
func init() {
for OS, archs := range Targets {
for arch, target := range archs {
target.OS = OS
target.Arch = arch
}
}
}

View File

@ -17,6 +17,7 @@ import (
"github.com/google/syzkaller/pkg/ast"
"github.com/google/syzkaller/pkg/compiler"
"github.com/google/syzkaller/pkg/osutil"
"github.com/google/syzkaller/sys"
)
var (
@ -25,20 +26,6 @@ var (
flagArch = flag.String("arch", "", "arch to generate")
)
type Arch struct {
CARCH []string
KernelHeaderArch string
CFlags []string
}
var archs = map[string]*Arch{
"amd64": {[]string{"__x86_64__"}, "x86", []string{"-m64"}},
"386": {[]string{"__i386__"}, "x86", []string{"-m32"}},
"arm64": {[]string{"__aarch64__"}, "arm64", []string{}},
"arm": {[]string{"__arm__"}, "arm", []string{"-D__LINUX_ARM_ARCH__=6", "-m32"}},
"ppc64le": {[]string{"__ppc64__", "__PPC64__", "__powerpc64__"}, "powerpc", []string{"-D__powerpc64__"}},
}
type File struct {
name string
undeclared map[string]bool
@ -61,7 +48,8 @@ func main() {
if *flagArch == "" {
failf("-arch flag is required")
}
if archs[*flagArch] == nil {
target := sys.Targets["linux"][*flagArch]
if target == nil {
failf("unknown arch %v", *flagArch)
}
n := len(flag.Args())
@ -84,7 +72,7 @@ func main() {
go func() {
defer wg.Done()
for f := range inc {
f.undeclared, f.err = processFile(f.name)
f.undeclared, f.err = processFile(target, f.name)
}
}()
}
@ -100,8 +88,8 @@ func main() {
}
}
func processFile(inname string) (map[string]bool, error) {
outname := strings.TrimSuffix(inname, ".txt") + "_" + *flagArch + ".const"
func processFile(target *sys.Target, inname string) (map[string]bool, error) {
outname := strings.TrimSuffix(inname, ".txt") + "_" + target.Arch + ".const"
indata, err := ioutil.ReadFile(inname)
if err != nil {
return nil, fmt.Errorf("failed to read input file: %v", err)
@ -121,10 +109,8 @@ func processFile(inname string) (map[string]bool, error) {
if len(info.Consts) == 0 {
return nil, nil
}
arch := archs[*flagArch]
includes := append(info.Includes, "asm/unistd.h")
consts, undeclared, err := fetchValues(arch.KernelHeaderArch, info.Consts,
includes, info.Incdirs, arch.CFlags, info.Defines)
consts, undeclared, err := fetchValues(target, info.Consts, includes, info.Incdirs, info.Defines)
if err != nil {
return nil, err
}

View File

@ -11,14 +11,16 @@ import (
"regexp"
"strconv"
"strings"
"github.com/google/syzkaller/sys"
)
// fetchValues converts literal constants (e.g. O_APPEND) or any other C expressions
// into their respective numeric values. It does so by builting and executing a C program
// that prints values of the provided expressions.
func fetchValues(arch string, vals, includes, incdirs, cflags []string,
func fetchValues(target *sys.Target, vals, includes, incdirs []string,
defines map[string]string) (map[string]uint64, map[string]bool, error) {
bin, out, err := runCompiler(arch, nil, includes, incdirs, cflags, nil, nil)
bin, out, err := runCompiler(target, nil, includes, incdirs, nil, nil)
if err != nil {
return nil, nil, fmt.Errorf("failed to run gcc: %v\n%v", err, string(out))
}
@ -30,7 +32,7 @@ func fetchValues(arch string, vals, includes, incdirs, cflags []string,
}
undeclared := make(map[string]bool)
bin, out, err = runCompiler(arch, vals, includes, incdirs, cflags, defines, undeclared)
bin, out, err = runCompiler(target, vals, includes, incdirs, defines, undeclared)
if err != nil {
for _, errMsg := range []string{
"error: ([a-zA-Z0-9_]+) undeclared",
@ -45,7 +47,7 @@ func fetchValues(arch string, vals, includes, incdirs, cflags []string,
}
}
}
bin, out, err = runCompiler(arch, vals, includes, incdirs, cflags, defines, undeclared)
bin, out, err = runCompiler(target, vals, includes, incdirs, defines, undeclared)
if err != nil {
return nil, nil, fmt.Errorf("failed to run gcc: %v\n%v", err, string(out))
}
@ -84,7 +86,7 @@ func fetchValues(arch string, vals, includes, incdirs, cflags []string,
return res, undeclared, nil
}
func runCompiler(arch string, vals, includes, incdirs, cflags []string, defines map[string]string, undeclared map[string]bool) (bin string, out []byte, err error) {
func runCompiler(target *sys.Target, vals, includes, incdirs []string, defines map[string]string, undeclared map[string]bool) (bin string, out []byte, err error) {
includeText := ""
for _, inc := range includes {
includeText += fmt.Sprintf("#include <%v>\n", inc)
@ -112,8 +114,9 @@ func runCompiler(arch string, vals, includes, incdirs, cflags []string, defines
}
binFile.Close()
arch := target.KernelHeaderArch
args := []string{"-x", "c", "-", "-o", binFile.Name(), "-fmessage-length=0"}
args = append(args, cflags...)
args = append(args, target.CFlags...)
args = append(args, []string{
// This would be useful to ensure that we don't include any host headers,
// but kernel includes at least <stdarg.h>

View File

@ -41,7 +41,6 @@ func main() {
}
type Job struct {
Arch string
Target *sys.Target
OK bool
Errors []string
@ -49,14 +48,13 @@ func main() {
ArchData []byte
}
var jobs []*Job
for arch, target := range archs {
for _, target := range archs {
jobs = append(jobs, &Job{
Arch: arch,
Target: target,
})
}
sort.Slice(jobs, func(i, j int) bool {
return jobs[i].Arch < jobs[j].Arch
return jobs[i].Target.Arch < jobs[j].Target.Arch
})
var wg sync.WaitGroup
wg.Add(len(jobs))
@ -68,7 +66,7 @@ func main() {
eh := func(pos ast.Pos, msg string) {
job.Errors = append(job.Errors, fmt.Sprintf("%v: %v\n", pos, msg))
}
consts := compiler.DeserializeConstsGlob(filepath.Join("sys", OS, "*_"+job.Arch+"\\.const"), eh)
consts := compiler.DeserializeConstsGlob(filepath.Join("sys", OS, "*_"+job.Target.Arch+"\\.const"), eh)
if consts == nil {
return
}
@ -78,9 +76,9 @@ func main() {
}
job.Unsupported = prog.Unsupported
sysFile := filepath.Join("sys", OS, job.Arch+".go")
sysFile := filepath.Join("sys", OS, job.Target.Arch+".go")
out := new(bytes.Buffer)
generate(OS, job.Arch, job.Target, prog, consts, out)
generate(job.Target, prog, consts, out)
writeSource(sysFile, out.Bytes())
job.ArchData = generateExecutorSyscalls(job.Target, prog.Syscalls)
@ -92,7 +90,7 @@ func main() {
var syscallArchs [][]byte
unsupported := make(map[string]int)
for _, job := range jobs {
fmt.Printf("generating %v/%v...\n", OS, job.Arch)
fmt.Printf("generating %v/%v...\n", job.Target.OS, job.Target.Arch)
for _, msg := range job.Errors {
fmt.Print(msg)
}
@ -128,25 +126,25 @@ func main() {
}
}
func generate(OS, arch string, target *sys.Target, prg *compiler.Prog, consts map[string]uint64, out io.Writer) {
func generate(target *sys.Target, prg *compiler.Prog, consts map[string]uint64, out io.Writer) {
fmt.Fprintf(out, "// AUTOGENERATED FILE\n")
fmt.Fprintf(out, "package %v\n\n", OS)
fmt.Fprintf(out, "package %v\n\n", target.OS)
fmt.Fprintf(out, "import . \"github.com/google/syzkaller/prog\"\n\n")
fmt.Fprintf(out, "func init() {\n")
fmt.Fprintf(out, "\tinitArch(syscalls_%v, resources_%v, structDescs_%v, consts_%v, %q, %v)\n",
arch, arch, arch, arch, arch, target.PtrSize)
target.Arch, target.Arch, target.Arch, target.Arch, target.Arch, target.PtrSize)
fmt.Fprintf(out, "}\n\n")
fmt.Fprintf(out, "var resources_%v = ", arch)
fmt.Fprintf(out, "var resources_%v = ", target.Arch)
serializer.Write(out, prg.Resources)
fmt.Fprintf(out, "\n\n")
fmt.Fprintf(out, "var structDescs_%v = ", arch)
fmt.Fprintf(out, "var structDescs_%v = ", target.Arch)
serializer.Write(out, prg.StructDescs)
fmt.Fprintf(out, "\n\n")
fmt.Fprintf(out, "var syscalls_%v = ", arch)
fmt.Fprintf(out, "var syscalls_%v = ", target.Arch)
serializer.Write(out, prg.Syscalls)
fmt.Fprintf(out, "\n\n")
@ -157,7 +155,7 @@ func generate(OS, arch string, target *sys.Target, prg *compiler.Prog, consts ma
sort.Slice(constArr, func(i, j int) bool {
return constArr[i].Name < constArr[j].Name
})
fmt.Fprintf(out, "var consts_%v = ", arch)
fmt.Fprintf(out, "var consts_%v = ", target.Arch)
serializer.Write(out, constArr)
fmt.Fprintf(out, "\n")
}