build-libc-list.py revision 2d1fdb26e458c4ddc04155c1d421bced3ba90cd0
1f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)#!/usr/bin/env python
2f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)#===- lib/dfsan/scripts/build-libc-list.py ---------------------------------===#
3f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)#
4f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)#                     The LLVM Compiler Infrastructure
5f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)#
6f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)# This file is distributed under the University of Illinois Open Source
7f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)# License. See LICENSE.TXT for details.
8f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)#
96e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)#===------------------------------------------------------------------------===#
106e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)# The purpose of this script is to identify every function symbol in a set of
11f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)# libraries (in this case, libc and libgcc) so that they can be marked as
12f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)# uninstrumented, thus allowing the instrumentation pass to treat calls to those
13f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)# functions correctly.
14f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)
15f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)import os
16f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)import subprocess
17f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)import sys
186e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)from optparse import OptionParser
19116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch
20f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)def defined_function_list(object):
21f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)  functions = []
22f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)  readelf_proc = subprocess.Popen(['readelf', '-s', '-W', object],
23f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)                                  stdout=subprocess.PIPE)
24f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)  readelf = readelf_proc.communicate()[0].split('\n')
25f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)  if readelf_proc.returncode != 0:
26f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)    raise subprocess.CalledProcessError(readelf_proc.returncode, 'readelf')
27f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)  for line in readelf:
28f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)    if (line[31:35] == 'FUNC' or line[31:36] == 'IFUNC') and \
29f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)       line[55:58] != 'UND':
30f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)      function_name = line[59:].split('@')[0]
31f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)      functions.append(function_name)
325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  return functions
335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)
34f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)p = OptionParser()
35f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)
36f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)p.add_option('--libc-dso-path', metavar='PATH',
37f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)             help='path to libc DSO directory',
385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)             default='/lib/x86_64-linux-gnu')
396e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)p.add_option('--libc-archive-path', metavar='PATH',
40f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)             help='path to libc archive directory',
41116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch             default='/usr/lib/x86_64-linux-gnu')
42116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch
43116680a4aac90f2aa7413d9095a592090648e557Ben Murdochp.add_option('--libgcc-dso-path', metavar='PATH',
44116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch             help='path to libgcc DSO directory',
45116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch             default='/lib/x86_64-linux-gnu')
46116680a4aac90f2aa7413d9095a592090648e557Ben Murdochp.add_option('--libgcc-archive-path', metavar='PATH',
47116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch             help='path to libgcc archive directory',
48116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch             default='/usr/lib/gcc/x86_64-linux-gnu/4.6')
496e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)
506e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)p.add_option('--with-libstdcxx', action='store_true',
51116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch             dest='with_libstdcxx',
52116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch             help='include libstdc++ in the list (inadvisable)')
53116680a4aac90f2aa7413d9095a592090648e557Ben Murdochp.add_option('--libstdcxx-dso-path', metavar='PATH',
54f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)             help='path to libstdc++ DSO directory',
55f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)             default='/usr/lib/x86_64-linux-gnu')
56f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)
57f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)(options, args) = p.parse_args()
58f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)
59f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)libs = [os.path.join(options.libc_dso_path, name) for name in
60116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch        ['ld-linux-x86-64.so.2',
61116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch         'libanl.so.1',
62f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)         'libBrokenLocale.so.1',
63f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)         'libcidn.so.1',
64f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)         'libcrypt.so.1',
65f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)         'libc.so.6',
66f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)         'libdl.so.2',
67f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)         'libm.so.6',
68f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)         'libnsl.so.1',
69f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)         'libpthread.so.0',
70f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)         'libresolv.so.2',
71f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)         'librt.so.1',
72f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)         'libthread_db.so.1',
73f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)         'libutil.so.1']]
74f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)libs += [os.path.join(options.libc_archive_path, name) for name in
75f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)         ['libc_nonshared.a',
76f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)          'libpthread_nonshared.a']]
77f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)
78libs.append(os.path.join(options.libgcc_dso_path, 'libgcc_s.so.1'))
79libs.append(os.path.join(options.libgcc_archive_path, 'libgcc.a'))
80
81if options.with_libstdcxx:
82  libs.append(os.path.join(options.libstdcxx_dso_path, 'libstdc++.so.6'))
83
84functions = []
85for l in libs:
86  if os.path.exists(l):
87    functions += defined_function_list(l)
88  else:
89    print >> sys.stderr, 'warning: library %s not found' % l
90
91functions = list(set(functions))
92functions.sort()
93
94for f in functions:
95  print 'fun:%s=uninstrumented' % f
96