// File: /workspace/github_c_makefile_star2_O2/justy989[P]ce/ce_vim.c
// Function: ce_vim_move_begin_little_word
CePoint_t ce_vim_move_begin_little_word(CeBuffer_t* buffer, CePoint_t start){
     WordState_t state = WORD_INSIDE_OTHER;

     start.x--;
     if(!ce_buffer_point_is_valid(buffer, start)){
          if(start.x == -1){
               start.y--;
               if(start.y < 0) return (CePoint_t){0, 0};
               start.x = ce_utf8_strlen(buffer->lines[start.y]);
               if(start.x > 0) start.x--;
               else return start;
               state = WORD_NEW_LINE;
          }else{
               return (CePoint_t){-1, -1};
          }
     }


     char* line_start = buffer->lines[start.y];
     char* itr = ce_utf8_iterate_to(line_start, start.x); // start one character back

     int64_t rune_len = 0;
     CeRune_t rune = ce_utf8_decode_reverse(itr, line_start, &rune_len);

     if(is_little_word_character(rune)){
          if(start.x == 0) return start;
          state = WORD_INSIDE_WORD;
     }else if(isspace(rune)){
          state = WORD_INSIDE_SPACE;
     }else{
          if(start.x == 0) return start;
     }

     itr -= rune_len;

     while(true){
          rune = ce_utf8_decode_reverse(itr, line_start, &rune_len);

          switch(state){
          default:
               assert(0);
               break;
          case WORD_INSIDE_WORD:
               if(isspace(rune)) goto END_LOOP;
               else if(!is_little_word_character(rune)) goto END_LOOP;
               break;
          case WORD_INSIDE_SPACE:
               if(is_little_word_character(rune)) state = WORD_INSIDE_WORD;
               else if(!isspace(rune)) state = WORD_INSIDE_OTHER;;
               break;
          case WORD_INSIDE_OTHER:
               if(isspace(rune)) goto END_LOOP;
               else if(is_little_word_character(rune)) goto END_LOOP;
               break;
          case WORD_NEW_LINE:
               if(is_little_word_character(rune)) state = WORD_INSIDE_WORD;
               if(isspace(rune)) state = WORD_INSIDE_SPACE;
               goto END_LOOP;
          }

          itr -= rune_len;
          start.x--;

          if(itr < line_start){
               if(state == WORD_INSIDE_WORD || state == WORD_INSIDE_OTHER) break;

               start.y--;
               if(start.y < 0) return (CePoint_t){0, 0};
               start.x = ce_utf8_strlen(buffer->lines[start.y]);
               if(start.x > 0) start.x--;
               else break;
               line_start = buffer->lines[start.y];
               itr = ce_utf8_iterate_to(line_start, start.x); // start one character back
               state = WORD_NEW_LINE;
          }
     }

END_LOOP:
     return start;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x18, %rsp
movq %rdx, %r12
movq %rsi, %r15
movq %rdi, %rbx
leaq -0x1(%rsi), %r14
movq %r14, %rsi
callq 0xe425
testq %rax, %rax
je 0x23aa0
pushq $0x2
popq %rbp
movq %rbx, 0x10(%rsp)
movq (%rbx), %rax
movq %r12, (%rsp)
movq (%rax,%r12,8), %r12
movq %r12, %rdi
movq %r14, %rsi
callq 0xe4a6
movq %rax, %r13
leaq 0x8(%rsp), %rdx
andq $0x0, (%rdx)
movq %rax, %rdi
movq %r12, %rsi
callq 0xfd39
movl %eax, %ebx
movl %eax, %edi
callq 0x23570
testb %al, %al
je 0x23ab2
xorl %ebp, %ebp
jmp 0x23ac4
testq %r15, %r15
je 0x23bf7
pushq $-0x1
popq %r14
movq %r14, %r12
jmp 0x23ad0
callq 0xd720
movq (%rax), %rax
movslq %ebx, %rcx
testb $0x20, 0x1(%rax,%rcx,2)
jne 0x23ae5
testq %r14, %r14
jne 0x23ae8
xorl %r14d, %r14d
movq (%rsp), %r12
movq %r14, %rax
movq %r12, %rdx
addq $0x18, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
pushq $0x1
popq %rbp
leaq 0x8(%rsp), %rax
subq (%rax), %r13
leaq 0x96f1(%rip), %rbx      # 0x2d1e8
movq %r13, %rdi
movq %r12, %rsi
leaq 0x8(%rsp), %rdx
callq 0xfd39
movl %eax, %r15d
movl %ebp, %eax
movslq (%rbx,%rax,4), %rax
addq %rbx, %rax
movslq %r15d, %rbp
jmpq *%rax
callq 0xd720
movq (%rax), %rax
testb $0x20, 0x1(%rax,%rbp,2)
jne 0x23acc
movl %r15d, %edi
callq 0x23570
testb %al, %al
jne 0x23b41
jmp 0x23acc
movl %r15d, %edi
callq 0x23570
testb %al, %al
je 0x23b77
xorl %eax, %eax
movb $0x1, %cl
xorl %ebp, %ebp
jmp 0x23b8f
callq 0xd720
movq (%rax), %rax
testb $0x20, 0x1(%rax,%rbp,2)
jne 0x23acc
movl %r15d, %edi
callq 0x23570
testb %al, %al
jne 0x23acc
movb $0x1, %al
xorl %ecx, %ecx
pushq $0x2
popq %rdx
movl %edx, %ebp
jmp 0x23b8f
callq 0xd720
movq (%rax), %rcx
xorl %eax, %eax
testb $0x20, 0x1(%rcx,%rbp,2)
sete %al
movl %eax, %ebp
incl %ebp
xorl %ecx, %ecx
subq 0x8(%rsp), %r13
decq %r14
cmpq %r12, %r13
jae 0x23af7
orb %al, %cl
jne 0x23acc
movq (%rsp), %r12
testq %r12, %r12
jle 0x23c22
decq %r12
movq 0x10(%rsp), %r15
movq (%r15), %rax
movq (%rax,%r12,8), %rdi
callq 0xe38c
movq %rax, %r14
testq %rax, %rax
jle 0x23ad0
decq %r14
movq (%r15), %rax
movq %r12, (%rsp)
movq (%rax,%r12,8), %r12
movq %r12, %rdi
movq %r14, %rsi
callq 0xe4a6
movq %rax, %r13
pushq $0x3
popq %rax
movl %eax, %ebp
jmp 0x23af7
testq %r12, %r12
jle 0x23c22
movq (%rbx), %rax
movq -0x8(%rax,%r12,8), %rdi
decq %r12
callq 0xe38c
movq %rax, %r14
testq %rax, %rax
jle 0x23ad0
decq %r14
pushq $0x3
jmp 0x23a5c
xorl %r14d, %r14d
xorl %r12d, %r12d
jmp 0x23ad0