diff --git a/CMakeLists.txt b/CMakeLists.txt
index 0bd4af3..33b391c 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -34,12 +34,11 @@ find_package(catkin REQUIRED COMPONENTS
## catkin specific configuration ##
###################################
-
catkin_package(
- INCLUDE_DIRS include
-# LIBRARIES xbee_ros_node
- CATKIN_DEPENDS roscpp std_msgs mavros_msgs
-# DEPENDS system_lib
+INCLUDE_DIRS include
+LIBRARIES xbee_setup
+CATKIN_DEPENDS roscpp std_msgs mavros_msgs
+DEPENDS Boost
)
###########
@@ -53,25 +52,34 @@ add_definitions(
## Specify additional locations of header files
include_directories(
- include ${xbee_ros_node_INCLUDE_DIRS}
+ include
+ ${xbee_ros_node_INCLUDE_DIRS}
${catkin_INCLUDE_DIRS}
+ ${Boost_INCLUDE_DIRS}
+ ${BOOST_INCLUDEDIR}
)
+add_library(xbee_setup
+ src/XBeeSetup.cpp
+ src/XBeeModule.cpp
+ src/XMLConfigParser.cpp
+)
+add_executable(xbee_mav src/Xbee.cpp src/XBeeFrame.cpp src/SerialDevice.cpp src/CommunicationManager.cpp src/PacketsHandler src/frame_generators.cpp)
+target_link_libraries(xbee_mav xbee_setup ${catkin_LIBRARIES})
-add_executable(xbee_mav src/Xbee.cpp src/XBeeFrame.cpp src/SerialDevice.cpp src/CommunicationManager.cpp src/PacketsHandler)
-target_link_libraries(xbee_mav ${catkin_LIBRARIES})
-
-add_executable(xbee_config src/main.cpp src/XBeeModule.cpp src/XMLConfigParser.cpp)
-target_link_libraries(xbee_config ${catkin_LIBRARIES})
+add_executable(xbee_config src/XMLConfigParser.cpp src/main.cpp)
+target_link_libraries(xbee_config xbee_setup ${catkin_LIBRARIES})
#add_executable(test_controller src/TestController.cpp)
#target_link_libraries(test_controller ${catkin_LIBRARIES})
-
add_executable(test_buzz src/TestBuzz.cpp)
target_link_libraries(test_buzz ${catkin_LIBRARIES})
+add_executable(test_buzz_cyclic src/TestBuzzCyclic.cpp)
+target_link_libraries(test_buzz_cyclic ${catkin_LIBRARIES})
+
#############
## Install ##
#############
@@ -81,4 +89,3 @@ target_link_libraries(test_buzz ${catkin_LIBRARIES})
#############
## Testing ##
#############
-
diff --git a/README.md b/README.md
index f5d1e80..64a87c8 100644
--- a/README.md
+++ b/README.md
@@ -1,52 +1,43 @@
-##Description
+# XbeeMav
+## Description
The "xbee_ros_node" package provides many tools (ROS nodes) to configure, test and communicate Xbee devices.
Four nodes are provided in the package:
- * config
+ * xbee_config
* xbee_mav
* test_controller
* test_buzz
-The "test_controller" and the "test_buzz" are dummy nodes. They are used only for testing purposes. The "config" node is used to configure the Xbees. The "xbee_mav" is used to communicates between Xbee devices in different modes (e.g. SOLO and SWARM).
+The "test_controller" and the "test_buzz" are dummy nodes. They are used only for testing purposes. The "xbee_config" node is used to configure the Xbees. The "xbee_mav" is used to communicates between Xbee devices in different modes (e.g. SOLO and SWARM).
-##Prerequisites
+## Prerequisites
* Linux OS
* ROS
* Serial device drivers. For FTDI, the Virtual COM port (VCP) drivers are mandatory (http://www.ftdichip.com/Drivers/VCP.htm).
-
-##Configuration of Xbee devices
-To configure an Xbee device, the "config" node is required. To build the "config" node:
+## Configuration of Xbee devices
- 1. Uncomment the following lines in "xbee_ros_node/CMakeLists.txt":
+To configure an Xbee device, the "xbee_config" node is required. To build the "xbee_config" node:
- add_executable(config src/main.cpp src/XbeeModule.cpp src/XMLConfigParser.cpp)
- target_link_libraries(config ${catkin_LIBRARIES})
-
- 2. Insert the correct path to the config file “Resources/Xbee_Config.xml” in “XMLConfigParser.cpp” (line 26):
-
- FILE_NAME = “/home/mistlab/catkin_ws/src/xbee_ros_node/Resources/Xbee_Config.xml”
-
- 3. Build the package:
+ 1. Build the package:
$ cd ~/catkin_ws
$ catkin_make
-
-To configure an Xbee device run the "config" node. By default, the VCP and the baud rate are respectively "/dev/ttyUSB0" and "9600". Before running the “config” node, please make sure:
+
+To configure an Xbee device run the "xbee_config" node. By default, the VCP and the baud rate are respectively "/dev/ttyUSB0" and "9600". Before running the “config” node, please make sure:
1. The Xbee device is plugged.
2. The serial adapter driver is installed.
3. You have full access to the correspondent serial port (e.g. ttyUSB0):
-
- $ cd ~/../../dev/
- $ sudo chmod 666 ttyUSB0
-
-Now you can run the “config” node (after running roscore):
+
+ $ sudo chmod 666 /dev/ttyUSB0
+
+Now you can run the "xbee_config" node (after running roscore):
$ cd ~/catkin_ws
- $ rosrun xbee_ros_node config /dev/ttyUSB0 9600
-
+ $ rosrun xbee_ros_node xbee_config /dev/ttyUSB0 9600
+
If this command generates an error:
* Error: open: No such file or directory:
@@ -54,24 +45,17 @@ If this command generates an error:
2. Make sure the appropriate driver is installed correctly.
3. Make sure the path to the VCP (e.g. /dev/ttyUSB0) is correct.
4. Install the newest Xbee firmware with “XCTU” and Write the default config.
-
+
* Error: open: Permission denied:
-
+
You do not have full access to the serial port. Please execute these commands:
-
- $ cd ~/../../dev/
- $ sudo chmod 666 ttyUSB0
-
+
+ $ sudo chmod 666 /dev/ttyUSB0
+
* Time Out: The Xbee Module is Not Responding:
-
- Baud rate mismatch. Please make sure the introduced baud rate (e.g. 9600) matches the baud rate used by the Xbee (by default is 9600). If the Xbee was previously configured with the “config” node the baud rate will be 230400.
-
- * Error: Config File Not Found:
-
- The path to the config file is incorrect. Change it in “XMLConfigParser.cpp” (line 26):
-
- FILE_NAME = “/home/mistlab/catkin_ws/src/xbee_ros_node/Resources/Xbee_Config.xml”
-
+
+ Baud rate mismatch. Please make sure the introduced baud rate (e.g. 9600) matches the baud rate used by the Xbee (by default is 9600). If the Xbee was previously configured with the “xbee_config” node the baud rate will be 230400.
+
The configuration will be loaded from "Resources/Xbee_Config.xml". Most of the existing values in the config file are optimized for Digi-Mesh. Some parameters are default values. However, all parameters can be edited. Please refer to **Table.1** before editing any parameter. More details can be found in “Xbee_Manual.pdf”. The commands table is in Chapter 3 (page 28).
**Table.1:** Most relevant Xbee Parameters.
@@ -104,14 +88,13 @@ The configuration will be loaded from "Resources/Xbee_Config.xml". Most of the e
|FT | Flow Control Threshold | 13F | Since we are using the highest baud rate, we might need to increase the flow control threshold. Testing will tell us if the integrity of the data is fine.|
|AP | API Enable | 1 | The XBee has to be set to API Mode to receive API frames. This allows recovering useful information in the headers of the frames such as source and destination address. We shouldn't ever need to escape API mode so we chose option [1]. Otherwise, the escape bytes would have to be escaped each time they occur. |
|AO | API Options | 0 | Will need to change to [1] (Explicit Rx Indicator) if we wand to be able to read Cluster ID. Otherwise, not very useful. |
-
+
## Test two Xbee devices
We consider the following setup (**Fig.1**). The block (Drone + Manifold) can be replaced by any Desktop/Laptop meeting the prerequisites.
-**Fig.1:** Experimental Setup:
-![][fig1]
-[fig1]: https://github.com/MISTLab/XbeeMav/tree/master/Resources/Fig1.png "Fig.1"
+**Fig.1:** Experimental Setup:
+![fig1](Resources/Fig1.png)
One of the drones will behave as a Master while the other one will act as a Slave. The Master drone will send commands to the Slave drone.
Each drone is running a dummy flight controller node "test_controller". According to the drone type Master/Slave, the "test_controller" node will respectively send or receive and display a command. The commands in the Master drone will be introduced with the keyboard. When a command is received in the Slave drone, it will be printed on the screen. The following table (**Table.2**) depicts the keys of each command:
@@ -128,9 +111,8 @@ Each drone is running a dummy flight controller node "test_controller". Accordin
| 23 | Start Mission |
-**Fig.2:** ROS nodes running on the drone:
-![][fig2]
-[fig2]: https://github.com/MISTLab/XbeeMav/tree/master/Resources/Fig2.png "Fig.2"
+**Fig.2:** ROS nodes running on the drone:
+![fig2](Resources/Fig2.png)
The communication between both drones is performed with Xbees. The “xbee_mav” node (**Fig.2**) will handle all communications with other ROS nodes (test_controller(Flight Controller) or test_buzz (ROS Buzz)) and the connected Xbee device. Therefore, both Xbees must be configured for Digi-Mesh with the maximum baud rate (230400).
We recognize two modes of communications:
@@ -141,7 +123,7 @@ We recognize two modes of communications:
All topics and services names of the “xbee_mav” node can be edited in the launch file "launch/xbeemav.launch". For other nodes (test_controller and test_buzz), topics and services names are hardcoded. Thus, they need to be modified in the source code.
-####SOLO mode
+#### SOLO mode
The "test_controller" node is needed:
1. Uncomment the following lines in "CMakeLists.txt":
@@ -152,13 +134,13 @@ The "test_controller" node is needed:
$ catkin_make
3. Run the "test controller" node in Matser/Slave (after running roscore):
$ cd ~/catkin_ws
- $ rosrun xbee_ros_node test_controller master
+ $ rosrun xbee_ros_node test_controller master
4. Run the "xbee_mav" node in SOLO mode. The drone type (Master/Slave) and the communication mode (SOLO/SWARM) need to be specified for the "xbee_mav". You can change these parameters in the launch file “launch/xbeemav.launch”:
$ cd ~/catkin_ws
$ roslaunch xbee_ros_node xbeemav.launch
5. Introduce some commands to the "test_controller". If the network was configured correctly, commands sent from one side should be received and displayed in the opposite side.
-####SWARM mode
+#### SWARM mode
The "test_buzz" node is required:
1. Uncomment the following lines in "CMakeLists.txt":
@@ -176,7 +158,7 @@ The "test_buzz" node is required:
Random payloads (Mavlink messages) will be created in the Master drone and transferred through the Xbees to the Slave drone for display. Payloads are arrays with random sizes of random 64 bits integers.
-## Communicate drones in a Swarm
+## Communicate drones in a Swarm
We consider the same setup in the testing phase (**Fig.1**). The "test_controller" and the "test_buzz" dummy nodes need to be replaced with real ones (“fligh_controller” and “ros_buzz”).
You can download the real nodes by clicking on the correspondent link:
@@ -184,14 +166,21 @@ You can download the real nodes by clicking on the correspondent link:
* ros_buzz : (https://github.com/MISTLab/ROSBuzz.git)
To run drones in SWARM mode you need to:
- 1. Comment the following lines in “xbee_ros_node/CMakeLists.txt”:
-
- add_executable(config src/main.cpp src/XbeeModule.cpp src/XMLConfigParser.cpp)
- target_link_libraries(config ${catkin_LIBRARIES})
- add_executable(test_controller src/TestController.cpp)
- target_link_libraries(test_controller ${catkin_LIBRARIES})
- add_executable(test_buzz src/TestBuzz.cpp)
- target_link_libraries(test_buzz ${catkin_LIBRARIES})
-
- 2. Build the three packages.
- 3. Run the launch file (this will run the flight_controller, ros_buzz and xbee_mav). The "xbee_mav" should run in SWARM mode. The drone type (Master/Slave) is not needed.
+ 1. Build the three packages.
+ 2. Run a launch file that will start the flight_controller, ros_buzz and xbee_mav. The "xbee_mav" should run in SWARM mode. The drone type (Master/Slave) is not needed.
+
+## ROS services
+The node xbee_mav provides a ROS service xbee_status that will return information
+about the xbee module. The information returned depends on the argument passed to
+the service (example: rosservice call /xbee_status "param_id: 'ARGUMENT'"). The different arguments that can be passed are described below:
+* id : Returns the xbee module short identifier.
+* deque_full : returns 1 if the out messages queue is full and 0 otherwise
+* rssi : Returns the average Received Signal Strength Indicator (RSSI). This RSSI value could be inaccurate since the average is obtained by getting the RSSI of the last message at a fixed frequency without any information about the sender.
+* trig_rssi_api_avg : Triggers a link testing procedure to obtain the RSSI with all the known nodes in the network. Returns false if there is no other node connected to the network.
+* trig_rssi_api_ID (where ID should be replaced by a number): Triggers a link testing procedure to obtain the RSSI with the corresponding ID. Returns false if the node is not present on the network.
+* get_rssi_api_avg : Returns the average of the average RSSI results of the link testing procedures.
+* get_rssi_api_ID (where ID should be replaced by a number): Returns the average RSSI result of the link testing procedure.
+* pl_raw_avg : Returns the average of the raw packet loss value among the connected nodes. Returns false if there is no other node connected to the network.
+* pl_raw_ID (where ID should be replaced by a number): Returns the raw packet loss value between this node and the node ID. Returns false if the node is not present on the network.
+* pl_filter_avg : same thing as pl_raw_avg but for the filtered value.
+* pl_filter_ID (where ID should be replaced by a number): same thing as pl_raw_ID but for the filtered value.
diff --git a/Resources/XBee_Config.xml b/Resources/XBee_Config.xml
index 17284b1..e33fdc8 100644
--- a/Resources/XBee_Config.xml
+++ b/Resources/XBee_Config.xml
@@ -5,11 +5,11 @@
00FFFFFFFFFFF7FFFF
1
5FFF
- 3
+ 0
4
A
0
- 0
+ 1
7
1
3
@@ -63,6 +63,5 @@
2B
60
3E8
- B0000
diff --git a/Resources/XbeeModule_DataSheet.pdf b/Resources/XbeeModule_DataSheet.pdf
new file mode 100644
index 0000000..41db1d3
Binary files /dev/null and b/Resources/XbeeModule_DataSheet.pdf differ
diff --git a/Resources/database.xml b/Resources/database.xml
index 3257dc9..52828fd 100644
--- a/Resources/database.xml
+++ b/Resources/database.xml
@@ -1,18 +1,39 @@
+
+
0013A20040D8CA1E
- 0013A200415278B8
+ 0013A200415278B8
0013A2004103B363
0013A200415278AD
- 0013A2004103B356
+ 0013A2004103B356
0013A200415278B7
0013A2004098A7A7
0013A2004098A7BA
- 0013A200415A9DDD
+ 0013A200415A9DDD
0013A200415A9DE4
0013A200415A9DDF
0013A200415A9DDE
- 0013A200415A9DE8
-
+ 0013A200415A9DE8
+ 0013A2004156FA60
+ 0013A2004156FA61
+ 0013A2004156FA57
+ 0013A200417DFE1D
+ 0013A200417DFE2B
+ 0013A200417DFE04
+ 0013A20041795D68
+ 0013A20041795E68
+ 0013A2004178AF0E
+
+ 0013A20041795D68
+ 0013A20041795E68
+ 0013A2004178AF0E
diff --git a/include/CommunicationManager.h b/include/CommunicationManager.h
index 74dbfba..2398083 100644
--- a/include/CommunicationManager.h
+++ b/include/CommunicationManager.h
@@ -1,113 +1,103 @@
/* CommunicationManager.h -- Communication Manager class for XBee:
- Handles all communications with other ROS nodes
- and the serial port -- */
+ Handles all communications with other ROS nodes
+ and the serial port -- */
/* ------------------------------------------------------------------------- */
/* September 20, 2016 -- @Copyright Aymen Soussia. All rights reserved. */
/* (aymen.soussia@gmail.com) */
-
#pragma once
+#include "PacketsHandler.h"
+#include "SerialDevice.h"
#include
-#include
-#include
-#include
-#include
-#include
-#include
+#include
+#include
+#include
#include
#include
-#include"PacketsHandler.h"
-#include"SerialDevice.h"
+#include
+#include
+#include
+namespace Mist {
-namespace Mist
-{
-
-
-namespace Xbee
-{
-
+namespace Xbee {
//*****************************************************************************
-struct Waypoint_S
-{
- unsigned int latitude;
- unsigned int longitude;
- double altitude;
- unsigned int staytime;
- unsigned int heading;
+struct Waypoint_S {
+ unsigned int latitude;
+ unsigned int longitude;
+ double altitude;
+ unsigned int staytime;
+ unsigned int heading;
};
-
//*****************************************************************************
class CommunicationManager
{
-public:
- CommunicationManager();
- ~CommunicationManager();
+ public:
+ CommunicationManager();
+ ~CommunicationManager();
- enum class DRONE_TYPE {MASTER, SLAVE};
- enum class RUNNING_MODE {SWARM, SOLO};
+ enum class DRONE_TYPE { MASTER, SLAVE };
+ enum class RUNNING_MODE { SWARM, SOLO };
- bool Init(const std::string& device, const std::size_t baud_rate);
- void Run(DRONE_TYPE drone_type, RUNNING_MODE running_mode);
+ bool Init(const std::string &device, const std::size_t baud_rate);
+ void Run(DRONE_TYPE drone_type, RUNNING_MODE running_mode);
-private:
+ private:
+ const unsigned char START_DLIMITER;
+ const std::size_t LOOP_RATE;
+ const uint8_t DEFAULT_RATE_DIVIDER_RSSI;
+ const uint8_t DEFAULT_RATE_DIVIDER_PACKET_LOSS;
+ const uint16_t DEFAULT_RSSI_PAYLOAD_SIZE;
+ const uint16_t DEFAULT_RSSI_ITERATIONS;
- const unsigned char START_DLIMITER;
- const std::size_t LOOP_RATE;
+ void Run_In_Solo_Mode(DRONE_TYPE drone_type);
+ void Run_In_Swarm_Mode();
+ void Display_Init_Communication_Failure();
+ void Send_Mavlink_Message_Callback(
+ const mavros_msgs::Mavlink::ConstPtr &mavlink_msg);
+ void Display_Drone_Type_and_Running_Mode(DRONE_TYPE drone_type,
+ RUNNING_MODE running_mode);
+ bool Serve_Flight_Controller(mavros_msgs::CommandInt::Request &request,
+ mavros_msgs::CommandInt::Response &response);
+ void Check_In_Messages_and_Transfer_To_Server();
+ void Process_In_Standard_Messages();
+ void Process_In_Acks_and_Pings();
+ void Process_In_Fragments();
+ void Process_In_Packets();
+ void Process_Command_Responses();
+ void Process_Packet_Loss();
+ bool Get_Param(mavros_msgs::ParamGet::Request &req,
+ mavros_msgs::ParamGet::Response &res);
+ bool getRosParams();
+ int getIntParam(std::string name, int default_value);
+ void triggerRssiUpdate();
+ std::string safeSubStr(const std::string strg,
+ const unsigned int index_max) const;
- void Run_In_Solo_Mode(DRONE_TYPE drone_type);
- void Run_In_Swarm_Mode();
- /*void Generate_Transmit_Request_Frame(
- const char* const message,
- std::string* frame,
- const unsigned char frame_ID =
- static_cast(0x01),
- const std::string& destination_adssress = "000000000000FFFF",
- const std::string& short_destination_adress = "FFFF",
- const std::string& broadcast_radius = "00",
- const std::string& options = "00");*/
- //void Check_In_Messages_and_Transfer_To_Topics();
- void Display_Init_Communication_Failure();
- //void Convert_HEX_To_Bytes(const std::string& HEX_data,
- //std::string* converted_data);
- //void Calculate_and_Append_Checksum(std::string* frame);
- //void Add_Length_and_Start_Delimiter(std::string* frame);
- void Send_Mavlink_Message_Callback(
- const mavros_msgs::Mavlink::ConstPtr& mavlink_msg);
- void Display_Drone_Type_and_Running_Mode(DRONE_TYPE drone_type,
- RUNNING_MODE running_mode);
- bool Serve_Flight_Controller(mavros_msgs::CommandInt::
- Request& request, mavros_msgs::CommandInt::Response& response);
- void Check_In_Messages_and_Transfer_To_Server();
- void Process_In_Standard_Messages();
- void Process_In_Acks_and_Pings();
- void Process_In_Fragments();
- void Process_In_Packets();
- void Process_Command_Responses();
- bool Get_Param(mavros_msgs::ParamGet::Request& req, mavros_msgs::ParamGet::Response& res);
-
- Mist::Xbee::SerialDevice serial_device_;
- Mist::Xbee::PacketsHandler packets_handler_;
- Thread_Safe_Deque in_std_messages_;
- Thread_Safe_Deque in_fragments_;
- Thread_Safe_Deque in_Acks_and_Pings_;
- Thread_Safe_Deque command_responses_;
- Thread_Safe_Deque in_packets_;
- ros::NodeHandle node_handle_;
- ros::Subscriber mavlink_subscriber_;
- ros::Publisher mavlink_publisher_;
- ros::ServiceClient mav_dji_client_;
- ros::ServiceServer mav_dji_server_;
- ros::ServiceServer StatusSrv_;
- std_msgs::UInt8 device_id_out;
- std::shared_ptr service_thread_; // TO DO delete !?
+ Mist::Xbee::SerialDevice serial_device_;
+ Mist::Xbee::PacketsHandler packets_handler_;
+ Thread_Safe_Deque in_std_messages_;
+ Thread_Safe_Deque in_fragments_;
+ Thread_Safe_Deque in_Acks_and_Pings_;
+ Thread_Safe_Deque command_responses_;
+ Thread_Safe_Deque in_packets_;
+ Thread_Safe_Deque in_packet_loss_;
+ ros::NodeHandle node_handle_;
+ ros::Subscriber mavlink_subscriber_;
+ ros::Publisher mavlink_publisher_;
+ ros::ServiceClient mav_dji_client_;
+ ros::ServiceServer mav_dji_server_;
+ ros::ServiceServer StatusSrv_;
+ std_msgs::UInt8 device_id_out;
+ std::shared_ptr service_thread_; // TO DO delete !?
+ std::uint16_t packet_loss_timer_;
+ uint8_t rate_divider_rssi_;
+ uint8_t rate_divider_packet_loss_;
+ uint16_t rssi_payload_size_;
+ uint16_t rssi_iterations_;
};
-
-
}
-
-
}
diff --git a/include/PacketsHandler.h b/include/PacketsHandler.h
index 178cea9..d092f4b 100644
--- a/include/PacketsHandler.h
+++ b/include/PacketsHandler.h
@@ -1,6 +1,6 @@
/* PacketsHandler.h-- Packets Handler class for XBee:
- Serialize, deserialize, fragment and reassemly mavlink
- messages -- */
+ Serialize, deserialize, fragment and reassemly mavlink
+ messages -- */
/* ------------------------------------------------------------------------- */
/* February 06, 2017 -- @Copyright Aymen Soussia. All rights reserved. */
/* (aymen.soussia@gmail.com) */
@@ -8,23 +8,24 @@
#pragma once
-#include
-#include
-#include
-#include