1
0
mirror of https://bitbucket.org/librepilot/librepilot.git synced 2024-12-01 09:24:10 +01:00

LP-548 OPLink will output OPLink receiver objects if mode is set to control or data and control and PPM output is not configured. Also adds support for OPLInkReceiver to all FCs.

This commit is contained in:
Brian Webb 2017-09-03 18:11:46 -07:00
parent 586a073d33
commit 9356ac91da
39 changed files with 214 additions and 59 deletions

View File

@ -551,11 +551,9 @@ static void ProcessTelemetryStream(UAVTalkConnection inConnectionHandle, UAVTalk
switch (objId) {
case OPLINKSTATUS_OBJID:
case OPLINKSETTINGS_OBJID:
case OPLINKRECEIVER_OBJID:
case MetaObjectId(OPLINKSTATUS_OBJID):
case MetaObjectId(OPLINKSETTINGS_OBJID):
case MetaObjectId(OPLINKRECEIVER_OBJID):
UAVTalkReceiveObject(inConnectionHandle);
UAVTalkReceiveObject(inConnectionHandle, true);
break;
case OBJECTPERSISTENCE_OBJID:
case MetaObjectId(OBJECTPERSISTENCE_OBJID):
@ -568,7 +566,7 @@ static void ProcessTelemetryStream(UAVTalkConnection inConnectionHandle, UAVTalk
// Second ack/nack will not match an open transaction or will apply to wrong transaction
// Question : how does GCS handle receiving the same object twice
// The OBJECTPERSISTENCE logic can be broken too if for example OPLM nacks and then REVO acks...
UAVTalkReceiveObject(inConnectionHandle);
UAVTalkReceiveObject(inConnectionHandle, true);
// relay packet to remote modem
UAVTalkRelayPacket(inConnectionHandle, outConnectionHandle);
break;
@ -616,7 +614,9 @@ static void ProcessRadioStream(UAVTalkConnection inConnectionHandle, UAVTalkConn
// These objects are received by the modem and are not transmitted to the telemetry port
// - OPLINKRECEIVER_OBJID : not sure why
// some objects will send back a response to the remote modem
UAVTalkReceiveObject(inConnectionHandle);
UAVTalkReceiveObject(inConnectionHandle, true);
// all other packets are relayed to the telemetry port
UAVTalkRelayPacket(inConnectionHandle, outConnectionHandle);
break;
default:
// all other packets are relayed to the telemetry port

View File

@ -43,7 +43,7 @@
#include "gpspositionsensor.h"
#include "manualcontrolcommand.h"
#include "manualcontrolsettings.h"
#include "oplinkstatus.h"
#include "oplinkreceiver.h"
#include "accessorydesired.h"
#include "attitudestate.h"
#include "airspeedstate.h"
@ -481,7 +481,7 @@ static void msp_send_analog(struct msp_bridge *m)
#ifdef PIOS_INCLUDE_OPLINKRCVR
if (channelGroups.Throttle == MANUALCONTROLSETTINGS_CHANNELGROUPS_OPLINK) {
int8_t rssi;
OPLinkStatusRSSIGet(&rssi);
OPLinkReceiverRSSIGet(&rssi);
// MSP values have no units, and OSD rssi display requires calibration anyway, so we will translate OPLINK_LOW_RSSI to OPLINK_HIGH_RSSI -> 0-1023
if (rssi < OPLINK_LOW_RSSI) {

View File

@ -52,7 +52,7 @@
#include "taskinfo.h"
#include "mavlink.h"
#include "hwsettings.h"
#include "oplinkstatus.h"
#include "oplinkreceiver.h"
#include "receiverstatus.h"
#include "manualcontrolsettings.h"
@ -250,7 +250,7 @@ static void mavlink_send_rc_channels()
#ifdef PIOS_INCLUDE_OPLINKRCVR
if (channelGroups.Throttle == MANUALCONTROLSETTINGS_CHANNELGROUPS_OPLINK) {
int8_t rssi;
OPLinkStatusRSSIGet(&rssi);
OPLinkReceiverRSSIGet(&rssi);
if (rssi < OPLINK_LOW_RSSI) {
rssi = OPLINK_LOW_RSSI;

View File

@ -54,14 +54,16 @@
# ifdef PIOS_INCLUDE_GCSRCVR
# include <pios_gcsrcvr_priv.h>
# endif
# ifdef PIOS_INCLUDE_OPLINKRCVR
# include <oplinkreceiver.h>
# include <pios_oplinkrcvr_priv.h>
# endif
#endif /* PIOS_INCLUDE_RCVR */
#ifdef PIOS_INCLUDE_RFM22B
# include <oplinksettings.h>
# include <oplinkstatus.h>
# ifdef PIOS_INCLUDE_RCVR
# include <oplinkreceiver.h>
# include <pios_oplinkrcvr_priv.h>
# include <pios_openlrs.h>
# include <pios_openlrs_rcvr_priv.h>
# endif /* PIOS_INCLUDE_RCVR */
@ -525,7 +527,7 @@ void PIOS_BOARD_IO_Configure_PPM_RCVR(const struct pios_ppm_cfg *ppm_cfg)
}
#endif /* PIOS_INCLUDE_PPM */
#ifdef PIOS_INCLUDE_GCSRCVR
#if defined(PIOS_INCLUDE_GCSRCVR)
void PIOS_BOARD_IO_Configure_GCS_RCVR()
{
GCSReceiverInitialize();
@ -539,6 +541,24 @@ void PIOS_BOARD_IO_Configure_GCS_RCVR()
}
#endif /* PIOS_INCLUDE_GCSRCVR */
#if defined(PIOS_INCLUDE_OPLINKRCVR) && defined(PIOS_INCLUDE_RCVR)
void PIOS_BOARD_IO_Configure_OPLink_RCVR()
{
uint32_t pios_oplinkrcvr_id;
OPLinkReceiverInitialize();
#if defined(PIOS_INCLUDE_RFM22B)
PIOS_OPLinkRCVR_Init(&pios_oplinkrcvr_id, pios_rfm22b_id);
#else /* PIOS_INCLUDE_RFM22B */
PIOS_OPLinkRCVR_Init(&pios_oplinkrcvr_id);
#endif /* PIOS_INCLUDE_RFM22B */
uint32_t pios_oplinkrcvr_rcvr_id;
if (PIOS_RCVR_Init(&pios_oplinkrcvr_rcvr_id, &pios_oplinkrcvr_rcvr_driver, pios_oplinkrcvr_id)) {
PIOS_Assert(0);
}
pios_rcvr_group_map[MANUALCONTROLSETTINGS_CHANNELGROUPS_OPLINK] = pios_oplinkrcvr_rcvr_id;
}
#endif /* PIOS_INCLUDE_OPLINKRCVR && PIOS_INCLUDE_RCVR */
#ifdef PIOS_INCLUDE_RFM22B
void PIOS_BOARD_IO_Configure_RFM22B()
@ -596,15 +616,6 @@ void PIOS_BOARD_IO_Configure_RFM22B()
if (PIOS_RFM22B_Init(&pios_rfm22b_id, PIOS_SPI_RFM22B_ADAPTER, rfm22b_cfg->slave_num, rfm22b_cfg, oplinkSettings.RFBand)) {
PIOS_Assert(0);
}
#if defined(PIOS_INCLUDE_OPLINKRCVR) && defined(PIOS_INCLUDE_RCVR)
uint32_t pios_oplinkrcvr_id;
PIOS_OPLinkRCVR_Init(&pios_oplinkrcvr_id, pios_rfm22b_id);
uint32_t pios_oplinkrcvr_rcvr_id;
if (PIOS_RCVR_Init(&pios_oplinkrcvr_rcvr_id, &pios_oplinkrcvr_rcvr_driver, pios_oplinkrcvr_id)) {
PIOS_Assert(0);
}
pios_rcvr_group_map[MANUALCONTROLSETTINGS_CHANNELGROUPS_OPLINK] = pios_oplinkrcvr_rcvr_id;
#endif /* PIOS_INCLUDE_OPLINKRCVR && PIOS_INCLUDE_RCVR */
/* Configure the radio com interface */
if (PIOS_COM_Init(&pios_com_pri_radio_id, &pios_rfm22b_com_driver, pios_rfm22b_id,

View File

@ -60,11 +60,14 @@ struct pios_oplinkrcvr_dev {
bool Fresh;
};
static struct pios_oplinkrcvr_dev *global_oplinkrcvr_dev;
static bool PIOS_oplinkrcvr_validate(struct pios_oplinkrcvr_dev *oplinkrcvr_dev)
{
return oplinkrcvr_dev->magic == PIOS_OPLINKRCVR_DEV_MAGIC;
}
#if defined(PIOS_INCLUDE_RFM22B)
static void PIOS_oplinkrcvr_ppm_callback(uint32_t oplinkrcvr_id, const int16_t *channels)
{
/* Recover our device context */
@ -78,10 +81,21 @@ static void PIOS_oplinkrcvr_ppm_callback(uint32_t oplinkrcvr_id, const int16_t *
for (uint8_t i = 0; i < OPLINKRECEIVER_CHANNEL_NUMELEM; ++i) {
oplinkrcvr_dev->oplinkreceiverdata.Channel[i] = (i < RFM22B_PPM_NUM_CHANNELS) ? channels[i] : PIOS_RCVR_TIMEOUT;
}
OPLinkReceiverSet(&oplinkrcvr_dev->oplinkreceiverdata);
// Update the RSSI and quality fields.
int8_t rssi;
OPLinkReceiverRSSIGet(&rssi);
oplinkrcvr_dev->oplinkreceiverdata.RSSI = rssi;
uint8_t quality;
OPLinkReceiverLinkQualityGet(&quality);
// Link quality is 0-128, so scale it down to 0-100
oplinkrcvr_dev->oplinkreceiverdata.LinkQuality = quality * 100 / 128;
//OPLinkReceiverSet(&oplinkrcvr_dev->oplinkreceiverdata);
oplinkrcvr_dev->Fresh = true;
}
#endif /* PIOS_INCLUDE_RFM22B */
#if defined(PIOS_INCLUDE_FREERTOS)
static struct pios_oplinkrcvr_dev *PIOS_oplinkrcvr_alloc(void)
@ -97,6 +111,9 @@ static struct pios_oplinkrcvr_dev *PIOS_oplinkrcvr_alloc(void)
oplinkrcvr_dev->Fresh = false;
oplinkrcvr_dev->supv_timer = 0;
/* The update callback cannot receive the device pointer, so set it in a global */
global_oplinkrcvr_dev = oplinkrcvr_dev;
return oplinkrcvr_dev;
}
#else
@ -119,7 +136,21 @@ static struct pios_oplinkrcvr_dev *PIOS_oplinkrcvr_alloc(void)
}
#endif /* if defined(PIOS_INCLUDE_FREERTOS) */
static void oplinkreceiver_updated(UAVObjEvent *ev)
{
struct pios_oplinkrcvr_dev *oplinkrcvr_dev = global_oplinkrcvr_dev;
if (ev->obj == OPLinkReceiverHandle()) {
OPLinkReceiverGet(&oplinkrcvr_dev->oplinkreceiverdata);
oplinkrcvr_dev->Fresh = true;
}
}
#if defined(PIOS_INCLUDE_RFM22B)
extern int32_t PIOS_OPLinkRCVR_Init(uint32_t *oplinkrcvr_id, uint32_t rfm22b_id)
#else
extern int32_t PIOS_OPLinkRCVR_Init(uint32_t *oplinkrcvr_id)
#endif
{
struct pios_oplinkrcvr_dev *oplinkrcvr_dev;
@ -134,8 +165,13 @@ extern int32_t PIOS_OPLinkRCVR_Init(uint32_t *oplinkrcvr_id, uint32_t rfm22b_id)
oplinkrcvr_dev->oplinkreceiverdata.Channel[i] = PIOS_RCVR_TIMEOUT;
}
#if defined(PIOS_INCLUDE_RFM22B)
/* Register ppm callback */
PIOS_RFM22B_SetPPMCallback(rfm22b_id, PIOS_oplinkrcvr_ppm_callback, (uint32_t)oplinkrcvr_dev);
#endif
/* Updates could come over the telemetry channel, so register uavobj callback */
OPLinkReceiverConnectCallback(oplinkreceiver_updated);
/* Register the failsafe timer callback. */
if (!PIOS_RTC_RegisterTickCallback(PIOS_oplinkrcvr_Supervisor, (uint32_t)oplinkrcvr_dev)) {
@ -199,14 +235,17 @@ static void PIOS_oplinkrcvr_Supervisor(uint32_t oplinkrcvr_id)
oplinkrcvr_dev->Fresh = false;
}
static uint8_t PIOS_OPLinkRCVR_Quality_Get(__attribute__((unused)) uint32_t oplinkrcvr_id)
static uint8_t PIOS_OPLinkRCVR_Quality_Get(uint32_t oplinkrcvr_id)
{
uint16_t oplink_quality;
/* Recover our device context */
struct pios_oplinkrcvr_dev *oplinkrcvr_dev = (struct pios_oplinkrcvr_dev *)oplinkrcvr_id;
OPLinkStatusLinkQualityGet(&oplink_quality);
if (!PIOS_oplinkrcvr_validate(oplinkrcvr_dev)) {
/* Invalid device specified */
return 0;
}
/* link_status is in the range 0-128, so scale to a % */
return oplink_quality * 100 / 128;
return oplinkrcvr_dev->oplinkreceiverdata.LinkQuality;
}
#endif /* PIOS_INCLUDE_OPLINKRCVR */

View File

@ -1798,6 +1798,7 @@ static enum pios_radio_event radio_txStart(struct pios_rfm22b_dev *radio_dev)
}
// Should we append PPM data to the packet?
bool ppm_valid = false;
if (radio_dev->ppm_send_mode) {
len = RFM22B_PPM_NUM_CHANNELS + (radio_dev->ppm_only_mode ? 2 : 1);
@ -1817,10 +1818,13 @@ static enum pios_radio_event radio_txStart(struct pios_rfm22b_dev *radio_dev)
if ((val == PIOS_RCVR_INVALID) || (val == PIOS_RCVR_TIMEOUT)) {
val = RFM22B_PPM_INVALID;
} else if (val > RFM22B_PPM_MAX_US) {
ppm_valid = true;
val = RFM22B_PPM_MAX;
} else if (val < RFM22B_PPM_MIN_US) {
ppm_valid = true;
val = RFM22B_PPM_MIN;
} else {
ppm_valid = true;
val = (val - RFM22B_PPM_MIN_US) / RFM22B_PPM_SCALE + RFM22B_PPM_MIN;
}
@ -1844,6 +1848,7 @@ static enum pios_radio_event radio_txStart(struct pios_rfm22b_dev *radio_dev)
}
// Append data from the com interface if applicable.
bool packet_data = false;
if (!radio_dev->ppm_only_mode) {
uint8_t newlen = 0;
bool need_yield = false;
@ -1863,6 +1868,7 @@ static enum pios_radio_event radio_txStart(struct pios_rfm22b_dev *radio_dev)
i++;
}
if (newlen) {
packet_data = true;
*(p + len) = radio_dev->last_stream_sent;
len += newlen + 1;
}
@ -1885,7 +1891,7 @@ static enum pios_radio_event radio_txStart(struct pios_rfm22b_dev *radio_dev)
}
// Only count the packet if it contains valid data.
if (radio_dev->ppm_only_mode || (len > RS_ECC_NPARITY)) {
if (ppm_valid || packet_data) {
TX_LED_ON;
radio_dev->stats.tx_byte_count += len;
}

View File

@ -268,4 +268,8 @@ void PIOS_BOARD_IO_Configure_RadioAuxStream(HwSettingsRadioAuxStreamOptions radi
void PIOS_BOARD_IO_Configure_GCS_RCVR();
#endif
#ifdef PIOS_INCLUDE_OPLINKRCVR
void PIOS_BOARD_IO_Configure_OPLink_RCVR();
#endif
#endif /* PIOS_BOARD_IO_H */

View File

@ -35,7 +35,11 @@
extern const struct pios_rcvr_driver pios_oplinkrcvr_rcvr_driver;
#if defined(PIOS_INCLUDE_RFM22B)
extern int32_t PIOS_OPLinkRCVR_Init(uint32_t *oplinkrcvr_id, uint32_t rfm22b_id);
#else
extern int32_t PIOS_OPLinkRCVR_Init(uint32_t *oplinkrcvr_id);
#endif
#endif /* PIOS_OPLINKRCVR_PRIV_H */

View File

@ -105,8 +105,8 @@
#define PIOS_INCLUDE_SRXL
#define PIOS_INCLUDE_HOTT
#define PIOS_INCLUDE_IBUS
/* #define PIOS_INCLUDE_GCSRCVR */
/* #define PIOS_INCLUDE_OPLINKRCVR */
#define PIOS_INCLUDE_GCSRCVR
#define PIOS_INCLUDE_OPLINKRCVR
/* PIOS abstract receiver interface */
#define PIOS_INCLUDE_RCVR

View File

@ -251,10 +251,13 @@ void PIOS_Board_Init(void)
break;
}
#ifdef PIOS_INCLUDE_GCSRCVR
PIOS_BOARD_IO_Configure_GCS_RCVR();
#endif
#if defined(PIOS_INCLUDE_GCSRCVR)
PIOS_BOARD_IO_Configure_GCSRCVR();
#endif /* PIOS_INCLUDE_GCSRCVR */
#ifdef PIOS_INCLUDE_OPLINKRCVR
PIOS_BOARD_IO_Configure_OPLink_RCVR();
#endif
#ifndef PIOS_ENABLE_DEBUG_PINS
switch ((HwSettingsCC_RcvrPortOptions)hwsettings_rcvrport) {

View File

@ -204,6 +204,7 @@ extern uint32_t pios_ws2811_id;
#define PIOS_RCVR_MAX_DEVS 3
#define PIOS_RCVR_MAX_CHANNELS 12
#define PIOS_GCSRCVR_TIMEOUT_MS 100
#define PIOS_OPLINK_RCVR_TIMEOUT_MS 100
// -------------------------
// Receiver PPM input

View File

@ -281,6 +281,10 @@ void PIOS_Board_Init(void)
PIOS_BOARD_IO_Configure_GCS_RCVR();
#endif
#ifdef PIOS_INCLUDE_OPLINKRCVR
PIOS_BOARD_IO_Configure_OPLink_RCVR();
#endif
/* Remap AFIO pin for PB4 (Servo 5 Out)*/
GPIO_PinRemapConfig(GPIO_Remap_SWJ_NoJTRST, ENABLE);

View File

@ -228,6 +228,7 @@ extern uint32_t pios_spi_flash_accel_adapter_id;
#define PIOS_RCVR_MAX_DEVS 3
#define PIOS_RCVR_MAX_CHANNELS 12
#define PIOS_GCSRCVR_TIMEOUT_MS 100
#define PIOS_OPLINK_RCVR_TIMEOUT_MS 100
// -------------------------
// Receiver PPM input

View File

@ -315,6 +315,10 @@ void PIOS_Board_Init(void)
PIOS_BOARD_IO_Configure_GCS_RCVR();
#endif
#ifdef PIOS_INCLUDE_OPLINKRCVR
PIOS_BOARD_IO_Configure_OPLink_RCVR();
#endif
#ifndef PIOS_ENABLE_DEBUG_PINS
// pios_servo_cfg points to the correct configuration based on input port settings
PIOS_Servo_Init(pios_servo_cfg);

View File

@ -28,7 +28,8 @@ include $(FLIGHT_ROOT_DIR)/make/firmware-defs.mk
override USE_DSP_LIB := NO
# List of mandatory modules to include
MODULES += RadioComBridge
MODULES += \
RadioComBridge
# List of optional modules to include
OPTMODULES =

View File

@ -32,6 +32,7 @@
#include <pios_board_info.h>
#include <pios_ppm_out.h>
#include <oplinksettings.h>
#include <oplinkreceiver.h>
#include <pios_openlrs.h>
#include <taskinfo.h>
#ifdef PIOS_INCLUDE_SERVO
@ -133,6 +134,7 @@ void PIOS_Board_Init(void)
}
OPLinkSettingsInitialize();
OPLinkReceiverInitialize();
/* Retrieve the settings object. */
OPLinkSettingsData oplinkSettings;
@ -450,6 +452,25 @@ static void PIOS_Board_PPM_callback(__attribute__((unused)) uint32_t context, co
ppm_value = 1000 + ((rssi + 127) * 9);
PIOS_PPM_OUT_Set(PIOS_PPM_OUTPUT, RFM22B_PPM_NUM_CHANNELS, ppm_value);
}
} else {
// If there is no PPM output defined, try sending the control outputs as a UAVObject.
OPLinkReceiverData recv_data;
for (uint8_t i = 0; i < OPLINKRECEIVER_CHANNEL_NUMELEM; ++i) {
if (i < RFM22B_PPM_NUM_CHANNELS) {
recv_data.Channel[i] = channels[i];
} else {
recv_data.Channel[i] = PIOS_RCVR_TIMEOUT;
}
}
// Update the RSSI and quality fields.
int8_t rssi;
OPLinkStatusRSSIGet(&rssi);
recv_data.RSSI = rssi;
uint16_t quality;
OPLinkStatusLinkQualityGet(&quality);
// Link quality is 0-128, so scale it down to 0-100
recv_data.LinkQuality = quality * 100 / 128;
OPLinkReceiverSet(&recv_data);
}
#if defined(PIOS_INCLUDE_SERVO)
for (uint8_t i = 0; i < servo_count; ++i) {

View File

@ -111,8 +111,8 @@
#define PIOS_INCLUDE_SRXL
#define PIOS_INCLUDE_HOTT
#define PIOS_INCLUDE_IBUS
/* #define PIOS_INCLUDE_GCSRCVR */
/* #define PIOS_INCLUDE_OPLINKRCVR */
#define PIOS_INCLUDE_GCSRCVR
#define PIOS_INCLUDE_OPLINKRCVR
/* PIOS abstract receiver interface */
#define PIOS_INCLUDE_RCVR

View File

@ -226,6 +226,14 @@ void PIOS_Board_Init(void)
PIOS_BOARD_IO_Configure_PPM_RCVR(&pios_ppm_cfg);
#endif
#ifdef PIOS_INCLUDE_GCSRCVR
PIOS_BOARD_IO_Configure_GCS_RCVR();
#endif
#ifdef PIOS_INCLUDE_OPLINKRCVR
PIOS_BOARD_IO_Configure_OPLink_RCVR();
#endif
#ifndef PIOS_ENABLE_DEBUG_PINS
PIOS_Servo_Init(&pios_servo_cfg);
#else

View File

@ -161,6 +161,7 @@ extern uint32_t pios_ws2811_id;
#define PIOS_RCVR_MAX_DEVS 3
#define PIOS_RCVR_MAX_CHANNELS 12
#define PIOS_GCSRCVR_TIMEOUT_MS 100
#define PIOS_OPLINK_RCVR_TIMEOUT_MS 100
// -------------------------
// Receiver PPM input

View File

@ -315,6 +315,10 @@ void PIOS_Board_Init(void)
PIOS_BOARD_IO_Configure_GCS_RCVR();
#endif
#ifdef PIOS_INCLUDE_OPLINKRCVR
PIOS_BOARD_IO_Configure_OPLink_RCVR();
#endif
#ifndef PIOS_ENABLE_DEBUG_PINS
// pios_servo_cfg points to the correct configuration based on input port settings
PIOS_Servo_Init(pios_servo_cfg);

View File

@ -258,6 +258,10 @@ void PIOS_Board_Init(void)
PIOS_BOARD_IO_Configure_GCS_RCVR();
#endif
#ifdef PIOS_INCLUDE_OPLINKRCVR
PIOS_BOARD_IO_Configure_OPLink_RCVR();
#endif
#ifdef PIOS_INCLUDE_WS2811
#include <pios_ws2811.h>
HwSettingsWS2811LED_OutOptions ws2811_pin_settings;

View File

@ -326,6 +326,10 @@ void PIOS_Board_Init(void)
PIOS_BOARD_IO_Configure_GCS_RCVR();
#endif
#ifdef PIOS_INCLUDE_OPLINKRCVR
PIOS_BOARD_IO_Configure_OPLink_RCVR();
#endif
#ifndef PIOS_ENABLE_DEBUG_PINS
switch (hwsettings_rcvrport) {
case HWSETTINGS_RV_RCVRPORT_DISABLED:

View File

@ -196,6 +196,7 @@ extern uint32_t pios_ws2811_id;
#define PIOS_RCVR_MAX_DEVS 3
#define PIOS_RCVR_MAX_CHANNELS 12
#define PIOS_GCSRCVR_TIMEOUT_MS 100
#define PIOS_OPLINK_RCVR_TIMEOUT_MS 100
// -------------------------
// Receiver PPM input

View File

@ -274,6 +274,10 @@ void PIOS_Board_Init(void)
PIOS_BOARD_IO_Configure_GCS_RCVR();
#endif
#ifdef PIOS_INCLUDE_OPLINKRCVR
PIOS_BOARD_IO_Configure_OPLink_RCVR();
#endif
#ifndef PIOS_ENABLE_DEBUG_PINS
PIOS_Servo_Init(&pios_servo_cfg_out);
#else

View File

@ -108,8 +108,8 @@
#define PIOS_INCLUDE_SRXL
#define PIOS_INCLUDE_HOTT
#define PIOS_INCLUDE_IBUS
/* #define PIOS_INCLUDE_GCSRCVR */
/* #define PIOS_INCLUDE_OPLINKRCVR */
#define PIOS_INCLUDE_GCSRCVR
#define PIOS_INCLUDE_OPLINKRCVR
/* PIOS abstract receiver interface */
#define PIOS_INCLUDE_RCVR

View File

@ -239,6 +239,14 @@ void PIOS_Board_Init(void)
#endif /* if defined(PIOS_INCLUDE_PWM) */
}
#ifdef PIOS_INCLUDE_GCSRCVR
PIOS_BOARD_IO_Configure_GCS_RCVR();
#endif
#ifdef PIOS_INCLUDE_OPLINKRCVR
PIOS_BOARD_IO_Configure_OPLink_RCVR();
#endif
#ifndef PIOS_ENABLE_DEBUG_PINS
// TODO: make use of HWSPRACINGF3SETTINGS_IOPORTS_[PPM]OUTPUTS
PIOS_Servo_Init(&pios_servo_cfg);

View File

@ -167,6 +167,7 @@ extern uint32_t pios_ws2811_id;
#define PIOS_RCVR_MAX_DEVS 3
#define PIOS_RCVR_MAX_CHANNELS 12
#define PIOS_GCSRCVR_TIMEOUT_MS 100
#define PIOS_OPLINK_RCVR_TIMEOUT_MS 100
// -------------------------
// Receiver PPM input

View File

@ -111,8 +111,8 @@
#define PIOS_INCLUDE_SRXL
#define PIOS_INCLUDE_HOTT
#define PIOS_INCLUDE_IBUS
/* #define PIOS_INCLUDE_GCSRCVR */
/* #define PIOS_INCLUDE_OPLINKRCVR */
#define PIOS_INCLUDE_GCSRCVR
#define PIOS_INCLUDE_OPLINKRCVR
/* PIOS abstract receiver interface */
#define PIOS_INCLUDE_RCVR

View File

@ -227,6 +227,14 @@ void PIOS_Board_Init(void)
PIOS_BOARD_IO_Configure_PPM_RCVR(&pios_ppm_cfg);
}
#ifdef PIOS_INCLUDE_GCSRCVR
PIOS_BOARD_IO_Configure_GCS_RCVR();
#endif
#ifdef PIOS_INCLUDE_OPLINKRCVR
PIOS_BOARD_IO_Configure_OPLink_RCVR();
#endif
#ifndef PIOS_ENABLE_DEBUG_PINS
PIOS_Servo_Init(&pios_servo_cfg);
#else

View File

@ -172,6 +172,7 @@ extern uint32_t pios_ws2811_id;
#define PIOS_RCVR_MAX_DEVS 3
#define PIOS_RCVR_MAX_CHANNELS 12
#define PIOS_GCSRCVR_TIMEOUT_MS 100
#define PIOS_OPLINK_RCVR_TIMEOUT_MS 100
// -------------------------
// Receiver PPM input

View File

@ -111,8 +111,8 @@
#define PIOS_INCLUDE_SRXL
#define PIOS_INCLUDE_HOTT
#define PIOS_INCLUDE_IBUS
/* #define PIOS_INCLUDE_GCSRCVR */
/* #define PIOS_INCLUDE_OPLINKRCVR */
#define PIOS_INCLUDE_GCSRCVR
#define PIOS_INCLUDE_OPLINKRCVR
#define PIOS_INCLUDE_FRSKY_SENSORHUB

View File

@ -254,6 +254,14 @@ void PIOS_Board_Init(void)
PIOS_BOARD_IO_Configure_UART(&pios_usart_cfg[0], PIOS_BOARD_IO_UART_COMBRIDGE);
}
#ifdef PIOS_INCLUDE_GCSRCVR
PIOS_BOARD_IO_Configure_GCS_RCVR();
#endif
#ifdef PIOS_INCLUDE_OPLINKRCVR
PIOS_BOARD_IO_Configure_OPLink_RCVR();
#endif
#ifdef PIOS_ENABLE_DEBUG_PINS
PIOS_DEBUG_Init(&pios_servo_cfg.channels, pios_servo_cfg.num_channels);
#else

View File

@ -135,6 +135,7 @@ extern uint32_t pios_ws2811_id;
#define PIOS_RCVR_MAX_DEVS 3
#define PIOS_RCVR_MAX_CHANNELS 12
#define PIOS_GCSRCVR_TIMEOUT_MS 100
#define PIOS_OPLINK_RCVR_TIMEOUT_MS 100
// -------------------------
// Receiver PPM input

View File

@ -202,7 +202,7 @@ bool UAVObjIsSingleInstance(UAVObjHandle obj);
bool UAVObjIsMetaobject(UAVObjHandle obj);
bool UAVObjIsSettings(UAVObjHandle obj);
bool UAVObjIsPriority(UAVObjHandle obj);
int32_t UAVObjUnpack(UAVObjHandle obj_handle, uint16_t instId, const uint8_t *dataIn);
int32_t UAVObjUnpack(UAVObjHandle obj_handle, uint16_t instId, const uint8_t *dataIn, bool create);
int32_t UAVObjPack(UAVObjHandle obj_handle, uint16_t instId, uint8_t *dataOut);
uint8_t UAVObjUpdateCRC(UAVObjHandle obj_handle, uint16_t instId, uint8_t crc);
int32_t UAVObjSave(UAVObjHandle obj_handle, uint16_t instId);

View File

@ -513,7 +513,7 @@ unlock_exit:
* \param[in] dataIn The byte array
* \return 0 if success or -1 if failure
*/
int32_t UAVObjUnpack(UAVObjHandle obj_handle, uint16_t instId, const uint8_t *dataIn)
int32_t UAVObjUnpack(UAVObjHandle obj_handle, uint16_t instId, const uint8_t *dataIn, bool create)
{
PIOS_Assert(obj_handle);
@ -538,12 +538,13 @@ int32_t UAVObjUnpack(UAVObjHandle obj_handle, uint16_t instId, const uint8_t *da
instEntry = getInstance(obj, instId);
// If the instance does not exist create it and any other instances before it
if (instEntry == NULL) {
if ((instEntry == NULL) && create) {
instEntry = createInstance(obj, instId);
}
if (instEntry == NULL) {
goto unlock_exit;
}
}
// Set the data
memcpy(InstanceData(instEntry), dataIn, obj->type->instance_size);
}

View File

@ -60,7 +60,7 @@ int32_t UAVTalkSendObjectRequest(UAVTalkConnection connection, UAVObjHandle obj,
UAVTalkRxState UAVTalkProcessInputStream(UAVTalkConnection connectionHandle, uint8_t *rxbuffer, uint8_t length);
UAVTalkRxState UAVTalkProcessInputStreamQuiet(UAVTalkConnection connectionHandle, uint8_t *rxbuffer, uint8_t length, uint8_t *position);
int32_t UAVTalkRelayPacket(UAVTalkConnection inConnectionHandle, UAVTalkConnection outConnectionHandle);
int32_t UAVTalkReceiveObject(UAVTalkConnection connectionHandle);
int32_t UAVTalkReceiveObject(UAVTalkConnection connectionHandle, bool create);
void UAVTalkGetStats(UAVTalkConnection connection, UAVTalkStats *stats, bool reset);
void UAVTalkAddStats(UAVTalkConnection connection, UAVTalkStats *stats, bool reset);
void UAVTalkResetStats(UAVTalkConnection connection);

View File

@ -51,7 +51,7 @@
static int32_t objectTransaction(UAVTalkConnectionData *connection, uint8_t type, UAVObjHandle obj, uint16_t instId, int32_t timeout);
static int32_t sendObject(UAVTalkConnectionData *connection, uint8_t type, uint32_t objId, uint16_t instId, UAVObjHandle obj);
static int32_t sendSingleObject(UAVTalkConnectionData *connection, uint8_t type, uint32_t objId, uint16_t instId, UAVObjHandle obj);
static int32_t receiveObject(UAVTalkConnectionData *connection, uint8_t type, uint32_t objId, uint16_t instId, uint8_t *data);
static int32_t receiveObject(UAVTalkConnectionData *connection, uint8_t type, uint32_t objId, uint16_t instId, uint8_t *data, bool create);
static void updateAck(UAVTalkConnectionData *connection, uint8_t type, uint32_t objId, uint16_t instId);
// UavTalk Process FSM functions
static bool UAVTalkProcess_SYNC(UAVTalkConnectionData *connection, UAVTalkInputProcessor *iproc, uint8_t *rxbuffer, uint8_t length, uint8_t *position);
@ -444,7 +444,7 @@ UAVTalkRxState UAVTalkProcessInputStream(UAVTalkConnection connectionHandle, uin
while (position < length) {
state = UAVTalkProcessInputStreamQuiet(connectionHandle, rxbuffer, length, &position);
if (state == UAVTALK_STATE_COMPLETE) {
UAVTalkReceiveObject(connectionHandle);
UAVTalkReceiveObject(connectionHandle, true);
}
}
return state;
@ -546,7 +546,7 @@ int32_t UAVTalkRelayPacket(UAVTalkConnection inConnectionHandle, UAVTalkConnecti
* \return 0 Success
* \return -1 Failure
*/
int32_t UAVTalkReceiveObject(UAVTalkConnection connectionHandle)
int32_t UAVTalkReceiveObject(UAVTalkConnection connectionHandle, bool create)
{
UAVTalkConnectionData *connection;
@ -557,7 +557,7 @@ int32_t UAVTalkReceiveObject(UAVTalkConnection connectionHandle)
return -1;
}
return receiveObject(connection, iproc->type, iproc->objId, iproc->instId, connection->rxBuffer);
return receiveObject(connection, iproc->type, iproc->objId, iproc->instId, connection->rxBuffer, create);
}
/**
@ -592,7 +592,7 @@ uint32_t UAVTalkGetPacketObjId(UAVTalkConnection connectionHandle)
* \return 0 Success
* \return -1 Failure
*/
static int32_t receiveObject(UAVTalkConnectionData *connection, uint8_t type, uint32_t objId, uint16_t instId, uint8_t *data)
static int32_t receiveObject(UAVTalkConnectionData *connection, uint8_t type, uint32_t objId, uint16_t instId, uint8_t *data, bool create)
{
UAVObjHandle obj;
int32_t ret = 0;
@ -613,8 +613,8 @@ static int32_t receiveObject(UAVTalkConnectionData *connection, uint8_t type, ui
case UAVTALK_TYPE_OBJ_TS:
// All instances not allowed for OBJ messages
if (obj && (instId != UAVOBJ_ALL_INSTANCES)) {
// Unpack object, if the instance does not exist it will be created!
if (UAVObjUnpack(obj, instId, data) == 0) {
// Unpack object, if create is true and the instance does not exist it will be created!
if (UAVObjUnpack(obj, instId, data, create) == 0) {
// Check if this object acks a pending OBJ_REQ message
// any OBJ message can ack a pending OBJ_REQ message
// even one that was not sent in response to the OBJ_REQ message
@ -632,8 +632,8 @@ static int32_t receiveObject(UAVTalkConnectionData *connection, uint8_t type, ui
UAVT_DEBUGLOG_CPRINTF(objId, "OBJ_ACK %X %d", objId, instId);
// All instances not allowed for OBJ_ACK messages
if (obj && (instId != UAVOBJ_ALL_INSTANCES)) {
// Unpack object, if the instance does not exist it will be created!
if (UAVObjUnpack(obj, instId, data) == 0) {
// Unpack object, if create is true and the instance does not exist it will be created!
if (UAVObjUnpack(obj, instId, data, create) == 0) {
UAVT_DEBUGLOG_CPRINTF(objId, "OBJ ACK %X %d", objId, instId);
// Object updated or created, transmit ACK
sendObject(connection, UAVTALK_TYPE_ACK, objId, instId, NULL);

View File

@ -56,7 +56,7 @@ class UavtalkDemo():
_port = int(port[3:]) - 1
else:
_port = port
serPort = serial.Serial(_port, 57600, timeout=.5)
serPort = serial.Serial(port, 115200, timeout=.5)
if not serPort.isOpen():
raise IOError("Failed to open serial port")

View File

@ -2,6 +2,8 @@
<object name="OPLinkReceiver" singleinstance="true" settings="false" category="System">
<description>A receiver channel group carried over the OPLink radio.</description>
<field name="Channel" units="us" type="int16" elements="16"/>
<field name="RSSI" units="dBm" type="int8" elements="1" defaultvalue="0"/>
<field name="LinkQuality" units="%" type="uint8" elements="1" defaultvalue="0"/>
<access gcs="readonly" flight="readwrite"/>
<telemetrygcs acked="false" updatemode="manual" period="0"/>
<telemetryflight acked="false" updatemode="periodic" period="1000"/>