-
Notifications
You must be signed in to change notification settings - Fork 13.6k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
ekf2: Allow use of RTK GPS heading #10355
Conversation
src/modules/ekf2/ekf2_main.cpp
Outdated
@@ -691,6 +691,14 @@ void Ekf2::run() | |||
vehicle_status_s vehicle_status = {}; | |||
sensor_selection_s sensor_selection = {}; | |||
|
|||
// get heading offset required for use of GPS yaw | |||
param_t handle = param_find("GPS_YAW_OFFSET"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Add this to vehicle_gps_position instead of accessing the parameter directly?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We could do, but that will increase log size unnecessarily
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If that's enough to push it over the edge we could consider a low rate (nearly static) metadata message as well. That could also contain the position.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Are you able to explain the reasons for not wanting to adopt the approach used here of checking the parameter value on startup? It seems like the simplest way to achieve the required result.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Generally it ends up being a bad idea to cross module boundaries. These parameters are internal data of that driver or module, not a system wide setting.
In the simple intended use case I'm sure this is fine, but how does it scale when there are multiple GPS receivers, or GPS from UAVCAN, Mavlink, or some mix of all of the above. What about the GPS being connected to one system, but running the estimator on another with messages passed via FastRTPS?
Yes I'm jumping ahead, but these are the reasons to try and keep things as modular as possible as we go along .
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@dagar Can you show me an example of a 'low rate (nearly static) metadata message'
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't think we have a good example at the moment, but it's an idea I want to pursue for the high rate messages like IMU. This isn't quite the same, but think of sensor_combined. The IMU is published (and logged) at high rate, but we publish the corresponding device ids separately in sensor_selection only when changed.
Is this GPS message with yaw still fairly low rate? If so I wouldn't worry about it for now.
Idea
sensor_gyro (0, 1, 2)
- contains x, y, z values at 250 Hz - 2kHz
sensor_gyro_info (0, 1, 2)
- contains metadata for the corresponding instance (device id, health, clipping, etc)
@@ -980,6 +990,8 @@ void Ekf2::run() | |||
_gps_state[1].lat = gps.lat; | |||
_gps_state[1].lon = gps.lon; | |||
_gps_state[1].alt = gps.alt; | |||
_gps_state[1].yaw_offset = gps_yaw_offset; | |||
_gps_state[1].fix_type = gps.fix_type; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
fix_type line repeated
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
will fix
src/modules/ekf2/ekf2_main.cpp
Outdated
@@ -980,6 +990,8 @@ void Ekf2::run() | |||
_gps_state[1].lat = gps.lat; | |||
_gps_state[1].lon = gps.lon; | |||
_gps_state[1].alt = gps.alt; | |||
_gps_state[1].yaw_offset = gps_yaw_offset; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
yaw (gps.heading) missing?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Will fix. Yaw not supported by GPS blending at the moment but will be adding support in a subsequent PR that enables a yaw output and non yaw output receiver to be used together.
Results from replay of log file Note: The jump in heading innovations when turning are the result of the bug in PX4/Firmware that was present when the original log data was generated. This was been subsequently fixed upstream by Replay log here: https://logs.px4.io/plot_app?log=67bf7874-8a52-4c56-9baf-eb9d46985dc1 |
@bkueng Are you able to repeat the test you did here: https://logs.px4.io/plot_app?log=25380997-1d97-4e3c-8006-58fd4d4e52c5 and supply the data log? |
Here are 2 logs on this branch with enabled GPS yaw fusion (logging from boot until shutdown):
The second one contains the rolling/pitching towards the end of the log. |
Inspection of the heading and GPS position and velocity innovations show that data is being fused correctly and the vehicle has a valid heading. Heading fusion stops as designed when the GPS antennas go through a bad orientation. 51d7e1e3-8562-46d3-8b3c-960e008516b5.ulg innovations 1005486e-e7f4-4088-9b20-22c48036d22a.ulg innovations - these are larger than for the previous log One of the limitations with the interface used by this type of GPS is that there is no data to populate the s_variance_m_s field so the default observation noise of 0.5 m/s as set by the EF2_GPS_V_NOISE parameter is used at all time regardless of receiver signal quality. Something to look at for later improvement is scaling the noise using eph if the s_variance_m_s data is not populated. |
Once we get an agreed method for messaging the heading offset, then this can be merged. |
cb24f39
to
71a1edc
Compare
@dagar I've added the heading offset to the GPS message along with protection in the ecl library if the heading_offset is undefined. The logs don't contain the additional heading_offset message, so the previous logs can't be used to test the change. Once you are happy with the changes, I will ask @bkueng to generate a new log when he has time. |
@priseborough Please stop using |
src/modules/ekf2/ekf2_main.cpp
Outdated
@@ -2223,6 +2227,10 @@ void Ekf2::calc_gps_blend_output() | |||
_gps_output[GPS_BLENDED_INSTANCE].nsats = _gps_blended_state.nsats; | |||
_gps_output[GPS_BLENDED_INSTANCE].vel_ned_valid = _gps_blended_state.vel_ned_valid; | |||
|
|||
// No suppoort for blending of yaw data at the moment |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
typo - suppoort
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
will fix
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do I see it correctly that we don't have heading fusion if we use dual gps?
src/drivers/gps/gps.cpp
Outdated
@@ -885,6 +888,7 @@ GPS::publish() | |||
// Heading/yaw data can be updated at a lower rate than the other navigation data. | |||
// The uORB message definition requires this data to be set to a NAN if no new valid data is available. | |||
_report_gps_pos.heading = NAN; | |||
_report_gps_pos.heading_offset = NAN; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This needs to be removed.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
will fix
src/drivers/gps/gps.cpp
Outdated
@@ -688,6 +690,7 @@ GPS::run() | |||
|
|||
case GPS_DRIVER_MODE_ASHTECH: | |||
_helper = new GPSDriverAshtech(&GPS::callback, this, &_report_gps_pos, _p_report_sat_info, heading_offset); | |||
_report_gps_pos.heading_offset = heading_offset; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you set this unconditionally for all drivers, so that it automatically works when we add heading support to another driver?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Will do.
@bkueng That is correct. I am still working out the best way to achieve that. The easiest is to always pass through the heading from the receiver that has it. If both do, then blend it using the position accuracy ratio, given we do not have a heading accuracy value from the receiver. |
I think passing it through is good enough for now. |
c6bc114
to
2079a2a
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@priseborough I was able to test it again, here's the log: https://logs.px4.io/plot_app?log=9bdbab10-cb54-4f9d-85e6-0b53f338235a
src/modules/ekf2/ekf2_main.cpp
Outdated
@@ -2070,9 +2070,11 @@ void Ekf2::update_gps_blend_states() | |||
|
|||
// Take GPS heading from the highest weighted receiver that is publishing a valid .heading value | |||
uint8_t gps_best_yaw_index = 0; | |||
best_weight = 0.0f |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There's a semicolon missing.
f243d20
to
f1d08d9
Compare
The heading_offset is 0 and the heading is NAN in that log. Did you upload the right file? |
The heading is there: |
386cebb
to
c4ca4b7
Compare
@priseborough I don't think we're there yet, but a rebase couldn't hurt to see how close we're getting. |
c4ca4b7
to
9e402c5
Compare
@bkueng drop VTOL and FW from omnibus? We can fix any parameter interdependencies that have crept in. Update: If we can drop VTOL/FW from Omnibus and merge #10530 we should have enough to unblock Paul. |
9e402c5
to
71a1045
Compare
71a1045
to
5e71d58
Compare
I've rebased. We are still 1345 bytes short on the px4fmu-v2 target. |
@bkueng Could you have a look? |
@priseborough you can disable any of the distance sensors: https://github.com/PX4/Firmware/blob/master/cmake/configs/nuttx_px4fmu-v2_default.cmake#L35 |
@bkueng Thanks! Do we have a more structured approach at fixing it? |
One thing that concerns me about the module disabling: for fmu-v2, we are disabling several modules, but we are going to get to a stage where I do want to use one module in specific on the fmu-v2, I won't be able to do it because of flash overflow. Though I do see that the ekf2 and ecl modules keeping growing in size, but I don't see where one would exactly be able to, for example, ignore the build of some of each features. For example, this one in particular: not everyone would actually want to use the RTK heading, and eventhough the parameter is there, the code for this feature is going to be built. If this was a critical feature, I would say ok, this needs to go in. But I don't really see the scalability of this, while we keep adding new features to the estimator and ECL and don't have a way of filtering which features we want to build, keeping accumulating flash space without even wanting to use those same features. |
5e71d58
to
9181bf1
Compare
@priseborough would you mind giving some feedback on my comment? Thanks |
@TSC21 it's a more general problem and ecl/EKF just happens to be the most recent victim. There's quite a lot of flash that could be regained from the drivers themselves with no loss of functionality. Ping me if you're interested. |
Adds feature requested by #10284
Requires PX4/PX4-ECL#497
Is inactive with default parameters.
Testing
See PX4/PX4-ECL#497 for details of previous testing using replay.
Testing this branch requires setting EKF2_AID_MASK = 129 and EKF2_MAG_TYPE = 5. That will force the EKF to wait until GPS yaw is available before performing the yaw alignment. If EKF2_MAG_TYPE = 0, then the yaw will be set using the magnetomer intially and then reset to the GPS yaw when it becomes available.
Testing using replay was repeated and documented in the comments below.