// File: /workspace/github_c_makefile_star2_O3/phoboslab[P]pl_mpeg/./pl_mpeg.h
// Function: plm_video_process_macroblock
void plm_video_process_macroblock(
	plm_video_t *self, uint8_t *s, uint8_t *d,
	int motion_h, int motion_v, int block_size, int interpolate
) {
	int dw = self->mb_width * block_size;

	int hp = motion_h >> 1;
	int vp = motion_v >> 1;
	int odd_h = (motion_h & 1) == 1;
	int odd_v = (motion_v & 1) == 1;

	unsigned int si = ((self->mb_row * block_size) + vp) * dw + (self->mb_col * block_size) + hp;
	unsigned int di = (self->mb_row * dw + self->mb_col) * block_size;
	
	unsigned int max_address = (dw * (self->mb_height * block_size - block_size + 1) - block_size);
	if (si > max_address || di > max_address) {
		return; // corrupt video
	}

	#define PLM_MB_CASE(INTERPOLATE, ODD_H, ODD_V, OP) \
		case ((INTERPOLATE << 2) | (ODD_H << 1) | (ODD_V)): \
			PLM_BLOCK_SET(d, di, dw, si, dw, block_size, OP); \
			break

	switch ((interpolate << 2) | (odd_h << 1) | (odd_v)) {
		PLM_MB_CASE(0, 0, 0, (s[si]));
		PLM_MB_CASE(0, 0, 1, (s[si] + s[si + dw] + 1) >> 1);
		PLM_MB_CASE(0, 1, 0, (s[si] + s[si + 1] + 1) >> 1);
		PLM_MB_CASE(0, 1, 1, (s[si] + s[si + 1] + s[si + dw] + s[si + dw + 1] + 2) >> 2);

		PLM_MB_CASE(1, 0, 0, (d[di] + (s[si]) + 1) >> 1);
		PLM_MB_CASE(1, 0, 1, (d[di] + ((s[si] + s[si + dw] + 1) >> 1) + 1) >> 1);
		PLM_MB_CASE(1, 1, 0, (d[di] + ((s[si] + s[si + 1] + 1) >> 1) + 1) >> 1);
		PLM_MB_CASE(1, 1, 1, (d[di] + ((s[si] + s[si + 1] + s[si + dw] + s[si + dw + 1] + 2) >> 2) + 1) >> 1);
	}

	#undef PLM_MB_CASE
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
movl 0x24(%rdi), %eax
imull %r9d, %eax
movl %ecx, %ebp
sarl %ebp
movl %r8d, %ebx
sarl %ebx
movl 0x28(%rdi), %r11d
movl 0x80(%rdi), %r10d
movl %r10d, %r14d
imull %r9d, %r14d
addl %ebx, %r14d
imull %eax, %r14d
movl 0x84(%rdi), %ebx
movl %ebx, %edi
imull %r9d, %edi
addl %ebp, %edi
addl %r14d, %edi
decl %r11d
imull %r9d, %r11d
incl %r11d
imull %eax, %r11d
subl %r9d, %r11d
cmpl %r11d, %edi
ja 0x5b48
imull %eax, %r10d
addl %ebx, %r10d
imull %r9d, %r10d
cmpl %r11d, %r10d
ja 0x5b48
movl 0x38(%rsp), %r11d
andl $0x1, %r8d
andl $0x1, %ecx
addl %ecx, %ecx
leal (%rcx,%r11,4), %ecx
orl %r8d, %ecx
cmpl $0x7, %ecx
ja 0x5b48
leaq 0x39f4(%rip), %r8       # 0x9270
movslq (%r8,%rcx,4), %rcx
addq %r8, %rcx
jmpq *%rcx
testl %r9d, %r9d
jle 0x5b48
subl %r9d, %eax
xorl %ecx, %ecx
movl %r9d, %r8d
movl %edi, %r11d
movb (%rsi,%r11), %r11b
movl %r10d, %ebx
movb %r11b, (%rdx,%rbx)
incl %edi
incl %r10d
decl %r8d
jne 0x5896
addl %eax, %edi
addl %eax, %r10d
incl %ecx
cmpl %r9d, %ecx
jne 0x5893
jmp 0x5b48
testl %r9d, %r9d
jle 0x5b48
subl %r9d, %eax
xorl %ecx, %ecx
movl %r9d, %r8d
movl %r10d, %r11d
movzbl (%rdx,%r11), %ebx
movl %edi, %r14d
movzbl (%rsi,%r14), %r14d
addl %r14d, %ebx
incl %ebx
shrl %ebx
movb %bl, (%rdx,%r11)
incl %edi
incl %r10d
decl %r8d
jne 0x58d0
addl %eax, %edi
addl %eax, %r10d
incl %ecx
cmpl %r9d, %ecx
jne 0x58cd
jmp 0x5b48
testl %r9d, %r9d
jle 0x5b48
subl %r9d, %eax
xorl %ecx, %ecx
movl %r9d, %r8d
movl %edi, %r11d
movzbl (%rsi,%r11), %r11d
incl %edi
movzbl (%rsi,%rdi), %ebx
addl %ebx, %r11d
incl %r11d
shrl %r11d
movl %r10d, %ebx
movb %r11b, (%rdx,%rbx)
incl %r10d
decl %r8d
jne 0x5917
addl %eax, %edi
addl %eax, %r10d
incl %ecx
cmpl %r9d, %ecx
jne 0x5914
jmp 0x5b48
testl %r9d, %r9d
jle 0x5b48
movl %eax, %ecx
subl %r9d, %ecx
xorl %r8d, %r8d
leal (%rax,%rdi), %ebx
xorl %r11d, %r11d
leal (%rdi,%r11), %r14d
leal (%r10,%r11), %r15d
movzbl (%rsi,%r14), %ebp
leal (%rdi,%r11), %r14d
incl %r14d
movzbl (%rsi,%r14), %r14d
addl %ebp, %r14d
leal (%rbx,%r11), %r12d
movzbl (%rsi,%r12), %r12d
addl %r14d, %r12d
leal (%rbx,%r11), %r14d
incl %r14d
movzbl (%rsi,%r14), %r14d
leal (%r14,%r12), %ebp
addl $0x2, %ebp
shrl $0x2, %ebp
movb %bpl, (%rdx,%r15)
incl %r11d
cmpl %r11d, %r9d
jne 0x5965
addl %ecx, %edi
addl %r11d, %edi
addl %ecx, %r10d
addl %r11d, %r10d
incl %r8d
cmpl %r9d, %r8d
jne 0x595f
jmp 0x5b48
testl %r9d, %r9d
jle 0x5b48
movl %eax, %ecx
subl %r9d, %ecx
xorl %r8d, %r8d
leal (%rax,%rdi), %ebx
xorl %r11d, %r11d
leal (%rdi,%r11), %r15d
leal (%r10,%r11), %r14d
movzbl (%rdx,%r14), %r12d
movzbl (%rsi,%r15), %ebp
leal (%rdi,%r11), %r15d
incl %r15d
movzbl (%rsi,%r15), %r15d
addl %ebp, %r15d
leal (%rbx,%r11), %r13d
movzbl (%rsi,%r13), %r13d
addl %r15d, %r13d
leal (%rbx,%r11), %r15d
incl %r15d
movzbl (%rsi,%r15), %r15d
addl %r13d, %r15d
addl $0x2, %r15d
shrl $0x2, %r15d
leal (%r12,%r15), %ebp
incl %ebp
shrl %ebp
movb %bpl, (%rdx,%r14)
incl %r11d
cmpl %r11d, %r9d
jne 0x59de
addl %ecx, %edi
addl %r11d, %edi
addl %ecx, %r10d
addl %r11d, %r10d
incl %r8d
cmpl %r9d, %r8d
jne 0x59d8
jmp 0x5b48
testl %r9d, %r9d
jle 0x5b48
movl %eax, %ecx
subl %r9d, %ecx
xorl %r8d, %r8d
movl %r9d, %r11d
movl %edi, %ebx
movzbl (%rsi,%rbx), %ebx
leal (%rax,%rdi), %r14d
movzbl (%rsi,%r14), %r14d
addl %r14d, %ebx
incl %ebx
shrl %ebx
movl %r10d, %r14d
movb %bl, (%rdx,%r14)
incl %edi
incl %r10d
decl %r11d
jne 0x5a62
addl %ecx, %edi
addl %ecx, %r10d
incl %r8d
cmpl %r9d, %r8d
jne 0x5a5f
jmp 0x5b48
testl %r9d, %r9d
jle 0x5b48
movl %eax, %ecx
subl %r9d, %ecx
xorl %r8d, %r8d
movl %r9d, %r11d
movl %r10d, %ebx
movzbl (%rdx,%rbx), %r14d
movl %edi, %r15d
movzbl (%rsi,%r15), %r15d
leal (%rax,%rdi), %r12d
movzbl (%rsi,%r12), %r12d
leal (%r15,%r12), %ebp
incl %ebp
shrl %ebp
movzbl %bpl, %r15d
leal (%r14,%r15), %ebp
incl %ebp
shrl %ebp
movb %bpl, (%rdx,%rbx)
incl %edi
incl %r10d
decl %r11d
jne 0x5aaf
addl %ecx, %edi
addl %ecx, %r10d
incl %r8d
cmpl %r9d, %r8d
jne 0x5aac
jmp 0x5b48
testl %r9d, %r9d
jle 0x5b48
subl %r9d, %eax
xorl %ecx, %ecx
movl %r9d, %r8d
movl %r10d, %r11d
movzbl (%rdx,%r11), %ebx
movl %edi, %r14d
movzbl (%rsi,%r14), %r14d
incl %edi
movzbl (%rsi,%rdi), %r15d
leal (%r14,%r15), %ebp
incl %ebp
shrl %ebp
movzbl %bpl, %r14d
addl %r14d, %ebx
incl %ebx
shrl %ebx
movb %bl, (%rdx,%r11)
incl %r10d
decl %r8d
jne 0x5b06
addl %eax, %edi
addl %eax, %r10d
incl %ecx
cmpl %r9d, %ecx
jne 0x5b03
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq