i have a problem with aci_gap_create_connection
MatenatK opened this issue · comments
Can you provide a minimal test that i can use to check the problem?
This is my minimal testing, and my result
import pyb
import gc
import ustruct
import urandom
import utime
from micropython import const
gc.threshold(4096)
import logging
from binascii import hexlify
from bluetooth_low_energy.modules.st_microelectronics.spbtle_rf import SPBTLE_RF
from bluetooth_low_energy.protocols.hci.vendor_specifics.st_microelectronics.bluenrg_ms import event as st_event
from bluetooth_low_energy.protocols.hci.vendor_specifics.st_microelectronics.bluenrg_ms import constant as st_constant
from bluetooth_low_energy.protocols.hci import HCI_EVENT_PKT
from bluetooth_low_energy.protocols.hci import uart
from bluetooth_low_energy.protocols.hci import event
from bluetooth_low_energy.protocols.hci import status
logging.basicConfig(level=logging.INFO)
log = logging.getLogger("examples.AppThT")
SCAN_P = const(0x4000)
SCAN_L = const(0x4000)
#Supervision timeout, arg in msec.
SUPERV_TIMEOUT = const(60)
#Connection period, arg in msec.
CONN_P = lambda x: int(x / 1.25)
#Connection length, arg in msec.
CONN_L = lambda x: int(x / 0.625)
CONN_P1 = CONN_P(50)
CONN_P2 = CONN_P(50)
CONN_L1 = CONN_L(1250)
CONN_L2 = CONN_L(1250)
class AppThT(SPBTLE_RF):
def __init__(self, *args, **kwargs):
super(AppThT, self).__init__(*args, **kwargs)
self.bdaddr = bytes(reversed([0x12, 0x34, 0x00, 0xE1, 0x80, 0x02]))
self.bdaddr_sever = bytes(reversed([0xe3, 0xbf, 0xb9, 0x03, 0x36, 0xe7]))
self.charUuid128_TX = bytes(reversed([0xa3,0x2e,0x55,0x20,0xe4,0x77,0x11,0xe2,0xa9,0xe3,0x00,0x02,0xa5,0xd5,0xc5,0x1b]))
self.charUuid128_RX = bytes(reversed([0x34,0x0a,0x1b,0x80,0xcf,0x4b,0x11,0xe1,0xac,0x36,0x00,0x02,0xa5,0xd5,0xc5,0x1b]))
self.connection_handle = None
self.name = b'PyBLE'
def run(self, *args, **kwargs):
def callback():
if self.connection_handle is not None:
pass
super(AppThT, self).run(callback=callback, callback_time = 1000)
def __start__(self):
#Reset BlueNRG-MS
self.reset()
#Check Evt_Blue_Initialized
if self.hci_wait_event(
subevtcode=st_event.EVT_BLUE_HAL_INITIALIZED
).struct.reason_code != st_constant.RESET_NORMAL:
raise ValueError("reason_code")
#Get the BlueNRG FW versions
version = self.get_version()
log.info("current version %s", version)
#Reset BlueNRG again otherwise we won't be able to change its MAC address.
#aci_hal_write_config_data() must be the first command after reset otherwise it will fail.
self.reset()
#Check Evt_Blue_Initialized
if self.hci_wait_event(
subevtcode=st_event.EVT_BLUE_HAL_INITIALIZED
).struct.reason_code != st_constant.RESET_NORMAL:
raise ValueError("reason_code")
# Configure BlueNRG address as public (its public address is used)
result = self.aci_hal_write_config_data(
offset=st_constant.CONFIG_DATA_PUBADDR_OFFSET,
length=st_constant.CONFIG_DATA_PUBADDR_LEN,
data=self.bdaddr
).response_struct
if result.status != status.BLE_STATUS_SUCCESS:
raise ValueError("aci_hal_write_config_data status: {:02x}".format(
result.status))
log.debug("aci_hal_write_config_data PUBADDR: %02x", result.status)
# Init BlueNRG GATT layer
result = self.aci_gatt_init().response_struct
if result.status != status.BLE_STATUS_SUCCESS:
raise ValueError("aci_gatt_init status: {:02x}".format(
result.status))
log.debug("aci_gatt_init %02x", result.status)
# Init BlueNRG GAP layer as peripheral or central
result = self.aci_gap_init_IDB05A1(
role=st_constant.GAP_CENTRAL_ROLE_IDB05A1,
privacy_enabled=bool(st_constant.PRIVACY_DISABLED),
device_name_char_len=len(self.name)).response_struct
if result.status != status.BLE_STATUS_SUCCESS:
raise ValueError("aci_gap_init status: {:02x}".format(
result.status))
log.debug("aci_gap_init %02x", result.status)
result = self.aci_gap_set_auth_requirement(
mitm_mode=st_constant.MITM_PROTECTION_REQUIRED,
oob_enable=bool(st_constant.OOB_AUTH_DATA_ABSENT),
oob_data=b'\x00'*16,
min_encryption_key_size= const(7),
max_encryption_key_size= const(16),
use_fixed_pin=bool(st_constant.USE_FIXED_PIN_FOR_PAIRING),
fixed_pin=123456,
bonding_mode=st_constant.BONDING).response_struct
if result.status != status.BLE_STATUS_SUCCESS:
raise ValueError("aci_gap_set_auth_requirement status: {:02x}".format(
result.status))
log.debug("aci_gap_set_auth_requirement %02x", result.status)
# Set output power level
result = self.aci_hal_set_tx_power_level(
en_high_power=1,
pa_level=5).response_struct
if result.status != status.BLE_STATUS_SUCCESS:
raise ValueError("aci_hal_set_tx_power_level status: {:02x}".format(
result.status))
log.debug("aci_hal_set_tx_power_level %02x", result.status)
# gap create connection
result = self.aci_gap_create_connection(
scan_interval = SCAN_P,
scan_window = SCAN_L,
peer_bdaddr_type = st_constant.RANDOM_ADDR,
peer_bdaddr= self.bdaddr_sever,
own_bdaddr_type= st_constant.PUBLIC_ADDR,
conn_min_interval= CONN_P1,
conn_max_interval= CONN_P2,
conn_latency = 0,
supervision_timeout = SUPERV_TIMEOUT,
min_conn_length = CONN_L1,
max_conn_length = CONN_L2).response_struct
if result.status != status.BLE_STATUS_SUCCESS:
raise ValueError("aci_gap_create_connection status: {:02x}".format(
result.status))
log.debug("aci_gap_create_connection %02x", result.status)
print("Basic Initialized END")
#END
def __stop__(self):
# Reset BlueNRG-MS
self.reset()
def __process__(self, evt):
# Process event received from BlueNRG-MS
hci_uart = uart.HCI_UART.from_buffer(evt)
log.debug(hci_uart)
if hci_uart.pkt_type == HCI_EVENT_PKT:
hci_evt = event.HCI_EVENT.from_buffer(hci_uart.data)
log.debug(hci_evt)
if hci_evt.evtcode == event.EVT_DISCONN_COMPLETE:
self.gap_disconnection_complete_cb()
elif hci_evt.evtcode == event.EVT_LE_META_EVENT:
if hci_evt.subevtcode == event.EVT_LE_CONN_COMPLETE:
self.gap_connection_complete_cb(
hci_evt.struct.peer_bdaddr,
hci_evt.struct.handle
)
elif hci_evt.evtcode == event.EVT_VENDOR:
if hci_evt.subevtcode == st_event.EVT_BLUE_GATT_ATTRIBUTE_MODIFIED:
self.attribute_modified_cb(
hci_evt.struct.attr_handle,
hci_evt.struct.data_length,
hci_evt.struct.att_data[:hci_evt.struct.data_length]
)
elif hci_evt.subevtcode == st_event.EVT_BLUE_GATT_DISC_READ_CHAR_BY_UUID_RESP:
self.evt_gatt_disc_read_char_by_uuid_resp(hci_evt.struct.attr_handle)
elif hci_evt.subevtcode == st_event.EVT_BLUE_GATT_NOTIFICATION:
log.debug("EVT_BLUE_GATT_NOTIFICATION")
self.notification_cb(
hci_evt.struct.conn_handle,
hci_evt.struct.attr_handle,
hci_evt.struct.event_data_length - 2,
hci_evt.struct.attr_value)
elif hci_evt.subevtcode == st_event.EVT_BLUE_ATT_READ_RESP:
log.debug("EVT_BLUE_ATT_READ_RESP")
self.BlueAttReadResp(
hci_evt.struct.conn_handle,
hci_evt.struct.event_data_length,
hci_evt.struct.attribute_value)
elif hci_evt.subevtcode == st_event.EVT_BLUE_GATT_PROCEDURE_COMPLETE:
# Wait for gatt procedure complete event trigger related to
# Discovery Charac by UUID
log.debug("EVT_BLUE_GATT_PROCEDURE_COMPLETE")
#log.info("EVT_BLUE_GATT_PROCEDURE_COMPLETE")
elif hci_evt.subevtcode == st_event.EVT_BLUE_GATT_WRITE_PERMIT_REQ:
print("EVT_BLUE_GATT_WRITE_PERMIT_REQ")
result = self.aci_gatt_write_response(
conn_handle=self.connection_handle,
attr_handle=hci_evt.struct.attr_handle,
write_status=False,
err_code=0,
att_val_len=hci_evt.struct.data_length,
att_val=hci_evt.struct.data_buffer[:hci_evt.struct.data_length]
).response_struct
if result.status != status.BLE_STATUS_SUCCESS:
self.attribute_modified_cb(
hci_evt.struct.attr_handle,
hci_evt.struct.data_length,
hci_evt.struct.data_buffer[:hci_evt.struct.data_length]
)
elif hci_evt.subevtcode == st_event.EVT_BLUE_GATT_READ_PERMIT_REQ:
self.read_request_cb(hci_evt.struct.attr_handle)
def gap_connection_complete_cb(self, address, handle):
log.info("gap_connection_complete_cb")
self.connection_handle = handle
print("gap_connection_completeed = "+str(self.connection_handle))
def gap_disconnection_complete_cb(self):
log.info("gap_disconnection_complete_cb")
self.connection_handle = None
self.set_connectable()
def attribute_modified_cb(self, handle, data_length, att_data):
log.debug("attribute_modified_cb %04x %d %s",
handle, data_length, hexlify(att_data))
def read_request_cb(self, handle):
log.debug("read_request_cb %04x", handle)
if self.connection_handle is not None:
result = self.aci_gatt_allow_read(
conn_handle=self.connection_handle).response_struct
if result.status != status.BLE_STATUS_SUCCESS:
raise ValueError("aci_gatt_allow_read status: {:02x}".format(
result.status))
log.debug("aci_gatt_allow_read %02x", result.status)
With hardware i can test (pyboard 1.1, custom espruino pico with stm32f413) i have no issue with your code.
Have you successfully executed all the examples provided into this repo with the f7 hardware?
Yes F767 can run all of your examples (basic, sensor_demo, bluest_protocol)
STM32F767ZI efficiently works in server mode, but if it works as a client it has a problem with aci_gap_create_connection command.
Have you tried the IDB05A1 that work on the l4 on the f7?
Yes! F7 can run all of examples, L4 also.
I mean, did you try the same X-NUCLEO-IDB05A1 board on the F7 that work correctly on the L4?
Yes i did
can please send me board configuration files for the F7 and pins configuration for BlueNRG_MS?
I have attached my file below.
With this config, I can run your example as good.
attached file: F767_con.zip
Can you please switch Logging level to DEBUG and paste me the output?
change:
log.info("gap_connection_complete_cb")
to
log.info("gap_connection_complete_cb %s", hexlify(bytearray(reversed(address)), ":"))
and:
log.debug(hci_uart)
to log.debug("%s", hci_uart)
log.debug(hci_evt)
to log.debug("%s", hci_evt)
Can you add some debug print into hci_send_cmd of bluenrg_ms.py?
I am sorry for this type of interaction but without hardware i can't help without your hand.
Can you add print after event = self.read(retry=retry)
?
Can you please enable print for header, param and for event? and can you poste the result for L4 and F7?
Have you tried to to use another spi port?
Without hardware I can not verify the problem, for now I close the issue ...