Background:
This question is about simulating one ErleCopter and one ErleRover simultaneously for a non-commercial research. I would like to have the quadcopter follow a rover, which in turn is to be tasked with following a line. I am trying to spawn the vehicles in Gazebo and control them using MAVProxy.
The Problem:
Any time I try this, I run into one of two problems:
- Spawning the second vehicle terminates the first MAVProxy instance, or
- The second vehicle spawned cannot be linked to the second instance of MAVProxy.
I'm not sure what to do about this because I am not sure if this problem is one problem or if it's composed of two sub-problems. The first problem is in spawning the robots and the second one is in controlling both independently (and obtain the state parameters of both vehicles and use that as feedback).
I believe a contributing factor to this problem is that I'm trying to do the simulation and both MAVProxy instances on one computer, a Lenovo-y50-70 is being used with Ubuntu 14.04. Two computers are not easy to obtain immediately and there are network stability issues where I am.
The Question:
The entire question probably reduces to "How to link second robot spawned by rosrun to second MAVproxy instance?".
Desired Outcome:
I would like help either getting the simulation to run as desired (two vehicles co-simulated in one virtual world with two MAVProxy instances, one linked to each vehicle), OR official documentation somewhere that this is not possible.
What I've Attempted:
Initial attempts can be seen in earlier edits of this question. For clarity, that information has been removed, but again, if interested, see an earlier version of this question. Fast-forwarding to the relevant:
The second robot has been spawned successfully as mentioned in this video by using the commands mentioned below.
cd path_to_urdf_model_files
rosrun gazebo_ros spawn_model -file rover.urdf -urdf -model rover_object
Note: ROS Indigo is different; gazebo_ros must be used instead of gazebo_worlds
The weird behaviour of the robot rotating about itself is probably because of MAVproxy; I have experienced this before. Attempt to establish separate network connections to Copter and Rover has been successful so far. The original structure is as shown below:
rover_circuit.launch -> apm_sitl.launch -> node.launch (node name: "mavros")
The current architecture is as shown below:
copter_circuit.launch -> apm_sitl_copter.launch -> node_copter.launch ("mavros_copter")
rover_circuit1.launch -> apm_sitl_rover.launch -> node_rover.launch ("mavros_rover")
rover_ciruit1.launch is as shown below:
<launch>
<include file="$(find mavros)/launch/apm_sitl_rover.launch"></include>
<arg name="enable_logging" default="true"/>
<arg name="enable_ground_truth" default="true"/>
<arg name="log_file" default="rover"/>
<arg name="tf_prefix" default="$(optenv ROS_NAMESPACE)"/>
<arg name="model" default="$(find ardupilot_sitl_gazebo_plugin)/urdf/rover.urdf"/>
<param name="robot_description" command="
$(find xacro)/xacro.py '$(arg model)'
enable_logging:=$(arg enable_logging)
enable_ground_truth:=$(arg enable_ground_truth)
log_file:=$(arg log_file)"
/>
<param name="tf_prefix" type="string" value="$(arg tf_prefix)" />
<node name="spawn_rover" pkg="gazebo_ros" type="spawn_model"
args="-param robot_description -urdf -model 'rover' " respawn="false" output="screen"></node>
</launch>
This is the minimal launch file, and it works. I had thought of rosrun apm_sitl_rover.launch followed by rosrun rover.urdf, but I have been unable to find a suitable package which launches apm_sitl_rover.launch directly. It is easy to roslaunch a launch file that has an method appended.
Naming issues and other network errors have been resolved.
Outstanding Problem Remaining:
I'm still having issues launching and linking the second vehicle, but now it seems like I've narrowed it down such that the only problem is with UDP bind port, which is 14555 by default, and this is crashing Gazebo for the second instance because the second instance is using the same bind port.
It looks like libmavconn is getting called somehow, particularly interface.cpp which has url_parse_host(bind_pair, bind_host, bind_port, "0.0.0.0", 14555); and the udp.h included in interface.cpp has a function MAVConnUDP() which has bind_port=14555, and this has resulted in "udp1: Bind address: 14555" and "GCS: DeviceError:udp:bind: Address already in use"
.
Trying to assess the connection between sim_vehicle.sh, libmavconn, and Gazebo, I was able to figure out that sim_vehicle.sh calls mavproxy.py in one of the ending lines which in turn uses pymavlink. I have been unable to find further relationship currently.
Leading Questions / An Approach to the Solution
As I have a strong intuition that this is the final stage, I currently resolve to fix this by using interface_copter.cpp and interface_rover.cpp. I think, if I could get answers to the following questions, I can work out where the failure is in successfully launching and link the second (or subsequent) vehicles:
How does sim_vehicle.sh trigger the libmavconn package and ultimately Gazebo?
Is there a software architecture diagram which describes the complete structure from sim_vehicle.sh to joints and controllers?