From 9a3e44d8f5ec5c946f697cb85c50fddbbc13fc9a Mon Sep 17 00:00:00 2001 From: cliechti Date: Fri, 11 Oct 2013 01:08:02 +0000 Subject: change error handling for errors while opening again (now similar to posix, clean close after error) git-svn-id: http://svn.code.sf.net/p/pyserial/code/trunk/pyserial@464 f19166aa-fa4f-0410-85c2-fa1106f25c8a --- serial/serialwin32.py | 80 +++++++++++++++++++++++++++++++++------------------ 1 file changed, 52 insertions(+), 28 deletions(-) diff --git a/serial/serialwin32.py b/serial/serialwin32.py index 6adde3d..6264bab 100644 --- a/serial/serialwin32.py +++ b/serial/serialwin32.py @@ -27,11 +27,14 @@ class Win32Serial(SerialBase): def __init__(self, *args, **kwargs): self.hComPort = None + self._overlappedRead = None + self._overlappedWrite = None self._rtsToggle = False self._rtsState = win32.RTS_CONTROL_ENABLE self._dtrState = win32.DTR_CONTROL_ENABLE + SerialBase.__init__(self, *args, **kwargs) def open(self): @@ -61,28 +64,40 @@ class Win32Serial(SerialBase): if self.hComPort == win32.INVALID_HANDLE_VALUE: self.hComPort = None # 'cause __del__ is called anyway raise SerialException("could not open port %r: %r" % (self.portstr, ctypes.WinError())) - self._isOpen = True - - # Setup a 4k buffer - win32.SetupComm(self.hComPort, 4096, 4096) - - # Save original timeout values: - self._orgTimeouts = win32.COMMTIMEOUTS() - win32.GetCommTimeouts(self.hComPort, ctypes.byref(self._orgTimeouts)) - - self._reconfigurePort() - # Clear buffers: - # Remove anything that was there - win32.PurgeComm(self.hComPort, - win32.PURGE_TXCLEAR | win32.PURGE_TXABORT | - win32.PURGE_RXCLEAR | win32.PURGE_RXABORT) + try: + self._overlappedRead = win32.OVERLAPPED() + self._overlappedRead.hEvent = win32.CreateEvent(None, 1, 0, None) + self._overlappedWrite = win32.OVERLAPPED() + #~ self._overlappedWrite.hEvent = win32.CreateEvent(None, 1, 0, None) + self._overlappedWrite.hEvent = win32.CreateEvent(None, 0, 0, None) + + # Setup a 4k buffer + win32.SetupComm(self.hComPort, 4096, 4096) + + # Save original timeout values: + self._orgTimeouts = win32.COMMTIMEOUTS() + win32.GetCommTimeouts(self.hComPort, ctypes.byref(self._orgTimeouts)) + + self._reconfigurePort() + + # Clear buffers: + # Remove anything that was there + win32.PurgeComm(self.hComPort, + win32.PURGE_TXCLEAR | win32.PURGE_TXABORT | + win32.PURGE_RXCLEAR | win32.PURGE_RXABORT) + except: + try: + self._close() + except: + # ignore any exception when closing the port + # also to keep original exception that happened when setting up + pass + self.hComPort = None + raise + else: + self._isOpen = True - self._overlappedRead = win32.OVERLAPPED() - self._overlappedRead.hEvent = win32.CreateEvent(None, 1, 0, None) - self._overlappedWrite = win32.OVERLAPPED() - #~ self._overlappedWrite.hEvent = win32.CreateEvent(None, 1, 0, None) - self._overlappedWrite.hEvent = win32.CreateEvent(None, 0, 0, None) def _reconfigurePort(self): """Set communication parameters on opened port.""" @@ -189,17 +204,26 @@ class Win32Serial(SerialBase): #~ def __del__(self): #~ self.close() + + def _close(self): + """internal close port helper""" + if self.hComPort: + # Restore original timeout values: + win32.SetCommTimeouts(self.hComPort, self._orgTimeouts) + # Close COM-Port: + win32.CloseHandle(self.hComPort) + if self._overlappedRead is not None: + win32.CloseHandle(self._overlappedRead.hEvent) + self._overlappedRead = None + if self._overlappedWrite is not None: + win32.CloseHandle(self._overlappedWrite.hEvent) + self._overlappedWrite = None + self.hComPort = None + def close(self): """Close port""" if self._isOpen: - if self.hComPort: - # Restore original timeout values: - win32.SetCommTimeouts(self.hComPort, self._orgTimeouts) - # Close COM-Port: - win32.CloseHandle(self.hComPort) - win32.CloseHandle(self._overlappedRead.hEvent) - win32.CloseHandle(self._overlappedWrite.hEvent) - self.hComPort = None + self._close() self._isOpen = False def makeDeviceName(self, port): -- cgit v1.2.1