// File: /workspace/github_cpp_makefile_star2_O2/zeeev[P]DASVC/bamtools/src/utils/bamtools_fasta.cpp
// Function: BamTools::Fasta::FastaPrivate::GetSequence(int const&, int const&, int const&, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>&)
bool Fasta::FastaPrivate::GetSequence(const int& refId, const int& start, const int& stop, string& sequence) {
 
    // make sure FASTA file is open
    if ( !IsOpen ) {
        cerr << "FASTA error : file not open for reading" << endl;
        return false;
    }
  
    // use index if available
    if ( HasIndex && !Index.empty() ) {
      
        // validate reference id 
        if ( (refId < 0) || (refId >= (int)Index.size()) ) {
            cerr << "FASTA error: invalid refId specified: " << refId << endl;
            return false;
        }
        
        // retrieve reference index data
        const FastaIndexData& referenceData = Index.at(refId);
        
        // validate stop position 
        if ( (start < 0) || (start > stop) || (stop > referenceData.Length) ) {
            cerr << "FASTA error: invalid start/stop positions specified: " << start << ", " << stop << endl;
            return false;
        }
        
        // seek to beginning of sequence data
        if ( fseeko(Stream, referenceData.Offset, SEEK_SET) != 0 ) {
            cerr << "FASTA error : could not sek in file" << endl;
            return false;
        }
      
        // retrieve full sequence
        string fullSequence = "";
        if ( !GetNextSequence(fullSequence) ) {
            cerr << "FASTA error : could not retrieve sequence from FASTA file" << endl;
            return false;
        }
        
        // set sub-sequence & return success
        const int seqLength = (stop - start) + 1;
        sequence = fullSequence.substr(start, seqLength);
        return true;
    }
    
    // else plow through sequentially
    else {
      
        // rewind FASTA file
        if ( !Rewind() ) {
            cerr << "FASTA error : could not rewind FASTA file" << endl;
            return false;
        }
     
        // iterate through fasta entries
        int currentId = 0;
        string header = "";
        string fullSequence = "";
        
        // get first entry
        GetNextHeader(header);
        GetNextSequence(fullSequence);
        
        while ( currentId != refId ) {
            GetNextHeader(header);
            GetNextSequence(fullSequence);
            ++currentId;
        }
        
        // get desired substring from sequence
        // TODO: error reporting on invalid start/stop positions
        if ( currentId == refId && (fullSequence.length() >= (size_t)stop) ) {          
            const int seqLength = (stop - start) + 1;
            sequence = fullSequence.substr(start, seqLength);
            return true;
        }
      
        // could not get sequence
        return false;
    }
  
    // return success
    return true;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x78, %rsp
cmpb $0x0, 0x8(%rdi)
je 0x64a03
movq %rcx, %r14
movq %rsi, %r13
movq %rdi, %r12
movq %rdx, 0x8(%rsp)
cmpb $0x1, 0x18(%rdi)
jne 0x64a16
movq 0x20(%r12), %rcx
movq 0x28(%r12), %rax
cmpq %rax, %rcx
je 0x64a16
movslq (%r13), %rsi
testq %rsi, %rsi
js 0x64b24
subq %rcx, %rax
pushq $0x38
popq %rcx
cqto
idivq %rcx
cmpl %eax, %esi
jge 0x64b24
movq %r8, %rbx
leaq 0x20(%r12), %rdi
callq 0x65004
movq 0x8(%rsp), %rcx
movl (%rcx), %ecx
testl %ecx, %ecx
js 0x64b3d
movl (%r14), %edx
cmpl %edx, %ecx
jg 0x64b3d
cmpl 0x20(%rax), %edx
jg 0x64b3d
movq (%r12), %rdi
movq 0x28(%rax), %rsi
xorl %edx, %edx
callq 0x35a60
testl %eax, %eax
je 0x64b7e
movq 0x305e9(%rip), %rdi     # 0x94fe0
leaq 0x11384(%rip), %rsi     # 0x75d82
jmp 0x64aa9
movq 0x305d6(%rip), %rdi     # 0x94fe0
leaq 0x1129a(%rip), %rsi     # 0x75cab
jmp 0x64aa9
movq %r8, 0x50(%rsp)
movq %r12, %rdi
callq 0x641b2
testb %al, %al
je 0x64a9b
leaq 0x11dc9(%rip), %rsi     # 0x767f7
leaq 0x30(%rsp), %rdi
leaq 0x10(%rsp), %rdx
callq 0x35280
leaq 0x11db3(%rip), %rsi     # 0x767f7
leaq 0x10(%rsp), %rdi
leaq 0x58(%rsp), %rdx
callq 0x35280
leaq 0x30(%rsp), %rsi
movq %r12, %rdi
callq 0x641d2
leaq 0x10(%rsp), %rsi
movq %r12, %rdi
callq 0x64428
xorl %r15d, %r15d
leaq 0x30(%rsp), %rbp
leaq 0x10(%rsp), %rbx
cmpl (%r13), %r15d
je 0x64ac9
movq %r12, %rdi
movq %rbp, %rsi
callq 0x641d2
movq %r12, %rdi
movq %rbx, %rsi
callq 0x64428
incl %r15d
jmp 0x64a7a
movq 0x3053e(%rip), %rdi     # 0x94fe0
leaq 0x110e8(%rip), %rsi     # 0x75b91
callq 0x355b0
movq %rax, %rdi
callq 0x35300
xorl %ebp, %ebp
movl %ebp, %eax
addq $0x78, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
movslq (%r14), %rax
cmpq %rax, 0x18(%rsp)
setae %bpl
jb 0x64b0e
movq 0x8(%rsp), %rcx
movslq (%rcx), %rdx
subl %edx, %eax
incl %eax
movslq %eax, %rcx
leaq 0x58(%rsp), %rdi
leaq 0x10(%rsp), %rsi
callq 0x35600
leaq 0x58(%rsp), %rsi
movq 0x50(%rsp), %rdi
callq 0x35340
leaq 0x58(%rsp), %rdi
callq 0x35730
leaq 0x10(%rsp), %rdi
callq 0x35730
leaq 0x30(%rsp), %rdi
callq 0x35730
jmp 0x64ab8
movq 0x304b5(%rip), %rdi     # 0x94fe0
leaq 0x111a1(%rip), %rsi     # 0x75cd3
callq 0x355b0
movl (%r13), %esi
jmp 0x64b71
movq 0x3049c(%rip), %rdi     # 0x94fe0
leaq 0x111fe(%rip), %rsi     # 0x75d49
callq 0x355b0
movq 0x8(%rsp), %rcx
movl (%rcx), %esi
movq %rax, %rdi
callq 0x35b00
leaq 0x11219(%rip), %rsi     # 0x75d7f
movq %rax, %rdi
callq 0x355b0
movl (%r14), %esi
movq %rax, %rdi
callq 0x35b00
jmp 0x64aae
leaq 0x11c72(%rip), %rsi     # 0x767f7
leaq 0x30(%rsp), %rdi
leaq 0x10(%rsp), %rdx
callq 0x35280
leaq 0x30(%rsp), %rsi
movq %r12, %rdi
callq 0x64428
movl %eax, %ebp
testb %al, %al
je 0x64be4
movl (%r14), %eax
movq 0x8(%rsp), %rcx
movslq (%rcx), %rdx
subl %edx, %eax
incl %eax
movslq %eax, %rcx
leaq 0x10(%rsp), %rdi
leaq 0x30(%rsp), %rsi
callq 0x35600
leaq 0x10(%rsp), %rsi
movq %rbx, %rdi
callq 0x35340
leaq 0x10(%rsp), %rdi
callq 0x35730
jmp 0x64b18
movq 0x303f5(%rip), %rdi     # 0x94fe0
leaq 0x111b4(%rip), %rsi     # 0x75da6
callq 0x355b0
movq %rax, %rdi
callq 0x35300
jmp 0x64b18
movq %rax, %rbx
leaq 0x10(%rsp), %rdi
callq 0x35730
jmp 0x64c1a
jmp 0x64c17
jmp 0x64c3e
movq %rax, %rbx
leaq 0x30(%rsp), %rdi
callq 0x35730
jmp 0x64c5c
movq %rax, %rbx
leaq 0x58(%rsp), %rdi
callq 0x35730
jmp 0x64c48
jmp 0x64c39
jmp 0x64c45
movq %rax, %rbx
jmp 0x64c52
movq %rax, %rbx
jmp 0x64c5c
jmp 0x64c45
movq %rax, %rbx
leaq 0x10(%rsp), %rdi
callq 0x35730
leaq 0x30(%rsp), %rdi
callq 0x35730
movq %rbx, %rdi
callq 0x35b50
movq %rax, %rdi
callq 0x3a198