about_flags.cc revision 1e9bf3e0803691d0a228da41fc608347b6db4340
1// Copyright (c) 2012 The Chromium Authors. All rights reserved. 2// Use of this source code is governed by a BSD-style license that can be 3// found in the LICENSE file. 4 5#include "chrome/browser/about_flags.h" 6 7#include <algorithm> 8#include <iterator> 9#include <map> 10#include <set> 11#include <utility> 12 13#include "ash/ash_switches.h" 14#include "base/command_line.h" 15#include "base/memory/singleton.h" 16#include "base/strings/string_number_conversions.h" 17#include "base/strings/utf_string_conversions.h" 18#include "base/values.h" 19#include "cc/base/switches.h" 20#include "chrome/browser/flags_storage.h" 21#include "chrome/common/chrome_content_client.h" 22#include "chrome/common/chrome_switches.h" 23#include "components/nacl/common/nacl_switches.h" 24#include "content/public/browser/user_metrics.h" 25#include "extensions/common/switches.h" 26#include "grit/chromium_strings.h" 27#include "grit/generated_resources.h" 28#include "grit/google_chrome_strings.h" 29#include "media/base/media_switches.h" 30#include "ui/base/l10n/l10n_util.h" 31#include "ui/base/ui_base_switches.h" 32#include "ui/compositor/compositor_switches.h" 33#include "ui/events/event_switches.h" 34#include "ui/gfx/switches.h" 35#include "ui/gl/gl_switches.h" 36#include "ui/keyboard/keyboard_switches.h" 37#include "ui/message_center/message_center_switches.h" 38#include "ui/surface/surface_switches.h" 39 40#if defined(USE_ASH) 41#include "ash/ash_switches.h" 42#endif 43 44#if defined(OS_CHROMEOS) 45#include "chromeos/chromeos_switches.h" 46#include "third_party/cros_system_api/switches/chrome_switches.h" 47#endif 48 49using content::UserMetricsAction; 50 51namespace about_flags { 52 53// Macros to simplify specifying the type. 54#define SINGLE_VALUE_TYPE_AND_VALUE(command_line_switch, switch_value) \ 55 Experiment::SINGLE_VALUE, \ 56 command_line_switch, switch_value, NULL, NULL, NULL, 0 57#define SINGLE_VALUE_TYPE(command_line_switch) \ 58 SINGLE_VALUE_TYPE_AND_VALUE(command_line_switch, "") 59#define ENABLE_DISABLE_VALUE_TYPE_AND_VALUE(enable_switch, enable_value, \ 60 disable_switch, disable_value) \ 61 Experiment::ENABLE_DISABLE_VALUE, enable_switch, enable_value, \ 62 disable_switch, disable_value, NULL, 3 63#define ENABLE_DISABLE_VALUE_TYPE(enable_switch, disable_switch) \ 64 ENABLE_DISABLE_VALUE_TYPE_AND_VALUE(enable_switch, "", disable_switch, "") 65#define MULTI_VALUE_TYPE(choices) \ 66 Experiment::MULTI_VALUE, NULL, NULL, NULL, NULL, choices, arraysize(choices) 67 68namespace { 69 70const unsigned kOsAll = kOsMac | kOsWin | kOsLinux | kOsCrOS | kOsAndroid; 71const unsigned kOsDesktop = kOsMac | kOsWin | kOsLinux | kOsCrOS; 72 73// Adds a |StringValue| to |list| for each platform where |bitmask| indicates 74// whether the experiment is available on that platform. 75void AddOsStrings(unsigned bitmask, ListValue* list) { 76 struct { 77 unsigned bit; 78 const char* const name; 79 } kBitsToOs[] = { 80 {kOsMac, "Mac"}, 81 {kOsWin, "Windows"}, 82 {kOsLinux, "Linux"}, 83 {kOsCrOS, "Chrome OS"}, 84 {kOsAndroid, "Android"}, 85 {kOsCrOSOwnerOnly, "Chrome OS (owner only)"}, 86 }; 87 for (size_t i = 0; i < ARRAYSIZE_UNSAFE(kBitsToOs); ++i) 88 if (bitmask & kBitsToOs[i].bit) 89 list->Append(new StringValue(kBitsToOs[i].name)); 90} 91 92// Convert switch constants to proper CommandLine::StringType strings. 93CommandLine::StringType GetSwitchString(const std::string& flag) { 94 CommandLine cmd_line(CommandLine::NO_PROGRAM); 95 cmd_line.AppendSwitch(flag); 96 DCHECK(cmd_line.argv().size() == 2); 97 return cmd_line.argv()[1]; 98} 99 100// Scoops flags from a command line. 101std::set<CommandLine::StringType> ExtractFlagsFromCommandLine( 102 const CommandLine& cmdline) { 103 std::set<CommandLine::StringType> flags; 104 // First do the ones between --flag-switches-begin and --flag-switches-end. 105 CommandLine::StringVector::const_iterator first = 106 std::find(cmdline.argv().begin(), cmdline.argv().end(), 107 GetSwitchString(switches::kFlagSwitchesBegin)); 108 CommandLine::StringVector::const_iterator last = 109 std::find(cmdline.argv().begin(), cmdline.argv().end(), 110 GetSwitchString(switches::kFlagSwitchesEnd)); 111 if (first != cmdline.argv().end() && last != cmdline.argv().end()) 112 flags.insert(first + 1, last); 113#if defined(OS_CHROMEOS) 114 // Then add those between --policy-switches-begin and --policy-switches-end. 115 first = std::find(cmdline.argv().begin(), cmdline.argv().end(), 116 GetSwitchString(chromeos::switches::kPolicySwitchesBegin)); 117 last = std::find(cmdline.argv().begin(), cmdline.argv().end(), 118 GetSwitchString(chromeos::switches::kPolicySwitchesEnd)); 119 if (first != cmdline.argv().end() && last != cmdline.argv().end()) 120 flags.insert(first + 1, last); 121#endif 122 return flags; 123} 124 125const Experiment::Choice kEnableCompositingForFixedPositionChoices[] = { 126 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 127 { IDS_GENERIC_EXPERIMENT_CHOICE_ENABLED, 128 switches::kEnableCompositingForFixedPosition, ""}, 129 { IDS_GENERIC_EXPERIMENT_CHOICE_DISABLED, 130 switches::kDisableCompositingForFixedPosition, ""}, 131 { IDS_FLAGS_COMPOSITING_FOR_FIXED_POSITION_HIGH_DPI, 132 switches::kEnableHighDpiCompositingForFixedPosition, ""} 133}; 134 135const Experiment::Choice kEnableCompositingForTransitionChoices[] = { 136 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 137 { IDS_GENERIC_EXPERIMENT_CHOICE_ENABLED, 138 switches::kEnableCompositingForTransition, ""}, 139 { IDS_GENERIC_EXPERIMENT_CHOICE_DISABLED, 140 switches::kDisableCompositingForTransition, ""}, 141}; 142 143const Experiment::Choice kEnableAcceleratedFixedRootBackgroundChoices[] = { 144 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 145 { IDS_GENERIC_EXPERIMENT_CHOICE_ENABLED, 146 switches::kEnableAcceleratedFixedRootBackground, ""}, 147 { IDS_GENERIC_EXPERIMENT_CHOICE_DISABLED, 148 switches::kDisableAcceleratedFixedRootBackground, ""}, 149}; 150 151const Experiment::Choice kGDIPresentChoices[] = { 152 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 153 { IDS_FLAGS_PRESENT_WITH_GDI_FIRST_SHOW, 154 switches::kDoFirstShowPresentWithGDI, ""}, 155 { IDS_FLAGS_PRESENT_WITH_GDI_ALL_SHOW, 156 switches::kDoAllShowPresentWithGDI, ""} 157}; 158 159const Experiment::Choice kTouchEventsChoices[] = { 160 { IDS_GENERIC_EXPERIMENT_CHOICE_AUTOMATIC, "", "" }, 161 { IDS_GENERIC_EXPERIMENT_CHOICE_ENABLED, 162 switches::kTouchEvents, 163 switches::kTouchEventsEnabled }, 164 { IDS_GENERIC_EXPERIMENT_CHOICE_DISABLED, 165 switches::kTouchEvents, 166 switches::kTouchEventsDisabled } 167}; 168 169const Experiment::Choice kTouchOptimizedUIChoices[] = { 170 { IDS_GENERIC_EXPERIMENT_CHOICE_AUTOMATIC, "", "" }, 171 { IDS_GENERIC_EXPERIMENT_CHOICE_ENABLED, 172 switches::kTouchOptimizedUI, 173 switches::kTouchOptimizedUIEnabled }, 174 { IDS_GENERIC_EXPERIMENT_CHOICE_DISABLED, 175 switches::kTouchOptimizedUI, 176 switches::kTouchOptimizedUIDisabled } 177}; 178 179const Experiment::Choice kNaClDebugMaskChoices[] = { 180 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 181 // Secure shell can be used on ChromeOS for forwarding the TCP port opened by 182 // debug stub to a remote machine. Since secure shell uses NaCl, we provide 183 // an option to switch off its debugging. 184 { IDS_NACL_DEBUG_MASK_CHOICE_EXCLUDE_UTILS, 185 switches::kNaClDebugMask, "!*://*/*ssh_client.nmf" }, 186 { IDS_NACL_DEBUG_MASK_CHOICE_INCLUDE_DEBUG, 187 switches::kNaClDebugMask, "*://*/*debug.nmf" } 188}; 189 190#if defined(OS_CHROMEOS) 191 192const Experiment::Choice kChromeCaptivePortalDetectionChoices[] = { 193 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 194 { IDS_FLAGS_CHROME_CAPTIVE_PORTAL_DETECTOR, 195 chromeos::switches::kEnableChromeCaptivePortalDetector, "" }, 196 { IDS_FLAGS_SHILL_CAPTIVE_PORTAL_DETECTOR, 197 chromeos::switches::kDisableChromeCaptivePortalDetector, "" } 198}; 199 200#endif 201 202const Experiment::Choice kImplSidePaintingChoices[] = { 203 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 204 { IDS_GENERIC_EXPERIMENT_CHOICE_ENABLED, 205 cc::switches::kEnableImplSidePainting, ""}, 206 { IDS_GENERIC_EXPERIMENT_CHOICE_DISABLED, 207 cc::switches::kDisableImplSidePainting, ""} 208}; 209 210const Experiment::Choice kDeadlineSchedulingChoices[] = { 211 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 212 { IDS_GENERIC_EXPERIMENT_CHOICE_ENABLED, 213 switches::kEnableDeadlineScheduling, ""}, 214 { IDS_GENERIC_EXPERIMENT_CHOICE_DISABLED, 215 switches::kDisableDeadlineScheduling, ""} 216}; 217 218const Experiment::Choice kUIDeadlineSchedulingChoices[] = { 219 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 220 { IDS_GENERIC_EXPERIMENT_CHOICE_ENABLED, 221 switches::kUIEnableDeadlineScheduling, ""}, 222 { IDS_GENERIC_EXPERIMENT_CHOICE_DISABLED, 223 switches::kUIDisableDeadlineScheduling, ""} 224}; 225 226const Experiment::Choice kLCDTextChoices[] = { 227 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 228 { IDS_GENERIC_EXPERIMENT_CHOICE_ENABLED, cc::switches::kEnableLCDText, ""}, 229 { IDS_GENERIC_EXPERIMENT_CHOICE_DISABLED, cc::switches::kDisableLCDText, ""} 230}; 231 232const Experiment::Choice kDelegatedRendererChoices[] = { 233 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 234 { IDS_GENERIC_EXPERIMENT_CHOICE_ENABLED, 235 switches::kEnableDelegatedRenderer, ""}, 236 { IDS_GENERIC_EXPERIMENT_CHOICE_DISABLED, 237 switches::kDisableDelegatedRenderer, ""} 238}; 239 240const Experiment::Choice kMaxTilesForInterestAreaChoices[] = { 241 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 242 { IDS_FLAGS_MAX_TILES_FOR_INTEREST_AREA_SHORT, 243 cc::switches::kMaxTilesForInterestArea, "64"}, 244 { IDS_FLAGS_MAX_TILES_FOR_INTEREST_AREA_TALL, 245 cc::switches::kMaxTilesForInterestArea, "128"}, 246 { IDS_FLAGS_MAX_TILES_FOR_INTEREST_AREA_GRANDE, 247 cc::switches::kMaxTilesForInterestArea, "256"}, 248 { IDS_FLAGS_MAX_TILES_FOR_INTEREST_AREA_VENTI, 249 cc::switches::kMaxTilesForInterestArea, "512"} 250}; 251 252const Experiment::Choice kDefaultTileWidthChoices[] = { 253 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 254 { IDS_FLAGS_DEFAULT_TILE_WIDTH_SHORT, 255 switches::kDefaultTileWidth, "128"}, 256 { IDS_FLAGS_DEFAULT_TILE_WIDTH_TALL, 257 switches::kDefaultTileWidth, "256"}, 258 { IDS_FLAGS_DEFAULT_TILE_WIDTH_GRANDE, 259 switches::kDefaultTileWidth, "512"}, 260 { IDS_FLAGS_DEFAULT_TILE_WIDTH_VENTI, 261 switches::kDefaultTileWidth, "1024"} 262}; 263 264#if defined(USE_ASH) 265const Experiment::Choice kAshOverviewDelayChoices[] = { 266 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 267 { IDS_FLAGS_OVERVIEW_DELAY_INSTANT, 268 ash::switches::kAshOverviewDelayOnAltTab, "0" }, 269 { IDS_FLAGS_OVERVIEW_DELAY_SHORT, 270 ash::switches::kAshOverviewDelayOnAltTab, "100" }, 271 { IDS_FLAGS_OVERVIEW_DELAY_LONG, 272 ash::switches::kAshOverviewDelayOnAltTab, "500" }, 273 { IDS_FLAGS_OVERVIEW_DELAY_NEVER, 274 ash::switches::kAshOverviewDelayOnAltTab, "10000" }, 275}; 276#endif 277 278const Experiment::Choice kDefaultTileHeightChoices[] = { 279 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 280 { IDS_FLAGS_DEFAULT_TILE_HEIGHT_SHORT, 281 switches::kDefaultTileHeight, "128"}, 282 { IDS_FLAGS_DEFAULT_TILE_HEIGHT_TALL, 283 switches::kDefaultTileHeight, "256"}, 284 { IDS_FLAGS_DEFAULT_TILE_HEIGHT_GRANDE, 285 switches::kDefaultTileHeight, "512"}, 286 { IDS_FLAGS_DEFAULT_TILE_HEIGHT_VENTI, 287 switches::kDefaultTileHeight, "1024"} 288}; 289 290const Experiment::Choice kSimpleCacheBackendChoices[] = { 291 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 292 { IDS_GENERIC_EXPERIMENT_CHOICE_DISABLED, 293 switches::kUseSimpleCacheBackend, "off" }, 294 { IDS_GENERIC_EXPERIMENT_CHOICE_ENABLED, 295 switches::kUseSimpleCacheBackend, "on"} 296}; 297 298#if defined(USE_AURA) 299const Experiment::Choice kTabCaptureUpscaleQualityChoices[] = { 300 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 301 { IDS_FLAGS_TAB_CAPTURE_SCALE_QUALITY_FAST, 302 switches::kTabCaptureUpscaleQuality, "fast" }, 303 { IDS_FLAGS_TAB_CAPTURE_SCALE_QUALITY_GOOD, 304 switches::kTabCaptureUpscaleQuality, "good" }, 305 { IDS_FLAGS_TAB_CAPTURE_SCALE_QUALITY_BEST, 306 switches::kTabCaptureUpscaleQuality, "best" }, 307}; 308 309const Experiment::Choice kTabCaptureDownscaleQualityChoices[] = { 310 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 311 { IDS_FLAGS_TAB_CAPTURE_SCALE_QUALITY_FAST, 312 switches::kTabCaptureDownscaleQuality, "fast" }, 313 { IDS_FLAGS_TAB_CAPTURE_SCALE_QUALITY_GOOD, 314 switches::kTabCaptureDownscaleQuality, "good" }, 315 { IDS_FLAGS_TAB_CAPTURE_SCALE_QUALITY_BEST, 316 switches::kTabCaptureDownscaleQuality, "best" }, 317}; 318#endif 319 320const Experiment::Choice kMapImageChoices[] = { 321 { IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, "", "" }, 322 { IDS_GENERIC_EXPERIMENT_CHOICE_ENABLED, 323 cc::switches::kEnableMapImage, ""}, 324 { IDS_GENERIC_EXPERIMENT_CHOICE_DISABLED, 325 cc::switches::kDisableMapImage, ""} 326}; 327 328// RECORDING USER METRICS FOR FLAGS: 329// ----------------------------------------------------------------------------- 330// The first line of the experiment is the internal name. If you'd like to 331// gather statistics about the usage of your flag, you should append a marker 332// comment to the end of the feature name, like so: 333// "my-special-feature", // FLAGS:RECORD_UMA 334// 335// After doing that, run //chrome/tools/extract_actions.py (see instructions at 336// the top of that file for details) to update the chromeactions.txt file, which 337// will enable UMA to record your feature flag. 338// 339// After your feature has shipped under a flag, you can locate the metrics under 340// the action name AboutFlags_internal-action-name. Actions are recorded once 341// per startup, so you should divide this number by AboutFlags_StartupTick to 342// get a sense of usage. Note that this will not be the same as number of users 343// with a given feature enabled because users can quit and relaunch the 344// application multiple times over a given time interval. The dashboard also 345// shows you how many (metrics reporting) users have enabled the flag over the 346// last seven days. However, note that this is not the same as the number of 347// users who have the flag enabled, since enabling the flag happens once, 348// whereas running with the flag enabled happens until the user flips the flag 349// again. 350 351// To add a new experiment add to the end of kExperiments. There are two 352// distinct types of experiments: 353// . SINGLE_VALUE: experiment is either on or off. Use the SINGLE_VALUE_TYPE 354// macro for this type supplying the command line to the macro. 355// . MULTI_VALUE: a list of choices, the first of which should correspond to a 356// deactivated state for this lab (i.e. no command line option). To specify 357// this type of experiment use the macro MULTI_VALUE_TYPE supplying it the 358// array of choices. 359// See the documentation of Experiment for details on the fields. 360// 361// When adding a new choice, add it to the end of the list. 362const Experiment kExperiments[] = { 363 { 364 "expose-for-tabs", // FLAGS:RECORD_UMA 365 IDS_FLAGS_TABPOSE_NAME, 366 IDS_FLAGS_TABPOSE_DESCRIPTION, 367 kOsMac, 368#if defined(OS_MACOSX) 369 // The switch exists only on OS X. 370 SINGLE_VALUE_TYPE(switches::kEnableExposeForTabs) 371#else 372 SINGLE_VALUE_TYPE("") 373#endif 374 }, 375 { 376 "conflicting-modules-check", // FLAGS:RECORD_UMA 377 IDS_FLAGS_CONFLICTS_CHECK_NAME, 378 IDS_FLAGS_CONFLICTS_CHECK_DESCRIPTION, 379 kOsWin, 380 SINGLE_VALUE_TYPE(switches::kConflictingModulesCheck) 381 }, 382 { 383 "ignore-gpu-blacklist", 384 IDS_FLAGS_IGNORE_GPU_BLACKLIST_NAME, 385 IDS_FLAGS_IGNORE_GPU_BLACKLIST_DESCRIPTION, 386 kOsAll, 387 SINGLE_VALUE_TYPE(switches::kIgnoreGpuBlacklist) 388 }, 389 { 390 "force-compositing-mode-2", 391 IDS_FLAGS_FORCE_COMPOSITING_MODE_NAME, 392 IDS_FLAGS_FORCE_COMPOSITING_MODE_DESCRIPTION, 393 kOsMac | kOsWin | kOsLinux, 394 ENABLE_DISABLE_VALUE_TYPE(switches::kForceCompositingMode, 395 switches::kDisableForceCompositingMode) 396 }, 397 { 398 "threaded-compositing-mode", 399 IDS_FLAGS_THREADED_COMPOSITING_MODE_NAME, 400 IDS_FLAGS_THREADED_COMPOSITING_MODE_DESCRIPTION, 401 kOsMac | kOsWin | kOsLinux, 402 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableThreadedCompositing, 403 switches::kDisableThreadedCompositing) 404 }, 405 { 406 "force-accelerated-composited-scrolling", 407 IDS_FLAGS_FORCE_ACCELERATED_OVERFLOW_SCROLL_MODE_NAME, 408 IDS_FLAGS_FORCE_ACCELERATED_OVERFLOW_SCROLL_MODE_DESCRIPTION, 409 kOsAll, 410 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableAcceleratedOverflowScroll, 411 switches::kDisableAcceleratedOverflowScroll) 412 }, 413 { 414 "force-universal-accelerated-composited-scrolling", 415 IDS_FLAGS_FORCE_UNIVERSAL_ACCELERATED_OVERFLOW_SCROLL_MODE_NAME, 416 IDS_FLAGS_FORCE_UNIVERSAL_ACCELERATED_OVERFLOW_SCROLL_MODE_DESCRIPTION, 417 kOsAll, 418 ENABLE_DISABLE_VALUE_TYPE( 419 switches::kEnableUniversalAcceleratedOverflowScroll, 420 switches::kDisableUniversalAcceleratedOverflowScroll) 421 }, 422 { 423 "present-with-GDI", 424 IDS_FLAGS_PRESENT_WITH_GDI_NAME, 425 IDS_FLAGS_PRESENT_WITH_GDI_DESCRIPTION, 426 kOsWin, 427 MULTI_VALUE_TYPE(kGDIPresentChoices) 428 }, 429 { 430 "enable-experimental-canvas-features", 431 IDS_FLAGS_ENABLE_EXPERIMENTAL_CANVAS_FEATURES_NAME, 432 IDS_FLAGS_ENABLE_EXPERIMENTAL_CANVAS_FEATURES_DESCRIPTION, 433 kOsAll, 434 SINGLE_VALUE_TYPE(switches::kEnableExperimentalCanvasFeatures) 435 }, 436 { 437 "disable-accelerated-2d-canvas", 438 IDS_FLAGS_DISABLE_ACCELERATED_2D_CANVAS_NAME, 439 IDS_FLAGS_DISABLE_ACCELERATED_2D_CANVAS_DESCRIPTION, 440 kOsAll, 441 SINGLE_VALUE_TYPE(switches::kDisableAccelerated2dCanvas) 442 }, 443 { 444 "disable-threaded-animation", 445 IDS_FLAGS_DISABLE_THREADED_ANIMATION_NAME, 446 IDS_FLAGS_DISABLE_THREADED_ANIMATION_DESCRIPTION, 447 kOsAll, 448 SINGLE_VALUE_TYPE(cc::switches::kDisableThreadedAnimation) 449 }, 450 { 451 "composited-layer-borders", 452 IDS_FLAGS_COMPOSITED_LAYER_BORDERS, 453 IDS_FLAGS_COMPOSITED_LAYER_BORDERS_DESCRIPTION, 454 kOsAll, 455 SINGLE_VALUE_TYPE(cc::switches::kShowCompositedLayerBorders) 456 }, 457 { 458 "show-fps-counter", 459 IDS_FLAGS_SHOW_FPS_COUNTER, 460 IDS_FLAGS_SHOW_FPS_COUNTER_DESCRIPTION, 461 kOsAll, 462 SINGLE_VALUE_TYPE(cc::switches::kShowFPSCounter) 463 }, 464 { 465 "accelerated-filters", 466 IDS_FLAGS_ACCELERATED_FILTERS, 467 IDS_FLAGS_ACCELERATED_FILTERS_DESCRIPTION, 468 kOsAll, 469 SINGLE_VALUE_TYPE(switches::kEnableAcceleratedFilters) 470 }, 471 { 472 "disable-webgl", 473 IDS_FLAGS_DISABLE_WEBGL_NAME, 474 IDS_FLAGS_DISABLE_WEBGL_DESCRIPTION, 475 kOsAll, 476 SINGLE_VALUE_TYPE(switches::kDisableExperimentalWebGL) 477 }, 478 { 479 "enable-d3d11", 480 IDS_FLAGS_ENABLE_D3D11_NAME, 481 IDS_FLAGS_ENABLE_D3D11_DESCRIPTION, 482 kOsWin, 483 SINGLE_VALUE_TYPE(switches::kEnableD3D11) 484 }, 485 { 486 "disable-webrtc", 487 IDS_FLAGS_DISABLE_WEBRTC_NAME, 488 IDS_FLAGS_DISABLE_WEBRTC_DESCRIPTION, 489 kOsAndroid, 490#if defined(OS_ANDROID) 491 SINGLE_VALUE_TYPE(switches::kDisableWebRTC) 492#else 493 SINGLE_VALUE_TYPE("") 494#endif 495 }, 496#if defined(ENABLE_WEBRTC) 497 { 498 "disable-device-enumeration", 499 IDS_FLAGS_DISABLE_DEVICE_ENUMERATION_NAME, 500 IDS_FLAGS_DISABLE_DEVICE_ENUMERATION_DESCRIPTION, 501 kOsAll, 502 SINGLE_VALUE_TYPE(switches::kDisableDeviceEnumeration) 503 }, 504 { 505 "disable-sctp-data-channels", 506 IDS_FLAGS_DISABLE_SCTP_DATA_CHANNELS_NAME, 507 IDS_FLAGS_DISABLE_SCTP_DATA_CHANNELS_DESCRIPTION, 508 kOsAll, 509 SINGLE_VALUE_TYPE(switches::kDisableSCTPDataChannels) 510 }, 511 { 512 "disable-webrtc-hw-decoding", 513 IDS_FLAGS_DISABLE_WEBRTC_HW_DECODING_NAME, 514 IDS_FLAGS_DISABLE_WEBRTC_HW_DECODING_DESCRIPTION, 515 kOsCrOS, 516 SINGLE_VALUE_TYPE(switches::kDisableWebRtcHWDecoding) 517 }, 518 { 519 "disable-webrtc-hw-encoding", 520 IDS_FLAGS_DISABLE_WEBRTC_HW_ENCODING_NAME, 521 IDS_FLAGS_DISABLE_WEBRTC_HW_ENCODING_DESCRIPTION, 522 kOsCrOS, 523 SINGLE_VALUE_TYPE(switches::kDisableWebRtcHWEncoding) 524 }, 525#endif 526#if defined(OS_ANDROID) 527 { 528 "disable-webaudio", 529 IDS_FLAGS_DISABLE_WEBAUDIO_NAME, 530 IDS_FLAGS_DISABLE_WEBAUDIO_DESCRIPTION, 531 kOsAndroid, 532 SINGLE_VALUE_TYPE(switches::kDisableWebAudio) 533 }, 534#endif 535 { 536 "fixed-position-creates-stacking-context", 537 IDS_FLAGS_FIXED_POSITION_CREATES_STACKING_CONTEXT_NAME, 538 IDS_FLAGS_FIXED_POSITION_CREATES_STACKING_CONTEXT_DESCRIPTION, 539 kOsAll, 540 ENABLE_DISABLE_VALUE_TYPE( 541 switches::kEnableFixedPositionCreatesStackingContext, 542 switches::kDisableFixedPositionCreatesStackingContext) 543 }, 544 { 545 "enable-compositing-for-fixed-position", 546 IDS_FLAGS_COMPOSITING_FOR_FIXED_POSITION_NAME, 547 IDS_FLAGS_COMPOSITING_FOR_FIXED_POSITION_DESCRIPTION, 548 kOsAll, 549 MULTI_VALUE_TYPE(kEnableCompositingForFixedPositionChoices) 550 }, 551 { 552 "enable-compositing-for-transition", 553 IDS_FLAGS_COMPOSITING_FOR_TRANSITION_NAME, 554 IDS_FLAGS_COMPOSITING_FOR_TRANSITION_DESCRIPTION, 555 kOsAll, 556 MULTI_VALUE_TYPE(kEnableCompositingForTransitionChoices) 557 }, 558 { 559 "enable-accelerated-fixed-root-background", 560 IDS_FLAGS_ACCELERATED_FIXED_ROOT_BACKGROUND_NAME, 561 IDS_FLAGS_ACCELERATED_FIXED_ROOT_BACKGROUND_DESCRIPTION, 562 kOsAll, 563 MULTI_VALUE_TYPE(kEnableAcceleratedFixedRootBackgroundChoices) 564 }, 565 // TODO(bbudge): When NaCl is on by default, remove this flag entry. 566 { 567 "enable-nacl", // FLAGS:RECORD_UMA 568 IDS_FLAGS_ENABLE_NACL_NAME, 569 IDS_FLAGS_ENABLE_NACL_DESCRIPTION, 570 kOsDesktop, 571 SINGLE_VALUE_TYPE(switches::kEnableNaCl) 572 }, 573 { 574 "enable-nacl-debug", // FLAGS:RECORD_UMA 575 IDS_FLAGS_ENABLE_NACL_DEBUG_NAME, 576 IDS_FLAGS_ENABLE_NACL_DEBUG_DESCRIPTION, 577 kOsDesktop, 578 SINGLE_VALUE_TYPE(switches::kEnableNaClDebug) 579 }, 580 { 581 "disable-pnacl", // FLAGS:RECORD_UMA 582 IDS_FLAGS_DISABLE_PNACL_NAME, 583 IDS_FLAGS_DISABLE_PNACL_DESCRIPTION, 584 kOsDesktop, 585 SINGLE_VALUE_TYPE(switches::kDisablePnacl) 586 }, 587 { 588 "nacl-debug-mask", // FLAGS:RECORD_UMA 589 IDS_FLAGS_NACL_DEBUG_MASK_NAME, 590 IDS_FLAGS_NACL_DEBUG_MASK_DESCRIPTION, 591 kOsDesktop, 592 MULTI_VALUE_TYPE(kNaClDebugMaskChoices) 593 }, 594 { 595 "extension-apis", // FLAGS:RECORD_UMA 596 IDS_FLAGS_EXPERIMENTAL_EXTENSION_APIS_NAME, 597 IDS_FLAGS_EXPERIMENTAL_EXTENSION_APIS_DESCRIPTION, 598 kOsDesktop, 599 SINGLE_VALUE_TYPE(extensions::switches::kEnableExperimentalExtensionApis) 600 }, 601 { 602 "extensions-on-chrome-urls", 603 IDS_FLAGS_EXTENSIONS_ON_CHROME_URLS_NAME, 604 IDS_FLAGS_EXTENSIONS_ON_CHROME_URLS_DESCRIPTION, 605 kOsAll, 606 SINGLE_VALUE_TYPE(extensions::switches::kExtensionsOnChromeURLs) 607 }, 608 { 609 "enable-fast-unload", 610 IDS_FLAGS_ENABLE_FAST_UNLOAD_NAME, 611 IDS_FLAGS_ENABLE_FAST_UNLOAD_DESCRIPTION, 612 kOsAll, 613 SINGLE_VALUE_TYPE(switches::kEnableFastUnload) 614 }, 615 { 616 "enable-adview", 617 IDS_FLAGS_ENABLE_ADVIEW_NAME, 618 IDS_FLAGS_ENABLE_ADVIEW_DESCRIPTION, 619 kOsDesktop, 620 SINGLE_VALUE_TYPE(switches::kEnableAdview) 621 }, 622 { 623 "enable-adview-src-attribute", 624 IDS_FLAGS_ENABLE_ADVIEW_SRC_ATTRIBUTE_NAME, 625 IDS_FLAGS_ENABLE_ADVIEW_SRC_ATTRIBUTE_DESCRIPTION, 626 kOsDesktop, 627 SINGLE_VALUE_TYPE(switches::kEnableAdviewSrcAttribute) 628 }, 629 { 630 "enable-app-window-controls", 631 IDS_FLAGS_ENABLE_APP_WINDOW_CONTROLS_NAME, 632 IDS_FLAGS_ENABLE_APP_WINDOW_CONTROLS_DESCRIPTION, 633 kOsDesktop, 634 SINGLE_VALUE_TYPE(switches::kEnableAppWindowControls) 635 }, 636 { 637 "script-badges", 638 IDS_FLAGS_SCRIPT_BADGES_NAME, 639 IDS_FLAGS_SCRIPT_BADGES_DESCRIPTION, 640 kOsDesktop, 641 SINGLE_VALUE_TYPE(switches::kScriptBadges) 642 }, 643 { 644 "script-bubble", 645 IDS_FLAGS_SCRIPT_BUBBLE_NAME, 646 IDS_FLAGS_SCRIPT_BUBBLE_DESCRIPTION, 647 kOsDesktop, 648 ENABLE_DISABLE_VALUE_TYPE_AND_VALUE(switches::kScriptBubble, "1", 649 switches::kScriptBubble, "0") 650 }, 651 { 652 "apps-new-install-bubble", 653 IDS_FLAGS_APPS_NEW_INSTALL_BUBBLE_NAME, 654 IDS_FLAGS_APPS_NEW_INSTALL_BUBBLE_DESCRIPTION, 655 kOsDesktop, 656 SINGLE_VALUE_TYPE(switches::kAppsNewInstallBubble) 657 }, 658 { 659 "disable-hyperlink-auditing", 660 IDS_FLAGS_DISABLE_HYPERLINK_AUDITING_NAME, 661 IDS_FLAGS_DISABLE_HYPERLINK_AUDITING_DESCRIPTION, 662 kOsAll, 663 SINGLE_VALUE_TYPE(switches::kNoPings) 664 }, 665 { 666 "tab-groups-context-menu", 667 IDS_FLAGS_TAB_GROUPS_CONTEXT_MENU_NAME, 668 IDS_FLAGS_TAB_GROUPS_CONTEXT_MENU_DESCRIPTION, 669 kOsWin, 670 SINGLE_VALUE_TYPE(switches::kEnableTabGroupsContextMenu) 671 }, 672 { 673 "enable-instant-extended-api", 674 IDS_FLAGS_ENABLE_INSTANT_EXTENDED_API, 675 IDS_FLAGS_ENABLE_INSTANT_EXTENDED_API_DESCRIPTION, 676 kOsMac | kOsWin | kOsCrOS, 677 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableInstantExtendedAPI, 678 switches::kDisableInstantExtendedAPI) 679 }, 680 { 681 "use-cacheable-new-tab-page", 682 IDS_FLAGS_ENABLE_INSTANT_EXTENDED_CACHEABLE_NTP, 683 IDS_FLAGS_ENABLE_INSTANT_EXTENDED_CACHEABLE_NTP_DESCRIPTION, 684 kOsMac | kOsWin | kOsCrOS, 685 SINGLE_VALUE_TYPE(switches::kUseCacheableNewTabPage) 686 }, 687 { 688 "enable-local-first-load-ntp", 689 IDS_FLAGS_ENABLE_LOCAL_FIRST_LOAD_NTP, 690 IDS_FLAGS_ENABLE_LOCAL_FIRST_LOAD_NTP_DESCRIPTION, 691 kOsMac | kOsWin | kOsCrOS, 692 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableLocalFirstLoadNTP, 693 switches::kDisableLocalFirstLoadNTP) 694 }, 695#if defined(OS_ANDROID) 696 { 697 "enable-new-ntp", 698 IDS_FLAGS_ENABLE_NEW_NTP, 699 IDS_FLAGS_ENABLE_NEW_NTP_DESCRIPTION, 700 kOsAndroid, 701 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableNewNTP, 702 switches::kDisableNewNTP) 703 }, 704#endif 705 { 706 "show-autofill-type-predictions", 707 IDS_FLAGS_SHOW_AUTOFILL_TYPE_PREDICTIONS_NAME, 708 IDS_FLAGS_SHOW_AUTOFILL_TYPE_PREDICTIONS_DESCRIPTION, 709 kOsAll, 710 SINGLE_VALUE_TYPE(autofill::switches::kShowAutofillTypePredictions) 711 }, 712 { 713 "enable-gesture-tap-highlight", 714 IDS_FLAGS_ENABLE_GESTURE_TAP_HIGHLIGHTING_NAME, 715 IDS_FLAGS_ENABLE_GESTURE_TAP_HIGHLIGHTING_DESCRIPTION, 716 kOsLinux | kOsCrOS, 717 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableGestureTapHighlight, 718 switches::kDisableGestureTapHighlight) 719 }, 720 { 721 "enable-smooth-scrolling", // FLAGS:RECORD_UMA 722 IDS_FLAGS_ENABLE_SMOOTH_SCROLLING_NAME, 723 IDS_FLAGS_ENABLE_SMOOTH_SCROLLING_DESCRIPTION, 724 // Can't expose the switch unless the code is compiled in. 725 // On by default for the Mac (different implementation in WebKit). 726 kOsWin | kOsLinux, 727 SINGLE_VALUE_TYPE(switches::kEnableSmoothScrolling) 728 }, 729 { 730 "enable-overlay-scrollbars", 731 IDS_FLAGS_ENABLE_OVERLAY_SCROLLBARS_NAME, 732 IDS_FLAGS_ENABLE_OVERLAY_SCROLLBARS_DESCRIPTION, 733 // Uses the system preference on Mac (a different implementation). 734 // On Android, this is always enabled. 735 kOsCrOS, 736 SINGLE_VALUE_TYPE(switches::kEnableOverlayScrollbars) 737 }, 738 { 739 "enable-panels", 740 IDS_FLAGS_ENABLE_PANELS_NAME, 741 IDS_FLAGS_ENABLE_PANELS_DESCRIPTION, 742 kOsDesktop, 743 SINGLE_VALUE_TYPE(switches::kEnablePanels) 744 }, 745 { 746 // See http://crbug.com/120416 for how to remove this flag. 747 "save-page-as-mhtml", // FLAGS:RECORD_UMA 748 IDS_FLAGS_SAVE_PAGE_AS_MHTML_NAME, 749 IDS_FLAGS_SAVE_PAGE_AS_MHTML_DESCRIPTION, 750 kOsMac | kOsWin | kOsLinux, 751 SINGLE_VALUE_TYPE(switches::kSavePageAsMHTML) 752 }, 753 { 754 "enable-autologin", 755 IDS_FLAGS_ENABLE_AUTOLOGIN_NAME, 756 IDS_FLAGS_ENABLE_AUTOLOGIN_DESCRIPTION, 757 kOsMac | kOsWin | kOsLinux, 758 SINGLE_VALUE_TYPE(switches::kEnableAutologin) 759 }, 760 { 761 "enable-quic", 762 IDS_FLAGS_ENABLE_QUIC_NAME, 763 IDS_FLAGS_ENABLE_QUIC_DESCRIPTION, 764 kOsAll, 765 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableQuic, 766 switches::kDisableQuic) 767 }, 768 { 769 "enable-quic-https", 770 IDS_FLAGS_ENABLE_QUIC_HTTPS_NAME, 771 IDS_FLAGS_ENABLE_QUIC_HTTPS_DESCRIPTION, 772 kOsAll, 773 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableQuicHttps, 774 switches::kDisableQuicHttps) 775 }, 776 { 777 "enable-spdy4a2", 778 IDS_FLAGS_ENABLE_SPDY4A2_NAME, 779 IDS_FLAGS_ENABLE_SPDY4A2_DESCRIPTION, 780 kOsAll, 781 SINGLE_VALUE_TYPE(switches::kEnableSpdy4a2) 782 }, 783 { 784 "enable-http2-draft-04", 785 IDS_FLAGS_ENABLE_HTTP2_DRAFT_04_NAME, 786 IDS_FLAGS_ENABLE_HTTP2_DRAFT_04_DESCRIPTION, 787 kOsAll, 788 SINGLE_VALUE_TYPE(switches::kEnableHttp2Draft04) 789 }, 790 { 791 "enable-async-dns", 792 IDS_FLAGS_ENABLE_ASYNC_DNS_NAME, 793 IDS_FLAGS_ENABLE_ASYNC_DNS_DESCRIPTION, 794 kOsWin | kOsMac | kOsLinux | kOsCrOS, 795 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableAsyncDns, 796 switches::kDisableAsyncDns) 797 }, 798 { 799 "disable-webkit-media-source", 800 IDS_FLAGS_DISABLE_WEBKIT_MEDIA_SOURCE_NAME, 801 IDS_FLAGS_DISABLE_WEBKIT_MEDIA_SOURCE_DESCRIPTION, 802 kOsAll, 803 SINGLE_VALUE_TYPE(switches::kDisableWebKitMediaSource) 804 }, 805 { 806 "disable-unprefixed-media-source", 807 IDS_FLAGS_DISABLE_UNPREFIXED_MEDIA_SOURCE_NAME, 808 IDS_FLAGS_DISABLE_UNPREFIXED_MEDIA_SOURCE_DESCRIPTION, 809 kOsAll, 810 SINGLE_VALUE_TYPE(switches::kDisableUnprefixedMediaSource) 811 }, 812 { 813 "enable-encrypted-media", 814 IDS_FLAGS_ENABLE_ENCRYPTED_MEDIA_NAME, 815 IDS_FLAGS_ENABLE_ENCRYPTED_MEDIA_DESCRIPTION, 816 kOsAll, 817 SINGLE_VALUE_TYPE(switches::kEnableEncryptedMedia) 818 }, 819 { 820 "disable-prefixed-encrypted-media", 821 IDS_FLAGS_DISABLE_PREFIXED_ENCRYPTED_MEDIA_NAME, 822 IDS_FLAGS_DISABLE_PREFIXED_ENCRYPTED_MEDIA_DESCRIPTION, 823 kOsAll, 824 SINGLE_VALUE_TYPE(switches::kDisablePrefixedEncryptedMedia) 825 }, 826#if defined(OS_ANDROID) 827 { 828 "disable-infobar-for-protected-media-identifier", 829 IDS_FLAGS_DISABLE_INFOBAR_FOR_PROTECTED_MEDIA_IDENTIFIER_NAME, 830 IDS_FLAGS_DISABLE_INFOBAR_FOR_PROTECTED_MEDIA_IDENTIFIER_DESCRIPTION, 831 kOsAndroid, 832 SINGLE_VALUE_TYPE(switches::kDisableInfobarForProtectedMediaIdentifier) 833 }, 834 { 835 "mediadrm-enable-non-compositing", 836 IDS_FLAGS_MEDIADRM_ENABLE_NON_COMPOSITING_NAME, 837 IDS_FLAGS_MEDIADRM_ENABLE_NON_COMPOSITING_DESCRIPTION, 838 kOsAndroid, 839 SINGLE_VALUE_TYPE(switches::kMediaDrmEnableNonCompositing) 840 }, 841#endif // defined(OS_ANDROID) 842 { 843 "enable-opus-playback", 844 IDS_FLAGS_ENABLE_OPUS_PLAYBACK_NAME, 845 IDS_FLAGS_ENABLE_OPUS_PLAYBACK_DESCRIPTION, 846 kOsDesktop, 847 SINGLE_VALUE_TYPE(switches::kEnableOpusPlayback) 848 }, 849 { 850 "disable-vp8-alpha-playback", 851 IDS_FLAGS_DISABLE_VP8_ALPHA_PLAYBACK_NAME, 852 IDS_FLAGS_DISABLE_VP8_ALPHA_PLAYBACK_DESCRIPTION, 853 kOsDesktop, 854 SINGLE_VALUE_TYPE(switches::kDisableVp8AlphaPlayback) 855 }, 856 { 857 "enable-managed-users", 858 IDS_FLAGS_ENABLE_LOCALLY_MANAGED_USERS_NAME, 859 IDS_FLAGS_ENABLE_LOCALLY_MANAGED_USERS_DESCRIPTION, 860 kOsMac | kOsWin | kOsLinux | kOsCrOSOwnerOnly, 861 SINGLE_VALUE_TYPE(switches::kEnableManagedUsers) 862 }, 863 { 864 "per-tile-painting", 865 IDS_FLAGS_PER_TILE_PAINTING_NAME, 866 IDS_FLAGS_PER_TILE_PAINTING_DESCRIPTION, 867 kOsMac | kOsLinux | kOsCrOS, 868 SINGLE_VALUE_TYPE(cc::switches::kEnablePerTilePainting) 869 }, 870 { 871 "enable-javascript-harmony", 872 IDS_FLAGS_ENABLE_JAVASCRIPT_HARMONY_NAME, 873 IDS_FLAGS_ENABLE_JAVASCRIPT_HARMONY_DESCRIPTION, 874 kOsAll, 875 SINGLE_VALUE_TYPE_AND_VALUE(switches::kJavaScriptFlags, "--harmony") 876 }, 877 { 878 "enable-tab-browser-dragging", 879 IDS_FLAGS_ENABLE_TAB_BROWSER_DRAGGING_NAME, 880 IDS_FLAGS_ENABLE_TAB_BROWSER_DRAGGING_DESCRIPTION, 881 kOsWin, 882 SINGLE_VALUE_TYPE(switches::kTabBrowserDragging) 883 }, 884 { 885 "disable-restore-session-state", 886 IDS_FLAGS_DISABLE_RESTORE_SESSION_STATE_NAME, 887 IDS_FLAGS_DISABLE_RESTORE_SESSION_STATE_DESCRIPTION, 888 kOsAll, 889 SINGLE_VALUE_TYPE(switches::kDisableRestoreSessionState) 890 }, 891 { 892 "disable-software-rasterizer", 893 IDS_FLAGS_DISABLE_SOFTWARE_RASTERIZER_NAME, 894 IDS_FLAGS_DISABLE_SOFTWARE_RASTERIZER_DESCRIPTION, 895#if defined(ENABLE_SWIFTSHADER) 896 kOsAll, 897#else 898 0, 899#endif 900 SINGLE_VALUE_TYPE(switches::kDisableSoftwareRasterizer) 901 }, 902 { 903 "enable-experimental-web-platform-features", 904 IDS_FLAGS_EXPERIMENTAL_WEB_PLATFORM_FEATURES_NAME, 905 IDS_FLAGS_EXPERIMENTAL_WEB_PLATFORM_FEATURES_DESCRIPTION, 906 kOsAll, 907 SINGLE_VALUE_TYPE(switches::kEnableExperimentalWebPlatformFeatures) 908 }, 909 { 910 "disable-ntp-other-sessions-menu", 911 IDS_FLAGS_NTP_OTHER_SESSIONS_MENU_NAME, 912 IDS_FLAGS_NTP_OTHER_SESSIONS_MENU_DESCRIPTION, 913 kOsDesktop, 914 SINGLE_VALUE_TYPE(switches::kDisableNTPOtherSessionsMenu) 915 }, 916#if defined(USE_ASH) 917 { 918 "enable-ash-oak", 919 IDS_FLAGS_ENABLE_ASH_OAK_NAME, 920 IDS_FLAGS_ENABLE_ASH_OAK_DESCRIPTION, 921 kOsAll, 922 SINGLE_VALUE_TYPE(ash::switches::kAshEnableOak), 923 }, 924#endif 925 { 926 "enable-devtools-experiments", 927 IDS_FLAGS_ENABLE_DEVTOOLS_EXPERIMENTS_NAME, 928 IDS_FLAGS_ENABLE_DEVTOOLS_EXPERIMENTS_DESCRIPTION, 929 kOsDesktop, 930 SINGLE_VALUE_TYPE(switches::kEnableDevToolsExperiments) 931 }, 932 { 933 "silent-debugger-extension-api", 934 IDS_FLAGS_SILENT_DEBUGGER_EXTENSION_API_NAME, 935 IDS_FLAGS_SILENT_DEBUGGER_EXTENSION_API_DESCRIPTION, 936 kOsDesktop, 937 SINGLE_VALUE_TYPE(switches::kSilentDebuggerExtensionAPI) 938 }, 939 { 940 "enable-suggestions-ntp", 941 IDS_FLAGS_NTP_SUGGESTIONS_PAGE_NAME, 942 IDS_FLAGS_NTP_SUGGESTIONS_PAGE_DESCRIPTION, 943 kOsDesktop, 944 SINGLE_VALUE_TYPE(switches::kEnableSuggestionsTabPage) 945 }, 946 { 947 "spellcheck-autocorrect", 948 IDS_FLAGS_SPELLCHECK_AUTOCORRECT, 949 IDS_FLAGS_SPELLCHECK_AUTOCORRECT_DESCRIPTION, 950 kOsWin | kOsLinux | kOsCrOS, 951 SINGLE_VALUE_TYPE(switches::kEnableSpellingAutoCorrect) 952 }, 953 { 954 "enable-scroll-prediction", 955 IDS_FLAGS_ENABLE_SCROLL_PREDICTION_NAME, 956 IDS_FLAGS_ENABLE_SCROLL_PREDICTION_DESCRIPTION, 957 kOsDesktop, 958 SINGLE_VALUE_TYPE(switches::kEnableScrollPrediction) 959 }, 960 { 961 "touch-events", 962 IDS_TOUCH_EVENTS_NAME, 963 IDS_TOUCH_EVENTS_DESCRIPTION, 964 kOsDesktop, 965 MULTI_VALUE_TYPE(kTouchEventsChoices) 966 }, 967 { 968 "touch-optimized-ui", 969 IDS_FLAGS_TOUCH_OPTIMIZED_UI_NAME, 970 IDS_FLAGS_TOUCH_OPTIMIZED_UI_DESCRIPTION, 971 kOsWin, 972 MULTI_VALUE_TYPE(kTouchOptimizedUIChoices) 973 }, 974 { 975 "disable-touch-adjustment", 976 IDS_DISABLE_TOUCH_ADJUSTMENT_NAME, 977 IDS_DISABLE_TOUCH_ADJUSTMENT_DESCRIPTION, 978 kOsWin | kOsLinux | kOsCrOS, 979 SINGLE_VALUE_TYPE(switches::kDisableTouchAdjustment) 980 }, 981#if defined(OS_CHROMEOS) 982 { 983 "ash-use-alternate-shelf", 984 IDS_FLAGS_ALTERNATE_SHELF_LAYOUT_NAME, 985 IDS_FLAGS_ALTERNATE_SHELF_LAYOUT_DESCRIPTION, 986 kOsCrOS, 987 ENABLE_DISABLE_VALUE_TYPE(ash::switches::kAshUseAlternateShelfLayout, 988 ash::switches::kAshDisableAlternateShelfLayout) 989 }, 990 { 991 "ash-disable-drag-off-shelf", 992 IDS_FLAGS_DRAG_OFF_SHELF_NAME, 993 IDS_FLAGS_DRAG_OFF_SHELF_DESCRIPTION, 994 kOsCrOS, 995 SINGLE_VALUE_TYPE(ash::switches::kAshDisableDragOffShelf) 996 }, 997 { 998 "enable-background-loader", 999 IDS_ENABLE_BACKLOADER_NAME, 1000 IDS_ENABLE_BACKLOADER_DESCRIPTION, 1001 kOsCrOS, 1002 SINGLE_VALUE_TYPE(chromeos::switches::kEnableBackgroundLoader) 1003 }, 1004 { 1005 "ash-enable-docked-windows", 1006 IDS_FLAGS_DOCKED_WINDOWS_NAME, 1007 IDS_FLAGS_DOCKED_WINDOWS_DESCRIPTION, 1008 kOsCrOS, 1009 SINGLE_VALUE_TYPE(ash::switches::kAshEnableDockedWindows) 1010 }, 1011#endif 1012 { 1013 "enable-download-resumption", 1014 IDS_FLAGS_ENABLE_DOWNLOAD_RESUMPTION_NAME, 1015 IDS_FLAGS_ENABLE_DOWNLOAD_RESUMPTION_DESCRIPTION, 1016 kOsDesktop, 1017 SINGLE_VALUE_TYPE(switches::kEnableDownloadResumption) 1018 }, 1019 { 1020 "allow-nacl-socket-api", 1021 IDS_FLAGS_ALLOW_NACL_SOCKET_API_NAME, 1022 IDS_FLAGS_ALLOW_NACL_SOCKET_API_DESCRIPTION, 1023 kOsDesktop, 1024 SINGLE_VALUE_TYPE_AND_VALUE(switches::kAllowNaClSocketAPI, "*") 1025 }, 1026 { 1027 "stacked-tab-strip", 1028 IDS_FLAGS_STACKED_TAB_STRIP_NAME, 1029 IDS_FLAGS_STACKED_TAB_STRIP_DESCRIPTION, 1030 kOsWin, 1031 SINGLE_VALUE_TYPE(switches::kEnableStackedTabStrip) 1032 }, 1033 { 1034 "force-device-scale-factor", 1035 IDS_FLAGS_FORCE_HIGH_DPI_NAME, 1036 IDS_FLAGS_FORCE_HIGH_DPI_DESCRIPTION, 1037 kOsCrOS, 1038 SINGLE_VALUE_TYPE_AND_VALUE(switches::kForceDeviceScaleFactor, "2") 1039 }, 1040#if defined(OS_CHROMEOS) 1041 { 1042 "allow-touchpad-three-finger-click", 1043 IDS_FLAGS_ALLOW_TOUCHPAD_THREE_FINGER_CLICK_NAME, 1044 IDS_FLAGS_ALLOW_TOUCHPAD_THREE_FINGER_CLICK_DESCRIPTION, 1045 kOsCrOS, 1046 SINGLE_VALUE_TYPE(chromeos::switches::kEnableTouchpadThreeFingerClick) 1047 }, 1048#endif 1049#if defined(USE_ASH) 1050 { 1051 "show-launcher-alignment-menu", 1052 IDS_FLAGS_SHOW_SHELF_ALIGNMENT_MENU_NAME, 1053 IDS_FLAGS_SHOW_SHELF_ALIGNMENT_MENU_DESCRIPTION, 1054 kOsAll, 1055 ENABLE_DISABLE_VALUE_TYPE( 1056 ash::switches::kShowShelfAlignmentMenu, 1057 ash::switches::kHideShelfAlignmentMenu) 1058 }, 1059 { 1060 "disable-minimize-on-second-launcher-item-click", 1061 IDS_FLAGS_DISABLE_MINIMIZE_ON_SECOND_LAUNCHER_ITEM_CLICK_NAME, 1062 IDS_FLAGS_DISABLE_MINIMIZE_ON_SECOND_LAUNCHER_ITEM_CLICK_DESCRIPTION, 1063 kOsAll, 1064 SINGLE_VALUE_TYPE(switches::kDisableMinimizeOnSecondLauncherItemClick) 1065 }, 1066 { 1067 "disable-overview-mode", 1068 IDS_FLAGS_DISABLE_OVERVIEW_MODE_NAME, 1069 IDS_FLAGS_DISABLE_OVERVIEW_MODE_DESCRIPTION, 1070 kOsCrOS, 1071 SINGLE_VALUE_TYPE(ash::switches::kAshDisableOverviewMode) 1072 }, 1073 { 1074 "overview-delay-on-alt-tab", 1075 IDS_FLAGS_OVERVIEW_DELAY_NAME, 1076 IDS_FLAGS_OVERVIEW_DELAY_DESCRIPTION, 1077 kOsCrOS, 1078 MULTI_VALUE_TYPE(kAshOverviewDelayChoices) 1079 }, 1080 { 1081 "show-touch-hud", 1082 IDS_FLAGS_SHOW_TOUCH_HUD_NAME, 1083 IDS_FLAGS_SHOW_TOUCH_HUD_DESCRIPTION, 1084 kOsAll, 1085 SINGLE_VALUE_TYPE(ash::switches::kAshTouchHud) 1086 }, 1087 { 1088 "enable-pinch", 1089 IDS_FLAGS_ENABLE_PINCH_SCALE_NAME, 1090 IDS_FLAGS_ENABLE_PINCH_SCALE_DESCRIPTION, 1091 kOsLinux | kOsWin | kOsCrOS, 1092 ENABLE_DISABLE_VALUE_TYPE(switches::kEnablePinch, switches::kDisablePinch), 1093 }, 1094 { 1095 "enable-pinch-virtual-viewport", 1096 IDS_FLAGS_ENABLE_PINCH_VIRTUAL_VIEWPORT_NAME, 1097 IDS_FLAGS_ENABLE_PINCH_VIRTUAL_VIEWPORT_DESCRIPTION, 1098 kOsLinux | kOsWin | kOsCrOS, 1099 SINGLE_VALUE_TYPE(cc::switches::kEnablePinchVirtualViewport), 1100 }, 1101#endif // defined(USE_ASH) 1102#if defined(OS_CHROMEOS) 1103 { 1104 "disable-boot-animation", 1105 IDS_FLAGS_DISABLE_BOOT_ANIMATION, 1106 IDS_FLAGS_DISABLE_BOOT_ANIMATION_DESCRIPTION, 1107 kOsCrOSOwnerOnly, 1108 SINGLE_VALUE_TYPE(chromeos::switches::kDisableBootAnimation), 1109 }, 1110 { 1111 "captive-portal-detector", 1112 IDS_FLAGS_CAPTIVE_PORTAL_DETECTOR_NAME, 1113 IDS_FLAGS_CAPTIVE_PORTAL_DETECTOR_DESCRIPTION, 1114 kOsCrOSOwnerOnly, 1115 MULTI_VALUE_TYPE(kChromeCaptivePortalDetectionChoices), 1116 }, 1117 { 1118 "file-manager-show-checkboxes", 1119 IDS_FLAGS_FILE_MANAGER_SHOW_CHECKBOXES_NAME, 1120 IDS_FLAGS_FILE_MANAGER_SHOW_CHECKBOXES_DESCRIPTION, 1121 kOsCrOS, 1122 SINGLE_VALUE_TYPE(chromeos::switches::kFileManagerShowCheckboxes) 1123 }, 1124 { 1125 "file-manager-enable-webstore-integration", 1126 IDS_FLAGS_FILE_MANAGER_ENABLE_WEBSTORE_INTEGRATION, 1127 IDS_FLAGS_FILE_MANAGER_ENABLE_WEBSTORE_INTEGRATION_DESCRIPTION, 1128 kOsCrOS, 1129 SINGLE_VALUE_TYPE(chromeos::switches::kFileManagerEnableWebstoreIntegration) 1130 }, 1131 { 1132 "disable-quickoffice-component-app", 1133 IDS_FLAGS_DISABLE_QUICKOFFICE_COMPONENT_APP_NAME, 1134 IDS_FLAGS_DISABLE_QUICKOFFICE_COMPONENT_APP_DESCRIPTION, 1135 kOsCrOS, 1136 SINGLE_VALUE_TYPE(chromeos::switches::kDisableQuickofficeComponentApp), 1137 }, 1138 { 1139 "enable-saml-signin", 1140 IDS_FLAGS_ENABLE_SAML_SIGNIN_NAME, 1141 IDS_FLAGS_ENABLE_SAML_SIGNIN_DESCRIPTION, 1142 kOsCrOS, 1143 SINGLE_VALUE_TYPE(chromeos::switches::kEnableSamlSignin), 1144 }, 1145 { 1146 "enable-multi-profiles", 1147 IDS_FLAGS_ENABLE_MULTI_PROFILES_NAME, 1148 IDS_FLAGS_ENABLE_MULTI_PROFILES_DESCRIPTION, 1149 kOsCrOS, 1150 SINGLE_VALUE_TYPE(switches::kMultiProfiles), 1151 }, 1152#endif // defined(OS_CHROMEOS) 1153 { 1154 "views-textfield", 1155 IDS_FLAGS_VIEWS_TEXTFIELD_NAME, 1156 IDS_FLAGS_VIEWS_TEXTFIELD_DESCRIPTION, 1157 kOsWin, 1158 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableViewsTextfield, 1159 switches::kDisableViewsTextfield), 1160 }, 1161 { "disable-accelerated-video-decode", 1162 IDS_FLAGS_DISABLE_ACCELERATED_VIDEO_DECODE_NAME, 1163 IDS_FLAGS_DISABLE_ACCELERATED_VIDEO_DECODE_DESCRIPTION, 1164 kOsWin | kOsCrOS, 1165 SINGLE_VALUE_TYPE(switches::kDisableAcceleratedVideoDecode), 1166 }, 1167 { 1168 "enable-contacts", 1169 IDS_FLAGS_ENABLE_CONTACTS_NAME, 1170 IDS_FLAGS_ENABLE_CONTACTS_DESCRIPTION, 1171 kOsCrOS, 1172 SINGLE_VALUE_TYPE(switches::kEnableContacts) 1173 }, 1174#if defined(USE_ASH) 1175 { 1176 "ash-debug-shortcuts", 1177 IDS_FLAGS_DEBUG_SHORTCUTS_NAME, 1178 IDS_FLAGS_DEBUG_SHORTCUTS_DESCRIPTION, 1179 kOsAll, 1180 SINGLE_VALUE_TYPE(ash::switches::kAshDebugShortcuts), 1181 }, 1182 { "ash-enable-advanced-gestures", 1183 IDS_FLAGS_ENABLE_ADVANCED_GESTURES_NAME, 1184 IDS_FLAGS_ENABLE_ADVANCED_GESTURES_DESCRIPTION, 1185 kOsCrOS, 1186 SINGLE_VALUE_TYPE(ash::switches::kAshEnableAdvancedGestures), 1187 }, 1188 { "ash-alternate-caption-button", 1189 IDS_FLAGS_ASH_FRAME_CAPTION_BUTTON_STYLE_NAME, 1190 IDS_FLAGS_ASH_FRAME_CAPTION_BUTTON_STYLE_DESCRIPTION, 1191 kOsCrOS, 1192 ENABLE_DISABLE_VALUE_TYPE( 1193 ash::switches::kAshEnableAlternateFrameCaptionButtonStyle, 1194 ash::switches::kAshDisableAlternateFrameCaptionButtonStyle), 1195 }, 1196 { 1197 "ash-disable-auto-maximizing", 1198 IDS_FLAGS_ASH_AUTO_MAXIMIZING_NAME, 1199 IDS_FLAGS_ASH_AUTO_MAXIMIZING_DESCRIPTION, 1200 kOsWin | kOsLinux | kOsCrOS, 1201 SINGLE_VALUE_TYPE(ash::switches::kAshDisableAutoMaximizing) 1202 }, 1203 { "ash-disable-drag-and-drop-applist-to-launcher", 1204 IDS_FLAGS_DND_APPLIST_TO_LAUNCHER_NAME, 1205 IDS_FLAGS_DND_APPLIST_TO_LAUNCHER_DESCRIPTION, 1206 kOsCrOS, 1207 SINGLE_VALUE_TYPE(ash::switches::kAshDisableDragAndDropAppListToLauncher), 1208 }, 1209#if defined(OS_LINUX) 1210 { "ash-enable-memory-monitor", 1211 IDS_FLAGS_ENABLE_MEMORY_MONITOR_NAME, 1212 IDS_FLAGS_ENABLE_MEMORY_MONITOR_DESCRIPTION, 1213 kOsCrOS, 1214 SINGLE_VALUE_TYPE(ash::switches::kAshEnableMemoryMonitor), 1215 }, 1216#endif 1217#if defined(OS_CHROMEOS) 1218 { "ash-enable-full-multi-profile-mode", 1219 IDS_FLAGS_ENABLE_FULL_MULTI_PROFILE_MODE, 1220 IDS_FLAGS_ENABLE_FULL_MULTI_PROFILE_MODE_DESCRIPTION, 1221 kOsCrOS, 1222 SINGLE_VALUE_TYPE(ash::switches::kAshEnableFullMultiProfileMode), 1223 }, 1224#endif 1225#endif 1226#if defined(OS_CHROMEOS) 1227 { 1228 "ash-audio-device-menu", 1229 IDS_FLAGS_ASH_AUDIO_DEVICE_MENU_NAME, 1230 IDS_FLAGS_ASH_AUDIO_DEVICE_MENU_DESCRIPTION, 1231 kOsCrOS, 1232 ENABLE_DISABLE_VALUE_TYPE(ash::switches::kAshEnableAudioDeviceMenu, 1233 ash::switches::kAshDisableAudioDeviceMenu) 1234 }, 1235 { 1236 "enable-carrier-switching", 1237 IDS_FLAGS_ENABLE_CARRIER_SWITCHING, 1238 IDS_FLAGS_ENABLE_CARRIER_SWITCHING_DESCRIPTION, 1239 kOsCrOS, 1240 SINGLE_VALUE_TYPE(chromeos::switches::kEnableCarrierSwitching) 1241 }, 1242 { 1243 "enable-request-tablet-site", 1244 IDS_FLAGS_ENABLE_REQUEST_TABLET_SITE_NAME, 1245 IDS_FLAGS_ENABLE_REQUEST_TABLET_SITE_DESCRIPTION, 1246 kOsCrOS, 1247 SINGLE_VALUE_TYPE(chromeos::switches::kEnableRequestTabletSite) 1248 }, 1249#endif 1250 { 1251 "debug-packed-apps", 1252 IDS_FLAGS_DEBUG_PACKED_APP_NAME, 1253 IDS_FLAGS_DEBUG_PACKED_APP_DESCRIPTION, 1254 kOsDesktop, 1255 SINGLE_VALUE_TYPE(switches::kDebugPackedApps) 1256 }, 1257 { 1258 "enable-password-generation", 1259 IDS_FLAGS_ENABLE_PASSWORD_GENERATION_NAME, 1260 IDS_FLAGS_ENABLE_PASSWORD_GENERATION_DESCRIPTION, 1261 kOsDesktop, 1262 ENABLE_DISABLE_VALUE_TYPE(autofill::switches::kEnablePasswordGeneration, 1263 autofill::switches::kDisablePasswordGeneration) 1264 }, 1265 { 1266 "enable-password-manager-reauthentication", 1267 IDS_FLAGS_PASSWORD_MANAGER_REAUTHENTICATION_NAME, 1268 IDS_FLAGS_PASSWORD_MANAGER_REAUTHENTICATION_DESCRIPTION, 1269 kOsMac, 1270 SINGLE_VALUE_TYPE(switches::kEnablePasswordManagerReauthentication) 1271 }, 1272 { 1273 "password-autofill-public-suffix-domain-matching", 1274 IDS_FLAGS_PASSWORD_AUTOFILL_PUBLIC_SUFFIX_DOMAIN_MATCHING_NAME, 1275 IDS_FLAGS_PASSWORD_AUTOFILL_PUBLIC_SUFFIX_DOMAIN_MATCHING_DESCRIPTION, 1276 kOsAndroid, 1277 ENABLE_DISABLE_VALUE_TYPE( 1278 switches::kEnablePasswordAutofillPublicSuffixDomainMatching, 1279 switches::kDisablePasswordAutofillPublicSuffixDomainMatching) 1280 }, 1281 { 1282 "enable-deferred-image-decoding", 1283 IDS_FLAGS_ENABLE_DEFERRED_IMAGE_DECODING_NAME, 1284 IDS_FLAGS_ENABLE_DEFERRED_IMAGE_DECODING_DESCRIPTION, 1285 kOsMac | kOsLinux | kOsCrOS, 1286 SINGLE_VALUE_TYPE(switches::kEnableDeferredImageDecoding) 1287 }, 1288 { 1289 "performance-monitor-gathering", 1290 IDS_FLAGS_PERFORMANCE_MONITOR_GATHERING_NAME, 1291 IDS_FLAGS_PERFORMANCE_MONITOR_GATHERING_DESCRIPTION, 1292 kOsAll, 1293 SINGLE_VALUE_TYPE(switches::kPerformanceMonitorGathering) 1294 }, 1295 { 1296 "enable-experimental-form-filling", 1297 IDS_FLAGS_ENABLE_EXPERIMENTAL_FORM_FILLING_NAME, 1298 IDS_FLAGS_ENABLE_EXPERIMENTAL_FORM_FILLING_DESCRIPTION, 1299 kOsWin | kOsCrOS, 1300 SINGLE_VALUE_TYPE(autofill::switches::kEnableExperimentalFormFilling) 1301 }, 1302 { 1303 "wallet-service-use-sandbox", 1304 IDS_FLAGS_WALLET_SERVICE_USE_SANDBOX_NAME, 1305 IDS_FLAGS_WALLET_SERVICE_USE_SANDBOX_DESCRIPTION, 1306 kOsCrOS | kOsWin | kOsMac, 1307 ENABLE_DISABLE_VALUE_TYPE_AND_VALUE( 1308 autofill::switches::kWalletServiceUseSandbox, "1", 1309 autofill::switches::kWalletServiceUseSandbox, "0") 1310 }, 1311 { 1312 "enable-interactive-autocomplete", 1313 IDS_FLAGS_ENABLE_INTERACTIVE_AUTOCOMPLETE_NAME, 1314 IDS_FLAGS_ENABLE_INTERACTIVE_AUTOCOMPLETE_DESCRIPTION, 1315 kOsWin | kOsCrOS | kOsAndroid | kOsMac, 1316 ENABLE_DISABLE_VALUE_TYPE( 1317 autofill::switches::kEnableInteractiveAutocomplete, 1318 autofill::switches::kDisableInteractiveAutocomplete) 1319 }, 1320#if defined(USE_AURA) 1321 { 1322 "overscroll-history-navigation", 1323 IDS_FLAGS_OVERSCROLL_HISTORY_NAVIGATION_NAME, 1324 IDS_FLAGS_OVERSCROLL_HISTORY_NAVIGATION_DESCRIPTION, 1325 kOsAll, 1326 ENABLE_DISABLE_VALUE_TYPE_AND_VALUE( 1327 switches::kOverscrollHistoryNavigation, "1", 1328 switches::kOverscrollHistoryNavigation, "0") 1329 }, 1330#endif 1331 { 1332 "scroll-end-effect", 1333 IDS_FLAGS_SCROLL_END_EFFECT_NAME, 1334 IDS_FLAGS_SCROLL_END_EFFECT_DESCRIPTION, 1335 kOsCrOS, 1336 ENABLE_DISABLE_VALUE_TYPE_AND_VALUE( 1337 switches::kScrollEndEffect, "1", 1338 switches::kScrollEndEffect, "0") 1339 }, 1340 { 1341 "enable-touch-side-bezels", 1342 IDS_FLAGS_ENABLE_TOUCH_SIDE_BEZELS_NAME, 1343 IDS_FLAGS_ENABLE_TOUCH_SIDE_BEZELS_DESCRIPTION, 1344 kOsCrOS, 1345 ENABLE_DISABLE_VALUE_TYPE_AND_VALUE( 1346 switches::kTouchSideBezels, "1", 1347 switches::kTouchSideBezels, "0") 1348 }, 1349 { 1350 "enable-touch-drag-drop", 1351 IDS_FLAGS_ENABLE_TOUCH_DRAG_DROP_NAME, 1352 IDS_FLAGS_ENABLE_TOUCH_DRAG_DROP_DESCRIPTION, 1353 kOsWin | kOsCrOS, 1354 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableTouchDragDrop, 1355 switches::kDisableTouchDragDrop) 1356 }, 1357 { 1358 "enable-touch-editing", 1359 IDS_FLAGS_ENABLE_TOUCH_EDITING_NAME, 1360 IDS_FLAGS_ENABLE_TOUCH_EDITING_DESCRIPTION, 1361 kOsCrOS, 1362 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableTouchEditing, 1363 switches::kDisableTouchEditing) 1364 }, 1365 { 1366 "enable-rich-notifications", 1367 IDS_FLAGS_ENABLE_RICH_NOTIFICATIONS_NAME, 1368 IDS_FLAGS_ENABLE_RICH_NOTIFICATIONS_DESCRIPTION, 1369 kOsWin | kOsMac, 1370 ENABLE_DISABLE_VALUE_TYPE( 1371 message_center::switches::kEnableRichNotifications, 1372 message_center::switches::kDisableRichNotifications) 1373 }, 1374 { 1375 "enable-sync-synced-notifications", 1376 IDS_FLAGS_ENABLE_SYNCED_NOTIFICATIONS_NAME, 1377 IDS_FLAGS_ENABLE_SYNCED_NOTIFICATIONS_DESCRIPTION, 1378 kOsDesktop, 1379 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableSyncSyncedNotifications, 1380 switches::kDisableSyncSyncedNotifications) 1381 }, 1382 { 1383 "disable-full-history-sync", 1384 IDS_FLAGS_FULL_HISTORY_SYNC_NAME, 1385 IDS_FLAGS_FULL_HISTORY_SYNC_DESCRIPTION, 1386 kOsAll, 1387 SINGLE_VALUE_TYPE(switches::kHistoryDisableFullHistorySync) 1388 }, 1389 { 1390 "enable-usermedia-screen-capture", 1391 IDS_FLAGS_ENABLE_SCREEN_CAPTURE_NAME, 1392 IDS_FLAGS_ENABLE_SCREEN_CAPTURE_DESCRIPTION, 1393 kOsDesktop, 1394 SINGLE_VALUE_TYPE(switches::kEnableUserMediaScreenCapturing) 1395 }, 1396 { 1397 "enable-apps-devtool-app", 1398 IDS_FLAGS_ENABLE_APPS_DEVTOOL_APP_NAME, 1399 IDS_FLAGS_ENABLE_APPS_DEVTOOL_APP_DESCRIPTION, 1400 kOsDesktop, 1401 SINGLE_VALUE_TYPE(switches::kAppsDevtool) 1402 }, 1403 { 1404 "impl-side-painting", 1405 IDS_FLAGS_IMPL_SIDE_PAINTING_NAME, 1406 IDS_FLAGS_IMPL_SIDE_PAINTING_DESCRIPTION, 1407 kOsAndroid | kOsLinux | kOsCrOS, 1408 MULTI_VALUE_TYPE(kImplSidePaintingChoices) 1409 }, 1410 { 1411 "deadline-scheduling", 1412 IDS_FLAGS_DEADLINE_SCHEDULING_NAME, 1413 IDS_FLAGS_DEADLINE_SCHEDULING_DESCRIPTION, 1414 kOsMac | kOsWin | kOsLinux | kOsCrOS | kOsAndroid, 1415 MULTI_VALUE_TYPE(kDeadlineSchedulingChoices) 1416 }, 1417 { 1418 "ui-deadline-scheduling", 1419 IDS_FLAGS_UI_DEADLINE_SCHEDULING_NAME, 1420 IDS_FLAGS_UI_DEADLINE_SCHEDULING_DESCRIPTION, 1421#ifdef USE_AURA 1422 kOsWin | kOsLinux | 1423#endif 1424 kOsCrOS, 1425 MULTI_VALUE_TYPE(kUIDeadlineSchedulingChoices) 1426 }, 1427 { 1428 "lcd-text-aa", 1429 IDS_FLAGS_LCD_TEXT_NAME, 1430 IDS_FLAGS_LCD_TEXT_DESCRIPTION, 1431 kOsDesktop, 1432 MULTI_VALUE_TYPE(kLCDTextChoices) 1433 }, 1434 { 1435 "delegated-renderer", 1436 IDS_FLAGS_DELEGATED_RENDERER_NAME, 1437 IDS_FLAGS_DELEGATED_RENDERER_DESCRIPTION, 1438#ifdef USE_AURA 1439 kOsWin | kOsLinux | 1440#endif 1441 kOsAndroid | kOsCrOS, 1442 MULTI_VALUE_TYPE(kDelegatedRendererChoices) 1443 }, 1444 { 1445 "enable-websocket-experimental-implementation", 1446 IDS_FLAGS_ENABLE_EXPERIMENTAL_WEBSOCKET_NAME, 1447 IDS_FLAGS_ENABLE_EXPERIMENTAL_WEBSOCKET_DESCRIPTION, 1448 kOsAll, 1449 SINGLE_VALUE_TYPE(switches::kEnableExperimentalWebSocket) 1450 }, 1451 { 1452 "max-tiles-for-interest-area", 1453 IDS_FLAGS_MAX_TILES_FOR_INTEREST_AREA_NAME, 1454 IDS_FLAGS_MAX_TILES_FOR_INTEREST_AREA_DESCRIPTION, 1455 kOsAndroid | kOsLinux | kOsCrOS, 1456 MULTI_VALUE_TYPE(kMaxTilesForInterestAreaChoices) 1457 }, 1458 { 1459 "enable-offline-mode", 1460 IDS_FLAGS_ENABLE_OFFLINE_MODE_NAME, 1461 IDS_FLAGS_ENABLE_OFFLINE_MODE_DESCRIPTION, 1462 kOsAll, 1463 SINGLE_VALUE_TYPE(switches::kEnableOfflineCacheAccess) 1464 }, 1465 { 1466 "default-tile-width", 1467 IDS_FLAGS_DEFAULT_TILE_WIDTH_NAME, 1468 IDS_FLAGS_DEFAULT_TILE_WIDTH_DESCRIPTION, 1469 kOsAll, 1470 MULTI_VALUE_TYPE(kDefaultTileWidthChoices) 1471 }, 1472 { 1473 "default-tile-height", 1474 IDS_FLAGS_DEFAULT_TILE_HEIGHT_NAME, 1475 IDS_FLAGS_DEFAULT_TILE_HEIGHT_DESCRIPTION, 1476 kOsAll, 1477 MULTI_VALUE_TYPE(kDefaultTileHeightChoices) 1478 }, 1479 // TODO(sky): ifdef needed until focus sorted out in DesktopNativeWidgetAura. 1480#if !defined(USE_AURA) 1481 { 1482 "track-active-visit-time", 1483 IDS_FLAGS_TRACK_ACTIVE_VISIT_TIME_NAME, 1484 IDS_FLAGS_TRACK_ACTIVE_VISIT_TIME_DESCRIPTION, 1485 kOsWin, 1486 SINGLE_VALUE_TYPE(switches::kTrackActiveVisitTime) 1487 }, 1488#endif 1489#if defined(OS_ANDROID) 1490 { 1491 "disable-gesture-requirement-for-media-playback", 1492 IDS_FLAGS_DISABLE_GESTURE_REQUIREMENT_FOR_MEDIA_PLAYBACK_NAME, 1493 IDS_FLAGS_DISABLE_GESTURE_REQUIREMENT_FOR_MEDIA_PLAYBACK_DESCRIPTION, 1494 kOsAndroid, 1495 SINGLE_VALUE_TYPE(switches::kDisableGestureRequirementForMediaPlayback) 1496 }, 1497#endif 1498#if defined(ENABLE_GOOGLE_NOW) 1499 { 1500 "enable-google-now", 1501 IDS_FLAGS_ENABLE_GOOGLE_NOW_INTEGRATION_NAME, 1502 IDS_FLAGS_ENABLE_GOOGLE_NOW_INTEGRATION_DESCRIPTION, 1503 kOsWin | kOsCrOS | kOsMac, 1504 ENABLE_DISABLE_VALUE_TYPE( 1505 switches::kEnableGoogleNowIntegration, 1506 switches::kDisableGoogleNowIntegration) 1507 }, 1508#endif 1509#if defined(OS_CHROMEOS) 1510 { 1511 "enable-virtual-keyboard", 1512 IDS_FLAGS_ENABLE_VIRTUAL_KEYBOARD_NAME, 1513 IDS_FLAGS_ENABLE_VIRTUAL_KEYBOARD_DESCRIPTION, 1514 kOsCrOS, 1515 SINGLE_VALUE_TYPE(keyboard::switches::kEnableVirtualKeyboard) 1516 }, 1517 { 1518 "enable-swipe-selection", 1519 IDS_FLAGS_ENABLE_SWIPE_SELECTION_NAME, 1520 IDS_FLAGS_ENABLE_SWIPE_SELECTION_DESCRIPTION, 1521 kOsCrOS, 1522 SINGLE_VALUE_TYPE(keyboard::switches::kEnableSwipeSelection) 1523 }, 1524#endif 1525 { 1526 "enable-simple-cache-backend", 1527 IDS_FLAGS_ENABLE_SIMPLE_CACHE_BACKEND_NAME, 1528 IDS_FLAGS_ENABLE_SIMPLE_CACHE_BACKEND_DESCRIPTION, 1529 kOsAll, 1530 MULTI_VALUE_TYPE(kSimpleCacheBackendChoices) 1531 }, 1532 { 1533 "enable-tcp-fast-open", 1534 IDS_FLAGS_ENABLE_TCP_FAST_OPEN_NAME, 1535 IDS_FLAGS_ENABLE_TCP_FAST_OPEN_DESCRIPTION, 1536 kOsLinux | kOsCrOS | kOsAndroid, 1537 SINGLE_VALUE_TYPE(switches::kEnableTcpFastOpen) 1538 }, 1539 { 1540 "apps-use-native-frame", 1541 IDS_FLAGS_ENABLE_NATIVE_FRAMES_FOR_APPS_NAME, 1542 IDS_FLAGS_ENABLE_NATIVE_FRAMES_FOR_APPS_DESCRIPTION, 1543 kOsMac | kOsWin, 1544 SINGLE_VALUE_TYPE(switches::kAppsUseNativeFrame) 1545 }, 1546 { 1547 "enable-syncfs-directory-operation", 1548 IDS_FLAGS_ENABLE_SYNC_DIRECTORY_OPERATION_NAME, 1549 IDS_FLAGS_ENABLE_SYNC_DIRECTORY_OPERATION_DESCRIPTION, 1550 kOsAll, 1551 SINGLE_VALUE_TYPE(switches::kSyncfsEnableDirectoryOperation), 1552 }, 1553#if defined(ENABLE_MDNS) 1554 { 1555 "disable-device-discovery", 1556 IDS_FLAGS_DISABLE_DEVICE_DISCOVERY_NAME, 1557 IDS_FLAGS_DISABLE_DEVICE_DISCOVERY_DESCRIPTION, 1558 kOsWin | kOsLinux | kOsCrOS, 1559 SINGLE_VALUE_TYPE(switches::kDisableDeviceDiscovery) 1560 }, 1561 { 1562 "device-discovery-notifications", 1563 IDS_FLAGS_DEVICE_DISCOVERY_NOTIFICATIONS_NAME, 1564 IDS_FLAGS_DEVICE_DISCOVERY_NOTIFICATIONS_DESCRIPTION, 1565 kOsWin | kOsLinux | kOsCrOS, 1566 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableDeviceDiscoveryNotifications, 1567 switches::kDisableDeviceDiscoveryNotifications) 1568 }, 1569 { 1570 "enable-privet-local-printing", 1571 IDS_FLAGS_ENABLE_PRIVET_LOCAL_PRINTING_NAME, 1572 IDS_FLAGS_ENABLE_PRIVET_LOCAL_PRINTING_DESCRIPTION, 1573 kOsWin | kOsLinux | kOsCrOS, 1574 SINGLE_VALUE_TYPE(switches::kEnablePrivetLocalPrinting) 1575 }, 1576#endif // ENABLE_MDNS 1577#if defined(OS_MACOSX) 1578 { 1579 "enable-app-shims", 1580 IDS_FLAGS_ENABLE_APP_SHIMS_NAME, 1581 IDS_FLAGS_ENABLE_APP_SHIMS_DESCRIPTION, 1582 kOsMac, 1583 SINGLE_VALUE_TYPE(switches::kEnableAppShims) 1584 }, 1585 { 1586 "enable-simplified-fullscreen", 1587 IDS_FLAGS_ENABLE_SIMPLIFIED_FULLSCREEN_NAME, 1588 IDS_FLAGS_ENABLE_SIMPLIFIED_FULLSCREEN_DESCRIPTION, 1589 kOsMac, 1590 SINGLE_VALUE_TYPE(switches::kEnableSimplifiedFullscreen) 1591 }, 1592#endif 1593#if defined(OS_CHROMEOS) || defined(OS_WIN) 1594 { 1595 "omnibox-auto-completion-for-ime", 1596 IDS_FLAGS_ENABLE_OMNIBOX_AUTO_COMPLETION_FOR_IME_NAME, 1597 IDS_FLAGS_ENABLE_OMNIBOX_AUTO_COMPLETION_FOR_IME_DESCRIPTION, 1598 kOsCrOS | kOsWin, 1599 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableOmniboxAutoCompletionForIme, 1600 switches::kDisableOmniboxAutoCompletionForIme) 1601 }, 1602#endif 1603#if defined(USE_AURA) 1604 { 1605 "tab-capture-upscale-quality", 1606 IDS_FLAGS_TAB_CAPTURE_UPSCALE_QUALITY_NAME, 1607 IDS_FLAGS_TAB_CAPTURE_UPSCALE_QUALITY_DESCRIPTION, 1608 kOsAll, 1609 MULTI_VALUE_TYPE(kTabCaptureUpscaleQualityChoices) 1610 }, 1611 { 1612 "tab-capture-downscale-quality", 1613 IDS_FLAGS_TAB_CAPTURE_DOWNSCALE_QUALITY_NAME, 1614 IDS_FLAGS_TAB_CAPTURE_DOWNSCALE_QUALITY_DESCRIPTION, 1615 kOsAll, 1616 MULTI_VALUE_TYPE(kTabCaptureDownscaleQualityChoices) 1617 }, 1618#endif 1619 { 1620 "enable-spelling-service-feedback", 1621 IDS_FLAGS_ENABLE_SPELLING_SERVICE_FEEDBACK_NAME, 1622 IDS_FLAGS_ENABLE_SPELLING_SERVICE_FEEDBACK_DESCRIPTION, 1623 kOsAll, 1624 SINGLE_VALUE_TYPE(switches::kEnableSpellingServiceFeedback) 1625 }, 1626 { 1627 "enable-webgl-draft-extensions", 1628 IDS_FLAGS_ENABLE_WEBGL_DRAFT_EXTENSIONS_NAME, 1629 IDS_FLAGS_ENABLE_WEBGL_DRAFT_EXTENSIONS_DESCRIPTION, 1630 kOsAll, 1631 SINGLE_VALUE_TYPE(switches::kEnableWebGLDraftExtensions) 1632 }, 1633 { 1634 "enable-html-imports", 1635 IDS_FLAGS_ENABLE_HTML_IMPORTS_NAME, 1636 IDS_FLAGS_ENABLE_HTML_IMPORTS_DESCRIPTION, 1637 kOsAll, 1638 SINGLE_VALUE_TYPE(switches::kEnableHTMLImports) 1639 }, 1640 { 1641 "high-dpi-support", 1642 IDS_FLAGS_HIDPI_NAME, 1643 IDS_FLAGS_HIDPI_DESCRIPTION, 1644 kOsWin, 1645 ENABLE_DISABLE_VALUE_TYPE_AND_VALUE(switches::kHighDPISupport, "1", 1646 switches::kHighDPISupport, "0") 1647 }, 1648#if defined(OS_CHROMEOS) 1649 { 1650 "enable-quickoffice-viewing", 1651 IDS_FLAGS_ENABLE_QUICKOFFICE_DESKTOP_VIEWING_NAME, 1652 IDS_FLAGS_ENABLE_QUICKOFFICE_DESKTOP_VIEWING_DESCRIPTION, 1653 kOsCrOS, 1654 SINGLE_VALUE_TYPE(switches::kEnableQuickofficeViewing), 1655 }, 1656 { 1657 "enable-sticky-keys", 1658 IDS_FLAGS_ENABLE_STICKY_KEYS_NAME, 1659 IDS_FLAGS_ENABLE_STICKY_KEYS_DESCRIPTION, 1660 kOsCrOS, 1661 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableStickyKeys, 1662 switches::kDisableStickyKeys) 1663 }, 1664#endif 1665 { 1666 "enable-web-midi", 1667 IDS_FLAGS_ENABLE_WEB_MIDI_NAME, 1668 IDS_FLAGS_ENABLE_WEB_MIDI_DESCRIPTION, 1669 kOsMac, 1670 SINGLE_VALUE_TYPE(switches::kEnableWebMIDI) 1671 }, 1672 { 1673 "enable-new-profile-management", 1674 IDS_FLAGS_ENABLE_NEW_PROFILE_MANAGEMENT_NAME, 1675 IDS_FLAGS_ENABLE_NEW_PROFILE_MANAGEMENT_DESCRIPTION, 1676 kOsWin, 1677 SINGLE_VALUE_TYPE(switches::kNewProfileManagement) 1678 }, 1679 { 1680 "enable-inline-signin", 1681 IDS_FLAGS_ENABLE_INLINE_SIGNIN_NAME, 1682 IDS_FLAGS_ENABLE_INLINE_SIGNIN_DESCRIPTION, 1683 kOsMac | kOsWin | kOsLinux, 1684 SINGLE_VALUE_TYPE(switches::kEnableInlineSignin) 1685 }, 1686 { 1687 "enable-google-profile-info", 1688 IDS_FLAGS_ENABLE_GOOGLE_PROFILE_INFO_NAME, 1689 IDS_FLAGS_ENABLE_GOOGLE_PROFILE_INFO_DESCRIPTION, 1690 kOsMac | kOsWin | kOsLinux, 1691 SINGLE_VALUE_TYPE(switches::kGoogleProfileInfo) 1692 }, 1693 { 1694 "disable-app-launcher", 1695 IDS_FLAGS_RESET_APP_LIST_INSTALL_STATE_NAME, 1696 IDS_FLAGS_RESET_APP_LIST_INSTALL_STATE_DESCRIPTION, 1697 kOsMac | kOsWin, 1698 SINGLE_VALUE_TYPE(switches::kResetAppListInstallState) 1699 }, 1700#if defined(ENABLE_APP_LIST) 1701 { 1702 "enable-app-launcher-start-page", 1703 IDS_FLAGS_ENABLE_APP_LIST_START_PAGE_NAME, 1704 IDS_FLAGS_ENABLE_APP_LIST_START_PAGE_DESCRIPTION, 1705 kOsWin | kOsCrOS, 1706 SINGLE_VALUE_TYPE(switches::kShowAppListStartPage) 1707 }, 1708#endif 1709#if defined(OS_CHROMEOS) 1710 { 1711 "disable-user-image-sync", 1712 IDS_FLAGS_DISABLE_USER_IMAGE_SYNC_NAME, 1713 IDS_FLAGS_DISABLE_USER_IMAGE_SYNC_DESCRIPTION, 1714 kOsCrOS, 1715 SINGLE_VALUE_TYPE(chromeos::switches::kDisableUserImageSync) 1716 }, 1717#endif 1718#if defined(OS_ANDROID) 1719 { 1720 "enable-accessibility-tab-switcher", 1721 IDS_FLAGS_ENABLE_ACCESSIBILITY_TAB_SWITCHER_NAME, 1722 IDS_FLAGS_ENABLE_ACCESSIBILITY_TAB_SWITCHER_DESCRIPTION, 1723 kOsAndroid, 1724 SINGLE_VALUE_TYPE(switches::kEnableAccessibilityTabSwitcher) 1725 }, 1726#endif 1727 { 1728 "disable-batched-shutdown", 1729 IDS_FLAGS_DISABLE_BATCHED_SHUTDOWN_NAME, 1730 IDS_FLAGS_DISABLE_BATCHED_SHUTDOWN_DESCRIPTION, 1731 kOsDesktop, 1732 SINGLE_VALUE_TYPE(switches::kDisableBatchedShutdown) 1733 }, 1734 { 1735 "map-image", 1736 IDS_FLAGS_MAP_IMAGE_NAME, 1737 IDS_FLAGS_MAP_IMAGE_DESCRIPTION, 1738 kOsAll, 1739 MULTI_VALUE_TYPE(kMapImageChoices) 1740 }, 1741 { 1742 "enable-add-to-homescreen", 1743 IDS_FLAGS_ENABLE_ADD_TO_HOMESCREEN_NAME, 1744 IDS_FLAGS_ENABLE_ADD_TO_HOMESCREEN_DESCRIPTION, 1745 kOsAndroid, 1746#if defined(OS_ANDROID) 1747 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableAddToHomescreen, 1748 switches::kDisableAddToHomescreen), 1749#else 1750 SINGLE_VALUE_TYPE("") 1751#endif 1752 }, 1753#if defined(OS_CHROMEOS) 1754 { 1755 "enable-first-run-ui", 1756 IDS_FLAGS_ENABLE_FIRST_RUN_UI_NAME, 1757 IDS_FLAGS_ENABLE_FIRST_RUN_UI_DESCRIPTION, 1758 kOsCrOS, 1759 SINGLE_VALUE_TYPE(chromeos::switches::kEnableFirstRunUI) 1760 }, 1761#endif 1762 { 1763 "disable-compositor-touch-hit-testing", 1764 IDS_FLAGS_DISABLE_COMPOSITOR_TOUCH_HIT_TESTING_NAME, 1765 IDS_FLAGS_DISABLE_COMPOSITOR_TOUCH_HIT_TESTING_DESCRIPTION, 1766 kOsAll, 1767 SINGLE_VALUE_TYPE(cc::switches::kDisableCompositorTouchHitTesting), 1768 }, 1769 { 1770 "enable-accelerated-scrollable-frames", 1771 IDS_FLAGS_ENABLE_ACCELERATED_SCROLLABLE_FRAMES_NAME, 1772 IDS_FLAGS_ENABLE_ACCELERATED_SCROLLABLE_FRAMES_DESCRIPTION, 1773 kOsAll, 1774 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableAcceleratedScrollableFrames, 1775 switches::kDisableAcceleratedScrollableFrames) 1776 }, 1777 { 1778 "enable-composited-scrolling-for-frames", 1779 IDS_FLAGS_ENABLE_COMPOSITED_SCROLLING_FOR_FRAMES_NAME, 1780 IDS_FLAGS_ENABLE_COMPOSITED_SCROLLING_FOR_FRAMES_DESCRIPTION, 1781 kOsAll, 1782 ENABLE_DISABLE_VALUE_TYPE(switches::kEnableCompositedScrollingForFrames, 1783 switches::kDisableCompositedScrollingForFrames) 1784 }, 1785 { 1786 "enable-streamlined-hosted-apps", 1787 IDS_FLAGS_ENABLE_STREAMLINED_HOSTED_APPS_NAME, 1788 IDS_FLAGS_ENABLE_STREAMLINED_HOSTED_APPS_DESCRIPTION, 1789 kOsWin | kOsCrOS, 1790 SINGLE_VALUE_TYPE(switches::kEnableStreamlinedHostedApps) 1791 }, 1792 { 1793 "enable-ephemeral-apps", 1794 IDS_FLAGS_ENABLE_EPHEMERAL_APPS_NAME, 1795 IDS_FLAGS_ENABLE_EPHEMERAL_APPS_DESCRIPTION, 1796 kOsWin | kOsCrOS, 1797 SINGLE_VALUE_TYPE(switches::kEnableEphemeralApps) 1798 }, 1799 { 1800 "enable-service-worker", 1801 IDS_FLAGS_ENABLE_SERVICE_WORKER_NAME, 1802 IDS_FLAGS_ENABLE_SERVICE_WORKER_DESCRIPTION, 1803 kOsAll, 1804 SINGLE_VALUE_TYPE(switches::kEnableServiceWorker) 1805 }, 1806#if defined(OS_ANDROID) 1807 { 1808 "disable-click-delay", 1809 IDS_FLAGS_DISABLE_CLICK_DELAY_NAME, 1810 IDS_FLAGS_DISABLE_CLICK_DELAY_DESCRIPTION, 1811 kOsAndroid, 1812 // Java-only switch: CommandLine.DISABLE_CLICK_DELAY 1813 SINGLE_VALUE_TYPE("disable-click-delay") 1814 }, 1815#endif 1816#if defined(OS_CHROMEOS) 1817 { 1818 "enable-ime-mode-indicator", 1819 IDS_FLAGS_ENABLE_IME_MODE_INDICATOR, 1820 IDS_FLAGS_ENABLE_IME_MODE_INDICATOR_DESCRIPTION, 1821 kOsCrOS, 1822 SINGLE_VALUE_TYPE(chromeos::switches::kEnableIMEModeIndicator) 1823 }, 1824#endif 1825 { 1826 "enable-translate-new-ux", 1827 IDS_FLAGS_ENABLE_TRANSLATE_NEW_UX_NAME, 1828 IDS_FLAGS_ENABLE_TRANSLATE_NEW_UX_DESCRIPTION, 1829 kOsDesktop, 1830 SINGLE_VALUE_TYPE(switches::kEnableTranslateNewUX) 1831 }, 1832}; 1833 1834const Experiment* experiments = kExperiments; 1835size_t num_experiments = arraysize(kExperiments); 1836 1837// Stores and encapsulates the little state that about:flags has. 1838class FlagsState { 1839 public: 1840 FlagsState() : needs_restart_(false) {} 1841 void ConvertFlagsToSwitches(FlagsStorage* flags_storage, 1842 CommandLine* command_line, 1843 SentinelsMode sentinels); 1844 bool IsRestartNeededToCommitChanges(); 1845 void SetExperimentEnabled( 1846 FlagsStorage* flags_storage, 1847 const std::string& internal_name, 1848 bool enable); 1849 void RemoveFlagsSwitches( 1850 std::map<std::string, CommandLine::StringType>* switch_list); 1851 void ResetAllFlags(FlagsStorage* flags_storage); 1852 void reset(); 1853 1854 // Returns the singleton instance of this class 1855 static FlagsState* GetInstance() { 1856 return Singleton<FlagsState>::get(); 1857 } 1858 1859 private: 1860 bool needs_restart_; 1861 std::map<std::string, std::string> flags_switches_; 1862 1863 DISALLOW_COPY_AND_ASSIGN(FlagsState); 1864}; 1865 1866// Adds the internal names for the specified experiment to |names|. 1867void AddInternalName(const Experiment& e, std::set<std::string>* names) { 1868 if (e.type == Experiment::SINGLE_VALUE) { 1869 names->insert(e.internal_name); 1870 } else { 1871 DCHECK(e.type == Experiment::MULTI_VALUE || 1872 e.type == Experiment::ENABLE_DISABLE_VALUE); 1873 for (int i = 0; i < e.num_choices; ++i) 1874 names->insert(e.NameForChoice(i)); 1875 } 1876} 1877 1878// Confirms that an experiment is valid, used in a DCHECK in 1879// SanitizeList below. 1880bool ValidateExperiment(const Experiment& e) { 1881 switch (e.type) { 1882 case Experiment::SINGLE_VALUE: 1883 DCHECK_EQ(0, e.num_choices); 1884 DCHECK(!e.choices); 1885 break; 1886 case Experiment::MULTI_VALUE: 1887 DCHECK_GT(e.num_choices, 0); 1888 DCHECK(e.choices); 1889 DCHECK(e.choices[0].command_line_switch); 1890 DCHECK_EQ('\0', e.choices[0].command_line_switch[0]); 1891 break; 1892 case Experiment::ENABLE_DISABLE_VALUE: 1893 DCHECK_EQ(3, e.num_choices); 1894 DCHECK(!e.choices); 1895 DCHECK(e.command_line_switch); 1896 DCHECK(e.command_line_value); 1897 DCHECK(e.disable_command_line_switch); 1898 DCHECK(e.disable_command_line_value); 1899 break; 1900 default: 1901 NOTREACHED(); 1902 } 1903 return true; 1904} 1905 1906// Removes all experiments from prefs::kEnabledLabsExperiments that are 1907// unknown, to prevent this list to become very long as experiments are added 1908// and removed. 1909void SanitizeList(FlagsStorage* flags_storage) { 1910 std::set<std::string> known_experiments; 1911 for (size_t i = 0; i < num_experiments; ++i) { 1912 DCHECK(ValidateExperiment(experiments[i])); 1913 AddInternalName(experiments[i], &known_experiments); 1914 } 1915 1916 std::set<std::string> enabled_experiments = flags_storage->GetFlags(); 1917 1918 std::set<std::string> new_enabled_experiments; 1919 std::set_intersection( 1920 known_experiments.begin(), known_experiments.end(), 1921 enabled_experiments.begin(), enabled_experiments.end(), 1922 std::inserter(new_enabled_experiments, new_enabled_experiments.begin())); 1923 1924 if (new_enabled_experiments != enabled_experiments) 1925 flags_storage->SetFlags(new_enabled_experiments); 1926} 1927 1928void GetSanitizedEnabledFlags( 1929 FlagsStorage* flags_storage, std::set<std::string>* result) { 1930 SanitizeList(flags_storage); 1931 *result = flags_storage->GetFlags(); 1932} 1933 1934// Variant of GetSanitizedEnabledFlags that also removes any flags that aren't 1935// enabled on the current platform. 1936void GetSanitizedEnabledFlagsForCurrentPlatform( 1937 FlagsStorage* flags_storage, std::set<std::string>* result) { 1938 GetSanitizedEnabledFlags(flags_storage, result); 1939 1940 // Filter out any experiments that aren't enabled on the current platform. We 1941 // don't remove these from prefs else syncing to a platform with a different 1942 // set of experiments would be lossy. 1943 std::set<std::string> platform_experiments; 1944 int current_platform = GetCurrentPlatform(); 1945 for (size_t i = 0; i < num_experiments; ++i) { 1946 if (experiments[i].supported_platforms & current_platform) 1947 AddInternalName(experiments[i], &platform_experiments); 1948#if defined(OS_CHROMEOS) 1949 if (experiments[i].supported_platforms & kOsCrOSOwnerOnly) 1950 AddInternalName(experiments[i], &platform_experiments); 1951#endif 1952 } 1953 1954 std::set<std::string> new_enabled_experiments; 1955 std::set_intersection( 1956 platform_experiments.begin(), platform_experiments.end(), 1957 result->begin(), result->end(), 1958 std::inserter(new_enabled_experiments, new_enabled_experiments.begin())); 1959 1960 result->swap(new_enabled_experiments); 1961} 1962 1963// Returns the Value representing the choice data in the specified experiment. 1964Value* CreateChoiceData(const Experiment& experiment, 1965 const std::set<std::string>& enabled_experiments) { 1966 DCHECK(experiment.type == Experiment::MULTI_VALUE || 1967 experiment.type == Experiment::ENABLE_DISABLE_VALUE); 1968 ListValue* result = new ListValue; 1969 for (int i = 0; i < experiment.num_choices; ++i) { 1970 DictionaryValue* value = new DictionaryValue; 1971 const std::string name = experiment.NameForChoice(i); 1972 value->SetString("internal_name", name); 1973 value->SetString("description", experiment.DescriptionForChoice(i)); 1974 value->SetBoolean("selected", enabled_experiments.count(name) > 0); 1975 result->Append(value); 1976 } 1977 return result; 1978} 1979 1980} // namespace 1981 1982std::string Experiment::NameForChoice(int index) const { 1983 DCHECK(type == Experiment::MULTI_VALUE || 1984 type == Experiment::ENABLE_DISABLE_VALUE); 1985 DCHECK_LT(index, num_choices); 1986 return std::string(internal_name) + testing::kMultiSeparator + 1987 base::IntToString(index); 1988} 1989 1990string16 Experiment::DescriptionForChoice(int index) const { 1991 DCHECK(type == Experiment::MULTI_VALUE || 1992 type == Experiment::ENABLE_DISABLE_VALUE); 1993 DCHECK_LT(index, num_choices); 1994 int description_id; 1995 if (type == Experiment::ENABLE_DISABLE_VALUE) { 1996 const int kEnableDisableDescriptionIds[] = { 1997 IDS_GENERIC_EXPERIMENT_CHOICE_DEFAULT, 1998 IDS_GENERIC_EXPERIMENT_CHOICE_ENABLED, 1999 IDS_GENERIC_EXPERIMENT_CHOICE_DISABLED, 2000 }; 2001 description_id = kEnableDisableDescriptionIds[index]; 2002 } else { 2003 description_id = choices[index].description_id; 2004 } 2005 return l10n_util::GetStringUTF16(description_id); 2006} 2007 2008void ConvertFlagsToSwitches(FlagsStorage* flags_storage, 2009 CommandLine* command_line, 2010 SentinelsMode sentinels) { 2011 FlagsState::GetInstance()->ConvertFlagsToSwitches(flags_storage, 2012 command_line, 2013 sentinels); 2014} 2015 2016bool AreSwitchesIdenticalToCurrentCommandLine( 2017 const CommandLine& new_cmdline, const CommandLine& active_cmdline) { 2018 std::set<CommandLine::StringType> new_flags = 2019 ExtractFlagsFromCommandLine(new_cmdline); 2020 std::set<CommandLine::StringType> active_flags = 2021 ExtractFlagsFromCommandLine(active_cmdline); 2022 2023 // Needed because std::equal doesn't check if the 2nd set is empty. 2024 if (new_flags.size() != active_flags.size()) 2025 return false; 2026 2027 return std::equal(new_flags.begin(), new_flags.end(), active_flags.begin()); 2028} 2029 2030void GetFlagsExperimentsData(FlagsStorage* flags_storage, 2031 FlagAccess access, 2032 base::ListValue* supported_experiments, 2033 base::ListValue* unsupported_experiments) { 2034 std::set<std::string> enabled_experiments; 2035 GetSanitizedEnabledFlags(flags_storage, &enabled_experiments); 2036 2037 int current_platform = GetCurrentPlatform(); 2038 2039 for (size_t i = 0; i < num_experiments; ++i) { 2040 const Experiment& experiment = experiments[i]; 2041 2042 DictionaryValue* data = new DictionaryValue(); 2043 data->SetString("internal_name", experiment.internal_name); 2044 data->SetString("name", 2045 l10n_util::GetStringUTF16(experiment.visible_name_id)); 2046 data->SetString("description", 2047 l10n_util::GetStringUTF16( 2048 experiment.visible_description_id)); 2049 2050 ListValue* supported_platforms = new ListValue(); 2051 AddOsStrings(experiment.supported_platforms, supported_platforms); 2052 data->Set("supported_platforms", supported_platforms); 2053 2054 switch (experiment.type) { 2055 case Experiment::SINGLE_VALUE: 2056 data->SetBoolean( 2057 "enabled", 2058 enabled_experiments.count(experiment.internal_name) > 0); 2059 break; 2060 case Experiment::MULTI_VALUE: 2061 case Experiment::ENABLE_DISABLE_VALUE: 2062 data->Set("choices", CreateChoiceData(experiment, enabled_experiments)); 2063 break; 2064 default: 2065 NOTREACHED(); 2066 } 2067 2068 bool supported = (experiment.supported_platforms & current_platform) != 0; 2069#if defined(OS_CHROMEOS) 2070 if (access == kOwnerAccessToFlags && 2071 (experiment.supported_platforms & kOsCrOSOwnerOnly) != 0) { 2072 supported = true; 2073 } 2074#endif 2075 if (supported) 2076 supported_experiments->Append(data); 2077 else 2078 unsupported_experiments->Append(data); 2079 } 2080} 2081 2082bool IsRestartNeededToCommitChanges() { 2083 return FlagsState::GetInstance()->IsRestartNeededToCommitChanges(); 2084} 2085 2086void SetExperimentEnabled(FlagsStorage* flags_storage, 2087 const std::string& internal_name, 2088 bool enable) { 2089 FlagsState::GetInstance()->SetExperimentEnabled(flags_storage, 2090 internal_name, enable); 2091} 2092 2093void RemoveFlagsSwitches( 2094 std::map<std::string, CommandLine::StringType>* switch_list) { 2095 FlagsState::GetInstance()->RemoveFlagsSwitches(switch_list); 2096} 2097 2098void ResetAllFlags(FlagsStorage* flags_storage) { 2099 FlagsState::GetInstance()->ResetAllFlags(flags_storage); 2100} 2101 2102int GetCurrentPlatform() { 2103#if defined(OS_MACOSX) 2104 return kOsMac; 2105#elif defined(OS_WIN) 2106 return kOsWin; 2107#elif defined(OS_CHROMEOS) // Needs to be before the OS_LINUX check. 2108 return kOsCrOS; 2109#elif defined(OS_LINUX) || defined(OS_OPENBSD) 2110 return kOsLinux; 2111#elif defined(OS_ANDROID) 2112 return kOsAndroid; 2113#else 2114#error Unknown platform 2115#endif 2116} 2117 2118void RecordUMAStatistics(FlagsStorage* flags_storage) { 2119 std::set<std::string> flags = flags_storage->GetFlags(); 2120 for (std::set<std::string>::iterator it = flags.begin(); it != flags.end(); 2121 ++it) { 2122 std::string action("AboutFlags_"); 2123 action += *it; 2124 content::RecordComputedAction(action); 2125 } 2126 // Since flag metrics are recorded every startup, add a tick so that the 2127 // stats can be made meaningful. 2128 if (flags.size()) 2129 content::RecordAction(UserMetricsAction("AboutFlags_StartupTick")); 2130 content::RecordAction(UserMetricsAction("StartupTick")); 2131} 2132 2133////////////////////////////////////////////////////////////////////////////// 2134// FlagsState implementation. 2135 2136namespace { 2137 2138typedef std::map<std::string, std::pair<std::string, std::string> > 2139 NameToSwitchAndValueMap; 2140 2141void SetFlagToSwitchMapping(const std::string& key, 2142 const std::string& switch_name, 2143 const std::string& switch_value, 2144 NameToSwitchAndValueMap* name_to_switch_map) { 2145 DCHECK(name_to_switch_map->end() == name_to_switch_map->find(key)); 2146 (*name_to_switch_map)[key] = std::make_pair(switch_name, switch_value); 2147} 2148 2149void FlagsState::ConvertFlagsToSwitches(FlagsStorage* flags_storage, 2150 CommandLine* command_line, 2151 SentinelsMode sentinels) { 2152 if (command_line->HasSwitch(switches::kNoExperiments)) 2153 return; 2154 2155 std::set<std::string> enabled_experiments; 2156 2157 GetSanitizedEnabledFlagsForCurrentPlatform(flags_storage, 2158 &enabled_experiments); 2159 2160 NameToSwitchAndValueMap name_to_switch_map; 2161 for (size_t i = 0; i < num_experiments; ++i) { 2162 const Experiment& e = experiments[i]; 2163 if (e.type == Experiment::SINGLE_VALUE) { 2164 SetFlagToSwitchMapping(e.internal_name, e.command_line_switch, 2165 e.command_line_value, &name_to_switch_map); 2166 } else if (e.type == Experiment::MULTI_VALUE) { 2167 for (int j = 0; j < e.num_choices; ++j) { 2168 SetFlagToSwitchMapping(e.NameForChoice(j), 2169 e.choices[j].command_line_switch, 2170 e.choices[j].command_line_value, 2171 &name_to_switch_map); 2172 } 2173 } else { 2174 DCHECK_EQ(e.type, Experiment::ENABLE_DISABLE_VALUE); 2175 SetFlagToSwitchMapping(e.NameForChoice(0), std::string(), std::string(), 2176 &name_to_switch_map); 2177 SetFlagToSwitchMapping(e.NameForChoice(1), e.command_line_switch, 2178 e.command_line_value, &name_to_switch_map); 2179 SetFlagToSwitchMapping(e.NameForChoice(2), e.disable_command_line_switch, 2180 e.disable_command_line_value, &name_to_switch_map); 2181 } 2182 } 2183 2184 if (sentinels == kAddSentinels) { 2185 command_line->AppendSwitch(switches::kFlagSwitchesBegin); 2186 flags_switches_.insert( 2187 std::pair<std::string, std::string>(switches::kFlagSwitchesBegin, 2188 std::string())); 2189 } 2190 for (std::set<std::string>::iterator it = enabled_experiments.begin(); 2191 it != enabled_experiments.end(); 2192 ++it) { 2193 const std::string& experiment_name = *it; 2194 NameToSwitchAndValueMap::const_iterator name_to_switch_it = 2195 name_to_switch_map.find(experiment_name); 2196 if (name_to_switch_it == name_to_switch_map.end()) { 2197 NOTREACHED(); 2198 continue; 2199 } 2200 2201 const std::pair<std::string, std::string>& 2202 switch_and_value_pair = name_to_switch_it->second; 2203 2204 CHECK(!switch_and_value_pair.first.empty()); 2205 command_line->AppendSwitchASCII(switch_and_value_pair.first, 2206 switch_and_value_pair.second); 2207 flags_switches_[switch_and_value_pair.first] = switch_and_value_pair.second; 2208 } 2209 if (sentinels == kAddSentinels) { 2210 command_line->AppendSwitch(switches::kFlagSwitchesEnd); 2211 flags_switches_.insert( 2212 std::pair<std::string, std::string>(switches::kFlagSwitchesEnd, 2213 std::string())); 2214 } 2215} 2216 2217bool FlagsState::IsRestartNeededToCommitChanges() { 2218 return needs_restart_; 2219} 2220 2221void FlagsState::SetExperimentEnabled(FlagsStorage* flags_storage, 2222 const std::string& internal_name, 2223 bool enable) { 2224 size_t at_index = internal_name.find(testing::kMultiSeparator); 2225 if (at_index != std::string::npos) { 2226 DCHECK(enable); 2227 // We're being asked to enable a multi-choice experiment. Disable the 2228 // currently selected choice. 2229 DCHECK_NE(at_index, 0u); 2230 const std::string experiment_name = internal_name.substr(0, at_index); 2231 SetExperimentEnabled(flags_storage, experiment_name, false); 2232 2233 // And enable the new choice, if it is not the default first choice. 2234 if (internal_name != experiment_name + "@0") { 2235 std::set<std::string> enabled_experiments; 2236 GetSanitizedEnabledFlags(flags_storage, &enabled_experiments); 2237 needs_restart_ |= enabled_experiments.insert(internal_name).second; 2238 flags_storage->SetFlags(enabled_experiments); 2239 } 2240 return; 2241 } 2242 2243 std::set<std::string> enabled_experiments; 2244 GetSanitizedEnabledFlags(flags_storage, &enabled_experiments); 2245 2246 const Experiment* e = NULL; 2247 for (size_t i = 0; i < num_experiments; ++i) { 2248 if (experiments[i].internal_name == internal_name) { 2249 e = experiments + i; 2250 break; 2251 } 2252 } 2253 DCHECK(e); 2254 2255 if (e->type == Experiment::SINGLE_VALUE) { 2256 if (enable) 2257 needs_restart_ |= enabled_experiments.insert(internal_name).second; 2258 else 2259 needs_restart_ |= (enabled_experiments.erase(internal_name) > 0); 2260 } else { 2261 if (enable) { 2262 // Enable the first choice. 2263 needs_restart_ |= enabled_experiments.insert(e->NameForChoice(0)).second; 2264 } else { 2265 // Find the currently enabled choice and disable it. 2266 for (int i = 0; i < e->num_choices; ++i) { 2267 std::string choice_name = e->NameForChoice(i); 2268 if (enabled_experiments.find(choice_name) != 2269 enabled_experiments.end()) { 2270 needs_restart_ = true; 2271 enabled_experiments.erase(choice_name); 2272 // Continue on just in case there's a bug and more than one 2273 // experiment for this choice was enabled. 2274 } 2275 } 2276 } 2277 } 2278 2279 flags_storage->SetFlags(enabled_experiments); 2280} 2281 2282void FlagsState::RemoveFlagsSwitches( 2283 std::map<std::string, CommandLine::StringType>* switch_list) { 2284 for (std::map<std::string, std::string>::const_iterator 2285 it = flags_switches_.begin(); it != flags_switches_.end(); ++it) { 2286 switch_list->erase(it->first); 2287 } 2288} 2289 2290void FlagsState::ResetAllFlags(FlagsStorage* flags_storage) { 2291 needs_restart_ = true; 2292 2293 std::set<std::string> no_experiments; 2294 flags_storage->SetFlags(no_experiments); 2295} 2296 2297void FlagsState::reset() { 2298 needs_restart_ = false; 2299 flags_switches_.clear(); 2300} 2301 2302} // namespace 2303 2304namespace testing { 2305 2306// WARNING: '@' is also used in the html file. If you update this constant you 2307// also need to update the html file. 2308const char kMultiSeparator[] = "@"; 2309 2310void ClearState() { 2311 FlagsState::GetInstance()->reset(); 2312} 2313 2314void SetExperiments(const Experiment* e, size_t count) { 2315 if (!e) { 2316 experiments = kExperiments; 2317 num_experiments = arraysize(kExperiments); 2318 } else { 2319 experiments = e; 2320 num_experiments = count; 2321 } 2322} 2323 2324const Experiment* GetExperiments(size_t* count) { 2325 *count = num_experiments; 2326 return experiments; 2327} 2328 2329} // namespace testing 2330 2331} // namespace about_flags 2332