Alsvinn  0.5.3
The fast FVM simulator with UQ support
numflux_util.hpp
Go to the documentation of this file.
1 /* Copyright (c) 2018 ETH Zurich, Kjetil Olsen Lye
2  * This program is free software: you can redistribute it and/or modify
3  * it under the terms of the GNU General Public License as published by
4  * the Free Software Foundation, either version 3 of the License, or
5  * (at your option) any later version.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program. If not, see <http://www.gnu.org/licenses/>.
14  */
15 
16 #pragma once
17 #include <array>
18 #include <type_traits>
19 #include "alsfvm/types.hpp"
20 
24 namespace alsfvm {
25 namespace numflux {
27 template <typename T>
28 class has_stencil {
29  typedef char one;
30  typedef long two;
31 
32  template <typename C> static one test(decltype(&C::hasStencil));
33  template <typename C> static two test(...);
34 
35 public:
36  enum { value = sizeof(test<T>(0)) == sizeof(char) };
37 };
38 // The following are two functions to get the
39 // stencil for a numerical flux. The default
40 // stencil is always "0,1", while some fluxes
41 // may have a larger stencil
42 
44 template<class NumericalFluxType>
45 
46 __device__ __host__ auto getStencil(NumericalFluxType)
47 -> typename
48 std::enable_if<has_stencil<NumericalFluxType>::value, decltype(NumericalFluxType::stencil())>::type {
49  return NumericalFluxType::stencil();
50 }
51 
54 template<class NumericalFluxType>
55 
57 typename std::enable_if < !has_stencil<NumericalFluxType>::value,
58 ivec2 >::type getStencil(NumericalFluxType) {
59  return { 0, 1 };
60 }
61 
62 template<class Flux, class Equation, size_t direction>
64  ivec2 indices,
65  typename Equation::ConstViews& left,
66  typename Equation::ConstViews& right,
67  typename Equation::ConservedVariables& out) {
68 
69  const ivec3 directionVector(direction == 0, direction == 1, direction == 2);
70  // This needs to be done with some smart template recursion
71 
72  // This is the value for j+1/2
73  auto rightIndex = indices[1];
74  auto middleIndex = indices[0];
75  typename Equation::AllVariables rightJpHf = eq.fetchAllVariables(left,
76  rightIndex);
77 
78 
79  // This is the value for j+1/2
80  typename Equation::AllVariables leftJpHf = eq.fetchAllVariables(right,
81  middleIndex);
82 
83 
84 
85  // F(U_l, U_r)
86  typename Equation::ConservedVariables fluxMiddleRight;
87  real waveSpeed = Flux::template computeFlux<direction>(eq, leftJpHf, rightJpHf,
88  fluxMiddleRight);
89 
90  out = fluxMiddleRight;
91  return waveSpeed;
92 }
93 
96 template<class Flux, class Equation, size_t direction>
98  ivec4 indices,
99  typename Equation::ConstViews& left,
100  typename Equation::ConstViews& right,
101  typename Equation::ConservedVariables& out) {
102  const ivec3 directionVector(direction == 0, direction == 1, direction == 2);
103 
104  typename Equation::AllVariables u0 = eq.fetchAllVariables(left, indices[0]);
105  typename Equation::AllVariables u1 = eq.fetchAllVariables(left, indices[1]);
106  typename Equation::AllVariables u2 = eq.fetchAllVariables(left, indices[2]);
107  typename Equation::AllVariables u3 = eq.fetchAllVariables(left, indices[3]);
108 
109  //
110  typename Equation::ConservedVariables fluxMiddleRight;
111  real waveSpeed = Flux::template computeFlux<direction>(eq, u0, u1, u2, u3,
112  fluxMiddleRight);
113 
114  out = fluxMiddleRight;
115  return waveSpeed;
116 }
117 
120 template<class Flux, class Equation, size_t direction>
122  ivec6 indices,
123  typename Equation::ConstViews& left,
124  typename Equation::ConstViews& right,
125  typename Equation::ConservedVariables& out) {
126  const ivec3 directionVector(direction == 0, direction == 1, direction == 2);
127 
128  typename Equation::AllVariables u0 = eq.fetchAllVariables(left, indices[0]);
129  typename Equation::AllVariables u1 = eq.fetchAllVariables(left, indices[1]);
130  typename Equation::AllVariables u2 = eq.fetchAllVariables(left, indices[2]);
131  typename Equation::AllVariables u3 = eq.fetchAllVariables(left, indices[3]);
132  typename Equation::AllVariables u4 = eq.fetchAllVariables(left, indices[4]);
133  typename Equation::AllVariables u5 = eq.fetchAllVariables(left, indices[5]);
134 
135  //
136  typename Equation::ConservedVariables fluxMiddleRight;
137  real waveSpeed = Flux::template computeFlux<direction>(eq, u0, u1, u2, u3, u4,
138  u5, fluxMiddleRight);
139 
140  out = fluxMiddleRight;
141  return waveSpeed;
142 }
143 
144 }
145 }
Definition: vec4.hpp:25
#define __host__
Definition: types.hpp:46
VolumeType type
Definition: VolumeFactory.cpp:85
Definition: vec2.hpp:24
double real
Definition: types.hpp:65
__device__ __host__ auto getStencil(NumericalFluxType) -> typename std::enable_if< has_stencil< NumericalFluxType >::value, decltype(NumericalFluxType::stencil())>::type
Gets the stencil for numerical fluxes that have a stencil defined.
Definition: numflux_util.hpp:46
SFINAE test, see http://stackoverflow.com/a/257382.
Definition: numflux_util.hpp:28
#define __device__
Definition: types.hpp:45
__device__ __host__ real computeFluxForStencil(const Equation &eq, ivec2 indices, typename Equation::ConstViews &left, typename Equation::ConstViews &right, typename Equation::ConservedVariables &out)
Definition: numflux_util.hpp:63
Various utility functions to implement the tecno flux.
Definition: types.hpp:30
Definition: numflux_util.hpp:36