VTK
|
00001 /*========================================================================= 00002 00003 Program: Visualization Toolkit 00004 Module: vtkPPixelTransfer.h 00005 00006 Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen 00007 All rights reserved. 00008 See Copyright.txt or http://www.kitware.com/Copyright.htm for details. 00009 00010 This software is distributed WITHOUT ANY WARRANTY; without even 00011 the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR 00012 PURPOSE. See the above copyright notice for more information. 00013 00014 =========================================================================*/ 00028 #ifndef __vtkPPixelTransfer_h 00029 #define __vtkPPixelTransfer_h 00030 00031 #include "vtkPixelTransfer.h" 00032 #include "vtkRenderingParallelLICModule.h" // for export 00033 #include "vtkSetGet.h" // for macros 00034 #include "vtkPixelExtent.h" // for pixel extent 00035 #include "vtkMPI.h" // for mpi 00036 #include "vtkMPIPixelTT.h" // for type traits 00037 #include "vtkMPIPixelView.h" // for mpi subarrays 00038 00039 // included vtkSystemIncludes.h in the base class. 00040 #include <iostream> // for ostream 00041 #include <vector> // for vector 00042 #include <cstring> // for memcpy 00043 00044 // #define vtkPPixelTransferDEBUG 00045 00046 class VTKRENDERINGPARALLELLIC_EXPORT vtkPPixelTransfer : public vtkPixelTransfer 00047 { 00048 public: 00049 vtkPPixelTransfer() 00050 : 00051 SrcRank(0), 00052 DestRank(0), 00053 UseBlockingSend(0), 00054 UseBlockingRecv(0) 00055 {} 00056 00058 00060 vtkPPixelTransfer( 00061 int srcRank, 00062 const vtkPixelExtent &srcWholeExt, 00063 const vtkPixelExtent &srcExt, 00064 int destRank, 00065 const vtkPixelExtent &destWholeExt, 00066 const vtkPixelExtent &destExt, 00067 int id=0) 00068 : 00069 Id(id), 00070 SrcRank(srcRank), 00071 SrcWholeExt(srcWholeExt), 00072 SrcExt(srcExt), 00073 DestRank(destRank), 00074 DestWholeExt(destWholeExt), 00075 DestExt(destExt), 00076 UseBlockingSend(0), 00077 UseBlockingRecv(0) 00078 {} 00080 00082 00084 vtkPPixelTransfer( 00085 int srcRank, 00086 const vtkPixelExtent &srcWholeExt, 00087 const vtkPixelExtent &targetExt, 00088 int destRank, 00089 const vtkPixelExtent &destWholeExt, 00090 int id) 00091 : 00092 Id(id), 00093 SrcRank(srcRank), 00094 SrcWholeExt(srcWholeExt), 00095 SrcExt(targetExt), 00096 DestRank(destRank), 00097 DestWholeExt(destWholeExt), 00098 DestExt(targetExt), 00099 UseBlockingSend(0), 00100 UseBlockingRecv(0) 00101 {} 00103 00105 00107 vtkPPixelTransfer( 00108 int srcRank, 00109 int destRank, 00110 const vtkPixelExtent &wholeExt, 00111 const vtkPixelExtent &targetExt, 00112 int id=0) 00113 : 00114 Id(id), 00115 SrcRank(srcRank), 00116 SrcWholeExt(wholeExt), 00117 SrcExt(targetExt), 00118 DestRank(destRank), 00119 DestWholeExt(wholeExt), 00120 DestExt(targetExt), 00121 UseBlockingSend(0), 00122 UseBlockingRecv(0) 00123 {} 00125 00127 00129 vtkPPixelTransfer( 00130 int srcRank, 00131 int destRank, 00132 const vtkPixelExtent &ext, 00133 int id=0) 00134 : 00135 Id(id), 00136 SrcRank(srcRank), 00137 SrcWholeExt(ext), 00138 SrcExt(ext), 00139 DestRank(destRank), 00140 DestWholeExt(ext), 00141 DestExt(ext), 00142 UseBlockingSend(0), 00143 UseBlockingRecv(0) 00144 {} 00146 00148 00150 vtkPPixelTransfer( 00151 int srcRank, 00152 const vtkPixelExtent &srcWholeExt, 00153 int destRank, 00154 const vtkPixelExtent &destWholeExt, 00155 int id=0) 00156 : 00157 Id(id), 00158 SrcRank(srcRank), 00159 SrcWholeExt(srcWholeExt), 00160 SrcExt(srcWholeExt), 00161 DestRank(destRank), 00162 DestWholeExt(destWholeExt), 00163 DestExt(destWholeExt), 00164 UseBlockingSend(0), 00165 UseBlockingRecv(0) 00166 {} 00168 00170 00173 vtkPPixelTransfer( 00174 const vtkPixelExtent &srcWholeExt, 00175 const vtkPixelExtent &srcExt, 00176 const vtkPixelExtent &destWholeExt, 00177 const vtkPixelExtent &destExt) 00178 : 00179 Id(0), 00180 SrcRank(0), 00181 SrcWholeExt(srcWholeExt), 00182 SrcExt(srcExt), 00183 DestRank(0), 00184 DestWholeExt(destWholeExt), 00185 DestExt(destExt), 00186 UseBlockingSend(0), 00187 UseBlockingRecv(0) 00188 {} 00190 00191 ~vtkPPixelTransfer(){} 00192 00194 00195 void SetSourceRank(int rank) 00196 { this->SrcRank=rank; } 00198 00199 int GetSourceRank() const 00200 { return this->SrcRank; } 00201 00202 void SetDestinationRank(int rank) 00203 { this->DestRank=rank; } 00204 00205 int GetDestinationRank() const 00206 { return this->DestRank; } 00207 00209 00212 bool Sender(int rank) const { return (this->SrcRank == rank); } 00213 bool Receiver(int rank) const { return (this->DestRank == rank); } 00214 bool Local(int rank) const 00215 { return (this->Sender(rank) && this->Receiver(rank)); } 00217 00219 00221 void SetSourceWholeExtent(vtkPixelExtent &srcExt) 00222 { this->SrcWholeExt=srcExt; } 00224 00225 vtkPixelExtent &GetSourceWholeExtent() 00226 { return this->SrcWholeExt; } 00227 00228 const vtkPixelExtent &GetSourceWholeExtent() const 00229 { return this->SrcWholeExt; } 00230 00232 00234 void SetSourceExtent(vtkPixelExtent &srcExt) 00235 { this->SrcExt=srcExt; } 00237 00238 vtkPixelExtent &GetSourceExtent() 00239 { return this->SrcExt; } 00240 00241 const vtkPixelExtent &GetSourceExtent() const 00242 { return this->SrcExt; } 00243 00245 00247 void SetDestinationWholeExtent(vtkPixelExtent &destExt) 00248 { this->DestWholeExt=destExt; } 00250 00251 vtkPixelExtent &GetDestinationWholeExtent() 00252 { return this->DestWholeExt; } 00253 00254 const vtkPixelExtent &GetDestinationWholeExtent() const 00255 { return this->DestWholeExt; } 00256 00258 00260 void SetDestinationExtent(vtkPixelExtent &destExt) 00261 { this->DestExt=destExt; } 00263 00264 vtkPixelExtent &GetDestinationExtent() 00265 { return this->DestExt; } 00266 00267 const vtkPixelExtent &GetDestinationExtent() const 00268 { return this->DestExt; } 00269 00271 00272 void SetTransactionId(int id) 00273 { this->Id=id; } 00275 00276 int GetTransactionId() const 00277 { return this->Id; } 00278 00280 00281 void SetUseBlockingSend(int val) 00282 { this->UseBlockingSend=val; } 00284 00285 int GetUseBlockingSend() const 00286 { return this->UseBlockingSend; } 00287 00288 void SetUseBlockingRecv(int val) 00289 { this->UseBlockingRecv=val; } 00290 00291 int GetUseBlockingRecv() const 00292 { return this->UseBlockingRecv; } 00293 00295 00296 template<typename SOURCE_TYPE, typename DEST_TYPE> 00297 int Execute( 00298 MPI_Comm comm, 00299 int rank, 00300 int nComps, 00301 SOURCE_TYPE *srcData, 00302 DEST_TYPE *destData, 00303 std::vector<MPI_Request> &reqs, 00304 std::deque<MPI_Datatype> &types, 00305 int tag); 00307 00309 00311 int Execute( 00312 MPI_Comm comm, 00313 int rank, 00314 int nComps, 00315 int srcType, 00316 void *srcData, 00317 int destType, 00318 void *destData, 00319 std::vector<MPI_Request> &reqs, 00320 std::deque<MPI_Datatype> &types, 00321 int tag); 00323 00325 00327 int Blit( 00328 int nComps, 00329 int srcType, 00330 void *srcData, 00331 int destType, 00332 void *destData); 00334 00335 private: 00336 // distpatch helper for vtk data type enum 00337 template<typename SOURCE_TYPE> 00338 int Execute( 00339 MPI_Comm comm, 00340 int rank, 00341 int nComps, 00342 SOURCE_TYPE *srcData, 00343 int destType, 00344 void *destData, 00345 std::vector<MPI_Request> &reqs, 00346 std::deque<MPI_Datatype> &types, 00347 int tag); 00348 00349 private: 00350 int Id; // transaction id 00351 int SrcRank; // rank who owns source memory 00352 vtkPixelExtent SrcWholeExt; // source extent 00353 vtkPixelExtent SrcExt; // source subset to transfer 00354 int DestRank; // rank who owns destination memory 00355 vtkPixelExtent DestWholeExt; // destination extent 00356 vtkPixelExtent DestExt; // destination subset 00357 int UseBlockingSend; // controls for non-blocking comm 00358 int UseBlockingRecv; 00359 }; 00360 00361 //----------------------------------------------------------------------------- 00362 template<typename SOURCE_TYPE> 00363 int vtkPPixelTransfer::Execute( 00364 MPI_Comm comm, 00365 int rank, 00366 int nComps, 00367 SOURCE_TYPE *srcData, 00368 int destType, 00369 void *destData, 00370 std::vector<MPI_Request> &reqs, 00371 std::deque<MPI_Datatype> &types, 00372 int tag) 00373 { 00374 // second layer of dispatch 00375 switch(destType) 00376 { 00377 vtkTemplateMacro( 00378 return this->Execute( 00379 comm, 00380 rank, 00381 nComps, 00382 srcData, 00383 (VTK_TT*)destData, 00384 reqs, 00385 types, 00386 tag)); 00387 } 00388 return 0; 00389 } 00390 00391 //----------------------------------------------------------------------------- 00392 template<typename SOURCE_TYPE, typename DEST_TYPE> 00393 int vtkPPixelTransfer::Execute( 00394 MPI_Comm comm, 00395 int rank, 00396 int nComps, 00397 SOURCE_TYPE *srcData, 00398 DEST_TYPE *destData, 00399 std::vector<MPI_Request> &reqs, 00400 std::deque<MPI_Datatype> &types, 00401 int tag) 00402 { 00403 int iErr = 0; 00404 if ((comm == MPI_COMM_NULL) || (this->Local(rank))) 00405 { 00406 // transaction is local, bypass mpi in favor of memcpy 00407 return vtkPixelTransfer::Blit( 00408 this->SrcWholeExt, 00409 this->SrcExt, 00410 this->DestWholeExt, 00411 this->DestExt, 00412 nComps, 00413 srcData, 00414 nComps, 00415 destData); 00416 } 00417 00418 if (rank == this->DestRank) 00419 { 00420 // use mpi to receive the data 00421 if (destData == NULL) 00422 { 00423 return -1; 00424 } 00425 00426 MPI_Datatype subarray; 00427 iErr = vtkMPIPixelViewNew<DEST_TYPE>( 00428 this->DestWholeExt, 00429 this->DestExt, 00430 nComps, 00431 subarray); 00432 if (iErr) 00433 { 00434 return -4; 00435 } 00436 00437 if (this->UseBlockingRecv) 00438 { 00439 MPI_Status stat; 00440 iErr = MPI_Recv( 00441 destData, 00442 1, 00443 subarray, 00444 this->SrcRank, 00445 tag, 00446 comm, 00447 &stat); 00448 } 00449 else 00450 { 00451 reqs.push_back(MPI_REQUEST_NULL); 00452 iErr = MPI_Irecv( 00453 destData, 00454 1, 00455 subarray, 00456 this->SrcRank, 00457 tag, 00458 comm, 00459 &reqs.back()); 00460 } 00461 00462 #define HOLD_RECV_TYPES 00463 #ifdef HOLD_RECV_YPES 00464 types.push_back(subarray); 00465 #else 00466 MPI_Type_free(&subarray); 00467 #endif 00468 00469 if (iErr) 00470 { 00471 return -5; 00472 } 00473 } 00474 00475 if (rank == this->SrcRank) 00476 { 00477 // use mpi to send the data 00478 if (srcData == NULL) 00479 { 00480 return -1; 00481 } 00482 00483 MPI_Datatype subarray; 00484 iErr = vtkMPIPixelViewNew<SOURCE_TYPE>( 00485 this->SrcWholeExt, 00486 this->SrcExt, 00487 nComps, 00488 subarray); 00489 if (iErr) 00490 { 00491 return -2; 00492 } 00493 00494 if (this->UseBlockingSend) 00495 { 00496 iErr = MPI_Ssend( 00497 srcData, 00498 1, 00499 subarray, 00500 this->DestRank, 00501 tag, 00502 comm); 00503 } 00504 else 00505 { 00506 MPI_Request req; 00507 iErr = MPI_Isend( 00508 srcData, 00509 1, 00510 subarray, 00511 this->DestRank, 00512 tag, 00513 comm, 00514 &req); 00515 #define SAVE_SEND_REQS 00516 #ifdef SAVE_SEND_REQS 00517 reqs.push_back(req); 00518 #else 00519 MPI_Request_free(&req); 00520 #endif 00521 } 00522 00523 #define HOLD_SEND_TYPES 00524 #ifdef HOLD_SEND_TYPES 00525 types.push_back(subarray); 00526 #else 00527 MPI_Type_free(&subarray); 00528 #endif 00529 00530 if (iErr) 00531 { 00532 return -3; 00533 } 00534 } 00535 00536 return iErr; 00537 } 00538 00539 ostream &operator<<(std::ostream &os, const vtkPPixelTransfer >); 00540 00541 #endif 00542 // VTK-HeaderTest-Exclude: vtkPPixelTransfer.h