Commit 44128e3c authored by dpranke's avatar dpranke Committed by Commit bot

Make the gn copy() tool honor dependencies.

Previously it didn't, and perhaps there was no need for
it to, but it seems like NaCl has a need. Specifically,
NaCl has two targets A and B with both run fine on their
own, but A can delete the output of B, and so needs to run
before B.

R=brettw@chromium.org
BUG=428576

Review URL: https://codereview.chromium.org/693443002

Cr-Commit-Position: refs/heads/master@{#302342}
parent 1c79f864
...@@ -71,6 +71,9 @@ void NinjaCopyTargetWriter::WriteCopyRules( ...@@ -71,6 +71,9 @@ void NinjaCopyTargetWriter::WriteCopyRules(
GetNinjaRulePrefixForToolchain(settings_) + GetNinjaRulePrefixForToolchain(settings_) +
Toolchain::ToolTypeToName(Toolchain::TYPE_COPY); Toolchain::ToolTypeToName(Toolchain::TYPE_COPY);
OutputFile input_dep =
WriteInputDepsStampAndGetDep(std::vector<const Target*>());
// Note that we don't write implicit deps for copy steps. "copy" only // Note that we don't write implicit deps for copy steps. "copy" only
// depends on the output files themselves, rather than having includes // depends on the output files themselves, rather than having includes
// (the possibility of generated #includes is the main reason for implicit // (the possibility of generated #includes is the main reason for implicit
...@@ -92,6 +95,11 @@ void NinjaCopyTargetWriter::WriteCopyRules( ...@@ -92,6 +95,11 @@ void NinjaCopyTargetWriter::WriteCopyRules(
// //
// Moreover, doing this assumes that the copy step is always a simple // Moreover, doing this assumes that the copy step is always a simple
// locally run command, so there is no need for a toolchain dependency. // locally run command, so there is no need for a toolchain dependency.
//
// Note that there is the need in some cases for order-only dependencies
// where a command might need to make sure something else runs before it runs
// to avoid conflicts. Such cases should be avoided where possible, but
// sometimes that's not possible.
for (size_t i = 0; i < target_->sources().size(); i++) { for (size_t i = 0; i < target_->sources().size(); i++) {
const SourceFile& input_file = target_->sources()[i]; const SourceFile& input_file = target_->sources()[i];
...@@ -104,6 +112,10 @@ void NinjaCopyTargetWriter::WriteCopyRules( ...@@ -104,6 +112,10 @@ void NinjaCopyTargetWriter::WriteCopyRules(
path_output_.WriteFile(out_, output_file); path_output_.WriteFile(out_, output_file);
out_ << ": " << tool_name << " "; out_ << ": " << tool_name << " ";
path_output_.WriteFile(out_, input_file); path_output_.WriteFile(out_, input_file);
if (!input_dep.value().empty()) {
out_ << " || ";
path_output_.WriteFile(out_, input_dep);
}
out_ << std::endl; out_ << std::endl;
} }
} }
...@@ -10,7 +10,7 @@ ...@@ -10,7 +10,7 @@
#include "tools/gn/target.h" #include "tools/gn/target.h"
#include "tools/gn/test_with_scope.h" #include "tools/gn/test_with_scope.h"
// Tests mutliple files with an output pattern and no toolchain dependency. // Tests multiple files with an output pattern and no toolchain dependency.
TEST(NinjaCopyTargetWriter, Run) { TEST(NinjaCopyTargetWriter, Run) {
TestWithScope setup; TestWithScope setup;
Err err; Err err;
...@@ -71,3 +71,33 @@ TEST(NinjaCopyTargetWriter, ToolchainDeps) { ...@@ -71,3 +71,33 @@ TEST(NinjaCopyTargetWriter, ToolchainDeps) {
std::string out_str = out.str(); std::string out_str = out.str();
EXPECT_EQ(expected_linux, out_str); EXPECT_EQ(expected_linux, out_str);
} }
TEST(NinjaCopyTargetWriter, OrderOnlyDeps) {
TestWithScope setup;
Err err;
setup.settings()->set_target_os(Settings::LINUX);
setup.build_settings()->SetBuildDir(SourceDir("//out/Debug/"));
Target target(setup.settings(), Label(SourceDir("//foo/"), "bar"));
target.set_output_type(Target::COPY_FILES);
target.sources().push_back(SourceFile("//foo/input1.txt"));
target.action_values().outputs() =
SubstitutionList::MakeForTest("//out/Debug/{{source_name_part}}.out");
target.inputs().push_back(SourceFile("//foo/script.py"));
target.SetToolchain(setup.toolchain());
ASSERT_TRUE(target.OnResolved(&err));
std::ostringstream out;
NinjaCopyTargetWriter writer(&target, out);
writer.Run();
const char expected_linux[] =
"build obj/foo/bar.inputdeps.stamp: stamp ../../foo/script.py\n"
"build input1.out: copy ../../foo/input1.txt || "
"obj/foo/bar.inputdeps.stamp\n"
"\n"
"build obj/foo/bar.stamp: stamp input1.out\n";
std::string out_str = out.str();
EXPECT_EQ(expected_linux, out_str);
}
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment