APM:Libraries
ToneAlarm_PX4.cpp
Go to the documentation of this file.
1 /*
2  ToneAlarm PX4 driver
3 */
4 /*
5  This program is free software: you can redistribute it and/or modify
6  it under the terms of the GNU General Public License as published by
7  the Free Software Foundation, either version 3 of the License, or
8  (at your option) any later version.
9 
10  This program is distributed in the hope that it will be useful,
11  but WITHOUT ANY WARRANTY; without even the implied warranty of
12  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13  GNU General Public License for more details.
14 
15  You should have received a copy of the GNU General Public License
16  along with this program. If not, see <http://www.gnu.org/licenses/>.
17  */
18 
19 #include <AP_HAL/AP_HAL.h>
20 
21 #if CONFIG_HAL_BOARD == HAL_BOARD_PX4 || CONFIG_HAL_BOARD == HAL_BOARD_VRBRAIN
22 #include "ToneAlarm_PX4.h"
23 #include "AP_Notify.h"
24 
25 #include <sys/types.h>
26 #include <sys/stat.h>
27 #include <fcntl.h>
28 #include <unistd.h>
29 #include <string.h>
30 
31 #include <drivers/drv_tone_alarm.h>
32 #include <stdio.h>
33 #include <errno.h>
34 
35 extern const AP_HAL::HAL& hal;
36 
38  #define AP_NOTIFY_PX4_TONE_QUIET_NEG_FEEDBACK 0
39  { "MFT200L4<<<B#A#2", false },
40  #define AP_NOTIFY_PX4_TONE_LOUD_NEG_FEEDBACK 1
41  { "MFT100L4>B#A#2P8B#A#2", false },
42  #define AP_NOTIFY_PX4_TONE_QUIET_NEU_FEEDBACK 2
43  { "MFT200L4<B#", false },
44  #define AP_NOTIFY_PX4_TONE_LOUD_NEU_FEEDBACK 3
45  { "MFT100L4>B#", false },
46  #define AP_NOTIFY_PX4_TONE_QUIET_POS_FEEDBACK 4
47  { "MFT200L4<A#B#", false },
48  #define AP_NOTIFY_PX4_TONE_LOUD_POS_FEEDBACK 5
49  { "MFT100L4>A#B#", false },
50  #define AP_NOTIFY_PX4_TONE_LOUD_READY_OR_FINISHED 6
51  { "MFT100L4>G#6A#6B#4", false },
52  #define AP_NOTIFY_PX4_TONE_QUIET_READY_OR_FINISHED 7
53  { "MFT200L4<G#6A#6B#4", false },
54  #define AP_NOTIFY_PX4_TONE_LOUD_ATTENTION_NEEDED 8
55  { "MFT100L4>A#A#A#A#", false },
56  #define AP_NOTIFY_PX4_TONE_QUIET_ARMING_WARNING 9
57  { "MNT75L1O2G", false },
58  #define AP_NOTIFY_PX4_TONE_LOUD_WP_COMPLETE 10
59  { "MFT200L8G>C3", false },
60  #define AP_NOTIFY_PX4_TONE_LOUD_LAND_WARNING_CTS 11
61  { "MBT200L2A-G-A-G-A-G-", true },
62  #define AP_NOTIFY_PX4_TONE_LOUD_VEHICLE_LOST_CTS 12
63  { "MBT200>A#1", true },
64  #define AP_NOTIFY_PX4_TONE_LOUD_BATTERY_ALERT_CTS 13
65  { "MBNT255>A#8A#8A#8A#8A#8A#8A#8A#8A#8A#8A#8A#8A#8A#8A#8A#8", true },
66  #define AP_NOTIFY_PX4_TONE_QUIET_COMPASS_CALIBRATING_CTS 14
67  { "MBNT255<C16P2", true },
68  #define AP_NOTIFY_PX4_TONE_WAITING_FOR_THROW 15
69  { "MBNT90L4O2A#O3DFN0N0N0", true},
70  #define AP_NOTIFY_PX4_TONE_LOUD_1 16
71  { "MFT100L8>B", false},
72  #define AP_NOTIFY_PX4_TONE_LOUD_2 17
73  { "MFT100L8>BB", false},
74  #define AP_NOTIFY_PX4_TONE_LOUD_3 18
75  { "MFT100L8>BBB", false},
76  #define AP_NOTIFY_PX4_TONE_LOUD_4 19
77  { "MFT100L8>BBBB", false},
78  #define AP_NOTIFY_PX4_TONE_LOUD_5 20
79  { "MFT100L8>BBBBB", false},
80  #define AP_NOTIFY_PX4_TONE_LOUD_6 21
81  { "MFT100L8>BBBBBB", false},
82  #define AP_NOTIFY_PX4_TONE_LOUD_7 22
83  { "MFT100L8>BBBBBBB", false},
84  #define AP_NOTIFY_PX4_TONE_TUNING_START 23
85  { "MFT100L20>C#D#", false},
86  #define AP_NOTIFY_PX4_TONE_TUNING_SAVE 24
87  { "MFT100L10DBDB>", false},
88  #define AP_NOTIFY_PX4_TONE_TUNING_ERROR 25
89  { "MFT100L10>BBBBBBBB", false},
90  #define AP_NOTIFY_PX4_TONE_LEAK_DETECTED 26
91  { "MBT255L8>A+AA-", true},
92  #define AP_NOTIFY_PX4_TONE_QUIET_SHUTDOWN 27
93  { "MFMST200L32O3ceP32cdP32ceP32c<c>c<cccP8L32>c>c<P32<c<c", false },
94  #define AP_NOTIFY_PX4_TONE_QUIET_NOT_READY_OR_NOT_FINISHED 28
95  { "MFT200L4<B#4A#6G#6", false },
96 };
97 
99 {
100  // open the tone alarm device
101  _tonealarm_fd = open(TONEALARM0_DEVICE_PATH, O_WRONLY);
102  if (_tonealarm_fd == -1) {
103  hal.console->printf("ToneAlarm_PX4: Unable to open " TONEALARM0_DEVICE_PATH);
104  return false;
105  }
106 
107  // set initial boot states. This prevents us issuing a arming
108  // warning in plane and rover on every boot
111  flags.pre_arm_check = 1;
112  _cont_tone_playing = -1;
113  return true;
114 }
115 
116 // play_tune - play one of the pre-defined tunes
117 void ToneAlarm_PX4::play_tone(const uint8_t tone_index)
118 {
119  uint32_t tnow_ms = AP_HAL::millis();
120  const Tone &tone_requested = _tones[tone_index];
121 
122  if(tone_requested.continuous) {
123  _cont_tone_playing = tone_index;
124  }
125 
126  _tone_playing = tone_index;
127  _tone_beginning_ms = tnow_ms;
128 
129  play_string(tone_requested.str);
130 }
131 
132 void ToneAlarm_PX4::play_string(const char *str) {
133  write(_tonealarm_fd, str, strlen(str) + 1);
134 }
135 
138  play_string("");
139  _tone_playing = -1;
140  }
141  _cont_tone_playing = -1;
142 }
143 
145  uint32_t tnow_ms = AP_HAL::millis();
146  // if we are supposed to be playing a continuous tone,
147  // and it was interrupted, and the interrupting tone has timed out,
148  // resume the continuous tone
149 
152  }
153 }
154 
155 // update - updates led according to timed_updated. Should be called at 50Hz
157 {
158  // exit immediately if we haven't initialised successfully
159  if (_tonealarm_fd == -1) {
160  return;
161  }
162 
163  // exit if buzzer is not enabled
164  if (pNotify->buzzer_enabled() == false) {
165  return;
166  }
167 
168  check_cont_tone();
169 
170  if (AP_Notify::flags.powering_off) {
171  if (!flags.powering_off) {
173  }
175  return;
176  }
177 
178  if (AP_Notify::flags.compass_cal_running != flags.compass_cal_running) {
179  if(AP_Notify::flags.compass_cal_running) {
182  } else {
184  stop_cont_tone();
185  }
186  }
187  }
189 
190  if (AP_Notify::events.compass_cal_canceled) {
192  return;
193  }
194 
195  if (AP_Notify::events.initiated_compass_cal) {
197  return;
198  }
199 
200  if (AP_Notify::events.compass_cal_saved) {
202  return;
203  }
204 
205  if (AP_Notify::events.compass_cal_failed) {
207  return;
208  }
209 
210  // don't play other tones if compass cal is running
211  if (AP_Notify::flags.compass_cal_running) {
212  return;
213  }
214 
215  // notify the user when autotune or mission completes
216  if (AP_Notify::flags.armed && (AP_Notify::events.autotune_complete || AP_Notify::events.mission_complete)) {
218  }
219 
220  //notify the user when autotune fails
221  if (AP_Notify::flags.armed && (AP_Notify::events.autotune_failed)) {
223  }
224 
225  // notify the user when a waypoint completes
226  if (AP_Notify::events.waypoint_complete) {
228  }
229 
230  // notify the user when their mode change was successful
231  if (AP_Notify::events.user_mode_change) {
232  if (AP_Notify::flags.armed) {
234  } else {
236  }
237  }
238 
239  // notify the user when their mode change failed
240  if (AP_Notify::events.user_mode_change_failed) {
241  if (AP_Notify::flags.armed) {
243  } else {
245  }
246  }
247 
248  // failsafe initiated mode change
249  if(AP_Notify::events.failsafe_mode_change) {
251  }
252 
253  // notify the user when arming fails
254  if (AP_Notify::events.arming_failed) {
256  }
257 
258  // notify the user when RC contact is lost
261  if (flags.failsafe_radio) {
262  // armed case handled by events.failsafe_mode_change
263  if (!AP_Notify::flags.armed) {
265  }
266  } else {
267  if (AP_Notify::flags.armed) {
269  } else {
271  }
272  }
273  }
274 
275  // notify the user when pre_arm checks are passing
278  if (flags.pre_arm_check) {
281  } else {
282  // only play sad tone if we've ever played happy tone:
285  }
286  }
287  }
288 
289  // check if arming status has changed
292  if (flags.armed) {
293  // arming tune
295  }else{
296  // disarming tune
298  if (!flags.leak_detected) {
299  stop_cont_tone();
300  }
301  }
302  }
303 
304  // check if battery status has changed
307  if (flags.failsafe_battery) {
308  // battery warning tune
310  }
311  }
312 
313  // check parachute release
316  if (flags.parachute_release) {
317  // parachute release warning tune
319  }
320  }
321 
322  // lost vehicle tone
325  if (flags.vehicle_lost) {
327  } else {
328  stop_cont_tone();
329  }
330  }
331 
332  // waiting to be thrown vehicle tone
335  if (flags.waiting_for_throw) {
337  } else {
338  stop_cont_tone();
339  }
340  }
341 
344  if (flags.leak_detected) {
346  } else {
347  stop_cont_tone();
348  }
349  }
350 
351  if (AP_Notify::events.tune_started) {
354  }
355  if (AP_Notify::events.tune_next) {
356  // signify which parameter in the set is starting
359  }
360  if (AP_Notify::events.tune_save) {
363  }
364  if (AP_Notify::events.tune_error) {
367  }
368 }
369 
370 
371 /*
372  handle a PLAY_TUNE message
373 */
374 void ToneAlarm_PX4::handle_play_tune(mavlink_message_t *msg)
375 {
376  // decode mavlink message
377  mavlink_play_tune_t packet;
378 
379  mavlink_msg_play_tune_decode(msg, &packet);
380 
381  play_string(packet.tune);
382 }
383 
384 
385 #endif // CONFIG_HAL_BOARD == HAL_BOARD_PX4
#define AP_NOTIFY_PX4_TONE_QUIET_POS_FEEDBACK
#define AP_NOTIFY_PX4_TONE_LOUD_NEG_FEEDBACK
#define AP_NOTIFY_PX4_TONE_QUIET_COMPASS_CALIBRATING_CTS
int open(const char *pathname, int flags)
POSIX Open a file with integer mode flags.
Definition: posix.c:885
void update()
update - updates led according to timed_updated. Should be called at 50Hz
#define AP_NOTIFY_PX4_TONE_TUNING_ERROR
AP_HAL::UARTDriver * console
Definition: HAL.h:110
void play_string(const char *str)
ssize_t write(int fd, const void *buf, size_t count)
POSIX Write count bytes from *buf to fileno fd.
Definition: posix.c:1169
const uint8_t continuous
Definition: ToneAlarm_PX4.h:73
#define AP_NOTIFY_PX4_TONE_TUNING_START
#define AP_NOTIFY_PX4_TONE_QUIET_NEU_FEEDBACK
#define AP_NOTIFY_PX4_TONE_LOUD_VEHICLE_LOST_CTS
bool _have_played_ready_tone
Definition: ToneAlarm_PX4.h:65
#define AP_NOTIFY_PX4_TONE_WAITING_FOR_THROW
void play_tone(const uint8_t tone_index)
play_tune - play one of the pre-defined tunes
#define AP_NOTIFY_PX4_TONE_LOUD_NEU_FEEDBACK
#define AP_NOTIFY_PX4_TONE_LEAK_DETECTED
#define AP_NOTIFY_PX4_MAX_TONE_LENGTH_MS
Definition: ToneAlarm_PX4.h:23
#define AP_NOTIFY_PX4_TONE_QUIET_NOT_READY_OR_NOT_FINISHED
virtual void printf(const char *,...) FMT_PRINTF(2
Definition: BetterStream.cpp:5
#define AP_NOTIFY_PX4_TONE_LOUD_ATTENTION_NEEDED
const AP_HAL::HAL & hal
-*- tab-width: 4; Mode: C++; c-basic-offset: 4; indent-tabs-mode: nil -*-
Definition: AC_PID_test.cpp:14
bool buzzer_enabled() const
Definition: AP_Notify.h:135
int8_t _cont_tone_playing
Definition: ToneAlarm_PX4.h:67
uint32_t millis()
Definition: system.cpp:157
#define AP_NOTIFY_PX4_TONE_LOUD_BATTERY_ALERT_CTS
#define AP_NOTIFY_PX4_TONE_LOUD_POS_FEEDBACK
#define AP_NOTIFY_PX4_TONE_QUIET_NEG_FEEDBACK
#define AP_NOTIFY_PX4_TONE_LOUD_READY_OR_FINISHED
bool init(void)
init - initialised the tone alarm
#define AP_NOTIFY_PX4_TONE_LOUD_WP_COMPLETE
const AP_Notify * pNotify
Definition: NotifyDevice.h:24
#define AP_NOTIFY_PX4_TONE_QUIET_SHUTDOWN
void check_cont_tone()
#define AP_NOTIFY_PX4_TONE_QUIET_READY_OR_FINISHED
static struct notify_flags_and_values_type flags
Definition: AP_Notify.h:117
int8_t _tone_playing
Definition: ToneAlarm_PX4.h:68
uint32_t _tone_beginning_ms
Definition: ToneAlarm_PX4.h:69
#define AP_NOTIFY_PX4_TONE_QUIET_ARMING_WARNING
static const Tone _tones[]
Definition: ToneAlarm_PX4.h:76
static struct notify_events_type events
Definition: AP_Notify.h:118
void handle_play_tune(mavlink_message_t *msg)
struct ToneAlarm_PX4::tonealarm_type flags
#define AP_NOTIFY_PX4_TONE_TUNING_SAVE
#define AP_NOTIFY_PX4_TONE_LOUD_1
const char * str
Definition: ToneAlarm_PX4.h:72