SpECTRE Documentation Coverage Report
Current view: top level - Evolution/Particles/MonteCarlo/Actions - FluidCouplingAction.hpp Coverage Total Hit
Commit: 0d1d717af84a81fb1284a20c4013708fe85cc2f0 Lines: 14.3 % 7 1
Test Date: 2026-10-22 17:29:42
Legend: Lines:     hit not hit

            Line data    Source code
       1            0 : // Distributed under the MIT License.
       2              : // See LICENSE.txt for details.
       3              : 
       4              : #pragma once
       5              : 
       6              : #include "DataStructures/DataBox/DataBox.hpp"
       7              : #include "DataStructures/DataVector.hpp"
       8              : #include "DataStructures/Index.hpp"
       9              : #include "DataStructures/Tensor/Tensor.hpp"
      10              : #include "Evolution/DgSubcell/ActiveGrid.hpp"
      11              : #include "Evolution/DgSubcell/Tags/ActiveGrid.hpp"
      12              : #include "Evolution/DgSubcell/Tags/Jacobians.hpp"
      13              : #include "Evolution/DgSubcell/Tags/Mesh.hpp"
      14              : #include "Evolution/Particles/MonteCarlo/CellVolume.hpp"
      15              : #include "Evolution/Particles/MonteCarlo/Tags.hpp"
      16              : #include "Evolution/Systems/GrMhd/ValenciaDivClean/Tags.hpp"
      17              : #include "Parallel/AlgorithmExecution.hpp"
      18              : #include "Parallel/GlobalCache.hpp"
      19              : 
      20            0 : namespace Particles::MonteCarlo {
      21              : 
      22              : /// Mutator adding the Monte-Carlo contribution
      23              : /// to the evolution of the fluid.
      24            1 : struct FluidCouplingMutator {
      25            0 :   static const size_t Dim = 3;
      26              : 
      27              :   // We modify the fluid evolved variables, and reset the coupling
      28              :   // terms to zero.
      29            0 :   using return_tags =
      30              :       tmpl::list<grmhd::ValenciaDivClean::Tags::TildeTau,
      31              :                  grmhd::ValenciaDivClean::Tags::TildeYe,
      32              :                  grmhd::ValenciaDivClean::Tags::TildeS<Frame::Inertial>,
      33              :                  Particles::MonteCarlo::Tags::CouplingTildeTau<DataVector>,
      34              :                  Particles::MonteCarlo::Tags::CouplingTildeRhoYe<DataVector>,
      35              :                  Particles::MonteCarlo::Tags::CouplingTildeS<DataVector, Dim>>;
      36            0 :   using argument_tags = tmpl::list<
      37              :       evolution::dg::subcell::Tags::Mesh<Dim>,
      38              :       evolution::dg::subcell::Tags::ActiveGrid,
      39              :       evolution::dg::subcell::fd::Tags::DetInverseJacobianLogicalToInertial>;
      40              : 
      41            0 :   static void apply(
      42              :       const gsl::not_null<Scalar<DataVector>*> tilde_tau,
      43              :       const gsl::not_null<Scalar<DataVector>*> tilde_ye,
      44              :       const gsl::not_null<tnsr::i<DataVector, Dim>*> tilde_s,
      45              :       const gsl::not_null<Scalar<DataVector>*> coupling_tilde_tau,
      46              :       const gsl::not_null<Scalar<DataVector>*> coupling_tilde_rho_ye,
      47              :       const gsl::not_null<tnsr::i<DataVector, Dim>*> coupling_tilde_s,
      48              :       const Mesh<Dim>& mesh,
      49              :       const evolution::dg::subcell::ActiveGrid& active_grid,
      50              :       const Scalar<DataVector>& det_inverse_jacobian_logical_to_inertial) {
      51              :     // Currently, MC skips all non-communication actions when not using
      52              :     // Subcell.
      53              :     if (active_grid != evolution::dg::subcell::ActiveGrid::Subcell) {
      54              :       return;
      55              :     }
      56              : 
      57              :     // Coupling terms are on the mesh with ghost zones, while the evolved
      58              :     // variables are not. We also need to normalize the coupling terms with the
      59              :     // cell volume to get the evolution of energy/momentum density
      60              :     const Index<3>& extents = mesh.extents();
      61              :     const size_t num_ghost_zones = 1;
      62              :     const Index<3> extents_with_ghost{extents[0] + 2 * num_ghost_zones,
      63              :                                       extents[1] + 2 * num_ghost_zones,
      64              :                                       extents[2] + 2 * num_ghost_zones};
      65              : 
      66              :     Scalar<DataVector> det_jacobian_logical_to_inertial(*tilde_tau);
      67              :     get(det_jacobian_logical_to_inertial) =
      68              :         1.0 / get(det_inverse_jacobian_logical_to_inertial);
      69              :     Scalar<DataVector> cell_inertial_three_volume =
      70              :         make_with_value<Scalar<DataVector>>(*tilde_tau, 0.0);
      71              :     cell_inertial_coordinate_three_volume_finite_difference(
      72              :         &cell_inertial_three_volume, mesh, det_jacobian_logical_to_inertial);
      73              : 
      74              :     for (size_t i = 0; i < extents[0]; i++) {
      75              :       for (size_t j = 0; j < extents[1]; j++) {
      76              :         for (size_t k = 0; k < extents[2]; k++) {
      77              :           // The coupling terms are computed on a grid with ghost zone points,
      78              :           // the fluid variables are on the grid without GZ points
      79              :           // Index without GZ
      80              :           const size_t local_idx = collapsed_index(Index<3>{i, j, k}, extents);
      81              :           // Index with GZ
      82              :           const size_t extended_idx =
      83              :               collapsed_index(Index<3>{i + num_ghost_zones, j + num_ghost_zones,
      84              :                                        k + num_ghost_zones},
      85              :                               extents_with_ghost);
      86              :           // The MC coupling calculates the change in energy, momentum, and
      87              :           // lepton number. We need to divide by the cell 3-volume to get
      88              :           // the change in the evolved variables.
      89              :           const double& volume = get(cell_inertial_three_volume)[local_idx];
      90              :           get(*tilde_tau)[local_idx] +=
      91              :               get(*coupling_tilde_tau)[extended_idx] / volume;
      92              :           get(*tilde_ye)[local_idx] +=
      93              :               get(*coupling_tilde_rho_ye)[extended_idx] / volume;
      94              :           for (size_t d = 0; d < 3; d++) {
      95              :             tilde_s->get(d)[local_idx] +=
      96              :                 coupling_tilde_s->get(d)[extended_idx] / volume;
      97              :           }
      98              :         }
      99              :       }
     100              :     }
     101              :     // Reset coupling terms to 0 after use
     102              :     get(*coupling_tilde_tau) = 0.0;
     103              :     get(*coupling_tilde_rho_ye) = 0.0;
     104              :     for (size_t d = 0; d < 3; d++) {
     105              :       coupling_tilde_s->get(d) = 0.0;
     106              :     }
     107              :   }
     108              : };
     109              : 
     110              : }  // namespace Particles::MonteCarlo
        

Generated by: LCOV version 2.0-1