#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 */
long abs(long);
extern void ExpandCentered_1D(double In[], long NxIn, double Out[], double h[],
                              long nh) {
  long k, i, j, i1, k0, i2;
  long kk, kn, nexp, n;
  nexp = NxIn * 2L;
  n = NxIn;
  kn = 2L * n;
  k0 = (nh / 2L) * 2 - 1L;
  for (i = 0L; i < NxIn; i++) {
    j = i * 2L;
    Out[j] = In[i] * h[0];
    for (k = 2L; k < nh; k = k + 2L) {
      i1 = i - k / 2L;
      i2 = i + k / 2L;
      if (i1 < 0L) {
        i1 = (2L * n - 1 - i1) % kn;
        if (i1 >= n)
          i1 = kn - i1 - 1L;
      }
      if (i2 >= n) {
        i2 = (i2) % kn;
        if (i2 >= n)
          i2 = kn - i2 - 1L;
      }
      Out[j] = Out[j] + h[k] * (In[i1] + In[i2]);
    }
    Out[j + 1] = 0.;
    for (k = -k0; k < nh; k = k + 2L) {
      kk = abs(k);
      i1 = i + (k + 1L) / 2L;
      if (i1 < 0L) {
        i1 = (2 * n - 1 - i1) % kn;
        if (i1 > n - 1)
          i1 = kn - i1 - 1L;
      }
      if (i1 >= n) {
        i1 = (i1) % kn;
        if (i1 >= n)
          i1 = kn - i1 - 1;
      }
      Out[j + 1L] = Out[j + 1L] + h[kk] * In[i1];
    }
  }
  for (j = nexp - 1L; j > 0L; j--)
    Out[j] = (Out[j] + Out[j - 1]) / 2.0;
  Out[0] /= 2.0;
}


x86 assembly (clang, -O0):
<ExpandCentered_1D>:
push   %rbp
mov    %rsp,%rbp
sub    $0x90,%rsp
mov    %rdi,-0x8(%rbp)
mov    %rsi,-0x10(%rbp)
mov    %rdx,-0x18(%rbp)
mov    %rcx,-0x20(%rbp)
mov    %r8,-0x28(%rbp)
mov    -0x10(%rbp),%rax
shl    $0x1,%rax
mov    %rax,-0x70(%rbp)
mov    -0x10(%rbp),%rax
mov    %rax,-0x78(%rbp)
mov    -0x78(%rbp),%rax
shl    $0x1,%rax
mov    %rax,-0x68(%rbp)
mov    -0x28(%rbp),%rax
mov    $0x2,%ecx
cqto
idiv   %rcx
shl    $0x1,%rax
sub    $0x1,%rax
mov    %rax,-0x50(%rbp)
movq   $0x0,-0x38(%rbp)
mov    -0x38(%rbp),%rax
cmp    -0x10(%rbp),%rax
jge    1449 <ExpandCentered_1D+0x339>
mov    -0x38(%rbp),%rax
shl    $0x1,%rax
mov    %rax,-0x40(%rbp)
mov    -0x8(%rbp),%rax
mov    -0x38(%rbp),%rcx
movsd  (%rax,%rcx,8),%xmm0
mov    -0x20(%rbp),%rax
mulsd  (%rax),%xmm0
mov    -0x18(%rbp),%rax
mov    -0x40(%rbp),%rcx
movsd  %xmm0,(%rax,%rcx,8)
movq   $0x2,-0x30(%rbp)
mov    -0x30(%rbp),%rax
cmp    -0x28(%rbp),%rax
jge    12f2 <ExpandCentered_1D+0x1e2>
mov    -0x38(%rbp),%rax
mov    %rax,-0x88(%rbp)
mov    -0x30(%rbp),%rax
mov    $0x2,%ecx
cqto
idiv   %rcx
mov    %rax,%rcx
mov    -0x88(%rbp),%rax
sub    %rcx,%rax
mov    %rax,-0x48(%rbp)
mov    -0x38(%rbp),%rax
mov    %rax,-0x80(%rbp)
mov    -0x30(%rbp),%rax
mov    $0x2,%ecx
cqto
idiv   %rcx
mov    %rax,%rcx
mov    -0x80(%rbp),%rax
add    %rcx,%rax
mov    %rax,-0x58(%rbp)
cmpq   $0x0,-0x48(%rbp)
jge    1259 <ExpandCentered_1D+0x149>
mov    -0x78(%rbp),%rax
shl    $0x1,%rax
sub    $0x1,%rax
sub    -0x48(%rbp),%rax
cqto
idivq  -0x68(%rbp)
mov    %rdx,-0x48(%rbp)
mov    -0x48(%rbp),%rax
cmp    -0x78(%rbp),%rax
jl     1254 <ExpandCentered_1D+0x144>
mov    -0x68(%rbp),%rax
sub    -0x48(%rbp),%rax
sub    $0x1,%rax
mov    %rax,-0x48(%rbp)
jmp    1259 <ExpandCentered_1D+0x149>
mov    -0x58(%rbp),%rax
cmp    -0x78(%rbp),%rax
jl     1298 <ExpandCentered_1D+0x188>
mov    -0x58(%rbp),%rax
cqto
idivq  -0x68(%rbp)
mov    %rdx,-0x58(%rbp)
mov    -0x58(%rbp),%rax
cmp    -0x78(%rbp),%rax
jl     1293 <ExpandCentered_1D+0x183>
mov    -0x68(%rbp),%rax
sub    -0x58(%rbp),%rax
sub    $0x1,%rax
mov    %rax,-0x58(%rbp)
jmp    1298 <ExpandCentered_1D+0x188>
mov    -0x18(%rbp),%rax
mov    -0x40(%rbp),%rcx
movsd  (%rax,%rcx,8),%xmm1
mov    -0x20(%rbp),%rax
mov    -0x30(%rbp),%rcx
movsd  (%rax,%rcx,8),%xmm0
mov    -0x8(%rbp),%rax
mov    -0x48(%rbp),%rcx
movsd  (%rax,%rcx,8),%xmm2
mov    -0x8(%rbp),%rax
mov    -0x58(%rbp),%rcx
addsd  (%rax,%rcx,8),%xmm2
mulsd  %xmm2,%xmm0
addsd  %xmm1,%xmm0
mov    -0x18(%rbp),%rax
mov    -0x40(%rbp),%rcx
movsd  %xmm0,(%rax,%rcx,8)
mov    -0x30(%rbp),%rax
add    $0x2,%rax
mov    %rax,-0x30(%rbp)
jmp    11b5 <ExpandCentered_1D+0xa5>
mov    -0x18(%rbp),%rax
mov    -0x40(%rbp),%rcx
xorps  %xmm0,%xmm0
movsd  %xmm0,0x8(%rax,%rcx,8)
xor    %eax,%eax
sub    -0x50(%rbp),%rax
mov    %rax,-0x30(%rbp)
mov    -0x30(%rbp),%rax
cmp    -0x28(%rbp),%rax
jge    1433 <ExpandCentered_1D+0x323>
mov    -0x30(%rbp),%rdi
call   1030 <abs@plt>
mov    %rax,-0x60(%rbp)
mov    -0x38(%rbp),%rax
mov    %rax,-0x90(%rbp)
mov    -0x30(%rbp),%rax
add    $0x1,%rax
mov    $0x2,%ecx
cqto
idiv   %rcx
mov    %rax,%rcx
mov    -0x90(%rbp),%rax
add    %rcx,%rax
mov    %rax,-0x48(%rbp)
cmpq   $0x0,-0x48(%rbp)
jge    13a5 <ExpandCentered_1D+0x295>
mov    -0x78(%rbp),%rax
shl    $0x1,%rax
sub    $0x1,%rax
sub    -0x48(%rbp),%rax
cqto
idivq  -0x68(%rbp)
mov    %rdx,-0x48(%rbp)
mov    -0x48(%rbp),%rax
mov    -0x78(%rbp),%rcx
sub    $0x1,%rcx
cmp    %rcx,%rax
jle    13a0 <ExpandCentered_1D+0x290>
mov    -0x68(%rbp),%rax
sub    -0x48(%rbp),%rax
sub    $0x1,%rax
mov    %rax,-0x48(%rbp)
jmp    13a5 <ExpandCentered_1D+0x295>
mov    -0x48(%rbp),%rax
cmp    -0x78(%rbp),%rax
jl     13e4 <ExpandCentered_1D+0x2d4>
mov    -0x48(%rbp),%rax
cqto
idivq  -0x68(%rbp)
mov    %rdx,-0x48(%rbp)
mov    -0x48(%rbp),%rax
cmp    -0x78(%rbp),%rax
jl     13df <ExpandCentered_1D+0x2cf>
mov    -0x68(%rbp),%rax
sub    -0x48(%rbp),%rax
sub    $0x1,%rax
mov    %rax,-0x48(%rbp)
jmp    13e4 <ExpandCentered_1D+0x2d4>
mov    -0x18(%rbp),%rax
mov    -0x40(%rbp),%rcx
movsd  0x8(%rax,%rcx,8),%xmm1
mov    -0x20(%rbp),%rax
mov    -0x60(%rbp),%rcx
movsd  (%rax,%rcx,8),%xmm0
mov    -0x8(%rbp),%rax
mov    -0x48(%rbp),%rcx
movsd  (%rax,%rcx,8),%xmm2
mulsd  %xmm2,%xmm0
addsd  %xmm1,%xmm0
mov    -0x18(%rbp),%rax
mov    -0x40(%rbp),%rcx
movsd  %xmm0,0x8(%rax,%rcx,8)
mov    -0x30(%rbp),%rax
add    $0x2,%rax
mov    %rax,-0x30(%rbp)
jmp    130d <ExpandCentered_1D+0x1fd>
jmp    1438 <ExpandCentered_1D+0x328>
mov    -0x38(%rbp),%rax
add    $0x1,%rax
mov    %rax,-0x38(%rbp)
jmp    1171 <ExpandCentered_1D+0x61>
mov    -0x70(%rbp),%rax
sub    $0x1,%rax
mov    %rax,-0x40(%rbp)
cmpq   $0x0,-0x40(%rbp)
jle    14a8 <ExpandCentered_1D+0x398>
mov    -0x18(%rbp),%rax
mov    -0x40(%rbp),%rcx
movsd  (%rax,%rcx,8),%xmm0
mov    -0x18(%rbp),%rax
mov    -0x40(%rbp),%rcx
sub    $0x1,%rcx
addsd  (%rax,%rcx,8),%xmm0
movsd  0xb7a(%rip),%xmm1
divsd  %xmm1,%xmm0
mov    -0x18(%rbp),%rax
mov    -0x40(%rbp),%rcx
movsd  %xmm0,(%rax,%rcx,8)
mov    -0x40(%rbp),%rax
add    $0xffffffffffffffff,%rax
mov    %rax,-0x40(%rbp)
jmp    1455 <ExpandCentered_1D+0x345>
mov    -0x18(%rbp),%rax
movsd  (%rax),%xmm0
movsd  0xb48(%rip),%xmm1
divsd  %xmm1,%xmm0
movsd  %xmm0,(%rax)
add    $0x90,%rsp
pop    %rbp
ret

x86 assembly (clang, -O2):
<ExpandCentered_1D>:
push   %rbp
push   %r15
push   %r14
push   %r13
push   %r12
push   %rbx
mov    %rdx,%r9
test   %rsi,%rsi
jle    1393 <ExpandCentered_1D+0x293>
lea    (%rsi,%rsi,1),%r14
mov    %r8,%rax
shr    $0x3f,%rax
add    %r8,%rax
and    $0xfffffffffffffffe,%rax
mov    $0x1,%ebp
mov    $0x1,%edx
sub    %rax,%rdx
mov    %rdx,-0x10(%rsp)
movq   $0xffffffffffffffff,-0x18(%rsp)
ff ff
xor    %r11d,%r11d
mov    %r14,-0x20(%rsp)
jmp    1170 <ExpandCentered_1D+0x70>
nopl   (%rax)
add    $0x1,%r11
mov    %r10,%rbp
add    $0x1,%rbp
addq   $0xffffffffffffffff,-0x20(%rsp)
addq   $0x1,-0x18(%rsp)
cmp    %rsi,%r11
je     135d <ExpandCentered_1D+0x25d>
lea    (%r11,%r11,1),%r15
mov    %r11,%rax
shl    $0x4,%rax
mov    %r11,-0x8(%rsp)
movsd  (%rdi,%r11,8),%xmm0
mulsd  (%rcx),%xmm0
movsd  %xmm0,(%r9,%rax,1)
cmp    $0x3,%r8
jl     1270 <ExpandCentered_1D+0x170>
mov    $0x2,%r13d
mov    -0x18(%rsp),%rbx
mov    -0x20(%rsp),%r10
mov    %rbp,%r11
jmp    11e4 <ExpandCentered_1D+0xe4>
nop
movsd  (%rdi,%r12,8),%xmm1
addsd  (%rdi,%rdx,8),%xmm1
mulsd  (%rcx,%r13,8),%xmm1
addsd  %xmm1,%xmm0
movsd  %xmm0,(%r9,%r15,8)
add    $0x2,%r13
add    $0x1,%r11
add    $0x1,%r10
add    $0xffffffffffffffff,%rbx
cmp    %r8,%r13
jge    1270 <ExpandCentered_1D+0x170>
mov    %rbx,%r12
test   %rbx,%rbx
jns    1210 <ExpandCentered_1D+0x110>
mov    %r10,%rax
or     %r14,%rax
shr    $0x20,%rax
je     1253 <ExpandCentered_1D+0x153>
mov    %r10,%rax
cqto
idiv   %r14
mov    %rdx,%r12
cmp    %rsi,%r12
jl     1210 <ExpandCentered_1D+0x110>
not    %r12
add    %r14,%r12
xchg   %ax,%ax
mov    %r11,%rdx
cmp    %rsi,%r11
jl     11b0 <ExpandCentered_1D+0xb0>
mov    %r11,%rax
or     %r14,%rax
shr    $0x20,%rax
je     1237 <ExpandCentered_1D+0x137>
mov    %r11,%rax
cqto
idiv   %r14
cmp    %rsi,%rdx
jl     11b0 <ExpandCentered_1D+0xb0>
jmp    1248 <ExpandCentered_1D+0x148>
mov    %r11d,%eax
xor    %edx,%edx
div    %r14d
cmp    %rsi,%rdx
jl     11b0 <ExpandCentered_1D+0xb0>
not    %rdx
add    %r14,%rdx
jmp    11b0 <ExpandCentered_1D+0xb0>
mov    %r10d,%eax
xor    %edx,%edx
div    %r14d
mov    %edx,%r12d
cmp    %rsi,%r12
jge    1208 <ExpandCentered_1D+0x108>
jmp    1210 <ExpandCentered_1D+0x110>
cs nopw 0x0(%rax,%rax,1)
nop
mov    %rbp,%r10
or     $0x1,%r15
movq   $0x0,(%r9,%r15,8)
cmp    %r8,-0x10(%rsp)
mov    -0x8(%rsp),%r11
jge    1150 <ExpandCentered_1D+0x50>
xorpd  %xmm0,%xmm0
mov    -0x10(%rsp),%rbx
jmp    12c1 <ExpandCentered_1D+0x1c1>
nopw   0x0(%rax,%rax,1)
movsd  (%rcx,%rbp,8),%xmm1
mulsd  (%rdi,%rax,8),%xmm1
addsd  %xmm1,%xmm0
movsd  %xmm0,(%r9,%r15,8)
add    $0x2,%rbx
cmp    %r8,%rbx
jge    1150 <ExpandCentered_1D+0x50>
mov    %rbx,%rbp
neg    %rbp
cmovs  %rbx,%rbp
lea    0x1(%rbx),%rax
shr    $0x3f,%rax
add    %rbx,%rax
add    $0x1,%rax
sar    %rax
add    %r11,%rax
jns    1310 <ExpandCentered_1D+0x210>
not    %rax
add    %r14,%rax
mov    %rax,%rdx
or     %r14,%rdx
shr    $0x20,%rdx
je     134f <ExpandCentered_1D+0x24f>
cqto
idiv   %r14
mov    %rdx,%rax
cmp    %rsi,%rax
jl     1310 <ExpandCentered_1D+0x210>
not    %rax
add    %r14,%rax
nopw   0x0(%rax,%rax,1)
cmp    %rsi,%rax
jl     12a0 <ExpandCentered_1D+0x1a0>
mov    %rax,%rdx
or     %r14,%rdx
shr    $0x20,%rdx
je     1334 <ExpandCentered_1D+0x234>
cqto
idiv   %r14
mov    %rdx,%rax
cmp    %rsi,%rax
jl     12a0 <ExpandCentered_1D+0x1a0>
jmp    1344 <ExpandCentered_1D+0x244>
xor    %edx,%edx
div    %r14d
mov    %edx,%eax
cmp    %rsi,%rax
jl     12a0 <ExpandCentered_1D+0x1a0>
not    %rax
add    %r14,%rax
jmp    12a0 <ExpandCentered_1D+0x1a0>
xor    %edx,%edx
div    %r14d
mov    %edx,%eax
cmp    %rsi,%rax
jge    1301 <ExpandCentered_1D+0x201>
jmp    1310 <ExpandCentered_1D+0x210>
test   %rsi,%rsi
jle    1393 <ExpandCentered_1D+0x293>
add    $0x1,%r14
movsd  0xc92(%rip),%xmm0
xchg   %ax,%ax
movsd  -0x10(%r9,%r14,8),%xmm1
addsd  -0x18(%r9,%r14,8),%xmm1
mulsd  %xmm0,%xmm1
movsd  %xmm1,-0x10(%r9,%r14,8)
add    $0xffffffffffffffff,%r14
cmp    $0x2,%r14
jg     1370 <ExpandCentered_1D+0x270>
movsd  (%r9),%xmm0
mulsd  0xc60(%rip),%xmm0
movsd  %xmm0,(%r9)
pop    %rbx
pop    %r12
pop    %r13
pop    %r14
pop    %r15
pop    %rbp
ret

LLVM IR (-O0):
define void @ExpandCentered_1D(double* %0, i64 %1, double* %2, double* %3, i64 %4) {
%6 = alloca double*
%7 = alloca i64
%8 = alloca double*
%9 = alloca double*
%10 = alloca i64
%11 = alloca i64
%12 = alloca i64
%13 = alloca i64
%14 = alloca i64
%15 = alloca i64
%16 = alloca i64
%17 = alloca i64
%18 = alloca i64
%19 = alloca i64
%20 = alloca i64
store double* %0, double** %6
store i64 %1, i64* %7
store double* %2, double** %8
store double* %3, double** %9
store i64 %4, i64* %10
%21 = load i64, i64* %7
%22 = mul nsw i64 %21, 2
store i64 %22, i64* %19
%23 = load i64, i64* %7
store i64 %23, i64* %20
%24 = load i64, i64* %20
%25 = mul nsw i64 2, %24
store i64 %25, i64* %18
%26 = load i64, i64* %10
%27 = sdiv i64 %26, 2
%28 = mul nsw i64 %27, 2
%29 = sub nsw i64 %28, 1
store i64 %29, i64* %15
store i64 0, i64* %12
br label %30
30: ; preds = %201, %5
%31 = load i64, i64* %12
%32 = load i64, i64* %7
%33 = icmp slt i64 %31, %32
br i1 %33, label %34, label %204
34: ; preds = %30
%35 = load i64, i64* %12
%36 = mul nsw i64 %35, 2
store i64 %36, i64* %13
%37 = load double*, double** %6
%38 = load i64, i64* %12
%39 = getelementptr inbounds double, double* %37, i64 %38
%40 = load double, double* %39
%41 = load double*, double** %9
%42 = getelementptr inbounds double, double* %41, i64 0
%43 = load double, double* %42
%44 = fmul double %40, %43
%45 = load double*, double** %8
%46 = load i64, i64* %13
%47 = getelementptr inbounds double, double* %45, i64 %46
store double %44, double* %47
store i64 2, i64* %11
br label %48
48: ; preds = %119, %34
%49 = load i64, i64* %11
%50 = load i64, i64* %10
%51 = icmp slt i64 %49, %50
br i1 %51, label %52, label %122
52: ; preds = %48
%53 = load i64, i64* %12
%54 = load i64, i64* %11
%55 = sdiv i64 %54, 2
%56 = sub nsw i64 %53, %55
store i64 %56, i64* %14
%57 = load i64, i64* %12
%58 = load i64, i64* %11
%59 = sdiv i64 %58, 2
%60 = add nsw i64 %57, %59
store i64 %60, i64* %16
%61 = load i64, i64* %14
%62 = icmp slt i64 %61, 0
br i1 %62, label %63, label %80
63: ; preds = %52
%64 = load i64, i64* %20
%65 = mul nsw i64 2, %64
%66 = sub nsw i64 %65, 1
%67 = load i64, i64* %14
%68 = sub nsw i64 %66, %67
%69 = load i64, i64* %18
%70 = srem i64 %68, %69
store i64 %70, i64* %14
%71 = load i64, i64* %14
%72 = load i64, i64* %20
%73 = icmp sge i64 %71, %72
br i1 %73, label %74, label %79
74: ; preds = %63
%75 = load i64, i64* %18
%76 = load i64, i64* %14
%77 = sub nsw i64 %75, %76
%78 = sub nsw i64 %77, 1
store i64 %78, i64* %14
br label %79
79: ; preds = %74, %63
br label %80
80: ; preds = %79, %52
%81 = load i64, i64* %16
%82 = load i64, i64* %20
%83 = icmp sge i64 %81, %82
br i1 %83, label %84, label %97
84: ; preds = %80
%85 = load i64, i64* %16
%86 = load i64, i64* %18
%87 = srem i64 %85, %86
store i64 %87, i64* %16
%88 = load i64, i64* %16
%89 = load i64, i64* %20
%90 = icmp sge i64 %88, %89
br i1 %90, label %91, label %96
91: ; preds = %84
%92 = load i64, i64* %18
%93 = load i64, i64* %16
%94 = sub nsw i64 %92, %93
%95 = sub nsw i64 %94, 1
store i64 %95, i64* %16
br label %96
96: ; preds = %91, %84
br label %97
97: ; preds = %96, %80
%98 = load double*, double** %8
%99 = load i64, i64* %13
%100 = getelementptr inbounds double, double* %98, i64 %99
%101 = load double, double* %100
%102 = load double*, double** %9
%103 = load i64, i64* %11
%104 = getelementptr inbounds double, double* %102, i64 %103
%105 = load double, double* %104
%106 = load double*, double** %6
%107 = load i64, i64* %14
%108 = getelementptr inbounds double, double* %106, i64 %107
%109 = load double, double* %108
%110 = load double*, double** %6
%111 = load i64, i64* %16
%112 = getelementptr inbounds double, double* %110, i64 %111
%113 = load double, double* %112
%114 = fadd double %109, %113
%115 = call double @llvm.fmuladd.f64(double %105, double %114, double %101)
%116 = load double*, double** %8
%117 = load i64, i64* %13
%118 = getelementptr inbounds double, double* %116, i64 %117
store double %115, double* %118
br label %119
119: ; preds = %97
%120 = load i64, i64* %11
%121 = add nsw i64 %120, 2
store i64 %121, i64* %11
br label %48
122: ; preds = %48
%123 = load double*, double** %8
%124 = load i64, i64* %13
%125 = add nsw i64 %124, 1
%126 = getelementptr inbounds double, double* %123, i64 %125
store double 0.000000e+00, double* %126
%127 = load i64, i64* %15
%128 = sub nsw i64 0, %127
store i64 %128, i64* %11
br label %129
129: ; preds = %197, %122
%130 = load i64, i64* %11
%131 = load i64, i64* %10
%132 = icmp slt i64 %130, %131
br i1 %132, label %133, label %200
133: ; preds = %129
%134 = load i64, i64* %11
%135 = call i64 @abs(i64 %134)
store i64 %135, i64* %17
%136 = load i64, i64* %12
%137 = load i64, i64* %11
%138 = add nsw i64 %137, 1
%139 = sdiv i64 %138, 2
%140 = add nsw i64 %136, %139
store i64 %140, i64* %14
%141 = load i64, i64* %14
%142 = icmp slt i64 %141, 0
br i1 %142, label %143, label %161
143: ; preds = %133
%144 = load i64, i64* %20
%145 = mul nsw i64 2, %144
%146 = sub nsw i64 %145, 1
%147 = load i64, i64* %14
%148 = sub nsw i64 %146, %147
%149 = load i64, i64* %18
%150 = srem i64 %148, %149
store i64 %150, i64* %14
%151 = load i64, i64* %14
%152 = load i64, i64* %20
%153 = sub nsw i64 %152, 1
%154 = icmp sgt i64 %151, %153
br i1 %154, label %155, label %160
155: ; preds = %143
%156 = load i64, i64* %18
%157 = load i64, i64* %14
%158 = sub nsw i64 %156, %157
%159 = sub nsw i64 %158, 1
store i64 %159, i64* %14
br label %160
160: ; preds = %155, %143
br label %161
161: ; preds = %160, %133
%162 = load i64, i64* %14
%163 = load i64, i64* %20
%164 = icmp sge i64 %162, %163
br i1 %164, label %165, label %178
165: ; preds = %161
%166 = load i64, i64* %14
%167 = load i64, i64* %18
%168 = srem i64 %166, %167
store i64 %168, i64* %14
%169 = load i64, i64* %14
%170 = load i64, i64* %20
%171 = icmp sge i64 %169, %170
br i1 %171, label %172, label %177
172: ; preds = %165
%173 = load i64, i64* %18
%174 = load i64, i64* %14
%175 = sub nsw i64 %173, %174
%176 = sub nsw i64 %175, 1
store i64 %176, i64* %14
br label %177
177: ; preds = %172, %165
br label %178
178: ; preds = %177, %161
%179 = load double*, double** %8
%180 = load i64, i64* %13
%181 = add nsw i64 %180, 1
%182 = getelementptr inbounds double, double* %179, i64 %181
%183 = load double, double* %182
%184 = load double*, double** %9
%185 = load i64, i64* %17
%186 = getelementptr inbounds double, double* %184, i64 %185
%187 = load double, double* %186
%188 = load double*, double** %6
%189 = load i64, i64* %14
%190 = getelementptr inbounds double, double* %188, i64 %189
%191 = load double, double* %190
%192 = call double @llvm.fmuladd.f64(double %187, double %191, double %183)
%193 = load double*, double** %8
%194 = load i64, i64* %13
%195 = add nsw i64 %194, 1
%196 = getelementptr inbounds double, double* %193, i64 %195
store double %192, double* %196
br label %197
197: ; preds = %178
%198 = load i64, i64* %11
%199 = add nsw i64 %198, 2
store i64 %199, i64* %11
br label %129
200: ; preds = %129
br label %201
201: ; preds = %200
%202 = load i64, i64* %12
%203 = add nsw i64 %202, 1
store i64 %203, i64* %12
br label %30
204: ; preds = %30
%205 = load i64, i64* %19
%206 = sub nsw i64 %205, 1
store i64 %206, i64* %13
br label %207
207: ; preds = %225, %204
%208 = load i64, i64* %13
%209 = icmp sgt i64 %208, 0
br i1 %209, label %210, label %228
210: ; preds = %207
%211 = load double*, double** %8
%212 = load i64, i64* %13
%213 = getelementptr inbounds double, double* %211, i64 %212
%214 = load double, double* %213
%215 = load double*, double** %8
%216 = load i64, i64* %13
%217 = sub nsw i64 %216, 1
%218 = getelementptr inbounds double, double* %215, i64 %217
%219 = load double, double* %218
%220 = fadd double %214, %219
%221 = fdiv double %220, 2.000000e+00
%222 = load double*, double** %8
%223 = load i64, i64* %13
%224 = getelementptr inbounds double, double* %222, i64 %223
store double %221, double* %224
br label %225
225: ; preds = %210
%226 = load i64, i64* %13
%227 = add nsw i64 %226, -1
store i64 %227, i64* %13
br label %207
228: ; preds = %207
%229 = load double*, double** %8
%230 = getelementptr inbounds double, double* %229, i64 0
%231 = load double, double* %230
%232 = fdiv double %231, 2.000000e+00
store double %232, double* %230
ret void
}

LLVM IR (-O2):
define void @ExpandCentered_1D(double* nocapture %0, i64 %1, double* nocapture %2, double* nocapture %3, i64 %4) {
%6 = shl nsw i64 %1, 1
%7 = icmp sgt i64 %1, 0
br i1 %7, label %8, label %110
8: ; preds = %5
%9 = sdiv i64 %4, -2
%10 = shl i64 %9, 1
%11 = icmp sgt i64 %4, 2
%12 = or i64 %10, 1
%13 = icmp slt i64 %12, %4
br label %15
14: ; preds = %96
br i1 %7, label %99, label %110
15: ; preds = %8, %96
%16 = phi i64 [ 0, %8 ], [ %97, %96 ]
%17 = shl nuw nsw i64 %16, 1
%18 = getelementptr inbounds double, double* %0, i64 %16
%19 = load double, double* %18
%20 = load double, double* %3
%21 = fmul double %19, %20
%22 = getelementptr inbounds double, double* %2, i64 %17
store double %21, double* %22
br i1 %11, label %23, label %59
23: ; preds = %15, %47
%24 = phi double [ %56, %47 ], [ %21, %15 ]
%25 = phi i64 [ %57, %47 ], [ 2, %15 ]
%26 = lshr exact i64 %25, 1
%27 = sub nsw i64 %16, %26
%28 = add nuw nsw i64 %26, %16
%29 = icmp slt i64 %27, 0
br i1 %29, label %30, label %38
30: ; preds = %23
%31 = xor i64 %27, -1
%32 = add i64 %6, %31
%33 = srem i64 %32, %6
%34 = icmp slt i64 %33, %1
br i1 %34, label %38, label %35
35: ; preds = %30
%36 = xor i64 %33, -1
%37 = add i64 %6, %36
br label %38
38: ; preds = %30, %35, %23
%39 = phi i64 [ %37, %35 ], [ %33, %30 ], [ %27, %23 ]
%40 = icmp slt i64 %28, %1
br i1 %40, label %47, label %41
41: ; preds = %38
%42 = srem i64 %28, %6
%43 = icmp slt i64 %42, %1
br i1 %43, label %47, label %44
44: ; preds = %41
%45 = xor i64 %42, -1
%46 = add i64 %6, %45
br label %47
47: ; preds = %41, %44, %38
%48 = phi i64 [ %46, %44 ], [ %42, %41 ], [ %28, %38 ]
%49 = getelementptr inbounds double, double* %3, i64 %25
%50 = load double, double* %49
%51 = getelementptr inbounds double, double* %0, i64 %39
%52 = load double, double* %51
%53 = getelementptr inbounds double, double* %0, i64 %48
%54 = load double, double* %53
%55 = fadd double %52, %54
%56 = tail call double @llvm.fmuladd.f64(double %50, double %55, double %24)
store double %56, double* %22
%57 = add nuw nsw i64 %25, 2
%58 = icmp slt i64 %57, %4
br i1 %58, label %23, label %59
59: ; preds = %47, %15
%60 = or i64 %17, 1
%61 = getelementptr inbounds double, double* %2, i64 %60
store double 0.000000e+00, double* %61
br i1 %13, label %62, label %96
62: ; preds = %59, %87
%63 = phi double [ %93, %87 ], [ 0.000000e+00, %59 ]
%64 = phi i64 [ %94, %87 ], [ %12, %59 ]
%65 = tail call i64 @llvm.abs.i64(i64 %64, i1 true)
%66 = add nsw i64 %64, 1
%67 = sdiv i64 %66, 2
%68 = add nsw i64 %67, %16
%69 = icmp slt i64 %68, 0
br i1 %69, label %70, label %78
70: ; preds = %62
%71 = xor i64 %68, -1
%72 = add i64 %6, %71
%73 = srem i64 %72, %6
%74 = icmp slt i64 %73, %1
br i1 %74, label %78, label %75
75: ; preds = %70
%76 = xor i64 %73, -1
%77 = add i64 %6, %76
br label %78
78: ; preds = %70, %75, %62
%79 = phi i64 [ %77, %75 ], [ %73, %70 ], [ %68, %62 ]
%80 = icmp slt i64 %79, %1
br i1 %80, label %87, label %81
81: ; preds = %78
%82 = srem i64 %79, %6
%83 = icmp slt i64 %82, %1
br i1 %83, label %87, label %84
84: ; preds = %81
%85 = xor i64 %82, -1
%86 = add i64 %6, %85
br label %87
87: ; preds = %81, %84, %78
%88 = phi i64 [ %86, %84 ], [ %82, %81 ], [ %79, %78 ]
%89 = getelementptr inbounds double, double* %3, i64 %65
%90 = load double, double* %89
%91 = getelementptr inbounds double, double* %0, i64 %88
%92 = load double, double* %91
%93 = tail call double @llvm.fmuladd.f64(double %90, double %92, double %63)
store double %93, double* %61
%94 = add nsw i64 %64, 2
%95 = icmp slt i64 %94, %4
br i1 %95, label %62, label %96
96: ; preds = %87, %59
%97 = add nuw nsw i64 %16, 1
%98 = icmp eq i64 %97, %1
br i1 %98, label %14, label %15
99: ; preds = %14, %99
%100 = phi i64 [ %101, %99 ], [ %6, %14 ]
%101 = add nsw i64 %100, -1
%102 = getelementptr inbounds double, double* %2, i64 %101
%103 = load double, double* %102
%104 = add nsw i64 %100, -2
%105 = getelementptr inbounds double, double* %2, i64 %104
%106 = load double, double* %105
%107 = fadd double %103, %106
%108 = fmul double %107, 5.000000e-01
store double %108, double* %102
%109 = icmp sgt i64 %100, 2
br i1 %109, label %99, label %110
110: ; preds = %99, %5, %14
%111 = load double, double* %2
%112 = fmul double %111, 5.000000e-01
store double %112, double* %2
ret void
}