void lorenz(const double *x, double *restrict y) {
  y[0] = 10.0 * (x[1] - x[0]);
  y[1] = 28.0 * x[0] - x[1] - x[0] * x[2];
  y[2] = x[0] * x[1] - (8.0 / 3.0) * x[2];
}


x86 assembly (clang, -O0):
<lorenz>:
push   %rbp
mov    %rsp,%rbp
mov    %rdi,-0x8(%rbp)
mov    %rsi,-0x10(%rbp)
mov    -0x8(%rbp),%rax
movsd  0x8(%rax),%xmm1
mov    -0x8(%rbp),%rax
subsd  (%rax),%xmm1
movsd  0xeeb(%rip),%xmm0
mulsd  %xmm1,%xmm0
mov    -0x10(%rbp),%rax
movsd  %xmm0,(%rax)
mov    -0x8(%rbp),%rax
movsd  (%rax),%xmm1
mov    -0x8(%rbp),%rax
movsd  0x8(%rax),%xmm0
movq   %xmm0,%rax
movabs $0x8000000000000000,%rcx
xor    %rcx,%rax
movq   %rax,%xmm0
movsd  0xea7(%rip),%xmm2
mulsd  %xmm2,%xmm1
addsd  %xmm0,%xmm1
mov    -0x8(%rbp),%rax
movsd  (%rax),%xmm0
mov    -0x8(%rbp),%rax
movsd  0x10(%rax),%xmm2
movq   %xmm0,%rax
movabs $0x8000000000000000,%rcx
xor    %rcx,%rax
movq   %rax,%xmm0
mulsd  %xmm2,%xmm0
addsd  %xmm1,%xmm0
mov    -0x10(%rbp),%rax
movsd  %xmm0,0x8(%rax)
mov    -0x8(%rbp),%rax
movsd  (%rax),%xmm0
mov    -0x8(%rbp),%rax
movsd  0x8(%rax),%xmm2
mov    -0x8(%rbp),%rax
movsd  0xe41(%rip),%xmm1
mulsd  0x10(%rax),%xmm1
movq   %xmm1,%rax
movabs $0x8000000000000000,%rcx
xor    %rcx,%rax
movq   %rax,%xmm1
mulsd  %xmm2,%xmm0
addsd  %xmm1,%xmm0
mov    -0x10(%rbp),%rax
movsd  %xmm0,0x10(%rax)
pop    %rbp
ret

x86 assembly (clang, -O2):
<lorenz>:
movsd  (%rdi),%xmm0
movupd 0x8(%rdi),%xmm1
movapd %xmm1,%xmm2
subsd  %xmm0,%xmm2
mulsd  0xee7(%rip),%xmm2
movsd  %xmm2,(%rsi)
movsd  0xee3(%rip),%xmm2
mulsd  %xmm0,%xmm2
subsd  %xmm1,%xmm2
movapd 0xeeb(%rip),%xmm3
xorpd  %xmm0,%xmm3
movapd %xmm1,%xmm4
unpckhpd %xmm1,%xmm4
mulsd  0xec7(%rip),%xmm4
unpcklpd %xmm4,%xmm2
unpcklpd %xmm0,%xmm3
shufpd $0x1,%xmm1,%xmm1
mulpd  %xmm3,%xmm1
addpd  %xmm2,%xmm1
movupd %xmm1,0x8(%rsi)
ret

LLVM IR (-O0):
define void @lorenz(double* %0, double* noalias %1) {
%3 = alloca double*
%4 = alloca double*
store double* %0, double** %3
store double* %1, double** %4
%5 = load double*, double** %3
%6 = getelementptr inbounds double, double* %5, i64 1
%7 = load double, double* %6
%8 = load double*, double** %3
%9 = getelementptr inbounds double, double* %8, i64 0
%10 = load double, double* %9
%11 = fsub double %7, %10
%12 = fmul double 1.000000e+01, %11
%13 = load double*, double** %4
%14 = getelementptr inbounds double, double* %13, i64 0
store double %12, double* %14
%15 = load double*, double** %3
%16 = getelementptr inbounds double, double* %15, i64 0
%17 = load double, double* %16
%18 = load double*, double** %3
%19 = getelementptr inbounds double, double* %18, i64 1
%20 = load double, double* %19
%21 = fneg double %20
%22 = call double @llvm.fmuladd.f64(double 2.800000e+01, double %17, double %21)
%23 = load double*, double** %3
%24 = getelementptr inbounds double, double* %23, i64 0
%25 = load double, double* %24
%26 = load double*, double** %3
%27 = getelementptr inbounds double, double* %26, i64 2
%28 = load double, double* %27
%29 = fneg double %25
%30 = call double @llvm.fmuladd.f64(double %29, double %28, double %22)
%31 = load double*, double** %4
%32 = getelementptr inbounds double, double* %31, i64 1
store double %30, double* %32
%33 = load double*, double** %3
%34 = getelementptr inbounds double, double* %33, i64 0
%35 = load double, double* %34
%36 = load double*, double** %3
%37 = getelementptr inbounds double, double* %36, i64 1
%38 = load double, double* %37
%39 = load double*, double** %3
%40 = getelementptr inbounds double, double* %39, i64 2
%41 = load double, double* %40
%42 = fmul double 0x4005555555555555, %41
%43 = fneg double %42
%44 = call double @llvm.fmuladd.f64(double %35, double %38, double %43)
%45 = load double*, double** %4
%46 = getelementptr inbounds double, double* %45, i64 2
store double %44, double* %46
ret void
}

LLVM IR (-O2):
define void @lorenz(double* nocapture %0, double* noalias nocapture writeonly %1) {
%3 = getelementptr inbounds double, double* %0, i64 1
%4 = load double, double* %0
%5 = bitcast double* %3 to <2 x double>*
%6 = load <2 x double>, <2 x double>* %5
%7 = extractelement <2 x double> %6, i64 0
%8 = fsub double %7, %4
%9 = fmul double %8, 1.000000e+01
store double %9, double* %1
%10 = fneg double %7
%11 = tail call double @llvm.fmuladd.f64(double %4, double 2.800000e+01, double %10)
%12 = fneg double %4
%13 = getelementptr inbounds double, double* %1, i64 1
%14 = extractelement <2 x double> %6, i64 1
%15 = fmul double %14, 0xC005555555555555
%16 = insertelement <2 x double> poison, double %4, i64 0
%17 = insertelement <2 x double> %16, double %12, i64 1
%18 = insertelement <2 x double> poison, double %15, i64 0
%19 = insertelement <2 x double> %18, double %11, i64 1
%20 = call <2 x double> @llvm.fmuladd.v2f64(<2 x double> %17, <2 x double> %6, <2 x double> %19)
%21 = shufflevector <2 x double> %20, <2 x double> poison, <2 x i32> <i32 1, i32 0>
%22 = bitcast double* %13 to <2 x double>*
store <2 x double> %21, <2 x double>* %22
ret void
}