Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Obtain source using debugging symbols

Is it possible to obtain the source of a linux shared library (.so) that was compiled with debugging information (gcc .. -g) ? Thank you for your time.

like image 511
nc3b Avatar asked Apr 03 '11 20:04

nc3b


People also ask

How do debugging symbols work?

A set of special characters generated when a program is compiled and containing information about the location of variables and functions in the resulting binary file, plus other service information. This data set can be used for step-by-step debugging of the program or examining third-party code.

How do I debug code in source?

To use source debugging, you must have your compiler or linker create symbol files (. pdb files) when the binaries are built. These symbol files show the debugger how the binary instructions correspond to the source lines. Also, the debugger must be able to access the actual source files.

What is debugging symbols in python?

A debug symbol is a special kind of symbol that attaches additional information to the symbol table of an object file, such as a shared library or an executable.

How do you compile a source file with debug information?

Generally, you want to compile your source files with the -g option to make your program more debuggable. The -g option causes the compilers to record debugging information (in stabs or Dwarf format) into the object files along with the code and data for the program.


1 Answers

The answer is: it depends - not only is the compile option -g necessary, but also the final created executable / shared libary may not be stripped during the build process.

Object files created with -g do contain a kind of sourcecode - just not sourcecode as you like it ...
If you use objdump -S on such a file, it'll intersperse the disassembly with sourcecode lines.

But what that shows is the actual compiled source - past any operation done by the preprocessor, and past any inlining done by the compiler.

That means you can get surprising output from it; if nothing else, its verbosity can look a bit like Cobol sources. Start with:

#include <algorithm>
#include <functional>
int main(int argc, char **argv)
{
    int array[] = { 1, 123, 1234, 12345, 123456 };
    std::sort(array, array + sizeof(array)/sizeof(*array), std::less<int>());
    return 0;
}

And run it through g++ -O8 -g -o t t.C and then objdump -S t. This will give you the output for main() similar to the following (what exactly you see of course depends on your compiler and/or library):


00000000004005e0 :
#include <algorithm>
#include <functional>

int main(int argc, char **argv)
{
  4005e0:       41 57                   push   %r15
                                  _ValueType<)
      __glibcxx_requires_valid_range(__first, __last);

      if (__first != __last)
        {
          std::__introsort_loop(__first, __last,
  4005e2:       ba 04 00 00 00          mov    $0x4,%edx
  4005e7:       41 56                   push   %r14
  4005e9:       41 55                   push   %r13
  4005eb:       41 54                   push   %r12
  4005ed:       41 bc 04 00 00 00       mov    $0x4,%r12d
  4005f3:       55                      push   %rbp
  4005f4:       53                      push   %rbx
  4005f5:       48 83 ec 38             sub    $0x38,%rsp
  4005f9:       4c 8d 74 24 10          lea    0x10(%rsp),%r14
        int array[] = { 1, 123, 1234, 12345, 123456 };
  4005fe:       c7 44 24 10 01 00 00    movl   $0x1,0x10(%rsp)
  400605:       00 
  400606:       c7 44 24 14 7b 00 00    movl   $0x7b,0x14(%rsp)
  40060d:       00 
  40060e:       c7 44 24 18 d2 04 00    movl   $0x4d2,0x18(%rsp)
  400615:       00 
  400616:       c7 44 24 1c 39 30 00    movl   $0x3039,0x1c(%rsp)
  40061d:       00 
  40061e:       4d 8d 7e 14             lea    0x14(%r14),%r15
  400622:       49 8d 6e 08             lea    0x8(%r14),%rbp
  400626:       4c 89 f7                mov    %r14,%rdi
  400629:       c7 44 24 20 40 e2 01    movl   $0x1e240,0x20(%rsp)
  400630:       00 
  400631:       c6 04 24 00             movb   $0x0,(%rsp)
  400635:       4c 89 fe                mov    %r15,%rsi
  400638:       e8 73 01 00 00          callq  4007b0 <_ZSt16__introsort_loopIPilSt4lessIiEEvT_S3_T0_T1_>
  40063d:       eb 01                   jmp    400640 <main+0x60>
  40063f:       90                      nop
      if (__first == __last) return;

      for (_RandomAccessIterator __i = __first + 1; __i != __last; ++__i)
        {
          typename iterator_traits<_RandomAccessIterator>::value_type
            __val = *__i;
  400640:       8b 5d fc                mov    -0x4(%rbp),%ebx
          if (__comp(__val, *__first))
  400643:       3b 5c 24 10             cmp    0x10(%rsp),%ebx
                                  _ValueType>)
      __glibcxx_requires_valid_range(__first, __last);

      if (__first != __last)
        {
          std::__introsort_loop(__first, __last,
  400647:       4b 8d 0c 34             lea    (%r12,%r14,1),%rcx

      for (_RandomAccessIterator __i = __first + 1; __i != __last; ++__i)
        {
          typename iterator_traits<_RandomAccessIterator>::value_type
            __val = *__i;
          if (__comp(__val, *__first))
  40064b:       7c 53                   jl     4006a0 <main+0xc0>
  template<typename _Tp>
    struct less : public binary_function<_Tp, _Tp, bool>
    {
      bool
      operator()(const _Tp& __x, const _Tp& __y) const
      { return __x < __y; }
  40064d:       8b 55 f8                mov    -0x8(%rbp),%edx
            {
              std::copy_backward(__first, __i, __i + 1);
              *__first = __val;
  400650:       48 8d 45 f8             lea    -0x8(%rbp),%rax
    __unguarded_linear_insert(_RandomAccessIterator __last, _Tp __val,
                              _Compare __comp)
    {
      _RandomAccessIterator __next = __last;
      --__next;
      while (__comp(__val, *__next))
  400654:       39 d3                   cmp    %edx,%ebx
  400656:       7c 0e                   jl     400666 <main+0x86>
  400658:       eb 1c                   jmp    400676 <main+0x96>
  40065a:       eb 04                   jmp    400660 <main+0x80>
  40065c:       90                      nop
  40065d:       90                      nop
  40065e:       90                      nop
  40065f:       90                      nop
  400660:       48 89 c1                mov    %rax,%rcx
  400663:       48 89 f0                mov    %rsi,%rax
        {
          *__last = *__next;
  400666:       89 11                   mov    %edx,(%rcx)
  400668:       8b 50 fc                mov    -0x4(%rax),%edx
          __last = __next;
          --__next;
  40066b:       48 8d 70 fc             lea    -0x4(%rax),%rsi
    __unguarded_linear_insert(_RandomAccessIterator __last, _Tp __val,
                              _Compare __comp)
    {
      _RandomAccessIterator __next = __last;
      --__next;
      while (__comp(__val, *__next))
  40066f:       39 d3                   cmp    %edx,%ebx
  400671:       7c ed                   jl     400660 <main+0x80>
  400673:       48 89 c1                mov    %rax,%rcx
        {
          *__last = *__next;
          __last = __next;
          --__next;
        }
      *__last = __val;
  400676:       89 19                   mov    %ebx,(%rcx)
  400678:       49 89 ed                mov    %rbp,%r13
  40067b:       48 83 c5 04             add    $0x4,%rbp
  40067f:       49 83 c4 04             add    $0x4,%r12
    __insertion_sort(_RandomAccessIterator __first,
                     _RandomAccessIterator __last, _Compare __comp)
    {
      if (__first == __last) return;

      for (_RandomAccessIterator __i = __first + 1; __i != __last; ++__i)
  400683:       4d 39 ef                cmp    %r13,%r15
  400686:       75 b8                   jne    400640 <main+0x60>
        std::sort(array, array + sizeof(array)/sizeof(*array), std::less<int>());

        return 0;
}
  400688:       48 83 c4 38             add    $0x38,%rsp
  40068c:       31 c0                   xor    %eax,%eax
  40068e:       5b                      pop    %rbx
  40068f:       5d                      pop    %rbp
  400690:       41 5c                   pop    %r12
  400692:       41 5d                   pop    %r13
  400694:       41 5e                   pop    %r14
  400696:       41 5f                   pop    %r15
  400698:       c3                      retq   
  400699:       eb 05                   jmp    4006a0 <main+0xc0>

How helpful the presence of this "sourcecode" would be is left as an exercise to the reader at this point ;-)

like image 166
FrankH. Avatar answered Sep 28 '22 14:09

FrankH.