// File: chhylp123[P]hifiasm/gfa_ut.cpp
// Function: integer_g_chain(poa_g_t*, ma_ug_t*, integer_aln_t*, long, integer_t*, ul_chain_t*)
int64_t integer_g_chain(poa_g_t *g, ma_ug_t *ug, integer_aln_t *a, int64_t a_n, integer_t *buf, ul_chain_t *res)
{
    res->v = res->s = res->e = (uint32_t)-1; res->sc = (uint64_t)-1; 
    res->q_sidx = res->q_eidx = res->t_sidx = res->t_eidx = (uint32_t)-1;
    if(a_n <= 0) return 0;
    int64_t i, k, *p, *f, tf, ti, csc, sc, max_f, max_k, vis_i, pas; integer_aln_t *li, *lk; 
    buf->vis.n = 0; vis_i = -1;
    for (i = 1; i < a_n; ++i) {//already sorted by qk
        if(((uint32_t)a[i].tn_rev_qk) <= ((uint32_t)a[i-1].tn_rev_qk)) break; ///== means there is a circle
        if(a[i].tk == a[i-1].tk) break;
        if(a[i].tk < a[i-1].tk) {
            pas = suffix_gorder_check(g, buf, a[i].tk, a[i-1].tk, vis_i==i?0:1, i); vis_i = i;
            if(pas) break;
        }
    }
    // fprintf(stderr, "[M::%s::] i::%ld, a_n::%ld\n", __func__, i, a_n);
    
    if(i >= a_n) {
        res->s = 0; res->e = a_n;
        return 1;
    }

    buf->p.n = buf->f.n = 0; 
    kv_resize(int64_t, buf->p, (uint64_t)a_n); p = buf->p.a;
    kv_resize(int64_t, buf->f, (uint64_t)a_n); f = buf->f.a;
    
    tf = ti = -1; buf->vis.n = 0; vis_i = -1;
    for (i = 0; i < a_n; ++i) {
        li = &(a[i]); csc = li->sc;
        max_f = csc; max_k = -1;
        
        for (k = i-1; k >= 0; --k) {
            lk = &(a[k]);
            ///qk of lk and li might be equal
            if(((uint32_t)lk->tn_rev_qk) >= ((uint32_t)li->tn_rev_qk)) continue;
            if(lk->tk == li->tk) continue;
            if(lk->tk > li->tk) {
                pas = suffix_gorder_check(g, buf, a[i].tk, a[k].tk, vis_i==i?0:1, i);
                // if(i == 17 && a[i].tk == 6 && k == 16 && a[k].tk == 60) {
                //     fprintf(stderr, "******i::%ld, a[i].tk::%u, k::%ld, a[k].tk::%u, vis_i::%ld, pas::%ld\n", 
                //         i, a[i].tk, k, a[k].tk, vis_i, pas);
                // }
                vis_i = i; if(pas) continue;
            }
            sc = csc + f[k];
            if(sc > max_f) {
                max_f = sc; max_k = k;
            }
        }
        f[i] = max_f; p[i] = max_k;
        if(tf < max_f) {
            tf = max_f; ti = i;
        }
        // fprintf(stderr, "[M::%s::i->%ld] qk::%u, tk::%u, max_k::%ld, max_f::%ld, ti::%ld\n", 
        // __func__, i, (uint32_t)li->tn_rev_qk, li->tk, max_k, max_f, ti);
    }

    if(ti < 0) return 0;
    for (i = ti, k = 0; i >= 0; i = p[i]) f[k++] = i;
    assert(k > 0);
    for (i = 0, k--; k >= 0; k--) {
        a[i] = a[f[k]]; i++;
    }
    res->s = 0; res->e = i;
    return 1;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0xb0, %rsp
movq %rdi, -0x10(%rbp)
movq %rsi, -0x18(%rbp)
movq %rdx, -0x20(%rbp)
movq %rcx, -0x28(%rbp)
movq %r8, -0x30(%rbp)
movq %r9, -0x38(%rbp)
movq -0x38(%rbp), %rax
movl $0xffffffff, 0x4(%rax)  # imm = 0xFFFFFFFF
movq -0x38(%rbp), %rax
movl $0xffffffff, (%rax)     # imm = 0xFFFFFFFF
movq -0x38(%rbp), %rax
movl $0xffffffff, 0x8(%rax)  # imm = 0xFFFFFFFF
movq -0x38(%rbp), %rax
movq $-0x1, 0x10(%rax)
movq -0x38(%rbp), %rax
movl $0xffffffff, 0x24(%rax) # imm = 0xFFFFFFFF
movq -0x38(%rbp), %rax
movl $0xffffffff, 0x20(%rax) # imm = 0xFFFFFFFF
movq -0x38(%rbp), %rax
movl $0xffffffff, 0x1c(%rax) # imm = 0xFFFFFFFF
movq -0x38(%rbp), %rax
movl $0xffffffff, 0x18(%rax) # imm = 0xFFFFFFFF
cmpq $0x0, -0x28(%rbp)
jg 0x332a0f
movq $0x0, -0x8(%rbp)
jmp 0x333050
movq -0x30(%rbp), %rax
movq $0x0, 0xa8(%rax)
movq $-0x1, -0x90(%rbp)
movq $0x1, -0x40(%rbp)
movq -0x40(%rbp), %rax
cmpq -0x28(%rbp), %rax
jge 0x332b46
movq -0x20(%rbp), %rax
imulq $0x18, -0x40(%rbp), %rcx
addq %rcx, %rax
movq 0x10(%rax), %rax
movq -0x20(%rbp), %rcx
movq -0x40(%rbp), %rdx
subq $0x1, %rdx
imulq $0x18, %rdx, %rdx
addq %rdx, %rcx
movq 0x10(%rcx), %rcx
cmpl %ecx, %eax
ja 0x332a6f
jmp 0x332b46
movq -0x20(%rbp), %rax
imulq $0x18, -0x40(%rbp), %rcx
addq %rcx, %rax
movl (%rax), %eax
movq -0x20(%rbp), %rcx
movq -0x40(%rbp), %rdx
subq $0x1, %rdx
imulq $0x18, %rdx, %rdx
addq %rdx, %rcx
cmpl (%rcx), %eax
jne 0x332a99
jmp 0x332b46
movq -0x20(%rbp), %rax
imulq $0x18, -0x40(%rbp), %rcx
addq %rcx, %rax
movl (%rax), %eax
movq -0x20(%rbp), %rcx
movq -0x40(%rbp), %rdx
subq $0x1, %rdx
imulq $0x18, %rdx, %rdx
addq %rdx, %rcx
cmpl (%rcx), %eax
jae 0x332b33
movq -0x10(%rbp), %rdi
movq -0x30(%rbp), %rsi
movq -0x20(%rbp), %rax
imulq $0x18, -0x40(%rbp), %rcx
addq %rcx, %rax
movl (%rax), %eax
movl %eax, %edx
movq -0x20(%rbp), %rax
movq -0x40(%rbp), %rcx
subq $0x1, %rcx
imulq $0x18, %rcx, %rcx
addq %rcx, %rax
movl (%rax), %eax
movl %eax, %ecx
movq -0x90(%rbp), %r9
movq -0x40(%rbp), %r10
movl $0x1, %eax
xorl %r8d, %r8d
cmpq %r10, %r9
cmovel %r8d, %eax
movslq %eax, %r8
movq -0x40(%rbp), %r9
callq 0x3324d0
movq %rax, -0x98(%rbp)
movq -0x40(%rbp), %rax
movq %rax, -0x90(%rbp)
cmpq $0x0, -0x98(%rbp)
je 0x332b31
jmp 0x332b46
jmp 0x332b33
jmp 0x332b35
movq -0x40(%rbp), %rax
addq $0x1, %rax
movq %rax, -0x40(%rbp)
jmp 0x332a31
movq -0x40(%rbp), %rax
cmpq -0x28(%rbp), %rax
jl 0x332b74
movq -0x38(%rbp), %rax
movl $0x0, (%rax)
movq -0x28(%rbp), %rax
movl %eax, %ecx
movq -0x38(%rbp), %rax
movl %ecx, 0x4(%rax)
movq $0x1, -0x8(%rbp)
jmp 0x333050
movq -0x30(%rbp), %rax
movq $0x0, 0x48(%rax)
movq -0x30(%rbp), %rax
movq $0x0, 0x60(%rax)
movq -0x30(%rbp), %rax
movq 0x68(%rax), %rax
cmpq -0x28(%rbp), %rax
jae 0x332c65
movq -0x28(%rbp), %rcx
movq -0x30(%rbp), %rax
movq %rcx, 0x68(%rax)
movq -0x30(%rbp), %rax
movq 0x68(%rax), %rcx
addq $-0x1, %rcx
movq %rcx, 0x68(%rax)
movq -0x30(%rbp), %rax
movq 0x68(%rax), %rcx
shrq %rcx
movq -0x30(%rbp), %rax
orq 0x68(%rax), %rcx
movq %rcx, 0x68(%rax)
movq -0x30(%rbp), %rax
movq 0x68(%rax), %rcx
shrq $0x2, %rcx
movq -0x30(%rbp), %rax
orq 0x68(%rax), %rcx
movq %rcx, 0x68(%rax)
movq -0x30(%rbp), %rax
movq 0x68(%rax), %rcx
shrq $0x4, %rcx
movq -0x30(%rbp), %rax
orq 0x68(%rax), %rcx
movq %rcx, 0x68(%rax)
movq -0x30(%rbp), %rax
movq 0x68(%rax), %rcx
shrq $0x8, %rcx
movq -0x30(%rbp), %rax
orq 0x68(%rax), %rcx
movq %rcx, 0x68(%rax)
movq -0x30(%rbp), %rax
movq 0x68(%rax), %rcx
shrq $0x10, %rcx
movq -0x30(%rbp), %rax
orq 0x68(%rax), %rcx
movq %rcx, 0x68(%rax)
movq -0x30(%rbp), %rax
movq 0x68(%rax), %rcx
addq $0x1, %rcx
movq %rcx, 0x68(%rax)
movq -0x30(%rbp), %rax
movq 0x70(%rax), %rdi
movq -0x30(%rbp), %rax
movq 0x68(%rax), %rsi
shlq $0x3, %rsi
callq 0x2360
movq %rax, %rcx
movq -0x30(%rbp), %rax
movq %rcx, 0x70(%rax)
jmp 0x332c67
movq -0x30(%rbp), %rax
movq 0x70(%rax), %rax
movq %rax, -0x50(%rbp)
movq -0x30(%rbp), %rax
movq 0x50(%rax), %rax
cmpq -0x28(%rbp), %rax
jae 0x332d4c
movq -0x28(%rbp), %rcx
movq -0x30(%rbp), %rax
movq %rcx, 0x50(%rax)
movq -0x30(%rbp), %rax
movq 0x50(%rax), %rcx
addq $-0x1, %rcx
movq %rcx, 0x50(%rax)
movq -0x30(%rbp), %rax
movq 0x50(%rax), %rcx
shrq %rcx
movq -0x30(%rbp), %rax
orq 0x50(%rax), %rcx
movq %rcx, 0x50(%rax)
movq -0x30(%rbp), %rax
movq 0x50(%rax), %rcx
shrq $0x2, %rcx
movq -0x30(%rbp), %rax
orq 0x50(%rax), %rcx
movq %rcx, 0x50(%rax)
movq -0x30(%rbp), %rax
movq 0x50(%rax), %rcx
shrq $0x4, %rcx
movq -0x30(%rbp), %rax
orq 0x50(%rax), %rcx
movq %rcx, 0x50(%rax)
movq -0x30(%rbp), %rax
movq 0x50(%rax), %rcx
shrq $0x8, %rcx
movq -0x30(%rbp), %rax
orq 0x50(%rax), %rcx
movq %rcx, 0x50(%rax)
movq -0x30(%rbp), %rax
movq 0x50(%rax), %rcx
shrq $0x10, %rcx
movq -0x30(%rbp), %rax
orq 0x50(%rax), %rcx
movq %rcx, 0x50(%rax)
movq -0x30(%rbp), %rax
movq 0x50(%rax), %rcx
addq $0x1, %rcx
movq %rcx, 0x50(%rax)
movq -0x30(%rbp), %rax
movq 0x58(%rax), %rdi
movq -0x30(%rbp), %rax
movq 0x50(%rax), %rsi
shlq $0x3, %rsi
callq 0x2360
movq %rax, %rcx
movq -0x30(%rbp), %rax
movq %rcx, 0x58(%rax)
jmp 0x332d4e
movq -0x30(%rbp), %rax
movq 0x58(%rax), %rax
movq %rax, -0x58(%rbp)
movq $-0x1, -0x68(%rbp)
movq $-0x1, -0x60(%rbp)
movq -0x30(%rbp), %rax
movq $0x0, 0xa8(%rax)
movq $-0x1, -0x90(%rbp)
movq $0x0, -0x40(%rbp)
movq -0x40(%rbp), %rax
cmpq -0x28(%rbp), %rax
jge 0x332f46
movq -0x20(%rbp), %rax
imulq $0x18, -0x40(%rbp), %rcx
addq %rcx, %rax
movq %rax, -0xa0(%rbp)
movq -0xa0(%rbp), %rax
movl 0x8(%rax), %eax
movq %rax, -0x70(%rbp)
movq -0x70(%rbp), %rax
movq %rax, -0x80(%rbp)
movq $-0x1, -0x88(%rbp)
movq -0x40(%rbp), %rax
subq $0x1, %rax
movq %rax, -0x48(%rbp)
cmpq $0x0, -0x48(%rbp)
jl 0x332ef6
movq -0x20(%rbp), %rax
imulq $0x18, -0x48(%rbp), %rcx
addq %rcx, %rax
movq %rax, -0xa8(%rbp)
movq -0xa8(%rbp), %rax
movq 0x10(%rax), %rax
movq -0xa0(%rbp), %rcx
movq 0x10(%rcx), %rcx
cmpl %ecx, %eax
jb 0x332e17
jmp 0x332ee5
movq -0xa8(%rbp), %rax
movl (%rax), %eax
movq -0xa0(%rbp), %rcx
cmpl (%rcx), %eax
jne 0x332e30
jmp 0x332ee5
movq -0xa8(%rbp), %rax
movl (%rax), %eax
movq -0xa0(%rbp), %rcx
cmpl (%rcx), %eax
jbe 0x332eb2
movq -0x10(%rbp), %rdi
movq -0x30(%rbp), %rsi
movq -0x20(%rbp), %rax
imulq $0x18, -0x40(%rbp), %rcx
addq %rcx, %rax
movl (%rax), %eax
movl %eax, %edx
movq -0x20(%rbp), %rax
imulq $0x18, -0x48(%rbp), %rcx
addq %rcx, %rax
movl (%rax), %eax
movl %eax, %ecx
movq -0x90(%rbp), %r9
movq -0x40(%rbp), %r10
movl $0x1, %eax
xorl %r8d, %r8d
cmpq %r10, %r9
cmovel %r8d, %eax
movslq %eax, %r8
movq -0x40(%rbp), %r9
callq 0x3324d0
movq %rax, -0x98(%rbp)
movq -0x40(%rbp), %rax
movq %rax, -0x90(%rbp)
cmpq $0x0, -0x98(%rbp)
je 0x332eb0
jmp 0x332ee5
jmp 0x332eb2
movq -0x70(%rbp), %rax
movq -0x58(%rbp), %rcx
movq -0x48(%rbp), %rdx
addq (%rcx,%rdx,8), %rax
movq %rax, -0x78(%rbp)
movq -0x78(%rbp), %rax
cmpq -0x80(%rbp), %rax
jle 0x332ee3
movq -0x78(%rbp), %rax
movq %rax, -0x80(%rbp)
movq -0x48(%rbp), %rax
movq %rax, -0x88(%rbp)
jmp 0x332ee5
movq -0x48(%rbp), %rax
addq $-0x1, %rax
movq %rax, -0x48(%rbp)
jmp 0x332dda
movq -0x80(%rbp), %rdx
movq -0x58(%rbp), %rax
movq -0x40(%rbp), %rcx
movq %rdx, (%rax,%rcx,8)
movq -0x88(%rbp), %rdx
movq -0x50(%rbp), %rax
movq -0x40(%rbp), %rcx
movq %rdx, (%rax,%rcx,8)
movq -0x60(%rbp), %rax
cmpq -0x80(%rbp), %rax
jge 0x332f33
movq -0x80(%rbp), %rax
movq %rax, -0x60(%rbp)
movq -0x40(%rbp), %rax
movq %rax, -0x68(%rbp)
jmp 0x332f35
movq -0x40(%rbp), %rax
addq $0x1, %rax
movq %rax, -0x40(%rbp)
jmp 0x332d8c
cmpq $0x0, -0x68(%rbp)
jge 0x332f5a
movq $0x0, -0x8(%rbp)
jmp 0x333050
movq -0x68(%rbp), %rax
movq %rax, -0x40(%rbp)
movq $0x0, -0x48(%rbp)
cmpq $0x0, -0x40(%rbp)
jl 0x332f9e
movq -0x40(%rbp), %rdx
movq -0x58(%rbp), %rax
movq -0x48(%rbp), %rcx
movq %rcx, %rsi
addq $0x1, %rsi
movq %rsi, -0x48(%rbp)
movq %rdx, (%rax,%rcx,8)
movq -0x50(%rbp), %rax
movq -0x40(%rbp), %rcx
movq (%rax,%rcx,8), %rax
movq %rax, -0x40(%rbp)
jmp 0x332f6a
cmpq $0x0, -0x48(%rbp)
jle 0x332fa7
jmp 0x332fc6
leaq 0x63fb2(%rip), %rdi     # 0x396f60
leaq 0x63204(%rip), %rsi     # 0x3961b9
movl $0x177d, %edx           # imm = 0x177D
leaq 0x64d2f(%rip), %rcx     # 0x397cf0
callq 0x2130
movq $0x0, -0x40(%rbp)
movq -0x48(%rbp), %rax
addq $-0x1, %rax
movq %rax, -0x48(%rbp)
cmpq $0x0, -0x48(%rbp)
jl 0x333031
movq -0x20(%rbp), %rcx
movq -0x58(%rbp), %rax
movq -0x48(%rbp), %rdx
imulq $0x18, (%rax,%rdx,8), %rax
addq %rax, %rcx
movq -0x20(%rbp), %rax
imulq $0x18, -0x40(%rbp), %rdx
addq %rdx, %rax
movq (%rcx), %rdx
movq %rdx, (%rax)
movq 0x8(%rcx), %rdx
movq %rdx, 0x8(%rax)
movq 0x10(%rcx), %rcx
movq %rcx, 0x10(%rax)
movq -0x40(%rbp), %rax
addq $0x1, %rax
movq %rax, -0x40(%rbp)
movq -0x48(%rbp), %rax
addq $-0x1, %rax
movq %rax, -0x48(%rbp)
jmp 0x332fda
movq -0x38(%rbp), %rax
movl $0x0, (%rax)
movq -0x40(%rbp), %rax
movl %eax, %ecx
movq -0x38(%rbp), %rax
movl %ecx, 0x4(%rax)
movq $0x1, -0x8(%rbp)
movq -0x8(%rbp), %rax
addq $0xb0, %rsp
popq %rbp
retq
nopl (%rax)