TrioCFD 1.9.9_beta
TrioCFD documentation
Loading...
Searching...
No Matches
Op_Div_VEFP1B_Elem.cpp
1/****************************************************************************
2* Copyright (c) 2026, CEA
3* All rights reserved.
4*
5* Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
6* 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
7* 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
8* 3. Neither the name of the copyright holder nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission.
9*
10* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
11* IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
12* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
13*
14*****************************************************************************/
15
16#include <Dirichlet_entree_fluide_leaves.h>
17#include <Check_espace_virtuel.h>
18#include <Op_Div_VEFP1B_Elem.h>
19#include <Dirichlet_homogene.h>
20#include <Schema_Temps_base.h>
21#include <Porosites_champ.h>
22#include <Neumann_val_ext.h>
23#include <Domaine_Cl_VEF.h>
24#include <communications.h>
25#include <EcrFicPartage.h>
26#include <Probleme_base.h>
27#include <VerifierCoin.h>
28#include <Domaine_VEF.h>
29#include <Periodique.h>
30#include <Dirichlet.h>
31#include <Symetrie.h>
32#include <Domaine.h>
33#include <SChaine.h>
34#include <Neumann.h>
35#include <Debog.h>
36#include <Device.h>
37
38Implemente_instanciable(Op_Div_VEFP1B_Elem, "Op_Div_VEFPreP1B_P1NC|Op_Div_VEF_P1NC", Operateur_Div_base);
39
40Sortie& Op_Div_VEFP1B_Elem::printOn(Sortie& s) const { return s << que_suis_je() ; }
41
42Entree& Op_Div_VEFP1B_Elem::readOn(Entree& is) { return is; }
43
44static int chercher_arete(int elem, int somi, int somj, const IntTab& elem_aretes, const IntTab& aretes_som)
45{
46 if (somi > somj)
47 {
48 int k = somi;
49 somi = somj;
50 somj = k;
51 }
52 for (int i_arete = 0; i_arete < 6; i_arete++)
53 {
54 int arete = elem_aretes(elem, i_arete);
55 int som1 = aretes_som(arete, 0);
56 if (somi == som1)
57 {
58 int som2 = aretes_som(arete, 1);
59 if (somj == som2)
60 return arete;
61 }
62 }
63 return -1;
64}
65
66static int verifier(const Op_Div_VEFP1B_Elem& op, int& init, const Domaine_VEF& domaine_VEF, const DoubleTab& vit, DoubleTab& div)
67{
68 init = 1;
69 DoubleTab v(vit);
70 v = 1;
71 DoubleTab r(div);
72 r = 0;
73 op.ajouter(v, r);
74 Cerr << "div(1,..,1) = " << r << finl;
75 Debog::verifier("div(1,..,1) =", r);
76 const DoubleTab& xv = domaine_VEF.xv();
77 v = xv;
78 {
79 for (int i = 0; i < v.dimension(0); i++)
80 v(i, 1) = 0;
81 }
82 r = 0;
83 op.ajouter(v, r);
84 Cerr << "div(x,0) = " << r << finl;
85 Debog::verifier("div(x,0) =", r);
86 return 1;
87}
88
89void Op_Div_VEFP1B_Elem::associer(const Domaine_dis_base& domaine_dis, const Domaine_Cl_dis_base& domaine_Cl_dis, const Champ_Inc_base&)
90{
91 le_dom_vef = ref_cast(Domaine_VEF, domaine_dis);
92 la_zcl_vef = ref_cast(Domaine_Cl_VEF, domaine_Cl_dis);
93}
94
95DoubleTab& Op_Div_VEFP1B_Elem::ajouter_elem(const DoubleTab& vit, DoubleTab& div) const
96{
97 const Domaine_VEF& domaine_VEF = ref_cast(Domaine_VEF, le_dom_vef.valeur());
98 assert(domaine_VEF.get_alphaE());
99 const Domaine& domaine = domaine_VEF.domaine();
100 const DoubleTab& face_normales = domaine_VEF.face_normales();
101 const IntTab& elem_faces = domaine_VEF.elem_faces();
102 const IntTab& face_voisins = domaine_VEF.face_voisins();
103 int nfe = domaine.nb_faces_elem();
104 int nb_elem = domaine.nb_elem();
105 int dim = Objet_U::dimension; // Objet_U::dimension can not be read from Kernel.
106
107 CIntTabView elem_faces_v = elem_faces.view_ro();
108 DoubleTabView div_v = div.view_rw(); // read-write
109 if (getenv("TRUST_USE_RANDOM_ACCESS")!=nullptr)
110 {
111 // Random access
112 RandomAccessView<int, 2> face_voisins_v = face_voisins.view_ro();
113 RandomAccessView<double, 2> face_normales_v = face_normales.view_ro();
114 RandomAccessView<double, 2> vit_v = vit.view_ro();
115 Kokkos::parallel_for(start_gpu_timer(__KERNEL_NAME__), nb_elem, KOKKOS_LAMBDA(
116 const int elem)
117 {
118 double pscf = 0;
119 for (int indice = 0; indice < nfe; indice++)
120 {
121 int face = elem_faces_v(elem, indice);
122 int signe = elem == face_voisins_v(face, 0) ? 1 : -1;
123 for (int comp = 0; comp < dim; comp++)
124 pscf += signe * vit_v(face, comp) * face_normales_v(face, comp);
125 }
126 div_v(elem, 0) += pscf;
127 });
128 }
129 else
130 {
131 CIntTabView face_voisins_v = face_voisins.view_ro();
132 CDoubleTabView face_normales_v = face_normales.view_ro();
133 CDoubleTabView vit_v = vit.view_ro();
134 Kokkos::parallel_for(start_gpu_timer(__KERNEL_NAME__), nb_elem, KOKKOS_LAMBDA(
135 const int elem)
136 {
137 double pscf = 0;
138 for (int indice = 0; indice < nfe; indice++)
139 {
140 int face = elem_faces_v(elem, indice);
141 int signe = elem == face_voisins_v(face, 0) ? 1 : -1;
142 for (int comp = 0; comp < dim; comp++)
143 pscf += signe * vit_v(face, comp) * face_normales_v(face, comp);
144 }
145 div_v(elem, 0) += pscf;
146 });
147 }
148 end_gpu_timer(__KERNEL_NAME__);
149 assert_invalide_items_non_calcules(div);
150 return div;
151}
152
153int find_cl_face(const Domaine& domaine, const int face)
154{
155 int i;
156 const int nb_cl = domaine.nb_front_Cl();
157 for (i = 0; i < nb_cl; i++)
158 {
159 const Frontiere& fr = domaine.frontiere(i);
160 const int debut = fr.num_premiere_face();
161 if (face >= debut && face < debut + fr.nb_faces())
162 return i;
163 const ArrOfInt& faces_virt = fr.get_faces_virt();
164 const int nb_faces_virt = faces_virt.size_array();
165 for (int j = 0; j < nb_faces_virt; j++)
166 if (face == faces_virt[j])
167 return i;
168 }
169 return -1;
170}
171
172KOKKOS_FUNCTION
173double calculer_coef_som(int type_elem, int dimension, int& nb_face_diri, int* indice_diri)
174{
175 if (type_elem == 0)
176 {
177 nb_face_diri = 0;
178 double coeff_som = 1. / (dimension * (dimension + 1));
179 return coeff_som;
180 }
181 else
182 {
183 if (dimension == 2)
184 {
185 switch(type_elem)
186 {
187 case 1:
188 nb_face_diri = 1;
189 indice_diri[0] = 2;
190 break;
191 case 2:
192 nb_face_diri = 1;
193 indice_diri[0] = 1;
194 break;
195 case 4:
196 nb_face_diri = 1;
197 indice_diri[0] = 0;
198 break;
199 case 3:
200 nb_face_diri = 2;
201 indice_diri[0] = 1;
202 indice_diri[1] = 2;
203 break;
204 case 5:
205 nb_face_diri = 2;
206 indice_diri[0] = 0;
207 indice_diri[1] = 2;
208 break;
209 case 6:
210 nb_face_diri = 2;
211 indice_diri[0] = 0;
212 indice_diri[1] = 1;
213 break;
214 default:
215 //abort();
216 break;
217 }
218 }
219 else if (dimension == 3)
220 {
221 switch(type_elem)
222 {
223 case 1:
224 nb_face_diri = 1;
225 indice_diri[0] = 3;
226 break;
227 case 2:
228 nb_face_diri = 1;
229 indice_diri[0] = 2;
230 break;
231 case 3:
232 nb_face_diri = 2;
233 indice_diri[0] = 3;
234 indice_diri[1] = 2;
235 break;
236 case 4:
237 nb_face_diri = 1;
238 indice_diri[0] = 1;
239 break;
240 case 5:
241 nb_face_diri = 2;
242 indice_diri[0] = 1;
243 indice_diri[1] = 3;
244 break;
245 case 6:
246 nb_face_diri = 2;
247 indice_diri[0] = 1;
248 indice_diri[1] = 2;
249 break;
250 case 7:
251 nb_face_diri = 3;
252 indice_diri[0] = 1;
253 indice_diri[1] = 2;
254 indice_diri[2] = 3;
255 break;
256 case 8:
257 nb_face_diri = 1;
258 indice_diri[0] = 0;
259 break;
260 case 9:
261 nb_face_diri = 2;
262 indice_diri[0] = 0;
263 indice_diri[1] = 3;
264 break;
265 case 10:
266 nb_face_diri = 2;
267 indice_diri[0] = 0;
268 indice_diri[1] = 2;
269 break;
270 case 11:
271 nb_face_diri = 3;
272 indice_diri[0] = 0;
273 indice_diri[1] = 2;
274 indice_diri[2] = 3;
275 break;
276 case 12:
277 nb_face_diri = 2;
278 indice_diri[0] = 0;
279 indice_diri[1] = 1;
280 break;
281 case 13:
282 nb_face_diri = 3;
283 indice_diri[0] = 0;
284 indice_diri[1] = 1;
285 indice_diri[2] = 3;
286 break;
287 case 14:
288 nb_face_diri = 3;
289 indice_diri[0] = 0;
290 indice_diri[1] = 1;
291 indice_diri[2] = 2;
292 break;
293 default:
294#ifndef TRUST_USE_GPU
295 abort();
296#endif
297 break;
298 }
299 }
300 else
301 {
302#ifndef TRUST_USE_GPU
303 abort();
304#endif
305 }
306 }
307 double coeff_som = 1. / (dimension * (dimension + 1 - nb_face_diri));
308 return coeff_som;
309}
310
311DoubleTab& Op_Div_VEFP1B_Elem::ajouter_som(const DoubleTab& tab_vit, DoubleTab& tab_div, DoubleTab& tab_flux_b) const
312{
313 const Domaine_VEF& domaine_VEF = ref_cast(Domaine_VEF, le_dom_vef.valeur());
314 assert(domaine_VEF.get_alphaS());
315 const Domaine& domaine = domaine_VEF.domaine();
316 int nfe = domaine.nb_faces_elem();
317 int nb_elem_tot = domaine.nb_elem_tot();
318 int nps = domaine_VEF.numero_premier_sommet();
319
320 // Initialize constant arrays
321 if (!som_initialized_)
322 {
323 som_initialized_ = true;
324 const IntTab& som_elem = domaine.les_elems();
325 som_.resize(nb_elem_tot, nfe);
326 nb_degres_liberte_.resize(domaine_VEF.domaine().nb_som_tot());
327 nb_degres_liberte_ = -1;
328 for (int elem = 0; elem < nb_elem_tot; elem++)
329 for (int indice = 0; indice < nfe; indice++)
330 {
331 int som = nps + domaine.get_renum_som_perio(som_elem(elem, indice));
332 nb_degres_liberte_(som - nps)++;
333 som_(elem, indice) = som;
334 }
335 corrige_sommets_sans_degre_liberte_ = (mp_min_vect(nb_degres_liberte_) == 0);
336 }
337
338 int dim = Objet_U::dimension;
339 int modif_traitement_diri = domaine_VEF.get_modif_div_face_dirichlet();
340 const Domaine_Cl_VEF& zcl = ref_cast(Domaine_Cl_VEF, la_zcl_vef.valeur());
341
342 CDoubleTabView face_normales = domaine_VEF.face_normales().view_ro();
343 CDoubleTabView vit = tab_vit.view_ro();
344 CIntArrView rang_elem_non_std = domaine_VEF.rang_elem_non_std().view_ro();
345 CIntArrView type_elem_Cl = zcl.type_elem_Cl().view_ro();
346 CIntTabView elem_faces = domaine_VEF.elem_faces().view_ro();
347 CIntTabView face_voisins = domaine_VEF.face_voisins().view_ro();
348 CIntTabView som_v = som_.view_ro();
349 DoubleArrView div = static_cast<DoubleVect&>(tab_div).view_rw();
350 Kokkos::parallel_for(start_gpu_timer(__KERNEL_NAME__),
351 range_1D(0, nb_elem_tot),
352 KOKKOS_LAMBDA (const int elem)
353 {
354 double sigma[3];
355 for (int comp = 0; comp < dim; comp++)
356 {
357 double s = 0;
358 for (int indice = 0; indice < nfe; indice++)
359 {
360 int face = elem_faces(elem, indice);
361 s += vit(face, comp);
362 }
363 sigma[comp] = s;
364 }
365
366 double coeff_som = 1. / (dim * (dim + 1));
367 if (modif_traitement_diri)
368 {
369 int indice_diri[4];
370 int nb_face_diri = 0;
371 int rang_elem = (int)rang_elem_non_std(elem);
372 int type_elem = rang_elem < 0 ? 0 : (int)type_elem_Cl(rang_elem);
373 coeff_som = calculer_coef_som(type_elem, dim, nb_face_diri, indice_diri);
374 // subtract the contribution from Dirichlet faces
375 for (int fdiri = 0; fdiri < nb_face_diri; fdiri++)
376 {
377 int indice = indice_diri[fdiri];
378 int face = elem_faces(elem,indice);
379 for (int comp = 0; comp < dim; comp++)
380 sigma[comp] -= vit(face,comp);
381 }
382 }
383
384 for (int indice = 0; indice < nfe; indice++)
385 {
386 int face = elem_faces(elem,indice);
387 double psc = 0;
388 for (int comp = 0; comp < dim; comp++)
389 psc += sigma[comp] * face_normales(face,comp);
390
391 int som = som_v(elem,indice);
392 int signe = (elem != face_voisins(face,0) ? -1 : 1);
393 Kokkos::atomic_add(&div(som), signe * coeff_som * psc);
394 }
395 });
396 end_gpu_timer(__KERNEL_NAME__);
397
398 const Domaine_Cl_VEF& domaine_Cl_VEF = la_zcl_vef.valeur();
399 const Conds_lim& les_cl = domaine_Cl_VEF.les_conditions_limites();
400 int nb_bords = les_cl.size();
401 int nb_comp = Objet_U::dimension;
402
403 IntArrView nb_degres_liberte = nb_degres_liberte_.view_rw();
404 DoubleTabView flux_b = tab_flux_b.view_wo();
405
406 for (int n_bord = 0; n_bord < nb_bords; n_bord++)
407 {
408 const Cond_lim& la_cl = domaine_Cl_VEF.les_conditions_limites(n_bord);
409 const Front_VF& le_bord = ref_cast(Front_VF, la_cl->frontiere_dis());
410 CIntArrView num_face = le_bord.num_face().view_ro();
411 int nb_faces_bord = le_bord.nb_faces();
412 int nb_faces_bord_tot = le_bord.nb_faces_tot();
413 assert(le_bord.nb_faces() == domaine_VEF.domaine().frontiere(n_bord).nb_faces());
414 if (!sub_type(Periodique, la_cl.valeur()))
415 {
416 int libre = 1;
417 if (sub_type(Dirichlet,la_cl.valeur()) || sub_type(Dirichlet_homogene, la_cl.valeur()) || sub_type(Dirichlet_entree_fluide, la_cl.valeur()) || sub_type(Symetrie, la_cl.valeur()))
418 libre = 0;
419
420 CIntTabView face_sommets = domaine_VEF.face_sommets().view_ro();
421 CIntArrView renum_som_perio = domaine.get_renum_som_perio().view_ro();
422
423 // Loop over real and virtual boundary faces
424 Kokkos::parallel_for(start_gpu_timer(__KERNEL_NAME__),
425 range_1D(0, nb_faces_bord_tot), KOKKOS_LAMBDA(
426 const int ind_face)
427 {
428 int face = num_face(ind_face);
429 double flux = 0.;
430 for (int comp = 0; comp < nb_comp; comp++)
431 flux += vit(face, comp) * face_normales(face, comp);
432 if (ind_face < nb_faces_bord)
433 flux_b(face, 0) = flux;
434 flux *= 1. / nb_comp;
435 for (int indice = 0; indice < (nfe - 1); indice++)
436 {
437 int som = renum_som_perio(face_sommets(face, indice));
438 Kokkos::atomic_add(&div(nps + som), flux);
439 if (libre)
440 Kokkos::atomic_add(&nb_degres_liberte(som), 1);
441 }
442 });
443 end_gpu_timer(__KERNEL_NAME__);
444 }
445 else
446 {
447 const Periodique& la_cl_perio = ref_cast(Periodique, la_cl.valeur());
448 CIntArrView face_associee = la_cl_perio.face_associee().view_ro();
449 // Loop over real and virtual boundary faces
450 Kokkos::parallel_for(start_gpu_timer(__KERNEL_NAME__),
451 range_1D(0, nb_faces_bord_tot), KOKKOS_LAMBDA(
452 const int ind_face)
453 {
454 int face = num_face(ind_face);
455 int face_perio = num_face(face_associee(ind_face));
456 double flux = 0.;
457 double flux_perio = 0.;
458 for (int comp = 0; comp < nb_comp; comp++)
459 {
460 flux += vit(face, comp) * face_normales(face, comp);
461 flux_perio += vit(face_perio, comp) * face_normales(face_perio, comp);
462 }
463 if (ind_face < (nb_faces_bord / 2))
464 {
465 flux_b(face, 0) = -flux;
466 flux_b(face_perio, 0) = flux_perio;
467 }
468 });
469 end_gpu_timer(__KERNEL_NAME__);
470 }
471 }
472 return tab_div;
473}
474
475DoubleTab& Op_Div_VEFP1B_Elem::ajouter_aretes(const DoubleTab& vit, DoubleTab& div) const
476{
477 const Domaine_VEF& domaine_VEF = ref_cast(Domaine_VEF, le_dom_vef.valeur());
478 assert(domaine_VEF.get_alphaA());
479 const Domaine& domaine = domaine_VEF.domaine();
480 const DoubleTab& face_normales = domaine_VEF.face_normales();
481 const IntTab& som_elem = domaine.les_elems();
482 const IntTab& elem_faces = domaine_VEF.elem_faces();
483 const IntTab& face_voisins = domaine_VEF.face_voisins();
484 const ArrOfInt& renum_arete_perio = domaine_VEF.get_renum_arete_perio();
485 const ArrOfInt& ok_arete = domaine_VEF.get_ok_arete();
486 int npa = domaine_VEF.numero_premiere_arete();
487 int nb_elem_tot = domaine.nb_elem_tot();
488 int elem, comp;
489
490 const IntTab& aretes_som = domaine_VEF.domaine().aretes_som();
491 const IntTab& elem_aretes = domaine_VEF.domaine().elem_aretes();
492 for (elem = 0; elem < nb_elem_tot; elem++)
493 {
494 for (int isom = 0; isom < 3; isom++)
495 {
496 int somi = som_elem(elem, isom);
497 int facei = elem_faces(elem, isom);
498 double signei = 1.;
499 if (face_voisins(facei, 0) != elem)
500 signei = -1.;
501 for (int jsom = isom + 1; jsom < 4; jsom++)
502 {
503 int somj = som_elem(elem, jsom);
504 int facej = elem_faces(elem, jsom);
505 double signej = 1.;
506 if (face_voisins(facej, 0) != elem)
507 signej = -1.;
508 int arete = renum_arete_perio[chercher_arete(elem, somi, somj, elem_aretes, aretes_som)];
509 if (ok_arete[arete])
510 {
511 int niinij = 0;
512 for (int ksom = 0; ksom < 4; ksom++)
513 {
514 if ((ksom == isom) || (ksom == jsom))
515 {
516 if (niinij == ksom)
517 niinij++;
518 double psc = 0;
519 for (comp = 0; comp < 3; comp++)
520 psc += (signei * face_normales(facei, comp) + signej * face_normales(facej, comp)) * vit(elem_faces(elem, ksom), comp);
521 div(npa + arete) -= 1. / 15. * psc;
522 }
523 else
524 {
525 if (niinij == ksom)
526 niinij++;
527 while ((niinij == jsom) || (niinij == isom))
528 niinij++;
529 assert(niinij < 4);
530 assert(niinij != isom);
531 assert(niinij != jsom);
532 assert(niinij != ksom);
533 int facek = elem_faces(elem, niinij);
534 double signek = 1.;
535 if (face_voisins(facek, 0) != elem)
536 signek = -1.;
537 double psc = 0;
538 for (comp = 0; comp < 3; comp++)
539 psc += signek * face_normales(facek, comp) * vit(elem_faces(elem, ksom), comp);
540 div(npa + arete) -= 2. / 15. * psc;
541 niinij = ksom;
542 }
543 }
544 }
545 }
546 }
547 }
548 return div;
549}
550
551DoubleTab& Op_Div_VEFP1B_Elem::ajouter(const DoubleTab& tab_velocity_tab, DoubleTab& tab_div) const
552{
553 const Domaine_VEF& domaine_VEF = ref_cast(Domaine_VEF, le_dom_vef.valeur());
554 const Domaine_Cl_VEF& domaine_Cl_VEF = la_zcl_vef.valeur();
555 // Some checks:
556 // The virtual space of velocity_tab must be up to date (test is done if check_enabled==1)
557 assert_espace_virtuel_vect(tab_velocity_tab);
558 // We don't care about the virtual space of div at input, but we do += on it.
559 assert_invalide_items_non_calcules(tab_div, 0.);
560
561#ifndef NDEBUG
562 // Ensure periodicity is enforced on velocity_tab (see FA814)
563 int nb_comp = tab_velocity_tab.dimension(1);
564 for (int n_bord = 0; n_bord < domaine_VEF.nb_front_Cl(); n_bord++)
565 {
566 const Cond_lim& la_cl = domaine_Cl_VEF.les_conditions_limites(n_bord);
567 if (sub_type(Periodique, la_cl.valeur()))
568 {
569 const Periodique& la_cl_perio = ref_cast(Periodique, la_cl.valeur());
570 const Front_VF& le_bord = ref_cast(Front_VF, la_cl->frontiere_dis());
571 int nb_faces_bord = le_bord.nb_faces();
572 CIntArrView face_associee = la_cl_perio.face_associee().view_ro();
573 CIntArrView num_face = le_bord.num_face().view_ro();
574 CDoubleTabView velocity_tab = tab_velocity_tab.view_ro();
575 Kokkos::parallel_for(start_gpu_timer(__KERNEL_NAME__), Kokkos::RangePolicy<>(0, nb_faces_bord), KOKKOS_LAMBDA(const int ind_face)
576 {
577 int ind_face_associee = face_associee(ind_face);
578 int face = num_face(ind_face);
579 int face_ass = num_face(ind_face_associee);
580 // PL: tolerance 1.e-4 because some cases do not satisfy this strictly (slow drift?)
581 for (int comp = 0; comp < nb_comp; comp++)
582 if (!est_egal(velocity_tab(face, comp), velocity_tab(face_ass, comp), 1.e-4))
583 {
584#ifndef TRUST_USE_GPU
585 Cerr << "vit1(" << face << "," << comp << ")=" << velocity_tab(face, comp) << finl;
586 Cerr << "vit2(" << face_ass << "," << comp << ")=" << velocity_tab(face_ass, comp) << finl;
587 Cerr << "Delta=" << velocity_tab(face, comp) - velocity_tab(face_ass, comp) << finl;
588 Cerr << "Periodic boundary condition is not correct in Op_Div_VEFP1B_Elem::ajouter" << finl;
589 Cerr << "Contact TRUST support." << finl;
590#endif
591 Process::Kokkos_exit("Error in Op_Div_VEFP1B_Elem::ajouter.");
592 }
593 }); // for face
594 end_gpu_timer(__KERNEL_NAME__);
595 } // sub_type Perio
596 }
597#endif
598 const DoubleVect& porosite_face = equation().milieu().porosite_face();
599 DoubleTab phi_vitesse_face_;
600 const DoubleTab& vit = modif_par_porosite_si_flag(tab_velocity_tab, phi_vitesse_face_, 1, porosite_face);
601
602 DoubleTab& flux_b = flux_bords_;
603 flux_b.resize(domaine_VEF.nb_faces_bord(), 1);
604 flux_b = 0.;
605
606 static int init = 1;
607 if (!init)
608 ::verifier(*this, init, domaine_VEF, vit, tab_div);
609 if (domaine_VEF.get_alphaE())
610 ajouter_elem(vit, tab_div);
611 if (domaine_VEF.get_alphaS())
612 ajouter_som(vit, tab_div, flux_b);
613 if (domaine_VEF.get_alphaA())
614 ajouter_aretes(vit, tab_div);
615
616 // correction of div u if vertex pressure is strongly imposed
617 if ((domaine_VEF.get_alphaS()) && ((domaine_VEF.get_cl_pression_sommet_faible() == 0)))
618 {
619 const Conds_lim& les_cl = domaine_Cl_VEF.les_conditions_limites();
620 int nps = domaine_VEF.numero_premier_sommet();
621 for (const auto &itr : les_cl)
622 {
623 const Cond_lim& la_cl = itr;
624 if (sub_type(Neumann,la_cl.valeur()) || sub_type(Neumann_val_ext, la_cl.valeur()))
625 {
626 const Front_VF& la_front_dis = ref_cast(Front_VF, la_cl->frontiere_dis());
627 int nb_faces = la_front_dis.nb_faces_tot();
628 int nsf = 0;
629 if (nb_faces != 0)
630 nsf = domaine_VEF.face_sommets().dimension(1);
631 CIntArrView num_face = la_front_dis.num_face().view_ro();
632 CIntTabView faces_sommets = domaine_VEF.face_sommets().view_ro();
633 DoubleArrView div = static_cast<DoubleVect&>(tab_div).view_wo();
634 Kokkos::parallel_for(start_gpu_timer(__KERNEL_NAME__),
635 range_1D(0, nb_faces), KOKKOS_LAMBDA(
636 const int ind_face)
637 {
638 int face = num_face(ind_face);
639 for (int som = 0; som < nsf; som++)
640 {
641 int som1 = faces_sommets(face, som);
642 div(nps + som1) = 0.;
643 }
644 });
645 end_gpu_timer(__KERNEL_NAME__);
646 }
647 }
648 }
649 if (domaine_VEF.get_alphaS() && corrige_sommets_sans_degre_liberte_)
651 //Optimization, not necessary:
652 //tab_div.echange_espace_virtuel();
653 return tab_div;
654}
655
656#ifdef VersionP1
657double tiers=1./3.;
658const IntTab& aretes_som=domaine_VEF.domaine().aretes_som();
659const IntTab& elem_aretes=domaine_VEF.domaine().elem_aretes();
660ArrOfDouble gradK(3);
661for(int isom=0; isom<3; isom++)
662 {
663 int somi = som_elem(elem,isom);
664 int facei = elem_faces(elem,isom);
665 double signei=1.;
666 if (face_voisins(facei,0) != elem)
667 signei=-1.;
668 for(int jsom=isom+1; jsom<4; jsom++)
669 {
670 int somj = som_elem(elem,jsom);
671 int facej = elem_faces(elem,jsom);
672 double signej=1.;
673 if (face_voisins(facej,0) != elem)
674 signej=-1.;
675 int arete = chercher_arete(elem, somi, somj,
676 elem_aretes, aretes_som);
677 for(comp=0; comp<dimension; comp++)
678 gradK(comp) = (signei*face_normales(facei,comp)+
679 signej*face_normales(facej,comp));
680 psc=0;
681 for(comp=0; comp<dimension; comp++)
682 psc+=tiers*(
683 -signei*face_normales(facei,comp)*vit(facei,comp)
684 -signej*face_normales(facej,comp)*vit(facej,comp)
685 +.5*gradK(comp)*sigma[comp]);
686 div(npa+arete)-=psc;
687 }
688 }
689#else
690#endif
691
692// Divide by the volume
693void Op_Div_VEFP1B_Elem::volumique_P0(DoubleTab& tab_div) const
694{
695 const Domaine_VEF& domaine_VEF = le_dom_vef.valeur();
696 int nb_elem = domaine_VEF.domaine().nb_elem_tot();
697 CDoubleArrView vol = domaine_VEF.volumes().view_ro();
698 DoubleArrView div = static_cast<DoubleVect&>(tab_div).view_rw();
699 Kokkos::parallel_for(start_gpu_timer(__KERNEL_NAME__), nb_elem, KOKKOS_LAMBDA(const int i) { div(i) /= vol(i); });
700 end_gpu_timer(__KERNEL_NAME__);
701}
702
703void Op_Div_VEFP1B_Elem::volumique(DoubleTab& tab_div) const
704{
705 const Domaine_VEF& domaine_VEF = ref_cast(Domaine_VEF, le_dom_vef.valeur());
706 int n = 0;
707 if (domaine_VEF.get_alphaE())
708 {
709 volumique_P0(tab_div);
710 n += domaine_VEF.nb_elem_tot();
711 }
712 if (domaine_VEF.get_alphaS())
713 {
714 int size_tot = domaine_VEF.volume_aux_sommets().size_totale();
715 CDoubleArrView vol = domaine_VEF.volume_aux_sommets().view_ro();
716 DoubleArrView div = static_cast<DoubleVect&>(tab_div).view_rw();
717 Kokkos::parallel_for(start_gpu_timer(__KERNEL_NAME__), size_tot, KOKKOS_LAMBDA(const int i) { div(n + i) /= vol(i); });
718 end_gpu_timer(__KERNEL_NAME__);
719 n += domaine_VEF.nb_som_tot();
720 }
721 if (domaine_VEF.get_alphaA())
722 {
723 const DoubleVect& vol = domaine_VEF.get_volumes_aretes();
724 int size_tot = vol.size_totale();
725 ToDo_Kokkos("critical");
726 for (int i = 0; i < size_tot; i++)
727 tab_div(n + i) /= vol(i);
728 }
729}
730
732{
733 // Set to zero the divergence at vertices with no degree of freedom
734 // (vertex only shared by faces with Dirichlet boundary conditions)
735 const Domaine_VEF& domaine_VEF = ref_cast(Domaine_VEF, le_dom_vef.valeur());
736 const Domaine& domaine = domaine_VEF.domaine();
737 const IntTab& elem_faces = domaine_VEF.elem_faces();
738 const IntTab& face_voisins = domaine_VEF.face_voisins();
739 const int nse = domaine.nb_som_elem();
740 int nb_faces_tot = domaine_VEF.nb_faces_tot();
741
742 Sortie& journal = Process::Journal();
743 int afficher_message = 0;
744 int nb_som = domaine.nb_som();
745
746 int ecrire_decoupage_som = 0;
747 int decoupage_som = 0;
748 // Write the decoupage_som file only once
749 // and only in sequential mode
750 if ((Process::is_sequential()) && equation().schema_temps().nb_pas_dt() == 0)
751 decoupage_som = 1;
752
753 SChaine decoup_som;
754 decoup_som << "1" << finl;
755 decoup_som << Objet_U::dimension << " " << nb_som << finl;
756 ArrOfInt somm(dimension + 2);
757 for (int k = 0; k < nb_som; k++)
758 {
759 int sommet = domaine.get_renum_som_perio(k);
760 if (nb_degres_liberte_(sommet) != 0)
761 continue;
762 if (!afficher_message)
763 {
764 afficher_message = 1;
765 Cerr << finl << "Problem with the mesh used for the VEF P1Bulle discretization." << finl;
766 journal << "List of nodes with no degrees of freedom :" << finl;
767 }
768 const double x = domaine.coord(sommet, 0);
769 const double y = domaine.coord(sommet, 1);
770 const double z = (Objet_U::dimension == 3) ? domaine.coord(sommet, 2) : 0.;
771
772 journal << "Error node " << sommet << " ( " << x << " " << y << " " << z << " )\n";
773 // Display the list of indices of real and virtual elements containing
774 // this vertex. Display the letter "v" for virtual elements.
775 journal << "Elements ";
776 const int nb_elem_tot = domaine.nb_elem_tot();
777 const int nb_elem = domaine.nb_elem();
778 const IntTab& som_elem = domaine.les_elems();
779 for (int elem = 0; elem < nb_elem_tot; elem++)
780 for (int som = 0; som < nse; som++)
781 if (som_elem(elem, som) == sommet)
782 {
783 journal << elem << ((elem >= nb_elem) ? "v " : " ");
784
785 // Write to the decoupage_som file
786 int face_opp = elem_faces(elem, som);
787 int elem_opp;
788 somm = -1;
789 somm(0) = sommet;
790
791 int elem1 = face_voisins(face_opp, 0);
792 int elem2 = face_voisins(face_opp, 1);
793
794 if (elem1 == elem)
795 elem_opp = elem2;
796 else
797 elem_opp = elem1;
798
799 int i = 2;
800 for (int som1 = 0; som1 < nse; som1++) // iterate over vertices of elem_opp
801 {
802 int ok = 1;
803 for (int som2 = 0; som2 < nse; som2++) // iterate over vertices of elem
804 if (som_elem(elem, som2) == som_elem(elem_opp, som1))
805 ok = 0;
806 if (ok)
807 somm(1) = som_elem(elem_opp, som1);
808 else
809 {
810 somm(i) = som_elem(elem_opp, som1); // vertices of the shared face
811 i++;
812 }
813 }
814 if (decoupage_som)
815 {
816 ecrire_decoupage_som = 1;
817 for (int j = 0; j < dimension + 2; j++)
818 decoup_som << somm(j) << " ";
819 decoup_som << elem << " " << elem_opp << finl;
820 }
821 }
822 journal << "\n";
823 // Display the list of faces containing this vertex.
824 // For boundary faces, display the boundary condition,
825 // for virtual faces, the letter "v"
826 journal << "\nFaces ";
827 const int nb_faces = domaine_VEF.nb_faces();
828 const int nb_som_face = domaine_VEF.face_sommets().dimension(1);
829 for (int face = 0; face < nb_faces_tot; face++)
830 {
831 for (int som = 0; som < nb_som_face; som++)
832 {
833 if (domaine_VEF.face_sommets(face, som) == sommet)
834 {
835 journal << face;
836 if (face >= nb_faces) // Virtual face
837 journal << "v";
838 const int cl = find_cl_face(domaine, face);
839 // Real boundary face:
840 if (cl >= 0)
841 {
842 const Nom& nom_bord = domaine.frontiere(cl).le_nom();
843 journal << "(boundary=" << nom_bord << ")";
844 }
845 journal << " ";
846 }
847 }
848 }
849 journal << finl;
850 }
851
852 if (ecrire_decoupage_som)
853 {
854 decoup_som << "-1";
855 SFichier fic(Objet_U::nom_du_cas() + ".decoupage_som");
856 fic << decoup_som.get_str() << finl;
857 fic.close();
858
859 }
860 if (afficher_message)
861 {
862 Nom nom_fichier(nom_du_cas());
863 Cerr << "Look at the .log file of processor " << Process::me() << " to know which nodes" << finl;
864 Cerr << "do not have enough degrees of freedom. You can also visualize" << finl;
865 Cerr << "your mesh to identify which elements have a problem and" << finl;
866 Cerr << "remesh your domain close to these nodes so that these have" << finl;
867 Cerr << "at least a degree of freedom." << finl;
868 Cerr << "The VEF P1Bulle discretization is not compatible with this type" << finl;
869 Cerr << "of mesh and boundary conditions used (Dirichlet, Symmetry ,...)" << finl << finl;
870 Cerr << "Other possibility, in your data file:" << finl;
871 if (dimension == 2)
872 Cerr << "If you have used \"Trianguler\", substituted by \"Trianguler_H\"." << finl << finl;
873 if (dimension == 3)
874 Cerr << "If you have used \"Tetraedriser\", substituted by \"Tetraedriser_homogene\" or \"Tetraedriser_par_prisme\"." << finl << finl;
875 Cerr << "Or insert the line:" << finl;
876 Cerr << "VerifierCoin " << domaine.le_nom() << " { [Read_file " << nom_fichier << ".decoupage_som] }" << finl;
877 Cerr << "after the mesh is finished to be read and built." << finl;
879 Cerr << "and BEFORE the keyword \"Decouper\" during the partition of the mesh." << finl;
880 else
881 Cerr << "and BEFORE the keyword \"Discretiser\"." << finl;
882 Cerr << "A few cells will be divided into 3 (2D) or 4 (3D)." << finl;
883 Cerr << finl;
885 }
886}
887
889{
890 const int impr_bord = (le_dom_vef->domaine().bords_a_imprimer().est_vide() ? 0 : 1);
892 double temps = sch.temps_courant();
893
894 int nb_compo = flux_bords_.dimension(1);
895 // Loop over boundaries to sum the fluxes per boundary into the flux_bord array
896 DoubleVect bilan(nb_compo);
897 bilan = 0;
898 int nb_cl = le_dom_vef->nb_front_Cl();
899 // flux_bords contains the sum of flux on each boundary:
900 DoubleTrav tab_flux_bords(3, nb_cl, nb_compo);
901 for (int num_cl = 0; num_cl < nb_cl; num_cl++)
902 {
903 const Cond_lim& la_cl = la_zcl_vef->les_conditions_limites(num_cl);
904 const Front_VF& frontiere_dis = ref_cast(Front_VF, la_cl->frontiere_dis());
905 int ndeb = frontiere_dis.num_premiere_face();
906 int nfin = ndeb + frontiere_dis.nb_faces();
907 int perio = (sub_type(Periodique,la_cl.valeur()) ? 1 : 0);
908 for (int face = ndeb; face < nfin; face++)
909 for (int k = 0; k < nb_compo; k++)
910 {
911 tab_flux_bords(0, num_cl, k) += flux_bords_(face, k);
912 if (perio)
913 {
914 if (face < (ndeb + frontiere_dis.nb_faces() / 2))
915 tab_flux_bords(1, num_cl, k) += flux_bords_(face, k);
916 else
917 tab_flux_bords(2, num_cl, k) += flux_bords_(face, k);
918 }
919 }
920 }
921 // Sum on all CPUs:
922 mp_sum_for_each_item(tab_flux_bords);
923
924 // Print
925 if (je_suis_maitre())
926 {
927 ouvrir_fichier(Flux_div, "", 1);
928 Flux_div.add_col(temps);
929 for (int num_cl = 0; num_cl < nb_cl; num_cl++)
930 {
931 const Cond_lim& la_cl = la_zcl_vef->les_conditions_limites(num_cl);
932 int perio = (sub_type(Periodique,la_cl.valeur()) ? 1 : 0);
933 for (int k = 0; k < nb_compo; k++)
934 {
935 if (perio)
936 {
937 Flux_div.add_col(tab_flux_bords(1, num_cl, k));
938 Flux_div.add_col(tab_flux_bords(2, num_cl, k));
939 }
940 else
941 Flux_div.add_col(tab_flux_bords(0, num_cl, k));
942 bilan(k) += tab_flux_bords(0, num_cl, k);
943 }
944 }
945
946 for (int k = 0; k < nb_compo; k++)
947 Flux_div.add_col(bilan(k));
948 Flux_div << finl;
949 }
950
951 const LIST(Nom) &Liste_bords_a_imprimer = le_dom_vef->domaine().bords_a_imprimer();
952 if (!Liste_bords_a_imprimer.est_vide())
953 {
954 EcrFicPartage Flux_face;
955 ouvrir_fichier_partage(Flux_face, "", impr_bord);
956 for (int num_cl = 0; num_cl < nb_cl; num_cl++)
957 {
958 const Frontiere_dis_base& la_fr = la_zcl_vef->les_conditions_limites(num_cl)->frontiere_dis();
959 const Cond_lim& la_cl = la_zcl_vef->les_conditions_limites(num_cl);
960 const Front_VF& frontiere_dis = ref_cast(Front_VF, la_cl->frontiere_dis());
961 int ndeb = frontiere_dis.num_premiere_face();
962 int nfin = ndeb + frontiere_dis.nb_faces();
963 if (le_dom_vef->domaine().bords_a_imprimer().contient(la_fr.le_nom()))
964 {
965 Flux_face << "# Flux par face sur " << la_fr.le_nom() << " au temps " << temps << " : " << finl;
966 for (int face = ndeb; face < nfin; face++)
967 {
968 if (dimension == 2)
969 Flux_face << "# Face a x= " << le_dom_vef->xv(face, 0) << " y= " << le_dom_vef->xv(face, 1) << " flux=";
970 else if (dimension == 3)
971 Flux_face << "# Face a x= " << le_dom_vef->xv(face, 0) << " y= " << le_dom_vef->xv(face, 1) << " z= " << le_dom_vef->xv(face, 2) << " flux=";
972 for (int k = 0; k < nb_compo; k++)
973 Flux_face << " " << flux_bords_(face, k);
974 Flux_face << finl;
975 }
976 Flux_face.syncfile();
977 }
978 }
979 }
980 return 1;
981}
Class Champ_Inc_base.
class Cond_lim Generic class used to represent any class
Definition Cond_lim.h:31
class Conds_lim This class represents a vector of boundary conditions.
Definition Conds_lim.h:32
static void verifier(const char *const msg, double)
Definition Debog.cpp:21
Dirichlet_entree_fluide This class represents a boundary condition imposing a quantity.
Classe Dirichlet_homogene This class is the base class of the hierarchy of homogeneous Dirichlet-type...
Dirichlet This class is the base class of the hierarchy of Dirichlet-type boundary conditions.
Definition Dirichlet.h:31
int_t nb_elem_tot() const
Definition Domaine.h:132
const IntTab_t & aretes_som() const
returns the connectivity array edges/vertices.
Definition Domaine.h:156
const Frontiere_t & frontiere(int i) const
Definition Domaine.h:539
int nb_faces_elem(int=0) const
Returns the number of faces of type i of the geometric elements that make up the domain.
Definition Domaine.h:484
int_t elem_aretes(int_t i, int j) const
returns the number of the j-th edge of the i-th element.
Definition Domaine.h:154
int_t nb_som_tot() const
Returns the total number of vertices of the domain i.e. the number of real and virtual vertices on th...
Definition Domaine.h:123
int type_elem_Cl(int i) const
class Domaine_Cl_dis_base Domaine_Cl_dis_base objects represent discretized boundary conditions
const Cond_lim & les_conditions_limites(int) const
Returns the i-th boundary condition.
class Domaine_VEF
Definition Domaine_VEF.h:53
int numero_premiere_arete() const
const IntVect & get_ok_arete() const
Definition Domaine_VEF.h:98
IntVect & rang_elem_non_std()
Definition Domaine_VEF.h:85
int numero_premier_sommet() const
const DoubleVect & get_volumes_aretes() const
Definition Domaine_VEF.h:99
int get_modif_div_face_dirichlet() const
Definition Domaine_VEF.h:95
int get_cl_pression_sommet_faible() const
Definition Domaine_VEF.h:96
int get_alphaA() const
Definition Domaine_VEF.h:93
const ArrOfInt & get_renum_arete_perio() const
Definition Domaine_VEF.h:97
const DoubleVect & volume_aux_sommets() const
Definition Domaine_VEF.h:89
int get_alphaS() const
Definition Domaine_VEF.h:92
int get_alphaE() const
Definition Domaine_VEF.h:91
int nb_faces() const
Returns the total number of faces.
Definition Domaine_VF.h:471
int nb_faces_tot() const
Returns the total number of faces.
Definition Domaine_VF.h:481
virtual double face_normales(int face, int comp) const
Definition Domaine_VF.h:47
double xv(int num_face, int k) const
Definition Domaine_VF.h:76
double volumes(int i) const
Definition Domaine_VF.h:113
int face_sommets(int i, int j) const
Returns the index of the i-th vertex of face num_face.
Definition Domaine_VF.h:582
int elem_faces(int i, int j) const
Returns the index of the i-th face of element num_elem; the face numbering convention is.
Definition Domaine_VF.h:542
int face_voisins(int num_face, int i) const
Returns the neighbouring element of num_face in direction i.
Definition Domaine_VF.h:418
int nb_faces_bord() const
Returns the number of faces on which boundary conditions are applied:
Definition Domaine_VF.h:512
class Domaine_dis_base This class is the base of the hierarchy of discretized domains.
int nb_elem_tot() const
int nb_front_Cl() const
const Domaine & domaine() const
int nb_som_tot() const
Sortie & syncfile() override
Triggers writing to disk of the data accumulated on the different processors since the last call to s...
Class defining operators and methods for all reading operation in an input flow (file,...
Definition Entree.h:42
virtual const Milieu_base & milieu() const =0
Probleme_base & probleme()
Returns the problem associated with the equation.
class Front_VF
Definition Front_VF.h:36
int nb_faces() const
Definition Front_VF.h:53
int num_premiere_face() const
Definition Front_VF.h:63
int nb_faces_tot() const
Definition Front_VF.h:58
int num_face(const int) const
Definition Front_VF.h:68
const ArrOfInt_t & get_faces_virt() const
Definition Frontiere.h:69
int_t num_premiere_face() const
Definition Frontiere.h:67
int_t nb_faces() const
Returns the number of faces of the boundary.
Definition Frontiere.h:59
class Frontiere_dis_base Class representing a discretized boundary.
const Nom & le_nom() const override
Returns the name of the geometric boundary.
DoubleVect & porosite_face()
Definition Milieu_base.h:62
const Equation_base & equation() const
Returns the reference to the equation pointed to by MorEqn::mon_equation.
Definition MorEqn.h:62
Classe Neumann_val_ext This class is the base class of the hierarchy of.
Classe Neumann This class is the base class of the hierarchy of Neumann-type boundary conditions.
Definition Neumann.h:31
class Nom: a character string for naming TRUST objects.
Definition Nom.h:31
const Nom & le_nom() const override
Returns *this.
Definition Nom.cpp:555
static int dimension
Definition Objet_U.h:94
friend class Sortie
Definition Objet_U.h:70
const Nom & que_suis_je() const
Returns the string identifying the class.
Definition Objet_U.cpp:104
virtual Entree & readOn(Entree &)
Reads an Objet_U from an input stream. Virtual method to override.
Definition Objet_U.cpp:289
static const Nom & nom_du_cas()
Returns a constant reference to the case name. This method is static.
Definition Objet_U.cpp:145
virtual Sortie & printOn(Sortie &) const
Writes the object to an output stream. Virtual method to override.
Definition Objet_U.cpp:278
class Op_Div_VEFP1B_Elem
void volumique(DoubleTab &) const override
int impr(Sortie &os) const override
DOES NOTHING - to override in derived classes.
DoubleTab & ajouter(const DoubleTab &, DoubleTab &) const override
public_for_cuda void volumique_P0(DoubleTab &) const
DoubleTab & ajouter_aretes(const DoubleTab &, DoubleTab &) const
DoubleTab & ajouter_elem(const DoubleTab &, DoubleTab &) const
DoubleTab & ajouter_som(const DoubleTab &, DoubleTab &, DoubleTab &) const
void associer(const Domaine_dis_base &, const Domaine_Cl_dis_base &, const Champ_Inc_base &) override
Classe Operateur_Div_base This class is the base of the hierarchy of operators representing.
DoubleTab flux_bords_
void ouvrir_fichier_partage(EcrFicPartage &, const Nom &, const int flag=1) const
Opening/creation of a shared file for printing an operator. To override in derived classes.
void ouvrir_fichier(SFichier &os, const Nom &, const int flag=1) const
Opening/creation of a file for printing an operator. To override in derived classes.
class Periodique This class represents a periodic boundary condition.
Definition Periodique.h:31
int face_associee(int i) const
Definition Periodique.h:35
const Schema_Temps_base & schema_temps() const
Returns the time scheme associated with the problem.
static KOKKOS_INLINE_FUNCTION void Kokkos_exit(const char *)
Exit routine for TRUST within a Kokkos region.
Definition Process.h:172
static void mp_sum_for_each_item(TRUSTArray< _TYPE_ > &x, int n=-1)
Definition Process.cpp:194
static bool is_parallel()
Definition Process.cpp:108
static Sortie & Journal(int message_level=0)
Returns a static Sortie object used as an event journal.
Definition Process.cpp:592
static int me()
Returns the rank of the local processor in the current communication group. See Comm_Group::rank() an...
Definition Process.cpp:122
static void exit(int exit_code=-1)
Exit routine for TRUST within a Kokkos region.
Definition Process.cpp:466
static int je_suis_maitre()
Returns 1 if on the master processor of the current group (i.e. me() == 0), 0 otherwise.
Definition Process.cpp:82
static bool is_sequential()
Definition Process.cpp:113
This class, derived from Sortie, accumulates what is sent to it into a character string.
Definition SChaine.h:26
const char * get_str() const
returns a copy of the string stored by the SChaine
Definition SChaine.cpp:72
SFichier is to the C++ ofstream class what Sortie is to the C++ ostream class.
Definition SFichier.h:29
class Schema_Temps_base
double temps_courant() const
Returns the current time.
Base class for output streams.
Definition Sortie.h:52
Symetrie On symmetry faces, the following properties hold:
Definition Symetrie.h:37
_SIZE_ size_array() const
std::enable_if_t< is_default_exec_space< EXEC_SPACE >, View< _TYPE_, _SHAPE_ > > view_wo()
Definition TRUSTTab.h:276
void resize(_SIZE_ n, RESIZE_OPTIONS opt=RESIZE_OPTIONS::COPY_INIT)
Definition TRUSTTab.tpp:469
std::enable_if_t< is_default_exec_space< EXEC_SPACE >, ConstView< _TYPE_, _SHAPE_ > > view_ro() const
Definition TRUSTTab.h:261
std::enable_if_t< is_default_exec_space< EXEC_SPACE >, View< _TYPE_, _SHAPE_ > > view_rw()
Definition TRUSTTab.h:291
_SIZE_ dimension(int d) const
Definition TRUSTTab.tpp:133
_SIZE_ size_totale() const
Definition TRUSTVect.tpp:61