// File: /workspace/github_c_makefile_star2_O2/justy989[P]ce/ce_app.c
// Function: extract_completion_from_response
CeComplete_t* _extract_completion_from_response(CeJsonObj_t* obj, CePoint_t* start){
     CeComplete_t* result = NULL;

     CeJsonFindResult_t result_find = ce_json_obj_find(obj, "result");
     if(result_find.type != CE_JSON_TYPE_OBJECT){
          return result;
     }

     // TODO: check isIncomplete

     CeJsonObj_t* result_obj = ce_json_obj_get_obj(obj, &result_find);

     CeJsonFindResult_t items_find = ce_json_obj_find(result_obj, "items");
     if(items_find.type != CE_JSON_TYPE_ARRAY){
          return result;
     }

     CeJsonArray_t* items_array = ce_json_obj_get_array(result_obj, &items_find);
     if(items_array == NULL){
          return result;
     }

     int64_t completion_count = 0;
     char** completions = NULL;
     char** descriptions = NULL;

     for(int64_t i = 0; i < items_array->count; i++){
          CeJsonValue_t* value = items_array->values + i;
          if(value->type != CE_JSON_TYPE_OBJECT){
               continue;
          }

          CeJsonFindResult_t insert_text_find = ce_json_obj_find(&value->obj, "insertText");
          if(insert_text_find.type != CE_JSON_TYPE_STRING){
               continue;
          }

          CeJsonFindResult_t detail_find = ce_json_obj_find(&value->obj, "detail");

          char* completion = strdup(ce_json_obj_get_string(&value->obj, &insert_text_find));


          CeJsonFindResult_t label_find = ce_json_obj_find(&value->obj, "label");

          char* description = NULL;
          if(label_find.type == CE_JSON_TYPE_STRING){
               int64_t completion_len = strlen(completion);
               char* match = strstr(ce_json_obj_get_string(&value->obj, &label_find),
                                    completion);
               if(match && strlen(match + completion_len) > 0){
                    char buffer[BUFSIZ];
                    if(detail_find.type == CE_JSON_TYPE_STRING){
                         snprintf(buffer, BUFSIZ, "%s%s",
                                  ce_json_obj_get_string(&value->obj, &detail_find),
                                  match + completion_len);
                    }else{
                         snprintf(buffer, BUFSIZ, "%s", match + completion_len);
                    }
                    description = strdup(buffer);
               }else if(detail_find.type == CE_JSON_TYPE_STRING){
                    description = strdup(ce_json_obj_get_string(&value->obj, &detail_find));
               }
          }else{
               description = strdup(ce_json_obj_get_string(&value->obj, &detail_find));
          }

          int64_t new_completion_count = completion_count + 1;
          completions = realloc(completions, new_completion_count * sizeof(completions[0]));
          descriptions = realloc(descriptions, new_completion_count * sizeof(descriptions[0]));
          completions[completion_count] = completion;
          descriptions[completion_count] = description;
          completion_count = new_completion_count;

          CeJsonFindResult_t text_edit_find = ce_json_obj_find(&value->obj, "textEdit");
          if(text_edit_find.type != CE_JSON_TYPE_OBJECT){
               continue;
          }
          CeJsonObj_t* text_edit_obj = ce_json_obj_get_obj(&value->obj, &text_edit_find);
          if(text_edit_obj == NULL){
               continue;
          }
          CeJsonFindResult_t range_find = ce_json_obj_find(text_edit_obj, "range");
          if(range_find.type != CE_JSON_TYPE_OBJECT){
               continue;
          }
          CeJsonObj_t* range_obj = ce_json_obj_get_obj(text_edit_obj, &range_find);
          if(range_obj == NULL){
               continue;
          }
          CeJsonFindResult_t start_find = ce_json_obj_find(range_obj, "start");
          if(start_find.type != CE_JSON_TYPE_OBJECT){
               continue;
          }
          CeJsonObj_t* start_obj = ce_json_obj_get_obj(range_obj, &start_find);
          if(start_obj == NULL){
               continue;
          }
          CeJsonFindResult_t line_find = ce_json_obj_find(start_obj, "line");
          if(line_find.type != CE_JSON_TYPE_NUMBER){
               continue;
          }
          CeJsonFindResult_t character_find = ce_json_obj_find(start_obj, "character");
          if(character_find.type != CE_JSON_TYPE_NUMBER){
               continue;
          }
          start->x = *ce_json_obj_get_number(start_obj, &character_find);
          start->y = *ce_json_obj_get_number(start_obj, &line_find);
     }

     result = malloc(sizeof(*result));
     memset(result, 0, sizeof(*result));
     ce_complete_init(result, (const char**)completions, (const char**)descriptions, completion_count);
     for(int64_t i = 0; i < completion_count; i++){
          free(completions[i]);
          free(descriptions[i]);
     }
     free(completions);
     free(descriptions);
     return result;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x20c8, %rsp           # imm = 0x20C8
movq %rsi, %r14
movq %rdi, %rbx
leaq 0x19b17(%rip), %rsi     # 0x2bbb9
callq 0x1af29
movl %eax, 0xb0(%rsp)
movq %rdx, 0xb8(%rsp)
cmpl $0x1, %eax
jne 0x1241b
leaq 0xb0(%rsp), %rsi
movq %rbx, %rdi
callq 0x1af8c
movq %rax, %rbx
leaq 0x19ae7(%rip), %rsi     # 0x2bbc0
movq %rax, %rdi
callq 0x1af29
movl %eax, 0xa0(%rsp)
movq %rdx, 0xa8(%rsp)
cmpl $0x2, %eax
jne 0x1241b
leaq 0xa0(%rsp), %rsi
movq %rbx, %rdi
callq 0x1afa7
testq %rax, %rax
je 0x1241b
movq %rax, %r13
movq %r14, 0x18(%rsp)
pushq $0x8
popq %rbp
leaq 0x19aa2(%rip), %r14     # 0x2bbc6
xorl %eax, %eax
xorl %r12d, %r12d
movq $0x0, (%rsp)
xorl %r15d, %r15d
movq %r13, 0x20(%rsp)
cmpq 0x8(%r13), %rax
jge 0x12432
movq (%r13), %rbx
cmpl $0x1, -0x8(%rbx,%rbp)
jne 0x1240f
movq %rax, 0x38(%rsp)
addq %rbp, %rbx
movq %rbx, %rdi
movq %r14, %rsi
callq 0x1af29
movl %eax, 0x90(%rsp)
movq %rdx, 0x98(%rsp)
cmpl $0x3, %eax
jne 0x1240a
movq %r12, 0x30(%rsp)
movq %rbx, %rdi
leaq 0x19a45(%rip), %rsi     # 0x2bbd1
callq 0x1af29
movl %eax, 0x8(%rsp)
movq %rdx, 0x10(%rsp)
movq %rbx, %rdi
leaq 0x90(%rsp), %rsi
callq 0x1afc2
movq %rax, %rdi
callq 0xd640
movq %rax, %r14
movq %rbx, %rdi
leaq 0x19a19(%rip), %rsi     # 0x2bbd8
callq 0x1af29
movl %eax, 0x80(%rsp)
movq %rdx, 0x88(%rsp)
cmpl $0x3, %eax
movq %r14, 0x28(%rsp)
jne 0x12256
movq %r14, %rdi
callq 0xd210
movq %rax, %r12
movq %rbx, %rdi
leaq 0x80(%rsp), %rsi
callq 0x1afc2
movq %rax, %rdi
movq %r14, %rsi
callq 0xd6f0
testq %rax, %rax
je 0x1224f
movq %rax, %r14
cmpb $0x0, (%rax,%r12)
je 0x1224f
addq %r12, %r14
cmpl $0x3, 0x8(%rsp)
jne 0x1226d
movq %rbx, %rdi
leaq 0x8(%rsp), %rsi
callq 0x1afc2
movl $0x2000, %esi           # imm = 0x2000
leaq 0xc0(%rsp), %r12
movq %r12, %rdi
leaq 0x1999e(%rip), %rdx     # 0x2bbde
movq %rax, %rcx
movq %r14, %r8
xorl %eax, %eax
callq 0xd260
jmp 0x1228e
cmpl $0x3, 0x8(%rsp)
jne 0x12268
movq %rbx, %rdi
leaq 0x8(%rsp), %rsi
callq 0x1afc2
movq %rax, %rdi
jmp 0x12291
xorl %r14d, %r14d
jmp 0x12299
movl $0x2000, %esi           # imm = 0x2000
leaq 0xc0(%rsp), %r12
movq %r12, %rdi
leaq 0x1b682(%rip), %rdx     # 0x2d906
movq %r14, %rcx
xorl %eax, %eax
callq 0xd260
movq %r12, %rdi
callq 0xd640
movq %rax, %r14
leaq 0x8(,%r15,8), %r12
movq (%rsp), %rdi
movq %r12, %rsi
callq 0xd520
movq %r15, %r13
movq %rax, %r15
movq 0x30(%rsp), %rdi
movq %r12, %rsi
callq 0xd520
movq %rax, %r12
movq %r15, (%rsp)
movq 0x28(%rsp), %rax
movq %rax, (%r15,%r13,8)
movq %r13, %r15
movq %r14, (%r12,%r13,8)
movq %rbx, %rdi
leaq 0x19902(%rip), %rsi     # 0x2bbe3
callq 0x1af29
movl %eax, 0xc0(%rsp)
movq %rdx, 0xc8(%rsp)
cmpl $0x1, %eax
movq 0x20(%rsp), %r13
leaq 0x198c2(%rip), %r14     # 0x2bbc6
jne 0x12407
movq %rbx, %rdi
leaq 0xc0(%rsp), %rsi
callq 0x1af8c
testq %rax, %rax
je 0x12407
movq %rax, %rbx
movq %rax, %rdi
leaq 0x198bc(%rip), %rsi     # 0x2bbec
callq 0x1af29
movl %eax, 0x70(%rsp)
movq %rdx, 0x78(%rsp)
cmpl $0x1, %eax
jne 0x12407
movq %rbx, %rdi
leaq 0x70(%rsp), %rsi
callq 0x1af8c
testq %rax, %rax
je 0x12407
movq %rax, %rbx
movq %rax, %rdi
leaq 0x1835f(%rip), %rsi     # 0x2a6c9
callq 0x1af29
movl %eax, 0x60(%rsp)
movq %rdx, 0x68(%rsp)
cmpl $0x1, %eax
jne 0x12407
movq %rbx, %rdi
leaq 0x60(%rsp), %rsi
callq 0x1af8c
testq %rax, %rax
je 0x12407
movq %rax, %rbx
movq %rax, %rdi
leaq 0x1891d(%rip), %rsi     # 0x2acbd
callq 0x1af29
movl %eax, 0x50(%rsp)
movq %rdx, 0x58(%rsp)
cmpl $0x4, %eax
jne 0x12407
movq %rbx, %rdi
leaq 0x19835(%rip), %rsi     # 0x2bbf2
callq 0x1af29
movl %eax, 0x40(%rsp)
movq %rdx, 0x48(%rsp)
cmpl $0x4, %eax
jne 0x12407
movq %rbx, %rdi
leaq 0x40(%rsp), %rsi
callq 0x1afdb
cvttsd2si (%rax), %rax
movq 0x18(%rsp), %r14
movq %rax, (%r14)
movq %rbx, %rdi
leaq 0x50(%rsp), %rsi
callq 0x1afdb
cvttsd2si (%rax), %rax
movq %rax, 0x8(%r14)
leaq 0x197bf(%rip), %r14     # 0x2bbc6
incq %r15
movq 0x38(%rsp), %rax
incq %rax
addq $0x18, %rbp
jmp 0x12139
xorl %ebx, %ebx
movq %rbx, %rax
addq $0x20c8, %rsp           # imm = 0x20C8
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
pushq $0x1
popq %rdi
pushq $0x20
popq %rsi
callq 0xd380
movq %rax, %rbx
movq %rax, %rdi
movq (%rsp), %r13
movq %r13, %rsi
movq %r12, %rdx
movq %r15, %rcx
callq 0x18d58
xorl %r14d, %r14d
testq %r15, %r15
cmovleq %r14, %r15
cmpq %r14, %r15
je 0x1247c
movq (%r13,%r14,8), %rdi
callq 0xd090
movq (%r12,%r14,8), %rdi
callq 0xd090
incq %r14
jmp 0x1245f
movq %r13, %rdi
callq 0xd090
movq %r12, %rdi
callq 0xd090
jmp 0x1241d