// File: /workspace/github_cpp_makefile_star2_O2/white0dew[P]WebServer/http/http_conn.cpp
// Function: http_conn::parse_request_line(char*)
http_conn::HTTP_CODE http_conn::parse_request_line(char *text)
{
    //在HTTP报文中，请求行用来说明请求类型
    //要访问的资源以及所使用的HTTP版本，其中各个部分之间通过\t或空格分隔。
    //请求行中最先含有空格和\t任一字符的位置并返回

    //strpbrk在源字符串（s1）中找出最先含有搜索字符串（s2）
    //中任一字符的位置并返回，若找不到则返回空指针
    m_url = strpbrk(text, " \t");
    //如果没有空格或\t，则报文格式有误
    if (!m_url)
    {
        return BAD_REQUEST;
    }
    //将该位置改为\0，用于将前面数据取出
    //(已读取的数据不再会匹配到\t）
    *m_url++ = '\0';

    //取出数据，并通过与GET和POST比较，以确定请求方式
    char *method = text;
    if (strcasecmp(method, "GET") == 0)
        m_method = GET;
    else if (strcasecmp(method, "POST") == 0)
    {
        m_method = POST;
        cgi = 1;
    }
    else
        return BAD_REQUEST;
    //m_url此时跳过了第一个空格或\t字符，但不知道之后是否还有
    //将m_url向后偏移，通过查找
    //继续跳过空格和\t字符，指向请求资源的第一个字符

    //strspn:检索字符串 str1 中第一个不在字符串 str2 中出现的字符下标
    //即跳过匹配的字符串片段
    m_url += strspn(m_url, " \t");

    //相同逻辑，判断HTTP版本号
    m_version = strpbrk(m_url, " \t");
    if (!m_version)
        return BAD_REQUEST;
    *m_version++ = '\0';
    m_version += strspn(m_version, " \t");
    //仅支持HTTP/1.1
    if (strcasecmp(m_version, "HTTP/1.1") != 0)
        return BAD_REQUEST;
    
    //对请求资源前7个字符进行判断
    //这里主要是有些报文的请求资源中会带有http://
    //这里需要对这种情况进行单独处理
    if (strncasecmp(m_url, "http://", 7) == 0)
    {
        m_url += 7;
        m_url = strchr(m_url, '/');
    }

    //同样增加https情况
    if (strncasecmp(m_url, "https://", 8) == 0)
    {
        m_url += 8;
        m_url = strchr(m_url, '/');
    }

    //一般的不会带有上述两种符号，直接是单独的/或/后面带访问资源
    if (!m_url || m_url[0] != '/')
        return BAD_REQUEST;
    //当url为/时，显示欢迎界面
    if (strlen(m_url) == 1)
        strcat(m_url, "judge.html");
    
    //请求行处理完毕，将主状态机转移处理请求头
    m_check_state = CHECK_STATE_HEADER;
    return NO_REQUEST;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %rbx
pushq %rax
movq %rsi, %r14
movq %rdi, %rbx
leaq 0x3d75(%rip), %rsi      # 0x8227
movq %r14, %rdi
callq 0x3620
movq %rax, 0xd08(%rbx)
pushq $0x2
popq %rbp
testq %rax, %rax
je 0x45a2
movq %rax, %rcx
incq %rcx
movq %rcx, 0xd08(%rbx)
movb $0x0, (%rax)
leaq 0x3d46(%rip), %rsi      # 0x822a
movq %r14, %rdi
callq 0x3400
testl %eax, %eax
je 0x451b
leaq 0x3d37(%rip), %rsi      # 0x822e
movq %r14, %rdi
callq 0x3400
testl %eax, %eax
jne 0x45a2
movl $0x1, 0xc3c(%rbx)
pushq $0x1
popq %rax
movl $0xde4, %ecx            # imm = 0xDE4
jmp 0x4522
xorl %eax, %eax
movl $0xc3c, %ecx            # imm = 0xC3C
movl %eax, (%rbx,%rcx)
movq 0xd08(%rbx), %r14
leaq 0x3cf4(%rip), %r15      # 0x8227
movq %r14, %rdi
movq %r15, %rsi
callq 0x3150
addq %rax, %r14
movq %r14, 0xd08(%rbx)
movq %r14, %rdi
movq %r15, %rsi
callq 0x3620
movq %rax, 0xd10(%rbx)
testq %rax, %rax
je 0x45a2
movq %rax, %rcx
incq %rcx
movq %rcx, 0xd10(%rbx)
movb $0x0, (%rax)
movq 0xd10(%rbx), %r14
leaq 0x3caa(%rip), %rsi      # 0x8227
movq %r14, %rdi
callq 0x3150
addq %rax, %r14
movq %r14, 0xd10(%rbx)
leaq 0x3c9d(%rip), %rsi      # 0x8233
movq %r14, %rdi
callq 0x3400
testl %eax, %eax
je 0x45af
movl %ebp, %eax
addq $0x8, %rsp
popq %rbx
popq %r14
popq %r15
popq %rbp
retq
movq 0xd08(%rbx), %r14
leaq 0x3c7f(%rip), %rsi      # 0x823c
pushq $0x7
popq %rdx
movq %r14, %rdi
callq 0x34d0
testl %eax, %eax
jne 0x45ec
addq $0x7, %r14
movq %r14, 0xd08(%rbx)
pushq $0x2f
popq %rsi
movq %r14, %rdi
callq 0x3130
movq %rax, %r14
movq %rax, 0xd08(%rbx)
leaq 0x3c51(%rip), %rsi      # 0x8244
pushq $0x8
popq %rdx
movq %r14, %rdi
callq 0x34d0
testl %eax, %eax
jne 0x4622
addq $0x8, %r14
movq %r14, 0xd08(%rbx)
pushq $0x2f
popq %rsi
movq %r14, %rdi
callq 0x3130
movq %rax, %r14
movq %rax, 0xd08(%rbx)
testq %r14, %r14
je 0x45a2
cmpb $0x2f, (%r14)
jne 0x45a2
movq %r14, %rdi
callq 0x3160
cmpq $0x1, %rax
jne 0x4662
movq %r14, %rdi
callq 0x3160
movabsq $0x74682e656764756a, %rcx # imm = 0x74682E656764756A
movq %rcx, (%r14,%rax)
movl $0x6c6d74, 0x7(%r14,%rax) # imm = 0x6C6D74
movl $0x1, 0xc38(%rbx)
xorl %ebp, %ebp
jmp 0x45a2
nop