Line data Source code
1 : /* 2 : This program is free software: you can redistribute it and/or modify 3 : it under the terms of the GNU General Public License as published by 4 : the Free Software Foundation, either version 3 of the License, or 5 : (at your option) any later version. 6 : 7 : This program is distributed in the hope that it will be useful, 8 : but WITHOUT ANY WARRANTY; without even the implied warranty of 9 : MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 10 : GNU General Public License for more details. 11 : 12 : You should have received a copy of the GNU General Public License 13 : along with this program. If not, see <http://www.gnu.org/licenses/>. 14 : */ 15 : /* 16 : Simulator for the TeraRangerTower proximity sensor 17 : */ 18 : 19 : #include "SIM_config.h" 20 : 21 : #if AP_SIM_PS_TERARANGERTOWER_ENABLED 22 : 23 : #include "SIM_PS_TeraRangerTower.h" 24 : 25 : #include <GCS_MAVLink/GCS.h> 26 : #include <AP_HAL/utility/sparse-endian.h> 27 : #include <stdio.h> 28 : #include <errno.h> 29 : 30 : using namespace SITL; 31 : 32 0 : uint32_t PS_TeraRangerTower::packet_for_location(const Location &location, 33 : uint8_t *data, 34 : uint8_t buflen) 35 : { 36 0 : return 0; 37 : } 38 : 39 54064 : void PS_TeraRangerTower::update_output(const Location &location) 40 : { 41 54064 : const uint32_t now = AP_HAL::millis(); 42 54064 : if (last_output_time_ms == 0) { 43 3 : last_output_time_ms = now; 44 53839 : return; 45 : } 46 54061 : const uint32_t time_delta = now - last_output_time_ms; 47 54061 : if (time_delta < 200) { // 5Hz update 48 53836 : return; 49 : } 50 225 : last_output_time_ms = now; 51 : 52 : struct PACKED { 53 : uint8_t HEADER1{'T'}; 54 : uint8_t HEADER2{'H'}; 55 : uint16_t measurements[8]; 56 : uint8_t checksum; 57 225 : } send_buffer; 58 : 59 2025 : for (uint8_t i=0; i<8; i++) { 60 1800 : const uint16_t bf_angle = (360 - (i * 45)) % 360; 61 1800 : float distance = measure_distance_at_angle_bf(location, bf_angle); 62 : // ::fprintf(stderr, "SIM: %f=%fm\n", current_degrees_bf, distance); 63 1800 : if (distance > MAX_RANGE) { 64 875 : send_buffer.measurements[i] = 0xffff; 65 : } else { 66 925 : send_buffer.measurements[i] = htobe16(distance * 1000); 67 : } 68 : } 69 : 70 225 : send_buffer.checksum = crc_crc8((uint8_t*)&send_buffer, 18); 71 : 72 225 : const ssize_t ret = write_to_autopilot((const char*)&send_buffer, sizeof(send_buffer)); 73 225 : if (ret != sizeof(send_buffer)) { 74 0 : abort(); 75 : } 76 : } 77 : 78 54064 : void PS_TeraRangerTower::update(const Location &location) 79 : { 80 54064 : update_output(location); 81 54064 : } 82 : 83 : #endif // AP_SIM_PS_TERARANGERTOWER_ENABLED