Don't allow ./ before target name.

Do not put a leading "./" on any ninja target paths when writing MSVS
project files.  Ninja.exe -tclean breaks on such paths.

BUG=chromium:791295

Change-Id: I5c427ddc41e1e18122022aa85cf6c1f0ff62fbfc
Reviewed-on: https://gn-review.googlesource.com/2580
Commit-Queue: Dirk Pranke <dpranke@chromium.org>
Reviewed-by: Dirk Pranke <dpranke@chromium.org>
diff --git a/tools/gn/visual_studio_writer.cc b/tools/gn/visual_studio_writer.cc
index 856d548..c4fd906 100644
--- a/tools/gn/visual_studio_writer.cc
+++ b/tools/gn/visual_studio_writer.cc
@@ -904,5 +904,8 @@
   DCHECK(!target->dependency_output_file().value().empty());
   ninja_path_output_.WriteFile(ninja_target_out,
                                target->dependency_output_file());
-  return ninja_target_out.str();
+  std::string s = ninja_target_out.str();
+  if (s.compare(0, 2, "./") == 0)
+    s = s.substr(2);
+  return s;
 }
diff --git a/tools/gn/visual_studio_writer.h b/tools/gn/visual_studio_writer.h
index d9bb883..3193646 100644
--- a/tools/gn/visual_studio_writer.h
+++ b/tools/gn/visual_studio_writer.h
@@ -53,6 +53,7 @@
   FRIEND_TEST_ALL_PREFIXES(VisualStudioWriterTest, ResolveSolutionFolders);
   FRIEND_TEST_ALL_PREFIXES(VisualStudioWriterTest,
                            ResolveSolutionFolders_AbsPath);
+  FRIEND_TEST_ALL_PREFIXES(VisualStudioWriterTest, NoDotSlash);
 
   // Solution project or folder.
   struct SolutionEntry {
diff --git a/tools/gn/visual_studio_writer_unittest.cc b/tools/gn/visual_studio_writer_unittest.cc
index 0fe736d..165bbb4 100644
--- a/tools/gn/visual_studio_writer_unittest.cc
+++ b/tools/gn/visual_studio_writer_unittest.cc
@@ -163,3 +163,38 @@
   ASSERT_EQ(writer.folders_[0].get(), writer.projects_[2]->parent_folder);
   ASSERT_EQ(writer.folders_[1].get(), writer.projects_[3]->parent_folder);
 }
+
+TEST_F(VisualStudioWriterTest, NoDotSlash) {
+  VisualStudioWriter writer(setup_.build_settings(), "Win32",
+                            VisualStudioWriter::Version::Vs2015,
+                            "10.0.17134.0");
+
+  std::string path = MakeTestPath("blah.vcxproj");
+  writer.projects_.push_back(
+      std::make_unique<VisualStudioWriter::SolutionProject>(
+          "base", path, MakeGuid(path, "project"), MakeTestPath("/foo"),
+          "Win32"));
+
+  std::unique_ptr<Tool> tool = std::make_unique<Tool>();
+  tool->set_outputs(SubstitutionList::MakeForTest(
+      "{{root_out_dir}}/{{target_output_name}}{{output_extension}}", ""));
+
+  Toolchain toolchain(setup_.settings(), Label(SourceDir("//tc/"), "tc"));
+  toolchain.SetTool(Toolchain::TYPE_ALINK, std::move(tool));
+
+  Target target(setup_.settings(), Label(SourceDir("//baz/"), "baz"));
+  target.set_output_type(Target::STATIC_LIBRARY);
+  target.SetToolchain(&toolchain);
+
+  Err err;
+  ASSERT_TRUE(target.OnResolved(&err));
+
+  VisualStudioWriter::SourceFileCompileTypePairs source_types;
+
+  std::stringstream file_contents;
+  writer.WriteProjectFileContents(file_contents, *writer.projects_.back(),
+                                  &target, "", &source_types, &err);
+
+  // Should find args of a ninja clean command, with no ./ before the file name.
+  ASSERT_NE(file_contents.str().find("-tclean baz"), std::string::npos);
+}