EnhancedSolver completed
This commit is contained in:
@@ -45,6 +45,7 @@ vis:
|
||||
$(info ===> GENERATE VISUALIZATION)
|
||||
@gnuplot -e "filename='pressure.dat'" ./surface.plot
|
||||
@gnuplot -e "filename='velocity.dat'" ./vector.plot
|
||||
@gnuplot -e "filename='residual.dat'" ./residual.plot
|
||||
|
||||
vis_clean:
|
||||
$(info ===> CLEAN VISUALIZATION)
|
||||
|
@@ -26,8 +26,8 @@ p_init 1.0 # initial value for pressure
|
||||
|
||||
xlength 7.0 # domain size in x-direction
|
||||
ylength 1.5 # domain size in y-direction
|
||||
imax 210 # number of interior cells in x-direction
|
||||
jmax 45 # number of interior cells in y-direction
|
||||
imax 200 # number of interior cells in x-direction
|
||||
jmax 40 # number of interior cells in y-direction
|
||||
|
||||
# Time Data:
|
||||
# ---------
|
||||
@@ -42,20 +42,20 @@ tau 0.5 # safety factor for time stepsize control (<0 constant delt)
|
||||
itermax 500 # maximal number of pressure iteration in one time step
|
||||
eps 0.0001 # stopping tolerance for pressure iteration
|
||||
rho 0.52
|
||||
omg 1.8 # relaxation parameter for SOR iteration
|
||||
omg 1.7 # relaxation parameter for SOR iteration
|
||||
gamma 0.9 # upwind differencing factor gamma
|
||||
|
||||
# Multigrid data:
|
||||
# ---------
|
||||
|
||||
levels 3 # Multigrid levels
|
||||
presmooth 15 # Pre-smoothning iterations
|
||||
presmooth 55 # Pre-smoothning iterations
|
||||
postsmooth 5 # Post-smoothning iterations
|
||||
|
||||
# Particle Tracing Data:
|
||||
# -----------------------
|
||||
|
||||
numberOfParticles 200
|
||||
numberOfParticles 500
|
||||
startTime 0 #if you want to see particles trapped in recirculation zone, startTime should be set to 0
|
||||
injectTimePeriod 1.0
|
||||
writeTimePeriod 0.5
|
||||
|
@@ -39,7 +39,7 @@ tau 0.5 # safety factor for time stepsize control (<0 constant delt)
|
||||
# Multigrid data:
|
||||
# ---------
|
||||
|
||||
levels 2 # Multigrid levels
|
||||
levels 3 # Multigrid levels
|
||||
presmooth 5 # Pre-smoothning iterations
|
||||
postsmooth 5 # Post-smoothning iterations
|
||||
|
||||
@@ -48,7 +48,7 @@ postsmooth 5 # Post-smoothning iterations
|
||||
|
||||
itermax 500 # maximal number of pressure iteration in one time step
|
||||
eps 0.00001 # stopping tolerance for pressure iteration
|
||||
omg 1.8 # relaxation parameter for SOR iteration
|
||||
omg 1.7 # relaxation parameter for SOR iteration
|
||||
gamma 0.9 # upwind differencing factor gamma
|
||||
|
||||
# Particle Tracing Data:
|
||||
|
@@ -42,14 +42,14 @@ tau 0.5 # safety factor for time stepsize control (<0 constant delt)
|
||||
itermax 1000 # maximal number of pressure iteration in one time step
|
||||
eps 0.001 # stopping tolerance for pressure iteration
|
||||
rho 0.5
|
||||
omg 1.8 # relaxation parameter for SOR iteration
|
||||
omg 1.7 # relaxation parameter for SOR iteration
|
||||
gamma 0.9 # upwind differencing factor gamma
|
||||
|
||||
# Multigrid data:
|
||||
# ---------
|
||||
|
||||
levels 3 # Multigrid levels
|
||||
presmooth 10 # Pre-smoothning iterations
|
||||
presmooth 20 # Pre-smoothning iterations
|
||||
postsmooth 5 # Post-smoothning iterations
|
||||
|
||||
# Particle Tracing Data:
|
||||
|
9
EnhancedSolver/2D-mpi/residual.plot
Normal file
9
EnhancedSolver/2D-mpi/residual.plot
Normal file
@@ -0,0 +1,9 @@
|
||||
set terminal png size 1800,768 enhanced font ,12
|
||||
set output 'residual.png'
|
||||
set datafile separator whitespace
|
||||
set xlabel "Timestep"
|
||||
set ylabel "Residual"
|
||||
|
||||
set logscale y 2
|
||||
|
||||
plot 'residual.dat' using 1:2 title "Residual"
|
@@ -14,7 +14,7 @@ static int sum(int* sizes, int position)
|
||||
{
|
||||
int sum = 0;
|
||||
|
||||
for (int i = 0; i < position; i++) {
|
||||
for (int i = 0; i < position; i += position) {
|
||||
sum += sizes[i];
|
||||
}
|
||||
|
||||
@@ -174,6 +174,17 @@ void commPartition(Comm* c, int jmax, int imax)
|
||||
#ifdef _MPI
|
||||
c->imaxLocal = imax;
|
||||
c->jmaxLocal = sizeOfRank(c->coords[JDIM], c->size, jmax);
|
||||
|
||||
c->neighbours[BOTTOM] = c->rank == 0 ? -1 : c->rank - 1;
|
||||
c->neighbours[TOP] = c->rank == (c->size - 1) ? -1 : c->rank + 1;
|
||||
c->neighbours[LEFT] = -1;
|
||||
c->neighbours[RIGHT] = -1;
|
||||
|
||||
c->coords[IDIM] = 0;
|
||||
c->coords[JDIM] = c->rank;
|
||||
|
||||
c->dims[IDIM] = 1;
|
||||
c->dims[JDIM] = c->size;
|
||||
#else
|
||||
c->imaxLocal = imax;
|
||||
c->jmaxLocal = jmax;
|
||||
@@ -182,15 +193,33 @@ void commPartition(Comm* c, int jmax, int imax)
|
||||
|
||||
void commUpdateDatatypes(Comm* oldcomm, Comm* newcomm, int imaxLocal, int jmaxLocal)
|
||||
{
|
||||
Comm* newcomm;
|
||||
|
||||
#if defined _MPI
|
||||
newcomm->comm = MPI_COMM_NULL;
|
||||
int result = MPI_Comm_dup(oldcomm->comm, &newcomm->comm);
|
||||
int result = MPI_Comm_dup(MPI_COMM_WORLD, &newcomm->comm);
|
||||
|
||||
if (result == MPI_ERR_COMM) {
|
||||
printf("\nNull communicator. Duplication failed !!\n");
|
||||
}
|
||||
|
||||
newcomm->rank = oldcomm->rank;
|
||||
newcomm->size = oldcomm->size;
|
||||
|
||||
newcomm->imaxLocal = imaxLocal / 2;
|
||||
newcomm->jmaxLocal = jmaxLocal / 2;
|
||||
|
||||
newcomm->neighbours[BOTTOM] = newcomm->rank == 0 ? -1 : newcomm->rank - 1;
|
||||
newcomm->neighbours[TOP] = newcomm->rank == (newcomm->size - 1) ? -1 : newcomm->rank + 1;
|
||||
newcomm->neighbours[LEFT] = -1;
|
||||
newcomm->neighbours[RIGHT] = -1;
|
||||
|
||||
newcomm->coords[IDIM] = 0;
|
||||
newcomm->coords[JDIM] = newcomm->rank;
|
||||
|
||||
newcomm->dims[IDIM] = 1;
|
||||
newcomm->dims[JDIM] = newcomm->size;
|
||||
|
||||
|
||||
#endif
|
||||
newcomm->imaxLocal = imaxLocal;
|
||||
newcomm->jmaxLocal = jmaxLocal;
|
||||
|
@@ -4,18 +4,18 @@
|
||||
* Use of this source code is governed by a MIT style
|
||||
* license that can be found in the LICENSE file.
|
||||
*/
|
||||
#include "comm.h"
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "comm.h"
|
||||
#include <string.h>
|
||||
|
||||
#ifdef _MPI
|
||||
// subroutines local to this module
|
||||
static int sum(int* sizes, int position)
|
||||
static int sum(int* sizes, int init, int offset, int coord)
|
||||
{
|
||||
int sum = 0;
|
||||
|
||||
for (int i = 0; i < position; i++) {
|
||||
for (int i = init - offset; coord > 0; i -= offset, --coord) {
|
||||
sum += sizes[i];
|
||||
}
|
||||
|
||||
@@ -79,8 +79,8 @@ static void assembleResult(Comm* c, double* src, double* dst, int imax, int jmax
|
||||
int newSizes[NDIMS] = { newSizesJ[i], newSizesI[i] };
|
||||
int coords[NDIMS];
|
||||
MPI_Cart_coords(c->comm, i, NDIMS, coords);
|
||||
int starts[NDIMS] = { sum(newSizesJ, coords[JDIM]),
|
||||
sum(newSizesI, coords[IDIM]) };
|
||||
int starts[NDIMS] = { sum(newSizesJ, i, 1, coords[JDIM]),
|
||||
sum(newSizesI, i, c->dims[JDIM], coords[IDIM]) };
|
||||
printf(
|
||||
"Rank: %d, Coords(i,j): %d %d, Size(i,j): %d %d, Target Size(i,j): %d %d "
|
||||
"Starts(i,j): %d %d\n",
|
||||
@@ -295,9 +295,16 @@ void commUpdateDatatypes(Comm* oldcomm, Comm* newcomm, int imaxLocal, int jmaxLo
|
||||
if (result == MPI_ERR_COMM) {
|
||||
printf("\nNull communicator. Duplication failed !!\n");
|
||||
}
|
||||
|
||||
newcomm->imaxLocal = imaxLocal;
|
||||
newcomm->jmaxLocal = jmaxLocal;
|
||||
|
||||
newcomm->rank = oldcomm->rank;
|
||||
newcomm->size = oldcomm->size;
|
||||
|
||||
memcpy(&newcomm->neighbours, &oldcomm->neighbours, sizeof(oldcomm->neighbours));
|
||||
memcpy(&newcomm->coords, &oldcomm->coords, sizeof(oldcomm->coords));
|
||||
memcpy(&newcomm->dims, &oldcomm->dims, sizeof(oldcomm->dims));
|
||||
|
||||
newcomm->imaxLocal = imaxLocal/2;
|
||||
newcomm->jmaxLocal = jmaxLocal/2;
|
||||
|
||||
MPI_Datatype jBufferType;
|
||||
MPI_Type_contiguous(imaxLocal, MPI_DOUBLE, &jBufferType);
|
||||
|
@@ -11,11 +11,11 @@
|
||||
|
||||
#ifdef _MPI
|
||||
// subroutines local to this module
|
||||
static int sum(int* sizes, int position)
|
||||
static int sum(int* sizes, int init, int offset, int coord)
|
||||
{
|
||||
int sum = 0;
|
||||
|
||||
for (int i = 0; i < position; i++) {
|
||||
for (int i = init - offset; coord > 0; i -= offset, --coord) {
|
||||
sum += sizes[i];
|
||||
}
|
||||
|
||||
@@ -79,8 +79,8 @@ static void assembleResult(Comm* c, double* src, double* dst, int imax, int jmax
|
||||
int newSizes[NDIMS] = { newSizesJ[i], newSizesI[i] };
|
||||
int coords[NDIMS];
|
||||
MPI_Cart_coords(c->comm, i, NDIMS, coords);
|
||||
int starts[NDIMS] = { sum(newSizesJ, coords[JDIM]),
|
||||
sum(newSizesI, coords[IDIM]) };
|
||||
int starts[NDIMS] = { sum(newSizesJ, i, 1, coords[JDIM]),
|
||||
sum(newSizesI, i, c->dims[JDIM], coords[IDIM]) };
|
||||
printf(
|
||||
"Rank: %d, Coords(i,j): %d %d, Size(i,j): %d %d, Target Size(i,j): %d %d "
|
||||
"Starts(i,j): %d %d\n",
|
||||
@@ -277,8 +277,12 @@ void commUpdateDatatypes(Comm* oldcomm, Comm* newcomm, int imaxLocal, int jmaxLo
|
||||
printf("\nNull communicator. Duplication failed !!\n");
|
||||
}
|
||||
|
||||
newcomm->imaxLocal = imaxLocal;
|
||||
newcomm->jmaxLocal = jmaxLocal;
|
||||
newcomm->rank = oldcomm->rank;
|
||||
newcomm->size = oldcomm->size;
|
||||
|
||||
|
||||
newcomm->imaxLocal = imaxLocal / 2;
|
||||
newcomm->jmaxLocal = jmaxLocal / 2;
|
||||
|
||||
MPI_Datatype jBufferType;
|
||||
MPI_Type_contiguous(imaxLocal, MPI_DOUBLE, &jBufferType);
|
||||
|
@@ -140,7 +140,6 @@ void initDiscretiztion(Discretization* d, Parameter* params)
|
||||
#ifdef _MPI
|
||||
MPI_Allgather(&d->xLocal, 1, MPI_DOUBLE, xLocal, 1, MPI_DOUBLE, d->comm.comm);
|
||||
MPI_Allgather(&d->yLocal, 1, MPI_DOUBLE, yLocal, 1, MPI_DOUBLE, d->comm.comm);
|
||||
#endif
|
||||
|
||||
d->xOffset = sumOffset(xLocal,
|
||||
d->comm.rank,
|
||||
@@ -149,6 +148,13 @@ void initDiscretiztion(Discretization* d, Parameter* params)
|
||||
d->yOffset = sumOffset(yLocal, d->comm.rank, 1, d->comm.coords[JDIM]);
|
||||
d->xOffsetEnd = d->xOffset + d->xLocal;
|
||||
d->yOffsetEnd = d->yOffset + d->yLocal;
|
||||
#else
|
||||
|
||||
d->xOffset = 0;
|
||||
d->yOffset = 0;
|
||||
d->xOffsetEnd = d->xOffset + d->xLocal;
|
||||
d->yOffsetEnd = d->yOffset + d->yLocal;
|
||||
#endif
|
||||
|
||||
printf("Rank : %d, xOffset : %.2f, yOffset : %.2f, xOffsetEnd : %.2f, yOffsetEnd : "
|
||||
"%.2f\n",
|
||||
|
@@ -50,6 +50,8 @@ int main(int argc, char** argv)
|
||||
|
||||
commInit(&d.comm, argc, argv);
|
||||
initParameter(&p);
|
||||
FILE* fp;
|
||||
fp = initResidualWriter();
|
||||
|
||||
if (argc != 2) {
|
||||
printf("Usage: %s <configFile>\n", argv[0]);
|
||||
@@ -83,7 +85,7 @@ int main(int argc, char** argv)
|
||||
double tau = d.tau;
|
||||
double te = d.te;
|
||||
double t = 0.0;
|
||||
|
||||
double res = 0.0;
|
||||
timeStart = getTimeStamp();
|
||||
while (t <= te) {
|
||||
if (tau > 0.0) computeTimestep(&d);
|
||||
@@ -92,9 +94,12 @@ int main(int argc, char** argv)
|
||||
setObjectBoundaryCondition(&d);
|
||||
computeFG(&d);
|
||||
computeRHS(&d);
|
||||
solve(&s, d.p, d.rhs);
|
||||
res = solve(&s, d.p, d.rhs);
|
||||
adaptUV(&d);
|
||||
trace(&particletracer, &d, t);
|
||||
|
||||
writeResidual(fp, t, res);
|
||||
|
||||
t += d.dt;
|
||||
|
||||
#ifdef VERBOSE
|
||||
@@ -112,7 +117,7 @@ int main(int argc, char** argv)
|
||||
if (commIsMaster(s.comm)) {
|
||||
printf("Solution took %.2fs\n", timeStop - timeStart);
|
||||
}
|
||||
|
||||
fclose(fp);
|
||||
freeParticles(&particletracer);
|
||||
writeResults(&d);
|
||||
commFinalize(s.comm);
|
||||
|
@@ -103,8 +103,9 @@ void initParticleTracer(
|
||||
particletracer->lastUpdateTime = params->startTime;
|
||||
particletracer->lastWriteTime = params->startTime;
|
||||
|
||||
particletracer->pointer = 0;
|
||||
particletracer->totalParticles = 0;
|
||||
particletracer->pointer = 0;
|
||||
particletracer->totalParticles = 0;
|
||||
particletracer->removedParticles = 0;
|
||||
|
||||
particletracer->imax = params->imax;
|
||||
particletracer->jmax = params->jmax;
|
||||
@@ -199,14 +200,7 @@ void initParticleTracer(
|
||||
|
||||
memcpy(particletracer->offset, offset, sizeof(offset));
|
||||
|
||||
for (int i = 0; i < particletracer->numberOfParticles; ++i) {
|
||||
double spacing = (double)i / (double)(particletracer->numberOfParticles - 1);
|
||||
particletracer->linSpaceLine[i].x = spacing * particletracer->x1 +
|
||||
(1.0 - spacing) * particletracer->x2;
|
||||
particletracer->linSpaceLine[i].y = spacing * particletracer->y1 +
|
||||
(1.0 - spacing) * particletracer->y2;
|
||||
particletracer->linSpaceLine[i].flag = true;
|
||||
}
|
||||
particleRandomizer(particletracer);
|
||||
|
||||
#ifdef _MPI
|
||||
// Create the mpi_particle datatype
|
||||
@@ -252,20 +246,37 @@ void printParticles(ParticleTracer* particletracer)
|
||||
particletracer->yOffsetEnd);
|
||||
}
|
||||
}
|
||||
void injectParticles(ParticleTracer* particletracer)
|
||||
void injectParticles(ParticleTracer* particletracer, double* s)
|
||||
{
|
||||
double x, y;
|
||||
compress(particletracer);
|
||||
particleRandomizer(particletracer);
|
||||
|
||||
int imaxLocal = particletracer->imaxLocal;
|
||||
int jmaxLocal = particletracer->jmaxLocal;
|
||||
|
||||
for (int i = 0; i < particletracer->numberOfParticles; ++i) {
|
||||
x = particletracer->linSpaceLine[i].x;
|
||||
y = particletracer->linSpaceLine[i].y;
|
||||
if (x >= particletracer->xOffset && y >= particletracer->yOffset &&
|
||||
x <= particletracer->xOffsetEnd && y <= particletracer->yOffsetEnd) {
|
||||
|
||||
particletracer->particlePool[particletracer->pointer].x = x;
|
||||
particletracer->particlePool[particletracer->pointer].y = y;
|
||||
particletracer->particlePool[particletracer->pointer].flag = true;
|
||||
++(particletracer->pointer);
|
||||
++(particletracer->totalParticles);
|
||||
particletracer->particlePool[particletracer->pointer].x = x;
|
||||
particletracer->particlePool[particletracer->pointer].y = y;
|
||||
|
||||
int i = particletracer->particlePool[particletracer->pointer].x /
|
||||
particletracer->dx;
|
||||
int j = particletracer->particlePool[particletracer->pointer].y /
|
||||
particletracer->dy;
|
||||
|
||||
int iOffset = particletracer->xOffset / particletracer->dx,
|
||||
jOffset = particletracer->yOffset / particletracer->dy;
|
||||
|
||||
if (S(i - iOffset, j - jOffset) == FLUID) {
|
||||
particletracer->particlePool[particletracer->pointer].flag = true;
|
||||
++(particletracer->pointer);
|
||||
++(particletracer->totalParticles);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -289,18 +300,16 @@ void advanceParticles(ParticleTracer* particletracer,
|
||||
double xlength = particletracer->xlength;
|
||||
double ylength = particletracer->ylength;
|
||||
|
||||
Particle buff[particletracer->size][100];
|
||||
Particle buff[particletracer->size][(particletracer->estimatedNumParticles)];
|
||||
memset(buff, 0, sizeof(buff));
|
||||
Particle recvbuff[particletracer->size][(particletracer->estimatedNumParticles)];
|
||||
memset(buff, 0, sizeof(recvbuff));
|
||||
|
||||
for (int i = 0; i < particletracer->size; ++i) {
|
||||
for (int j = 0; j < 100; ++j) {
|
||||
buff[i][j].x = 0.0;
|
||||
buff[i][j].y = 0.0;
|
||||
buff[i][j].flag = false;
|
||||
}
|
||||
}
|
||||
int particleBufIndex[particletracer->size];
|
||||
int particleBufIndex[particletracer->size],
|
||||
recvparticleBufIndex[particletracer->size];
|
||||
|
||||
memset(particleBufIndex, 0, sizeof(particleBufIndex));
|
||||
memset(recvparticleBufIndex, 0, sizeof(recvparticleBufIndex));
|
||||
|
||||
for (int i = 0; i < particletracer->totalParticles; ++i) {
|
||||
if (particletracer->particlePool[i].flag == true) {
|
||||
@@ -345,12 +354,12 @@ void advanceParticles(ParticleTracer* particletracer,
|
||||
particletracer->particlePool[i].y = new_y;
|
||||
|
||||
if (((new_x < particletracer->xOffset) ||
|
||||
(new_x >= particletracer->xOffsetEnd) ||
|
||||
(new_x > particletracer->xOffsetEnd) ||
|
||||
(new_y < particletracer->yOffset) ||
|
||||
(new_y >= particletracer->yOffsetEnd))) {
|
||||
(new_y > particletracer->yOffsetEnd))) {
|
||||
// New logic to transfer particles to neighbouring ranks or discard the
|
||||
// particle.
|
||||
|
||||
#ifdef _MPI
|
||||
for (int i = 0; i < particletracer->size; ++i) {
|
||||
if ((new_x >=
|
||||
particletracer->offset[i + particletracer->size * XOFFSET]) &&
|
||||
@@ -367,6 +376,7 @@ void advanceParticles(ParticleTracer* particletracer,
|
||||
++particleBufIndex[i];
|
||||
}
|
||||
}
|
||||
#endif
|
||||
particletracer->particlePool[i].flag = false;
|
||||
particletracer->removedParticles++;
|
||||
}
|
||||
@@ -384,14 +394,43 @@ void advanceParticles(ParticleTracer* particletracer,
|
||||
|
||||
#ifdef _MPI
|
||||
for (int i = 0; i < particletracer->size; ++i) {
|
||||
if (i != particletracer->rank) {
|
||||
MPI_Send(buff[i], 100, particletracer->mpi_particle, i, 0, comm->comm);
|
||||
if (i != comm->rank) {
|
||||
MPI_Send(&particleBufIndex[i], 1, MPI_INT, i, 0, comm->comm);
|
||||
}
|
||||
}
|
||||
for (int i = 0; i < particletracer->size; ++i) {
|
||||
if (i != particletracer->rank) {
|
||||
MPI_Recv(buff[i],
|
||||
100,
|
||||
MPI_Recv(&recvparticleBufIndex[i],
|
||||
1,
|
||||
MPI_INT,
|
||||
i,
|
||||
0,
|
||||
comm->comm,
|
||||
MPI_STATUS_IGNORE);
|
||||
|
||||
// if (0 !=recvparticleBufIndex[i]) {
|
||||
// printf("Rank %d will receive %d particles from rank %d\n",
|
||||
// particletracer->rank,
|
||||
// recvparticleBufIndex[i],
|
||||
// i);
|
||||
// }
|
||||
}
|
||||
}
|
||||
|
||||
for (int i = 0; i < particletracer->size; ++i) {
|
||||
if (i != particletracer->rank) {
|
||||
MPI_Send(buff[i],
|
||||
particleBufIndex[i],
|
||||
particletracer->mpi_particle,
|
||||
i,
|
||||
0,
|
||||
comm->comm);
|
||||
}
|
||||
}
|
||||
for (int i = 0; i < particletracer->size; ++i) {
|
||||
if (i != particletracer->rank) {
|
||||
MPI_Recv(recvbuff[i],
|
||||
recvparticleBufIndex[i],
|
||||
particletracer->mpi_particle,
|
||||
i,
|
||||
0,
|
||||
@@ -401,16 +440,14 @@ void advanceParticles(ParticleTracer* particletracer,
|
||||
}
|
||||
for (int i = 0; i < particletracer->size; ++i) {
|
||||
if (i != particletracer->rank) {
|
||||
for (int j = 0; j < 100; ++j) {
|
||||
if (buff[i][j].flag == true) {
|
||||
particletracer->particlePool[particletracer->pointer].x = buff[i][j]
|
||||
.x;
|
||||
particletracer->particlePool[particletracer->pointer].y = buff[i][j]
|
||||
.y;
|
||||
particletracer->particlePool[particletracer->pointer].flag = true;
|
||||
++(particletracer->pointer);
|
||||
++(particletracer->totalParticles);
|
||||
}
|
||||
for (int j = 0; j < recvparticleBufIndex[i]; ++j) {
|
||||
particletracer->particlePool[particletracer->pointer].x = recvbuff[i][j]
|
||||
.x;
|
||||
particletracer->particlePool[particletracer->pointer].y = recvbuff[i][j]
|
||||
.y;
|
||||
particletracer->particlePool[particletracer->pointer].flag = true;
|
||||
++(particletracer->pointer);
|
||||
++(particletracer->totalParticles);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -427,7 +464,7 @@ void freeParticles(ParticleTracer* particletracer)
|
||||
void writeParticles(ParticleTracer* particletracer, Comm* comm)
|
||||
{
|
||||
int collectedBuffIndex[particletracer->size];
|
||||
|
||||
compress(particletracer);
|
||||
#ifdef _MPI
|
||||
|
||||
MPI_Gather(&particletracer->totalParticles,
|
||||
@@ -480,13 +517,12 @@ void writeParticles(ParticleTracer* particletracer, Comm* comm)
|
||||
// fprintf(fp, "CYCLE 1 1 int\n");
|
||||
// fprintf(fp, "1\n");
|
||||
|
||||
#ifdef _MPI
|
||||
int overallTotalParticles = sum(collectedBuffIndex, particletracer->size);
|
||||
|
||||
// fprintf(fp, "POINTS %d float\n", overallTotalParticles);
|
||||
|
||||
// printf("Total particles : %d\n", overallTotalParticles);
|
||||
|
||||
#ifdef _MPI
|
||||
for (int i = 1; i < particletracer->size; ++i) {
|
||||
Particle recvBuff[collectedBuffIndex[i]];
|
||||
MPI_Recv(&recvBuff,
|
||||
@@ -501,10 +537,17 @@ void writeParticles(ParticleTracer* particletracer, Comm* comm)
|
||||
double x = recvBuff[j].x;
|
||||
double y = recvBuff[j].y;
|
||||
fprintf(fp, "%f %f\n", x, y);
|
||||
|
||||
// printf("Rank : 0 receiving from rank %d X : %.2f, Y : %.2f with totalpt
|
||||
// : %d\n", i, x, y, particletracer->totalParticles);
|
||||
}
|
||||
}
|
||||
#else
|
||||
int overallTotalParticles = particletracer->totalParticles;
|
||||
|
||||
// fprintf(fp, "POINTS %d float\n", overallTotalParticles);
|
||||
|
||||
// printf("Total particles : %d\n", overallTotalParticles);
|
||||
#endif
|
||||
for (int i = 0; i < particletracer->totalParticles; ++i) {
|
||||
double x = particletracer->particlePool[i].x;
|
||||
@@ -568,7 +611,7 @@ void trace(ParticleTracer* particletracer, Discretization* d, double time)
|
||||
{
|
||||
if (time >= particletracer->startTime) {
|
||||
if ((time - particletracer->lastInjectTime) >= particletracer->injectTimePeriod) {
|
||||
injectParticles(particletracer);
|
||||
injectParticles(particletracer, d->grid.s);
|
||||
particletracer->lastInjectTime = time;
|
||||
}
|
||||
if ((time - particletracer->lastWriteTime) >= particletracer->writeTimePeriod) {
|
||||
@@ -591,7 +634,7 @@ void compress(ParticleTracer* particletracer)
|
||||
Particle tempPool[particletracer->totalParticles];
|
||||
int totalParticles = 0;
|
||||
|
||||
printf("Performing compression ...");
|
||||
// printf("\nPerforming compression ...");
|
||||
|
||||
for (int i = 0; i < particletracer->totalParticles; ++i) {
|
||||
if (memPool[i].flag == true) {
|
||||
@@ -602,11 +645,31 @@ void compress(ParticleTracer* particletracer)
|
||||
}
|
||||
}
|
||||
|
||||
printf(" remove %d particles\n", particletracer->totalParticles - totalParticles);
|
||||
// printf(" remove %d particles\n", particletracer->totalParticles - totalParticles);
|
||||
|
||||
particletracer->totalParticles = totalParticles;
|
||||
particletracer->removedParticles = 0;
|
||||
particletracer->pointer = totalParticles + 1;
|
||||
particletracer->pointer = totalParticles;
|
||||
|
||||
memcpy(particletracer->particlePool, tempPool, totalParticles * sizeof(Particle));
|
||||
}
|
||||
|
||||
void particleRandomizer(ParticleTracer* particletracer)
|
||||
{
|
||||
memset(particletracer->linSpaceLine,
|
||||
0,
|
||||
sizeof(Particle) * particletracer->numberOfParticles);
|
||||
|
||||
for (int i = 0; i < particletracer->numberOfParticles; ++i) {
|
||||
|
||||
particletracer->linSpaceLine[i].x = (((double)rand() / RAND_MAX) *
|
||||
(particletracer->x2 -
|
||||
particletracer->x1)) +
|
||||
particletracer->x1;
|
||||
particletracer->linSpaceLine[i].y = (((double)rand() / RAND_MAX) *
|
||||
(particletracer->y2 -
|
||||
particletracer->y1)) +
|
||||
particletracer->y1;
|
||||
particletracer->linSpaceLine[i].flag = true;
|
||||
}
|
||||
}
|
@@ -52,7 +52,7 @@ typedef struct {
|
||||
} ParticleTracer;
|
||||
|
||||
extern void initParticleTracer(ParticleTracer*, Discretization*, Parameter*);
|
||||
extern void injectParticles(ParticleTracer*);
|
||||
extern void injectParticles(ParticleTracer*, double*);
|
||||
extern void advanceParticles(ParticleTracer*, double*, double*, double*, Comm*, double);
|
||||
extern void freeParticles(ParticleTracer*);
|
||||
extern void writeParticles(ParticleTracer*, Comm*);
|
||||
@@ -60,5 +60,6 @@ extern void printParticleTracerParameters(ParticleTracer*);
|
||||
extern void printParticles(ParticleTracer*);
|
||||
extern void trace(ParticleTracer*, Discretization*, double);
|
||||
extern void compress(ParticleTracer*);
|
||||
extern void particleRandomizer(ParticleTracer*);
|
||||
|
||||
#endif
|
@@ -6,8 +6,8 @@
|
||||
*/
|
||||
#include <math.h>
|
||||
#include <mpi.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "progress.h"
|
||||
|
||||
@@ -49,3 +49,22 @@ void stopProgress()
|
||||
printf("\n");
|
||||
fflush(stdout);
|
||||
}
|
||||
|
||||
FILE* initResidualWriter()
|
||||
{
|
||||
FILE* fp;
|
||||
fp = fopen("residual.dat", "w");
|
||||
|
||||
if (fp == NULL) {
|
||||
printf("Error!\n");
|
||||
exit(-1);
|
||||
}
|
||||
|
||||
return fp;
|
||||
|
||||
}
|
||||
|
||||
void writeResidual(FILE* fp, double ts, double res)
|
||||
{
|
||||
fprintf(fp, "%f, %f\n", ts, res);
|
||||
}
|
@@ -4,11 +4,14 @@
|
||||
* Use of this source code is governed by a MIT-style
|
||||
* license that can be found in the LICENSE file.
|
||||
*/
|
||||
#include <stdio.h>
|
||||
|
||||
#ifndef __PROGRESS_H_
|
||||
#define __PROGRESS_H_
|
||||
|
||||
extern void initProgress(double);
|
||||
extern void printProgress(double);
|
||||
extern void stopProgress();
|
||||
|
||||
extern FILE* initResidualWriter(void);
|
||||
extern void writeResidual(FILE*, double, double);
|
||||
#endif
|
||||
|
@@ -312,7 +312,7 @@ void initSolver(Solver* s, Discretization* d, Parameter* p)
|
||||
}
|
||||
}
|
||||
|
||||
void solve(Solver* s, double* p, double* rhs)
|
||||
double solve(Solver* s, double* p, double* rhs)
|
||||
{
|
||||
double res = multiGrid(s, p, rhs, 0, s->comm);
|
||||
|
||||
@@ -321,4 +321,5 @@ void solve(Solver* s, double* p, double* rhs)
|
||||
printf("Residuum: %.6f\n", res);
|
||||
}
|
||||
#endif
|
||||
return res;
|
||||
}
|
||||
|
@@ -48,7 +48,7 @@ void initSolver(Solver* s, Discretization* d, Parameter* p)
|
||||
s->comm = &d->comm;
|
||||
}
|
||||
|
||||
void solve(Solver* s, double* p, double* rhs)
|
||||
double solve(Solver* s, double* p, double* rhs)
|
||||
{
|
||||
int imax = s->grid->imax;
|
||||
int jmax = s->grid->jmax;
|
||||
@@ -126,4 +126,6 @@ void solve(Solver* s, double* p, double* rhs)
|
||||
printf("Solver took %d iterations to reach %f\n", it, sqrt(res));
|
||||
}
|
||||
#endif
|
||||
|
||||
return res;
|
||||
}
|
||||
|
@@ -24,7 +24,7 @@ typedef struct {
|
||||
Comm* comm;
|
||||
} Solver;
|
||||
|
||||
void initSolver(Solver*, Discretization*, Parameter*);
|
||||
void solve(Solver*, double*, double*);
|
||||
void printSolver(Solver* , double*, char*);
|
||||
extern void initSolver(Solver*, Discretization*, Parameter*);
|
||||
extern double solve(Solver*, double*, double*);
|
||||
extern void printSolver(Solver* , double*, char*);
|
||||
#endif
|
||||
|
@@ -8,7 +8,7 @@ set size ratio -1
|
||||
set object 1 rect from 0.0,0.0 to 1.0,0.5 lw 5
|
||||
|
||||
|
||||
do for [ts=0:300] {
|
||||
do for [ts=0:550] {
|
||||
plot "particles_".ts.".dat" with points pointtype 7
|
||||
}
|
||||
unset output
|
||||
|
Reference in New Issue
Block a user