Current section
Files
Jump to
Current section
Files
lib/mavlink_util/arm.ex
defmodule XMAVLink.Util.Arm do
@moduledoc false
@arm_retry_interval 3000
require Logger
alias Common.Message.CommandLong
alias Common.Message.Heartbeat
alias XMAVLink.Router, as: MAV
import XMAVLink.Util.CacheManager, only: [msg: 1]
import XMAVLink.Util.FocusManager, only: [focus: 0]
def arm() do
with {:ok, {system_id, component_id, mavlink_version}} <- focus() do
arm(system_id, component_id, mavlink_version)
end
end
def arm(system_id, component_id, mavlink_version) do
with {:ok, _, %Heartbeat{system_status: system_status}}
when system_status in [
:mav_state_standby,
:mav_state_active,
:mav_state_critical,
:mav_state_emergency
] <-
msg(Heartbeat) do
MAV.subscribe(message: Heartbeat, source_system: system_id)
MAV.pack_and_send(
%CommandLong{
command: :mav_cmd_component_arm_disarm,
confirmation: 1,
# Arm
param1: 1.0,
param2: 0.0,
param3: 0.0,
param4: 0.0,
param5: 0.0,
param6: 0.0,
param7: 0.0,
target_component: component_id,
target_system: system_id
},
mavlink_version
)
receive do
%Heartbeat{base_mode: base_mode} ->
cond do
:mav_mode_flag_safety_armed in base_mode ->
MAV.unsubscribe()
Logger.info("Armed vehicle #{system_id}.#{component_id}")
:ok
true ->
arm(system_id, component_id, mavlink_version)
end
after
@arm_retry_interval ->
arm(system_id, component_id, mavlink_version)
end
else
%Heartbeat{system_status: invalid_system_status} ->
Logger.warning(
"Cannot arm vehicle #{system_id}.#{component_id}: #{Common.describe(invalid_system_status)}"
)
{:error, :cannot_arm_invalid_vehicle_status}
_ ->
Logger.warning(
"Could not determine current status of vehicle #{system_id}.#{component_id}"
)
{:error, :could_not_determine_vehicle_status}
end
end
def disarm() do
with {:ok, {system_id, component_id, mavlink_version}} <- focus() do
disarm(system_id, component_id, mavlink_version)
end
end
def disarm(system_id, component_id, mavlink_version) do
MAV.subscribe(message: Heartbeat, source_system: system_id)
MAV.pack_and_send(
%CommandLong{
command: :mav_cmd_component_arm_disarm,
confirmation: 1,
# Disarm
param1: 0.0,
param2: 0.0,
param3: 0.0,
param4: 0.0,
param5: 0.0,
param6: 0.0,
param7: 0.0,
target_component: component_id,
target_system: system_id
},
mavlink_version
)
receive do
%Heartbeat{base_mode: base_mode} ->
cond do
:mav_mode_flag_safety_armed not in base_mode ->
MAV.unsubscribe()
Logger.info("Disarmed vehicle #{system_id}.#{component_id}")
:ok
true ->
disarm(system_id, component_id, mavlink_version)
end
after
@arm_retry_interval ->
disarm(system_id, component_id, mavlink_version)
end
end
end