#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 */

/* Variables and functions */
int /*<<< orphan*/ PrintArray(int *, int);
int /*<<< orphan*/ free(int *);
scalar_t__ malloc(int);
int /*<<< orphan*/ memcpy(int *, int *, int);
int /*<<< orphan*/ printf(char *);
void merge(int a[], int p, int q, int r) {
  int nLeft = q - p + 1;
  int nRight = r - q;
  int *L = (int *)malloc(sizeof(int) * nLeft);
  int *R = (int *)malloc(sizeof(int) * nRight);
  memcpy(L, a + p, nLeft * sizeof(int));
  memcpy(R, a + q + 1, nRight * sizeof(int));
  printf("Left: \n");
  PrintArray(L, nLeft);
  printf("Right: \n");
  PrintArray(R, nRight);
  int i = 0;
  int j = 0;
  int k = p;
  while (i < nLeft && j < nRight) {
    if (L[i] <= R[j]) {
      a[k++] = L[i++];
    } else {
      a[k++] = R[j++];
    }
  }
  while (i < nLeft) {
    a[k++] = L[i++];
  }
  while (j < nRight) {
    a[k++] = R[j++];
  }
  printf("After merge: \n");
  PrintArray(a, r - p + 1);
  free(L);
  free(R);
}


x86 assembly (clang, -O0):
<merge>:
push   %rbp
mov    %rsp,%rbp
sub    $0x40,%rsp
mov    %rdi,-0x8(%rbp)
mov    %esi,-0xc(%rbp)
mov    %edx,-0x10(%rbp)
mov    %ecx,-0x14(%rbp)
mov    -0x10(%rbp),%eax
sub    -0xc(%rbp),%eax
add    $0x1,%eax
mov    %eax,-0x18(%rbp)
mov    -0x14(%rbp),%eax
sub    -0x10(%rbp),%eax
mov    %eax,-0x1c(%rbp)
movslq -0x18(%rbp),%rax
shl    $0x2,%rax
mov    %eax,%edi
call   1060 <malloc@plt>
mov    %rax,-0x28(%rbp)
movslq -0x1c(%rbp),%rax
shl    $0x2,%rax
mov    %eax,%edi
call   1060 <malloc@plt>
mov    %rax,-0x30(%rbp)
mov    -0x28(%rbp),%rdi
mov    -0x8(%rbp),%rsi
movslq -0xc(%rbp),%rax
shl    $0x2,%rax
add    %rax,%rsi
movslq -0x18(%rbp),%rax
shl    $0x2,%rax
mov    %eax,%edx
call   1050 <memcpy@plt>
mov    -0x30(%rbp),%rdi
mov    -0x8(%rbp),%rsi
movslq -0x10(%rbp),%rax
shl    $0x2,%rax
add    %rax,%rsi
add    $0x4,%rsi
movslq -0x1c(%rbp),%rax
shl    $0x2,%rax
mov    %eax,%edx
call   1050 <memcpy@plt>
lea    0xe11(%rip),%rdi
call   1040 <printf@plt>
mov    -0x28(%rbp),%rdi
mov    -0x18(%rbp),%esi
call   1070 <PrintArray@plt>
lea    0xe01(%rip),%rdi
call   1040 <printf@plt>
mov    -0x30(%rbp),%rdi
mov    -0x1c(%rbp),%esi
call   1070 <PrintArray@plt>
movl   $0x0,-0x34(%rbp)
movl   $0x0,-0x38(%rbp)
mov    -0xc(%rbp),%eax
mov    %eax,-0x3c(%rbp)
mov    -0x34(%rbp),%ecx
xor    %eax,%eax
cmp    -0x18(%rbp),%ecx
mov    %al,-0x3d(%rbp)
jge    1249 <merge+0xf9>
mov    -0x38(%rbp),%eax
cmp    -0x1c(%rbp),%eax
setl   %al
mov    %al,-0x3d(%rbp)
mov    -0x3d(%rbp),%al
test   $0x1,%al
jne    1259 <merge+0x109>
jmp    12d3 <merge+0x183>
mov    -0x28(%rbp),%rax
movslq -0x34(%rbp),%rcx
mov    (%rax,%rcx,4),%eax
mov    -0x30(%rbp),%rcx
movslq -0x38(%rbp),%rdx
cmp    (%rcx,%rdx,4),%eax
jg     12a4 <merge+0x154>
mov    -0x28(%rbp),%rax
mov    -0x34(%rbp),%ecx
mov    %ecx,%edx
add    $0x1,%edx
mov    %edx,-0x34(%rbp)
movslq %ecx,%rcx
mov    (%rax,%rcx,4),%edx
mov    -0x8(%rbp),%rax
mov    -0x3c(%rbp),%ecx
mov    %ecx,%esi
add    $0x1,%esi
mov    %esi,-0x3c(%rbp)
movslq %ecx,%rcx
mov    %edx,(%rax,%rcx,4)
jmp    12ce <merge+0x17e>
mov    -0x30(%rbp),%rax
mov    -0x38(%rbp),%ecx
mov    %ecx,%edx
add    $0x1,%edx
mov    %edx,-0x38(%rbp)
movslq %ecx,%rcx
mov    (%rax,%rcx,4),%edx
mov    -0x8(%rbp),%rax
mov    -0x3c(%rbp),%ecx
mov    %ecx,%esi
add    $0x1,%esi
mov    %esi,-0x3c(%rbp)
movslq %ecx,%rcx
mov    %edx,(%rax,%rcx,4)
jmp    122c <merge+0xdc>
jmp    12d8 <merge+0x188>
mov    -0x34(%rbp),%eax
cmp    -0x18(%rbp),%eax
jge    1313 <merge+0x1c3>
mov    -0x28(%rbp),%rax
mov    -0x34(%rbp),%ecx
mov    %ecx,%edx
add    $0x1,%edx
mov    %edx,-0x34(%rbp)
movslq %ecx,%rcx
mov    (%rax,%rcx,4),%edx
mov    -0x8(%rbp),%rax
mov    -0x3c(%rbp),%ecx
mov    %ecx,%esi
add    $0x1,%esi
mov    %esi,-0x3c(%rbp)
movslq %ecx,%rcx
mov    %edx,(%rax,%rcx,4)
jmp    12d8 <merge+0x188>
jmp    1318 <merge+0x1c8>
mov    -0x38(%rbp),%eax
cmp    -0x1c(%rbp),%eax
jge    1353 <merge+0x203>
mov    -0x30(%rbp),%rax
mov    -0x38(%rbp),%ecx
mov    %ecx,%edx
add    $0x1,%edx
mov    %edx,-0x38(%rbp)
movslq %ecx,%rcx
mov    (%rax,%rcx,4),%edx
mov    -0x8(%rbp),%rax
mov    -0x3c(%rbp),%ecx
mov    %ecx,%esi
add    $0x1,%esi
mov    %esi,-0x3c(%rbp)
movslq %ecx,%rcx
mov    %edx,(%rax,%rcx,4)
jmp    1318 <merge+0x1c8>
lea    0xcb7(%rip),%rdi
call   1040 <printf@plt>
mov    -0x8(%rbp),%rdi
mov    -0x14(%rbp),%esi
sub    -0xc(%rbp),%esi
add    $0x1,%esi
call   1070 <PrintArray@plt>
mov    -0x28(%rbp),%rdi
call   1030 <free@plt>
mov    -0x30(%rbp),%rdi
call   1030 <free@plt>
add    $0x40,%rsp
pop    %rbp
ret

x86 assembly (clang, -O2):
<merge>:
push   %rbp
push   %r15
push   %r14
push   %r13
push   %r12
push   %rbx
sub    $0x28,%rsp
mov    %edx,%ebx
mov    %esi,%ebp
mov    %rdi,%r14
mov    %edx,%r13d
sub    %esi,%r13d
lea    0x1(%r13),%eax
mov    %eax,0x1c(%rsp)
mov    %ecx,0x8(%rsp)
mov    %ecx,%r15d
sub    %edx,%r15d
lea    0x4(,%r13,4),%edi
mov    %edi,0x10(%rsp)
call   1060 <malloc@plt>
mov    %rax,(%rsp)
lea    0x0(,%r15,4),%edi
mov    %edi,0x18(%rsp)
call   1060 <malloc@plt>
mov    %rax,%r12
mov    %ebp,0xc(%rsp)
movslq %ebp,%rax
mov    %r14,%rbp
lea    (%r14,%rax,4),%r14
mov    (%rsp),%rdi
mov    %r14,%rsi
mov    0x10(%rsp),%edx
call   1050 <memcpy@plt>
mov    %rbx,0x20(%rsp)
movslq %ebx,%rax
mov    %rbp,0x10(%rsp)
lea    0x4(,%rax,4),%rsi
add    %rbp,%rsi
mov    %r12,%rdi
mov    0x18(%rsp),%edx
call   1050 <memcpy@plt>
lea    0xe11(%rip),%rdi
call   1040 <puts@plt>
mov    (%rsp),%rdi
mov    0x1c(%rsp),%esi
call   1070 <PrintArray@plt>
lea    0xdff(%rip),%rdi
call   1040 <puts@plt>
mov    %r12,%rdi
mov    %r15d,%esi
call   1070 <PrintArray@plt>
xor    %esi,%esi
test   %r13d,%r13d
js     128b <merge+0x13b>
mov    $0x0,%ecx
mov    0xc(%rsp),%r11d
mov    %r11d,%eax
test   %r15d,%r15d
mov    (%rsp),%r9
jle    1278 <merge+0x128>
xor    %ecx,%ecx
mov    %r11d,%eax
xor    %esi,%esi
nopl   0x0(%rax)
mov    %esi,%edx
mov    %ecx,%edi
mov    %esi,%ecx
mov    (%r9,%rcx,4),%ebp
mov    %edi,%ecx
mov    (%r12,%rcx,4),%ebx
xor    %ecx,%ecx
xor    %esi,%esi
cmp    %ebx,%ebp
setg   %cl
setle  %sil
cmovg  %ebx,%ebp
add    %edx,%esi
add    %edi,%ecx
mov    %ebp,(%r14)
add    $0x1,%eax
cmp    %r13d,%esi
jg     1278 <merge+0x128>
add    $0x4,%r14
cmp    %r15d,%ecx
jl     1240 <merge+0xf0>
cmp    %r13d,%esi
jle    129e <merge+0x14e>
mov    0x8(%rsp),%ebx
mov    0x10(%rsp),%r14
jmp    13c6 <merge+0x276>
xor    %ecx,%ecx
mov    0xc(%rsp),%r11d
mov    %r11d,%eax
mov    (%rsp),%r9
cmp    %r13d,%esi
jg     127d <merge+0x12d>
cltq
movslq %esi,%r10
add    %r11d,%esi
mov    0x20(%rsp),%rbx
sub    %esi,%ebx
cmp    $0x7,%ebx
mov    0x10(%rsp),%r14
jb     1397 <merge+0x247>
lea    (%r14,%rax,4),%rdx
lea    (%r10,%rbx,1),%rsi
lea    (%r9,%rsi,4),%rsi
add    $0x4,%rsi
cmp    %rsi,%rdx
jae    12e9 <merge+0x199>
lea    (%rax,%rbx,1),%rdx
lea    (%r14,%rdx,4),%rdx
add    $0x4,%rdx
lea    (%r9,%r10,4),%rsi
cmp    %rdx,%rsi
jb     1397 <merge+0x247>
add    $0x1,%rbx
mov    %rbx,%r8
and    $0xfffffffffffffff8,%r8
lea    -0x8(%r8),%rdx
mov    %rdx,%r9
shr    $0x3,%r9
add    $0x1,%r9
test   %rdx,%rdx
je     1363 <merge+0x213>
mov    %r9,%rdi
and    $0xfffffffffffffffe,%rdi
mov    (%rsp),%rdx
lea    (%rdx,%r10,4),%rdx
add    $0x30,%rdx
lea    (%r14,%rax,4),%rbp
add    $0x30,%rbp
xor    %esi,%esi
cs nopw 0x0(%rax,%rax,1)
nop
movups -0x30(%rdx,%rsi,4),%xmm0
movups -0x20(%rdx,%rsi,4),%xmm1
movups %xmm0,-0x30(%rbp,%rsi,4)
movups %xmm1,-0x20(%rbp,%rsi,4)
movups -0x10(%rdx,%rsi,4),%xmm0
movups (%rdx,%rsi,4),%xmm1
movups %xmm0,-0x10(%rbp,%rsi,4)
movups %xmm1,0x0(%rbp,%rsi,4)
add    $0x10,%rsi
add    $0xfffffffffffffffe,%rdi
jne    1330 <merge+0x1e0>
jmp    1365 <merge+0x215>
xor    %esi,%esi
test   $0x1,%r9b
mov    (%rsp),%r9
je     138c <merge+0x23c>
lea    (%rsi,%r10,1),%rdx
add    %rax,%rsi
movups (%r9,%rdx,4),%xmm0
movups 0x10(%r9,%rdx,4),%xmm1
movups %xmm0,(%r14,%rsi,4)
movups %xmm1,0x10(%r14,%rsi,4)
add    %r8,%rax
cmp    %r8,%rbx
je     13c2 <merge+0x272>
add    %r8,%r10
lea    (%r9,%r10,4),%rdx
sub    %r10d,%r13d
add    $0x1,%r13d
lea    (%r14,%rax,4),%rdi
xor    %esi,%esi
nopl   0x0(%rax,%rax,1)
mov    (%rdx,%rsi,4),%ebp
mov    %ebp,(%rdi,%rsi,4)
add    $0x1,%rsi
cmp    %esi,%r13d
jne    13b0 <merge+0x260>
add    %rsi,%rax
mov    0x8(%rsp),%ebx
mov    %r11d,%r13d
cmp    %r15d,%ecx
jge    14e3 <merge+0x393>
movslq %eax,%r10
movslq %ecx,%rax
movslq %r15d,%rcx
lea    0x1(%rax),%rdx
cmp    %rdx,%rcx
mov    %rdx,%r11
cmovg  %rcx,%r11
sub    %rax,%r11
cmp    $0x8,%r11
jb     14be <merge+0x36e>
lea    (%r14,%r10,4),%rsi
cmp    %rdx,%rcx
cmovg  %rcx,%rdx
lea    (%r12,%rdx,4),%rdi
cmp    %rdi,%rsi
jae    1421 <merge+0x2d1>
add    %r10,%rdx
sub    %rax,%rdx
lea    (%r14,%rdx,4),%rdx
lea    (%r12,%rax,4),%rsi
cmp    %rdx,%rsi
jb     14be <merge+0x36e>
mov    %r11,%r8
and    $0xfffffffffffffff8,%r8
lea    -0x8(%r8),%rdx
mov    %rdx,%r9
shr    $0x3,%r9
add    $0x1,%r9
test   %rdx,%rdx
je     151e <merge+0x3ce>
mov    %r9,%rbp
and    $0xfffffffffffffffe,%rbp
lea    (%r12,%rax,4),%rdx
add    $0x30,%rdx
lea    (%r14,%r10,4),%rsi
add    $0x30,%rsi
xor    %edi,%edi
nopl   0x0(%rax)
movups -0x30(%rdx,%rdi,4),%xmm0
movups -0x20(%rdx,%rdi,4),%xmm1
movups %xmm0,-0x30(%rsi,%rdi,4)
movups %xmm1,-0x20(%rsi,%rdi,4)
movups -0x10(%rdx,%rdi,4),%xmm0
movups (%rdx,%rdi,4),%xmm1
movups %xmm0,-0x10(%rsi,%rdi,4)
movups %xmm1,(%rsi,%rdi,4)
add    $0x10,%rdi
add    $0xfffffffffffffffe,%rbp
jne    1460 <merge+0x310>
test   $0x1,%r9b
je     14b3 <merge+0x363>
lea    (%rdi,%rax,1),%rdx
add    %r10,%rdi
movups (%r12,%rdx,4),%xmm0
movups 0x10(%r12,%rdx,4),%xmm1
movups %xmm0,(%r14,%rdi,4)
movups %xmm1,0x10(%r14,%rdi,4)
cmp    %r8,%r11
je     14e3 <merge+0x393>
add    %r8,%rax
add    %r8,%r10
lea    (%r14,%r10,4),%rdx
cs nopw 0x0(%rax,%rax,1)
nopl   0x0(%rax)
mov    (%r12,%rax,4),%esi
add    $0x1,%rax
mov    %esi,(%rdx)
add    $0x4,%rdx
cmp    %rcx,%rax
jl     14d0 <merge+0x380>
lea    0xb25(%rip),%rdi
call   1040 <puts@plt>
sub    %r13d,%ebx
add    $0x1,%ebx
mov    %r14,%rdi
mov    %ebx,%esi
call   1070 <PrintArray@plt>
mov    (%rsp),%rdi
call   1030 <free@plt>
mov    %r12,%rdi
add    $0x28,%rsp
pop    %rbx
pop    %r12
pop    %r13
pop    %r14
pop    %r15
pop    %rbp
jmp    1030 <free@plt>
xor    %edi,%edi
test   $0x1,%r9b
jne    1496 <merge+0x346>
jmp    14b3 <merge+0x363>

LLVM IR (-O0):
@.str = [8 x i8] c"Left: \0A\00"
@.str.1 = [9 x i8] c"Right: \0A\00"
@.str.2 = [15 x i8] c"After merge: \0A\00"
define void @merge(i32* %0, i32 %1, i32 %2, i32 %3) {
%5 = alloca i32*
%6 = alloca i32
%7 = alloca i32
%8 = alloca i32
%9 = alloca i32
%10 = alloca i32
%11 = alloca i32*
%12 = alloca i32*
%13 = alloca i32
%14 = alloca i32
%15 = alloca i32
store i32* %0, i32** %5
store i32 %1, i32* %6
store i32 %2, i32* %7
store i32 %3, i32* %8
%16 = load i32, i32* %7
%17 = load i32, i32* %6
%18 = sub nsw i32 %16, %17
%19 = add nsw i32 %18, 1
store i32 %19, i32* %9
%20 = load i32, i32* %8
%21 = load i32, i32* %7
%22 = sub nsw i32 %20, %21
store i32 %22, i32* %10
%23 = load i32, i32* %9
%24 = sext i32 %23 to i64
%25 = mul i64 4, %24
%26 = trunc i64 %25 to i32
%27 = call i64 @malloc(i32 %26)
%28 = inttoptr i64 %27 to i32*
store i32* %28, i32** %11
%29 = load i32, i32* %10
%30 = sext i32 %29 to i64
%31 = mul i64 4, %30
%32 = trunc i64 %31 to i32
%33 = call i64 @malloc(i32 %32)
%34 = inttoptr i64 %33 to i32*
store i32* %34, i32** %12
%35 = load i32*, i32** %11
%36 = load i32*, i32** %5
%37 = load i32, i32* %6
%38 = sext i32 %37 to i64
%39 = getelementptr inbounds i32, i32* %36, i64 %38
%40 = load i32, i32* %9
%41 = sext i32 %40 to i64
%42 = mul i64 %41, 4
%43 = trunc i64 %42 to i32
%44 = call i32 @memcpy(i32* %35, i32* %39, i32 %43)
%45 = load i32*, i32** %12
%46 = load i32*, i32** %5
%47 = load i32, i32* %7
%48 = sext i32 %47 to i64
%49 = getelementptr inbounds i32, i32* %46, i64 %48
%50 = getelementptr inbounds i32, i32* %49, i64 1
%51 = load i32, i32* %10
%52 = sext i32 %51 to i64
%53 = mul i64 %52, 4
%54 = trunc i64 %53 to i32
%55 = call i32 @memcpy(i32* %45, i32* %50, i32 %54)
%56 = call i32 @printf(i8* getelementptr inbounds ([8 x i8], [8 x i8]* @.str, i64 0, i64 0))
%57 = load i32*, i32** %11
%58 = load i32, i32* %9
%59 = call i32 @PrintArray(i32* %57, i32 %58)
%60 = call i32 @printf(i8* getelementptr inbounds ([9 x i8], [9 x i8]* @.str.1, i64 0, i64 0))
%61 = load i32*, i32** %12
%62 = load i32, i32* %10
%63 = call i32 @PrintArray(i32* %61, i32 %62)
store i32 0, i32* %13
store i32 0, i32* %14
%64 = load i32, i32* %6
store i32 %64, i32* %15
br label %65
65: ; preds = %111, %4
%66 = load i32, i32* %13
%67 = load i32, i32* %9
%68 = icmp slt i32 %66, %67
br i1 %68, label %69, label %73
69: ; preds = %65
%70 = load i32, i32* %14
%71 = load i32, i32* %10
%72 = icmp slt i32 %70, %71
br label %73
73: ; preds = %69, %65
%74 = phi i1 [ false, %65 ], [ %72, %69 ]
br i1 %74, label %75, label %112
75: ; preds = %73
%76 = load i32*, i32** %11
%77 = load i32, i32* %13
%78 = sext i32 %77 to i64
%79 = getelementptr inbounds i32, i32* %76, i64 %78
%80 = load i32, i32* %79
%81 = load i32*, i32** %12
%82 = load i32, i32* %14
%83 = sext i32 %82 to i64
%84 = getelementptr inbounds i32, i32* %81, i64 %83
%85 = load i32, i32* %84
%86 = icmp sle i32 %80, %85
br i1 %86, label %87, label %99
87: ; preds = %75
%88 = load i32*, i32** %11
%89 = load i32, i32* %13
%90 = add nsw i32 %89, 1
store i32 %90, i32* %13
%91 = sext i32 %89 to i64
%92 = getelementptr inbounds i32, i32* %88, i64 %91
%93 = load i32, i32* %92
%94 = load i32*, i32** %5
%95 = load i32, i32* %15
%96 = add nsw i32 %95, 1
store i32 %96, i32* %15
%97 = sext i32 %95 to i64
%98 = getelementptr inbounds i32, i32* %94, i64 %97
store i32 %93, i32* %98
br label %111
99: ; preds = %75
%100 = load i32*, i32** %12
%101 = load i32, i32* %14
%102 = add nsw i32 %101, 1
store i32 %102, i32* %14
%103 = sext i32 %101 to i64
%104 = getelementptr inbounds i32, i32* %100, i64 %103
%105 = load i32, i32* %104
%106 = load i32*, i32** %5
%107 = load i32, i32* %15
%108 = add nsw i32 %107, 1
store i32 %108, i32* %15
%109 = sext i32 %107 to i64
%110 = getelementptr inbounds i32, i32* %106, i64 %109
store i32 %105, i32* %110
br label %111
111: ; preds = %99, %87
br label %65
112: ; preds = %73
br label %113
113: ; preds = %117, %112
%114 = load i32, i32* %13
%115 = load i32, i32* %9
%116 = icmp slt i32 %114, %115
br i1 %116, label %117, label %129
117: ; preds = %113
%118 = load i32*, i32** %11
%119 = load i32, i32* %13
%120 = add nsw i32 %119, 1
store i32 %120, i32* %13
%121 = sext i32 %119 to i64
%122 = getelementptr inbounds i32, i32* %118, i64 %121
%123 = load i32, i32* %122
%124 = load i32*, i32** %5
%125 = load i32, i32* %15
%126 = add nsw i32 %125, 1
store i32 %126, i32* %15
%127 = sext i32 %125 to i64
%128 = getelementptr inbounds i32, i32* %124, i64 %127
store i32 %123, i32* %128
br label %113
129: ; preds = %113
br label %130
130: ; preds = %134, %129
%131 = load i32, i32* %14
%132 = load i32, i32* %10
%133 = icmp slt i32 %131, %132
br i1 %133, label %134, label %146
134: ; preds = %130
%135 = load i32*, i32** %12
%136 = load i32, i32* %14
%137 = add nsw i32 %136, 1
store i32 %137, i32* %14
%138 = sext i32 %136 to i64
%139 = getelementptr inbounds i32, i32* %135, i64 %138
%140 = load i32, i32* %139
%141 = load i32*, i32** %5
%142 = load i32, i32* %15
%143 = add nsw i32 %142, 1
store i32 %143, i32* %15
%144 = sext i32 %142 to i64
%145 = getelementptr inbounds i32, i32* %141, i64 %144
store i32 %140, i32* %145
br label %130
146: ; preds = %130
%147 = call i32 @printf(i8* getelementptr inbounds ([15 x i8], [15 x i8]* @.str.2, i64 0, i64 0))
%148 = load i32*, i32** %5
%149 = load i32, i32* %8
%150 = load i32, i32* %6
%151 = sub nsw i32 %149, %150
%152 = add nsw i32 %151, 1
%153 = call i32 @PrintArray(i32* %148, i32 %152)
%154 = load i32*, i32** %11
%155 = call i32 @free(i32* %154)
%156 = load i32*, i32** %12
%157 = call i32 @free(i32* %156)
ret void
}

LLVM IR (-O2):
@str = [7 x i8] c"Left: \00"
@str.3 = [8 x i8] c"Right: \00"
@str.4 = [14 x i8] c"After merge: \00"
define void @merge(i32* %0, i32 %1, i32 %2, i32 %3) {
%5 = sub nsw i32 %2, %1
%6 = add nsw i32 %5, 1
%7 = sub nsw i32 %3, %2
%8 = shl i32 %6, 2
%9 = tail call i64 @malloc(i32 %8)
%10 = inttoptr i64 %9 to i32*
%11 = shl i32 %7, 2
%12 = tail call i64 @malloc(i32 %11)
%13 = inttoptr i64 %12 to i32*
%14 = sext i32 %1 to i64
%15 = getelementptr inbounds i32, i32* %0, i64 %14
%16 = tail call i32 @memcpy(i32* %10, i32* %15, i32 %8)
%17 = sext i32 %2 to i64
%18 = getelementptr inbounds i32, i32* %0, i64 %17
%19 = getelementptr inbounds i32, i32* %18, i64 1
%20 = tail call i32 @memcpy(i32* %13, i32* %19, i32 %11)
%21 = tail call i32 @puts(i8* dereferenceable(1) getelementptr inbounds ([7 x i8], [7 x i8]* @str, i64 0, i64 0))
%22 = tail call i32 @PrintArray(i32* %10, i32 %6)
%23 = tail call i32 @puts(i8* dereferenceable(1) getelementptr inbounds ([8 x i8], [8 x i8]* @str.3, i64 0, i64 0))
%24 = tail call i32 @PrintArray(i32* %13, i32 %7)
%25 = icmp sgt i32 %5, -1
%26 = icmp sgt i32 %7, 0
%27 = select i1 %25, i1 %26, i1 false
br i1 %27, label %123, label %30
28: ; preds = %123
%29 = trunc i64 %141 to i32
br label %30
30: ; preds = %28, %4
%31 = phi i32 [ 0, %4 ], [ %137, %28 ]
%32 = phi i32 [ 0, %4 ], [ %139, %28 ]
%33 = phi i32 [ %1, %4 ], [ %29, %28 ]
%34 = icmp sgt i32 %31, %5
br i1 %34, label %148, label %35
35: ; preds = %30
%36 = sext i32 %33 to i64
%37 = sext i32 %31 to i64
%38 = add i32 %2, 1
%39 = sub i32 %38, %1
%40 = add i32 %31, %1
%41 = sub i32 %2, %40
%42 = zext i32 %41 to i64
%43 = add nuw nsw i64 %42, 1
%44 = icmp ult i32 %41, 7
br i1 %44, label %120, label %45
45: ; preds = %35
%46 = getelementptr i32, i32* %0, i64 %36
%47 = add i32 %31, %1
%48 = sub i32 %2, %47
%49 = zext i32 %48 to i64
%50 = add nsw i64 %36, %49
%51 = add nsw i64 %50, 1
%52 = getelementptr i32, i32* %0, i64 %51
%53 = getelementptr i32, i32* %10, i64 %37
%54 = add nsw i64 %37, %49
%55 = add nsw i64 %54, 1
%56 = getelementptr i32, i32* %10, i64 %55
%57 = icmp ult i32* %46, %56
%58 = icmp ult i32* %53, %52
%59 = and i1 %57, %58
br i1 %59, label %120, label %60
60: ; preds = %45
%61 = and i64 %43, 8589934584
%62 = add nsw i64 %61, %37
%63 = add nsw i64 %61, %36
%64 = add nsw i64 %61, -8
%65 = lshr exact i64 %64, 3
%66 = add nuw nsw i64 %65, 1
%67 = and i64 %66, 1
%68 = icmp eq i64 %64, 0
br i1 %68, label %102, label %69
69: ; preds = %60
%70 = and i64 %66, 4611686018427387902
br label %71
71: ; preds = %71, %69
%72 = phi i64 [ 0, %69 ], [ %99, %71 ]
%73 = phi i64 [ 0, %69 ], [ %100, %71 ]
%74 = add i64 %72, %37
%75 = add i64 %72, %36
%76 = getelementptr inbounds i32, i32* %10, i64 %74
%77 = bitcast i32* %76 to <4 x i32>*
%78 = load <4 x i32>, <4 x i32>* %77
%79 = getelementptr inbounds i32, i32* %76, i64 4
%80 = bitcast i32* %79 to <4 x i32>*
%81 = load <4 x i32>, <4 x i32>* %80
%82 = getelementptr inbounds i32, i32* %0, i64 %75
%83 = bitcast i32* %82 to <4 x i32>*
store <4 x i32> %78, <4 x i32>* %83
%84 = getelementptr inbounds i32, i32* %82, i64 4
%85 = bitcast i32* %84 to <4 x i32>*
store <4 x i32> %81, <4 x i32>* %85
%86 = or i64 %72, 8
%87 = add i64 %86, %37
%88 = add i64 %86, %36
%89 = getelementptr inbounds i32, i32* %10, i64 %87
%90 = bitcast i32* %89 to <4 x i32>*
%91 = load <4 x i32>, <4 x i32>* %90
%92 = getelementptr inbounds i32, i32* %89, i64 4
%93 = bitcast i32* %92 to <4 x i32>*
%94 = load <4 x i32>, <4 x i32>* %93
%95 = getelementptr inbounds i32, i32* %0, i64 %88
%96 = bitcast i32* %95 to <4 x i32>*
store <4 x i32> %91, <4 x i32>* %96
%97 = getelementptr inbounds i32, i32* %95, i64 4
%98 = bitcast i32* %97 to <4 x i32>*
store <4 x i32> %94, <4 x i32>* %98
%99 = add nuw i64 %72, 16
%100 = add i64 %73, 2
%101 = icmp eq i64 %100, %70
br i1 %101, label %102, label %71
102: ; preds = %71, %60
%103 = phi i64 [ 0, %60 ], [ %99, %71 ]
%104 = icmp eq i64 %67, 0
br i1 %104, label %118, label %105
105: ; preds = %102
%106 = add i64 %103, %37
%107 = add i64 %103, %36
%108 = getelementptr inbounds i32, i32* %10, i64 %106
%109 = bitcast i32* %108 to <4 x i32>*
%110 = load <4 x i32>, <4 x i32>* %109
%111 = getelementptr inbounds i32, i32* %108, i64 4
%112 = bitcast i32* %111 to <4 x i32>*
%113 = load <4 x i32>, <4 x i32>* %112
%114 = getelementptr inbounds i32, i32* %0, i64 %107
%115 = bitcast i32* %114 to <4 x i32>*
store <4 x i32> %110, <4 x i32>* %115
%116 = getelementptr inbounds i32, i32* %114, i64 4
%117 = bitcast i32* %116 to <4 x i32>*
store <4 x i32> %113, <4 x i32>* %117
br label %118
118: ; preds = %102, %105
%119 = icmp eq i64 %43, %61
br i1 %119, label %145, label %120
120: ; preds = %45, %35, %118
%121 = phi i64 [ %37, %45 ], [ %37, %35 ], [ %62, %118 ]
%122 = phi i64 [ %36, %45 ], [ %36, %35 ], [ %63, %118 ]
br label %234
123: ; preds = %4, %123
%124 = phi i64 [ %141, %123 ], [ %14, %4 ]
%125 = phi i32 [ %139, %123 ], [ 0, %4 ]
%126 = phi i32 [ %137, %123 ], [ 0, %4 ]
%127 = zext i32 %126 to i64
%128 = getelementptr inbounds i32, i32* %10, i64 %127
%129 = load i32, i32* %128
%130 = zext i32 %125 to i64
%131 = getelementptr inbounds i32, i32* %13, i64 %130
%132 = load i32, i32* %131
%133 = icmp sgt i32 %129, %132
%134 = select i1 %133, i32 %132, i32 %129
%135 = xor i1 %133, true
%136 = zext i1 %135 to i32
%137 = add nuw nsw i32 %126, %136
%138 = zext i1 %133 to i32
%139 = add nuw nsw i32 %125, %138
%140 = getelementptr inbounds i32, i32* %0, i64 %124
store i32 %134, i32* %140
%141 = add i64 %124, 1
%142 = icmp sle i32 %137, %5
%143 = icmp slt i32 %139, %7
%144 = select i1 %142, i1 %143, i1 false
br i1 %144, label %123, label %28
145: ; preds = %234, %118
%146 = phi i64 [ %63, %118 ], [ %240, %234 ]
%147 = trunc i64 %146 to i32
br label %148
148: ; preds = %145, %30
%149 = phi i32 [ %33, %30 ], [ %147, %145 ]
%150 = icmp slt i32 %32, %7
br i1 %150, label %151, label %253
151: ; preds = %148
%152 = sext i32 %149 to i64
%153 = sext i32 %32 to i64
%154 = sext i32 %7 to i64
%155 = add nsw i64 %153, 1
%156 = call i64 @llvm.smax.i64(i64 %154, i64 %155)
%157 = sub i64 %156, %153
%158 = icmp ult i64 %157, 8
br i1 %158, label %231, label %159
159: ; preds = %151
%160 = getelementptr i32, i32* %0, i64 %152
%161 = add nsw i64 %153, 1
%162 = call i64 @llvm.smax.i64(i64 %154, i64 %161)
%163 = add i64 %162, %152
%164 = sub i64 %163, %153
%165 = getelementptr i32, i32* %0, i64 %164
%166 = getelementptr i32, i32* %13, i64 %153
%167 = getelementptr i32, i32* %13, i64 %162
%168 = icmp ult i32* %160, %167
%169 = icmp ult i32* %166, %165
%170 = and i1 %168, %169
br i1 %170, label %231, label %171
171: ; preds = %159
%172 = and i64 %157, -8
%173 = add i64 %172, %153
%174 = add i64 %172, %152
%175 = add i64 %172, -8
%176 = lshr exact i64 %175, 3
%177 = add nuw nsw i64 %176, 1
%178 = and i64 %177, 1
%179 = icmp eq i64 %175, 0
br i1 %179, label %213, label %180
180: ; preds = %171
%181 = and i64 %177, 4611686018427387902
br label %182
182: ; preds = %182, %180
%183 = phi i64 [ 0, %180 ], [ %210, %182 ]
%184 = phi i64 [ 0, %180 ], [ %211, %182 ]
%185 = add i64 %183, %153
%186 = add i64 %183, %152
%187 = getelementptr inbounds i32, i32* %13, i64 %185
%188 = bitcast i32* %187 to <4 x i32>*
%189 = load <4 x i32>, <4 x i32>* %188
%190 = getelementptr inbounds i32, i32* %187, i64 4
%191 = bitcast i32* %190 to <4 x i32>*
%192 = load <4 x i32>, <4 x i32>* %191
%193 = getelementptr inbounds i32, i32* %0, i64 %186
%194 = bitcast i32* %193 to <4 x i32>*
store <4 x i32> %189, <4 x i32>* %194
%195 = getelementptr inbounds i32, i32* %193, i64 4
%196 = bitcast i32* %195 to <4 x i32>*
store <4 x i32> %192, <4 x i32>* %196
%197 = or i64 %183, 8
%198 = add i64 %197, %153
%199 = add i64 %197, %152
%200 = getelementptr inbounds i32, i32* %13, i64 %198
%201 = bitcast i32* %200 to <4 x i32>*
%202 = load <4 x i32>, <4 x i32>* %201
%203 = getelementptr inbounds i32, i32* %200, i64 4
%204 = bitcast i32* %203 to <4 x i32>*
%205 = load <4 x i32>, <4 x i32>* %204
%206 = getelementptr inbounds i32, i32* %0, i64 %199
%207 = bitcast i32* %206 to <4 x i32>*
store <4 x i32> %202, <4 x i32>* %207
%208 = getelementptr inbounds i32, i32* %206, i64 4
%209 = bitcast i32* %208 to <4 x i32>*
store <4 x i32> %205, <4 x i32>* %209
%210 = add nuw i64 %183, 16
%211 = add i64 %184, 2
%212 = icmp eq i64 %211, %181
br i1 %212, label %213, label %182
213: ; preds = %182, %171
%214 = phi i64 [ 0, %171 ], [ %210, %182 ]
%215 = icmp eq i64 %178, 0
br i1 %215, label %229, label %216
216: ; preds = %213
%217 = add i64 %214, %153
%218 = add i64 %214, %152
%219 = getelementptr inbounds i32, i32* %13, i64 %217
%220 = bitcast i32* %219 to <4 x i32>*
%221 = load <4 x i32>, <4 x i32>* %220
%222 = getelementptr inbounds i32, i32* %219, i64 4
%223 = bitcast i32* %222 to <4 x i32>*
%224 = load <4 x i32>, <4 x i32>* %223
%225 = getelementptr inbounds i32, i32* %0, i64 %218
%226 = bitcast i32* %225 to <4 x i32>*
store <4 x i32> %221, <4 x i32>* %226
%227 = getelementptr inbounds i32, i32* %225, i64 4
%228 = bitcast i32* %227 to <4 x i32>*
store <4 x i32> %224, <4 x i32>* %228
br label %229
229: ; preds = %213, %216
%230 = icmp eq i64 %157, %172
br i1 %230, label %253, label %231
231: ; preds = %159, %151, %229
%232 = phi i64 [ %153, %159 ], [ %153, %151 ], [ %173, %229 ]
%233 = phi i64 [ %152, %159 ], [ %152, %151 ], [ %174, %229 ]
br label %244
234: ; preds = %120, %234
%235 = phi i64 [ %237, %234 ], [ %121, %120 ]
%236 = phi i64 [ %240, %234 ], [ %122, %120 ]
%237 = add nsw i64 %235, 1
%238 = getelementptr inbounds i32, i32* %10, i64 %235
%239 = load i32, i32* %238
%240 = add nsw i64 %236, 1
%241 = getelementptr inbounds i32, i32* %0, i64 %236
store i32 %239, i32* %241
%242 = trunc i64 %237 to i32
%243 = icmp eq i32 %39, %242
br i1 %243, label %145, label %234
244: ; preds = %231, %244
%245 = phi i64 [ %247, %244 ], [ %232, %231 ]
%246 = phi i64 [ %250, %244 ], [ %233, %231 ]
%247 = add nsw i64 %245, 1
%248 = getelementptr inbounds i32, i32* %13, i64 %245
%249 = load i32, i32* %248
%250 = add nsw i64 %246, 1
%251 = getelementptr inbounds i32, i32* %0, i64 %246
store i32 %249, i32* %251
%252 = icmp slt i64 %247, %154
br i1 %252, label %244, label %253
253: ; preds = %244, %229, %148
%254 = tail call i32 @puts(i8* dereferenceable(1) getelementptr inbounds ([14 x i8], [14 x i8]* @str.4, i64 0, i64 0))
%255 = sub i32 1, %1
%256 = add i32 %255, %3
%257 = tail call i32 @PrintArray(i32* %0, i32 %256)
%258 = tail call i32 @free(i32* %10)
%259 = tail call i32 @free(i32* %13)
ret void
}