Coverage for /Syzygy/common/asan_parameters.cc

CoverageLines executed / instrumented / missingexe / inst / missLanguageGroup
92.9%1821960.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/common/asan_parameters.h"
  16    :  
  17    :  #include <windows.h>
  18    :  
  19    :  #include <algorithm>
  20    :  
  21    :  #include "base/command_line.h"
  22    :  #include "base/logging.h"
  23    :  #include "base/strings/string_number_conversions.h"
  24    :  #include "base/strings/string_tokenizer.h"
  25    :  #include "base/strings/string_util.h"
  26    :  #include "base/strings/stringprintf.h"
  27    :  #include "base/strings/utf_string_conversions.h"
  28    :  
  29    :  namespace common {
  30    :  
  31    :  namespace {
  32    :  
  33    :  using base::CommandLine;
  34    :  
  35    :  // Trinary return values used to indicate if a flag was updated or not.
  36    :  enum FlagResult {
  37    :    kFlagNotPresent,
  38    :    kFlagSet,
  39    :    kFlagError
  40    :  };
  41    :  
  42    :  // Templated utility class for parsing parameter values from a command-line.
  43    :  // @tparam Converter Defines the types and parsing.
  44    :  template<typename Parser>
  45    :  struct UpdateValueFromCommandLine {
  46    :    // Try to update the value of a variable from a command-line.
  47    :    // @param cmd_line The command line who might contain a given parameter.
  48    :    // @param param_name The parameter that we want to read.
  49    :    // @param value Will receive the value of the parameter if it's present.
  50    :    // @returns kFlagNotPresent if the flag was not present and left at its
  51    :    //     default; kFlagSet if the flag was present, valid and modified; or
  52    :    //     kFlagError if the flag was present but invalid. Logs an error on
  53    :    //     failure, and an info message on successful parsing.
  54    :    static FlagResult Do(const base::CommandLine& cmd_line,
  55    :                         const std::string& param_name,
  56  E :                         typename Parser::ValueType* value) {
  57  E :      DCHECK_NE(reinterpret_cast<Parser::ValueType*>(NULL), value);
  58    :  
  59  E :      if (!cmd_line.HasSwitch(param_name))
  60  E :        return kFlagNotPresent;
  61    :  
  62  E :      std::string value_str = cmd_line.GetSwitchValueASCII(param_name);
  63  E :      Parser::IntermediateType new_value = 0;
  64  E :      if (!Parser::Convert(value_str, &new_value)) {
  65  E :        LOG(ERROR) << "Failed to parse \"" << param_name << "\" value of \""
  66    :                   << value_str << "\".";
  67  E :        return kFlagError;
  68    :      }
  69    :  
  70  E :      *value = new_value;
  71  E :      VLOG(1) << "Set \"" << param_name << "\" to " << *value << ".";
  72  E :      return kFlagSet;
  73  E :    }
  74    :  };
  75    :  
  76    :  // Parses a uint32_t value from a string provided on the command-line.
  77    :  struct Uint32Parser {
  78    :    typedef size_t IntermediateType;
  79    :    typedef uint32_t ValueType;
  80  E :    static bool Convert(const std::string& value_str, IntermediateType* value) {
  81  E :      return base::StringToSizeT(value_str, value);
  82  E :    }
  83    :  };
  84    :  typedef UpdateValueFromCommandLine<Uint32Parser> UpdateUint32FromCommandLine;
  85    :  
  86    :  // Parses a float value from a string provided on the command-line.
  87    :  struct FloatParser {
  88    :    typedef double IntermediateType;
  89    :    typedef float ValueType;
  90  E :    static bool Convert(const std::string& value_str, IntermediateType* value) {
  91  E :      return base::StringToDouble(value_str, value);
  92  E :    }
  93    :  };
  94    :  typedef UpdateValueFromCommandLine<FloatParser> UpdateFloatFromCommandLine;
  95    :  
  96    :  // Try to update the value of an array of ignored stack ids from a command-line.
  97    :  // We expect the values to be in hexadecimal format and separated by a
  98    :  // semi-colon.
  99    :  // @param cmd_line The command line to parse.
 100    :  // @param param_name The parameter that we want to read.
 101    :  // @param values Will receive the set of parsed values.
 102    :  // @returns true on success, false otherwise.
 103    :  bool ReadIgnoredStackIdsFromCommandLine(const base::CommandLine& cmd_line,
 104    :                                          const std::string& param_name,
 105  E :                                          std::set<AsanStackId>* values) {
 106  E :    DCHECK(values != NULL);
 107  E :    if (!cmd_line.HasSwitch(param_name))
 108  E :      return true;
 109    :  
 110  E :    std::string value_str = cmd_line.GetSwitchValueASCII(param_name);
 111  E :    base::StringTokenizer string_tokenizer(value_str, ";");
 112  E :    while (string_tokenizer.GetNext()) {
 113  E :      int64_t new_value = 0;
 114  E :      if (!base::HexStringToInt64(string_tokenizer.token(), &new_value)) {
 115  E :        LOG(ERROR) << "Failed to parse \"" << param_name << "\" value of \""
 116    :                   << string_tokenizer.token() << "\".";
 117  E :        return false;
 118    :      }
 119    :  
 120  E :      VLOG(1) << "Parsed \"" << param_name << "\" value of "
 121    :              << base::StringPrintf("0x%016llX", new_value) << ".";
 122  E :      values->insert(static_cast<AsanStackId>(new_value));
 123  E :    }
 124    :  
 125  E :    return true;
 126  E :  }
 127    :  
 128    :  }  // namespace
 129    :  
 130    :  // SYZYgy Asan Runtime Options.
 131    :  const char kAsanParametersSectionName[] = ".syzyaro";
 132    :  const uint32_t kAsanParametersSectionCharacteristics =
 133    :      IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_MEM_READ;
 134    :  
 135    :  // Default values of HeapProxy parameters
 136    :  const uint32_t kDefaultQuarantineSize = 16 * 1024 * 1024;
 137    :  const uint32_t kDefaultQuarantineBlockSize = 4 * 1024 * 1024;
 138    :  const uint32_t kDefaultTrailerPaddingSize = 0;
 139    :  const float kDefaultAllocationGuardRate = 1.0;
 140    :  
 141    :  // Default values of StackCaptureCache parameters.
 142    :  const uint32_t kDefaultReportingPeriod = 0;
 143    :  const uint32_t kDefaultBottomFramesToSkip = 0;
 144    :  
 145    :  // Default values of StackCapture parameters.
 146    :  // From http://msdn.microsoft.com/en-us/library/bb204633.aspx,
 147    :  // The maximum number of frames which CaptureStackBackTrace can be asked
 148    :  // to traverse must be less than 63, so this can't be any larger than 62.
 149    :  const uint32_t kDefaultMaxNumFrames = 62;
 150    :  
 151    :  // Default values of AsanRuntime parameters.
 152    :  const bool kDefaultExitOnFailure = false;
 153    :  const bool kDefaultCheckHeapOnFailure = true;
 154    :  const bool kDefaultDisableBreakpadReporting = false;
 155    :  const bool kDefaultFeatureRandomization = false;
 156    :  const bool kDefaultReportInvalidAccesses = false;
 157    :  
 158    :  // Default values of AsanLogger parameters.
 159    :  const bool kDefaultMiniDumpOnFailure = false;
 160    :  const bool kDefaultLogAsText = true;
 161    :  
 162    :  // Default values of ZebraBlockHeap parameters.
 163    :  const uint32_t kDefaultZebraBlockHeapSize = 16 * 1024 * 1024;
 164    :  const float kDefaultZebraBlockHeapQuarantineRatio = 0.25f;
 165    :  
 166    :  // Default values of the BlockHeapManager parameters.
 167    :  const bool kDefaultEnableRateTargetedHeaps = true;
 168    :  const bool kDefaultEnableZebraBlockHeap = false;
 169    :  const bool kDefaultEnableAllocationFilter = false;
 170    :  const float kDefaultQuarantineFloodFillRate = 0.5f;
 171    :  const bool kDefaultPreventDuplicateCorruptionCrashes = false;
 172    :  
 173    :  // Default values of LargeBlockHeap parameters.
 174    :  extern const bool kDefaultEnableLargeBlockHeap = true;
 175    :  // We want to maintain an allocation overhead of around 45%, which has been
 176    :  // our historic average for Chrome. Overhead in this heap is 2 pages, so want
 177    :  // 2 / 0.45 = 4.44 < 5 page minimum.
 178    :  extern const size_t kDefaultLargeAllocationThreshold = 5 * 4096;
 179    :  
 180    :  const char kSyzyAsanOptionsEnvVar[] = "SYZYGY_ASAN_OPTIONS";
 181    :  
 182    :  // String names of HeapProxy parameters.
 183    :  const char kParamQuarantineSize[] = "quarantine_size";
 184    :  const char kParamQuarantineBlockSize[] = "quarantine_block_size";
 185    :  const char kParamTrailerPaddingSize[] = "trailer_padding_size";
 186    :  extern const char kParamAllocationGuardRate[] = "allocation_guard_rate";
 187    :  
 188    :  // String names of StackCaptureCache parameters.
 189    :  const char kParamReportingPeriod[] = "compression_reporting_period";
 190    :  const char kParamBottomFramesToSkip[] = "bottom_frames_to_skip";
 191    :  
 192    :  // String names of StackCapture parameters.
 193    :  const char kParamMaxNumFrames[] = "max_num_frames";
 194    :  
 195    :  // String names of AsanRuntime parameters.
 196    :  const char kParamIgnoredStackIds[] = "ignored_stack_ids";
 197    :  const char kParamExitOnFailure[] = "exit_on_failure";
 198    :  const char kParamNoCheckHeapOnFailure[] = "no_check_heap_on_failure";
 199    :  const char kParamDisableBreakpadReporting[]  = "disable_breakpad";
 200    :  const char kParamFeatureRandomization[] = "feature_randomization";
 201    :  const char kParamReportInvalidAccesses[] = "report_invalid_accesses";
 202    :  
 203    :  // String names of AsanLogger parameters.
 204    :  const char kParamMiniDumpOnFailure[] = "minidump_on_failure";
 205    :  const char kParamNoLogAsText[] = "no_log_as_text";
 206    :  
 207    :  // String names of ZebraBlockHeap parameters.
 208    :  const char kParamZebraBlockHeapSize[] = "zebra_block_heap_size";
 209    :  const char kParamZebraBlockHeapQuarantineRatio[] =
 210    :      "zebra_block_heap_quarantine_ratio";
 211    :  
 212    :  // String names of BlockHeapManager parameters.
 213    :  const char kParamDisableCtMalloc[] = "disable_ctmalloc";
 214    :  const char kParamEnableZebraBlockHeap[] = "enable_zebra_block_heap";
 215    :  const char kParamEnableAllocationFilter[] = "enable_allocation_filter";
 216    :  const char kParamQuarantineFloodFillRate[] = "quarantine_flood_fill_rate";
 217    :  const char kParamPreventDuplicateCorruptionCrashes[] =
 218    :      "prevent_duplicate_corruption_crashes";
 219    :  
 220    :  // String names of LargeBlockHeap parameters.
 221    :  const char kParamDisableLargeBlockHeap[] = "disable_large_block_heap";
 222    :  const char kParamLargeAllocationThreshold[] = "large_allocation_threshold";
 223    :  
 224  E :  InflatedAsanParameters::InflatedAsanParameters() {
 225    :    // Clear the AsanParameters portion of ourselves.
 226  E :    ::memset(this, 0, sizeof(AsanParameters));
 227  E :  }
 228    :  
 229    :  FlatAsanParameters::FlatAsanParameters(
 230  E :      const InflatedAsanParameters& asan_parameters) {
 231  E :    bool have_ignored_stack_ids = !asan_parameters.ignored_stack_ids_set.empty();
 232    :  
 233  E :    size_t struct_size = sizeof(AsanParameters);
 234  E :    size_t ignored_stack_ids_size = 0;
 235  E :    if (have_ignored_stack_ids) {
 236  E :      ignored_stack_ids_size = sizeof(AsanStackId) *
 237    :          (asan_parameters.ignored_stack_ids_set.size() + 1);
 238    :    }
 239  E :    size_t data_size = struct_size + ignored_stack_ids_size;
 240    :  
 241  E :    data_.resize(data_size, 0);
 242  E :    ::memcpy(data_.data(), &asan_parameters, struct_size);
 243    :  
 244    :    // Get typed pointers to the underlying data.
 245  E :    AsanParameters* params = reinterpret_cast<AsanParameters*>(data_.data());
 246  E :    AsanStackId* ignored_stack_ids = NULL;
 247  E :    if (have_ignored_stack_ids) {
 248  E :      ignored_stack_ids = reinterpret_cast<AsanStackId*>(
 249    :          data_.data() + struct_size);
 250    :    }
 251    :  
 252    :    // Patch things up.
 253    :    // The structure size is not supposed to be too large to fit into uint32_t.
 254  E :    params->size = static_cast<uint32_t>(data_size);
 255  E :    params->ignored_stack_ids = ignored_stack_ids;
 256    :  
 257  E :    if (have_ignored_stack_ids) {
 258    :      // Fill in the ignored stack IDs.
 259    :      std::set<AsanStackId>::const_iterator id_it =
 260  E :          asan_parameters.ignored_stack_ids_set.begin();
 261  E :      for (; id_it != asan_parameters.ignored_stack_ids_set.end(); ++id_it)
 262  E :        *(ignored_stack_ids++) = *id_it;
 263  E :      *(ignored_stack_ids++) = 0;  // Terminating NULL.
 264  E :      DCHECK_EQ(data_.data() + data_size,
 265  E :                reinterpret_cast<uint8_t*>(ignored_stack_ids));
 266    :    }
 267  E :  }
 268    :  
 269  E :  void SetDefaultAsanParameters(AsanParameters* asan_parameters) {
 270  E :    DCHECK_NE(reinterpret_cast<AsanParameters*>(NULL), asan_parameters);
 271    :  
 272  E :    ::memset(asan_parameters, 0, sizeof(AsanParameters));
 273    :  
 274  E :    asan_parameters->size = sizeof(AsanParameters);
 275  E :    asan_parameters->version = kAsanParametersVersion;
 276  E :    asan_parameters->quarantine_size = kDefaultQuarantineSize;
 277  E :    asan_parameters->reporting_period = kDefaultReportingPeriod;
 278  E :    asan_parameters->bottom_frames_to_skip = kDefaultBottomFramesToSkip;
 279  E :    asan_parameters->max_num_frames = kDefaultMaxNumFrames;
 280  E :    asan_parameters->trailer_padding_size = kDefaultTrailerPaddingSize;
 281  E :    asan_parameters->ignored_stack_ids = NULL;
 282  E :    asan_parameters->quarantine_block_size = kDefaultQuarantineBlockSize;
 283  E :    asan_parameters->minidump_on_failure = kDefaultMiniDumpOnFailure;
 284  E :    asan_parameters->exit_on_failure = kDefaultExitOnFailure;
 285  E :    asan_parameters->check_heap_on_failure = kDefaultCheckHeapOnFailure;
 286  E :    asan_parameters->log_as_text = kDefaultLogAsText;
 287  E :    asan_parameters->disable_breakpad_reporting =
 288    :        kDefaultDisableBreakpadReporting;
 289  E :    asan_parameters->allocation_guard_rate = kDefaultAllocationGuardRate;
 290  E :    asan_parameters->zebra_block_heap_size = kDefaultZebraBlockHeapSize;
 291  E :    asan_parameters->zebra_block_heap_quarantine_ratio =
 292    :        kDefaultZebraBlockHeapQuarantineRatio;
 293    :    // CtMalloc has been deprecated.
 294  E :    asan_parameters->deprecated_enable_ctmalloc = false;
 295  E :    asan_parameters->enable_zebra_block_heap = kDefaultEnableZebraBlockHeap;
 296  E :    asan_parameters->enable_large_block_heap = kDefaultEnableLargeBlockHeap;
 297  E :    asan_parameters->enable_allocation_filter = kDefaultEnableAllocationFilter;
 298  E :    asan_parameters->large_allocation_threshold =
 299    :        kDefaultLargeAllocationThreshold;
 300  E :    asan_parameters->feature_randomization = kDefaultFeatureRandomization;
 301  E :    asan_parameters->quarantine_flood_fill_rate =
 302    :        kDefaultQuarantineFloodFillRate;
 303  E :    asan_parameters->prevent_duplicate_corruption_crashes =
 304    :        kDefaultPreventDuplicateCorruptionCrashes;
 305  E :    asan_parameters->report_invalid_accesses = kDefaultReportInvalidAccesses;
 306  E :  }
 307    :  
 308    :  bool InflateAsanParameters(const AsanParameters* pod_params,
 309  E :                             InflatedAsanParameters* inflated_params) {
 310    :    // This must be kept up to date with AsanParameters as it evolves.
 311    :    static const size_t kSizeOfAsanParametersByVersion[] = {
 312    :        40, 44, 48, 52, 52, 52, 56, 56, 56, 56, 60, 60, 60, 60, 60};
 313    :    static_assert(
 314    :        arraysize(kSizeOfAsanParametersByVersion) == kAsanParametersVersion + 1,
 315    :        "Size of parameters version out of date.");
 316    :  
 317  E :    SetDefaultAsanParameters(inflated_params);
 318    :  
 319  E :    const uint8_t* data = reinterpret_cast<const uint8_t*>(pod_params);
 320  E :    const uint8_t* data_end = data + pod_params->size;
 321    :  
 322    :    // This is the size of known POD data in the version of the structure
 323    :    // being inflated.
 324    :    size_t min_pod_size = kSizeOfAsanParametersByVersion[
 325  E :        std::min(kAsanParametersVersion, pod_params->version)];
 326  E :    const uint8_t* min_pod_end = data + min_pod_size;
 327    :  
 328    :    // If we have stack IDs, ensure the pointer is to a valid location.
 329  E :    if (pod_params->ignored_stack_ids != NULL) {
 330    :      const uint8_t* ignored_stack_ids =
 331  E :          reinterpret_cast<const uint8_t*>(pod_params->ignored_stack_ids);
 332  E :      if (ignored_stack_ids < min_pod_end || ignored_stack_ids >= data_end) {
 333  E :        LOG(ERROR) << "Invalid ignored_stack_ids pointer.";
 334  E :        return false;
 335    :      }
 336    :    }
 337    :  
 338    :    // Only copy as many parameters as the structure contains, or that our version
 339    :    // of the runtime understands.
 340  E :    DCHECK_LE(min_pod_size, sizeof(AsanParameters));
 341  E :    ::memcpy(inflated_params, pod_params, min_pod_size);
 342    :  
 343    :    // Patch up the params to reflect our runtime version.
 344  E :    inflated_params->size = sizeof(AsanParameters);
 345  E :    inflated_params->version = kAsanParametersVersion;
 346  E :    (static_cast<AsanParameters*>(inflated_params))->ignored_stack_ids = NULL;
 347    :  
 348    :    // Populate the ignored stack ids.
 349  E :    const AsanStackId* stack_id = pod_params->ignored_stack_ids;
 350  E :    if (stack_id == NULL)
 351  E :      return true;
 352  E :    while (*stack_id != NULL) {
 353  E :      if (reinterpret_cast<const uint8_t*>(stack_id) > data_end) {
 354  E :        LOG(ERROR) << "AsanParameters::ignored_stack_ids list is not NULL "
 355    :                   << "terminated.";
 356  E :        return false;
 357    :      }
 358  E :      inflated_params->ignored_stack_ids_set.insert(*stack_id);
 359  E :      ++stack_id;
 360  E :    }
 361    :  
 362  E :    return true;
 363  E :  }
 364    :  
 365    :  namespace {
 366    :  
 367    :  // Parses a boolean flag. Returns true if the flag was present in the given
 368    :  // command line, and sets the parsed value in |value|. If |name| is "foo" then
 369    :  // the switches "--foo" and "--enable_foo" will result in |value| being set to
 370    :  // true. A switch of "--disable_foo" will result in |value| being set to false.
 371    :  // The presence of none of these switches will result in the function returning
 372    :  // false, and |value| being left as is.
 373    :  bool ParseBooleanFlag(const char* name, const base::CommandLine& cmd_line,
 374  E :                        bool* value) {
 375  E :    DCHECK_NE(static_cast<const char*>(nullptr), name);
 376  E :    DCHECK_NE(static_cast<bool*>(nullptr), value);
 377    :  
 378  E :    std::string raw = std::string("--") + std::string(name);
 379  E :    std::string enable = std::string("--enable_") + std::string(name);
 380  E :    std::string disable = std::string("--enable_") + std::string(name);
 381    :  
 382    :    // Parse the command-line from left to right so that position matters. This
 383    :    // allows the same flag to be toggled back and forth on a single command
 384    :    // line.
 385  E :    bool ret = false;
 386  E :    for (const auto& s16 : cmd_line.argv()) {
 387  E :      std::string s = base::WideToUTF8(s16);
 388  E :      if (s == raw || s == enable) {
 389  E :        *value = true;
 390  E :        ret = true;
 391  E :        continue;
 392    :      }
 393    :  
 394  E :      if (s == disable) {
 395  i :        *value = false;
 396  i :        ret = true;
 397  i :        continue;
 398    :      }
 399  E :    }
 400    :  
 401  E :    return ret;
 402  E :  }
 403    :  
 404    :  }  // namespace
 405    :  
 406    :  bool ParseAsanParameters(const base::StringPiece16& param_string,
 407  E :                           InflatedAsanParameters* asan_parameters) {
 408  E :    DCHECK_NE(reinterpret_cast<InflatedAsanParameters*>(NULL), asan_parameters);
 409    :  
 410    :    // Prepends the flags with a dummy executable name to keep the
 411    :    // base::CommandLine parser happy.
 412  E :    std::wstring str(param_string.as_string());
 413  E :    str.insert(0, L" ");
 414  E :    str.insert(0, L"dummy.exe");
 415  E :    base::CommandLine cmd_line = base::CommandLine::FromString(str);
 416    :  
 417    :    // Parse the quarantine size flag.
 418    :    if (UpdateUint32FromCommandLine::Do(cmd_line, kParamQuarantineSize,
 419  E :            &asan_parameters->quarantine_size) == kFlagError) {
 420  E :      return false;
 421    :    }
 422    :  
 423    :    // Parse the quarantine block size.
 424    :    if (UpdateUint32FromCommandLine::Do(cmd_line, kParamQuarantineBlockSize,
 425  E :            &asan_parameters->quarantine_block_size) == kFlagError) {
 426  i :      return false;
 427    :    }
 428    :  
 429    :    // Parse the trailer padding size flag.
 430    :    if (UpdateUint32FromCommandLine::Do(cmd_line, kParamTrailerPaddingSize,
 431  E :            &asan_parameters->trailer_padding_size) == kFlagError) {
 432  i :      return false;
 433    :    }
 434    :  
 435    :    // Parse the allocation guard rate.
 436    :    if (UpdateFloatFromCommandLine::Do(cmd_line, kParamAllocationGuardRate,
 437  E :            &asan_parameters->allocation_guard_rate) == kFlagError) {
 438  i :      return false;
 439    :    }
 440    :  
 441    :    // Parse the reporting period flag.
 442    :    if (UpdateUint32FromCommandLine::Do(cmd_line, kParamReportingPeriod,
 443  E :            &asan_parameters->reporting_period) == kFlagError) {
 444  i :      return false;
 445    :    }
 446    :  
 447    :    // Parse the bottom frames to skip flag.
 448    :    if (UpdateUint32FromCommandLine::Do(cmd_line, kParamBottomFramesToSkip,
 449  E :            &asan_parameters->bottom_frames_to_skip) == kFlagError) {
 450  i :      return false;
 451    :    }
 452    :  
 453    :    // Parse the max number of frames flag.
 454    :    if (UpdateUint32FromCommandLine::Do(cmd_line, kParamMaxNumFrames,
 455  E :            &asan_parameters->max_num_frames) == kFlagError) {
 456  i :      return false;
 457    :    }
 458    :  
 459    :    // Parse the ignored stack ids.
 460  E :    if (!ReadIgnoredStackIdsFromCommandLine(cmd_line, kParamIgnoredStackIds,
 461    :             &asan_parameters->ignored_stack_ids_set)) {
 462  E :      return false;
 463    :    }
 464    :  
 465    :    // Parse the zebra block heap size flag.
 466    :    if (UpdateUint32FromCommandLine::Do(cmd_line, kParamZebraBlockHeapSize,
 467  E :            &asan_parameters->zebra_block_heap_size) == kFlagError) {
 468  i :      return false;
 469    :    }
 470    :  
 471    :    // Parse the zebra block heap quarantine ratio flag.
 472    :    if (UpdateFloatFromCommandLine::Do(cmd_line,
 473    :            kParamZebraBlockHeapQuarantineRatio,
 474  E :            &asan_parameters->zebra_block_heap_quarantine_ratio) == kFlagError) {
 475  i :      return false;
 476    :    }
 477    :  
 478    :    // Parse the large block heap allocation threshold.
 479    :    if (UpdateUint32FromCommandLine::Do(cmd_line,
 480    :            kParamLargeAllocationThreshold,
 481  E :            &asan_parameters->large_allocation_threshold) == kFlagError) {
 482  i :      return false;
 483    :    }
 484    :  
 485    :    // Parse the quarantine flood-fill rate.
 486    :    if (UpdateFloatFromCommandLine::Do(cmd_line,
 487    :            kParamQuarantineFloodFillRate,
 488  E :            &asan_parameters->quarantine_flood_fill_rate) == kFlagError) {
 489  i :      return false;
 490    :    }
 491    :  
 492    :    // Parse the other (boolean) flags.
 493    :    // TODO(chrisha): Transition these all to new style flags.
 494  E :    if (cmd_line.HasSwitch(kParamMiniDumpOnFailure))
 495  E :      asan_parameters->minidump_on_failure = true;
 496  E :    if (cmd_line.HasSwitch(kParamExitOnFailure))
 497  E :      asan_parameters->exit_on_failure = true;
 498  E :    if (cmd_line.HasSwitch(kParamNoLogAsText))
 499  E :      asan_parameters->log_as_text = false;
 500  E :    if (cmd_line.HasSwitch(kParamNoCheckHeapOnFailure))
 501  E :      asan_parameters->check_heap_on_failure = false;
 502  E :    if (cmd_line.HasSwitch(kParamDisableBreakpadReporting))
 503  E :      asan_parameters->disable_breakpad_reporting = true;
 504  E :    if (cmd_line.HasSwitch(kParamDisableCtMalloc))
 505  i :      LOG(WARNING) << "Ignoring deprecated " << kParamDisableCtMalloc << " flag.";
 506  E :    if (cmd_line.HasSwitch(kParamEnableZebraBlockHeap))
 507  E :      asan_parameters->enable_zebra_block_heap = true;
 508  E :    if (cmd_line.HasSwitch(kParamDisableLargeBlockHeap))
 509  E :      asan_parameters->enable_large_block_heap = false;
 510  E :    if (cmd_line.HasSwitch(kParamEnableAllocationFilter))
 511  E :      asan_parameters->enable_allocation_filter = true;
 512  E :    if (cmd_line.HasSwitch(kParamPreventDuplicateCorruptionCrashes))
 513  E :      asan_parameters->prevent_duplicate_corruption_crashes = true;
 514  E :    if (cmd_line.HasSwitch(kParamReportInvalidAccesses))
 515  E :      asan_parameters->report_invalid_accesses = true;
 516    :  
 517    :    // New style boolean flags with both positive and negative setters. This
 518    :    // allows them to be set one way in the baked in configuration, and set
 519    :    // another way in the environment specified runtime configuration.
 520  E :    bool value = false;
 521  E :    if (ParseBooleanFlag(kParamFeatureRandomization, cmd_line, &value))
 522  E :      asan_parameters->feature_randomization = value;
 523    :  
 524  E :    return true;
 525  E :  }
 526    :  
 527    :  }  // namespace common

Coverage information generated Fri Jul 29 11:00:21 2016.