// File: npazosmendez[P]branchsearch/branchsearch.cpp
// Function: main
int main(int argc, char** argv){
    args_t args(argc, argv);

    if (args.fetch_before) system("git fetch");

    // variables
    char regex_value[MAX_BRANCH_NAME_LENGTH] = {0};
    int index = 0;
    int selected_branch = 0;
    vector<branch_t> all_branches = get_branches(args.locals_only);
    vector<branch_t*> filtered_branches;
    for (int i = 0; i < all_branches.size(); ++i){
        filtered_branches.push_back(&all_branches[i]);
    }

    if (args.fast_switch != NULL){
        branch_t target_branch;
        if (best_match(all_branches, args.fast_switch, target_branch)){
            switch_to_branch(target_branch, args.pull_after);
        } else {
            endwin();
            fprintf(stderr, "No branches matching '%s'\n", args.fast_switch);
            exit(1);
        }
    }

    // setup curses
    initscr();
    cbreak();
    noecho();
    nodelay(stdscr, TRUE);
    curs_set(0);
    scrollok(stdscr, TRUE);
    keypad(stdscr, TRUE);
    use_default_colors();
    start_color();

    int max_height, max_width;
    getmaxyx(stdscr, max_height, max_width);
    max_branch_shown = max_height - 5;

    print_window(regex_value, filtered_branches, selected_branch);

    // handle keyboard input and loop until a branch is selected
    while (1) {
        if (kbhit()) {
            int c = getch();
            if(c == KEY_BACKSPACE){
                if(index > 0){
                    index--;
                    regex_value[index] = 0;
                }
            }else if (c == NEW_LINE){
                if(filtered_branches.size()) switch_to_branch(*filtered_branches[selected_branch], args.pull_after);
            }else if (c == KEY_UP){
                if(selected_branch > 0) selected_branch--;
            }else if (c == KEY_DOWN){
                if(selected_branch < filtered_branches.size()-1 && selected_branch < max_branch_shown - 1) selected_branch++;
            }else if (c == KEY_DC){
                if(filtered_branches.size() and filtered_branches[selected_branch]->local){
                    delete_branch(filtered_branches, selected_branch);
                    all_branches = get_branches(args.locals_only);
                }
            }else{
                regex_value[index] = c;
                index++;
            }
            filter_branches(all_branches, regex_value, filtered_branches);
            print_window(regex_value, filtered_branches, selected_branch);
        }
    }
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x390, %rsp            # imm = 0x390
movl $0x0, -0x4(%rbp)
movl %edi, -0x8(%rbp)
movq %rsi, -0x10(%rbp)
movl -0x8(%rbp), %esi
movq -0x10(%rbp), %rdx
leaq -0x20(%rbp), %rdi
callq 0x7fb0
testb $0x1, -0x17(%rbp)
je 0x6cab
leaq 0x30588(%rip), %rdi     # 0x3722e
callq 0x53c0
leaq -0x220(%rbp), %rdi
xorl %esi, %esi
movl $0x1f4, %edx            # imm = 0x1F4
callq 0x5250
movl $0x0, -0x224(%rbp)
movl $0x0, -0x228(%rbp)
movb -0x16(%rbp), %al
leaq -0x240(%rbp), %rdi
andb $0x1, %al
movzbl %al, %esi
callq 0x5ca0
leaq -0x258(%rbp), %rdi
callq 0x8130
movl $0x0, -0x25c(%rbp)
movslq -0x25c(%rbp), %rax
movq %rax, -0x350(%rbp)
leaq -0x240(%rbp), %rdi
callq 0x7de0
movq %rax, %rcx
movq -0x350(%rbp), %rax
cmpq %rcx, %rax
jae 0x6d7e
movslq -0x25c(%rbp), %rsi
leaq -0x240(%rbp), %rdi
callq 0x7e60
movq %rax, -0x268(%rbp)
leaq -0x258(%rbp), %rdi
leaq -0x268(%rbp), %rsi
callq 0x7e80
jmp 0x6d54
jmp 0x6d56
movl -0x25c(%rbp), %eax
addl $0x1, %eax
movl %eax, -0x25c(%rbp)
jmp 0x6cfc
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x270(%rbp)
movl %eax, -0x274(%rbp)
jmp 0x72b9
cmpq $0x0, -0x20(%rbp)
je 0x6e7f
leaq -0x2a0(%rbp), %rdi
movq %rdi, -0x360(%rbp)
callq 0x7790
movq -0x360(%rbp), %rdx
movq -0x20(%rbp), %rsi
leaq -0x240(%rbp), %rdi
callq 0x6920
movb %al, -0x351(%rbp)
jmp 0x6dbb
movb -0x351(%rbp), %al
testb $0x1, %al
jne 0x6dc7
jmp 0x6e33
leaq -0x2c8(%rbp), %rdi
leaq -0x2a0(%rbp), %rsi
callq 0x8150
jmp 0x6ddc
movzbl -0x18(%rbp), %esi
andl $0x1, %esi
leaq -0x2c8(%rbp), %rdi
callq 0x6750
jmp 0x6df1
leaq -0x2c8(%rbp), %rdi
callq 0x7be0
jmp 0x6e60
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x270(%rbp)
movl %eax, -0x274(%rbp)
jmp 0x6e6e
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x270(%rbp)
movl %eax, -0x274(%rbp)
leaq -0x2c8(%rbp), %rdi
callq 0x7be0
jmp 0x6e6e
callq 0x5550
jmp 0x6e3a
movq 0x4b17f(%rip), %rax     # 0x51fc0
movq (%rax), %rdi
movq -0x20(%rbp), %rdx
leaq 0x303e9(%rip), %rsi     # 0x37238
movb $0x0, %al
callq 0x5660
movl $0x1, %edi
callq 0x5560
leaq -0x2a0(%rbp), %rdi
callq 0x7be0
jmp 0x6e7f
leaq -0x2a0(%rbp), %rdi
callq 0x7be0
jmp 0x72b9
callq 0x5680
jmp 0x6e86
callq 0x5120
jmp 0x6e8d
callq 0x5520
jmp 0x6e94
movq 0x4b10d(%rip), %rax     # 0x51fa8
movq (%rax), %rdi
movl $0x1, %esi
callq 0x52b0
jmp 0x6eaa
xorl %edi, %edi
callq 0x5390
jmp 0x6eb3
movq 0x4b0ee(%rip), %rax     # 0x51fa8
movq (%rax), %rdi
movl $0x1, %esi
callq 0x5530
jmp 0x6ec9
movq 0x4b0d8(%rip), %rax     # 0x51fa8
movq (%rax), %rdi
movl $0x1, %esi
callq 0x5190
jmp 0x6edf
callq 0x5310
jmp 0x6ee6
callq 0x50c0
jmp 0x6eed
xorl %eax, %eax
movq 0x4b0b2(%rip), %rcx     # 0x51fa8
cmpq (%rcx), %rax
je 0x6f14
movq 0x4b0a6(%rip), %rax     # 0x51fa8
movq (%rax), %rax
movswl 0x4(%rax), %eax
addl $0x1, %eax
movl %eax, -0x364(%rbp)
jmp 0x6f21
movl $0xffffffff, %eax       # imm = 0xFFFFFFFF
movl %eax, -0x364(%rbp)
jmp 0x6f21
movl -0x364(%rbp), %eax
movl %eax, -0x2cc(%rbp)
xorl %eax, %eax
movq 0x4b072(%rip), %rcx     # 0x51fa8
cmpq (%rcx), %rax
je 0x6f54
movq 0x4b066(%rip), %rax     # 0x51fa8
movq (%rax), %rax
movswl 0x6(%rax), %eax
addl $0x1, %eax
movl %eax, -0x368(%rbp)
jmp 0x6f61
movl $0xffffffff, %eax       # imm = 0xFFFFFFFF
movl %eax, -0x368(%rbp)
jmp 0x6f61
movl -0x368(%rbp), %eax
movl %eax, -0x2d0(%rbp)
movl -0x2cc(%rbp), %eax
addl $-0x5, %eax
movl %eax, 0x4b4c4(%rip)     # 0x52440
leaq -0x220(%rbp), %rax
movq %rax, -0x370(%rbp)
leaq -0x2e8(%rbp), %rdi
leaq -0x258(%rbp), %rsi
callq 0x8190
jmp 0x6f9f
movq -0x370(%rbp), %rdi
movl -0x228(%rbp), %edx
leaq -0x2e8(%rbp), %rsi
callq 0x63a0
jmp 0x6fba
leaq -0x2e8(%rbp), %rdi
callq 0x8280
jmp 0x6fc8
callq 0x5960
movl %eax, -0x374(%rbp)
jmp 0x6fd5
movl -0x374(%rbp), %eax
cmpl $0x0, %eax
je 0x72b4
movq 0x4afbd(%rip), %rax     # 0x51fa8
movq (%rax), %rdi
callq 0x5180
movl %eax, -0x378(%rbp)
jmp 0x6ffb
movl -0x378(%rbp), %eax
movl %eax, -0x2ec(%rbp)
cmpl $0x107, -0x2ec(%rbp)    # imm = 0x107
jne 0x7064
cmpl $0x0, -0x224(%rbp)
jle 0x705f
movl -0x224(%rbp), %eax
addl $-0x1, %eax
movl %eax, -0x224(%rbp)
movslq -0x224(%rbp), %rax
movb $0x0, -0x220(%rbp,%rax)
jmp 0x705f
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x270(%rbp)
movl %eax, -0x274(%rbp)
leaq -0x2e8(%rbp), %rdi
callq 0x8280
jmp 0x72b9
jmp 0x722c
cmpl $0xa, -0x2ec(%rbp)
jne 0x70f2
leaq -0x258(%rbp), %rdi
callq 0x7c20
cmpq $0x0, %rax
je 0x70ed
movslq -0x228(%rbp), %rsi
leaq -0x258(%rbp), %rdi
callq 0x7c40
movq (%rax), %rsi
leaq -0x318(%rbp), %rdi
callq 0x8150
jmp 0x70a7
movzbl -0x18(%rbp), %esi
andl $0x1, %esi
leaq -0x318(%rbp), %rdi
callq 0x6750
jmp 0x70bc
leaq -0x318(%rbp), %rdi
callq 0x7be0
jmp 0x70ed
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x270(%rbp)
movl %eax, -0x274(%rbp)
leaq -0x318(%rbp), %rdi
callq 0x7be0
jmp 0x72b9
jmp 0x722a
cmpl $0x103, -0x2ec(%rbp)    # imm = 0x103
jne 0x711b
cmpl $0x0, -0x228(%rbp)
jle 0x7116
movl -0x228(%rbp), %eax
addl $-0x1, %eax
movl %eax, -0x228(%rbp)
jmp 0x7228
cmpl $0x102, -0x2ec(%rbp)    # imm = 0x102
jne 0x717b
movslq -0x228(%rbp), %rax
movq %rax, -0x380(%rbp)
leaq -0x258(%rbp), %rdi
callq 0x7c20
movq %rax, %rcx
movq -0x380(%rbp), %rax
subq $0x1, %rcx
cmpq %rcx, %rax
jae 0x7176
movl -0x228(%rbp), %eax
movl 0x4b2e0(%rip), %ecx     # 0x52440
subl $0x1, %ecx
cmpl %ecx, %eax
jge 0x7176
movl -0x228(%rbp), %eax
addl $0x1, %eax
movl %eax, -0x228(%rbp)
jmp 0x7226
cmpl $0x14a, -0x2ec(%rbp)    # imm = 0x14A
jne 0x71ff
leaq -0x258(%rbp), %rdi
callq 0x7c20
cmpq $0x0, %rax
je 0x71fd
movslq -0x228(%rbp), %rsi
leaq -0x258(%rbp), %rdi
callq 0x7c40
movq (%rax), %rax
testb $0x1, 0x20(%rax)
je 0x71fd
movl -0x228(%rbp), %esi
leaq -0x258(%rbp), %rdi
callq 0x65e0
jmp 0x71c9
movzbl -0x16(%rbp), %esi
andl $0x1, %esi
leaq -0x330(%rbp), %rdi
callq 0x5ca0
jmp 0x71de
leaq -0x240(%rbp), %rdi
leaq -0x330(%rbp), %rsi
callq 0x82e0
leaq -0x330(%rbp), %rdi
callq 0x7b80
jmp 0x7224
movl -0x2ec(%rbp), %eax
movb %al, %cl
movslq -0x224(%rbp), %rax
movb %cl, -0x220(%rbp,%rax)
movl -0x224(%rbp), %eax
addl $0x1, %eax
movl %eax, -0x224(%rbp)
jmp 0x7226
jmp 0x7228
jmp 0x722a
jmp 0x722c
leaq -0x240(%rbp), %rdi
leaq -0x220(%rbp), %rsi
leaq -0x258(%rbp), %rdx
callq 0x67e0
jmp 0x7248
leaq -0x220(%rbp), %rax
movq %rax, -0x388(%rbp)
leaq -0x348(%rbp), %rdi
leaq -0x258(%rbp), %rsi
callq 0x8190
jmp 0x726b
movq -0x388(%rbp), %rdi
movl -0x228(%rbp), %edx
leaq -0x348(%rbp), %rsi
callq 0x63a0
jmp 0x7286
leaq -0x348(%rbp), %rdi
callq 0x8280
jmp 0x72b4
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x270(%rbp)
movl %eax, -0x274(%rbp)
leaq -0x348(%rbp), %rdi
callq 0x8280
jmp 0x72b9
jmp 0x6fc6
leaq -0x258(%rbp), %rdi
callq 0x8280
leaq -0x240(%rbp), %rdi
callq 0x7b80
movq -0x270(%rbp), %rdi
callq 0x5780
nopl (%rax)