// File: FreeSlave[P]vhlt/hlcsg/brush.cpp
// Function: SortSides(brushhull_t*)
void SortSides (brushhull_t *h)
{
	int numsides;
	bface_t **sides;
	vec3_t *normals;
	bool *isused;
	int i, j;
	int *sorted;
	bface_t *f;
	for (numsides = 0, f = h->faces; f; f = f->next)
	{
		numsides++;
	}
	sides = (bface_t **)malloc (numsides * sizeof (bface_t *));
	hlassume (sides != NULL, assume_NoMemory);
	normals = (vec3_t *)malloc (numsides * sizeof (vec3_t));
	hlassume (normals != NULL, assume_NoMemory);
	isused = (bool *)malloc (numsides * sizeof (bool));
	hlassume (isused != NULL, assume_NoMemory);
	sorted = (int *)malloc (numsides * sizeof (int));
	hlassume (sorted != NULL, assume_NoMemory);
	for (i = 0, f = h->faces; f; i++, f = f->next)
	{
		sides[i] = f;
		isused[i] = false;
		const plane_t *p = &g_mapplanes[f->planenum];
		VectorCopy (p->normal, normals[i]);
	}
	for (i = 0; i < numsides; i++)
	{
		int bestside;
		int bestaxial = -1;
		for (j = 0; j < numsides; j++)
		{
			if (isused[j])
			{
				continue;
			}
			int axial = (fabs (normals[j][0]) < NORMAL_EPSILON) + (fabs (normals[j][1]) < NORMAL_EPSILON) + (fabs (normals[j][2]) < NORMAL_EPSILON);
			if (axial > bestaxial)
			{
				bestside = j;
				bestaxial = axial;
			}
		}
		sorted[i] = bestside;
		isused[bestside] = true;
	}
	for (i = -1; i < numsides; i++)
	{
		*(i >= 0? &sides[sorted[i]]->next: &h->faces) = (i + 1 < numsides? sides[sorted[i + 1]]: NULL);
	}
	free (sides);
	free (normals);
	free (isused);
	free (sorted);
}

// Assembly:
subq $0x78, %rsp
movq %rdi, 0x70(%rsp)
movl $0x0, 0x6c(%rsp)
movq 0x70(%rsp), %rax
movq 0x30(%rax), %rax
movq %rax, 0x38(%rsp)
cmpq $0x0, 0x38(%rsp)
je 0x15841
movl 0x6c(%rsp), %eax
addl $0x1, %eax
movl %eax, 0x6c(%rsp)
movq 0x38(%rsp), %rax
movq (%rax), %rax
movq %rax, 0x38(%rsp)
jmp 0x1581f
movslq 0x6c(%rsp), %rdi
shlq $0x3, %rdi
callq 0x4500
movq %rax, 0x60(%rsp)
cmpq $0x0, 0x60(%rsp)
setne %al
movzbl %al, %edi
andl $0x1, %edi
movl $0x1, %esi
callq 0xc400
movslq 0x6c(%rsp), %rax
imulq $0x18, %rax, %rdi
callq 0x4500
movq %rax, 0x58(%rsp)
cmpq $0x0, 0x58(%rsp)
setne %al
movzbl %al, %edi
andl $0x1, %edi
movl $0x1, %esi
callq 0xc400
movslq 0x6c(%rsp), %rdi
shlq $0x0, %rdi
callq 0x4500
movq %rax, 0x50(%rsp)
cmpq $0x0, 0x50(%rsp)
setne %al
movzbl %al, %edi
andl $0x1, %edi
movl $0x1, %esi
callq 0xc400
movslq 0x6c(%rsp), %rdi
shlq $0x2, %rdi
callq 0x4500
movq %rax, 0x40(%rsp)
cmpq $0x0, 0x40(%rsp)
setne %al
movzbl %al, %edi
andl $0x1, %edi
movl $0x1, %esi
callq 0xc400
movl $0x0, 0x4c(%rsp)
movq 0x70(%rsp), %rax
movq 0x30(%rax), %rax
movq %rax, 0x38(%rsp)
cmpq $0x0, 0x38(%rsp)
je 0x159cb
movq 0x38(%rsp), %rdx
movq 0x60(%rsp), %rax
movslq 0x4c(%rsp), %rcx
movq %rdx, (%rax,%rcx,8)
movq 0x50(%rsp), %rax
movslq 0x4c(%rsp), %rcx
movb $0x0, (%rax,%rcx)
movq 0x38(%rsp), %rax
movslq 0x8(%rax), %rcx
leaq 0x20c505c(%rip), %rax   # 0x20da9a0
shlq $0x6, %rcx
addq %rcx, %rax
movq %rax, 0x30(%rsp)
movq 0x30(%rsp), %rax
movsd (%rax), %xmm0
movq 0x58(%rsp), %rax
movslq 0x4c(%rsp), %rcx
imulq $0x18, %rcx, %rcx
addq %rcx, %rax
movsd %xmm0, (%rax)
movq 0x30(%rsp), %rax
movsd 0x8(%rax), %xmm0
movq 0x58(%rsp), %rax
movslq 0x4c(%rsp), %rcx
imulq $0x18, %rcx, %rcx
addq %rcx, %rax
movsd %xmm0, 0x8(%rax)
movq 0x30(%rsp), %rax
movsd 0x10(%rax), %xmm0
movq 0x58(%rsp), %rax
movslq 0x4c(%rsp), %rcx
imulq $0x18, %rcx, %rcx
addq %rcx, %rax
movsd %xmm0, 0x10(%rax)
movl 0x4c(%rsp), %eax
addl $0x1, %eax
movl %eax, 0x4c(%rsp)
movq 0x38(%rsp), %rax
movq (%rax), %rax
movq %rax, 0x38(%rsp)
jmp 0x15907
movl $0x0, 0x4c(%rsp)
movl 0x4c(%rsp), %eax
cmpl 0x6c(%rsp), %eax
jge 0x15b17
movl $0xffffffff, 0x28(%rsp) # imm = 0xFFFFFFFF
movl $0x0, 0x48(%rsp)
movl 0x48(%rsp), %eax
cmpl 0x6c(%rsp), %eax
jge 0x15ae8
movq 0x50(%rsp), %rax
movslq 0x48(%rsp), %rcx
testb $0x1, (%rax,%rcx)
je 0x15a14
jmp 0x15ad8
movq 0x58(%rsp), %rax
movslq 0x48(%rsp), %rcx
imulq $0x18, %rcx, %rcx
addq %rcx, %rax
movsd (%rax), %xmm1
movaps 0x17a80(%rip), %xmm0    # 0x2d4b0
pand %xmm0, %xmm1
movsd 0x1462c(%rip), %xmm0    # 0x2a068
ucomisd %xmm1, %xmm0
seta %al
andb $0x1, %al
movzbl %al, %eax
movq 0x58(%rsp), %rcx
movslq 0x48(%rsp), %rdx
imulq $0x18, %rdx, %rdx
addq %rdx, %rcx
movsd 0x8(%rcx), %xmm1
movaps 0x17a4b(%rip), %xmm0    # 0x2d4b0
pand %xmm0, %xmm1
movsd 0x145f7(%rip), %xmm0    # 0x2a068
ucomisd %xmm1, %xmm0
seta %cl
andb $0x1, %cl
movzbl %cl, %ecx
addl %ecx, %eax
movq 0x58(%rsp), %rcx
movslq 0x48(%rsp), %rdx
imulq $0x18, %rdx, %rdx
addq %rdx, %rcx
movsd 0x10(%rcx), %xmm1
movaps 0x17a13(%rip), %xmm0    # 0x2d4b0
pand %xmm0, %xmm1
movsd 0x145bf(%rip), %xmm0    # 0x2a068
ucomisd %xmm1, %xmm0
seta %cl
andb $0x1, %cl
movzbl %cl, %ecx
addl %ecx, %eax
movl %eax, 0x24(%rsp)
movl 0x24(%rsp), %eax
cmpl 0x28(%rsp), %eax
jle 0x15ad6
movl 0x48(%rsp), %eax
movl %eax, 0x2c(%rsp)
movl 0x24(%rsp), %eax
movl %eax, 0x28(%rsp)
jmp 0x15ad8
movl 0x48(%rsp), %eax
addl $0x1, %eax
movl %eax, 0x48(%rsp)
jmp 0x159f1
movl 0x2c(%rsp), %edx
movq 0x40(%rsp), %rax
movslq 0x4c(%rsp), %rcx
movl %edx, (%rax,%rcx,4)
movq 0x50(%rsp), %rax
movslq 0x2c(%rsp), %rcx
movb $0x1, (%rax,%rcx)
movl 0x4c(%rsp), %eax
addl $0x1, %eax
movl %eax, 0x4c(%rsp)
jmp 0x159d3
movl $0xffffffff, 0x4c(%rsp) # imm = 0xFFFFFFFF
movl 0x4c(%rsp), %eax
cmpl 0x6c(%rsp), %eax
jge 0x15bc0
movl 0x4c(%rsp), %eax
addl $0x1, %eax
cmpl 0x6c(%rsp), %eax
jge 0x15b5d
movq 0x60(%rsp), %rax
movq 0x40(%rsp), %rcx
movl 0x4c(%rsp), %edx
addl $0x1, %edx
movslq %edx, %rdx
movslq (%rcx,%rdx,4), %rcx
movq (%rax,%rcx,8), %rax
movq %rax, 0x18(%rsp)
jmp 0x15b66
xorl %eax, %eax
movq %rax, 0x18(%rsp)
jmp 0x15b66
movq 0x18(%rsp), %rax
movq %rax, 0x10(%rsp)
cmpl $0x0, 0x4c(%rsp)
jl 0x15b95
movq 0x60(%rsp), %rax
movq 0x40(%rsp), %rcx
movslq 0x4c(%rsp), %rdx
movslq (%rcx,%rdx,4), %rcx
movq (%rax,%rcx,8), %rax
movq %rax, 0x8(%rsp)
jmp 0x15ba3
movq 0x70(%rsp), %rax
addq $0x30, %rax
movq %rax, 0x8(%rsp)
movq 0x10(%rsp), %rcx
movq 0x8(%rsp), %rax
movq %rcx, (%rax)
movl 0x4c(%rsp), %eax
addl $0x1, %eax
movl %eax, 0x4c(%rsp)
jmp 0x15b1f
movq 0x60(%rsp), %rdi
callq 0x4470
movq 0x58(%rsp), %rdi
callq 0x4470
movq 0x50(%rsp), %rdi
callq 0x4470
movq 0x40(%rsp), %rdi
callq 0x4470
addq $0x78, %rsp
retq
nopl (%rax)