// File: /workspace/github_cpp_makefile_star2_O1/mlugo2[P]SunshineGPU/src/gpu.cpp
// Function: gpu::mad_instr(unsigned long long)
void gpu::mad_instr(u64 instr)
{
	u128 temp0, temp1, temp2;

	// Determine destination and source paths
	u8 dest = get_dest_type(instr);
	u8 destIndex = get_dest_index(instr);
	u8 destW = get_dest_w(instr);
	u8 destZ = get_dest_z(instr);
	u8 destY = get_dest_y(instr);
	u8 destX = get_dest_x(instr);

	u8 src0 = get_srcN_type(instr, 0);
	u8 src0Index = get_srcN_index(instr, 0);
	u8 src0W = get_srcN_w(instr, 0);
	u8 src0Z = get_srcN_z(instr, 0);
	u8 src0Y = get_srcN_y(instr, 0);
	u8 src0X = get_srcN_x(instr, 0);

	u8 src1 = get_srcN_type(instr, 1);
	u8 src1Index = get_srcN_index(instr, 1);
	u8 src1W = get_srcN_w(instr, 1);
	u8 src1Z = get_srcN_z(instr, 1);
	u8 src1Y = get_srcN_y(instr, 1);
	u8 src1X = get_srcN_x(instr, 1);

	u8 src2 = get_srcN_type(instr, 2);
	u8 src2Index = get_srcN_index(instr, 2);
	u8 src2W = get_srcN_w(instr, 2);
	u8 src2Z = get_srcN_z(instr, 2);
	u8 src2Y = get_srcN_y(instr, 2);
	u8 src2X = get_srcN_x(instr, 2);

	// Swizzle it
	temp0 = swizzle(main_mem[src0][src0Index], src0W, src0Z, src0Y, src0X);

	temp1 = swizzle(main_mem[src1][src1Index], src1W, src1Z, src1Y, src1X);

	temp2 = swizzle(main_mem[src2][src2Index], src2W, src2Z, src2Y, src2X);

	// Negate it
	if (get_srcN_neg(instr, 0))
	{
		temp0.x = -temp0.x;
		temp0.y = -temp0.y;
		temp0.z = -temp0.z;
		temp0.w = -temp0.w;
	}

	if (get_srcN_neg(instr, 1))
	{
		temp1.x = -temp1.x;
		temp1.y = -temp1.y;
		temp1.z = -temp1.z;
		temp1.w = -temp1.w;
	}

	if (get_srcN_neg(instr, 2))
	{
		temp2.x = -temp2.x;
		temp2.y = -temp2.y;
		temp2.z = -temp2.z;
		temp2.w = -temp2.w;
	}

	// Bop it..
	if ( dest == TEMP_REG )
	{
		if (destW) main_mem[dest][destIndex].w = temp0.w * temp1.w + temp2.w;
		if (destZ) main_mem[dest][destIndex].z = temp0.z * temp1.z + temp2.z;
		if (destY) main_mem[dest][destIndex].y = temp0.y * temp1.y + temp2.y;
		if (destX) main_mem[dest][destIndex].x = temp0.x * temp1.x + temp2.x;
	}
	else
	{
		if (destW) VOB[destIndex].w = temp0.w * temp1.w + temp2.w;
		if (destZ) VOB[destIndex].z = temp0.z * temp1.z + temp2.z;
		if (destY) VOB[destIndex].y = temp0.y * temp1.y + temp2.y;
		if (destX) VOB[destIndex].x = temp0.x * temp1.x + temp2.x;
	}
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x68, %rsp
movq %rsi, %r14
movq %rsi, %rax
shrq $0x2d, %rax
andl $0x3, %eax
movq %rsi, %r9
shrq $0x29, %r9
andl $0xf, %r9d
shrq $0x27, %rsi
movq %r14, %rdx
shrq $0x25, %rdx
movq %r14, %rcx
shrq $0x23, %rcx
movq %r14, %r8
shrq $0x21, %r8
movl %r14d, %r10d
shrl $0x18, %r10d
movl %r10d, 0x20(%rsp)
movl %r14d, %r13d
shrl $0x16, %r13d
movl %r14d, %r10d
shrl $0x14, %r10d
movl %r10d, 0x10(%rsp)
movl %r14d, %ebp
shrl $0x12, %ebp
movl %r14d, %r10d
shrl $0x9, %r10d
movl %r10d, 0xc(%rsp)
movl %r14d, %r15d
shrl $0x7, %r15d
movl %r14d, %r10d
shrb $0x5, %r10b
andb $0x3, %r10b
movb %r10b, 0xb(%rsp)
movl %r14d, %r10d
shrb $0x3, %r10b
andb $0x3, %r10b
movb %r10b, 0xa(%rsp)
shll $0x8, %eax
addq %rdi, %rax
addq $0x7d6c0, %rax          # imm = 0x7D6C0
movq %rdi, %rbx
movq %rdi, 0x38(%rsp)
shll $0x4, %r9d
movsd (%r9,%rax), %xmm0
movsd 0x8(%r9,%rax), %xmm1
andl $0x3, %esi
andl $0x3, %edx
andl $0x3, %ecx
andl $0x3, %r8d
callq 0x83f6
movaps %xmm0, 0x50(%rsp)
movaps %xmm1, 0x40(%rsp)
movl $0x300, %r12d           # imm = 0x300
movl %r13d, %eax
andl %r12d, %eax
addq %rbx, %rax
addq $0x7d6c0, %rax          # imm = 0x7D6C0
movl $0xf0, %ebx
movl %r13d, %ecx
andl %ebx, %ecx
movsd (%rcx,%rax), %xmm0
movsd 0x8(%rcx,%rax), %xmm1
movl 0x20(%rsp), %esi
andl $0x3, %esi
andl $0x3, %r13d
movl 0x10(%rsp), %ecx
andl $0x3, %ecx
andl $0x3, %ebp
movl %r13d, %edx
movl %ebp, %r8d
callq 0x83f6
movaps %xmm0, 0x10(%rsp)
movaps %xmm1, 0x20(%rsp)
andl %r15d, %r12d
movq 0x38(%rsp), %rcx
leaq (%rcx,%r12), %rax
addq $0x7d6c0, %rax          # imm = 0x7D6C0
movq %rcx, %r12
andl %r15d, %ebx
movsd (%rbx,%rax), %xmm0
movsd 0x8(%rbx,%rax), %xmm1
movl 0xc(%rsp), %esi
andl $0x3, %esi
andl $0x3, %r15d
movzbl 0xb(%rsp), %ecx
movzbl 0xa(%rsp), %r8d
movl %r15d, %edx
callq 0x83f6
btq $0x2f, %r14
movaps 0x3887(%rip), %xmm2     # 0x9260
jae 0x59ed
movaps 0x40(%rsp), %xmm3
xorps %xmm2, %xmm3
movaps 0x50(%rsp), %xmm5
xorps %xmm2, %xmm5
jmp 0x59f7
movaps 0x40(%rsp), %xmm3
movaps 0x50(%rsp), %xmm5
btq $0x20, %r14
movaps 0x20(%rsp), %xmm4
movaps 0x10(%rsp), %xmm6
jae 0x5a0e
xorps %xmm2, %xmm4
xorps %xmm2, %xmm6
movq %r14, %rsi
shrq $0x32, %rsi
movq %r14, %rdx
shrq $0x31, %rdx
movq %r14, %rcx
shrq $0x30, %rcx
btl $0x11, %r14d
jae 0x5a30
xorps %xmm2, %xmm1
xorps %xmm2, %xmm0
movq %r14, %rax
shrq $0x34, %rax
btq $0x38, %r14
jb 0x5ae0
addq $0x7d6c0, %r12          # imm = 0x7D6C0
btq $0x33, %r14
jae 0x5a69
movaps %xmm5, %xmm2
mulss %xmm6, %xmm2
addss %xmm0, %xmm2
movl %eax, %edi
andl $0xf, %edi
shll $0x4, %edi
movss %xmm2, (%r12,%rdi)
testb $0x1, %sil
je 0x5a92
shufps $0x55, %xmm5, %xmm5     # xmm5 = xmm5[1,1,1,1]
shufps $0x55, %xmm6, %xmm6     # xmm6 = xmm6[1,1,1,1]
shufps $0x55, %xmm0, %xmm0     # xmm0 = xmm0[1,1,1,1]
mulss %xmm5, %xmm6
addss %xmm0, %xmm6
movl %eax, %esi
andl $0xf, %esi
shll $0x4, %esi
movss %xmm6, 0x4(%r12,%rsi)
testb $0x1, %dl
je 0x5ab1
movaps %xmm3, %xmm0
mulss %xmm4, %xmm0
addss %xmm1, %xmm0
movl %eax, %edx
andl $0xf, %edx
shll $0x4, %edx
movss %xmm0, 0x8(%r12,%rdx)
testb $0x1, %cl
je 0x5b7b
andl $0xf, %eax
shufps $0x55, %xmm3, %xmm3     # xmm3 = xmm3[1,1,1,1]
shufps $0x55, %xmm4, %xmm4     # xmm4 = xmm4[1,1,1,1]
shufps $0x55, %xmm1, %xmm1     # xmm1 = xmm1[1,1,1,1]
mulss %xmm3, %xmm4
addss %xmm1, %xmm4
shll $0x4, %eax
movss %xmm4, 0xc(%r12,%rax)
jmp 0x5b7b
btq $0x33, %r14
jae 0x5b04
movaps %xmm5, %xmm2
mulss %xmm6, %xmm2
addss %xmm0, %xmm2
movl %eax, %edi
andl $0xf, %edi
shll $0x4, %edi
movss %xmm2, 0x7dec0(%r12,%rdi)
testb $0x1, %sil
je 0x5b30
shufps $0x55, %xmm5, %xmm5     # xmm5 = xmm5[1,1,1,1]
shufps $0x55, %xmm6, %xmm6     # xmm6 = xmm6[1,1,1,1]
shufps $0x55, %xmm0, %xmm0     # xmm0 = xmm0[1,1,1,1]
mulss %xmm5, %xmm6
addss %xmm0, %xmm6
movl %eax, %esi
andl $0xf, %esi
shll $0x4, %esi
movss %xmm6, 0x7dec4(%r12,%rsi)
testb $0x1, %dl
je 0x5b52
movaps %xmm3, %xmm0
mulss %xmm4, %xmm0
addss %xmm1, %xmm0
movl %eax, %edx
andl $0xf, %edx
shll $0x4, %edx
movss %xmm0, 0x7dec8(%r12,%rdx)
testb $0x1, %cl
je 0x5b7b
shufps $0x55, %xmm3, %xmm3     # xmm3 = xmm3[1,1,1,1]
shufps $0x55, %xmm4, %xmm4     # xmm4 = xmm4[1,1,1,1]
shufps $0x55, %xmm1, %xmm1     # xmm1 = xmm1[1,1,1,1]
mulss %xmm3, %xmm4
addss %xmm1, %xmm4
andl $0xf, %eax
shll $0x4, %eax
movss %xmm4, 0x7decc(%r12,%rax)
addq $0x68, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq