// File: /workspace/github_c_makefile_star2_O2/arkanis[P]process-map/map.c
// Function: UpdateTaskTraces
void UpdateTaskTraces(TaskTraces* traces, AddrRange ranges[], size_t rangeCount, size_t mapHilbertCurveOrder) {
	traces->currentTime++;
	// We use a hilbert curve order that can map each address to an x/y coordinate with byte accuracy (up from 4k per
	// pixel on the map). Because of that the addressOnMap below is calculated in bytes instead of 4k pages and the
	// calculated coordinates are later divided by 64 (side length of a 4k square).
	size_t byteAccurateHilberCurveOrder = mapHilbertCurveOrder + 6;
	
	for (size_t t = 0; t < traces->taskCount; t++) {
		if (traces->tasks[t].dead)
			continue;
		if ( ptrace(PTRACE_INTERRUPT, traces->tasks[t].pid, NULL, NULL) != 0 ) {
			traces->tasks[t].dead = true;
		  	perror("ptrace(PTRACE_INTERRUPT)");
		}
	}
	for (size_t t = 0; t < traces->taskCount; t++) {
		if (traces->tasks[t].dead)
			continue;
		Task* task = &traces->tasks[t];
		
		struct user_regs_struct regs;
		if ( waitpid(task->pid, NULL, 0) == -1 )                     perror("waitpid()");
		if ( ptrace(PTRACE_GETREGS, task->pid, NULL, &regs) != 0 )   perror("ptrace(PTRACE_GETREGS)");
		if ( ptrace(PTRACE_CONT, task->pid, NULL, NULL) != 0 )       perror("ptrace(PTRACE_CONT)");
		
		uint64_t addressOnMap = 0;
		for (size_t r = 0; r < rangeCount; r++) {
			if (regs.rip >= ranges[r].startAddr && regs.rip < ranges[r].endAddr) {
				addressOnMap = ranges[r].startPage * pageSize + (regs.rip - ranges[r].startAddr);
				break;
			}
		}
		
		int x, y;
		HilberCurveDistToPos(byteAccurateHilberCurveOrder, addressOnMap, &x, &y);
		TaskSample sample = (TaskSample){ .x = x / 64.0f, .y = y / 64.0f, .t = traces->currentTime };
		
		size_t currentParticleIndex = traces->currentTime % particleCount;
		glBindBuffer(GL_ARRAY_BUFFER, task->particleVBO);
			glBufferSubData(GL_ARRAY_BUFFER, currentParticleIndex * sizeof(TaskSample), sizeof(TaskSample), &sample);
		glBindBuffer(GL_ARRAY_BUFFER, 0);
	}
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x108, %rsp            # imm = 0x108
movq %rcx, %rbx
movq %rdx, 0x18(%rsp)
movq %rdi, %r15
incl 0x30(%rdi)
movq %rsi, 0x10(%rsp)
pushq $0x1c
popq %r14
leaq 0x482f6(%rip), %r13     # 0x59657
xorl %r12d, %r12d
movq 0x8(%r15), %rax
cmpq %rax, %r12
jae 0x113ac
movq (%r15), %rax
cmpb $0x0, (%rax,%r14)
jne 0x11391
movl -0x1c(%rax,%r14), %esi
movl $0x4207, %edi           # imm = 0x4207
xorl %edx, %edx
xorl %ecx, %ecx
xorl %eax, %eax
callq 0x63e0
testq %rax, %rax
jne 0x1139a
incq %r12
addq $0x20, %r14
jmp 0x11364
movq (%r15), %rax
movb $0x1, (%rax,%r14)
movq %r13, %rdi
callq 0x6740
jmp 0x11391
addq $0x6, %rbx
leaq 0x8b891(%rip), %rbp     # 0x9cc48
xorl %r14d, %r14d
cmpq %rax, %r14
jae 0x1151c
movq (%r15), %r12
movq %r14, %rcx
shlq $0x5, %rcx
cmpb $0x0, 0x1c(%r12,%rcx)
jne 0x114e1
addq %rcx, %r12
movl (%r12), %edi
xorl %esi, %esi
xorl %edx, %edx
callq 0x6490
cmpl $-0x1, %eax
je 0x114e9
movl (%r12), %esi
pushq $0xc
popq %rdi
xorl %edx, %edx
leaq 0x30(%rsp), %rcx
xorl %eax, %eax
callq 0x63e0
testq %rax, %rax
jne 0x114fa
movl (%r12), %esi
pushq $0x7
popq %rdi
xorl %edx, %edx
xorl %ecx, %ecx
xorl %eax, %eax
callq 0x63e0
testq %rax, %rax
jne 0x1150b
movq 0xb0(%rsp), %rcx
movq 0x10(%rsp), %rax
movq 0x18(%rsp), %rdx
subq $0x1, %rdx
jb 0x11459
movq %rcx, %rsi
subq (%rax), %rsi
jb 0x11451
cmpq 0x8(%rax), %rcx
jb 0x1145d
addq $0xa0, %rax
jmp 0x1143d
xorl %esi, %esi
jmp 0x11468
movq 0x30(%rax), %rax
shlq $0xc, %rax
addq %rax, %rsi
movq %rbx, %rdi
leaq 0xc(%rsp), %rdx
leaq 0x8(%rsp), %rcx
callq 0x11803
movss 0x8(%rsp), %xmm0
movss 0xc(%rsp), %xmm1
unpcklps %xmm0, %xmm1            # xmm1 = xmm1[0],xmm0[0],xmm1[1],xmm0[1]
cvtdq2ps %xmm1, %xmm0
mulps 0x47e7d(%rip), %xmm0    # 0x59310
movlps %xmm0, 0x20(%rsp)
movl 0x30(%r15), %eax
movl %eax, 0x28(%rsp)
xorl %edx, %edx
movl $0x7d0, %ecx            # imm = 0x7D0
divl %ecx
movl %edx, %r13d
movl 0x18(%r12), %esi
movl $0x8892, %edi           # imm = 0x8892
callq *(%rbp)
imull $0xc, %r13d, %esi
movl $0x8892, %edi           # imm = 0x8892
pushq $0xc
popq %rdx
leaq 0x20(%rsp), %rcx
leaq 0x8b77f(%rip), %rax     # 0x9cc50
callq *(%rax)
movl $0x8892, %edi           # imm = 0x8892
xorl %esi, %esi
callq *(%rbp)
movq 0x8(%r15), %rax
incq %r14
jmp 0x113ba
leaq 0x48180(%rip), %rdi     # 0x59670
callq 0x6740
jmp 0x113f2
leaq 0x48179(%rip), %rdi     # 0x5967a
callq 0x6740
jmp 0x11410
leaq 0x4817f(%rip), %rdi     # 0x59691
callq 0x6740
jmp 0x1142b
addq $0x108, %rsp            # imm = 0x108
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq