On Tue, Sep 13, 2005 at 07:49:49PM +0400, Alexey Tourbin wrote: > $ find /bin /usr/bin /lib /usr/lib -type f -maxdepth 1 |file -f - |awk -F': +' '$2~/ELF.*(dynamic|shared)/{print$1}' |xargs nm -D |awk 'NF>1{print NF-1,$(NF-1)}' |sort |uniq -c |sort -n > 25 2 a > 54 1 v > 5864 1 w > 6488 2 R > 9310 2 A > 24821 2 D > 27751 2 B > 38616 2 V > 65737 2 W > 236795 1 U > 359673 2 T > $ > Зато "буквы" не "пересекаются" по наличию или отсутствию адреса. > То есть отдельное поле в дампе для "есть адрес/нет адреса" не нужно. > Наверное, это банальная истина, но вот я её с понтом проверил. Итого, получен (почти) полный дамп всех ELF-символов сизифа, в следующем виде: $ pwd /home/at/.qa-robot/rpmelfsym $ du -hs dump.old 350M dump.old $ head dump.old 7colors /usr/bin/sevencolors A _DYNAMIC 7colors /usr/bin/sevencolors A _GLOBAL_OFFSET_TABLE_ 7colors /usr/bin/sevencolors A __bss_start 7colors /usr/bin/sevencolors A _edata 7colors /usr/bin/sevencolors A _end 7colors /usr/bin/sevencolors B game 7colors /usr/bin/sevencolors D __data_start 7colors /usr/bin/sevencolors D options 7colors /usr/bin/sevencolors D rhomb_xpm_data 7colors /usr/bin/sevencolors R _IO_stdin_used $ Как видно из списка выше, буковки [AaBDRTVW] имеют адрес, то есть в принципе эти символы кем-то могут провайдиться. Буковки [Uvw] не имеют адреса, то есть эти символы "оживают" в процессе динамической линковки. Теперь следите за моей логикой. Буковки, которые имеют адрес, складываем в кучку provides. Остальные буковки по смыслу ложатся в кучку requires. Далее нужно сравнивнить эти две кучки: символы, которые есть в кучке requires, но которые отсутствуют в кучке provides, ЗАВЕДОМО не могут правильно резольвиться динамическим линкером. Это правило -- СЛАБОЕ правило в том смысле, что позволяет обнаружить только ЯВНЫЕ, ЗАВЕДОМО недопустимые, ошибочные символы в ELF'ах. Оно не учитывает связи между ELF'ами, попросту допуская, что при совпадении символов в requires и provides нужная связь между ELF'ами имеется. Для requires и provides буду использовать обозначения "ref" и "def" соответственно (как в lorder из v7). $ awk -F'\t' '$3~/[AaBDRTVW]/' dump.old >def $ awk -F'\t' '$3~/[Uvw]/' dump.old >ref Проверяем, не осталось ли за бортом других буковок. $ wc -l dump.old def ref 4897331 dump.old 2793772 def 2103559 ref 9794662 total $ echo $(( 2793772 + 2103559 )) 4897331 $ Не осталось. Теперь нужно отыскать символы в кучке "ref", которые не "спариваются" с символами в кучке "def". Это умеет делать join. Для этого нужно предварительно отсортировать def и ref по ключевому полю, т.е. по символам (последнее поле, #4). $ sort -t$'\t' -k4,4 -o def def & sort -t$'\t' -k4,4 -o ref ref & [1] 15993 [2] 15994 $ man join (sort тормознуто сортирует, читаю man join) [2] + done sort -t$'\t' -k4,4 -o ref ref [1] + done sort -t$'\t' -k4,4 -o def def $ join -t$'\t' -j 4 -v 1 ref def -o '1.1 1.2 1.3 1.4' >join.out $ wc -l join.out 18243 join.out $ Есть такие символы! $ head -20 join.out tomboy /usr/lib/tomboy/libtomboy.so U GTK_IS_SOURCE_VIEW directfb /usr/lib/directfb-0.9.21/gfxdrivers/libdirectfb_nsc.so U Gal_set_source_transparency libcdf /usr/lib/libcdf_idl.so.0.0.0 U IDL_MakeTempArray libcdf /usr/lib/libcdf_idl.so.0.0.0 U IDL_StoreScalar libcdf /usr/lib/libcdf_idl.so.0.0.0 U IDL_StrDelete libcdf /usr/lib/libcdf_idl.so.0.0.0 U IDL_StrStore libcdf /usr/lib/libcdf_idl.so.0.0.0 U IDL_VarCopy libgcj3.4 /usr/lib/lib-gnu-java-awt-peer-gtk.so.5.0.0 U LINK_ReallyLinkClass libgcj3.4-debug /usr/lib/debug/lib-gnu-java-awt-peer-gtk.so.5.0.0 U LINK_ReallyLinkClass libgcj3.4 /usr/lib/lib-gnu-java-awt-peer-gtk.so.5.0.0 U LINK_ReallyLinkKnownClass libgcj3.4-debug /usr/lib/debug/lib-gnu-java-awt-peer-gtk.so.5.0.0 U LINK_ReallyLinkKnownClass mod_ssl-sxnet /usr/lib/apache/mod_sxnet.so U Malloc mnogosearch-ruby /usr/lib/ruby/vendor_ruby/1.8/i586-linux-gnu/mnogo.so U UdmEnvErrCode abiword /usr/lib/AbiWord-2.4/plugins/libAbiGimp.so U _Z10progExistsPKc python-module-PyKDE /usr/lib/python2.4/site-packages/kdeprint.so U _Z11rangeToSizeRK7QString TORCS /usr/lib/torcs/modules/graphic/ssggraph.so U _Z14ssgCullAndDrawP7ssgRoot TORCS /usr/lib/torcs/texmapper-bin U _Z14ssgCullAndDrawP7ssgRoot boost-test /usr/lib/libboost_unit_test_framework-gcc-1_32.so.1.32.0 U _Z20init_unit_test_suiteiPPc boost-test /usr/lib/libboost_unit_test_framework-gcc-mt-1_32.so.1.32.0 U _Z20init_unit_test_suiteiPPc boost-test-devel /usr/lib/libboost_unit_test_framework-gcc-d-1_32.so.1.32.0 U _Z20init_unit_test_suiteiPPc $ Похоже на правду. По поводу GTK_IS_SOURCE_VIEW всё ясно -- это нераскрытый макрос (в смысле препроцессора cpp). По поводу Gal_set_source_transparency -- проверяем: $ grep -wi Gal_set_source_transparency dump.old directfb /usr/lib/directfb-0.9.21/gfxdrivers/libdirectfb_nsc.so U Gal_set_source_transparency $ Нет такого символа в дампе. Кто предоставляет символы Gal_*? $ awk -F'\t' '$3=="T"&&$4~/^Gal_/' dump.old directfb /usr/lib/directfb-0.9.21/gfxdrivers/libdirectfb_nsc.so T Gal_bresenham_line directfb /usr/lib/directfb-0.9.21/gfxdrivers/libdirectfb_nsc.so T Gal_cleanup_interface ... $ Ага, сам же directfb их и предоставляет. Что-то в нём не стыкуется. $ awk -F'\t' '$4~/^Gal_.*transp/' dump.old directfb /usr/lib/directfb-0.9.21/gfxdrivers/libdirectfb_nsc.so U Gal_set_source_transparency $ Странно. Ладно, едем дальше. libcdf_idl, символы IDL_*. $ awk -F'\t' '$3=="T"&&$4~/^IDL_/' dump.old ORBit-devel /usr/bin/orbit-idl T IDL_tree_traverse_parents ORBit2-devel /usr/bin/orbit-idl-2 T IDL_tree_traverse_parents ORBit2-devel /usr/bin/orbit-idl-2 T IDL_tree_traverse_parents_full libIDL /usr/lib/libIDL-2.so.0.0.0 T IDL_attr_dcl_new libIDL /usr/lib/libIDL-2.so.0.0.0 T IDL_binop_new ... libORBit /usr/lib/libIDL-0.6.so.0.4.4 T IDL_attr_dcl_new libORBit /usr/lib/libIDL-0.6.so.0.4.4 T IDL_binop_new libORBit /usr/lib/libIDL-0.6.so.0.4.4 T IDL_boolean_new libORBit /usr/lib/libIDL-0.6.so.0.4.4 T IDL_case_stmt_new ... $ Ясно, это всякие ORBit'ы и IDL'и, но таких символов в них нету. Странно. Попробуем на всякий случай `ldd -r'. $ ldd -r /usr/lib/libcdf_idl.so.0.0.0 libc.so.6 => /lib/i686/libc.so.6 (0x4005d000) /lib/ld-linux.so.2 => /lib/ld-linux.so.2 (0x80000000) undefined symbol: IDL_StoreScalar (/usr/lib/libcdf_idl.so.0.0.0) undefined symbol: IDL_VarCopy (/usr/lib/libcdf_idl.so.0.0.0) undefined symbol: IDL_StrStore (/usr/lib/libcdf_idl.so.0.0.0) undefined symbol: IDL_StrDelete (/usr/lib/libcdf_idl.so.0.0.0) undefined symbol: IDL_MakeTempArray (/usr/lib/libcdf_idl.so.0.0.0) $ Круто! Эта библиотека по части IDL_ ни с кем не слинкована, а вывод `ldd -r' подтвержает то, что мы только что увидели в join.out. По поводу libgcj3.4 я судить не берусь. Дальше идет mod_ssl-sxnet Malloc. $ grep -w Malloc dump.old mod_ssl-sxnet /usr/lib/apache/mod_sxnet.so U Malloc $ Нет такого символа нигде! Далее идёт boost -- опять же не берусь судить. Потом всякое приплюснутое. И так далее. ... Что делать будем? PS: там дальше много всяких __gmon_start__ символов идёт, так что всё не слишком плохо.