<html><head><meta name="color-scheme" content="light dark"></head><body><pre style="word-wrap: break-word; white-space: pre-wrap;">\documentclass[onecolumn,letterpaper,11pt]{article}

%=================================================================
\input{common_latex/common_latex_packages}
\input{common_latex/common_latex_definitions}
\input{common_latex/common_latex_help_format}
%=================================================================

\begin{document}

\begin{labcover}
\labtitle{pContactMgrV20: Managing Platform Contacts}
\vspace{0.1in}
\labdate{February 2025}
\vspace{0.1in}
\labauth{Michael Benjamin, mikerb@mit.edu}
\labauth{Department of Mechanical Engineering}
\labauth{MIT, Cambridge MA 02139}
\labsrc{project-pavlab/appdocs/app\_pcmanager\_v20} 
\labtoc{small}
\end{labcover}

\wikidoc{file=IvPTools.PCManagerV20}
\wikidoc{bugz=pContactMgrV20}
\wikidoc{auth=mikerb@mit.edu}

%================================================================
\newpage
\section{Overview}
%================================================================
\label{sec_pcmanager}
%\index{pContactMgrV20}
%\index{Contact Management}

Note: The \app{pContactMgrV20} app is a substantially re-written
version of its predecessor, \app{pBasicContactMgr}. The new version is
meant to be largely backward compatible with the previous version. The
new version has better support for larger streams of contact
information over longer missions. It has better guards on memory
management and should be more efficient in terms of CPU load. It also
has much better support for filtering contacts with greater control
over how different contacts may be handled uniquely. The latter is in
support of apps in the Swarm Autonomy Toolbox which require these
features from a contact manager.

\vspace{0.1in}
\noindent
The \app{pContactMgrV20} application deals with information about
other known vehicles in its vicinity. It is not a sensor application,
but rather handles incoming "contact reports" which may represent
information received by the vehicle over a communications link, or may
be the result of on-board sensor processing. The primary use case
involves the generation of alert messages corresponding to contact
relative position criteria configured by the consumers of the alerts.
The \app{pContactMgrV20} posts to the MOOSDB summary reports about
known contacts, which supports functionality of other MOOS applications. 

\vspace{0.1in}
\noindent
The basic idea is shown below:

\vspace{0.15in}
\begin{figure}[H]
  \centering 
  \includegraphics[width=0.56\textwidth]{figures/pcm_topology.png}
  \caption{{\bf The pContactMgrV20 Application:} The
    \vvar{pContactMgrV20} utility receives \mvvar{NODE\_REPORT}
    information from other MOOS applications and manages a list of
    unique contact records. It may post additional user-configurable
    alerts to the MOOSDB based on the contact information and
    user-configurable conditions. The source of contact information
    may be external (via communications) or internal (via on-board
    sensor processing). The pSensor and iCommsDevice modules shown
    here are fictional applications meant to convey these two sources
    of information abstractly.}
\label{fig_pcmanager}
\end{figure}
\vspace{0.1in}

\vspace{0.1in}
\noindent
The contact manager is typically used in coordinating with the IvP
Helm, but a key design goal of the contact manager is to remain helm
agnostic.  The design or configuration of the contact manager need not
know anything about the helm or any other application for that
matter. The configuration or design of the helm, and helm behaviors,
on the other hand needs to coordinate its function with the contact
manager.  Although contact manager alerts are simply MOOS variables,
with no explicit linking or dependency on the helm or helm libraries,
the alerts are commonly used by the helm to trigger the spawning of a
behavior associated with a contact (Section
\ref{sec_cmgr_helm_coord}). The configuration of the contact manager,
for use with the helm, is also the job of the helm behaviors which
post a MOOS variable to request dynamic alert configurations of the
contact manager (Section \ref{sec_cmgr_helm_reg}).

%================================================================
\section{Contact Alert Structure and Configuration}
%================================================================

A {\em contact alert} is an internal data structure of the contact
manager, which may be configured to comprise several types of alerts
in a given mission. Configuration of alerts may be done through the
mission (\var{.moos}) file, or they may be configured by other
apps in the MOOS community that publish an alert request. The latter
is the most common, but both may coexist. Here the data structure
is defined, start-up configuration from the mission file, and
run-time configuration through MOOS mail messages. 




%================================================================
\subsection{The Contact Alert Structure}
\label{sec_cmgr_alert_struct}

The {\em contact alert} data structure contains the following fields:

\vspace{0.1in}
\noindent
The core components:

\begin{packed_itemize}
\item \var{alert id}: A unique name for the alert.
\item \var{alert\_range}: A minimal range in meters that will cause an
  alert trigger.
\item \var{cpa\_range}: A larger range in meters that may trigger an
  alert before breaching the minimal range.
\item \var{on\_flag}: An alert posting, or \var{VarDataPair}, to be
  published when the alert has been triggered. Multiple flags may be
  provided.
\item \var{off\_flag}: An alert posting, or \var{VarDataPair}, to be
  published when the alert trigger criteria has switched off. Multiple
  flags may be provided.
\end{packed_itemize}

\vspace{0.1in}
\noindent
The filter components:

\begin{packed_itemize}
\item \var{ignore\_name}: One or more contact names to be ignored.
\item \var{match\_name}: One or more contact names to be matched.

\item \var{ignore\_type}: One or more contact types to be ignored.
\item \var{match\_type}: One or more contact types to be matched.

\item \var{ignore\_group}: One or more contact groups to be ignored.
\item \var{match\_group}: One or more contact groups to be matched.

\item \var{ignore\_region}: A region where contacts will be ignored.
\item \var{match\_region}: A region where contacts will be ignored.
\end{packed_itemize}

%-----------------------------------------------------------------
\subsubsection*{Range Components}

The \var{alert\_range} component represents a threshold range to a
contact, in meters. When a contact moves within this range, an alert
will be generated. This is discussed in Section \ref{sec_cmgr_range_trigger}.
The \var{cpa\_range} component also represents a threshold range, in
meters. Typically this \var{cpa\_range} is greater than the
\var{alert\_range} parameter. It is never less than the
\var{alert\_range}. When a contact is noted to be within the
\var{cpa\_range}, the contact and ownship trajectories are considered,
to calculate the closest point of approach (CPA). If the CPA range is
determined to be within the \var{alert\_range}, an alert is generated,
even if the present range between ownship and contact is outside the
\var{alert\_range}. This is also discussed in Section
\ref{sec_cmgr_range_trigger}.

%-----------------------------------------------------------------
\subsubsection*{Flag Posting Components}

A flag describes a MOOS posting. It will be a pair, in the form of
\msvar{MOOS\_VARIABLE = value}. The value component may be string
containing macros to allow the alert posting to contain information
about the contact or ownship. This is discussed more in Section
\ref{sec_cmgr_alert_mconfig}.

%-----------------------------------------------------------------
\subsubsection*{Filter Components}

The filter components allow the user to require that a contact meet a
configured set of criteria in order for the alert to be applicable.
This criteria can be based on either the contact name, platform type,
group name, or region of the operation area where the contact
presently resides. The {\em ignore} options indicate the contact
should be ignored if one or more of the criteria hold. The {\em match}
options indicate the contact should be ignored {\em unless} the match
options are satisfied. This is discussed further in Section
\ref{sec_cmgr_filters}.


%-----------------------------------------------------------------
\subsubsection*{Alert Validity}

The alert ID, the alert range, and one or more postings are regarded
as mandatory for the alert to be considered valid. All other fields
are optional. The {\em cpa range} must be a value equal to or larger
than the {\em alert range}.  An invalid alert provided on startup will
result in a configuration warning. An invalid alert received via an
incoming mail message will result in a run warning.

%================================================================
\subsection{Alert Configuration from the Mission File}
\label{sec_cmgr_alert_config}

Alerts may be
configured in the mission file with the \pvar{alert} parameter.
A single alert type may be defined over several lines, where each line
contains the alert id of the alert type being configured. For example:

\prevblue
\begin{verbatim}
  alert = id=&lt;alert-id&gt;, on_flag=&lt;VarDataPair&gt;, off_flag=&lt;VarDataPair&gt;
  alert = id=&lt;alert-id&gt;, alert_range=&lt;distance&gt;,  cpa_range=&lt;distance&gt;
\end{verbatim}
\postverb

\noindent
A simple example:

\prevblue
\begin{verbatim}
  alert = id=K8, on_flag=SAY_MOOS=alarm, off_flag=SAY_MOOS=ok, alert_range=20, cpa_range=30 
\end{verbatim}
\postverb

\noindent
Or, equivalently:

\prevblue
\begin{verbatim}
  alert = id=K8, on_flag=SAY_MOOS=alarm
  alert = id=K8, off_flag=SAY_MOOS=ok
  alert = id=K8, alert_range=20
  alert = id=K8, cpa_range=30 
\end{verbatim}
\postverb


%================================================================
\subsection{Alert Configuration from Incoming Mail}
\label{sec_cmgr_alert_mconfig}

Alert configuration can also be requested at run time, originating from another
MOOS app via a message to \mvar{BCM\_ALERT\_REQUEST}. The contents of this
message are identical to the one-line configuration used in a mission file
shown above.

\prevgreen
\begin{verbatim}
BCM_ALERT_REQUEST = id=k8, on_flag=SAY_MOOS=alert, alert_range=20, cpa_range=40 
\end{verbatim}
\postverb

\noindent
This kind of dynamic request is essential to the operation of the IvP Helm
for contact related behaviors such as collision avoidance. This is discussed
in Section \ref{sec_cmgr_helm_coord}.


%================================================================
\subsection{Flag Macros}
\label{sec_cmgr_flag_macros}

The \var{on\_flag} component of an alert is a posting, or
\var{VarDataPair}, that will be published by \app{pContactMgrV20} to
the \app{MOOSDB} when an alert is triggered. The data component of
this posting may be a string, and may contain one or more supported
macros to be expanded at the time of the post. For example the
\var{\$[VNAME]} macro contains the name of the contact related to the
alert. This can be used to spawn a collision avoidance behavior as
discussed in Section \ref{sec_cmgr_helm_coord}. The full set of
supported macros is below:

\vspace{0.1in}
\noindent
\begin{packed_itemize}
\item \var{\$[VNAME]}: The name of the contact. 
\item \var{\$[X]}: The position of the contact in local $x$ coordinates. 
\item \var{\$[Y]}: The position of the contact in local $y$ coordinates. 
\item \var{\$[LAT]}: The latitude position of the contact in earth coordinates. 
\item \var{\$[LON]}: The longitude position of the contact in earth coordinates. 
\item \var{\$[HDG]}: The reported heading of the contact. 
\item \var{\$[SPD]}: The reported speed of the contact.   
\item \var{\$[DEP]}: The reported depth of the contact.   
\item \var{\$[VTYPE]}: The reported vessel type of the contact. 
\item \var{\$[UTIME]}: The UTC time of the last report for the contact. 
\end{packed_itemize}

\vspace{0.1in}
\noindent
Multiple macro types may be used in the same \var{on\_flag} or \var{off\_flag}.



%================================================================
\newpage
\section{Alert Triggering}
%================================================================
\label{sec_cmgr_alert_trigger}

%================================================================
\subsection{Trigger Criteria Base on Range and CPA Range}
\label{sec_cmgr_range_trigger}

Alerts are triggered for all contacts based on range between ownship
and the reported contact position. It is assumed that each incoming
contact report minimally contains the contact's name and present
position. An alert will be triggered if the current range to the
contact falls within the distance given by \var{alert\_range}, as in
Contact-A in Figure \ref{fig_pcm_alerts}. 

\vspace{0.15in}
\begin{figure}[H]
  \centering 
  \includegraphics[width=0.65\textwidth]{figures/pcmanager-alerts.png}
  \caption{{\bf Alert Triggers:} An alert may be triggered by the
    contact manager if the contact is within the \vvar{alert\_range},
    as with Contact-A. It may also be triggered if the contact is
    within the \vvar{cpa\_range}, and the contact's CPA distance is
    within the \vvar{alert\_range}, as with Contact-B. Contact-C shown
    here would not trigger an alert since its CPA distance is its
    current range and is not within the \vvar{alert\_range}. Contact-D
    also would not trigger an alert despite the fact that its CPA with
    ownship is apparently small, since its current absolute range is
    greater than \vvar{cpa\_range}.}
\label{fig_pcm_alerts}
\end{figure}
\vspace{0.1in}

\noindent
An alert may also be configured with a second trigger criteria
consisting of another range to contact, \var{cpa\_range}. The range is
enforced to be equal to or larger than the \var{alert\_range}.  If
\var{cpa\_range} is left unspecified, it will be set to the
\var{alert\_range}, effectively disabling this feature.  When a
contact is outside the \var{alert\_range}, but within the
\var{cpa\_range}, as with Contact-B in Figure \ref{fig_pcm_alerts},
the closest point of approach (CPA) between the contact and ownship is
calculated given their presently-known position and trajectories. If
the CPA distance falls below the \var{alert\_range} value, an alert is
triggered.


%----------------------------------------------------------------
\subsubsection*{Turning Off an Alert and a Schmitt Trigger}

Once an alert has been triggered, presumably a posting has been made,
specified with the \var{on\_flag} parameter. Typically there is
nothing further to do when the trigger criteria is no longer met. As
discussed later in the case of the helm, a collision avoidance
behavior will spawn with initial alert, and the behavior will be
deleted later when the contact passes beyond the \var{cpa\_range} of
ownship. The only catch is that the same contact, with the same
contact ID, may later change course and once again close range on
ownship. A new alert will need to be triggered, and new behavior
spawned. For this reason, when the contact opens beyond the
\var{cpa\_range}, the contact manager marks the contact/alert pair as
    {\em off}. If that contact does indeed change course and approach
    ownship, a new alert will be trigger, a new posting will be
    published and a new collision avoidance behavior will be spawned.
    However, when events are triggered on/off based on a range
    threshold, it opens the door that a noisy sensor may create a
    thrashing of a rapid succession of alert on/off declarations and
    behavior spawning and deletions. In physics there is the notion of
    a {\em Schmitt trigger} which is a switch with a small positive
    feedback that increases the threshold for changing state in both
    directions. For example this could be accomplished in our
    situation by adding a few meters to the \var{cpa\_range} as the
    contact is opening range, and subtracting a few meters from
    \var{cpa\_range} when the contact is closing range to ownship.
    This isn't necessary however since the nature of the
    \var{cpa\_range} is such that, for a contact to trigger an alert,
    it must not only be closing range to ownship, it must be on a
    heading that creates a CPA to ownship within the \var{range}
    setting (like Contact-B in Figure \ref{fig_pcm_alerts}). As a
    contact is opening range, and turning off the alert, even if it
    were magically within the \var{cpa\_range} an instant later, it
    would not have a CPA within the \var{range} circle until it comes
    about with a significant heading change. This creates natural
    Schmitt trigger effect.



%================================================================
\subsection{Alert Triggering Internal Data Structures}
\label{sec_cmgr_data_struct}

The contact manager maintains a few key data structures for managing
alert generation and other status updates:

\begin{packed_itemize}
\item Contact Status Table
\item Contact Alert Table
\item Retired Contacts
\end{packed_itemize}

\noindent
As contact information is updated in the contact manager, the contact's
position and timestamp of the most recent update is stored in the
contact status table. This range is the simple linear distance. The CPA
range projects both vehicles into the future to calculate the expected
CPA range. The extrapolated range is based on an extrapolated contact
position based on the current time and time of the last position update
for that contact.

\vspace{0.1in}
\noindent
Each data structure is depicted below:

\vspace{0.15in}
\begin{figure}[H]
  \centering 
  \includegraphics[width=0.8\textwidth]{figures/platform_alert_record.png}
  \caption{{\bf Internal Data Structures:} Information is updated based
    on the arrival new contact information, updates on internally calculated
    status, and retiring of contacts out of range and not recently updated.}
\label{fig_pcm_data}
\end{figure}
\vspace{0.1in}

\noindent
Based on the updated values of the contact status table, each contact
is judged based on the alert range criteria for each alert. The
contact alert table is updated accordingly. If a cell switches from
\var{false} to \var{true}, the \var{on\_flag(s)} for that alert and
contact are posted. If the cell switches from \var{true} to
\var{false}, the \var{off\_flag(s)} are posted.

\vspace{0.1in}
\noindent
A contact may be {\em retired} for one of two reasons. (1) It may have
been a long time since its last position update, longer than the
threshold set by \pvar{contact\_max\_age}, which has a default of 600
seconds. (2) Or it may now be far away, beyond the range set by the
parameter \pvar{reject\_range} which has a default value of 2000
meters. If it is retired, the contact is reclaimed from the two
tables, and is placed on the retirement list.  This list also has a
maximum size, pruned first-in-first-out.


%================================================================
\subsection{Publications about Internal Status}
\label{sec_cmgr_status}

There are several MOOS variables published by the contact manager
that reflect some of the information in the above internal data
structures:

\begin{packed_itemize}
\item \mvar{CONTACTS\_LIST}: A comma-separated list of names for all
  contacts in the contact status table.
\item \mvar{CONTACTS\_ALERTED}: A list of contacts that are currently
  in the alerted state, per alert ID.
\item \mvar{CONTACTS\_COUNT}: The number of currently alerted contacts.
\item \mvar{CONTACTS\_UNALERTED}: A list of contacts that are
  currently in the unalerted state, per alert ID.
\item \mvar{CONTACTS\_RETIRED}: A comma-separated list of names for
  retired contacts.
\item \mvar{CONTACTS\_RECAP}: A summary, name, range and report age,
  for contacts in the contact status table.
\end{packed_itemize}

\noindent
Here are some examples:

\prevgreen
\begin{verbatim}
   CONTACTS_LIST      = delta,gus,charlie,henry
   CONTACTS_ALERTED   = (delta,avd)(charlie,avd)
   CONTACTS_COUNT     = 2
   CONTACTS_UNALERTED = (gus,avd)(henry,avd)
   CONTACTS_RETIRED   = bravo,foxtrot,kilroy
   CONTACTS_RECAP     = name=ike,age=11.3,range=193.1 # name=gus,age=0.7,range=48.2 # 
                        name=charlie,age=1.9,range=73.1 # name=henry,age=4.0,range=18.2
\end{verbatim}
\postverb

\vspace{0.1in}
\noindent
All variables are only published when changed.  The
\mvar{CONTACTS\_RECAP} variable will very likely change content on
each iteration since it contains the numerical ranges to moving
contacts from a moving ownship. If published and logged on every
iteration this will generate large amounts of perhaps unnecessary log
data. By default, this variable will publish once per second, but this
is changeable with the \pvar{contacts\_recap\_interval}. It may be set
to any non-negative value, or the string \var{"off"} to turn it off
completely. Of course if log file size is a concern, the frequency of
logging can always be adjusted in the \app{pLogger} settings.

\vspace{0.1in}
\noindent
A fair question might be - why retain in memory any information
related to contacts that currently do not have an active alert. As
will be discussed in Section \ref{sec_cmgr_closest} and Section
\ref{sec_cmgr_clusters}, the contact manager generates other reports
that may include contacts that may not presently warrant an alert. 


%=====================================================================
\newpage
\section{Contact Manager Coordination with the Helm}
%=====================================================================
\label{sec_cmgr_helm_coord}

The contact manager was designed primarily to support the IvP Helm,
but also designed in a manner to make as few assumptions as possible
about the helm implementation. The helm is a contact manager user, a
consumer of contact manager alerts. It is the helm's responsibility to
submit registrations to the contact manager for alerts, with the alert
registration defining the conditions and format for the desired alert.
The contact manager will blindly abide, and will generate alerts of
the requested format, when the requested range conditions and filter
conditions (if any) are met. This process is described in more detail
in this section. More details on helm behavior templates, updates and
behavior spawning can be found in the helm documentation.


%=====================================================================
\subsection{Helm Registration for Alerts}
\label{sec_cmgr_helm_reg}

When the helm starts up, it populates a set of behaviors. Some
behaviors are static, created at launch time, and persist throughout
the mission. Other behaviors are configured as templates, placeholders
for perhaps many future behaviors of that type. This is the case for
contact-related behaviors such as collision avoidance.  As Figure
\ref{fig_helm_start} shows below, the behavior template is implemented
to post an alert registration message upon startup.

\vspace{0.1in}
\begin{figure}[H]
  \centering
  \includegraphics[width=0.75\textwidth]{figures/bcm_helm_start.png}
  \caption{{\bf Alert Registration}: When the helm starts, contact-related
    behaviors, configured as templates, will post a registration to the
    contact manager. The registration contains information about the desired
    format and threshold criteria for future alerts.}
  \label{fig_helm_start}
\end{figure}
\vspace{0.1in}


\noindent
The alert registration format was discussed previously in Section
\ref{sec_cmgr_alert_mconfig}. For helm contact-related behaviors, the
\var{on\_flag} specifies a posting to the MOOS variable named in the
behavior's \bvar{updates} parameter configuration, e.g.,
\mvar{CONTACT\_INFO} in the below example.

\prevgreen
\begin{verbatim}
BCM_ALERT_REQUEST = id=avoid, alert_range=20, cpa_range=40, ignore_type=cargo \
                    on_flag=CONTACT_INFO=name=avd_$[VNAME] # contact=$[VNAME]
                    
\end{verbatim}
\postverb

\vspace{0.1in}
\noindent
The rest of the alert request specifies the alert and cpa range values
so the contact manager knows the conditions this behavior template is
expecting to receive alert postings, i.e., publications to
\mvar{CONTACT\_INFO} in this case. After this start up process, the
helm, with respect to this behavior is in listen-and-wait mode, until
an alert is received.



%=====================================================================
\subsection{Helm Action Upon Receiving an Alert}


Figure \ref{fig_helm_spawn} below depicts alert sequence of
events. First a contact crosses a range threshold relative to
ownship. Second, this is detected and noted in the contact
manager. This results in an alert posting of a format that a behavior
template in the helm is expecting. Finally the helm will spawn a
behavior dedicated exclusively to dealing with this contact.

\vspace{0.1in}
\begin{figure}[H]
  \centering
  \includegraphics[width=0.75\textwidth]{figures/bcm_helm_spawn.png}
  \caption{{\bf Alert to Spawning}: (1) A contact closes range to ownship,
    crossing a range threshold. (2) The contact manager makes note and changes
    the internal record associated with the contact. (3) An alert it generated
    and received by the helm. (4) The helm spawns a new contact-related behavior
    dedicated to this contact.}
  \label{fig_helm_spawn}
\end{figure}
\vspace{0.1in}

\noindent
The posting, following the \mvar{BCM\_ALERT\_REQUEST} example above, will have
the following form:

\prevgreen
\begin{verbatim}
  CONTACT_INFO=name=avd_$[VNAME] # contact=$[VNAME]
\end{verbatim}
\postverb

\noindent
The contact manager will use the contact name, e.g., \var{vessel\_23},
to expand the \var{\$[VNAME]} macros and the posting will look more
like:

\prevgreen
\begin{verbatim}
  CONTACT_INFO=name=avd_vessel_023 # contact=vessel_023
\end{verbatim}
\postverb

\noindent
See the helm documentation for more information on behavior updates
and template behaviors. In short, the helm will first check to see if
a behavior already exists that (1) is listening for parameter updates
through the MOOS variable \mvar{CONTACT\_INFO}, and (2) has the unique
name of \var{avd\_vessel\_23}. If so, it would regard the remainder of
the \mvar{CONTACT\_INFO} message as an update to the existing
behavior.  If a behavior by that name does not already exist, and
there is a behavior template that is listening for parameter updates on
the MOOS variable \mvar{CONTACT\_INFO}, a new behavior is then spawned
with the name \var{avd\_vessel\_023}, and the remainder of the
\mvar{CONTACT\_INFO} message is treated as an update to this newly
spawned behavior.


%=====================================================================
\subsection{Helm Action Upon Alert Retirement}
\label{sec_cmgr_retired}

When a contact opens range to ownship sufficiently far, beyond the
\var{cpa\_range}, the contact manager will alter its internal state
associated with the contact/alert pair. See the alert status table in
Figure \ref{fig_pcm_data}. From the helm's perspective no further
action is required. Contact-related behaviors are implemented to {\em
  complete}, and be promptly deleted by the helm, once the contact
goes beyond a certain range. As you might guess, this range is
automatically set to be equal to the \var{cpa\_range} the contact
manager uses. So, roughly at the same time, the contact manager
denotes the alert for this contact to be {\em off}, and the helm lets
the contact behavior complete and be removed from memory. If the
contact and ownship should later cross paths again, the contact
manager would simply generate a new alert and the helm would spawn a
new behavior.

\vspace{0.1in}
\noindent
An example mission is available for showing the use of the contact
manager and its coordination with the helm to spawn behaviors for
collision avoidance. This mission is \var{m2\_berta} and is described
in the IvP Helm documentation.  In this mission two vehicles are
configured to repeatedly go in and out of collision avoidance range,
and the contact manager repeatedly posts alerts that result in the
spawning of a collision avoidance behavior in the helm. Each time the
vehicle goes out of range, the behavior completes and dies off from
the helm and is declared to the contact manager to be resolved.




%=====================================================================
\section{Exclusion Filters}
%=====================================================================
\label{sec_cmgr_filters}

In certain missions it is desirable to treat different contacts
differently. This may be based on the contact platform type, e.g.,
sailboats versus motorboats. It may be based on contact group
affiliation, e.g., red team versus blue team. It may be based on
contact location in the operation area, or perhaps simply relative
to ownship. One example that comes up frequently in field trials
is the desire for the robot to ignore the nearby test boat holding
the test operators.

\vspace{0.1in}
\noindent
There are a number of options for configuring the contact manager to
achieve the desired effect. In all cases, the configuration may be
done at the alert level, or at the contact manager level. At the
contact manager level, one may simply want to ignore all sailboats. At
the alert level it's also possible that the helm may have one
collision avoidance behavior configured and tuned for motorboats and
should ignore sailboats, and another behavior configured and tuned for
sailboats and should ignore motorboats.

\vspace{0.1in}
\noindent
Filters are also generally of a {\em match} type or an {\em ignore}
type. For example the contact manager may be configured to ignore all
sailboats by specifying an ignore filter based on sailboats. Or it may
be configured to only regard sailboats by setting a match filter for
sailboats. If multiple ignore filters are provided, a contact will be
ignored if any one ignore filter applies to the contact. If multiple
match filters are provided, a contact will be ignored only if all
match filters do not apply to the contact. If any criteria fail, the
contact will be ignored. For example, for a given sailboat, if
sailboats are explicitly named in a match filter, but also named in an
ignore filter, it will be ignored.

%=====================================================================
\subsection{Exclusion Filters Based on Contact Name, Type or Group}
\label{sec_cmgr_tgfilter}

Name, type and group filters are available at the contact manager
level with the following \app{pContactMgrV20} configuration
parameters:

\begin{packed_itemize}
\item \pvar{match\_name}: A comma-separated list of match names
\item \pvar{match\_group}: A comma-separated list of match groups
\item \pvar{match\_type}: A comma-separated list of match types
\item \pvar{ignore\_name}: A comma-separated list of names to ignore
\item \pvar{ignore\_group}: A comma-separated list of groups to ignore
\item \pvar{ignore\_type}: A comma-separated list of types to ignore
\end{packed_itemize}

\noindent
Here are some examples:

\prevblue
\begin{verbatim}
 match_name   =  henry
 match_group  =  blue_team
 match_type   =  motor_boat, crew_shell
 ignore_name  =  abe,ben, cal
 ignore_group =  red_team, work_boat
 ignore_type  =  sail_boat
\end{verbatim}
\postverb

\noindent
If a contact survives the filters at the contact manager level, it
still must survive any filters that may have been declared at the
individual alert level. The \var{match\_group}, \var{match\_type},
\var{ignore\_group}, and \var{ignore\_type} components work the same,
but are embedded in an alert configuration. As a \app{pContactMgrV20}
configuration parameter, it may look like:

\prevblue
\begin{verbatim}
  alert = id=K8, on_flag=SAY_MOOS=alarm, off_flag=SAY_MOOS=ok, ignore_name=hal   \
          alert_range=20, cpa_range=30, match_group=blue_team
\end{verbatim}
\postverb

\noindent
As an alert configured by a mail request to the contact manager, it
may look like:

\prevgreen
\begin{verbatim}
BCM_ALERT_REQUEST = id=k8, onflag=SAY_MOOS=alert, alert_range=20, cpa_range=40, \
                    match_group=blue_team
\end{verbatim}
\postverb

\noindent
If a contact does not report its type information, it may be rejected
if (a) there is at least one \pvar{ignore\_type} specified, {\em and}, (2)
the contact manager configuration parameter \pvar{strict\_ignore} is
set to \var{true}, which is the default value. The same holds true
if the contact has missing group information.



%=====================================================================
\subsection{Exclusion Filters Based on Contact Position Relative to a Region}
\label{sec_cmgr_rfilter}

Like the group and type filters, region filters are available at the
contact manager level with the following \app{pContactMgrV20}
configuration parameters:

\begin{packed_itemize}
\item \pvar{match\_region}: A convex polygon
\item \pvar{ignore\_region}: A convex polygon
\end{packed_itemize}

\noindent
Multiple regions of each kind may be specified. These regions may be
contiguous, overlapping or non-overlapping. Thus non-convex regions
can be specified by splitting into a set of convex regions.  For match
regions, the contact must be in at least one region or else it is
filtered out. For ignore regions, if the contact is any one (or more)
regions, it will be filtered out. If the contact fails according to
any kind filter, it fails overall.  Here are some examples:

\prevblue
\begin{verbatim}
 match_region  =  pts={10,-40:-50,-80:-30,-140:50,-100}
 ignore_ignore =  pts={50,-60:80,-70:120,-110:100,-150:60,-160:30,-110}
\end{verbatim}
\postverb

\noindent
If a contact survives the region filters at the contact manager level,
it still must survive any filters that may have been declared at the
individual alert level. The \var{match\_region}, and
\var{ignore\_region} components work the same, but are embedded in an
alert configuration. As a \app{pContactMgrV20} configuration
parameter, it may look like:

\prevblue
\begin{verbatim}
  alert = id=K8, on_flag=SAY_MOOS=alarm, off_flag=SAY_MOOS=ok,   \
          alert_range=20, cpa_range=30, match_group=blue_team    \
          match_region=pts={10,-40:-50,-80:-30,-140:50,-100}
\end{verbatim}
\postverb

\noindent
As an alert configured by a mail request to the contact manager, it
may look like:

\prevgreen
\begin{verbatim}
BCM_ALERT_REQUEST = id=k8, onflag=SAY_MOOS=alert, alert_range=20, cpa_range=40, \
                    match_region=pts={10,-40:-50,-80:-30,-140:50,-100}
\end{verbatim}
\postverb

\noindent
Note: Whereas type and group information tend not to change for a contact
during operation, its position in or out of a region may very well change.
If a contact that was previously being track, with an entry in memory, fails
a region filter, it is also wiped from memory in the contact manager. This
is to prevent contact information from becoming stale in memory.

%=====================================================================
\subsection{Exclusion Filters Based on Contact Range to Ownship}
\label{sec_cmgr_reject}

Last but not least, the simplest exclusion filter is to ignore any
contact substantially far from ownship.  Using the
\pvar{reject\_range} parameter this range can be set from the
configuration block of \app{pContactMgrV20}:

\prevblue
\begin{verbatim}
  reject_range = 2000
\end{verbatim}
\postverb

\noindent
The default value is 2000 meters. To disable this filter, either set
it to a very large value, or give it the string value
\var{"off"}. Keep in mind that the \pvar{reject\_range} serves a
second purpose, as discussed in Section \ref{sec_cmgr_data_struct}, as
a threshold for retiring a contact from the contact manager's internal
data structures. Retiring occurs if either (a) the contact range
exceeds the \pvar{reject\_range}, or (b) if contact reports are stale
beyond a certain time. By turning off the \pvar{reject\_range},
contact retirement can only be caused by staleness. Presently there
are no warnings produced if the \pvar{reject\_range} is lower than any
of the alert ranges. This check will likely be added in future
releases.

%=====================================================================
\section{Additional Contact Manager Reports}
%=====================================================================

%=====================================================================
\subsection{Closest Contact Reports}
\label{sec_cmgr_closest}

The contact manager will publish information about the contact
currently with the closest range to ownship. It will publish four
variables, \mvar{CONTACT\_CLOSEST} naming the vehicle that is closest,
\mvar{CONTACT\_CLOSEST\_TIME} indicating the time at which the named
contact became the closest contact, \mvar{CONTACT\_CLOSEST\_RANGE}
indicating the actual current range to the closest contact, and
\mvar{CONTACT\_RANGES} with an ordered list of ranges for all known
contacts. For example:

\prevgreen
\begin{verbatim}
   CONTACT_CLOSEST = "vessel_0971"
   CONTACT_CLOSEST_TIME = 7725262005.34
   CONTACT_CLOSEST_RANGE = 48.32
   CONTACT_RANGES = 48.32,56.3,112.08
\end{verbatim}
\postverb

\noindent
The first two variables above in practice will not change very often,
perhaps on the order of once per several seconds. The contact range
however will likely change on every iteration. While negligible in
terms of MOOS bandwidth, it may be annoying in terms of logged data,
so it can be configured to be off, by setting the parameter
\pvar{post\_closest\_range=false}. The same is true for the variable
\mvar{CONTACT\_RANGES}, which can be disabled by setting
\pvar{post\_all\_ranges=false}.  The default value for both is
true. The rate of data logged can also always be adjusted in the
\app{pLogger} configuration.

%=====================================================================
\subsection{Customizable Contact Reports Based on a Range Threshold}
\label{sec_cmgr_clusters}

The contact manager may optionally be configured to produce
customizable contact reports based on a range threshold. These reports
are simply a list of contacts. A subscriber to the contact manager
could otherwise glean this information via the \mvar{CONTACTS\_RECAP}
message which contains the full list of all contacts and ranges. The
customizable contact report described here is simply a more convenient
low-bandwidth alternative option.

%-----------------------------------------------------------------
\subsubsection{Format of the Contact Reports}

The format of the report is simply a comma-separated list of contacts.
For example:

\prevgreen
\begin{verbatim}
   CONTACTS_050 = vid_0027, vid_0197, vid_8645
\end{verbatim}
\postverb

\noindent
This report is published only when the list of contacts changes, so it
is considerably less bandwidth and easier to parse than the
\mvar{CONTACTS\_RECAP} message if the user simply wants to know which
contacts are currently within 50 meters. Note the variable name,
\mvar{CONTACTS\_050}, was chosen with the \mvar{\_050} suffix as an
easy reminder of the meaning of the list. This is just a useful
convention, and not enforced in any way. Selecting the name of the
variable, and range is described next.

%-----------------------------------------------------------------
\subsubsection{Requesting a Customized Contact Report}
\label{sec_cmgr_repreq}

The MOOS variable used for posting the report, and the range
threshold, are specified via the incoming MOOS variable
\mvar{BCM\_REPORT\_REQUEST}. For example:

\prevgreen
\begin{verbatim}
   BCM_REPORT_REQUEST = "var=CONTACTS_050, range=50, group=blueteam"
   BCM_REPORT_REQUEST = "var=CONTACTS_100, range=100"
   BCM_REPORT_REQUEST = "var=CONTACTS_200, range=200, type=sailboat, refresh=true"
\end{verbatim}
\postverb

\noindent
The order in the components in the string do not matter. It is
recommended to use a MOOS variable naming convention, such as
\mvar{CONTACTS\_050} above, to indicate the meaning of the report.
The variable name and range components are mandatory, while the group
and type components are optional. If the group or type component is
used, then a contact must satisfy all criteria to be included on the
contact list for that report. When the \var{refresh=true} component
is detected, a new report will be generated immediately, even if the
content of the report has not changed from a previous posting. 

%-----------------------------------------------------------------
\subsubsection{Timeout of Custom Reports}

While a valid custom report request will generate at least one custom
report immediately, the generation of further reports will cease after
some point in time unless further requests arrive. By default the
duration is 10 seconds, but may be changed to say 60 seconds with the
following parameter: \pvar{range\_report\_timeout=60}.






%================================================================
\section{Guarding Against Unbounded Memory Growth}
%================================================================
\label{sec_cmgr_growth}

In some systems it may be possible for the sensors or sensor system to
be generating many contacts, with unique IDs, over time. This problem
may arise simply from long duration (days+) missions in high contact
density situations. It may also be partly a result of a sensor that
easily loses track on a contact, generating several IDs for the same
contact as it approaches and ultimately departs the ownship vicinity.

\vspace{0.1in}
\noindent
The contact manager reasons about two types of data, tied to (a) active
contacts, and (b) retired contacts. The key data structures were shown
in Figure \ref{fig_pcm_data}. In this section, the contact manager
policies to guard against unbounded growth are described.


%================================================================
\subsection{Managing Retired Contacts}

As a contact is retired, it is moved to an internal list of retired
contacts, and this list is published as \mvar{CONTACTS\_RETIRED}. This
is useful for debugging and verifying contact manager operation. With
shore test missions having only a handful of contacts, this list can hold
all contacts ever retired. In more realistic missions, the list needs
to be managed.

\vspace{0.1in}
\noindent
As discussed in Section \ref{sec_cmgr_retired}, the newly retired
contact will stay on the \mvar{CONTACTS\_RETIRED} list until it is
pushed off, first-in first-out, when newer retired contacts are
added. The size of the list is set by the \pvar{max\_retired\_history}
parameter to be in the range $[1,50]$, ensuring that even this list
does not grow unbounded. The default is 5. The sequence of steps at
the end of each iteration of the contact manager is the following:

\begin{packed_itemize}
\item Add newly retired contacts to the retired list
\item Publish the retired list to \mvar{CONTACTS\_RETIRED}
\item If needed, prune the retired list to size \pvar{max\_retired\_history}
\end{packed_itemize}

\vspace{0.1in}
\noindent
This means that (a) the list published to \mvar{CONTACTS\_RETIRED} on
some iterations may be longer than \pvar{max\_retired\_history}, and
(b) every contact that is ever retired will show up on at least one
publication to \mvar{CONTACTS\_RETIRED}.

%================================================================
\subsection{Managing Active Contacts into Retirement}

To have an absolute guard against unbounded memory, the contact
manager has a strict upper limit on the number of contacts, configured
with the parameter, \pvar{max\_contacts}. This is set to 500 by
default. Although most systems have enough memory to probably handle
many thousands of contacts, 500 is probably generously high. The user
takes responsibility to set this value.

%----------------------------------------------------------------
\subsubsection{Normal Retirement}

As ownship and contacts pass each other, coming in and out range, or
comms and sensor range, contact retirement proceeds simply. 
At the end of each contact manager iteration, after receiving all
incoming contact updates and generating any applicable alerts or
status postings, the contact manager will retire any contact that
meets the following criteria:

\begin{packed_itemize}
\item The contact is beyond the range set by the parameter
  \pvar{reject\_range}, or

\item The timestamp of the contact's most recent report is stale
  beyond the time set by the parameter \pvar{max\_contact\_age}. 
\end{packed_itemize}

\vspace{0.1in}
\noindent
The default value for \pvar{reject\_range} is 2000 meters, and the
default value for \pvar{max\_contact\_age} is 60 seconds.  If, at this
point, the number of contacts is still greater than
\pvar{max\_contacts}, then contacts will need to be forced into
retirement, or {\em culled}.


%----------------------------------------------------------------
\subsubsection{Forced Retirement}

If normal retirement doesn't achieve the desired result of reducing
the total contacts to be less than or equal to \pvar{max\_contacts},
the following two additional steps will be taken:

\begin{packed_itemize}

\item A tighter maximum age is applied to each contact's
  staleness. Contacts with a timestamp larger than {\em half} the time
  set by the parameter of the \pvar{max\_contact\_age} will be
  removed.

\item Finally, if the above step leaves more culling to be done,
  contacts will be removed based range, until only the N closest
  contacts remain, where N is equal to \pvar{max\_contacts}.
\end{packed_itemize}
\vspace{0.1in}
\noindent


%----------------------------------------------------------------
\subsubsection{The Consequences of Forced Retirement}

A contact that has been forced into retirement may have been in
the alerted state with respect to one or more alert types. The forced
retirement means it did not have a normal transition from being
alerted to unalerted. If there was an \var{off\_flag} configured for
the alert, it will not get posted as normal. This should be considered
when/if using an \var{off\_flag}.

\vspace{0.1in}
\noindent
If a culled contact was in an alerted state for one or more alert
types, it might reappear a short time later as the contact manager
again receives information about this contact. In fact, if the contact
happens to be the (N+1)th contact in terms of range, it conceivably
could reappear and be culled on successive iterations. What are the
consequences of this in terms of alerts? The alert requests used by
the contact-related behaviors are designed such that successive
identical alerts are harmlessly redundant.

\vspace{0.1in}
\noindent
For example, consider the \var{on\_flag} from the earlier example:

\prevgreen
\begin{verbatim}
  CONTACT_INFO=name=avd_vessel_023 # contact=vessel_02
\end{verbatim}
\postverb

\vspace{0.1in}
\noindent
If a contact behavior did not exist, one would be spawned as
normal. If one had already been spawned, the helm would direct this
update to that behavior (re)setting the \var{name} and \var{contact}
parameters to the same value as before. In either case the
regeneration of the alert is either doing its job or is harmless.

\vspace{0.1in}
\noindent
A culled contact may however affect the accuracy of customized range
reports. If the user has asked to be notified of all contacts within
say 10,000 meters, but there are more than \pvar{max\_contact} vessels
within this range, then the range report may not be accurate.

%================================================================
\section{Disabling and Re-enabling Contacts}
%================================================================
\label{sec_disable}

Note: This feature was introduce after Release 24.8 for the following
release. 

\vspace{0.1in}
\noindent
In certain USV applications, especially with an operator in the loop
either on-board or remotely, contacts arrive in the contact manager
that may be identified as being of no risk for collision. In these
cases, the operator may wish to communicate to the autonomy system,
that no behaviors should be spawned for the contact, i.e., the contact
should be {\em disabled}. Likewise the operator may change their mind
and may subsequently request that a contact be {\em enabled} or
re-enabled.

\vspace{0.1in}
\noindent
This augmentation to contact manager is mostly implemented through
changes to the IvP Helm and behaviors. The contact manager is simply
one way to initiate the disabling or enabling of a behavior. In the
below, first the mods to the helm and behaviors are described, followed
by the manner in which the contact manager can be used for this
purpose.

%================================================================
\subsection{The Helm Role in Disabling and Enabling Behaviors}
\label{sec_helm_disable}

A new state, the {\em disabled} state, was added added generally to
IvP behaviors. When a behavior is disabled, it will simple not
participate in the helm. A disabled behavior is not deleted from the
helm, in case there is a subsequent request to re-enable the behavior.
By default a behavior cannot be disabled. Only certain contact
behaviors can be disabled. For now, these are only the collision
avoidance behaviors. To allow a behavior to be disabled, the below
configuration parameter is used:

\vspace{0.1in}
\noindent
\bvar{can\_disable = true}

\vspace{0.1in}
\noindent
If a helm behavior is not designed to allow it to be disabled, the above
setting will produce a helm configuration warning. 

\vspace{0.1in}
\noindent
The helm registers for the variable \mvar{BHV\_ABLE\_FILTER}, which can
contain messages like the following:

\vspace{0.1in}
\begin{consoleverb}
  BHV_ABLE_FILTER = action=disable, contact=ID345
  BHV_ABLE_FILTER = action=enable, contact=ID345
  BHV_ABLE_FILTER = action=disable, bhv_type=AvoidCollision
  BHV_ABLE_FILTER = action=disable, contact=ID345, bhv_type=AvoidCollision
  BHV_ABLE_FILTER = action=disable, contact=ID345, gen_type=safety
\end{consoleverb}
\vspace{0.1in}

\noindent
In the first case, simply the contact ID is given. This will match to
a behavior with the name \var{foo\_ID345}. Note, this will also apply
to behavior a behavior named \var{bar\_ID345}, as with any other
behavior associated with a given contact.  In the second case, the
action is to (re-enable) the same behavior. In the third case, the
\var{AvoidCollision} behavior will be disabled for all such behaviors
for all contacts. In the fourth case, the \var{AvoidCollision} behavior
will be disabled only if contact name ends in \var{ID345}. In the
fifth case, all safety behaviors will be disabled if the contact ends
in \var{ID345}.

\vspace{0.1in}
\noindent
The helm stores an ordered list of filter messages, based on time of
arrival.  On each iteration, this ordered list is applied to all
instantiated behaviors.  Applying a disable message to a behavior that
is already disabled, has no effect. But by applying the whole recent
list to all behaviors on each iteration in ensures that disable
requests that arrive in the helm before a behavior is spawned, will be
applied as soon as the behavior is spawned.

%================================================================
\subsection{The Contact Manager Role in Disabling Contact/Behaviors}
\label{sec_cmgr_disable}

The contact manager can broker disabling and (re)enabling helm behaviors first
by naming a MOOS variable for receiving such requests:

\vspace{0.1in}
\noindent
\pvar{disable\_var = XYZ\_DISABLE\_TARGET}

\vspace{0.1in}
\noindent
If no variable is configured as above, the contact manager will not be
able to receive requests for disabling. Note also the subtle
difference between the two terms:

\begin{packed_itemize}
\item {\em disabling a contact}: this implies disabling all
  disableable helm behaviors associated with a given contact. 
\item {\em disabling a behavior}: this implies disabling a particular
  disableable helm behavior.
\end{packed_itemize}

\vspace{0.1in}
\noindent
In practice the two are equivalent, since typically there is only one
disableable (collision avoidance) behavior configured for the helm.
This may not be true when/if other contact related behaviors are
augmented to allow disabling.

%----------------------------------------------------------------
\subsubsection{Simple Disabling by Contact ID}

The simplest way to use the contact manager to disable a behavior
is to send mail to the \pvar{disable\_var} with the contact ID. If the
ID is, for example, \var{ID345}, and the \pvar{disable\_var} is
\pvar{XYZ\_DISABLE\_TARGET}, then any app making the following post
will do

\vspace{0.1in}
\noindent
\mvar{XYZ\_DISABLE\_TARGET = ID345}

\vspace{0.1in}
\noindent
This result in the contact manager will be to publish the message the
helm needs to receive for the desired effect.

\vspace{0.1in}
\noindent
\mvar{BHV\_ABLE\_FILTER = action=disable, contact=ID345}

\vspace{0.1in}
\noindent
Note if the behavior in the helm has the name, say \var{avd\_ID345},
the match will be made. 

%----------------------------------------------------------------
\subsubsection{Simple Re-Enabling by Contact ID}
\label{sec_cmgr_enable}

The simplest way to use the contact manager to (re)enable a behavior
is to send mail to the \pvar{enable\_var} with the contact ID. If the
ID is, for example, \var{ID345}, and the \pvar{enable\_var} is
\pvar{XYZ\_REENABLE\_TARGET}, then any app making the following post
will do

\vspace{0.1in}
\noindent
\mvar{XYZ\_REENABLE\_TARGET = ID345}

\vspace{0.1in}
\noindent
This result in the contact manager will be to publish the message the
helm needs to receive for the desired effect.

\vspace{0.1in}
\noindent
\mvar{BHV\_ABLE\_FILTER = action=enable, contact=ID345}

%----------------------------------------------------------------
\subsubsection{Precision Disabling by Contact ID and Behavior Type}

If the contact manager user wishes to be more precise about exactly
which behavior to disable, then following message should be used:

\vspace{0.1in}
\noindent
\mvar{XYZ\_DISABLE\_TARGET = action=disable, contact=ID345}

\vspace{0.1in}
\noindent
This format follows the format used by the helm for input expected
on the \mvar{BHV\_ABLE\_FILTER}. Essentially, if the contact manager
sees a disable message in the form of something other than a simple
contact ID, then it will simply pass through the message to the
helm in the format expected by the helm.

%----------------------------------------------------------------
\subsubsection{Disable and Enable History Held by the Contact Manager}

The contact manager keeps an ordered list of disabled and enabled
contact IDs. This allows the contact manager to know (a) the most
recently disabled contact ID, (b) the most recently enabled contact
ID, and (c) the total disabled contacts. 

%----------------------------------------------------------------
\subsubsection{Disable/Enable Events, Flags and Macros}
\label{sec_cmgr_edflags}

There are three supported event flags tied to the disabling or
enabling a contact:

\begin{packed_itemize}
\item The \pvar{able\_flag} is posted whenever a contact is enabled or
  disabled. 
\item The \pvar{disable\_flag} is posted whenever a contact is disabled.
\item The \pvar{enable\_flag} is posted whenever a contact is enabled.
\end{packed_itemize}

\vspace{0.1in}
\noindent
Like most other flags in other apps and behaviors, the value of the flag
is a MOOS variable and value. The value component can contain anything
the user wants. The following macros are also supported in the
value part of the flag:

\begin{packed_itemize}
\item \var{\$[RECENT\_DISABLE]}: The name of the most recently
  disabled contact. Or \var{"none"} if no contact has been disabled.
\item \var{\$[RECENT\_ENABLE]}: The name of the most recently
  enabled contact. Or \var{"none"} if no contact has been (re)enabled.
\item \var{\$[TOTAL\_DISABLED]}: The total number of currently disabled
  contacts. 
\item \var{\$[ALL\_DISABLED]}: A comma-separated list of all currently
  disabled contacts, or \var{"none"} if no contacts are disabled.
\end{packed_itemize}

\noindent
Note: the macros described in Section \ref{sec_cmgr_flag_macros}, for
use in the \pvar{on\_flag} and \pvar{off\_flag}, are not available
when posting the \pvar{able\_flag}, \pvar{disable\_flag}, or
\pvar{enable\_flag}.


%================================================================
\subsection{Early Warnings}
\label{sec_cmgr_ewarn}

An {\em early warning} is an event about a contact that can be
configured to post a flag to bring the contact to the attention of an
operator. Presumably the early warning is generated with enough time
for the operator to have the chance to disable a contact if they wish.
The warning is configured with a few optional parameters, with the first
being the amount of time, in seconds, at which a warning event should
happen:

\vspace{0.1in}
\noindent
\pvar{early\_warning\_time = 10}

\vspace{0.1in}
\noindent
The time interval, 10 seconds in this example, is the amount of time
before a contact reaches a range to ownship at which an alert would
otherwise be posted. For example, if a collision avoidance behavior in
the helm has arranged to receive an alert at 40 meters, the early
warning will event will happen 10 seconds before reaching the range of
40 meters.  The {\em rate of closure}, based on both ownship and
contact position, speed and relative bearing, is applied to the early
warning time and current range, to ensure that the warning is roughly
10 seconds prior to breaching the alert range, assuming both ownship
and contact remain on their current trajectories. If ownship and/or
contact change their speed or headings, the rate of closure is
automatically updated and the early warning event will shift
correspondingly.

\vspace{0.1in}
\noindent
The event that occurs with the early warning is configurable by the
user with another parameter for \app{pContactMgrV20}, using the following
event flag parameter:

\vspace{0.1in}
\noindent
\pvar{early\_warning\_flag = MOOS\_VAR = value}

\vspace{0.1in}
\noindent
For example:

\vspace{0.1in}
\noindent
\pvar{early\_warning\_flag = CMGR\_WARNING = Warning=\$[CONTACT], at \$[RNG], at \$[UTC]}

\vspace{0.1in}
\noindent
Like most other flags in other apps and behaviors, the value of the flag
is a MOOS variable and value. The value component can contain anything
the user wants. The following macros are also supported in the
value part of the early warning flags:

\begin{packed_itemize}
\item \var{\$[CONTACT]}: The name of contact. 
\item \var{\$[RNG]}: The range to the contact based on the last node report
  received from the contact, or about the contact.
\item \var{\$[RNG\_EXT]}: The extrapolated range to the contact based
  on the last node report received from the contact, or about the
  contact, and the time since the report was received. 
\item \var{\$[UTC]}: The current UTC time, in seconds.
\item \var{\$[CPA]}: The closest of approach to the contact for this encounter.
  Mostly useful in a \pvar{cease\_warning\_flag}.
\item \var{\$[ROC]}: The current rate of closure to the contact based on ownship
  and contact position, speed and relative bearing.
\end{packed_itemize}

\noindent
Note: the macros described in Section \ref{sec_cmgr_flag_macros}, for
use in the \pvar{on\_flag} and \pvar{off\_flag}, are not available
when posting the \pvar{able\_flag}, \pvar{disable\_flag}, or
\pvar{enable\_flag}, and the macros defined in Section
\ref{sec_cmgr_edflags} are not available when posting with
\pvar{early\_warning\_flag} or \pvar{cease\_warning\_flag}.

\vspace{0.1in}
\noindent
When a contact generates an early warning, the range at that
moment is noted and stored relative to the contact. When or if the
contact passes and opens range to ownship and once again beyond that
stored range, a \pvar{cease\_warning\_flag} is published. To guard
against thrashing, the cease warning range is \var{1.05} times the
stored range.  A warning flag may look like:

\vspace{0.1in}
\noindent
\pvar{cease\_warning\_flag = CMGR\_WARNING = off}

\vspace{0.1in}
\noindent
Or, for example, if there is a desire to keep track of the CPA for all
encounters, the following could be added. There is no limit to the
number of warning flags that can be configured.

\vspace{0.1in}
\noindent
\pvar{cease\_warning\_flag = ENCOUNTER\_CPA = \$[CPA]}

\vspace{0.1in}
\noindent
Finally, an early warning range visual can be enabled. This is a viewable circle
with ownship at the center, rendering the range at which a contact will trigger
an early warning. To enable this:

\vspace{0.1in}
\noindent
\pvar{early\_warning\_radii = true}  \newline
\pvar{ewarn\_radii\_color = yellow}

\vspace{0.1in}
\noindent
The default for the former is \var{false}, and the default for the
latter is \var{"yellow"}.


%================================================================
\section{Deferring to Earth Coordinates over Local Coordinates}
%================================================================
\label{sec_cmgr_latlon}

Incoming node reports contain the position information of the contact
and may be specified in either local x-y coordinates, or earth
latitude longitude coordinates or both. By default
\app{pContactMgrV20} uses the local coordinates for calculations and
the earth coordinates are merely redundant. It may instead be
configured, with the \pvar{contact\_local\_coords} parameter, to have
its local coordinates set from the earth coordinates if the local
coordinates are missing:

\prevblue
\begin{verbatim}
  contact_local_coords = lazy_lat_lon
\end{verbatim}
\postverb

\noindent
It may also be configured to always use the earth coordinates, even 
if the local coordinates are set:

\prevblue
\begin{verbatim}
  contact_local_coords = force_lat_lon
\end{verbatim}
\postverb

\noindent
The default setting is \var{verbatim}, meaning no action is taken to
convert coordinates. If either of the other two above settings are
used, the latitude and longitude coordinates of the local datum, or
\var{(0,0)} point must be specified in the MOOS mission file, with
\pvar{LatOrigin} and \pvar{LongOrigin} configuration parameters. (They
are typically present in all mission files anyway.)



%================================================================
\section{Terminal and AppCast Output}
%================================================================
\label{sec_cmgr_appcast}

The status of the contact manager may be monitored from from an open
console window where \app{pContactMgrV20} is launched. Example
output is shown below in Listing \ref{lst_cmgr_appcast}.

\vspace{0.2in}
\begin{listing}{Example pContactMgrV20 terminal and appcast output}
\label{lst_cmgr_appcast}
\footnotesize
\begin{verbatim}
 1  ===================================================================
 2  pContactMgrV20 abe                                         0/0(377)
 3  ===================================================================
 4  X/Y from Lat/Lon:   false
 5  Contact Max Age:    3600
 6  Reject Range:       2000
 7  BCM_ALERT_REQUESTs: 2
 8  DisplayRadii:       false
 9  
10  Alert Configurations (1):
11  ---------------------
12  1 ID: avdcol_
13    Alert Ranges: 35/45
14    Source: pHelmIvP
15    OnFlag: CONTACT_INFO=name=$[VNAME] # contact=$[VNAME]
16  
17  Alert Status Summary: 
18  ----------------------
19         List: ben,cal,deb
20      Alerted: (deb,avdcol_)
21      Retired: 
22        Recap: vname=ben,range=82.72,age=0.83 # vname=cal,range=73.42,age=0.66 # 
23               vname=deb,range=26.32,age=0.81
24  
25  Contact Status Summary:
26  -----------------------
27  Contact     Range    Alerts    Alerts
28             Actual    Total     Active
29  -------    ------    ------    ------
30  ben          82.7    0         0     
31  cal          73.4    1         0     
32  deb          26.3    3         1     
33  
34  Custom Contact Reports:
35  -----------------------
36  VarName     Range     Group     VType     Contacts
37  -------     -----     -----     -----     --------
38  
39  ===================================================================
40  Most Recent Events (4):
41  ===================================================================
42  [179.51]: CONTACT_INFO=name=deb # contact=deb
43  [72.09]: CONTACT_INFO=name=deb # contact=deb
44  [71.06]: CONTACT_INFO=name=deb # contact=deb
45  [33.44]: CONTACT_INFO=name=cal # contact=cal
\end{verbatim}
\end{listing}
\normalsize

\vspace{0.15in}
\noindent
On line 2, the \var{"0/0"} indicates there were no configuration warnings
and no run-time warnings (thus far). The \var{"(377)"} represents the 
iteration counter of \app{pContactMgrV20}. Line 4 indicates that contact
position in local coordinates is being derived directly from reported local
coordinates in incoming node reports (Section \ref{sec_cmgr_latlon}). Line 5
shows the maximum age of a contact report before the contact is dropped (Section
\ref{sec_cmgr_data_struct}). Line 6 indicates the contact range beyond which
it will be ignored (Section \ref{sec_cmgr_reject}). Line 7 indicates the number of
alert request messages that have been received (Section \ref{sec_cmgr_rfilter}).
Line 8 indicates whether visual circles are to be displayed showing the range
and cpa range for a named alert (Section \ref{sec_cmgr_visuals}).
In lines 10-15, the alerts configured by the mission file or incoming
requests are shown. If multiple alerts types are configured, they
would each be listed here separated by their alert id.

\vspace{0.1in}
\noindent
In lines 17-23, the alert status of the contact manager is
output. These five lines are equivalent to the content of the
\msvar{CONTACTS\_*} variables described in Section
\ref{sec_cmgr_status}.  The block beginning line 34 would show any
custom contact report configurations (Section \ref{sec_cmgr_clusters}),
but there are no custom reports in this example.  In lines 25-32, the
status and alert history for each known contact is shown.  Finally,
starting on line 42, a limited list of recent events is shown.  In
this example, four alerts are shown, three for the vehicle \var{deb},
and one for the vehicle \var{cal}. In this particular mission,
vehicles routinely proceed in and out of range to ownship, so
the helm has been alerted about \var{deb} three times.


%================================================================
\section{Configuration Parameters for pContactMgrV20}
%================================================================
%\index{pContactMgrV20!Configuration Parameters}
%\index{Configuration Parameters!pContactMgrV20}

The following parameters are defined for \app{pContactMgrV20}. A
more detailed description is provided in other parts of this
section. Parameters having default values are indicated so.

\vspace{0.15in}
\begin{listing}{Configuration Parameters for pContactMgrV20}
\label{lst_cmgr_params}
\renewcommand{\arraystretch}{1.1}
\begin{longtable}{rp{0.72\textwidth}} 

  \pvar{able\_flag}: &amp; A flag to be posted whenever a contact is
  disabled or (re)enabled. Section \ref{sec_cmgr_edflags}. \\

  \pvar{alert}: &amp; A description of a single alert. Section
  \ref{sec_cmgr_alert_config}. \\
  
  \psvar{alert\_range\_color}: &amp; The default color for
  rendering the alert range radius. Legal values: any color in Colors
  Appendix . The default is {\em gray70}. Section
  \ref{sec_cmgr_visuals}. \\

  \pvar{alert\_verbose}: &amp; If true, verbose debugging output will be
  published to the variable \mvar{ALERT\_VERBOSE}. The default is
  \var{false}. \\
  
  \pvar{cease\_warning\_flag}: &amp; A flag to be posted when or if an
  early warning event is configured and had been triggered, but is now
  no longer relevant. Section \ref{sec_cmgr_ewarn}. \\

  \pvar{contact\_local\_coords}: &amp; Determines if the local coordinates
  of incoming node reports are filled by translated latitude longitude
  coordinates. Legal values: \var{verbatim}, \var{lazy\_lat\_lon},
  \var{force\_lat\_lon}.  The default is \var{verbatim}, meaning no
  translation action is taken. Section \ref{sec_cmgr_latlon}.\\

  \pvar{contact\_max\_age}: &amp; Seconds between reports before a contact
  is retired and dropped from the list. Legal values: any non-negative
  number. The default is 600. Sections \ref{sec_cmgr_retired},
  and \ref{sec_cmgr_growth}. \\

  \pvar{cpa\_range\_color}: &amp; The default color for rendering
  the cpa range radius. Legal values: any color in the Colors
  Appendix. The default is {\em gray30}. Section
  \ref{sec_cmgr_visuals}.\\

  \pvar{decay}: &amp; An optional way of treating delays in between
  incoming contact reports. Legal values are comma-separated pair of
  numbers, e.g., \var{"15,30"}, where the first number represents the
  interval of time where the contact position will be extrapolated
  linearly into the future given its last known heading and speed.
  After 15 seconds, the contact speed used for extrapolation will
  linearly reduce to zero at 30 seconds. The default value is
  \var{"15,30"}. Extrapolation may be turned off by setting this
  value to \var{"0,0"}. \\

  \pvar{display\_radii}: &amp; If true, the two alert ranges are posted as
  viewable circles. Legal values: \var{true}, \var{false}. The default
  is \var{false}. \\

  \pvar{disable\_var}: &amp; The name of a MOOS variable for receiving
  requests for disabling contacts. If no variable is configured, the
  contact manager will not be able to receive requests for disabling.
  Section \ref{sec_cmgr_disable}. \\

  \pvar{disable\_flag}: &amp; A flag to be posted whenever a contact is
  disabled. Section \ref{sec_cmgr_edflags}. \\

  \pvar{display\_radii\_id}: &amp; If multiple alert IDs are configured,
  this parameter can be used to indicate which alert will have its
  range circles rendered when rendering is enabled. Section
  \ref{sec_cmgr_visuals}. \\

  \pvar{early\_warning\_flag}: &amp; A flag to be posted when or if an
  early warning event is configured. Section \ref{sec_cmgr_ewarn}. \\

  \pvar{early\_warning\_radii}: &amp; If \var{true}, a visual range circle
  is posted to convey the range at which an early warning will be
  triggered.  The default is \var{false}.  Section
  \ref{sec_cmgr_ewarn}. \\

  \pvar{early\_warning\_time}: &amp; The number of seconds, before a
  contact alert is generated, when an early warning event posting is
  made, if configured.  Section \ref{sec_cmgr_ewarn}. \\

  \pvar{enable\_var}: &amp; The name of a MOOS variable for receiving
  requests for enabling contacts. If no variable is configured, the
  contact manager will not be able to receive requests for enabling.
  Section \ref{sec_cmgr_disable}. \\

  \pvar{enable\_flag}: &amp; A flag to be posted whenever a contact is
  enabled. Section \ref{sec_cmgr_edflags}. \\

  \pvar{ewarn\_radii\_color}: &amp; The color of a range circle associated
  with a configured early warning. Section \ref{sec_cmgr_ewarn}. \\

  \pvar{ignore\_group}: &amp; A comma-separated list of contact groups to
  ignore, defined at the global contact manager level. Section
  \ref{sec_cmgr_tgfilter}. \\
  
  \pvar{ignore\_name}: &amp; A comma-separated list of contact names to
  ignore, defined at the global contact manager level. Section
  \ref{sec_cmgr_tgfilter}. \\
  
  \pvar{ignore\_region}: &amp; A convex polygon wherein contacts will be
  ignored, defined at the global contact manager level. Section
  \ref{sec_cmgr_rfilter}. \\

  \pvar{ignore\_type}: &amp; A comma-separated list of contact types to
  ignore, defined at the global contact manager level. Section
  \ref{sec_cmgr_tgfilter}. \\

  \pvar{match\_group}: &amp; A comma-separated list of contact groups to
  match, defined at the global contact manager level. Section
  \ref{sec_cmgr_tgfilter}. \\
  
  \pvar{match\_name}: &amp; A comma-separated list of contact names to
  match, defined at the global contact manager level. Section
  \ref{sec_cmgr_tgfilter}. \\
  
  \pvar{match\_region}: &amp; A convex polygon outside of which contacts
  will be ignored, defined at the global contact manager
  level. Section \ref{sec_cmgr_rfilter}. \\

  \pvar{match\_type}: &amp; A comma-separated list of contact types to
  match, defined at the global contact manager level. Section
  \ref{sec_cmgr_tgfilter}. \\

  \pvar{max\_retired\_hist}: &amp; Maximum amount of contacts held in the
  contact managers memory at any given time before increasingly more
  dire measures are taken to remove/retire contacts. Section
  \ref{sec_cmgr_growth}. \\

  \pvar{max\_retired\_hist}: &amp; Limit the number of contacts listed in
  the \mvar{CONTACTS\_RETIRED} list to this number.  The default is 5,
  and legal values are in the range $[1,50]$.  Regardless of this
  setting, all retired contacts will be included in a
  \mvar{CONTACTS\_RETIRED} posting at least once. (Section
  \ref{sec_cmgr_data_struct}). \\

  \pvar{post\_all\_ranges}: &amp; If true, the range to all contacts is
  posted in an ordered, comma-separated list. The default is
  \var{false}. Section \ref{sec_cmgr_closest}. \\

  \pvar{post\_closest\_range}: &amp; If true, the range to the closest
  contact is posted, rounded to the nearest meter. The default is
  \var{false}. Section \ref{sec_cmgr_closest}. \\

  \pvar{recap\_interval}: &amp; Sets a threshold number of seconds between
  successive postings of the \mvar{CONTACTS\_RECAP} variable.  This
  variable may be just too verbose for certain use cases, and if
  logged, can contribute to log file bloat. The default is one second.
  It can be shut off completely by setting it to string value
  \var{"off"}. Section \ref{sec_cmgr_status}. \\
  
  \pvar{reject\_range}: &amp; A range, in meters, beyond which new
  contacts will be ignored, and existing contacts will be dropped.
  This is one of the guards against unbounded memory growth, discussed
  in Section \ref{sec_cmgr_growth}.  The default value is 2000
  meters. \\

  \pvar{strict\_ignore}: &amp; if true, both group and type exclusion
  filtering will reject a contact if the contact is not reporting its
  group or type information and there are ignore filters. Section
  \ref{sec_cmgr_tgfilter}. \\


\end{longtable}
\end{listing}

%================================================================
\subsection{An Example MOOS Configuration Block}

To see an example MOOS configuration block, enter the following from
the command-line:

\vspace{0.15in}
\noindent
\begin{consoleverb}
 $ pContactMgrV20 --example or -e
\end{consoleverb}
\vspace{0.15in}

\noindent
This will show the output shown in Listing \ref{lst_cmgr_econfig} below.

\vspace{0.25in}
\begin{listing}{Example configuration of the pContactMgrV20 application}
\label{lst_cmgr_econfig}
\footnotesize
\begin{verbatim}

  1  =============================================================== 
  2  pContactMgrV20 Example MOOS Configuration                     
  3  =============================================================== 
  4                                                                 
  5  ProcessConfig = pContactMgrV20                                
  6  {                                                               
  7    AppTick   = 4                                                 
  8    CommsTick = 4                                                 
  9                                                                  
 10  // Alert configurations (one or more, keyed by id)            
 11  // Note: Alert config in this block is deprecated. Normally   
 12  // now configured dynamically via BCM_ALERT_REQUEST mail.     
 13  alert = id=say, on_flag=SAY_MOOS=hello                        
 14  alert = id=say, off_flag=SAY_MOOS=bye                         
 15  alert = id=say, alert_range=80, cpa_range=100                 
 16                                                                
 17  // Type and group info about ownship                          
 18  ownship_group = blue_team                                     
 19  ownship_type  = kayak                                         
 20                                                                
 21  // Global alert filters (providing nothing is fine)           
 22  ignore_name = henry,gilda                                     
 23  match_name  = abe, cal                                        
 24                                                                
 25  ignore_group = alpha                                          
 26  match_group  = bravo,gamma                                    
 27                                                                
 28  ignore_type = usv,uuv                                         
 29  match_type  = ship                                            
 30                                                                
 31  ignore_region = pts={60,-40:60,-160:150,-160:150,-40}         
 32  match_region  = pts={60,70:60,160:150,160:150,70}             
 33                                                                
 34  strict_ignore = true             // Default is true           
 35                                                                
 36  // Policy for retaining potential stale contacts              
 37  contact_max_age  = 60            //  Default is 60 secs.      
 38  max_retired_history = 5          //  Default is 5 contacts    
 39                                                                
 40  // Configuring other output                                   
 41  display_radii     = false        // Default is false          
 42  alert_verbose     = false        // Default is false          
 43  alert_range_color = color        // default is gray65         
 44                                                                
 45  // Policy for linear extrapolation of stale contacts          
 46  decay = 15,30                    // Default is 15,30 secs     
 47                                                                
 48  recap_interval       = 1         // Default is 1 sec          
 49  range_report_timeout = 10        // Default is 10 secs        
 50  range_report_maxsize = 20        // Default is 20 reports     
 51                                                                
 52  contact_local_coords = verbatim  // Default is verbatim       
 53  post_closest_range   = false     // Default is false          
 54  post_closest_relbng  = false     // Default is false          
 55  post_all_ranges      = false     // Default is false          
 56                                                                
 57  reject_range = 2000              // Default is 2000 meters    
 58  max_contacts = 500               // Default is 500            
 59  alert_verbose = false            // Default is false          
 60                                                                
 61  // 24.8.x support for disabling/enabling contacts             
 62  disable_var  = DISABLE_TARGET    // Default is null string    
 63  enable_var   = REENABLE_TARGET   // Default is null string    
 64  able_flag    = MOOS_VAR = val                                 
 65  disable_flag = MOOS_VAR = val                                 
 66  enable_flag  = MOOS_VAR = val                                 
 67                                                                
 68  // 24.8.x support for disabling/enabling contacts             
 69  early_warning_time  = 30        // Default is -1 (off)        
 70  early_warning_radii = true      // Default is false           
 71  ewarn_radii_color   = yellow    // Default is yellow          
 72                                                                
 73  early_warning_flag  = MOOS_VAR = val                          
 74  cease_warning_flag  = MOOS_VAR = val                          
 75                                                                
 76  app_logging = true               // Default is false          
 77                                                                
 78  hold_alerts_for_helm = true      // Default is false   
 79 
 80 }                  
\end{verbatim}
\end{listing}
\normalsize
  
%================================================================
\section{Publications and Subscriptions for pContactMgrV20}
%================================================================
%\index{pContactMgrV20!Publications and Subscriptions}
%\index{Publications and Subscriptions!pContactMgrV20}
\label{sec_cmgr_interface}

The interface for \app{pContactMgrV20}, in terms of publications and
subscriptions, is described below. This same information may also be
obtained from the terminal with:

\begin{consoleverb}
 $ pContactMgrV20 --interface or -i
\end{consoleverb}

%================================================================
\subsection{Variables Published by pContactMgrV20}
\label{sec_cmgr_pubs}

The primary output of \app{pContactMgrV20} to the MOOSDB is the set of
user-configured alerts, early warnings, or enable flags.  Other
variables are published on each iteration where a change is detected
on its value:

\begin{packed_itemize}[2]
\item \mvar{APPCAST}: Contains an appcast report identical to the
  terminal output. Appcasts are posted only after an appcast request
  is received from an appcast viewing utility. Section
  \ref{sec_cmgr_appcast}.

\item \mvar{ALERT\_VERBOSE}: Verbose or debugging output published
  to this variable if \pvar{alert\_verbose} is set to \var{true}.
  
\item \mvar{CONTACT\_CLOSEST}: Name of the closest contact. Section
  \ref{sec_cmgr_closest}.
  
\item \mvar{CONTACT\_CLOSEST\_TIME}: The time at which the closest
  contact became the closest contact. Section \ref{sec_cmgr_closest}.
  
\item \mvar{CONTACT\_CLOSEST\_RANGE}: The range of the closest
  contact. Section \ref{sec_cmgr_closest}.
  
\item \mvar{CONTACT\_MGR\_WARNING}: A warning message indicating
  possible mishandling of or missing data.

\item \mvar{CONTACT\_RANGES}: A comma-separated and ordered list of
  all contact ranges.  Section \ref{sec_cmgr_closest}.
  
\item \mvar{CONTACTS\_ALERTED}: A list of contacts for which alerts
  have been posted. Section \ref{sec_cmgr_status}.
  
\item \mvar{CONTACTS\_COUNT}: The number of contacts currently
  alerted.  Section \ref{sec_cmgr_status}.
  
\item \mvar{CONTACTS\_LIST}: A comma-separated list of contacts.
  Section \ref{sec_cmgr_status}.
  
\item \mvar{CONTACTS\_RECAP}: A comma-separated list of contact
  summaries.  Section \ref{sec_cmgr_status}.
  
\item \mvar{CONTACTS\_RETIRED}: A list of contacts removed due to the
  information staleness.  Section \ref{sec_cmgr_status}.

\item \mvar{CONTACTS\_UNALERTED}: A list of contacts for which alerts
  are pending, based on the range criteria.  Section
  \ref{sec_cmgr_status}.
    
\item \mvar{PCONTACTMGRV20\_PID}: The system process ID of the contact
  manager.

\item \mvar{VIEW\_CIRCLE}: A rendering of the alert ranges.
Section \ref{sec_cmgr_visuals}.

  
\end{packed_itemize}

\noindent
Some examples:
\prevgreen
\begin{verbatim}
   CONTACTS_LIST      = gus,joe,ken,kay
   CONTACTS_ALERTED   = gus,kay
   CONTACTS_UNALERTED = ken,joe
   CONTACTS_RETIRED   = bravo,foxtrot,kilroy
   CONTACTS_RECAP     = name=gus,age=7.3,range=13.1 # name=ken,age=0.7,range=48.1 # \
                        name=joe,age=1.9,range=73.1 # name=kay,age=4.0,range=18.2
\end{verbatim}
\postverb[0in]

%================================================================
\subsection{Variables Subscribed for by pContactMgrV20}
\label{sec_cmgr_subs}

The \app{pContactMgrV20} application will subscribe for the
following MOOS variables:

\begin{packed_itemize}[2]
\item \mvar{APPCAST\_REQ}: A request to generate and post a new
  appcast report, with reporting criteria, and expiration.

\item \mvar{BCM\_ALERT\_REQUEST}: If false, no postings will be made
  for rendering the alert and cpa range circles. Section \ref{sec_cmgr_alert_mconfig}.

\item \mvar{BCM\_DISPLAY\_RADII}: If false, no postings will be made
  for rendering the alert and cpa range circles. Section \ref{sec_cmgr_visuals}.

\item \mvar{BCM\_REPORT\_REQUEST}: If false, no postings will be made
  for rendering the alert and cpa range circles. Section \ref{sec_cmgr_repreq}

\item \mvar{NAV\_HEADING}: Present ownship heading in degrees.
    
\item \mvar{NAV\_SPEED}: Present ownship speed in meters per second.

\item \mvar{NAV\_X}: Present position of ownship in local $x$
  coordinates.
    
\item \mvar{NAV\_Y}: Present position of ownship in local $y$
  coordinates.
    
\item \mvar{NODE\_REPORT}: A report about a known contact.
\end{packed_itemize}

%================================================================
\subsection{Command Line Usage of pContactMgrV20}
\label{sec_cmgr_cmdline}
%\index{Command Line Usage!pContactMgrV20}
%\index{pContactMgrV20!Command Line Usage}

The \app{pContactMgrV20} application is typically launched as a part
of a batch of processes by pAntler, but may also be launched from the
command line by the user.  To see command-line options enter the
following from the command-line:

\vspace{0.15in}
\begin{consoleverb}
 $ pContactMgrV20 --help or -h 
\end{consoleverb}
\vspace{0.15in}

\noindent
This will show the output shown in Listing \ref{lst_pcm_usage} below.

\vspace{0.1in}
\begin{listing}{Command line usage for the \app{pContactMgrV20} application}
\label{lst_pcm_usage}
\footnotesize
\begin{verbatim}
  1  =============================================================== 
  2  Usage: pContactMgrV20 file.moos [OPTIONS]                     
  3  =============================================================== 
  4                                                                  
  5  SYNOPSIS:                                                       
  6  ------------------------------------                            
  7    The contact manager deals with other known vehicles in its    
  8    vicinity. It handles incoming reports perhaps received via a  
  9    sensor application or over a communications link. Minimally   
 10    it posts summary reports to the MOOSDB, but may also be       
 11    configured to post alerts with user-configured content about  
 12    one or more of the contacts.                                  
 13                                                                  
 14  Options:                                                        
 15    --alias=&lt;ProcessName&gt;                                      
 16        Launch pContactMgrV20 with the given process            
 17        name rather than pContactMgrV20.                        
 18    --example, -e                                                 
 19        Display example MOOS configuration block.                 
 20    --help, -h                                                    
 21        Display this help message.                                
 22    --interface, -i                                               
 23        Display MOOS publications and subscriptions.              
 24    --version,-v                                                  
 25        Display the release version of pContactMgrV20.          
 26                                                                  
 27  Note: If argv[2] does not otherwise match a known option,       
 28        then it will be interpreted as a run alias. This is       
 29        to support pAntler launching conventions.         
\end{verbatim}
\end{listing}
\normalsize


%================================================================
\section{Visuals}
\label{sec_cmgr_visuals}

\noindent
The contact manager will optionally generate visual artifacts, in the
form of postings to the variable \mvar{VIEW\_CIRCLE}, for consumption
by \app{pMarineViewer} for rendering the alert range and cpa range.
Rendering of ranges is done with the following three configuration
parameters:

\prevblue
\begin{verbatim}
  diplay_radii = true
  alert_range_color = &lt;color&gt; 
  cpa_range_color = &lt;color&gt; 
\end{verbatim}
\postverb

\noindent
The default value for \pvar{display\_radii} is false. The default value
for \pvar{alert\_range\_color} is \var{gray70}, and the default value for
\pvar{cpa\_range\_color} is \var{gray30}.  See the Colors Appendix
for more on colors.

\vspace{0.1in}
\noindent
If multiple alerts are configured in the contact manager, the user may
need to specify which alert ID to render. If no alert ID is specified,
the contact manager will choose the first one in its memory. To
specifify the ID, the following parameter may be used:

\prevblue
\begin{verbatim}
  diplay_radii_id = &lt;alert_id&gt;
\end{verbatim}
\postverb

\noindent
The posting of rendering circles by \app{pContactMgrV20} may also be
be adjusted dynamically via the incoming MOOS message
\mvar{BCM\_DISPLAY\_RADII}.  The value of this message may be either

\begin{packed_itemize}
\item \var{true} or \var{on},
\item \var{false} of \var{off},
\item \var{toggle},
\item A configured alert ID
\end{packed_itemize}

\end{document}

</pre></body></html>