There are three possibilities for each decoding step:

        - Decode as much real UTF-8 as possible.
        - Decode a six-byte CESU-8 sequence at the current position.
        - Decode a Java-style null at the current position.

        This method figures out which step is appropriate, and does it.

def _buffer_decode_step(self, input, errors, final):
        """
        There are three possibilities for each decoding step:

        - Decode as much real UTF-8 as possible.
        - Decode a six-byte CESU-8 sequence at the current position.
        - Decode a Java-style null at the current position.

        This method figures out which step is appropriate, and does it.
        """
        # Get a reference to the superclass method that we'll be using for
        # most of the real work.
        sup = UTF8IncrementalDecoder._buffer_decode

        # Find the next byte position that indicates a variant of UTF-8.
        match = SPECIAL_BYTES_RE.search(input)
        if match is None:
            return sup(input, errors, final)

        cutoff = match.start()
        if cutoff > 0:
            return sup(input[:cutoff], errors, True)

        # Some byte sequence that we intend to handle specially matches
        # at the beginning of the input.
        if input.startswith(b'\xc0'):
            if len(input) > 1:
                # Decode the two-byte sequence 0xc0 0x80.
                return '\u0000', 2
            else:
                if final:
                    # We hit the end of the stream. Let the superclass method
                    # handle it.
                    return sup(input, errors, True)
                else:
                    # Wait to see another byte.
                    return '', 0
        else:
            # Decode a possible six-byte sequence starting with 0xed.
            return self._buffer_decode_surrogates(sup, input, errors, final)