void CopyArray2(float *a, float *b, int len) {
  int i = 0;
  while (i < len) {
    b[i] = a[i];
    b[i + 1] = a[i + 1];
    i += 2;
  }
}


x86 assembly (clang, -O0):
<CopyArray2>:
push   %rbp
mov    %rsp,%rbp
mov    %rdi,-0x8(%rbp)
mov    %rsi,-0x10(%rbp)
mov    %edx,-0x14(%rbp)
movl   $0x0,-0x18(%rbp)
mov    -0x18(%rbp),%eax
cmp    -0x14(%rbp),%eax
jge    116e <CopyArray2+0x6e>
mov    -0x8(%rbp),%rax
movslq -0x18(%rbp),%rcx
movss  (%rax,%rcx,4),%xmm0
mov    -0x10(%rbp),%rax
movslq -0x18(%rbp),%rcx
movss  %xmm0,(%rax,%rcx,4)
mov    -0x8(%rbp),%rax
mov    -0x18(%rbp),%ecx
add    $0x1,%ecx
movslq %ecx,%rcx
movss  (%rax,%rcx,4),%xmm0
mov    -0x10(%rbp),%rax
mov    -0x18(%rbp),%ecx
add    $0x1,%ecx
movslq %ecx,%rcx
movss  %xmm0,(%rax,%rcx,4)
mov    -0x18(%rbp),%eax
add    $0x2,%eax
mov    %eax,-0x18(%rbp)
jmp    1116 <CopyArray2+0x16>
pop    %rbp
ret

x86 assembly (clang, -O2):
<CopyArray2>:
test   %edx,%edx
jle    11ff <CopyArray2+0xff>
mov    %edx,%r10d
lea    -0x1(%r10),%r9
cmp    $0x6,%r9
jae    111c <CopyArray2+0x1c>
xor    %ecx,%ecx
jmp    11e0 <CopyArray2+0xe0>
lea    0x1(%r10),%rax
and    $0xfffffffffffffffe,%rax
lea    (%rdi,%rax,4),%rcx
cmp    %rsi,%rcx
jbe    113d <CopyArray2+0x3d>
lea    (%rsi,%rax,4),%rax
cmp    %rdi,%rax
jbe    113d <CopyArray2+0x3d>
xor    %ecx,%ecx
jmp    11e0 <CopyArray2+0xe0>
shr    %r9
add    $0x1,%r9
mov    %r9,%rcx
and    $0xfffffffffffffffc,%rcx
lea    -0x4(%rcx),%rax
mov    %rax,%r8
shr    $0x2,%r8
add    $0x1,%r8
test   %rax,%rax
je     1200 <CopyArray2+0x100>
mov    %r8,%rax
and    $0xfffffffffffffffe,%rax
xor    %edx,%edx
nopl   0x0(%rax)
movups (%rdi,%rdx,4),%xmm0
movups 0x10(%rdi,%rdx,4),%xmm1
movups %xmm0,(%rsi,%rdx,4)
movups %xmm1,0x10(%rsi,%rdx,4)
movups 0x20(%rdi,%rdx,4),%xmm0
movups 0x30(%rdi,%rdx,4),%xmm1
movups %xmm0,0x20(%rsi,%rdx,4)
movups %xmm1,0x30(%rsi,%rdx,4)
add    $0x10,%rdx
add    $0xfffffffffffffffe,%rax
jne    1170 <CopyArray2+0x70>
test   $0x1,%r8b
je     11d3 <CopyArray2+0xd3>
lea    0x0(,%rdx,4),%rax
mov    %rax,%r8
or     $0x10,%r8
movups (%rdi,%rdx,4),%xmm0
movups (%rdi,%r8,1),%xmm1
mov    %rax,%rdx
or     $0x4,%rdx
or     $0x14,%rax
movups %xmm0,-0x4(%rsi,%rdx,1)
movups %xmm1,-0x4(%rsi,%rax,1)
cmp    %rcx,%r9
je     11ff <CopyArray2+0xff>
add    %rcx,%rcx
nopl   0x0(%rax,%rax,1)
movss  (%rdi,%rcx,4),%xmm0
movss  %xmm0,(%rsi,%rcx,4)
movss  0x4(%rdi,%rcx,4),%xmm0
movss  %xmm0,0x4(%rsi,%rcx,4)
add    $0x2,%rcx
cmp    %r10,%rcx
jb     11e0 <CopyArray2+0xe0>
ret
xor    %edx,%edx
test   $0x1,%r8b
jne    11a6 <CopyArray2+0xa6>
jmp    11d3 <CopyArray2+0xd3>

LLVM IR (-O0):
define void @CopyArray2(float* %0, float* %1, i32 %2) {
%4 = alloca float*
%5 = alloca float*
%6 = alloca i32
%7 = alloca i32
store float* %0, float** %4
store float* %1, float** %5
store i32 %2, i32* %6
store i32 0, i32* %7
br label %8
8: ; preds = %12, %3
%9 = load i32, i32* %7
%10 = load i32, i32* %6
%11 = icmp slt i32 %9, %10
br i1 %11, label %12, label %35
12: ; preds = %8
%13 = load float*, float** %4
%14 = load i32, i32* %7
%15 = sext i32 %14 to i64
%16 = getelementptr inbounds float, float* %13, i64 %15
%17 = load float, float* %16
%18 = load float*, float** %5
%19 = load i32, i32* %7
%20 = sext i32 %19 to i64
%21 = getelementptr inbounds float, float* %18, i64 %20
store float %17, float* %21
%22 = load float*, float** %4
%23 = load i32, i32* %7
%24 = add nsw i32 %23, 1
%25 = sext i32 %24 to i64
%26 = getelementptr inbounds float, float* %22, i64 %25
%27 = load float, float* %26
%28 = load float*, float** %5
%29 = load i32, i32* %7
%30 = add nsw i32 %29, 1
%31 = sext i32 %30 to i64
%32 = getelementptr inbounds float, float* %28, i64 %31
store float %27, float* %32
%33 = load i32, i32* %7
%34 = add nsw i32 %33, 2
store i32 %34, i32* %7
br label %8
35: ; preds = %8
ret void
}

LLVM IR (-O2):
define void @CopyArray2(float* nocapture %0, float* nocapture writeonly %1, i32 %2) {
%4 = icmp sgt i32 %2, 0
br i1 %4, label %5, label %104
5: ; preds = %3
%6 = zext i32 %2 to i64
%7 = add nsw i64 %6, -1
%8 = lshr i64 %7, 1
%9 = add nuw i64 %8, 1
%10 = icmp ult i64 %7, 6
br i1 %10, label %91, label %11
11: ; preds = %5
%12 = add nuw nsw i64 %6, 1
%13 = and i64 %12, 8589934590
%14 = getelementptr float, float* %1, i64 %13
%15 = getelementptr float, float* %0, i64 %13
%16 = icmp ugt float* %15, %1
%17 = icmp ugt float* %14, %0
%18 = and i1 %16, %17
br i1 %18, label %91, label %19
19: ; preds = %11
%20 = and i64 %9, -4
%21 = shl i64 %20, 1
%22 = add i64 %20, -4
%23 = lshr exact i64 %22, 2
%24 = add nuw nsw i64 %23, 1
%25 = and i64 %24, 1
%26 = icmp eq i64 %22, 0
br i1 %26, label %70, label %27
27: ; preds = %19
%28 = and i64 %24, 9223372036854775806
%29 = getelementptr inbounds float, float* %1, i64 -1
%30 = getelementptr inbounds float, float* %1, i64 -1
%31 = getelementptr inbounds float, float* %1, i64 -1
%32 = getelementptr inbounds float, float* %1, i64 -1
br label %33
33: ; preds = %33, %27
%34 = phi i64 [ 0, %27 ], [ %65, %33 ]
%35 = phi i64 [ 0, %27 ], [ %66, %33 ]
%36 = shl i64 %34, 1
%37 = or i64 %36, 4
%38 = getelementptr inbounds float, float* %0, i64 %36
%39 = getelementptr inbounds float, float* %0, i64 %37
%40 = bitcast float* %38 to <4 x float>*
%41 = bitcast float* %39 to <4 x float>*
%42 = load <4 x float>, <4 x float>* %40
%43 = load <4 x float>, <4 x float>* %41
%44 = or i64 %36, 1
%45 = or i64 %36, 5
%46 = getelementptr inbounds float, float* %29, i64 %44
%47 = bitcast float* %46 to <4 x float>*
%48 = getelementptr inbounds float, float* %30, i64 %45
%49 = bitcast float* %48 to <4 x float>*
store <4 x float> %42, <4 x float>* %47
store <4 x float> %43, <4 x float>* %49
%50 = shl i64 %34, 1
%51 = or i64 %50, 8
%52 = or i64 %50, 12
%53 = getelementptr inbounds float, float* %0, i64 %51
%54 = getelementptr inbounds float, float* %0, i64 %52
%55 = bitcast float* %53 to <4 x float>*
%56 = bitcast float* %54 to <4 x float>*
%57 = load <4 x float>, <4 x float>* %55
%58 = load <4 x float>, <4 x float>* %56
%59 = or i64 %50, 9
%60 = or i64 %50, 13
%61 = getelementptr inbounds float, float* %31, i64 %59
%62 = bitcast float* %61 to <4 x float>*
%63 = getelementptr inbounds float, float* %32, i64 %60
%64 = bitcast float* %63 to <4 x float>*
store <4 x float> %57, <4 x float>* %62
store <4 x float> %58, <4 x float>* %64
%65 = add nuw i64 %34, 8
%66 = add i64 %35, 2
%67 = icmp eq i64 %66, %28
br i1 %67, label %68, label %33
68: ; preds = %33
%69 = shl i64 %65, 1
br label %70
70: ; preds = %68, %19
%71 = phi i64 [ 0, %19 ], [ %69, %68 ]
%72 = icmp eq i64 %25, 0
br i1 %72, label %89, label %73
73: ; preds = %70
%74 = or i64 %71, 4
%75 = getelementptr inbounds float, float* %0, i64 %71
%76 = getelementptr inbounds float, float* %0, i64 %74
%77 = bitcast float* %75 to <4 x float>*
%78 = bitcast float* %76 to <4 x float>*
%79 = load <4 x float>, <4 x float>* %77
%80 = load <4 x float>, <4 x float>* %78
%81 = or i64 %71, 1
%82 = or i64 %71, 5
%83 = getelementptr inbounds float, float* %1, i64 -1
%84 = getelementptr inbounds float, float* %1, i64 -1
%85 = getelementptr inbounds float, float* %83, i64 %81
%86 = bitcast float* %85 to <4 x float>*
%87 = getelementptr inbounds float, float* %84, i64 %82
%88 = bitcast float* %87 to <4 x float>*
store <4 x float> %79, <4 x float>* %86
store <4 x float> %80, <4 x float>* %88
br label %89
89: ; preds = %70, %73
%90 = icmp eq i64 %9, %20
br i1 %90, label %104, label %91
91: ; preds = %11, %5, %89
%92 = phi i64 [ 0, %11 ], [ 0, %5 ], [ %21, %89 ]
br label %93
93: ; preds = %91, %93
%94 = phi i64 [ %102, %93 ], [ %92, %91 ]
%95 = getelementptr inbounds float, float* %0, i64 %94
%96 = load float, float* %95
%97 = getelementptr inbounds float, float* %1, i64 %94
store float %96, float* %97
%98 = or i64 %94, 1
%99 = getelementptr inbounds float, float* %0, i64 %98
%100 = load float, float* %99
%101 = getelementptr inbounds float, float* %1, i64 %98
store float %100, float* %101
%102 = add nuw nsw i64 %94, 2
%103 = icmp ult i64 %102, %6
br i1 %103, label %93, label %104
104: ; preds = %93, %89, %3
ret void
}