// File: lukasz-wiecaszek[P]h264iframedecoder/picture.cpp
// Function: ymn::h264::picture::calculate_neighbours_part1()
void picture::calculate_neighbours_part1()
{
    int y = m_context_variables.mb_y;
    int n = m_context_variables.mb_pos;
    int mb_width = m_decoder.m_dimensions.mb_width;
    mb& mb = m_mbs[n];

    if (m_context_variables.mb_aff_frame) {
        int shift = y & 1 ? 3 * mb_width : 2 * mb_width;

        mb.A = (n % mb_width) ? get_mb(n - 1 - (y & 1) * mb_width) : nullptr;
        mb.B = get_mb(n - shift);
        mb.C = ((n + 1) % mb_width) ? get_mb(n - shift + 1) : nullptr;
        mb.D = (n % mb_width) ? get_mb(n - shift - 1) : nullptr;
    }
    else {
        if (m_picture_structure == picture_structure_e::frame) {
            mb.A = (n % mb_width) ? get_mb(n - 1) : nullptr;
            mb.B = get_mb(n - mb_width);
            mb.C = ((n + 1) % mb_width) ? get_mb(n - mb_width + 1) : nullptr;
            mb.D = (n % mb_width) ? get_mb(n - mb_width - 1) : nullptr;
        }
        else {
            int shift = 2 * mb_width;

            mb.A = (n % mb_width) ? get_mb(n - 1) : nullptr;
            mb.B = get_mb(n - shift);
            mb.C = ((n + 1) % mb_width) ? get_mb(n - shift + 1) : nullptr;
            mb.D = (n % mb_width) ? get_mb(n - shift - 1) : nullptr;
        }
    }

    /* To calculate left and top references it is necessary to know
    whether the current macroblock is a frame or field macroblock.
    This is why left and top references will be calculated later (in part2)
    when current macroblock frame/field status is already known. */
    mb.left = nullptr;
    mb.left_pair[0] = nullptr;
    mb.left_pair[1] = nullptr;
    mb.top = nullptr;
}

// Assembly:
subq $0x88, %rsp
movq %rdi, 0x80(%rsp)
movq 0x80(%rsp), %rax
movq %rax, 0x58(%rsp)
movl 0x20(%rax), %ecx
movl %ecx, 0x7c(%rsp)
movl 0x24(%rax), %ecx
movl %ecx, 0x78(%rsp)
movq 0x8(%rax), %rcx
movl 0x88340(%rcx), %ecx
movl %ecx, 0x74(%rsp)
movq 0xdb8(%rax), %rcx
movslq 0x78(%rsp), %rdx
imulq $0xb0, %rdx, %rdx
addq %rdx, %rcx
movq %rcx, 0x68(%rsp)
testb $0x1, 0x18(%rax)
je 0x1d0b9
movl 0x7c(%rsp), %eax
andl $0x1, %eax
cmpl $0x0, %eax
je 0x1cfb4
imull $0x3, 0x74(%rsp), %eax
movl %eax, 0x54(%rsp)
jmp 0x1cfbe
movl 0x74(%rsp), %eax
shll %eax
movl %eax, 0x54(%rsp)
movl 0x54(%rsp), %eax
movl %eax, 0x64(%rsp)
movl 0x78(%rsp), %eax
cltd
idivl 0x74(%rsp)
cmpl $0x0, %edx
je 0x1cffa
movq 0x58(%rsp), %rdi
movl 0x78(%rsp), %esi
subl $0x1, %esi
movl 0x7c(%rsp), %eax
andl $0x1, %eax
imull 0x74(%rsp), %eax
subl %eax, %esi
callq 0x1d800
movq %rax, 0x48(%rsp)
jmp 0x1d003
xorl %eax, %eax
movq %rax, 0x48(%rsp)
jmp 0x1d003
movq 0x58(%rsp), %rdi
movq 0x48(%rsp), %rcx
movq 0x68(%rsp), %rax
movq %rcx, 0x18(%rax)
movl 0x78(%rsp), %esi
subl 0x64(%rsp), %esi
callq 0x1d800
movq %rax, %rcx
movq 0x68(%rsp), %rax
movq %rcx, 0x20(%rax)
movl 0x78(%rsp), %eax
addl $0x1, %eax
cltd
idivl 0x74(%rsp)
cmpl $0x0, %edx
je 0x1d05c
movq 0x58(%rsp), %rdi
movl 0x78(%rsp), %esi
subl 0x64(%rsp), %esi
addl $0x1, %esi
callq 0x1d800
movq %rax, 0x40(%rsp)
jmp 0x1d065
xorl %eax, %eax
movq %rax, 0x40(%rsp)
jmp 0x1d065
movq 0x40(%rsp), %rcx
movq 0x68(%rsp), %rax
movq %rcx, 0x28(%rax)
movl 0x78(%rsp), %eax
cltd
idivl 0x74(%rsp)
cmpl $0x0, %edx
je 0x1d09d
movq 0x58(%rsp), %rdi
movl 0x78(%rsp), %esi
subl 0x64(%rsp), %esi
subl $0x1, %esi
callq 0x1d800
movq %rax, 0x38(%rsp)
jmp 0x1d0a6
xorl %eax, %eax
movq %rax, 0x38(%rsp)
jmp 0x1d0a6
movq 0x38(%rsp), %rcx
movq 0x68(%rsp), %rax
movq %rcx, 0x30(%rax)
jmp 0x1d299
movq 0x58(%rsp), %rax
cmpl $0x0, 0x10(%rax)
jne 0x1d1ad
movl 0x78(%rsp), %eax
cltd
idivl 0x74(%rsp)
cmpl $0x0, %edx
je 0x1d0ee
movq 0x58(%rsp), %rdi
movl 0x78(%rsp), %esi
subl $0x1, %esi
callq 0x1d800
movq %rax, 0x30(%rsp)
jmp 0x1d0f7
xorl %eax, %eax
movq %rax, 0x30(%rsp)
jmp 0x1d0f7
movq 0x58(%rsp), %rdi
movq 0x30(%rsp), %rcx
movq 0x68(%rsp), %rax
movq %rcx, 0x18(%rax)
movl 0x78(%rsp), %esi
subl 0x74(%rsp), %esi
callq 0x1d800
movq %rax, %rcx
movq 0x68(%rsp), %rax
movq %rcx, 0x20(%rax)
movl 0x78(%rsp), %eax
addl $0x1, %eax
cltd
idivl 0x74(%rsp)
cmpl $0x0, %edx
je 0x1d150
movq 0x58(%rsp), %rdi
movl 0x78(%rsp), %esi
subl 0x74(%rsp), %esi
addl $0x1, %esi
callq 0x1d800
movq %rax, 0x28(%rsp)
jmp 0x1d159
xorl %eax, %eax
movq %rax, 0x28(%rsp)
jmp 0x1d159
movq 0x28(%rsp), %rcx
movq 0x68(%rsp), %rax
movq %rcx, 0x28(%rax)
movl 0x78(%rsp), %eax
cltd
idivl 0x74(%rsp)
cmpl $0x0, %edx
je 0x1d191
movq 0x58(%rsp), %rdi
movl 0x78(%rsp), %esi
subl 0x74(%rsp), %esi
subl $0x1, %esi
callq 0x1d800
movq %rax, 0x20(%rsp)
jmp 0x1d19a
xorl %eax, %eax
movq %rax, 0x20(%rsp)
jmp 0x1d19a
movq 0x20(%rsp), %rcx
movq 0x68(%rsp), %rax
movq %rcx, 0x30(%rax)
jmp 0x1d297
movl 0x74(%rsp), %eax
shll %eax
movl %eax, 0x60(%rsp)
movl 0x78(%rsp), %eax
cltd
idivl 0x74(%rsp)
cmpl $0x0, %edx
je 0x1d1dd
movq 0x58(%rsp), %rdi
movl 0x78(%rsp), %esi
subl $0x1, %esi
callq 0x1d800
movq %rax, 0x18(%rsp)
jmp 0x1d1e6
xorl %eax, %eax
movq %rax, 0x18(%rsp)
jmp 0x1d1e6
movq 0x58(%rsp), %rdi
movq 0x18(%rsp), %rcx
movq 0x68(%rsp), %rax
movq %rcx, 0x18(%rax)
movl 0x78(%rsp), %esi
subl 0x60(%rsp), %esi
callq 0x1d800
movq %rax, %rcx
movq 0x68(%rsp), %rax
movq %rcx, 0x20(%rax)
movl 0x78(%rsp), %eax
addl $0x1, %eax
cltd
idivl 0x74(%rsp)
cmpl $0x0, %edx
je 0x1d23f
movq 0x58(%rsp), %rdi
movl 0x78(%rsp), %esi
subl 0x60(%rsp), %esi
addl $0x1, %esi
callq 0x1d800
movq %rax, 0x10(%rsp)
jmp 0x1d248
xorl %eax, %eax
movq %rax, 0x10(%rsp)
jmp 0x1d248
movq 0x10(%rsp), %rcx
movq 0x68(%rsp), %rax
movq %rcx, 0x28(%rax)
movl 0x78(%rsp), %eax
cltd
idivl 0x74(%rsp)
cmpl $0x0, %edx
je 0x1d280
movq 0x58(%rsp), %rdi
movl 0x78(%rsp), %esi
subl 0x60(%rsp), %esi
subl $0x1, %esi
callq 0x1d800
movq %rax, 0x8(%rsp)
jmp 0x1d289
xorl %eax, %eax
movq %rax, 0x8(%rsp)
jmp 0x1d289
movq 0x8(%rsp), %rcx
movq 0x68(%rsp), %rax
movq %rcx, 0x30(%rax)
jmp 0x1d299
movq 0x68(%rsp), %rax
movq $0x0, 0x38(%rax)
movq 0x68(%rsp), %rax
movq $0x0, 0x40(%rax)
movq 0x68(%rsp), %rax
movq $0x0, 0x48(%rax)
movq 0x68(%rsp), %rax
movq $0x0, 0x50(%rax)
addq $0x88, %rsp
retq
nopw %cs:(%rax,%rax)