Commit 7eb9fbc6 authored by Gus Grubba's avatar Gus Grubba

Merge branch 'master' of https://github.com/mavlink/qgroundcontrol into qgc4

# Conflicts:
#	qgroundcontrol.qrc
#	src/Microhard/MicrohardSettings.qml
#	src/VehicleSetup/FirmwareUpgrade.qml
parents 745bec25 ef731572
Subproject commit 171c83700c6318af9ffb4a7ee733567b55a14543 Subproject commit 600bbff722a13cfa61fe053de1da07069bab1d10
...@@ -482,6 +482,7 @@ HEADERS += \ ...@@ -482,6 +482,7 @@ HEADERS += \
src/Settings/AppSettings.h \ src/Settings/AppSettings.h \
src/Settings/AutoConnectSettings.h \ src/Settings/AutoConnectSettings.h \
src/Settings/BrandImageSettings.h \ src/Settings/BrandImageSettings.h \
src/Settings/FirmwareUpgradeSettings.h \
src/Settings/FlightMapSettings.h \ src/Settings/FlightMapSettings.h \
src/Settings/FlyViewSettings.h \ src/Settings/FlyViewSettings.h \
src/Settings/OfflineMapsSettings.h \ src/Settings/OfflineMapsSettings.h \
...@@ -659,6 +660,7 @@ SOURCES += \ ...@@ -659,6 +660,7 @@ SOURCES += \
src/Settings/AppSettings.cc \ src/Settings/AppSettings.cc \
src/Settings/AutoConnectSettings.cc \ src/Settings/AutoConnectSettings.cc \
src/Settings/BrandImageSettings.cc \ src/Settings/BrandImageSettings.cc \
src/Settings/FirmwareUpgradeSettings.cc \
src/Settings/FlightMapSettings.cc \ src/Settings/FlightMapSettings.cc \
src/Settings/FlyViewSettings.cc \ src/Settings/FlyViewSettings.cc \
src/Settings/OfflineMapsSettings.cc \ src/Settings/OfflineMapsSettings.cc \
......
...@@ -213,8 +213,6 @@ ...@@ -213,8 +213,6 @@
<qresource prefix="/json"> <qresource prefix="/json">
<file alias="APMMavlinkStreamRate.SettingsGroup.json">src/Settings/APMMavlinkStreamRate.SettingsGroup.json</file> <file alias="APMMavlinkStreamRate.SettingsGroup.json">src/Settings/APMMavlinkStreamRate.SettingsGroup.json</file>
<file alias="BreachReturn.FactMetaData.json">src/MissionManager/BreachReturn.FactMetaData.json</file> <file alias="BreachReturn.FactMetaData.json">src/MissionManager/BreachReturn.FactMetaData.json</file>
<file alias="OfflineMaps.SettingsGroup.json">src/Settings/OfflineMaps.SettingsGroup.json</file>
<file alias="PlanView.SettingsGroup.json">src/Settings/PlanView.SettingsGroup.json</file>
<file alias="App.SettingsGroup.json">src/Settings/App.SettingsGroup.json</file> <file alias="App.SettingsGroup.json">src/Settings/App.SettingsGroup.json</file>
<file alias="AutoConnect.SettingsGroup.json">src/Settings/AutoConnect.SettingsGroup.json</file> <file alias="AutoConnect.SettingsGroup.json">src/Settings/AutoConnect.SettingsGroup.json</file>
<file alias="BrandImage.SettingsGroup.json">src/Settings/BrandImage.SettingsGroup.json</file> <file alias="BrandImage.SettingsGroup.json">src/Settings/BrandImage.SettingsGroup.json</file>
...@@ -223,6 +221,7 @@ ...@@ -223,6 +221,7 @@
<file alias="CameraSpec.FactMetaData.json">src/MissionManager/CameraSpec.FactMetaData.json</file> <file alias="CameraSpec.FactMetaData.json">src/MissionManager/CameraSpec.FactMetaData.json</file>
<file alias="CorridorScan.SettingsGroup.json">src/MissionManager/CorridorScan.SettingsGroup.json</file> <file alias="CorridorScan.SettingsGroup.json">src/MissionManager/CorridorScan.SettingsGroup.json</file>
<file alias="EditPositionDialog.FactMetaData.json">src/QmlControls/EditPositionDialog.FactMetaData.json</file> <file alias="EditPositionDialog.FactMetaData.json">src/QmlControls/EditPositionDialog.FactMetaData.json</file>
<file alias="FirmwareUpgrade.SettingsGroup.json">src/Settings/FirmwareUpgrade.SettingsGroup.json</file>
<file alias="FlightMap.SettingsGroup.json">src/Settings/FlightMap.SettingsGroup.json</file> <file alias="FlightMap.SettingsGroup.json">src/Settings/FlightMap.SettingsGroup.json</file>
<file alias="FlyView.SettingsGroup.json">src/Settings/FlyView.SettingsGroup.json</file> <file alias="FlyView.SettingsGroup.json">src/Settings/FlyView.SettingsGroup.json</file>
<file alias="FWLandingPattern.FactMetaData.json">src/MissionManager/FWLandingPattern.FactMetaData.json</file> <file alias="FWLandingPattern.FactMetaData.json">src/MissionManager/FWLandingPattern.FactMetaData.json</file>
...@@ -233,6 +232,8 @@ ...@@ -233,6 +232,8 @@
<file alias="MavCmdInfoSub.json">src/MissionManager/MavCmdInfoSub.json</file> <file alias="MavCmdInfoSub.json">src/MissionManager/MavCmdInfoSub.json</file>
<file alias="MavCmdInfoVTOL.json">src/MissionManager/MavCmdInfoVTOL.json</file> <file alias="MavCmdInfoVTOL.json">src/MissionManager/MavCmdInfoVTOL.json</file>
<file alias="MissionSettings.FactMetaData.json">src/MissionManager/MissionSettings.FactMetaData.json</file> <file alias="MissionSettings.FactMetaData.json">src/MissionManager/MissionSettings.FactMetaData.json</file>
<file alias="OfflineMaps.SettingsGroup.json">src/Settings/OfflineMaps.SettingsGroup.json</file>
<file alias="PlanView.SettingsGroup.json">src/Settings/PlanView.SettingsGroup.json</file>
<file alias="QGCMapCircle.Facts.json">src/MissionManager/QGCMapCircle.Facts.json</file> <file alias="QGCMapCircle.Facts.json">src/MissionManager/QGCMapCircle.Facts.json</file>
<file alias="RallyPoint.FactMetaData.json">src/MissionManager/RallyPoint.FactMetaData.json</file> <file alias="RallyPoint.FactMetaData.json">src/MissionManager/RallyPoint.FactMetaData.json</file>
<file alias="RTK.SettingsGroup.json">src/Settings/RTK.SettingsGroup.json</file> <file alias="RTK.SettingsGroup.json">src/Settings/RTK.SettingsGroup.json</file>
......
add_library(AutoPilotPlugins add_library(AutoPilotPlugins
APM/APMAirframeComponent.cc APM/APMAirframeComponent.cc
APM/APMAirframeComponentAirframes.cc
APM/APMAirframeComponentController.cc APM/APMAirframeComponentController.cc
APM/APMAirframeLoader.cc
APM/APMAutoPilotPlugin.cc APM/APMAutoPilotPlugin.cc
APM/APMCameraComponent.cc APM/APMCameraComponent.cc
APM/APMCompassCal.cc APM/APMCompassCal.cc
......
...@@ -107,8 +107,8 @@ QGCCameraManager::_handleHeartbeat(const mavlink_message_t &message) ...@@ -107,8 +107,8 @@ QGCCameraManager::_handleHeartbeat(const mavlink_message_t &message)
{ {
mavlink_heartbeat_t heartbeat; mavlink_heartbeat_t heartbeat;
mavlink_msg_heartbeat_decode(&message, &heartbeat); mavlink_msg_heartbeat_decode(&message, &heartbeat);
//-- If this heartbeat is from a different component within the vehicle //-- Only pay attention to "camera" component IDs
if(_vehicleReadyState && _vehicle->id() == message.sysid && _vehicle->defaultComponentId() != message.compid) { if(_vehicleReadyState && _vehicle->id() == message.sysid && message.compid >= MAV_COMP_ID_CAMERA && message.compid <= MAV_COMP_ID_CAMERA6) {
//-- First time hearing from this one? //-- First time hearing from this one?
QString sCompID = QString::number(message.compid); QString sCompID = QString::number(message.compid);
if(!_cameraInfoRequest.contains(sCompID)) { if(!_cameraInfoRequest.contains(sCompID)) {
...@@ -135,8 +135,7 @@ QGCCameraManager::_handleHeartbeat(const mavlink_message_t &message) ...@@ -135,8 +135,7 @@ QGCCameraManager::_handleHeartbeat(const mavlink_message_t &message)
} }
} else { } else {
pInfo->tryCount++; pInfo->tryCount++;
//-- Request camera info. Again. It could be something other than a camera, in which //-- Request camera info again.
// case, we won't ever receive it.
_requestCameraInfo(message.compid); _requestCameraInfo(message.compid);
} }
} }
......
...@@ -15,13 +15,12 @@ ...@@ -15,13 +15,12 @@
#include <QSettings> #include <QSettings>
#define SHORT_TIMEOUT 2500
#define LONG_TIMEOUT 5000 #define LONG_TIMEOUT 5000
static const char *kMICROHARD_GROUP = "Microhard"; static const char *kMICROHARD_GROUP = "Microhard";
static const char *kLOCAL_IP = "LocalIP"; static const char *kLOCAL_IP = "LocalIP";
static const char *kREMOTE_IP = "RemoteIP"; static const char *kREMOTE_IP = "RemoteIP";
static const char *kGROUND_IP = "GroundIP";
static const char *kAIR_IP = "AirIP";
static const char *kNET_MASK = "NetMask"; static const char *kNET_MASK = "NetMask";
static const char *kCFG_PASSWORD = "ConfigPassword"; static const char *kCFG_PASSWORD = "ConfigPassword";
static const char *kENC_KEY = "EncryptionKey"; static const char *kENC_KEY = "EncryptionKey";
...@@ -38,8 +37,6 @@ MicrohardManager::MicrohardManager(QGCApplication* app, QGCToolbox* toolbox) ...@@ -38,8 +37,6 @@ MicrohardManager::MicrohardManager(QGCApplication* app, QGCToolbox* toolbox)
settings.beginGroup(kMICROHARD_GROUP); settings.beginGroup(kMICROHARD_GROUP);
_localIPAddr = settings.value(kLOCAL_IP, QString("192.168.168.1")).toString(); _localIPAddr = settings.value(kLOCAL_IP, QString("192.168.168.1")).toString();
_remoteIPAddr = settings.value(kREMOTE_IP, QString("192.168.168.2")).toString(); _remoteIPAddr = settings.value(kREMOTE_IP, QString("192.168.168.2")).toString();
_groundIPAddr = settings.value(kGROUND_IP, QString("192.168.168.101")).toString();
_airIPAddr = settings.value(kAIR_IP, QString("192.168.168.213")).toString();
_netMask = settings.value(kNET_MASK, QString("255.255.255.0")).toString(); _netMask = settings.value(kNET_MASK, QString("255.255.255.0")).toString();
_configPassword = settings.value(kCFG_PASSWORD, QString("admin")).toString(); _configPassword = settings.value(kCFG_PASSWORD, QString("admin")).toString();
_encryptionKey = settings.value(kENC_KEY, QString("1234567890")).toString(); _encryptionKey = settings.value(kENC_KEY, QString("1234567890")).toString();
...@@ -117,10 +114,10 @@ MicrohardManager::setToolbox(QGCToolbox* toolbox) ...@@ -117,10 +114,10 @@ MicrohardManager::setToolbox(QGCToolbox* toolbox)
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
bool bool
MicrohardManager::setIPSettings(QString localIP_, QString remoteIP_, QString groundIP_, QString airIP_, QString netMask_, QString cfgPassword_, QString encryptionKey_) MicrohardManager::setIPSettings(QString localIP_, QString remoteIP_, QString netMask_, QString cfgPassword_, QString encryptionKey_)
{ {
if (_localIPAddr != localIP_ || _remoteIPAddr != remoteIP_ || _netMask != netMask_ || if (_localIPAddr != localIP_ || _remoteIPAddr != remoteIP_ || _netMask != netMask_ ||
_configPassword != cfgPassword_ || _encryptionKey != encryptionKey_ || _groundIPAddr != groundIP_ || _airIPAddr != airIP_) _configPassword != cfgPassword_ || _encryptionKey != encryptionKey_)
{ {
if (_mhSettingsLoc && _encryptionKey != encryptionKey_) { if (_mhSettingsLoc && _encryptionKey != encryptionKey_) {
_mhSettingsLoc->setEncryptionKey(encryptionKey_); _mhSettingsLoc->setEncryptionKey(encryptionKey_);
...@@ -128,8 +125,6 @@ MicrohardManager::setIPSettings(QString localIP_, QString remoteIP_, QString gro ...@@ -128,8 +125,6 @@ MicrohardManager::setIPSettings(QString localIP_, QString remoteIP_, QString gro
_localIPAddr = localIP_; _localIPAddr = localIP_;
_remoteIPAddr = remoteIP_; _remoteIPAddr = remoteIP_;
_groundIPAddr = groundIP_;
_airIPAddr = airIP_;
_netMask = netMask_; _netMask = netMask_;
_configPassword = cfgPassword_; _configPassword = cfgPassword_;
_encryptionKey = encryptionKey_; _encryptionKey = encryptionKey_;
...@@ -138,8 +133,6 @@ MicrohardManager::setIPSettings(QString localIP_, QString remoteIP_, QString gro ...@@ -138,8 +133,6 @@ MicrohardManager::setIPSettings(QString localIP_, QString remoteIP_, QString gro
settings.beginGroup(kMICROHARD_GROUP); settings.beginGroup(kMICROHARD_GROUP);
settings.setValue(kLOCAL_IP, localIP_); settings.setValue(kLOCAL_IP, localIP_);
settings.setValue(kREMOTE_IP, remoteIP_); settings.setValue(kREMOTE_IP, remoteIP_);
settings.setValue(kGROUND_IP, groundIP_);
settings.setValue(kAIR_IP, airIP_);
settings.setValue(kNET_MASK, netMask_); settings.setValue(kNET_MASK, netMask_);
settings.setValue(kCFG_PASSWORD, cfgPassword_); settings.setValue(kCFG_PASSWORD, cfgPassword_);
settings.setValue(kENC_KEY, encryptionKey_); settings.setValue(kENC_KEY, encryptionKey_);
...@@ -169,7 +162,7 @@ MicrohardManager::_setEnabled() ...@@ -169,7 +162,7 @@ MicrohardManager::_setEnabled()
connect(_mhSettingsRem, &MicrohardSettings::connected, this, &MicrohardManager::_connectedRem); connect(_mhSettingsRem, &MicrohardSettings::connected, this, &MicrohardManager::_connectedRem);
connect(_mhSettingsRem, &MicrohardSettings::rssiUpdated, this, &MicrohardManager::_rssiUpdatedRem); connect(_mhSettingsRem, &MicrohardSettings::rssiUpdated, this, &MicrohardManager::_rssiUpdatedRem);
} }
_workTimer.start(1000); _workTimer.start(SHORT_TIMEOUT);
} else { } else {
//-- Stop everything //-- Stop everything
_close(); _close();
...@@ -268,5 +261,5 @@ MicrohardManager::_checkMicrohard() ...@@ -268,5 +261,5 @@ MicrohardManager::_checkMicrohard()
_mhSettingsRem->getStatus(); _mhSettingsRem->getStatus();
} }
} }
_workTimer.start(_isConnected ? 1000 : LONG_TIMEOUT); _workTimer.start(_isConnected ? SHORT_TIMEOUT : LONG_TIMEOUT);
} }
...@@ -32,13 +32,11 @@ public: ...@@ -32,13 +32,11 @@ public:
Q_PROPERTY(int downlinkRSSI READ downlinkRSSI NOTIFY linkChanged) Q_PROPERTY(int downlinkRSSI READ downlinkRSSI NOTIFY linkChanged)
Q_PROPERTY(QString localIPAddr READ localIPAddr NOTIFY localIPAddrChanged) Q_PROPERTY(QString localIPAddr READ localIPAddr NOTIFY localIPAddrChanged)
Q_PROPERTY(QString remoteIPAddr READ remoteIPAddr NOTIFY remoteIPAddrChanged) Q_PROPERTY(QString remoteIPAddr READ remoteIPAddr NOTIFY remoteIPAddrChanged)
Q_PROPERTY(QString groundIPAddr READ groundIPAddr NOTIFY groundIPAddrChanged)
Q_PROPERTY(QString airIPAddr READ airIPAddr NOTIFY airIPAddrChanged)
Q_PROPERTY(QString netMask READ netMask NOTIFY netMaskChanged) Q_PROPERTY(QString netMask READ netMask NOTIFY netMaskChanged)
Q_PROPERTY(QString configPassword READ configPassword NOTIFY configPasswordChanged) Q_PROPERTY(QString configPassword READ configPassword NOTIFY configPasswordChanged)
Q_PROPERTY(QString encryptionKey READ encryptionKey NOTIFY encryptionKeyChanged) Q_PROPERTY(QString encryptionKey READ encryptionKey NOTIFY encryptionKeyChanged)
Q_INVOKABLE bool setIPSettings (QString localIP, QString remoteIP, QString groundIP, QString airIP, QString netMask, QString cfgPassword, QString encyrptionKey); Q_INVOKABLE bool setIPSettings (QString localIP, QString remoteIP, QString netMask, QString cfgPassword, QString encyrptionKey);
explicit MicrohardManager (QGCApplication* app, QGCToolbox* toolbox); explicit MicrohardManager (QGCApplication* app, QGCToolbox* toolbox);
~MicrohardManager () override; ~MicrohardManager () override;
...@@ -51,8 +49,6 @@ public: ...@@ -51,8 +49,6 @@ public:
int downlinkRSSI () { return _uplinkRSSI; } int downlinkRSSI () { return _uplinkRSSI; }
QString localIPAddr () { return _localIPAddr; } QString localIPAddr () { return _localIPAddr; }
QString remoteIPAddr () { return _remoteIPAddr; } QString remoteIPAddr () { return _remoteIPAddr; }
QString airIPAddr () { return _airIPAddr; }
QString groundIPAddr () { return _groundIPAddr; }
QString netMask () { return _netMask; } QString netMask () { return _netMask; }
QString configPassword () { return _configPassword; } QString configPassword () { return _configPassword; }
QString encryptionKey () { return _encryptionKey; } QString encryptionKey () { return _encryptionKey; }
...@@ -63,8 +59,6 @@ signals: ...@@ -63,8 +59,6 @@ signals:
void connectedChanged (); void connectedChanged ();
void localIPAddrChanged (); void localIPAddrChanged ();
void remoteIPAddrChanged (); void remoteIPAddrChanged ();
void airIPAddrChanged ();
void groundIPAddrChanged ();
void netMaskChanged (); void netMaskChanged ();
void configPasswordChanged (); void configPasswordChanged ();
void encryptionKeyChanged (); void encryptionKeyChanged ();
...@@ -98,8 +92,6 @@ private: ...@@ -98,8 +92,6 @@ private:
int _uplinkRSSI = 0; int _uplinkRSSI = 0;
QString _localIPAddr; QString _localIPAddr;
QString _remoteIPAddr; QString _remoteIPAddr;
QString _groundIPAddr;
QString _airIPAddr;
QString _netMask; QString _netMask;
QString _configPassword; QString _configPassword;
QString _encryptionKey; QString _encryptionKey;
......
...@@ -199,27 +199,6 @@ Rectangle { ...@@ -199,27 +199,6 @@ Rectangle {
inputMethodHints: Qt.ImhFormattedNumbersOnly inputMethodHints: Qt.ImhFormattedNumbersOnly
Layout.minimumWidth: _valueWidth Layout.minimumWidth: _valueWidth
} }
QGCLabel {
text: qsTr("Ground Unit IP Address:")
Layout.minimumWidth: _labelWidth
}
QGCTextField {
id: groundIP
text: QGroundControl.microhardManager.groundIPAddr
enabled: true
inputMethodHints: Qt.ImhFormattedNumbersOnly
Layout.minimumWidth: _valueWidth
}
QGCLabel {
text: qsTr("Air Unit IP Address:")
}
QGCTextField {
id: airIP
text: QGroundControl.microhardManager.airIPAddr
enabled: true
inputMethodHints: Qt.ImhFormattedNumbersOnly
Layout.minimumWidth: _valueWidth
}
QGCLabel { QGCLabel {
text: qsTr("Network Mask:") text: qsTr("Network Mask:")
} }
...@@ -264,16 +243,12 @@ Rectangle { ...@@ -264,16 +243,12 @@ Rectangle {
function testEnabled() { function testEnabled() {
if(localIP.text === QGroundControl.microhardManager.localIPAddr && if(localIP.text === QGroundControl.microhardManager.localIPAddr &&
remoteIP.text === QGroundControl.microhardManager.remoteIPAddr && remoteIP.text === QGroundControl.microhardManager.remoteIPAddr &&
groundIP.text === QGroundControl.microhardManager.groundIPAddr &&
airIP.text === QGroundControl.microhardManager.airIPAddr &&
netMask.text === QGroundControl.microhardManager.netMask && netMask.text === QGroundControl.microhardManager.netMask &&
configPassword.text === QGroundControl.microhardManager.configPassword && configPassword.text === QGroundControl.microhardManager.configPassword &&
encryptionKey.text === QGroundControl.microhardManager.encryptionKey) encryptionKey.text === QGroundControl.microhardManager.encryptionKey)
return false return false
if(!validateIPaddress(localIP.text)) return false if(!validateIPaddress(localIP.text)) return false
if(!validateIPaddress(remoteIP.text)) return false if(!validateIPaddress(remoteIP.text)) return false
if(!validateIPaddress(groundIP.text)) return false
if(!validateIPaddress(airIP.text)) return false
if(!validateIPaddress(netMask.text)) return false if(!validateIPaddress(netMask.text)) return false
return true return true
} }
...@@ -281,7 +256,7 @@ Rectangle { ...@@ -281,7 +256,7 @@ Rectangle {
text: qsTr("Apply") text: qsTr("Apply")
anchors.horizontalCenter: parent.horizontalCenter anchors.horizontalCenter: parent.horizontalCenter
onClicked: { onClicked: {
QGroundControl.microhardManager.setIPSettings(localIP.text, remoteIP.text, groundIP.text, airIP.text, netMask.text, configPassword.text, encryptionKey.text) QGroundControl.microhardManager.setIPSettings(localIP.text, remoteIP.text, netMask.text, configPassword.text, encryptionKey.text)
} }
} }
...@@ -289,4 +264,4 @@ Rectangle { ...@@ -289,4 +264,4 @@ Rectangle {
} }
} }
} }
} }
[
{
"name": "defaultFirmwareType",
"shortDescription": "Default firmware type for flashing",
"type": "uint32",
"defaultValue": 12
},
{
"name": "apmChibiOS",
"type": "uint32",
"enumStrings": "ChibiOS,NuttX",
"enumValues": "0,1",
"defaultValue": 0
},
{
"name": "apmVehicleType",
"type": "uint32",
"enumStrings": "Multi-Rotor,Helicopter,Plane,Rover,Sub",
"enumValues": "0,1,2,3,4",
"defaultValue": 0
}
]
/****************************************************************************
*
* (c) 2009-2016 QGROUNDCONTROL PROJECT <http://www.qgroundcontrol.org>
*
* QGroundControl is licensed according to the terms in the file
* COPYING.md in the root of the source code directory.
*
****************************************************************************/
#include "FirmwareUpgradeSettings.h"
#include <QQmlEngine>
#include <QtQml>
DECLARE_SETTINGGROUP(FirmwareUpgrade, "FirmwareUpgrade")
{
qmlRegisterUncreatableType<FirmwareUpgradeSettings>("QGroundControl.SettingsManager", 1, 0, "FirmwareUpgradeSettings", "Reference only");
}
DECLARE_SETTINGSFACT(FirmwareUpgradeSettings, defaultFirmwareType)
DECLARE_SETTINGSFACT(FirmwareUpgradeSettings, apmChibiOS)
DECLARE_SETTINGSFACT(FirmwareUpgradeSettings, apmVehicleType)
/****************************************************************************
*
* (c) 2009-2016 QGROUNDCONTROL PROJECT <http://www.qgroundcontrol.org>
*
* QGroundControl is licensed according to the terms in the file
* COPYING.md in the root of the source code directory.
*
****************************************************************************/
#pragma once
#include "SettingsGroup.h"
#include "QGCMAVLink.h"
class FirmwareUpgradeSettings : public SettingsGroup
{
Q_OBJECT
public:
FirmwareUpgradeSettings(QObject* parent = nullptr);
DEFINE_SETTING_NAME_GROUP()
DEFINE_SETTINGFACT(defaultFirmwareType)
DEFINE_SETTINGFACT(apmChibiOS)
DEFINE_SETTINGFACT(apmVehicleType)
};
...@@ -27,6 +27,7 @@ SettingsManager::SettingsManager(QGCApplication* app, QGCToolbox* toolbox) ...@@ -27,6 +27,7 @@ SettingsManager::SettingsManager(QGCApplication* app, QGCToolbox* toolbox)
, _planViewSettings (nullptr) , _planViewSettings (nullptr)
, _brandImageSettings (nullptr) , _brandImageSettings (nullptr)
, _offlineMapsSettings (nullptr) , _offlineMapsSettings (nullptr)
, _firmwareUpgradeSettings (nullptr)
#if !defined(NO_ARDUPILOT_DIALECT) #if !defined(NO_ARDUPILOT_DIALECT)
, _apmMavlinkStreamRateSettings (nullptr) , _apmMavlinkStreamRateSettings (nullptr)
#endif #endif
...@@ -50,8 +51,9 @@ void SettingsManager::setToolbox(QGCToolbox *toolbox) ...@@ -50,8 +51,9 @@ void SettingsManager::setToolbox(QGCToolbox *toolbox)
_planViewSettings = new PlanViewSettings (this); _planViewSettings = new PlanViewSettings (this);
_brandImageSettings = new BrandImageSettings (this); _brandImageSettings = new BrandImageSettings (this);
_offlineMapsSettings = new OfflineMapsSettings (this); _offlineMapsSettings = new OfflineMapsSettings (this);
_firmwareUpgradeSettings = new FirmwareUpgradeSettings (this);
#if !defined(NO_ARDUPILOT_DIALECT) #if !defined(NO_ARDUPILOT_DIALECT)
_apmMavlinkStreamRateSettings = new APMMavlinkStreamRateSettings (this); _apmMavlinkStreamRateSettings = new APMMavlinkStreamRateSettings(this);
#endif #endif
#if defined(QGC_AIRMAP_ENABLED) #if defined(QGC_AIRMAP_ENABLED)
_airMapSettings = new AirMapSettings (this); _airMapSettings = new AirMapSettings (this);
......
...@@ -25,6 +25,7 @@ ...@@ -25,6 +25,7 @@
#include "BrandImageSettings.h" #include "BrandImageSettings.h"
#include "OfflineMapsSettings.h" #include "OfflineMapsSettings.h"
#include "APMMavlinkStreamRateSettings.h" #include "APMMavlinkStreamRateSettings.h"
#include "FirmwareUpgradeSettings.h"
#if defined(QGC_AIRMAP_ENABLED) #if defined(QGC_AIRMAP_ENABLED)
#include "AirMapSettings.h" #include "AirMapSettings.h"
#endif #endif
...@@ -51,6 +52,7 @@ public: ...@@ -51,6 +52,7 @@ public:
Q_PROPERTY(QObject* planViewSettings READ planViewSettings CONSTANT) Q_PROPERTY(QObject* planViewSettings READ planViewSettings CONSTANT)
Q_PROPERTY(QObject* brandImageSettings READ brandImageSettings CONSTANT) Q_PROPERTY(QObject* brandImageSettings READ brandImageSettings CONSTANT)
Q_PROPERTY(QObject* offlineMapsSettings READ offlineMapsSettings CONSTANT) Q_PROPERTY(QObject* offlineMapsSettings READ offlineMapsSettings CONSTANT)
Q_PROPERTY(QObject* firmwareUpgradeSettings READ firmwareUpgradeSettings CONSTANT)
#if !defined(NO_ARDUPILOT_DIALECT) #if !defined(NO_ARDUPILOT_DIALECT)
Q_PROPERTY(QObject* apmMavlinkStreamRateSettings READ apmMavlinkStreamRateSettings CONSTANT) Q_PROPERTY(QObject* apmMavlinkStreamRateSettings READ apmMavlinkStreamRateSettings CONSTANT)
#endif #endif
...@@ -70,6 +72,7 @@ public: ...@@ -70,6 +72,7 @@ public:
PlanViewSettings* planViewSettings (void) { return _planViewSettings; } PlanViewSettings* planViewSettings (void) { return _planViewSettings; }
BrandImageSettings* brandImageSettings (void) { return _brandImageSettings; } BrandImageSettings* brandImageSettings (void) { return _brandImageSettings; }
OfflineMapsSettings* offlineMapsSettings (void) { return _offlineMapsSettings; } OfflineMapsSettings* offlineMapsSettings (void) { return _offlineMapsSettings; }
FirmwareUpgradeSettings* firmwareUpgradeSettings (void) { return _firmwareUpgradeSettings; }
#if !defined(NO_ARDUPILOT_DIALECT) #if !defined(NO_ARDUPILOT_DIALECT)
APMMavlinkStreamRateSettings* apmMavlinkStreamRateSettings(void) { return _apmMavlinkStreamRateSettings; } APMMavlinkStreamRateSettings* apmMavlinkStreamRateSettings(void) { return _apmMavlinkStreamRateSettings; }
#endif #endif
...@@ -87,6 +90,7 @@ private: ...@@ -87,6 +90,7 @@ private:
PlanViewSettings* _planViewSettings; PlanViewSettings* _planViewSettings;
BrandImageSettings* _brandImageSettings; BrandImageSettings* _brandImageSettings;
OfflineMapsSettings* _offlineMapsSettings; OfflineMapsSettings* _offlineMapsSettings;
FirmwareUpgradeSettings* _firmwareUpgradeSettings;
#if !defined(NO_ARDUPILOT_DIALECT) #if !defined(NO_ARDUPILOT_DIALECT)
APMMavlinkStreamRateSettings* _apmMavlinkStreamRateSettings; APMMavlinkStreamRateSettings* _apmMavlinkStreamRateSettings;
#endif #endif
......
...@@ -3333,6 +3333,10 @@ void Vehicle::_handleCommandAck(mavlink_message_t& message) ...@@ -3333,6 +3333,10 @@ void Vehicle::_handleCommandAck(mavlink_message_t& message)
//_startPlanRequest(); //_startPlanRequest();
} }
if (ack.command == MAV_CMD_FLASH_BOOTLOADER && ack.result == MAV_RESULT_ACCEPTED) {
qgcApp()->showMessage(tr("Bootloader flash succeeded"));
}
if (_mavCommandQueue.count() && ack.command == _mavCommandQueue[0].command) { if (_mavCommandQueue.count() && ack.command == _mavCommandQueue[0].command) {
_mavCommandAckTimer.stop(); _mavCommandAckTimer.stop();
showError = _mavCommandQueue[0].showError; showError = _mavCommandQueue[0].showError;
......
...@@ -58,7 +58,8 @@ SetupPage { ...@@ -58,7 +58,8 @@ SetupPage {
readonly property int _defaultFimwareTypePX4: 12 readonly property int _defaultFimwareTypePX4: 12
readonly property int _defaultFimwareTypeAPM: 3 readonly property int _defaultFimwareTypeAPM: 3
property var _defaultFirmwareFact: QGroundControl.settingsManager.appSettings.defaultFirmwareType property var _firmwareUpgradeSettings: QGroundControl.settingsManager.firmwareUpgradeSettings
property var _defaultFirmwareFact: _firmwareUpgradeSettings.defaultFirmwareType
property bool _defaultFirmwareIsPX4: true property bool _defaultFirmwareIsPX4: true
property string firmwareWarningMessage property string firmwareWarningMessage
...@@ -77,6 +78,18 @@ SetupPage { ...@@ -77,6 +78,18 @@ SetupPage {
controller.startBoardSearch() controller.startBoardSearch()
_defaultFirmwareIsPX4 = _defaultFirmwareFact.rawValue === _defaultFimwareTypePX4 // we don't want this to be bound and change as radios are selected _defaultFirmwareIsPX4 = _defaultFirmwareFact.rawValue === _defaultFimwareTypePX4 // we don't want this to be bound and change as radios are selected
} }
function firmwareVersionChanged(model) {
firmwareVersionWarningLabel.visible = false
// All of this bizarre, setting model to null and index to 1 and then to 0 is to work around
// strangeness in the combo box implementation. This sequence of steps correctly changes the combo model
// without generating any warnings and correctly updates the combo text with the new selection.
firmwareBuildTypeCombo.model = null
firmwareBuildTypeCombo.model = model
firmwareBuildTypeCombo.currentIndex = 1
firmwareBuildTypeCombo.currentIndex = 0
}
QGCPalette { id: qgcPal; colorGroupEnabled: true }
FirmwareUpgradeController { FirmwareUpgradeController {
id: controller id: controller
...@@ -139,7 +152,7 @@ SetupPage { ...@@ -139,7 +152,7 @@ SetupPage {
function updatePX4VersionDisplay() { function updatePX4VersionDisplay() {
var versionString = "" var versionString = ""
if (_advanced.checked) { if (_advanced.checked) {
switch (controller.selectedFirmwareType) { switch (controller.selectedFirmwareBuildType) {
case FirmwareUpgradeController.StableFirmware: case FirmwareUpgradeController.StableFirmware:
versionString = controller.px4StableVersion versionString = controller.px4StableVersion
break break
...@@ -150,8 +163,8 @@ SetupPage { ...@@ -150,8 +163,8 @@ SetupPage {
} else { } else {
versionString = controller.px4StableVersion versionString = controller.px4StableVersion
} }
px4FlightStackRadio1.text = qsTr("PX4 Flight Stack ") + versionString px4FlightStackRadio.text = qsTr("PX4 Pro ") + versionString
px4FlightStackRadio2.text = qsTr("PX4 Flight Stack ") + versionString //px4FlightStackRadio2.text = qsTr("PX4 Pro ") + versionString
} }
Component.onCompleted: { Component.onCompleted: {
...@@ -161,12 +174,11 @@ SetupPage { ...@@ -161,12 +174,11 @@ SetupPage {
} }
function accept() { function accept() {
hideDialog()
if (_singleFirmwareMode) { if (_singleFirmwareMode) {
controller.flashSingleFirmwareMode(controller.selectedFirmwareType) controller.flashSingleFirmwareMode(controller.selectedFirmwareBuildType)
} else { } else {
var stack var stack
var firmwareType = firmwareVersionCombo.model.get(firmwareVersionCombo.currentIndex).firmwareType var firmwareBuildType = firmwareBuildTypeCombo.model.get(firmwareBuildTypeCombo.currentIndex).firmwareType
var vehicleType = FirmwareUpgradeController.DefaultVehicleFirmware var vehicleType = FirmwareUpgradeController.DefaultVehicleFirmware
if (px4Flow) { if (px4Flow) {
...@@ -175,11 +187,25 @@ SetupPage { ...@@ -175,11 +187,25 @@ SetupPage {
} else { } else {
stack = apmFlightStack.checked ? FirmwareUpgradeController.AutoPilotStackAPM : FirmwareUpgradeController.AutoPilotStackPX4 stack = apmFlightStack.checked ? FirmwareUpgradeController.AutoPilotStackAPM : FirmwareUpgradeController.AutoPilotStackPX4
if (apmFlightStack.checked) { if (apmFlightStack.checked) {
vehicleType = controller.vehicleTypeFromVersionIndex(vehicleTypeSelectionCombo.currentIndex) if (firmwareBuildType === FirmwareUpgradeController.CustomFirmware) {
vehicleType = apmVehicleTypeCombo.currentIndex
} else {
if (controller.apmFirmwareNames.length === 0) {
// Not ready yet, or no firmware available
return
} }
var firmwareUrl = controller.apmFirmwareUrls[ardupilotFirmwareSelectionCombo.currentIndex]
if (firmwareUrl == "") {
return
}
controller.flashFirmwareUrl(controller.apmFirmwareUrls[ardupilotFirmwareSelectionCombo.currentIndex])
hideDialog()
return
} }
}
controller.flash(stack, firmwareType, vehicleType) }
controller.flash(stack, firmwareBuildType, vehicleType)
hideDialog()
} }
} }
...@@ -195,7 +221,7 @@ SetupPage { ...@@ -195,7 +221,7 @@ SetupPage {
} }
ListModel { ListModel {
id: firmwareTypeList id: firmwareBuildTypeList
ListElement { ListElement {
text: qsTr("Standard Version (stable)") text: qsTr("Standard Version (stable)")
...@@ -275,65 +301,86 @@ SetupPage { ...@@ -275,65 +301,86 @@ SetupPage {
readonly property string _singleFirmwareLabel: qsTr("Press Ok to upgrade your vehicle.") readonly property string _singleFirmwareLabel: qsTr("Press Ok to upgrade your vehicle.")
} }
function firmwareVersionChanged(model) { QGCLabel { text: qsTr("Flight Stack") }
firmwareVersionWarningLabel.visible = false
// All of this bizarre, setting model to null and index to 1 and then to 0 is to work around RowLayout {
// strangeness in the combo box implementation. This sequence of steps correctly changes the combo model spacing: _margins
// without generating any warnings and correctly updates the combo text with the new selection. layoutDirection: px4FlightStackRadio.checked ? Qt.LeftToRight : Qt.RightToLeft
firmwareVersionCombo.model = null
firmwareVersionCombo.model = model
firmwareVersionCombo.currentIndex = 1
firmwareVersionCombo.currentIndex = 0
}
// The following craziness of three radio buttons to represent two radio buttons is so that the // The following craziness of three radio buttons to represent two radio buttons is so that the
// order can be changed such that the default firmware button is always on the top // order can be changed such that the default firmware button is always on the top
//-- Visible only if you have an option. If it's the only option, it's already setup. //-- Visible only if you have an option. If it's the only option, it's already setup.
QGCRadioButton { QGCRadioButton {
id: px4FlightStackRadio1 id: px4FlightStackRadio
text: qsTr("PX4 Flight Stack ") exclusiveGroup: firmwareGroup
text: qsTr("PX4 Pro ")
textBold: _defaultFirmwareIsPX4 textBold: _defaultFirmwareIsPX4
checked: _defaultFirmwareIsPX4 checked: _defaultFirmwareIsPX4
visible: _defaultFirmwareIsPX4 && !_singleFirmwareMode && !px4Flow && QGroundControl.hasAPMSupport visible: !_singleFirmwareMode && !px4Flow
onClicked: { onClicked: {
_defaultFirmwareFact.rawValue = _defaultFimwareTypePX4 _defaultFirmwareFact.rawValue = _defaultFimwareTypePX4
parent.firmwareVersionChanged(firmwareTypeList) firmwareVersionChanged(firmwareBuildTypeList)
} }
} }
QGCRadioButton { QGCRadioButton {
id: apmFlightStack id: apmFlightStack
text: qsTr("ArduPilot Flight Stack") exclusiveGroup: firmwareGroup
text: qsTr("ArduPilot")
textBold: !_defaultFirmwareIsPX4 textBold: !_defaultFirmwareIsPX4
checked: !_defaultFirmwareIsPX4 checked: !_defaultFirmwareIsPX4
visible: !_singleFirmwareMode && !px4Flow && QGroundControl.hasAPMSupport visible: !_singleFirmwareMode && !px4Flow && QGroundControl.hasAPMSupport
onClicked: { onClicked: {
_defaultFirmwareFact.rawValue = _defaultFimwareTypeAPM _defaultFirmwareFact.rawValue = _defaultFimwareTypeAPM
parent.firmwareVersionChanged(firmwareTypeList) firmwareVersionChanged(firmwareBuildTypeList)
}
} }
} }
//-- Visible only if you have an option. If it's the only option, it's already setup. FactComboBox {
QGCRadioButton { anchors.left: parent.left
id: px4FlightStackRadio2 anchors.right: parent.right
text: qsTr("PX4 Flight Stack ") visible: !px4Flow && apmFlightStack.checked
visible: !_defaultFirmwareIsPX4 && !_singleFirmwareMode && !px4Flow && QGroundControl.hasAPMSupport fact: _firmwareUpgradeSettings.apmChibiOS
indexModel: false
onClicked: {
_defaultFirmwareFact.rawValue = _defaultFimwareTypePX4
parent.firmwareVersionChanged(firmwareTypeList)
} }
FactComboBox {
id: apmVehicleTypeCombo
anchors.left: parent.left
anchors.right: parent.right
visible: !px4Flow && apmFlightStack.checked
fact: _firmwareUpgradeSettings.apmVehicleType
indexModel: false
} }
QGCComboBox { QGCComboBox {
id: vehicleTypeSelectionCombo id: ardupilotFirmwareSelectionCombo
anchors.left: parent.left anchors.left: parent.left
anchors.right: parent.right anchors.right: parent.right
visible: !px4Flow && apmFlightStack.checked visible: !px4Flow && apmFlightStack.checked && !controller.downloadingFirmwareList && controller.apmFirmwareNames.length !== 0
model: controller.apmAvailableVersions model: controller.apmFirmwareNames
onModelChanged: console.log("model", model)
}
QGCLabel {
anchors.left: parent.left
anchors.right: parent.right
wrapMode: Text.WordWrap
text: qsTr("Downloading list of available firmwares...")
visible: controller.downloadingFirmwareList
}
QGCLabel {
anchors.left: parent.left
anchors.right: parent.right
wrapMode: Text.WordWrap
text: qsTr("No Firmware Available")
visible: !controller.downloadingFirmwareList && controller.apmFirmwareNames.length === 0
} }
QGCComboBox { QGCComboBox {
...@@ -363,7 +410,7 @@ SetupPage { ...@@ -363,7 +410,7 @@ SetupPage {
checked: px4Flow ? true : false checked: px4Flow ? true : false
onClicked: { onClicked: {
firmwareVersionCombo.currentIndex = 0 firmwareBuildTypeCombo.currentIndex = 0
firmwareVersionWarningLabel.visible = false firmwareVersionWarningLabel.visible = false
updatePX4VersionDisplay() updatePX4VersionDisplay()
} }
...@@ -385,15 +432,15 @@ SetupPage { ...@@ -385,15 +432,15 @@ SetupPage {
} }
QGCComboBox { QGCComboBox {
id: firmwareVersionCombo id: firmwareBuildTypeCombo
anchors.left: parent.left anchors.left: parent.left
anchors.right: parent.right anchors.right: parent.right
visible: showFirmwareTypeSelection visible: showFirmwareTypeSelection
model: _singleFirmwareMode ? singleFirmwareModeTypeList : (px4Flow ? px4FlowTypeList : firmwareTypeList) model: _singleFirmwareMode ? singleFirmwareModeTypeList : (px4Flow ? px4FlowTypeList : firmwareBuildTypeList)
currentIndex: controller.selectedFirmwareType currentIndex: controller.selectedFirmwareBuildType
onActivated: { onActivated: {
controller.selectedFirmwareType = model.get(index).firmwareType controller.selectedFirmwareBuildType = model.get(index).firmwareType
if (model.get(index).firmwareType === FirmwareUpgradeController.BetaFirmware) { if (model.get(index).firmwareType === FirmwareUpgradeController.BetaFirmware) {
firmwareVersionWarningLabel.visible = true firmwareVersionWarningLabel.visible = true
firmwareVersionWarningLabel.text = qsTr("WARNING: BETA FIRMWARE. ") + firmwareVersionWarningLabel.text = qsTr("WARNING: BETA FIRMWARE. ") +
......
...@@ -7,11 +7,6 @@ ...@@ -7,11 +7,6 @@
* *
****************************************************************************/ ****************************************************************************/
/// @file
/// @brief PX4 Firmware Upgrade UI
/// @author Don Gagne <don@thegagnes.com>
#include "FirmwareUpgradeController.h" #include "FirmwareUpgradeController.h"
#include "Bootloader.h" #include "Bootloader.h"
//-- TODO: #include "QGCQFileDialog.h" //-- TODO: #include "QGCQFileDialog.h"
...@@ -19,6 +14,8 @@ ...@@ -19,6 +14,8 @@
#include "QGCFileDownload.h" #include "QGCFileDownload.h"
#include "QGCOptions.h" #include "QGCOptions.h"
#include "QGCCorePlugin.h" #include "QGCCorePlugin.h"
#include "FirmwareUpgradeSettings.h"
#include "SettingsManager.h"
#include <QStandardPaths> #include <QStandardPaths>
#include <QRegularExpression> #include <QRegularExpression>
...@@ -27,9 +24,22 @@ ...@@ -27,9 +24,22 @@
#include <QJsonArray> #include <QJsonArray>
#include <QNetworkProxy> #include <QNetworkProxy>
const char* FirmwareUpgradeController::_manifestFirmwareJsonKey = "firmware";
const char* FirmwareUpgradeController::_manifestBoardIdJsonKey = "board_id";
const char* FirmwareUpgradeController::_manifestMavTypeJsonKey = "mav-type";
const char* FirmwareUpgradeController::_manifestFormatJsonKey = "format";
const char* FirmwareUpgradeController::_manifestUrlJsonKey = "url";
const char* FirmwareUpgradeController::_manifestMavFirmwareVersionTypeJsonKey = "mav-firmware-version-type";
const char* FirmwareUpgradeController::_manifestUSBIDJsonKey = "USBID";
const char* FirmwareUpgradeController::_manifestMavFirmwareVersionJsonKey = "mav-firmware-version";
const char* FirmwareUpgradeController::_manifestBootloaderStrJsonKey = "bootloader_str";
const char* FirmwareUpgradeController::_manifestLatestKey = "latest";
const char* FirmwareUpgradeController::_manifestPlatformKey = "platform";
const char* FirmwareUpgradeController::_manifestBrandNameKey = "brand_name";
struct FirmwareToUrlElement_t { struct FirmwareToUrlElement_t {
FirmwareUpgradeController::AutoPilotStackType_t stackType; FirmwareUpgradeController::AutoPilotStackType_t stackType;
FirmwareUpgradeController::FirmwareType_t firmwareType; FirmwareUpgradeController::FirmwareBuildType_t firmwareType;
FirmwareUpgradeController::FirmwareVehicleType_t vehicleType; FirmwareUpgradeController::FirmwareVehicleType_t vehicleType;
QString url; QString url;
}; };
...@@ -45,13 +55,26 @@ uint qHash(const FirmwareUpgradeController::FirmwareIdentifier& firmwareId) ...@@ -45,13 +55,26 @@ uint qHash(const FirmwareUpgradeController::FirmwareIdentifier& firmwareId)
FirmwareUpgradeController::FirmwareUpgradeController(void) FirmwareUpgradeController::FirmwareUpgradeController(void)
: _singleFirmwareURL (qgcApp()->toolbox()->corePlugin()->options()->firmwareUpgradeSingleURL()) : _singleFirmwareURL (qgcApp()->toolbox()->corePlugin()->options()->firmwareUpgradeSingleURL())
, _singleFirmwareMode (!_singleFirmwareURL.isEmpty()) , _singleFirmwareMode (!_singleFirmwareURL.isEmpty())
, _downloadingFirmwareList (false)
, _downloadManager (nullptr) , _downloadManager (nullptr)
, _downloadNetworkReply (nullptr) , _downloadNetworkReply (nullptr)
, _statusLog (nullptr) , _statusLog (nullptr)
, _selectedFirmwareType (StableFirmware) , _selectedFirmwareBuildType (StableFirmware)
, _image (nullptr) , _image (nullptr)
, _apmBoardDescriptionReplaceText ("<APMBoardDescription>") , _apmBoardDescriptionReplaceText ("<APMBoardDescription>")
, _apmChibiOSSetting (qgcApp()->toolbox()->settingsManager()->firmwareUpgradeSettings()->apmChibiOS())
, _apmVehicleTypeSetting (qgcApp()->toolbox()->settingsManager()->firmwareUpgradeSettings()->apmVehicleType())
{ {
_manifestMavFirmwareVersionTypeToFirmwareBuildTypeMap["OFFICIAL"] = StableFirmware;
_manifestMavFirmwareVersionTypeToFirmwareBuildTypeMap["BETA"] = BetaFirmware;
_manifestMavFirmwareVersionTypeToFirmwareBuildTypeMap["DEV"] = DeveloperFirmware;
_manifestMavTypeToFirmwareVehicleTypeMap["Copter"] = CopterFirmware;
_manifestMavTypeToFirmwareVehicleTypeMap["HELICOPTER"] = HeliFirmware;
_manifestMavTypeToFirmwareVehicleTypeMap["FIXED_WING"] = PlaneFirmware;
_manifestMavTypeToFirmwareVehicleTypeMap["GROUND_ROVER"] = RoverFirmware;
_manifestMavTypeToFirmwareVehicleTypeMap["SUBMARINE"] = SubFirmware;
_threadController = new PX4FirmwareUpgradeThreadController(this); _threadController = new PX4FirmwareUpgradeThreadController(this);
Q_CHECK_PTR(_threadController); Q_CHECK_PTR(_threadController);
...@@ -70,8 +93,12 @@ FirmwareUpgradeController::FirmwareUpgradeController(void) ...@@ -70,8 +93,12 @@ FirmwareUpgradeController::FirmwareUpgradeController(void)
connect(&_eraseTimer, &QTimer::timeout, this, &FirmwareUpgradeController::_eraseProgressTick); connect(&_eraseTimer, &QTimer::timeout, this, &FirmwareUpgradeController::_eraseProgressTick);
connect(_apmChibiOSSetting, &Fact::rawValueChanged, this, &FirmwareUpgradeController::_buildAPMFirmwareNames);
connect(_apmVehicleTypeSetting, &Fact::rawValueChanged, this, &FirmwareUpgradeController::_buildAPMFirmwareNames);
_initFirmwareHash(); _initFirmwareHash();
_determinePX4StableVersion(); _determinePX4StableVersion();
_downloadArduPilotManifest();
} }
FirmwareUpgradeController::~FirmwareUpgradeController() FirmwareUpgradeController::~FirmwareUpgradeController()
...@@ -97,7 +124,7 @@ void FirmwareUpgradeController::startBoardSearch(void) ...@@ -97,7 +124,7 @@ void FirmwareUpgradeController::startBoardSearch(void)
} }
void FirmwareUpgradeController::flash(AutoPilotStackType_t stackType, void FirmwareUpgradeController::flash(AutoPilotStackType_t stackType,
FirmwareType_t firmwareType, FirmwareBuildType_t firmwareType,
FirmwareVehicleType_t vehicleType) FirmwareVehicleType_t vehicleType)
{ {
qCDebug(FirmwareUpgradeLog) << "_flash stackType:firmwareType:vehicleType" << stackType << firmwareType << vehicleType; qCDebug(FirmwareUpgradeLog) << "_flash stackType:firmwareType:vehicleType" << stackType << firmwareType << vehicleType;
...@@ -108,6 +135,18 @@ void FirmwareUpgradeController::flash(AutoPilotStackType_t stackType, ...@@ -108,6 +135,18 @@ void FirmwareUpgradeController::flash(AutoPilotStackType_t stackType,
// We haven't found the bootloader yet. Need to wait until then to flash // We haven't found the bootloader yet. Need to wait until then to flash
_startFlashWhenBootloaderFound = true; _startFlashWhenBootloaderFound = true;
_startFlashWhenBootloaderFoundFirmwareIdentity = firmwareId; _startFlashWhenBootloaderFoundFirmwareIdentity = firmwareId;
_firmwareFilename.clear();
}
}
void FirmwareUpgradeController::flashFirmwareUrl(QString firmwareFlashUrl)
{
_firmwareFilename = firmwareFlashUrl;
if (_bootloaderFound) {
_downloadFirmware();
} else {
// We haven't found the bootloader yet. Need to wait until then to flash
_startFlashWhenBootloaderFound = true;
} }
} }
...@@ -116,7 +155,7 @@ void FirmwareUpgradeController::flash(const FirmwareIdentifier& firmwareId) ...@@ -116,7 +155,7 @@ void FirmwareUpgradeController::flash(const FirmwareIdentifier& firmwareId)
flash(firmwareId.autopilotStackType, firmwareId.firmwareType, firmwareId.firmwareVehicleType); flash(firmwareId.autopilotStackType, firmwareId.firmwareType, firmwareId.firmwareVehicleType);
} }
void FirmwareUpgradeController::flashSingleFirmwareMode(FirmwareType_t firmwareType) void FirmwareUpgradeController::flashSingleFirmwareMode(FirmwareBuildType_t firmwareType)
{ {
flash(SingleFirmwareMode, firmwareType, DefaultVehicleFirmware); flash(SingleFirmwareMode, firmwareType, DefaultVehicleFirmware);
} }
...@@ -132,6 +171,9 @@ void FirmwareUpgradeController::_foundBoard(bool firstAttempt, const QSerialPort ...@@ -132,6 +171,9 @@ void FirmwareUpgradeController::_foundBoard(bool firstAttempt, const QSerialPort
_foundBoardInfo = info; _foundBoardInfo = info;
_foundBoardType = static_cast<QGCSerialPortInfo::BoardType_t>(boardType); _foundBoardType = static_cast<QGCSerialPortInfo::BoardType_t>(boardType);
_foundBoardTypeName = boardName; _foundBoardTypeName = boardName;
qDebug() << info.manufacturer() << info.description();
_startFlashWhenBootloaderFound = false; _startFlashWhenBootloaderFound = false;
if (_foundBoardType == QGCSerialPortInfo::BoardTypeSiKRadio) { if (_foundBoardType == QGCSerialPortInfo::BoardTypeSiKRadio) {
...@@ -178,7 +220,9 @@ void FirmwareUpgradeController::_foundBootloader(int bootloaderVersion, int boar ...@@ -178,7 +220,9 @@ void FirmwareUpgradeController::_foundBootloader(int bootloaderVersion, int boar
flash(_startFlashWhenBootloaderFoundFirmwareIdentity); flash(_startFlashWhenBootloaderFoundFirmwareIdentity);
} }
_loadAPMVersions(_bootloaderBoardID); if (_rgManifestFirmwareInfo.count()) {
_buildAPMFirmwareNames();
}
} }
...@@ -197,19 +241,6 @@ void FirmwareUpgradeController::_initFirmwareHash() ...@@ -197,19 +241,6 @@ void FirmwareUpgradeController::_initFirmwareHash()
{ AutoPilotStackPX4, StableFirmware, DefaultVehicleFirmware, "http://gumstix-aerocore.s3.amazonaws.com/PX4/stable/aerocore_default.px4"}, { AutoPilotStackPX4, StableFirmware, DefaultVehicleFirmware, "http://gumstix-aerocore.s3.amazonaws.com/PX4/stable/aerocore_default.px4"},
{ AutoPilotStackPX4, BetaFirmware, DefaultVehicleFirmware, "http://gumstix-aerocore.s3.amazonaws.com/PX4/beta/aerocore_default.px4"}, { AutoPilotStackPX4, BetaFirmware, DefaultVehicleFirmware, "http://gumstix-aerocore.s3.amazonaws.com/PX4/beta/aerocore_default.px4"},
{ AutoPilotStackPX4, DeveloperFirmware, DefaultVehicleFirmware, "http://gumstix-aerocore.s3.amazonaws.com/PX4/master/aerocore_default.px4"}, { AutoPilotStackPX4, DeveloperFirmware, DefaultVehicleFirmware, "http://gumstix-aerocore.s3.amazonaws.com/PX4/master/aerocore_default.px4"},
#if !defined(NO_ARDUPILOT_DIALECT)
{ AutoPilotStackAPM, BetaFirmware, CopterFirmware, "http://firmware.ardupilot.org/Copter/beta/PX4/ArduCopter-v2.px4"},
{ AutoPilotStackAPM, StableFirmware, HeliFirmware, "http://gumstix-aerocore.s3.amazonaws.com/Copter/stable/PX4-heli/ArduCopter-v2.px4"},
{ AutoPilotStackAPM, StableFirmware, PlaneFirmware, "http://gumstix-aerocore.s3.amazonaws.com/Plane/stable/PX4/ArduPlane-v2.px4"},
{ AutoPilotStackAPM, StableFirmware, RoverFirmware, "http://gumstix-aerocore.s3.amazonaws.com/Rover/stable/PX4/APMrover2-v2.px4"},
{ AutoPilotStackAPM, BetaFirmware, HeliFirmware, "http://firmware.ardupilot.org/Copter/beta/PX4-heli/ArduCopter-v2.px4"},
{ AutoPilotStackAPM, BetaFirmware, PlaneFirmware, "http://firmware.ardupilot.org/Plane/beta/PX4/ArduPlane-v2.px4"},
{ AutoPilotStackAPM, BetaFirmware, RoverFirmware, "http://firmware.ardupilot.org/Rover/beta/PX4/APMrover2-v2.px4"},
{ AutoPilotStackAPM, DeveloperFirmware, CopterFirmware, "http://gumstix-aerocore.s3.amazonaws.com/Copter/latest/PX4/ArduCopter-v2.px4"},
{ AutoPilotStackAPM, DeveloperFirmware, HeliFirmware, "http://gumstix-aerocore.s3.amazonaws.com/Copter/latest/PX4-heli/ArduCopter-v2.px4"},
{ AutoPilotStackAPM, DeveloperFirmware, PlaneFirmware, "http://gumstix-aerocore.s3.amazonaws.com/Plane/latest/PX4/ArduPlane-v2.px4"},
{ AutoPilotStackAPM, DeveloperFirmware, RoverFirmware, "http://gumstix-aerocore.s3.amazonaws.com/Rover/latest/PX4/APMrover2-v2.px4"}
#endif
}; };
//////////////////////////////////// AUAVX2_1 firmwares ////////////////////////////////////////////////// //////////////////////////////////// AUAVX2_1 firmwares //////////////////////////////////////////////////
...@@ -217,23 +248,6 @@ void FirmwareUpgradeController::_initFirmwareHash() ...@@ -217,23 +248,6 @@ void FirmwareUpgradeController::_initFirmwareHash()
{ AutoPilotStackPX4, StableFirmware, DefaultVehicleFirmware, "http://px4-travis.s3.amazonaws.com/Firmware/stable/auav-x21_default.px4"}, { AutoPilotStackPX4, StableFirmware, DefaultVehicleFirmware, "http://px4-travis.s3.amazonaws.com/Firmware/stable/auav-x21_default.px4"},
{ AutoPilotStackPX4, BetaFirmware, DefaultVehicleFirmware, "http://px4-travis.s3.amazonaws.com/Firmware/beta/auav-x21_default.px4"}, { AutoPilotStackPX4, BetaFirmware, DefaultVehicleFirmware, "http://px4-travis.s3.amazonaws.com/Firmware/beta/auav-x21_default.px4"},
{ AutoPilotStackPX4, DeveloperFirmware, DefaultVehicleFirmware, "http://px4-travis.s3.amazonaws.com/Firmware/master/auav-x21_default.px4"}, { AutoPilotStackPX4, DeveloperFirmware, DefaultVehicleFirmware, "http://px4-travis.s3.amazonaws.com/Firmware/master/auav-x21_default.px4"},
#if !defined(NO_ARDUPILOT_DIALECT)
{ AutoPilotStackAPM, StableFirmware, CopterFirmware, "http://firmware.ardupilot.org/Copter/stable/PX4/ArduCopter-v3.px4"},
{ AutoPilotStackAPM, StableFirmware, HeliFirmware, "http://firmware.ardupilot.org/Copter/stable/PX4-heli/ArduCopter-v3.px4"},
{ AutoPilotStackAPM, StableFirmware, PlaneFirmware, "http://firmware.ardupilot.org/Plane/stable/PX4/ArduPlane-v2.px4"},
{ AutoPilotStackAPM, StableFirmware, RoverFirmware, "http://firmware.ardupilot.org/Rover/stable/PX4/APMrover2-v2.px4"},
{ AutoPilotStackAPM, StableFirmware, SubFirmware, "http://firmware.ardupilot.org/Sub/stable/PX4/ArduSub-v2.px4"},
{ AutoPilotStackAPM, BetaFirmware, CopterFirmware, "http://firmware.ardupilot.org/Copter/beta/PX4/ArduCopter-v3.px4"},
{ AutoPilotStackAPM, BetaFirmware, HeliFirmware, "http://firmware.ardupilot.org/Copter/beta/PX4-heli/ArduCopter-v3.px4"},
{ AutoPilotStackAPM, BetaFirmware, PlaneFirmware, "http://firmware.ardupilot.org/Plane/beta/PX4/ArduPlane-v3.px4"},
{ AutoPilotStackAPM, BetaFirmware, RoverFirmware, "http://firmware.ardupilot.org/Rover/beta/PX4/APMrover2-v3.px4"},
{ AutoPilotStackAPM, BetaFirmware, SubFirmware, "http://firmware.ardupilot.org/Sub/beta/PX4/ArduSub-v3.px4"},
{ AutoPilotStackAPM, DeveloperFirmware, CopterFirmware, "http://firmware.ardupilot.org/Copter/latest/PX4/ArduCopter-v3.px4"},
{ AutoPilotStackAPM, DeveloperFirmware, HeliFirmware, "http://firmware.ardupilot.org/Copter/latest/PX4-heli/ArduCopter-v3.px4"},
{ AutoPilotStackAPM, DeveloperFirmware, PlaneFirmware, "http://firmware.ardupilot.org/Plane/latest/PX4/ArduPlane-v3.px4"},
{ AutoPilotStackAPM, DeveloperFirmware, RoverFirmware, "http://firmware.ardupilot.org/Rover/latest/PX4/APMrover2-v3.px4"},
{ AutoPilotStackAPM, DeveloperFirmware, SubFirmware, "http://firmware.ardupilot.org/Sub/latest/PX4/ArduSub-v3.px4"}
#endif
}; };
//////////////////////////////////// MindPXFMUV2 firmwares ////////////////////////////////////////////////// //////////////////////////////////// MindPXFMUV2 firmwares //////////////////////////////////////////////////
FirmwareToUrlElement_t rgMindPXFMUV2FirmwareArray[] = { FirmwareToUrlElement_t rgMindPXFMUV2FirmwareArray[] = {
...@@ -288,7 +302,7 @@ void FirmwareUpgradeController::_initFirmwareHash() ...@@ -288,7 +302,7 @@ void FirmwareUpgradeController::_initFirmwareHash()
{ ThreeDRRadio, StableFirmware, DefaultVehicleFirmware, "http://px4-travis.s3.amazonaws.com/SiK/stable/radio~hm_trp.ihx"} { ThreeDRRadio, StableFirmware, DefaultVehicleFirmware, "http://px4-travis.s3.amazonaws.com/SiK/stable/radio~hm_trp.ihx"}
}; };
// We build the maps for PX4 and ArduPilot firmwares dynamically using the data below // We build the maps for PX4 firmwares dynamically using the data below
#if 0 #if 0
Example URLs for PX4 and ArduPilot Example URLs for PX4 and ArduPilot
...@@ -298,77 +312,14 @@ void FirmwareUpgradeController::_initFirmwareHash() ...@@ -298,77 +312,14 @@ void FirmwareUpgradeController::_initFirmwareHash()
#endif #endif
QString px4Url ("http://px4-travis.s3.amazonaws.com/Firmware/%1/px4fmu-%2_default.px4"); QString px4Url ("http://px4-travis.s3.amazonaws.com/Firmware/%1/px4fmu-%2_default.px4");
QString apmUrl ("http://firmware.ardupilot.org/%1/%2/%3/%4-v%5.px4");
QString apmChibiOSUrl ("http://firmware.ardupilot.org/%1/%2/fmuv%3%4/%5.apj");
QMap<FirmwareType_t, QString> px4MapFirmwareTypeToDir; QMap<FirmwareBuildType_t, QString> px4MapFirmwareTypeToDir;
px4MapFirmwareTypeToDir[StableFirmware] = QStringLiteral("stable"); px4MapFirmwareTypeToDir[StableFirmware] = QStringLiteral("stable");
px4MapFirmwareTypeToDir[BetaFirmware] = QStringLiteral("beta"); px4MapFirmwareTypeToDir[BetaFirmware] = QStringLiteral("beta");
px4MapFirmwareTypeToDir[DeveloperFirmware] = QStringLiteral("master"); px4MapFirmwareTypeToDir[DeveloperFirmware] = QStringLiteral("master");
#if !defined(NO_ARDUPILOT_DIALECT)
QMap<FirmwareVehicleType_t, QString> apmMapVehicleTypeToDir;
apmMapVehicleTypeToDir[CopterFirmware] = QStringLiteral("Copter");
apmMapVehicleTypeToDir[HeliFirmware] = QStringLiteral("Copter");
apmMapVehicleTypeToDir[PlaneFirmware] = QStringLiteral("Plane");
apmMapVehicleTypeToDir[RoverFirmware] = QStringLiteral("Rover");
apmMapVehicleTypeToDir[SubFirmware] = QStringLiteral("Sub");
#endif
#if !defined(NO_ARDUPILOT_DIALECT)
QMap<FirmwareVehicleType_t, QString> apmChibiOSMapVehicleTypeToDir;
apmChibiOSMapVehicleTypeToDir[CopterChibiOSFirmware] = QStringLiteral("Copter");
apmChibiOSMapVehicleTypeToDir[HeliChibiOSFirmware] = QStringLiteral("Copter");
apmChibiOSMapVehicleTypeToDir[PlaneChibiOSFirmware] = QStringLiteral("Plane");
apmChibiOSMapVehicleTypeToDir[RoverChibiOSFirmware] = QStringLiteral("Rover");
apmChibiOSMapVehicleTypeToDir[SubChibiOSFirmware] = QStringLiteral("Sub");
#endif
#if !defined(NO_ARDUPILOT_DIALECT)
QMap<FirmwareType_t, QString> apmMapFirmwareTypeToDir;
apmMapFirmwareTypeToDir[StableFirmware] = QStringLiteral("stable");
apmMapFirmwareTypeToDir[BetaFirmware] = QStringLiteral("beta");
apmMapFirmwareTypeToDir[DeveloperFirmware] = QStringLiteral("latest");
#endif
#if !defined(NO_ARDUPILOT_DIALECT)
QMap<FirmwareVehicleType_t, QString> apmMapVehicleTypeToPX4Dir;
apmMapVehicleTypeToPX4Dir[CopterFirmware] = QStringLiteral("PX4");
apmMapVehicleTypeToPX4Dir[HeliFirmware] = QStringLiteral("PX4-heli");
apmMapVehicleTypeToPX4Dir[PlaneFirmware] = QStringLiteral("PX4");
apmMapVehicleTypeToPX4Dir[RoverFirmware] = QStringLiteral("PX4");
apmMapVehicleTypeToPX4Dir[SubFirmware] = QStringLiteral("PX4");
#endif
#if !defined(NO_ARDUPILOT_DIALECT)
QMap<FirmwareVehicleType_t, QString> apmMapVehicleTypeToFilename;
apmMapVehicleTypeToFilename[CopterFirmware] = QStringLiteral("ArduCopter");
apmMapVehicleTypeToFilename[HeliFirmware] = QStringLiteral("ArduCopter");
apmMapVehicleTypeToFilename[PlaneFirmware] = QStringLiteral("ArduPlane");
apmMapVehicleTypeToFilename[RoverFirmware] = QStringLiteral("APMrover2");
apmMapVehicleTypeToFilename[SubFirmware] = QStringLiteral("ArduSub");
#endif
#if !defined(NO_ARDUPILOT_DIALECT)
QMap<FirmwareVehicleType_t, QString> apmChibiOSMapVehicleTypeToFmuDir;
apmChibiOSMapVehicleTypeToFmuDir[CopterChibiOSFirmware] = QString();
apmChibiOSMapVehicleTypeToFmuDir[HeliChibiOSFirmware] = QStringLiteral("-heli");
apmChibiOSMapVehicleTypeToFmuDir[PlaneChibiOSFirmware] = QString();
apmChibiOSMapVehicleTypeToFmuDir[RoverChibiOSFirmware] = QString();
apmChibiOSMapVehicleTypeToFmuDir[SubChibiOSFirmware] = QString();
#endif
#if !defined(NO_ARDUPILOT_DIALECT)
QMap<FirmwareVehicleType_t, QString> apmChibiOSMapVehicleTypeToFilename;
apmChibiOSMapVehicleTypeToFilename[CopterChibiOSFirmware] = QStringLiteral("arducopter");
apmChibiOSMapVehicleTypeToFilename[HeliChibiOSFirmware] = QStringLiteral("arducopter-heli");
apmChibiOSMapVehicleTypeToFilename[PlaneChibiOSFirmware] = QStringLiteral("arduplane");
apmChibiOSMapVehicleTypeToFilename[RoverChibiOSFirmware] = QStringLiteral("ardurover");
apmChibiOSMapVehicleTypeToFilename[SubChibiOSFirmware] = QStringLiteral("ardusub");
#endif
// PX4 Firmwares // PX4 Firmwares
for (const FirmwareType_t& firmwareType: px4MapFirmwareTypeToDir.keys()) { for (const FirmwareBuildType_t& firmwareType: px4MapFirmwareTypeToDir.keys()) {
QString dir = px4MapFirmwareTypeToDir[firmwareType]; QString dir = px4MapFirmwareTypeToDir[firmwareType];
_rgFMUV5Firmware.insert (FirmwareIdentifier(AutoPilotStackPX4, firmwareType, DefaultVehicleFirmware), px4Url.arg(dir).arg("v5")); _rgFMUV5Firmware.insert (FirmwareIdentifier(AutoPilotStackPX4, firmwareType, DefaultVehicleFirmware), px4Url.arg(dir).arg("v5"));
_rgFMUV4PROFirmware.insert (FirmwareIdentifier(AutoPilotStackPX4, firmwareType, DefaultVehicleFirmware), px4Url.arg(dir).arg("v4pro")); _rgFMUV4PROFirmware.insert (FirmwareIdentifier(AutoPilotStackPX4, firmwareType, DefaultVehicleFirmware), px4Url.arg(dir).arg("v4pro"));
...@@ -377,49 +328,6 @@ void FirmwareUpgradeController::_initFirmwareHash() ...@@ -377,49 +328,6 @@ void FirmwareUpgradeController::_initFirmwareHash()
_rgPX4FMUV2Firmware.insert (FirmwareIdentifier(AutoPilotStackPX4, firmwareType, DefaultVehicleFirmware), px4Url.arg(dir).arg("v2")); _rgPX4FMUV2Firmware.insert (FirmwareIdentifier(AutoPilotStackPX4, firmwareType, DefaultVehicleFirmware), px4Url.arg(dir).arg("v2"));
} }
#if !defined(NO_ARDUPILOT_DIALECT)
// ArduPilot non-ChibiOS Firmwares for direct board id to fmu mappings
for (const FirmwareType_t& firmwareType: apmMapFirmwareTypeToDir.keys()) {
QString firmwareTypeDir = apmMapFirmwareTypeToDir[firmwareType];
for (const FirmwareVehicleType_t& vehicleType: apmMapVehicleTypeToDir.keys()) {
QString vehicleTypeDir = apmMapVehicleTypeToDir[vehicleType];
QString px4Dir = apmMapVehicleTypeToPX4Dir[vehicleType];
QString filename = apmMapVehicleTypeToFilename[vehicleType];
_rgFMUV5Firmware.insert (FirmwareIdentifier(AutoPilotStackAPM, firmwareType, vehicleType), apmUrl.arg(vehicleTypeDir).arg(firmwareTypeDir).arg(px4Dir).arg(filename).arg("5"));
_rgFMUV4Firmware.insert (FirmwareIdentifier(AutoPilotStackAPM, firmwareType, vehicleType), apmUrl.arg(vehicleTypeDir).arg(firmwareTypeDir).arg(px4Dir).arg(filename).arg("4"));
_rgFMUV3Firmware.insert (FirmwareIdentifier(AutoPilotStackAPM, firmwareType, vehicleType), apmUrl.arg(vehicleTypeDir).arg(firmwareTypeDir).arg(px4Dir).arg(filename).arg("3"));
_rgPX4FMUV2Firmware.insert (FirmwareIdentifier(AutoPilotStackAPM, firmwareType, vehicleType), apmUrl.arg(vehicleTypeDir).arg(firmwareTypeDir).arg(px4Dir).arg(filename).arg("2"));
}
}
// ArduPilot ChibiOS Firmwares for direct board id to fmu mappings. Used when bootloader is not new ArduPilot bootloader.
for (const FirmwareType_t& firmwareType: apmMapFirmwareTypeToDir.keys()) {
QString firmwareTypeDir = apmMapFirmwareTypeToDir[firmwareType];
for (const FirmwareVehicleType_t& vehicleType: apmChibiOSMapVehicleTypeToDir.keys()) {
QString vehicleTypeDir = apmChibiOSMapVehicleTypeToDir[vehicleType];
QString fmuDir = apmChibiOSMapVehicleTypeToFmuDir[vehicleType];
QString filename = apmChibiOSMapVehicleTypeToFilename[vehicleType];
_rgFMUV5Firmware.insert (FirmwareIdentifier(AutoPilotStackAPM, firmwareType, vehicleType), apmChibiOSUrl.arg(vehicleTypeDir).arg(firmwareTypeDir).arg("5").arg(fmuDir).arg(filename));
_rgFMUV4Firmware.insert (FirmwareIdentifier(AutoPilotStackAPM, firmwareType, vehicleType), apmChibiOSUrl.arg(vehicleTypeDir).arg(firmwareTypeDir).arg("4").arg(fmuDir).arg(filename));
_rgFMUV3Firmware.insert (FirmwareIdentifier(AutoPilotStackAPM, firmwareType, vehicleType), apmChibiOSUrl.arg(vehicleTypeDir).arg(firmwareTypeDir).arg("3").arg(fmuDir).arg(filename));
_rgPX4FMUV2Firmware.insert (FirmwareIdentifier(AutoPilotStackAPM, firmwareType, vehicleType), apmChibiOSUrl.arg(vehicleTypeDir).arg(firmwareTypeDir).arg("2").arg(fmuDir).arg(filename));
}
}
// ArduPilot ChibiOS Firmwares when board id is an unknown type but follows ArduPilot port info naming conventions.
// This is only used if the board is using the new ArduPilot bootloader port naming scheme.
for (const FirmwareType_t& firmwareType: apmMapFirmwareTypeToDir.keys()) {
QString firmwareTypeDir = apmMapFirmwareTypeToDir[firmwareType];
for (const FirmwareVehicleType_t& vehicleType: apmChibiOSMapVehicleTypeToDir.keys()) {
QString namedURL("http://firmware.ardupilot.org/%1/%2/%3%4/%5.apj");
QString vehicleTypeDir = apmChibiOSMapVehicleTypeToDir[vehicleType];
QString fmuDir = apmChibiOSMapVehicleTypeToFmuDir[vehicleType];
QString filename = apmChibiOSMapVehicleTypeToFilename[vehicleType];
_rgAPMChibiosReplaceNamedBoardFirmware.insert(FirmwareIdentifier(AutoPilotStackAPM, firmwareType, vehicleType), namedURL.arg(vehicleTypeDir).arg(firmwareTypeDir).arg(_apmBoardDescriptionReplaceText).arg(fmuDir).arg(filename));
}
}
#endif
int size = sizeof(rgAeroCoreFirmwareArray)/sizeof(rgAeroCoreFirmwareArray[0]); int size = sizeof(rgAeroCoreFirmwareArray)/sizeof(rgAeroCoreFirmwareArray[0]);
for (int i = 0; i < size; i++) { for (int i = 0; i < size; i++) {
const FirmwareToUrlElement_t& element = rgAeroCoreFirmwareArray[i]; const FirmwareToUrlElement_t& element = rgAeroCoreFirmwareArray[i];
...@@ -550,24 +458,6 @@ QHash<FirmwareUpgradeController::FirmwareIdentifier, QString>* FirmwareUpgradeCo ...@@ -550,24 +458,6 @@ QHash<FirmwareUpgradeController::FirmwareIdentifier, QString>* FirmwareUpgradeCo
break; break;
} }
// Check for ArduPilot ChibiOS bootloader
QStringList rgManufacturers = { QStringLiteral("ArduPilot"), QStringLiteral("Hex/ProfiCNC"), QStringLiteral("Holybro") };
QString apmDescriptionSuffix("-BL");
if (rgManufacturers.contains(_foundBoardInfo.manufacturer()) && _foundBoardInfo.description().endsWith(apmDescriptionSuffix)) {
// Board ios using a ChibiOS bootloader. Prefer naming scheme from that over board ids for ArduPilot entries.
// First remove the ChibiOS by board id entries from the list
for (const FirmwareIdentifier& firmwareId: _rgAPMChibiosReplaceNamedBoardFirmware.keys()) {
_rgFirmwareDynamic.remove(firmwareId);
}
// Now add the ChibiOS by board description entries to the list
for (const FirmwareIdentifier& firmwareId: _rgAPMChibiosReplaceNamedBoardFirmware.keys()) {
QString namedUrl = _rgAPMChibiosReplaceNamedBoardFirmware[firmwareId];
_rgFirmwareDynamic.insert(firmwareId, namedUrl.replace(_apmBoardDescriptionReplaceText, _foundBoardInfo.description().left(_foundBoardInfo.description().length() - apmDescriptionSuffix.length())));
}
}
return &_rgFirmwareDynamic; return &_rgFirmwareDynamic;
} }
...@@ -659,7 +549,7 @@ void FirmwareUpgradeController::_firmwareDownloadError(QString errorMsg) ...@@ -659,7 +549,7 @@ void FirmwareUpgradeController::_firmwareDownloadError(QString errorMsg)
} }
/// @brief returns firmware type as a string /// @brief returns firmware type as a string
QString FirmwareUpgradeController::firmwareTypeAsString(FirmwareType_t type) const QString FirmwareUpgradeController::firmwareTypeAsString(FirmwareBuildType_t type) const
{ {
switch (type) { switch (type) {
case StableFirmware: case StableFirmware:
...@@ -757,119 +647,62 @@ void FirmwareUpgradeController::_eraseComplete(void) ...@@ -757,119 +647,62 @@ void FirmwareUpgradeController::_eraseComplete(void)
_eraseTimer.stop(); _eraseTimer.stop();
} }
void FirmwareUpgradeController::_loadAPMVersions(uint32_t bootloaderBoardID) void FirmwareUpgradeController::setSelectedFirmwareBuildType(FirmwareBuildType_t firmwareType)
{ {
_apmVersionMap.clear(); _selectedFirmwareBuildType = firmwareType;
emit selectedFirmwareBuildTypeChanged(_selectedFirmwareBuildType);
QHash<FirmwareIdentifier, QString>* prgFirmware = _firmwareHashForBoardId(static_cast<int>(bootloaderBoardID)); _buildAPMFirmwareNames();
for (FirmwareIdentifier firmwareId: prgFirmware->keys()) {
if (firmwareId.autopilotStackType == AutoPilotStackAPM) {
QString versionFile = QFileInfo(prgFirmware->value(firmwareId)).path() + "/git-version.txt";
qCDebug(FirmwareUpgradeLog) << "Downloading" << versionFile;
QGCFileDownload* downloader = new QGCFileDownload(this);
connect(downloader, &QGCFileDownload::downloadFinished, this, &FirmwareUpgradeController::_apmVersionDownloadFinished);
downloader->download(versionFile);
}
}
} }
void FirmwareUpgradeController::_apmVersionDownloadFinished(QString remoteFile, QString localFile) void FirmwareUpgradeController::_buildAPMFirmwareNames(void)
{ {
qCDebug(FirmwareUpgradeLog) << "Download complete" << remoteFile << localFile; qCDebug(FirmwareUpgradeLog) << "_buildAPMFirmwareNames";
// Now read the version file and pull out the version string bool chibios = _apmChibiOSSetting->rawValue().toInt() == 0;
FirmwareVehicleType_t vehicleType = static_cast<FirmwareVehicleType_t>(_apmVehicleTypeSetting->rawValue().toInt());
QFile versionFile(localFile); _apmFirmwareNames.clear();
versionFile.open(QIODevice::ReadOnly | QIODevice::Text); _apmFirmwareUrls.clear();
QTextStream stream(&versionFile);
QString versionContents = stream.readAll();
QString version; QString apmDescriptionSuffix("-BL");
QRegularExpression re("APMVERSION: (.*)$"); bool bootloaderMatch = _foundBoardInfo.description().endsWith(apmDescriptionSuffix);
QRegularExpressionMatch match = re.match(versionContents);
if (match.hasMatch()) {
version = match.captured(1);
}
if (version.isEmpty()) { for (const ManifestFirmwareInfo_t& firmwareInfo: _rgManifestFirmwareInfo) {
qWarning() << "Unable to parse version info from file" << remoteFile; bool match = false;
sender()->deleteLater(); if (firmwareInfo.firmwareBuildType == _selectedFirmwareBuildType && firmwareInfo.chibios == chibios && firmwareInfo.vehicleType == vehicleType) {
return; if (bootloaderMatch) {
if (firmwareInfo.rgBootloaderPortString.contains(_foundBoardInfo.description())) {
qCDebug(FirmwareUpgradeLog) << "Bootloader match:" << firmwareInfo.friendlyName << _foundBoardInfo.description() << firmwareInfo.rgBootloaderPortString << firmwareInfo.url << firmwareInfo.vehicleType;
match = true;
} }
} else {
// In order to determine the firmware and vehicle type for this file we find the matching entry in the firmware list if (firmwareInfo.rgVID.contains(_foundBoardInfo.vendorIdentifier()) && firmwareInfo.rgPID.contains(_foundBoardInfo.productIdentifier())) {
qCDebug(FirmwareUpgradeLog) << "Fallback match:" << firmwareInfo.friendlyName << _foundBoardInfo.vendorIdentifier() << _foundBoardInfo.productIdentifier() << _bootloaderBoardID << firmwareInfo.url << firmwareInfo.vehicleType;
QHash<FirmwareIdentifier, QString>* prgFirmware = _firmwareHashForBoardId(static_cast<int>(_bootloaderBoardID)); match = true;
QString remotePath = QFileInfo(remoteFile).path();
for (FirmwareIdentifier firmwareId: prgFirmware->keys()) {
if (remotePath == QFileInfo((*prgFirmware)[firmwareId]).path()) {
qCDebug(FirmwareUpgradeLog) << "Adding version to map, version:firwmareType:vehicleType" << version << firmwareId.firmwareType << firmwareId.firmwareVehicleType;
_apmVersionMap[firmwareId.firmwareType][firmwareId.firmwareVehicleType] = version;
} }
} }
emit apmAvailableVersionsChanged();
sender()->deleteLater();
}
void FirmwareUpgradeController::setSelectedFirmwareType(FirmwareType_t firmwareType)
{
_selectedFirmwareType = firmwareType;
emit selectedFirmwareTypeChanged(_selectedFirmwareType);
emit apmAvailableVersionsChanged();
}
QStringList FirmwareUpgradeController::apmAvailableVersions(void)
{
QStringList list;
QList<FirmwareVehicleType_t> vehicleTypes;
// This allows us to force the order of the combo box display
vehicleTypes << CopterChibiOSFirmware << HeliChibiOSFirmware << PlaneChibiOSFirmware << RoverChibiOSFirmware << SubChibiOSFirmware << CopterFirmware << HeliFirmware << PlaneFirmware << RoverFirmware << SubFirmware;
_apmVehicleTypeFromCurrentVersionList.clear();
for (FirmwareVehicleType_t vehicleType: vehicleTypes) {
if (_apmVersionMap[_selectedFirmwareType].contains(vehicleType)) {
QString version;
switch (vehicleType) {
case CopterFirmware:
version = tr("NuttX - MultiRotor:");
break;
case HeliFirmware:
version = tr("NuttX - Heli:");
break;
case CopterChibiOSFirmware:
version = tr("ChibiOS- MultiRotor:");
break;
case HeliChibiOSFirmware:
version = tr("ChibiOS - Heli:");
break;
case PlaneChibiOSFirmware:
case RoverChibiOSFirmware:
case SubChibiOSFirmware:
version = tr("ChibiOS - ");
break;
default:
version = tr("NuttX - ");
break;
} }
version += _apmVersionMap[_selectedFirmwareType][vehicleType]; // Do a final filter on fmuv2/fmuv3
_apmVehicleTypeFromCurrentVersionList.append(vehicleType); if (match && _bootloaderBoardID == Bootloader::boardIDPX4FMUV3) {
match = !firmwareInfo.fmuv2;
}
list << version; if (match) {
_apmFirmwareNames.append(firmwareInfo.friendlyName);
_apmFirmwareUrls.append(firmwareInfo.url);
} }
} }
return list; if (_apmFirmwareNames.count() > 1) {
_apmFirmwareNames.prepend(tr("Choose board type"));
_apmFirmwareUrls.prepend(QString());
}
emit apmFirmwareNamesChanged();
} }
FirmwareUpgradeController::FirmwareVehicleType_t FirmwareUpgradeController::vehicleTypeFromVersionIndex(int index) FirmwareUpgradeController::FirmwareVehicleType_t FirmwareUpgradeController::vehicleTypeFromFirmwareSelectionIndex(int index)
{ {
if (index < 0 || index >= _apmVehicleTypeFromCurrentVersionList.count()) { if (index < 0 || index >= _apmVehicleTypeFromCurrentVersionList.count()) {
qWarning() << "Invalid index, index:count" << index << _apmVehicleTypeFromCurrentVersionList.count(); qWarning() << "Invalid index, index:count" << index << _apmVehicleTypeFromCurrentVersionList.count();
...@@ -944,3 +777,147 @@ void FirmwareUpgradeController::_px4ReleasesGithubDownloadError(QString errorMsg ...@@ -944,3 +777,147 @@ void FirmwareUpgradeController::_px4ReleasesGithubDownloadError(QString errorMsg
{ {
qCWarning(FirmwareUpgradeLog) << "PX4 releases github download failed" << errorMsg; qCWarning(FirmwareUpgradeLog) << "PX4 releases github download failed" << errorMsg;
} }
void FirmwareUpgradeController::_downloadArduPilotManifest(void)
{
_downloadingFirmwareList = true;
emit downloadingFirmwareListChanged(true);
QGCFileDownload* downloader = new QGCFileDownload(this);
connect(downloader, &QGCFileDownload::downloadFinished, this, &FirmwareUpgradeController::_ardupilotManifestDownloadFinished);
connect(downloader, &QGCFileDownload::error, this, &FirmwareUpgradeController::_ardupilotManifestDownloadError);
#if 0
downloader->download(QStringLiteral("http://firmware.ardupilot.org/manifest.json.gz"));
#else
downloader->download(QStringLiteral("http://firmware.ardupilot.org/manifest.json"));
#endif
}
void FirmwareUpgradeController::_ardupilotManifestDownloadFinished(QString remoteFile, QString localFile)
{
Q_UNUSED(remoteFile);
// Delete the QGCFileDownload object
sender()->deleteLater();
qDebug() << "_ardupilotManifestDownloadFinished" << remoteFile << localFile;
#if 0
QFile gzipFile(localFile);
if (!gzipFile.open(QIODevice::ReadOnly | QIODevice::Text)) {
qCWarning(FirmwareUpgradeLog) << "Unable to open ArduPilot firmware manifest file" << localFile << gzipFile.errorString();
QFile::remove(localFile);
return;
}
// Store decompressed size as first four bytes. This is required by qUncompress routine.
QByteArray raw;
int decompressedSize = 3073444;
raw.append((unsigned char)((decompressedSize >> 24) & 0xFF));
raw.append((unsigned char)((decompressedSize >> 16) & 0xFF));
raw.append((unsigned char)((decompressedSize >> 8) & 0xFF));
raw.append((unsigned char)((decompressedSize >> 0) & 0xFF));
raw.append(gzipFile.readAll());
QByteArray bytes = qUncompress(raw);
#else
QFile jsonFile(localFile);
if (!jsonFile.open(QIODevice::ReadOnly | QIODevice::Text)) {
qCWarning(FirmwareUpgradeLog) << "Unable to open ArduPilot firmware manifest file" << localFile << jsonFile.errorString();
QFile::remove(localFile);
return;
}
QByteArray bytes = jsonFile.readAll();
jsonFile.close();
#endif
QFile::remove(localFile);
QJsonParseError jsonParseError;
QJsonDocument doc = QJsonDocument::fromJson(bytes, &jsonParseError);
if (jsonParseError.error != QJsonParseError::NoError) {
qCWarning(FirmwareUpgradeLog) << "Unable to open ArduPilot manifest json document" << localFile << jsonParseError.errorString();
}
QJsonObject json = doc.object();
QJsonArray rgFirmware = json[_manifestFirmwareJsonKey].toArray();
for (int i=0; i<rgFirmware.count(); i++) {
const QJsonObject& firmwareJson = rgFirmware[i].toObject();
FirmwareVehicleType_t firmwareVehicleType = _manifestMavTypeToFirmwareVehicleType(firmwareJson[_manifestMavTypeJsonKey].toString());
FirmwareBuildType_t firmwareBuildType = _manifestMavFirmwareVersionTypeToFirmwareBuildType(firmwareJson[_manifestMavFirmwareVersionTypeJsonKey].toString());
QString format = firmwareJson[_manifestFormatJsonKey].toString();
QString platform = firmwareJson[_manifestPlatformKey].toString();
if (firmwareVehicleType != DefaultVehicleFirmware && firmwareBuildType != CustomFirmware && (format == QStringLiteral("apj") || format == QStringLiteral("px4"))) {
if (platform.contains("-heli") && firmwareVehicleType != HeliFirmware) {
continue;
}
_rgManifestFirmwareInfo.append(ManifestFirmwareInfo_t());
ManifestFirmwareInfo_t& firmwareInfo = _rgManifestFirmwareInfo.last();
firmwareInfo.boardId = static_cast<uint32_t>(firmwareJson[_manifestBoardIdJsonKey].toInt());
firmwareInfo.firmwareBuildType = firmwareBuildType;
firmwareInfo.vehicleType = firmwareVehicleType;
firmwareInfo.url = firmwareJson[_manifestUrlJsonKey].toString();
firmwareInfo.version = firmwareJson[_manifestMavFirmwareVersionJsonKey].toString();
firmwareInfo.chibios = format == QStringLiteral("apj");
firmwareInfo.fmuv2 = platform.contains(QStringLiteral("fmuv2"));
QJsonArray bootloaderArray = firmwareJson[_manifestBootloaderStrJsonKey].toArray();
for (int j=0; j<bootloaderArray.count(); j++) {
firmwareInfo.rgBootloaderPortString.append(bootloaderArray[j].toString());
}
QJsonArray usbidArray = firmwareJson[_manifestUSBIDJsonKey].toArray();
for (int j=0; j<usbidArray.count(); j++) {
QStringList vidpid = usbidArray[j].toString().split('/');
QString vid = vidpid[0];
QString pid = vidpid[1];
bool ok;
firmwareInfo.rgVID.append(vid.right(vid.count() - 2).toInt(&ok, 16));
firmwareInfo.rgPID.append(pid.right(pid.count() - 2).toInt(&ok, 16));
}
QString brandName = firmwareJson[_manifestBrandNameKey].toString();
firmwareInfo.friendlyName = QStringLiteral("%1 - %2").arg(brandName.isEmpty() ? platform : brandName).arg(firmwareInfo.version);
}
}
if (_bootloaderFound) {
_buildAPMFirmwareNames();
}
_downloadingFirmwareList = false;
emit downloadingFirmwareListChanged(false);
}
void FirmwareUpgradeController::_ardupilotManifestDownloadError(QString errorMsg)
{
qCWarning(FirmwareUpgradeLog) << "ArduPilot Manifest download failed" << errorMsg;
}
FirmwareUpgradeController::FirmwareBuildType_t FirmwareUpgradeController::_manifestMavFirmwareVersionTypeToFirmwareBuildType(const QString& manifestMavFirmwareVersionType)
{
if (_manifestMavFirmwareVersionTypeToFirmwareBuildTypeMap.contains(manifestMavFirmwareVersionType)) {
return _manifestMavFirmwareVersionTypeToFirmwareBuildTypeMap[manifestMavFirmwareVersionType];
} else {
return CustomFirmware;
}
}
FirmwareUpgradeController::FirmwareVehicleType_t FirmwareUpgradeController::_manifestMavTypeToFirmwareVehicleType(const QString& manifestMavType)
{
if (_manifestMavTypeToFirmwareVehicleTypeMap.contains(manifestMavType)) {
return _manifestMavTypeToFirmwareVehicleTypeMap[manifestMavType];
} else {
return DefaultVehicleFirmware;
}
}
...@@ -7,16 +7,12 @@ ...@@ -7,16 +7,12 @@
* *
****************************************************************************/ ****************************************************************************/
#pragma once
/// @file
/// @author Don Gagne <don@thegagnes.com>
#ifndef FirmwareUpgradeController_H
#define FirmwareUpgradeController_H
#include "PX4FirmwareUpgradeThread.h" #include "PX4FirmwareUpgradeThread.h"
#include "LinkManager.h" #include "LinkManager.h"
#include "FirmwareImage.h" #include "FirmwareImage.h"
#include "Fact.h"
#include <QObject> #include <QObject>
#include <QUrl> #include <QUrl>
...@@ -38,7 +34,7 @@ class FirmwareUpgradeController : public QObject ...@@ -38,7 +34,7 @@ class FirmwareUpgradeController : public QObject
public: public:
typedef enum { typedef enum {
AutoPilotStackPX4, AutoPilotStackPX4 = 0,
AutoPilotStackAPM, AutoPilotStackAPM,
PX4FlowPX4, PX4FlowPX4,
PX4FlowAPM, PX4FlowAPM,
...@@ -47,35 +43,30 @@ public: ...@@ -47,35 +43,30 @@ public:
} AutoPilotStackType_t; } AutoPilotStackType_t;
typedef enum { typedef enum {
StableFirmware, StableFirmware = 0,
BetaFirmware, BetaFirmware,
DeveloperFirmware, DeveloperFirmware,
CustomFirmware CustomFirmware
} FirmwareType_t; } FirmwareBuildType_t;
typedef enum { typedef enum {
CopterFirmware, CopterFirmware = 0,
HeliFirmware, HeliFirmware,
PlaneFirmware, PlaneFirmware,
RoverFirmware, RoverFirmware,
SubFirmware, SubFirmware,
CopterChibiOSFirmware,
HeliChibiOSFirmware,
PlaneChibiOSFirmware,
RoverChibiOSFirmware,
SubChibiOSFirmware,
DefaultVehicleFirmware DefaultVehicleFirmware
} FirmwareVehicleType_t; } FirmwareVehicleType_t;
Q_ENUM(AutoPilotStackType_t) Q_ENUM(AutoPilotStackType_t)
Q_ENUM(FirmwareType_t) Q_ENUM(FirmwareBuildType_t)
Q_ENUM(FirmwareVehicleType_t) Q_ENUM(FirmwareVehicleType_t)
class FirmwareIdentifier class FirmwareIdentifier
{ {
public: public:
FirmwareIdentifier(AutoPilotStackType_t stack = AutoPilotStackPX4, FirmwareIdentifier(AutoPilotStackType_t stack = AutoPilotStackPX4,
FirmwareType_t firmware = StableFirmware, FirmwareBuildType_t firmware = StableFirmware,
FirmwareVehicleType_t vehicle = DefaultVehicleFirmware) FirmwareVehicleType_t vehicle = DefaultVehicleFirmware)
: autopilotStackType(stack), firmwareType(firmware), firmwareVehicleType(vehicle) {} : autopilotStackType(stack), firmwareType(firmware), firmwareVehicleType(vehicle) {}
...@@ -88,20 +79,22 @@ public: ...@@ -88,20 +79,22 @@ public:
// members // members
AutoPilotStackType_t autopilotStackType; AutoPilotStackType_t autopilotStackType;
FirmwareType_t firmwareType; FirmwareBuildType_t firmwareType;
FirmwareVehicleType_t firmwareVehicleType; FirmwareVehicleType_t firmwareVehicleType;
}; };
FirmwareUpgradeController(void); FirmwareUpgradeController(void);
~FirmwareUpgradeController(); ~FirmwareUpgradeController();
Q_PROPERTY(bool downloadingFirmwareList MEMBER _downloadingFirmwareList NOTIFY downloadingFirmwareListChanged)
Q_PROPERTY(QString boardPort READ boardPort NOTIFY boardFound) Q_PROPERTY(QString boardPort READ boardPort NOTIFY boardFound)
Q_PROPERTY(QString boardDescription READ boardDescription NOTIFY boardFound) Q_PROPERTY(QString boardDescription READ boardDescription NOTIFY boardFound)
Q_PROPERTY(QString boardType MEMBER _foundBoardTypeName NOTIFY boardFound) Q_PROPERTY(QString boardType MEMBER _foundBoardTypeName NOTIFY boardFound)
Q_PROPERTY(bool pixhawkBoard READ pixhawkBoard NOTIFY boardFound) Q_PROPERTY(bool pixhawkBoard READ pixhawkBoard NOTIFY boardFound)
Q_PROPERTY(bool px4FlowBoard READ px4FlowBoard NOTIFY boardFound) Q_PROPERTY(bool px4FlowBoard READ px4FlowBoard NOTIFY boardFound)
Q_PROPERTY(FirmwareType_t selectedFirmwareType READ selectedFirmwareType WRITE setSelectedFirmwareType NOTIFY selectedFirmwareTypeChanged) Q_PROPERTY(FirmwareBuildType_t selectedFirmwareBuildType READ selectedFirmwareBuildType WRITE setSelectedFirmwareBuildType NOTIFY selectedFirmwareBuildTypeChanged)
Q_PROPERTY(QStringList apmAvailableVersions READ apmAvailableVersions NOTIFY apmAvailableVersionsChanged) Q_PROPERTY(QStringList apmFirmwareNames MEMBER _apmFirmwareNames NOTIFY apmFirmwareNamesChanged)
Q_PROPERTY(QStringList apmFirmwareUrls MEMBER _apmFirmwareUrls NOTIFY apmFirmwareNamesChanged)
Q_PROPERTY(QString px4StableVersion READ px4StableVersion NOTIFY px4StableVersionChanged) Q_PROPERTY(QString px4StableVersion READ px4StableVersion NOTIFY px4StableVersionChanged)
Q_PROPERTY(QString px4BetaVersion READ px4BetaVersion NOTIFY px4BetaVersionChanged) Q_PROPERTY(QString px4BetaVersion READ px4BetaVersion NOTIFY px4BetaVersionChanged)
...@@ -119,13 +112,15 @@ public: ...@@ -119,13 +112,15 @@ public:
/// Called when the firmware type has been selected by the user to continue the flash process. /// Called when the firmware type has been selected by the user to continue the flash process.
Q_INVOKABLE void flash(AutoPilotStackType_t stackType, Q_INVOKABLE void flash(AutoPilotStackType_t stackType,
FirmwareType_t firmwareType = StableFirmware, FirmwareBuildType_t firmwareType = StableFirmware,
FirmwareVehicleType_t vehicleType = DefaultVehicleFirmware ); FirmwareVehicleType_t vehicleType = DefaultVehicleFirmware );
Q_INVOKABLE void flashFirmwareUrl(QString firmwareUrl);
/// Called to flash when upgrade is running in singleFirmwareMode /// Called to flash when upgrade is running in singleFirmwareMode
Q_INVOKABLE void flashSingleFirmwareMode(FirmwareType_t firmwareType); Q_INVOKABLE void flashSingleFirmwareMode(FirmwareBuildType_t firmwareType);
Q_INVOKABLE FirmwareVehicleType_t vehicleTypeFromVersionIndex(int index); Q_INVOKABLE FirmwareVehicleType_t vehicleTypeFromFirmwareSelectionIndex(int index);
// overload, not exposed to qml side // overload, not exposed to qml side
void flash(const FirmwareIdentifier& firmwareId); void flash(const FirmwareIdentifier& firmwareId);
...@@ -141,28 +136,28 @@ public: ...@@ -141,28 +136,28 @@ public:
QString boardPort(void) { return _foundBoardInfo.portName(); } QString boardPort(void) { return _foundBoardInfo.portName(); }
QString boardDescription(void) { return _foundBoardInfo.description(); } QString boardDescription(void) { return _foundBoardInfo.description(); }
FirmwareType_t selectedFirmwareType(void) { return _selectedFirmwareType; } FirmwareBuildType_t selectedFirmwareBuildType(void) { return _selectedFirmwareBuildType; }
void setSelectedFirmwareType(FirmwareType_t firmwareType); void setSelectedFirmwareBuildType(FirmwareBuildType_t firmwareType);
QString firmwareTypeAsString(FirmwareType_t type) const; QString firmwareTypeAsString(FirmwareBuildType_t type) const;
QStringList apmAvailableVersions(void); QString px4StableVersion (void) { return _px4StableVersion; }
QString px4StableVersion(void) { return _px4StableVersion; } QString px4BetaVersion (void) { return _px4BetaVersion; }
QString px4BetaVersion(void) { return _px4BetaVersion; }
bool pixhawkBoard(void) const { return _foundBoardType == QGCSerialPortInfo::BoardTypePixhawk; } bool pixhawkBoard(void) const { return _foundBoardType == QGCSerialPortInfo::BoardTypePixhawk; }
bool px4FlowBoard(void) const { return _foundBoardType == QGCSerialPortInfo::BoardTypePX4Flow; } bool px4FlowBoard(void) const { return _foundBoardType == QGCSerialPortInfo::BoardTypePX4Flow; }
signals: signals:
void boardFound(void); void boardFound (void);
void noBoardFound(void); void noBoardFound (void);
void boardGone(void); void boardGone (void);
void flashComplete(void); void flashComplete (void);
void flashCancelled(void); void flashCancelled (void);
void error(void); void error (void);
void selectedFirmwareTypeChanged(FirmwareType_t firmwareType); void selectedFirmwareBuildTypeChanged(FirmwareBuildType_t firmwareType);
void apmAvailableVersionsChanged(void); void apmFirmwareNamesChanged (void);
void px4StableVersionChanged(const QString& px4StableVersion); void px4StableVersionChanged (const QString& px4StableVersion);
void px4BetaVersionChanged(const QString& px4BetaVersion); void px4BetaVersionChanged (const QString& px4BetaVersion);
void downloadingFirmwareListChanged (bool downloadingFirmwareList);
private slots: private slots:
void _firmwareDownloadProgress(qint64 curr, qint64 total); void _firmwareDownloadProgress(qint64 curr, qint64 total);
...@@ -180,22 +175,25 @@ private slots: ...@@ -180,22 +175,25 @@ private slots:
void _eraseStarted(void); void _eraseStarted(void);
void _eraseComplete(void); void _eraseComplete(void);
void _eraseProgressTick(void); void _eraseProgressTick(void);
void _apmVersionDownloadFinished(QString remoteFile, QString localFile);
void _px4ReleasesGithubDownloadFinished(QString remoteFile, QString localFile); void _px4ReleasesGithubDownloadFinished(QString remoteFile, QString localFile);
void _px4ReleasesGithubDownloadError(QString errorMsg); void _px4ReleasesGithubDownloadError(QString errorMsg);
void _ardupilotManifestDownloadFinished(QString remoteFile, QString localFile);
void _ardupilotManifestDownloadError(QString errorMsg);
void _buildAPMFirmwareNames(void);
private: private:
void _getFirmwareFile(FirmwareIdentifier firmwareId);
void _initFirmwareHash();
void _downloadFirmware(void);
void _appendStatusLog(const QString& text, bool critical = false);
void _errorCancel(const QString& msg);
void _loadAPMVersions(uint32_t bootloaderBoardID);
QHash<FirmwareIdentifier, QString>* _firmwareHashForBoardId(int boardId); QHash<FirmwareIdentifier, QString>* _firmwareHashForBoardId(int boardId);
void _determinePX4StableVersion(void); void _getFirmwareFile(FirmwareIdentifier firmwareId);
void _initFirmwareHash (void);
void _downloadFirmware (void);
void _appendStatusLog (const QString& text, bool critical = false);
void _errorCancel (const QString& msg);
void _determinePX4StableVersion (void);
void _downloadArduPilotManifest (void);
QString _singleFirmwareURL; QString _singleFirmwareURL;
bool _singleFirmwareMode; bool _singleFirmwareMode;
bool _downloadingFirmwareList;
QString _portName; QString _portName;
QString _portDescription; QString _portDescription;
...@@ -220,7 +218,7 @@ private: ...@@ -220,7 +218,7 @@ private:
QHash<FirmwareIdentifier, QString> _rgAPMChibiosReplaceNamedBoardFirmware; QHash<FirmwareIdentifier, QString> _rgAPMChibiosReplaceNamedBoardFirmware;
QHash<FirmwareIdentifier, QString> _rgFirmwareDynamic; QHash<FirmwareIdentifier, QString> _rgFirmwareDynamic;
QMap<FirmwareType_t, QMap<FirmwareVehicleType_t, QString> > _apmVersionMap; QMap<FirmwareBuildType_t, QMap<FirmwareVehicleType_t, QString> > _apmVersionMap;
QList<FirmwareVehicleType_t> _apmVehicleTypeFromCurrentVersionList; QList<FirmwareVehicleType_t> _apmVehicleTypeFromCurrentVersionList;
/// Information which comes back from the bootloader /// Information which comes back from the bootloader
...@@ -259,7 +257,7 @@ private: ...@@ -259,7 +257,7 @@ private:
QGCSerialPortInfo::BoardType_t _foundBoardType; QGCSerialPortInfo::BoardType_t _foundBoardType;
QString _foundBoardTypeName; QString _foundBoardTypeName;
FirmwareType_t _selectedFirmwareType; FirmwareBuildType_t _selectedFirmwareBuildType;
FirmwareImage* _image; FirmwareImage* _image;
...@@ -267,9 +265,46 @@ private: ...@@ -267,9 +265,46 @@ private:
QString _px4BetaVersion; // Version strange for latest PX4 beta QString _px4BetaVersion; // Version strange for latest PX4 beta
const QString _apmBoardDescriptionReplaceText; const QString _apmBoardDescriptionReplaceText;
static const char* _manifestFirmwareJsonKey;
static const char* _manifestBoardIdJsonKey;
static const char* _manifestMavTypeJsonKey;
static const char* _manifestFormatJsonKey;
static const char* _manifestUrlJsonKey;
static const char* _manifestMavFirmwareVersionTypeJsonKey;
static const char* _manifestUSBIDJsonKey;
static const char* _manifestMavFirmwareVersionJsonKey;
static const char* _manifestBootloaderStrJsonKey;
static const char* _manifestLatestKey;
static const char* _manifestPlatformKey;
static const char* _manifestBrandNameKey;
typedef struct {
uint32_t boardId;
FirmwareBuildType_t firmwareBuildType;
FirmwareVehicleType_t vehicleType;
QString url;
QString version;
QStringList rgBootloaderPortString;
QList<int> rgVID;
QList<int> rgPID;
QString friendlyName;
bool chibios;
bool fmuv2;
} ManifestFirmwareInfo_t;
QList<ManifestFirmwareInfo_t> _rgManifestFirmwareInfo;
QMap<QString, FirmwareBuildType_t> _manifestMavFirmwareVersionTypeToFirmwareBuildTypeMap;
QMap<QString, FirmwareVehicleType_t> _manifestMavTypeToFirmwareVehicleTypeMap;
QStringList _apmFirmwareNames;
QStringList _apmFirmwareUrls;
Fact* _apmChibiOSSetting;
Fact* _apmVehicleTypeSetting;
FirmwareBuildType_t _manifestMavFirmwareVersionTypeToFirmwareBuildType (const QString& manifestMavFirmwareVersionType);
FirmwareVehicleType_t _manifestMavTypeToFirmwareVehicleType (const QString& manifestMavType);
}; };
// global hashing function // global hashing function
uint qHash(const FirmwareUpgradeController::FirmwareIdentifier& firmwareId); uint qHash(const FirmwareUpgradeController::FirmwareIdentifier& firmwareId);
#endif
...@@ -712,17 +712,18 @@ VideoReceiver::startRecording(const QString &videoFile) ...@@ -712,17 +712,18 @@ VideoReceiver::startRecording(const QString &videoFile)
gst_object_ref(_sink->mux); gst_object_ref(_sink->mux);
gst_object_ref(_sink->filesink); gst_object_ref(_sink->filesink);
gst_bin_add_many(GST_BIN(_pipeline), _sink->queue, _sink->parse, _sink->mux, _sink->filesink, nullptr); gst_bin_add_many(GST_BIN(_pipeline), _sink->queue, _sink->parse, _sink->mux, nullptr);
gst_element_link_many(_sink->queue, _sink->parse, _sink->mux, _sink->filesink, nullptr); gst_element_link_many(_sink->queue, _sink->parse, _sink->mux, nullptr);
gst_element_sync_state_with_parent(_sink->queue); gst_element_sync_state_with_parent(_sink->queue);
gst_element_sync_state_with_parent(_sink->parse); gst_element_sync_state_with_parent(_sink->parse);
gst_element_sync_state_with_parent(_sink->mux); gst_element_sync_state_with_parent(_sink->mux);
gst_element_sync_state_with_parent(_sink->filesink);
// Install a probe on the recording branch to drop buffers until we hit our first keyframe // Install a probe on the recording branch to drop buffers until we hit our first keyframe
// When we hit our first keyframe, we can offset the timestamps appropriately according to the first keyframe time // When we hit our first keyframe, we can offset the timestamps appropriately according to the first keyframe time
// This will ensure the first frame is a keyframe at t=0, and decoding can begin immediately on playback // This will ensure the first frame is a keyframe at t=0, and decoding can begin immediately on playback
// Once we have this valid frame, we attach the filesink.
// Attaching it here would cause the filesink to fail to preroll and to stall the pipeline for a few seconds.
GstPad* probepad = gst_element_get_static_pad(_sink->queue, "src"); GstPad* probepad = gst_element_get_static_pad(_sink->queue, "src");
gst_pad_add_probe(probepad, (GstPadProbeType)(GST_PAD_PROBE_TYPE_BUFFER /* | GST_PAD_PROBE_TYPE_BLOCK */), _keyframeWatch, this, nullptr); // to drop the buffer or to block the buffer? gst_pad_add_probe(probepad, (GstPadProbeType)(GST_PAD_PROBE_TYPE_BUFFER /* | GST_PAD_PROBE_TYPE_BLOCK */), _keyframeWatch, this, nullptr); // to drop the buffer or to block the buffer?
gst_object_unref(probepad); gst_object_unref(probepad);
...@@ -875,6 +876,12 @@ VideoReceiver::_keyframeWatch(GstPad* pad, GstPadProbeInfo* info, gpointer user_ ...@@ -875,6 +876,12 @@ VideoReceiver::_keyframeWatch(GstPad* pad, GstPadProbeInfo* info, gpointer user_
gst_element_set_base_time(pThis->_pipeline, time); // offset pipeline timestamps to start at zero again gst_element_set_base_time(pThis->_pipeline, time); // offset pipeline timestamps to start at zero again
buf->dts = 0; // The offset will not apply to this current buffer, our first frame, timestamp is zero buf->dts = 0; // The offset will not apply to this current buffer, our first frame, timestamp is zero
buf->pts = 0; buf->pts = 0;
// Add the filesink once we have a valid I-frame
gst_bin_add_many(GST_BIN(pThis->_pipeline), pThis->_sink->filesink, nullptr);
gst_element_link_many(pThis->_sink->mux, pThis->_sink->filesink, nullptr);
gst_element_sync_state_with_parent(pThis->_sink->filesink);
qCDebug(VideoReceiverLog) << "Got keyframe, stop dropping buffers"; qCDebug(VideoReceiverLog) << "Got keyframe, stop dropping buffers";
} }
} }
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment