tensorflow/compiler/tf2xla/graph_compiler_util.cc
// Each fetch id identifies the positional output of some node.  For each fetch
// node, adds a new _Retval node instead, and adds the node to `retval_nodes`.
Each fetch id identifies the positional output of some node.  For each fetch
node, adds a new _Retval node instead, and adds the node to `retval_nodes`.
Each fetch id identifies the positional output of some node . For each fetch node adds a new _Retval node instead and adds the node to ` retval_nodes ` .
Status AddRetvalNodes(Graph* graph, const NodeMap& node_map,
                      const protobuf::RepeatedPtrField<tf2xla::Fetch>& fetches,
                      std::unordered_set<const Node*>* retval_nodes) {
  for (int ret_index = 0; ret_index < fetches.size(); ++ret_index) {
    const tf2xla::TensorId& id = fetches[ret_index].id();
    auto it = node_map.find(id.node_name());
    if (it == node_map.end()) {
      return errors::NotFound("Can't find fetch id: ", TensorIdToString(id));
    }
    Node* fetch_node = it->second;
    if (id.output_index() >= fetch_node->num_outputs()) {
      return errors::InvalidArgument("Invalid fetch id: ", TensorIdToString(id),
                                     ", output index should be < ",
                                     fetch_node->num_outputs());
    }
    Node* retval_node = nullptr;
    TF_RETURN_IF_ERROR(
        NodeBuilder(absl::StrCat("_retval_", ret_index),
                    FunctionLibraryDefinition::kRetOp)
            .Input(fetch_node, id.output_index())
            .Attr("T", BaseType(fetch_node->output_type(id.output_index())))
            .Attr("index", ret_index)
            .Attr(kFetchIdAttr, TensorIdToString(id))
            .Finalize(graph, &retval_node));
    retval_nodes->insert(retval_node);
  }
  return Status::OK();
}
Status AddRetvalNodes ( Graph * graph , const NodeMap & node_map , const protobuf :: RepeatedPtrField < tf2xla :: Fetch > & fetches , std :: unordered_set < const Node * > * retval_nodes ) { for ( int ret_index = 0 ; ret_index < fetches . size ( ) ; ++ ret_index ) { const tf2xla :: TensorId & id = fetches [ ret_index ] . id ( ) ; auto it = node_map . find ( id . node_name ( ) ) ; if ( it == node_map . end ( ) ) { return errors :: NotFound ( " " , TensorIdToString ( id ) ) ; } Node * fetch_node = it -> second ; if ( id . output_index ( ) >= fetch_node -> num_outputs ( ) ) { return errors :: InvalidArgument ( " " , TensorIdToString ( id ) , " " , fetch_node -> num_outputs ( ) ) ; } Node * retval_node = nullptr ; TF_RETURN_IF_ERROR ( NodeBuilder ( absl :: StrCat ( " " , ret_index ) , FunctionLibraryDefinition :: kRetOp ) . Input ( fetch_node , id . output_index ( ) ) . Attr ( " " , BaseType ( fetch_node -> output_type ( id . output_index ( ) ) ) ) . Attr ( " " , ret_index ) . Attr ( kFetchIdAttr , TensorIdToString ( id ) ) . Finalize ( graph , & retval_node ) ) ; retval_nodes -> insert ( retval_node ) ; } return Status :: OK ( ) ; }
Each fetch id identifies the positional output of some node.
Each fetch id identifies the positional output of some node .
// Connects fetch_node -> retval_node.