LCOV - code coverage report
Current view: top level - AP_DAL - AP_DAL_RangeFinder.cpp (source / functions) Hit Total Coverage
Test: lcov.info Lines: 46 75 61.3 %
Date: 2026-09-09 11:02:08 Functions: 7 10 70.0 %

          Line data    Source code
       1             : #include "AP_DAL_RangeFinder.h"
       2             : 
       3             : #include <AP_Logger/AP_Logger.h>
       4             : 
       5             : #include <AP_RangeFinder/AP_RangeFinder_Backend.h>
       6             : 
       7             : #if AP_RANGEFINDER_ENABLED
       8             : 
       9             : #include "AP_DAL.h"
      10             : #include <AP_BoardConfig/AP_BoardConfig.h>
      11             : #include <AP_Vehicle/AP_Vehicle_Type.h>
      12             : #include <AP_InternalError/AP_InternalError.h>
      13             : 
      14         172 : AP_DAL_RangeFinder::AP_DAL_RangeFinder()
      15             : {
      16             : #if !APM_BUILD_TYPE(APM_BUILD_AP_DAL_Standalone) && !APM_BUILD_TYPE(APM_BUILD_Replay)
      17         172 :     _RRNH.num_sensors = AP::rangefinder()->num_sensors();
      18         370 :     _RRNI = NEW_NOTHROW log_RRNI[_RRNH.num_sensors];
      19         172 :     _backend = NEW_NOTHROW AP_DAL_RangeFinder_Backend *[_RRNH.num_sensors];
      20         172 :     if (!_RRNI || !_backend) {
      21           0 :         goto failed;
      22             :     }
      23         370 :     for (uint8_t i=0; i<_RRNH.num_sensors; i++) {
      24         198 :         _RRNI[i].instance = i;
      25             :     }
      26         370 :     for (uint8_t i=0; i<_RRNH.num_sensors; i++) {
      27             :         // this avoids having to discard a const....
      28         198 :         _backend[i] = NEW_NOTHROW AP_DAL_RangeFinder_Backend(_RRNI[i]);
      29         198 :         if (!_backend[i]) {
      30           0 :             goto failed;
      31             :         }
      32             :     }
      33         172 :     return;
      34           0 : failed:
      35           0 :     AP_BoardConfig::allocation_error("DAL backends");
      36             : #endif
      37             : }
      38             : 
      39     1857646 : float AP_DAL_RangeFinder::ground_clearance_orient(enum Rotation orientation) const
      40             : {
      41             : #if !APM_BUILD_TYPE(APM_BUILD_AP_DAL_Standalone)
      42     1857646 :     const auto *rangefinder = AP::rangefinder();
      43             : 
      44     1857646 :     if (orientation != ROTATION_PITCH_270) {
      45             :         // the EKF only asks for this from a specific orientation.  Thankfully.
      46           0 :         INTERNAL_ERROR(AP_InternalError::error_t::flow_of_control);
      47           0 :         return rangefinder->ground_clearance_orient(orientation);
      48             :     }
      49             : #endif
      50             : 
      51     1857646 :     return _RRNH.ground_clearance;
      52             : }
      53             : 
      54      154191 : float AP_DAL_RangeFinder::max_distance_orient(enum Rotation orientation) const
      55             : {
      56             : #if !APM_BUILD_TYPE(APM_BUILD_AP_DAL_Standalone)
      57      154191 :     if (orientation != ROTATION_PITCH_270) {
      58           0 :         const auto *rangefinder = AP::rangefinder();
      59             :         // the EKF only asks for this from a specific orientation.  Thankfully.
      60           0 :         INTERNAL_ERROR(AP_InternalError::error_t::flow_of_control);
      61           0 :         return rangefinder->max_distance_orient(orientation);
      62             :     }
      63             : #endif
      64             : 
      65      154191 :     return _RRNH.max_distance;
      66             : }
      67             : 
      68     4663689 : void AP_DAL_RangeFinder::start_frame()
      69             : {
      70     4663689 :     const auto *rangefinder = AP::rangefinder();
      71     4663689 :     if (rangefinder == nullptr) {
      72           0 :         return;
      73             :     }
      74             : 
      75     4663689 :     const log_RRNH old = _RRNH;
      76             : 
      77             :     // EKF only asks for this *down*.
      78     4663689 :     _RRNH.ground_clearance = rangefinder->ground_clearance_orient(ROTATION_PITCH_270);
      79     4663689 :     _RRNH.max_distance = rangefinder->max_distance_orient(ROTATION_PITCH_270);
      80             : 
      81     4663689 :     WRITE_REPLAY_BLOCK_IFCHANGED(RRNH, _RRNH, old);
      82             : 
      83     9891562 :     for (uint8_t i=0; i<_RRNH.num_sensors; i++) {
      84     5227873 :         auto *backend = rangefinder->get_backend(i);
      85     5227873 :         if (backend == nullptr) {
      86       52406 :             continue;
      87             :         }
      88     5175467 :         _backend[i]->start_frame(backend);
      89             :     }
      90             : }
      91             : 
      92             : 
      93             : 
      94             : 
      95         198 : AP_DAL_RangeFinder_Backend::AP_DAL_RangeFinder_Backend(struct log_RRNI &RRNI) :
      96         198 :     _RRNI(RRNI)
      97             : {
      98         198 : }
      99             : 
     100     5175467 : void AP_DAL_RangeFinder_Backend::start_frame(AP_RangeFinder_Backend *backend) {
     101     5175467 :     const log_RRNI old = _RRNI;
     102     5175467 :     _RRNI.orientation = backend->orientation();
     103     5175467 :     _RRNI.status = (uint8_t)backend->status();
     104     5175467 :     _RRNI.pos_offset = backend->get_pos_offset();
     105     5175467 :     _RRNI.distance = backend->distance();
     106     5175467 :     WRITE_REPLAY_BLOCK_IFCHANGED(RRNI, _RRNI, old);
     107     5175467 : }
     108             : 
     109             : // return true if we have a range finder with the specified orientation
     110           0 : bool AP_DAL_RangeFinder::has_orientation(enum Rotation orientation) const
     111             : {
     112           0 :     for (uint8_t i=0; i<_RRNH.num_sensors; i++) {
     113           0 :         if (_RRNI[i].orientation == orientation) {
     114           0 :             return true;
     115             :         }
     116             :     }
     117           0 :     return false;
     118             : }
     119             : 
     120             : 
     121      974403 : AP_DAL_RangeFinder_Backend *AP_DAL_RangeFinder::get_backend(uint8_t id) const
     122             : {
     123      974403 :    if (id >= RANGEFINDER_MAX_INSTANCES) {
     124           0 :        INTERNAL_ERROR(AP_InternalError::error_t::flow_of_control);
     125           0 :        return nullptr;
     126             :    }
     127      974403 :    if (id >= _RRNH.num_sensors) {
     128      375353 :         return nullptr;
     129             :     }
     130             : 
     131      599050 :    return _backend[id];
     132             : }
     133             : 
     134           0 : void AP_DAL_RangeFinder::handle_message(const log_RRNH &msg)
     135             : {
     136           0 :     _RRNH = msg;
     137           0 :     if (_RRNH.num_sensors > 0 && _RRNI == nullptr) {
     138           0 :         _RRNI = NEW_NOTHROW log_RRNI[_RRNH.num_sensors];
     139           0 :         _backend = NEW_NOTHROW AP_DAL_RangeFinder_Backend *[_RRNH.num_sensors];
     140             :     }
     141           0 : }
     142             : 
     143           0 : void AP_DAL_RangeFinder::handle_message(const log_RRNI &msg)
     144             : {
     145           0 :     if (_RRNI != nullptr && msg.instance < _RRNH.num_sensors) {
     146           0 :         _RRNI[msg.instance] = msg;
     147           0 :         if (_backend != nullptr && _backend[msg.instance] == nullptr) {
     148           0 :             _backend[msg.instance] = NEW_NOTHROW AP_DAL_RangeFinder_Backend(_RRNI[msg.instance]);
     149             :         }
     150             :     }
     151           0 : }
     152             : 
     153             : #endif  // AP_RANGEFINDER_ENABLED

Generated by: LCOV version 1.14