Instrument Control SCPI

I am currently trying to create 2x test Rigs using the following bits of kit…

Operating System - Raspberry Pi 400 0r Raspberry 4B running Basic Raspbian

Digital to Analogue convertor - MCP4725 12 Bit DAC

Analogue to Digital convertor - ADS1115 16 Bit I2C ADC

Opto Isolation circuit for Pi protection while using the ADC & DAC

Power Supply - Farnell H 60/50

Electronic load - APM EL200VDC2400W or APM EL00VDC4400W (single mode, not on parallel mode)

The test procedure needs to be run direct from a script and displayed through a GUI to Select a Model Under test from a list or Manually type the Model number in & all test figures/parameters should then be pulled from a variable Table.

I have used NI max control panel on windows 10 PC to check comms and a web browser to get the addressing.

2400W serial address : USB::0x0952::0x6400::0180042227000001::RAW

2400W TCP IP address : TCPIP::162.168.1.201::5025::SOCKET

4400W serial address : USB::0x0952::0x6400::0161722226000002::RAW

4400W TCP IP address : TCPIP::162.168.1.202::5025::SOCKET

So far, I have set Static Ip Addresses on the 2 loads as 192.168.1.201 & 192.168.1.202 while my Raspberry Pi is sat on 192.168.1.105.the devices are connected through a network switch and I am able to ping both Electronic loads from both my Raspberry Pi and my Windows PC.

I am currently communicating with the devices using USB - Serial adapter & generic ID of the Instrument for now.

**>>>*import pyvisa as visa*

<i>*>>>*import time

*>>>*rm = visa.ResourceManager('@py')

*>>>print(*rm.list_resources())

('ASRL/dev/ttyUSB0::INSTR', 'ASRL/dev/ttyAMA0::INSTR')</i>

<i>*>>>*PSU = rm.open_resource('ASRL/dev/ttyUSB0::INSTR')</i>

**>>>*PSU*

<i><'SerialInstrument'('ASRL/dev/ttyUSB0::INSTR')></i>

*>>> print(psu.query('*IDN?'))*

*APM,EL200VDC4400W,0161722226000002,V100R009C01/V100R006C01/V100R005C01,ADVANCED*

I was unable to successfully connect using specific TCP or USB.

The problem I have is I can send a measure/fetch command to the Electronic load for a Voltage or Current & most of the time instead of getting the value back I am simply receiving “SET OK”.

If I repeat the same measure/fetch function 2-3 times I do get the value.

Below samples all typed consecutively…

*>>> psu.query('spec:test?')*

*'OFF\n'*

*>>> psu.query('spec:curr:l?')*

*'OFF\n'*

*>>> psu.query('spec:curr:l?')*

*'OFF\n'*

*>>> psu.query('spec:curr:h?')*

*'0,%\n'*

*>>> psu.query('spec:curr:l?')*

*'0,%\n'*

*>>> psu.query('spec:curr:c?')*

*'0,%\n'*

*>>> psu.query('spec:curr:c?')*

*'0,%\n'*

*>>> psu.query('spec:curr:c')*

*'0,A\n'*

*>>> psu.query('spec:curr:c?')*

*'0,A\n'*

*>>> psu.query('spec:curr:h?')*

*'0,A\n'*

*>>> psu.query('spec:curr:l?')*

*'0,%\n'*

*>>> print(psu.query('FETC:CURR?'))*

*0,%*

*>>> psu.query('FETC:CURR?')*

*'1.9962\n'*

*>>> psu.query('FETC:volt?')*

*'1.9963\n'*

*>>> psu.query('FETC:volt?')*

*'11.9852\n'*

I am assuming at the moment that the issue is merely down to the termination/end characters being mismatched.

You will see a few lines of code where I am trying to counter this but so far not successful in the following attempts.

<i>el.term_chars = 2

el.term_chars = \r\n

el.end_input = last_bit_end_input</i>

el.end_input = term_chars_end_input

I was also thinking The below Extract on page 2 of the " SCPI Communication Protocol for EL Series High-density Programmable DC Electronic Load" manual could be what is causing the problem?
Note 1 pressing the Enter Key

SCPI Command Descriptions

SCPI is a programmable language standard designed especially for programmable instruments. It defines how to communicate with the instruments from an external computer. The APM programmable DC Electronic Load uses SCPI programming language with two categories of commands : basic commands (IEEE-488.2 common commands), and APM programmable DC Electronic Load.

Note: 1) Press the [Enter] key before sending each command.

  1. There are two ways to send commands containing “” in the commands.

For example,

SYSTem:ERRor[:NEXT]? send : SYSTem:ERRor? or SYSTem:ERRor:NEXT?.

My coding skills are very basic and at most self taught.

Originally I was taught to code with drawing packages (pen up/pen down…) & HTML coding about 20 years ago.

I have also covered Robot and PLC programming over last 2 decades

Jack of all Master on none.

I have created A Dropbox for all my playing around code & Manuals.

test.py, test2.py, test3.py are the scripts I’m using to simply connect to the electronic load and pull some current & voltage Readings back.

Trying to keep it simple I kept everything as single line instruction.

measure.py is the resulting python output from the run scripts within terminal including visa debugging.

Kindest Regards

Dan

2 Likes

Hi Dan,

Definitely sounds like the answer is in the instruction set manual.

Just to confirm, are you able to connect and receive something back? Was this through the serial connection?

James and Michael have some good replies on these topics :slight_smile:

1 Like

Hi Liam

Thanks for your response.

Just to clarify I have been able to connect the APM Loads to my windows PC and using NI Max software I am able to communicate with the Electronic Load, sending & receiving feedback.

This the same for both TCP & USB through USB-232 adapter.

I am also able to write the line code in Raspberry Pi Terminal a line at a time and successfully retrieve the Voltages and Currents from the Loads with
el.query(‘MEAS:VOLT?’)
&
el.query(‘FETC:VOLT?’)

However I still get false reads sometimes with this method even when putting time.sleep(0.5) before/after these commands.

So when I try to run the script itself its just returning “SET_OK” instead of the required values.
This is shown in the Measure.py file in the Dropbox Link above.

Kind regards
Dan

1 Like

Hi Dan,

Just to clarify, your problem was that running the commands from a Python terminal works, but running them in the script fails?

Does increasing the delay to a few seconds do anything? What about "up-arrow"ing the query commands in the terminal to spam them quickly, do any fail?

When you say false readings, are they wrong values, or just replaced with “SET_OK” acknowledgments.

Sorry if I’m not drilling down on this issue, I haven’t worked with PyVISA before, but I do own a Rigol PSU that I can test with if need be.

Hope we can get to the bottom of this one!
-James

This is definitely a weird issue

Hi James

Thank you for response.

Yes that is pretty much the issue I have.
The False readings are either ‘SET OK’ or the measured Value being placed in the Wrong Location.
I edited the below script so all time.sleep commands were 5 seconds to get the Shell output below.
I have also added the Terminal output when inputting a line at a time.

so here is my script at the moment.

import pyvisa as visa #Bring in the VISA library
import time #Set timing Ref
rm = visa.ResourceManager('@py') #Create a resource manager
rm.list_resources() #see attached devices
#el = rm.open_resource('ASRL/dev/ttyUSB1::INSTR') #Mask the Electronic Load by name over USB - 232.
el = rm.open_resource('TCPIP0::192.168.1.202::5025::SOCKET') #Mask the Electronic Load by name over LAN.
el.read_termination  = '\n'
el.write_termination = '\n'
print(el.query('*IDN?')) #Return the Electronic Load ID string to tell us it's there
time.sleep (.5)
el.write('SYST:REM')  #swich to remote mode
#print(el.query('SYST:cOMM:PROT?'))
el.write('MODE CCH')
el.write('SYST:COMM:PROT 1')
el.write('LOAD:stat 0') #Ensure Electronic load is safe
el.write('SYST:*RST')#Reset the Electronic Load to Default
el.write('CURR:STAT:A 0')
el.write('CURR:STAT:B 0')
time.sleep (1.5)
#el.query('*OPC?')
el.query('meas:volt?') #Read the Output voltage from the Electronic Load / UUT
time.sleep (1.5)   
#el.query('*OPC?')
#el.query('*WAI')
el.query('fetch:volt?')
V1 = el.query('read:volt?')
time.sleep (1.5)
#el.query('*OPC?')
#print(V1.rstrip() +'V')
print (('Voltage with No Load\n')+V1.rstrip()+'Volts\n')
#time.sleep (1.5)
el.write('load:stat 1')
el.query('*OPC?')
print('Load status\n'+el.query('LOAD:STAT?'))
#print(el.query('*OPC?'))
el.write('CURR:STAT:A 1.3')
el.write('CURR:STAT:B 2.8')
el.write('CURR:STAT A')
#print(el.query('*OPC?'))
time.sleep (1.5)
#print(el.query('*sre?'))
#el.query('*OPC?')
el.query('meas:volt?') #Read the Output voltage from the Electronic Load / UUT
#el.write('*OPC')
#print(el.query('*OPC?'))
time.sleep (1.5)
V2 = el.query('FETC:volt')
#el.write('*OPC')
time.sleep (1.5)
#print (V2.rstrip() +'V') 
#el.query('*OPC?')
el.query('meas:curr?') #Read the Output voltage from the Electronic Load / UUT
#el.write('*OPC')
#el.query('*OPC?')
time.sleep (1.5)
#print(el.query('*OPC?'))
C1 = el.query('fetc:curr?')
time.sleep (1.5)
#el.query('*OPC?')
print (('Voltage under Load\n')+V2.rstrip()+'V\n''@'+C1.rstrip()+'A\n') 
el.write('CURR:STAT:A 0')
el.write('CURR:STAT:B 0')
#var = el.query('STAT:OPER:COND?')
#print (var)
el.write ('load:stat 0')
el.write('SYST:loc')  #swich to local mode
el.close

and this is the shell response running through Thonny…

>>> %Run test3.py
APM,EL200VDC4400W,0161722226000002,V100R009C01/V100R006C01/V100R005C01,ADVANCED
Voltage with No Load
OKVolts

Load status
SET_OK
Voltage under Load
12.1905V
@SET_OKA

>>> %Run test3.py
APM,EL200VDC4400W,0161722226000002,V100R009C01/V100R006C01/V100R005C01,ADVANCED
Voltage with No Load
SET_OKVolts

Load status
SET_OK
Voltage under Load
SET_OKV
@12.1907A

See how the Load Status OK has been put where V1 should be(Voltage with no Load) in first run & the singular Voltage Reading I did get has been Places in C1 (Current Reading) in the second test run.

The Change I made between these 2 runs was to change…

el.read_termination = ‘\n’
el.write_termination = ‘\n’

to

el.read_termination = os.linesep
el.write_termination = os.linesep

The Only Reason for trying this is I have noticed between using NI max & the USR-TCP2232-Test.exe software that the Manufacturer supplied me with that NI-max is adding \n automatically when sending commands. However the USR software does not and if I add \n to the end of the command it still wont return the IDN but if I press Enter a the end of the command it works.

\n is enter I thought?

And Finally The Terminal text…

pi@raspberrypi:~ $ python
Python 3.9.2 (default, Mar 12 2021, 04:06:34) 
[GCC 10.2.1 20210110] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> import pyvisa as visa
>>> import os
>>> import time
>>> rm = visa.ResourceManager('@py')
>>> rm.list_resources() 
('ASRL/dev/ttyUSB0::INSTR', 'ASRL/dev/ttyAMA0::INSTR')
>>> el = rm.open_resource('TCPIP0::192.168.1.202::5025::SOCKET')
>>> el.read_termination  = os.linesep
>>> el.write_termination = os.linesep
>>> print(el.query('*IDN?'))
APM,EL200VDC4400W,0161722226000002,V100R009C01/V100R006C01/V100R005C01,ADVANCED
>>> el.write('SYST:REM')
9
>>> el.write('MODE CCH')
9
>>> el.write('SYST:COMM:PROT 1')
17
>>> el.query('meas:volt?')
'SET_OK'
>>> el.query('meas:volt?')
'SET_OK'
>>> el.query('meas:volt?')
'OK'
>>> el.query('meas:volt?')
'12.191'
>>> 

I had to measure 4 times to get value.

Kind Regards
Dan

1 Like