internal static extern unsafe bool ReadDirectoryChangesW( SafeFileHandle hDirectory, byte[] lpBuffer, int nBufferLength, [MarshalAs(UnmanagedType.Bool)] bool bWatchSubtree, int dwNotifyFilter, out int lpBytesReturned, NativeOverlapped* lpOverlapped, IntPtr lpCompletionRoutine);
internal void Callback(uint errorCode, uint numBytes, NativeOverlapped* pNOlap) { // Execute the task _scheduler.TryExecuteTask(_task); // Put this item back into the pool for someone else to use var pool = _scheduler._availableWorkItems; if (pool != null) pool.PutObject(this); else Overlapped.Free(pNOlap); }
private unsafe static void CompletionCallback(uint errorCode, uint numBytes, NativeOverlapped* nativeOverlapped) { ThreadPoolBoundHandleOverlapped overlapped = (ThreadPoolBoundHandleOverlapped)Overlapped.Unpack(nativeOverlapped); // // The Win32 thread pool implementation of ThreadPoolBoundHandle does not permit reuse of NativeOverlapped // pointers without freeing them and allocating new a new one. We need to ensure that code using the CLR // ThreadPool implementation follows those rules. // if (overlapped._completed) throw new InvalidOperationException(SR.InvalidOperation_NativeOverlappedReused); overlapped._completed = true; if (overlapped._boundHandle == null) throw new InvalidOperationException(SR.Argument_NativeOverlappedAlreadyFree); overlapped._userCallback(errorCode, numBytes, nativeOverlapped); }
private bool WriteData(byte[] data, int timeout) { if (_deviceCapabilities.OutputReportByteLength <= 0) { return(false); } uint bytesWritten = 0; // Optimization: Don't create a new buffer & copy if given data array is of sufficient size. byte[] buffer; if (data.Length == _deviceCapabilities.OutputReportByteLength) { buffer = data; } else { buffer = CreateOutputBuffer(); Array.Copy(data, 0, buffer, 0, Math.Min(data.Length, _deviceCapabilities.OutputReportByteLength)); } // TODO: Do that thing that tells the CLR not to move the 'byte[] data' object around in memory. // As there may be a race condition if the location moves during the Write() Win32 call. if (_deviceWriteMode == DeviceMode.Overlapped) { var security = new NativeMethods.SECURITY_ATTRIBUTES(); var overlapped = new NativeOverlapped(); var overlapTimeout = timeout <= 0 ? NativeMethods.WAIT_INFINITE : timeout; security.lpSecurityDescriptor = IntPtr.Zero; security.bInheritHandle = true; security.nLength = Marshal.SizeOf(security); overlapped.OffsetLow = 0; overlapped.OffsetHigh = 0; overlapped.EventHandle = NativeMethods.CreateEvent(ref security, Convert.ToInt32(false), Convert.ToInt32(true), ""); try { NativeMethods.WriteFile(Handle, buffer, (uint)buffer.Length, out bytesWritten, ref overlapped); } catch { return(false); } var result = NativeMethods.WaitForSingleObject(overlapped.EventHandle, overlapTimeout); switch (result) { case NativeMethods.WAIT_OBJECT_0: NativeMethods.CloseHandle(overlapped.EventHandle); return(true); case NativeMethods.WAIT_TIMEOUT: return(false); case NativeMethods.WAIT_FAILED: return(false); default: return(false); } } else { try { var overlapped = new NativeOverlapped(); return(NativeMethods.WriteFile(Handle, buffer, (uint)buffer.Length, out bytesWritten, ref overlapped)); } catch { return(false); } } }
protected HidDeviceData ReadData(int timeout) { var buffer = new byte[] { }; var status = HidDeviceData.ReadStatus.NoDataRead; IntPtr nonManagedBuffer; if (_deviceCapabilities.InputReportByteLength > 0) { uint bytesRead = 0; buffer = CreateInputBuffer(); nonManagedBuffer = Marshal.AllocHGlobal(buffer.Length); if (_deviceReadMode == DeviceMode.Overlapped) { var security = new NativeMethods.SECURITY_ATTRIBUTES(); var overlapped = new NativeOverlapped(); var overlapTimeout = timeout <= 0 ? NativeMethods.WAIT_INFINITE : timeout; security.lpSecurityDescriptor = IntPtr.Zero; security.bInheritHandle = true; security.nLength = Marshal.SizeOf(security); overlapped.OffsetLow = 0; overlapped.OffsetHigh = 0; overlapped.EventHandle = NativeMethods.CreateEvent(ref security, Convert.ToInt32(false), Convert.ToInt32(true), string.Empty); try { var success = NativeMethods.ReadFile(Handle, nonManagedBuffer, (uint)buffer.Length, out bytesRead, ref overlapped); if (success) { status = HidDeviceData.ReadStatus.Success; // No check here to see if bytesRead > 0 . Perhaps not necessary? } else { var result = NativeMethods.WaitForSingleObject(overlapped.EventHandle, overlapTimeout); switch (result) { case NativeMethods.WAIT_OBJECT_0: status = HidDeviceData.ReadStatus.Success; NativeMethods.GetOverlappedResult(Handle, ref overlapped, out bytesRead, false); break; case NativeMethods.WAIT_TIMEOUT: status = HidDeviceData.ReadStatus.WaitTimedOut; buffer = new byte[] { }; break; case NativeMethods.WAIT_FAILED: status = HidDeviceData.ReadStatus.WaitFail; buffer = new byte[] { }; break; default: status = HidDeviceData.ReadStatus.NoDataRead; buffer = new byte[] { }; break; } } Marshal.Copy(nonManagedBuffer, buffer, 0, (int)bytesRead); } catch { status = HidDeviceData.ReadStatus.ReadError; } finally { CloseDeviceIO(overlapped.EventHandle); Marshal.FreeHGlobal(nonManagedBuffer); } } else { try { var overlapped = new NativeOverlapped(); NativeMethods.ReadFile(Handle, nonManagedBuffer, (uint)buffer.Length, out bytesRead, ref overlapped); status = HidDeviceData.ReadStatus.Success; Marshal.Copy(nonManagedBuffer, buffer, 0, (int)bytesRead); } catch { status = HidDeviceData.ReadStatus.ReadError; } finally { Marshal.FreeHGlobal(nonManagedBuffer); } } } return(new HidDeviceData(buffer, status)); }
internal unsafe void Callback(uint errorCode, uint numBytes, NativeOverlapped* _overlapped) { try { this._event.Set(); } finally { Overlapped.Free(_overlapped); } }
public static bool UnsafeQueueNativeOverlapped(NativeOverlapped* overlapped) { }
public static unsafe Overlapped Unpack (NativeOverlapped *nativeOverlappedPtr) { if(((IntPtr)nativeOverlappedPtr) == IntPtr.Zero) { throw new ArgumentNullException("nativeOverlappedPtr"); } return new Overlapped(nativeOverlappedPtr->OffsetLow, nativeOverlappedPtr->OffsetHigh, nativeOverlappedPtr->EventHandle, null); }
internal unsafe static extern uint HttpWaitForDisconnect(SafeHandle requestQueueHandle, ulong connectionId, NativeOverlapped* pOverlapped);
private static extern int GetOverlappedResult(SafeHandle handle, ref NativeOverlapped overlapped, out int numBytesWritten, int wait);
public void Run() { IntPtr hPipe = IntPtr.Zero; IntPtr hEventCmdWait = IntPtr.Zero; IntPtr hEventConnect = IntPtr.Zero; IntPtr[] hEventArray = new IntPtr[2]; NativeOverlapped stOver = new NativeOverlapped(); if (m_iCtrlCmdEventID != -1) { string strCmdEvent; strCmdEvent = CMD_CTRL_EVENT_WAIT + m_iCtrlCmdEventID.ToString(); hEventCmdWait = CommonUtil._CreateEvent(false, true, strCmdEvent); } hEventConnect = CommonUtil._CreateEvent(false, false, m_strEventName); hEventArray[0] = m_hStopEvent; hEventArray[1] = CommonUtil._CreateEvent(false, false, null); while (true) { if (hPipe == IntPtr.Zero) { while (true) { hPipe = CommonUtil._CreateNamedPipe(m_strPipeName, CommonUtil.PIPE_ACCESS_DUPLEX | CommonUtil.FILE_FLAG_WRITE_THROUGH | CommonUtil.FILE_FLAG_OVERLAPPED, CommonUtil.PIPE_TYPE_BYTE, 1, SEND_BUFF_SIZE, RES_BUFF_SIZE, PIPE_TIMEOUT); if (Marshal.GetLastWin32Error() == CommonUtil.ERROR_PIPE_BUSY) { Thread.Sleep(100); } else { if (hPipe == IntPtr.Zero) { hPipe = IntPtr.Zero; } break; } } stOver.EventHandle = hEventArray[1]; CommonUtil._ConnectNamedPipe(hPipe, ref stOver); CommonUtil._SetEvent(hEventConnect); } uint uiRes = CommonUtil._WaitForMultipleObjects(2, hEventArray, false, CommonUtil.INFINITE); if (uiRes == CommonUtil.WAIT_OBJECT_0) { //STOP break; } else if (uiRes == CommonUtil.WAIT_OBJECT_0 + 1) { //ほかのサーバーで処理中? if (hEventCmdWait != IntPtr.Zero) { CommonUtil._WaitForSingleObject(hEventCmdWait, CommonUtil.INFINITE); } //コマンド受信 if (m_pCmdProc != null) { CMD_STREAM stCmd = new CMD_STREAM(); CMD_STREAM stRes = new CMD_STREAM(); uint dwRead = 0; uint dwWrite = 0; do { byte[] bHead = new byte[8]; Array.Copy(BitConverter.GetBytes(stCmd.uiParam), 0, bHead, 0, sizeof(uint)); Array.Copy(BitConverter.GetBytes(stCmd.uiSize), 0, bHead, 4, sizeof(uint)); if (CommonUtil._ReadFile(hPipe, ref bHead, sizeof(uint) * 2, out dwRead, IntPtr.Zero) == false) { break; } stCmd.uiParam = BitConverter.ToUInt32(bHead, 0); stCmd.uiSize = BitConverter.ToUInt32(bHead, 4); if (stCmd.uiSize > 0) { stCmd.bData = new byte[stCmd.uiSize]; uint dwReadNum = 0; while (dwReadNum < stCmd.uiSize) { uint dwReadSize = 0; if (stCmd.uiSize - dwReadNum < SEND_BUFF_SIZE) { dwReadSize = stCmd.uiSize - dwReadNum; } else { dwReadSize = SEND_BUFF_SIZE; } byte[] bRead = new byte[dwReadSize]; if (CommonUtil._ReadFile(hPipe, ref bRead, dwReadSize, out dwRead, IntPtr.Zero) == false) { break; } Array.Copy(bRead, dwReadNum, stCmd.bData, 0, dwRead); dwReadNum += dwRead; } if (dwReadNum < stCmd.uiSize) { break; } } m_pCmdProc.Invoke(m_pParam, stCmd, ref stRes); if (stRes.uiParam == (uint)ErrCode.CMD_NO_RES) { break; } Array.Copy(BitConverter.GetBytes(stRes.uiParam), 0, bHead, 0, sizeof(uint)); Array.Copy(BitConverter.GetBytes(stRes.uiSize), 0, bHead, 4, sizeof(uint)); if (CommonUtil._WriteFile(hPipe, ref bHead, sizeof(uint) * 2, out dwWrite, IntPtr.Zero) == false) { break; } if (stRes.uiSize > 0) { if (stRes.bData == null) { break; } if (CommonUtil._WriteFile(hPipe, ref stRes.bData, stRes.uiSize, out dwWrite, IntPtr.Zero) == false) { break; } } } while (stRes.uiParam == (uint)ErrCode.CMD_NEXT); //Emun用の繰り返し } CommonUtil._FlushFileBuffers(hPipe); CommonUtil._DisconnectNamedPipe(hPipe); CommonUtil._CloseHandle(hPipe); hPipe = IntPtr.Zero; if (hEventCmdWait != IntPtr.Zero) { CommonUtil._SetEvent(hEventCmdWait); } } } if (hPipe != IntPtr.Zero) { CommonUtil._FlushFileBuffers(hPipe); CommonUtil._DisconnectNamedPipe(hPipe); CommonUtil._CloseHandle(hPipe); } CommonUtil._CloseHandle(hEventArray[1]); CommonUtil._CloseHandle(hEventConnect); if (hEventCmdWait != IntPtr.Zero) { CommonUtil._CloseHandle(hEventCmdWait); } }
public static Overlapped Unpack(NativeOverlapped* nativeOverlappedPtr) {}
public static void Free(NativeOverlapped* nativeOverlappedPtr) {}
public Overlapped() { WaitEvent = new ManualResetEvent(false); OverlappedStructShadow = new NativeOverlapped(); OverlappedStructShadow.Event = WaitEvent.SafeWaitHandle.DangerousGetHandle(); OverlappedStruct = Marshal.AllocHGlobal(Marshal.SizeOf(OverlappedStructShadow)); Marshal.StructureToPtr(OverlappedStructShadow, OverlappedStruct, false); }
public extern static bool WinUsb_WritePipe(IntPtr interfaceHandle, byte pipeId, [In] byte[] buffer, uint bufferLength, IntPtr lengthTransferred, ref NativeOverlapped overlapped);
// // Callback called from the ThreadPool executing on a IOCP thread. // private static unsafe void AsyncFSCallback(uint errorCode, uint bytesTransferred, NativeOverlapped* overlapped) { // // Get the underlying AsyncResult object. // // Console.WriteLine("IOCP callback: {0}, {1}", errorCode, bytesTransferred); SimpleFileStreamAsyncResult fsar = (SimpleFileStreamAsyncResult)Overlapped.Unpack(overlapped).AsyncResult; // // Free the native overlapped structure. // Overlapped.Free(overlapped); // // Do the I/O completion processing. // fsar.OnComplete((int)bytesTransferred, errorCode != 0 ? GetIOException((int)errorCode) : null); }
internal static extern bool WriteFile(SafeFileHandle hFile, byte[] lpBuffer, uint nNumberOfBytesToWrite, out uint lpNumberOfBytesWritten, [In] ref NativeOverlapped lpOverlapped);
private static extern bool WriteFile(SafeFileHandle hFile, byte[] lpBuffer, int nNumberOfBytesToWrite, out int lpNumberOfBytesWritten, ref NativeOverlapped lpOverlapped);
internal static extern bool CancelIoEx(SafeFileHandle hFile, ref NativeOverlapped lpOverlapped);
private static extern bool WriteFileEx(SafeFileHandle hFile, byte[] lpBuffer, int nNumberOfBytesToWrite, ref NativeOverlapped lpOverlapped, FileIOCompletionRoutine lpCompletionRoutine);
public unsafe void FreeNativeOverlapped(NativeOverlapped* overlapped);
public int ReadRegion(string path, MemoryRegion region, Action <int, int> progress) { SafeFileHandle asyncWriteHandle = CreateFile(path, Win32HardwareIOSupport.GENERIC_WRITE | Win32HardwareIOSupport.GENERIC_READ, Win32HardwareIOSupport.FILE_SHARE_WRITE | Win32HardwareIOSupport.FILE_SHARE_READ, IntPtr.Zero, Win32HardwareIOSupport.OPEN_EXISTING, Win32HardwareIOSupport.FILE_FLAG_OVERLAPPED | Win32HardwareIOSupport.FILE_FLAG_NO_BUFFERING, IntPtr.Zero); if (asyncWriteHandle.IsInvalid) { Marshal.ThrowExceptionForHR(Marshal.GetHRForLastWin32Error()); } SafeFileHandle asyncReadHandle = CreateFile(path, Win32HardwareIOSupport.GENERIC_READ | Win32HardwareIOSupport.GENERIC_WRITE, Win32HardwareIOSupport.FILE_SHARE_WRITE | Win32HardwareIOSupport.FILE_SHARE_READ, IntPtr.Zero, Win32HardwareIOSupport.OPEN_EXISTING, Win32HardwareIOSupport.FILE_FLAG_OVERLAPPED | Win32HardwareIOSupport.FILE_FLAG_NO_BUFFERING, IntPtr.Zero); if (asyncReadHandle.IsInvalid) { Marshal.ThrowExceptionForHR(Marshal.GetHRForLastWin32Error()); } int currentPacketLength = 0; uint trBytes; int pendingPackets = 0; int noRequestedBytes = (int)region.Size; int noReadedBytes = (int)region.Size; uint currentAddress = region.Address; byte lastError = 0; EventWaitHandle hWrite1Event = new EventWaitHandle(false, EventResetMode.AutoReset); EventWaitHandle hWrite2Event = new EventWaitHandle(false, EventResetMode.AutoReset); EventWaitHandle hReadEvent = new EventWaitHandle(false, EventResetMode.AutoReset); NativeOverlapped write1Over = new NativeOverlapped(); write1Over.OffsetHigh = 0; write1Over.OffsetLow = 0; write1Over.EventHandle = hWrite1Event.SafeWaitHandle.DangerousGetHandle(); NativeOverlapped write2Over = new NativeOverlapped(); write2Over.OffsetHigh = 0; write2Over.OffsetLow = 0; write2Over.EventHandle = hWrite2Event.SafeWaitHandle.DangerousGetHandle(); NativeOverlapped readOver = new NativeOverlapped(); readOver.OffsetHigh = 0; readOver.OffsetLow = 0; readOver.EventHandle = hReadEvent.SafeWaitHandle.DangerousGetHandle(); MemSafeHandle pWrite1 = new MemSafeHandle(Marshal.AllocHGlobal(65)); MemSafeHandle pWrite2 = new MemSafeHandle(Marshal.AllocHGlobal(65)); MemSafeHandle pRead = new MemSafeHandle(Marshal.AllocHGlobal(65)); currentPacketLength = (int)_bytesPerPacket < noRequestedBytes ? (int)_bytesPerPacket : noRequestedBytes; ArrayToMem(GetDataReq.getCommandPacket(currentAddress, (byte)currentPacketLength), pWrite1); if (!WriteFile(asyncWriteHandle, pWrite1.DangerousGetHandle(), 65, out trBytes, ref write1Over)) { if (Marshal.GetLastWin32Error() != Win32HardwareIOSupport.ERROR_IO_PENDING) { Marshal.ThrowExceptionForHR(Marshal.GetHRForLastWin32Error()); } } else { hWrite1Event.Set(); } pendingPackets++; noRequestedBytes -= currentPacketLength; currentAddress += (uint)currentPacketLength; if (noRequestedBytes > 0) { currentPacketLength = (int)_bytesPerPacket < noRequestedBytes ? (int)_bytesPerPacket : noRequestedBytes; ArrayToMem(GetDataReq.getCommandPacket(currentAddress, (byte)currentPacketLength), pWrite2); if (!WriteFile(asyncWriteHandle, pWrite2.DangerousGetHandle(), 65, out trBytes, ref write2Over)) { if (Marshal.GetLastWin32Error() != Win32HardwareIOSupport.ERROR_IO_PENDING) { Marshal.ThrowExceptionForHR(Marshal.GetHRForLastWin32Error()); } } else { hWrite2Event.Set(); } pendingPackets++; noRequestedBytes -= currentPacketLength; currentAddress += (uint)currentPacketLength; } byte[] rawdata = new byte[65]; if (!ReadFile(asyncReadHandle, pRead.DangerousGetHandle(), 65, out trBytes, ref readOver)) { if (Marshal.GetLastWin32Error() != Win32HardwareIOSupport.ERROR_IO_PENDING) { Marshal.ThrowExceptionForHR(Marshal.GetHRForLastWin32Error()); } } else { hReadEvent.Set(); } while (noReadedBytes > 0) { if (WaitHandle.WaitAny(new WaitHandle[] { hWrite1Event, hWrite2Event, hReadEvent }, 10000) == WaitHandle.WaitTimeout) { throw new Exception("Hardware doesn't answer. Read time out. no readed bytes:" + noReadedBytes.ToString() + " pending packets:" + pendingPackets.ToString() + " no requested bytes:" + noRequestedBytes.ToString() + " current addr:" + currentAddress.ToString()); } if ((write1Over.InternalLow.ToInt32() != 0x103) && (pendingPackets < 10) && (noRequestedBytes > 0)) { write1Over.OffsetHigh = 0; write1Over.OffsetLow = 0; write1Over.InternalLow = IntPtr.Zero; write1Over.InternalHigh = IntPtr.Zero; currentPacketLength = (int)_bytesPerPacket < noRequestedBytes ? (int)_bytesPerPacket : noRequestedBytes; ArrayToMem(GetDataReq.getCommandPacket(currentAddress, (byte)currentPacketLength), pWrite1); if (!WriteFile(asyncWriteHandle, pWrite1.DangerousGetHandle(), 65, out trBytes, ref write1Over)) { if (Marshal.GetLastWin32Error() != Win32HardwareIOSupport.ERROR_IO_PENDING) { Marshal.ThrowExceptionForHR(Marshal.GetHRForLastWin32Error()); } } else { hWrite1Event.Set(); } pendingPackets++; noRequestedBytes -= currentPacketLength; currentAddress += (uint)currentPacketLength; } if ((write2Over.InternalLow.ToInt32() != 0x103) && (pendingPackets < 10) && (noRequestedBytes > 0)) { write2Over.OffsetHigh = 0; write2Over.OffsetLow = 0; write2Over.InternalLow = IntPtr.Zero; write2Over.InternalHigh = IntPtr.Zero; currentPacketLength = (int)_bytesPerPacket < noRequestedBytes ? (int)_bytesPerPacket : noRequestedBytes; ArrayToMem(GetDataReq.getCommandPacket(currentAddress, (byte)currentPacketLength), pWrite2); if (!WriteFile(asyncWriteHandle, pWrite2.DangerousGetHandle(), 65, out trBytes, ref write2Over)) { if (Marshal.GetLastWin32Error() != Win32HardwareIOSupport.ERROR_IO_PENDING) { Marshal.ThrowExceptionForHR(Marshal.GetHRForLastWin32Error()); } } else { hWrite2Event.Set(); } pendingPackets++; noRequestedBytes -= currentPacketLength; currentAddress += (uint)currentPacketLength; } if ((readOver.InternalLow.ToInt32() != 0x103)) { MemToArray(pRead, rawdata); progress((int)(region.Size - noReadedBytes), (int)region.Size); if (pendingPackets > 0) { readOver.OffsetHigh = 0; readOver.OffsetLow = 0; readOver.InternalLow = IntPtr.Zero; readOver.InternalHigh = IntPtr.Zero; if (!ReadFile(asyncReadHandle, pRead.DangerousGetHandle(), 65, out trBytes, ref readOver)) { if (Marshal.GetLastWin32Error() != Win32HardwareIOSupport.ERROR_IO_PENDING) { Marshal.ThrowExceptionForHR(Marshal.GetHRForLastWin32Error()); } } else { hReadEvent.Set(); } } } } asyncWriteHandle.Close(); asyncReadHandle.Close(); if (lastError != 0) { string error = null; try { } catch (KeyNotFoundException) { error = "Unknown hardware error: " + lastError.ToString(); } throw new Exception(error); } return(0); }
internal unsafe static extern uint HttpReceiveHttpRequest(SafeHandle requestQueueHandle, ulong requestId, uint flags, HTTP_REQUEST* pRequestBuffer, uint requestBufferLength, uint* pBytesReturned, NativeOverlapped* pOverlapped);
unsafe internal static extern int ReadFile(SafeFileHandle handle, byte* bytes, int numBytesToRead, IntPtr numBytesRead_mustBeZero, NativeOverlapped* overlapped);
internal unsafe static extern uint HttpSendResponseEntityBody(SafeHandle requestQueueHandle, ulong requestId, uint flags, ushort entityChunkCount, HTTP_DATA_CHUNK* pEntityChunks, uint* pBytesSent, SafeLocalAllocHandle pRequestBuffer, uint requestBufferLength, NativeOverlapped* pOverlapped, void* pLogData);
internal static extern unsafe bool CancelIoEx(SafeHandle handle, NativeOverlapped* lpOverlapped);
public WinSerialStream(string port_name, int baud_rate, int data_bits, Parity parity, StopBits sb, bool dtr_enable, bool rts_enable, Handshake hs, int read_timeout, int write_timeout, int read_buffer_size, int write_buffer_size) { handle = CreateFile(port_name, GenericRead | GenericWrite, 0, 0, OpenExisting, FileFlagOverlapped, 0); if (handle == -1) { ReportIOError(port_name); } // Set port low level attributes SetAttributes(baud_rate, parity, data_bits, sb, hs); // Clean buffers and set sizes if (!PurgeComm(handle, PurgeRxClear | PurgeTxClear) || !SetupComm(handle, read_buffer_size, write_buffer_size)) { ReportIOError(null); } // Set timeouts this.read_timeout = read_timeout; this.write_timeout = write_timeout; timeouts = new Timeouts(read_timeout, write_timeout); if (!SetCommTimeouts(handle, timeouts)) { ReportIOError(null); } /// Set DTR and RTS SetSignal(SerialSignal.Dtr, dtr_enable); if (hs != Handshake.RequestToSend && hs != Handshake.RequestToSendXOnXOff) { SetSignal(SerialSignal.Rts, rts_enable); } // Init overlapped structures NativeOverlapped wo = new NativeOverlapped(); write_event = new ManualResetEvent(false); #if NET_2_0 wo.EventHandle = write_event.Handle; #else wo.EventHandle = (int)write_event.Handle; #endif write_overlapped = Marshal.AllocHGlobal(Marshal.SizeOf(typeof(NativeOverlapped))); Marshal.StructureToPtr(wo, write_overlapped, true); NativeOverlapped ro = new NativeOverlapped(); read_event = new ManualResetEvent(false); #if NET_2_0 ro.EventHandle = read_event.Handle; #else ro.EventHandle = (int)read_event.Handle; #endif read_overlapped = Marshal.AllocHGlobal(Marshal.SizeOf(typeof(NativeOverlapped))); Marshal.StructureToPtr(ro, read_overlapped, true); }
// // Read file native // private unsafe int ReadFileNative(byte[] buffer, int offset, int count, NativeOverlapped* overlapped, out int errorCode) { errorCode = 0; int result; int bytesRead = 0; fixed (byte* bufferStart = buffer) { result = (_isAsync) ? Win32Native.ReadFile(_handle, bufferStart + offset, count, IntPtr.Zero, overlapped) : Win32Native.ReadFile(_handle, bufferStart + offset, count, out bytesRead, IntPtr.Zero); } if (result == 0) { errorCode = Marshal.GetLastWin32Error(); return -1; } return bytesRead; }
public virtual int SharedLockFile( sqlite3_file pFile, long offset, long length ) { #if !(SQLITE_SILVERLIGHT || WINDOWS_MOBILE) Debug.Assert( length == SHARED_SIZE ); Debug.Assert( offset == SHARED_FIRST ); NativeOverlapped ovlp = new NativeOverlapped(); ovlp.OffsetLow = (int)offset; ovlp.OffsetHigh = 0; ovlp.EventHandle = IntPtr.Zero; return LockFileEx( pFile.fs.Handle, LOCKFILE_FAIL_IMMEDIATELY, 0, (uint)length, 0, ref ovlp ) ? 1 : 0; #else return 1; #endif }
public static extern bool GetOverlappedResult(IntPtr hFile, ref NativeOverlapped lpOverlapped, ref uint lpNumberOfBytesTransferred, [MarshalAs(UnmanagedType.Bool)] bool bWait);
private unsafe void RunDiversion() { var packet = new WinDivertBuffer(); var addr = new WinDivertAddress(); uint recvLength = 0; NativeOverlapped recvOverlapped; IntPtr recvEvent = IntPtr.Zero; recvEvent = WinDivertSharp.WinAPI.Kernel32.CreateEvent(IntPtr.Zero, false, false, IntPtr.Zero); if (recvEvent == IntPtr.Zero || recvEvent == new IntPtr(-1)) { LoggerProxy.Default.Error("Failed to initialize receive IO event."); return; } uint recvAsyncIoLen = 0; bool isLocalIpv4 = false; bool modifiedPacket = false; bool dropPacket = false; Span <byte> payloadBufferPtr = null; while (m_running) { try { payloadBufferPtr = null; recvLength = 0; addr.Reset(); modifiedPacket = false; dropPacket = false; isLocalIpv4 = false; recvAsyncIoLen = 0; recvOverlapped = new NativeOverlapped(); WinAPI.Kernel32.ResetEvent(recvEvent); recvOverlapped.EventHandle = recvEvent; #region Packet Reading Code if (!WinDivert.WinDivertRecvEx(m_diversionHandle, packet, 0, ref addr, ref recvLength, ref recvOverlapped)) { var error = Marshal.GetLastWin32Error(); // 997 == ERROR_IO_PENDING if (error != 997) { LoggerProxy.Default.Warn(string.Format("Unknown IO error ID {0}while awaiting overlapped result.", error)); continue; } // 258 == WAIT_TIMEOUT while (m_running && WinDivertSharp.WinAPI.Kernel32.WaitForSingleObject(recvEvent, 1000) == (uint)WaitForSingleObjectResult.WaitTimeout) { } if (!WinDivertSharp.WinAPI.Kernel32.GetOverlappedResult(m_diversionHandle, ref recvOverlapped, ref recvAsyncIoLen, false)) { LoggerProxy.Default.Warn("Failed to get overlapped result."); continue; } recvLength = recvAsyncIoLen; } #endregion Packet Reading Code if (addr.Direction == WinDivertDirection.Outbound) { var parseResult = WinDivert.WinDivertHelperParsePacket(packet, recvLength); #region New TCP Connection Detection if (parseResult.TcpHeader != null && parseResult.TcpHeader->Syn > 0) { // Brand new outbound connection. Grab the PID of the process holding this // port and map it. if (parseResult.IPv4Header != null) { var connInfo = GetLocalPacketInfo(parseResult.TcpHeader->SrcPort, parseResult.IPv4Header->SrcAddr); HandleNewTcpConnection(connInfo, parseResult.TcpHeader, false); // Handle the special case of entirely blocking internet for this application/port. if (Volatile.Read(ref m_v4ShouldFilter[parseResult.TcpHeader->SrcPort]) == (int)FirewallAction.BlockInternetForApplication) { dropPacket = true; } } if (parseResult.IPv6Header != null) { var connInfo = GetLocalPacketInfo(parseResult.TcpHeader->SrcPort, parseResult.IPv6Header->SrcAddr); HandleNewTcpConnection(connInfo, parseResult.TcpHeader, true); // Handle the special case of entirely blocking internet for this application/port. if (Volatile.Read(ref m_v6ShouldFilter[parseResult.TcpHeader->SrcPort]) == (int)FirewallAction.BlockInternetForApplication) { dropPacket = true; } } } // Now that we've processed any potentially new connections, let's see if the // packet belongs to an existing flow that was marked to be blocked. // Check if this packet belongs to an IPV4 flow marked for blocking. if (parseResult.IPv4Header != null) { // Handle the special case of entirely blocking internet for this application/port. if (Volatile.Read(ref m_v4ShouldFilter[parseResult.TcpHeader->SrcPort]) == (int)FirewallAction.BlockInternetForApplication) { dropPacket = true; } } // Check if this packet belongs to an IPV6 flow marked for blocking. if (!dropPacket && parseResult.IPv6Header != null) { // Handle the special case of entirely blocking internet for this application/port. if (Volatile.Read(ref m_v6ShouldFilter[parseResult.TcpHeader->SrcPort]) == (int)FirewallAction.BlockInternetForApplication) { dropPacket = true; } } #endregion New TCP Connection Detection // I put the checks for ipv4 and ipv6 as a double if statement rather than an // else if because I'm not sure how that would affect dual-mode sockets. Perhaps // it's possible for both headers to be defined. Probably not, but since I don't // know, I err on the side of awesome, or uhh, something like that. // We check local packets for TOR/SOCKS packets here. However, if we don't find // something we want to block on local addresses, then we want to skip these for // the rest of the filtering and just let them through. if (dropPacket == false && parseResult.IPv4Header != null && parseResult.TcpHeader != null) { // Let's explain the weird arcane logic here. First, we check if the current // flow should even be filtered. We do this, because there's a good chance // that this flow belongs to our proxy's connections, which we never want to // filter. If we didn't check this, then we would end up setting the // isLocalIpv4 flag to true on every single one of our proxy's connections, // and clients would never get packets ever because with that flag set, the // direction of the packets wouldn't be sorted. // // So, we check this, ensure it's actually something we want to filter. Then, // we check if the packet is destined for a local address. We set the flag // accordingly, and if true, then we will allow these packets to go out uninterrupted. // // If false, who cares. Regardless of true or false, we check to see if this // is a TOR/SOCKS4/5 proxy CONNECT, and drop it if it is. // // Also note, by letting local/private address destined packets go, we also // solve the problem of private TLS connections using private TLS self signed // certs, such as logging into one's router. If we didn't do this check and // let these through, we would break such connections. if (Volatile.Read(ref m_v4ShouldFilter[parseResult.TcpHeader->SrcPort]) == (int)FirewallAction.FilterApplication) { isLocalIpv4 = parseResult.IPv4Header->DstAddr.IsPrivateIpv4Address(); if (isLocalIpv4) { #if !ENGINE_NO_BLOCK_TOR byte[] payload = null; if (payloadBufferPtr != null && payloadBufferPtr.Length > 0) { payload = payloadBufferPtr.ToArray(); if (payload.IsSocksProxyConnect()) { LoggerProxy.Default.Info("Blocking SOCKS proxy connect."); continue; } } #endif } } } if (dropPacket == false && !isLocalIpv4) { if (parseResult.IPv4Header != null && parseResult.TcpHeader != null) { if (parseResult.TcpHeader->SrcPort == m_v4HttpProxyPort || parseResult.TcpHeader->SrcPort == m_v4HttpsProxyPort) { // Means that the data is originating from our proxy in response to a // client's request, which means it was originally meant to go // somewhere else. We need to reorder the data such as the src and // destination ports and addresses and divert it back inbound, so it // appears to be an inbound response from the original external server. modifiedPacket = true; parseResult.TcpHeader->SrcPort = Volatile.Read(ref m_v4ReturnPorts[parseResult.TcpHeader->DstPort]); addr.Direction = WinDivertDirection.Inbound; var dstIp = parseResult.IPv4Header->DstAddr; parseResult.IPv4Header->DstAddr = parseResult.IPv4Header->SrcAddr; parseResult.IPv4Header->SrcAddr = dstIp; } else { // This means outbound traffic has been captured that we know for // sure is not coming from our proxy in response to a client, but we // don't know that it isn't the upstream portion of our proxy trying // to fetch a response on behalf of a connected client. So, we need // to check if we have a cached result for information about the // binary generating the outbound traffic for two reasons. // // First, we need to ensure that it's not us, obviously. Secondly, we // need to ensure that the binary has been granted firewall access to // generate outbound traffic. if (Volatile.Read(ref m_v4ShouldFilter[parseResult.TcpHeader->SrcPort]) == (int)FirewallAction.FilterApplication) { modifiedPacket = true; // If the process was identified as a process that is permitted // to access the internet, and is not a system process or // ourselves, then we divert its packets back inbound to the // local machine, changing the destination port appropriately. var dstAddress = parseResult.IPv4Header->DstAddr; parseResult.IPv4Header->DstAddr = parseResult.IPv4Header->SrcAddr; parseResult.IPv4Header->SrcAddr = dstAddress; addr.Direction = WinDivertDirection.Inbound; Volatile.Write(ref m_v4ReturnPorts[parseResult.TcpHeader->SrcPort], parseResult.TcpHeader->DstPort); // Unless we know for sure this is an encrypted connection via // the HTTP port, we should always default to sending to the // non-encrypted listener. var encrypted = Volatile.Read(ref m_v4EncryptionHints[parseResult.TcpHeader->SrcPort]); parseResult.TcpHeader->DstPort = encrypted ? m_v4HttpsProxyPort : m_v4HttpProxyPort; } } } // The ipV6 version works exactly the same, just with larger storage for the // larger addresses. Look at the ipv4 version notes for clarification on anything. if (parseResult.IPv6Header != null && parseResult.TcpHeader != null) { if (parseResult.TcpHeader->SrcPort == m_v6HttpProxyPort || parseResult.TcpHeader->SrcPort == m_v6HttpsProxyPort) { modifiedPacket = true; parseResult.TcpHeader->SrcPort = Volatile.Read(ref m_v6ReturnPorts[parseResult.TcpHeader->DstPort]); addr.Direction = WinDivertDirection.Inbound; var dstIp = parseResult.IPv6Header->DstAddr; parseResult.IPv6Header->DstAddr = parseResult.IPv6Header->SrcAddr; parseResult.IPv6Header->SrcAddr = dstIp; } else { if (Volatile.Read(ref m_v6ShouldFilter[parseResult.TcpHeader->SrcPort]) == (int)FirewallAction.FilterApplication) { modifiedPacket = true; // If the process was identified as a process that is permitted // to access the internet, and is not a system process or // ourselves, then we divert its packets back inbound to the // local machine, changing the destination port appropriately. var dstAddress = parseResult.IPv6Header->DstAddr; parseResult.IPv6Header->DstAddr = parseResult.IPv6Header->SrcAddr; parseResult.IPv6Header->SrcAddr = dstAddress; addr.Direction = WinDivertDirection.Inbound; Volatile.Write(ref m_v6ReturnPorts[parseResult.TcpHeader->SrcPort], parseResult.TcpHeader->DstPort); // Unless we know for sure this is an encrypted connection via // the HTTP port, we should always default to sending to the // non-encrypted listener. var encrypted = Volatile.Read(ref m_v6EncryptionHints[parseResult.TcpHeader->SrcPort]); parseResult.TcpHeader->DstPort = encrypted ? m_v6HttpsProxyPort : m_v6HttpProxyPort; } } } } // if(!isLocalIpv4) } // if (addr.Direction == WINDIVERT_DIRECTION_OUTBOUND) if (!dropPacket) { if (modifiedPacket) { var sumsCalculated = WinDivert.WinDivertHelperCalcChecksums(packet, recvLength, ref addr, WinDivertChecksumHelperParam.All); if (sumsCalculated <= 0) { LoggerProxy.Default.Warn("Modified packet reported that no checksums were calculated"); } } WinDivert.WinDivertSendEx(m_diversionHandle, packet, recvLength, 0, ref addr); } } catch (Exception loopException) { LoggerProxy.Default.Error(loopException); } } // while (m_running) }
public static extern bool WinDivertRecvEx([In] IntPtr handle, byte[] pPacket, uint packetLen, ulong flags, ref WINDIVERT_ADDRESS pAddr, ref uint readLen, ref NativeOverlapped lpOverlapped);
public static async Task CompactVHD(string loc, CancellationToken cancellationToken, IProgress <Tuple <int, string> > progress) { var vhdCompactOverlapEvent = new ManualResetEvent(false); var vhdCompactOverlap = new NativeOverlapped { EventHandle = vhdCompactOverlapEvent.SafeWaitHandle.DangerousGetHandle() }; // Perform file-system-aware compaction var stType = VIRTUAL_STORAGE_TYPE.VHD; var param = OPEN_VIRTUAL_DISK_PARAMETERS.DefaultV2; var err = OpenVirtualDisk(stType, loc, VIRTUAL_DISK_ACCESS_MASK.VIRTUAL_DISK_ACCESS_NONE, OPEN_VIRTUAL_DISK_FLAG.OPEN_VIRTUAL_DISK_FLAG_NONE, param, out var hVhd); err.ThrowIfFailed(); if (!ConvertStringSecurityDescriptorToSecurityDescriptor("O:BAG:BAD:(A;;GA;;;WD)", SDDL_REVISION.SDDL_REVISION_1, out var sd, out var hLen)) { Win32Error.ThrowLastError(); } var aParam = ATTACH_VIRTUAL_DISK_PARAMETERS.Default; err = AttachVirtualDisk(hVhd, (IntPtr)sd, ATTACH_VIRTUAL_DISK_FLAG.ATTACH_VIRTUAL_DISK_FLAG_PERMANENT_LIFETIME | ATTACH_VIRTUAL_DISK_FLAG.ATTACH_VIRTUAL_DISK_FLAG_READ_ONLY, 0, aParam, IntPtr.Zero); err.ThrowIfFailed(); var cParam = COMPACT_VIRTUAL_DISK_PARAMETERS.Default; err = CompactVirtualDisk(hVhd, COMPACT_VIRTUAL_DISK_FLAG.COMPACT_VIRTUAL_DISK_FLAG_NONE, cParam, ref vhdCompactOverlap); if (err != Win32Error.ERROR_IO_PENDING) { err.ThrowIfFailed(); } // Loop getting status var taskComplete = await GetProgress(hVhd, 1); // Cleanup first op err = DetachVirtualDisk(hVhd, DETACH_VIRTUAL_DISK_FLAG.DETACH_VIRTUAL_DISK_FLAG_NONE, 0); err.ThrowIfFailed(); hVhd.Dispose(); // If first op fails, don't bother with the second if (!taskComplete) { return; } // Perform file-system-agnostic compaction vhdCompactOverlapEvent.Reset(); err = OpenVirtualDisk(stType, loc, VIRTUAL_DISK_ACCESS_MASK.VIRTUAL_DISK_ACCESS_NONE, OPEN_VIRTUAL_DISK_FLAG.OPEN_VIRTUAL_DISK_FLAG_NONE, param, out hVhd); err.ThrowIfFailed(); err = CompactVirtualDisk(hVhd, COMPACT_VIRTUAL_DISK_FLAG.COMPACT_VIRTUAL_DISK_FLAG_NONE, cParam, ref vhdCompactOverlap); if (err != Win32Error.ERROR_IO_PENDING) { err.ThrowIfFailed(); } // Loop getting status await GetProgress(hVhd, 2); hVhd.Dispose(); async Task <bool> GetProgress(SafeVIRTUAL_DISK_HANDLE phVhd, int step) { var prog = new VIRTUAL_DISK_PROGRESS(); var start = step == 1 ? 0 : 50; var end = step == 1 ? 50 : 100; ReportProgress(start); while (true) { var perr = GetVirtualDiskOperationProgress(phVhd, ref vhdCompactOverlap, out prog); perr.ThrowIfFailed(); if (cancellationToken.IsCancellationRequested) { return(false); } switch (prog.OperationStatus) { case 0: ReportProgress(end); return(true); case Win32Error.ERROR_IO_PENDING: ReportProgress(start + (int)(prog.CurrentValue * 50 / prog.CompletionValue)); break; default: throw new Win32Error((int)prog.OperationStatus).GetException(); } if (prog.CurrentValue == prog.CompletionValue) { return(true); } await Task.Delay(250, cancellationToken); } } void ReportProgress(int percent) => progress.Report(new Tuple <int, string>(percent, $"Compacting VHD volume \"{loc}\"")); /*var prog = new Progress<int>(i => progress.Report(new Tuple<int, string>(i / 2, loc))); * var taskComplete = false; * try * { * var param = new OPEN_VIRTUAL_DISK_PARAMETERS(0); * using (new PrivilegedCodeBlock(SystemPrivilege.ManageVolume)) * using (var vhd = VirtualDisk.Open(loc, OPEN_VIRTUAL_DISK_FLAG.OPEN_VIRTUAL_DISK_FLAG_NONE, param, VIRTUAL_DISK_ACCESS_MASK.VIRTUAL_DISK_ACCESS_ATTACH_RO | VIRTUAL_DISK_ACCESS_MASK.VIRTUAL_DISK_ACCESS_METAOPS)) * { * var flags = ATTACH_VIRTUAL_DISK_FLAG.ATTACH_VIRTUAL_DISK_FLAG_READ_ONLY; * var aparam = ATTACH_VIRTUAL_DISK_PARAMETERS.Default; * if (!ConvertStringSecurityDescriptorToSecurityDescriptor("O:BAG:BAD:(A;;GA;;;WD)", SDDL_REVISION.SDDL_REVISION_1, out Vanara.InteropServices.SafeHGlobalHandle sd, out uint hLen)) * Vanara.PInvoke.Win32Error.ThrowLastError(); * vhd.Attach(flags, ref aparam, (IntPtr)sd); * taskComplete = await vhd.Compact(cancellationToken, prog); * vhd.Detach(); * } * } * catch * { * taskComplete = true; * throw; * } * * // If first op fails, don't bother with the second * if (!taskComplete) return; * * prog = new Progress<int>(i => progress.Report(new Tuple<int, string>(50 + i / 2, loc))); * // Perform file-system-agnostic compaction * using (var vd = VirtualDisk.Open(loc)) * { * await vd.Compact(cancellationToken, prog); * }*/ }
public static extern bool WinDivertSendEx([In] IntPtr handle, [In] byte[] pPacket, uint packetLen, ulong flags, [In] ref WINDIVERT_ADDRESS pAddr, ref uint writeLen, ref NativeOverlapped lpOverlapped);
internal static extern bool ReadFile(SafeFileHandle hFile, IntPtr lpBuffer, uint nNumberOfBytesToRead, out uint lpNumberOfBytesRead, [In] ref NativeOverlapped lpOverlapped);
public static extern Boolean ReadFile([In()] CreateFileWHandle hFile, Byte[] lpBuffer, Int32 nNumberOfBytesToRead, ref IntPtr lpNumberOfBytesRead, ref NativeOverlapped lpOverlapped);
internal static extern bool GetOverlappedResult(SafeHandle hFile, [In] ref NativeOverlapped lpOverlapped, out uint lpNumberOfBytesTransferred, [MarshalAs(UnmanagedType.Bool)] bool bWait);
public static extern Boolean WriteFile([In()] CreateFileWHandle hFile, [In()] Byte[] lpBuffer, Int32 nNumberOfBytesToWrite, ref IntPtr lpNumberOfBytesWritten, ref NativeOverlapped lpOverlapped);
public static extern bool WriteFile( SafeFileHandle hFile, IntPtr lpBuffer, uint nNumberOfBytesToWrite, out uint lpNumberOfBytesWritten, ref NativeOverlapped lpOverlapped);
internal static extern unsafe uint HttpReceiveClientCertificate(SafeHandle requestQueueHandle, ulong connectionId, uint flags, HTTP_SSL_CLIENT_CERT_INFO* pSslClientCertInfo, uint sslClientCertInfoSize, uint* pBytesReceived, NativeOverlapped* pOverlapped);
// Function to output an entire frame to the USB3 Chip public bool Send_test_sequence(bool altOn) { FTDI.FT_STATUS ftStatus = FTDI.FT_STATUS.FT_OK; FTDI d3xxDevice = new FTDI(); bool bLoopbackFails = false; UInt32 words_per_line = 40; byte[] line_one = new byte[words_per_line]; byte[] line_two = new byte[words_per_line]; UInt32 bytesWritten = 0; bool TestResult = false; //var pOverlapped = new System.Threading.NativeOverlapped(); //if (!TestLoopbackPrepare.bBasicLoopbackWorking) //{ // Debug.WriteLine("ERROR: Basic Loopback failed, test will be skipped!"); // return TestResult; //} // Open our FTDI601 USB3 Chip ftStatus = d3xxDevice.OpenBySerialNumber(FTDI.FT_60XCONFIGURATION_DEFAULT_SERIALNUMBER); if (ftStatus != FTDI.FT_STATUS.FT_OK) { Debug.WriteLine("OpenByIndex failed! ftStatus={0}", ftStatus); return(TestResult); } /////////////////////////////////////////////// ////////////// Chip Configuration ///////////// /////////////////////////////////////////////// //// Set our config Values //var conf = new FTDI.FT_60XCONFIGURATION //{ // // Set default values // VendorID = FTDI.FT_60XCONFIGURATION_DEFAULT_VENDORID, // ProductID = FTDI.FT_60XCONFIGURATION_DEFAULT_PRODUCTID_601, // PowerAttributes = FTDI.FT_60XCONFIGURATION_DEFAULT_POWERATTRIBUTES, // PowerConsumption = FTDI.FT_60XCONFIGURATION_DEFAULT_POWERCONSUMPTION, // BatteryChargingGPIOConfig = FTDI.FT_60XCONFIGURATION_DEFAULT_BATTERYCHARGING, // OptionalFeatureSupport = FTDI.FT_60XCONFIGURATION_DEFAULT_OPTIONALFEATURE, // MSIO_Control = FTDI.FT_60XCONFIGURATION_DEFAULT_MSIOCONTROL, // GPIO_Control = FTDI.FT_60XCONFIGURATION_DEFAULT_GPIOCONTROL, // FlashEEPROMDetection = 0, // SerialNumber = FTDI.FT_60XCONFIGURATION_DEFAULT_SERIALNUMBER, // // Set custom values // FIFOMode = (byte)FTDI.FT_60XCONFIGURATION_FIFO_MODE.MODE_245, // //FIFOClock = (byte)FTDI.FT_60XCONFIGURATION_FIFO_CLK.CLK_100_MHZ: // FIFOClock = (byte)FTDI.FT_60XCONFIGURATION_FIFO_CLK.CLK_66_MHZ, // ChannelConfig = (byte)FTDI.FT_60XCONFIGURATION_CHANNEL_CONFIG.ONE_OUTPIPE, // Manufacturer = "Awesome Inc", // Description = "Being Awesome" //}; ////conf.SerialNumber = "123456789012345"; //ftStatus = d3xxDevice.SetChipConfiguration(conf); //if (ftStatus != FTDI.FT_STATUS.FT_OK) { Console.WriteLine("Fatal Error"); }; //// Need to close afterwards and wait at least 2s before re-opening (from datasheet) //ftStatus = d3xxDevice.Close(); //if (ftStatus != FTDI.FT_STATUS.FT_OK) { Console.WriteLine("Fatal Error"); }; //Thread.Sleep(2000); //ftStatus = d3xxDevice.OpenByIndex(0); //if (ftStatus != FTDI.FT_STATUS.FT_OK) { Console.WriteLine("OpenByIndex failed! ftStatus={0}", ftStatus); return TestResult; } //// Read what is set //ftStatus = d3xxDevice.GetChipConfiguration(conf); //if (ftStatus != FTDI.FT_STATUS.FT_OK) { Console.WriteLine("Fatal Error"); }; //// Print results //Console.WriteLine("\tChip Configuration"); //Console.WriteLine("\tVendorID : 0x{0:X4}", conf.VendorID); //Console.WriteLine("\tProductID : 0x{0:X4}", conf.ProductID); //Console.WriteLine("\tManufacturer : " + conf.Manufacturer); //Console.WriteLine("\tDescription : " + conf.Description); //Console.WriteLine("\tSerialNumber : " + conf.SerialNumber); //Console.WriteLine("\tPowerAttributes : 0x{0:X2}", conf.PowerAttributes); //Console.WriteLine("\tPowerConsumption : 0x{0:X4}", conf.PowerConsumption); //Console.WriteLine("\tFIFOClock : 0x{0:X4}", conf.FIFOClock); //Console.WriteLine("\tFIFOMode : 0x{0:X2}", conf.FIFOMode); //Console.WriteLine("\tChannelConfig : 0x{0:X2}", conf.ChannelConfig); //Console.WriteLine("\tOptionalFeatureSupport : 0x{0:X4}", conf.OptionalFeatureSupport); //Console.WriteLine("\tBatteryChargingGPIOConfig: 0x{0:X2}", conf.BatteryChargingGPIOConfig); //Console.WriteLine("\tMSIO_Control : 0x{0:X8}", conf.MSIO_Control); //Console.WriteLine("\tGPIO_Control : 0x{0:X8}", conf.GPIO_Control); //Console.WriteLine("\tFlashEEPROMDetection : 0x{0:X2}", conf.FlashEEPROMDetection); //if (conf.FlashEEPROMDetection > 0) //{ // bool bROM = (conf.FlashEEPROMDetection & (1 << (byte)FTDI.FT_60XCONFIGURATION_FLASH_ROM_BIT.ROM)) > 0; // Debug.WriteLine("\t\tMEMORY : {0}", bROM ? "Rom" : "Flash"); // if (bROM) // { // bool bMemoryExist = (conf.FlashEEPROMDetection & (1 << (byte)FTDI.FT_60XCONFIGURATION_FLASH_ROM_BIT.MEMORY_NOTEXIST)) > 0; // Debug.WriteLine("\t\tMEMORY_NOTEXIST : {0}", bMemoryExist ? "Invalid" : "Valid"); // } // bool bCustom = (conf.FlashEEPROMDetection & (1 << (byte)FTDI.FT_60XCONFIGURATION_FLASH_ROM_BIT.CUSTOM)) > 0; // Debug.WriteLine("\t\tVALUES : {0}", bCustom ? "Custom" : "Default"); // if (!bCustom) // { // Default configuration // bool bGPIO0 = (conf.FlashEEPROMDetection & (1 << (byte)FTDI.FT_60XCONFIGURATION_FLASH_ROM_BIT.GPIO_0)) > 0; // bool bGPIO1 = (conf.FlashEEPROMDetection & (1 << (byte)FTDI.FT_60XCONFIGURATION_FLASH_ROM_BIT.GPIO_1)) > 0; // Debug.WriteLine("\t\tGPIO_0 : {0}", bGPIO0 ? "High" : "Low"); Debug.WriteLine("\t\tGPIO_1 : {0}", bGPIO1 ? "High" : "Low"); // if (bGPIO0 && bGPIO1) // { // Debug.WriteLine("\t\tChannel : 4 channels, 600 mode"); // } // else if (!bGPIO0 && bGPIO1) // { // Debug.WriteLine("\t\tChannel : 2 channels, 600 mode"); // } // else if (bGPIO0 && !bGPIO1) // { // Debug.WriteLine("\t\tChannel : 1 channel, 600 mode"); // } // else if (!bGPIO0 && !bGPIO1) // { // Debug.WriteLine("\t\tChannel : 1 channel, 245 mode"); // } // } // else // { // Custom configuration // bool bInvalidData = (conf.FlashEEPROMDetection & (1 << (byte)FTDI.FT_60XCONFIGURATION_FLASH_ROM_BIT.CUSTOMDATA_INVALID)) > 0; // bool bInvalidDataChecksum = (conf.FlashEEPROMDetection & (1 << (byte)FTDI.FT_60XCONFIGURATION_FLASH_ROM_BIT.CUSTOMDATACHKSUM_INVALID)) > 0; // Debug.WriteLine("\t\tCUSTOMDATA : {0}", bInvalidData ? "Invalid" : "Valid"); Debug.WriteLine("\t\tCUSTOMDATACHKSUM: {0}", bInvalidDataChecksum ? "Invalid" : "Valid"); // } //} ////ftStatus = d3xxDevice.Close(); ////if (ftStatus != FTDI.FT_STATUS.FT_OK) { Console.WriteLine("Fatal Error"); }; // Disable Input Timeouts //d3xxDevice.SetPipeTimeout(0x82, 0); //PipeTimeout.Disable(d3xxDevice, 0x82); // Disable tiomeouts on our output pipe d3xxDevice.SetPipeTimeout(0x02, 0); //d3xxDevice.SetPipeTimeout(0x02, 500); // We drive the entire FPGA design off of the FIFO's 100MHz vlock, therefore we want clock to run all the time // Set a timeout of 0 to achieve this, without this, clock will only be on for 10 seconds d3xxDevice.SetSuspendTimeout(0); // Diagnostics Code System.Collections.Generic.List <FT_PIPE_INFORMATION> info = d3xxDevice.DataPipeInformation; //d3xxDevice.ResetChipConfiguration(); //var conf = new FTDI.FT_60XCONFIGURATION(); //FT_STATUS status = d3xxDevice.GetChipConfiguration(conf); // Setup GPIO UInt32 ulDirection = ((byte)FTDI.FT_GPIO_DIRECTION.OUT << (byte)FTDI.FT_GPIO.GPIO_0) | ((byte)FTDI.FT_GPIO_DIRECTION.OUT << (byte)FTDI.FT_GPIO.GPIO_1); //UInt32 ulMask = (UInt32)FTDI.FT_GPIO_MASK.GPIO_ALL; //ftStatus = d3xxDevice.EnableGPIO(ulMask, ulDirection); //if (ftStatus != FTDI.FT_STATUS.FT_OK) //{ // Debug.WriteLine("EnableGPIO failed! ftStatus={0}", ftStatus); // return TestResult; //} // Write next_frame_rdy signal //ftStatus = d3xxDevice.EnableGPIO((UInt32)FTDI.FT_GPIO_MASK.GPIO_ALL, ulDirection); //ftStatus = d3xxDevice.WriteGPIO((UInt32)FTDI.FT_GPIO_MASK.GPIO_1, 3); //ftStatus = d3xxDevice.WriteGPIO((UInt32)FTDI.FT_GPIO_MASK.GPIO_1, 0); //ftStatus = d3xxDevice.EnableGPIO((UInt32)0, ulDirection); //for (UInt32 i = 0; i < 100; i++) //{ ///////////////////////////////////////////// ///////////// Single Lines Test ///////////// ///////////////////////////////////////////// //// Line 1 //for (UInt32 j = 0; j < line_one.Length; j++) //{ // //line_one[j] = (byte)(0xAA); // line_one[j] = (byte)(j << 4); //} //// Line 2 //for (UInt32 j = 0; j < line_two.Length; j++) //{ // //line_two[j] = (byte)(0x55); // line_two[j] = (byte)(j << 4); //} //// Write Line1 //ftStatus = d3xxDevice.WritePipe(0x02, line_one, (UInt32)line_one.Length, ref bytesWritten); //// Write Line2 //ftStatus = d3xxDevice.WritePipe(0x02, line_two, (UInt32)line_two.Length, ref bytesWritten); /////////////////////////////////////////// /////////// Entire Image Test ///////////// /////////////////////////////////////////// //bool altOn = true; //altOn = false; //uint lines_per_frame = 1280; // Just use 50 lines for now (less than 8kb, 1 buffer, until get to the bottom of the USB FIFO issue) //uint lines_per_frame = 256+2+3;// 1280;// 1304;// 66;// 1304;// 1280; //uint lines_per_frame = 256+2+3; //uint lines_per_frame = 512 - 4; // This can varyu, no idea why or how uint lines_per_frame = 1280;// 32;// 512;// 1280;//512;// 256;// 64;//32;// 64;// 2;// 16;// 6;// 64; // This can varyu, no idea why or how uint bytes_per_line = words_per_line * 4; uint total_bytes_per_frame = lines_per_frame * bytes_per_line; byte[] Frame1 = new byte[total_bytes_per_frame]; // Load up all of our 32-bit words with alternating data // Iterate through 8 bytes at a time for (int curr_byte = 0; curr_byte < (total_bytes_per_frame - 7); curr_byte += 8) { if (altOn) { //// Pattern on even 32-bit words //Frame1[curr_byte + 0] = 0xAA; //Frame1[curr_byte + 1] = 0xAA; //Frame1[curr_byte + 2] = 0xAA; //Frame1[curr_byte + 3] = 0xAA; //// Pattern on odd 32-bit words //Frame1[curr_byte + 4] = 0x55; //Frame1[curr_byte + 5] = 0x55; //Frame1[curr_byte + 6] = 0x55; //Frame1[curr_byte + 7] = 0x55; //// Pattern on even 32-bit words //Frame1[curr_byte + 0] = 0xFF; //Frame1[curr_byte + 1] = 0xFF; //Frame1[curr_byte + 2] = 0xFF; //Frame1[curr_byte + 3] = 0xFF; //// Pattern on odd 32-bit words //Frame1[curr_byte + 4] = 0x00; //Frame1[curr_byte + 5] = 0x00; //Frame1[curr_byte + 6] = 0x00; //Frame1[curr_byte + 7] = 0x00; //// Counting //Frame1[curr_byte + 0] = 0x01; //Frame1[curr_byte + 1] = 0x02; //Frame1[curr_byte + 2] = 0x03; //Frame1[curr_byte + 3] = 0x04; //Frame1[curr_byte + 4] = 0x05; //Frame1[curr_byte + 5] = 0x06; //Frame1[curr_byte + 6] = 0x07; //Frame1[curr_byte + 7] = 0x08; // Counting remembering we only get to write to half of pixels.... Frame1[curr_byte + 0] = 0x01; Frame1[curr_byte + 1] = 0x02; Frame1[curr_byte + 2] = 0xFF; Frame1[curr_byte + 3] = 0xFF; Frame1[curr_byte + 4] = 0x03; Frame1[curr_byte + 5] = 0x04; Frame1[curr_byte + 6] = 0xFF; Frame1[curr_byte + 7] = 0xFF; //// All Off //Frame1[curr_byte + 0] = 0x00; //Frame1[curr_byte + 1] = 0x00; //Frame1[curr_byte + 2] = 0x00; //Frame1[curr_byte + 3] = 0x00; //Frame1[curr_byte + 4] = 0x00; //Frame1[curr_byte + 5] = 0x00; //Frame1[curr_byte + 6] = 0x00; //Frame1[curr_byte + 7] = 0x00; } else { //// Pattern on even 32-bit words //Frame1[curr_byte + 0] = 0x55; //Frame1[curr_byte + 1] = 0x55; //Frame1[curr_byte + 2] = 0x55; //Frame1[curr_byte + 3] = 0x55; //// Pattern on odd 32-bit words //Frame1[curr_byte + 4] = 0xAA; //Frame1[curr_byte + 5] = 0xAA; //Frame1[curr_byte + 6] = 0xAA; //Frame1[curr_byte + 7] = 0xAA; //// Global Counting //Frame1[curr_byte + 0] = (byte)(curr_byte+0); //Frame1[curr_byte + 1] = (byte)(curr_byte+1); //Frame1[curr_byte + 2] = (byte)(curr_byte+2); //Frame1[curr_byte + 3] = (byte)(curr_byte+3); //Frame1[curr_byte + 4] = (byte)(curr_byte+4); //Frame1[curr_byte + 5] = (byte)(curr_byte+5); //Frame1[curr_byte + 6] = (byte)(curr_byte+6); //Frame1[curr_byte + 7] = (byte)(curr_byte+7); //// Corners Test Image //Frame1[curr_byte + 0] = TestImages.corners[curr_byte + 0]; //Frame1[curr_byte + 1] = TestImages.corners[curr_byte + 1]; //Frame1[curr_byte + 2] = TestImages.corners[curr_byte + 2]; //Frame1[curr_byte + 3] = TestImages.corners[curr_byte + 3]; //Frame1[curr_byte + 4] = TestImages.corners[curr_byte + 4]; //Frame1[curr_byte + 5] = TestImages.corners[curr_byte + 5]; //Frame1[curr_byte + 6] = TestImages.corners[curr_byte + 6]; //Frame1[curr_byte + 7] = TestImages.corners[curr_byte + 7]; //// All-on Test Image //Frame1[curr_byte + 0] = TestImages.all_on[curr_byte + 0]; //Frame1[curr_byte + 1] = TestImages.all_on[curr_byte + 1]; //Frame1[curr_byte + 2] = TestImages.all_on[curr_byte + 2]; //Frame1[curr_byte + 3] = TestImages.all_on[curr_byte + 3]; //Frame1[curr_byte + 4] = TestImages.all_on[curr_byte + 4]; //Frame1[curr_byte + 5] = TestImages.all_on[curr_byte + 5]; //Frame1[curr_byte + 6] = TestImages.all_on[curr_byte + 6]; //Frame1[curr_byte + 7] = TestImages.all_on[curr_byte + 7]; //// Incrementing Words //Frame1[curr_byte + 0] = TestImages.incr_words[curr_byte + 0]; //Frame1[curr_byte + 1] = TestImages.incr_words[curr_byte + 1]; //Frame1[curr_byte + 2] = TestImages.incr_words[curr_byte + 2]; //Frame1[curr_byte + 3] = TestImages.incr_words[curr_byte + 3]; //Frame1[curr_byte + 4] = TestImages.incr_words[curr_byte + 4]; //Frame1[curr_byte + 5] = TestImages.incr_words[curr_byte + 5]; //Frame1[curr_byte + 6] = TestImages.incr_words[curr_byte + 6]; //Frame1[curr_byte + 7] = TestImages.incr_words[curr_byte + 7]; // Smiley Face Frame1[curr_byte + 0] = TestImages.smiley_face[curr_byte + 0]; Frame1[curr_byte + 1] = TestImages.smiley_face[curr_byte + 1]; Frame1[curr_byte + 2] = TestImages.smiley_face[curr_byte + 2]; Frame1[curr_byte + 3] = TestImages.smiley_face[curr_byte + 3]; Frame1[curr_byte + 4] = TestImages.smiley_face[curr_byte + 4]; Frame1[curr_byte + 5] = TestImages.smiley_face[curr_byte + 5]; Frame1[curr_byte + 6] = TestImages.smiley_face[curr_byte + 6]; Frame1[curr_byte + 7] = TestImages.smiley_face[curr_byte + 7]; } } // Run in streaming mode for max performance with fixed block sizes ftStatus = d3xxDevice.SetStreamPipe(0x02, total_bytes_per_frame); if (ftStatus != FTDI.FT_STATUS.FT_OK) { Debug.WriteLine("Couldnt set to streaming mode! ftStatus={0}", ftStatus); d3xxDevice.AbortPipe(0x02); bLoopbackFails = true; } // Output Frame //ftStatus = d3xxDevice.WritePipe(0x02, Frame1, (UInt32)total_bytes_per_frame, ref bytesWritten); NativeOverlapped pOverlapped = new NativeOverlapped(); //for (int i = 0; i < 1280; i++) //{ //ftStatus = d3xxDevice.WritePipe(0x02, Frame1, (UInt32)total_bytes_per_frame, ref bytesWritten); Thread.Sleep(10); // Write ftStatus = d3xxDevice.WritePipeAsync(0x02, Frame1, (UInt32)total_bytes_per_frame, ref bytesWritten, ref pOverlapped); // Async wait ftStatus = d3xxDevice.WaitAsync(ref pOverlapped, ref bytesWritten, true); Thread.Sleep(10); if ((ftStatus != FTDI.FT_STATUS.FT_OK) || (bytesWritten != total_bytes_per_frame)) { Console.WriteLine("Error with async transfer"); } ; // Print Transfer Details Console.WriteLine("Bytes: " + bytesWritten.ToString() + " Status: " + ftStatus.ToString()); //// Just send 32 lines at a time, 40 times //for(int i=0; i<40; i++) //{ // ftStatus = d3xxDevice.WritePipe(0x02, Frame1, (UInt32)total_bytes_per_frame, ref bytesWritten); // Thread.Sleep(10); // if ((ftStatus != FTDI.FT_STATUS.FT_OK) || (bytesWritten != total_bytes_per_frame)) // { // Console.WriteLine("Error with async transfer"); // }; // // Print Transfer Details // Console.WriteLine("Bytes: " + bytesWritten.ToString() + " Status: " + ftStatus.ToString()); //} //ftStatus = d3xxDevice.WritePipe(0x02, Frame1, (UInt32)total_bytes_per_frame, ref bytesWritten); ////Thread.Sleep(10); //// Write ////ftStatus = d3xxDevice.WritePipeAsync(0x02, Frame1, (UInt32)total_bytes_per_frame, ref bytesWritten, ref pOverlapped); //// Async wait ////ftStatus = d3xxDevice.WaitAsync(ref pOverlapped, ref bytesWritten, true); ////Thread.Sleep(1); //if ((ftStatus != FTDI.FT_STATUS.FT_OK) || (bytesWritten != total_bytes_per_frame)) //{ // Console.WriteLine("Error with async transfer"); //}; //// Print Transfer Details //Console.WriteLine("Bytes: " + bytesWritten.ToString() + " Status: " + ftStatus.ToString()); // Print Pipe State //foreach (var desc in d3xxDevice.DataPipeInformation) //{ // Console.WriteLine("\tPIPE INFORMATION"); // Console.WriteLine("\tPipeType : {0:d} ({1})", desc.PipeType, desc.PipeType.ToString()); // Console.WriteLine("\tPipeId : 0x{0:X2}", desc.PipeId); // Console.WriteLine("\tMaximumPacketSize : 0x{0:X4}", desc.MaximumPacketSize); // Console.WriteLine("\tInterval : 0x{0:X2}", desc.Interval); //} //Frame1[row].ToList().ForEach(i => Console.WriteLine(i.ToString())); //Thread.Sleep(1); //} //// Pump all our lines, lots of data!! //for (int row = 0; row < lines_per_frame; row++) //{ // //ftStatus = d3xxDevice.WritePipe(0x02, Frame1[row], (UInt32)bytes_per_line, ref bytesWritten); // // Write // ftStatus = d3xxDevice.WritePipeAsync(0x02, Frame1[row], (UInt32)bytes_per_line, ref bytesWritten, ref pOverlapped); // // Async wait // ftStatus = d3xxDevice.WaitAsync(ref pOverlapped, ref bytesWritten, true); // if (ftStatus != FTDI.FT_STATUS.FT_OK || bytesWritten != bytes_per_line){ Console.WriteLine("Error with async transfer"); }; // // Print Transfer Details // Console.WriteLine("Bytes: " + bytesWritten.ToString() + " Status: " + ftStatus.ToString() ); // // Print Pipe State // foreach (var desc in d3xxDevice.DataPipeInformation) // { // Console.WriteLine("\tPIPE INFORMATION"); // Console.WriteLine("\tPipeType : {0:d} ({1})", desc.PipeType, desc.PipeType.ToString()); // Console.WriteLine("\tPipeId : 0x{0:X2}", desc.PipeId); // Console.WriteLine("\tMaximumPacketSize : 0x{0:X4}", desc.MaximumPacketSize); // Console.WriteLine("\tInterval : 0x{0:X2}", desc.Interval); // } // //Frame1[row].ToList().ForEach(i => Console.WriteLine(i.ToString())); // //Thread.Sleep(100); //} if (ftStatus != FTDI.FT_STATUS.FT_OK) { Debug.WriteLine("WritePipe failed! ftStatus={0}", ftStatus); d3xxDevice.AbortPipe(0x02); bLoopbackFails = true; //break; } //if (bytesWritten != writeBytes.Length) //{ // Debug.WriteLine("WritePipe failed! bytesWritten={0} != writeBytes.Length={1}", bytesWritten, writeBytes.Length); // bLoopbackFails = true; // break; //} //Debug.WriteLine("\t[{0:d}] WritePipe {1:d}", i, bytesWritten); // Write next_line_rdy signal //ftStatus = d3xxDevice.EnableGPIO((UInt32)FTDI.FT_GPIO_MASK.GPIO_ALL, ulDirection); //ftStatus = d3xxDevice.WriteGPIO((UInt32)FTDI.FT_GPIO_MASK.GPIO_0, 3); //ftStatus = d3xxDevice.WriteGPIO((UInt32)FTDI.FT_GPIO_MASK.GPIO_0, 0); //ftStatus = d3xxDevice.EnableGPIO((UInt32)0, ulDirection); // UInt32 bytesRead = 0; // while (true) // { // ftStatus = d3xxDevice.ReadPipe(0x82, readBytes, (UInt32)readBytes.Length, ref bytesRead); // if (ftStatus != FTDI.FT_STATUS.FT_OK) // { // Debug.WriteLine("ReadPipe failed! ftStatus={0}", ftStatus); // d3xxDevice.AbortPipe(0x82); // bLoopbackFails = true; // break; // } // if (bytesRead == 0) // { // Debug.WriteLine("ReadPipe bytesRead == 0, retry"); // continue; // } // else if (bytesRead != readBytes.Length) // { // Debug.WriteLine("ReadPipe failed! bytesRead={0} != readBytes.Length={1}", bytesRead, readBytes.Length); // bLoopbackFails = true; // break; // } // break; // } // Debug.WriteLine("\t[{0:d}] ReadPipe {1:d}", i, bytesRead); // bool same = writeBytes.SequenceEqual(readBytes); // if (same == false) // { // Debug.WriteLine("Loopback fails! SequenceEqual fails!"); // bLoopbackFails = true; // break; // } //} Thread.Sleep(200); d3xxDevice.AbortPipe(0x02); Thread.Sleep(200); Thread.Sleep(200); d3xxDevice.FlushPipe(0x02); Thread.Sleep(200); ftStatus = d3xxDevice.Close(); //d3xxDevice.ResetDevicePort(); if (ftStatus != FTDI.FT_STATUS.FT_OK) { Debug.WriteLine("Close failed! ftStatus={0}", ftStatus); return(TestResult); } if (!bLoopbackFails) { TestResult = true; } return(TestResult); }
private static extern bool ConnectNamedPipe(IntPtr namedPipeHandle, ref NativeOverlapped overlapped);
public unsafe static object GetNativeOverlappedState(NativeOverlapped* overlapped);
private static extern bool ReadFile(IntPtr fileHandle, [Out] byte[] dataBuffer, uint nNumberOfBytesToRead, out uint lpNumberOfBytesRead, [In] ref NativeOverlapped overlapped);
public static unsafe void Free(NativeOverlapped *nativeOverlappedPtr) { // Since there is no way to allocate a native overlapped // structure in this implementation, the only thing we // need to do here is check for null. if(((IntPtr)nativeOverlappedPtr) == IntPtr.Zero) { throw new ArgumentNullException("nativeOverlappedPtr"); } }
private static extern bool WriteFile(IntPtr fileHandle, [Out] byte[] dataBuffer, uint nNumberOfBytesToWrite, out uint lpNumberOfBytesWritten, [In] ref NativeOverlapped overlapped);
internal unsafe static extern uint HttpSendHttpResponse(SafeHandle requestQueueHandle, ulong requestId, uint flags, HTTP_RESPONSE* pHttpResponse, void* pCachePolicy, uint* pBytesSent, SafeLocalAllocHandle pRequestBuffer, uint requestBufferLength, NativeOverlapped* pOverlapped, void* pLogData);
private void ProcessPipeMessage() { NativeOverlapped overlapped = new NativeOverlapped(); byte[] readMessage; using (MemoryStream ms = new MemoryStream()) { while (true) { // Loop as follows: // Peek at the pipe to see how much data is available // Read the data and append it to the buffer // If we get ERROR_MORE_DATA, repeat UInt32 bytesRead, bytesAvailable, bytesLeft; // First peek into the pipe to see how much data is waiting. byte[] peekBuf = new byte[0]; if (!PeekNamedPipe(Handle, peekBuf, (UInt32)peekBuf.Length, out bytesRead, out bytesAvailable, out bytesLeft)) { throw new Win32Exception( string.Format("PeekNamedPipe failed. bytesRead={0} bytesAvailable={1} bytesLeft={2}", bytesRead, bytesAvailable, bytesLeft), new Win32Exception()); } // Sanity check: throw away message if it is > 1 MB if (ms.Length + bytesLeft > 1024 * 1024) { throw new Exception("Indecently large message sent into named pipe: rejecting."); } // Now allocate a buffer of the correct size and read in the message. byte[] readBuf = new byte[bytesAvailable]; if (!ReadFile(Handle, readBuf, (UInt32)readBuf.Length, out bytesRead, ref overlapped)) { Win32Exception exn = new Win32Exception(); if (exn.NativeErrorCode == ERROR_MORE_DATA) { // The peek may have looked into the pipe before the write operation // had completed, and so reported a message size before the whole // message was sent. In this case we need to go round the loop again // with a larger buffer. ms.Write(readBuf, 0, (int)bytesRead); continue; } else { throw new Win32Exception( string.Format("ReadFile failed. readBuf.Length={0} bytesRead={1}", readBuf.Length, bytesRead), exn); } } else { ms.Write(readBuf, 0, (int)bytesRead); break; } } readMessage = ms.ToArray(); } // Now perform a zero-byte write. This causes the CallNamedPipe call to // return successfully in the splash screen. UInt32 bytesWritten; byte[] toWrite = new byte[0]; if (!WriteFile(Handle, toWrite, (UInt32)toWrite.Length, out bytesWritten, ref overlapped)) { throw new Win32Exception( string.Format("WriteFile failed. toWrite.Length={0} bytesWritten={1}", toWrite.Length, bytesWritten), new Win32Exception()); } PipeReadEventArgs e = new PipeReadEventArgs(readMessage); if (e.Message == STOP_LISTENING_MSG) { log.Debug("NamedPipe thread was told to stop listening"); run = false; return; } // Now inform any listeners of the received data. if (Read != null) { Read(null, e); } }
internal unsafe static extern uint HttpReceiveRequestEntityBody(SafeHandle requestQueueHandle, ulong requestId, uint flags, void* pEntityBuffer, uint entityBufferLength, out uint bytesReturned, NativeOverlapped* pOverlapped);
private static extern bool UnlockFileEx(IntPtr hFile, uint dwReserved, uint nNumberOfBytesToLockLow, uint nNumberOfBytesToLockHigh, [In] ref NativeOverlapped lpOverlapped);
internal unsafe static extern uint HttpReceiveClientCertificate(SafeHandle requestQueueHandle, ulong connectionId, uint flags, byte* pSslClientCertInfo, uint sslClientCertInfoSize, uint* pBytesReceived, NativeOverlapped* pOverlapped);
public extern static bool WriteFile( IntPtr hFile, // HANDLE byte[] lpBuffer, // LPCVOID uint nNumberOfBytesToWrite, // DWORD out uint lpNumberOfBytesWritten, // LPDWORD [In] ref NativeOverlapped lpOverlapped);
private static unsafe void OnOverlappedOperationCompleted(uint errorCode, uint numBytes, NativeOverlapped* overlapped) { OverlappedContext result = (OverlappedContext)ThreadPoolBoundHandle.GetNativeOverlappedState(overlapped); result.ErrorCode = (int)errorCode; result.BytesWritten = (int)numBytes; // Signal original thread to indicate overlapped completed result.Event.Set(); }
public extern static bool WriteFileEx( IntPtr hFile, byte[] lpBuffer, uint nNumberOfBytesToWrite, [In] ref NativeOverlapped lpOverlapped, WriteFileCompletionDelegate lpCompletionRoutine);
unsafe internal static extern bool ConnectNamedPipe(SafePipeHandle handle, NativeOverlapped* overlapped);
public extern static bool ReadFile( IntPtr hFile, byte[] lpBuffer, uint nNumberofBytesToRead, ref NativeOverlapped lpOverlapped);
internal static unsafe extern bool CancelIoEx(SafeFileHandle handle, NativeOverlapped* lpOverlapped);
/// <summary> /// reads an Input report from the device using interrupt transfers. /// </summary> /// /// <param name="hidHandle"> the handle for learning about the device and exchanging Feature reports. </param> /// <param name="readHandle"> the handle for reading Input reports from the device. </param> /// <param name="writeHandle"> the handle for writing Output reports to the device. </param> /// <param name="myDeviceDetected"> tells whether the device is currently attached. </param> /// <param name="inputReportBuffer"> contains the requested report. </param> /// <param name="success"> read success </param> internal override void Read(SafeFileHandle hidHandle, SafeFileHandle readHandle, SafeFileHandle writeHandle, ref Boolean myDeviceDetected, ref Byte[] inputReportBuffer, ref Boolean success) { IntPtr eventObject = IntPtr.Zero; NativeOverlapped HidOverlapped = new NativeOverlapped(); IntPtr nonManagedBuffer = IntPtr.Zero; IntPtr nonManagedOverlapped = IntPtr.Zero; Int32 numberOfBytesRead = 0; Int32 result = 0; try { // Set up the overlapped structure for ReadFile. PrepareForOverlappedTransfer(ref HidOverlapped, ref eventObject); // Allocate memory for the input buffer and overlapped structure. nonManagedBuffer = Marshal.AllocHGlobal(inputReportBuffer.Length); nonManagedOverlapped = Marshal.AllocHGlobal(Marshal.SizeOf(HidOverlapped)); Marshal.StructureToPtr(HidOverlapped, nonManagedOverlapped, false); // *** // API function: ReadFile // Purpose: Attempts to read an Input report from the device. // Accepts: // A device handle returned by CreateFile // (for overlapped I/O, CreateFile must have been called with FILE_FLAG_OVERLAPPED), // A pointer to a buffer for storing the report. // The Input report length in bytes returned by HidP_GetCaps, // A pointer to a variable that will hold the number of bytes read. // An overlapped structure whose hEvent member is set to an event object. // Returns: the report in ReadBuffer. // The overlapped call returns immediately, even if the data hasn't been received yet. // To read multiple reports with one ReadFile, increase the size of ReadBuffer // and use NumberOfBytesRead to determine how many reports were returned. // Use a larger buffer if the application can't keep up with reading each report // individually. // *** success = FileIO.ReadFile(readHandle, nonManagedBuffer, inputReportBuffer.Length, ref numberOfBytesRead, nonManagedOverlapped); if (!success) { Debug.WriteLine("waiting for ReadFile"); // API function: WaitForSingleObject // Purpose: waits for at least one report or a timeout. // Used with overlapped ReadFile. // Accepts: // An event object created with CreateEvent // A timeout value in milliseconds. // Returns: A result code. result = FileIO.WaitForSingleObject(eventObject, 3000); // Find out if ReadFile completed or timeout. switch (result) { case (System.Int32)FileIO.WAIT_OBJECT_0: // ReadFile has completed success = true; Debug.WriteLine("ReadFile completed successfully."); // Get the number of bytes read. // API function: GetOverlappedResult // Purpose: gets the result of an overlapped operation. // Accepts: // A device handle returned by CreateFile. // A pointer to an overlapped structure. // A pointer to a variable to hold the number of bytes read. // False to return immediately. // Returns: non-zero on success and the number of bytes read. FileIO.GetOverlappedResult(readHandle, nonManagedOverlapped, ref numberOfBytesRead, false); break; case FileIO.WAIT_TIMEOUT: // Cancel the operation on timeout CancelTransfer(hidHandle, readHandle, writeHandle, eventObject); Debug.WriteLine("Readfile timeout"); success = false; myDeviceDetected = false; break; default: // Cancel the operation on other error. CancelTransfer(hidHandle, readHandle, writeHandle, eventObject); Debug.WriteLine("Readfile undefined error"); success = false; myDeviceDetected = false; break; } } if (success) { // A report was received. // Copy the received data to inputReportBuffer for the application to use. Marshal.Copy(nonManagedBuffer, inputReportBuffer, 0, numberOfBytesRead); } } catch (Exception ex) { DisplayException(MODULE_NAME, ex); throw; } finally { if (nonManagedBuffer != IntPtr.Zero) { Marshal.FreeHGlobal(nonManagedBuffer); } if (nonManagedOverlapped != IntPtr.Zero) { Marshal.FreeHGlobal(nonManagedOverlapped); } } }
internal static unsafe extern int WriteFile(SafeHandle handle, byte* bytes, int numBytesToWrite, IntPtr numBytesWritten_mustBeZero, NativeOverlapped* lpOverlapped);
unsafe private static void AsyncFSCallback(uint errorCode, uint numBytes, NativeOverlapped* pOverlapped) { //Console.WriteLine("AsyncFSCallback called. errorCode: "+errorCode+" numBytes: "+numBytes); // Unpack overlapped Overlapped overlapped = Overlapped.Unpack(pOverlapped); // Free the overlapped struct in EndRead/EndWrite. // Extract async result from overlapped FileStreamAsyncResult asyncResult = (FileStreamAsyncResult)overlapped.AsyncResult; asyncResult._numBytes = (int)numBytes; // Handle reading from & writing to closed pipes. While I'm not sure // this is entirely necessary anymore, maybe it's possible for // an async read on a pipe to be issued and then the pipe is closed, // returning this error. This may very well be necessary. if (errorCode == ERROR_BROKEN_PIPE || errorCode == ERROR_NO_DATA) errorCode = 0; asyncResult._errorCode = (int)errorCode; //Console.WriteLine("AsyncFSCallback: errorCode: "+errorCode+" numBytes: "+numBytes+" was synchronous: "+asyncResult.CompletedSynchronously); // Call the user-provided callback. It can and often should // call EndRead or EndWrite. There's no reason to use an async // delegate here - we're already on a threadpool thread. // IAsyncResult's completedSynchronously property must return // false here, saying the user callback was called on another thread. asyncResult._completedSynchronously = false; asyncResult._isComplete = true; // ensure _isComplete is set before reading _waitHandle Thread.MemoryBarrier(); // The OS does not signal this event. We must do it ourselves. ManualResetEvent wh = asyncResult._waitHandle; if (wh != null) { Contract.Assert(!wh.SafeWaitHandle.IsClosed, "ManualResetEvent already closed!"); bool r = wh.Set(); Contract.Assert(r, "ManualResetEvent::Set failed!"); if (!r) __Error.WinIOError(); } AsyncCallback userCallback = asyncResult._userCallback; if (userCallback != null) userCallback(asyncResult); }