Update to more uses of C++11.

Adds move constructors to some fundamental types such as SourceFile,
SourceDir, and Label.

Removes most uses of swap and custom swap definitions in favor of move
semantics.

Converts most default class member initialization to declare default
values in the definition.

Moves more to using implicit and defaulted-in-the-header constructors
and destructors. The previous style was inherited from Chrome which had
those rules out of concern for code size. But for this small project the
header-based ones are a little easier to follow.

Change-Id: I7d5c3bd4ac9863c34b1072fdefef81e59e555a7f
Reviewed-on: https://gn-review.googlesource.com/c/gn/+/5080
Commit-Queue: Brett Wilson <brettw@google.com>
Reviewed-by: Scott Graham <scottmg@chromium.org>
diff --git a/tools/gn/analyzer.cc b/tools/gn/analyzer.cc
index 312c22a..c58cf8c 100644
--- a/tools/gn/analyzer.cc
+++ b/tools/gn/analyzer.cc
@@ -142,11 +142,12 @@
   strings = GetStringVector(*dict, "files", &err);
   if (err.has_error())
     return err;
-  for (auto s : strings) {
-    if (!IsPathSourceAbsolute(s) && !IsPathAbsolute(s))
+  for (auto& s : strings) {
+    if (!IsPathSourceAbsolute(s) && !IsPathAbsolute(s)) {
       return Err(Location(),
                  "\"" + s + "\" is not a source-absolute or absolute path.");
-    inputs->source_vec.push_back(SourceFile(s));
+    }
+    inputs->source_vec.emplace_back(std::move(s));
   }
 
   strings = GetStringVector(*dict, "additional_compile_targets", &err);
diff --git a/tools/gn/build_settings.cc b/tools/gn/build_settings.cc
index 3cc211b..711c6b8 100644
--- a/tools/gn/build_settings.cc
+++ b/tools/gn/build_settings.cc
@@ -22,8 +22,6 @@
       build_dir_(other.build_dir_),
       build_args_(other.build_args_) {}
 
-BuildSettings::~BuildSettings() = default;
-
 void BuildSettings::SetRootTargetLabel(const Label& r) {
   root_target_label_ = r;
 }
diff --git a/tools/gn/build_settings.h b/tools/gn/build_settings.h
index 51a7d6b..646472f 100644
--- a/tools/gn/build_settings.h
+++ b/tools/gn/build_settings.h
@@ -30,7 +30,6 @@
 
   BuildSettings();
   BuildSettings(const BuildSettings& other);
-  ~BuildSettings();
 
   // Root target label.
   const Label& root_target_label() const { return root_target_label_; }
diff --git a/tools/gn/builder_record.cc b/tools/gn/builder_record.cc
index 36fd465..14e87b6 100644
--- a/tools/gn/builder_record.cc
+++ b/tools/gn/builder_record.cc
@@ -7,13 +7,7 @@
 #include "tools/gn/item.h"
 
 BuilderRecord::BuilderRecord(ItemType type, const Label& label)
-    : type_(type),
-      label_(label),
-      originally_referenced_from_(nullptr),
-      should_generate_(false),
-      resolved_(false) {}
-
-BuilderRecord::~BuilderRecord() = default;
+    : type_(type), label_(label) {}
 
 // static
 const char* BuilderRecord::GetNameForType(ItemType type) {
diff --git a/tools/gn/builder_record.h b/tools/gn/builder_record.h
index dc96f7f..9dcc366 100644
--- a/tools/gn/builder_record.h
+++ b/tools/gn/builder_record.h
@@ -40,7 +40,6 @@
   };
 
   BuilderRecord(ItemType type, const Label& label);
-  ~BuilderRecord();
 
   ItemType type() const { return type_; }
   const Label& label() const { return label_; }
@@ -97,9 +96,9 @@
   ItemType type_;
   Label label_;
   std::unique_ptr<Item> item_;
-  const ParseNode* originally_referenced_from_;
-  bool should_generate_;
-  bool resolved_;
+  const ParseNode* originally_referenced_from_ = nullptr;
+  bool should_generate_ = false;
+  bool resolved_ = false;
 
   BuilderRecordSet all_deps_;
   BuilderRecordSet unresolved_deps_;
diff --git a/tools/gn/bundle_data.cc b/tools/gn/bundle_data.cc
index 3af92d2..4251c8f 100644
--- a/tools/gn/bundle_data.cc
+++ b/tools/gn/bundle_data.cc
@@ -40,7 +40,7 @@
   }
   if (is_file_from_asset_catalog && asset_catalog) {
     std::string asset_catalog_path = dir.as_string();
-    *asset_catalog = SourceFile(SourceFile::SWAP_IN, &asset_catalog_path);
+    *asset_catalog = SourceFile(std::move(asset_catalog_path));
   }
   return is_file_from_asset_catalog;
 }
@@ -162,7 +162,7 @@
 SourceFile BundleData::GetCompiledAssetCatalogPath() const {
   DCHECK(!assets_catalog_sources_.empty());
   std::string assets_car_path = resources_dir_.value() + "/Assets.car";
-  return SourceFile(SourceFile::SWAP_IN, &assets_car_path);
+  return SourceFile(std::move(assets_car_path));
 }
 
 SourceFile BundleData::GetBundleRootDirOutput(const Settings* settings) const {
@@ -171,7 +171,7 @@
   if (last_separator != std::string::npos)
     root_dir_value = root_dir_value.substr(0, last_separator);
 
-  return SourceFile(SourceFile::SWAP_IN, &root_dir_value);
+  return SourceFile(std::move(root_dir_value));
 }
 
 SourceDir BundleData::GetBundleRootDirOutputAsDir(
diff --git a/tools/gn/bundle_file_rule.cc b/tools/gn/bundle_file_rule.cc
index 2b9881c..2b81cdf 100644
--- a/tools/gn/bundle_file_rule.cc
+++ b/tools/gn/bundle_file_rule.cc
@@ -87,7 +87,7 @@
           SubstitutionWriter::OUTPUT_ABSOLUTE, SourceDir()));
     }
   }
-  *expanded_source_file = SourceFile(SourceFile::SWAP_IN, &output_path);
+  *expanded_source_file = SourceFile(std::move(output_path));
   return true;
 }
 
diff --git a/tools/gn/c_include_iterator.cc b/tools/gn/c_include_iterator.cc
index 0c5476d..540d118 100644
--- a/tools/gn/c_include_iterator.cc
+++ b/tools/gn/c_include_iterator.cc
@@ -120,11 +120,7 @@
 const int CIncludeIterator::kMaxNonIncludeLines = 10;
 
 CIncludeIterator::CIncludeIterator(const InputFile* input)
-    : input_file_(input),
-      file_(input->contents()),
-      offset_(0),
-      line_number_(0),
-      lines_since_last_include_(0) {}
+    : input_file_(input), file_(input->contents()) {}
 
 CIncludeIterator::~CIncludeIterator() = default;
 
diff --git a/tools/gn/c_include_iterator.h b/tools/gn/c_include_iterator.h
index e81a60c..86a0954 100644
--- a/tools/gn/c_include_iterator.h
+++ b/tools/gn/c_include_iterator.h
@@ -43,13 +43,13 @@
   base::StringPiece file_;
 
   // 0-based offset into the file.
-  size_t offset_;
+  size_t offset_ = 0;
 
-  int line_number_;  // One-based. Indicates the last line we read.
+  int line_number_ = 0;  // One-based. Indicates the last line we read.
 
   // Number of lines we've processed since seeing the last include (or the
   // beginning of the file) with some exceptions.
-  int lines_since_last_include_;
+  int lines_since_last_include_ = 0;
 
   DISALLOW_COPY_AND_ASSIGN(CIncludeIterator);
 };
diff --git a/tools/gn/commands.cc b/tools/gn/commands.cc
index b7cd871..cf38725 100644
--- a/tools/gn/commands.cc
+++ b/tools/gn/commands.cc
@@ -238,7 +238,7 @@
     return false;
   }
 
-  // Filter into a copy of the vector, then swap to output.
+  // Filter into a copy of the vector, then replace the output.
   std::vector<const Target*> result;
   result.reserve(targets->size());
 
@@ -247,7 +247,7 @@
       result.push_back(target);
   }
 
-  targets->swap(result);
+  *targets = std::move(result);
   return true;
 }
 
@@ -260,7 +260,7 @@
   if (targets->empty() || type == Target::UNKNOWN)
     return true;  // Nothing to filter out.
 
-  // Filter into a copy of the vector, then swap to output.
+  // Filter into a copy of the vector, then replace the output.
   std::vector<const Target*> result;
   result.reserve(targets->size());
 
@@ -272,7 +272,7 @@
       result.push_back(target);
   }
 
-  targets->swap(result);
+  *targets = std::move(result);
   return true;
 }
 
diff --git a/tools/gn/config.cc b/tools/gn/config.cc
index e021fe4..e28fd30 100644
--- a/tools/gn/config.cc
+++ b/tools/gn/config.cc
@@ -11,7 +11,7 @@
 Config::Config(const Settings* settings,
                const Label& label,
                const std::set<SourceFile>& build_dependency_files)
-    : Item(settings, label, build_dependency_files), resolved_(false) {}
+    : Item(settings, label, build_dependency_files) {}
 
 Config::~Config() = default;
 
diff --git a/tools/gn/config.h b/tools/gn/config.h
index ad04973..040d54e 100644
--- a/tools/gn/config.h
+++ b/tools/gn/config.h
@@ -60,7 +60,7 @@
   // Contains the own_values combined with sub-configs. Most configs don't have
   // sub-configs. So as an optimization, this is not populated if there are no
   // items in configs_. The resolved_values() getter handles this.
-  bool resolved_;
+  bool resolved_ = false;
   ConfigValues composite_values_;
 
   UniqueVector<LabelConfigPair> configs_;
diff --git a/tools/gn/config_values_extractors.h b/tools/gn/config_values_extractors.h
index 5bb4229..cbcbed5 100644
--- a/tools/gn/config_values_extractors.h
+++ b/tools/gn/config_values_extractors.h
@@ -30,8 +30,7 @@
 //     DoSomething(iter.cur());
 class ConfigValuesIterator {
  public:
-  explicit ConfigValuesIterator(const Target* target)
-      : target_(target), cur_index_(-1) {}
+  explicit ConfigValuesIterator(const Target* target) : target_(target) {}
 
   bool done() const {
     return cur_index_ >= static_cast<int>(target_->configs().size());
@@ -66,7 +65,7 @@
 
   // Represents an index into the target_'s configs() or, when -1, the config
   // values on the target itself.
-  int cur_index_;
+  int cur_index_ = -1;
 };
 
 template <typename T, class Writer>
diff --git a/tools/gn/create_bundle_target_generator.cc b/tools/gn/create_bundle_target_generator.cc
index 3556b5d..a54d171 100644
--- a/tools/gn/create_bundle_target_generator.cc
+++ b/tools/gn/create_bundle_target_generator.cc
@@ -98,7 +98,7 @@
             str + "\".");
     return false;
   }
-  bundle_dir->SwapValue(&str);
+  *bundle_dir = SourceDir(std::move(str));
   return true;
 }
 
@@ -128,7 +128,8 @@
         std::make_pair(iter.first.as_string(), iter.second.string_value()));
   }
 
-  target_->bundle_data().xcode_extra_attributes().swap(xcode_extra_attributes);
+  target_->bundle_data().xcode_extra_attributes() =
+      std::move(xcode_extra_attributes);
   return true;
 }
 
@@ -217,7 +218,7 @@
                                   err_))
     return false;
 
-  target_->bundle_data().code_signing_sources().swap(script_sources);
+  target_->bundle_data().code_signing_sources() = std::move(script_sources);
   return true;
 }
 
diff --git a/tools/gn/escape.h b/tools/gn/escape.h
index 888d1b3..af5f8b8 100644
--- a/tools/gn/escape.h
+++ b/tools/gn/escape.h
@@ -41,16 +41,11 @@
 };
 
 struct EscapeOptions {
-  EscapeOptions()
-      : mode(ESCAPE_NONE),
-        platform(ESCAPE_PLATFORM_CURRENT),
-        inhibit_quoting(false) {}
-
-  EscapingMode mode;
+  EscapingMode mode = ESCAPE_NONE;
 
   // Controls how "fork" escaping is done. You will generally want to keep the
   // default "current" platform.
-  EscapingPlatform platform;
+  EscapingPlatform platform = ESCAPE_PLATFORM_CURRENT;
 
   // When the escaping mode is ESCAPE_SHELL, the escaper will normally put
   // quotes around things with spaces. If this value is set to true, we'll
@@ -60,7 +55,7 @@
   // false. Note that Windows has strange behavior where the meaning of the
   // backslashes changes according to if it is followed by a quote. The
   // escaping rules assume that a double-quote will be appended to the result.
-  bool inhibit_quoting;
+  bool inhibit_quoting = false;
 };
 
 // Escapes the given input, returnining the result.
diff --git a/tools/gn/filesystem_utils.cc b/tools/gn/filesystem_utils.cc
index 2fc4b24..cc121b3 100644
--- a/tools/gn/filesystem_utils.cc
+++ b/tools/gn/filesystem_utils.cc
@@ -869,7 +869,7 @@
     result_str.append(FilePathToUTF8(path_comp[i]));
     result_str.push_back('/');
   }
-  return SourceDir(result_str);
+  return SourceDir(std::move(result_str));
 }
 
 SourceDir SourceDirForCurrentDirectory(const base::FilePath& source_root) {
diff --git a/tools/gn/generated_file_target_generator.cc b/tools/gn/generated_file_target_generator.cc
index 1854d5b..2971221 100644
--- a/tools/gn/generated_file_target_generator.cc
+++ b/tools/gn/generated_file_target_generator.cc
@@ -17,10 +17,7 @@
     const FunctionCallNode* function_call,
     Target::OutputType type,
     Err* err)
-    : TargetGenerator(target, scope, function_call, err),
-      output_type_(type),
-      contents_defined_(false),
-      data_keys_defined_(false) {}
+    : TargetGenerator(target, scope, function_call, err), output_type_(type) {}
 
 GeneratedFileTargetGenerator::~GeneratedFileTargetGenerator() = default;
 
diff --git a/tools/gn/generated_file_target_generator.h b/tools/gn/generated_file_target_generator.h
index fb2523d..206555f 100644
--- a/tools/gn/generated_file_target_generator.h
+++ b/tools/gn/generated_file_target_generator.h
@@ -38,8 +38,8 @@
   bool IsMetadataCollectionTarget(const base::StringPiece& variable,
                                   const ParseNode* origin);
 
-  bool contents_defined_;
-  bool data_keys_defined_;
+  bool contents_defined_ = false;
+  bool data_keys_defined_ = false;
 
   Target::OutputType output_type_;
 
diff --git a/tools/gn/input_file.cc b/tools/gn/input_file.cc
index 438ab38..dc5ca37 100644
--- a/tools/gn/input_file.cc
+++ b/tools/gn/input_file.cc
@@ -7,7 +7,7 @@
 #include "base/files/file_util.h"
 
 InputFile::InputFile(const SourceFile& name)
-    : name_(name), dir_(name_.GetDir()), contents_loaded_(false) {}
+    : name_(name), dir_(name_.GetDir()) {}
 
 InputFile::~InputFile() = default;
 
diff --git a/tools/gn/input_file.h b/tools/gn/input_file.h
index 49e5f85..7a64c65 100644
--- a/tools/gn/input_file.h
+++ b/tools/gn/input_file.h
@@ -56,7 +56,7 @@
   base::FilePath physical_name_;
   std::string friendly_name_;
 
-  bool contents_loaded_;
+  bool contents_loaded_ = false;
   std::string contents_;
 
   DISALLOW_COPY_AND_ASSIGN(InputFile);
diff --git a/tools/gn/input_file_manager.cc b/tools/gn/input_file_manager.cc
index 2290dc7..aad8cc8 100644
--- a/tools/gn/input_file_manager.cc
+++ b/tools/gn/input_file_manager.cc
@@ -298,7 +298,7 @@
     InputFileData* data = input_files_[name].get();
     data->loaded = true;
     if (success) {
-      data->tokens.swap(tokens);
+      data->tokens = std::move(tokens);
       data->parsed_root = std::move(root);
     } else {
       data->parse_error = *err;
@@ -318,7 +318,7 @@
     if (data->completion_event)
       data->completion_event->Signal();
 
-    callbacks.swap(data->scheduled_callbacks);
+    callbacks = std::move(data->scheduled_callbacks);
   }
 
   // Run pending invocations. Theoretically we could schedule each of these
diff --git a/tools/gn/input_file_manager.h b/tools/gn/input_file_manager.h
index 20874d1..c4f19e9 100644
--- a/tools/gn/input_file_manager.h
+++ b/tools/gn/input_file_manager.h
@@ -38,7 +38,7 @@
  public:
   // Callback issued when a file is laoded. On auccess, the parse node will
   // refer to the root block of the file. On failure, this will be NULL.
-  typedef base::Callback<void(const ParseNode*)> FileLoadCallback;
+  using FileLoadCallback = base::Callback<void(const ParseNode*)>;
 
   InputFileManager();
 
@@ -137,8 +137,8 @@
   mutable std::mutex lock_;
 
   // Maps repo-relative filenames to the corresponding owned pointer.
-  typedef std::unordered_map<SourceFile, std::unique_ptr<InputFileData>>
-      InputFileMap;
+  using InputFileMap =
+      std::unordered_map<SourceFile, std::unique_ptr<InputFileData>>;
   InputFileMap input_files_;
 
   // Tracks all dynamic inputs. The data are holders for memory management
diff --git a/tools/gn/label.cc b/tools/gn/label.cc
index e8494be..22b6f81 100644
--- a/tools/gn/label.cc
+++ b/tools/gn/label.cc
@@ -250,8 +250,6 @@
     //tools/gn  ->  //tools/gn:gn
 )*";
 
-Label::Label() = default;
-
 Label::Label(const SourceDir& dir,
              const base::StringPiece& name,
              const SourceDir& toolchain_dir,
@@ -265,10 +263,6 @@
   name_.assign(name.data(), name.size());
 }
 
-Label::Label(const Label& other) = default;
-
-Label::~Label() = default;
-
 // static
 Label Label::Resolve(const SourceDir& current_dir,
                      const Label& current_toolchain,
diff --git a/tools/gn/label.h b/tools/gn/label.h
index 3c3d85a..6606a6b 100644
--- a/tools/gn/label.h
+++ b/tools/gn/label.h
@@ -17,7 +17,7 @@
 // part, so it starts with a slash, and has one colon.
 class Label {
  public:
-  Label();
+  Label() = default;
 
   // Makes a label given an already-separated out path and name.
   // See also Resolve().
@@ -28,8 +28,6 @@
 
   // Makes a label with an empty toolchain.
   Label(const SourceDir& dir, const base::StringPiece& name);
-  Label(const Label& other);
-  ~Label();
 
   // Resolves a string from a build file that may be relative to the
   // current directory into a fully qualified label. On failure returns an
@@ -71,20 +69,9 @@
   }
   bool operator!=(const Label& other) const { return !operator==(other); }
   bool operator<(const Label& other) const {
-    if (int c = dir_.value().compare(other.dir_.value()))
-      return c < 0;
-    if (int c = name_.compare(other.name_))
-      return c < 0;
-    if (int c = toolchain_dir_.value().compare(other.toolchain_dir_.value()))
-      return c < 0;
-    return toolchain_name_ < other.toolchain_name_;
-  }
-
-  void swap(Label& other) {
-    dir_.swap(other.dir_);
-    name_.swap(other.name_);
-    toolchain_dir_.swap(other.toolchain_dir_);
-    toolchain_name_.swap(other.toolchain_name_);
+    return std::tie(dir_, name_, toolchain_dir_, toolchain_name_) <
+           std::tie(other.dir_, other.name_, other.toolchain_dir_,
+                    other.toolchain_name_);
   }
 
   // Returns true if the toolchain dir/name of this object matches some
@@ -117,10 +104,6 @@
 
 }  // namespace std
 
-inline void swap(Label& lhs, Label& rhs) {
-  lhs.swap(rhs);
-}
-
 extern const char kLabels_Help[];
 
 #endif  // TOOLS_GN_LABEL_H_
diff --git a/tools/gn/lib_file.cc b/tools/gn/lib_file.cc
index 9c55aaa..81e54fb 100644
--- a/tools/gn/lib_file.cc
+++ b/tools/gn/lib_file.cc
@@ -6,8 +6,6 @@
 
 #include "base/logging.h"
 
-LibFile::LibFile() = default;
-
 LibFile::LibFile(const SourceFile& source_file) : source_file_(source_file) {}
 
 LibFile::LibFile(const base::StringPiece& lib_name)
@@ -15,11 +13,6 @@
   DCHECK(!lib_name.empty());
 }
 
-void LibFile::Swap(LibFile* other) {
-  name_.swap(other->name_);
-  source_file_.swap(other->source_file_);
-}
-
 const std::string& LibFile::value() const {
   return is_source_file() ? source_file_.value() : name_;
 }
diff --git a/tools/gn/lib_file.h b/tools/gn/lib_file.h
index f1f073f..58621eb 100644
--- a/tools/gn/lib_file.h
+++ b/tools/gn/lib_file.h
@@ -17,11 +17,11 @@
 // a library name (a string).
 class LibFile {
  public:
-  LibFile();
+  LibFile() = default;
+
   explicit LibFile(const base::StringPiece& lib_name);
   explicit LibFile(const SourceFile& source_file);
 
-  void Swap(LibFile* other);
   bool is_source_file() const { return name_.empty(); }
 
   // Returns name, or source_file().value() (whichever is set).
@@ -51,8 +51,4 @@
 
 }  // namespace std
 
-inline void swap(LibFile& lhs, LibFile& rhs) {
-  lhs.Swap(&rhs);
-}
-
 #endif  // TOOLS_GN_LIB_FILE_H_
diff --git a/tools/gn/loader.cc b/tools/gn/loader.cc
index a069fb8..b0f81bc 100644
--- a/tools/gn/loader.cc
+++ b/tools/gn/loader.cc
@@ -120,7 +120,8 @@
     std::unique_ptr<ToolchainRecord> new_record =
         std::make_unique<ToolchainRecord>(build_settings_, Label(), Label());
     ToolchainRecord* record = new_record.get();
-    toolchain_records_[Label()] = std::move(new_record);
+    Label empty_label;  // VS issues spurious warning using ...[Label()].
+    toolchain_records_[empty_label] = std::move(new_record);
 
     // The default build config is no dependent on the toolchain definition,
     // since we need to load the build config before we know what the default
@@ -383,7 +384,7 @@
     for (const auto& load : old_loads) {
       if (load.toolchain_name.is_null()) {
         // Fix up toolchain label
-        invocations_.insert(LoadID(load.file, label));
+        invocations_.emplace(load.file, label);
       } else {
         // Can keep the old one.
         invocations_.insert(load);
diff --git a/tools/gn/location.cc b/tools/gn/location.cc
index b9e4c22..2e7b27b 100644
--- a/tools/gn/location.cc
+++ b/tools/gn/location.cc
@@ -10,7 +10,7 @@
 #include "base/strings/string_number_conversions.h"
 #include "tools/gn/input_file.h"
 
-Location::Location() : file_(nullptr), line_number_(-1), column_number_(-1) {}
+Location::Location() = default;
 
 Location::Location(const InputFile* file,
                    int line_number,
diff --git a/tools/gn/location.h b/tools/gn/location.h
index de9b2fd..471391b 100644
--- a/tools/gn/location.h
+++ b/tools/gn/location.h
@@ -31,10 +31,10 @@
   std::string Describe(bool include_column_number) const;
 
  private:
-  const InputFile* file_;  // Null when unset.
-  int line_number_;        // -1 when unset. 1-based.
-  int column_number_;      // -1 when unset. 1-based.
-  int byte_;               // Index into the buffer, 0-based.
+  const InputFile* file_ = nullptr;  // Null when unset.
+  int line_number_ = -1;             // -1 when unset. 1-based.
+  int column_number_ = -1;           // -1 when unset. 1-based.
+  int byte_ = 0;                     // Index into the buffer, 0-based.
 };
 
 // Represents a range in a source file. Used for error reporting.
diff --git a/tools/gn/metadata.h b/tools/gn/metadata.h
index 3c16d27..06bd495 100644
--- a/tools/gn/metadata.h
+++ b/tools/gn/metadata.h
@@ -29,7 +29,6 @@
  public:
   using Contents = Scope::KeyValueMap;
 
-  // Members must be set explicitly.
   Metadata() = default;
 
   const ParseNode* origin() const { return origin_; }
@@ -38,7 +37,7 @@
   // The contents of this metadata varaiable.
   const Contents& contents() const { return contents_; }
   Contents& contents() { return contents_; }
-  void set_contents(Contents&& contents) { contents_.swap(contents); }
+  void set_contents(Contents&& contents) { contents_ = std::move(contents); }
 
   // The relative source directory to use when rebasing.
   const SourceDir& source_dir() const { return source_dir_; }
@@ -59,7 +58,7 @@
                 Err* err) const;
 
  private:
-  const ParseNode* origin_;
+  const ParseNode* origin_ = nullptr;
   Contents contents_;
   SourceDir source_dir_;
 
diff --git a/tools/gn/ninja_create_bundle_target_writer.cc b/tools/gn/ninja_create_bundle_target_writer.cc
index 32ae58e..dab4485 100644
--- a/tools/gn/ninja_create_bundle_target_writer.cc
+++ b/tools/gn/ninja_create_bundle_target_writer.cc
@@ -51,8 +51,10 @@
   // The compile_xcassets tool is only required if the target has asset
   // catalog resources to compile.
   if (TargetRequireAssetCatalogCompilation(target)) {
-    if (!target->toolchain()->GetTool(GeneralTool::kGeneralToolCompileXCAssets)) {
-      FailWithMissingToolError(GeneralTool::kGeneralToolCompileXCAssets, target);
+    if (!target->toolchain()->GetTool(
+            GeneralTool::kGeneralToolCompileXCAssets)) {
+      FailWithMissingToolError(GeneralTool::kGeneralToolCompileXCAssets,
+                               target);
       return false;
     }
   }
@@ -305,7 +307,7 @@
   // Since the code signature step depends on all the files from the bundle,
   // the create_bundle stamp can just depends on the output of the signature
   // script (dependencies are transitive).
-  output_files->swap(code_signing_output_files);
+  *output_files = std::move(code_signing_output_files);
 
   out_ << ": " << code_signing_rule_name;
   out_ << " | ";
diff --git a/tools/gn/ordered_set.h b/tools/gn/ordered_set.h
index 5081112..fda4e12 100644
--- a/tools/gn/ordered_set.h
+++ b/tools/gn/ordered_set.h
@@ -14,9 +14,9 @@
 template <typename T>
 class OrderedSet {
  private:
-  typedef std::set<T> set_type;
-  typedef typename set_type::const_iterator set_iterator;
-  typedef std::vector<set_iterator> vector_type;
+  using set_type = std::set<T>;
+  using set_iterator = typename set_type::const_iterator;
+  using vector_type = std::vector<set_iterator>;
 
  public:
   static const size_t npos = static_cast<size_t>(-1);
diff --git a/tools/gn/output_file.cc b/tools/gn/output_file.cc
index f92e097..e0c82fc 100644
--- a/tools/gn/output_file.cc
+++ b/tools/gn/output_file.cc
@@ -7,9 +7,7 @@
 #include "tools/gn/filesystem_utils.h"
 #include "tools/gn/source_file.h"
 
-OutputFile::OutputFile() : value_() {}
-
-OutputFile::OutputFile(std::string&& v) : value_(v) {}
+OutputFile::OutputFile(std::string&& v) : value_(std::move(v)) {}
 
 OutputFile::OutputFile(const std::string& v) : value_(v) {}
 
@@ -19,16 +17,13 @@
                         build_settings->build_dir(),
                         build_settings->root_path_utf8())) {}
 
-OutputFile::~OutputFile() = default;
-
 SourceFile OutputFile::AsSourceFile(const BuildSettings* build_settings) const {
   DCHECK(!value_.empty());
   DCHECK(value_[value_.size() - 1] != '/');
 
   std::string path = build_settings->build_dir().value();
   path.append(value_);
-  NormalizePath(&path);
-  return SourceFile(path);
+  return SourceFile(std::move(path));
 }
 
 SourceDir OutputFile::AsSourceDir(const BuildSettings* build_settings) const {
@@ -40,5 +35,5 @@
   std::string path = build_settings->build_dir().value();
   path.append(value_);
   NormalizePath(&path);
-  return SourceDir(path);
+  return SourceDir(std::move(path));
 }
diff --git a/tools/gn/output_file.h b/tools/gn/output_file.h
index a3a64e0..cd3ee33 100644
--- a/tools/gn/output_file.h
+++ b/tools/gn/output_file.h
@@ -17,12 +17,13 @@
 // relative to the output directory.
 class OutputFile {
  public:
-  OutputFile();
+  OutputFile() = default;
+
   explicit OutputFile(std::string&& v);
   explicit OutputFile(const std::string& v);
+
   OutputFile(const BuildSettings* build_settings,
              const SourceFile& source_file);
-  ~OutputFile();
 
   std::string& value() { return value_; }
   const std::string& value() const { return value_; }
@@ -59,8 +60,4 @@
 
 }  // namespace std
 
-inline void swap(OutputFile& lhs, OutputFile& rhs) {
-  lhs.value().swap(rhs.value());
-}
-
 #endif  // TOOLS_GN_OUTPUT_FILE_H_
diff --git a/tools/gn/scheduler.cc b/tools/gn/scheduler.cc
index 3e4eee9..f4960b9 100644
--- a/tools/gn/scheduler.cc
+++ b/tools/gn/scheduler.cc
@@ -16,14 +16,7 @@
 
 Scheduler::Scheduler()
     : main_thread_run_loop_(MsgLoop::Current()),
-      input_file_manager_(new InputFileManager),
-      verbose_logging_(false),
-      pool_work_count_lock_(),
-      pool_work_count_cv_(),
-      worker_pool_(),
-      is_failed_(false),
-      suppress_output_for_testing_(false),
-      has_been_shutdown_(false) {
+      input_file_manager_(new InputFileManager) {
   g_scheduler = this;
 }
 
diff --git a/tools/gn/scheduler.h b/tools/gn/scheduler.h
index 0e2203c..d005df5 100644
--- a/tools/gn/scheduler.h
+++ b/tools/gn/scheduler.h
@@ -115,7 +115,7 @@
 
   scoped_refptr<InputFileManager> input_file_manager_;
 
-  bool verbose_logging_;
+  bool verbose_logging_ = false;
 
   base::AtomicRefCount work_count_;
 
@@ -132,14 +132,14 @@
   WorkerPool worker_pool_;
 
   mutable std::mutex lock_;
-  bool is_failed_;
+  bool is_failed_ = false;
 
-  bool suppress_output_for_testing_;
+  bool suppress_output_for_testing_ = false;
 
   // Used to track whether the worker pool has been shutdown. This is necessary
   // to clean up after tests that make a scheduler but don't run the message
   // loop.
-  bool has_been_shutdown_;
+  bool has_been_shutdown_ = false;
 
   // Protected by the lock. See the corresponding Add/Get functions above.
   std::vector<base::FilePath> gen_dependencies_;
diff --git a/tools/gn/scope.h b/tools/gn/scope.h
index 585f151..6c26cdb 100644
--- a/tools/gn/scope.h
+++ b/tools/gn/scope.h
@@ -38,9 +38,9 @@
 // variables. So you should use a non-const containing scope whenever possible.
 class Scope {
  public:
-  typedef std::map<base::StringPiece, Value> KeyValueMap;
+  using KeyValueMap = std::map<base::StringPiece, Value>;
   // Holds an owning list of Items.
-  typedef std::vector<std::unique_ptr<Item>> ItemVector;
+  using ItemVector = std::vector<std::unique_ptr<Item>>;
 
   // A flag to indicate whether a function should recurse into nested scopes,
   // or only operate on the current scope.
diff --git a/tools/gn/settings.cc b/tools/gn/settings.cc
index 737e72a..c630fa7 100644
--- a/tools/gn/settings.cc
+++ b/tools/gn/settings.cc
@@ -10,10 +10,7 @@
 
 Settings::Settings(const BuildSettings* build_settings,
                    const std::string& output_subdir_name)
-    : build_settings_(build_settings),
-      import_manager_(),
-      base_config_(this),
-      greedy_target_generation_(false) {
+    : build_settings_(build_settings), base_config_(this) {
   if (output_subdir_name.empty()) {
     toolchain_output_dir_ = build_settings->build_dir();
   } else {
@@ -30,5 +27,3 @@
   if (!toolchain_output_dir_.is_null())
     toolchain_gen_dir_ = SourceDir(toolchain_output_dir_.value() + "gen/");
 }
-
-Settings::~Settings() = default;
diff --git a/tools/gn/settings.h b/tools/gn/settings.h
index f0a6691..eb9952f 100644
--- a/tools/gn/settings.h
+++ b/tools/gn/settings.h
@@ -35,7 +35,6 @@
   // Otherwise, it must end in a slash.
   Settings(const BuildSettings* build_settings,
            const std::string& output_subdir_name);
-  ~Settings();
 
   const BuildSettings* build_settings() const { return build_settings_; }
 
@@ -108,7 +107,7 @@
 
   Scope base_config_;
 
-  bool greedy_target_generation_;
+  bool greedy_target_generation_ = false;
 
   DISALLOW_COPY_AND_ASSIGN(Settings);
 };
diff --git a/tools/gn/setup.cc b/tools/gn/setup.cc
index e461e26..f3db362 100644
--- a/tools/gn/setup.cc
+++ b/tools/gn/setup.cc
@@ -38,6 +38,7 @@
 
 #if defined(OS_WIN)
 #include <windows.h>
+
 #include "base/win/scoped_process_information.h"
 #endif
 
@@ -197,8 +198,7 @@
 
   int mb_length = static_cast<int>(mb.length());
   // Compute the length of the buffer.
-  int charcount =
-      MultiByteToWideChar(CP_ACP, 0, mb.data(), mb_length, NULL, 0);
+  int charcount = MultiByteToWideChar(CP_ACP, 0, mb.data(), mb_length, NULL, 0);
   if (charcount == 0)
     return std::wstring();
 
@@ -297,12 +297,8 @@
       loader_(new LoaderImpl(&build_settings_)),
       builder_(loader_.get()),
       root_build_file_("//BUILD.gn"),
-      check_public_headers_(false),
       dotfile_settings_(&build_settings_, std::string()),
-      dotfile_scope_(&dotfile_settings_),
-      default_args_(nullptr),
-      fill_arguments_(true),
-      gen_empty_args_(false) {
+      dotfile_scope_(&dotfile_settings_) {
   dotfile_settings_.set_toolchain_label(Label());
 
   build_settings_.set_item_defined_callback(
@@ -314,8 +310,6 @@
   loader_->set_task_runner(scheduler_.task_runner());
 }
 
-Setup::~Setup() = default;
-
 bool Setup::DoSetup(const std::string& build_dir, bool force_create) {
   return DoSetup(build_dir, force_create,
                  *base::CommandLine::ForCurrentProcess());
@@ -446,7 +440,7 @@
   if (cmdline.HasSwitch(switches::kArgs) ||
       (gen_empty_args_ && !PathExists(build_arg_file))) {
     if (!FillArgsFromCommandLine(switch_value.empty() ? kDefaultArgsGn
-                                                    : switch_value)) {
+                                                      : switch_value)) {
       return false;
     }
     SaveArgsToFile();
@@ -538,7 +532,8 @@
   base::CreateDirectory(build_arg_file.DirName());
 
   std::string contents = args_input_file_->contents();
-  commands::FormatStringToString(contents, commands::TreeDumpMode::kInactive, &contents);
+  commands::FormatStringToString(contents, commands::TreeDumpMode::kInactive,
+                                 &contents);
 #if defined(OS_WIN)
   // Use Windows lineendings for this file since it will often open in
   // Notepad which can't handle Unix ones.
diff --git a/tools/gn/setup.h b/tools/gn/setup.h
index cf0136a..9aef073 100644
--- a/tools/gn/setup.h
+++ b/tools/gn/setup.h
@@ -34,7 +34,6 @@
 class Setup {
  public:
   Setup();
-  ~Setup();
 
   // Configures the build for the current command line. On success returns
   // true. On failure, prints the error and returns false.
@@ -148,7 +147,7 @@
 
   SourceFile root_build_file_;
 
-  bool check_public_headers_;
+  bool check_public_headers_ = false;
 
   // See getter for info.
   std::unique_ptr<std::vector<LabelPattern>> check_patterns_;
@@ -168,14 +167,14 @@
 
   // Default overrides, specified in the dotfile.
   // Owned by the Value (if it exists) in the dotfile_scope_.
-  const Scope* default_args_;
+  const Scope* default_args_ = nullptr;
 
   // Set to true when we should populate the build arguments from the command
   // line or build argument file. See setter above.
-  bool fill_arguments_;
+  bool fill_arguments_ = true;
 
   // Generate an empty args.gn file if it does not exists.
-  bool gen_empty_args_;
+  bool gen_empty_args_ = false;
 
   // State for invoking the command line args. We specifically want to keep
   // this around for the entire run so that Values can blame to the command
diff --git a/tools/gn/source_dir.cc b/tools/gn/source_dir.cc
index 50b4517..7def4b2 100644
--- a/tools/gn/source_dir.cc
+++ b/tools/gn/source_dir.cc
@@ -4,6 +4,8 @@
 
 #include "tools/gn/source_dir.h"
 
+#include <string>
+
 #include "base/logging.h"
 #include "tools/gn/filesystem_utils.h"
 #include "tools/gn/source_file.h"
@@ -57,23 +59,18 @@
 
 }  // namespace
 
-SourceDir::SourceDir() = default;
-
-SourceDir::SourceDir(const base::StringPiece& p) : value_(p.data(), p.size()) {
+SourceDir::SourceDir(const std::string& s) : value_(s) {
   if (!EndsWithSlash(value_))
     value_.push_back('/');
   AssertValueSourceDirString(value_);
 }
 
-SourceDir::SourceDir(SwapIn, std::string* s) {
-  value_.swap(*s);
+SourceDir::SourceDir(std::string&& s) : value_(std::move(s)) {
   if (!EndsWithSlash(value_))
     value_.push_back('/');
   AssertValueSourceDirString(value_);
 }
 
-SourceDir::~SourceDir() = default;
-
 template <typename StringType>
 std::string SourceDir::ResolveRelativeAs(
     bool as_file,
@@ -137,11 +134,6 @@
   return ResolvePath(value_, false, source_root);
 }
 
-void SourceDir::SwapValue(std::string* v) {
-  value_.swap(*v);
-  AssertValueSourceDirString(value_);
-}
-
 // Explicit template instantiation
 template std::string SourceDir::ResolveRelativeAs(
     bool as_file,
diff --git a/tools/gn/source_dir.h b/tools/gn/source_dir.h
index bfc260d..8b6dcc9 100644
--- a/tools/gn/source_dir.h
+++ b/tools/gn/source_dir.h
@@ -27,14 +27,10 @@
 // Two slashes at the beginning indicate a path relative to the source root.
 class SourceDir {
  public:
-  enum SwapIn { SWAP_IN };
+  SourceDir() = default;
 
-  SourceDir();
-  explicit SourceDir(const base::StringPiece& p);
-  // Swaps the given string in without copies. The given string will be empty
-  // after this call.
-  SourceDir(SwapIn, std::string* s);
-  ~SourceDir();
+  SourceDir(const std::string& s);
+  explicit SourceDir(std::string&& s);
 
   // Resolves a file or dir name (based on as_file parameter) relative
   // to this source directory. Will return an empty string on error
@@ -137,13 +133,9 @@
   bool operator!=(const SourceDir& other) const { return !operator==(other); }
   bool operator<(const SourceDir& other) const { return value_ < other.value_; }
 
-  void swap(SourceDir& other) { value_.swap(other.value_); }
-
  private:
   friend class SourceFile;
   std::string value_;
-
-  // Copy & assign supported.
 };
 
 namespace std {
@@ -158,8 +150,4 @@
 
 }  // namespace std
 
-inline void swap(SourceDir& lhs, SourceDir& rhs) {
-  lhs.swap(rhs);
-}
-
 #endif  // TOOLS_GN_SOURCE_DIR_H_
diff --git a/tools/gn/source_file.cc b/tools/gn/source_file.cc
index f925546..ce24207 100644
--- a/tools/gn/source_file.cc
+++ b/tools/gn/source_file.cc
@@ -53,26 +53,20 @@
 
 }  // namespace
 
-SourceFile::SourceFile() : type_(SOURCE_UNKNOWN) {}
-
-SourceFile::SourceFile(const base::StringPiece& p)
-    : value_(p.data(), p.size()) {
+SourceFile::SourceFile(const std::string& value) : value_(value) {
   DCHECK(!value_.empty());
   AssertValueSourceFileString(value_);
   NormalizePath(&value_);
   type_ = GetSourceFileType(value_);
 }
 
-SourceFile::SourceFile(SwapIn, std::string* value) {
-  value_.swap(*value);
+SourceFile::SourceFile(std::string&& value) : value_(std::move(value)) {
   DCHECK(!value_.empty());
   AssertValueSourceFileString(value_);
   NormalizePath(&value_);
   type_ = GetSourceFileType(value_);
 }
 
-SourceFile::~SourceFile() = default;
-
 std::string SourceFile::GetName() const {
   if (is_null())
     return std::string();
@@ -88,7 +82,7 @@
 
   DCHECK(value_.find('/') != std::string::npos);
   size_t last_slash = value_.rfind('/');
-  return SourceDir(base::StringPiece(&value_[0], last_slash + 1));
+  return SourceDir(value_.substr(0, last_slash + 1));
 }
 
 base::FilePath SourceFile::Resolve(const base::FilePath& source_root) const {
diff --git a/tools/gn/source_file.h b/tools/gn/source_file.h
index ed814c8..081cda6 100644
--- a/tools/gn/source_file.h
+++ b/tools/gn/source_file.h
@@ -42,19 +42,13 @@
     SOURCE_NUMTYPES,
   };
 
-  enum SwapIn { SWAP_IN };
-
-  SourceFile();
+  SourceFile() = default;
 
   // Takes a known absolute source file. Always begins in a slash.
-  explicit SourceFile(const base::StringPiece& p);
-  SourceFile(const SourceFile& other) = default;
+  explicit SourceFile(const std::string& value);
+  explicit SourceFile(std::string&& value);
 
-  // Constructs from the given string by swapping in the contents of the given
-  // value. The value will be the empty string after this call.
-  SourceFile(SwapIn, std::string* value);
-
-  ~SourceFile();
+  ~SourceFile() = default;
 
   bool is_null() const { return value_.empty(); }
   const std::string& value() const { return value_; }
@@ -97,20 +91,13 @@
     return value_ < other.value_;
   }
 
-  void swap(SourceFile& other) {
-    value_.swap(other.value_);
-    std::swap(type_, other.type_);
-  }
-
  private:
   friend class SourceDir;
 
   void SetValue(const std::string& value);
 
   std::string value_;
-  Type type_;
-
-  // Copy & assign supported.
+  Type type_ = SOURCE_UNKNOWN;
 };
 
 namespace std {
@@ -125,10 +112,6 @@
 
 }  // namespace std
 
-inline void swap(SourceFile& lhs, SourceFile& rhs) {
-  lhs.swap(rhs);
-}
-
 // Represents a set of tool types.
 class SourceFileTypeSet {
  public:
diff --git a/tools/gn/source_file_unittest.cc b/tools/gn/source_file_unittest.cc
index 110707a..d26b359 100644
--- a/tools/gn/source_file_unittest.cc
+++ b/tools/gn/source_file_unittest.cc
@@ -3,6 +3,7 @@
 // found in the LICENSE file.
 
 #include "tools/gn/source_file.h"
+
 #include "util/test/test.h"
 
 // The SourceFile object should normalize the input passed to the constructor.
@@ -13,7 +14,7 @@
   EXPECT_EQ("//bar.cc", a.value());
 
   std::string b_str("//foo/././../bar.cc");
-  SourceFile b(SourceFile::SwapIn(), &b_str);
+  SourceFile b(std::move(b_str));
   EXPECT_TRUE(b_str.empty());  // Should have been swapped in.
   EXPECT_EQ("//bar.cc", b.value());
 }
diff --git a/tools/gn/substitution_writer.cc b/tools/gn/substitution_writer.cc
index 8ca261e..8ce1105 100644
--- a/tools/gn/substitution_writer.cc
+++ b/tools/gn/substitution_writer.cc
@@ -212,7 +212,7 @@
   CHECK(!result_value.empty() && result_value[0] == '/')
       << "The result of the pattern \"" << pattern.AsString()
       << "\" was not a path beginning in \"/\" or \"//\".";
-  return SourceFile(SourceFile::SWAP_IN, &result_value);
+  return SourceFile(std::move(result_value));
 }
 
 // static
diff --git a/tools/gn/target.cc b/tools/gn/target.cc
index 60de120..7c9cd6d 100644
--- a/tools/gn/target.cc
+++ b/tools/gn/target.cc
@@ -279,15 +279,7 @@
 Target::Target(const Settings* settings,
                const Label& label,
                const std::set<SourceFile>& build_dependency_files)
-    : Item(settings, label, build_dependency_files),
-      output_type_(UNKNOWN),
-      output_prefix_override_(false),
-      output_extension_set_(false),
-      all_headers_public_(true),
-      check_includes_(true),
-      complete_static_lib_(false),
-      testonly_(false),
-      toolchain_(nullptr) {}
+    : Item(settings, label, build_dependency_files) {}
 
 Target::~Target() = default;
 
diff --git a/tools/gn/target.h b/tools/gn/target.h
index 60014d7..549b354 100644
--- a/tools/gn/target.h
+++ b/tools/gn/target.h
@@ -369,20 +369,20 @@
   void CheckSourcesGenerated() const;
   void CheckSourceGenerated(const SourceFile& source) const;
 
-  OutputType output_type_;
+  OutputType output_type_ = UNKNOWN;
   std::string output_name_;
-  bool output_prefix_override_;
+  bool output_prefix_override_ = false;
   SourceDir output_dir_;
   std::string output_extension_;
-  bool output_extension_set_;
+  bool output_extension_set_ = false;
 
   FileList sources_;
   SourceFileTypeSet source_types_used_;
-  bool all_headers_public_;
+  bool all_headers_public_ = true;
   FileList public_headers_;
-  bool check_includes_;
-  bool complete_static_lib_;
-  bool testonly_;
+  bool check_includes_ = true;
+  bool complete_static_lib_ = false;
+  bool testonly_ = false;
   std::vector<std::string> data_;
   BundleData bundle_data_;
   OutputFile write_runtime_deps_output_;
@@ -426,7 +426,7 @@
   RustValues rust_values_;
 
   // Toolchain used by this target. Null until target is resolved.
-  const Toolchain* toolchain_;
+  const Toolchain* toolchain_ = nullptr;
 
   // Output files. Empty until the target is resolved.
   std::vector<OutputFile> computed_outputs_;
diff --git a/tools/gn/target_generator.cc b/tools/gn/target_generator.cc
index cfcc4e3..09de19d 100644
--- a/tools/gn/target_generator.cc
+++ b/tools/gn/target_generator.cc
@@ -178,7 +178,7 @@
   if (!ExtractListOfRelativeFiles(scope_->settings()->build_settings(), *value,
                                   scope_->GetSourceDir(), &dest_sources, err_))
     return false;
-  target_->sources().swap(dest_sources);
+  target_->sources() = std::move(dest_sources);
   return true;
 }
 
@@ -194,7 +194,7 @@
   if (!ExtractListOfRelativeFiles(scope_->settings()->build_settings(), *value,
                                   scope_->GetSourceDir(), &dest_public, err_))
     return false;
-  target_->public_headers().swap(dest_public);
+  target_->public_headers() = std::move(dest_public);
   return true;
 }
 
diff --git a/tools/gn/tokenizer.cc b/tools/gn/tokenizer.cc
index 9625203..09f0b4b 100644
--- a/tools/gn/tokenizer.cc
+++ b/tools/gn/tokenizer.cc
@@ -69,12 +69,7 @@
 }  // namespace
 
 Tokenizer::Tokenizer(const InputFile* input_file, Err* err)
-    : input_file_(input_file),
-      input_(input_file->contents()),
-      err_(err),
-      cur_(0),
-      line_number_(1),
-      column_number_(1) {}
+    : input_file_(input_file), input_(input_file->contents()), err_(err) {}
 
 Tokenizer::~Tokenizer() = default;
 
diff --git a/tools/gn/tokenizer.h b/tools/gn/tokenizer.h
index 67590df..7b66ac0 100644
--- a/tools/gn/tokenizer.h
+++ b/tools/gn/tokenizer.h
@@ -79,10 +79,10 @@
   const InputFile* input_file_;
   const base::StringPiece input_;
   Err* err_;
-  size_t cur_;  // Byte offset into input buffer.
+  size_t cur_ = 0;  // Byte offset into input buffer.
 
-  int line_number_;
-  int column_number_;
+  int line_number_ = 1;
+  int column_number_ = 1;
 
   DISALLOW_COPY_AND_ASSIGN(Tokenizer);
 };
diff --git a/tools/gn/tool.cc b/tools/gn/tool.cc
index 8e06d11..d67933e 100644
--- a/tools/gn/tool.cc
+++ b/tools/gn/tool.cc
@@ -11,8 +11,7 @@
 
 const char* Tool::kToolNone = "";
 
-Tool::Tool(const char* n)
-    : defined_from_(nullptr), restat_(false), complete_(false), name_(n) {}
+Tool::Tool(const char* n) : name_(n) {}
 
 Tool::~Tool() = default;
 
diff --git a/tools/gn/tool.h b/tools/gn/tool.h
index 2f853ef..b963ebf 100644
--- a/tools/gn/tool.h
+++ b/tools/gn/tool.h
@@ -217,8 +217,8 @@
                  Err* err);
   bool ReadOutputExtension(Scope* scope, Err* err);
 
-  const ParseNode* defined_from_;
-  const char* name_;
+  const ParseNode* defined_from_ = nullptr;
+  const char* name_ = nullptr;
 
   SubstitutionPattern command_;
   std::string command_launcher_;
@@ -229,12 +229,12 @@
   SubstitutionList outputs_;
   SubstitutionList runtime_outputs_;
   std::string output_prefix_;
-  bool restat_;
+  bool restat_ = false;
   SubstitutionPattern rspfile_;
   SubstitutionPattern rspfile_content_;
   LabelPtrPair<Pool> pool_;
 
-  bool complete_;
+  bool complete_ = false;
 
   SubstitutionBits substitution_bits_;
 
diff --git a/tools/gn/unique_vector.h b/tools/gn/unique_vector.h
index 732b663..ec8bb27 100644
--- a/tools/gn/unique_vector.h
+++ b/tools/gn/unique_vector.h
@@ -27,28 +27,20 @@
 template <typename T>
 class UniquifyRef {
  public:
-  UniquifyRef()
-      : value_(nullptr),
-        vect_(nullptr),
-        index_(static_cast<size_t>(-1)),
-        hash_val_(0) {}
+  UniquifyRef() = default;
 
   // Initialize with a pointer to a value.
-  explicit UniquifyRef(const T* v)
-      : value_(v), vect_(nullptr), index_(static_cast<size_t>(-1)) {
-    FillHashValue();
-  }
+  explicit UniquifyRef(const T* v) : value_(v) { FillHashValue(); }
 
   // Initialize with an array + index.
-  UniquifyRef(const std::vector<T>* v, size_t i)
-      : value_(nullptr), vect_(v), index_(i) {
+  UniquifyRef(const std::vector<T>* v, size_t i) : vect_(v), index_(i) {
     FillHashValue();
   }
 
   // Initialize with an array + index and a known hash value to prevent
   // re-hashing.
   UniquifyRef(const std::vector<T>* v, size_t i, size_t hash_value)
-      : value_(nullptr), vect_(v), index_(i), hash_val_(hash_value) {}
+      : vect_(v), index_(i), hash_val_(hash_value) {}
 
   const T& value() const { return value_ ? *value_ : (*vect_)[index_]; }
   size_t hash_val() const { return hash_val_; }
@@ -61,13 +53,13 @@
   }
 
   // When non-null, points to the object.
-  const T* value_;
+  const T* value_ = nullptr;
 
   // When value is null these are used.
-  const std::vector<T>* vect_;
-  size_t index_;
+  const std::vector<T>* vect_ = nullptr;
+  size_t index_ = static_cast<size_t>(-1);
 
-  size_t hash_val_;
+  size_t hash_val_ = 0;
 };
 
 template <typename T>
@@ -131,18 +123,15 @@
     return true;
   }
 
-  // Like push_back but swaps in the type to avoid a copy.
-  bool PushBackViaSwap(T* t) {
-    using std::swap;
-
-    Ref ref(t);
+  bool push_back(T&& t) {
+    Ref ref(&t);
     if (set_.find(ref) != set_.end())
       return false;  // Already have this one.
 
-    size_t new_index = vector_.size();
-    vector_.resize(new_index + 1);
-    swap(vector_[new_index], *t);
-    set_.insert(Ref(&vector_, vector_.size() - 1, ref.hash_val()));
+    auto ref_hash_val = ref.hash_val();  // Save across moving t.
+
+    vector_.push_back(std::move(t));  // Invalidates |ref|.
+    set_.insert(Ref(&vector_, vector_.size() - 1, ref_hash_val));
     return true;
   }
 
diff --git a/tools/gn/unique_vector_unittest.cc b/tools/gn/unique_vector_unittest.cc
index afea1e2..008d284 100644
--- a/tools/gn/unique_vector_unittest.cc
+++ b/tools/gn/unique_vector_unittest.cc
@@ -2,11 +2,12 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
+#include "tools/gn/unique_vector.h"
+
 #include <stddef.h>
 
 #include <algorithm>
 
-#include "tools/gn/unique_vector.h"
 #include "util/test/test.h"
 
 TEST(UniqueVector, PushBack) {
@@ -30,14 +31,14 @@
   EXPECT_EQ(static_cast<size_t>(-1), foo.IndexOf(99));
 }
 
-TEST(UniqueVector, PushBackViaSwap) {
+TEST(UniqueVector, PushBackMove) {
   UniqueVector<std::string> vect;
   std::string a("a");
-  EXPECT_TRUE(vect.PushBackViaSwap(&a));
+  EXPECT_TRUE(vect.push_back(std::move(a)));
   EXPECT_EQ("", a);
 
   a = "a";
-  EXPECT_FALSE(vect.PushBackViaSwap(&a));
+  EXPECT_FALSE(vect.push_back(std::move(a)));
   EXPECT_EQ("a", a);
 
   EXPECT_EQ(0u, vect.IndexOf("a"));
diff --git a/tools/gn/visual_studio_writer.cc b/tools/gn/visual_studio_writer.cc
index 9dbd4b3..5f4380c 100644
--- a/tools/gn/visual_studio_writer.cc
+++ b/tools/gn/visual_studio_writer.cc
@@ -817,7 +817,7 @@
     } else {
       std::string folder_path_str = folder_path.as_string();
       std::unique_ptr<SolutionEntry> folder = std::make_unique<SolutionEntry>(
-          FindLastDirComponent(SourceDir(folder_path)).as_string(),
+          FindLastDirComponent(SourceDir(std::string(folder_path))).as_string(),
           folder_path_str, MakeGuid(folder_path_str, kGuidSeedFolder));
       project->parent_folder = folder.get();
       processed_paths[folder_path] = folder.get();
@@ -863,7 +863,8 @@
       } else {
         std::unique_ptr<SolutionEntry> new_folder =
             std::make_unique<SolutionEntry>(
-                FindLastDirComponent(SourceDir(parent_path)).as_string(),
+                FindLastDirComponent(SourceDir(std::string(parent_path)))
+                    .as_string(),
                 parent_path.as_string(),
                 MakeGuid(parent_path.as_string(), kGuidSeedFolder));
         processed_paths[parent_path] = new_folder.get();