Error on Python serial import
Question:
When I try to import the serial I get the following error:
Traceback (most recent call last):
File "C:Documents and Settingseduardo.pereiraworkspacethgspeaktst.py", line 7, in <module>
import serial
File "C:Python27libsite-packagesserial__init__.py", line 27, in <module>
from serial.serialwin32 import Serial
File "C:Python27libsite-packagesserialserialwin32.py", line 15, in <module>
from serial import win32
File "C:Python27libsite-packagesserialwin32.py", line 182, in <module>
CancelIoEx = _stdcall_libraries['kernel32'].CancelIoEx
File "C:Python27libctypes__init__.py", line 375, in __getattr__
func = self.__getitem__(name)
File "C:Python27libctypes__init__.py", line 380, in __getitem__
func = self._FuncPtr((name_or_ordinal, self))
AttributeError: function 'CancelIoEx' not found
I have installed the latest version of pySerial, Python 2.7 runing on a WinXP laptop. Tried everywhere and found no similar problem. Is there any solution for that?
Thanks in advance…
Answers:
The version of pySerial that you’re using is trying to call a function that’s only available in Windows Vista, whereas you’re running Windows XP.
It might be worth experimenting with using an older version of pySerial.
The code in question was added to pySerial on 3 May 2016, so a version just prior to that might be a good start.
Older versions seem unavailable. But, this worked for me (assuming nanpy version 3.1.1):
- open file libsite-packagesserialserialwin32.py
- delete methods
_cancel_overlapped_io()
, cancel_read()
, cancel_write()
in lines 436-455 nearly at the botton of the file
- change method _close() als follows:
(Python)
def _close(self):
"""internal close port helper"""
if self._port_handle is not None:
# Restore original timeout values:
win32.SetCommTimeouts(self._port_handle, self._orgTimeouts)
# Close COM-Port:
if self._overlapped_read is not None:
win32.CloseHandle(self._overlapped_read.hEvent)
self._overlapped_read = None
if self._overlapped_write is not None:
win32.CloseHandle(self._overlapped_write.hEvent)
self._overlapped_write = None
win32.CloseHandle(self._port_handle)
self._port_handle = None
Additionally, create a non-default serial connection when starting the communication, otherwise you’ll be bound to some linux device:
a = ArduinoApi(SerialManager("COM5:"))
for i in range(10):
a.pinMode(13, a.OUTPUT)
a.digitalWrite(13, a.HIGH)
# etc.
And in serialwin32.py comments
#CancelIoEx = _stdcall_libraries['kernel32'].CancelIoEx
#CancelIoEx.restype = BOOL
#CancelIoEx.argtypes = [HANDLE, LPOVERLAPPED]
There is no obvious reason why CancelIO was replaced with the cross-thread version CancelIOex, which allows code in one thread to cancel IO in another thread. Certainly cpython 2.x is single threaded.
To get pySerial to run on python 2.7 on Win2K, I just changed CancelIOex in serial back to CancelIO.
When I try to import the serial I get the following error:
Traceback (most recent call last):
File "C:Documents and Settingseduardo.pereiraworkspacethgspeaktst.py", line 7, in <module>
import serial
File "C:Python27libsite-packagesserial__init__.py", line 27, in <module>
from serial.serialwin32 import Serial
File "C:Python27libsite-packagesserialserialwin32.py", line 15, in <module>
from serial import win32
File "C:Python27libsite-packagesserialwin32.py", line 182, in <module>
CancelIoEx = _stdcall_libraries['kernel32'].CancelIoEx
File "C:Python27libctypes__init__.py", line 375, in __getattr__
func = self.__getitem__(name)
File "C:Python27libctypes__init__.py", line 380, in __getitem__
func = self._FuncPtr((name_or_ordinal, self))
AttributeError: function 'CancelIoEx' not found
I have installed the latest version of pySerial, Python 2.7 runing on a WinXP laptop. Tried everywhere and found no similar problem. Is there any solution for that?
Thanks in advance…
The version of pySerial that you’re using is trying to call a function that’s only available in Windows Vista, whereas you’re running Windows XP.
It might be worth experimenting with using an older version of pySerial.
The code in question was added to pySerial on 3 May 2016, so a version just prior to that might be a good start.
Older versions seem unavailable. But, this worked for me (assuming nanpy version 3.1.1):
- open file libsite-packagesserialserialwin32.py
- delete methods
_cancel_overlapped_io()
,cancel_read()
,cancel_write()
in lines 436-455 nearly at the botton of the file - change method _close() als follows:
(Python)
def _close(self):
"""internal close port helper"""
if self._port_handle is not None:
# Restore original timeout values:
win32.SetCommTimeouts(self._port_handle, self._orgTimeouts)
# Close COM-Port:
if self._overlapped_read is not None:
win32.CloseHandle(self._overlapped_read.hEvent)
self._overlapped_read = None
if self._overlapped_write is not None:
win32.CloseHandle(self._overlapped_write.hEvent)
self._overlapped_write = None
win32.CloseHandle(self._port_handle)
self._port_handle = None
Additionally, create a non-default serial connection when starting the communication, otherwise you’ll be bound to some linux device:
a = ArduinoApi(SerialManager("COM5:"))
for i in range(10):
a.pinMode(13, a.OUTPUT)
a.digitalWrite(13, a.HIGH)
# etc.
And in serialwin32.py comments
#CancelIoEx = _stdcall_libraries['kernel32'].CancelIoEx
#CancelIoEx.restype = BOOL
#CancelIoEx.argtypes = [HANDLE, LPOVERLAPPED]
There is no obvious reason why CancelIO was replaced with the cross-thread version CancelIOex, which allows code in one thread to cancel IO in another thread. Certainly cpython 2.x is single threaded.
To get pySerial to run on python 2.7 on Win2K, I just changed CancelIOex in serial back to CancelIO.