JaiaBot  1.19.0
JaiaBot micro-AUV software
All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
xbee.h
Go to the documentation of this file.
1 // Copyright 2011-2021:
2 // GobySoft, LLC (2013-)
3 // Massachusetts Institute of Technology (2007-2014)
4 // Community contributors (see AUTHORS file)
5 // File authors:
6 // Toby Schneider <toby@gobysoft.org>
7 // Ed Sanville <edsanville@gmail.com>
8 //
9 //
10 // This file is part of the Goby Underwater Autonomy Project Libraries
11 // ("The Goby Libraries").
12 //
13 // The Goby Libraries are free software: you can redistribute them and/or modify
14 // them under the terms of the GNU Lesser General Public License as published by
15 // the Free Software Foundation, either version 2.1 of the License, or
16 // (at your option) any later version.
17 //
18 // The Goby Libraries are distributed in the hope that they will be useful,
19 // but WITHOUT ANY WARRANTY; without even the implied warranty of
20 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 // GNU Lesser General Public License for more details.
22 //
23 // You should have received a copy of the GNU Lesser General Public License
24 // along with Goby. If not, see <http://www.gnu.org/licenses/>.
25 
26 #ifndef XBEE_H
27 #define XBEE_H
28 
29 #include <boost/asio.hpp> // for serial_port
30 #include <map> // for map
31 #include <queue>
32 #include <string> // for string
33 
34 // basic file operations
35 #include <fstream>
36 #include <iostream>
37 
38 #include <functional>
39 
40 #include "xbee.pb.h"
41 
42 namespace jaiabot
43 {
44 namespace comms
45 {
46 typedef unsigned char byte;
47 
48 // SerialNumber is an immutable value that uniquely identifies an XBee modem
49 // The XBee can only address packets to serial numbers, not to the user-configurable NodeId
50 // However, the SerialNumber can be modified using ATUL (low 32-bit word) and ATUH (high 32-bit word)
51 typedef uint64_t SerialNumber;
52 
53 // NodeId is a user-configurable id for an XBee modem, which corresponds to the modem_id from Goby
54 typedef std::string NodeId;
55 
56 enum class NodeType
57 {
58  HUB,
59  BOT
60 };
61 
62 inline SerialNumber serial_from_node_data(NodeType type, int fleet_id, int bot_or_hub_id)
63 {
64  // TES: testing with XBee on 1/27/25 seems to show that ATUH can't be any arbitrary value but 13A200 (the ATSH value for the modem I was testing on) seems to work fine
65  SerialNumber high_word = 0x13A200;
66  SerialNumber fleet64 = fleet_id & 0xFFFF, type64 = (type == NodeType::HUB) ? 0x0 : 0x1,
67  id64 = bot_or_hub_id & 0x7FFF;
68  SerialNumber low_word = ((fleet64 << 16) + (type64 << 15) + id64) & 0xFFFFFFFF;
69 
70  return (high_word << 32) + low_word;
71 }
72 
73 // Packet structure for queuing up packets for transmit
74 struct Packet
75 {
77  std::string data;
78 
79  Packet() {}
80  Packet(const NodeId& dest, const std::string& data) : dest(dest), data(data) {}
81 };
82 
84 {
85  public:
87  void startup(const std::string& port_name, const int baud_rate, const NodeId& my_node_id,
88  const uint16_t network_id, const std::string& xbee_info_location,
89  const bool& use_encryption, const std::string& encryption_password,
90  const std::string& mesh_unicast_retries, const std::string& unicast_mac_retries,
91  const std::string& network_delay_slots,
92  const std::string& broadcast_multi_transmits, int fleet, unsigned subnet_mask);
93  void shutdown();
94 
95  void send_packet(const NodeId& dest, const std::string& s);
96  void send_test_links(const NodeId& dest, const NodeId& com_dest);
97 
98  std::vector<std::string> get_packets();
99 
100  void do_work();
101 
102  static const NodeId broadcast;
103 
105 
106  // Adding a peer to the lookup table
107  void add_peer(const NodeId node_id, NodeType type, int bot_or_hub_id, int fleet_id);
108  void add_peer(const NodeId node_id, NodeType type, int bot_or_hub_id)
109  {
110  add_peer(node_id, type, bot_or_hub_id, fleet_id_);
111  }
112 
113  // Get Diagnostics
115 
116  private:
117  static const SerialNumber broadcast_serial_number;
118 
119  std::shared_ptr<boost::asio::io_context> io;
120  boost::asio::serial_port* port;
121  NodeId my_node_id;
122  SerialNumber my_serial_number;
123  byte frame_id;
124  std::string glog_group;
125  int fleet_id_{-1};
126  unsigned subnet_mask_{0xFFFF};
127 
128  // Map of node_id onto serial number
129  std::map<NodeId, SerialNumber> node_id_to_serial_number_map;
130 
131  std::vector<std::string> received_packets;
132 
133  // Called during startup
134  void get_my_serial_number();
135  void get_maximum_payload_size();
136  void broadcast_node_id();
137 
138  // Packet sending
139  void send_packet(const SerialNumber& dest, const std::string& data);
140 
141  // Low level reads and writes
142  void write(const std::string& raw);
143  std::string read_until(const std::string& delimiter);
144  size_t bytes_available();
145  void read(void* ptr, const size_t n_bytes);
146  void async_read_with_timeout(std::string& buffer, const std::string& delimiter,
147  int timeout_seconds,
148  std::function<void(const std::string&)> handler);
149 
150  // Convert string to hex
151  std::string convertToHex(const std::string& str);
152 
153  // Command mode stuff
154  void enter_command_mode();
155  void assert_ok();
156  void exit_command_mode();
157 
158  // Frame stuff
159  std::string read_frame();
160 
161  // API mode stuff
162  SerialNumber read_frame_discover_node_response(const NodeId& node_id);
163  SerialNumber get_serial_number(const NodeId& node_id);
164  std::string api_transmit_request(const SerialNumber& dest, const byte frame_id, const byte* ptr,
165  const size_t length);
166  std::string api_explicit_transmit_request(const SerialNumber& dest,
167  const SerialNumber& com_dest, const byte frame_id);
168  // Processing frames
169  void process_frame();
170  void process_frame_if_available();
171  void process_frame_extended_transmit_status(const std::string& response_string);
172  void process_frame_at_command_response(const std::string& response_string);
173  void process_frame_receive_packet(const std::string& response_string);
174  void process_frame_node_identification_indicator(const std::string& response_string);
175  void process_frame_explicit_rx_indicator(const std::string& response_string);
176 
177  // Query RSSI from Radio
178  void query_rssi();
179  // Query Received Error Count
180  void query_er();
181  // Query Received Good Count
182  void query_gd();
183  // Query Bytes Transmitted
184  void query_bc();
185  // Query Transmission Failure Count
186  void query_tr();
187 
188  // Check if we received diagnostics
189  bool received_rssi_{false};
190  bool received_er_{false};
191  bool received_gd_{false};
192  bool received_bc_{false};
193  bool received_tr_{false};
194 
195  // RSSI fields
196  uint16_t current_rssi_{0};
197  uint16_t history_rssi_{0};
198  int rssi_query_count_{1};
199  uint16_t max_rssi_{0};
200  uint16_t min_rssi_{150};
201  uint16_t average_rssi_{0};
202 
203  // Bytes Transmitted
204  uint32_t bytes_transmitted_{0};
205 
206  // Received Error Count
207  uint16_t received_error_count_{0};
208 
209  // Received Good Count
210  uint16_t received_good_count_{0};
211 
212  // Transmission Failure Count
213  uint16_t transmission_failure_count_{0};
214 
215  std::string my_xbee_info_location_{""};
216 };
217 } // namespace comms
218 } // namespace jaiabot
219 
220 #endif
void add_peer(const NodeId node_id, NodeType type, int bot_or_hub_id, int fleet_id)
static const NodeId broadcast
Definition: xbee.h:102
uint16_t max_payload_size
Definition: xbee.h:104
void send_packet(const NodeId &dest, const std::string &s)
std::vector< std::string > get_packets()
void send_test_links(const NodeId &dest, const NodeId &com_dest)
void startup(const std::string &port_name, const int baud_rate, const NodeId &my_node_id, const uint16_t network_id, const std::string &xbee_info_location, const bool &use_encryption, const std::string &encryption_password, const std::string &mesh_unicast_retries, const std::string &unicast_mac_retries, const std::string &network_delay_slots, const std::string &broadcast_multi_transmits, int fleet, unsigned subnet_mask)
void add_peer(const NodeId node_id, NodeType type, int bot_or_hub_id)
Definition: xbee.h:108
uint64_t SerialNumber
Definition: xbee.h:51
SerialNumber serial_from_node_data(NodeType type, int fleet_id, int bot_or_hub_id)
Definition: xbee.h:62
unsigned char byte
Definition: xbee.h:46
std::string NodeId
Definition: xbee.h:54
Packet(const NodeId &dest, const std::string &data)
Definition: xbee.h:80
std::string data
Definition: xbee.h:77