/// <summary> /// Deregister memory window /// </summary> /// <param name="bufferDescriptor">Buffer Descriptor point to memory windows</param> /// <returns></returns> public void DeregisterMemoryWindow(RdmaBufferDescriptorV1 bufferDescriptor) { foreach (SmbdMemoryWindow mw in memoryWindowList) { if (mw.BufferDescriptor.Token != bufferDescriptor.Token) { continue; } // get memory window if (mw.IsValid) { UInt64 resultId; NtStatus status = (NtStatus)rdmaEndpoint.Invalidate(mw.RdmaMW, out resultId); if (status == NtStatus.STATUS_SUCCESS) { requestCount++; rdmaNotificationSemaphore.Release(); } } rdmaAdapter.DeregisterMemory(mw.MemoryHandlerId); memoryWindowList.Remove(mw); return; } }
/// <summary> /// deregister each memory region indicated by each SMBDirect Buffer Descriptor V1 /// structure with the underlying RDMA provider /// </summary> /// <param name="bufferDescriptor">Buffer Descriptor point to registered buffer</param> public void DeregisterBuffer(SmbdBufferDescriptorV1 bufferDescriptor) { RdmaBufferDescriptorV1 rdmaBufferDescriptor = new RdmaBufferDescriptorV1(); rdmaBufferDescriptor.Length = bufferDescriptor.Length; rdmaBufferDescriptor.Token = bufferDescriptor.Token; rdmaBufferDescriptor.Offset = bufferDescriptor.Offset; Connection.Endpoint.DeregisterMemoryWindow(rdmaBufferDescriptor); }
/// <summary> /// Read data from registered buffer /// </summary> /// <param name="data"></param> /// <param name="bufferDescriptor">Buffer Descriptor point to registered buffer</param> public NtStatus ReadRegisteredBuffer(byte[] data, SmbdBufferDescriptorV1 bufferDescriptor) { RdmaBufferDescriptorV1 rdmaBufferDescriptor = new RdmaBufferDescriptorV1(); rdmaBufferDescriptor.Length = bufferDescriptor.Length; rdmaBufferDescriptor.Token = bufferDescriptor.Token; rdmaBufferDescriptor.Offset = bufferDescriptor.Offset; return(Connection.Endpoint.ReadMemoryWindow(data, rdmaBufferDescriptor)); }
/// <summary> /// Read data from memory window /// </summary> /// <param name="data"></param> /// <param name="bufferDescriptor">Buffer Descriptor point to memory windows</param> public NtStatus ReadMemoryWindow(byte[] data, RdmaBufferDescriptorV1 bufferDescriptor) { foreach (SmbdMemoryWindow mw in memoryWindowList) { if (mw.BufferDescriptor.Token != bufferDescriptor.Token) { continue; } // get memory window if (mw.IsValid) { NtStatus status = (NtStatus)RdmaEndpoint.ReadFromMemory(mw.MemoryHandlerId, data); return(status); } return(NtStatus.STATUS_INVALID_PARAMETER_2); } return(NtStatus.STATUS_INVALID_PARAMETER_2); }
/// <summary> /// Register memory windows /// </summary> /// <param name="size">Size of memory to register</param> /// <param name="flag"></param> /// <param name="reversed">if it is true, little-endian and big-endian will be reversed in bufferDescriptor</param> /// <param name="bufferDescriptor">Buffer Descriptor point to memory windows</param> /// <returns></returns> public NtStatus RegisterMemoryWindow( uint size, RdmaOperationReadWriteFlag flag, bool reversed, out RdmaBufferDescriptorV1 bufferDescriptor) { bufferDescriptor = new RdmaBufferDescriptorV1(); // regiser the buffer SmbdMemoryWindow memoryWindow = new SmbdMemoryWindow(); memoryWindow.IsValid = true; NtStatus status = (NtStatus)rdmaAdapter.RegisterMemory(size, out memoryWindow.MemoryHandlerId); if (status != NtStatus.STATUS_SUCCESS) { return(status); } // create memory window SmbdRequest invalidRequest = new SmbdRequest(); invalidRequest.Type = RequestType.Invalid; status = (NtStatus)rdmaAdapter.CreateMemoryWindow(invalidRequest.ResultId, out memoryWindow.RdmaMW); memoryWindow.InvalidResultId = invalidRequest.ResultId; if (status != NtStatus.STATUS_SUCCESS) { return(status); } // invalid notification request has been submitted requestCount++; rdmaNotificationSemaphore.Release(); // bind UInt64 resultId; status = (NtStatus)rdmaEndpoint.Bind( memoryWindow.MemoryHandlerId, memoryWindow.RdmaMW, flag, reversed, out memoryWindow.BufferDescriptor, out resultId); if (status != NtStatus.STATUS_SUCCESS) { return(status); } lock (locker) { this.receiveRequestList.Add(invalidRequest); } SmbdRequestResult requestResult = GetRequestResult(new TimeSpan(0, 0, 5), RequestType.Bind); this.LogEvent(string.Format("Bind memory window with result id: {0}. And get notification with id: {1}, status: {2}", resultId, requestResult.ResultId, requestResult.ResultInfo.Status )); status = (NtStatus)requestResult.ResultInfo.Status; if (status != NtStatus.STATUS_SUCCESS) { return(status); } this.memoryWindowList.Add(memoryWindow); bufferDescriptor = memoryWindow.BufferDescriptor; return(status); }
/// <summary> /// Write data to memory window /// </summary> /// <param name="data"></param> /// <param name="bufferDescriptor">Buffer Descriptor point to memory windows</param> public NtStatus WriteMemoryWindow(byte[] data, RdmaBufferDescriptorV1 bufferDescriptor) { foreach (SmbdMemoryWindow mw in memoryWindowList) { if (mw.BufferDescriptor.Token != bufferDescriptor.Token) { continue; } // get memory window if (mw.IsValid) { NtStatus status = (NtStatus)RdmaEndpoint.WriteToMemory(mw.MemoryHandlerId, data); return status; } return NtStatus.STATUS_INVALID_PARAMETER_2; } return NtStatus.STATUS_INVALID_PARAMETER_2; }
/// <summary> /// Register memory windows /// </summary> /// <param name="size">Size of memory to register</param> /// <param name="flag"></param> /// <param name="reversed">if it is true, little-endian and big-endian will be reversed in bufferDescriptor</param> /// <param name="bufferDescriptor">Buffer Descriptor point to memory windows</param> /// <returns></returns> public NtStatus RegisterMemoryWindow( uint size, RdmaOperationReadWriteFlag flag, bool reversed, out RdmaBufferDescriptorV1 bufferDescriptor) { bufferDescriptor = new RdmaBufferDescriptorV1(); // regiser the buffer SmbdMemoryWindow memoryWindow = new SmbdMemoryWindow(); memoryWindow.IsValid = true; NtStatus status = (NtStatus)rdmaAdapter.RegisterMemory(size, out memoryWindow.MemoryHandlerId); if (status != NtStatus.STATUS_SUCCESS) { return status; } // create memory window SmbdRequest invalidRequest = new SmbdRequest(); invalidRequest.Type = RequestType.Invalid; status = (NtStatus)rdmaAdapter.CreateMemoryWindow(invalidRequest.ResultId, out memoryWindow.RdmaMW); memoryWindow.InvalidResultId = invalidRequest.ResultId; if (status != NtStatus.STATUS_SUCCESS) { return status; } // invalid notification request has been submitted requestCount++; rdmaNotificationSemaphore.Release(); // bind UInt64 resultId; status = (NtStatus)rdmaEndpoint.Bind( memoryWindow.MemoryHandlerId, memoryWindow.RdmaMW, flag, reversed, out memoryWindow.BufferDescriptor, out resultId); if (status != NtStatus.STATUS_SUCCESS) { return status; } lock (locker) { this.receiveRequestList.Add(invalidRequest); } SmbdRequestResult requestResult = GetRequestResult(new TimeSpan(0, 0, 5), RequestType.Bind); this.LogEvent(string.Format("Bind memory window with result id: {0}. And get notification with id: {1}, status: {2}", resultId, requestResult.ResultId, requestResult.ResultInfo.Status )); status = (NtStatus)requestResult.ResultInfo.Status; if (status != NtStatus.STATUS_SUCCESS) { return status; } this.memoryWindowList.Add(memoryWindow); bufferDescriptor = memoryWindow.BufferDescriptor; return status; }
/// <summary> /// Write data to registered buffer /// </summary> /// <param name="data"></param> /// <param name="bufferDescriptor">Buffer Descriptor point to registered buffer</param> public NtStatus WriteRegisteredBuffer(byte[] data, SmbdBufferDescriptorV1 bufferDescriptor) { RdmaBufferDescriptorV1 rdmaBufferDescriptor = new RdmaBufferDescriptorV1(); rdmaBufferDescriptor.Length = bufferDescriptor.Length; rdmaBufferDescriptor.Token = bufferDescriptor.Token; rdmaBufferDescriptor.Offset = bufferDescriptor.Offset; return Connection.Endpoint.WriteMemoryWindow(data, rdmaBufferDescriptor); }