16e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne#!/usr/bin/env python 26e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne#===- lib/dfsan/scripts/build-libc-list.py ---------------------------------===# 36e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne# 46e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne# The LLVM Compiler Infrastructure 56e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne# 66e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne# This file is distributed under the University of Illinois Open Source 76e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne# License. See LICENSE.TXT for details. 86e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne# 96e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne#===------------------------------------------------------------------------===# 106e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne# The purpose of this script is to identify every function symbol in a set of 116e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne# libraries (in this case, libc and libgcc) so that they can be marked as 126e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne# uninstrumented, thus allowing the instrumentation pass to treat calls to those 136e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne# functions correctly. 146e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 156e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourneimport os 166e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourneimport subprocess 176e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourneimport sys 186e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbournefrom optparse import OptionParser 196e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 206e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbournedef defined_function_list(object): 216e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne functions = [] 226e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne readelf_proc = subprocess.Popen(['readelf', '-s', '-W', object], 236e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne stdout=subprocess.PIPE) 246e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne readelf = readelf_proc.communicate()[0].split('\n') 256e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne if readelf_proc.returncode != 0: 266e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne raise subprocess.CalledProcessError(readelf_proc.returncode, 'readelf') 276e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne for line in readelf: 286e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne if (line[31:35] == 'FUNC' or line[31:36] == 'IFUNC') and \ 296d1862363c88c183b0ed7740fca876342cf0474bStephen Hines line[39:44] != 'LOCAL' and \ 306e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne line[55:58] != 'UND': 316e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne function_name = line[59:].split('@')[0] 326e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne functions.append(function_name) 336e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne return functions 346e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 356e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbournep = OptionParser() 362d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hines 372d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hinesp.add_option('--libc-dso-path', metavar='PATH', 382d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hines help='path to libc DSO directory', 396e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne default='/lib/x86_64-linux-gnu') 402d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hinesp.add_option('--libc-archive-path', metavar='PATH', 412d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hines help='path to libc archive directory', 426e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne default='/usr/lib/x86_64-linux-gnu') 432d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hines 442d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hinesp.add_option('--libgcc-dso-path', metavar='PATH', 452d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hines help='path to libgcc DSO directory', 462d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hines default='/lib/x86_64-linux-gnu') 472d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hinesp.add_option('--libgcc-archive-path', metavar='PATH', 482d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hines help='path to libgcc archive directory', 496e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne default='/usr/lib/gcc/x86_64-linux-gnu/4.6') 502d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hines 516e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbournep.add_option('--with-libstdcxx', action='store_true', 526e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne dest='with_libstdcxx', 536e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne help='include libstdc++ in the list (inadvisable)') 542d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hinesp.add_option('--libstdcxx-dso-path', metavar='PATH', 552d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hines help='path to libstdc++ DSO directory', 562d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hines default='/usr/lib/x86_64-linux-gnu') 572d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hines 586e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne(options, args) = p.parse_args() 596e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 602d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hineslibs = [os.path.join(options.libc_dso_path, name) for name in 616e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne ['ld-linux-x86-64.so.2', 626e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 'libanl.so.1', 636e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 'libBrokenLocale.so.1', 646e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 'libcidn.so.1', 656e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 'libcrypt.so.1', 666e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 'libc.so.6', 676e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 'libdl.so.2', 686e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 'libm.so.6', 696e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 'libnsl.so.1', 706e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 'libpthread.so.0', 716e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 'libresolv.so.2', 726e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 'librt.so.1', 736e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 'libthread_db.so.1', 746e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 'libutil.so.1']] 752d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hineslibs += [os.path.join(options.libc_archive_path, name) for name in 766e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne ['libc_nonshared.a', 776e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 'libpthread_nonshared.a']] 782d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hines 792d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hineslibs.append(os.path.join(options.libgcc_dso_path, 'libgcc_s.so.1')) 802d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hineslibs.append(os.path.join(options.libgcc_archive_path, 'libgcc.a')) 812d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hines 826e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourneif options.with_libstdcxx: 832d1fdb26e458c4ddc04155c1d421bced3ba90cd0Stephen Hines libs.append(os.path.join(options.libstdcxx_dso_path, 'libstdc++.so.6')) 846e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 856e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbournefunctions = [] 866e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbournefor l in libs: 876e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne if os.path.exists(l): 886e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne functions += defined_function_list(l) 896e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne else: 906e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne print >> sys.stderr, 'warning: library %s not found' % l 916e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 926e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbournefunctions = list(set(functions)) 936e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbournefunctions.sort() 946e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne 956e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbournefor f in functions: 966e4c46dc162803cc99c2a5e068fc28adb873a431Peter Collingbourne print 'fun:%s=uninstrumented' % f 97