source: rtems-tools/tester/covoar/CoverageMapBase.cc @ 99c90b3

5
Last change on this file since 99c90b3 was 99c90b3, checked in by Chris Johns <chrisj@…>, on 08/05/18 at 23:41:08

tester/covoar: Integrate DWARF function data.

Use DAWRF function data to create the executable coverage
maps. Integrate the existing objdump processing with this
data.

  • Refactor CoverageMapBase? to have the address ranges and address info as separate objects. Move the to address info into a vector. Add support for multiple address ranges.
  • DesiredSymbols? is only interested in function symbols.
  • ExecutableInfo? creates coverage maps from DWARF function data.
  • Add warning flags to the covoar build.
  • Varous C++11 refactoring.
  • Property mode set to 100644
File size: 8.6 KB
RevLine 
[100f517]1
2/*! @file CoverageMapBase.cc
3 *  @brief CoverageMapBase Implementation
4 *
[fb987e8]5 *  This file contains the implementation of the functions
[100f517]6 *  which provide a base level of functionality of a CoverageMap.
7 */
8
9#include <limits.h>
[bf8e59f]10
11#include <iostream>
12#include <iomanip>
[100f517]13
[99c90b3]14#include <rld.h>
15
[100f517]16#include "CoverageMapBase.h"
17
18namespace Coverage {
19
[99c90b3]20  AddressInfo::AddressInfo ()
21    : isStartOfInstruction (false),
22      wasExecuted (false),
23      isBranch (false),
24      isNop (false),
25      wasTaken (false),
26      wasNotTaken (false)
[100f517]27  {
[99c90b3]28  }
[100f517]29
[99c90b3]30  AddressRange::AddressRange ()
31    : lowAddress(0),
32      highAddress(0)
33  {
34  }
[100f517]35
[99c90b3]36  AddressRange::AddressRange (const std::string& name,
37                              uint32_t           lowAddress,
38                              uint32_t           highAddress)
39    : fileName (name),
40      lowAddress (lowAddress),
41      highAddress (highAddress)
42  {
43    info.resize( size( ) );
44  }
[100f517]45
[99c90b3]46  size_t AddressRange::size () const
47  {
48    return highAddress - lowAddress + 1;
49  }
[100f517]50
[99c90b3]51  bool AddressRange::inside (uint32_t address) const
52  {
53    return address >= lowAddress && address <= highAddress;
54  }
[100f517]55
[99c90b3]56  AddressInfo& AddressRange::get (uint32_t address)
57  {
58    if ( !inside( address ) )
59      throw rld::error( "address outside range", "AddressRange::get" );
60    size_t slot = address - lowAddress;
61    if (slot >= info.size ())
62      throw rld::error( "address slot not found", "AddressRange::get" );
63    return info[slot];
64  }
[100f517]65
[99c90b3]66  const AddressInfo& AddressRange::get (uint32_t address) const
67  {
68    if ( !inside( address ) )
69      throw rld::error( "address outside range", "AddressRange::get" );
70    size_t slot = address - lowAddress;
71    if (slot >= info.size ())
72      throw rld::error( "address slot not found", "AddressRange::get" );
73    return info[slot];
[100f517]74  }
75
[99c90b3]76  void AddressRange::dump (std::ostream& out, bool show_slots) const
[100f517]77  {
[99c90b3]78    out << std::hex << std::setfill('0')
79        << "Address range: low = " << std::setw(8) << lowAddress
80        << " high = " << std::setw(8) << highAddress
81        << std::endl;
82    if (show_slots) {
83      size_t slot = 0;
84      for (auto& i : info) {
85        out << std::hex << std::setfill('0')
86            << "0x" << std::setw(8) << slot++ + lowAddress
87            << "- isStartOfInstruction:"
88            << (char*) (i.isStartOfInstruction ? "yes" : "no")
89            << " wasExecuted:"
90            << (char*) (i.wasExecuted ? "yes" : "no")
91            << std::endl
92            << "           isBranch:"
93            << (char*) (i.isBranch ? "yes" : "no")
94            << " wasTaken:"
95            << (char*) (i.wasTaken ? "yes" : "no")
96            << " wasNotTaken:"
97            << (char*) (i.wasNotTaken ? "yes" : "no")
98            << std::dec << std::setfill(' ')
99            << std::endl;
100      }
101    }
[100f517]102  }
[fb987e8]103
[99c90b3]104  CoverageMapBase::CoverageMapBase(
105    const std::string& exefileName,
106    uint32_t           low,
107    uint32_t           high
108    ) : exefileName (exefileName)
[100f517]109  {
[99c90b3]110    Ranges.push_back( AddressRange( exefileName, low, high ) );
111  }
[100f517]112
[99c90b3]113  CoverageMapBase::~CoverageMapBase()
114  {
[100f517]115  }
[fb987e8]116
[99c90b3]117  void CoverageMapBase::Add( uint32_t low, uint32_t high )
[100f517]118  {
[99c90b3]119    Ranges.push_back( AddressRange( exefileName, low, high ) );
120  }
[100f517]121
[99c90b3]122  bool CoverageMapBase::validAddress( const uint32_t address ) const
123  {
124    for ( auto r : Ranges )
125      if (r.inside( address ))
[100f517]126        return true;
127    return false;
128  }
129
[bf8e59f]130  void CoverageMapBase::dump( void ) const
131  {
[99c90b3]132    std::cerr << "Coverage Map Contents:" << std::endl;
133    for (auto& r : Ranges)
134      r.dump( std::cerr );
135  }
136
137  uint32_t CoverageMapBase::getSize() const
138  {
139    size_t size = 0;
140    for (auto& r : Ranges)
141      size += r.size ();
142    return size;
[100f517]143  }
144
145  bool CoverageMapBase::getBeginningOfInstruction(
146    uint32_t  address,
147    uint32_t* beginning
148  ) const
149  {
[bf8e59f]150    bool         status = false;
151    uint32_t     start;
152    AddressRange range;
[100f517]153
[99c90b3]154    status = getRange( address, range );
[100f517]155    if ( status != true )
156      return status;
157
158    start = address;
159
160    while (start >= range.lowAddress ) {
[99c90b3]161      if (isStartOfInstruction( start - range.lowAddress )) {
[100f517]162        *beginning = start;
163        status = true;
164        break;
165      }
166      else
167        start--;
168    }
169
170    return status;
171  }
172
173  int32_t CoverageMapBase::getFirstLowAddress() const
174  {
[99c90b3]175    /*
176     * This is broken, do not trust it.
177     */
[bf8e59f]178    return Ranges.front().lowAddress;
[100f517]179  }
180
[99c90b3]181  bool CoverageMapBase::getRange( uint32_t address, AddressRange& range ) const
[100f517]182  {
[bf8e59f]183    for ( auto r : Ranges ) {
[99c90b3]184      if (r.inside( address )) {
185        range.lowAddress = r.lowAddress;
186        range.highAddress = r.highAddress;
187        range.info = r.info;
[100f517]188        return true;
189      }
190    }
191    return false;
[99c90b3]192  }
[100f517]193
[99c90b3]194  AddressInfo& CoverageMapBase::getInfo( uint32_t address )
195  {
196    for ( auto& r : Ranges )
197      if (r.inside( address ))
198        return r.get( address );
199    throw rld::error( "address out of bounds", "CoverageMapBase::getInfo" );
[100f517]200  }
201
[99c90b3]202  const AddressInfo& CoverageMapBase::getInfo( uint32_t address ) const
[100f517]203  {
[99c90b3]204    for ( auto& r : Ranges )
205      if (r.inside( address ))
206        return r.get( address );
207    throw rld::error( "address out of bounds", "CoverageMapBase::getInfo" );
[100f517]208  }
209
210  void CoverageMapBase::setIsStartOfInstruction(
211    uint32_t    address
212  )
213  {
[99c90b3]214    if ( validAddress( address ) )
215      getInfo( address ).isStartOfInstruction = true;
[100f517]216  }
217
218  bool CoverageMapBase::isStartOfInstruction( uint32_t address ) const
219  {
[99c90b3]220    if ( !validAddress( address ) )
[100f517]221      return false;
[99c90b3]222    return getInfo( address ).isStartOfInstruction;
[100f517]223  }
224
225  void CoverageMapBase::setWasExecuted( uint32_t address )
226  {
[99c90b3]227    if ( validAddress( address ) )
228      getInfo( address ).wasExecuted += 1;
[100f517]229  }
230
231  void CoverageMapBase::sumWasExecuted( uint32_t address, uint32_t addition)
232  {
[99c90b3]233    if ( validAddress( address ) )
234      getInfo( address ).wasExecuted += addition;
[100f517]235  }
236
237  bool CoverageMapBase::wasExecuted( uint32_t address ) const
238  {
[99c90b3]239    bool result = false;
240    if ( validAddress( address ) && (getInfo( address ).wasExecuted > 0))
241      result = true;
[100f517]242    return result;
243  }
244
245  uint32_t CoverageMapBase::getWasExecuted( uint32_t address ) const
246  {
[99c90b3]247    if ( !validAddress( address ) )
[100f517]248      return 0;
[99c90b3]249    return getInfo( address ).wasExecuted;
[100f517]250  }
251
252  void CoverageMapBase::setIsBranch(
253    uint32_t    address
254  )
255  {
[99c90b3]256    if ( validAddress( address ) )
257      getInfo( address ).isBranch = true;
[100f517]258  }
259
260  bool CoverageMapBase::isNop( uint32_t address ) const
261  {
[99c90b3]262    if ( !validAddress( address ) )
[100f517]263      return false;
[99c90b3]264    return getInfo( address ).isNop;
[100f517]265  }
266
267  void CoverageMapBase::setIsNop(
268    uint32_t    address
269  )
270  {
[99c90b3]271    if ( !validAddress( address ) )
[100f517]272      return;
[99c90b3]273    getInfo( address ).isNop = true;
[100f517]274  }
275
276  bool CoverageMapBase::isBranch( uint32_t address ) const
277  {
[99c90b3]278    if ( !validAddress( address ) )
[100f517]279      return false;
[99c90b3]280    return getInfo( address ).isBranch;
[100f517]281  }
282
283  void CoverageMapBase::setWasTaken(
284    uint32_t    address
285  )
286  {
[99c90b3]287    if ( !validAddress( address ) )
[100f517]288      return;
[99c90b3]289    getInfo( address ).wasTaken += 1;
[100f517]290  }
291
292  void CoverageMapBase::setWasNotTaken(
293    uint32_t    address
294  )
295  {
[99c90b3]296    if ( !validAddress( address ) )
[100f517]297      return;
[99c90b3]298    getInfo( address ).wasNotTaken += 1;
[100f517]299  }
300
301  bool CoverageMapBase::wasAlwaysTaken( uint32_t address ) const
302  {
[99c90b3]303    if ( !validAddress( address ) )
[100f517]304      return false;
[99c90b3]305    const AddressInfo& info = getInfo( address );
306    return info.wasTaken && !info.wasNotTaken;
[100f517]307  }
308
309  bool CoverageMapBase::wasNeverTaken( uint32_t address ) const
310  {
[99c90b3]311    if ( !validAddress( address ) )
[100f517]312      return false;
[99c90b3]313    const AddressInfo& info = getInfo( address );
314    return !info.wasTaken && info.wasNotTaken;
[100f517]315  }
316
317  bool CoverageMapBase::wasNotTaken( uint32_t address ) const
318  {
[99c90b3]319    bool result = true;
320    if ( !validAddress( address ) )
321      result = false;
322    else if ( getInfo( address ).wasNotTaken <= 0 )
323      result = false;
324    return result;
[100f517]325  }
326
327  void CoverageMapBase::sumWasNotTaken( uint32_t address, uint32_t addition)
328  {
[99c90b3]329    if ( validAddress( address ) )
330      getInfo( address ).wasNotTaken += addition;
[100f517]331  }
332
333  uint32_t CoverageMapBase::getWasNotTaken( uint32_t address ) const
334  {
[99c90b3]335    if ( !validAddress( address ) )
[100f517]336      return 0;
[99c90b3]337    return getInfo( address ).wasNotTaken;
[100f517]338  }
339
340  bool CoverageMapBase::wasTaken( uint32_t address ) const
341  {
[99c90b3]342    bool result = true;
343    if ( !validAddress( address ) )
[100f517]344      result = false;
[99c90b3]345    else if ( getInfo( address ).wasTaken <= 0 )
[100f517]346      result = false;
347    return result;
348  }
349
350  void CoverageMapBase::sumWasTaken( uint32_t address, uint32_t addition)
351  {
[99c90b3]352    if ( !validAddress( address ) )
[100f517]353      return;
[99c90b3]354    getInfo( address ).wasTaken += addition;
[100f517]355  }
356
357  uint32_t CoverageMapBase::getWasTaken( uint32_t address ) const
358  {
[99c90b3]359    if ( !validAddress( address ) )
[100f517]360      return 0;
[99c90b3]361    return getInfo( address ).wasTaken;
[100f517]362  }
363}
Note: See TracBrowser for help on using the repository browser.