// Copyright (c) 2017, the Dart project authors.  Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.

#include "bin/main_options.h"

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#include "bin/dartdev_isolate.h"
#include "bin/error_exit.h"
#include "bin/file_system_watcher.h"
#include "bin/options.h"
#include "bin/platform.h"
#include "bin/utils.h"
#include "platform/syslog.h"
#if !defined(DART_IO_SECURE_SOCKET_DISABLED)
#include "bin/security_context.h"
#endif  // !defined(DART_IO_SECURE_SOCKET_DISABLED)
#include "bin/socket.h"
#include "include/dart_api.h"
#include "platform/assert.h"
#include "platform/globals.h"
#include "platform/hashmap.h"

namespace dart {
namespace bin {

// These strings must match the enum SnapshotKind in main_options.h.
static const char* const kSnapshotKindNames[] = {
    "none",
    "kernel",
    "app-jit",
    NULL,
};

// These strings must match the enum VerbosityLevel in main_options.h.
static const char* const kVerbosityLevelNames[] = {
    "error", "warning", "info", "all", nullptr,
};

SnapshotKind Options::gen_snapshot_kind_ = kNone;
VerbosityLevel Options::verbosity_ = kAll;
bool Options::enable_vm_service_ = false;

#define OPTION_FIELD(variable) Options::variable##_

#define STRING_OPTION_DEFINITION(name, variable)                               \
  const char* OPTION_FIELD(variable) = NULL;                                   \
  DEFINE_STRING_OPTION(name, OPTION_FIELD(variable))
STRING_OPTIONS_LIST(STRING_OPTION_DEFINITION)
#undef STRING_OPTION_DEFINITION

#define BOOL_OPTION_DEFINITION(name, variable)                                 \
  bool OPTION_FIELD(variable) = false;                                         \
  DEFINE_BOOL_OPTION(name, OPTION_FIELD(variable))
BOOL_OPTIONS_LIST(BOOL_OPTION_DEFINITION)
#if defined(DEBUG)
DEBUG_BOOL_OPTIONS_LIST(BOOL_OPTION_DEFINITION)
#endif
#undef BOOL_OPTION_DEFINITION

#define SHORT_BOOL_OPTION_DEFINITION(short_name, long_name, variable)          \
  bool OPTION_FIELD(variable) = false;                                         \
  DEFINE_BOOL_OPTION_SHORT(short_name, long_name, OPTION_FIELD(variable))
SHORT_BOOL_OPTIONS_LIST(SHORT_BOOL_OPTION_DEFINITION)
#undef SHORT_BOOL_OPTION_DEFINITION

#define ENUM_OPTION_DEFINITION(name, type, variable)                           \
  DEFINE_ENUM_OPTION(name, type, OPTION_FIELD(variable))
ENUM_OPTIONS_LIST(ENUM_OPTION_DEFINITION)
#undef ENUM_OPTION_DEFINITION

#define CB_OPTION_DEFINITION(callback)                                         \
  static bool callback##Helper(const char* arg, CommandLineOptions* o) {       \
    return Options::callback(arg, o);                                          \
  }                                                                            \
  DEFINE_CB_OPTION(callback##Helper)
CB_OPTIONS_LIST(CB_OPTION_DEFINITION)
#undef CB_OPTION_DEFINITION

#if !defined(DART_PRECOMPILED_RUNTIME)
DFE* Options::dfe_ = NULL;

DEFINE_STRING_OPTION_CB(dfe, { Options::dfe()->set_frontend_filename(value); });
#endif  // !defined(DART_PRECOMPILED_RUNTIME)

static void hot_reload_test_mode_callback(CommandLineOptions* vm_options) {
  // Identity reload.
  vm_options->AddArgument("--identity_reload");
  // Start reloading quickly.
  vm_options->AddArgument("--reload_every=4");
  // Reload from optimized and unoptimized code.
  vm_options->AddArgument("--reload_every_optimized=false");
  // Reload less frequently as time goes on.
  vm_options->AddArgument("--reload_every_back_off");
  // Ensure that every isolate has reloaded once before exiting.
  vm_options->AddArgument("--check_reloaded");
#if !defined(DART_PRECOMPILED_RUNTIME)
  Options::dfe()->set_use_incremental_compiler(true);
#endif  // !defined(DART_PRECOMPILED_RUNTIME)
}

DEFINE_BOOL_OPTION_CB(hot_reload_test_mode, hot_reload_test_mode_callback);

static void hot_reload_rollback_test_mode_callback(
    CommandLineOptions* vm_options) {
  // Identity reload.
  vm_options->AddArgument("--identity_reload");
  // Start reloading quickly.
  vm_options->AddArgument("--reload_every=4");
  // Reload from optimized and unoptimized code.
  vm_options->AddArgument("--reload_every_optimized=false");
  // Reload less frequently as time goes on.
  vm_options->AddArgument("--reload_every_back_off");
  // Ensure that every isolate has reloaded once before exiting.
  vm_options->AddArgument("--check_reloaded");
  // Force all reloads to fail and execute the rollback code.
  vm_options->AddArgument("--reload_force_rollback");
#if !defined(DART_PRECOMPILED_RUNTIME)
  Options::dfe()->set_use_incremental_compiler(true);
#endif  // !defined(DART_PRECOMPILED_RUNTIME)
}

DEFINE_BOOL_OPTION_CB(hot_reload_rollback_test_mode,
                      hot_reload_rollback_test_mode_callback);

void Options::PrintVersion() {
  Syslog::Print("Dart SDK version: %s\n", Dart_VersionString());
}

// clang-format off
void Options::PrintUsage() {
  Syslog::Print(
      "Usage: dart [<vm-flags>] <dart-script-file> [<script-arguments>]\n"
      "\n"
      "Executes the Dart script <dart-script-file> with "
      "the given list of <script-arguments>.\n"
      "\n");
  if (!Options::verbose_option()) {
    Syslog::Print(
"Common VM flags:\n"
#if !defined(PRODUCT)
"--enable-asserts\n"
"  Enable assert statements.\n"
#endif  // !defined(PRODUCT)
"--help or -h\n"
"  Display this message (add -v or --verbose for information about\n"
"  all VM options).\n"
"--packages=<path>\n"
"  Where to find a package spec file.\n"
"--define=<key>=<value> or -D<key>=<value>\n"
"  Define an environment declaration. To specify multiple declarations,\n"
"  use multiple instances of this option.\n"
#if !defined(PRODUCT)
"--observe[=<port>[/<bind-address>]]\n"
"  The observe flag is a convenience flag used to run a program with a\n"
"  set of options which are often useful for debugging under Observatory.\n"
"  These options are currently:\n"
"      --enable-vm-service[=<port>[/<bind-address>]]\n"
"      --serve-devtools\n"
"      --pause-isolates-on-exit\n"
"      --pause-isolates-on-unhandled-exceptions\n"
"      --warn-on-pause-with-no-debugger\n"
"  This set is subject to change.\n"
"  Please see these options (--help --verbose) for further documentation.\n"
"--write-service-info=<file_uri>\n"
"  Outputs information necessary to connect to the VM service to the\n"
"  specified file in JSON format. Useful for clients which are unable to\n"
"  listen to stdout for the Observatory listening message.\n"
#endif  // !defined(PRODUCT)
"--snapshot-kind=<snapshot_kind>\n"
"--snapshot=<file_name>\n"
"  These snapshot options are used to generate a snapshot of the loaded\n"
"  Dart script:\n"
"    <snapshot-kind> controls the kind of snapshot, it could be\n"
"                    kernel(default) or app-jit\n"
"    <file_name> specifies the file into which the snapshot is written\n"
"--version\n"
"  Print the SDK version.\n");
  } else {
    Syslog::Print(
"Supported options:\n"
#if !defined(PRODUCT)
"--enable-asserts\n"
"  Enable assert statements.\n"
#endif  // !defined(PRODUCT)
"--help or -h\n"
"  Display this message (add -v or --verbose for information about\n"
"  all VM options).\n"
"--packages=<path>\n"
"  Where to find a package spec file.\n"
"--define=<key>=<value> or -D<key>=<value>\n"
"  Define an environment declaration. To specify multiple declarations,\n"
"  use multiple instances of this option.\n"
#if !defined(PRODUCT)
"--observe[=<port>[/<bind-address>]]\n"
"  The observe flag is a convenience flag used to run a program with a\n"
"  set of options which are often useful for debugging under Observatory.\n"
"  These options are currently:\n"
"      --enable-vm-service[=<port>[/<bind-address>]]\n"
"      --serve-devtools\n"
"      --pause-isolates-on-exit\n"
"      --pause-isolates-on-unhandled-exceptions\n"
"      --warn-on-pause-with-no-debugger\n"
"  This set is subject to change.\n"
"  Please see these options for further documentation.\n"
#endif  // !defined(PRODUCT)
"--version\n"
"  Print the VM version.\n"
"\n"
"--trace-loading\n"
"  enables tracing of library and script loading\n"
"\n"
#if !defined(PRODUCT)
"--enable-vm-service[=<port>[/<bind-address>]]\n"
"  Enables the VM service and listens on specified port for connections\n"
"  (default port number is 8181, default bind address is localhost).\n"
"\n"
"--disable-service-auth-codes\n"
"  Disables the requirement for an authentication code to communicate with\n"
"  the VM service. Authentication codes help protect against CSRF attacks,\n"
"  so it is not recommended to disable them unless behind a firewall on a\n"
"  secure device.\n"
"\n"
"--enable-service-port-fallback\n"
"  When the VM service is told to bind to a particular port, fallback to 0 if\n"
"  it fails to bind instead of failing to start.\n"
"\n"
#endif  // !defined(PRODUCT)
"--root-certs-file=<path>\n"
"  The path to a file containing the trusted root certificates to use for\n"
"  secure socket connections.\n"
"--root-certs-cache=<path>\n"
"  The path to a cache directory containing the trusted root certificates to\n"
"  use for secure socket connections.\n"
#if defined(DART_HOST_OS_LINUX) || \
    defined(DART_HOST_OS_ANDROID) || \
    defined(DART_HOST_OS_FUCHSIA)
"--namespace=<path>\n"
"  The path to a directory that dart:io calls will treat as the root of the\n"
"  filesystem.\n"
#endif  // defined(DART_HOST_OS_LINUX) || defined(DART_HOST_OS_ANDROID)
"\n"
"The following options are only used for VM development and may\n"
"be changed in any future version:\n");
    const char* print_flags = "--print_flags";
    char* error = Dart_SetVMFlags(1, &print_flags);
    ASSERT(error == NULL);
  }
}
// clang-format on

dart::SimpleHashMap* Options::environment_ = NULL;
bool Options::ProcessEnvironmentOption(const char* arg,
                                       CommandLineOptions* vm_options) {
  return OptionProcessor::ProcessEnvironmentOption(arg, vm_options,
                                                   &Options::environment_);
}

void Options::DestroyEnvironment() {
  if (environment_ != NULL) {
    for (SimpleHashMap::Entry* p = environment_->Start(); p != NULL;
         p = environment_->Next(p)) {
      free(p->key);
      free(p->value);
    }
    delete environment_;
    environment_ = NULL;
  }
}

bool Options::ExtractPortAndAddress(const char* option_value,
                                    int* out_port,
                                    const char** out_ip,
                                    int default_port,
                                    const char* default_ip) {
  // [option_value] has to be one of the following formats:
  //   - ""
  //   - ":8181"
  //   - "=8181"
  //   - ":8181/192.168.0.1"
  //   - "=8181/192.168.0.1"
  //   - "=8181/::1"

  if (*option_value == '\0') {
    *out_ip = default_ip;
    *out_port = default_port;
    return true;
  }

  if ((*option_value != '=') && (*option_value != ':')) {
    return false;
  }

  int port = atoi(option_value + 1);
  const char* slash = strstr(option_value, "/");
  if (slash == NULL) {
    *out_ip = default_ip;
    *out_port = port;
    return true;
  }

  *out_ip = slash + 1;
  *out_port = port;
  return true;
}

// Returns true if arg starts with the characters "--" followed by option, but
// all '_' in the option name are treated as '-'.
static bool IsOption(const char* arg, const char* option) {
  if (arg[0] != '-' || arg[1] != '-') {
    // Special case first two characters to avoid recognizing __flag.
    return false;
  }
  for (int i = 0; option[i] != '\0'; i++) {
    auto c = arg[i + 2];
    if (c == '\0') {
      // Not long enough.
      return false;
    }
    if ((c == '_' ? '-' : c) != option[i]) {
      return false;
    }
  }
  return true;
}

const char* Options::vm_service_server_ip_ = DEFAULT_VM_SERVICE_SERVER_IP;
int Options::vm_service_server_port_ = INVALID_VM_SERVICE_SERVER_PORT;
bool Options::ProcessEnableVmServiceOption(const char* arg,
                                           CommandLineOptions* vm_options) {
#if !defined(PRODUCT)
  const char* value =
      OptionProcessor::ProcessOption(arg, "--enable-vm-service");
  if (value == NULL) {
    return false;
  }
  if (!ExtractPortAndAddress(
          value, &vm_service_server_port_, &vm_service_server_ip_,
          DEFAULT_VM_SERVICE_SERVER_PORT, DEFAULT_VM_SERVICE_SERVER_IP)) {
    Syslog::PrintErr(
        "unrecognized --enable-vm-service option syntax. "
        "Use --enable-vm-service[=<port number>[/<bind address>]]\n");
    return false;
  }
#if !defined(DART_PRECOMPILED_RUNTIME)
  dfe()->set_use_incremental_compiler(true);
#endif  // !defined(DART_PRECOMPILED_RUNTIME)
  enable_vm_service_ = true;
  return true;
#else
  // VM service not available in product mode.
  return false;
#endif  // !defined(PRODUCT)
}

bool Options::ProcessObserveOption(const char* arg,
                                   CommandLineOptions* vm_options) {
#if !defined(PRODUCT)
  const char* value = OptionProcessor::ProcessOption(arg, "--observe");
  if (value == NULL) {
    return false;
  }
  if (!ExtractPortAndAddress(
          value, &vm_service_server_port_, &vm_service_server_ip_,
          DEFAULT_VM_SERVICE_SERVER_PORT, DEFAULT_VM_SERVICE_SERVER_IP)) {
    Syslog::PrintErr(
        "unrecognized --observe option syntax. "
        "Use --observe[=<port number>[/<bind address>]]\n");
    return false;
  }

  // These options should also be documented in the help message.
  vm_options->AddArgument("--pause-isolates-on-exit");
  vm_options->AddArgument("--pause-isolates-on-unhandled-exceptions");
  vm_options->AddArgument("--profiler");
  vm_options->AddArgument("--warn-on-pause-with-no-debugger");
#if !defined(DART_PRECOMPILED_RUNTIME)
  dfe()->set_use_incremental_compiler(true);
#endif  // !defined(DART_PRECOMPILED_RUNTIME)
  enable_vm_service_ = true;
  return true;
#else
  // VM service not available in product mode.
  return false;
#endif  // !defined(PRODUCT)
}

// Explicitly handle VM flags that can be parsed by DartDev's run command.
bool Options::ProcessVMDebuggingOptions(const char* arg,
                                        CommandLineOptions* vm_options) {
#define IS_DEBUG_OPTION(name, arg)                                             \
  if (strncmp(name, arg, strlen(name)) == 0) {                                 \
    vm_options->AddArgument(arg);                                              \
    return true;                                                               \
  }

// This is an exhaustive set of VM flags that are accepted by 'dart run'. Flags
// defined in main_options.h do not need to be handled here as they already
// have handlers generated.
//
// NOTE: When updating this list of VM flags, be sure to make the corresponding
// changes in pkg/dartdev/lib/src/commands/run.dart.
#define HANDLE_DARTDEV_VM_DEBUG_OPTIONS(V, arg)                                \
  V("--enable-asserts", arg)                                                   \
  V("--pause-isolates-on-exit", arg)                                           \
  V("--no-pause-isolates-on-exit", arg)                                        \
  V("--pause-isolates-on-start", arg)                                          \
  V("--no-pause-isolates-on-start", arg)                                       \
  V("--pause-isolates-on-unhandled-exception", arg)                            \
  V("--no-pause-isolates-on-unhandled-exception", arg)                         \
  V("--warn-on-pause-with-no-debugger", arg)                                   \
  V("--no-warn-on-pause-with-no-debugger", arg)
  HANDLE_DARTDEV_VM_DEBUG_OPTIONS(IS_DEBUG_OPTION, arg);

#undef IS_DEBUG_OPTION
#undef HANDLE_DARTDEV_VM_DEBUG_OPTIONS

  return false;
}

bool Options::ParseArguments(int argc,
                             char** argv,
                             bool vm_run_app_snapshot,
                             CommandLineOptions* vm_options,
                             char** script_name,
                             CommandLineOptions* dart_options,
                             bool* print_flags_seen,
                             bool* verbose_debug_seen) {
  // Store the executable name.
  Platform::SetExecutableName(argv[0]);

  // Start the rest after the executable name.
  int i = 1;

  CommandLineOptions temp_vm_options(vm_options->max_count());

  bool enable_dartdev_analytics = false;
  bool disable_dartdev_analytics = false;
  bool serve_devtools = true;

  // Parse out the vm options.
  while (i < argc) {
    bool skipVmOption = false;
    if (OptionProcessor::TryProcess(argv[i], &temp_vm_options)) {
      i++;
    } else {
      // Check if this flag is a potentially valid VM flag.
      if (!OptionProcessor::IsValidFlag(argv[i])) {
        break;
      }
      // The following flags are processed as DartDev flags and are not to
      // be treated as if they are VM flags.
      if (IsOption(argv[i], "print-flags")) {
        *print_flags_seen = true;
      } else if (IsOption(argv[i], "verbose-debug")) {
        *verbose_debug_seen = true;
      } else if (IsOption(argv[i], "enable-analytics")) {
        enable_dartdev_analytics = true;
        skipVmOption = true;
      } else if (IsOption(argv[i], "disable-analytics")) {
        disable_dartdev_analytics = true;
        skipVmOption = true;
      } else if (IsOption(argv[i], "no-analytics")) {
        // Just add this option even if we don't go to dartdev.
        // It is irelevant for the vm.
        dart_options->AddArgument("--no-analytics");
        skipVmOption = true;
      } else if (IsOption(argv[i], "serve-devtools")) {
        serve_devtools = true;
        skipVmOption = true;
      } else if (IsOption(argv[i], "no-serve-devtools")) {
        serve_devtools = false;
        skipVmOption = true;
      } else if (IsOption(argv[i], "dds")) {
        // This flag is set by default in dartdev, so we ignore it. --no-dds is
        // a VM flag as disabling DDS changes how we configure the VM service,
        // so we don't need to handle that case here.
        skipVmOption = true;
      }
      if (!skipVmOption) {
        temp_vm_options.AddArgument(argv[i]);
      }
      i++;
    }
  }

#if !defined(DART_PRECOMPILED_RUNTIME)
  Options::dfe()->set_use_dfe();
#else
  // DartDev is not supported in AOT.
  Options::disable_dart_dev_ = true;
#endif  // !defined(DART_PRECOMPILED_RUNTIME)
  if (Options::deterministic()) {
    // Both an embedder and VM flag.
    temp_vm_options.AddArgument("--deterministic");
  }

  Socket::set_short_socket_read(Options::short_socket_read());
  Socket::set_short_socket_write(Options::short_socket_write());
#if !defined(DART_IO_SECURE_SOCKET_DISABLED)
  SSLCertContext::set_root_certs_file(Options::root_certs_file());
  SSLCertContext::set_root_certs_cache(Options::root_certs_cache());
  SSLCertContext::set_long_ssl_cert_evaluation(
      Options::long_ssl_cert_evaluation());
  SSLCertContext::set_bypass_trusting_system_roots(
      Options::bypass_trusting_system_roots());
#endif  // !defined(DART_IO_SECURE_SOCKET_DISABLED)

  FileSystemWatcher::set_delayed_filewatch_callback(
      Options::delayed_filewatch_callback());

  // The arguments to the VM are at positions 1 through i-1 in argv.
  Platform::SetExecutableArguments(i, argv);

  bool implicitly_use_dart_dev = false;
  bool run_script = false;
  // Get the script name.
  if (i < argc) {
#if !defined(DART_PRECOMPILED_RUNTIME)
    // If the script name is a valid file or a URL, we'll run the script
    // directly. Otherwise, this might be a DartDev command and we need to try
    // to find the DartDev snapshot so we can forward the command and its
    // arguments.
    bool is_potential_file_path = !DartDevIsolate::ShouldParseCommand(argv[i]);
#else
    bool is_potential_file_path = true;
#endif  // !defined(DART_PRECOMPILED_RUNTIME)
    if (Options::disable_dart_dev() ||
        (Options::snapshot_filename() != nullptr) ||
        (is_potential_file_path && !enable_vm_service_)) {
      *script_name = Utils::StrDup(argv[i]);
      run_script = true;
      i++;
    }
#if !defined(DART_PRECOMPILED_RUNTIME)
    else {  // NOLINT
      DartDevIsolate::set_should_run_dart_dev(true);
    }
    if (!Options::disable_dart_dev() && enable_vm_service_) {
      // Handle the special case where the user is running a Dart program
      // without using a DartDev command and wants to use the VM service. Here
      // we'll run the program using DartDev as it's used to spawn a DDS
      // instance.
      if (is_potential_file_path) {
        implicitly_use_dart_dev = true;
      }
    }
#endif  // !defined(DART_PRECOMPILED_RUNTIME)
  }
#if !defined(DART_PRECOMPILED_RUNTIME)
  else if (!Options::disable_dart_dev()) {  // NOLINT
    // Handles following invocation arguments:
    //   - dart help
    //   - dart --help
    //   - dart
    if (((Options::help_option() && !Options::verbose_option()) ||
         (argc == 1))) {
      DartDevIsolate::set_should_run_dart_dev(true);
      // Let DartDev handle the default help message.
      dart_options->AddArgument("help");
      return true;
    }
    // Handles cases where only analytics flags are provided. We need to start
    // the DartDev isolate to set this state.
    else if (enable_dartdev_analytics || disable_dartdev_analytics) {  // NOLINT
      // The analytics flags are a special case as we don't have a target script
      // or DartDev command but we still want to launch DartDev.
      DartDevIsolate::set_should_run_dart_dev(true);
      dart_options->AddArgument(enable_dartdev_analytics
                                    ? "--enable-analytics"
                                    : "--disable-analytics");
      return true;
    }
    // Let the VM handle '--version' and '--help --disable-dart-dev'.
    // Otherwise, we'll launch the DartDev isolate to print its help message
    // and set an error exit code.
    else if (!Options::help_option() && !Options::version_option()) {  // NOLINT
      DartDevIsolate::PrintUsageErrorOnRun();
      return true;
    }
    return false;
  }
#endif  // !defined(DART_PRECOMPILED_RUNTIME)
  // Handle argument parsing errors.
  else {  // NOLINT
    return false;
  }
  USE(enable_dartdev_analytics);
  USE(disable_dartdev_analytics);

  const char** vm_argv = temp_vm_options.arguments();
  int vm_argc = temp_vm_options.count();

  vm_options->AddArguments(vm_argv, vm_argc);

  // If running with dartdev, attempt to parse VM flags which are part of the
  // dartdev command (e.g., --enable-vm-service, --observe, etc).
  if (!run_script) {
    int tmp_i = i;
    // We only run the CLI implicitly if the service is enabled and the user
    // didn't run with the 'run' command. If they did provide a command, we need
    // to skip it here to continue parsing VM flags.
    if (!implicitly_use_dart_dev) {
      tmp_i++;
    }
    while (tmp_i < argc) {
      // Check if this flag is a potentially valid VM flag. If not, we've likely
      // hit a script name and are done parsing VM flags.
      if (!OptionProcessor::IsValidFlag(argv[tmp_i]) &&
          !OptionProcessor::IsValidShortFlag(argv[tmp_i])) {
        break;
      }
      OptionProcessor::TryProcess(argv[tmp_i], vm_options);
      tmp_i++;
    }
  }
  bool first_option = true;
  // Parse out options to be passed to dart main.
  while (i < argc) {
    if (implicitly_use_dart_dev && first_option) {
      // Special case where user enables VM service without using a dartdev
      // run command. If 'run' is provided, it will be the first argument
      // processed in this loop.
      dart_options->AddArgument("run");

      // Ensure we can enable / disable DevTools when invoking 'dart run'
      // implicitly.
      if (enable_vm_service_) {
        if (serve_devtools) {
          dart_options->AddArgument("--serve-devtools");
        } else {
          dart_options->AddArgument("--no-serve-devtools");
        }
      }
    } else {
      dart_options->AddArgument(argv[i]);
      i++;
    }
    // Add DDS specific flags immediately after the dartdev command.
    if (first_option) {
      // DDS is only enabled for the run command. Make sure we don't pass DDS
      // specific flags along with other commands, otherwise argument parsing
      // will fail unexpectedly.
      bool run_command = implicitly_use_dart_dev;
      if (!run_command && strcmp(argv[i - 1], "run") == 0) {
        run_command = true;
      }
      if (!Options::disable_dart_dev() && !Options::disable_dds() &&
          enable_vm_service_ && run_command) {
        const char* dds_format_str = "--launch-dds=%s\\:%d";
        size_t size =
            snprintf(nullptr, 0, dds_format_str, vm_service_server_ip(),
                     vm_service_server_port());
        // Make room for '\0'.
        ++size;
        char* dds_uri = new char[size];
        snprintf(dds_uri, size, dds_format_str, vm_service_server_ip(),
                 vm_service_server_port());
        dart_options->AddArgument(dds_uri);

        // Only add --disable-service-auth-codes if dartdev is being run
        // implicitly. Otherwise it will already be forwarded.
        if (implicitly_use_dart_dev && Options::vm_service_auth_disabled()) {
          dart_options->AddArgument("--disable-service-auth-codes");
        }
      }
      first_option = false;
    }
  }

  // Verify consistency of arguments.

  // snapshot_depfile is an alias for depfile. Passing them both is an error.
  if ((snapshot_deps_filename_ != NULL) && (depfile_ != NULL)) {
    Syslog::PrintErr("Specify only one of --depfile and --snapshot_depfile\n");
    return false;
  }
  if (snapshot_deps_filename_ != NULL) {
    depfile_ = snapshot_deps_filename_;
    snapshot_deps_filename_ = NULL;
  }

  if ((packages_file_ != NULL) && (strlen(packages_file_) == 0)) {
    Syslog::PrintErr("Empty package file name specified.\n");
    return false;
  }
  if ((gen_snapshot_kind_ != kNone) && (snapshot_filename_ == NULL)) {
    Syslog::PrintErr(
        "Generating a snapshot requires a filename (--snapshot).\n");
    return false;
  }
  if ((gen_snapshot_kind_ == kNone) && (depfile_ != NULL) &&
      (snapshot_filename_ == NULL) && (depfile_output_filename_ == NULL)) {
    Syslog::PrintErr(
        "Generating a depfile requires an output filename"
        " (--depfile-output-filename or --snapshot).\n");
    return false;
  }
  if ((gen_snapshot_kind_ != kNone) && vm_run_app_snapshot) {
    Syslog::PrintErr(
        "Specifying an option to generate a snapshot and"
        " run using a snapshot is invalid.\n");
    return false;
  }

  // If --snapshot is given without --snapshot-kind, default to script snapshot.
  if ((snapshot_filename_ != NULL) && (gen_snapshot_kind_ == kNone)) {
    gen_snapshot_kind_ = kKernel;
  }

  return true;
}

}  // namespace bin
}  // namespace dart
