#define NULL ((void *)0)
typedef unsigned long size_t; // Customize by platform.
typedef long intptr_t;
typedef unsigned long uintptr_t;
typedef long scalar_t__; // Either arithmetic or pointer type.
/* By default, we understand bool (as a convenience). */
typedef int bool;
#define false 0
#define true 1

/* Forward declarations */

/* Type definitions */
typedef int uint8_t;
typedef scalar_t__ uint32_t;

/* Variables and functions */
int /*<<< orphan*/ memcpy(void *, int *, int);
void *parambinder_alloc(int);
void *pack_anary(void *f, void *arg) {
  static uint8_t template[16] = {0x68, 0, 0, 0, 0,    0xE8,
                                 0,    0, 0, 0, 0x5E, 0xC3};
  void *code = parambinder_alloc(16);
  if (code) {
    memcpy(code, template, 12);
    *(void **)((uint32_t)code + 1) = arg;
    *(uint32_t *)((uint32_t)code + 6) = (uint32_t)f - ((uint32_t)code + 6 + 4);
  }
  return code;
}


x86 assembly (clang, -O0):
<pack_anary>:
push   %rbp
mov    %rsp,%rbp
sub    $0x20,%rsp
mov    %rdi,-0x8(%rbp)
mov    %rsi,-0x10(%rbp)
mov    $0x10,%edi
call   1030 <parambinder_alloc@plt>
mov    %rax,-0x18(%rbp)
cmpq   $0x0,-0x18(%rbp)
je     1185 <pack_anary+0x65>
mov    -0x18(%rbp),%rdi
lea    0x2eec(%rip),%rsi
mov    $0xc,%edx
call   1040 <memcpy@plt>
mov    -0x10(%rbp),%rcx
mov    -0x18(%rbp),%rax
mov    %rcx,0x1(%rax)
mov    -0x8(%rbp),%rcx
mov    -0x18(%rbp),%rax
add    $0x6,%rax
add    $0x4,%rax
sub    %rax,%rcx
mov    -0x18(%rbp),%rax
mov    %rcx,0x6(%rax)
mov    -0x18(%rbp),%rax
add    $0x20,%rsp
pop    %rbp
ret

x86 assembly (clang, -O2):
<pack_anary>:
push   %r15
push   %r14
push   %rbx
mov    %rsi,%r15
mov    %rdi,%r14
mov    $0x10,%edi
call   1030 <parambinder_alloc@plt>
mov    %rax,%rbx
test   %rax,%rax
je     1160 <pack_anary+0x40>
lea    0x2efc(%rip),%rsi
mov    %rbx,%rdi
mov    $0xc,%edx
call   1040 <memcpy@plt>
mov    %r15,0x1(%rbx)
sub    %rbx,%r14
add    $0xfffffffffffffff6,%r14
mov    %r14,0x6(%rbx)
mov    %rbx,%rax
pop    %rbx
pop    %r14
pop    %r15
ret

LLVM IR (-O0):
@pack_anary.template = internal global [16 x i32] [i32 104, i32 0, i32 0, i32 0, i32 0, i32 232, i32 0, i32 0, i32 0, i32 0, i32 94, i32 195, i32 0, i32 0, i32 0, i32 0]
define i8* @pack_anary(i8* %0, i8* %1) {
%3 = alloca i8*
%4 = alloca i8*
%5 = alloca i8*
store i8* %0, i8** %3
store i8* %1, i8** %4
%6 = call i8* @parambinder_alloc(i32 16)
store i8* %6, i8** %5
%7 = load i8*, i8** %5
%8 = icmp ne i8* %7, null
br i1 %8, label %9, label %28
9: ; preds = %2
%10 = load i8*, i8** %5
%11 = call i32 @memcpy(i8* %10, i32* getelementptr inbounds ([16 x i32], [16 x i32]* @pack_anary.template, i64 0, i64 0), i32 12)
%12 = load i8*, i8** %4
%13 = load i8*, i8** %5
%14 = ptrtoint i8* %13 to i64
%15 = add nsw i64 %14, 1
%16 = inttoptr i64 %15 to i8**
store i8* %12, i8** %16
%17 = load i8*, i8** %3
%18 = ptrtoint i8* %17 to i64
%19 = load i8*, i8** %5
%20 = ptrtoint i8* %19 to i64
%21 = add nsw i64 %20, 6
%22 = add nsw i64 %21, 4
%23 = sub nsw i64 %18, %22
%24 = load i8*, i8** %5
%25 = ptrtoint i8* %24 to i64
%26 = add nsw i64 %25, 6
%27 = inttoptr i64 %26 to i64*
store i64 %23, i64* %27
br label %28
28: ; preds = %9, %2
%29 = load i8*, i8** %5
ret i8* %29
}

LLVM IR (-O2):
@pack_anary.template = internal global [16 x i32] [i32 104, i32 0, i32 0, i32 0, i32 0, i32 232, i32 0, i32 0, i32 0, i32 0, i32 94, i32 195, i32 0, i32 0, i32 0, i32 0]
define i8* @pack_anary(i8* %0, i8* %1) {
%3 = tail call i8* @parambinder_alloc(i32 16)
%4 = icmp eq i8* %3, null
br i1 %4, label %15, label %5
5: ; preds = %2
%6 = tail call i32 @memcpy(i8* %3, i32* getelementptr inbounds ([16 x i32], [16 x i32]* @pack_anary.template, i64 0, i64 0), i32 12)
%7 = ptrtoint i8* %3 to i64
%8 = add nsw i64 %7, 1
%9 = inttoptr i64 %8 to i8**
store i8* %1, i8** %9
%10 = ptrtoint i8* %0 to i64
%11 = add nsw i64 %7, 6
%12 = add i64 %10, -10
%13 = sub i64 %12, %7
%14 = inttoptr i64 %11 to i64*
store i64 %13, i64* %14
br label %15
15: ; preds = %5, %2
ret i8* %3
}