// File: Altius[P]hotspot2/src/hotspot2_part1.cpp
// Function: parseAndProcessInput(int const&, int const&, int const&, std::basic_ofstream<char, std::char_traits<char>>&)
bool parseAndProcessInput(const int& windowSize, const int& samplingInterval, const int& MAlength,
			  ofstream& ofsPvalData)
{
  const int BUFSIZE(1000);
  char buf[BUFSIZE], *p;
  long linenum(0);
  int fieldnum;
  const int halfWindowSize(windowSize / 2); // integer division
  SiteRange curSite, prevSite;
  
  BackgroundRegionManager brm(samplingInterval, MAlength);
  SiteManager sm(ofsPvalData);

  prevSite.chrom = NULL;
  prevSite.endPos = -1;
  curSite.ID = NULL;
  curSite.hasPval = false;
  curSite.pval = -1.;
#ifdef DEBUG
  curSite.sampled = false;
#endif

  long start, end;

  while (cin.getline(buf, BUFSIZE))
    {
      linenum++;
      fieldnum = 1;
      p = strtok(buf, "\t");
      curSite.chrom = intern(string(p));
      fieldnum++;
      if (!(p = strtok(NULL, "\t")))
        {
        MissingField:
          cerr << "Error:  Missing required field " << fieldnum
               << " on line " << linenum << "." << endl
               << endl;
          return false;
        }
      start = atol(p);
      fieldnum++;
      if (!(p = strtok(NULL, "\t")))
        goto MissingField;
      end = atol(p);
      fieldnum++;
      if (!(p = strtok(NULL, "\t")))
        goto MissingField;
      //curSite.ID = intern(string(p));
      fieldnum++;
      if (!(p = strtok(NULL, "\t")))
        goto MissingField;
      curSite.count = atoi(p);
      // ignore any further fields

      // When contiguous stretches of sites with identical counts are observed
      // within a line of input, they need to be processed one site at a time,
      // for statistical reasons.
      for (int siteEnd = start + 1; siteEnd <= end; siteEnd++)
        {
          curSite.endPos = siteEnd;
	  curSite.begPos = curSite.endPos - 1;

          if (curSite.chrom != prevSite.chrom || curSite.endPos > prevSite.endPos + halfWindowSize)
            {
              brm.computePandFlush(sm); // Compute P-values for all unprocessed sites in the window.
	      // Writes values to disk.
              // This method removes all count data from brm.
              brm.setBounds(curSite.chrom, curSite.endPos, curSite.endPos + windowSize - 1);
            }

          if (!brm.isSliding() && curSite.endPos < brm.getRightEdge())
            {
              brm.add(curSite);
              sm.addSite(curSite);
            }
          else
            brm.slideAndCompute(curSite, sm); // calls sm.addSite(curSite)

          prevSite = curSite;
        }
    }

  brm.computePandFlush(sm); // See explanatory comment above.
  sm.writeLastUnreportedSite();

  return true;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x770, %rsp            # imm = 0x770
movq %rdi, -0x10(%rbp)
movq %rsi, -0x18(%rbp)
movq %rdx, -0x20(%rbp)
movq %rcx, -0x28(%rbp)
movl $0x3e8, -0x2c(%rbp)     # imm = 0x3E8
movq $0x0, -0x430(%rbp)
movq -0x10(%rbp), %rax
movl (%rax), %eax
movl %eax, %ecx
shrl $0x1f, %ecx
addl %ecx, %eax
sarl %eax
movl %eax, -0x438(%rbp)
movq -0x18(%rbp), %rsi
movq -0x20(%rbp), %rdx
leaq -0x650(%rbp), %rdi
callq 0x40c0
movq -0x28(%rbp), %rsi
leaq -0x6a8(%rbp), %rdi
callq 0xafd0
jmp 0x8ae8
movq $0x0, -0x4c0(%rbp)
movq $-0x1, -0x498(%rbp)
movq $0x0, -0x478(%rbp)
movb $0x0, -0x448(%rbp)
fld1
fchs
fstpt -0x470(%rbp)
movq 0x124b7(%rip), %rdi     # 0x1afd8
leaq -0x420(%rbp), %rsi
movl $0x3e8, %edx            # imm = 0x3E8
callq 0x3090
movq %rax, -0x700(%rbp)
jmp 0x8b3b
movq -0x700(%rbp), %rdi
movq (%rdi), %rax
movq -0x18(%rax), %rax
addq %rax, %rdi
callq 0x3350
movb %al, -0x701(%rbp)
jmp 0x8b59
movb -0x701(%rbp), %al
testb $0x1, %al
jne 0x8b68
jmp 0x8fd9
movq -0x430(%rbp), %rax
incq %rax
movq %rax, -0x430(%rbp)
movl $0x1, -0x434(%rbp)
leaq 0xac46(%rip), %rsi      # 0x137d0
leaq -0x420(%rbp), %rdi
callq 0x33c0
movq %rax, -0x428(%rbp)
movq -0x428(%rbp), %rax
movq %rax, -0x718(%rbp)
leaq -0x6e9(%rbp), %rdi
movq %rdi, -0x710(%rbp)
callq 0x3440
movq -0x718(%rbp), %rsi
movq -0x710(%rbp), %rdx
leaq -0x6e8(%rbp), %rdi
callq 0xb000
jmp 0x8bda
leaq -0x6e8(%rbp), %rdi
callq 0x3640
movq %rax, -0x720(%rbp)
jmp 0x8bef
movq -0x720(%rbp), %rax
movq %rax, -0x480(%rbp)
leaq -0x6e8(%rbp), %rdi
callq 0x3150
leaq -0x6e9(%rbp), %rdi
callq 0x32b0
movl -0x434(%rbp), %eax
addl $0x1, %eax
movl %eax, -0x434(%rbp)
xorl %eax, %eax
movl %eax, %edi
leaq 0xaba1(%rip), %rsi      # 0x137d0
callq 0x33c0
movq %rax, -0x428(%rbp)
cmpq $0x0, %rax
jne 0x8d87
jmp 0x8c47
movq 0x123a2(%rip), %rdi     # 0x1aff0
leaq 0xab7d(%rip), %rsi      # 0x137d2
callq 0x3240
movq %rax, -0x728(%rbp)
jmp 0x8c63
movq -0x728(%rbp), %rdi
movl -0x434(%rbp), %esi
callq 0x3420
movq %rax, -0x730(%rbp)
jmp 0x8c7e
movq -0x730(%rbp), %rdi
leaq 0xaa4f(%rip), %rsi      # 0x136db
callq 0x3240
movq %rax, -0x738(%rbp)
jmp 0x8c9a
movq -0x738(%rbp), %rdi
movq -0x430(%rbp), %rsi
callq 0x3470
movq %rax, -0x740(%rbp)
jmp 0x8cb6
movq -0x740(%rbp), %rdi
leaq 0xaa9e(%rip), %rsi      # 0x13762
callq 0x3240
movq %rax, -0x748(%rbp)
jmp 0x8cd2
movq -0x748(%rbp), %rdi
movq 0x122c8(%rip), %rsi     # 0x1afa8
callq 0x3280
movq %rax, -0x750(%rbp)
jmp 0x8cee
movq -0x750(%rbp), %rdi
movq 0x122ac(%rip), %rsi     # 0x1afa8
callq 0x3280
jmp 0x8d03
movb $0x0, -0x1(%rbp)
movl $0x1, -0x6f0(%rbp)
jmp 0x900a
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x6b0(%rbp)
movl %eax, -0x6b4(%rbp)
jmp 0x903c
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x6b0(%rbp)
movl %eax, -0x6b4(%rbp)
jmp 0x9030
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x6b0(%rbp)
movl %eax, -0x6b4(%rbp)
jmp 0x8d76
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x6b0(%rbp)
movl %eax, -0x6b4(%rbp)
leaq -0x6e8(%rbp), %rdi
callq 0x3150
leaq -0x6e9(%rbp), %rdi
callq 0x32b0
jmp 0x9030
movq -0x428(%rbp), %rdi
callq 0x3320
movq %rax, -0x6c0(%rbp)
movl -0x434(%rbp), %eax
addl $0x1, %eax
movl %eax, -0x434(%rbp)
xorl %eax, %eax
movl %eax, %edi
leaq 0xaa1c(%rip), %rsi      # 0x137d0
callq 0x33c0
movq %rax, -0x428(%rbp)
cmpq $0x0, %rax
jne 0x8dcb
jmp 0x8c47
movq -0x428(%rbp), %rdi
callq 0x3320
movq %rax, -0x6c8(%rbp)
movl -0x434(%rbp), %eax
addl $0x1, %eax
movl %eax, -0x434(%rbp)
xorl %eax, %eax
movl %eax, %edi
leaq 0xa9d8(%rip), %rsi      # 0x137d0
callq 0x33c0
movq %rax, -0x428(%rbp)
cmpq $0x0, %rax
jne 0x8e0f
jmp 0x8c47
movl -0x434(%rbp), %eax
addl $0x1, %eax
movl %eax, -0x434(%rbp)
xorl %eax, %eax
movl %eax, %edi
leaq 0xa9a7(%rip), %rsi      # 0x137d0
callq 0x33c0
movq %rax, -0x428(%rbp)
cmpq $0x0, %rax
jne 0x8e40
jmp 0x8c47
movq -0x428(%rbp), %rdi
callq 0x33b0
movl %eax, -0x450(%rbp)
movq -0x6c0(%rbp), %rax
addq $0x1, %rax
movl %eax, -0x6f4(%rbp)
movslq -0x6f4(%rbp), %rax
cmpq -0x6c8(%rbp), %rax
jg 0x8fd4
movslq -0x6f4(%rbp), %rax
movq %rax, -0x458(%rbp)
movq -0x458(%rbp), %rax
subq $0x1, %rax
movq %rax, -0x460(%rbp)
movq -0x480(%rbp), %rax
cmpq -0x4c0(%rbp), %rax
jne 0x8ec4
movq -0x458(%rbp), %rax
movq -0x498(%rbp), %rcx
movslq -0x438(%rbp), %rdx
addq %rdx, %rcx
cmpq %rcx, %rax
jle 0x8f04
leaq -0x650(%rbp), %rdi
leaq -0x6a8(%rbp), %rsi
callq 0x5d00
jmp 0x8ed9
movq -0x480(%rbp), %rsi
movl -0x458(%rbp), %edx
movq -0x10(%rbp), %rax
movl (%rax), %edi
movl %edx, %eax
movl %edi, %ecx
leal -0x1(%rax,%rcx), %ecx
leaq -0x650(%rbp), %rdi
callq 0x4250
jmp 0x8f02
jmp 0x8f04
leaq -0x650(%rbp), %rdi
callq 0xb0b0
movq %rax, -0x758(%rbp)
jmp 0x8f19
movq -0x758(%rbp), %rax
testb $0x1, (%rax)
jne 0x8f8a
movq -0x458(%rbp), %rax
movq %rax, -0x768(%rbp)
leaq -0x650(%rbp), %rdi
callq 0xb0d0
movq %rax, -0x760(%rbp)
jmp 0x8f48
movq -0x768(%rbp), %rax
movq -0x760(%rbp), %rcx
movslq (%rcx), %rcx
cmpq %rcx, %rax
jge 0x8f8a
leaq -0x650(%rbp), %rdi
leaq -0x480(%rbp), %rsi
callq 0x4330
jmp 0x8f73
leaq -0x6a8(%rbp), %rdi
leaq -0x480(%rbp), %rsi
callq 0x3c70
jmp 0x8f88
jmp 0x8fa8
leaq -0x650(%rbp), %rdi
leaq -0x480(%rbp), %rsi
leaq -0x6a8(%rbp), %rdx
callq 0x5f70
jmp 0x8fa6
jmp 0x8fa8
leaq -0x4c0(%rbp), %rdi
leaq -0x480(%rbp), %rsi
movl $0x40, %edx
callq 0x3200
movl -0x6f4(%rbp), %eax
addl $0x1, %eax
movl %eax, -0x6f4(%rbp)
jmp 0x8e63
jmp 0x8b1a
leaq -0x650(%rbp), %rdi
leaq -0x6a8(%rbp), %rsi
callq 0x5d00
jmp 0x8fee
leaq -0x6a8(%rbp), %rdi
callq 0xa620
jmp 0x8ffc
movb $0x1, -0x1(%rbp)
movl $0x1, -0x6f0(%rbp)
leaq -0x6a8(%rbp), %rdi
callq 0xb0f0
leaq -0x650(%rbp), %rdi
callq 0xb110
movb -0x1(%rbp), %al
andb $0x1, %al
addq $0x770, %rsp            # imm = 0x770
popq %rbp
retq
leaq -0x6a8(%rbp), %rdi
callq 0xb0f0
leaq -0x650(%rbp), %rdi
callq 0xb110
movq -0x6b0(%rbp), %rdi
callq 0x3430
nopw %cs:(%rax,%rax)