gattc: add Read() characteristic method implementations for Linux and nRF528xx

Signed-off-by: deadprogram <ron@hybridgroup.com>
This commit is contained in:
deadprogram 2020-10-03 10:13:15 +02:00
parent 3e31cedee9
commit 47770f6c59
5 changed files with 59 additions and 0 deletions

@ -219,6 +219,16 @@ func handleEvent() {
}
}
}
case C.BLE_GATTC_EVT_READ_RSP:
readEvent := gattcEvent.params.unionfield_read_rsp()
if debug {
println("evt: read response, data length", readEvent.len)
}
readingCharacteristic.handle_value.Set(readEvent.handle)
readingCharacteristic.offset = readEvent.offset
// Create a Go slice from the data.
readingCharacteristic.value = (*[255]byte)(unsafe.Pointer(&readEvent.data[0]))[:readEvent.len:readEvent.len]
case C.BLE_GATTC_EVT_HVX:
hvxEvent := gattcEvent.params.unionfield_hvx()
switch hvxEvent._type {

@ -68,6 +68,12 @@ func main() {
}
for _, char := range chars {
println("-- characteristic", char.UUID().String())
val, err := char.Read()
if err != nil {
println("---", err.Error())
} else {
println("--- value =", string(val))
}
}
}

@ -145,3 +145,8 @@ func (c *DeviceCharacteristic) EnableNotifications(callback func(buf []byte)) er
return nil
}
// Read reads the current characteristic value.
func (c DeviceCharacteristic) Read() (data []byte, err error) {
return nil, nil
}

@ -232,3 +232,9 @@ func (c *DeviceCharacteristic) EnableNotifications(callback func(buf []byte)) er
}()
return c.characteristic.StartNotify()
}
// Read reads the current characteristic value.
func (c DeviceCharacteristic) Read() ([]byte, error) {
options := make(map[string]interface{})
return c.characteristic.ReadValue(options)
}

@ -337,6 +337,38 @@ func (c *DeviceCharacteristic) WriteWithoutResponse(p []byte) (n int, err error)
return len(p), nil
}
// A global used to pass information from the event handler back to the
// Read function below.
var readingCharacteristic struct {
handle_value volatile.Register16
offset uint16
value []byte
}
// Read reads the current characteristic value up to MTU length.
// A future enhancement would be to be able to retrieve a longer
// value by making multiple calls.
func (c DeviceCharacteristic) Read() ([]byte, error) {
errCode := C.sd_ble_gattc_read(c.connectionHandle, c.valueHandle, 0)
if errCode != 0 {
return nil, Error(errCode)
}
// wait for response with data
for readingCharacteristic.handle_value.Get() == 0 {
arm.Asm("wfe")
}
// copy data since value is slice to unsafe pointer.
data := make([]byte, len(readingCharacteristic.value))
copy(data, readingCharacteristic.value)
// prepare for next read
readingCharacteristic.handle_value.Set(0)
return data, nil
}
type gattcNotificationCallback struct {
connectionHandle uint16
valueHandle uint16 // may be 0 if the slot is empty