aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDmitry Vyukov <dvyukov@google.com>2015-12-28 10:45:30 +0100
committerDmitry Vyukov <dvyukov@google.com>2015-12-28 10:45:30 +0100
commit7aee64145fe814abd8008cae3dbc24dcfc6b4e8b (patch)
tree5671d8bd7e762e795020667e4f39744af92f3e98
parent4d3db6d4c86f0b3162a39dbef1d1fc8031062b10 (diff)
host: detect more unsupported syscalls
-rw-r--r--host/host.go51
1 files changed, 42 insertions, 9 deletions
diff --git a/host/host.go b/host/host.go
index e98e0e38f..c49a6a725 100644
--- a/host/host.go
+++ b/host/host.go
@@ -30,12 +30,8 @@ func DetectSupportedSyscalls() (map[*sys.Call]bool, error) {
return nil, err
}
supported := make(map[*sys.Call]bool)
- tested := make(map[string]bool)
for _, c := range sys.Calls {
- if _, ok := tested[c.CallName]; !ok {
- tested[c.CallName] = isSupported(kallsyms, c)
- }
- if tested[c.CallName] {
+ if isSupported(kallsyms, c) {
supported[c] = true
}
}
@@ -43,14 +39,22 @@ func DetectSupportedSyscalls() (map[*sys.Call]bool, error) {
}
func isSupported(kallsyms []byte, c *sys.Call) bool {
- // TODO: detect unsupported socket families.
- // TOOD: detect syscalls that open /dev/ files (e.g. open$ptmx).
if c.NR == -1 {
return false // don't even have a syscall number
}
- if !strings.HasPrefix(c.CallName, "syz_") {
- return bytes.Index(kallsyms, []byte(" T sys_"+c.CallName+"\n")) != -1
+ if strings.HasPrefix(c.CallName, "syz_") {
+ return isSupportedSyzkall(kallsyms, c)
+ }
+ if strings.HasPrefix(c.Name, "socket$") {
+ return isSupportedSocket(kallsyms, c)
}
+ if strings.HasPrefix(c.Name, "open$") {
+ return isSupportedOpen(kallsyms, c)
+ }
+ return bytes.Index(kallsyms, []byte(" T sys_"+c.CallName+"\n")) != -1
+}
+
+func isSupportedSyzkall(kallsyms []byte, c *sys.Call) bool {
switch c.CallName {
case "syz_openpts":
return true
@@ -67,3 +71,32 @@ func isSupported(kallsyms []byte, c *sys.Call) bool {
panic("unknown syzkall")
}
}
+
+func isSupportedSocket(kallsyms []byte, c *sys.Call) bool {
+ af, ok := c.Args[0].(sys.ConstType)
+ if !ok {
+ println(c.Name)
+ panic("socket family is not const")
+ }
+ fd, err := syscall.Socket(int(af.Val), 0, 0)
+ if fd != -1 {
+ syscall.Close(fd)
+ }
+ return err != syscall.ENOSYS && err != syscall.EAFNOSUPPORT
+}
+
+func isSupportedOpen(kallsyms []byte, c *sys.Call) bool {
+ ptr, ok := c.Args[0].(sys.PtrType)
+ if !ok {
+ panic("first open arg is not a pointer")
+ }
+ fname, ok := ptr.Type.(sys.StrConstType)
+ if !ok {
+ return true
+ }
+ fd, err := syscall.Open(fname.Val, syscall.O_RDONLY, 0)
+ if fd != -1 {
+ syscall.Close(fd)
+ }
+ return err == nil
+}