// File: /workspace/github_cpp_makefile_star2_O3/gersteinlab[P]MUSIC/src/ms_genome_sequence_tools.cpp
// Function: batch_extract_region_sequences(char*, std::vector<t_annot_region*, std::allocator<t_annot_region*>>*)
void batch_extract_region_sequences(char* chr_data_dir, vector<t_annot_region*>* regions)
{
	//vector<t_annot_region*>* regions = load_BED(regions_bed_fp);

	vector<char*>* chr_ids = get_chr_ids(regions);

	for(int i_chr = 0; i_chr < (int)chr_ids->size(); i_chr++)
	{
		vector<t_annot_region*>* cur_chr_regions = get_regions_per_chromosome(regions, chr_ids->at(i_chr));

		fprintf(stderr, "Extracting sequences in %s\n", chr_ids->at(i_chr));

		// Sort the regions.
		sort(cur_chr_regions->begin(), cur_chr_regions->end(), sort_regions);

		char chr_seq_fp[1000];
		sprintf(chr_seq_fp, "%s/%s.bin", chr_data_dir, chr_ids->at(i_chr));
		if(check_file(chr_seq_fp))
		{
			FILE* f_chr = open_f(chr_seq_fp, "rb");

			// Go over all the regions.
			for(int i_reg = 0; i_reg < (int)cur_chr_regions->size(); i_reg++)
			{
				fprintf(stderr, "%d (%ld)             \r", i_reg, cur_chr_regions->size());

				int l_reg = cur_chr_regions->at(i_reg)->end - cur_chr_regions->at(i_reg)->start + 1;
				int f_start = cur_chr_regions->at(i_reg)->start - 1 + sizeof(int);
				int f_end = f_start + l_reg - 1;

				int length = f_end - f_start + 1;

				char* seq_buffer = new char[length + 2];
				memset(seq_buffer, 0, sizeof(char) * (length + 1));

				// Read the data.
				fseek(f_chr, f_start, SEEK_SET);

				// Fill the buffer.
				fread(seq_buffer, length, 1, f_chr);

				// If the requested strand is on negative strand, do reverse complementing.
				if(cur_chr_regions->at(i_reg)->strand == '-')
				{
					// Replace the sequence buffer with its reverse complement.
					char* reverse_complement_seq = get_reverse_complement(seq_buffer, 0, t_string::string_length(seq_buffer) - 1);
					delete [] seq_buffer;
					seq_buffer = reverse_complement_seq;
				}

				//fprintf(stderr, "%s\t%d\t%d\t.\t.\t%c\t%s\n", cur_chr_regions->at(i_reg)->chrom, 
				//	cur_chr_regions->at(i_reg)->start, cur_chr_regions->at(i_reg)->end, 
				//	cur_chr_regions->at(i_reg)->strand, seq_buffer);
			
				// Save the sequence to data entry of region.
				cur_chr_regions->at(i_reg)->data = (void*)seq_buffer;
			} // i_reg.

			fprintf(stderr, "\n");

			fclose(f_chr);
		}
		else
		{
			fprintf(stderr, "Could not find %s\n", chr_seq_fp);
			for(int i_reg = 0; i_reg < (int)cur_chr_regions->size(); i_reg++)
			{
				cur_chr_regions->at(i_reg)->data = NULL;
			} // i_reg loop.
		}
	} // i_chr loop.
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x428, %rsp            # imm = 0x428
movq %rsi, %r13
movq %rdi, 0x18(%rsp)
movq %rsi, %rdi
callq 0x171f7
movq %rax, %r15
movq (%rax), %rax
movq 0x8(%r15), %rdx
subq %rax, %rdx
sarq $0x3, %rdx
testl %edx, %edx
jle 0x22a56
movq 0x1687c(%rip), %rbx     # 0x38fe0
xorl %r12d, %r12d
movq %r15, 0x10(%rsp)
cmpq %r12, %rdx
jbe 0x22a68
movq (%rax,%r12,8), %rsi
movq %r13, %rdi
callq 0x19bcb
movq %rax, %rbp
movq (%r15), %rax
movq 0x8(%r15), %rdx
subq %rax, %rdx
sarq $0x3, %rdx
cmpq %r12, %rdx
jbe 0x22a68
movq (%rbx), %rdi
movq %r12, 0x28(%rsp)
movq (%rax,%r12,8), %rdx
leaq 0xbb54(%rip), %rsi      # 0x2e302
xorl %eax, %eax
callq 0x2250
movq (%rbp), %r14
movq %rbp, 0x20(%rsp)
movq 0x8(%rbp), %r15
cmpq %r15, %r14
je 0x22976
movq %r15, %rbx
subq %r14, %rbx
movq %rbx, %rax
sarq $0x3, %rax
bsrq %rax, %rdx
xorl $0x3f, %edx
addl %edx, %edx
xorq $0x7e, %rdx
movq %r14, %rdi
movq %r15, %rsi
leaq -0xb8ee(%rip), %rcx     # 0x16f04
callq 0x1c455
leaq 0x8(%r14), %rax
cmpq $0x81, %rbx
movq %r15, (%rsp)
jl 0x228f8
movq %r13, 0x8(%rsp)
movl $0x8, %r15d
movq %rax, 0x30(%rsp)
movq %rax, %rbx
movq %r14, %r12
leaq (%r14,%r15), %r13
movq (%r14,%r15), %rdi
movq (%r14), %rsi
callq 0x16f04
movq (%r14,%r15), %rbp
testb %al, %al
movq %r13, 0x38(%rsp)
je 0x22854
movq 0x30(%rsp), %rdi
movq %r14, %rsi
movq %r15, %rdx
callq 0x22b0
movq %r14, %r13
jmp 0x22885
movq (%r12), %rsi
movq %rbp, %rdi
callq 0x16f04
testb %al, %al
je 0x22885
movq %rbx, %rcx
leaq -0x8(%rcx), %r13
movq -0x10(%rcx), %rsi
movq -0x8(%rcx), %rax
movq %rax, (%rcx)
movq %rbp, %rdi
callq 0x16f04
movq %r13, %rcx
testb %al, %al
jne 0x22867
movq %rbp, (%r13)
addq $0x8, %r15
addq $0x8, %rbx
cmpq $0x80, %r15
movq 0x38(%rsp), %r12
jne 0x22822
subq $-0x80, %r14
cmpq (%rsp), %r14
movq 0x8(%rsp), %r13
je 0x22976
movq -0x8(%r14), %rsi
movq (%r14), %rbx
movq %rbx, %rdi
callq 0x16f04
movq %r14, %r15
testb %al, %al
je 0x228e9
movq %r14, %rcx
leaq -0x8(%rcx), %r15
movq -0x10(%rcx), %rsi
movq -0x8(%rcx), %rax
movq %rax, (%rcx)
movq %rbx, %rdi
callq 0x16f04
movq %r15, %rcx
testb %al, %al
jne 0x228cb
movq %rbx, (%r15)
addq $0x8, %r14
cmpq (%rsp), %r14
jne 0x228b2
jmp 0x22976
cmpq %r15, %rax
je 0x22976
movq %r14, %rbp
movq %rbp, %r15
movq %rax, %rbp
movq (%rax), %rdi
movq (%r14), %rsi
callq 0x16f04
movq (%rbp), %rbx
testb %al, %al
je 0x22936
movq %rbp, %rdx
subq %r14, %rdx
subq %rdx, %r15
addq $0x10, %r15
movq %r15, %rdi
movq %r14, %rsi
callq 0x22b0
movq %r14, %r15
jmp 0x22969
movq (%r15), %rsi
movq %rbx, %rdi
callq 0x16f04
movq %rbp, %r15
testb %al, %al
je 0x22969
movq %rbp, %rcx
leaq -0x8(%rcx), %r15
movq -0x10(%rcx), %rsi
movq -0x8(%rcx), %rax
movq %rax, (%rcx)
movq %rbx, %rdi
callq 0x16f04
movq %r15, %rcx
testb %al, %al
jne 0x2294b
movq %rbx, (%r15)
leaq 0x8(%rbp), %rax
cmpq (%rsp), %rax
jne 0x22900
movq 0x10(%rsp), %r15
movq (%r15), %rax
movq 0x8(%r15), %rdx
subq %rax, %rdx
sarq $0x3, %rdx
movq 0x28(%rsp), %r12
cmpq %r12, %rdx
jbe 0x22a68
movq 0x20(%rsp), %rbp
movq %rbp, %rbx
addq $0x8, %rbx
movq (%rax,%r12,8), %rcx
leaq 0x40(%rsp), %r14
movq %r14, %rdi
leaq 0x85dd(%rip), %rsi      # 0x2af93
movq 0x18(%rsp), %rdx
xorl %eax, %eax
callq 0x2080
movq %r14, %rdi
callq 0x25d35
movq %r14, %rdi
testb %al, %al
je 0x22a32
leaq 0xb558(%rip), %rsi      # 0x2df30
callq 0x25d5a
movq %rax, %r14
movq 0x8(%rbp), %rdi
subq (%rbp), %rdi
sarq $0x3, %rdi
testl %edi, %edi
jg 0x22a46
movq 0x165e9(%rip), %rbx     # 0x38fe0
movq (%rbx), %rsi
movl $0xa, %edi
callq 0x2210
movq %r14, %rdi
callq 0x2170
incq %r12
movq (%r15), %rax
movq 0x8(%r15), %rcx
subq %rax, %rcx
movq %rcx, %rdx
sarq $0x3, %rdx
shrq $0x3, %rcx
movslq %ecx, %rcx
cmpq %rcx, %r12
jl 0x2276c
jmp 0x22a56
movq %rbx, %rsi
movq %rbp, %rdx
callq 0x5219
movq 0x1659c(%rip), %rbx     # 0x38fe0
jmp 0x22a0c
movq %rbx, %rsi
movq %rbp, %rdx
movq %r14, %rcx
callq 0x5288
jmp 0x229f0
addq $0x428, %rsp            # imm = 0x428
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
leaq 0x9e61(%rip), %rdi      # 0x2c8d0
movq %r12, %rsi
xorl %eax, %eax
callq 0x2270