ΣSigmaStudio Ask AI Русский Log in

SigmaStudio Python COM argument list pass reference to return a byte array

SigmaDSP & SigmaStudio Brewster Aug 18, 2020 00:00 5 replies Original on forum ↗
Subscribe
Brewster Question
Aug 18, 2020 00:00

Hoping someone might have figured this out (or knows how to figure this out) previously as I'm down to trial and error now and it's been nothing but errors. I think this question applies to some of the standard SS com server functions that return arrays in the arguments, but what I found so far hasn't worked for my case. Specifically I eventually tried something like:

arg3 = VARIANT(pythoncom.VT_BYREF | pythoncom.VT_ARRAY | pythoncom.VT_VARIANT, [])
from https://wiki.analog.com/resources/tools-software/sigmastudio/toolbox/filters/firfilter

but it fails too.

I realize this is more a Python/COM question than a SS question, but I'm definitely at the beginning of the learning curve, and COM seems to act like a black box, I haven't found a way to trace in to it in a meaningful way yet. I did turn on the debug flags in dynamic.py but that didn't offer any insight.

I'm trying to call a function from the A2B SigmaStudio add-on:

public bool A2B_MASTER_REGISTER_READ(string ICName, int masterAddress, int readAddress, int readNumberBytes, ref byte[] bytesRead)

and I tried this (and various combinations including adding VT_VARIANT):

readdata = []
readdata_v = VARIANT( pythoncom.VT_ARRAY | pythoncom.VT_BYREF | pythoncom.VT_UI1, readdata)
stat = server.A2B_MASTER_REGISTER_READ("IC 1", 0x68, 0x02, 1, readdata_v)

But what I get back from a print(readdata_v):

win32com.client.VARIANT(24593, 'IC 1')

I'm baffled how the first argument is ending up there.

Every other reasonable combination of VARIANT flags that I've tried have produced some sort of OLE unknown type error, like:

pywintypes.com_error: (-2147024809, 'The parameter is incorrect.', (0, None, 'Specified OLE variant is invalid.', None, 0, -2147024809), None)

Any other functions that return the value or only pass values all have worked fine, it's just this one case where the returned information is by a pointer to an array, and that's foreign to Python.

Thanks for any suggestions.

Brewster

Edit Notes
fixed typos and added fail message example

[edited by: Brewster at 9:08 PM (GMT -4) on 18 Aug 2020]

sigma studio

com

win32com

python

ADIApproved Reply
Aug 19, 2020 00:00

Hello,

Debugging these COM errors is not a simple task... As you've noted, the layers between Python and SigmaStudio are somewhat black boxes with cryptic errors.

I think I have a suspicion of what is going on. In one of the previous blocks, I discovered an unusual phenomenon where the returned values are all flipped left to right. That is, in a function which takes arguments

string ICName, int masterAddress, int readAddress, int readNumberBytes, ref byte[] bytesRead

I needed to recall ICName to access bytesRead, recall readAddress to access readNumberBytes... Etc.

I'll check this theory on the function in question tomorrow.

Joshua

ADIApproved Reply
Aug 20, 2020 00:00

Hello,
Please try the following and let me know the result. If I'm right, the print of ic_name will actually contain your register value. I haven't hooked up the A2B hardware yet to test this. If my assumption is incorrect I will set up the hardware.

ic_name = VARIANT(pythoncom.VT_BYREF | pythoncom.VT_BSTR, "IC 1")
readdata = []
readdata_v = VARIANT( pythoncom.VT_ARRAY | pythoncom.VT_BYREF | pythoncom.VT_UI1, readdata)
stat = server.A2B_MASTER_REGISTER_READ(ic_name, 0x68, 0x02, 1, readdata_v)
print(ic_name)

Brewster Reply
Aug 22, 2020 00:00

Hi Joshua,

Sorry for the delayed response. Didn't do what you hoped, here's the code:

readdata = bytearray(8)
readdata_v = VARIANT( pythoncom.VT_ARRAY | pythoncom.VT_BYREF | pythoncom.VT_UI1, readdata)
ic_name = VARIANT( pythoncom.VT_BYREF| pythoncom.VT_BSTR , "IC 1")
stat = server.A2B_MASTER_REGISTER_READ("IC 1", 0x68, 0x02, 1, readdata_v )

print('return is')
print(stat)
print('readdata_v is')
print(readdata_v)
print('ic_name is')
print(ic_name)
And the output is:

return is
True
readdata_v is
win32com.client.VARIANT(24593, 'IC 1')
ic_name is
win32com.client.VARIANT(16392, 'IC 1')

For yuks I tried a couple of other VARIANT types for ic_name but it still returns 'IC 1'.

Brewster

ADIApproved Reply
Aug 23, 2020 00:00

Let's try this one more time, the first argument in line 4 should be set to ic_name rather than "IC 1":

readdata = bytearray(8)
readdata_v = VARIANT( pythoncom.VT_ARRAY | pythoncom.VT_BYREF | pythoncom.VT_UI1, readdata)
ic_name = VARIANT( pythoncom.VT_BYREF| pythoncom.VT_BSTR , "IC 1")
stat = server.A2B_MASTER_REGISTER_READ(ic_name, 0x68, 0x02, 1, readdata_v )

print('return is')
print(stat)
print('readdata_v is')
print(readdata_v)
print('ic_name is')
print(ic_name)

Brewster Reply
Aug 23, 2020 00:00

<doh> Guess I took an extra 'dumb' pill yesterday...

I definitely owe you a beer or 3 for figuring this one out:

ic_name is
win32com.client.VARIANT(16392, memory at 0x00000000038A1E80)
ic_name.value[0] is
173

(173 being 0xAD, the vendor ID...there should have been < and > around the first print value but I can't figure out how this site wants them escaped to make them print.)

Though I guess the million $ question is this a bug somewhere on the SIgmaStudio side for not handling the way Python uses COM or is it a bug in Win32com?

For now this unsticks me but longer term probably need to get to the bottom of it since more and more people are using Python?

Thanks,

Brewster