BuildValue ExternalCommand:: getResultForOutput(Node* node, const BuildValue& value) { // If the value was a failed or skipped command, propagate the failure. if (value.isFailedCommand() || value.isSkippedCommand()) return BuildValue::makeFailedInput(); // Otherwise, we should have a successful command -- return the actual // result for the output. assert(value.isSuccessfulCommand()); // If the node is virtual, the output is always a virtual input value. if (static_cast<BuildNode*>(node)->isVirtual()) { return BuildValue::makeVirtualInput(); } // Find the index of the output node. // // FIXME: This is O(N). We don't expect N to be large in practice, but it // could be. auto it = std::find(outputs.begin(), outputs.end(), node); assert(it != outputs.end()); auto idx = it - outputs.begin(); assert(idx < value.getNumOutputs()); auto& info = value.getNthOutputInfo(idx); if (info.isMissing()) return BuildValue::makeMissingOutput(); return BuildValue::makeExistingInput(info); }
bool ExternalCommand::canUpdateIfNewerWithResult(const BuildValue& result) { // Unless `allowModifiedOutputs` is specified, we always need to update if // ran. if (!allowModifiedOutputs) return false; // If it was specified, then we can update if all of our outputs simply exist. for (unsigned i = 0, e = result.getNumOutputs(); i != e; ++i) { const FileInfo& outputInfo = result.getNthOutputInfo(i); // If the output is missing, we need to rebuild. if (outputInfo.isMissing()) return false; } return true; }