amosborne / rigol-ds1000z

Python library for interfacing with Rigol DS1000Z series oscilloscopes.
https://amosborne.github.io/rigol-ds1000z/
MIT License
16 stars 4 forks source link

Error: Could not open VISA library #2

Open MichaDit opened 1 year ago

MichaDit commented 1 year ago

Traceback (most recent call last): File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\runpy.py", line 197, in _run_module_as_main return _run_code(code, main_globals, None, File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\runpy.py", line 87, in _run_code exec(code, run_globals) File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\Scripts\rigol-ds1000z.exe__main.py", line 7, in File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\site-packages\rigol_ds1000z\cli.py", line 59, in main tui.run(args.visa) File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\site-packages\rigol_ds1000z\app\tui.py", line 227, in run Rigol_DS100Z_TUI.run(visa=visa, title="rigol-ds1000z") File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\site-packages\textual\app.py", line 206, in run asyncio.run(run_app()) File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\asyncio\runners.py", line 44, in run return loop.run_until_complete(main) File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\asyncio\base_events.py", line 647, in run_until_complete return future.result() File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\site-packages\textual\app.py", line 203, in run_app app = cls(screen=screen, driver_class=driver, **kwargs) File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\site-packages\rigol_ds1000z\app\tui.py", line 28, in init self.oscope = Rigol_DS1000Z(visa).open() File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\site-packages\rigol_ds1000z\src\oscope.py", line 28, in init visas = find_visas() File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\site-packages\rigol_ds1000z\utils.py", line 21, in find_visas visa_manager = ResourceManager(visa_backend) File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\site-packages\pyvisa\highlevel.py", line 2992, in new visa_library = open_visa_library(visa_library) File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\site-packages\pyvisa\highlevel.py", line 2904, in open_visa_library return cls(argument) File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\site-packages\pyvisa\highlevel.py", line 175, in new__ raise OSError("Could not open VISA library:\n" + "\n".join(errs)) OSError: Could not open VISA library:

There is no IVI driver installed, only pyvisa-py. In find_visas() the exception catches on LibraryError, but here it is OSError.

With IVI driver:

Traceback (most recent call last): File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\runpy.py", line 197, in _run_module_as_main return _run_code(code, main_globals, None, File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\runpy.py", line 87, in _run_code exec(code, run_globals) File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\Scripts\rigol-ds1000z.exe__main__.py", line 7, in File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\site-packages\rigol_ds1000z\cli.py", line 59, in main tui.run(args.visa) File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\site-packages\rigol_ds1000z\app\tui.py", line 227, in run Rigol_DS100Z_TUI.run(visa=visa, title="rigol-ds1000z") File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\site-packages\textual\app.py", line 206, in run asyncio.run(run_app()) File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\asyncio\runners.py", line 44, in run return loop.run_until_complete(main) File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\asyncio\base_events.py", line 647, in run_until_complete return future.result() asyncio.exceptions.CancelledError

amosborne commented 1 year ago

Hello-- I'm sorry you are having this issue, I'm happy to help resolve it. Would you mind telling me a little bit more: what Python version are you using and what command(s) did you run?

MichaDit commented 1 year ago

Sorry for the late response. Just executing rigol-ds1000z.exe from Powershell, adding -v TCPIP0::192.168.1.26::INSTR or TCPIP0::192.168.1.26::5555::SOCKET to connect directly does not change anything. The connection via pyvisa to the instrument definitly works.

Attached the requested infos (from pc w/o ivi):

Machine Details: Platform ID: Windows-10-10.0.19044-SP0 Processor: Intel64 Family 6 Model 165 Stepping 2, GenuineIntel

Python: Implementation: CPython Executable: C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\python.exe Version: 3.9.13 Compiler: MSC v.1929 64 bit (AMD64) Bits: 64bit Build: May 17 2022 16:36:42 (#tags/v3.9.13:6de2ca5) Unicode: UCS4

PyVISA Version: 1.13.0

Backends: ivi: Version: 1.13.0 (bundled with PyVISA) Binary library: Not found py: Version: 0.5.3 ASRL INSTR: Available via PySerial (3.5) USB INSTR: PyUSB does not seem to be properly installed. Please refer to PyUSB documentation and install a suitable backend like libusb 0.1, libusb 1.0, libusbx, libusb-win32 or OpenUSB. No backend available USB RAW: PyUSB does not seem to be properly installed. Please refer to PyUSB documentation and install a suitable backend like libusb 0.1, libusb 1.0, libusbx, libusb-win32 or OpenUSB. No backend available TCPIP INSTR: Available TCPIP SOCKET: Available GPIB INSTR: Please install linux-gpib (Linux) or gpib-ctypes (Windows, Linux) to use this resource type. Note that installing gpib-ctypes will give you access to a broader range of funcionality. No module named 'gpib'

Package Version


asgiref 3.6.0 async-timeout 4.0.2 attrs 22.2.0 black 23.1.0 click 8.1.3 colorama 0.4.6 colorednoise 2.1.0 commonmark 0.9.1 contourpy 1.0.7 cycler 0.11.0 Django 4.1.7 exceptiongroup 1.1.1 fonttools 4.39.2 ghp-import 2.1.0 ifaddr 0.2.0 importlib-metadata 6.1.0 importlib-resources 5.12.0 iniconfig 2.0.0 Jinja2 3.1.2 kiwisolver 1.4.4 linkify-it-py 2.0.0 Markdown 3.4.1 markdown-it-py 2.2.0 MarkupSafe 2.1.2 matplotlib 3.7.1 mdit-py-plugins 0.3.5 mdurl 0.1.2 mergedeep 1.3.4 mkdocs 1.4.2 mkdocs-exclude 1.0.2 mypy-extensions 1.0.0 numpy 1.24.2 packaging 23.0 pandas 1.5.3 pathspec 0.11.1 Pillow 9.4.0 pip 23.0.1 platformdirs 3.1.1 pluggy 1.0.0 psutil 5.9.4 Pygments 2.14.0 pyparsing 3.0.9 pyserial 3.5 pytest 7.2.2 python-dateutil 2.8.2 pytz 2022.7.1 pyusb 1.2.1 PyVISA 1.13.0 PyVISA-py 0.5.3 PyYAML 6.0 pyyaml_env_tag 0.1 rich 12.6.0 rigol-ds1000z 0.3.0 Rigol1000z-remote 0.3.1 scipy 1.10.1 setuptools 67.6.0 si-prefix 1.2.2 six 1.16.0 sqlparse 0.4.3 textual 0.1.18 tomli 2.0.1 tqdm 4.65.0 typing_extensions 4.5.0 tzdata 2022.7 uc-micro-py 1.0.1 watchdog 2.3.1 zeroconf 0.47.3 zipp 3.15.0

amosborne commented 1 year ago

Got it, thank you. You must be connecting over Ethernet, not USB?

Let me run some tests on my end and get back to you tomorrow.

MichaDit commented 1 year ago

Got it, thank you. You must be connecting over Ethernet, not USB?

Yes, via Ethernet, my other PC can connect via USB too, if that helps.

amosborne commented 1 year ago

I'm not sure I ever tested with Ethernet, to be honest. I was always using USB-- that's my bad.

You may be the first person (other than me) to ever try to use this package without installing the IVI backend. We might be able to find the issue sooner if you wanted to try using USB instead of Ethernet. You would need to install libusb per the pyUSB documentation. This way we can know whether the issue is the general lack of an IVI backend versus the difference between Ethernet and USB.

In the meantime time I'll go dig out a scope and an Ethernet cable.

amosborne commented 1 year ago

I've got a hotfix branch for you over here: 297bfc9

Of note, the VISA TCPIP resource address for my instrument is of the form TCPIP0::192.168.0.227::inst0::INSTR. pyVISA appears to not be capable of identifying unknown LAN-connected VISA resources on its own; I think you will have to specify the resource address. (edited)

I haven't pushed it to PyPI yet because the pyUSB backend appears to be misbehaving now. I'm not really sure what changed... tests that passed for me a few months ago are now failing intermittently.

Anyways, let me know if the LAN connection works for you.

MichaDit commented 1 year ago

Of note, the VISA TCPIP resource address for my instrument is of the form TCPIP0::192.168.0.227::inst0::INSTR. pyVISA appears to not be capable of identifying unknown LAN-connected VISA resources on its own; I think you will have to specify the resource address. (edited)

It is possible to connect the instrument w/ or w/o resource address ::inst0. psutil is needed to discover instruments over TCP/IP, but could be it works only in conjunction with ivi backend. Just a note: the socket connection is much faster than the usual TCP/IP.

I haven't pushed it to PyPI yet because the pyUSB backend appears to be misbehaving now. I'm not really sure what changed... tests that passed for me a few months ago are now failing intermittently.

There is a restriction of the instrument, if USB is physically connected, LAN does not work anymore, even if there is no active (VISA) connection over USB... There is another bug on USB regarding reading of waveforms...

Anyways, let me know if the LAN connection works for you.

Could you give me a hint how I can test the hotfix 297bfc9?

amosborne commented 1 year ago

OK, thanks I will look at psutil as well as using a socket connection. You're correct, you don't need the ::isnt0.

There is another bug on USB regarding reading of waveforms...

In my code or in the instrument firmware?

Could you give me a hint how I can test the hotfix 297bfc9?

You would need to pull the branch into your fork, and then run locally from there. I use Poetry for package management and virtual environments; you would need to install Poetry, then run poetry install to install the dependencies then run poetry run rigol-ds1000z -v ... to connect to your instrument.

I'm still mucking around with some changes on my end-- but if you're interested in trying it out in the meantime I'm all for it.

MichaDit commented 1 year ago

First, USB is now working with the hotfix 297bfc9, but TCP/IP (and autodiscovery) still not (TB below).

Poetry had some complaints about packages, but is a known issue. After fixing the complaints and starting with -v USB0::[device] still an error as it cannot access a serial port (TB below). To fix this the drivers for the COM-Ports were deleted. After that it eventually started the TUI w/o errors (no test if function works).

TCP/IP error:

Traceback (most recent call last): File "", line 1, in File "D:\Dokumente\Software-Projekte\Rigol TUI dev\rigol_ds1000z\cli.py", line 59, in main tui.run(args.visa) File "D:\Dokumente\Software-Projekte\Rigol TUI dev\rigol_ds1000z\app\tui.py", line 227, in run Rigol_DS100Z_TUI.run(visa=visa, title="rigol-ds1000z") File "C:\Users\Fuchks\AppData\Local\pypoetry\Cache\virtualenvs\rigol-ds1000z-wKTeWv7b-py3.9\lib\site-packages\textual\app.py", line 206, in run asyncio.run(run_app()) File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\asyncio\runners.py", line 44, in run return loop.run_until_complete(main) File "C:\Program Files (x86)\Microsoft Visual Studio\Shared\Python39_64\lib\asyncio\base_events.py", line 647, in run_until_complete return future.result() File "C:\Users\Fuchks\AppData\Local\pypoetry\Cache\virtualenvs\rigol-ds1000z-wKTeWv7b-py3.9\lib\site-packages\textual\app.py", line 203, in run_app app = cls(screen=screen, driver_class=driver, **kwargs) File "D:\Dokumente\Software-Projekte\Rigol TUI dev\rigol_ds1000z\app\tui.py", line 28, in init self.oscope = Rigol_DS1000Z(visa).open() File "D:\Dokumente\Software-Projekte\Rigol TUI dev\rigol_ds1000z\src\oscope.py", line 53, in open self.visa_rsrc = ResourceManager(self.visa_backend).open_resource( AttributeError: 'Rigol_DS1000Z' object has no attribute 'visa_backend'

COM-Port error:

\AppData\Local\pypoetry\Cache\virtualenvs\rigol-ds1000z-wKTeWv7b-py3.9\lib\site-packages\serial\serialwin32.py", line 64, in open raise SerialException("could not open port {!r}: {!r}".format(self.portstr, ctypes.WinError())) serial.serialutil.SerialException: could not open port 'COM8': OSError(22, 'Das Zeitlimit für die Semaphore wurde erreicht.', None, 121)

For the autodiscovery part, it should not try to connect to all resources that are discovered. Filtering the resources to the DS1000Z USB device and to all TCP/IP devices should get rid of most error sources.

Example for filtering the device list:

rm = visa.ResourceManager()                         # None for autodiscovery, "@py" for PyVISA-py, "@ivi" for IVI (NI-Visa etc)
instruments = rm.list_resources()
ds1z = list([x for x in instruments if ("::DS1Z" in x) | ("TCPIP::" in x)])     # filter for DS1000Z compatible devices

psutil is needed to discover instruments over TCP/IP, but could be it works only in conjunction with ivi backend.

My investigation results: It only works with backend pyvisa-py "@py" and a newer version (0.6.3 works, 0.5.3 not)

There is another bug on USB regarding reading of waveforms...

The instrument has the bug (gives wrong results, maybe only on higher mem depth settings), but it should be accounted for in the TUI.

amosborne commented 1 year ago

Thanks! My latest commit efaacb9cc4fa28ad1a072ee94141fb67a51fb294 adds psutil to do the TCPIP discovery.

I've successfully tested both USBTMC and TCPIP protocols with either the IVI or pvisa-py backends. I see two issues remaining from my testing that I haven't been able to resolve:

  1. There appears to be some sort of resource leak when the pyvisa-py backend does its TCPIP discovery routine with psutil. I tend to get a ResourceWarning indicating that an event loop or socket has not been closed.
  2. I have not been able to establish a TCPIP::()::SOCKET connection with instrument using pyvisa. I think this should be possible, given that I can communicate with the instrument over telnet.

TPCIP responsiveness is much slower relative to USBTMC-- but I think we knew that already.

MichaDit commented 1 year ago
  1. I have not been able to establish a TCPIP::()::SOCKET connection with instrument using pyvisa. I think this should be possible, given that I can communicate with the instrument over telnet.

Try it with explicit write_termination and read_termination (should not hurt for any type of connection):

instrument = rm.open_resource(f"TCPIP0::[IP]::5555::SOCKET", write_termination = '\n', read_termination = '\n')
hiviah commented 1 year ago

So I am having the same issue. USB is broken on Rigol and vendor refuses to fix it (Linux, but generally newer USB host boards). So we are left with Ethernet. Rigol DS1104Z works with DSRemote, but I need to script it to take 1000 traces (see below).

This part works without exception:

import pyvisa
rm = pyvisa.ResourceManager()
instrument = rm.open_resource("TCPIP0::10.2.1.2::INSTR", write_termination = '\n', read_termination = '\n')

But it doesn't open any connection. Rigol_DS1000Z class does not take this argument (it expects str) and I always end up with the same "Could not open VISA library" anyway.

The reason I need 1000 traces automatically is because Chipwhisperer Husky leaks clock into other signals and I need to average noise out (insert "Hal fixing lightbulb" video here). As I found out, SCPI is not a standard, each scope has it different, after trying out several packages I found this one, which should be the closest, but does not seem work with TCP.

Thanks for the package but I've just been through so many hoops, there always seems to be another one.

hiviah commented 1 year ago

So I installed other python 3.10.10 (not via pyenv which is broken), new venv, poetry. Tried the lan-hotfix branch.

Then hardcoded VISA string into utils.py in find_visa as return ("TCPIP0::10.2.1.2::INSTR", "@py").

I can get screenshot, it just takes over minute:

% time rigol-ds1000z -v "TCPIP0::10.2.1.2::INSTR" -d pichcur4.png                                  
rigol-ds1000z -v "TCPIP0::10.2.1.2::INSTR" -d pichcur4.png  1.29s user 0.99s system 3% cpu 1:04.39 total

I can get small sample of waveform (1200), this has probably has something to do with that I need RAW mode to get all the samples: rigol-ds1000z -v "TCPIP0::10.2.1.2::INSTR" -w 4 tjost5.csv

But it's hard without properly specifying TCPIP VISA string in ipython or python script.

Just running rigol-ds1000z without any parameters with the hardcoded VISA string seem to work, but takes very long time, waveform saving is still just 1200 samples (also takes very long, ethernet dump seems it's sending too many repeating commands).

amosborne commented 1 year ago

I'm sorry, it's been a minute since I've looked at this thread. It is hard for me to track how many different issues we are talking about. It seems to me there is one issue in what flexibility is offered by the application to specify VISA addresses, and another in the speed over TCPIP. Is there anything else I've missed?

You also said that USB is broken on the Rigol instrument... how so?

To be honest, I think the majority of the users of this package are Windows/USB (as am I) rather than Linux/LAN. You two are certainly power users. I do not have the bandwidth right now to work this issue on my own but I am happy to receive pull requests with proposed solutions to my code if you are able to discover a robust resolution.

hiviah commented 1 year ago

I'll try to make a PR to fix the ability to add TCPIP via VISA string.

The USB bug I mentioned is detailed here in DSRemote repo - https://gitlab.com/Teuniz/DSRemote/-/issues/5 (in short, USB 2.0 High Speed cannot have endpoint descriptor with 64 bytes wMaxPacketSize as the spec requires 512 bytes, but this is what DS1000Z series do)

Just one question, what parameters are needed to read RAW whole memory so I can test it all together?

import rigol_ds1000z
rr = rigol_ds1000z.Rigol_DS1000Z(visa="TCPIP::10.2.1.2::INSTR")
rr.waveform?
Signature:     
rr.waveform(
    source: Union[int, str, NoneType] = None,
    mode: Optional[str] = None,
    format: Optional[str] = None,
    start: Optional[int] = None,
    stop: Optional[int] = None,
)

From DS1000Z programming manual :WAVeform:STARt will probably expect RAW or something similar in one of the parameters, but unsure whether it's supposed to work in one go (like all 6 Mpts per channel).

amosborne commented 1 year ago

I have not tested this, but in reading the programming manual I would expect the following call to read out the entire internal memory for channel 1: rr.waveform(source=1, mode="RAW", format="BYTE", start=1, stop=120000).