Skip to content

Commit

Permalink
compiler: Correct depfile generation when there are no outputs
Browse files Browse the repository at this point in the history
Prevents the compiler from generating a malformed depfile if an inpout file did not lead to any meaningful generation. This is an edge case that is not exercised often.

PiperOrigin-RevId: 542354842
  • Loading branch information
protobuf-github-bot authored and copybara-github committed Jun 21, 2023
1 parent b0b926a commit a44fc2b
Showing 1 changed file with 26 additions and 21 deletions.
47 changes: 26 additions & 21 deletions src/google/protobuf/compiler/command_line_interface.cc
Original file line number Diff line number Diff line change
Expand Up @@ -2520,6 +2520,7 @@ bool CommandLineInterface::GenerateDependencyManifestFile(
output_filenames.push_back(descriptor_set_out_name_);
}

// Create the depfile, even if it will be empty.
int fd;
do {
fd = open(dependency_out_name_.c_str(),
Expand All @@ -2531,30 +2532,34 @@ bool CommandLineInterface::GenerateDependencyManifestFile(
return false;
}

io::FileOutputStream out(fd);
io::Printer printer(&out, '$');
// Only write to the depfile if there is at least one output_filename.
// Otherwise, the depfile will be malformed.
if (!output_filenames.empty()) {
io::FileOutputStream out(fd);
io::Printer printer(&out, '$');

for (int i = 0; i < output_filenames.size(); i++) {
printer.Print(output_filenames[i]);
if (i == output_filenames.size() - 1) {
printer.Print(":");
} else {
printer.Print(" \\\n");
for (size_t i = 0; i < output_filenames.size(); i++) {
printer.Print(output_filenames[i]);
if (i == output_filenames.size() - 1) {
printer.Print(":");
} else {
printer.Print(" \\\n");
}
}
}

for (int i = 0; i < file_set.file_size(); i++) {
const FileDescriptorProto& file = file_set.file(i);
const std::string& virtual_file = file.name();
std::string disk_file;
if (source_tree &&
source_tree->VirtualFileToDiskFile(virtual_file, &disk_file)) {
printer.Print(" $disk_file$", "disk_file", disk_file);
if (i < file_set.file_size() - 1) printer.Print("\\\n");
} else {
std::cerr << "Unable to identify path for file " << virtual_file
<< std::endl;
return false;
for (int i = 0; i < file_set.file_size(); i++) {
const FileDescriptorProto& file = file_set.file(i);
const std::string& virtual_file = file.name();
std::string disk_file;
if (source_tree &&
source_tree->VirtualFileToDiskFile(virtual_file, &disk_file)) {
printer.Print(" $disk_file$", "disk_file", disk_file);
if (i < file_set.file_size() - 1) printer.Print("\\\n");
} else {
std::cerr << "Unable to identify path for file " << virtual_file
<< std::endl;
return false;
}
}
}

Expand Down

0 comments on commit a44fc2b

Please sign in to comment.