/* ---------------------------------------------------------------------- */ 
/* SonarMessages.h                                                        */ 
/* ---------------------------------------------------------------------- */ 
/*                                                                        */ 
/* Describes the standard sonar messages which can be sent between a      */ 
/* topside and the EdgeTech Interface.  Messages always consist of 2      */ 
/* parts:                                                                 */ 
/*      1) A header which contains the message type and length            */ 
/*      2) The actual data                                                */ 
/*                                                                        */ 
/* Note that two communications circuits (TCP sockets) are used.          */ 
/* One socket is used for commands and the other socket is used for data. */ 
/*                                                                        */ 
/* ---------------------------------------------------------------------- */ 
/*                                                                        */ 
/* (c) Copyright 1998 - 2010, 2011  EdgeTech                              */ 
/*                                                                        */ 
/* This file contains proprietary information, and trade secrets of       */ 
/* EdgeTech, and may not be disclosed or reproduced without the prior     */ 
/* written consent of EdgeTech.                                           */ 
/*                                                                        */ 
/* EdgeTech is not responsible for the consequences of the use or misuse  */ 
/* of this software, even if they result from defects in it.              */ 
/*                                                                        */ 
/* This information may change without notice.                            */  
/* ---------------------------------------------------------------------- */ 
 
#ifndef __SonarMessages_H__
#define __SonarMessages_H__


/* ---------------------------------------------------------------------- */ 
/* Includes                                                               */ 
/* ---------------------------------------------------------------------- */ 

#include <time.h>

#include "PublicMessageOffsets.h"


/* ---------------------------------------------------------------------- */ 
/* Structure defines                                                      */ 
/* ---------------------------------------------------------------------- */ 

#define FILE_NAME_SIZE                       (80)
#define SONAR_MESSAGE_SHORT_STRING_LENGTH   (128)
#define SONAR_MESSAGE_STRING_LENGTH         (256)


/* ---------------------------------------------------------------------- */ 
/*  Message Header                                                        */ 
/* ---------------------------------------------------------------------- */ 
/* All messages are preceeded with a header which indicates the size of   */ 
/* the message to follow in bytes and its type.  The header is of type    */ 
/* SonarMessageHeaderType. A version number is included to accomodate     */ 
/* future changes / extensions in the protocol.                           */ 
/* ---------------------------------------------------------------------- */ 

typedef struct
{
  /* Marker for the start of header                                       */ 
  unsigned short int startOfMessage;

  /* The version of the protocol in use                                   */ 
  unsigned char version;

  /* Session Identifier                                                   */ 
  unsigned char sessionID;

  /* The message format as per SonarMessageType                           */ 
  unsigned short int sonarMessage;

  /* The action to perform as per SonarCommandType                        */ 
  unsigned char sonarCommand;

  /* Indicates subsystem (0 is first) for a multi-system device.          */ 
  unsigned char subSystem;

  /* Indicates channel (0 is first) for a multi-channel subsystem.        */ 
  unsigned char channel;

  /* Sequence number of message.  A reply to this message will contain    */ 
  /* this value.  A topside can optionally use this field to track replys */ 
  unsigned char sequence;

  /* Header space reserved for future use.                                */ 
  unsigned char reservedHeader[2];

  /* Size of message in bytes to follow                                   */ 
  long int byteCount;         

}  SonarMessageHeaderType;


/* ---------------------------------------------------------------------- */ 
/* Header defines                                                         */ 
/* ---------------------------------------------------------------------- */ 

/* Start of header word                                                   */ 
#define SONAR_MESSAGE_HEADER_START         (0x1601)

/* The version of the protocol in use                                     */ 
#define SONAR_PROTOCOL_CURRENT_VERSION       (0x0A)


/* ---------------------------------------------------------------------- */ 
/* Command Types                                                          */ 
/* ---------------------------------------------------------------------- */ 
/* Command type(sonarCommand in header).  A topside will send SET         */ 
/* commands, which return no values, GET commands, which return the       */ 
/* current parameter set.  The bottom unit only sends REPLY messages in   */ 
/* response to a GET or unsolicited data.                                 */ 
/* ---------------------------------------------------------------------- */ 

typedef enum
{
  /* Send a value or execute a command                                    */ 
  SONAR_COMMAND_SET = 0,     

  /* Request current value / last value of item.  All GETs can be sent    */ 
  /* with a byte count of 0.  Some GET messages will accept parameters.   */ 
  /* See the individual message descriptions for details.                 */ 
  SONAR_COMMAND_GET,

  /* Reply to a COMMAND_GET or unsolicited error msgs                     */ 
  SONAR_COMMAND_REPLY,   

  /* Error replay to a command.  The command was not executed.            */ 
  /* In this case, the return value is the error (SonarMessageLongType)   */ 
  /* as defined by SonarMessageErrorType.                                 */ 
  SONAR_COMMAND_ERROR,

  /* Similar to a REPLY for the data socket, but is playback data.  This  */ 
  /* will only occur when storage playback is enabled.                    */ 
  SONAR_COMMAND_PLAYBACK,
  
  /* Similar to a REPLY for the data socket, but is QC data.  This will   */ 
  /* only occur when QC data is enabled.                                  */ 
  SONAR_COMMAND_QUALITY,
  
}  SonarCommandType;


/* ---------------------------------------------------------------------- */ 
/* Error codes that can be returned as SONAR_COMMAND_ERROR                */ 
/* ---------------------------------------------------------------------- */ 

typedef enum
{
  /* 0: No error                                                          */ 
  SONAR_MESSAGE_ERROR_NONE,

  /* 1: General command failure indicator                                 */ 
  SONAR_MESSAGE_ERROR_FAILED,

  /* 2: Message size does not match expected size                         */ 
  SONAR_MESSAGE_ERROR_DATA_SIZE,

  /* 3: Subsystem number is not present in this system                    */ 
  SONAR_MESSAGE_ERROR_SUBSYSTEM,

  /* 4: Channel number is not present in this system                      */ 
  SONAR_MESSAGE_ERROR_CHANNEL,

  /* 5: sonarMessage field contains an unknown command                    */ 
  SONAR_MESSAGE_ERROR_UNKNOWN,

  /* 6: Pulse file error.  Pulse not loaded                               */ 
  SONAR_MESSAGE_ERROR_PULSE_FILE,

  /* 7: Session ID error.  Command rejected                               */ 
  SONAR_MESSAGE_ERROR_SESSION_ID,

  /* 8: Override required:  Command rejected                              */ 
  SONAR_MESSAGE_ERROR_OVERRIDE_REQUIRED,

}  SonarMessageErrorType;


/* ---------------------------------------------------------------------- */ 
/* Message Types                                                          */ 
/* ---------------------------------------------------------------------- */ 
/* sonarMessage field indicates the type of data to follow.               */ 
/* ---------------------------------------------------------------------- */ 

typedef enum
{
  /* -------------------------------------------------------------------- */ 
  /* Overall commands.                                                    */ 
  /* For the following messages, the channel and subSystem should be 0.   */ 
  /* -------------------------------------------------------------------- */ 

  /* Null message - can be used to test communications                    */ 
  SONAR_MESSAGE_NONE = MESSAGE_OFFSET_STANDARD,

  /* Reset to default values (No Data) on set                             */ 
  /* Note:  The subsystem should be 255 to reset the entire system or     */ 
  /* the specific subsystem number.  The channel must be 0.               */ 
  SONAR_MESSAGE_SYSTEM_RESET,   

  /* Get or set the time (TimestampType)                                  */ 
  /* Note that because of the nagle algorithm on sockets, the actual      */ 
  /* message can be delayed.  To set the time with greater accuracy, say, */ 
  /* within 10 ms, the nagle algorithm should be disabled by the sender.  */ 
  /* Or a subsequent message bigger than the maximum network packet size  */ 
  /* should be sent following this message (usually about 1600 bytes).    */ 
  /* Note:  This is a system command, the subsystem and channel numbers   */ 
  /* must be 0.                                                           */ 
  /* NOTE: The SONAR_MESSAGE_NONE message can be any size desired.        */ 
  SONAR_MESSAGE_SYSTEM_TIME,    

  /* Change the time by the delta in milliseconds (SonarMessageLongType)  */ 
  /* NOTE that in order to get accurate time sync, a delta must be set via*/ 
  /* this message, and it must be based on the GetTickCount() function.   */ 
  /* The normal GetSystemTime() is only accurate to about 50 ms.          */ 
  /* Note:  This is a system command, the subsystem and channel numbers   */ 
  /* must be 0.                                                           */ 
  /* The value is the difference in time between the sonar's time and the */ 
  /* topsides time.  Therefore this value should be subtracted from the   */ 
  /* sonar's local time base.                                             */ 
  SONAR_MESSAGE_TIME_DELTA,

  /* Get the software version string (SonarMessageStringType)             */ 
  /* Note:  This is a system command, the subsystem and channel numbers   */ 
  /* must be 0.  The version string consists of an alphabetic string      */ 
  /* followed by a version number of the form N.M where N and M are both  */ 
  /* integers.                                                            */ 
  SONAR_MESSAGE_SYSTEM_VERSION,

  /* Shutdown System                                                      */ 
  /* Accepts a (SonarMessageLongType), which can have any of the          */ 
  /* following values: 0: Exit sonar program only, 1: Shutdown, 2: Reboot */ 
  SONAR_MESSAGE_SYSTEM_SHUTDOWN,

  /* User defined message                                                 */ 
  /* Accepts a (UserDefinedMessageHeaderType) followed by user data.      */ 
  SONAR_MESSAGE_USER_DEFINED,

  /* Status request / returned (SonarMessageStatusType)                   */ 
  /* Note:  This is a system command, the subsystem and channel numbers   */ 
  /* must be 0.                                                           */ 
  SONAR_MESSAGE_SYSTEM_STATUS = MESSAGE_OFFSET_STATUS,
  
  /* Alive messages are echoed back on the same connection.  This allows  */ 
  /* for the detection of lost connection links.  Accepts a long parameter*/ 
  /* (SonarMessageLongType) which is echoed back to the caller and is     */ 
  /* typically a sequence number.                                         */ 
  /* Note:  This is a system command, the subsystem and channel numbers   */ 
  /* must be 0.                                                           */ 
  SONAR_MESSAGE_ALIVE,

  /* Override data lockout caused by suspected system failure in the      */ 
  /* sonar system.  Once an overrride message is sent, the sonar system   */ 
  /* will not stop the data flow because of potential data quality        */ 
  /* problems.                                                            */ 
  SONAR_MESSAGE_OVERRIDE,

  /* Run all of the power on self test diagnostics.  This will normally   */ 
  /* cause an audible chirp on the subbottom (if present) and side scan   */ 
  /* low (if present) and other internal diagnostics.  This can either    */ 
  /* cause OR CLEAR a POST error code.  If a post error code is detected  */ 
  /* sonar data WILL NOT be returned to the topside unless an override    */ 
  /* message is sent.  The subsystem and channel should be set to 0 for   */ 
  /* this message.  The sonarCommand field in the header should be set to */ 
  /* SONAR_COMMAND_GET as this command returns the post status bit field  */ 
  /* as the lsb 8 bits of its return value (SonarMessageLongType).  See   */ 
  /* the SonarMessageStatusType and the serviceNeeded field for a list    */ 
  /* of the possible return values.                                       */ 
  SONAR_MESSAGE_RUN_POST_DIAGNOSTICS,

  /* Get the type of system (SonarMessageLongType).  Where:               */ 
  /*    0 - No Acquisition                                                */ 
  /*    1 - single frequency multi-pulse sidescan                         */ 
  /*    2 - single frequency sidescan - 560A - 272 towfish                */ 
  /*    3 - simultaneous dual frequency sidescan - 560D - DF1000 towfish  */ 
  /*    4 - simultaneous dual frequency sidescan                          */ 
  /*    5 - sub-bottom sonar                                              */ 
  /*    6 - combined sub-bottom and dual frequency sidescan               */ 
  /*    7 - single frequency synthetic aperature sidescan                 */ 
  /*    8 - single frequency sidescan                                     */ 
  /*    9 - simultaneous dual frequency multi-pulse sidescan              */ 
  /*   10 - 4125 ultra portable sidescan - two disparate configurations   */ 
  /*   11 - one frequency focused sidescan, one frequency standard        */ 
  /*   12 - single frequency multipulse Bathymetric system                */ 
  /*   13 - single frequency monopulse Bathymetric system                 */ 
  /* Note:  This is a system command, the subsystem and channel numbers   */ 
  /* must be 0.                                                           */ 
  SONAR_MESSAGE_SYSTEM_TYPE,

  /* Get the operational status of the system (SonarMessageLongType).     */ 
  /* Where:  0 - Operational, 1 - Not operational.                        */ 
  /* Note:  This is a system command, the subsystem and channel numbers   */ 
  /* must be 0.                                                           */ 
  SONAR_MESSAGE_SYSTEM_OPERATIONAL,

  /* Time sync status request / returned (SonarMessageTimesyncStatusType) */ 
  /* Note:  This is a system command, the subsystem and channel numbers   */ 
  /* must be 0.                                                           */ 
  SONAR_MESSAGE_TIMESYNC_STATUS,

  
  /* -------------------------------------------------------------------- */ 
  /* Sonar Return Data                                                    */ 
  /* -------------------------------------------------------------------- */ 

  /* Subbottom data returned to topside (JSFDataType)                     */ 
  /* This is returned from the sonar and is not a command message.        */ 
  SONAR_MESSAGE_DATA = MESSAGE_OFFSET_DATA,

  /* Window for data transmission (SonarMessageWindowType)                */ 
  /* Subsystem and channel must be valid.                                 */ 
  SONAR_MESSAGE_DATA_NETWORK_WINDOW, 

  /* Sidescan data returned to topside (SidescanHeaderType)               */ 
  /* This is returned from the sonar and is not a command message.        */ 
  SONAR_MESSAGE_DATA_SIDESCAN,

  /* Activate / Deactivate return data type.  The data for the subsystem  */ 
  /* / channel specified in the header is activated / deactivated         */ 
  /* (0 - deactivate : 1 - activate)   (SonarMessageLongType)             */ 
  /* Subsystem and channel must be valid.                                 */ 
  SONAR_MESSAGE_DATA_ACTIVE,

  /* -------------------------------------------------------------------- */ 
  /* Compressed header data messages                                      */ 
  /* -------------------------------------------------------------------- */ 

  /* Subbottom data returned to topside (CompactSonarHeaderType)          */ 
  /* This is returned from the sonar and is not a command message.        */ 
  /* The compression library will unpack this and replace with            */ 
  /* a SONAR_MESSAGE_DATA message.                                        */ 
  SONAR_MESSAGE_DATA_COMPACTHEADER,

  /* Sidescan data returned to topside (CompactSonarHeaderType)           */ 
  /* This is returned from the sonar and is not a command message.        */ 
  /* The compression library will unpack this and replace with            */ 
  /* a SONAR_MESSAGE_DATA_SIDESCAN message                                */ 
  SONAR_MESSAGE_DATA_SIDESCAN_COMPACTHEADER,

  /* -------------------------------------------------------------------- */ 
  /* SAS data messages                                                    */ 
  /* -------------------------------------------------------------------- */ 

  /* SAS data output for processing (SASDataType)                         */ 
  /* this is returned from the SAS processor and is not a command message.*/ 
  SONAR_MESSAGE_DATA_SAS,

  /* -------------------------------------------------------------------- */ 
  /* Quality data messages                                                */ 
  /* -------------------------------------------------------------------- */ 

  /* QC data parameters (SonarMessageQCParametersType)                    */ 
  /* Subsystem must be valid.                                             */ 
  SONAR_MESSAGE_QC_PARAMETERS,


  /* -------------------------------------------------------------------- */ 
  /* Processing of data                                                   */ 
  /* -------------------------------------------------------------------- */ 

  /* Window for processing optimization (SonarMessageWindowType)          */ 
  /* Subsystem and channel must be valid.                                 */ 
  SONAR_MESSAGE_PROCESSING_ENHANCE_WINDOW = MESSAGE_OFFSET_PROCESS,

  /* Samples to ignore due to direct path on AGC, normalization           */ 
  /* algorithms (SonarMessageLongType)                                    */ 
  /* Subsystem and channel must be valid.                                 */ 
  /* If this value is positive the units are output samples.  If 0 or -1  */ 
  /* agc processing starts at time 0 (and does not exclude the transmit   */ 
  /* pulse length.  If less than -1, the units are considered to be micro */ 
  /* seconds after the transmit pulse, so for example to exclude a return */ 
  /* at the 3 ms point in the acoustic record use the value -3000.        */ 
  SONAR_MESSAGE_PROCESSING_DIRECT_PATH,


  /* -------------------------------------------------------------------- */ 
  /* Management of pulses                                                 */ 
  /* -------------------------------------------------------------------- */ 

  /* Enable/disable ping: 0 => disable, 1=>enable (SonarMessageLongType)  */ 
  /* Note:  This is a subsystem command, the channel number must be 0.    */ 
  SONAR_MESSAGE_PING = MESSAGE_OFFSET_PULSES,

  /* 1000.0 * DAC gain to scale outgoing pulse by (SonarMessageLongType)  */ 
  /* Subsystem and channel must be valid.                                 */ 
  /* A value of 1000 will apply full power (the maximum amount aka 100%)  */ 
  SONAR_MESSAGE_PING_GAIN,

  /* A set message takes no parameters.  A set message resets the list of */ 
  /* pulse records so that the next get message will return the first     */ 
  /* record in the list.                                                  */ 
  /* A get message with a (SonarMessageLongType) parameter, returns up to */ 
  /* the specified number of pulse records as an array of                 */ 
  /* (SonarMessagePingType) values, up to a maximum of 30.                */ 
  /* Note that the maximum pulses supported is 30, so requesting 30 will  */ 
  /* provide all possible pulses in one message.                          */ 
  /* A get message can also be sent with no parameters, in this case it   */ 
  /* returns a single (SonarMessagePingType) structure.                   */ 
  /* The pulse record following the last valid pulse record will have a   */ 
  /* NULL pulse name field.                                               */ 
  /* Note:  This is a subsystem command, the channel number must be 0.    */ 
  SONAR_MESSAGE_PING_LIST,   

  /* Select an outgoing set of pulses, and matched filters.               */ 
  /* (SonarMessageStringType)                                             */ 
  /* Note:  This is a subsystem command, the channel number must be 0.    */ 
  SONAR_MESSAGE_PING_SELECT,  

  /* Number of pings pers second required * 1000                          */ 
  /* (SonarMessageLongType)                                               */ 
  /* Actual ping rate may be slightly lower (2048 sample granuality)      */ 
  /* Note:  This is a subsystem command, the channel number must be 0.    */ 
  SONAR_MESSAGE_PING_RATE,

  /* Set trigger for internal(0), external(1), coupled(2), or gated(3)    */ 
  /* (SonarMessageLongType).  Coupled mode causes a system to be triggered*/ 
  /* by another one (eg Sidescan triggered by Subbottom)                  */ 
  /* See SONAR_MESSAGE_PING_COUPLING_PARAMETERS message.  In gated mode   */ 
  /* the external trigger is used as a trigger inhibit, and the inhibit   */ 
  /* time is based on the coupling parameter delay.                       */ 
  /* Note:  This is a subsystem command, the channel number must be 0.    */ 
  SONAR_MESSAGE_PING_TRIGGER,

  /* Set delay for external trigger in ms (SonarMessageLongType).  This   */ 
  /* message applies only to the soft trigger.  A soft trigger uses the   */ 
  /* ethernet to transmit trigger requests to an underwater electronics   */ 
  /* bottle and is not present in an FS-SB standard system.  See the      */ 
  /* SONAR_MESSAGE_PING_COUPLING_PARAMETERS message for a hardwired       */ 
  /* trigger delay.                                                       */ 
  /* Note:  This is a subsystem command, the channel number must be 0.    */ 
  /*                                                                      */ 
  /* WARNING: THIS MESSAGE IS NO LONGER SUPPORTED                         */ 
  SONAR_MESSAGE_PING_DELAY,

  /* A get message takes a parameter that is 1000 * the ping rate in Hz.  */ 
  /* (SonarMessageLongType) and returns a (SonarMessageLongType) with the */ 
  /* maximum number of samples that can be received for that ping rate.   */ 
  /* A get message can also be sent with no parameters, in this case it   */ 
  /* returns the maximum number of samples for the current ping rate.     */ 
  /* Note:  This is a subsystem command, the channel number must be 0.    */ 
  SONAR_MESSAGE_PING_MAX_SAMPLES,

  /* Set the ping rate for sidescan systems.  Sets the ping rate  based   */ 
  /* on the range in millimeters. (SonarMessageLongType)                  */ 
  /* Note:  This is a subsystem command, the channel number must be 0.    */ 
  SONAR_MESSAGE_PING_RANGE,

  /* Set the coupling parameters for this system when in trigger mode     */ 
  /* coupled, and the hardware trigger delay in external trigger modes.   */ 
  /* (SonarMessageCouplingParametersType)                                 */ 
  /* Note:  This is a subsystem command, the channel number must be 0.    */ 
  SONAR_MESSAGE_PING_COUPLING_PARAMETERS,

  /* Get the list of human readable strings and fish IDs.  Only a         */ 
  /* SONAR_COMMAND_GET message is meaningful.  Returns an array of        */ 
  /* (SonarMessageFishType) records.  The number of records can be        */ 
  /* determined by the size of the return message.                        */ 
  /* This message should be used to get the available EdgeTech fish to    */ 
  /* present to the end user.  The user should first select the fish      */ 
  /* which is attached to the sonar processing system, and should then    */ 
  /* select a pulse only from the subset of the selected fish.            */ 
  /* Note:  This is a subsystem command, the channel number must be 0.    */ 
  SONAR_MESSAGE_PING_FISH_LIST,

  /* Sets the (multi-ping) operating mode (SonarMessageLongType)          */ 
  /* Value 0 => Standard operating mode, 1 => Multiple ping mode          */ 
  /* This is a subsystem command and the channel should be set to 0.      */ 
  /*                                                                      */ 
  /* This message has a different effect on sub-bottom and sidescan       */ 
  /* systems.                                                             */ 
  /*                                                                      */ 
  /* For sidescan systems:  This message is handled by the Discover       */ 
  /* external topside interface, and switches the mode of the specified   */ 
  /* subsystem.  Only one subsystem at a time may currently be in multiple*/ 
  /* ping mode.  If a subsystem is in multiple ping mode it is the only   */ 
  /* subsystem that may have pinging enabled.  These restrictions may be  */ 
  /* altered in the future.                                               */ 
  /*                                                                      */ 
  /* For Sub-bottom systems:  A value of 0, multiple pings are disabled,  */ 
  /* and data is referenced to the ping time.  If the data window requires*/ 
  /* more data than can be provided for the specified ping rate, then the */ 
  /* ping rate will be reduced.                                           */ 
  /* A value of 1, multiple pings are enabled, and the data window will   */ 
  /* NOT effect the ping rate.  In this case, the initialSkip parameter   */ 
  /* of the data window determines which ping time in the history buffer  */ 
  /* to reference when delivering data.  A data window is not permitted to*/ 
  /* cross ping boundaries, and if the initial skip plus the number of    */ 
  /* samples desired (suitably decimated) cases the window to either cross*/ 
  /* ping boundaries or deliver "invalid" data at the end of a ping       */ 
  /* (equivelent to the pulse length) then the amount of data delivered   */ 
  /* will be reduced.  On some systems, or in external trigger mode this  */ 
  /* can cause the amount of data delivered to vary from ping to ping.    */ 
  /* When multiple pings are enabled, a history buffer of prior pings is  */ 
  /* maintained.  Since this history is 8 entrys deep, the maximum number */ 
  /* of pings in the water is 8.  This value may change in the future.    */ 
  SONAR_MESSAGE_PING_MODE,

  /* A set message takes no parameters.  A set message resets the list of */ 
  /* pulse records so that the next get message will return the first     */ 
  /* record in the list.                                                  */ 
  /* A get message with a (SonarMessageLongType) parameter, returns up to */ 
  /* the specified number of pulse records as an array of                 */ 
  /* (SonarMessagePingEnhancedType) values, up to a maximum of 30.        */ 
  /* Note that the maximum pulses supported is 30, so requesting 30 will  */ 
  /* provide all possible pulses in one message.                          */ 
  /* A get message can also be sent with no parameters, in this case it   */ 
  /* returns a single (SonarMessagePingEnhancedType) structure.           */ 
  /* The pulse record following the last valid pulse record will have a   */ 
  /* NULL pulse name field.                                               */ 
  /* Note:  This is a subsystem command, the channel number must be 0.    */ 
  SONAR_MESSAGE_PING_LIST_ENHANCED,

  /* Set the pulse auto select mode.  When non-zero, auto pulse selection */ 
  /* is enabled.  When enabled, pulses cannot be selected via PING_SELECT */ 
  /* messages, but are determined by the operating ping rate or range.    */ 
  /* The parameter passed (SonarMessageLongType) is the maximum number of */ 
  /* pulses in the water for a Multiping sidescan type system.  Set this  */ 
  /* to 1 to disable multiping but enable auto mode.  The presently       */ 
  /* supported values are 0 through 4.  This is a subsystem level command */ 
  /* and the channel number should be set to 0.                           */ 
  SONAR_MESSAGE_PING_AUTOSELECTMODE,


  /* -------------------------------------------------------------------- */ 
  /* ADC Control                                                          */ 
  /* -------------------------------------------------------------------- */ 

  /* Set gain factor for ADC when AGC disabled (SonarMessageLongType)     */ 
  /* Value is * 1000.0 (only 1, 2, 4, 8, 16, 32, 64, 128, 256, 512, 1024, */ 
  /* and 2048 supported)                                                  */ 
  /* Subsystem and channel must be valid.  Ignored on sidescan systems.   */ 
  SONAR_MESSAGE_ADC_GAIN = MESSAGE_OFFSET_ADC,

  /* 0=> disable, 1=> enable (Automatic Gain Control)                     */ 
  /* (SonarMessageLongType)                                               */ 
  /* Subsystem and channel must be valid.  Ignored on sidescan systems.   */ 
  SONAR_MESSAGE_ADC_AGC,

  /* ADC rate in Hz * 1000.  This is a read only value and changes with   */ 
  /* the pulse selected (SonarMessageLongType)                            */ 
  /* Note:  This is a subsystem command, the channel number must be 0.    */ 
  SONAR_MESSAGE_ADC_RATE,

}  SonarMessageType;


/* ---------------------------------------------------------------------- */ 
/* Message Data Structures                                                */ 
/* ---------------------------------------------------------------------- */ 
/* The data component of the messages varies with the sonarMessage as     */ 
/* defined by the structures below.                                       */ 
/* ---------------------------------------------------------------------- */ 

/* ---------------------------------------------------------------------- */ 
/* Timestamp structure                                                    */ 
/* ---------------------------------------------------------------------- */ 

typedef struct
{
  /* Time in seconds since the dawn of time                               */ 
  long time; // time_t time;

  /* Milliseconds supplement to time                                      */ 
  long int milliseconds;

} TimestampType;


/* ---------------------------------------------------------------------- */ 
/* General integer parameter                                              */ 
/* ---------------------------------------------------------------------- */ 

typedef struct
{
  long value;                              /* Value for message           */ 

}  SonarMessageLongType;


/* ---------------------------------------------------------------------- */ 
/* General purpose string argument.                                       */ 
/* ---------------------------------------------------------------------- */ 

typedef struct
{
  char name[SONAR_MESSAGE_STRING_LENGTH];  /* String parameter            */ 

}  SonarMessageStringType;


/* ---------------------------------------------------------------------- */ 
/* General purpose string argument.                                       */ 
/* ---------------------------------------------------------------------- */ 

typedef struct
{
  char name[SONAR_MESSAGE_SHORT_STRING_LENGTH];  /* Short String parameter*/ 

}  SonarMessageShortStringType;


/* ---------------------------------------------------------------------- */ 
/* SONAR_MESSAGE_STATUS parameters                                        */ 
/* ---------------------------------------------------------------------- */ 

typedef struct
{
  /* Incremented each time a ping is dropped.                             */ 
  unsigned long overflowCount; 

  /* The current error count.                                             */ 
  unsigned long errorCount;    

  /* Error ids of last 10 errors.                                         */ 
  short int lastError[10];     

  /* Disk space available for sonar data storage in kb.                   */ 
  unsigned long freeDiskSpace;

  /* Indicates that data is being received (increments over time).        */ 
  unsigned long dataAcquisitionActivityIndicator;

  /* General service warning message                                      */ 
  /* This is a bit map with one bit for each power on self test status.   */ 
  /* A non-zero bit indicates a POST test failure.                        */ 
  /* Bit 0 : SB Power Amp feedback on channel 0 test failed.              */ 
  /* Bit 1 : SB Power Amp feedback on secondary channel (1) test failed.  */ 
  /* Bit 2 : Interface Card diagnostic failed.                            */ 
  /* Bit 3 : Health Monitor Sensors (formerly the 48 Volt Power Check)    */ 
  /* Bit 4 : Ambient Temperature Sensor Check Failed                      */ 
  /* Bit 5 : Internal Configuration Error (Missing Pulse File, etc)       */ 
  /* Bit 6 : Reserved                                                     */ 
  /* Bit 7 : Temperature sensor failure suspected                         */ 
  unsigned char serviceNeeded;

  /* Ambient Temperature out of range flags.                              */ 
  /* Bit 0 : Temperature is out of range.                                 */ 
  unsigned char temperatureFlags;

  /* Humidity out of range indicator                                      */ 
  /* Bit 0 : Humidity reading outside of expected range                   */ 
  unsigned char humidityFlags;

  /* Storage subsystem flags                                              */ 
  /* Bit 0 : Disk storage is enabled (should be set when on).             */ 
  /* Bit 1 : Disk primary drive error detected.  Operator needs to reset. */ 
  /* Bit 2 : Disk write error on drive - all storage disabled.            */ 
  /* Bit 7 : Disk playback is enabled.                                    */ 
  unsigned char storageFlags;

  /* Ambient Temperature status.                                          */ 
  /* 0 : Temperature is OK                                                */ 
  /* 1 : Temperature is in error - below minimum possible value.          */ 
  /* 2 : Temperature is below recommended value.                          */ 
  /* 3 : Temperature is above recommended value.                          */ 
  /* 4 : Temperature is too high - PINGING IS DISABLED.                   */ 
  /* 5 : Temperature is in error - above maximum possible value.          */ 
  unsigned char temperatureStatus;

  /* Status of time synchronization.                                      */ 
  /* Bits 0-3 : Source for time sync.  This can be any of:                */ 
  /*      0 : No time sync active.                                        */ 
  /*      1 : CPU (CPUS RTC - (assumes an NTP server is active)           */ 
  /*      2 : Network time sync active.                                   */ 
  /*      3 : ZDA time sync active.                                       */ 
  /*      4 : RMC time sync active.                                       */ 
  /*      5 : GGA time sync active.                                       */ 
  /*      6 : GLL time sync active.                                       */ 
  /* Others : Reserved.                                                   */ 
  /* Bits 4-6 : Status of time sync.  This can be any of:                 */ 
  /*      0 : Good sync (within 50 ms)                                    */ 
  /*      1 : Fair sync (within 300 ms)                                   */ 
  /*      2 : Marginal sync (within 1 second)                             */ 
  /*      7 : Failed time sync (no source or large erros)                 */ 
  /*  Bit 7 : If set a PPS is enabled but either not active or not at the */ 
  /*          expected pulse per second rate.                             */ 
  unsigned char timeStatus;

  /* Internal resets to date.                                             */ 
  unsigned short resetCount;

  /* Bottle temperature in Degrees C * 1000.                              */ 
  long int bottleTemperature;

  /* Ambient temperature in Degrees C * 1000.                             */ 
  long int ambientTemperature;

  /* Check of 48 Volt Power in milli-Volts.                               */ 
  long int power48Volts;

  /* Humidity sensor reading in % (0 to 100)                              */ 
  long int humidity;

  /* Low rate misc io analog values.                                      */ 
  short int lowRateIO[4];

  /* Serial Port Summary Status.  There are 4 bits for each of up to 16   */ 
  /* ports.  Each 4 bit value indicates the state of the port, which can  */ 
  /* be any of the following:                                             */ 
  /* 0 : Port is not configured for io (inactive).                        */ 
  /* 1 : Active and normal operation.                                     */ 
  /* 2 : Authorization failure.                                           */ 
  /* 3 : Port error (eg open failed - physical port does not exist)       */ 
  /* 4 : Port inactive (eg no connected device or wrong baud rate)        */ 
  /* 5 : No valid data - bytes are being received buy does not parse.     */ 
  /* 6 : Too much data - perhaps the port has been configurated for too   */ 
  /*     low of a baud rate (does not meet MinIdlePercent keyword value.  */ 
  unsigned char serialPortState[8];

  /* Runtime alert bits.  This is a bit mask with the following bits:     */ 
  /* 0 : Cannot find sonar acquisition device                             */ 
  /* 1 : No network connection.                                           */ 
  /* 2 : Password expired.                                                */ 
  /* 3 : Data recording file error.                                       */ 
  /* 4 : Serial port error.                                               */ 
  /* 5 : Time sync not active.                                            */ 
  /* 6 : System is out of the water, ping rate limits being applied.      */ 
  /* 7 : One PPS Trigger In Event not active or at wrong rate.            */ 
  /* 8 : Container Message received with non-recent time stamp.           */ 
  /* 9 : Power Amp Fault Detected (eg overcurrent or other event).        */ 
  /*10 : CRC Fault                                                        */ 
  int runtimeAlerts;
  
  /* Reserved for future expansion.                                       */ 
  int reserved[5];

}  SonarMessageStatusType;


/* ---------------------------------------------------------------------- */ 
/* SONAR_MESSAGE_STATUS parameters                                        */ 
/* ---------------------------------------------------------------------- */ 

typedef struct
{
  /*   0 -   3 : Time since 1/1/1970 in seconds (time() value)            */ 
  unsigned long secondsSince1970; 

  /*   4 -   7 : Nanosecond supplement to time                            */ 
  unsigned long nanoseconds;

  /*   8 -  11 : Estimated time delta in microseconds                     */ 
  long estimatedTimeDelta;

  /*  12 -  12 : Time Sync Status:                                        */ 
  /* 0  - Time Sync Current                                               */ 
  /* 1  - No Time Sync                                                    */ 
  /* 2  - No Time Source                                                  */ 
  unsigned char timeSyncStatus; 

  /*  13 -  13 : Time Sync Method:                                        */ 
  /* 0  - No Time Sync                                                    */ 
  /* 1  - Automatic - (ZDA / Posisition Source / Client)                  */ 
  /* 2  - ZDA only                                                        */ 
  /* 3  - ZDA or Position Source                                          */ 
  /* 4  - Client only                                                     */ 
  unsigned char timeSyncMethod; 

  /*  14 -  14 : Source of current time sync:                             */ 
  /* 0  - No Time Sync                                                    */ 
  /* 1  - ZDA                                                             */ 
  /* 2  - Position Source                                                 */ 
  /* 3  - Client                                                          */ 
  unsigned char timeSyncSource; 

  /*  15 -  15 : Port for time sync input                                 */ 
  unsigned char timeSyncPort;    

}  SonarMessageTimesyncStatusType;


/* ---------------------------------------------------------------------- */ 
/* Ping First / Next data files                                           */ 
/* ---------------------------------------------------------------------- */ 

typedef struct
{
  /* Name used to identify this pulse for selection.                      */ 
  char fileName[FILE_NAME_SIZE];  

  /* Type of pulse.                                                       */ 
  /* If non-zero, bits 4 and up should encode the MPX number which is 1   */ 
  /* for non-multiping pulses and 2 for mpx 2 pulses.                     */ 
  unsigned short pulseType;

  /* approximate maximum ping rate in Hz.                                 */ 
  unsigned char  maxPingRate;

  /* approximate data sample rate in kHz.                                 */ 
  unsigned char  dataRate;

  /* Minimum frequency in Hz.                                             */ 
  unsigned long  fMin;   

  /* Maximum frequency in Hz.                                             */ 
  unsigned long  fMax;   

  /* Pulse duration in milliSeconds                                       */ 
  unsigned long  time;   

  /* Unique pulse identifier                                              */ 
  unsigned short pulseID;    

  /* Unused field - round to long boundary.                               */ 
  unsigned short reserved;

  /* Pulse description - null terminated ASCII string                     */ 
  char description[SONAR_MESSAGE_STRING_LENGTH];  

  /* Type of sonar pulse was designed for.                                */ 
  unsigned long systemType;

}  SonarMessagePingType;



/* ---------------------------------------------------------------------- */ 
/* Ping First / Next data files with enhanced details                     */ 
/* Added to support multiping and its variants                            */ 
/* ---------------------------------------------------------------------- */ 

/* Maximum pulses per pulsefile (for multiping support)                   */ 

#define MAX_PULSES_PER_PULSEFILE (8)

typedef struct
{
  /* Name used to identify this pulse for selection.                      */ 
  char fileName[FILE_NAME_SIZE];  

  /* Type of pulse.                                                       */ 
  unsigned short pulseType;

  /* Number of pulses for multiping                                       */ 
  unsigned short numberOfPulses;

  /* approximate maximum ping rate in Hz.                                 */ 
  float maxPingRate;

  /* approximate data sample rate in kHz.                                 */ 
  /* For processed data                                                   */ 
  float dataRate;

  /* Minimum frequency in Hz.                                             */ 
  /* Index 0 : Port or single channel                                     */ 
  /* Index 1 : Stbd if present                                            */ 
  float fMin[2][MAX_PULSES_PER_PULSEFILE];   

  /* Maximum frequency in Hz.                                             */ 
  /* Index 0 : Port or single channel                                     */ 
  /* Index 1 : Stbd if present                                            */ 
  float fMax[2][MAX_PULSES_PER_PULSEFILE];

  /* Pulse duration in milliSeconds                                       */ 
  float time[2][MAX_PULSES_PER_PULSEFILE];   

  /* Unique pulse identifier                                              */ 
  unsigned short pulseID;    

  /* Unused field - round to long boundary.                               */ 
  unsigned short reserved;

  /* Pulse description - null terminated ASCII string                     */ 
  char description[SONAR_MESSAGE_STRING_LENGTH];  

  /* Type of sonar pulse was designed for.                                */ 
  unsigned long systemType;

  /* Option bits                                                          */ 
  /* Bit 0: When set data is basebanded.  When clear data is decimated    */ 
  /*   This option effects where the data is in the frequency space.      */ 
  long flags;

  /* Reserved for future use                                              */ 
  long reserved2[16];

}  SonarMessagePingEnhancedType;


/* ---------------------------------------------------------------------- */ 
/* List of supported towfish (systemType) and their human readable text.  */ 
/* ---------------------------------------------------------------------- */ 

typedef struct
{
  /* Type of sonar.  Each pulse, as specified in the SonarMessagePingType */ 
  /* message is for a specific type of sonar towfish.  This is the unique */ 
  /* identifier for that sonar towfish.                                   */ 
  unsigned long systemType;

  /* Human readable text description of this system.  This string should  */ 
  /* be presented to an end user to select a fish type.  Only pulses for  */ 
  /* a selected fish should be presented to an end user for selection.    */ 
  char systemName[20];

}  SonarMessageFishType;


/* ---------------------------------------------------------------------- */ 
/* Window for network data                                                */ 
/* ---------------------------------------------------------------------- */ 

typedef struct
{
  /* Ping decimation factor                                               */ 
  /* A value of N returns 1 pings worth of data for every actual N pings  */ 
  /* in the water.  The minimum and recommended value for most            */ 
  /* applications is 1.                                                   */ 
  unsigned short frameDecimation; 

  /* Pixel decimation factor                                              */ 
  /* This value determines the effective sample rate of data received.    */ 
  /* The minimum value of 1 returns data at the maximum sample rate       */ 
  /* (SRMAX), where as a value of N returns data at a sample rate of      */ 
  /* (SRMAX) / N.  The sample rate reduction is achieved by grouping data */ 
  /* into N sample blocks and selecting only the maximum sample from each */ 
  /* block.  A value greater than 1 may result in aliasing of the data    */ 
  /* The sampleInterval field of each returned data record will change    */ 
  /* with this value.                                                     */ 
  unsigned short decimation;      

  /* Samples to skip.  This parameter is used to discard data in the      */ 
  /* water column.  The samples to skip are AFTER decimation              */ 
  unsigned long initialSkip;      

  /* Total samples to return                                              */ 
  /* If this value is set to zero, the maximum amount of data possible    */ 
  /* using the current ping rate or range will be sent.                   */ 
  /* SEG-Y limits the number of samples per packet to an unsigned short.  */ 
  /* If larger sample sizes are required multiple packets must be used.   */ 
  /* Important note: If the trigger mode (for this subsystem) is not      */ 
  /* "coupled" and not configured for hullmount mode (multiping) then a   */ 
  /* large value for (initialSkip + totalSamples) will  cause the ping    */ 
  /* rate to slow down so that the requested amount of data can be        */ 
  /* provided.  A value of 0 will NOT cause the ping rate to slow down    */ 
  unsigned long totalSamples;

  /* Packet size in samples                                               */ 
  /* Due to buffer limitations the current system retricts this to under  */ 
  /* 512KB.                                                               */ 
  /* For most applications, this value should be set to a large number    */ 
  /* to avoid multiple packets of data per ping (eg 250000)               */ 
  unsigned long maxPacketSize;

}  SonarMessageWindowType;


/* ---------------------------------------------------------------------- */ 
/* Coupling Parameters data structure.                                    */ 
/* ---------------------------------------------------------------------- */ 

typedef struct
{
  /* Subsystem number to trigger this subsystem on                        */ 
  long subSystem;

  /* Trigger on every Nth event (minimum value of 1).                     */ 
  long triggerDivisor;

  /* Trigger delay in micro-seconds for external or coupled modes.        */ 
  /* Trigger inhibit time for gated mode.  (minimum value of 0)           */ 
  long triggerDelay;

}  SonarMessageCouplingParametersType;


/* ---------------------------------------------------------------------- */ 
/* Compact Sonar Data Header Structure                                    */ 
/* ---------------------------------------------------------------------- */ 

typedef struct
{
  /*  0 -  1 : Ping number (increments with ping)                         */ 
  unsigned short int pingNum;

  /*  2 -  3 : starting Depth (window offset) in samples                  */ 
  unsigned short int startDepth;       

  /*  4 -  5 : Maximum absolute value for ADC samples for this packet     */ 
  unsigned short ADCMax;

  /*  6 -  6 : -- defined as 2 -N volts for lsb                           */ 
  char weightingFactor;

  /*  7 -  7 : Data format                                                */ 
  /*   0 = 1 short  per sample  - envelope data                           */ 
  /*   1 = 2 shorts per sample  - stored as real(1), imag(1),             */ 
  /*   2 = 1 short  per sample  - before matched filter (raw)             */ 
  /*   3 = 1 short  per sample  - real part analytic signal               */ 
  /*   NOTE: For type = 1, the total number of bytes of data to follow is */ 
  /*   4 * samples.  For all other types the total bytes is 2 * samples.  */ 
  unsigned char dataFormat;

  /*  8 - 11 : Sample interval in ns of stored data                       */ 
  unsigned long int sampleInterval;

  /* 12 - 13 : Milliecond Counter                                         */ 
  unsigned short int millisecondCounter;

  /* 14 - 14 : aproximate applied gain = 2 ** (N / 16.0)                  */ 
  unsigned char appliedGain;

  /* 15 - 15 : Reserved                                                   */ 
  unsigned char reserved;

  /* Sonar data should follow the header.  The number of samples can be   */ 
  /* computed from the byteCount in the SonarMessageHeaderType that       */ 
  /* preceeds this header (eg: for envelope data                          */ 
  /* samples = (byteCount - sizeof(CompactSonarHeaderType))/2             */ 
}  CompactSonarHeaderType;


/* ---------------------------------------------------------------------- */ 
/* QC Parameters data structure.                                          */ 
/* ---------------------------------------------------------------------- */ 

typedef struct
{
  /*  0 -  1 : QC data source, 0 - None, 1 - Network, 2 - Disk            */ 
  unsigned short int source;

  /*  2 -  3 : subsampleing method, 0 - Max, 1 - Avg, 2 - None,           */ 
  unsigned short int subsampleMethod;       

  /*  4 -  5 : long track subsample rate, 1 of N                          */ 
  unsigned short int longTrackSubSampling;

  /*  6 -  7 : cross track subsample rate, 1 of N                         */ 
  unsigned short int crossTrackSubSampling;

  /*  8 -  9 : channel blending mask                                      */ 
  /* bit mask of channels to blend per side for multi-channel data.       */ 
  unsigned short int blendingMask;

}  SonarMessageQCParametersType;


/* ---------------------------------------------------------------------- */ 
/* User Defined Message Header                                            */ 
/* ---------------------------------------------------------------------- */ 

typedef struct
{
  /*   0 -   3 : ID assigned to the user defining these messages.         */ 
  /* EdgeTech assigned unique user ID.                                    */ 
  /* -------------------------------------------------------------------- */ 
  /* User                                     ID                          */ 
  /* EdgeTech                               1 -  1000                     */ 
  /* Kongsberg                           1001 -  1100                     */ 
  /* -------------------------------------------------------------------- */ 
  unsigned long int userID;

  /*  4 -   7 : User defined message type                                 */ 
  unsigned long int messageType;

  /*  8 -  15 : Timestamp                                                 */ 
  TimestampType     timestamp; 

}  UserDefinedMessageHeaderType;

/* ---------------------------------------------------------------------- */ 

#endif  /* Not __SonarMessages_H__ */ 

/* ---------------------------------------------------------------------- */ 
/*                         end SonarMessages.h                            */ 
/* ---------------------------------------------------------------------- */ 

