code: def compute_row_mask(
      shape: Tuple[int, int],
      span_len: int,
      max_mask_prob: float,
      row_lens: Optional[Tensor] = None,
      min_num_spans: int = 0,
      device: Optional[Device] = None,
  ) -> Optional[Tensor]:
      """Compute a random row mask of the specified shape.
  
      :param shape:
          The shape of the mask.
      :param span_len:
          The length of each mask span.
      :param max_mask_prob:
          The maximum probability of masking an element among all elements in a
          row. Note that, due to mask span overlap, the effective probability
          might be smaller. The implementation also guarantees that there is
          always at least one unmasked element in each row.
      :param row_lens:
          The length of each row. *Shape:* :math:`(R)`, where :math:`R` is the
          number of rows.
      :param min_num_spans:
          The minimum number of mask spans per row.
      :param device:
          The device on which to initialize the mask.
  
      :returns:
          The boolean row mask. *:Shape:* ``shape``.
      """
      num_rows, max_row_len = shape
  
      if row_lens is None:
          # We only mask rows that are longer than the mask span length.
          if span_len >= max_row_len:
              raise ValueError(
                  f"The size of the second dimension of `shape` must be greater than `span_len` ({span_len}), but is {max_row_len} instead."
              )
  
          row_lens = torch.full(
              (num_rows,), max_row_len, device=device, dtype=torch.int64
          )
      else:
          row_lens = row_lens.view(num_rows)
  
          # We only mask rows that are longer than the mask span length.
          if (span_len >= row_lens).any():
              raise ValueError(
                  f"All lengths in `row_lens` must be greater than `span_len` ({span_len}), but at least one length is smaller. row_lens: {row_lens}"
              )
  
      indices = _compute_mask_spans(
          row_lens, span_len, max_mask_prob, min_num_spans
      )
      if indices is None:
          return row_lens.new_empty((0, 0))
  
      return _generate_mask(indices, max_row_len).to(device)
  
file_path: fairseq2/src/fairseq2/nn/utils/mask.py
imports: from typing import Optional, Tuple
  import torch
  from torch import Tensor
  from fairseq2.nn.ops import repeat_interleave
  from fairseq2.typing import DataType, Device
label_desc: Use image node_id 2 for calling a global function with example usage: compute_row_mask(shape, span_len, max_mask_prob, row_lens, min_num_spans, device) and returns: _generate_mask, row_lens