summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--ChangeLog4
-rw-r--r--safety/README10
-rw-r--r--safety/data/opcodes-i686107
-rw-r--r--safety/data/opcodes-ia6489
-rw-r--r--safety/data/opcodes-x86_64104
-rw-r--r--safety/data/references94
-rwxr-xr-xsafety/safety.py245
7 files changed, 4 insertions, 649 deletions
diff --git a/ChangeLog b/ChangeLog
index 8eb41250..ad961375 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,7 @@
+2008-04-01 Frank Ch. Eigler <fche@elastic.org>
+
+ * safety/*: Removed subdirectory containing abandoned experiment.
+
2008-03-31 Frank Ch. Eigler <fche@elastic.org>
* configure.ac: Bump version to 0.7.
diff --git a/safety/README b/safety/README
deleted file mode 100644
index 61eda4a2..00000000
--- a/safety/README
+++ /dev/null
@@ -1,10 +0,0 @@
-This is a static safety-checker for SystemTap modules. It attempts to
-validate modules by checking the opcodes used and the external references
-against a whitelist.
-
-The script relies on external data files to provide the whitelists, which by
-default are in the <script-dir>/data directory. The 'references' file
-provides a plain list of allowed references. The 'opcodes' file provides a
-list of regular expressions that match allowed opcodes. Either data file may
-have an optional kernel and/or architecture suffix, as in 'opcodes-i686' or
-'references-2.6.9-32.ELsmp-x86_64'.
diff --git a/safety/data/opcodes-i686 b/safety/data/opcodes-i686
deleted file mode 100644
index 123fa2b0..00000000
--- a/safety/data/opcodes-i686
+++ /dev/null
@@ -1,107 +0,0 @@
-aaa
-aad
-aam
-aas
-adc[bwl]?
-add[bwl]?
-and[bwl]?
-bound[wl]?
-bsf[wl]?
-bsr[wl]?
-bswapl?
-btc[wl]?
-btr[wl]?
-bts[wl]?
-bt[wl]?
-call
-cbtw
-cbw
-cdq
-clc
-cld
-cli
-cltd
-cmc
-cmovn?(?:a|ae|b|be|c|e|g|ge|l|le|o|p|pe|po|s|z)[wl]?
-cmp[bwl]?
-cmps[bwl]?
-cmpxchg8b
-cmpxchg[bwl]?
-cpuid
-cwd
-cwde
-cwtd
-cwtl
-daa
-das
-dec[bwl]?
-div[bwl]?
-enter
-idiv[bwl]?
-imul[bwl]?
-inc[bwl]?
-je?cxz
-jmp
-jn?(?:a|ae|b|be|c|e|g|ge|l|le|o|p|pe|po|s|z)
-lcall
-lds[wl]?
-leave
-lea[wl]?
-les[wl]?
-lfence
-lfs[wl]?
-lgs[wl]?
-lods[bwl]?
-loopn?[ze]?
-lret
-lss[wl]?
-mfence
-movaps
-mov[bwl]?
-movs[bwl]?
-movsb[wl]?
-movswl?
-movzb[wl]?
-movzwl?
-mul[bwl]?
-neg[bwl]?
-nop
-not[bwl]?
-or[bwl]?
-pause
-popa[wl]?
-popf[wl]?
-pop[wl]?
-prefetch(?:t[012]|nta)
-pusha[wl]?
-pushf[wl]?
-push[wl]?
-rcl[bwl]?
-rcr[bwl]?
-rdmsr
-rdtsc
-ret
-rol[bwl]?
-ror[bwl]?
-sahf
-sal[bwl]?
-sar[bwl]?
-sbb[bwl]?
-scas[bwl]?
-setn?(?:a|ae|b|be|c|e|g|ge|l|le|o|p|pe|po|s|z)
-shl[bwl]?
-shld[bwl]?
-shr[bwl]?
-shrd[bwl]?
-smov[lw]?
-stc
-std
-sti
-stos[bwl]?
-sub[bwl]?
-test[bwl]?
-xadd[bwl]?
-xchg[bwl]?
-xlat
-xlatb
-xor[bwl]?
diff --git a/safety/data/opcodes-ia64 b/safety/data/opcodes-ia64
deleted file mode 100644
index edb1792e..00000000
--- a/safety/data/opcodes-ia64
+++ /dev/null
@@ -1,89 +0,0 @@
-add[sl]?
-addp4
-alloc
-and
-andcm
-br(?:\.cond)?(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-br\.cond(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-br\.call(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-br\.ret(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-br\.cloop(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-br\.ctop(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-br\.cexit(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-br\.wtop(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-br\.wexit(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-brl(?:\.cond)?(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-brl\.call(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-brp(?:\.(?:sptk|loop|exit|dptk))(?:\.imp)?
-brp\.ret(?:\.(?:sptk|loop|exit|dptk))(?:\.imp)?
-chk\.s(?:\.[im])?
-chk\.a\.(?:clr|nc)
-clrrrb
-cmp\.(?:eq|ne|l[te]u?|g[te]u?)(?:\.(?:unc|or|and|or.andcm|orcm|andcm|and.orcm))?
-cmp4\.(?:eq|ne|l[te]u?|g[te]u?)(?:\.(?:unc|or|and|or.andcm|orcm|andcm|and.orcm))?
-cmpxchg[1248]\.(?:acq|rel)(?:\.nt[1a])?
-cmp8xchg16\.(?:acq|rel)(?:\.nt[1a])?
-cover
-czx[12]\.[lr]
-dep(?:\.z)?
-extr(?:\.u)?
-fetchadd[48]\.(?:acq|rel)(?:\.nt[1a])?
-getf\.(?:s|d|exp|sig)
-hint(?:\.[ibmfx])?
-ld[1248](?:\.(?:s|a|sa|c\.nc|c\.clr|c\.clr\.acq|acq|bias))?(?:\.nt[1a])?
-ld8\.fill(?:\.nt[1a])?
-ld16(?:\.acq)?(?:\.nt[1a])?
-ldf8(?:\.(?:s|a|sa|c\.nc|c\.clr))?(?:\.nt[1a])?
-lfetch(?:.fault)?(?:\.excl)?(?:\.nt[12a])?
-mf
-mix[124]\.[lr]
-mov(?:\.[im])?
-mov(?:\.ret)?(?:\.sptk|\.dptk)?(?:\.imp)?
-movl
-mux[12]
-nop(?:\.[ibmfx])?
-or
-pack2\.[us]ss
-pack4.sss
-padd[124]
-padd[12]\.(?:sss|uus|uuu)
-pavg[12](?:\.raz)
-pavgsub[12]
-pcmp[124]\.(?:eq|gt)
-pmax1\.u
-pmax2
-pmin1\.u
-pmin2
-pmpy2\.[rl]
-pmpyshr2(?:\.u)?
-popcnt
-psad1
-pshl[24]
-pshladd2
-pshr[24](?:\.u)?
-pshradd2
-psub[124]
-psub[12]\.(?:sss|uus|uuu)
-rsm
-setf\.(?:s|d|exp|sig)
-shl
-shladd
-shladdp4
-shr(?:\.u)?
-shrp
-srlz\.[id]
-ssm
-st[1248](?:\.rel)?(?:\.nta)?
-st16(?:\.rel)?(?:\.nta)?
-st8\.spill(?:\.nta)?
-stf8(?:\.nta)?
-sub
-sxt[124]
-tbit\.n?z(?:\.(?:unc|or|and|or.andcm|orcm|andcm|and.orcm))?
-tnat\.n?z(?:\.(?:unc|or|and|or.andcm|orcm|andcm|and.orcm))?
-unpack[124]\.[hl]
-xchg[1248](?:\.nt[1a])?
-xma\.[lh]u?
-xmpy\.[lh]u?
-xor
-zxt[124]
diff --git a/safety/data/opcodes-x86_64 b/safety/data/opcodes-x86_64
deleted file mode 100644
index b89df879..00000000
--- a/safety/data/opcodes-x86_64
+++ /dev/null
@@ -1,104 +0,0 @@
-adc[bwlq]?
-add[bwlq]?
-and[bwlq]?
-boundl?
-bsf[wlq]?
-bsr[wlq]?
-bswap[lq]?
-btc[wlq]?
-btr[wlq]?
-bts[wlq]?
-bt[wlq]?
-callq?
-cbtw
-cbw
-cdq
-cdqe
-clc
-cld
-cli
-cltd
-cltq
-cmc
-cmovn?(?:a|ae|b|be|c|e|g|ge|l|le|o|p|pe|po|s|z)[wlq]?
-cmp[bwlq]?
-cmps[bwlq]?
-cmpxchg16b
-cmpxchg8b
-cmpxchg[bwlq]?
-cpuid
-cqo
-cqtd
-cqto
-cwd
-cwde
-cwtd
-cwtl
-dec[bwlq]?
-div[bwlq]?
-enterq?
-idiv[bwlq]?
-imul[bwlq]?
-inc[bwlq]?
-jcxz
-jmpq?
-jn?(?:a|ae|b|be|c|e|g|ge|l|le|o|p|pe|po|s|z)
-lcallq?
-leaveq?
-lea[wlq]?
-lfence
-lfs[wl]?
-lgs[wl]?
-lods[bwlq]?
-loopn?[ze]?
-lretq?
-lss[wl]?
-mfence
-movaps
-mov[bwlq]?
-movs[bwlq]?
-movsb[wlq]?
-movslq?
-movsw[lq]?
-movzb[wlq]?
-movzw[lq]?
-mul[bwlq]?
-neg[bwlq]?
-nop
-not[bwlq]?
-or[bwlq]?
-pause
-popf[wlq]?
-pop[wlq]?
-prefetch(?:t[012]|nta)
-pushf[wlq]?
-push[wlq]?
-rcl[bwlq]?
-rcr[bwlq]?
-rdmsr
-rdtsc
-retq?
-rol[bwlq]?
-ror[bwlq]?
-sahf
-sal[bwlq]?
-sar[bwlq]?
-sbb[bwlq]?
-scas[bwlq]?
-setn?(?:a|ae|b|be|c|e|g|ge|l|le|o|p|pe|po|s|z)
-shl[bwlq]?
-shld[bwlq]?
-shr[bwlq]?
-shrd[bwlq]?
-smov[lw]?
-stc
-std
-sti
-stos[bwlq]?
-sub[bwlq]?
-test[bwlq]?
-xadd[bwlq]?
-xchg[bwlq]?
-xlat
-xlatb
-xor[bwlq]?
diff --git a/safety/data/references b/safety/data/references
deleted file mode 100644
index bfea8e86..00000000
--- a/safety/data/references
+++ /dev/null
@@ -1,94 +0,0 @@
-__alloc_percpu
-autoremove_wake_function
-__bitmap_weight
-cond_resched
-__const_udelay
-copy_from_user
-__copy_from_user_ll
-copy_to_user
-__copy_user
-copy_user_generic
-cpu_callout_map
-cpu_online_map
-cpu_possible_map
-cpu_to_node
-create_proc_entry
-del_timer_sync
-__divdi3
-do_gettimeofday
-__down_failed
-__find_next_bit
-find_next_bit
-finish_wait
-free_percpu
-__get_user_4
-init_timer
-__init_timer_base
-jiffies
-kallsyms_lookup_name
-kfree
-__kmalloc
-kmalloc_node
-kmem_cache_alloc
-malloc_sizes
-memcmp
-memcpy
-memset
-__might_sleep
-__moddi3
-__mod_timer
-mod_timer
-msleep
-node_online_map
-param_get_int
-param_get_long
-param_get_string
-param_set_copystring
-param_set_int
-param_set_long
-per_cpu__cpu_info
-prepare_to_wait
-printk
-proc_mkdir
-proc_root
-_read_lock
-_read_trylock
-_read_unlock
-register_kprobe
-register_kretprobe
-register_profile_notifier
-register_timer_hook
-remove_proc_entry
-schedule
-schedule_delayed_work
-scnprintf
-simple_strtol
-snprintf
-_spin_lock
-_spin_lock_irqsave
-_spin_trylock
-_spin_unlock
-_spin_unlock_irqrestore
-sprintf
-strcmp
-strlcat
-strlcpy
-strlen
-strncmp
-strncpy
-__strncpy_from_user
-strsep
-__udivdi3
-__umoddi3
-unregister_kprobe
-unregister_kretprobe
-unregister_profile_notifier
-unregister_timer_hook
-unw_init_running
-unw_unwind
-__up_wakeup
-vscnprintf
-vsnprintf
-__wake_up
-_write_trylock
-_write_unlock
diff --git a/safety/safety.py b/safety/safety.py
deleted file mode 100755
index 8607ce75..00000000
--- a/safety/safety.py
+++ /dev/null
@@ -1,245 +0,0 @@
-#!/usr/bin/env python
-# -*- coding: utf-8 -*-
-# vim: noet sw=4 ts=4 enc=utf-8
-"A static safety-checker for SystemTap modules."
-
-# Copyright (C) 2006 Intel Corporation.
-#
-# This file is part of systemtap, and is free software. You can
-# redistribute it and/or modify it under the terms of the GNU General
-# Public License (GPL); either version 2, or (at your option) any
-# later version.
-
-
-# in python 2.4, set & frozenset are builtins
-# in python 2.3, the equivalents live in the 'sets' module
-from sys import hexversion as __hexversion
-if __hexversion < 0x020400f0:
- from sets import Set as set, ImmutableSet as frozenset
-
-
-def main(argv):
- """
- CLI to the SystemTap static safety-checker.
-
- Provides a command-line interface for running the SystemTap module
- safety checker. Use '-h' or '--help' for a description of the
- command-line options.
-
- Returns the number of modules that failed the check.
- """
- bad = 0
- (options, args) = __parse_args(argv[1:])
- safe = StaticSafety(options.arch, options.release, options.datapath)
- for m in args:
- if not safe.check_module(m):
- bad += 1
- return bad
-
-
-def __parse_args(argv):
- from optparse import OptionParser
- parser = OptionParser(usage="usage: %prog [options] [module]...",
- description=__doc__)
- parser.add_option('--data-path', dest='datapath', metavar='PATH',
- help='specify the whitelist data files [default: <script-dir>/data]')
- parser.add_option('-m', '--machine', '--architecture', dest='arch',
- help='specify the machine architecture of the target')
- parser.add_option('-r', '--kernel-release', dest='release',
- help='specify the kernel release running on the target')
- return parser.parse_args(argv)
-
-
-class StaticSafety:
- "Manage a safety-checking session."
-
- def __init__(self, arch=None, release=None, datapath=None):
- from os import uname
- self.__arch = arch or uname()[4]
- self.__release = release or uname()[2]
- self.__build_data_path(datapath)
- self.__build_search_suffixes()
- self.__load_allowed_references()
- self.__load_allowed_opcodes()
-
- def __build_data_path(self, datapath):
- "Determine where the data directory resides."
- from sys import argv
- from os.path import dirname, isdir, realpath
- if datapath is None:
- local = dirname(realpath(argv[0]))
- self.__data_path = local + '/data'
- else:
- self.__data_path = datapath
-
- if not isdir(self.__data_path):
- raise StandardError(
- "Can't find the data directory! (looking in %s)"
- % self.__data_path)
-
- def __build_search_suffixes(self):
- "Construct arch & kernel-versioning search suffixes."
- ss = set()
-
- # add empty string
- ss.add('')
-
- # add architecture search path
- archsfx = '-%s' % self.__arch
- ss.add(archsfx)
-
- # add full kernel-version-release (2.6.NN-FOOBAR) + arch
- relsfx = '-%s' % self.__release
- ss.add(relsfx)
- ss.add(relsfx + archsfx)
-
- # add kernel version (2.6.NN) + arch
- dash_i = relsfx.find('-')
- if dash_i > 0:
- ss.add(relsfx[:dash_i])
- ss.add(relsfx[:dash_i] + archsfx)
-
- # start dropping decimals
- dot_i = relsfx.rfind('.', 0, dash_i)
- while dot_i > 0:
- ss.add(relsfx[:dot_i])
- ss.add(relsfx[:dot_i] + archsfx)
- dot_i = relsfx.rfind('.', 0, dot_i)
-
- self.__search_suffixes = frozenset(ss)
-
- def __load_allowed_references(self):
- "Build the list of allowed external references from the data files."
- wr = set()
- for sfx in self.__search_suffixes:
- try:
- refs = open(self.__data_path + '/references' + sfx)
- for line in refs:
- wr.add(line.rstrip())
- refs.close()
- except IOError:
- pass
- if not len(wr):
- raise StandardError("No whitelisted references found!")
- self.__white_references = frozenset(wr)
-
- def __load_allowed_opcodes(self):
- "Build the regular expression matcher for allowed opcodes from the data files."
- from re import compile
- wo = []
- for sfx in self.__search_suffixes:
- try:
- opcs = open(self.__data_path + '/opcodes' + sfx)
- for line in opcs:
- wo.append(line.rstrip())
- opcs.close()
- except IOError:
- pass
- if not len(wo):
- raise StandardError("No whitelisted opcodes found!")
- self.__white_opcodes_re = compile(r'^(?:' + r'|'.join(wo) + r')$')
-
- def __check_references(self, module):
- "Check that all unresolved references in the module are allowed."
- from os import popen
- from re import compile
-
- sym_re = compile(r'^([\w@.]+) [Uw]\s+$')
- def check(line):
- m = sym_re.match(line)
- if m:
- ref = m.group(1)
- if ref not in self.__white_references:
- print 'ERROR: Invalid reference to %s' % ref
- return False
- return True
- print 'WARNING: Unmatched line:\n %s' % `line`
- return True
-
- command = 'nm --format=posix --no-sort --undefined-only ' + `module`
- ok = True
- nm = popen(command)
- for line in nm:
- ok &= check(line)
- if nm.close():
- ok = False
- return ok
-
- def __check_opcodes(self, module):
- "Check that all disassembled opcodes in the module are allowed."
- from os import popen
- from re import compile
-
- skip_ud2a = [0]
-
- ignore_re = compile(r'^$|^\s+\.{3}$|^.*Disassembly of section|^.*file format')
- if self.__arch == 'ia64':
- opc = r'(?:\[[IBFLMX]{3}\]\s+)?(?:\(p\d\d\)\s+)?([\w.]+)\b'
- elif self.__arch == 'x86_64' or self.__arch == 'i686':
- opc = r'(?:lock\s+)?|(?:repn?[ze]?\s+)?|(?:rex\w+\s+)?(\w+)\b'
- else:
- opc = r'(\w+)\b'
- opc_re = compile(r'^[A-Fa-f\d]+\s+<([^>]+)>\s+%s' % opc)
- def check(line):
- m = ignore_re.match(line)
- if m:
- return True
- m = opc_re.match(line)
- if m:
- loc, opc = m.groups()
- if opc == 'ud2a':
- # The kernel abuses ud2a for BUG checks by following it
- # directly with __LINE__ and __FILE__. Objdump doesn't
- # know this though, so it tries to interpret the data as
- # real instructions. Because x86(-64) instructions are
- # variable-length, it's hard to tell when objdump is synced
- # up again. We'll fast-forward to the next function
- # boundary and hope things are better there.
- for skip in objdump:
- mskip = opc_re.match(skip)
- if mskip:
- locskip = mskip.group(1)
- # a loc without an offset marks a new function
- if '+' not in locskip:
- return check(skip)
- skip_ud2a[0] += 1
- return True
- elif not self.__white_opcodes_re.match(opc):
- print "ERROR: Invalid opcode '%s' at <%s>" % (opc, loc)
- return False
- return True
- print 'WARNING: Unmatched line:\n %s' % `line`
- return True
-
- command = 'objdump --disassemble --prefix-addresses ' + `module`
- ok = True
- objdump = popen(command)
- for line in objdump:
- ok &= check(line)
- if objdump.close():
- ok = False
-
- if skip_ud2a[0]:
- #print 'WARNING: Skipped %d lines due to ud2a corruption' % skip_ud2a[0]
- pass
-
- return ok
-
- def check_module(self, module):
- "Check a module for exclusively safe opcodes and external references."
- from os.path import isfile
- if not isfile(module):
- print 'ERROR: %s is not a file!' % `module`
- return False
- res = self.__check_references(module) and self.__check_opcodes(module)
- if res:
- print 'PASS: %s' % module
- else:
- print 'FAIL: %s' % module
- return res
-
-
-if __name__ == '__main__':
- from sys import exit, argv
- exit(main(argv))
-