1 #include <../src/vec/is/sf/impls/basic/gatherv/sfgatherv.h> 2 3 typedef PetscSFPack_Allgatherv PetscSFPack_Gather; 4 #define PetscSFPackGet_Gather PetscSFPackGet_Allgatherv 5 6 /* Reuse the type. The difference is some fields (i.e., displs, recvcounts) are not used in Gather, which is not a big deal */ 7 typedef PetscSF_Allgatherv PetscSF_Gather; 8 9 PETSC_INTERN PetscErrorCode PetscSFBcastAndOpBegin_Gather(PetscSF sf,MPI_Datatype unit,const void *rootdata,void *leafdata,MPI_Op op) 10 { 11 PetscErrorCode ierr; 12 PetscSFPack_Gatherv link; 13 PetscMPIInt rank,sendcount; 14 MPI_Comm comm; 15 void *recvbuf; 16 17 PetscFunctionBegin; 18 ierr = PetscSFPackGet_Gatherv(sf,unit,rootdata,leafdata,&link);CHKERRQ(ierr); 19 ierr = PetscObjectGetComm((PetscObject)sf,&comm);CHKERRQ(ierr); 20 21 if (op == MPIU_REPLACE) { 22 recvbuf = leafdata; 23 } else { 24 ierr = MPI_Comm_rank(comm,&rank);CHKERRQ(ierr); 25 if (!link->leaf && !rank) {ierr = PetscMalloc(sf->nleaves*link->unitbytes,&link->leaf);CHKERRQ(ierr);} 26 recvbuf = link->leaf; 27 } 28 29 ierr = PetscMPIIntCast(sf->nroots,&sendcount);CHKERRQ(ierr); 30 ierr = MPIU_Igather(rootdata,sendcount,unit,recvbuf,sendcount,unit,0/*rank 0*/,comm,&link->request);CHKERRQ(ierr); 31 PetscFunctionReturn(0); 32 } 33 34 static PetscErrorCode PetscSFReduceBegin_Gather(PetscSF sf,MPI_Datatype unit,const void *leafdata,void *rootdata,MPI_Op op) 35 { 36 PetscErrorCode ierr; 37 PetscSFPack_Gatherv link; 38 PetscMPIInt recvcount; 39 MPI_Comm comm; 40 void *recvbuf; 41 42 PetscFunctionBegin; 43 ierr = PetscSFPackGet_Gatherv(sf,unit,rootdata,leafdata,&link);CHKERRQ(ierr); 44 ierr = PetscObjectGetComm((PetscObject)sf,&comm);CHKERRQ(ierr); 45 46 if (op == MPIU_REPLACE) { 47 recvbuf = rootdata; 48 } else { 49 if (!link->root) {ierr = PetscMalloc(sf->nroots*link->unitbytes,&link->root);CHKERRQ(ierr);} 50 recvbuf = link->root; 51 } 52 53 ierr = PetscMPIIntCast(sf->nroots,&recvcount);CHKERRQ(ierr); 54 ierr = MPIU_Iscatter(leafdata,recvcount,unit,recvbuf,recvcount,unit,0/*rank 0*/,comm,&link->request);CHKERRQ(ierr); 55 PetscFunctionReturn(0); 56 } 57 58 PETSC_INTERN PetscErrorCode PetscSFCreate_Gather(PetscSF sf) 59 { 60 PetscErrorCode ierr; 61 PetscSF_Gather *dat = (PetscSF_Gather*)sf->data; 62 63 PetscFunctionBegin; 64 /* Inherit from Allgatherv */ 65 sf->ops->Reset = PetscSFReset_Allgatherv; 66 sf->ops->Destroy = PetscSFDestroy_Allgatherv; 67 sf->ops->GetGraph = PetscSFGetGraph_Allgatherv; 68 sf->ops->GetRootRanks = PetscSFGetRootRanks_Allgatherv; 69 sf->ops->GetLeafRanks = PetscSFGetLeafRanks_Allgatherv; 70 sf->ops->BcastAndOpEnd = PetscSFBcastAndOpEnd_Allgatherv; 71 sf->ops->ReduceEnd = PetscSFReduceEnd_Allgatherv; 72 sf->ops->FetchAndOpEnd = PetscSFFetchAndOpEnd_Allgatherv; 73 sf->ops->CreateLocalSF = PetscSFCreateLocalSF_Allgatherv; 74 75 /* Inherit from Gatherv */ 76 sf->ops->FetchAndOpBegin = PetscSFFetchAndOpBegin_Gatherv; 77 78 /* Gather stuff */ 79 sf->ops->BcastAndOpBegin = PetscSFBcastAndOpBegin_Gather; 80 sf->ops->ReduceBegin = PetscSFReduceBegin_Gather; 81 82 ierr = PetscNewLog(sf,&dat);CHKERRQ(ierr); 83 sf->data = (void*)dat; 84 PetscFunctionReturn(0); 85 } 86 87