jupyter:
jupytext:
formats: ipynb,md
text_representation:
extension: .md
format_name: markdown
format_version: '1.2'
jupytext_version: 1.3.0
kernelspec:
display_name: Python 3
language: python
name: python3
import redpitaya_scpi as scpi
import numpy as np
import time
# Red Pitaya Stuff
address = "rp-f06897.local"
rp_s = scpi.scpi(address)
dec_exp = np.array([0,3,6,10,13,16])
dec = 2**dec_exp
t_total = np.array([131.072e-6, 1.049e-3, 8.389e-3, 134.218e-3,1.074, 8.590])
dec
ASCII Version
rp_s.tx_txt('ACQ:RST')
rp_s.tx_txt('ACQ:DATA:FORMAT ASCII')
rp_s.tx_txt("ACQ:DEC 1024")
rp_s.tx_txt('ACQ:START')
rp_s.tx_txt('ACQ:TRIG NOW')
while 1:
rp_s.tx_txt('ACQ:TRIG:STAT?')
if rp_s.rx_txt() == 'TD':
break
The above triggers and runs the acquisition.
rp_s.tx_txt('ACQ:DATA:UNITS VOLTS')
rp_s.tx_txt('ACQ:DATA:FORMAT ASCII')
rp_s.tx_txt('ACQ:SOUR1:DATA?')
buf = rp_s.rx_txt()
rp_s.tx_txt('ACQ:SOUR2:DATA?')
buf = rp_s.rx_txt()
print('\nBuffer: \n')
print(buf[0:100])
Binary version
From python file, it seems you need to use the rx_arb()
routine:
https://github.com/RedPitaya/RedPitaya/blob/master/Examples/python/redpitaya_scpi.py
But there are no real instructions on how?
Probably the best documentation of this is the source code of the SCPI server itself:
https://github.com/RedPitaya/RedPitaya/tree/master/scpi-server/src
I think the relevant function is RP_AcqDataOldestAllQ
:
https://github.com/RedPitaya/RedPitaya/blob/master/scpi-server/src/acquire.c
I guess this from here:
https://github.com/RedPitaya/RedPitaya/blob/master/scpi-server/src/scpi-commands.c
{.pattern = "ACQ:SOUR#:DATA?", .callback = RP_AcqDataOldestAllQ,},
OK, wait, I just found this:
https://github.com/RedPitaya/RedPitaya/blob/master/test/scpi/acq_bin_test.py
If I run the above code, my red pitaya then also seems to completely crash...its built-in webserver is no longer responsive.
And all subsequent attempst to connect with ASCII code above also fail until I manage to stop and restart the SCPI server?
Ok, I found some useful code:
https://github.com/RedPitaya/RedPitaya/blob/master/test/scpi/acq_bin_test.py
It shows in principle how to use the binary read.
rp_s.tx_txt('ACQ:DATA:UNITS VOLTS')
rp_s.tx_txt('ACQ:DATA:FORMAT BIN')
rp_s.tx_txt('ACQ:SOUR1:DATA?')
buf = rp_s.rx_arb()
print(buf)
OK, this just does not work.
And now if I try to execute the ASCII code above, I get errors!
---------------------------------------------------------------------------
UnicodeDecodeError Traceback (most recent call last)
<ipython-input-19-5f026792b443> in <module>
2 rp_s.tx_txt('ACQ:DATA:FORMAT ASCII')
3 rp_s.tx_txt('ACQ:SOUR1:DATA?')
----> 4 buf = rp_s.rx_txt()
5
6 print('\nBuffer: \n')
~/Documents/GitHub/gary-misc-notebooks/redpitaya_scpi.py in rx_txt(self, chunksize)
42 msg = ''
43 while 1:
---> 44 chunk = self._socket.recv(chunksize + len(self.delimiter)).decode('utf-8') # Receive chunk size of 2^n preferably
45 msg += chunk
46 if (len(chunk) and chunk[-2:] == self.delimiter):
UnicodeDecodeError: 'utf-8' codec can't decode byte 0xfd in position 4008: invalid start byte
I think that the rx_arb()
code is just not clearing the socket properly.
I did this for a while:
while len(rp_s._socket.recv(1)) > 0:
;
Now I'm not getting anything new from the socket. Let's go back up and try the ASCII code again.
2020-03-15 22:29:31
Ha! The ASCII code works again! Yes!
Let's try just manually reading from the socket ourselves after a binary data request.
def my_read():
# The first thing it sends is always a #
#
# One thing I don't understand here is that even if I do a recv(10),
# I always get only one answer back. Like somehow we are getting a
# terimination signal in the socket? I don't know enough about sockets.
# This doesn't work though for the the number of digits.
# Maybe I need to look in the SCPI server code.
#
buf = rp_s._socket.recv(1)
print(buf.decode('utf-8'))
# The second thing it sends is the number of digits in the byte count.
buf = rp_s._socket.recv(1)
digits_in_byte_count = int(buf)
# The third thing it sends is the byte count
buf = rp_s._socket.recv(digits_in_byte_count)
print(buf.decode('utf-8'))
byte_count = int(buf)
# Now we're ready read! You might thing we would just to a recv(byte_count), but somehow this often
# results in an incomplete transfer? Maybe related to first point above?
# The RP code just reads one byte at a time until it's gets all
# it wants? I tried that and it seems to work. But it is not mega-fast? 317 ms, whereas we should be
# able to get data off much faster than that! It is 65536 bytes = 5 ms at 100 MBit / second.
# But 317 ms is still at least a lot better than the ASCII read which takes 1.3 seconds!
buf = []
while len(buf) != byte_count:
buf.append(rp_s._socket.recv(1))
print(len(buf))
rp_s.tx_txt('ACQ:DATA:UNITS VOLTS')
rp_s.tx_txt('ACQ:DATA:FORMAT BIN')
rp_s.tx_txt('ACQ:SOUR1:DATA?')
my_read()
rp_s.tx_txt('ACQ:SOUR2:DATA?')
my_read()
For if we need to clear the buffer
n = 0
while True:
rp_s._socket.recv(1)
n += 1
print(n)
len(buf)*8/100e6