Return which chunks a file doesn't have.

    Specifically, we return a list of the chunks specified by a
    length-offset range which are not in the datastore.

    Args:
      fd: The database object to read chunks from.
      length: Length to read.
      offset: File offset to read from.

    Returns:
      A list of chunk numbers.

def GetMissingChunks(self, fd, length, offset):
    """Return which chunks a file doesn't have.

    Specifically, we return a list of the chunks specified by a
    length-offset range which are not in the datastore.

    Args:
      fd: The database object to read chunks from.
      length: Length to read.
      offset: File offset to read from.

    Returns:
      A list of chunk numbers.
    """
    start_chunk = offset // fd.chunksize
    end_chunk = (offset + length - 1) // fd.chunksize

    relevant_chunks = range(start_chunk, end_chunk + 1)

    missing_chunks = set(relevant_chunks)
    for idx, metadata in iteritems(fd.ChunksMetadata(relevant_chunks)):
      if not self.DataRefreshRequired(last=metadata.get("last", None)):
        missing_chunks.remove(idx)

    return sorted(missing_chunks)