• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1#!/bin/sh
2#
3# Copyright (C) 2011 The Android Open Source Project
4#
5# Licensed under the Apache License, Version 2.0 (the "License");
6# you may not use this file except in compliance with the License.
7# You may obtain a copy of the License at
8#
9#      http://www.apache.org/licenses/LICENSE-2.0
10#
11# Unless required by applicable law or agreed to in writing, software
12# distributed under the License is distributed on an "AS IS" BASIS,
13# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14# See the License for the specific language governing permissions and
15# limitations under the License.
16#
17# gen-system-symbols.sh
18#
19# This tool is used to read the shared library from a source directory
20# (SRC) and extract the list of functions and variables.
21#
22# Then, for each library, it will generate in (DST) two text files
23# named <library>.functions.txt and <library>.variables.txt
24#
25
26# Only runs on Linux because it requires the "readelf" utility
27#
28
29. `dirname $0`/prebuilt-common.sh
30
31VERBOSE=no
32VERBOSE2=no
33
34PROGRAM_PARAMETERS="<src-dir> <dst-dir>"
35PROGRAM_DESCRIPTION=\
36"This program is used to parse all shared libraries in <src-dir>
37and extract, for each one of them, the list of functions and variables
38that it exports.
39
40For some of these libraries, it will remove symbols that are not meant
41to be imported (unless you use --no-symbol-filtering)
42
43These lists will then be saved into two files:
44
45  <dst-dir>/<libname>.functions.txt
46  <dst-dir>/<libname>.variables.txt
47"
48
49NO_FILTERING=
50register_var_option "--no-symbol-filtering" NO_FILTERING "Disable symbol filtering"
51
52extract_parameters "$@"
53
54parse_params ()
55{
56    SRCDIR=$1
57    DSTDIR=$2
58
59    if [ -z "$SRCDIR" ]; then
60        dump "ERROR: Missing first parameter (source directory path), see --help"
61        exit 1
62    fi
63
64    if [ -z "$DSTDIR" ]; then
65        dump "ERROR: Missing second parameter (destination directory path), see --help"
66        exit 1
67    fi
68
69    if [ ! -d "$SRCDIR" ]; then
70        dump "ERROR: Not a source directory: $SRCDIR"
71        exit 1
72    fi
73
74    mkdir -p $DSTDIR
75    fail_panic "Could not create destination directory: $DSTDIR"
76}
77
78parse_params $PARAMETERS
79
80READELF=readelf
81
82# $1: shared library path
83get_library_functions ()
84{
85    $READELF -s -D -W $1 | awk '$5 ~ /FUNC/ && $6 ~ /GLOBAL|WEAK/ && $8 !~ /UND/ { print $9; }' | sort -u
86}
87
88# $1: shared library path
89get_library_variables ()
90{
91    $READELF -s -D -W $1 | awk '$5 ~ /OBJECT/ && $6 ~ /GLOBAL|WEAK/ && $8 !~ /UND/ { print $9; }' | sort -u
92}
93
94# Temp file used to list shared library symbol exclusions
95# See set_symbol_excludes and extract_shared_library_xxxx functions below
96SYMBOL_EXCLUDES=/tmp/ndk-$USER/ndk-symbol-excludes.txt
97
98# Temp file used to list shared library symbol inclusions, these
99# are essentially overrides to the content of SYMBOL_EXCLUDES
100SYMBOL_INCLUDES=/tmp/ndk-$USER/ndk-symbol-includes.txt
101
102# Temp file used to filter symbols
103SYMBOL_TMPFILE=/tmp/ndk-$USER/ndk-symbols-list.txt
104
105# Reset the symbol exclusion list to its default
106reset_symbol_excludes ()
107{
108    # By default, do not export C++ mangled symbol, which all start with _Z
109    echo '^_Z' > $SYMBOL_EXCLUDES
110
111    # __INIT_ARRAY__, __FINI_ARRAY__ and _GLOBAL_OFFSET_TABLE_ are special symbols
112    # that should normally be hidden.
113    echo "^__INIT_ARRAY__" >> $SYMBOL_EXCLUDES
114    echo "^__FINI_ARRAY__" >> $SYMBOL_EXCLUDES
115    echo "^_GLOBAL_OFFSET_TABLE_" >> $SYMBOL_EXCLUDES
116    > $SYMBOL_INCLUDES
117}
118
119# Add new exclusion patterns to SYMBOL_EXCLUDES
120set_symbol_excludes ()
121{
122    (echo "$@" | tr ' ' '\n') >> $SYMBOL_EXCLUDES
123}
124
125# Add new inclusion patterns to SYMBOL_INCLUDES
126set_symbol_includes ()
127{
128    (echo "$@" | tr ' ' '\n') >> $SYMBOL_INCLUDES
129}
130
131# Clear symbol exclusion/inclusion files
132clear_symbol_excludes ()
133{
134    rm -f $SYMBOL_EXCLUDES $SYMBOL_INCLUDES
135}
136
137# Filter the list of symbols from a file
138# $1: path to symbol list file
139filter_symbols ()
140{
141    (grep -v -f $SYMBOL_EXCLUDES $1 ; grep -f $SYMBOL_INCLUDES $1) | sort -u
142}
143
144# $1: Library name
145# $2+: List of symbols (functions or variables)
146# Out: sorted list of filtered symbols, based on library name
147filter_library_symbols ()
148{
149    local LIB=$1
150    shift
151    local SYMBOLS="$@"
152    (echo "$SYMBOLS" | tr ' ' '\n' | sort -u) > $SYMBOL_TMPFILE
153
154    reset_symbol_excludes
155
156    case $LIB in
157        libc.so)
158            # Remove a few internal symbols that should not be exposed
159            # from the C library (we plan to clean that up soon by using the
160            # "hidden" visibility attribute in the near future).
161            #
162            set_symbol_excludes \
163                '^the_' '^dns_' 'load_domain_search_list' 'res_get_dns_changed' \
164                '^_resolv_cache' '^_dns_getht' '^_thread_atexit' \
165                '^free_malloc_leak_info' 'fake_gmtime_r' 'fake_localtime_r' \
166                '^gAllocationsMutex' '^gHashTable' '^gMallocLeakZygoteChild'
167            # libc.so now absort libstdc++ use to have, thus contains C++ symbols from now on
168            set_symbol_includes '^_Z.*'
169            ;;
170        libstdc++.so)
171            # This used to be the only library that is allowed to export C++ symbols for now.
172            set_symbol_includes '^_Z.*'
173            ;;
174        liblog.so)
175            set_symbol_excludes '^.*'         # exclude everything
176            set_symbol_includes '^__android_' # except __android_xxxx functions
177            ;;
178        libOpenSLES.so)
179            set_symbol_excludes '^_' '^MPH_' # remove MPH_to_xxx definitions
180            ;;
181        libGLESv*.so)
182            # Exclude non-OES extension entry points
183            set_symbol_excludes 'EXT$'
184            set_symbol_excludes 'AMD$'
185            set_symbol_excludes 'ANGLE$'
186            set_symbol_excludes 'APPLE$'
187            set_symbol_excludes 'IMG$'
188            set_symbol_excludes 'NV$'
189            set_symbol_excludes 'QCOM$'
190            ;;
191    esac
192    filter_symbols "$SYMBOL_TMPFILE"
193}
194
195for LIB in $(cd $SRCDIR && ls lib*.so); do
196    SRCLIB=$SRCDIR/$LIB
197    log "Extracting symbols from $LIB"
198    FUNCS=$(get_library_functions $SRCLIB)
199    VARS=$(get_library_variables $SRCLIB)
200    if [ -z "$NO_FILTERING" ]; then
201        FUNCS=$(filter_library_symbols $LIB $FUNCS)
202        VARS=$(filter_library_symbols $LIB $VARS)
203    fi
204    NUMFUNCS=$(echo $FUNCS | wc -w)
205    NUMVARS=$(echo $VARS | wc -w)
206    log "    Found $NUMFUNCS functions and $NUMVARS variables"
207    (echo "$FUNCS" | tr ' ' '\n') > $DSTDIR/$LIB.functions.txt
208    (echo "$VARS" | tr ' ' '\n') > $DSTDIR/$LIB.variables.txt
209done
210