Coverage for /Syzygy/agent/asan/shadow_marker.cc

CoverageLines executed / instrumented / missingexe / inst / missLanguageGroup
100.0%84840.C++source

Line-by-line coverage:

   1    :  // Copyright 2014 Google Inc. All Rights Reserved.
   2    :  //
   3    :  // Licensed under the Apache License, Version 2.0 (the "License");
   4    :  // you may not use this file except in compliance with the License.
   5    :  // You may obtain a copy of the License at
   6    :  //
   7    :  //     http://www.apache.org/licenses/LICENSE-2.0
   8    :  //
   9    :  // Unless required by applicable law or agreed to in writing, software
  10    :  // distributed under the License is distributed on an "AS IS" BASIS,
  11    :  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12    :  // See the License for the specific language governing permissions and
  13    :  // limitations under the License.
  14    :  
  15    :  #include "syzygy/agent/asan/shadow_marker.h"
  16    :  
  17    :  #include "base/logging.h"
  18    :  
  19    :  namespace agent {
  20    :  namespace asan {
  21    :  
  22    :  namespace {
  23    :  
  24    :  // Some constants related to the structure of shadow marker values.
  25    :  static const uint8 kActiveBit = 0x20;
  26    :  static const uint8 kBlockEndNestedBit = 0x01;
  27    :  static const uint8 kBlockStartDataMask = 0x7;
  28    :  static const uint8 kBlockStartNestedBit = 0x08;
  29    :  static const uint8 kFirstNibble = 0xF0;
  30    :  static const uint8 kRedzoneBit = 0x80;
  31    :  
  32    :  // ShadowMarker name generator. This maps an enumeration value to a name via
  33    :  // template specialization.
  34    :  template<size_t kIndex> struct ShadowMarkerNameGenerator {
  35    :    static const uintptr_t kName = 0;
  36    :  };
  37    :  #define SHADOW_MARKER_NAME_GENERATOR_MACRO(name, value)  \
  38    :      template<> struct ShadowMarkerNameGenerator<value> {  \
  39    :        static const char* kName;  \
  40    :      };  \
  41    :      const char* ShadowMarkerNameGenerator<value>::kName =  \
  42    :          _STRINGIZE(name);
  43    :  SHADOW_MARKER_GENERATOR(SHADOW_MARKER_NAME_GENERATOR_MACRO)
  44    :  #undef SHADOW_MARKER_NAME_GENERATOR_MACRO
  45    :  
  46    :  }  // namespace
  47    :  
  48    :  // This generates an array of shadow marker names, populating valid markers
  49    :  // with their names as defined by the template specialization above. Invalid
  50    :  // markers map to NULL as defined by the base template.
  51    :  #define ITERATE_2(F, base)  F(base) F(base + 1)
  52    :  #define ITERATE_4(F, base)  ITERATE_2(F, base) ITERATE_2(F, base + 2)
  53    :  #define ITERATE_8(F, base)  ITERATE_4(F, base) ITERATE_4(F, base + 4)
  54    :  #define ITERATE_16(F, base)  ITERATE_8(F, base) ITERATE_8(F, base + 8)
  55    :  #define ITERATE_32(F, base)  ITERATE_16(F, base) ITERATE_16(F, base + 16)
  56    :  #define ITERATE_64(F, base)  ITERATE_32(F, base) ITERATE_32(F, base + 32)
  57    :  #define ITERATE_128(F, base)  ITERATE_64(F, base) ITERATE_64(F, base + 64)
  58    :  #define ITERATE_256(F)  ITERATE_128(F, 0) ITERATE_128(F, 128)
  59    :  #define GET_SHADOW_MARKER_STRING_PTR(index)  \
  60    :      reinterpret_cast<const char*>(ShadowMarkerNameGenerator<index>::kName),
  61    :  const char* kShadowMarkerNames[256] = {
  62    :      ITERATE_256(GET_SHADOW_MARKER_STRING_PTR)
  63  E :  };
  64    :  #undef GET_SHADOW_MARKER_STRING_PTR
  65    :  #undef ITERATE_256
  66    :  #undef ITERATE_128
  67    :  #undef ITERATE_64
  68    :  #undef ITERATE_32
  69    :  #undef ITERATE_16
  70    :  #undef ITERATE_8
  71    :  #undef ITERATE_4
  72    :  #undef ITERATE_2
  73    :  
  74  E :  bool ShadowMarkerHelper::IsRedzone(ShadowMarkerValue marker) {
  75  E :    return (marker.value & kRedzoneBit) == kRedzoneBit;
  76  E :  }
  77    :  
  78  E :  bool ShadowMarkerHelper::IsActiveBlock(ShadowMarkerValue marker) {
  79    :    return marker.value == kHeapLeftPaddingMarker ||
  80    :        marker.value == kHeapRightPaddingMarker ||
  81    :        marker.value == kHeapFreedMarker ||
  82    :        IsActiveBlockStart(marker) ||
  83  E :        IsActiveBlockEnd(marker);
  84  E :  }
  85    :  
  86  E :  bool ShadowMarkerHelper::IsHistoricBlock(ShadowMarkerValue marker) {
  87    :  return marker.value == kHeapHistoricLeftPaddingMarker ||
  88    :        marker.value == kHeapHistoricRightPaddingMarker ||
  89    :        marker.value == kHeapHistoricFreedMarker ||
  90    :        IsHistoricBlockStart(marker) ||
  91  E :        IsHistoricBlockEnd(marker);
  92  E :  }
  93    :  
  94  E :  bool ShadowMarkerHelper::IsBlock(ShadowMarkerValue marker) {
  95  E :    return IsActiveBlock(marker) || IsHistoricBlock(marker);
  96  E :  }
  97    :  
  98  E :  bool ShadowMarkerHelper::IsActiveBlockStart(ShadowMarkerValue marker) {
  99  E :    return (marker.value & kFirstNibble) == kHeapBlockStartMarker0;
 100  E :  }
 101    :  
 102  E :  bool ShadowMarkerHelper::IsHistoricBlockStart(ShadowMarkerValue marker) {
 103  E :    return (marker.value & kFirstNibble) == kHeapHistoricBlockStartMarker0;
 104  E :  }
 105    :  
 106  E :  bool ShadowMarkerHelper::IsBlockStart(ShadowMarkerValue marker) {
 107    :    static const uint8 kMask = kFirstNibble ^ kActiveBit;
 108  E :    return (marker.value & kMask) == kHeapHistoricBlockStartMarker0;
 109  E :  }
 110    :  
 111  E :  bool ShadowMarkerHelper::IsNestedBlockStart(ShadowMarkerValue marker) {
 112  E :    if (!IsBlockStart(marker))
 113  E :      return false;
 114  E :    return (marker.value & kBlockStartNestedBit) == kBlockStartNestedBit;
 115  E :  }
 116    :  
 117  E :  uint8 ShadowMarkerHelper::GetBlockStartData(ShadowMarkerValue marker) {
 118  E :    return marker.value & kBlockStartDataMask;
 119  E :  }
 120    :  
 121  E :  bool ShadowMarkerHelper::IsActiveBlockEnd(ShadowMarkerValue marker) {
 122    :    return (marker.value & ~kBlockEndNestedBit) ==
 123  E :        kHeapBlockEndMarker;
 124  E :  }
 125    :  
 126  E :  bool ShadowMarkerHelper::IsHistoricBlockEnd(ShadowMarkerValue marker) {
 127    :    return (marker.value & ~kBlockEndNestedBit) ==
 128  E :        kHeapHistoricBlockEndMarker;
 129  E :  }
 130    :  
 131  E :  bool ShadowMarkerHelper::IsBlockEnd(ShadowMarkerValue marker) {
 132    :    // Block end markers have arbitrary values for the active bit
 133    :    // and the block end nested bit.
 134    :    static const uint8 kMask =
 135    :        static_cast<uint8>(~(kActiveBit | kBlockEndNestedBit));
 136  E :    return (marker.value & kMask) == kHeapHistoricBlockEndMarker;
 137  E :  }
 138    :  
 139  E :  bool ShadowMarkerHelper::IsNestedBlockEnd(ShadowMarkerValue marker) {
 140  E :    if (!IsBlockEnd(marker))
 141  E :      return false;
 142  E :    return (marker.value & kBlockEndNestedBit) == kBlockEndNestedBit;
 143  E :  }
 144    :  
 145  E :  bool ShadowMarkerHelper::IsHistoricLeftRedzone(ShadowMarkerValue marker) {
 146    :    return marker.value == kHeapHistoricLeftPaddingMarker ||
 147  E :        IsHistoricBlockStart(marker);
 148  E :  }
 149    :  
 150  E :  bool ShadowMarkerHelper::IsActiveLeftRedzone(ShadowMarkerValue marker) {
 151    :    return marker.value == kHeapLeftPaddingMarker ||
 152  E :        IsActiveBlockStart(marker);
 153  E :  }
 154    :  
 155  E :  bool ShadowMarkerHelper::IsLeftRedzone(ShadowMarkerValue marker) {
 156    :    return (marker.value & ~kActiveBit) == kHeapHistoricLeftPaddingMarker ||
 157  E :        IsBlockStart(marker);
 158  E :  }
 159    :  
 160  E :  bool ShadowMarkerHelper::IsHistoricRightRedzone(ShadowMarkerValue marker) {
 161    :    return marker.value == kHeapHistoricRightPaddingMarker ||
 162  E :        IsHistoricBlockEnd(marker);
 163  E :  }
 164    :  
 165  E :  bool ShadowMarkerHelper::IsActiveRightRedzone(ShadowMarkerValue marker) {
 166    :    return marker.value == kHeapRightPaddingMarker ||
 167  E :        IsActiveBlockEnd(marker);
 168  E :  }
 169    :  
 170  E :  bool ShadowMarkerHelper::IsRightRedzone(ShadowMarkerValue marker) {
 171    :    return (marker.value & ~kActiveBit) == kHeapHistoricRightPaddingMarker ||
 172  E :        IsBlockEnd(marker);
 173  E :  }
 174    :  
 175  E :  ShadowMarker ShadowMarkerHelper::ToHistoric(ShadowMarkerValue marker) {
 176  E :    DCHECK(IsActiveBlock(marker));
 177  E :    return static_cast<ShadowMarker>(marker.value & ~kActiveBit);
 178  E :  }
 179    :  
 180    :  ShadowMarker ShadowMarkerHelper::BuildBlockStart(
 181  E :      bool active, bool nested, uint8 data) {
 182  E :    DCHECK_EQ(0, data & ~kBlockStartDataMask);
 183  E :    uint8 marker = kHeapHistoricBlockStartMarker0;
 184  E :    if (active)
 185  E :      marker |= kActiveBit;
 186  E :    if (nested)
 187  E :      marker |= kBlockStartNestedBit;
 188  E :    marker |= data;
 189  E :    return static_cast<ShadowMarker>(marker);
 190  E :  }
 191    :  
 192  E :  ShadowMarker ShadowMarkerHelper::BuildBlockEnd(bool active, bool nested) {
 193  E :    uint8 marker = kHeapHistoricBlockEndMarker;
 194  E :    if (active)
 195  E :      marker |= kActiveBit;
 196  E :    if (nested)
 197  E :      marker |= kBlockEndNestedBit;
 198  E :    return static_cast<ShadowMarker>(marker);
 199  E :  }
 200    :  
 201    :  }  // namespace asan
 202    :  }  // namespace agent

Coverage information generated Thu Jan 14 17:40:38 2016.