#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*/ free(double **);
double **malloc(int);
void Merge(double **data, int first, int mid, int last, int col) {
  double **holder = malloc((last - first + 1) * sizeof(double *));
  int i = first;
  int j = mid + 1;
  int k = 0;
  while (i < mid + 1 && j < last + 1) {
    if (data[i][col] <= data[j][col]) {
      holder[k] = data[i];
      ++i;
    } else {
      holder[k] = data[j];
      ++j;
    }
    ++k;
  }
  while (i < mid + 1) {
    holder[k] = data[i];
    ++i;
    ++k;
  }
  while (j < last + 1) {
    holder[k] = data[j];
    ++j;
    ++k;
  }
  for (k = 0; k < last - first + 1; ++k)
    data[first + k] = holder[k];
  free(holder);
  return;
}


x86 assembly (clang, -O0):
<Merge>:
push   %rbp
mov    %rsp,%rbp
sub    $0x30,%rsp
mov    %rdi,-0x8(%rbp)
mov    %esi,-0xc(%rbp)
mov    %edx,-0x10(%rbp)
mov    %ecx,-0x14(%rbp)
mov    %r8d,-0x18(%rbp)
mov    -0x14(%rbp),%eax
sub    -0xc(%rbp),%eax
add    $0x1,%eax
cltq
shl    $0x3,%rax
mov    %eax,%edi
call   1040 <malloc@plt>
mov    %rax,-0x20(%rbp)
mov    -0xc(%rbp),%eax
mov    %eax,-0x24(%rbp)
mov    -0x10(%rbp),%eax
add    $0x1,%eax
mov    %eax,-0x28(%rbp)
movl   $0x0,-0x2c(%rbp)
mov    -0x24(%rbp),%ecx
mov    -0x10(%rbp),%edx
add    $0x1,%edx
xor    %eax,%eax
cmp    %edx,%ecx
mov    %al,-0x2d(%rbp)
jge    1190 <Merge+0x70>
mov    -0x28(%rbp),%eax
mov    -0x14(%rbp),%ecx
add    $0x1,%ecx
cmp    %ecx,%eax
setl   %al
mov    %al,-0x2d(%rbp)
mov    -0x2d(%rbp),%al
test   $0x1,%al
jne    11a0 <Merge+0x80>
jmp    1229 <Merge+0x109>
mov    -0x8(%rbp),%rax
movslq -0x24(%rbp),%rcx
mov    (%rax,%rcx,8),%rax
movslq -0x18(%rbp),%rcx
movsd  (%rax,%rcx,8),%xmm1
mov    -0x8(%rbp),%rax
movslq -0x28(%rbp),%rcx
mov    (%rax,%rcx,8),%rax
movslq -0x18(%rbp),%rcx
movsd  (%rax,%rcx,8),%xmm0
ucomisd %xmm1,%xmm0
jb     11fa <Merge+0xda>
mov    -0x8(%rbp),%rax
movslq -0x24(%rbp),%rcx
mov    (%rax,%rcx,8),%rdx
mov    -0x20(%rbp),%rax
movslq -0x2c(%rbp),%rcx
mov    %rdx,(%rax,%rcx,8)
mov    -0x24(%rbp),%eax
add    $0x1,%eax
mov    %eax,-0x24(%rbp)
jmp    121b <Merge+0xfb>
mov    -0x8(%rbp),%rax
movslq -0x28(%rbp),%rcx
mov    (%rax,%rcx,8),%rdx
mov    -0x20(%rbp),%rax
movslq -0x2c(%rbp),%rcx
mov    %rdx,(%rax,%rcx,8)
mov    -0x28(%rbp),%eax
add    $0x1,%eax
mov    %eax,-0x28(%rbp)
mov    -0x2c(%rbp),%eax
add    $0x1,%eax
mov    %eax,-0x2c(%rbp)
jmp    1169 <Merge+0x49>
jmp    122e <Merge+0x10e>
mov    -0x24(%rbp),%eax
mov    -0x10(%rbp),%ecx
add    $0x1,%ecx
cmp    %ecx,%eax
jge    126e <Merge+0x14e>
mov    -0x8(%rbp),%rax
movslq -0x24(%rbp),%rcx
mov    (%rax,%rcx,8),%rdx
mov    -0x20(%rbp),%rax
movslq -0x2c(%rbp),%rcx
mov    %rdx,(%rax,%rcx,8)
mov    -0x24(%rbp),%eax
add    $0x1,%eax
mov    %eax,-0x24(%rbp)
mov    -0x2c(%rbp),%eax
add    $0x1,%eax
mov    %eax,-0x2c(%rbp)
jmp    122e <Merge+0x10e>
jmp    1273 <Merge+0x153>
mov    -0x28(%rbp),%eax
mov    -0x14(%rbp),%ecx
add    $0x1,%ecx
cmp    %ecx,%eax
jge    12b3 <Merge+0x193>
mov    -0x8(%rbp),%rax
movslq -0x28(%rbp),%rcx
mov    (%rax,%rcx,8),%rdx
mov    -0x20(%rbp),%rax
movslq -0x2c(%rbp),%rcx
mov    %rdx,(%rax,%rcx,8)
mov    -0x28(%rbp),%eax
add    $0x1,%eax
mov    %eax,-0x28(%rbp)
mov    -0x2c(%rbp),%eax
add    $0x1,%eax
mov    %eax,-0x2c(%rbp)
jmp    1273 <Merge+0x153>
movl   $0x0,-0x2c(%rbp)
mov    -0x2c(%rbp),%eax
mov    -0x14(%rbp),%ecx
sub    -0xc(%rbp),%ecx
add    $0x1,%ecx
cmp    %ecx,%eax
jge    12f9 <Merge+0x1d9>
mov    -0x20(%rbp),%rax
movslq -0x2c(%rbp),%rcx
mov    (%rax,%rcx,8),%rdx
mov    -0x8(%rbp),%rax
mov    -0xc(%rbp),%ecx
add    -0x2c(%rbp),%ecx
movslq %ecx,%rcx
mov    %rdx,(%rax,%rcx,8)
mov    -0x2c(%rbp),%eax
add    $0x1,%eax
mov    %eax,-0x2c(%rbp)
jmp    12ba <Merge+0x19a>
mov    -0x20(%rbp),%rdi
call   1030 <free@plt>
add    $0x30,%rsp
pop    %rbp
ret

x86 assembly (clang, -O2):
<Merge>:
push   %rbp
push   %r15
push   %r14
push   %r13
push   %r12
push   %rbx
sub    $0x18,%rsp
mov    %r8d,0xc(%rsp)
mov    %ecx,%r13d
mov    %edx,%ebp
mov    %esi,0x8(%rsp)
mov    %rdi,%rbx
mov    %ecx,%eax
sub    %esi,%eax
mov    %rax,0x10(%rsp)
lea    0x8(,%rax,8),%edi
call   1050 <malloc@plt>
mov    %rax,%r15
lea    0x1(%rbp),%r12d
xor    %r14d,%r14d
cmp    %ebp,0x8(%rsp)
jg     11cd <Merge+0x9d>
cmp    %r13d,%ebp
jge    11cd <Merge+0x9d>
movslq 0xc(%rsp),%rcx
xor    %r14d,%r14d
mov    0x8(%rsp),%eax
cs nopw 0x0(%rax,%rax,1)
nop
cltq
mov    (%rbx,%rax,8),%rdx
movslq %r12d,%r12
mov    (%rbx,%r12,8),%rsi
movsd  (%rsi,%rcx,8),%xmm0
movsd  (%rdx,%rcx,8),%xmm1
ucomisd %xmm1,%xmm0
sbb    $0xffffffff,%eax
ucomisd %xmm1,%xmm0
cmovb  %rsi,%rdx
adc    $0x0,%r12d
mov    %rdx,(%r15,%r14,8)
add    $0x1,%r14
cmp    %ebp,%eax
jg     11d1 <Merge+0xa1>
cmp    %r13d,%r12d
jle    1190 <Merge+0x60>
jmp    11d1 <Merge+0xa1>
mov    0x8(%rsp),%eax
cmp    %ebp,%eax
jg     11f9 <Merge+0xc9>
mov    %r14d,%ecx
lea    (%r15,%rcx,8),%rdi
movslq %eax,%rcx
lea    (%rbx,%rcx,8),%rsi
sub    %eax,%ebp
lea    0x8(,%rbp,8),%rdx
call   1040 <memcpy@plt>
add    %ebp,%r14d
add    $0x1,%r14d
cmp    %r13d,%r12d
jg     121c <Merge+0xec>
mov    %r14d,%eax
lea    (%r15,%rax,8),%rdi
movslq %r12d,%rax
lea    (%rbx,%rax,8),%rsi
sub    %r12d,%r13d
lea    0x8(,%r13,8),%rdx
call   1040 <memcpy@plt>
mov    0x10(%rsp),%rdx
test   %edx,%edx
js     123d <Merge+0x10d>
movslq 0x8(%rsp),%rax
lea    (%rbx,%rax,8),%rdi
add    $0x1,%edx
shl    $0x3,%rdx
mov    %r15,%rsi
call   1040 <memcpy@plt>
mov    %r15,%rdi
add    $0x18,%rsp
pop    %rbx
pop    %r12
pop    %r13
pop    %r14
pop    %r15
pop    %rbp
jmp    1030 <free@plt>

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

LLVM IR (-O2):
define void @Merge(double** nocapture %0, i32 %1, i32 %2, i32 %3, i32 %4) {
%6 = sub nsw i32 %3, %1
%7 = shl i32 %6, 3
%8 = add i32 %7, 8
%9 = tail call double** @malloc(i32 %8)
%10 = bitcast double** %9 to i8*
%11 = add i32 %2, 1
%12 = icmp sle i32 %1, %2
%13 = icmp slt i32 %2, %3
%14 = and i1 %12, %13
br i1 %14, label %15, label %19
15: ; preds = %5
%16 = sext i32 %4 to i64
br label %37
17: ; preds = %37
%18 = trunc i64 %59 to i32
br label %19
19: ; preds = %17, %5
%20 = phi i32 [ %1, %5 ], [ %55, %17 ]
%21 = phi i32 [ %11, %5 ], [ %57, %17 ]
%22 = phi i32 [ 0, %5 ], [ %18, %17 ]
%23 = icmp sgt i32 %20, %2
br i1 %23, label %63, label %24
24: ; preds = %19
%25 = zext i32 %22 to i64
%26 = getelementptr double*, double** %9, i64 %25
%27 = bitcast double** %26 to i8*
%28 = sext i32 %20 to i64
%29 = getelementptr double*, double** %0, i64 %28
%30 = bitcast double** %29 to i8*
%31 = sub i32 %2, %20
%32 = zext i32 %31 to i64
%33 = shl nuw nsw i64 %32, 3
%34 = add nuw nsw i64 %33, 8
%35 = add i32 %22, %31
%36 = add i32 %35, 1
br label %63
37: ; preds = %15, %37
%38 = phi i64 [ 0, %15 ], [ %59, %37 ]
%39 = phi i32 [ %11, %15 ], [ %57, %37 ]
%40 = phi i32 [ %1, %15 ], [ %55, %37 ]
%41 = sext i32 %40 to i64
%42 = getelementptr inbounds double*, double** %0, i64 %41
%43 = load double*, double** %42
%44 = getelementptr inbounds double, double* %43, i64 %16
%45 = load double, double* %44
%46 = sext i32 %39 to i64
%47 = getelementptr inbounds double*, double** %0, i64 %46
%48 = load double*, double** %47
%49 = getelementptr inbounds double, double* %48, i64 %16
%50 = load double, double* %49
%51 = fcmp ugt double %45, %50
%52 = select i1 %51, double* %48, double* %43
%53 = xor i1 %51, true
%54 = zext i1 %53 to i32
%55 = add nsw i32 %40, %54
%56 = zext i1 %51 to i32
%57 = add nsw i32 %39, %56
%58 = getelementptr inbounds double*, double** %9, i64 %38
store double* %52, double** %58
%59 = add nuw i64 %38, 1
%60 = icmp sle i32 %55, %2
%61 = icmp sle i32 %57, %3
%62 = select i1 %60, i1 %61, i1 false
br i1 %62, label %37, label %17
63: ; preds = %24, %19
%64 = phi i32 [ %22, %19 ], [ %36, %24 ]
%65 = icmp sgt i32 %21, %3
br i1 %65, label %77, label %66
66: ; preds = %63
%67 = zext i32 %64 to i64
%68 = getelementptr double*, double** %9, i64 %67
%69 = bitcast double** %68 to i8*
%70 = sext i32 %21 to i64
%71 = getelementptr double*, double** %0, i64 %70
%72 = bitcast double** %71 to i8*
%73 = sub i32 %3, %21
%74 = zext i32 %73 to i64
%75 = shl nuw nsw i64 %74, 3
%76 = add nuw nsw i64 %75, 8
br label %77
77: ; preds = %66, %63
%78 = icmp slt i32 %6, 0
br i1 %78, label %87, label %79
79: ; preds = %77
%80 = sext i32 %1 to i64
%81 = getelementptr double*, double** %0, i64 %80
%82 = bitcast double** %81 to i8*
%83 = add i32 %3, 1
%84 = sub i32 %83, %1
%85 = zext i32 %84 to i64
%86 = shl nuw nsw i64 %85, 3
br label %87
87: ; preds = %79, %77
%88 = tail call i32 @free(double** %9)
ret void
}