Changeset 23518


Ignore:
Timestamp:
12/07/18 15:30:01 (6 years ago)
Author:
Mathieu Morlighem
Message:

NEW: added communications to vertices

Location:
issm/trunk-jpl/src/c
Files:
4 edited

Legend:

Unmodified
Added
Removed
  • issm/trunk-jpl/src/c/classes/Inputs/DatasetInput.cpp

    r22266 r23518  
    7373        MARSHALLING(enum_type);
    7474        MARSHALLING(numids);
    75         MARSHALLING_DYNAMIC(ids,int,numids)
     75        MARSHALLING_DYNAMIC(ids,int,numids);
    7676        if (marshall_direction == MARSHALLING_BACKWARD) inputs = new Inputs();
    7777        inputs->Marshall(pmarshalled_data,pmarshalled_data_size,marshall_direction);
  • issm/trunk-jpl/src/c/classes/Vertices.cpp

    r23506 r23518  
    2525/*Object constructors and destructor*/
    2626Vertices::Vertices(){/*{{{*/
    27         enum_type=VerticesEnum;
     27        this->enum_type       = VerticesEnum;
     28        this->common_recv     = NULL;
     29        this->common_recv_ids = NULL;
     30        this->common_send     = NULL;
     31        this->common_send_ids = NULL;
    2832        return;
    2933}
    3034/*}}}*/
    3135Vertices::~Vertices(){/*{{{*/
     36
     37        int num_proc=IssmComm::GetSize();
     38
     39        if(common_recv); xDelete<int>(common_recv);
     40        if(common_send); xDelete<int>(common_send);
     41        if(common_recv_ids){
     42                for(int i=0;i<num_proc;i++) if(common_recv_ids[i]) xDelete<int>(common_recv_ids[i]);
     43                xDelete<int*>(common_recv_ids);
     44        }
     45        if(common_send_ids){
     46                for(int i=0;i<num_proc;i++) if(common_send_ids[i]) xDelete<int>(common_send_ids[i]);
     47                xDelete<int*>(common_send_ids);
     48        }
    3249        return;
    3350}
     
    3552
    3653/*Numerics management*/
     54void Vertices::Marshall(char** pmarshalled_data,int* pmarshalled_data_size, int marshall_direction){ /*{{{*/
     55
     56        int num_procs=IssmComm::GetSize();
     57        int test = num_procs;
     58        MARSHALLING_ENUM(VerticesEnum);
     59        MARSHALLING(test);
     60        if(test!=num_procs) _error_("number of cores is not the same as before");
     61        MARSHALLING_DYNAMIC(this->common_recv,int,num_procs);
     62        MARSHALLING_DYNAMIC(this->common_send,int,num_procs);
     63        if(marshall_direction == MARSHALLING_BACKWARD){
     64                this->common_recv_ids = xNew<int*>(num_procs);
     65                this->common_send_ids = xNew<int*>(num_procs);
     66        }
     67        for(int i=0;i<num_procs;i++){
     68                MARSHALLING_DYNAMIC(this->common_recv_ids[i],int,this->common_recv[i]);
     69                MARSHALLING_DYNAMIC(this->common_send_ids[i],int,this->common_send[i]);
     70        }
     71        DataSet::Marshall(pmarshalled_data,pmarshalled_data_size,marshall_direction);
     72}
     73/*}}}*/
    3774void  Vertices::DistributePids(int numberofobjects){/*{{{*/
    3875
  • issm/trunk-jpl/src/c/classes/Vertices.h

    r23502 r23518  
    1515
    1616        public:
     17                int*  common_recv;
     18                int** common_recv_ids;
     19                int*  common_send;
     20                int** common_send_ids;
    1721
    1822                /*constructors, destructors:*/
    1923                Vertices();
    2024                ~Vertices();
     25
     26                /*Objects virtual functions*/
     27                void Marshall(char** pmarshalled_data,int* pmarshalled_data_size, int marshall_direction);
    2128
    2229                /*numerics:*/
  • issm/trunk-jpl/src/c/modules/ModelProcessorx/CreateElementsVerticesAndMaterials.cpp

    r23516 r23518  
    244244        iomodel->FindConstant(&isoceancoupling,"md.transient.isoceancoupling");
    245245
    246         /*Fetch data:*/
     246        /*Fetch data that will be used by the Vertex Constructor*/
    247247        iomodel->FetchData(6,"md.mesh.x","md.mesh.y","md.mesh.z","md.geometry.base","md.geometry.thickness","md.mask.ice_levelset");
    248248        if (iomodel->domaintype == Domain3DsurfaceEnum) iomodel->FetchData(3,"md.mesh.lat","md.mesh.long","md.mesh.r");
    249249        else iomodel->FetchDataToInput(elements,"md.mesh.scale_factor",MeshScaleFactorEnum,1.);
    250250        if (isoceancoupling) iomodel->FetchData(2,"md.mesh.lat","md.mesh.long");
    251 
    252251        if (solution_type!=LoveSolutionEnum) CreateNumberNodeToElementConnectivity(iomodel);
    253252
    254         int lid = 0;
     253        const int MAXCONNECTIVITY = 5;
     254        int*      epart = iomodel->epart;
     255
     256        /*Determine element width*/
     257        int  elements_width;
     258        switch(iomodel->meshelementtype){
     259                case TriaEnum:  elements_width=3; break;
     260                case TetraEnum: elements_width=4; break;
     261                case PentaEnum: elements_width=6; break;
     262                default: _error_("mesh elements "<< EnumToStringx(iomodel->meshelementtype) <<" not supported yet");
     263        }
     264
     265        /*Get my_rank:*/
     266        int my_rank   = IssmComm::GetRank();
     267        int num_procs = IssmComm::GetSize();
     268
     269        /*create matrix that keeps track of all ranks that have vertex i, and initialize as -1 (Common to all CPUs)*/
     270        int* vertices_ranks = xNew<int>(MAXCONNECTIVITY*iomodel->numberofvertices);
     271        for(int i=0;i<MAXCONNECTIVITY*iomodel->numberofvertices;i++) vertices_ranks[i] = -1;
     272
     273        /*For all vertices, cound how many cpus hold vertex i (initialize with 0)*/
     274        int* vertices_proc_count = xNewZeroInit<int>(iomodel->numberofvertices);
     275
     276        /*Create vector of size total nbv, initialized with -1, that will keep track of local ids*/
     277        int* vertices_lids  = xNew<int>(iomodel->numberofvertices);
     278        for(int i=0;i<iomodel->numberofvertices;i++) vertices_lids[i] = -1;
     279
     280        /*Go through all elements and mark all vertices for all partitions*/
     281        int  lid = 0;
     282        for(int i=0;i<iomodel->numberofelements;i++){
     283                for(int j=0;j<elements_width;j++){
     284
     285                        /*Get current vertex sid*/
     286                        int vid = iomodel->elements[elements_width*i+j]-1;
     287
     288                        /*See if it has already been marked*/
     289                        bool found = false;
     290                        for(int k=0;k<vertices_proc_count[vid];k++){
     291                                if(vertices_ranks[MAXCONNECTIVITY*vid+k] == epart[i]){
     292                                        found = true;
     293                                        break;
     294                                }
     295                        }
     296
     297                        /*On go below if this vertex has not been seen yet in this partition*/
     298                        if(!found){
     299                                /*This rank has not been marked for this vertex just yet so go ahead and mark it*/
     300                                vertices_ranks[MAXCONNECTIVITY*vid+vertices_proc_count[vid]] = epart[i];
     301                                vertices_proc_count[vid]++;
     302
     303                                /*Keep track of local ids!*/
     304                                if(epart[i]==my_rank){
     305                                        vertices_lids[vid] = lid;
     306                                        lid++;
     307                                }
     308
     309                                /*Make sure we don't go too far in the table*/
     310                                if(vertices_proc_count[vid]>MAXCONNECTIVITY) _error_("need to increase MAXCONNECTIVITY (this is hard coded, contact ISSM developer)");
     311                        }
     312                }
     313        }
     314
     315        /*Now, Count how many clones we have with other partitions*/
     316        int*  common_send = xNew<int>(num_procs);
     317        int*  common_recv = xNew<int>(num_procs);
     318        int** common_send_ids = xNew<int*>(num_procs);
     319        int** common_recv_ids = xNew<int*>(num_procs);
     320
     321        /*First step: allocate, Step 2: populate*/
     322        for(int step=0;step<2;step++){
     323
     324                if(step==1){
     325                        /*Allocate send and receive arrays of ids now*/
     326                        for(int i=0;i<num_procs;i++){
     327                                _assert_(common_send[i]>=0 && common_recv[i]>=0);
     328                                common_send_ids[i] = xNew<int>(common_send[i]);
     329                                common_recv_ids[i] = xNew<int>(common_recv[i]);
     330                        }
     331                }
     332
     333                /*Re/Initialize counters to 0*/
     334                for(int i=0;i<num_procs;i++){
     335                        common_recv[i]=0;
     336                        common_send[i]=0;
     337                }
     338
     339                /*Go through table and find clones/masters etc*/
     340                for(int i=0;i<iomodel->numberofvertices;i++){
     341
     342                        /*If we did not find this vertex in our current partition, go to next vertex*/
     343                        if(vertices_lids[i] == -1) continue;
     344
     345                        /*Find in what column this rank belongs*/
     346                        int col = -1;
     347                        for(int j=0;j<MAXCONNECTIVITY;j++){
     348                                if(vertices_ranks[MAXCONNECTIVITY*i+j] == my_rank){
     349                                        col = j;
     350                                        break;
     351                                }
     352                        }
     353                        _assert_(col!=-1);
     354
     355                        /*If col==0, it is either not on boundary, or a master*/
     356                        if(col==0){
     357                                /*1. is this vertex on the boundary? Skip if not*/
     358                                if(vertices_ranks[MAXCONNECTIVITY*i+col+1]==-1){
     359                                        continue;
     360                                }
     361                                else{
     362                                        for(int j=1;j<vertices_proc_count[i];j++){
     363                                                _assert_(vertices_ranks[MAXCONNECTIVITY*i+j]>=0);
     364                                                int rank = vertices_ranks[MAXCONNECTIVITY*i+j];
     365                                                if(step==1){
     366                                                        common_send_ids[rank][common_send[rank]] = vertices_lids[i];
     367                                                }
     368                                                common_send[rank]++;
     369                                        }
     370                                }
     371                        }
     372                        else{
     373                                /*3. It is a slave, record that we need to receive for this cpu*/
     374                                int rank = vertices_ranks[MAXCONNECTIVITY*i+0];
     375                                if(step==1){
     376                                        common_recv_ids[rank][common_recv[rank]] = vertices_lids[i];
     377                                }
     378                                common_recv[rank]++;
     379                        }
     380                }
     381        }
     382        xDelete<int>(vertices_proc_count);
     383        xDelete<int>(vertices_ranks);
     384
    255385        for(int i=0;i<iomodel->numberofvertices;i++){
    256                 if(iomodel->my_vertices[i]) vertices->AddObject(new Vertex(i+1,i,lid++,i,iomodel));
    257         }
     386                if(vertices_lids[i]!=-1) vertices->AddObject(new Vertex(i+1,i,vertices_lids[i],i,iomodel));
     387        }
     388        xDelete<int>(vertices_lids);
    258389
    259390        /*Free data: */
     
    261392        if (iomodel->domaintype == Domain3DsurfaceEnum) iomodel->DeleteData(3,"md.mesh.lat","md.mesh.long","md.mesh.r");
    262393        if (isoceancoupling) iomodel->DeleteData(2,"md.mesh.lat","md.mesh.long");
     394
     395        vertices->common_send=common_send;
     396        vertices->common_recv=common_recv;
     397        vertices->common_send_ids=common_send_ids;
     398        vertices->common_recv_ids=common_recv_ids;
    263399}/*}}}*/
    264400
Note: See TracChangeset for help on using the changeset viewer.