Hello,
i have problems with getting back data from a library-call to PIGPIO-Library and i2cReadDevice.
Library: The pigpio library
I also downloaded and want to use this:
A Xojo library for pigpio features in Raspberry Pi projects:
The library itself works and simple calls (only with uinteger and not with ByRef) works fine.
But when i try to exchange data (referenced with ByRef) it is not working:
Declaration:
Method Name: i2cReadDevice
Parameters: i2chandle as uinteger, byref value as ptr, count as uinteger
Return-Type: Integer
Scope: Protected
Code:
Dim DebugString As String
Dim i As Integer
Dim r As Integer
Dim Handle As Integer
Dim DataBuffer As New MemoryBlock(256)
Dim DataBufferPtr As ptr = DataBuffer
' Open I2CDevice
Handle=PIGPIO.i2cOpen(1,8)
' Read data from I2C-Device
If Handle >=0 Then
r = pigpio.i2cReadDevice(Handle, DataBufferPtr, 11)
DebugString= "R="+Str(r)+" "
End If
' Close Device
r=PIGPIO.i2cClose(Handle)
' Display result on GUI
For i=0 To 10
DebugString=DebugString+Str(DataBuffer.Byte(i))+" "
Next i
MainWindow.Label1.Text=DebugString
But problem: The DebugString contains only 256 times a null (0x00h), even i get back correct “r-value” and the operation on I2C-bus is executed correctly. When i do a debug (remote-debug) and stop after the call, the MemoryBlock contains also 256 bytes of 0x00h
I think i make a mistake with pointer, it’s not clear to me how to use correctly.
Can anyone help me?
@Marco Bungalski i2cReadDevice can change the value of the Ptr passed ByRef, i.e. DataBufferPtr in this case. You must use the returned value and not the buffer (DataBuffer) that you allocated (which is why you always end up with 256 times null).
Hello Stphane,
can you give me an example how to do this (how to access the returned bytes), please?
@Marco Bungalski Sure. This should work:
[code]Dim DebugString As String
Dim i, r, Handle As Integer
Dim DataBuffer As New MemoryBlock(256) //It may also work with" Dim DataBuffer as MemoryBlock". It depends on pigpio
Handle=PIGPIO.i2cOpen(1,8)
If Handle >=0 Then
r = pigpio.i2cReadDevice(Handle, DataBuffer, 11)
DebugString= “R=”+Str®+" "
r=PIGPIO.i2cClose(Handle)
if DataBuffer<>nil then
For i=0 To 10
DebugString=DebugString+Str(DataBuffer.Byte(i))+" "
Next I
end if
MainWindow.Label1.Text=DebugString
Else
//Display error
End if [/code]
The problem with your code is that you dereferenced (you should Google that to see how common this mistake is) DataBuffer, i.e. you copied its Ptr to DataBufferPtr. As a consequence, if DataBuffer changes its Ptr, DataBufferPtr still holds the old value. Unfortunately, the way MemoryBlocks are converted to Ptr in Xojo does not make it very obvious.
Hello Stphane,
i changed it but i get an error during compiling of line
r = pigpio.i2cReadDevice(Handle, DataBuffer, 11)
Steuerung.Lese_AEingaenge, line 26
Parameter “value” expects type Ptr, but this is class MemoryBlock.
r = pigpio.i2cReadDevice(Handle, DataBuffer, 11)
@Marco Bungalski OK, so this should work:
[code]Dim DebugString As String
Dim i, r, Handle As Integer
Dim DataBuffer As New MemoryBlock(256) //It may also work with" Dim DataBuffer as MemoryBlock". It depends on pigpio
Dim DataBufferPtr as Ptr = DataBuffer //<<<ADDED
Handle=PIGPIO.i2cOpen(1,8)
If Handle >=0 Then
r = pigpio.i2cReadDevice(Handle, DataBufferPtr, 11)
DataBuffer = dataBufferPtr //<<<ADDED
DebugString= “R=”+Str®+" "
r=PIGPIO.i2cClose(Handle)
if DataBuffer<>nil then
For i=0 To 10
DebugString=DebugString+Str(DataBuffer.Byte(i))+" "
Next I
end if
MainWindow.Label1.Text=DebugString
Else
//Display error
End if[/code]
Still not working.
I tried
[code]’ *****************************
’ * Lesen der Analog-Eingnge *
’ *****************************
Dim DebugString As String
Dim i As Integer
Dim r As Integer
Dim Handle As Integer
Dim DataBuffer As MemoryBlock
Dim DataBufferPtr As ptr = DataBuffer
’ Open I2CDevice
Handle=PIGPIO.i2cOpen(1,8)
If Handle >=0 Then
r = pigpio.i2cReadDevice(Handle, DataBufferPtr, 11)
DataBuffer = dataBufferPtr
DebugString= “R=”+Str®+" "
End If
’ Close Device
r=PIGPIO.i2cClose(Handle)
If DataBuffer<>Nil Then
For i=0 To 10
DebugString=DebugString+Str(DataBuffer.Byte(i))+" "
Next i
End If
MainWindow.Label1.Text=DebugString
[/code]
and also with
Dim DataBuffer As new MemoryBlock(256)[/code] instead of [code]Dim DataBuffer As MemoryBlock
With Dim DataBuffer As MemoryBlock
the App hangs with “Event loop” and with Dim DataBuffer As new MemoryBlock(256)
the App terminats with sigHandler: Unhandled signal 11, terminating when the line DebugString=DebugString+Str(DataBuffer.Byte(i))+" "
is executed.
But DataBuffer is not Nil, so maybe thats the right way
@Marco Bungalski OK. Do you have a link to the PIGPIO’s documentation on how to use i2cReadDevice?
Yes, both links are in my first post.
I also checked and see, that the size of DataBuffer is -1.
@Marco Bungalski OK so the actual function is defined as
int i2cReadDevice(unsigned handle, char *buf, unsigned count)
so it should be declared in Xojo-pigpio as
i2cReadDevice( handle as integer, buf as Ptr, count as integer) as integer
There should be no ByRef involved. So it should eventually be:
[code]’ *****************************
’ * Lesen der Analog-Eingänge *
’ *****************************
Dim DebugString As String
Dim i As Integer
Dim r As Integer
Dim Handle As Integer
Dim DataBuffer As New MemoryBlock( 256 ) //<<< Create an empty buffer
Dim DataBufferPtr As ptr = DataBuffer
’ Open I2CDevice
Handle=PIGPIO.i2cOpen(1,8)
If Handle >=0 Then
r = pigpio.i2cReadDevice(Handle, DataBufferPtr, 11) //DataBuffer should work too as it is no longer a ByRef argument
DebugString= “R=”+Str®+" "
End If
’ Close Device
r=PIGPIO.i2cClose(Handle)
DebugString=DebugString+DataBuffer.StringValue( 0, 11 )
MainWindow.Label1.Text=DebugString[/code]
Stphane - Thanks a lot for quick answer and patience. Now it is working!
I only wonder, why in this XoJo lib from Ulrich Bogun the methods are different declared…
But no matter, finally this code works fine:
Declaration:
Method Name: i2cReadDevice
Parameters: i2chandle as uinteger, value as ptr, count as uinteger
Return Type: Integer
Lib: libpigpio.so
Soft: Yes
Objective-C: No
Code:
[code]Dim DebugString As String
Dim i As Integer
Dim r As Integer
Dim Handle As Integer
Dim DataBuffer As New MemoryBlock(256)
Dim DataBufferPtr As ptr = DataBuffer
’ Open I2CDevice
Handle=PIGPIO.i2cOpen(1,8)
If Handle >=0 Then
r = pigpio.i2cReadDevice(Handle, DataBufferPtr, 11)
DebugString= “R=”+Str®+" "
End If
’ Close Device
r=PIGPIO.i2cClose(Handle)
For i=0 To 10
DebugString=DebugString+Str(DataBuffer.Byte(i))+" "
Next i
MainWindow.Label1.Text=DebugString
[/code]
Marco
@Marco Bungalski Glad it finally works.
That’s a bug in the library. You should let Ulrich Bogun know about that so he can fix it.