LCOV - code coverage report
Current view: directory - toolkit/crashreporter/google-breakpad/src/common - dwarf_line_to_module.h (source / functions) Found Hit Coverage
Test: app.info Lines: 3 3 100.0 %
Date: 2012-06-02 Functions: 3 2 66.7 %

       1                 : // -*- mode: c++ -*-
       2                 : 
       3                 : // Copyright (c) 2010 Google Inc.
       4                 : // All rights reserved.
       5                 : //
       6                 : // Redistribution and use in source and binary forms, with or without
       7                 : // modification, are permitted provided that the following conditions are
       8                 : // met:
       9                 : //
      10                 : //     * Redistributions of source code must retain the above copyright
      11                 : // notice, this list of conditions and the following disclaimer.
      12                 : //     * Redistributions in binary form must reproduce the above
      13                 : // copyright notice, this list of conditions and the following disclaimer
      14                 : // in the documentation and/or other materials provided with the
      15                 : // distribution.
      16                 : //     * Neither the name of Google Inc. nor the names of its
      17                 : // contributors may be used to endorse or promote products derived from
      18                 : // this software without specific prior written permission.
      19                 : //
      20                 : // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
      21                 : // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
      22                 : // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
      23                 : // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
      24                 : // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
      25                 : // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
      26                 : // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
      27                 : // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
      28                 : // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
      29                 : // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
      30                 : // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
      31                 : 
      32                 : // Original author: Jim Blandy <jimb@mozilla.com> <jimb@red-bean.com>
      33                 : 
      34                 : // The DwarfLineToModule class accepts line number information from a
      35                 : // DWARF parser and adds it to a google_breakpad::Module. The Module
      36                 : // can write that data out as a Breakpad symbol file.
      37                 : 
      38                 : #ifndef COMMON_LINUX_DWARF_LINE_TO_MODULE_H
      39                 : #define COMMON_LINUX_DWARF_LINE_TO_MODULE_H
      40                 : 
      41                 : #include "common/module.h"
      42                 : #include "common/dwarf/dwarf2reader.h"
      43                 : 
      44                 : namespace google_breakpad {
      45                 : 
      46                 : // A class for producing a vector of google_breakpad::Module::Line
      47                 : // instances from parsed DWARF line number data.  
      48                 : //
      49                 : // An instance of this class can be provided as a handler to a
      50                 : // dwarf2reader::LineInfo DWARF line number information parser. The
      51                 : // handler accepts source location information from the parser and
      52                 : // uses it to produce a vector of google_breakpad::Module::Line
      53                 : // objects, referring to google_breakpad::Module::File objects added
      54                 : // to a particular google_breakpad::Module.
      55                 : //
      56                 : // GNU toolchain omitted sections support:
      57                 : // ======================================
      58                 : //
      59                 : // Given the right options, the GNU toolchain will omit unreferenced
      60                 : // functions from the final executable. Unfortunately, when it does so, it
      61                 : // does not remove the associated portions of the DWARF line number
      62                 : // program; instead, it gives the DW_LNE_set_address instructions referring
      63                 : // to the now-deleted code addresses of zero. Given this input, the DWARF
      64                 : // line parser will call AddLine with a series of lines starting at address
      65                 : // zero. For example, here is the output from 'readelf -wl' for a program
      66                 : // with four functions, the first three of which have been omitted:
      67                 : //
      68                 : //   Line Number Statements:
      69                 : //    Extended opcode 2: set Address to 0x0
      70                 : //    Advance Line by 14 to 15
      71                 : //    Copy
      72                 : //    Special opcode 48: advance Address by 3 to 0x3 and Line by 1 to 16
      73                 : //    Special opcode 119: advance Address by 8 to 0xb and Line by 2 to 18
      74                 : //    Advance PC by 2 to 0xd
      75                 : //    Extended opcode 1: End of Sequence
      76                 : // 
      77                 : //    Extended opcode 2: set Address to 0x0
      78                 : //    Advance Line by 14 to 15
      79                 : //    Copy
      80                 : //    Special opcode 48: advance Address by 3 to 0x3 and Line by 1 to 16
      81                 : //    Special opcode 119: advance Address by 8 to 0xb and Line by 2 to 18
      82                 : //    Advance PC by 2 to 0xd
      83                 : //    Extended opcode 1: End of Sequence
      84                 : // 
      85                 : //    Extended opcode 2: set Address to 0x0
      86                 : //    Advance Line by 19 to 20
      87                 : //    Copy
      88                 : //    Special opcode 48: advance Address by 3 to 0x3 and Line by 1 to 21
      89                 : //    Special opcode 76: advance Address by 5 to 0x8 and Line by 1 to 22
      90                 : //    Advance PC by 2 to 0xa
      91                 : //    Extended opcode 1: End of Sequence
      92                 : // 
      93                 : //    Extended opcode 2: set Address to 0x80483a4
      94                 : //    Advance Line by 23 to 24
      95                 : //    Copy
      96                 : //    Special opcode 202: advance Address by 14 to 0x80483b2 and Line by 1 to 25
      97                 : //    Special opcode 76: advance Address by 5 to 0x80483b7 and Line by 1 to 26
      98                 : //    Advance PC by 6 to 0x80483bd
      99                 : //    Extended opcode 1: End of Sequence
     100                 : //
     101                 : // Instead of collecting runs of lines describing code that is not there,
     102                 : // we try to recognize and drop them. Since the linker doesn't explicitly
     103                 : // distinguish references to dropped sections from genuine references to
     104                 : // code at address zero, we must use a heuristic. We have chosen:
     105                 : //
     106                 : // - If a line starts at address zero, omit it. (On the platforms
     107                 : //   breakpad targets, it is extremely unlikely that there will be code
     108                 : //   at address zero.)
     109                 : //
     110                 : // - If a line starts immediately after an omitted line, omit it too.
     111                 : class DwarfLineToModule: public dwarf2reader::LineInfoHandler {
     112                 :  public:
     113                 :   // As the DWARF line info parser passes us line records, add source
     114                 :   // files to MODULE, and add all lines to the end of LINES. LINES
     115                 :   // need not be empty. If the parser hands us a zero-length line, we
     116                 :   // omit it. If the parser hands us a line that extends beyond the
     117                 :   // end of the address space, we clip it. It's up to our client to
     118                 :   // sort out which lines belong to which functions; we don't add them
     119                 :   // to any particular function in MODULE ourselves.
     120            4723 :   DwarfLineToModule(Module *module, vector<Module::Line> *lines)
     121                 :       : module_(module),
     122                 :         lines_(lines),
     123                 :         highest_file_number_(-1),
     124                 :         omitted_line_end_(0),
     125                 :         warned_bad_file_number_(false),
     126            4723 :         warned_bad_directory_number_(false) { }
     127                 :   
     128            4723 :   ~DwarfLineToModule() { }
     129                 : 
     130                 :   void DefineDir(const std::string &name, uint32 dir_num);
     131                 :   void DefineFile(const std::string &name, int32 file_num,
     132                 :                   uint32 dir_num, uint64 mod_time,
     133                 :                   uint64 length);
     134                 :   void AddLine(uint64 address, uint64 length,
     135                 :                uint32 file_num, uint32 line_num, uint32 column_num);
     136                 : 
     137                 :  private:
     138                 : 
     139                 :   typedef std::map<uint32, std::string> DirectoryTable;
     140                 :   typedef std::map<uint32, Module::File *> FileTable;
     141                 : 
     142                 :   // The module we're contributing debugging info to. Owned by our
     143                 :   // client.
     144                 :   Module *module_;
     145                 : 
     146                 :   // The vector of lines we're accumulating. Owned by our client.
     147                 :   //
     148                 :   // In a Module, as in a breakpad symbol file, lines belong to
     149                 :   // specific functions, but DWARF simply assigns lines to addresses;
     150                 :   // one must infer the line/function relationship using the
     151                 :   // functions' beginning and ending addresses. So we can't add these
     152                 :   // to the appropriate function from module_ until we've read the
     153                 :   // function info as well. Instead, we accumulate lines here, and let
     154                 :   // whoever constructed this sort it all out.
     155                 :   vector<Module::Line> *lines_;
     156                 : 
     157                 :   // A table mapping directory numbers to paths.
     158                 :   DirectoryTable directories_;
     159                 : 
     160                 :   // A table mapping file numbers to Module::File pointers.
     161                 :   FileTable files_;
     162                 : 
     163                 :   // The highest file number we've seen so far, or -1 if we've seen
     164                 :   // none.  Used for dynamically defined file numbers.
     165                 :   int32 highest_file_number_;
     166                 :   
     167                 :   // This is the ending address of the last line we omitted, or zero if we
     168                 :   // didn't omit the previous line. It is zero before we have received any
     169                 :   // AddLine calls.
     170                 :   uint64 omitted_line_end_;
     171                 : 
     172                 :   // True if we've warned about:
     173                 :   bool warned_bad_file_number_; // bad file numbers
     174                 :   bool warned_bad_directory_number_; // bad directory numbers
     175                 : };
     176                 : 
     177                 : } // namespace google_breakpad
     178                 : 
     179                 : #endif // COMMON_LINUX_DWARF_LINE_TO_MODULE_H

Generated by: LCOV version 1.7