mirror of
https://github.com/liquidraver/ZephCore.git
synced 2026-09-17 04:54:20 +00:00
1. USB takeover opcode mismatch ZephyrCompanionUSB.cpp checked payload[0] == 0x03 with a comment claiming CMD_APP_START, but CMD_APP_START is 0x01 (0x03 is CMD_SEND_CHANNEL_TXT_MSG). The USB handshake silently dropped the companion app's first frame on every connection; the app appeared broken over USB until the user happened to send a channel message. 2. CMD_SET_ADVERT_NAME didn't propagate to BLE adv data Name changes were persisted to prefs but the advertising payload and GATT device name kept the old value until reboot. Added zephcore_ble_update_name() and called it from the handler. 3. No advertising-health watchdog If bt_le_adv_start() ever failed transiently (HCI timeout, controller pacing), the device would silently stop advertising and stay undiscoverable until reboot. Added an adv_running flag and a 5s watchdog in the companion housekeeping handler that nudges adv back on if it stops outside a connection. Tracks Arduino nrf52's equivalent 10s watchdog.
103 lines
3.2 KiB
C
103 lines
3.2 KiB
C
/*
|
|
* SPDX-License-Identifier: Apache-2.0
|
|
* ZephCore BLE Adapter — NUS service, advertising, security, TX/RX
|
|
*/
|
|
#pragma once
|
|
|
|
#include <zephyr/kernel.h>
|
|
#include <stdbool.h>
|
|
#include <stdint.h>
|
|
#include <stddef.h>
|
|
|
|
#ifdef __cplusplus
|
|
extern "C" {
|
|
#endif
|
|
|
|
/* Callbacks from BLE adapter to main */
|
|
struct ble_callbacks {
|
|
/* RX frame received; runs on system work queue — must not block */
|
|
void (*on_rx_frame)(const uint8_t *data, uint16_t len);
|
|
/* TX queue drained */
|
|
void (*on_tx_idle)(void);
|
|
/* BLE connected */
|
|
void (*on_connected)(void);
|
|
/* BLE disconnected */
|
|
void (*on_disconnected)(void);
|
|
};
|
|
|
|
enum zephcore_iface {
|
|
ZEPHCORE_IFACE_NONE,
|
|
ZEPHCORE_IFACE_BLE,
|
|
ZEPHCORE_IFACE_USB,
|
|
};
|
|
|
|
/** Register callbacks and auth handlers. Call before bt_enable(). */
|
|
void zephcore_ble_init(const struct ble_callbacks *cbs);
|
|
|
|
/** Load settings, build adv data, start advertising. Call from bt_ready(). */
|
|
void zephcore_ble_start(const char *device_name);
|
|
|
|
/** Queue a frame for BLE TX. Returns bytes queued, or 0 on failure. */
|
|
size_t zephcore_ble_send(const uint8_t *data, uint16_t len);
|
|
|
|
/** Enable/disable BLE. Disabling disconnects and stops advertising. */
|
|
void zephcore_ble_set_enabled(bool enable);
|
|
|
|
/** True if BLE is the active transport and ready to send. */
|
|
bool zephcore_ble_is_active(void);
|
|
|
|
/** True if BLE has an active connection (regardless of interface state). */
|
|
bool zephcore_ble_is_connected(void);
|
|
|
|
/** True if TX queue is full and overflow retry is active. */
|
|
bool zephcore_ble_is_congested(void);
|
|
|
|
/** True if the controller is currently broadcasting advertising PDUs.
|
|
* Returns FALSE during an active connection (Zephyr stops adv when the
|
|
* BT_MAX_CONN=1 slot is consumed) and FALSE after any explicit stop.
|
|
* Companion main loop polls this each housekeeping tick (~5s) and calls
|
|
* zephcore_ble_set_enabled(true) if adv ever stops outside a connection. */
|
|
bool zephcore_ble_is_advertising(void);
|
|
|
|
void zephcore_ble_set_passkey(uint32_t passkey);
|
|
uint32_t zephcore_ble_get_passkey(void);
|
|
|
|
/** Get/set active interface (BLE/USB coexistence). */
|
|
enum zephcore_iface zephcore_ble_get_active_iface(void);
|
|
void zephcore_ble_set_active_iface(enum zephcore_iface iface);
|
|
|
|
/** Get recv/send queues for USB path sharing. */
|
|
struct k_msgq *zephcore_ble_get_recv_queue(void);
|
|
struct k_msgq *zephcore_ble_get_send_queue(void);
|
|
|
|
/** Kick the TX drain work. Call after putting frames in the send queue. */
|
|
void zephcore_ble_kick_tx(void);
|
|
|
|
/**
|
|
* Disconnect the current BLE connection (if any).
|
|
* Used by USB when it takes over as active interface.
|
|
*/
|
|
void zephcore_ble_disconnect(void);
|
|
|
|
/**
|
|
* Apply deferred connection parameters.
|
|
* Call after the initial app sync is complete (channels + contacts +
|
|
* offline messages) so the param negotiation doesn't disrupt throughput
|
|
* during the sync burst.
|
|
*/
|
|
void zephcore_ble_conn_params_ready(void);
|
|
|
|
/**
|
|
* Rebuild advertising payload + GATT device name from a new prefs name.
|
|
* If currently advertising (no active connection), stops and restarts
|
|
* adv so the new name is published immediately. If connected, the new
|
|
* payload takes effect on the next adv cycle after disconnect.
|
|
*
|
|
* Call from CMD_SET_ADVERT_NAME handler after persisting prefs.
|
|
*/
|
|
void zephcore_ble_update_name(const char *new_name);
|
|
|
|
#ifdef __cplusplus
|
|
}
|
|
#endif
|