@@ -328,6 +328,8 @@ template <typename ELFT> class GNUStyle : public DumpStyle<ELFT> {
328
328
OS.flush ();
329
329
return OS;
330
330
}
331
+ void printHashedSymbol (const ELFO *Obj, const Elf_Sym *FirstSym, uint32_t Sym,
332
+ StringRef StrTable, uint32_t Bucket);
331
333
void printRelocation (const ELFO *Obj, const Elf_Shdr *SymTab,
332
334
const Elf_Rela &R, bool IsRela);
333
335
void printSymbol (const ELFO *Obj, const Elf_Sym *Symbol, const Elf_Sym *First,
@@ -2812,15 +2814,120 @@ void GNUStyle<ELFT>::printSymbol(const ELFO *Obj, const Elf_Sym *Symbol,
2812
2814
printField (Entry);
2813
2815
OS << " \n " ;
2814
2816
}
2817
+ template <class ELFT >
2818
+ void GNUStyle<ELFT>::printHashedSymbol(const ELFO *Obj, const Elf_Sym *FirstSym,
2819
+ uint32_t Sym, StringRef StrTable,
2820
+ uint32_t Bucket) {
2821
+ std::string Num, Buc, Name, Value, Size , Binding, Type, Visibility, Section;
2822
+ unsigned Width, Bias = 0 ;
2823
+ if (ELFT::Is64Bits) {
2824
+ Bias = 8 ;
2825
+ Width = 16 ;
2826
+ } else {
2827
+ Bias = 0 ;
2828
+ Width = 8 ;
2829
+ }
2830
+ Field Fields[9 ] = {0 , 6 , 11 , 20 + Bias, 25 + Bias,
2831
+ 34 + Bias, 41 + Bias, 49 + Bias, 53 + Bias};
2832
+ Num = to_string (format_decimal (Sym, 5 ));
2833
+ Buc = to_string (format_decimal (Bucket, 3 )) + " :" ;
2834
+
2835
+ const auto Symbol = FirstSym + Sym;
2836
+ Value = to_string (format_hex_no_prefix (Symbol->st_value , Width));
2837
+ Size = to_string (format_decimal (Symbol->st_size , 5 ));
2838
+ unsigned char SymbolType = Symbol->getType ();
2839
+ if (Obj->getHeader ()->e_machine == ELF::EM_AMDGPU &&
2840
+ SymbolType >= ELF::STT_LOOS && SymbolType < ELF::STT_HIOS)
2841
+ Type = printEnum (SymbolType, makeArrayRef (AMDGPUSymbolTypes));
2842
+ else
2843
+ Type = printEnum (SymbolType, makeArrayRef (ElfSymbolTypes));
2844
+ unsigned Vis = Symbol->getVisibility ();
2845
+ Binding = printEnum (Symbol->getBinding (), makeArrayRef (ElfSymbolBindings));
2846
+ Visibility = printEnum (Vis, makeArrayRef (ElfSymbolVisibilities));
2847
+ Section = getSymbolSectionNdx (Obj, Symbol, FirstSym);
2848
+ Name = this ->dumper ()->getFullSymbolName (Symbol, StrTable, true );
2849
+ Fields[0 ].Str = Num;
2850
+ Fields[1 ].Str = Buc;
2851
+ Fields[2 ].Str = Value;
2852
+ Fields[3 ].Str = Size ;
2853
+ Fields[4 ].Str = Type;
2854
+ Fields[5 ].Str = Binding;
2855
+ Fields[6 ].Str = Visibility;
2856
+ Fields[7 ].Str = Section;
2857
+ Fields[8 ].Str = Name;
2858
+ for (auto &Entry : Fields)
2859
+ printField (Entry);
2860
+ OS << " \n " ;
2861
+ }
2815
2862
2816
2863
template <class ELFT > void GNUStyle<ELFT>::printSymbols(const ELFO *Obj) {
2864
+ if (opts::DynamicSymbols)
2865
+ return ;
2817
2866
this ->dumper ()->printSymbolsHelper (true );
2818
2867
this ->dumper ()->printSymbolsHelper (false );
2819
2868
}
2820
2869
2821
2870
template <class ELFT >
2822
2871
void GNUStyle<ELFT>::printDynamicSymbols(const ELFO *Obj) {
2823
- this ->dumper ()->printSymbolsHelper (true );
2872
+ if (this ->dumper ()->getDynamicStringTable ().size () == 0 )
2873
+ return ;
2874
+ auto StringTable = this ->dumper ()->getDynamicStringTable ();
2875
+ auto DynSyms = this ->dumper ()->dynamic_symbols ();
2876
+ auto GnuHash = this ->dumper ()->getGnuHashTable ();
2877
+ auto SysVHash = this ->dumper ()->getHashTable ();
2878
+
2879
+ // If no hash or .gnu.hash found, try using symbol table
2880
+ if (GnuHash == nullptr && SysVHash == nullptr )
2881
+ this ->dumper ()->printSymbolsHelper (true );
2882
+
2883
+ // Try printing .hash
2884
+ if (this ->dumper ()->getHashTable ()) {
2885
+ OS << " \n Symbol table of .hash for image:\n " ;
2886
+ if (ELFT::Is64Bits)
2887
+ OS << " Num Buc: Value Size Type Bind Vis Ndx Name" ;
2888
+ else
2889
+ OS << " Num Buc: Value Size Type Bind Vis Ndx Name" ;
2890
+ OS << " \n " ;
2891
+
2892
+ uint32_t NBuckets = SysVHash->nbucket ;
2893
+ uint32_t NChains = SysVHash->nchain ;
2894
+ auto Buckets = SysVHash->buckets ();
2895
+ auto Chains = SysVHash->chains ();
2896
+ for (uint32_t Buc = 0 ; Buc < NBuckets; Buc++) {
2897
+ if (Buckets[Buc] == ELF::STN_UNDEF)
2898
+ continue ;
2899
+ for (uint32_t Ch = Buckets[Buc]; Ch < NChains; Ch = Chains[Ch]) {
2900
+ if (Ch == ELF::STN_UNDEF)
2901
+ break ;
2902
+ printHashedSymbol (Obj, &DynSyms[0 ], Ch, StringTable, Buc);
2903
+ }
2904
+ }
2905
+ }
2906
+
2907
+ // Try printing .gnu.hash
2908
+ if (GnuHash) {
2909
+ OS << " \n Symbol table of .gnu.hash for image:\n " ;
2910
+ if (ELFT::Is64Bits)
2911
+ OS << " Num Buc: Value Size Type Bind Vis Ndx Name" ;
2912
+ else
2913
+ OS << " Num Buc: Value Size Type Bind Vis Ndx Name" ;
2914
+ OS << " \n " ;
2915
+ uint32_t NBuckets = GnuHash->nbuckets ;
2916
+ auto Buckets = GnuHash->buckets ();
2917
+ for (uint32_t Buc = 0 ; Buc < NBuckets; Buc++) {
2918
+ if (Buckets[Buc] == ELF::STN_UNDEF)
2919
+ continue ;
2920
+ uint32_t Index = Buckets[Buc];
2921
+ uint32_t GnuHashable = Index - GnuHash->symndx ;
2922
+ // Print whole chain
2923
+ while (true ) {
2924
+ printHashedSymbol (Obj, &DynSyms[0 ], Index++, StringTable, Buc);
2925
+ // Chain ends at symbol with stopper bit
2926
+ if ((GnuHash->values (DynSyms.size ())[GnuHashable++] & 1 ) == 1 )
2927
+ break ;
2928
+ }
2929
+ }
2930
+ }
2824
2931
}
2825
2932
2826
2933
static inline std::string printPhdrFlags (unsigned Flag) {
0 commit comments