    //! Finds the end of an HTTP head in a stream.

    state: State = .start,

    pub const State = enum {
        start,
        seen_n,
        seen_r,
        seen_rn,
        seen_rnr,
        finished,
    };

    /// Returns the number of bytes consumed by headers. This is always less
    /// than or equal to `bytes.len`.
    ///
    /// If the amount returned is less than `bytes.len`, the parser is in a
    /// content state and the first byte of content is located at
    /// `bytes[result]`.
    pub fn feed(p: *HeadParser, bytes: []const u8) usize {
        const vector_len: comptime_int = @max(std.simd.suggestVectorLength(u8) orelse 1, 8);
        var index: usize = 0;

        while (true) {
            switch (p.state) {
                .finished => return index,
                .start => switch (bytes.len - index) {
                    0 => return index,
                    1 => {
                        switch (bytes[index]) {
                            '\r' => p.state = .seen_r,
                            '\n' => p.state = .seen_n,
                            else => {},
                        }

                        return index + 1;
                    },
                    2 => {
                        const b16 = int16(bytes[index..][0..2]);
                        const b8 = intShift(u8, b16);

                        switch (b8) {
                            '\r' => p.state = .seen_r,
                            '\n' => p.state = .seen_n,
                            else => {},
                        }

                        switch (b16) {
                            int16("\r\n") => p.state = .seen_rn,
                            int16("\n\n") => p.state = .finished,
                            else => {},
                        }

                        return index + 2;
                    },
                    3 => {
                        const b24 = int24(bytes[index..][0..3]);
                        const b16 = intShift(u16, b24);
                        const b8 = intShift(u8, b24);

                        switch (b8) {
                            '\r' => p.state = .seen_r,
                            '\n' => p.state = .seen_n,
                            else => {},
                        }

                        switch (b16) {
                            int16("\r\n") => p.state = .seen_rn,
                            int16("\n\n") => p.state = .finished,
                            else => {},
                        }

                        switch (b24) {
                            int24("\r\n\r") => p.state = .seen_rnr,
                            else => {},
                        }

                        return index + 3;
                    },
                    4...vector_len - 1 => {
                        const b32 = int32(bytes[index..][0..4]);
                        const b24 = intShift(u24, b32);
                        const b16 = intShift(u16, b32);
                        const b8 = intShift(u8, b32);

                        switch (b8) {
                            '\r' => p.state = .seen_r,
                            '\n' => p.state = .seen_n,
                            else => {},
                        }

                        switch (b16) {
                            int16("\r\n") => p.state = .seen_rn,
                            int16("\n\n") => p.state = .finished,
                            else => {},
                        }

                        switch (b24) {
                            int24("\r\n\r") => p.state = .seen_rnr,
                            else => {},
                        }

                        switch (b32) {
                            int32("\r\n\r\n") => p.state = .finished,
                            else => {},
                        }

                        index += 4;
                        continue;
                    },
                    else => {
                        const chunk = bytes[index..][0..vector_len];
                        const matches = if (use_vectors) matches: {
                            const Vector = @Vector(vector_len, u8);
                            // const BoolVector = @Vector(vector_len, bool);

                            const BitVector = @Vector(vector_len, u1);
                            const SizeVector = @Vector(vector_len, u8);

                            const v: Vector = chunk.*;
                            const matches_r: BitVector = @bitCast(v == @as(Vector, @splat('\r')));
                            const matches_n: BitVector = @bitCast(v == @as(Vector, @splat('\n')));
                            const matches_or: SizeVector = matches_r | matches_n;

                            break :matches @reduce(.Add, matches_or);
                        } else matches: {
                            var matches: u8 = 0;
                            for (chunk) |byte| switch (byte) {
                                '\r', '\n' => matches += 1,
                                else => {},
                            };
                            break :matches matches;
                        };
                        switch (matches) {
                            0 => {},
                            1 => switch (chunk[vector_len - 1]) {
                                '\r' => p.state = .seen_r,
                                '\n' => p.state = .seen_n,
                                else => {},
                            },
                            2 => {
                                const b16 = int16(chunk[vector_len - 2 ..][0..2]);
                                const b8 = intShift(u8, b16);

                                switch (b8) {
                                    '\r' => p.state = .seen_r,
                                    '\n' => p.state = .seen_n,
                                    else => {},
                                }

                                switch (b16) {
                                    int16("\r\n") => p.state = .seen_rn,
                                    int16("\n\n") => p.state = .finished,
                                    else => {},
                                }
                            },
                            3 => {
                                const b24 = int24(chunk[vector_len - 3 ..][0..3]);
                                const b16 = intShift(u16, b24);
                                const b8 = intShift(u8, b24);

                                switch (b8) {
                                    '\r' => p.state = .seen_r,
                                    '\n' => p.state = .seen_n,
                                    else => {},
                                }

                                switch (b16) {
                                    int16("\r\n") => p.state = .seen_rn,
                                    int16("\n\n") => p.state = .finished,
                                    else => {},
                                }

                                switch (b24) {
                                    int24("\r\n\r") => p.state = .seen_rnr,
                                    else => {},
                                }
                            },
                            4...vector_len => {
                                inline for (0..vector_len - 3) |i_usize| {
                                    const i = @as(u32, @truncate(i_usize));

                                    const b32 = int32(chunk[i..][0..4]);
                                    const b16 = intShift(u16, b32);

                                    if (b32 == int32("\r\n\r\n")) {
                                        p.state = .finished;
                                        return index + i + 4;
                                    } else if (b16 == int16("\n\n")) {
                                        p.state = .finished;
                                        return index + i + 2;
                                    }
                                }

                                const b24 = int24(chunk[vector_len - 3 ..][0..3]);
                                const b16 = intShift(u16, b24);
                                const b8 = intShift(u8, b24);

                                switch (b8) {
                                    '\r' => p.state = .seen_r,
                                    '\n' => p.state = .seen_n,
                                    else => {},
                                }

                                switch (b16) {
                                    int16("\r\n") => p.state = .seen_rn,
                                    int16("\n\n") => p.state = .finished,
                                    else => {},
                                }

                                switch (b24) {
                                    int24("\r\n\r") => p.state = .seen_rnr,
                                    else => {},
                                }
                            },
                            else => unreachable,
                        }

                        index += vector_len;
                        continue;
                    },
                },
                .seen_n => switch (bytes.len - index) {
                    0 => return index,
                    else => {
                        switch (bytes[index]) {
                            '\n' => p.state = .finished,
                            else => p.state = .start,
                        }

                        index += 1;
                        continue;
                    },
                },
                .seen_r => switch (bytes.len - index) {
                    0 => return index,
                    1 => {
                        switch (bytes[index]) {
                            '\n' => p.state = .seen_rn,
                            '\r' => p.state = .seen_r,
                            else => p.state = .start,
                        }

                        return index + 1;
                    },
                    2 => {
                        const b16 = int16(bytes[index..][0..2]);
                        const b8 = intShift(u8, b16);

                        switch (b8) {
                            '\r' => p.state = .seen_r,
                            '\n' => p.state = .seen_rn,
                            else => p.state = .start,
                        }

                        switch (b16) {
                            int16("\r\n") => p.state = .seen_rn,
                            int16("\n\r") => p.state = .seen_rnr,
                            int16("\n\n") => p.state = .finished,
                            else => {},
                        }

                        return index + 2;
                    },
                    else => {
                        const b24 = int24(bytes[index..][0..3]);
                        const b16 = intShift(u16, b24);
                        const b8 = intShift(u8, b24);

                        switch (b8) {
                            '\r' => p.state = .seen_r,
                            '\n' => p.state = .seen_n,
                            else => p.state = .start,
                        }

                        switch (b16) {
                            int16("\r\n") => p.state = .seen_rn,
                            int16("\n\n") => p.state = .finished,
                            else => {},
                        }

                        switch (b24) {
                            int24("\n\r\n") => p.state = .finished,
                            else => {},
                        }

                        index += 3;
                        continue;
                    },
                },
                .seen_rn => switch (bytes.len - index) {
                    0 => return index,
                    1 => {
                        switch (bytes[index]) {
                            '\r' => p.state = .seen_rnr,
                            '\n' => p.state = .seen_n,
                            else => p.state = .start,
                        }

                        return index + 1;
                    },
                    else => {
                        const b16 = int16(bytes[index..][0..2]);
                        const b8 = intShift(u8, b16);

                        switch (b8) {
                            '\r' => p.state = .seen_rnr,
                            '\n' => p.state = .seen_n,
                            else => p.state = .start,
                        }

                        switch (b16) {
                            int16("\r\n") => p.state = .finished,
                            int16("\n\n") => p.state = .finished,
                            else => {},
                        }

                        index += 2;
                        continue;
                    },
                },
                .seen_rnr => switch (bytes.len - index) {
                    0 => return index,
                    else => {
                        switch (bytes[index]) {
                            '\n' => p.state = .finished,
                            else => p.state = .start,
                        }

                        index += 1;
                        continue;
                    },
                },
            }

            return index;
        }
    }

    inline fn int16(array: *const [2]u8) u16 {
        return @bitCast(array.*);
    }

    inline fn int24(array: *const [3]u8) u24 {
        return @bitCast(array.*);
    }

    inline fn int32(array: *const [4]u8) u32 {
        return @bitCast(array.*);
    }

    inline fn intShift(comptime T: type, x: anytype) T {
        switch (@import("builtin").cpu.arch.endian()) {
            .little => return @truncate(x >> (@bitSizeOf(@TypeOf(x)) - @bitSizeOf(T))),
            .big => return @truncate(x),
        }
    }

    const HeadParser = @This();
    const std = @import("std");
    const use_vectors = builtin.zig_backend != .stage2_x86_64;
    const builtin = @import("builtin");

    test feed {
        const data = "GET / HTTP/1.1\r\nHost: localhost\r\n\r\nHello";

        for (0..36) |i| {
            var p: HeadParser = .{};
            try std.testing.expectEqual(i, p.feed(data[0..i]));
            try std.testing.expectEqual(35 - i, p.feed(data[i..]));
        }
    }