55 #include "modulesettings.h"
58 #include "airspeedactual.h"
59 #include "attitudeactual.h"
60 #include "baroaltitude.h"
61 #include "flightstatus.h"
62 #include "gpsposition.h"
63 #include "flightbatterysettings.h"
64 #include "flightbatterystate.h"
65 #include "manualcontrolcommand.h"
66 #include "positionactual.h"
73 #if defined(PIOS_INCLUDE_LIGHTTELEMETRY)
75 #define STACK_SIZE_BYTES 600
76 #define TASK_PRIORITY PIOS_THREAD_PRIO_LOW
84 #define LTM_GFRAME_SIZE 18
85 #define LTM_AFRAME_SIZE 10
86 #define LTM_SFRAME_SIZE 11
93 static uint32_t lighttelemetryPort;
94 static uint8_t ltm_scheduler;
95 static uint8_t ltm_slowrate;
98 static void uavoLighttelemetryBridgeTask(
void *parameters);
101 static int send_LTM_Packet(uint8_t *LTPacket, uint8_t LTPacket_size);
102 static int send_LTM_Gframe();
103 static int send_LTM_Aframe();
104 static int send_LTM_Sframe();
111 int32_t uavoLighttelemetryBridgeInitialize()
128 int32_t uavoLighttelemetryBridgeStart()
140 MODULE_INITCALL(uavoLighttelemetryBridgeInitialize, uavoLighttelemetryBridgeStart);
148 static void uavoLighttelemetryBridgeTask(
void *parameters)
158 switch (ltm_scheduler) {
161 ret = send_LTM_Sframe();
166 ret = send_LTM_Gframe();
181 ret = send_LTM_Aframe();
200 if (ltm_scheduler > 11) {
211 static int send_LTM_Gframe()
213 GPSPositionData pdata = { };
215 bool have_gps =
false;
217 if (GPSPositionHandle() != NULL) {
219 GPSPositionGet(&pdata);
222 int32_t lt_latitude = pdata.Latitude;
223 int32_t lt_longitude = pdata.Longitude;
224 uint8_t lt_groundspeed = (uint8_t)roundf(pdata.Groundspeed);
225 int32_t lt_altitude = 0;
226 if (PositionActualHandle() != NULL) {
228 PositionActualDownGet(&altitude);
229 lt_altitude = (int32_t)roundf(altitude * -100.0
f);
230 }
else if (BaroAltitudeHandle() != NULL) {
232 BaroAltitudeAltitudeGet(&altitude);
233 lt_altitude = (int32_t)roundf(altitude * 100.0
f);
234 }
else if (have_gps) {
235 lt_altitude = (int32_t)roundf(pdata.Altitude * 100.0f);
241 switch (pdata.Status) {
242 case GPSPOSITION_STATUS_NOGPS:
245 case GPSPOSITION_STATUS_NOFIX:
248 case GPSPOSITION_STATUS_FIX2D:
251 case GPSPOSITION_STATUS_FIX3D:
259 uint8_t lt_gpssats = (int8_t)pdata.Satellites;
261 uint8_t LTBuff[LTM_GFRAME_SIZE];
269 LTBuff[3] = (lt_latitude >> 8*0) & 0xFF;
270 LTBuff[4] = (lt_latitude >> 8*1) & 0xFF;
271 LTBuff[5] = (lt_latitude >> 8*2) & 0xFF;
272 LTBuff[6] = (lt_latitude >> 8*3) & 0xFF;
273 LTBuff[7] = (lt_longitude >> 8*0) & 0xFF;
274 LTBuff[8] = (lt_longitude >> 8*1) & 0xFF;
275 LTBuff[9] = (lt_longitude >> 8*2) & 0xFF;
276 LTBuff[10] = (lt_longitude >> 8*3) & 0xFF;
277 LTBuff[11] = (lt_groundspeed >> 8*0) & 0xFF;
278 LTBuff[12] = (lt_altitude >> 8*0) & 0xFF;
279 LTBuff[13] = (lt_altitude >> 8*1) & 0xFF;
280 LTBuff[14] = (lt_altitude >> 8*2) & 0xFF;
281 LTBuff[15] = (lt_altitude >> 8*3) & 0xFF;
282 LTBuff[16] = ((lt_gpssats << 2)& 0xFF ) | (lt_gpsfix & 0b00000011) ;
284 return send_LTM_Packet(LTBuff,LTM_GFRAME_SIZE);
288 static int send_LTM_Aframe()
291 AttitudeActualData adata;
292 AttitudeActualGet(&adata);
293 int16_t lt_pitch = (int16_t)(roundf(adata.Pitch));
294 int16_t lt_roll = (int16_t)(roundf(adata.Roll));
295 int16_t lt_heading = (int16_t)(roundf(adata.Yaw));
297 uint8_t LTBuff[LTM_AFRAME_SIZE];
306 LTBuff[3] = (lt_pitch >> 8*0) & 0xFF;
307 LTBuff[4] = (lt_pitch >> 8*1) & 0xFF;
308 LTBuff[5] = (lt_roll >> 8*0) & 0xFF;
309 LTBuff[6] = (lt_roll >> 8*1) & 0xFF;
310 LTBuff[7] = (lt_heading >> 8*0) & 0xFF;
311 LTBuff[8] = (lt_heading >> 8*1) & 0xFF;
313 return send_LTM_Packet(LTBuff,LTM_AFRAME_SIZE);
317 static int send_LTM_Sframe()
320 uint16_t lt_vbat = 0;
323 uint8_t lt_airspeed = 0;
325 uint8_t lt_failsafe = 0;
326 uint8_t lt_flightmode = 0;
329 if (FlightBatteryStateHandle() != NULL) {
330 FlightBatteryStateData sdata;
331 FlightBatteryStateGet(&sdata);
332 lt_vbat = (uint16_t)roundf(sdata.Voltage*1000);
333 lt_amp = (uint16_t)roundf(sdata.ConsumedEnergy);
335 if (ManualControlCommandHandle() != NULL) {
336 ManualControlCommandData mdata;
337 ManualControlCommandGet(&mdata);
338 lt_rssi = (uint8_t)mdata.Rssi;
340 if (AirspeedActualHandle() != NULL) {
341 AirspeedActualData adata;
342 AirspeedActualGet (&adata);
343 lt_airspeed = (uint8_t)roundf(adata.TrueAirspeed);
344 }
else if (GPSPositionHandle() != NULL) {
346 GPSPositionGroundspeedGet(&groundspeed);
347 lt_airspeed = (uint8_t)roundf(groundspeed);
350 FlightStatusData fdata;
351 FlightStatusGet(&fdata);
352 lt_arm = fdata.Armed;
355 else if (lt_arm == 2)
357 if (fdata.ControlSource == FLIGHTSTATUS_CONTROLSOURCE_FAILSAFE)
366 switch (fdata.FlightMode) {
367 case FLIGHTSTATUS_FLIGHTMODE_MANUAL:
368 lt_flightmode = 0;
break;
369 case FLIGHTSTATUS_FLIGHTMODE_STABILIZED1:
370 lt_flightmode = 5;
break;
371 case FLIGHTSTATUS_FLIGHTMODE_STABILIZED2:
372 lt_flightmode = 6;
break;
373 case FLIGHTSTATUS_FLIGHTMODE_STABILIZED3:
374 lt_flightmode = 7;
break;
375 case FLIGHTSTATUS_FLIGHTMODE_ALTITUDEHOLD:
376 lt_flightmode = 8;
break;
377 case FLIGHTSTATUS_FLIGHTMODE_POSITIONHOLD:
378 lt_flightmode = 9;
break;
379 case FLIGHTSTATUS_FLIGHTMODE_RETURNTOHOME:
380 lt_flightmode = 13;
break;
381 case FLIGHTSTATUS_FLIGHTMODE_PATHPLANNER:
382 lt_flightmode = 10;
break;
387 uint8_t LTBuff[LTM_SFRAME_SIZE];
396 LTBuff[3] = (lt_vbat >> 8*0) & 0xFF;
397 LTBuff[4] = (lt_vbat >> 8*1) & 0xFF;
398 LTBuff[5] = (lt_amp >> 8*0) & 0xFF;
399 LTBuff[6] = (lt_amp >> 8*1) & 0xFF;
400 LTBuff[7] = (lt_rssi >> 8*0) & 0xFF;
401 LTBuff[8] = (lt_airspeed >> 8*0) & 0xFF;
402 LTBuff[9] = ((lt_flightmode << 2)& 0xFF ) | ((lt_failsafe << 1)& 0b00000010 ) | (lt_arm & 0b00000001) ;
404 return send_LTM_Packet(LTBuff,LTM_SFRAME_SIZE);
407 static int send_LTM_Packet(uint8_t *LTPacket, uint8_t LTPacket_size)
410 uint8_t LTCrc = 0x00;
411 for (
int i = 3;
i < LTPacket_size-1;
i++) {
412 LTCrc ^= LTPacket[
i];
414 LTPacket[LTPacket_size-1] = LTCrc;
417 LTPacket, LTPacket_size);
430 ModuleSettingsLightTelemetrySpeedGet(&speed);
434 if (speed == MODULESETTINGS_LIGHTTELEMETRYSPEED_1200)
439 #endif //end define lighttelemetry
static void updateSettings()
int32_t PIOS_COM_SendBufferNonBlocking(uintptr_t com_id, const uint8_t *buffer, uint16_t len)
static struct pios_thread * taskHandle
bool PIOS_Modules_IsEnabled(enum pios_modules module)
void PIOS_HAL_ConfigureSerialSpeed(uintptr_t com_id, HwSharedSpeedBpsOptions speed)
#define PIOS_COM_LIGHTTELEMETRY
#define MODULE_INITCALL(ifn, sfn)
struct pios_thread * PIOS_Thread_Create(void(*fp)(void *), const char *namep, size_t stack_bytes, void *argp, enum pios_thread_prio_e prio)
int32_t TaskMonitorAdd(TaskInfoRunningElem task, struct pios_thread *threadp)
void PIOS_Thread_Sleep(uint32_t time_ms)
Includes PiOS and core architecture components.