// File: melop[P]admixem/config.cpp
// Function: MarkerConfigurations::LoadFromFile(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char>>)
void MarkerConfigurations::LoadFromFile(string szConfigFile) {

	FILE *pConfigFile;

	printf("Start loading marker file %s ...\n", szConfigFile.c_str());

	_szConfigFilename = szConfigFile; // save name of config file

	pConfigFile = fopen(szConfigFile.c_str(), "r");

	if (!pConfigFile) {
		printf("%s\n", "Cannot open marker file ...");
		throw "Cannot open marker file!";
	}


	char szBuffer[2048];

	if (fgets(szBuffer, 2048, pConfigFile) == NULL) {
		throw "Error reading marker file!";
	}

	int nHaploidChrNum;

	sscanf(szBuffer, "HaploidChromosomeNum =  %d", &nHaploidChrNum); // Read in chromosome number

	if (nHaploidChrNum == NULL) {
		throw "Haploid Chromosome Number in marker file incorrect!";
	}

	this->_nHaploidChrNum = nHaploidChrNum; //save the haploid chromosome number

	//initialize arrays:
	this->pChrLen = new double[nHaploidChrNum];
	this->pPaternalTransBias = new double[nHaploidChrNum];
	this->pCentromerePos = new double[nHaploidChrNum];

	vector<int> vIndexCounters; //init index counter
	vMarkerIndex.clear();

	for (int i=0;i<_nHaploidChrNum;i++) {
		vIndexCounters.push_back(0);
		map<double, int> oTempMap;
		vMarkerIndex.push_back(oTempMap);
	}
	
	for (int nPop=0;nPop<2;nPop++) 
	{
		vMarkerFreq.insert( vMarkerFreq.end(), new map<double, double>[nHaploidChrNum] );
	}

	int nCurrChr = 0;

	int nNum;
	double nAbsPos, nFreqPop1, nFreqPop2;
	//char sAbsPos[100], sFreqPop1[100], sFreqPop2[100];
	bool bIgnoreMarkerFreq = (SimulConfig.GetConfig("IgnoreMarkerFreq") == "yes");

	while(fgets(szBuffer, 2048, pConfigFile) != NULL) 
	{

		//sscanf(szBuffer, "%d %*f %f %f %f", &nNum, &nAbsPos, &nFreqPop1, &nFreqPop2);

		if (szBuffer[0] == ':') { // it's a chr definition line

			double nChrLen;
			double nCentromerePos;
			double nPaternalTransBias; // when transmitting gametes, the bias towards paternal chr. 0.5 is neutral, 0 is maternal

			int nItemsRead = sscanf(szBuffer, ":chr %d len = %lf centromere = %lf paternaltransbias = %lf", &nCurrChr, &nChrLen , &nCentromerePos, &nPaternalTransBias);

			if (nItemsRead < 4) {
				nPaternalTransBias = 0.5;
			}
			//nCurrChr = (int)strtol( sCurrChr , NULL, 10);
			//nChrLen = strtod( sChrLen, NULL );
			//nCentromerePos = strtod( sCentromerePos , NULL);

			
			nCurrChr--; 

			//printf("%d %f %f", nCurrChr, nChrLen , nCentromerePos );

			if (nCurrChr > nHaploidChrNum) 
			{
				throw "The chromosome number is larger than total chromosome number!";
			}

			// save chromosome information:
			pChrLen[nCurrChr] = nChrLen;
			pPaternalTransBias[nCurrChr] = nPaternalTransBias;
			nTotalGenomeLen += nChrLen;
			pCentromerePos[nCurrChr] = nCentromerePos;
			printf("Reading markers on chromosome %d , length=%f, centromere=%f paternalTransBias=%f ...\n", (nCurrChr + 1), nChrLen, nCentromerePos,nPaternalTransBias);

		}
		else if (sscanf(szBuffer, "%d %*lf %lf %lf %lf", &nNum, &nAbsPos, &nFreqPop1, &nFreqPop2)==4) {

			if (vMarkerFreq[0][nCurrChr].find(nAbsPos) == vMarkerFreq[0][nCurrChr].end()) { // make sure the position is not occupied
				
				vMarkerFreq[0][nCurrChr][nAbsPos] = bIgnoreMarkerFreq? 1: nFreqPop1;
				vMarkerFreq[1][nCurrChr][nAbsPos] = bIgnoreMarkerFreq? 0: nFreqPop2;

				vMarkerIndex[nCurrChr][nAbsPos] = vIndexCounters.at(nCurrChr);
				vIndexCounters.at(nCurrChr) += 1;
			}
			else
			{

				printf("Warning: repetitive definition of position  %f on chromosome %d found. second one will be ignored\n", nAbsPos, nCurrChr );
			}
		}

		else {

		}

		
		/*
		if (sscanf_s(szBuffer, "%d %*f %f %f %f", &nNum, &nAbsPos, &nFreqPop1, &nFreqPop2)!=4) { // if this is not a data line try parsing: :chr 1	len = 3.3e+007	centromere = 1.1e+007
			
			double nChrLen;
			double nCentromerePos;
			
			//sscanf(szBuffer, ":chr %d	len = %f	centromere = %f", &nCurrChr, &nChrLen , &nCentromerePos);

			if (sscanf_s(szBuffer, ":chr %d len = %f centromere = %f", &nCurrChr, &nChrLen , &nCentromerePos) != 3) {
				continue;
			}

			nCurrChr--; 

			//printf("%d %f %f", nCurrChr, nChrLen , nCentromerePos );

			if (nCurrChr > nHaploidChrNum) 
			{
				throw "The chromosome number is larger than total chromosome number!";
			}

			// save chromosome information:
			pChrLen[nCurrChr] = nChrLen;
			pCentromerePos[nCurrChr] = nCentromerePos;

		}
		else { //this is a dataline!
			vMarkerFreq[0][nCurrChr][nAbsPos] = nFreqPop1;
			vMarkerFreq[1][nCurrChr][nAbsPos] = nFreqPop2;
			//printf("%d %f %f %f\n", nNum, nAbsPos, nFreqPop1, nFreqPop2 );
		}

		*/

	}

	fclose(pConfigFile);

	//printf("%f",vMarkerFreq[0][0].begin()->first );

}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0xa20, %rsp            # imm = 0xA20
movq %rsi, -0x968(%rbp)
movq %rdi, %rax
movq -0x968(%rbp), %rdi
movq %rdi, -0x958(%rbp)
movq %rax, -0x8(%rbp)
movq %rdi, -0x10(%rbp)
movq -0x8(%rbp), %rax
movq %rax, -0x960(%rbp)
callq 0x81d0
movq %rax, %rsi
leaq 0x5b3e3(%rip), %rdi     # 0x76c18
movb $0x0, %al
callq 0x8080
movq -0x960(%rbp), %rdi
movq -0x958(%rbp), %rsi
addq $0x10, %rdi
callq 0x8070
movq -0x958(%rbp), %rdi
callq 0x81d0
movq %rax, %rdi
leaq 0x5d6d9(%rip), %rsi     # 0x78f42
callq 0x85e0
movq %rax, -0x18(%rbp)
cmpq $0x0, -0x18(%rbp)
jne 0x1b8b5
leaq 0x5baa6(%rip), %rdi     # 0x77326
leaq 0x5b3b3(%rip), %rsi     # 0x76c3a
movb $0x0, %al
callq 0x8080
movl $0x8, %edi
callq 0x8230
movq %rax, %rdi
leaq 0x5b3b4(%rip), %rax     # 0x76c56
movq %rax, (%rdi)
movq 0x8e69c(%rip), %rsi     # 0xa9f48
xorl %eax, %eax
movl %eax, %edx
callq 0x8820
leaq -0x820(%rbp), %rdi
movq -0x18(%rbp), %rdx
movl $0x800, %esi            # imm = 0x800
callq 0x8750
cmpq $0x0, %rax
jne 0x1b8f7
movl $0x8, %edi
callq 0x8230
movq %rax, %rdi
leaq 0x5b38b(%rip), %rax     # 0x76c6f
movq %rax, (%rdi)
movq 0x8e65a(%rip), %rsi     # 0xa9f48
xorl %eax, %eax
movl %eax, %edx
callq 0x8820
leaq -0x820(%rbp), %rdi
leaq 0x5b385(%rip), %rsi     # 0x76c8a
leaq -0x824(%rbp), %rdx
movb $0x0, %al
callq 0x8480
movslq -0x824(%rbp), %rax
cmpq $0x0, %rax
jne 0x1b947
movl $0x8, %edi
callq 0x8230
movq %rax, %rdi
leaq 0x5b371(%rip), %rax     # 0x76ca5
movq %rax, (%rdi)
movq 0x8e60a(%rip), %rsi     # 0xa9f48
xorl %eax, %eax
movl %eax, %edx
callq 0x8820
movq -0x960(%rbp), %rax
movl -0x824(%rbp), %ecx
movl %ecx, 0x8(%rax)
movslq -0x824(%rbp), %rax
movl $0x8, %ecx
mulq %rcx
movq %rax, %rdi
seto %cl
movq $-0x1, %rax
testb $0x1, %cl
cmovneq %rax, %rdi
callq 0x8040
movq %rax, %rcx
movq -0x960(%rbp), %rax
movq %rcx, 0x30(%rax)
movslq -0x824(%rbp), %rax
movl $0x8, %ecx
mulq %rcx
movq %rax, %rdi
seto %cl
movq $-0x1, %rax
testb $0x1, %cl
cmovneq %rax, %rdi
callq 0x8040
movq %rax, %rcx
movq -0x960(%rbp), %rax
movq %rcx, 0x38(%rax)
movslq -0x824(%rbp), %rax
movl $0x8, %ecx
mulq %rcx
movq %rax, %rdi
seto %cl
movq $-0x1, %rax
testb $0x1, %cl
cmovneq %rax, %rdi
callq 0x8040
movq %rax, %rcx
movq -0x960(%rbp), %rax
movq %rcx, 0x48(%rax)
leaq -0x840(%rbp), %rdi
callq 0x2a060
movq -0x960(%rbp), %rdi
addq $0x68, %rdi
callq 0x2a080
movl $0x0, -0x844(%rbp)
movq -0x960(%rbp), %rcx
movl -0x844(%rbp), %eax
cmpl 0x8(%rcx), %eax
jge 0x1bad7
movl $0x0, -0x848(%rbp)
leaq -0x840(%rbp), %rdi
leaq -0x848(%rbp), %rsi
callq 0x2a0a0
jmp 0x1ba54
leaq -0x888(%rbp), %rdi
movq %rdi, -0x970(%rbp)
callq 0x2a0d0
movq -0x960(%rbp), %rdi
movq -0x970(%rbp), %rsi
addq $0x68, %rdi
callq 0x2a0f0
jmp 0x1ba80
leaq -0x888(%rbp), %rdi
callq 0x2a160
movl -0x844(%rbp), %eax
addl $0x1, %eax
movl %eax, -0x844(%rbp)
jmp 0x1ba1f
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x850(%rbp)
movl %eax, -0x854(%rbp)
jmp 0x1c16a
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x850(%rbp)
movl %eax, -0x854(%rbp)
leaq -0x888(%rbp), %rdi
callq 0x2a160
jmp 0x1c16a
movl $0x0, -0x88c(%rbp)
cmpl $0x2, -0x88c(%rbp)
jge 0x1bc2a
movq -0x960(%rbp), %rdi
addq $0x50, %rdi
movq %rdi, -0x988(%rbp)
callq 0x2a1c0
movq %rax, -0x8a0(%rbp)
leaq -0x898(%rbp), %rdi
leaq -0x8a0(%rbp), %rsi
callq 0x2a1f0
movslq -0x824(%rbp), %rax
movq %rax, -0x980(%rbp)
movl $0x30, %ecx
mulq %rcx
movq %rax, %rdi
seto %cl
addq $0x8, %rdi
movq $-0x1, %rax
cmovbq %rax, %rdi
testb %cl, %cl
cmovneq %rax, %rdi
callq 0x8040
movq %rax, -0x978(%rbp)
jmp 0x1bb5e
movq -0x980(%rbp), %rax
movq -0x978(%rbp), %rcx
movq %rax, (%rcx)
addq $0x8, %rcx
movq %rcx, -0x990(%rbp)
cmpq $0x0, %rax
je 0x1bbd7
movq -0x990(%rbp), %rax
movq -0x980(%rbp), %rcx
imulq $0x30, %rcx, %rdx
movq %rax, %rcx
addq %rdx, %rcx
movq %rcx, -0x9a0(%rbp)
movq %rax, -0x998(%rbp)
movq -0x998(%rbp), %rdi
movq %rdi, -0x9a8(%rbp)
callq 0x2a230
movq -0x9a8(%rbp), %rax
movq -0x9a0(%rbp), %rcx
addq $0x30, %rax
cmpq %rcx, %rax
movq %rax, -0x998(%rbp)
jne 0x1bba6
movq -0x988(%rbp), %rdi
movq -0x990(%rbp), %rax
movq %rax, -0x8a8(%rbp)
movq -0x898(%rbp), %rsi
leaq -0x8a8(%rbp), %rdx
callq 0x2a180
movq %rax, -0x9b0(%rbp)
jmp 0x1bc08
movq -0x9b0(%rbp), %rax
movq %rax, -0x8b0(%rbp)
movl -0x88c(%rbp), %eax
addl $0x1, %eax
movl %eax, -0x88c(%rbp)
jmp 0x1bae1
movl $0x0, -0x8b4(%rbp)
leaq -0x919(%rbp), %rdi
movq %rdi, -0x9b8(%rbp)
callq 0x8870
movq -0x9b8(%rbp), %rdx
leaq 0x5b084(%rip), %rsi     # 0x76cd9
leaq -0x918(%rbp), %rdi
callq 0xcb30
jmp 0x1bc63
leaq 0x8edee(%rip), %rsi     # 0xaaa58
leaq -0x8f8(%rbp), %rdi
leaq -0x918(%rbp), %rdx
callq 0x1c190
jmp 0x1bc7f
leaq 0x5cc3e(%rip), %rsi     # 0x788c4
leaq -0x8f8(%rbp), %rdi
callq 0xcbe0
movb %al, -0x9b9(%rbp)
jmp 0x1bc9a
leaq -0x8f8(%rbp), %rdi
callq 0x82e0
leaq -0x918(%rbp), %rdi
callq 0x82e0
leaq -0x919(%rbp), %rdi
callq 0x8540
movb -0x9b9(%rbp), %al
andb $0x1, %al
movb %al, -0x8d1(%rbp)
movq -0x18(%rbp), %rdx
leaq -0x820(%rbp), %rdi
movl $0x800, %esi            # imm = 0x800
callq 0x8750
movq %rax, -0x9c8(%rbp)
jmp 0x1bcea
movq -0x9c8(%rbp), %rax
cmpq $0x0, %rax
je 0x1c14a
movsbl -0x820(%rbp), %eax
cmpl $0x3a, %eax
jne 0x1bea3
leaq -0x820(%rbp), %rdi
leaq 0x5afd1(%rip), %rsi     # 0x76cea
leaq -0x8b4(%rbp), %rdx
leaq -0x928(%rbp), %rcx
leaq -0x930(%rbp), %r8
leaq -0x938(%rbp), %r9
movb $0x0, %al
callq 0x8480
movl %eax, -0x93c(%rbp)
cmpl $0x4, -0x93c(%rbp)
jge 0x1bdc0
movsd 0x5a93d(%rip), %xmm0    # 0x76690
movsd %xmm0, -0x938(%rbp)
jmp 0x1bdc0
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x850(%rbp)
movl %eax, -0x854(%rbp)
jmp 0x1bdaf
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x850(%rbp)
movl %eax, -0x854(%rbp)
jmp 0x1bda3
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x850(%rbp)
movl %eax, -0x854(%rbp)
leaq -0x8f8(%rbp), %rdi
callq 0x82e0
leaq -0x918(%rbp), %rdi
callq 0x82e0
leaq -0x919(%rbp), %rdi
callq 0x8540
jmp 0x1c16a
movl -0x8b4(%rbp), %eax
addl $-0x1, %eax
movl %eax, -0x8b4(%rbp)
movl -0x8b4(%rbp), %eax
cmpl -0x824(%rbp), %eax
jle 0x1be09
movl $0x8, %edi
callq 0x8230
movq %rax, %rdi
leaq 0x5af34(%rip), %rax     # 0x76d25
movq %rax, (%rdi)
movq 0x8e14d(%rip), %rsi     # 0xa9f48
xorl %eax, %eax
movl %eax, %edx
callq 0x8820
jmp 0x1c182
movq -0x960(%rbp), %rax
movsd -0x928(%rbp), %xmm0
movq 0x30(%rax), %rcx
movslq -0x8b4(%rbp), %rdx
movsd %xmm0, (%rcx,%rdx,8)
movsd -0x938(%rbp), %xmm0
movq 0x38(%rax), %rcx
movslq -0x8b4(%rbp), %rdx
movsd %xmm0, (%rcx,%rdx,8)
movsd -0x928(%rbp), %xmm1
movsd 0x40(%rax), %xmm0
addsd %xmm1, %xmm0
movsd %xmm0, 0x40(%rax)
movsd -0x930(%rbp), %xmm0
movq 0x48(%rax), %rax
movslq -0x8b4(%rbp), %rcx
movsd %xmm0, (%rax,%rcx,8)
movl -0x8b4(%rbp), %esi
incl %esi
movsd -0x928(%rbp), %xmm0
movsd -0x930(%rbp), %xmm1
movsd -0x938(%rbp), %xmm2
leaq 0x5aece(%rip), %rdi     # 0x76d63
movb $0x3, %al
callq 0x8080
jmp 0x1be9e
jmp 0x1c145
leaq -0x820(%rbp), %rdi
leaq 0x5af08(%rip), %rsi     # 0x76db9
leaq -0x8b8(%rbp), %rdx
leaq -0x8c0(%rbp), %rcx
leaq -0x8c8(%rbp), %r8
leaq -0x8d0(%rbp), %r9
movb $0x0, %al
callq 0x8480
cmpl $0x4, %eax
jne 0x1c141
movq -0x960(%rbp), %rdi
addq $0x50, %rdi
xorl %eax, %eax
movl %eax, %esi
callq 0x2a280
movq (%rax), %rdi
movslq -0x8b4(%rbp), %rax
leaq (%rax,%rax,2), %rax
shlq $0x4, %rax
addq %rax, %rdi
leaq -0x8c0(%rbp), %rsi
callq 0x2a2a0
movq %rax, -0x9d0(%rbp)
jmp 0x1bf1b
movq -0x960(%rbp), %rdi
movq -0x9d0(%rbp), %rax
movq %rax, -0x948(%rbp)
addq $0x50, %rdi
xorl %eax, %eax
movl %eax, %esi
callq 0x2a280
movq (%rax), %rdi
movslq -0x8b4(%rbp), %rax
imulq $0x30, %rax, %rax
addq %rax, %rdi
callq 0x2a2d0
movq %rax, -0x950(%rbp)
leaq -0x948(%rbp), %rdi
leaq -0x950(%rbp), %rsi
callq 0x2a250
testb $0x1, %al
jne 0x1bf76
jmp 0x1c11f
testb $0x1, -0x8d1(%rbp)
je 0x1bf91
movsd 0x5a089(%rip), %xmm0    # 0x76010
movsd %xmm0, -0x9d8(%rbp)
jmp 0x1bfa1
movsd -0x8c8(%rbp), %xmm0
movsd %xmm0, -0x9d8(%rbp)
movq -0x960(%rbp), %rdi
movsd -0x9d8(%rbp), %xmm0
movsd %xmm0, -0x9e8(%rbp)
addq $0x50, %rdi
xorl %eax, %eax
movl %eax, %esi
callq 0x2a280
movq (%rax), %rdi
movslq -0x8b4(%rbp), %rax
leaq (%rax,%rax,2), %rax
shlq $0x4, %rax
addq %rax, %rdi
leaq -0x8c0(%rbp), %rsi
callq 0x2a300
movq %rax, -0x9e0(%rbp)
jmp 0x1bfef
movq -0x9e0(%rbp), %rax
movsd -0x9e8(%rbp), %xmm0
movsd %xmm0, (%rax)
testb $0x1, -0x8d1(%rbp)
je 0x1c018
xorps %xmm0, %xmm0
movsd %xmm0, -0x9f0(%rbp)
jmp 0x1c028
movsd -0x8d0(%rbp), %xmm0
movsd %xmm0, -0x9f0(%rbp)
movq -0x960(%rbp), %rdi
movsd -0x9f0(%rbp), %xmm0
movsd %xmm0, -0xa00(%rbp)
addq $0x50, %rdi
movl $0x1, %esi
callq 0x2a280
movq (%rax), %rdi
movslq -0x8b4(%rbp), %rax
leaq (%rax,%rax,2), %rax
shlq $0x4, %rax
addq %rax, %rdi
leaq -0x8c0(%rbp), %rsi
callq 0x2a300
movq %rax, -0x9f8(%rbp)
jmp 0x1c077
movq -0x9f8(%rbp), %rax
movsd -0xa00(%rbp), %xmm0
movsd %xmm0, (%rax)
movslq -0x8b4(%rbp), %rsi
leaq -0x840(%rbp), %rdi
callq 0x2a3e0
movq %rax, -0xa08(%rbp)
jmp 0x1c0a6
movq -0x960(%rbp), %rdi
movq -0xa08(%rbp), %rax
movl (%rax), %eax
movl %eax, -0xa14(%rbp)
addq $0x68, %rdi
movslq -0x8b4(%rbp), %rsi
callq 0x2a420
movq %rax, %rdi
leaq -0x8c0(%rbp), %rsi
callq 0x2a440
movq %rax, -0xa10(%rbp)
jmp 0x1c0e4
movq -0xa10(%rbp), %rax
movl -0xa14(%rbp), %ecx
movl %ecx, (%rax)
movslq -0x8b4(%rbp), %rsi
leaq -0x840(%rbp), %rdi
callq 0x2a3e0
movq %rax, -0xa20(%rbp)
jmp 0x1c10f
movq -0xa20(%rbp), %rax
movl (%rax), %ecx
addl $0x1, %ecx
movl %ecx, (%rax)
jmp 0x1c13f
movsd -0x8c0(%rbp), %xmm0
movl -0x8b4(%rbp), %esi
leaq 0x5ac99(%rip), %rdi     # 0x76dcd
movb $0x1, %al
callq 0x8080
jmp 0x1c13d
jmp 0x1c13f
jmp 0x1c143
jmp 0x1c143
jmp 0x1c145
jmp 0x1bccc
movq -0x18(%rbp), %rdi
callq 0x84b0
jmp 0x1c155
leaq -0x840(%rbp), %rdi
callq 0x2a520
addq $0xa20, %rsp            # imm = 0xA20
popq %rbp
retq
leaq -0x840(%rbp), %rdi
callq 0x2a520
movq -0x850(%rbp), %rdi
callq 0x8860
nopw %cs:(%rax,%rax)