long call_with_5_arg(int (*func)(), int argc, char **argv) {
  long ret;
  __asm__ __volatile__("movq %6,%%r8\n\t"
                       "movq %5,%%rcx\n\t"
                       "movq %4,%%rdx\n\t"
                       "movq %3,%%rsi\n\t"
                       "movq %2,%%rdi\n\t"
                       "xor %%rax,%%rax\n\t"
                       "call *%1\n\t"
                       "movq %%rax, %0"
                       : "=r"(ret)
                       : "r"(func), "m"(argv[3]), "m"(argv[4]), "m"(argv[5]),
                         "m"(argv[6]), "m"(argv[7])
                       : "rax", "rcx", "rdx", "rsi", "rdi", "r8");
  return ret;
}


x86 assembly (clang, -O0):
<call_with_5_arg>:
push   %rbp
mov    %rsp,%rbp
push   %r15
push   %r14
push   %rbx
mov    %rdi,-0x20(%rbp)
mov    %esi,-0x24(%rbp)
mov    %rdx,-0x30(%rbp)
mov    -0x20(%rbp),%r9
mov    -0x30(%rbp),%r10
add    $0x18,%r10
mov    -0x30(%rbp),%r11
add    $0x20,%r11
mov    -0x30(%rbp),%rbx
add    $0x28,%rbx
mov    -0x30(%rbp),%r14
add    $0x30,%r14
mov    -0x30(%rbp),%r15
add    $0x38,%r15
mov    (%r15),%r8
mov    (%r14),%rcx
mov    (%rbx),%rdx
mov    (%r11),%rsi
mov    (%r10),%rdi
xor    %rax,%rax
call   *%r9
mov    %rax,%r9
mov    %r9,-0x40(%rbp)
mov    -0x40(%rbp),%rax
mov    %rax,-0x38(%rbp)
mov    -0x38(%rbp),%rax
pop    %rbx
pop    %r14
pop    %r15
pop    %rbp
ret

x86 assembly (clang, -O2):
<call_with_5_arg>:
mov    %rdx,%r9
mov    %rdi,%r10
mov    0x38(%r9),%r8
mov    0x30(%r9),%rcx
mov    0x28(%r9),%rdx
mov    0x20(%r9),%rsi
mov    0x18(%r9),%rdi
xor    %rax,%rax
call   *%r10
mov    %rax,%r9
mov    %r9,%rax
ret

LLVM IR (-O0):
define i64 @call_with_5_arg(i32 (...)* %0, i32 %1, i8** %2) {
%4 = alloca i32 (...)*
%5 = alloca i32
%6 = alloca i8**
%7 = alloca i64
store i32 (...)* %0, i32 (...)** %4
store i32 %1, i32* %5
store i8** %2, i8*** %6
%8 = load i32 (...)*, i32 (...)** %4
%9 = load i8**, i8*** %6
%10 = getelementptr inbounds i8*, i8** %9, i64 3
%11 = load i8**, i8*** %6
%12 = getelementptr inbounds i8*, i8** %11, i64 4
%13 = load i8**, i8*** %6
%14 = getelementptr inbounds i8*, i8** %13, i64 5
%15 = load i8**, i8*** %6
%16 = getelementptr inbounds i8*, i8** %15, i64 6
%17 = load i8**, i8*** %6
%18 = getelementptr inbounds i8*, i8** %17, i64 7
%19 = call i64 asm sideeffect "movq $6,%r8\0A\09movq $5,%rcx\0A\09movq $4,%rdx\0A\09movq $3,%rsi\0A\09movq $2,%rdi\0A\09xor %rax,%rax\0A\09call *$1\0A\09movq %rax, $0", "=r,r,*m,*m,*m,*m,*m,~{rax},~{rcx},~{rdx},~{rsi},~{rdi},~{r8},~{dirflag},~{fpsr},~{flags}"(i32 (...)* %8, i8** elementtype(i8*) %10, i8** elementtype(i8*) %12, i8** elementtype(i8*) %14, i8** elementtype(i8*) %16, i8** elementtype(i8*) %18)
store i64 %19, i64* %7
%20 = load i64, i64* %7
ret i64 %20
}

LLVM IR (-O2):
define i64 @call_with_5_arg(i32 (...)* %0, i32 %1, i8** %2) {
%4 = getelementptr inbounds i8*, i8** %2, i64 3
%5 = getelementptr inbounds i8*, i8** %2, i64 4
%6 = getelementptr inbounds i8*, i8** %2, i64 5
%7 = getelementptr inbounds i8*, i8** %2, i64 6
%8 = getelementptr inbounds i8*, i8** %2, i64 7
%9 = tail call i64 asm sideeffect "movq $6,%r8\0A\09movq $5,%rcx\0A\09movq $4,%rdx\0A\09movq $3,%rsi\0A\09movq $2,%rdi\0A\09xor %rax,%rax\0A\09call *$1\0A\09movq %rax, $0", "=r,r,*m,*m,*m,*m,*m,~{rax},~{rcx},~{rdx},~{rsi},~{rdi},~{r8},~{dirflag},~{fpsr},~{flags}"(i32 (...)* %0, i8** elementtype(i8*) %4, i8** elementtype(i8*) %5, i8** elementtype(i8*) %6, i8** elementtype(i8*) %7, i8** elementtype(i8*) %8)
ret i64 %9
}