double overlap(int num_asym_sd, int num_sym_sd, double *trans_contr,
               double *final_eigen) {
  int number;
  double *eigen_ptr, result;
  result = 0.0;
  number = num_asym_sd;
  if (number) {
    eigen_ptr = final_eigen;
    do {
      result += (*(eigen_ptr++)) * (*(trans_contr++));
    } while (--number);
  }
  if ((number = num_sym_sd)) {
    eigen_ptr = final_eigen + num_asym_sd;
    do {
      result += (*(eigen_ptr++)) * (*(trans_contr++));
    } while (--number);
  }
  return result;
}


x86 assembly (clang, -O0):
<overlap>:
push   %rbp
mov    %rsp,%rbp
mov    %edi,-0x4(%rbp)
mov    %esi,-0x8(%rbp)
mov    %rdx,-0x10(%rbp)
mov    %rcx,-0x18(%rbp)
xorps  %xmm0,%xmm0
movsd  %xmm0,-0x30(%rbp)
mov    -0x4(%rbp),%eax
mov    %eax,-0x1c(%rbp)
cmpl   $0x0,-0x1c(%rbp)
je     1181 <overlap+0x81>
mov    -0x18(%rbp),%rax
mov    %rax,-0x28(%rbp)
mov    -0x28(%rbp),%rax
mov    %rax,%rcx
add    $0x8,%rcx
mov    %rcx,-0x28(%rbp)
movsd  (%rax),%xmm0
mov    -0x10(%rbp),%rax
mov    %rax,%rcx
add    $0x8,%rcx
mov    %rcx,-0x10(%rbp)
movsd  (%rax),%xmm2
movsd  -0x30(%rbp),%xmm1
mulsd  %xmm2,%xmm0
addsd  %xmm1,%xmm0
movsd  %xmm0,-0x30(%rbp)
mov    -0x1c(%rbp),%eax
add    $0xffffffff,%eax
mov    %eax,-0x1c(%rbp)
cmp    $0x0,%eax
jne    1132 <overlap+0x32>
jmp    1181 <overlap+0x81>
mov    -0x8(%rbp),%eax
mov    %eax,-0x1c(%rbp)
cmp    $0x0,%eax
je     11f2 <overlap+0xf2>
mov    -0x18(%rbp),%rax
movslq -0x4(%rbp),%rcx
shl    $0x3,%rcx
add    %rcx,%rax
mov    %rax,-0x28(%rbp)
mov    -0x28(%rbp),%rax
mov    %rax,%rcx
add    $0x8,%rcx
mov    %rcx,-0x28(%rbp)
movsd  (%rax),%xmm0
mov    -0x10(%rbp),%rax
mov    %rax,%rcx
add    $0x8,%rcx
mov    %rcx,-0x10(%rbp)
movsd  (%rax),%xmm2
movsd  -0x30(%rbp),%xmm1
mulsd  %xmm2,%xmm0
addsd  %xmm1,%xmm0
movsd  %xmm0,-0x30(%rbp)
mov    -0x1c(%rbp),%eax
add    $0xffffffff,%eax
mov    %eax,-0x1c(%rbp)
cmp    $0x0,%eax
jne    11a3 <overlap+0xa3>
jmp    11f2 <overlap+0xf2>
movsd  -0x30(%rbp),%xmm0
pop    %rbp
ret

x86 assembly (clang, -O2):
<overlap>:
test   %edi,%edi
je     114b <overlap+0x4b>
lea    -0x1(%rdi),%r8d
mov    %edi,%r10d
and    $0x3,%r10d
je     1151 <overlap+0x51>
xor    %eax,%eax
xorpd  %xmm0,%xmm0
mov    %rcx,%r9
nopw   0x0(%rax,%rax,1)
movsd  (%r9),%xmm1
add    $0x8,%r9
mulsd  (%rdx),%xmm1
add    $0x8,%rdx
addsd  %xmm1,%xmm0
add    $0x1,%eax
cmp    %eax,%r10d
jne    1120 <overlap+0x20>
mov    %edi,%r10d
sub    %eax,%r10d
cmp    $0x3,%r8d
jae    1161 <overlap+0x61>
jmp    11bb <overlap+0xbb>
xorpd  %xmm0,%xmm0
jmp    11bb <overlap+0xbb>
xorpd  %xmm0,%xmm0
mov    %edi,%r10d
mov    %rcx,%r9
cmp    $0x3,%r8d
jb     11bb <overlap+0xbb>
mov    %r10d,%r8d
xor    %eax,%eax
cs nopw 0x0(%rax,%rax,1)
movsd  (%r9,%rax,8),%xmm1
mulsd  (%rdx),%xmm1
movsd  0x8(%r9,%rax,8),%xmm2
addsd  %xmm0,%xmm1
mulsd  0x8(%rdx),%xmm2
addsd  %xmm1,%xmm2
movsd  0x10(%r9,%rax,8),%xmm1
mulsd  0x10(%rdx),%xmm1
addsd  %xmm2,%xmm1
movsd  0x18(%r9,%rax,8),%xmm0
mulsd  0x18(%rdx),%xmm0
add    $0x20,%rdx
addsd  %xmm1,%xmm0
add    $0x4,%rax
cmp    %eax,%r8d
jne    1170 <overlap+0x70>
test   %esi,%esi
je     1256 <overlap+0x156>
movslq %edi,%rax
lea    (%rcx,%rax,8),%rax
lea    -0x1(%rsi),%r8d
mov    %esi,%edi
and    $0x3,%edi
je     11fd <overlap+0xfd>
xor    %ecx,%ecx
nopw   0x0(%rax,%rax,1)
movsd  (%rax),%xmm1
add    $0x8,%rax
mulsd  (%rdx),%xmm1
add    $0x8,%rdx
addsd  %xmm1,%xmm0
add    $0x1,%ecx
cmp    %ecx,%edi
jne    11e0 <overlap+0xe0>
sub    %ecx,%esi
cmp    $0x3,%r8d
jb     1256 <overlap+0x156>
mov    %esi,%ecx
xor    %esi,%esi
nopw   0x0(%rax,%rax,1)
movsd  (%rax,%rsi,8),%xmm1
movsd  0x8(%rax,%rsi,8),%xmm2
mulsd  (%rdx,%rsi,8),%xmm1
mulsd  0x8(%rdx,%rsi,8),%xmm2
addsd  %xmm0,%xmm1
movsd  0x10(%rax,%rsi,8),%xmm3
mulsd  0x10(%rdx,%rsi,8),%xmm3
addsd  %xmm1,%xmm2
movsd  0x18(%rax,%rsi,8),%xmm0
mulsd  0x18(%rdx,%rsi,8),%xmm0
addsd  %xmm2,%xmm3
addsd  %xmm3,%xmm0
add    $0x4,%rsi
cmp    %esi,%ecx
jne    1210 <overlap+0x110>
ret

LLVM IR (-O0):
define double @overlap(i32 %0, i32 %1, double* %2, double* %3) {
%5 = alloca i32
%6 = alloca i32
%7 = alloca double*
%8 = alloca double*
%9 = alloca i32
%10 = alloca double*
%11 = alloca double
store i32 %0, i32* %5
store i32 %1, i32* %6
store double* %2, double** %7
store double* %3, double** %8
store double 0.000000e+00, double* %11
%12 = load i32, i32* %5
store i32 %12, i32* %9
%13 = load i32, i32* %9
%14 = icmp ne i32 %13, 0
br i1 %14, label %15, label %31
15: ; preds = %4
%16 = load double*, double** %8
store double* %16, double** %10
br label %17
17: ; preds = %26, %15
%18 = load double*, double** %10
%19 = getelementptr inbounds double, double* %18, i32 1
store double* %19, double** %10
%20 = load double, double* %18
%21 = load double*, double** %7
%22 = getelementptr inbounds double, double* %21, i32 1
store double* %22, double** %7
%23 = load double, double* %21
%24 = load double, double* %11
%25 = call double @llvm.fmuladd.f64(double %20, double %23, double %24)
store double %25, double* %11
br label %26
26: ; preds = %17
%27 = load i32, i32* %9
%28 = add nsw i32 %27, -1
store i32 %28, i32* %9
%29 = icmp ne i32 %28, 0
br i1 %29, label %17, label %30
30: ; preds = %26
br label %31
31: ; preds = %30, %4
%32 = load i32, i32* %6
store i32 %32, i32* %9
%33 = icmp ne i32 %32, 0
br i1 %33, label %34, label %53
34: ; preds = %31
%35 = load double*, double** %8
%36 = load i32, i32* %5
%37 = sext i32 %36 to i64
%38 = getelementptr inbounds double, double* %35, i64 %37
store double* %38, double** %10
br label %39
39: ; preds = %48, %34
%40 = load double*, double** %10
%41 = getelementptr inbounds double, double* %40, i32 1
store double* %41, double** %10
%42 = load double, double* %40
%43 = load double*, double** %7
%44 = getelementptr inbounds double, double* %43, i32 1
store double* %44, double** %7
%45 = load double, double* %43
%46 = load double, double* %11
%47 = call double @llvm.fmuladd.f64(double %42, double %45, double %46)
store double %47, double* %11
br label %48
48: ; preds = %39
%49 = load i32, i32* %9
%50 = add nsw i32 %49, -1
store i32 %50, i32* %9
%51 = icmp ne i32 %50, 0
br i1 %51, label %39, label %52
52: ; preds = %48
br label %53
53: ; preds = %52, %31
%54 = load double, double* %11
ret double %54
}

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