From 8c47ad9366ff3674d82aef2b8374fbb890ebee42 Mon Sep 17 00:00:00 2001
From: Aaron Councilman <aaronjc4@illinois.edu>
Date: Mon, 17 Feb 2025 18:38:41 -0600
Subject: [PATCH] Add explicit clone to cfd and allow gpu float error

---
 juno_samples/rodinia/cfd/src/euler.jn     | 16 +++++++++++++++-
 juno_samples/rodinia/cfd/src/main.rs      | 23 ++++++++++++-----------
 juno_samples/rodinia/cfd/src/pre_euler.jn | 16 +++++++++++++++-
 3 files changed, 42 insertions(+), 13 deletions(-)

diff --git a/juno_samples/rodinia/cfd/src/euler.jn b/juno_samples/rodinia/cfd/src/euler.jn
index 42663305..5645823a 100644
--- a/juno_samples/rodinia/cfd/src/euler.jn
+++ b/juno_samples/rodinia/cfd/src/euler.jn
@@ -249,6 +249,20 @@ fn time_step<nelr: usize>(
   return variables;
 }
 
+fn copy_vars<nelr: usize>(variables: Variables::<nelr>) -> Variables::<nelr> {
+  let result : Variables::<nelr>;
+
+  for i = 0 to nelr {
+    result.density[i] = variables.density[i];
+    result.momentum.x[i] = variables.momentum.x[i];
+    result.momentum.y[i] = variables.momentum.y[i];
+    result.momentum.z[i] = variables.momentum.z[i];
+    result.energy[i] = variables.energy[i];
+  }
+
+  return result;
+}
+
 #[entry]
 fn euler<nelr: usize>(
   iterations: usize,
@@ -263,7 +277,7 @@ fn euler<nelr: usize>(
   ff_flux_contribution_momentum_z: float3,
 ) -> Variables::<nelr> {
   for i = 0 to iterations {
-    let old_variables = variables;
+    let old_variables = copy_vars::<nelr>(variables);
     let step_factors = compute_step_factor::<nelr>(variables, areas);
 
     for j = 0 to RK {
diff --git a/juno_samples/rodinia/cfd/src/main.rs b/juno_samples/rodinia/cfd/src/main.rs
index 80e177c1..0f2ae3b8 100644
--- a/juno_samples/rodinia/cfd/src/main.rs
+++ b/juno_samples/rodinia/cfd/src/main.rs
@@ -34,7 +34,7 @@ fn run_euler(
     ff_fc_momentum_y: &Float3,
     ff_fc_momentum_z: &Float3,
 ) -> Vec<f32> {
-    let mut variables = HerculesMutBox::from(variables);
+    let variables = HerculesImmBox::from(variables.as_slice());
     let areas = HerculesImmBox::from(areas);
     let elements_surrounding_elements = HerculesImmBox::from(elements_surrounding_elements);
     let normals = HerculesImmBox::from(normals);
@@ -87,7 +87,7 @@ fn run_pre_euler(
     ff_fc_momentum_y: &Float3,
     ff_fc_momentum_z: &Float3,
 ) -> Vec<f32> {
-    let mut variables = HerculesMutBox::from(variables);
+    let variables = HerculesImmBox::from(variables.as_slice());
     let areas = HerculesImmBox::from(areas);
     let elements_surrounding_elements = HerculesImmBox::from(elements_surrounding_elements);
     let normals = HerculesImmBox::from(normals);
@@ -127,6 +127,15 @@ fn run_pre_euler(
     .to_vec()
 }
 
+fn compare_float(x: f32, y: f32) -> bool {
+    (x - y).abs() < 1e-5
+}
+
+fn compare_floats(xs: &[f32], ys: &[f32]) -> bool {
+    xs.len() == ys.len()
+        && xs.iter().zip(ys.iter()).all(|(x, y)| compare_float(*x, *y))
+}
+
 fn cfd_harness(args: CFDInputs) {
     let CFDInputs {
         data_file,
@@ -213,15 +222,7 @@ fn cfd_harness(args: CFDInputs) {
             )
         };
 
-    if res_juno != res_rust {
-        let len = res_juno.len();
-        let diff =
-            res_juno.into_iter()
-                    .zip(res_rust.into_iter())
-                    .enumerate()
-                    .filter(|(_, (x, y))| x != y)
-                    .collect::<Vec<_>>();
-        println!("Mismatch at {} locations of {}", diff.len(), len);
+    if !compare_floats(&res_juno, &res_rust) {
         panic!("Mismatch in results");
     }
 }
diff --git a/juno_samples/rodinia/cfd/src/pre_euler.jn b/juno_samples/rodinia/cfd/src/pre_euler.jn
index b4071d7d..d5499c96 100644
--- a/juno_samples/rodinia/cfd/src/pre_euler.jn
+++ b/juno_samples/rodinia/cfd/src/pre_euler.jn
@@ -328,6 +328,20 @@ fn time_step<nelr: usize>(
   return variables;
 }
 
+fn copy_vars<nelr: usize>(variables: Variables::<nelr>) -> Variables::<nelr> {
+  let result : Variables::<nelr>;
+
+  for i = 0 to nelr {
+    result.density[i] = variables.density[i];
+    result.momentum.x[i] = variables.momentum.x[i];
+    result.momentum.y[i] = variables.momentum.y[i];
+    result.momentum.z[i] = variables.momentum.z[i];
+    result.energy[i] = variables.energy[i];
+  }
+
+  return result;
+}
+
 #[entry]
 fn pre_euler<nelr: usize>(
   iterations: usize,
@@ -342,7 +356,7 @@ fn pre_euler<nelr: usize>(
   ff_fc_momentum_z: float3,
 ) -> Variables::<nelr> {
   for i = 0 to iterations {
-    let old_variables = variables;
+    let old_variables = copy_vars::<nelr>(variables);
     let step_factors = compute_step_factor::<nelr>(variables, areas);
 
     for j = 0 to RK {
-- 
GitLab