class_docstr: Similar to the torch version, but support non-Tensor outputs.
  
  The caller is expected to provide a dict (*parent_ctx_dict*) that will hold
  the non-Tensor outputs. These should be combined with the Tensor *outputs*
  by calling ``unpack_non_tensors``.
code: def forward(ctx, run_function, parent_ctx_dict, kwarg_keys, *args):
      if (
          torch.is_grad_enabled()
      ):  # grad may be disabled, e.g., during validation
          checkpoint.check_backward_validity(args)
  
      ctx.run_function = run_function
      ctx.kwarg_keys = kwarg_keys
      ctx.fwd_rng_state = utils.get_rng_state()
  
      tensor_inputs, packed_non_tensor_inputs = split_non_tensors(args)
      if parent_ctx_dict["offload"]:
          ctx.fwd_device = tuple(x.device for x in tensor_inputs)
          ctx.grad_requirements = tuple(
              x.requires_grad for x in tensor_inputs
          )
          tensor_inputs = tuple(
              x.to(torch.device("cpu"), non_blocking=True)
              for x in tensor_inputs
          )
  
      else:
          ctx.fwd_device, ctx.grad_requirements = None, None
  
      ctx.save_for_backward(*tensor_inputs)
      ctx.packed_non_tensor_inputs = packed_non_tensor_inputs
  
      with torch.no_grad():
          unpacked_args, unpacked_kwargs = unpack_kwargs(
              kwarg_keys, args
          )
          outputs = run_function(*unpacked_args, **unpacked_kwargs)
  
      if isinstance(outputs, torch.Tensor):
          return outputs
      else:
          # Autograd Functions don't like non-Tensor outputs. We can split the
          # non-Tensor and Tensor outputs, returning the former by reference
          # through *parent_ctx_dict* and returning the latter directly.
          outputs, packed_non_tensor_outputs = split_non_tensors(
              outputs
          )
          parent_ctx_dict[
              "packed_non_tensor_outputs"
          ] = packed_non_tensor_outputs
          return outputs
  
file_path: fairseq/fairseq/modules/checkpoint_activations.py
imports: import functools
  from typing import Any, Dict, List, Tuple, Union
  import torch
  import torch.utils.checkpoint
  from fairseq import utils
label_desc: Use image node_id 1 for calling the CheckpointFunction obj's underlying member method code with example usage: obj.forward(ctx, run_function, parent_ctx_dict, kwarg_keys) and returns: outputs, outputs