1
0
Fork 0
mirror of https://github.com/betaflight/betaflight.git synced 2025-07-13 03:20:00 +03:00

Fix virtualled (#14276)

This commit is contained in:
Petr Ledvina 2025-03-01 07:40:02 +01:00 committed by GitHub
parent 0b4b1123cd
commit 99e8dd8840
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
5 changed files with 52 additions and 57 deletions

View file

@ -5096,7 +5096,9 @@ const cliResourceValue_t resourceTable[] = {
DEFW( OWNER_I2C_SCL, PG_I2C_CONFIG, i2cConfig_t, ioTagScl, I2CDEV_COUNT ), DEFW( OWNER_I2C_SCL, PG_I2C_CONFIG, i2cConfig_t, ioTagScl, I2CDEV_COUNT ),
DEFW( OWNER_I2C_SDA, PG_I2C_CONFIG, i2cConfig_t, ioTagSda, I2CDEV_COUNT ), DEFW( OWNER_I2C_SDA, PG_I2C_CONFIG, i2cConfig_t, ioTagSda, I2CDEV_COUNT ),
#endif #endif
DEFA( OWNER_LED, PG_STATUS_LED_CONFIG, statusLedConfig_t, ioTags[0], STATUS_LED_NUMBER ), #if !defined(USE_VIRTUAL_LED)
DEFA( OWNER_LED, PG_STATUS_LED_CONFIG, statusLedConfig_t, ioTags[0], STATUS_LED_COUNT ),
#endif
#ifdef USE_SPEKTRUM_BIND #ifdef USE_SPEKTRUM_BIND
DEFS( OWNER_RX_BIND, PG_RX_CONFIG, rxConfig_t, spektrum_bind_pin_override_ioTag ), DEFS( OWNER_RX_BIND, PG_RX_CONFIG, rxConfig_t, spektrum_bind_pin_override_ioTag ),
DEFS( OWNER_RX_BIND_PLUG, PG_RX_CONFIG, rxConfig_t, spektrum_bind_plug_ioTag ), DEFS( OWNER_RX_BIND_PLUG, PG_RX_CONFIG, rxConfig_t, spektrum_bind_plug_ioTag ),

View file

@ -1749,7 +1749,9 @@ const clivalue_t valueTable[] = {
{ "frsky_spi_a1_source", VAR_UINT8 | MASTER_VALUE | MODE_LOOKUP, .config.lookup = { TABLE_RX_FRSKY_SPI_A1_SOURCE }, PG_RX_CC2500_SPI_CONFIG, offsetof(rxCc2500SpiConfig_t, a1Source) }, { "frsky_spi_a1_source", VAR_UINT8 | MASTER_VALUE | MODE_LOOKUP, .config.lookup = { TABLE_RX_FRSKY_SPI_A1_SOURCE }, PG_RX_CC2500_SPI_CONFIG, offsetof(rxCc2500SpiConfig_t, a1Source) },
{ "cc2500_spi_chip_detect", VAR_UINT8 | HARDWARE_VALUE | MODE_LOOKUP, .config.lookup = { TABLE_OFF_ON }, PG_RX_CC2500_SPI_CONFIG, offsetof(rxCc2500SpiConfig_t, chipDetectEnabled) }, { "cc2500_spi_chip_detect", VAR_UINT8 | HARDWARE_VALUE | MODE_LOOKUP, .config.lookup = { TABLE_OFF_ON }, PG_RX_CC2500_SPI_CONFIG, offsetof(rxCc2500SpiConfig_t, chipDetectEnabled) },
#endif #endif
{ "led_inversion", VAR_UINT8 | HARDWARE_VALUE, .config.minmaxUnsigned = { 0, ((1 << STATUS_LED_NUMBER) - 1) }, PG_STATUS_LED_CONFIG, offsetof(statusLedConfig_t, inversion) }, #if !defined(USE_VIRTUAL_LED)
{ "led_inversion", VAR_UINT8 | HARDWARE_VALUE, .config.minmaxUnsigned = { 0, ((1 << STATUS_LED_COUNT) - 1) }, PG_STATUS_LED_CONFIG, offsetof(statusLedConfig_t, inversion) },
#endif
#ifdef USE_DASHBOARD #ifdef USE_DASHBOARD
{ "dashboard_i2c_bus", VAR_UINT8 | HARDWARE_VALUE, .config.minmaxUnsigned = { 0, I2CDEV_COUNT }, PG_DASHBOARD_CONFIG, offsetof(dashboardConfig_t, device) }, { "dashboard_i2c_bus", VAR_UINT8 | HARDWARE_VALUE, .config.minmaxUnsigned = { 0, I2CDEV_COUNT }, PG_DASHBOARD_CONFIG, offsetof(dashboardConfig_t, device) },
{ "dashboard_i2c_addr", VAR_UINT8 | HARDWARE_VALUE, .config.minmaxUnsigned = { I2C_ADDR7_MIN, I2C_ADDR7_MAX }, PG_DASHBOARD_CONFIG, offsetof(dashboardConfig_t, address) }, { "dashboard_i2c_addr", VAR_UINT8 | HARDWARE_VALUE, .config.minmaxUnsigned = { I2C_ADDR7_MIN, I2C_ADDR7_MAX }, PG_DASHBOARD_CONFIG, offsetof(dashboardConfig_t, address) },

View file

@ -27,32 +27,26 @@
#include "light_led.h" #include "light_led.h"
#if !(defined(UNIT_TEST) || defined(USE_VIRTUAL_LED)) #if !defined(USE_VIRTUAL_LED)
PG_REGISTER_WITH_RESET_FN(statusLedConfig_t, statusLedConfig, PG_STATUS_LED_CONFIG, 0); static IO_t leds[STATUS_LED_COUNT];
static IO_t leds[STATUS_LED_NUMBER];
static uint8_t ledInversion = 0; static uint8_t ledInversion = 0;
#ifndef LED0_PIN PG_REGISTER_WITH_RESET_TEMPLATE(statusLedConfig_t, statusLedConfig, PG_STATUS_LED_CONFIG, 0);
#define LED0_PIN NONE
PG_RESET_TEMPLATE(statusLedConfig_t, statusLedConfig,
.ioTags = {
#if STATUS_LED_COUNT > 0 && defined(LED0_PIN)
[0] = IO_TAG(LED0_PIN),
#endif #endif
#if STATUS_LED_COUNT > 1 && defined(LED1_PIN)
#ifndef LED1_PIN [1] = IO_TAG(LED1_PIN),
#define LED1_PIN NONE
#endif #endif
#if STATUS_LED_COUNT > 2 && defined(LED2_PIN)
#ifndef LED2_PIN [2] = IO_TAG(LED2_PIN),
#define LED2_PIN NONE
#endif #endif
},
void pgResetFn_statusLedConfig(statusLedConfig_t *statusLedConfig) .inversion = 0
{
statusLedConfig->ioTags[0] = IO_TAG(LED0_PIN);
statusLedConfig->ioTags[1] = IO_TAG(LED1_PIN);
statusLedConfig->ioTags[2] = IO_TAG(LED2_PIN);
statusLedConfig->inversion = 0
#ifdef LED0_INVERTED #ifdef LED0_INVERTED
| BIT(0) | BIT(0)
#endif #endif
@ -62,35 +56,37 @@ void pgResetFn_statusLedConfig(statusLedConfig_t *statusLedConfig)
#ifdef LED2_INVERTED #ifdef LED2_INVERTED
| BIT(2) | BIT(2)
#endif #endif
; ,
} );
void ledInit(const statusLedConfig_t *statusLedConfig) void ledInit(const statusLedConfig_t *statusLedConfig)
{ {
ledInversion = statusLedConfig->inversion; ledInversion = statusLedConfig->inversion;
for (int i = 0; i < STATUS_LED_NUMBER; i++) { for (int i = 0; i < (int)ARRAYLEN(leds); i++) {
if (statusLedConfig->ioTags[i]) { leds[i] = IOGetByTag(statusLedConfig->ioTags[i]);
leds[i] = IOGetByTag(statusLedConfig->ioTags[i]); if (leds[i]) {
IOInit(leds[i], OWNER_LED, RESOURCE_INDEX(i)); IOInit(leds[i], OWNER_LED, RESOURCE_INDEX(i));
IOConfigGPIO(leds[i], IOCFG_OUT_PP); IOConfigGPIO(leds[i], IOCFG_OUT_PP);
} else {
leds[i] = IO_NONE;
} }
ledSet(i, false);
} }
LED0_OFF;
LED1_OFF;
LED2_OFF;
} }
void ledToggle(int led) void ledToggle(int led)
{ {
if (led < 0 || led >= (int)ARRAYLEN(leds)) {
return;
}
IOToggle(leds[led]); IOToggle(leds[led]);
} }
void ledSet(int led, bool on) void ledSet(int led, bool on)
{ {
const bool inverted = (1 << (led)) & ledInversion; if (led < 0 || led >= (int)ARRAYLEN(leds)) {
return;
}
const bool inverted = ledInversion & (1 << led);
IOWrite(leds[led], on ? inverted : !inverted); IOWrite(leds[led], on ? inverted : !inverted);
} }
#endif #endif

View file

@ -24,31 +24,9 @@
#include "drivers/io_types.h" #include "drivers/io_types.h"
#include "common/utils.h" #include "common/utils.h"
#define STATUS_LED_NUMBER 3 #define STATUS_LED_COUNT 3
typedef struct statusLedConfig_s {
ioTag_t ioTags[STATUS_LED_NUMBER];
uint8_t inversion;
} statusLedConfig_t;
// Helpful macros // Helpful macros
#if defined(UNIT_TEST) || defined(USE_VIRTUAL_LED)
#define LED0_TOGGLE NOOP
#define LED0_OFF NOOP
#define LED0_ON NOOP
#define LED1_TOGGLE NOOP
#define LED1_OFF NOOP
#define LED1_ON NOOP
#define LED2_TOGGLE NOOP
#define LED2_OFF NOOP
#define LED2_ON NOOP
#else
PG_DECLARE(statusLedConfig_t, statusLedConfig);
#define LED0_TOGGLE ledToggle(0) #define LED0_TOGGLE ledToggle(0)
#define LED0_OFF ledSet(0, false) #define LED0_OFF ledSet(0, false)
@ -62,6 +40,22 @@ PG_DECLARE(statusLedConfig_t, statusLedConfig);
#define LED2_OFF ledSet(2, false) #define LED2_OFF ledSet(2, false)
#define LED2_ON ledSet(2, true) #define LED2_ON ledSet(2, true)
// use dummy functions for unittest
#if defined(USE_VIRTUAL_LED)
// ledInit is missing intentionally
static inline void ledToggle(int led) { UNUSED(led); }
static inline void ledSet(int led, bool state) { UNUSED(led); UNUSED(state); }
#else
typedef struct statusLedConfig_s {
ioTag_t ioTags[STATUS_LED_COUNT];
uint8_t inversion;
} statusLedConfig_t;
PG_DECLARE(statusLedConfig_t, statusLedConfig);
void ledInit(const statusLedConfig_t *statusLedConfig); void ledInit(const statusLedConfig_t *statusLedConfig);
void ledToggle(int led); void ledToggle(int led);
void ledSet(int led, bool state); void ledSet(int led, bool state);

View file

@ -58,6 +58,7 @@
#define USE_LED_STRIP_STATUS_MODE #define USE_LED_STRIP_STATUS_MODE
#define USE_SERVOS #define USE_SERVOS
#define USE_TRANSPONDER #define USE_TRANSPONDER
#define USE_VIRTUAL_LED
#define USE_VCP #define USE_VCP
#define USE_UART1 #define USE_UART1
#define USE_UART2 #define USE_UART2