/// <summary> /// Given the header data, this routine will set up the receive of the /// serialized data on the shadow communicator. /// </summary> /// <param name="status"> /// The status message returned from the completion of the first /// receive (of the header data). /// </param> protected void SetupSerializedReceive(Unsafe.MPI_Status status) { // Save the tag originalTag = status.MPI_TAG; // Extract the header SerializedMessageHeader header = (SerializedMessageHeader)headerObj; // Create the stream stream = new UnmanagedMemoryStream(header.bytes); unsafe { // Receive serialized data via the shadow communicator int errorCode = Unsafe.MPI_Irecv(stream.Buffer, header.bytes, Unsafe.MPI_BYTE, status.MPI_SOURCE, header.tag, shadowComm, out request); if (errorCode != Unsafe.MPI_SUCCESS) { stream.Dispose(); throw Environment.TranslateErrorIntoException(errorCode); } } }
public override CompletedStatus Test() { if (cachedStatus != null) { return(cachedStatus); } Unsafe.MPI_Status status; int flag; unsafe { int errorCode = Unsafe.MPI_Test(ref request, out flag, out status); if (errorCode != Unsafe.MPI_SUCCESS) { throw Environment.TranslateErrorIntoException(errorCode); } } if (flag == 0) { return(null); } if (stream == null) { // We completed the receive of the header message. // Cleanup this receive request = Unsafe.MPI_REQUEST_NULL; handle.Free(); SerializedMessageHeader header = (SerializedMessageHeader)headerObj; if (header.bytes == 0) { // If the second message is empty, we're done GC.SuppressFinalize(this); cachedStatus = new CompletedStatus(status, 1); return(cachedStatus); } // Setup the serialized receive and test again, just in case SetupSerializedReceive(status); return(Test()); } // We completed the receive of the serialized data. // Cleanup request = Unsafe.MPI_REQUEST_NULL; GC.SuppressFinalize(this); // Deserialize the data try { BinaryFormatter formatter = new BinaryFormatter(); value = (T)formatter.Deserialize(stream); status.MPI_TAG = originalTag; cachedStatus = new CompletedStatus(status, 1); } finally { stream.Dispose(); } return(cachedStatus); }