def _clean_index(key, length):
    """
    Validates and normalizes a cell range index.

    >>> _clean_index(0, 10)
    0
    >>> _clean_index(-10, 10)
    0
    >>> _clean_index(10, 10)
    Traceback (most recent call last):
    ...
    IndexError: Cell index out of range.
    >>> _clean_index(-11, 10)
    Traceback (most recent call last):
    ...
    IndexError: Cell index out of range.
    >>> _clean_index(None, 10)
    Traceback (most recent call last):
    ...
    TypeError: Cell indices must be integers, NoneType given.

    """
    if not isinstance(key, integer_types):
        raise TypeError('Cell indices must be integers, %s given.' % type(key).__name__)
    if -length <= key < 0:
        return key + length
    elif 0 <= key < length:
        return key
    else:
        raise IndexError('Cell index out of range.')