summaryrefslogtreecommitdiffstats
path: root/compiler-rt/lib/asan/scripts/asan_symbolize.py
diff options
context:
space:
mode:
authorAlexander Potapenko <glider@google.com>2012-01-26 17:06:50 +0000
committerAlexander Potapenko <glider@google.com>2012-01-26 17:06:50 +0000
commit02a71626e3765502f59e1be769ebabb5b944bb3f (patch)
treed999279ebeeaf368d899244f74059bf2bb50c69a /compiler-rt/lib/asan/scripts/asan_symbolize.py
parent98f0c713d994a55d5fed21717daff776179400d2 (diff)
downloadbcm5719-llvm-02a71626e3765502f59e1be769ebabb5b944bb3f.tar.gz
bcm5719-llvm-02a71626e3765502f59e1be769ebabb5b944bb3f.zip
More accurate atos execution which depends on the file type (EXECUTE, DYLIB) of the binary.
More Linux-like output on Mac (to match more output tests). llvm-svn: 149064
Diffstat (limited to 'compiler-rt/lib/asan/scripts/asan_symbolize.py')
-rwxr-xr-xcompiler-rt/lib/asan/scripts/asan_symbolize.py63
1 files changed, 49 insertions, 14 deletions
diff --git a/compiler-rt/lib/asan/scripts/asan_symbolize.py b/compiler-rt/lib/asan/scripts/asan_symbolize.py
index 154e1f2994b..357593d532b 100755
--- a/compiler-rt/lib/asan/scripts/asan_symbolize.py
+++ b/compiler-rt/lib/asan/scripts/asan_symbolize.py
@@ -14,6 +14,8 @@ import string
import subprocess
pipes = {}
+filetypes = {}
+DEBUG=False
def patch_address(frameno, addr_s):
''' Subtracts 1 or 2 from the top frame's address.
@@ -30,6 +32,15 @@ def patch_address(frameno, addr_s):
return hex(addr)
return addr_s
+
+def fix_filename(file_name):
+ for path_to_cut in sys.argv[1:]:
+ file_name = re.sub(".*" + path_to_cut, "", file_name)
+ file_name = re.sub(".*asan_[a-z_]*.cc:[0-9]*", "_asan_rtl_", file_name)
+ file_name = re.sub(".*crtstuff.c:0", "???:0", file_name)
+ return file_name
+
+
# TODO(glider): need some refactoring here
def symbolize_addr2line(line):
#0 0x7f6e35cf2e45 (/blah/foo.so+0x11fe45)
@@ -50,15 +61,25 @@ def symbolize_addr2line(line):
except:
function_name = ""
file_name = ""
- for path_to_cut in sys.argv[1:]:
- file_name = re.sub(".*" + path_to_cut, "", file_name)
- file_name = re.sub(".*asan_[a-z_]*.cc:[0-9]*", "_asan_rtl_", file_name)
- file_name = re.sub(".*crtstuff.c:0", "???:0", file_name)
+ file_name = fix_filename(file_name)
print match.group(1), "in", function_name, file_name
else:
print line.rstrip()
+
+def get_macho_filetype(binary):
+ if not filetypes.has_key(binary):
+ otool_pipe = subprocess.Popen(["otool", "-Vh", binary],
+ stdin=subprocess.PIPE, stdout=subprocess.PIPE)
+ otool_line = "".join(otool_pipe.stdout.readlines())
+ for t in ["DYLIB", "EXECUTE"]:
+ if t in otool_line:
+ filetypes[binary] = t
+ otool_pipe.stdin.close()
+ return filetypes[binary]
+
+
def symbolize_atos(line):
#0 0x7f6e35cf2e45 (/blah/foo.so+0x11fe45)
match = re.match('^( *#([0-9]+) *)(0x[0-9a-f]+) *\((.*)\+(0x[0-9a-f]+)\)', line)
@@ -66,32 +87,46 @@ def symbolize_atos(line):
#print line
prefix = match.group(1)
frameno = match.group(2)
- addr = match.group(3)
+ orig_addr = match.group(3)
binary = match.group(4)
offset = match.group(5)
- addr = patch_address(frameno, addr)
- load_addr = int(addr, 16) - int(offset, 16)
+ addr = patch_address(frameno, orig_addr)
+ load_addr = hex(int(orig_addr, 16) - int(offset, 16))
+ filetype = get_macho_filetype(binary)
+
if not pipes.has_key(binary):
# Guess which arch we're running. 10 = len("0x") + 8 hex digits.
if len(addr) > 10:
arch = "x86_64"
else:
arch = "i386"
- #print "atos -o %s -arch %s " % (binary, arch)
- pipes[binary] = subprocess.Popen(["atos", "-o", binary, "-arch", arch],
+
+ if filetype == "DYLIB":
+ load_addr = "0x0"
+ if DEBUG:
+ print "atos -o %s -arch %s -l %s" % (binary, arch, load_addr)
+ pipes[binary] = subprocess.Popen(["atos", "-o", binary, "-arch", arch, "-l", load_addr],
stdin=subprocess.PIPE, stdout=subprocess.PIPE,)
p = pipes[binary]
- # TODO(glider): how to tell if the address is absolute?
- if ".app/" in binary and not ".framework" in binary:
- print >>p.stdin, "%s" % addr
+ if filetype == "DYLIB":
+ print >>p.stdin, "%s" % offset
else:
print >>p.stdin, "%s" % addr
# TODO(glider): it's more efficient to make a batch atos run for each binary.
p.stdin.close()
atos_line = p.stdout.readline().rstrip()
+ # A well-formed atos response looks like this:
+ # foo(type1, type2) (in object.name) (filename.cc:80)
+ match = re.match('^(.*) \(in (.*)\) \((.*:\d*)\)$', atos_line)
+ #print "atos_line: ", atos_line
+ if match:
+ function_name = match.group(1)
+ function_name = re.sub("\(.*?\)", "", function_name)
+ file_name = fix_filename(match.group(3))
+ print "%s%s in %s %s" % (prefix, addr, function_name, file_name)
+ else:
+ print "%s%s in %s" % (prefix, addr, atos_line)
del pipes[binary]
-
- print "%s%s in %s" % (prefix, addr, atos_line)
else:
print line.rstrip()
OpenPOWER on IntegriCloud