private function getStream(int $cursor = null, int $length = null) : string
    {
        if ($cursor === null) {
            $cursor = $this->cursor;
        }

        // If the cached length isn't the same or if the cursor has actually gone backwards, use the original input
        if ($this->streamCache['length'] !== $length || $this->streamCache['cursor'] > $cursor) {
            $this->streamCache['cursor'] = $cursor;
            $this->streamCache['length'] = $length;

            if ($length === null) {
                $this->streamCache['stream'] = substr($this->input, $cursor);
            } else {
                $this->streamCache['stream'] = substr($this->input, $cursor, $length);
            }
        } elseif ($this->streamCache['length'] === $length && $this->streamCache['cursor'] !== $cursor) {
            // Grab the substring from the cached stream
            $cursorDifference = $cursor - $this->streamCache['cursor'];

            if ($length === null) {
                $this->streamCache['stream'] = substr($this->streamCache['stream'], $cursorDifference);
            } else {
                $this->streamCache['stream'] = substr($this->streamCache['stream'], $cursorDifference, $length);
            }

            $this->streamCache['cursor'] = $cursor;
        }

        return $this->streamCache['stream'];
    }