int main(int argc, char *argv[]) { int i, j, k;//-- counters HashTable* BT_Node_Ptr; HashTable* BT_Elem_Ptr; //-- MPI int myid, numprocs; MPI_Init(&argc,&argv); MPI_Comm_size(MPI_COMM_WORLD, &numprocs); MPI_Comm_rank(MPI_COMM_WORLD, &myid); #ifdef DEBUG if (myid==0){ int w; printf("type in a number: \n"); (void) scanf ("%d", &w); } // MPI_Barrier(MPI_COMM_WORLD); #endif /* create new MPI datastructures for class objects */ MPI_New_Datatype(); /* read original data from serial preprocessing code and then initialize element stiffness routines info */ double epsilon = 1., intfrictang = 1, bedfrictang = 1, gamma = 1; double frict_tiny = 0.1, mu = .0001, rho = 2200, porosity = 1; MatProps matprops(intfrictang, bedfrictang, porosity, mu, rho, epsilon, gamma, frict_tiny, (double) 1, (double) 1, (double) 1); int max_time_steps = 3000, numoutput = 1, adaptflag; double end_time = 10000.0; /* * viz_flag is used to determine which viz output to use * viz_flag%2 == 0 means output tecplotxxxx.plt * viz_flag%3 == 0 means output mshplotxxxx.plt * viz_flag%5 == 0 means output pady's stuff (viz_filenames.out and viz_outputxxx.plt) * viz_flag%7 == 0 means output hdf stuff (not implemented yet) */ int viz_flag = 0; int order_flag = 0; //order flag for time stepping scheme -- not used as of 6/19/03 Read_data(&BT_Node_Ptr, myid, &BT_Elem_Ptr, &matprops, &max_time_steps, &end_time, &numoutput, &adaptflag, &viz_flag, &order_flag); printf("bed friction angle is %e and internal friction angle is %e, epsilon is %e\n", (double) (matprops.bedfrict*180./PI), (double) (matprops.intfrict*180./PI), (double) (matprops.epsilon)); printf("METHOD ORDER %d \n",ORDER); double dummyt=-100.; double maxFluxIntegral=0; //overall maximum of the integral of the //flux on the element boundary int h_c=0; // H_adapt(BT_Elem_Ptr, BT_Node_Ptr, h_c, dummyt, &matprops); //H_adapt(BT_Elem_Ptr, BT_Node_Ptr, h_c, dummyt, &matprops); if(viz_flag%3==0) meshplotter(BT_Elem_Ptr, BT_Node_Ptr, 0,&matprops); /* cccccccccccccccccccccccccccccccccccccccccccccccccccccccccc cccccccccccccccccccccccccccccccccccccccccccccccccccccccccc Time Stepping Loop cccccccccccccccccccccccccccccccccccccccccccccccccccccccccc cccccccccccccccccccccccccccccccccccccccccccccccccccccccccc */ int time_step = 0; double time = 0; while(time_step <= max_time_steps && time < end_time) { //if(myid ==0) // printf("doing time_step = %d and time is %e\n",time_step, // time*sqrt(matprops.LENGTH_SCALE/matprops.GRAVITY_SCALE)); /* * mesh adaption routines */ double TARGET = 0.005; double UNREFINE_TARGET=GEOFLOW_TINY; int h_count = 0; if (time_step < 0) matprops.frict_tiny=0.1; else if (time_step >= 0) matprops.frict_tiny=0.000001; if(adaptflag != 0) { if(time_step%4 == 0 ) { H_adapt(BT_Elem_Ptr, BT_Node_Ptr, h_count, TARGET, &matprops, &maxFluxIntegral); } else if(time_step%4 == 2 ) { unrefine(BT_Elem_Ptr, BT_Node_Ptr, UNREFINE_TARGET, myid, numprocs, time_step, &matprops); } //P_adapt(BT_Elem_Ptr, BT_Node_Ptr, TARGET); //CN if(viz_flag%3==0) //CN meshplotter(BT_Elem_Ptr, BT_Node_Ptr, time_step+1,&matprops); /* * mesh repartitioning routines */ if(time_step % 10 == 1 && numprocs > 1) { delete_ghost_elms(BT_Elem_Ptr, myid); repartition(BT_Elem_Ptr, BT_Node_Ptr, time_step); // move_data(numprocs, myid, BT_Elem_Ptr, BT_Node_Ptr); } } step(BT_Elem_Ptr, BT_Node_Ptr, myid, numprocs, end_time, &time, &matprops, time_step, &maxFluxIntegral,numoutput); // printf(" maxFluxIntegral %e in hpfem.C \n ",maxFluxIntegral); // exit(0); calc_volume(BT_Elem_Ptr, BT_Node_Ptr, myid, numprocs, &matprops); /* * output results to file */ if(time_step % numoutput == 0) { move_data(numprocs, myid, BT_Elem_Ptr, BT_Node_Ptr); if(viz_flag%3==0) meshplotter(BT_Elem_Ptr, BT_Node_Ptr, time_step+1,&matprops); } time_step++; } move_data(numprocs, myid, BT_Elem_Ptr, BT_Node_Ptr); if(viz_flag%3==0) meshplotter(BT_Elem_Ptr, BT_Node_Ptr, time_step+1,&matprops); printf("%d Finished -- Final simulation time %e\n",myid,time); MPI_Finalize(); return(0); }
int main(int argc, char *argv[]) { int i;//-- counters HashTable* BT_Node_Ptr; HashTable* BT_Elem_Ptr; //-- MPI int myid, master, numprocs; int namelen; char processor_name[MPI_MAX_PROCESSOR_NAME]; MPI_Status status; MPI_Init(&argc,&argv); //PetscInitializeNoArguments(); PetscInitialize(&argc,&argv,PETSC_NULL,PETSC_NULL); MPI_Comm_size(MPI_COMM_WORLD, &numprocs); MPI_Comm_rank(MPI_COMM_WORLD, &myid); MPI_Get_processor_name(processor_name, &namelen); char debugfilename[256]; sprintf(debugfilename,"hpfem%04d.debug",myid); double start, end; start = MPI_Wtime(); /* create new MPI datastructures for class objects */ MPI_New_Datatype(); char filename[50]; sprintf(filename,"debug.main.%04d",myid); /* read original data from serial preprocessing code and then initialize element stiffness routines info */ int material_count=0, output_flag; double epsilon = 1., intfrictang = 1, *bedfrictang = NULL, gamma = 1; double frict_tiny = 0.1, mu = 1.0e-03, rho = 1600, rhof = 1000, porosity = 1; char **matnames=NULL; int xdmerr; StatProps statprops; MatProps matprops(material_count, matnames, intfrictang, bedfrictang, porosity, mu, rho, rhof, epsilon, gamma, frict_tiny, 1.0, 1.0, 1.0); TimeProps timeprops; timeprops.starttime=time(NULL); MapNames mapnames; PileProps pileprops; FluxProps fluxprops; OutLine outline; DISCHARGE discharge; int adaptflag; double end_time = 10000.0; /* * viz_flag is used to determine which viz output to use * nonzero 1st bit of viz_flag means output tecplotxxxx.plt * nonzero 2nd bit of viz_flag means output mshplotxxxx.plt * nonzero 4th bit of viz_flag means output xdmfxxxxx.xmf * nonzero 5th bit of viz_flag means output grass_sites files order_flag == 1 means use first order method order_flag == 2 means use second order method */ int viz_flag = 0, order_flag, savefileflag=1; //savefileflag will be flipped so first savefile will end in 0 int Init_Node_Num, Init_Elem_Num, srctype; double v_star; // v/v_slump double nz_star; /* temporary... used for negligible velocity as stopping criteria paper... plan to include in v_star implicitly later */ Read_data(myid, &matprops, &pileprops, &statprops, &timeprops, &fluxprops, &adaptflag, &viz_flag, &order_flag, &mapnames, &discharge, &outline, &srctype ); if(!loadrun(myid, numprocs, &BT_Node_Ptr, &BT_Elem_Ptr, &matprops, &timeprops, &mapnames, &adaptflag, &order_flag, &statprops, &discharge, &outline)) { Read_grid(myid, numprocs, &BT_Node_Ptr, &BT_Elem_Ptr, &matprops, &outline); setup_geoflow(BT_Elem_Ptr, BT_Node_Ptr, myid, numprocs, &matprops,&timeprops); move_data(numprocs, myid, BT_Elem_Ptr, BT_Node_Ptr,&timeprops); AssertMeshErrorFree(BT_Elem_Ptr,BT_Node_Ptr,numprocs,myid,-1.0); //initialize pile height and if appropriate perform initial adaptation init_piles(BT_Elem_Ptr, BT_Node_Ptr, myid, numprocs, adaptflag, &matprops, &timeprops, &mapnames, &pileprops, &fluxprops, &statprops); } if (myid==0) { for(int imat=1; imat<=matprops.material_count; imat++) printf("bed friction angle for \"%s\" is %g\n",matprops.matnames[imat], matprops.bedfrict[imat]*180.0/PI); printf("internal friction angle is %g, epsilon is %g \n method order = %i\n", matprops.intfrict*180.0/PI, matprops.epsilon, order_flag ); printf("REFINE_LEVEL=%d\n",REFINE_LEVEL); } //printdate(BT_Elem_Ptr, BT_Node_Ptr,&matprops, &fluxprops,&timeprops); MPI_Barrier(MPI_COMM_WORLD); calc_stats(BT_Elem_Ptr, BT_Node_Ptr, myid, &matprops, &timeprops, &statprops, &discharge, 0.0); output_discharge(&matprops, &timeprops, &discharge, myid); move_data(numprocs, myid, BT_Elem_Ptr, BT_Node_Ptr,&timeprops); // int jiter; // for( jiter=0; jiter <3; jiter++){ // LaplacianData Laplacian (BT_Elem_Ptr, BT_Node_Ptr ,1 ,.001); // implicit_solver(&Laplacian); // } // HashEntryPtr *buck = BT_Elem_Ptr->getbucketptr(); // for(jiter=0; jiter<BT_Elem_Ptr->get_no_of_buckets(); jiter++){ // if(*(buck+jiter)) // { // HashEntryPtr currentPtr = *(buck+jiter); // while(currentPtr) // { // Element* Curr_El=(Element*)(currentPtr->value); // if(Curr_El->get_adapted_flag()>0)//||(timeprops_ptr->iter%5==2))) // { //if this is a refined element don't involve!!! // double phi = *(Curr_El->get_state_vars()+4); // if(phi>1) phi=1; // if(phi<0) phi=0; // Curr_El->update_phase2(phi); // Curr_El->update_phase1(phi); // } // currentPtr=currentPtr->next; // } // } // } //============================================================================================================= // int num_buck=BT_Elem_Ptr->get_no_of_buckets(); // HashEntryPtr* buck = BT_Elem_Ptr->getbucketptr(); // int num_nonzero_elem=0, *all_num_nonzero_elem; // for(i=0; i<num_buck; i++) // if(*(buck+i)){ // HashEntryPtr currentPtr = *(buck+i); // while(currentPtr){ // Element* Curr_El=(Element*)(currentPtr->value); // if((Curr_El->get_adapted_flag()>0)&& // (myid==Curr_El->get_myprocess())) // if(*(Curr_El->pass_key())==3842346279 && *(Curr_El->pass_key()+1)==2368179492) // { // int xp=Curr_El->get_positive_x_side(); // int yp=(xp+1)%4, xm=(xp+2)%4, ym=(xp+3)%4; // Node* nym = (Node*) BT_Node_Ptr->lookup(Curr_El->getNode()+(ym+4)*2); // assert(nym->flux[1]); // } // currentPtr=currentPtr->next; // } // } //===================================================================================================== if(myid==0) output_summary(&timeprops, &statprops, savefileflag); if(viz_flag&1) tecplotter(BT_Elem_Ptr, BT_Node_Ptr, &matprops, &timeprops, &mapnames, statprops.vstar ); if(viz_flag&2) meshplotter(BT_Elem_Ptr, BT_Node_Ptr, &matprops, &timeprops, &mapnames, statprops.vstar); //printdate(BT_Elem_Ptr, BT_Node_Ptr,&matprops, &fluxprops,&timeprops); #ifdef HAVE_HDF5 if(viz_flag&8) xdmerr=write_xdmf(BT_Elem_Ptr,BT_Node_Ptr,&timeprops,&matprops,&mapnames,XDMF_NEW); #endif if(viz_flag&16){ if(myid==0) grass_sites_header_output(&timeprops); grass_sites_proc_output(BT_Elem_Ptr, BT_Node_Ptr, myid, &matprops, &timeprops);} /* cccccccccccccccccccccccccccccccccccccccccccccccccccccccccc cccccccccccccccccccccccccccccccccccccccccccccccccccccccccc Time Stepping Loop cccccccccccccccccccccccccccccccccccccccccccccccccccccccccc cccccccccccccccccccccccccccccccccccccccccccccccccccccccccc */ long element_counter=0; // for performance count elements/timestep/proc int ifstop=0; double max_momentum=100; //nondimensional /* ifend(0.5*statprops.vmean) is a hack, the original intent (when we were intending to use vstar as a stopping criteria) whas to have the calculation when vstar dropped back down below 1, instead we're using the ifend() function to stop the simulation when the volume averaged velocity falls back down below 2 meters... this hack is only for the colima hazard map runs, otherwise pass ifend() a constant valued */ while(!(timeprops.ifend(0)) && !ifstop)//(timeprops.ifend(0.5*statprops.vmean)) && !ifstop) { /* * mesh adaption routines */ double TARGET = .05; //double UNREFINE_TARGET = .005; double UNREFINE_TARGET = .01; int h_count = 0; if (timeprops.iter < 50) matprops.frict_tiny=0.1; else matprops.frict_tiny=0.000000001; //check for changes in topography and update if necessary //may want to put an "if(timeprops.iter %20==0)" (20 is arbitrary) here if(timeprops.iter==200){ update_topo(BT_Elem_Ptr, BT_Node_Ptr, myid, numprocs, &matprops, &timeprops,&mapnames); } if((adaptflag!=0)&&(timeprops.iter%5==4)) { AssertMeshErrorFree(BT_Elem_Ptr,BT_Node_Ptr,numprocs,myid,-2.0); H_adapt(BT_Elem_Ptr, BT_Node_Ptr, h_count, TARGET, &matprops, &fluxprops, &timeprops, 5); move_data(numprocs, myid, BT_Elem_Ptr, BT_Node_Ptr,&timeprops); unrefine(BT_Elem_Ptr, BT_Node_Ptr, UNREFINE_TARGET, myid, numprocs, &timeprops, &matprops); MPI_Barrier(MPI_COMM_WORLD);//for debug move_data(numprocs, myid, BT_Elem_Ptr, BT_Node_Ptr,&timeprops); //this move_data() here for debug... to make AssertMeshErrorFree() Work if((numprocs>1)&&(timeprops.iter%10==9)) { repartition2(BT_Elem_Ptr, BT_Node_Ptr, &timeprops); move_data(numprocs, myid, BT_Elem_Ptr, BT_Node_Ptr,&timeprops); //this move_data() here for debug... to make AssertMeshErrorFree() Work } move_data(numprocs, myid, BT_Elem_Ptr, BT_Node_Ptr,&timeprops); } step(BT_Elem_Ptr, BT_Node_Ptr, myid, numprocs, &matprops, &timeprops, &pileprops, &fluxprops, &statprops, &order_flag, &outline, &discharge,adaptflag); /* * output results to file */ if(timeprops.ifoutput()) { // if (timeprops.iter%30==1){//(timeprops.iter<1000 && timeprops.iter%60==58) //output_flag=1; //else if ( timeprops.iter%200==198) //output_flag=1; // if(output_flag) // { move_data(numprocs, myid, BT_Elem_Ptr, BT_Node_Ptr,&timeprops); output_discharge(&matprops, &timeprops, &discharge, myid); //output_flag=0; if(myid==0){ output_summary(&timeprops, &statprops, savefileflag); } if(viz_flag&1) tecplotter(BT_Elem_Ptr, BT_Node_Ptr, &matprops, &timeprops, &mapnames,statprops.vstar); if(viz_flag&2) meshplotter(BT_Elem_Ptr, BT_Node_Ptr, &matprops, &timeprops, &mapnames,statprops.vstar); #ifdef HAVE_HDF5 if(viz_flag&8) xdmerr=write_xdmf(BT_Elem_Ptr,BT_Node_Ptr,&timeprops,&matprops,&mapnames,XDMF_OLD); #endif if(viz_flag&16){ if(myid==0) grass_sites_header_output(&timeprops); grass_sites_proc_output(BT_Elem_Ptr, BT_Node_Ptr, myid, &matprops, &timeprops); } } #ifdef PERFTEST int countedvalue=timeprops.iter%2+1; int e_buckets=BT_Elem_Ptr->get_no_of_buckets(); HashEntry* entryp; for(i=0; i<e_buckets; i++) { entryp = *(BT_Elem_Ptr->getbucketptr() + i); while(entryp) { Element * EmTemp = (Element*)entryp->value; assert(EmTemp); assert(EmTemp->get_counted()!=countedvalue); if((EmTemp->get_adapted_flag()>=NOTRECADAPTED)&& (EmTemp->get_adapted_flag()<=BUFFER) ) { //if this element doesn't belong on this processor don't involve element_counter++; EmTemp->put_counted(countedvalue); } entryp = entryp->next; } } MPI_Barrier(MPI_COMM_WORLD); #endif } MPI_Barrier(MPI_COMM_WORLD); move_data(numprocs, myid, BT_Elem_Ptr, BT_Node_Ptr,&timeprops); MPI_Barrier(MPI_COMM_WORLD); output_discharge(&matprops, &timeprops, &discharge, myid); MPI_Barrier(MPI_COMM_WORLD); if(myid==0) output_summary(&timeprops, &statprops, savefileflag); //printf("hpfem.C 1: xcen=%g\n",statprops.xcen); if(viz_flag&1) tecplotter(BT_Elem_Ptr, BT_Node_Ptr, &matprops, &timeprops, &mapnames, statprops.vstar); //printf("hpfem.C 2: xcen=%g\n",statprops.xcen); MPI_Barrier(MPI_COMM_WORLD); if(viz_flag&2) meshplotter(BT_Elem_Ptr, BT_Node_Ptr, &matprops, &timeprops, &mapnames, statprops.vstar); MPI_Barrier(MPI_COMM_WORLD); #ifdef HAVE_HDF5 if(viz_flag&8) xdmerr=write_xdmf(BT_Elem_Ptr,BT_Node_Ptr,&timeprops,&matprops,&mapnames,XDMF_CLOSE); MPI_Barrier(MPI_COMM_WORLD); #endif if(viz_flag&16){ if(myid==0) grass_sites_header_output(&timeprops); grass_sites_proc_output(BT_Elem_Ptr, BT_Node_Ptr, myid, &matprops, &timeprops);} MPI_Barrier(MPI_COMM_WORLD); // write out ending warning, maybe flow hasn't finished moving sim_end_warning(BT_Elem_Ptr, &matprops, &timeprops, statprops.vstar); MPI_Barrier(MPI_COMM_WORLD); //write out the final pile statistics (and run time) if(myid==0) out_final_stats(&timeprops, &statprops); MPI_Barrier(MPI_COMM_WORLD); //write out stochastic simulation statistics //if(statprops.lhs.runid>=0) if(myid==0) output_stoch_stats(&matprops, &statprops); MPI_Barrier(MPI_COMM_WORLD); //saverun(&BT_Node_Ptr, myid, numprocs, &BT_Elem_Ptr, &matprops, &timeprops, &mapnames, // adaptflag, order_flag, &statprops, &discharge, &outline, &savefileflag); Was not possible because the saverun function doesn't write the information for laplacian, moreover element constructor requires some modifications MPI_Barrier(MPI_COMM_WORLD); //output maximum flow depth a.k.a. flow outline OutLine outline2; double dxy[2]; dxy[0]=outline.dx; dxy[1]=outline.dy; outline2.init2(dxy,outline.xminmax,outline.yminmax); int NxNyout=outline.Nx*outline.Ny; MPI_Reduce(*(outline.pileheight),*(outline2.pileheight),NxNyout, MPI_DOUBLE,MPI_SUM,0,MPI_COMM_WORLD); if(myid==0) outline2.output(&matprops,&statprops); #ifdef PERFTEST long m = element_counter, ii; MPI_Allreduce ( &element_counter, &ii, 1, MPI_LONG, MPI_SUM, MPI_COMM_WORLD ); end=MPI_Wtime(); char perffilename[256]; sprintf(perffilename,"perform%04d.%04d",numprocs,myid); FILE *fpperf=fopen(perffilename,"w"); fprintf(fpperf,"%d Finished -- used %ld elements of %ld total in %e seconds, %e\n",myid,m,ii,end-start, ii/(end-start)); fclose(fpperf); #endif PetscFinalize(); MPI_Finalize(); return(0); }