// File: /workspace/github_cpp_makefile_star2_O2/cloudinary[P]fuif/transform/dct.h
// Function: inv_DCT(Image&, std::vector<int, std::allocator<int>>&)
bool inv_DCT(Image &input, std::vector<int> &parameters) {
    if (!parameters.size()) default_DCT_parameters(parameters,input);
    int beginc = input.nb_meta_channels + parameters[0];
    int endc = input.nb_meta_channels + parameters[1];
    int nb_channels = endc-beginc+1;
    int offset = input.channel.size() - 63*nb_channels;

    if (offset <= endc) {
        e_printf("Invalid number of channels to apply inverse DCT.\n");
        return false;
    }
    v_printf(3,"Undoing DCT on channels %i..%i with AC coefficients in channels %i..%i\n",beginc,endc,offset,offset+63*nb_channels-1);


    std::vector<std::vector<int>> ordering;
    std::vector<int> comp;
    std::vector<int> coeff;
    default_DCT_scanscript(nb_channels,ordering,comp,coeff);

    for (int c=beginc; c<=endc; c++) {
        int bw = input.channel[c-beginc+offset].w; // consider first AC, in case we did repeated DCT (TODO: try repeated DCT to see if it even makes sense)
        int bh = input.channel[c-beginc+offset].h;
        if (input.channel[c].w < bw) bw = input.channel[c].w;
        if (input.channel[c].h < bh) bh = input.channel[c].h;

        v_printf(3,"  Channel %i : %ix%i image from %ix%i blocks\n",c,bw*8,bh*8,bw,bh);
        Channel outch(bw*8,bh*8,0,0);
        outch.component = input.channel[c].component;
        outch.hshift = input.channel[c].hshift - 3;
        outch.vshift = input.channel[c].vshift - 3;
        outch.hcshift = input.channel[c].hcshift - 3;
        outch.vcshift = input.channel[c].hcshift - 3;
        float DCoffset = (input.maxval + 1.0) * 4.0;
        for (int by=0; by<bh; by++) {
          for (int bx=0; bx<bw; bx++) {
            double block[64];
            block[0] = input.channel[c].value(by,bx) + DCoffset;
            for (int i=1; i<64; i++) block[i] = input.channel[offset-nb_channels+ ordering[c-beginc][jpeg_zigzag[i]]].value(by,bx);
            ComputeBlockIDCTDouble(block);
            for (int y=0; y<8; y++)
            for (int x=0; x<8; x++) outch.value(by*8+y, bx*8+x) = round(block[y*8+x]);
          }
        }
        input.channel[c] = outch;
    }
    input.channel.erase(input.channel.begin()+offset,input.channel.begin()+offset+nb_channels*63);
    return true;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x338, %rsp            # imm = 0x338
movq %rdi, %r15
movq (%rsi), %rcx
cmpq %rcx, 0x8(%rsi)
jne 0x653c
movq %rsi, %rbx
movq %rsi, %rdi
movq %r15, %rsi
callq 0x62ba
movq (%rbx), %rcx
movl 0x6c(%r15), %eax
movl (%rcx), %ebx
movl 0x4(%rcx), %r14d
leal (%r14,%rax), %r12d
subl %ebx, %r14d
leal 0x1(%r14), %ebp
movq 0x8(%r15), %r9
movq %r15, 0x28(%rsp)
subq (%r15), %r9
shrq $0x6, %r9
imull $0x3f, %ebp, %r15d
movl %r9d, %r13d
subl %r15d, %r13d
cmpl %r12d, %r13d
movl %r12d, 0x18(%rsp)
movl %r13d, 0x14(%rsp)
jle 0x68c0
addl %eax, %ebx
decl %r9d
leaq 0x172db(%rip), %rsi     # 0x1d865
pushq $0x3
popq %rdi
movl %ebx, %edx
movl %r12d, %ecx
movl %r13d, %r8d
xorl %eax, %eax
callq 0x16c30
leaq 0x90(%rsp), %rsi
andq $0x0, 0x10(%rsi)
xorps %xmm0, %xmm0
movaps %xmm0, (%rsi)
leaq 0xd0(%rsp), %rdx
movaps %xmm0, (%rdx)
andq $0x0, 0x10(%rdx)
leaq 0xb0(%rsp), %rcx
movaps %xmm0, (%rcx)
andq $0x0, 0x10(%rcx)
movl %ebp, %edi
callq 0x612f
movslq %r15d, %rax
movq %rax, 0x30(%rsp)
notl %r14d
addl %r13d, %r14d
movslq %ebx, %rcx
movslq %r12d, %rax
movq %rax, 0x40(%rsp)
movslq %r13d, %rax
shlq $0x6, %rax
movq %rax, 0x20(%rsp)
leaq 0xf0(%rsp), %r12
movslq %r14d, %rax
movq %rax, 0x70(%rsp)
movq %rcx, 0x38(%rsp)
movq %rcx, %rdx
movq 0x28(%rsp), %rbx
cmpq 0x40(%rsp), %rdx
jg 0x68d0
movq %rdx, %rcx
subq 0x38(%rsp), %rcx
movq (%rbx), %rax
movq %rcx, 0x78(%rsp)
shlq $0x6, %rcx
addq %rax, %rcx
movq 0x20(%rsp), %rsi
movl 0x18(%rsi,%rcx), %r9d
movl 0x1c(%rsi,%rcx), %r10d
movq %rdx, %rsi
shlq $0x6, %rsi
movl 0x18(%rax,%rsi), %ecx
movq %rsi, 0x8(%rsp)
movl 0x1c(%rax,%rsi), %eax
cmpl %r9d, %ecx
cmovll %ecx, %r9d
cmpl %r10d, %eax
cmovll %eax, %r10d
leal (,%r9,8), %ebp
leal (,%r10,8), %r15d
subq $0x8, %rsp
pushq $0x3
popq %rdi
leaq 0x17224(%rip), %rsi     # 0x1d8ad
movq %rdx, 0x50(%rsp)
movl %ebp, %ecx
movl %r15d, %r8d
movq %r9, %r14
xorl %eax, %eax
movq %r10, %r13
pushq %r10
callq 0x16c30
popq %rax
popq %rcx
movq %r12, %rdi
movl %ebp, %esi
movl %r15d, %edx
xorl %ecx, %ecx
xorl %r8d, %r8d
pushq $0x1
popq %r9
pushq $0x0
pushq $0x0
pushq $0x0
pushq $0x0
callq 0xa470
addq $0x20, %rsp
movq (%rbx), %rax
movq 0x8(%rsp), %rdx
movl 0x3c(%rax,%rdx), %ecx
movl %ecx, 0x12c(%rsp)
movq 0x2c(%rax,%rdx), %xmm0
paddd 0x16fb9(%rip), %xmm0    # 0x1d6a0
movq %xmm0, 0x11c(%rsp)
movl 0x34(%rax,%rdx), %ecx
addl $-0x3, %ecx
movl %ecx, 0x124(%rsp)
movl 0x34(%rax,%rdx), %eax
addl $-0x3, %eax
movl %eax, 0x128(%rsp)
cvtsi2sdl 0x60(%rbx), %xmm0
addsd 0x16acf(%rip), %xmm0    # 0x1d1e8
mulsd 0x16acf(%rip), %xmm0    # 0x1d1f0
cvtsd2ss %xmm0, %xmm0
movss %xmm0, 0x1c(%rsp)
testl %r14d, %r14d
movl $0x0, %eax
cmovlel %eax, %r14d
movq %r14, 0x60(%rsp)
testl %r13d, %r13d
cmovlel %eax, %r13d
movq %r13, 0x50(%rsp)
xorl %r15d, %r15d
cmpq 0x50(%rsp), %r15
je 0x689b
leaq (,%r15,8), %rax
movq %rax, 0x80(%rsp)
xorl %r13d, %r13d
movq %r15, 0x58(%rsp)
cmpq 0x60(%rsp), %r13
je 0x6893
movq (%rbx), %rdi
addq 0x8(%rsp), %rdi
movl %r15d, %esi
movl %r13d, %edx
callq 0xa44a
movswl (%rax), %eax
cvtsi2ss %eax, %xmm0
addss 0x1c(%rsp), %xmm0
cvtss2sd %xmm0, %xmm0
movsd %xmm0, 0x130(%rsp)
pushq $0x1
popq %r14
cmpq $0x40, %r14
je 0x67fe
movq 0x90(%rsp), %rax
imulq $0x18, 0x78(%rsp), %rcx
leaq 0x16cab(%rip), %rdx     # 0x1d470
movslq (%rdx,%r14,4), %rdx
movq (%rax,%rcx), %rax
movslq (%rax,%rdx,4), %rdi
addq 0x70(%rsp), %rdi
shlq $0x6, %rdi
addq (%rbx), %rdi
movl %r15d, %esi
movl %r13d, %edx
callq 0xa44a
movswl (%rax), %eax
cvtsi2sd %eax, %xmm0
movsd %xmm0, 0x130(%rsp,%r14,8)
incq %r14
jmp 0x67aa
leaq 0x130(%rsp), %rbx
movq %rbx, %rdi
callq 0x6123
movq %r13, 0x68(%rsp)
leaq (,%r13,8), %r14
movq %rbx, %rbp
xorl %eax, %eax
cmpq $0x8, %rax
je 0x687c
movq %rax, 0x88(%rsp)
movl %eax, %r15d
orl 0x80(%rsp), %r15d
xorl %r13d, %r13d
cmpq $0x8, %r13
je 0x686b
movsd (%rbp,%r13,8), %xmm0
callq 0x3150
cvttsd2si %xmm0, %ebx
movl %r13d, %edx
orl %r14d, %edx
movq %r12, %rdi
movl %r15d, %esi
callq 0xa44a
movw %bx, (%rax)
incq %r13
jmp 0x683c
movq 0x88(%rsp), %rax
incq %rax
addq $0x40, %rbp
jmp 0x6820
movq 0x68(%rsp), %r13
incq %r13
movq 0x28(%rsp), %rbx
movq 0x58(%rsp), %r15
jmp 0x676e
incq %r15
jmp 0x674b
movq 0x8(%rsp), %rdi
addq (%rbx), %rdi
movq %r12, %rsi
callq 0xa526
movq %r12, %rdi
callq 0xabc2
movq 0x48(%rsp), %rdx
incq %rdx
jmp 0x6618
leaq 0x16f6c(%rip), %rdi     # 0x1d833
xorl %eax, %eax
callq 0x16b80
jmp 0x6913
movq 0x20(%rsp), %rsi
addq (%rbx), %rsi
movq 0x30(%rsp), %rdx
shlq $0x6, %rdx
addq %rsi, %rdx
movq %rbx, %rdi
callq 0xa676
leaq 0xb0(%rsp), %rdi
callq 0x5374
leaq 0xd0(%rsp), %rdi
callq 0x5374
leaq 0x90(%rsp), %rdi
callq 0xa654
movl 0x14(%rsp), %eax
cmpl 0x18(%rsp), %eax
setg %al
addq $0x338, %rsp            # imm = 0x338
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
jmp 0x6938
jmp 0x6938
jmp 0x693d
jmp 0x6938
movq %rax, %rbx
jmp 0x694d
movq %rax, %rbx
leaq 0xf0(%rsp), %rdi
callq 0xabc2
leaq 0xb0(%rsp), %rdi
callq 0x5374
leaq 0xd0(%rsp), %rdi
callq 0x5374
leaq 0x90(%rsp), %rdi
callq 0xa654
movq %rbx, %rdi
callq 0x35d0