--- old/src/hotspot/share/utilities/elfFile.cpp 2018-02-15 12:29:53.739953573 -0500 +++ new/src/hotspot/share/utilities/elfFile.cpp 2018-02-15 12:29:53.540953990 -0500 @@ -105,9 +105,9 @@ } } -ElfFile::ElfFile(const char* filepath) : +ElfFile::ElfFile(const char* filepath, bool load_debug_info) : _string_tables(NULL), _symbol_tables(NULL), _funcDesc_table(NULL), - _next(NULL), _status(NullDecoder::no_error), + _next(NULL), _status(NullDecoder::no_error), _debuginfo(NULL), _shdr_string_table(NULL), _file(NULL), _filepath(NULL) { memset(&_elfHdr, 0, sizeof(_elfHdr)); @@ -121,10 +121,22 @@ _status = parse_elf(filepath); - // we no longer need section header string table - if (_shdr_string_table != NULL) { - delete _shdr_string_table; - _shdr_string_table = NULL; + // See if we should try to load external debug info + if (_status == NullDecoder::no_debug_symbols && load_debug_info) { + log_debug(decoder)("No debug symbols in %s, trying external debuginfo", _filepath); + _debuginfo = load_debuginfo(); + } + + if (NullDecoder::is_error(_status)) { + // Not be able to decode, cleanup + cleanup_tables(); + } else { + log_debug(decoder)("%s contains debug symbols", _filepath); + // No longer need section header string table, which is not used for decoding + if (_shdr_string_table != NULL) { + delete _shdr_string_table; + _shdr_string_table = NULL; + } } } @@ -201,6 +213,9 @@ return NullDecoder::file_invalid; } + // test if the file contains debug symbols + NullDecoder::decoder_status stat = NullDecoder::no_debug_symbols; + // walk elf file's section headers, and load string tables Elf_Shdr shdr; if (!freader.set_position(_elfHdr.e_shoff)) { @@ -230,6 +245,10 @@ if (table == NULL) { return NullDecoder::out_of_memory; } + // see if we have debug symbols + if (shdr.sh_type == SHT_SYMTAB) { + stat = NullDecoder::no_error; + } add_symbol_table(table); } } @@ -255,7 +274,7 @@ return NullDecoder::out_of_memory; } #endif - return NullDecoder::no_error; + return stat; } int ElfFile::section_by_name(const char* name, Elf_Shdr& hdr) { @@ -288,6 +307,14 @@ } bool ElfFile::decode(address addr, char* buf, int buflen, int* offset) { + if (_debuginfo != NULL) { + return _debuginfo->decode(addr, buf, buflen, offset); + } else { + return decode_impl(addr, buf, buflen, offset); + } +} + +bool ElfFile::decode_impl(address addr, char* buf, int buflen, int* offset) { // something already went wrong, just give up if (NullDecoder::is_error(_status)) { return false;