VirtualFluids 0.2.0
Parallel CFD LBM Solver
Loading...
Searching...
No Matches
Simulation.cpp
Go to the documentation of this file.
1//=======================================================================================
2// ____ ____ __ ______ __________ __ __ __ __
3// \ \ | | | | | _ \ |___ ___| | | | | / \ | |
4// \ \ | | | | | |_) | | | | | | | / \ | |
5// \ \ | | | | | _ / | | | | | | / /\ \ | |
6// \ \ | | | | | | \ \ | | | \__/ | / ____ \ | |____
7// \ \ | | |__| |__| \__\ |__| \________/ /__/ \__\ |_______|
8// \ \ | | ________________________________________________________________
9// \ \ | | | ______________________________________________________________|
10// \ \| | | | __ __ __ __ ______ _______
11// \ | | |_____ | | | | | | | | | _ \ / _____)
12// \ | | _____| | | | | | | | | | | \ \ \_______
13// \ | | | | |_____ | \_/ | | | | |_/ / _____ |
14// \ _____| |__| |________| \_______/ |__| |______/ (_______/
15//
16// This file is part of VirtualFluids. VirtualFluids is free software: you can
17// redistribute it and/or modify it under the terms of the GNU General Public
18// License as published by the Free Software Foundation, either version 3 of
19// the License, or (at your option) any later version.
20//
21// VirtualFluids is distributed in the hope that it will be useful, but WITHOUT
22// ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
23// FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
24// for more details.
25//
26// SPDX-License-Identifier: GPL-3.0-or-later
27// SPDX-FileCopyrightText: Copyright © VirtualFluids Project contributors, see AUTHORS.md in root folder
28//
33//=======================================================================================
34#include "Simulation.h"
35
36#include <memory>
37#include <string>
38#include <vector>
39
40#include <helper_timer.h>
41
43
47
48#include <logger/Logger.h>
49
53
61#include "Kernel/Kernel.h"
65#include "Output/DataWriter.h"
68#include "Output/FileWriter.h"
75#include "Parameter/Parameter.h"
79#include "PostProcessor/Cp.h"
92
93namespace vf::gpu {
94
95std::string getFileName(const std::string& fname, int step, int myID)
96{
97 return std::string(fname + "_Restart_" + std::to_string(myID) + "_" + std::to_string(step));
98}
99
100Simulation::Simulation(std::shared_ptr<Parameter> para, std::shared_ptr<GridBuilder> builder,
101 const BoundaryConditionFactory* bcFactory, GridScalingFactory* scalingFactory)
102 : Simulation(para, std::make_shared<CudaMemoryManager>(para), builder, bcFactory, std::make_shared<TurbulenceModelFactory>(para), scalingFactory)
103{
104}
105
106Simulation::Simulation(std::shared_ptr<Parameter> para, std::shared_ptr<CudaMemoryManager> memoryManager, std::shared_ptr<GridBuilder> builder,
107 const BoundaryConditionFactory* bcFactory, GridScalingFactory* scalingFactory)
108 : Simulation(para, memoryManager, builder, bcFactory, std::make_shared<TurbulenceModelFactory>(para), scalingFactory)
109{
110}
111
112Simulation::Simulation(std::shared_ptr<Parameter> para, std::shared_ptr<GridBuilder> builder,
113 const BoundaryConditionFactory* bcFactory, SPtr<TurbulenceModelFactory> tmFactory,
114 GridScalingFactory* scalingFactory)
115 : Simulation(para, std::make_shared<CudaMemoryManager>(para), builder, bcFactory, tmFactory, scalingFactory)
116{
117}
118
119Simulation::Simulation(std::shared_ptr<Parameter> para, std::shared_ptr<CudaMemoryManager> memoryManager, std::shared_ptr<GridBuilder> builder,
120 const BoundaryConditionFactory* bcFactory, SPtr<TurbulenceModelFactory> tmFactory,
121 GridScalingFactory* scalingFactory)
122 : para(para), cudaMemoryManager(memoryManager),
124 communicator(*vf::parallel::MPICommunicator::getInstance())
125#else
126 communicator(*vf::parallel::NullCommunicator::getInstance())
127#endif
128 ,
129 kernelFactory(std::make_unique<KernelFactoryImp>()), preProcessorFactory(std::make_shared<PreProcessorFactoryImp>()),
130 dataWriter(std::make_unique<FileWriter>())
131{
132 auto gridGenerator = GridProvider::makeGridGenerator(builder, para, cudaMemoryManager, communicator);
133 init(*gridGenerator, bcFactory, tmFactory, scalingFactory);
134}
135
136Simulation::Simulation(std::shared_ptr<Parameter> para, std::shared_ptr<CudaMemoryManager> memoryManager,
138 : para(para), cudaMemoryManager(memoryManager), communicator(communicator), kernelFactory(std::make_unique<KernelFactoryImp>()),
139 preProcessorFactory(std::make_shared<PreProcessorFactoryImp>()), dataWriter(std::make_unique<FileWriter>())
140{
141 this->tmFactory = SPtr<TurbulenceModelFactory>( new TurbulenceModelFactory(para) );
142 init(gridProvider, bcFactory, tmFactory, scalingFactory);
143}
144
145void Simulation::init(GridProvider &gridProvider, const BoundaryConditionFactory *bcFactory, SPtr<TurbulenceModelFactory> tmFactory, GridScalingFactory *scalingFactory)
146{
147 gridProvider.initalGridInformations();
148
149 const int deviceId = communicator.mapCudaDevicesOnHosts(para->getDevices(), para->getMaxDev());
150
152
153 para->initLBMSimulationParameter();
154
155 gridProvider.allocAndCopyForcing();
156 gridProvider.allocAndCopyQuadricLimiters();
157
158 gridProvider.setDimensions();
159 gridProvider.setBoundingBox();
160
161 para->setRe(para->getVelocity() * (real)1.0 / para->getViscosity());
162
163 restart_object = std::make_shared<ASCIIRestartObject>();
164
165 VF_LOG_TRACE("vis_ratio: {}", para->getViscosityRatio());
166 VF_LOG_TRACE("u0_ratio: {}", para->getVelocityRatio());
167 VF_LOG_TRACE("delta_rho: {}", para->getDensityRatio());
168
169 cudaMemoryManager->setMemsizeGPU(0, true);
171 allocNeighborsOffsetsScalesAndBoundaries(gridProvider, bcFactory);
172
174 VF_LOG_INFO("Start initializing precollision interactors");
175 for (SPtr<PreCollisionInteractor>& interactor : para->getInteractors()) {
176 interactor->init();
177 interactor->getTaggedFluidNodes(&gridProvider);
178 }
179
180 VF_LOG_INFO("Start initializing samplers");
181 for (SPtr<Sampler>& sampler : para->getSamplers()) {
182 sampler->init();
183 sampler->getTaggedFluidNodes(&gridProvider);
184 }
185
187 // CUDA streams
188 if (para->getUseStreams()) {
189 para->getStreamManager()->registerAndLaunchStream(CudaStreamIndex::SubDomainBorder);
190 para->getStreamManager()->registerAndLaunchStream(CudaStreamIndex::Bulk);
191 para->getStreamManager()->createCudaEvents();
192 }
194
195 if (para->getKernelNeedsFluidNodeIndicesToRun()) {
196 gridProvider.sortFluidNodeTags();
197 gridProvider.allocArrays_taggedFluidNodes();
198 }
200 // Kernel init
202 VF_LOG_TRACE("make Kernels");
203 kernels = kernelFactory->makeKernels(para);
204 for (const auto& kernel : kernels) {
205 kernel->checkKernelParameters(para->getMaxLevel(), para->getVelocity(),
206 para->getParH(para->getMaxLevel())->viscosity);
207 }
208
209 if (para->getDiffOn()) {
210 VF_LOG_TRACE("make AD Kernels");
211 adKernels = kernelFactory->makeAdvectionDiffusionKernels(para);
212 std::vector<PreProcessorType> preProADTypes = adKernels.at(0)->getPreProcessorTypes();
213 preProcessorAD = preProcessorFactory->makePreProcessor(preProADTypes, para);
214 }
215
217 // PreProcessor init
219 VF_LOG_TRACE("make Preprocessors");
220 std::vector<PreProcessorType> preProTypes = kernels.at(0)->getPreProcessorTypes();
221 preProcessor = preProcessorFactory->makePreProcessor(preProTypes, para);
222
224 // Allocate Memory for Drag Lift Calculation
226 if (para->getCalcDragLift())
227 allocDragLift(para.get(), cudaMemoryManager.get());
228
230 // Mean
232 if (para->getCalcMean()) {
233 VF_LOG_TRACE("alloc Calculation for Mean Values");
234 if (para->getDiffOn())
235 allocMeanAD(para.get(), cudaMemoryManager.get());
236 else
237 allocMean(para.get(), cudaMemoryManager.get());
238 }
239
241 // Turbulence Intensity
243 if (para->getCalcTurbulenceIntensity()) {
244 VF_LOG_TRACE("alloc arrays for calculating Turbulence Intensity");
245 allocTurbulenceIntensity(para.get(), cudaMemoryManager.get());
246 }
247
249 // allocate memory and initialize 2nd, 3rd and higher order moments
251 if (para->getCalc2ndOrderMoments()) {
252 alloc2ndMoments(para.get(), cudaMemoryManager.get());
253 init2ndMoments(para.get());
254 }
255 if (para->getCalc3rdOrderMoments()) {
256 alloc3rdMoments(para.get(), cudaMemoryManager.get());
257 init3rdMoments(para.get());
258 }
259 if (para->getCalcHighOrderMoments()) {
260 allocHigherOrderMoments(para.get(), cudaMemoryManager.get());
261 initHigherOrderMoments(para.get());
262 }
263
265 // MeasurePoints
267 if (para->getUseMeasurePoints()) {
268 VF_LOG_TRACE("read measure points");
269 ReaderMeasurePoints::readMeasurePoints(para.get(), cudaMemoryManager.get());
270 }
271
273 // enSightGold
275 // excludeGridInterfaceNodesForMirror(para, 7);
277 // printCaseFile(para);
279 // printGeoFile(para, true); //true for binary
281
282 VF_LOG_INFO("init lattice...");
283 initLattice(para, preProcessor, preProcessorAD, cudaMemoryManager);
284 VF_LOG_INFO("done");
285
287 // find indices of corner nodes for multiGPU communication
289 if (para->getDevices().size() > 2) {
290 VF_LOG_INFO("Find indices of edge nodes for multiGPU communication");
292 }
294 // Memory alloc for CheckPoint / Restart
296 if (para->getDoCheckPoint() || para->getDoRestart()) {
297 VF_LOG_INFO("Alloc Memory for CheckPoint / Restart");
298 for (int lev = para->getCoarse(); lev <= para->getFine(); lev++) {
299 cudaMemoryManager->cudaAllocFsForCheckPointAndRestart(lev);
300 }
301 }
302
304 // Restart
306 if (para->getDoRestart()) {
307 VF_LOG_INFO("Restart...\n...get the Object...");
308
309 const auto name = getFileName(para->getFName(), para->getTimeDoRestart(), para->getMyProcessID());
310 restart_object->deserialize(name, para);
311
312 VF_LOG_INFO("...copy Memory for Restart...");
313 for (int lev = para->getCoarse(); lev <= para->getFine(); lev++) {
315 cudaMemoryManager->cudaCopyFsForRestart(lev);
317 // macroscopic values
318 calculateMacroscopicQuantities(para->getParD(lev)->velocityX, para->getParD(lev)->velocityY, para->getParD(lev)->velocityZ,
319 para->getParD(lev)->rho, para->getParD(lev)->pressure, para->getParD(lev)->typeOfGridNode,
320 para->getParD(lev)->neighborX, para->getParD(lev)->neighborY,
321 para->getParD(lev)->neighborZ, para->getParD(lev)->numberOfNodes,
322 para->getParD(lev)->numberofthreads, para->getParD(lev)->distributions.f[0],
323 para->getParD(lev)->isEvenTimestep);
324 getLastCudaError("Kernel calculateMacroscopicQuantities execution failed");
325 }
326 VF_LOG_INFO("done.");
327 }
328
330 // Init UpdateGrid
332 this->updateGrid27 = std::make_unique<UpdateGrid27>(para, communicator, cudaMemoryManager, kernels, adKernels, bcFactory,
333 tmFactory, scalingFactory);
334
336 // Write Initialized Files
338 VF_LOG_INFO("Write initialized Files ...");
339 dataWriter->writeInit(para, cudaMemoryManager);
340 VF_LOG_INFO("... done.");
341
342#if DEBUG_FS
343 VF_LOG_INFO("Allocating host memory for DistributionWriter.");
345#endif
346
347 VF_LOG_INFO("used Device Memory: {} MB", cudaMemoryManager->getMemsizeGPU() / 1000000.0);
348
349 performanceOutput = std::make_unique<PerformanceMeasurement>(*para);
350 metaData = createMetaData(*para);
352}
353
355{
356 this->kineticEnergyAnalyzer = std::make_unique<KineticEnergyAnalyzer>(this->para, tAnalyse);
357}
358
360{
361 this->enstrophyAnalyzer = std::make_unique<EnstrophyAnalyzer>(this->para, tAnalyse);
362}
363
364void Simulation::setDataWriter(std::shared_ptr<DataWriter> dataWriter_)
365{
366 this->dataWriter = dataWriter_;
367}
368
369void Simulation::setFactories(std::unique_ptr<KernelFactory> &&kernelFactory_,
370 std::unique_ptr<PreProcessorFactory> &&preProcessorFactory_)
371{
372 this->kernelFactory = std::move(kernelFactory_);
373 this->preProcessorFactory = std::move(preProcessorFactory_);
374}
375
377{
378 previousTimestepForAveraging = para->getTimeCalcMedStart();
379 previousTimestepForTurbulenceIntensityCalculation = 0;
380 timestepForMeasuringPoints = 0;
381
382 para->setStepEnsight(0);
383
384 averageTimer.start();
385}
386
387void Simulation::allocNeighborsOffsetsScalesAndBoundaries(GridProvider &gridProvider, const BoundaryConditionFactory* bcFactory)
388{
389 gridProvider.allocArrays_CoordNeighborGeo();
390 gridProvider.allocArrays_OffsetScale();
391 gridProvider.allocArrays_BoundaryValues(bcFactory); // allocArrays_BoundaryValues() has to be called after allocArrays_OffsetScale() because of initCommunicationArraysForCommAfterFinetoCoarse()
392 gridProvider.allocArrays_BoundaryQs();
393}
394
396{
397 this->initTimers();
398
400 // Time loop
402 for(uint timestep = para->getTimestepStart(); timestep <= para->getTimestepEnd(); timestep++) {
403 this->calculateTimestep(timestep);
404 }
405
407 // printDragLift(para);
409
418 // for (int lev = 7; lev <= 8; lev++)
419 //{
420 // printCpTop(para, lev);
421 //}
426
427 // //////////////////////////////////////////////////////////////////////////
428 // //Copy Measure Values
429 // for (int lev=para->getCoarse(); lev <= para->getFine(); lev++)
430 //{
431 // VF_LOG_INFO("Copy MeasurePoints at level = {}", lev);
432 // para->cudaCopyMeasurePointsToHost(lev);
433 // para->copyMeasurePointsArrayToVector(lev);
434 // VF_LOG_INFO("Write MeasurePoints at level = {}", lev);
435 // for(int j = 0; j < (int)para->getParH(lev)->MP.size(); j++)
436 // {
437 // MeasurePointWriter::writeMeasurePoints(para, lev, j, 0);
438 // }
439 //}
440 // //////////////////////////////////////////////////////////////////////////
441 finalize();
442}
443
445{
446 this->updateGrid27->updateGrid(0, timestep);
448 // run Analyzers for kinetic energy and enstrophy for TGV in 3D
449 // these analyzers only work on level 0
451 if (this->kineticEnergyAnalyzer || this->enstrophyAnalyzer) {
452 updateGrid27->exchangeData(0);
453 }
454 if (this->kineticEnergyAnalyzer)
455 this->kineticEnergyAnalyzer->run(timestep);
456 if (this->enstrophyAnalyzer)
457 this->enstrophyAnalyzer->run(timestep);
460 //Calc Mean
462 if (para->getCalcMean() && ((int)timestep >= para->getTimeCalcMedStart()) && ((int)timestep <= para->getTimeCalcMedEnd()))
463 {
464 for (int lev=para->getCoarse(); lev <= para->getFine(); lev++)
465 {
466 //calculateMean(para->getParD(lev)->vx_SP_Med,
467 // para->getParD(lev)->vy_SP_Med,
468 // para->getParD(lev)->vz_SP_Med,
469 // para->getParD(lev)->rho_SP_Med,
470 // para->getParD(lev)->press_SP_Med,
471 // para->getParD(lev)->geoSP,
472 // para->getParD(lev)->neighborX_SP,
473 // para->getParD(lev)->neighborY_SP,
474 // para->getParD(lev)->neighborZ_SP,
475 // para->getParD(lev)->size_Mat_SP,
476 // para->getParD(lev)->numberofthreads,
477 // para->getParD(lev)->d0SP.f[0],
478 // para->getParD(lev)->evenOrOdd);
479 //getLastCudaError("calculateMacroscopicQuantities execution failed");
480 calculateMeanCompressible(para->getParD(lev)->meanVelocityInXdirection,
481 para->getParD(lev)->meanVelocityInYdirection,
482 para->getParD(lev)->meanVelocityInZdirection,
483 para->getParD(lev)->meanDensity,
484 para->getParD(lev)->meanPressure,
485 para->getParD(lev)->typeOfGridNode,
486 para->getParD(lev)->neighborX,
487 para->getParD(lev)->neighborY,
488 para->getParD(lev)->neighborZ,
489 para->getParD(lev)->numberOfNodes,
490 para->getParD(lev)->numberofthreads,
491 para->getParD(lev)->distributions.f[0],
492 para->getParD(lev)->isEvenTimestep);
493 getLastCudaError("CalcMacMedCompSP27 execution failed");
494 }
495 }
496 if (para->getCalcTurbulenceIntensity()) {
497 for (int lev = para->getCoarse(); lev <= para->getFine(); lev++) {
499 para->getParD(lev)->vxx,
500 para->getParD(lev)->vyy,
501 para->getParD(lev)->vzz,
502 para->getParD(lev)->vxy,
503 para->getParD(lev)->vxz,
504 para->getParD(lev)->vyz,
505 para->getParD(lev)->vx_mean,
506 para->getParD(lev)->vy_mean,
507 para->getParD(lev)->vz_mean,
508 para->getParD(lev)->distributions.f[0],
509 para->getParD(lev)->typeOfGridNode,
510 para->getParD(lev)->neighborX,
511 para->getParD(lev)->neighborY,
512 para->getParD(lev)->neighborZ,
513 para->getParD(lev)->numberOfNodes,
514 para->getParD(lev)->isEvenTimestep,
515 para->getParD(lev)->numberofthreads
516 );
517 }
518 }
519
521 // CheckPoint
523 if (para->getDoCheckPoint() && para->getTimeDoCheckPoint() > 0 && timestep % para->getTimeDoCheckPoint() == 0 &&
524 timestep > 0 && !para->overWritingRestart(timestep)) {
525 averageTimer.end();
526 VF_LOG_INFO("Copy data for CheckPoint t = {}....", timestep);
527 for (int lev = para->getCoarse(); lev <= para->getFine(); lev++) {
528 cudaMemoryManager->cudaCopyFsForCheckPoint(lev);
529 }
530 VF_LOG_INFO("Write data for CheckPoint t = {}...", timestep);
531 const auto name = getFileName(para->getFName(), timestep, para->getMyProcessID());
532 restart_object->serialize(name, para);
533 VF_LOG_INFO("done");
534 averageTimer.start();
535 }
536
538 // Measure Points
540 // set MP-Time
541 if (para->getUseMeasurePoints()) {
542 if ((timestep % para->getTimestepForMeasurePoints()) == 0) {
543 unsigned int valuesPerClockCycle = (unsigned int)(para->getclockCycleForMeasurePoints() / para->getTimestepForMeasurePoints());
544 for (int lev = para->getCoarse(); lev <= para->getFine(); lev++) {
546 para->getParD(lev)->velocityInXdirectionAtMeasurePoints,
547 para->getParD(lev)->velocityInYdirectionAtMeasurePoints,
548 para->getParD(lev)->velocityInZdirectionAtMeasurePoints,
549 para->getParD(lev)->densityAtMeasurePoints,
550 para->getParD(lev)->indicesOfMeasurePoints,
551 para->getParD(lev)->numberOfMeasurePoints,
553 timestepForMeasuringPoints,
554 para->getParD(lev)->typeOfGridNode,
555 para->getParD(lev)->neighborX,
556 para->getParD(lev)->neighborY,
557 para->getParD(lev)->neighborZ,
558 para->getParD(lev)->numberOfNodes,
559 para->getParD(lev)->distributions.f[0],
560 para->getParD(lev)->numberofthreads,
561 para->getParD(lev)->isEvenTimestep);
562 }
563 timestepForMeasuringPoints++;
564 }
565 // Copy Measure Values
566 if ((timestep % (unsigned int)para->getclockCycleForMeasurePoints()) == 0) {
567 for (int lev = para->getCoarse(); lev <= para->getFine(); lev++) {
568 cudaMemoryManager->cudaCopyMeasurePointsToHost(lev);
569 para->copyMeasurePointsArrayToVector(lev);
570 VF_LOG_INFO("Write MeasurePoints at level = {} and timestep = {}", lev, timestep);
571 for (int j = 0; j < (int)para->getParH(lev)->MeasurePointVector.size(); j++)
572 {
573 MeasurePointWriter::writeMeasurePoints(para.get(), lev, j, timestep);
574 }
575 // MeasurePointWriter::calcAndWriteMeanAndFluctuations(para.get(), lev, t, para->getTStartOut());
576 }
577 timestepForMeasuringPoints = 0;
578 }
579 }
580
582 // File IO
584 if (para->getTimestepOut() > 0 && timestep % para->getTimestepOut() == 0 && timestep >= para->getTimestepStartOut()) {
585 averageTimer.end();
586 metaData.simulation.runtimeSeconds += averageTimer.getTimeInSeconds();
587 performanceOutput->log(averageTimer, timestep, communicator);
588
589 if (para->getPrintFiles()) {
590 readAndWriteFiles(timestep);
591 }
592 averageTimer.start();
593 }
594}
595
597{
598 averageTimer.end();
599 metaData.simulation.runtimeSeconds += averageTimer.getTimeInSeconds();
600 performanceOutput->log(averageTimer, para->getTimestepEnd(), communicator);
601 metaData.simulation.nups = performanceOutput->getNups();
602 metaData.simulation.runtimeSeconds = performanceOutput->totalRuntimeInSeconds();
604
605 vf::basics::writeYAML(metaData, para->getFName() + ".yaml");
606}
607
608
609void Simulation::readAndWriteFiles(uint timestep)
610{
611 VF_LOG_INFO("Write files t = {} ...", timestep);
612
613 for (int lev = para->getCoarse(); lev <= para->getFine(); lev++) {
614
615 updateGrid27->exchangeData(lev);
616
617 // if (para->getCalcMean() && ((int)t > para->getTimeCalcMedStart()) && ((int)t <= para->getTimeCalcMedEnd()))
618 // {
619 // unsigned int tdiff = t - t_prev;
620 // calculateMacrosopicMean(para->getParD(lev)->vx_SP_Med,
621 // para->getParD(lev)->vy_SP_Med,
622 // para->getParD(lev)->vz_SP_Med,
623 // para->getParD(lev)->rho_SP_Med,
624 // para->getParD(lev)->press_SP_Med,
625 // para->getParD(lev)->geoSP,
626 // para->getParD(lev)->neighborX_SP,
627 // para->getParD(lev)->neighborY_SP,
628 // para->getParD(lev)->neighborZ_SP,
629 // tdiff,
630 // para->getParD(lev)->size_Mat_SP,
631 // para->getParD(lev)->numberofthreads,
632 // para->getParD(lev)->evenOrOdd);
633 // getLastCudaError("calculateMacrosopicMean execution failed");
634 // }
635 // calculateMacroscopicQuantities(para->getParD(lev)->vx_SP,
636 // para->getParD(lev)->vy_SP,
637 // para->getParD(lev)->vz_SP,
638 // para->getParD(lev)->rho,
639 // para->getParD(lev)->pressure,
640 // para->getParD(lev)->geoSP,
641 // para->getParD(lev)->neighborX_SP,
642 // para->getParD(lev)->neighborY_SP,
643 // para->getParD(lev)->neighborZ_SP,
644 // para->getParD(lev)->size_Mat_SP,
645 // para->getParD(lev)->numberofthreads,
646 // para->getParD(lev)->d0SP.f[0],
647 // para->getParD(lev)->evenOrOdd);
648 // getLastCudaError("calculateMacroscopicQuantities execution failed");
649 calculateMacroscopicQuantitiesCompressible(para->getParD(lev)->velocityX,
650 para->getParD(lev)->velocityY,
651 para->getParD(lev)->velocityZ,
652 para->getParD(lev)->rho,
653 para->getParD(lev)->pressure,
654 para->getParD(lev)->typeOfGridNode,
655 para->getParD(lev)->neighborX,
656 para->getParD(lev)->neighborY,
657 para->getParD(lev)->neighborZ,
658 para->getParD(lev)->numberOfNodes,
659 para->getParD(lev)->numberofthreads,
660 para->getParD(lev)->distributions.f[0],
661 para->getParD(lev)->isEvenTimestep);
662 getLastCudaError("calculateMacroscopicQuantities execution failed");
663
664 cudaMemoryManager->cudaCopyPrint(lev);
665 if (para->getCalcMean()) {
666 cudaMemoryManager->cudaCopyMeanPrint(lev);
667 }
668
670 std::string fname = para->getFName() + "_ID_" + StringUtil::toString<int>(para->getMyProcessID()) + "_t_" + StringUtil::toString<int>(timestep);
671 if (this->kineticEnergyAnalyzer)
672 this->kineticEnergyAnalyzer->writeToFile(fname);
673 if (this->enstrophyAnalyzer)
674 this->enstrophyAnalyzer->writeToFile(fname);
676 if (para->getDiffOn())
677 cudaMemoryManager->cudaCopyConcentrationDeviceToHost(lev);
680 //if ((para->getParH(lev)->cpTop.size() > 0) && (t > para->getTStartOut()))
681 //{
682 // printCpTopIntermediateStep(para, t, lev);
683 //}
685 //MeasurePointWriter::writeSpacialAverageForXZSlices(para, lev, t);
687 //MeasurePointWriter::writeTestAcousticXY(para, lev, t);
688 //MeasurePointWriter::writeTestAcousticYZ(para, lev, t);
689 //MeasurePointWriter::writeTestAcousticXZ(para, lev, t);
691 }
693 //t_prev = t;
695 //calculate 2nd, 3rd and higher order moments
697 if (para->getCalc2ndOrderMoments()) calc2ndMoments(para.get(), cudaMemoryManager.get());
698 if (para->getCalc3rdOrderMoments()) calc3rdMoments(para.get(), cudaMemoryManager.get());
699 if (para->getCalcHighOrderMoments()) calcHigherOrderMoments(para.get(), cudaMemoryManager.get());
702 //calculate mean on host
704 if (para->getCalcMean() && ((int)timestep > para->getTimeCalcMedStart()) && ((int)timestep <= para->getTimeCalcMedEnd()) && ((timestep%(unsigned int)para->getclockCycleForMeasurePoints())==0)) {
705 unsigned int tdiff = timestep - previousTimestepForAveraging;
706 calcMean(para.get(), tdiff);
708 //added for incremental averaging
709 previousTimestepForAveraging = timestep;
710 resetMean(para.get());
712 }
713 if (para->getCalcTurbulenceIntensity()) {
714 uint t_diff = timestep - previousTimestepForTurbulenceIntensityCalculation;
715 calcTurbulenceIntensity(para.get(), cudaMemoryManager.get(), t_diff);
716 //writeAllTiDatafToFile(para.get(), t);
717 }
719 dataWriter->writeTimestep(para, timestep);
721 if (para->getCalcTurbulenceIntensity()) {
722 previousTimestepForTurbulenceIntensityCalculation = timestep;
723 resetVelocityFluctuationsAndMeans(para.get(), cudaMemoryManager.get());
724 }
726 if (para->getCalcDragLift())
727 {
728 printDragLift(para.get(), cudaMemoryManager.get(), timestep);
729 }
731
732#if DEBUG_FS
733 // Write distributions (f's) for debugging purposes.
734 DistributionDebugWriter::copyDistributionsToHost(*para, *cudaMemoryManager);
736#endif
737
739 VF_LOG_INFO("... done");
741}
742
744{
745 // CudaFreeHostMemory
746 for (int lev = para->getCoarse(); lev <= para->getFine(); lev++) {
747 cudaMemoryManager->cudaFreeCoord(lev);
748 cudaMemoryManager->cudaFreeSP(lev);
749 if (para->getCalcMean()) {
750 cudaMemoryManager->cudaFreeMeanSP(lev);
751 }
752 }
753 if (para->getMaxLevel() > 1) {
754 for (int lev = para->getCoarse(); lev < para->getFine(); lev++) {
755 cudaMemoryManager->cudaFreeInterfaceCF(lev);
756 cudaMemoryManager->cudaFreeInterfaceFC(lev);
757 cudaMemoryManager->cudaFreeInterfaceOffCF(lev);
758 cudaMemoryManager->cudaFreeInterfaceOffFC(lev);
759 }
760 }
761
762
763 //Boundary conditions
764 for (int lev = para->getCoarse(); lev <= para->getFine(); lev++) {
765 cudaMemoryManager->cudaFreeNoSlipBC(lev);
766 cudaMemoryManager->cudaFreeSlipBC(lev);
767 cudaMemoryManager->cudaFreeVeloBC(lev);
768 cudaMemoryManager->cudaFreeGeomBC(lev);
769 cudaMemoryManager->cudaFreeStressBC(lev);
770 cudaMemoryManager->cudaFreePrecursorBC(lev);
771 cudaMemoryManager->cudaFreeOutflowBC(lev);
772 cudaMemoryManager->cudaFreeDirectionalBoundaryCondition(lev);
773 }
774
776 // Temp
777 if (para->getDiffOn()) {
778 for (int lev = para->getCoarse(); lev < para->getFine(); lev++) {
779 cudaMemoryManager->cudaFreeConcentration(lev);
780 cudaMemoryManager->cudaFreeConcentrationNoFluxBC(lev);
781 cudaMemoryManager->cudaFreeConcentrationFluxBC(lev);
782 cudaMemoryManager->cudaFreeConcentrationDirichletBC(lev);
783 cudaMemoryManager->cudaFreeConcentrationNeumannBC(lev);
784 cudaMemoryManager->cudaFreeSurfaceLayerBC(lev);
785 cudaMemoryManager->cudaFreeDirectionalADBoundaryCondition(lev);
786
787 if(para->getUseTurbulentDiffusivity())
788 cudaMemoryManager->cudaFreeTurbulentDiffusivity(lev);
789 if(para->getBuoyancyEnabled())
790 cudaMemoryManager->cudaFreeLocalReferenceTemperature(lev);
791 }
792 }
793
795 // free second order moments
796 if (para->getCalc2ndOrderMoments()) {
797 for (int lev = para->getCoarse(); lev <= para->getFine(); lev++) {
798 cudaMemoryManager->cudaFree2ndMoments(lev);
799 }
800 }
802 // free third order moments
803 if (para->getCalc3rdOrderMoments()) {
804 for (int lev = para->getCoarse(); lev <= para->getFine(); lev++) {
805 cudaMemoryManager->cudaFree3rdMoments(lev);
806 }
807 }
809 // free higher order moments
810 if (para->getCalcHighOrderMoments()) {
811 for (int lev = para->getCoarse(); lev <= para->getFine(); lev++) {
812 cudaMemoryManager->cudaFreeHigherMoments(lev);
813 }
814 }
815
817 //Multi GPU
819 //3D domain decomposition
820 if (para->getNumprocs() > 1) {
821 for (int lev = para->getCoarse(); lev < para->getFine(); lev++) {
822 auto& parH = para->getParHostAsReference(lev);
823 auto& parD = para->getParDeviceAsReference(lev);
825 for (uint i = 0; i < para->getNumberOfProcessNeighborsX(lev, "send"); i++) {
826 cudaMemoryManager->cudaFreeProcessNeighbor(parH.sendProcessNeighborsX[i], parD.sendProcessNeighborsX[i]);
827 cudaMemoryManager->cudaFreeProcessNeighbor(parH.recvProcessNeighborsX[i], parD.recvProcessNeighborsX[i]);
828 }
830 for (uint i = 0; i < para->getNumberOfProcessNeighborsY(lev, "send"); i++) {
831 cudaMemoryManager->cudaFreeProcessNeighbor(parH.sendProcessNeighborsY[i], parD.sendProcessNeighborsY[i]);
832 cudaMemoryManager->cudaFreeProcessNeighbor(parH.recvProcessNeighborsY[i], parD.recvProcessNeighborsY[i]);
833 }
835 for (uint i = 0; i < para->getNumberOfProcessNeighborsZ(lev, "send"); i++) {
836 cudaMemoryManager->cudaFreeProcessNeighbor(parH.sendProcessNeighborsZ[i], parD.sendProcessNeighborsZ[i]);
837 cudaMemoryManager->cudaFreeProcessNeighbor(parH.recvProcessNeighborsZ[i], parD.recvProcessNeighborsZ[i]);
838 }
839 }
840 }
842 // Turbulence Intensity
843 if (para->getCalcTurbulenceIntensity()) {
844 cudaFreeTurbulenceIntensityArrays(para.get(), cudaMemoryManager.get());
845 }
846
847 // Cuda Streams
848 if (para->getUseStreams()) {
849 para->getStreamManager()->destroyCudaEvents();
850 para->getStreamManager()->terminateStreams();
851 }
852}
853
854}
855
#define VF_LOG_TRACE(...)
Definition Logger.h:48
#define VF_LOG_INFO(...)
Definition Logger.h:50
double getTimeInSeconds() const
Definition Timer.cpp:58
static void copyDistributionsToHost(const Parameter &para, const CudaMemoryManager &cudaMemoryManager)
Copy distributions from device to host. Call this function before writing data.
static void writeDistributions(const Parameter &para, uint timestep)
write the distributions for all levels
static void allocateDistributionsOnHost(const CudaMemoryManager &cudaMemoryManager)
allocate memory for the distributions on the host
static std::shared_ptr< GridProvider > makeGridGenerator(std::shared_ptr< GridBuilder > builder, std::shared_ptr< Parameter > para, std::shared_ptr< CudaMemoryManager > cudaMemoryManager, vf::parallel::Communicator &communicator)
static void writeMeasurePoints(Parameter *para, int level, int index, int t)
void setFactories(std::unique_ptr< KernelFactory > &&kernelFactory, std::unique_ptr< PreProcessorFactory > &&preProcessorFactory)
Simulation(std::shared_ptr< Parameter > para, std::shared_ptr< GridBuilder > builder, const BoundaryConditionFactory *bcFactory, GridScalingFactory *scalingFactory=nullptr)
void addKineticEnergyAnalyzer(uint tAnalyse)
void addEnstrophyAnalyzer(uint tAnalyse)
void setDataWriter(std::shared_ptr< DataWriter > dataWriter)
void finalize()
finalize simulation. Only needs to be called when using calculateTimestep!
void calculateTimestep(uint timestep)
can be used as an alternative to run(), if the simulation needs to be controlled from the outside (e....
void initTimers()
needed to initialize the simulation timers if calculateTimestep is used instead of run()
An abstract class for communication between processes in parallel computation.
virtual int mapCudaDevicesOnHosts(const std::vector< unsigned int > &devices, int numberOfDevices) const =0
std::shared_ptr< T > SPtr
float real
Definition DataTypes.h:42
unsigned int uint
Definition DataTypes.h:47
void logPostSimulation(const MetaData &meta_data)
Definition MetaData.cpp:140
void writeYAML(const MetaData &meta_data, const std::string &filename)
void logPreSimulation(const MetaData &meta_data)
Definition MetaData.cpp:82
void verifyAndSetDevice(int deviceId)
void CalcTurbulenceIntensityDevice(real *vxx, real *vyy, real *vzz, real *vxy, real *vxz, real *vyz, real *vx_mean, real *vy_mean, real *vz_mean, real *DD, uint *typeOfGridNode, unsigned int *neighborX, unsigned int *neighborY, unsigned int *neighborZ, unsigned long long numberOfLBnodes, bool isEvenTimestep, uint numberOfThreads)
void resetMean(Parameter *para)
Definition CalcMean.cpp:72
void findEdgeNodesCommMultiGPU(Parameter &parameter)
Function for finding edge nodes in the multi-gpu implementation.
void calcTurbulenceIntensity(Parameter *para, CudaMemoryManager *cudaMemoryManager, uint tdiff)
void printDragLift(Parameter *para, CudaMemoryManager *cudaMemoryManager, int timestep)
Definition DragLift.cpp:105
std::string getFileName(const std::string &fname, int step, int myID)
void allocMeanAD(Parameter *para, CudaMemoryManager *cudaMemoryManager)
Definition CalcMean.cpp:84
void allocMean(Parameter *para, CudaMemoryManager *cudaMemoryManager)
Definition CalcMean.cpp:45
void calc3rdMoments(Parameter *para, CudaMemoryManager *cudaMemoryManager)
void initHigherOrderMoments(Parameter *para)
void allocHigherOrderMoments(Parameter *para, CudaMemoryManager *cudaMemoryManager)
void allocTurbulenceIntensity(Parameter *para, CudaMemoryManager *cudaMemoryManager)
void alloc2ndMoments(Parameter *para, CudaMemoryManager *cudaMemoryManager)
void initLattice(SPtr< Parameter > para, SPtr< PreProcessor > preProcessor, SPtr< PreProcessor > preProcessorAD, SPtr< CudaMemoryManager > cudaMemoryManager)
void allocDragLift(Parameter *para, CudaMemoryManager *cudaMemoryManager)
Definition DragLift.cpp:90
void init3rdMoments(Parameter *para)
void alloc3rdMoments(Parameter *para, CudaMemoryManager *cudaMemoryManager)
void calc2ndMoments(Parameter *para, CudaMemoryManager *cudaMemoryManager)
void calcMean(Parameter *para, uint tdiff)
Definition CalcMean.cpp:59
void calcHigherOrderMoments(Parameter *para, CudaMemoryManager *cudaMemoryManager)
void resetVelocityFluctuationsAndMeans(Parameter *para, CudaMemoryManager *cudaMemoryManager)
void init2ndMoments(Parameter *para)
vf::basics::MetaData createMetaData(const Parameter &parameter)
void cudaFreeTurbulenceIntensityArrays(Parameter *para, CudaMemoryManager *cudaMemoryManager)
Simulation simulation
Definition MetaData.h:119