Skip to content

Commit

Permalink
Change SmartPort sensor IDs for GPS and Modes
Browse files Browse the repository at this point in the history
The current implementation of INAV SmartPort telemetry uses temperature sensor IDs for Modes and GNSS data. This causes issues on transmitter firmware that more strictly adhere to the telemetry ID's intended use. The Tmp sensors can't be converted to a different type, so they can't be read correctly.

This PR changes the IDs to some that are not associated with specific functions or types. There is also an option to use the legacy IDs to allow for a deprecation period. This legacy option should be removed in INAV 10.0.
  • Loading branch information
MrD-RC committed Mar 29, 2024
1 parent ee382be commit 6f58bdb
Show file tree
Hide file tree
Showing 6 changed files with 117 additions and 87 deletions.
10 changes: 10 additions & 0 deletions docs/Settings.md
Original file line number Diff line number Diff line change
Expand Up @@ -1162,6 +1162,16 @@ S.Port telemetry: Send pitch and roll degrees*10 instead of raw accelerometer da

---

### frsky_use_legacy_gps_mode_sensor_ids

S.Port telemetry: If `ON`, send the legacy telemetry IDs for modes (Tmp1) and GNSS (Tmp2). These are old IDs, deprecated, and will be removed in INAV 10.0. Tools and scripts using these IDs should be updated to use the new IDs of **470** for Modes and **480** for GNSS. Default: 'OFF'

| Default | Min | Max |
| --- | --- | --- |
| OFF | OFF | ON |

---

### fw_autotune_max_rate_deflection

The target percentage of maximum mixer output used for determining the rates in `AUTO` and `LIMIT`.
Expand Down
8 changes: 6 additions & 2 deletions docs/Telemetry.md
Original file line number Diff line number Diff line change
Expand Up @@ -102,17 +102,21 @@ The following sensors are transmitted
* **VSpd** : vertical speed, unit is cm/s.
* **Hdg** : heading, North is 0°, South is 180°.
* **AccX,Y,Z** : accelerometer values (not sent if `frsky_pitch_roll = ON`).
* **Tmp1** : flight mode, sent as 5 digits. Number is sent as **ABCDE** detailed below. The numbers are additives (for example: if digit C is 6, it means both position hold and altitude hold are active) :
* **470** : flight mode, sent as 5 digits. Number is sent as **ABCDE** detailed below. The numbers are additives (for example: if digit C is 6, it means both position hold and altitude hold are active) :
* **A** : 1 = flaperon mode, 2 = auto tune mode, 4 = failsafe mode
* **B** : 1 = return to home, 2 = waypoint mode, 4 = headfree mode
* **C** : 1 = heading hold, 2 = altitude hold, 4 = position hold
* **D** : 1 = angle mode, 2 = horizon mode, 4 = passthru mode
* **E** : 1 = ok to arm, 2 = arming is prevented, 4 = armed
* **Tmp2** : GPS lock status, accuracy, home reset trigger, and number of satellites. Number is sent as **ABCD** detailed below. Typical minimum GPS 3D lock value is 3906 (GPS locked and home fixed, HDOP highest accuracy, 6 satellites).

_NOTE_ This sensor used to be **Tmp1**. The ID has been reassigned in INAV 8.0. The old ID of **Tmp1** can still be used, by using `set frsky_use_legacy_gps_mode_sensor_ids = ON`. This is deprecated and will be removed in INAV 10.0. All tools and scripts using the old IDs should be updated to use the new ID.
* **480** : GPS lock status, accuracy, home reset trigger, and number of satellites. Number is sent as **ABCD** detailed below. Typical minimum GPS 3D lock value is 3906 (GPS locked and home fixed, HDOP highest accuracy, 6 satellites).
* **A** : 1 = GPS fix, 2 = GPS home fix, 4 = home reset (numbers are additive)
* **B** : GPS accuracy based on HDOP (0 = lowest to 9 = highest accuracy)
* **C** : number of satellites locked (digit C & D are the number of locked satellites)
* **D** : number of satellites locked (if 14 satellites are locked, C = 1 & D = 4)

_NOTE_ This sensor used to be **Tmp2**. The ID has been reassigned in INAV 8.0. The old ID of **Tmp2** can still be used, by using `set frsky_use_legacy_gps_mode_sensor_ids = ON`. This is deprecated and will be removed in INAV 10.0. All tools and scripts using the old IDs should be updated to use the new ID.
* **GAlt** : GPS altitude, sea level is zero.
* **ASpd** : true air speed, from pitot sensor. This is _Knots * 10_
* **A4** : average cell value. Warning : unlike FLVSS and MLVSS sensors, you do not get actual lowest value of a cell, but an average : (total lipo voltage) / (number of cells)
Expand Down
4 changes: 4 additions & 0 deletions src/main/fc/settings.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -2986,6 +2986,10 @@ groups:
description: "S.Port telemetry: Send pitch and roll degrees*10 instead of raw accelerometer data"
default_value: OFF
type: bool
- name: frsky_use_legacy_gps_mode_sensor_ids
description: "S.Port telemetry: If `ON`, send the legacy telemetry IDs for modes (Tmp1) and GNSS (Tmp2). These are old IDs, deprecated, and will be removed in INAV 10.0. Tools and scripts using these IDs should be updated to use the new IDs of **470** for Modes and **480** for GNSS. Default: 'OFF'"
default_value: OFF
type: bool
- name: report_cell_voltage
description: "S.Port and IBUS telemetry: Send the average cell voltage if set to ON"
default_value: OFF
Expand Down
180 changes: 95 additions & 85 deletions src/main/telemetry/smartport.c
Original file line number Diff line number Diff line change
Expand Up @@ -63,66 +63,68 @@
// these data identifiers are obtained from https://github.com/opentx/opentx/blob/2.3/radio/src/telemetry/frsky.h
enum
{
FSSP_DATAID_SPEED = 0x0830 ,
FSSP_DATAID_VFAS = 0x0210 ,
FSSP_DATAID_CURRENT = 0x0200 ,
FSSP_DATAID_RPM = 0x050F ,
FSSP_DATAID_ALTITUDE = 0x0100 ,
FSSP_DATAID_FUEL = 0x0600 ,
FSSP_DATAID_ADC1 = 0xF102 ,
FSSP_DATAID_ADC2 = 0xF103 ,
FSSP_DATAID_LATLONG = 0x0800 ,
FSSP_DATAID_CAP_USED = 0x0600 ,
FSSP_DATAID_VARIO = 0x0110 ,
FSSP_DATAID_CELLS = 0x0300 ,
FSSP_DATAID_CELLS_LAST = 0x030F ,
FSSP_DATAID_HEADING = 0x0840 ,
FSSP_DATAID_FPV = 0x0450 ,
FSSP_DATAID_PITCH = 0x0430 ,
FSSP_DATAID_ROLL = 0x0440 ,
FSSP_DATAID_ACCX = 0x0700 ,
FSSP_DATAID_ACCY = 0x0710 ,
FSSP_DATAID_ACCZ = 0x0720 ,
FSSP_DATAID_T1 = 0x0400 ,
FSSP_DATAID_T2 = 0x0410 ,
FSSP_DATAID_HOME_DIST = 0x0420 ,
FSSP_DATAID_GPS_ALT = 0x0820 ,
FSSP_DATAID_ASPD = 0x0A00 ,
FSSP_DATAID_A3 = 0x0900 ,
FSSP_DATAID_A4 = 0x0910 ,
FSSP_DATAID_AZIMUTH = 0x0460
FSSP_DATAID_SPEED = 0x0830,
FSSP_DATAID_VFAS = 0x0210,
FSSP_DATAID_CURRENT = 0x0200,
FSSP_DATAID_RPM = 0x050F,
FSSP_DATAID_ALTITUDE = 0x0100,
FSSP_DATAID_FUEL = 0x0600,
FSSP_DATAID_ADC1 = 0xF102,
FSSP_DATAID_ADC2 = 0xF103,
FSSP_DATAID_LATLONG = 0x0800,
FSSP_DATAID_CAP_USED = 0x0600,
FSSP_DATAID_VARIO = 0x0110,
FSSP_DATAID_CELLS = 0x0300,
FSSP_DATAID_CELLS_LAST = 0x030F,
FSSP_DATAID_HEADING = 0x0840,
FSSP_DATAID_FPV = 0x0450,
FSSP_DATAID_PITCH = 0x0430,
FSSP_DATAID_ROLL = 0x0440,
FSSP_DATAID_ACCX = 0x0700,
FSSP_DATAID_ACCY = 0x0710,
FSSP_DATAID_ACCZ = 0x0720,
FSSP_DATAID_LEGACY_MODES = 0x0400, // Deprecated. Should be removed in INAV 10.0
FSSP_DATAID_LEGACY_GNSS = 0x0410, // Deprecated. Should be removed in INAV 10.0
FSSP_DATAID_HOME_DIST = 0x0420,
FSSP_DATAID_GPS_ALT = 0x0820,
FSSP_DATAID_ASPD = 0x0A00,
FSSP_DATAID_A3 = 0x0900,
FSSP_DATAID_A4 = 0x0910,
FSSP_DATAID_AZIMUTH = 0x0460,
FSSP_DATAID_MODES = 0x0470,
FSSP_DATAID_GNSS = 0x0480,
};

const uint16_t frSkyDataIdTable[] = {
FSSP_DATAID_SPEED ,
FSSP_DATAID_VFAS ,
FSSP_DATAID_CURRENT ,
//FSSP_DATAID_RPM ,
FSSP_DATAID_ALTITUDE ,
FSSP_DATAID_FUEL ,
//FSSP_DATAID_ADC1 ,
//FSSP_DATAID_ADC2 ,
FSSP_DATAID_LATLONG ,
FSSP_DATAID_LATLONG , // twice
//FSSP_DATAID_CAP_USED ,
FSSP_DATAID_VARIO ,
//FSSP_DATAID_CELLS ,
FSSP_DATAID_SPEED,
FSSP_DATAID_VFAS,
FSSP_DATAID_CURRENT,
//FSSP_DATAID_RPM,
FSSP_DATAID_ALTITUDE,
FSSP_DATAID_FUEL,
//FSSP_DATAID_ADC1,
//FSSP_DATAID_ADC2,
FSSP_DATAID_LATLONG,
FSSP_DATAID_LATLONG, // twice
//FSSP_DATAID_CAP_USED,
FSSP_DATAID_VARIO,
//FSSP_DATAID_CELLS,
//FSSP_DATAID_CELLS_LAST,
FSSP_DATAID_HEADING ,
FSSP_DATAID_FPV ,
FSSP_DATAID_PITCH ,
FSSP_DATAID_ROLL ,
FSSP_DATAID_ACCX ,
FSSP_DATAID_ACCY ,
FSSP_DATAID_ACCZ ,
FSSP_DATAID_T1 ,
FSSP_DATAID_T2 ,
FSSP_DATAID_HOME_DIST ,
FSSP_DATAID_GPS_ALT ,
FSSP_DATAID_ASPD ,
// FSSP_DATAID_A3 ,
FSSP_DATAID_A4 ,
FSSP_DATAID_AZIMUTH ,
FSSP_DATAID_HEADING,
FSSP_DATAID_FPV,
FSSP_DATAID_PITCH,
FSSP_DATAID_ROLL,
FSSP_DATAID_ACCX,
FSSP_DATAID_ACCY,
FSSP_DATAID_ACCZ,
FSSP_DATAID_MODES,
FSSP_DATAID_GNSS,
FSSP_DATAID_HOME_DIST,
FSSP_DATAID_GPS_ALT,
FSSP_DATAID_ASPD,
// FSSP_DATAID_A3,
FSSP_DATAID_A4,
FSSP_DATAID_AZIMUTH,
0
};

Expand Down Expand Up @@ -467,27 +469,27 @@ void processSmartPortTelemetry(smartPortPayload_t *payload, volatile bool *clear
smartPortIdCnt++;

switch (id) {
case FSSP_DATAID_VFAS :
case FSSP_DATAID_VFAS:
if (isBatteryVoltageConfigured()) {
uint16_t vfasVoltage = telemetryConfig()->report_cell_voltage ? getBatteryAverageCellVoltage() : getBatteryVoltage();
smartPortSendPackage(id, vfasVoltage);
*clearToSend = false;
}
break;
case FSSP_DATAID_CURRENT :
case FSSP_DATAID_CURRENT:
if (isAmperageConfigured()) {
smartPortSendPackage(id, getAmperage() / 10); // given in 10mA steps, unknown requested unit
*clearToSend = false;
}
break;
//case FSSP_DATAID_RPM :
case FSSP_DATAID_ALTITUDE :
//case FSSP_DATAID_RPM:
case FSSP_DATAID_ALTITUDE:
if (sensors(SENSOR_BARO)) {
smartPortSendPackage(id, getEstimatedActualPosition(Z)); // unknown given unit, requested 100 = 1 meter
*clearToSend = false;
}
break;
case FSSP_DATAID_FUEL :
case FSSP_DATAID_FUEL:
if (telemetryConfig()->smartportFuelUnit == SMARTPORT_FUEL_UNIT_PERCENT) {
smartPortSendPackage(id, calculateBatteryPercentage()); // Show remaining battery % if smartport_fuel_percent=ON
*clearToSend = false;
Expand All @@ -496,63 +498,71 @@ void processSmartPortTelemetry(smartPortPayload_t *payload, volatile bool *clear
*clearToSend = false;
}
break;
//case FSSP_DATAID_ADC1 :
//case FSSP_DATAID_ADC2 :
//case FSSP_DATAID_CAP_USED :
case FSSP_DATAID_VARIO :
//case FSSP_DATAID_ADC1:
//case FSSP_DATAID_ADC2:
//case FSSP_DATAID_CAP_USED:
case FSSP_DATAID_VARIO:
if (sensors(SENSOR_BARO)) {
smartPortSendPackage(id, lrintf(getEstimatedActualVelocity(Z))); // unknown given unit but requested in 100 = 1m/s
*clearToSend = false;
}
break;
case FSSP_DATAID_HEADING :
case FSSP_DATAID_HEADING:
smartPortSendPackage(id, attitude.values.yaw * 10); // given in 10*deg, requested in 10000 = 100 deg
*clearToSend = false;
break;
case FSSP_DATAID_PITCH :
case FSSP_DATAID_PITCH:
if (telemetryConfig()->frsky_pitch_roll) {
smartPortSendPackage(id, attitude.values.pitch); // given in 10*deg
*clearToSend = false;
}
break;
case FSSP_DATAID_ROLL :
case FSSP_DATAID_ROLL:
if (telemetryConfig()->frsky_pitch_roll) {
smartPortSendPackage(id, attitude.values.roll); // given in 10*deg
*clearToSend = false;
}
break;
case FSSP_DATAID_ACCX :
case FSSP_DATAID_ACCX:
if (!telemetryConfig()->frsky_pitch_roll) {
smartPortSendPackage(id, lrintf(100 * acc.accADCf[X]));
*clearToSend = false;
}
break;
case FSSP_DATAID_ACCY :
case FSSP_DATAID_ACCY:
if (!telemetryConfig()->frsky_pitch_roll) {
smartPortSendPackage(id, lrintf(100 * acc.accADCf[Y]));
*clearToSend = false;
}
break;
case FSSP_DATAID_ACCZ :
case FSSP_DATAID_ACCZ:
if (!telemetryConfig()->frsky_pitch_roll) {
smartPortSendPackage(id, lrintf(100 * acc.accADCf[Z]));
*clearToSend = false;
}
break;
case FSSP_DATAID_T1 :
case FSSP_DATAID_MODES:
{
if (telemetryConfig()->frsky_use_legacy_gps_mode_sensor_ids)
id = FSSP_DATAID_LEGACY_MODES;

smartPortSendPackage(id, frskyGetFlightMode());
*clearToSend = false;
break;
}
#ifdef USE_GPS
case FSSP_DATAID_T2 :
if (smartPortShouldSendGPSData()) {
smartPortSendPackage(id, frskyGetGPSState());
*clearToSend = false;
case FSSP_DATAID_GNSS:
{
if (telemetryConfig()->frsky_use_legacy_gps_mode_sensor_ids)
id = FSSP_DATAID_LEGACY_GNSS;

if (smartPortShouldSendGPSData()) {
smartPortSendPackage(id, frskyGetGPSState());
*clearToSend = false;
}
break;
}
break;
case FSSP_DATAID_SPEED :
case FSSP_DATAID_SPEED:
if (smartPortShouldSendGPSData()) {
//convert to knots: 1cm/s = 0.0194384449 knots
//Speed should be sent in knots/1000 (GPS speed is in cm/s)
Expand All @@ -561,7 +571,7 @@ void processSmartPortTelemetry(smartPortPayload_t *payload, volatile bool *clear
*clearToSend = false;
}
break;
case FSSP_DATAID_LATLONG :
case FSSP_DATAID_LATLONG:
if (smartPortShouldSendGPSData()) {
uint32_t tmpui = 0;
// the same ID is sent twice, one for longitude, one for latitude
Expand All @@ -581,25 +591,25 @@ void processSmartPortTelemetry(smartPortPayload_t *payload, volatile bool *clear
*clearToSend = false;
}
break;
case FSSP_DATAID_HOME_DIST :
case FSSP_DATAID_HOME_DIST:
if (smartPortShouldSendGPSData()) {
smartPortSendPackage(id, GPS_distanceToHome);
*clearToSend = false;
}
break;
case FSSP_DATAID_GPS_ALT :
case FSSP_DATAID_GPS_ALT:
if (smartPortShouldSendGPSData()) {
smartPortSendPackage(id, gpsSol.llh.alt); // cm
*clearToSend = false;
}
break;
case FSSP_DATAID_FPV :
case FSSP_DATAID_FPV:
if (smartPortShouldSendGPSData()) {
smartPortSendPackage(id, gpsSol.groundCourse); // given in 10*deg
*clearToSend = false;
}
break;
case FSSP_DATAID_AZIMUTH :
case FSSP_DATAID_AZIMUTH:
if (smartPortShouldSendGPSData()) {
int16_t h = GPS_directionToHome;
if (h < 0) {
Expand All @@ -614,13 +624,13 @@ void processSmartPortTelemetry(smartPortPayload_t *payload, volatile bool *clear
}
break;
#endif
case FSSP_DATAID_A4 :
case FSSP_DATAID_A4:
if (isBatteryVoltageConfigured()) {
smartPortSendPackage(id, getBatteryAverageCellVoltage());
*clearToSend = false;
}
break;
case FSSP_DATAID_ASPD :
case FSSP_DATAID_ASPD:
#ifdef USE_PITOT
if (sensors(SENSOR_PITOT) && pitotIsHealthy()) {
smartPortSendPackage(id, getAirspeedEstimate() * 0.194384449f); // cm/s to knots*1
Expand Down
1 change: 1 addition & 0 deletions src/main/telemetry/telemetry.c
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,7 @@ PG_RESET_TEMPLATE(telemetryConfig_t, telemetryConfig,
.telemetry_switch = SETTING_TELEMETRY_SWITCH_DEFAULT,
.telemetry_inverted = SETTING_TELEMETRY_INVERTED_DEFAULT,
.frsky_pitch_roll = SETTING_FRSKY_PITCH_ROLL_DEFAULT,
.frsky_use_legacy_gps_mode_sensor_ids = SETTING_FRSKY_USE_LEGACY_GPS_MODE_SENSOR_IDS_DEFAULT,
.report_cell_voltage = SETTING_REPORT_CELL_VOLTAGE_DEFAULT,
.hottAlarmSoundInterval = SETTING_HOTT_ALARM_SOUND_INTERVAL_DEFAULT,
.halfDuplex = SETTING_TELEMETRY_HALFDUPLEX_DEFAULT,
Expand Down
1 change: 1 addition & 0 deletions src/main/telemetry/telemetry.h
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@ typedef struct telemetryConfig_s {
uint8_t telemetry_switch; // Use aux channel to change serial output & baudrate( MSP / Telemetry ). It disables automatic switching to Telemetry when armed.
uint8_t telemetry_inverted; // Flip the default inversion of the protocol - Same as serialrx_inverted in rx.c, but for telemetry.
uint8_t frsky_pitch_roll;
bool frsky_use_legacy_gps_mode_sensor_ids;
uint8_t report_cell_voltage;
uint8_t hottAlarmSoundInterval;
uint8_t halfDuplex;
Expand Down

0 comments on commit 6f58bdb

Please sign in to comment.