/****************************************************************************/
/* Copyright 1992 to 1995, MBARI                                            */
/****************************************************************************/
/* Summary  : IBC Quad Serial Port Interface Module for VxWorks             */
/* Filename : quadSerCmd.c                                                  */
/* Author   : Douglas Au                                                    */
/* Project  : New ROV                                                       */
/* Version  : Version 1.0                                                   */
/* Created  : 08/21/95                                                      */
/* Modified : 08/21/95                                                      */
/* Archived :                                                               */
/****************************************************************************/
/* Modification History:                                                    */
/* $Header:
 * $Log:
 *
 * Initial revision
 *
 *
 */
/****************************************************************************/

#include <vxWorks.h>                /* vxWorks system declarations          */
#include <semLib.h>                 /* vxWorks semaphore functions          */
#include <wdLib.h>                  /* vxWorks watch dog timer support decls*/
#include <msgQLib.h>                /* vxWorks Message Queue Library        */

#include <mbariTypes.h>             /* mbari style guide type declarations  */
#include <mbariConst.h>             /* Miscellaneous constants              */

#include "sio32.h"                  /* SIO32 hardware and driver information*/
#include <sio32Server.h>            /* Sio32 server communication services  */
#include <sio32Client.h>            /* Sio32 client communication services  */
#include <microCmd.h>               /* Microcontoller command functions     */

#include "applic.h"                 /* Microcontroller applications         */
#include "microcmd.h"               /* Microcontroller commands             */
#include "ibc_card.h"               /* IBC Card Types                       */
#include "ibc_cmd.h"                /* IBC Card Serial Commands             */

#include "quadSerCmd.h"             /* Function Prototypes for quadSerCmd.c */

/****************************************************************************/
/* Function    : Quad_Serial_Read                                           */
/* Purpose     : Reads from Quad Serial Port                                */
/* Inputs      : Sio32 channel, IBC Board Address, channel, buffer          */
/* Outputs     : Returns number of bytes read or ERROR                      */
/****************************************************************************/
    STATUS
Quad_Serial_Read( sio32Chan *IBC_SerialChan, Word boardAddr, Word chan,
    Byte *readBuffer, Int16 nBytes )
{
    Int16   len;
    Byte    reply[MAX_PACKET_LEN];  /* Command Result from microcontroller  */

                                    /* Send command to microcontroller      */
    if ((len = sendMicroCommand( IBC_SerialChan, &reply, MAX_PACKET_LEN,
         4, IBC_CPU_APP | QUAD_SER_READ, boardAddr, chan, nBytes )) == ERROR )
        return(ERROR);
                                    /* Check if command result is CMD OK    */
    if (wordFromBuf(&reply, 0) != CMD_OK)
        return(ERROR);              /* Command failed so return ERROR       */

                                    /* Command OK so update readBuffer      */
    bcopy(reply + sizeof(Word), readBuffer, len - sizeof(Word));

    return (len - sizeof(Word));    /* Return bytes read                    */
} /* Quad_Serial_Read() */

/****************************************************************************/
/* Function    : Quad_Serial_Write                                          */
/* Purpose     : Writes to Quad Serial Port                                 */
/* Inputs      : Sio32 channel, IBC Board Address                           */
/* Outputs     : Returns OK or ERROR                                        */
/****************************************************************************/
    STATUS
Quad_Serial_Write( sio32Chan *IBC_SerialChan, Word boardAddr, Word chan,
    Byte *writeBuffer, Int16 nBytes )
{
    Word    reply;
    Byte    Packet[MAX_PACKET_LEN]; /* Command Result from microcontroller  */

    nBytes = min(nBytes, MAX_PACKET_LEN - sizeof(Word) * 4);

    wordsToBuf(Packet, 4, IBC_CPU_APP | QUAD_SER_WRITE, boardAddr, chan,
               nBytes);

    bcopy( writeBuffer, Packet + sizeof(Word) * 4, nBytes);

    return (microWriteBufReply( IBC_SerialChan,
        nBytes + sizeof(Word) * 4, Packet));
} /* Quad_Serial_Write() */

/****************************************************************************/
/* Function    : Quad_Serial_SetTermChar                                    */
/* Purpose     : Sets Term Char of Quad Serial Port                         */
/* Inputs      : Sio32 channel, IBC Board Address, channel,termchar         */
/* Outputs     : Returns OK or ERROR                                        */
/****************************************************************************/
    STATUS
Quad_Serial_SetTermChar( sio32Chan *IBC_SerialChan, Word boardAddr, Word chan,
                       char termChar )
{
    Word    status;               /* Command Result from microcontroller  */

                                    /* Send command to microcontroller      */
    if ( sendMicroCommand( IBC_SerialChan, &status, sizeof(Word),
         4, IBC_CPU_APP | QUAD_SER_SET_TERM_CHAR,  boardAddr, chan, termChar )
         == ERROR ) return(ERROR);

                                    /* Check if command result is CMD OK    */
    return (wordFromBuf(&status, 0) == CMD_OK ? OK : ERROR);

} /* Quad_Serial_SetTermChar() */

/******************************************************************************/
/* Function    : Quad_Serial_SetLineParm                                      */
/* Purpose     : Sets Line Parms of Quad Serial Port                          */
/* Inputs      : Sio32 channel, IBC Board Address, channel, baudrate, stopbits*/
/*               databits, parity                                             */
/* Outputs     : Returns OK or ERROR                                          */
/******************************************************************************/
    STATUS
Quad_Serial_SetLineParm( sio32Chan *IBC_SerialChan, Word boardAddr, Word chan,
    Nat16 baud, Nat16 data, Nat16 stop, Nat16 par, MBool handshake,
    Int16 proto )
{
    Word    status;               /* Command Result from microcontroller  */

                                    /* Send command to microcontroller      */
    if ( sendMicroCommand( IBC_SerialChan, &status, sizeof(Word),
         9, IBC_CPU_APP | QUAD_SER_SET_LINE_PARM,  boardAddr, chan, baud,
           data, stop, par, handshake, proto) == ERROR )
        return(ERROR);

                                    /* Check if command result is CMD OK    */
    return (wordFromBuf(&status, 0) == CMD_OK ? OK : ERROR);

} /* Quad_Serial_SetLineParm() */

/****************************************************************************/
/* Function    : Quad_Serial_GetLineParm                                    */
/* Purpose     : Gets Line Parameter for Serial Port                        */
/* Inputs      : Sio32 channel, IBC Board Address, channel, buffer          */
/* Outputs     : Returns Line Parms or ERROR                                */
/****************************************************************************/
    STATUS
Quad_Serial_GetLineParm( sio32Chan *IBC_SerialChan, Word boardAddr, Word chan,
    Nat16 *baud, Nat16 *data, Nat16 *stop, Nat16 *par, MBool *handshake,
    Int16 *proto )
{
    Int16   cmdStatus;              /* Command Status                       */
    Word    reply[7];               /* Command Result from microcontroller  */

                                    /* Send command to microcontroller      */
    if ( sendMicroCommand( IBC_SerialChan, &reply, sizeof(Word) * 7,
         3, IBC_CPU_APP | QUAD_SER_GET_LINE_PARM, boardAddr, chan) == ERROR)
         return(ERROR);

                                    /* Check if command result is CMD OK    */
    if (wordFromBuf(&reply, 0) != CMD_OK)
        return(ERROR);              /* Command failed so return ERROR       */

                                    /* Command OK so update thresholds      */
    wordsFromBuf(reply, 7, &cmdStatus, baud, data, stop, par, handshake,
                 proto);
    return (OK);
} /* Quad_Serial_GetLineParms() */

/****************************************************************************/
/* Function    : Quad_Serial_SendBreak                                      */
/* Purpose     : Sends Break Command to Serial Port                         */
/* Inputs      : Sio32 channel, IBC Board Address, channel                  */
/* Outputs     : Returns OK or ERROR                                        */
/****************************************************************************/
    STATUS
Quad_Serial_SendBreak( sio32Chan *IBC_SerialChan, Word boardAddr, Word chan,
                    Nat16 mode)
{
    Word    status;               /* Command Result from microcontroller  */

                                    /* Send command to microcontroller      */
    if ( sendMicroCommand( IBC_SerialChan, &status, sizeof(Word),
         4, IBC_CPU_APP | QUAD_SER_SEND_BREAK,  boardAddr, chan, mode )
         == ERROR ) return(ERROR);

                                  /* Check if command result is CMD OK    */
    return (wordFromBuf(&status, 0) == CMD_OK ? OK : ERROR);

} /* Quad_Serial_SendBreak() */

/****************************************************************************/
/* Function    : Quad_Serial_Open                                           */
/* Purpose     : Opens serial channel                                       */
/* Inputs      : Sio32 channel, IBC Board Address, channel                  */
/* Outputs     : Returns OK or ERROR                                        */
/****************************************************************************/
    STATUS
Quad_Serial_Open( sio32Chan *IBC_SerialChan, Word boardAddr, Word chan )
{
    Word    status;                 /* Command Status                       */

                                    /* Send command to microcontroller      */
    if ( sendMicroCommand( IBC_SerialChan, &status, sizeof(Word),
         3, IBC_CPU_APP | QUAD_SER_OPEN_CHAN, boardAddr, chan )
         == ERROR ) return(ERROR);

                                    /* Check if command result is CMD OK    */
    return (wordFromBuf(&status, 0) == CMD_OK ? OK : ERROR);

} /* Quad_Serial_Open() */

/****************************************************************************/
/* Function    : Quad_Serial_Close                                          */
/* Purpose     : Closes serial channel                                      */
/* Inputs      : Sio32 channel, IBC Board Address, channel                  */
/* Outputs     : Returns OK or ERROR                                        */
/****************************************************************************/
    STATUS
Quad_Serial_Close( sio32Chan *IBC_SerialChan, Word boardAddr, Word chan )
{
    Word    status;                 /* Command Status                       */

                                    /* Send command to microcontroller      */
    if ( sendMicroCommand( IBC_SerialChan, &status, sizeof(Word),
         3, IBC_CPU_APP | QUAD_SER_CLOSE_CHAN,  boardAddr, chan )
         == ERROR ) return(ERROR);

                                    /* Check if command result is CMD OK    */
    return (wordFromBuf(&status, 0) == CMD_OK ? OK : ERROR);

} /* Quad_Serial_Close() */

/****************************************************************************/
/* Function    : Quad_Serial_Flush                                          */
/* Purpose     : Flushes serial channel                                     */
/* Inputs      : Sio32 channel, IBC Board Address, chan                     */
/* Outputs     : Returns OK or ERROR                                        */
/****************************************************************************/
    STATUS
Quad_Serial_Flush( sio32Chan *IBC_SerialChan, Word boardAddr, Word chan )
{
    Int16   cmdStatus;              /* Command Status                       */
    Word    reply[2];               /* Command Result from microcontroller  */

                                    /* Send command to microcontroller      */
    if ( sendMicroCommand( IBC_SerialChan, &reply, sizeof(Word) * 2,
         3, IBC_CPU_APP | QUAD_SER_FLUSH,  boardAddr, chan )
         == ERROR ) return(ERROR);

                                    /* Check if command result is CMD OK    */
    if (wordFromBuf(&reply, 0) != CMD_OK)
        return(ERROR);              /* Command failed so return ERROR       */

                                    /* Command OK   */
    wordsFromBuf(reply, 1, &cmdStatus);

    return (OK);                    /* Return OK                            */
} /* Quad_Serial_Flush() */

/****************************************************************************/
/* Function    : Quad_Serial_RxBytes                                        */
/* Purpose     : Returns Number of Bytes in Receive queue                   */
/* Inputs      : Sio32 channel, IBC Board Address, termchar                 */
/* Outputs     : Returns OK or ERROR                                        */
/****************************************************************************/
    Int16
Quad_Serial_RxBytes( sio32Chan *IBC_SerialChan, Word boardAddr )
{
    Int16   cmdStatus;              /* Command Status                       */
    Word    reply[2];               /* Command Result from microcontroller  */
    Int16   bytes;                  /* Number of Bytes                      */
                                    /* Send command to microcontroller      */
    if ( sendMicroCommand( IBC_SerialChan, &reply, sizeof(Word) * 2,
         2, IBC_CPU_APP | QUAD_SER_RX_BYTES,  boardAddr )
         == ERROR ) return(ERROR);

                                    /* Check if command result is CMD OK    */
    if (wordFromBuf(&reply, 0) != CMD_OK)
        return(ERROR);              /* Command failed so return ERROR       */

                                    /* Command OK   */
    wordsFromBuf(reply, 2, &cmdStatus, &bytes);

    return (bytes);                 /* Return OK                            */
} /* Quad_Serial_RxBytes() */

/****************************************************************************/
/* Function    : Quad_Serial_TxBytes                                        */
/* Purpose     : Returns Number of Bytes in Transmit queue                  */
/* Inputs      : Sio32 channel, IBC Board Address, termchar                 */
/* Outputs     : Returns Int16                                              */
/****************************************************************************/
    Int16
Quad_Serial_TxBytes( sio32Chan *IBC_SerialChan, Word boardAddr )
{
    Int16   cmdStatus;              /* Command Status                       */
    Word    reply[2];               /* Command Result from microcontroller  */
    Int16   bytes;                  /* Number of Bytes                      */
                                    /* Send command to microcontroller      */
    if ( sendMicroCommand( IBC_SerialChan, &reply, sizeof(Word) * 2,
         2, IBC_CPU_APP | QUAD_SER_TX_BYTES,  boardAddr )
         == ERROR ) return(ERROR);

                                    /* Check if command result is CMD OK    */
    if (wordFromBuf(&reply, 0) != CMD_OK)
        return(ERROR);              /* Command failed so return ERROR       */

                                    /* Command OK   */
    wordsFromBuf(reply, 2, &cmdStatus, &bytes);

    return (bytes);                 /* Return OK                            */
} /* Quad_Serial_TxBytes() */

/****************************************************************************/
/* Function    : Quad_Serial_TermChars                                     */
/* Purpose     : Returns Number of Term Characters Received                 */
/* Inputs      : Sio32 channel, IBC Board Address, termchar                 */
/* Outputs     : Returns Int16                                              */
/****************************************************************************/
    Int16
Quad_Serial_TermChars( sio32Chan *IBC_SerialChan, Word boardAddr, Word chan )
{
    Int16   cmdStatus;              /* Command Status                       */
    Word    reply[2];               /* Command Result from microcontroller  */
    Int16   termChars;              /* Number of Term Chars                 */
                                    /* Send command to microcontroller      */
    if ( sendMicroCommand( IBC_SerialChan, &reply, sizeof(Word) * 2,
         3, IBC_CPU_APP | QUAD_SER_TERM_CHARS,  boardAddr, chan )
         == ERROR ) return(ERROR);

                                    /* Check if command result is CMD OK    */
    if (wordFromBuf(&reply, 0) != CMD_OK)
        return(ERROR);              /* Command failed so return ERROR       */

                                    /* Command OK   */
    wordsFromBuf(reply, 2, &cmdStatus, &termChars);

    return (termChars);             /* Return OK                            */
} /* Quad_Serial_TermChars() */

/****************************************************************************/
/* Function    : IBC_QUAD_SER_GetPsuStatus                                */
/* Purpose     : Read IBC Quad Serial Board Alarms                          */
/* Inputs      : Sio32 channel, Board Address, Various Alarms               */
/* Outputs     : Returns OK or ERROR                                        */
/****************************************************************************/
    STATUS
IBC_QUAD_SERIAL_GetPsuStatus( sio32Chan *IBC_SerialChan, Word boardAddr,
    Nat16 *psuStatus )
{
    Int16   cmdStatus;              /* Command Status                       */
    Word    reply[2];               /* Command Result from microcontroller  */

                                    /* Send command to microcontroller      */
    if ( sendMicroCommand( IBC_SerialChan, &reply, sizeof(Word) * 2,
         2, IBC_CPU_APP | QUAD_SER_GET_PSU_STATUS,  boardAddr )
         == ERROR ) return(ERROR);

                                    /* Check if command result is CMD OK    */
    if (wordFromBuf(&reply, 0) != CMD_OK)
        return(ERROR);              /* Command failed so return ERROR       */

                                    /* Command OK so update alarms          */
    *psuStatus =  wordFromBuf(&reply, sizeof(Word));

    return (OK);                    /* Return OK                            */
} /* IBC_QUAD_SERIAL_GetPsuStatus() */




















