void output_dump( const struct Field fldi, const double t) { FILE *ht; int dump_version,i; int size_x, size_y, size_z; int marker, included_field; int nfield; long int filesize; ht=NULL; DEBUG_START_FUNC; size_x = NX; size_y = NY; size_z = NZ; // This is a check when we try to read a dump file dump_version = OUTPUT_DUMP_VERSION; // This is a hard coded marker to check that we have correctly read the file marker = DUMP_MARKER; if(rank==0) { ht=fopen(OUTPUT_DUMP_WRITE,"w"); if(ht==NULL) ERROR_HANDLER( ERROR_CRITICAL, "Error opening dump file."); fwrite(&dump_version, sizeof(int), 1, ht); fwrite(&size_x , sizeof(int), 1, ht); fwrite(&size_y , sizeof(int), 1, ht); fwrite(&size_z , sizeof(int), 1, ht); // Included fields // First bit is Boussinesq fields // Second bit is MHD fields // Other fields can be added from that stage... included_field=0; #ifdef BOUSSINESQ included_field+=1; #endif #ifdef MHD included_field+=2; #endif fwrite(&included_field, sizeof(int), 1, ht); } write_field(ht, fldi.vx); write_field(ht, fldi.vy); write_field(ht, fldi.vz); #ifdef BOUSSINESQ write_field(ht, fldi.th); #endif #ifdef MHD write_field(ht, fldi.bx); write_field(ht, fldi.by); write_field(ht, fldi.bz); #endif if(rank==0) { fwrite(&t , sizeof(double) , 1 , ht); fwrite(&noutput_flow , sizeof(int) , 1 , ht); fwrite(&lastoutput_time , sizeof(double) , 1 , ht); fwrite(&lastoutput_flow , sizeof(double) , 1 , ht); fwrite(&lastoutput_dump , sizeof(double) , 1 , ht); // Any extra information should be put here. if(param.numericalkevol){//AJB 09/03/12 for(i=0;i<9;i++){ fwrite(&kbasis[i],sizeof(double),1,ht); } } fwrite(&marker , sizeof(int) , 1 , ht); // Check everything was fine with the file if(ferror(ht)) ERROR_HANDLER( ERROR_CRITICAL, "Error writing dump file"); fclose(ht); } // predict the file size: nfield = 3; // Velocity fields #ifdef BOUSSINESQ nfield += 1; #endif #ifdef MHD nfield += 3; #endif filesize = nfield * sizeof(double complex) * NTOTAL_COMPLEX * NPROC + 4 * sizeof( double) + 7 * sizeof( int ); if(param.numericalkevol) {//AJB 09/03/12 filesize = nfield * sizeof(double complex) * NTOTAL_COMPLEX * NPROC + 13 * sizeof( double) + 7 * sizeof( int ); } if( check_file_size( OUTPUT_DUMP_WRITE, filesize ) ) { MPI_Printf("Error checking the dump size, got %d instead of %d\n", (int) check_file_size( OUTPUT_DUMP_WRITE, filesize), (int) filesize); ERROR_HANDLER( ERROR_CRITICAL, "Error writing dump file, check your quotas"); } // This bit prevents the code from losing all the dump files (this kind of thing happens sometimes...) // With this routine, one will always have a valid restart dump, either in OUTPUT_DUMP_WRITE, OUTPUT_DUMP or OUTPUT_DUMP_SAV // (it should normally be in OUTPUT_DUMP) if(rank==0) { remove(OUTPUT_DUMP_SAV); // Delete the previously saved output dump rename(OUTPUT_DUMP, OUTPUT_DUMP_SAV); // Save the current dump file rename(OUTPUT_DUMP_WRITE, OUTPUT_DUMP); // Move the new dump file to its final location } if( check_file_size( OUTPUT_DUMP, filesize ) ) { MPI_Printf("Error checking the dump size, got %d instead of %d\n", (int) check_file_size( OUTPUT_DUMP, filesize), (int) filesize); ERROR_HANDLER( ERROR_CRITICAL, "Error writing dump file, check your quotas"); } #ifdef MPI_SUPPORT MPI_Barrier(MPI_COMM_WORLD); #endif DEBUG_END_FUNC; return; }
void read_dump( struct Field fldo, double *t, char dump_file[]) { FILE *ht; int dump_version,i; int size_x, size_y, size_z, included_field; int marker; DEBUG_START_FUNC; if( !file_exist(dump_file) ) { // The file cannot be opened MPI_Printf("File %s not found\n",dump_file); ERROR_HANDLER(ERROR_CRITICAL, "Cannot open dump file."); } ht=fopen(dump_file,"r"); // The file has been opened by process 0 if(rank==0) { fread(&dump_version, sizeof(int), 1, ht); if( dump_version != OUTPUT_DUMP_VERSION) ERROR_HANDLER( ERROR_CRITICAL, "Incorrect dump file version."); fread(&size_x , sizeof(int), 1, ht); fread(&size_y , sizeof(int), 1, ht); fread(&size_z , sizeof(int), 1, ht); if(size_x != NX) ERROR_HANDLER( ERROR_CRITICAL, "Incorrect X grid size in dump file."); if(size_y != NY) ERROR_HANDLER( ERROR_CRITICAL, "Incorrect Y grid size in dump file."); if(size_z != NZ) ERROR_HANDLER( ERROR_CRITICAL, "Incorrect Y grid size in dump file."); fread(&included_field, sizeof(int), 1, ht); } #ifdef MPI_SUPPORT MPI_Bcast( &included_field, 1, MPI_INT, 0, MPI_COMM_WORLD); #endif MPI_Printf("Reading velocity field\n"); read_field(ht, fldo.vx); read_field(ht, fldo.vy); read_field(ht, fldo.vz); #ifdef BOUSSINESQ // Do we have Boussinesq Field in the dump? if(included_field & 1) { // Yes MPI_Printf("Reading Boussinesq field\n"); read_field(ht, fldo.th); } else { // No ERROR_HANDLER( ERROR_WARNING, "No Boussinesq field in the dump, using initial conditions."); } #endif #ifdef MHD // Do we have MHD field in the dump? if(included_field & 2) { // Yes MPI_Printf("Reading MHD field\n"); read_field(ht, fldo.bx); read_field(ht, fldo.by); read_field(ht, fldo.bz); } else { //No ERROR_HANDLER( ERROR_WARNING, "No MHD field in the dump, using initial conditions."); } #endif if(param.restart) { // If the dump is used to restart, we need these extra variables if(rank==0) { fread(t , sizeof(double) , 1 , ht); fread(&noutput_flow , sizeof(int) , 1 , ht); fread(&lastoutput_time , sizeof(double) , 1 , ht); fread(&lastoutput_flow , sizeof(double) , 1 , ht); fread(&lastoutput_dump , sizeof(double) , 1 , ht); if(param.numericalkevol){//AJB 09/03/12 for(i=0;i<9;i++){ fread(&kbasis[i],sizeof(double),1,ht); } } fread(&marker , sizeof(int) , 1, ht); if(marker != DUMP_MARKER) ERROR_HANDLER( ERROR_CRITICAL, "Incorrect marker. Probably an incorrect dump file!"); } // Transmit the values to all processes #ifdef MPI_SUPPORT MPI_Bcast( t, 1, MPI_DOUBLE, 0, MPI_COMM_WORLD); MPI_Bcast( &noutput_flow, 1, MPI_INT, 0, MPI_COMM_WORLD); MPI_Bcast( &lastoutput_time, 1, MPI_DOUBLE, 0, MPI_COMM_WORLD); MPI_Bcast( &lastoutput_flow, 1, MPI_DOUBLE, 0, MPI_COMM_WORLD); MPI_Bcast( &lastoutput_dump, 1, MPI_DOUBLE, 0, MPI_COMM_WORLD); if(param.numericalkevol){//AJB 09/03/12 MPI_Bcast( kbasis, 9 , MPI_DOUBLE, 0, MPI_COMM_WORLD); } #endif MPI_Printf("Restarting at t=%e...\n",*t); } if(rank==0) { if(ferror(ht)) ERROR_HANDLER( ERROR_CRITICAL, "Error reading dump file"); fclose(ht); } DEBUG_END_FUNC; return; }
/** Init the flow arrays... */ void init_flow(struct Field fldi) { int i,n; int j,k; double dummy_var; DEBUG_START_FUNC; // Initialise vectors to 0 for( n = 0 ; n < fldi.nfield ; n++) { for( i = 0 ; i < NTOTAL_COMPLEX ; i++) { fldi.farray[n][i] = 0.0; } } #ifdef COMPRESSIBLE // Initialise the density to 1... if(rank==0) { fldi.d[0] = (double) NTOTAL; } #endif if(param.init_large_scale_noise) init_LargeScaleNoise(fldi); if(param.init_large_scale_2D_noise) init_LargeScale2DNoise(fldi); if(param.init_vortex) init_KidaVortex(fldi); if(param.init_spatial_structure) init_SpatialStructure(fldi); if(param.init_white_noise) init_WhiteNoise(fldi); if(param.init_bench) init_Bench(fldi); if(param.init_mean_field) init_MeanField(fldi); if(param.init_dump) { read_dump(fldi, &dummy_var,"init.dmp"); MPI_Printf("Initial conditions read successfully from the restart dump\n"); } #ifdef BOUNDARY_C boundary_c(fldi); #endif projector(fldi.vx,fldi.vy,fldi.vz); #ifdef MHD projector(fldi.bx,fldi.by,fldi.bz); #endif #ifdef WITH_PARTICLES #ifdef WITH_ROTATION if(rank==0) { kappa_tau2 = 2.0*param.omega*(2.0*param.omega-param.shear) * param.particles_stime * param.particles_stime + (param.particles_dg_ratio + 1.0) * (param.particles_dg_ratio + 1.0); // This is a non trivial equilibrium for the particles+gas system fldi.vx[0] = param.particles_epsilon*param.particles_stime*param.particles_dg_ratio / kappa_tau2 * ( (double) NTOTAL); fldi.vy[0] = param.particles_epsilon*param.particles_dg_ratio*(1.0+param.particles_dg_ratio)/(2.0*param.omega*kappa_tau2) * ( (double) NTOTAL); } #endif #endif #ifdef DEBUG MPI_Printf("Initflow:\n"); D_show_all(fldi); MPI_Printf("**************************************************************************************\n"); #endif DEBUG_END_FUNC; return; }