00001 #ifndef MOC_H_ 00002 #define MOC_H_ 00003 00004 #include <stdint.h> 00005 #include "moc_datatype.h" 00006 #include "moc_error_codes.h" 00007 00008 00009 00010 /** 00011 * Indicates, in a receive, to accept a message with any tag value. 00012 **/ 00013 #define MOC_ANY_TAG 1000 00014 00015 /** 00016 * Reserved Tag for Broadcast-Messages (MOC_Bcast). 00017 **/ 00018 #define MOC_BCAST_TAG 250 00019 00020 /** 00021 * Specifies a rank that can be used to send or receive from no-one. 00022 **/ 00023 #define MOC_PROC_NULL 1000 00024 00025 /** 00026 * Indicates, in a receive, to accept a message from any source. 00027 **/ 00028 #define MOC_ANY_SOURCE 1001 00029 00030 /** 00031 * Maximum byte-count which can be transferred by one DMA-transfer. 00032 **/ 00033 #define MAX_DMA_CALL_SIZE 16384 00034 00035 /** 00036 * Maximum byte-count of a MOC-message. It's only the theoretical size, because 00037 * practically the SPU's local-stores can only hold much fewer bytes. 00038 **/ 00039 #define MAX_MOC_MESSAGE_SIZE 16777215 00040 00041 00042 00043 /** 00044 * \internal 00045 * \addtogroup internal_p2p_imm 00046 **/ 00047 //@{ 00048 00049 /** 00050 * \internal 00051 * @name Possible structures for MOC_Request.request_data. 00052 **/ 00053 //@{ 00054 00055 /** 00056 * \internal 00057 * Struct with information about a non-blocking DMA-Communication. 00058 **/ 00059 typedef struct imoc_dma_request_struct 00060 { 00061 char *buffer; 00062 void *target; 00063 uint32_t size; 00064 uint32_t remainder; 00065 uint32_t dest; 00066 uint32_t tag_id; 00067 } imoc_dma_request; 00068 00069 /** 00070 * \internal 00071 * Struct with information about a non-blocking ISsend-Communication. 00072 **/ 00073 typedef struct imoc_issend_request_struct 00074 { 00075 uint8_t mid; 00076 uint8_t isFinished; 00077 uint8_t source; 00078 uint8_t tag; 00079 uint32_t message_size; 00080 } imoc_issend_request; 00081 00082 //@} 00083 //@} 00084 00085 00086 00087 /** 00088 * \addtogroup environment_error 00089 * 00090 * This section describes how errors are handled. 00091 * 00092 * Every function should return an integer if possible. This integer should be 00093 * MOC_SUCCESS if the operation teminated successfully otherwise an error-code 00094 * telling the reason of the error is returned. 00095 **/ 00096 //@{ 00097 00098 /** 00099 * Maximal length of error-text. 00100 **/ 00101 #define MOC_MAX_ERROR_STRING 255 00102 00103 /** 00104 * Returns an error-text for a given error code. 00105 * 00106 * The error-text is already terminated by '\\0'. 00107 * 00108 * \param errorcode \b in Error code returned by an MPI routine 00109 * \param string \b out Text that corresponds to the errorcode 00110 * \param resultlen \b out Length of string 00111 * \retval MOC_SUCCESS No error; MPI routine completed successfully. 00112 * \retval MOC_ERR_ARG Invalid argument. Most likely an error-code out of range. 00113 **/ 00114 int MOC_Error_string ( int errorcode, char *string, int *resultlen ); 00115 00116 /** 00117 * Converts an error code into an error class. 00118 * 00119 * \param errorcode \b in Error code returned by an MPI routine 00120 * \param errorclass \b out Error class associated with errorcode 00121 * \retval MOC_SUCCESS No error; MPI routine completed successfully. 00122 * \retval MOC_ERR_COMM Invalid argument. Most likely an error-code out of range. 00123 **/ 00124 int MOC_Error_class ( int errorcode, int *errorclass ); 00125 00126 //@} 00127 00128 00129 00130 00131 00132 /** 00133 * \addtogroup environment_information 00134 * 00135 * Functions to return some information about the execution environment and 00136 * the MOC-implementation. 00137 **/ 00138 //@{ 00139 00140 /** 00141 * Major version-number of this MOC-Implementation 00142 **/ 00143 #define MOC_VERSION 0 00144 00145 /** 00146 * Minor version-number of this MOC-Implementation 00147 **/ 00148 #define MOC_SUBVERSION 9 00149 00150 /** 00151 * The maximum length of the string returned by MOC_Get_processor_name. 00152 **/ 00153 #define MOC_MAX_PROCESSOR_NAME 4 00154 00155 /** 00156 * Gets the name of the processor. 00157 * 00158 * \note This function returns "SPU" if the calling process is running on a SPU otherwise 00159 * it's running on the "PPU". 00160 * 00161 * \param name \b out Specifies the processor-type the calling process is runnning on 00162 * \param resultlen \b out Length (in characters) of the name 00163 * \retval MOC_SUCCESS No error; MPI routine completed successfully. 00164 **/ 00165 int MOC_Get_processor_name ( char *name, int *resultlen); 00166 00167 /** 00168 * Returns the major and minor version of this MOC-implementation. 00169 * 00170 * \note Can be called before MOC_Init and after MOC_Finalize. 00171 * 00172 * @param version \b out Major version of this MOC-implementation 00173 * @param subversion \b out Minor version of this MOC-implementation 00174 * @retval MOC_SUCCESS Function returned successfully 00175 **/ 00176 int MOC_Get_version(int *version, int *subversion); 00177 00178 //@} 00179 00180 00181 00182 00183 00184 /** 00185 * \addtogroup environment_startup 00186 **/ 00187 //@{ 00188 /** 00189 * @name PPU & SPU 00190 **/ 00191 //@{ 00192 00193 /** 00194 * Terminates MPI execution environment. 00195 * 00196 * \note All processes must call this routine before exiting. 00197 * 00198 * \retval MOC_SUCCESS No error; MPI routine completed successfully. 00199 **/ 00200 int MOC_Finalize (void); 00201 00202 //@} 00203 //@} 00204 00205 00206 00207 00208 00209 /** 00210 * \addtogroup p2p_status 00211 * 00212 * Receiving operations return a status-object holding information about 00213 * the message. 00214 * 00215 * There are three Fields of the status-Struct which are predefined by the MPI-Standard: 00216 * MOC_SOURCE gives the message-source, MOC_TAG gives the message-tag and MOC_ERROR gives 00217 * an error-code (not implemented by MOC at the moment). To get the number of element the 00218 * function \ref MOC_Get_count should be used. 00219 **/ 00220 //@{ 00221 00222 /** 00223 * Structure holding information about a received message. 00224 **/ 00225 typedef struct MOC_Status_struct 00226 { 00227 uint8_t MOC_SOURCE; /**< message-source */ 00228 uint8_t MOC_TAG; /**< message-tag */ 00229 int MOC_ERROR; /**< error-code */ 00230 int message_size; /**< message-size in byte (internal-variable) */ 00231 uint8_t mid; /**< message-ID (internal-variable) */ 00232 } MOC_Status; /**< */ 00233 00234 /** 00235 * Gets the number of received elements which is encoded in MOC_Status. 00236 * 00237 * @param status \b in status-object 00238 * @param datatype \b in Type of received elements 00239 * @param count \b out Number of received elements 00240 * @retval MOC_SUCCESS No error; MPI routine completed successfully. 00241 * @retval ... error-code 00242 **/ 00243 int MOC_Get_count(MOC_Status *status, MOC_Datatype datatype, int *count); 00244 00245 //@} 00246 00247 00248 00249 00250 00251 00252 00253 /** 00254 * \addtogroup comm_main 00255 * 00256 * \details 00257 * Currently there is no support for creating and managing user-defined groups and 00258 * communicators and probably never will be. The local storage of a SPU is very small 00259 * and also the maximal number of nodes is limited to a small number and so there is 00260 * doubt if the benefits will be greater than the overhead introduced by supporting 00261 * user-defined groups and communicators. 00262 * 00263 * Only the predefined communicators \ref MOC_COMM_WORLD, \ref MOC_COMM_SELF and 00264 * \ref MOC_COMM_NULL are available. 00265 * 00266 * The only operations which are currently implemented are \ref MOC_Comm_size and \ref 00267 * MOC_Comm_rank. 00268 **/ 00269 /** 00270 * \addtogroup comm_mgt 00271 * 00272 * Funktions for managing communicators. Because of reasons already stated (see \ref comm_main) 00273 * there is no support for user-defined communicators. So this section is limited to functions 00274 * which return the size of a specific communicator or the rank of the calling process. 00275 **/ 00276 //@{ 00277 00278 /** 00279 * Communicator-Handle. 00280 * 00281 * Masks the actual type which is used to encode the communicator. 00282 * Char is used and therefore the maximum number of possible communicators is limited to 256. 00283 * But because there are three predefined communicators (MPI_COMM_NULL, MPI_COMM_WORLD and 00284 * MPI_COMM_SELF) only 253 user-defined communicators are possible. 00285 **/ 00286 typedef int MOC_Comm; 00287 00288 /** 00289 * Specifies a null communicator. 00290 **/ 00291 #define MOC_COMM_NULL 0 00292 00293 /** 00294 * Specifies a constant that contains all of the processes. 00295 **/ 00296 #define MOC_COMM_WORLD 1 00297 00298 /** 00299 * Specifies a constant that contains only the calling process. 00300 **/ 00301 #define MOC_COMM_SELF 2 00302 00303 /** 00304 * Determines the rank of the calling process in the communicator. 00305 * 00306 * \param comm \b in commicator-handle 00307 * \param rank \b out rank of the calling process in group of comm 00308 * \retval MOC_SUCCESS No error; MPI routine completed successfully. 00309 * \retval MOC_ERR_COMM Invalid communicator. A common error is to use a null communicator in a call. 00310 **/ 00311 int MOC_Comm_rank ( MOC_Comm comm, int *rank ); 00312 00313 /** 00314 * Determines the size of the group associated with a communictor. 00315 * 00316 * \param comm \b in commicator-handle 00317 * \param size \b out number of processes in the group of comm 00318 * \retval MOC_SUCCESS No error; MPI routine completed successfully. 00319 * \retval MOC_ERR_COMM Invalid communicator. A common error is to use a null communicator in a call. 00320 **/ 00321 int MOC_Comm_size ( MOC_Comm comm, int *size ); 00322 00323 //@} 00324 00325 00326 00327 00328 00329 00330 /** 00331 * \addtogroup environment_timer 00332 * 00333 * Functions to measure time. 00334 * 00335 * On the PPU gettimeofday from time.h is used. On the SPU either also gettimeofday or the 00336 * spu-timer-library is used depending on the configuration during compilation of the MOC-library. 00337 * When gettimeofday is used on the SPU the time is global in the MOC-environment with the 00338 * disadvantage that the SPU-threads get their times from the PPU using DMA causing inaccuracy and 00339 * delays. 00340 **/ 00341 //@{ 00342 00343 /** 00344 * Returns a floating-point number of seconds, representing elapsed wall-clock 00345 * time since some time in the past. 00346 * 00347 * @return wall-clock time in seconds. 00348 **/ 00349 double MOC_Wtime(void); 00350 00351 /** 00352 * Returns the resolution of Moc_Wtime in seconds. 00353 * 00354 * @return resolution in seconds. 00355 **/ 00356 double MOC_Wtick(void); 00357 00358 //@} 00359 00360 00361 00362 00363 00364 00365 00366 /** 00367 * \addtogroup p2p_main 00368 **/ 00369 //@{ 00370 00371 /** 00372 * Indicates, at which message-size \ref MOC_Send switches to synchronous send. 00373 */ 00374 #define MOC_SEND_TRESHOLD 4096 00375 00376 00377 /** 00378 * Performs a blocking standard mode send operation. 00379 * 00380 * \note This routine may block until the message is received. 00381 * 00382 * @param buf \b in Pointer to buffer where data is stored 00383 * @param count \b in Number of elements to be send (not equal to actual byte-value) 00384 * @param datatype \b in Type of elements to be send 00385 * @param dest \b in Rank of receiving process 00386 * @param tag \b in Tag of message 00387 * @param comm \b in communicator of message 00388 * @retval MOC_SUCCESS No error; MPI routine completed successfully. 00389 * @retval ... error-code 00390 **/ 00391 int MOC_Send(void* buf, int count, MOC_Datatype datatype, int dest, int tag, MOC_Comm comm); 00392 00393 /** 00394 * Performs a blocking standard mode receive operation. 00395 * 00396 * \note This routine blocks until the message is received. 00397 * 00398 * @param buf \b inout Buffer into which data should be stored 00399 * @param count \b in Number of elements in receive buffer (not equal to actual byte-value) 00400 * @param datatype \b in Datatype of each receive buffer element 00401 * @param source \b in Rank of source 00402 * @param tag \b in Tag of message 00403 * @param comm \b in Communicator of message 00404 * @param status \b inout Object holding status-information (has to be allocated by user) 00405 * @retval MOC_SUCCESS No error; MPI routine completed successfully. 00406 * @retval ... error-code 00407 **/ 00408 int MOC_Recv(void* buf, int count, MOC_Datatype datatype, int source, int tag, 00409 MOC_Comm comm, MOC_Status *status); 00410 00411 /** 00412 * Waits till a message is received and returns information without actually 00413 * receiving the message. 00414 * 00415 * @param source \b in source of message 00416 * @param tag \b in message-tag 00417 * @param comm \b in communicator 00418 * @param status \b out status-object holding information about message 00419 * @retval MOC_SUCCESS No error; MPI routine completed successfully. 00420 * @retval ... error-code 00421 **/ 00422 int MOC_Probe(int source, int tag, MOC_Comm comm, MOC_Status *status); 00423 00424 /** 00425 * Tests if a message is available and returns information without actually 00426 * receiving the message. 00427 * 00428 * @param source \b in source of message 00429 * @param tag \b in message-tag 00430 * @param comm \b in communicator 00431 * @param flag \b out boolean value telling if a message is available 00432 * @param status \b out status-object holding information about message 00433 * @retval MOC_SUCCESS No error; MPI routine completed successfully. 00434 * @retval ... error-code 00435 **/ 00436 int MOC_Iprobe(int source, int tag, MOC_Comm comm, int *flag, MOC_Status *status); 00437 00438 //@} 00439 00440 00441 00442 00443 00444 00445 /** 00446 * \addtogroup p2p_synch 00447 **/ 00448 //@{ 00449 00450 /** 00451 * Performs a blocking synchronous mode send operation. 00452 * 00453 * \note This routine blocks until the message is received. 00454 * 00455 * @param buf \b in Pointer to buffer where data is stored 00456 * @param count \b in Number of elements to be send (not equal to actual byte-value) 00457 * @param datatype \b in Type of elements to be send 00458 * @param dest \b in Rank of receiving process 00459 * @param tag \b in Tag of message 00460 * @param comm \b in communicator of message 00461 * @retval MOC_SUCCESS No error; MPI routine completed successfully. 00462 * @retval ... error-code 00463 **/ 00464 int MOC_Ssend(void* buf, int count, MOC_Datatype datatype, int dest, int tag, MOC_Comm comm); 00465 00466 //@} 00467 00468 00469 00470 00471 00472 /** 00473 * \addtogroup p2p_buffered 00474 **/ 00475 //@{ 00476 00477 /** 00478 * Performs a blocking buffered mode send operation. 00479 * 00480 * \note This routine blocks until the send-buffer is free. 00481 * 00482 * @param buf \b in Pointer to buffer where data is stored 00483 * @param count \b in Number of elements to be send (not equal to actual byte-value) 00484 * @param datatype \b in Type of elements to be send 00485 * @param dest \b in Rank of receiving process 00486 * @param tag \b in Tag of message 00487 * @param comm \b in communicator of message 00488 * @retval MOC_SUCCESS No error; MPI routine completed successfully. 00489 * @retval ... error-code 00490 **/ 00491 int MOC_Bsend(void* buf, int count, MOC_Datatype datatype, int dest, int tag, MOC_Comm comm); 00492 00493 //@} 00494 00495 00496 00497 00498 00499 /** 00500 * \addtogroup p2p_sendrecv 00501 **/ 00502 //@{ 00503 00504 /** 00505 * Execute a blocking send and receive operation. Both send and receive use the same 00506 * communicator, but possibly different tags. The send buffer and receive buffers may 00507 * be disjoint, and may have different lengths and datatypes. 00508 * 00509 * @param sendbuf \b in Pointer to buffer where data is stored 00510 * @param sendcount \b in Number of elements to be send (not equal to actual byte-value) 00511 * @param sendtype \b in Type of elements to be send 00512 * @param dest \b in Rank of receiving process 00513 * @param sendtag \b in Tag of message to be send 00514 * 00515 * @param recvbuf \b inout Buffer into which data should be stored 00516 * @param recvcount \b in Number of elements in receive buffer (not equal to actual byte-value) 00517 * @param recvtype \b in Datatype of each receive buffer element 00518 * @param source \b in Rank of source 00519 * @param recvtag \b in Tag of message to be received 00520 * 00521 * @param comm \b in Communicator of message 00522 * @param status \b inout Object holding status-information (has to be allocated by user) 00523 * 00524 * @retval MOC_SUCCESS No error; MPI routine completed successfully. 00525 * @retval ... error-code 00526 **/ 00527 int MOC_Sendrecv(void *sendbuf, int sendcount, MOC_Datatype sendtype, int dest, 00528 int sendtag, void *recvbuf, int recvcount, MOC_Datatype recvtype, 00529 int source, int recvtag, MOC_Comm comm, MOC_Status *status); 00530 00531 /** 00532 * Execute a blocking send and receive. The same buffer is used both for the send 00533 * and for the receive, so that the message sent is replaced by the message 00534 * received. 00535 * 00536 * @param buf \b inout Pointer to buffer 00537 * @param count \b in Number of elements (not equal to actual byte-value) 00538 * @param datatype \b in Type of elements 00539 * 00540 * @param dest \b in Rank of receiving process 00541 * @param sendtag \b in Tag of message to be send 00542 * 00543 * @param source \b in Rank of source 00544 * @param recvtag \b in Tag of message to be received 00545 * 00546 * @param comm \b in Communicator of message 00547 * @param status \b inout Object holding status-information (has to be allocated by user) 00548 * 00549 * @retval MOC_SUCCESS No error; MPI routine completed successfully. 00550 * @retval ... error-code 00551 **/ 00552 int MOC_Sendrecv_replace(void* buf, int count, MOC_Datatype datatype, int dest, 00553 int sendtag, int source, int recvtag, MOC_Comm comm, 00554 MOC_Status *status); 00555 00556 //@} 00557 00558 00559 00560 00561 /** 00562 * \addtogroup p2p_imm 00563 **/ 00564 //@{ 00565 00566 /** 00567 * Communication-Request (Handle) 00568 **/ 00569 typedef struct moc_request_struct 00570 { 00571 int request_type; 00572 union 00573 { 00574 imoc_dma_request dma_data; 00575 imoc_issend_request issend_request; 00576 } request_data ; 00577 } MOC_Request /**< Communication-Request (Handle) */; 00578 00579 /** 00580 * Performs a non-blocking standard mode send operation. 00581 * 00582 * \note This routine returns as soon as possible. 00583 * 00584 * @param buf \b in Pointer to buffer where data is stored 00585 * @param count \b in Number of elements to be send (not equal to actual byte-value) 00586 * @param datatype \b in Type of elements to be send 00587 * @param dest \b in Rank of receiving process 00588 * @param tag \b in Tag of message 00589 * @param comm \b in communicator of message 00590 * @param request \b out communication request (handle) 00591 * @retval MOC_SUCCESS No error; MPI routine completed successfully. 00592 * @retval ... error-code 00593 **/ 00594 int MOC_ISend(void* buf, int count, MOC_Datatype datatype, int dest, int tag, MOC_Comm comm, 00595 MOC_Request *request); 00596 00597 /** 00598 * Performs a non-blocking synchronous mode send operation. 00599 * 00600 * \note This routine returns as soon as possible (After the message-envelope has 00601 * been written into the receiver's message-queue). 00602 * 00603 * @param buf \b in Pointer to buffer where data is stored 00604 * @param count \b in Number of elements to be send (not equal to actual byte-value) 00605 * @param datatype \b in Type of elements to be send 00606 * @param dest \b in Rank of receiving process 00607 * @param tag \b in Tag of message 00608 * @param comm \b in communicator of message 00609 * @param request \b out communication request (handle) 00610 * @retval MOC_SUCCESS No error; MPI routine completed successfully. 00611 * @retval ... error-code 00612 **/ 00613 int MOC_ISsend(void* buf, int count, MOC_Datatype datatype, int dest, int tag, MOC_Comm comm, 00614 MOC_Request *request); 00615 00616 /** 00617 * Tests, if a non-blocking communication has been completed. 00618 * 00619 * @param request \b in Communication-Request (Handle) 00620 * @param flag \b out true, if communication-request has been completed 00621 * @param status \b out Object holding status-information 00622 * @retval MOC_SUCCESS No error; MPI routine completed successfully. 00623 * @retval ... error-code 00624 **/ 00625 int MOC_Test(MOC_Request *request, int *flag, MOC_Status *status); 00626 00627 /** 00628 * Wait till a non-blocking communication has been completed. 00629 * 00630 * @param request \b in Communication-Request (Handle) 00631 * @param status \b out Object holding status-information 00632 * @retval MOC_SUCCESS No error; MPI routine completed successfully. 00633 * @retval ... error-code 00634 **/ 00635 int MOC_Wait(MOC_Request *request, MOC_Status *status); 00636 00637 //@} 00638 00639 00640 00641 00642 00643 00644 /** 00645 * \addtogroup broadcast 00646 **/ 00647 //@{ 00648 00649 /** 00650 * Broadcasts a message from the process with rank "root" to all other processes of the group. 00651 * 00652 * \note The broadcast-message can also be received by a MOC_Recv using MOC_BCAST_TAG. 00653 * 00654 * @param buffer \b inout starting address of buffer 00655 * @param count \b in number of elements to be send or received 00656 * @param datatype \b in Type of elements to be send or received 00657 * @param root \b in rank of the process who sends the broadcast-message 00658 * @param comm \b in communicator of message 00659 **/ 00660 int MOC_Bcast(void* buffer, int count, MOC_Datatype datatype, int root, MOC_Comm comm ); 00661 00662 /** 00663 * Blocks the caller until all processes in the communicator have called it; that is, the 00664 * call returns at any process only after all members of the communicator have entered the 00665 * call. 00666 * 00667 * @param comm \b in communicator of message 00668 * @retval MOC_SUCCESS No error; MPI routine completed successfully. 00669 * @retval ... error-code 00670 **/ 00671 int MOC_Barrier(MOC_Comm comm ); 00672 00673 //@} 00674 00675 00676 00677 00678 00679 #endif /*MOC_H_*/ 00680
1.5.6