OLD | NEW |
(Empty) | |
| 1 // Copyright (c) 2006, Google Inc. |
| 2 // All rights reserved. |
| 3 // |
| 4 // Redistribution and use in source and binary forms, with or without |
| 5 // modification, are permitted provided that the following conditions are |
| 6 // met: |
| 7 // |
| 8 // * Redistributions of source code must retain the above copyright |
| 9 // notice, this list of conditions and the following disclaimer. |
| 10 // * Redistributions in binary form must reproduce the above |
| 11 // copyright notice, this list of conditions and the following disclaimer |
| 12 // in the documentation and/or other materials provided with the |
| 13 // distribution. |
| 14 // * Neither the name of Google Inc. nor the names of its |
| 15 // contributors may be used to endorse or promote products derived from |
| 16 // this software without specific prior written permission. |
| 17 // |
| 18 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS |
| 19 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT |
| 20 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR |
| 21 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT |
| 22 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, |
| 23 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT |
| 24 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, |
| 25 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY |
| 26 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
| 27 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE |
| 28 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
| 29 // |
| 30 // Author: Satoru Takabayashi |
| 31 // |
| 32 // This library provides Symbolize() function that symbolizes program |
| 33 // counters to their corresponding symbol names on linux platforms. |
| 34 // This library has a minimal implementation of an ELF symbol table |
| 35 // reader (i.e. it doesn't depend on libelf, etc.). |
| 36 // |
| 37 // The algorithm used in Symbolize() is as follows. |
| 38 // |
| 39 // 1. Go through a list of maps in /proc/self/maps and find the map |
| 40 // containing the program counter. |
| 41 // |
| 42 // 2. Open the mapped file and find a regular symbol table inside. |
| 43 // Iterate over symbols in the symbol table and look for the symbol |
| 44 // containing the program counter. If such a symbol is found, |
| 45 // obtain the symbol name, and demangle the symbol if possible. |
| 46 // If the symbol isn't found in the regular symbol table (binary is |
| 47 // stripped), try the same thing with a dynamic symbol table. |
| 48 // |
| 49 // Note that Symbolize() is originally implemented to be used in |
| 50 // FailureSignalHandler() in base/google.cc. Hence it doesn't use |
| 51 // malloc() and other unsafe operations. It should be both |
| 52 // thread-safe and async-signal-safe. |
| 53 |
| 54 #ifndef BASE_SYMBOLIZE_H_ |
| 55 #define BASE_SYMBOLIZE_H_ |
| 56 |
| 57 #include "utilities.h" |
| 58 #include "config.h" |
| 59 #include "glog/logging.h" |
| 60 |
| 61 #ifdef HAVE_SYMBOLIZE |
| 62 |
| 63 #if defined(__ELF__) // defined by gcc on Linux |
| 64 #include <elf.h> |
| 65 #include <link.h> // For ElfW() macro. |
| 66 |
| 67 // If there is no ElfW macro, let's define it by ourself. |
| 68 #ifndef ElfW |
| 69 # if SIZEOF_VOID_P == 4 |
| 70 # define ElfW(type) Elf32_##type |
| 71 # elif SIZEOF_VOID_P == 8 |
| 72 # define ElfW(type) Elf64_##type |
| 73 # else |
| 74 # error "Unknown sizeof(void *)" |
| 75 # endif |
| 76 #endif |
| 77 |
| 78 _START_GOOGLE_NAMESPACE_ |
| 79 |
| 80 // Gets the section header for the given name, if it exists. Returns true on |
| 81 // success. Otherwise, returns false. |
| 82 bool GetSectionHeaderByName(int fd, const char *name, size_t name_len, |
| 83 ElfW(Shdr) *out); |
| 84 |
| 85 _END_GOOGLE_NAMESPACE_ |
| 86 |
| 87 #endif /* __ELF__ */ |
| 88 |
| 89 _START_GOOGLE_NAMESPACE_ |
| 90 |
| 91 // Installs a callback function, which will be called right before a symbol name |
| 92 // is printed. The callback is intended to be used for showing a file name and a |
| 93 // line number preceding a symbol name. |
| 94 // "fd" is a file descriptor of the object file containing the program |
| 95 // counter "pc". The callback function should write output to "out" |
| 96 // and return the size of the output written. On error, the callback |
| 97 // function should return -1. |
| 98 typedef int (*SymbolizeCallback)(int fd, void *pc, char *out, size_t out_size, |
| 99 uint64 relocation); |
| 100 void InstallSymbolizeCallback(SymbolizeCallback callback); |
| 101 |
| 102 _END_GOOGLE_NAMESPACE_ |
| 103 |
| 104 #endif |
| 105 |
| 106 _START_GOOGLE_NAMESPACE_ |
| 107 |
| 108 // Symbolizes a program counter. On success, returns true and write the |
| 109 // symbol name to "out". The symbol name is demangled if possible |
| 110 // (supports symbols generated by GCC 3.x or newer). Otherwise, |
| 111 // returns false. |
| 112 bool Symbolize(void *pc, char *out, int out_size); |
| 113 |
| 114 _END_GOOGLE_NAMESPACE_ |
| 115 |
| 116 #endif // BASE_SYMBOLIZE_H_ |
OLD | NEW |