Integrator Resources

The official home for NAI Support

Not sure where to start? Try Quick Start Guide or ask a question below!

Toggle Components with Visual Button
JavaScript Form Processing

nai can cfg

nai can cfg

Explanation

About the Sample Application Code

This C code sample is a part of the software support kit (SSK) provided by North Atlantic Industries (NAI). It is designed to interact with NAI’s embedded function modules, specifically focusing on CAN (Controller Area Network) communication. Below is a walkthrough of the key components of this code:

Include Directives

The header files included at the beginning provide necessary declarations and function prototypes used in the program:

  • stdio.h, ctype.h, stdlib.h, string.h: Standard C libraries for input/output, character handling, standard library functions, and string manipulation.

  • Custom headers (naiapp_boardaccess_menu.h, naiapp_boardaccess_query.h, etc.) and CAN-specific headers (nai_can_cfg.h, nai_can_int.h, nai.h, naibrd.h, naibrd_can.h): These are used for accessing board-specific functions and CAN functionalities provided by NAI.

Key Functions

CAN Identification Functions

  • bool_t IsCAN(uint32_t moduleID): Determines if a given module ID corresponds to a CAN-capable module.

  • bool_t IsCAN_J1939(int32_t cardIndex, int32_t module, int32_t channel): Checks if the specified channel follows the J1939 protocol.

  • bool_t IsCAN_AB(int32_t cardIndex, int32_t module, int32_t channel): Checks if the specified channel follows the CAN AB protocol.

Configuration Functions

  • bool_t GetCANCfg(int32_t defcard, int32_t defmod, int32_t defchan, int32_t *cardIndex, int32_t *module, int32_t *canchan, bool_t *iscanAB): Prompts the user to specify the CAN configuration, including the card, module, and channel to be used.

  • bool_t QueryUserForTiming(int32_t cardIndex, int32_t module, int32_t channel, int32_t* prescaler, int32_t* sjw, int32_t* tseg1, int32_t* tseg2): Queries the user for timing parameters like prescaler, synchronization jump width (sjw), and time segments (tseg1, tseg2) for CAN bus configuration.

Filtering Functions

  • bool_t GetRxFiltering(int32_t cardIndex, int32_t module, int32_t canchan): Prompts the user to enable receiving of specific types of CAN messages (CAN-A, CAN-B, or both).

  • bool_t GetAccFiltering(int32_t cardIndex, int32_t module, int32_t canchan): Queries the user to enable Acceptance Mask/Code Filtering and applies the specified acceptance masks and codes to filter CAN messages.

Setting Protocols and Timing

  • void setCANTiming(int32_t cardIndex, int32_t module, nai_can_baud_rate_type_t can_timing, int32_t* channelList, int32_t channelListSize): Configures CAN timings for specified channels.

  • void setChannelToCANJ1939(int32_t cardIndex, int32_t module, int32_t modid, int32_t* channelList, int32_t channelListSize): Sets channels to CAN J1939 protocol for CB3 modules.

  • void setChannelToCANAB(int32_t cardIndex, int32_t module, int32_t modid, int32_t* channelList, int32_t channelListSize): Sets channels to CAN AB protocol for CB3 modules.

Helper Functions

  • char* getBaudRateString(nai_can_baud_rate_type_t baudRate): Returns a string description of the baud rate.

  • char* getProtocolString(nai_can_protocol_type_t protocol): Returns a string description of the CAN protocol.

  • char* getFaultTypeString(nai_can_swt_fault_type_t faultType): Returns a string description of the fault type.

  • FIFO* allocateSpaceForFIFO(int32_t maxNumFramesOnFIFO, int32_t sizeOfFramePayload): Allocates memory for FIFO (First In First Out) buffers used in CAN communication.

Main Communication Functions

  • bool_t clearRxFIFOChannel(int32_t cardIndex, int32_t module, int32_t channel): Empties the receive FIFO on the specified channel.

  • void transmitFIFOChannelData(int32_t cardIndex, int32_t module, int32_t channel, CanDataFrame* frameData, int32_t numOfFramesOnFifo, int32_t maxNumOfFrames): Transmits data from the FIFO buffer on the specified channel.

  • void transmitAllFIFOData(int32_t cardIndex, int32_t module, FIFO* fifoData[NAI_GEN5_CAN_MAX_CHANNEL_COUNT], int32_t min, int32_t max): Transmits all data from the FIFO buffers across multiple channels.

Summary

This code sample includes comprehensive functions for configuring and managing CAN communication, including setting protocols, obtaining user inputs for configurations, and handling data transmission and reception. It ensures robust handling of both J1939 and AB CAN protocols, and provides detailed user interaction for various configurations and settings.

This detailed functionality makes it ideal for users looking to integrate and test CAN communication with NAI embedded modules in their applications.

#include <stdio.h>
#include <ctype.h>
#include <stdlib.h>
#include <string.h>

/* Common Sample Program include files */
#include "include/naiapp_boardaccess_menu.h"
#include "include/naiapp_boardaccess_query.h"
#include "include/naiapp_boardaccess_access.h"
#include "include/naiapp_boardaccess_display.h"
#include "include/naiapp_boardaccess_utils.h"

/* Common CAN Sample Program include files */
#include "nai_can_cfg.h"
#include "nai_can_int.h"
/* naibrd include files */
#include "nai.h"
#include "naibrd.h"
#include "functions/naibrd_can.h"

bool_t IsCAN(uint32_t moduleID)
{
   bool_t bCANFunc = FALSE;
   switch (moduleID)
   {
      case NAI_MODULE_ID_P6:
      case NAI_MODULE_ID_PA:
      case NAI_MODULE_ID_CB1:
      case NAI_MODULE_ID_CB2:
      case NAI_MODULE_ID_CB3:
         bCANFunc = TRUE;
         break;
      default:
         bCANFunc = FALSE;
         break;
   }
   return bCANFunc;
}

bool_t IsCAN_J1939(int32_t cardIndex, int32_t module, int32_t channel)
{
   bool_t isJ1939 = FALSE;
   nai_can_protocol_type_t protocol;
   uint32_t modid = naibrd_GetModuleID(cardIndex, module);
   naibrd_CAN_GetProtocol(cardIndex, module, channel, &protocol);

   if (protocol == NAI_CAN_PROTOCOL_J1939)
   {
      isJ1939 = TRUE;
   }
   else if (modid == NAI_MODULE_ID_PA)
   {
      isJ1939 = TRUE;
   }

   return isJ1939;
}

bool_t IsCAN_AB(int32_t cardIndex, int32_t module, int32_t channel)
{
   bool_t isAB = FALSE;
   nai_can_protocol_type_t protocol;
   uint32_t modid = naibrd_GetModuleID(cardIndex, module);
   naibrd_CAN_GetProtocol(cardIndex, module, channel, &protocol);

   if (protocol == NAI_CAN_PROTOCOL_AB)
   {
      isAB = TRUE;
   }
   else if (modid == NAI_MODULE_ID_P6)
   {
      isAB = TRUE;
   }

   return isAB;
}

bool_t GetCANCfg(int32_t defcard, int32_t defmod, int32_t defchan, int32_t *cardIndex, int32_t *module, int32_t *canchan, bool_t *iscanAB)
{
   bool_t bQuit;
   bool_t bContinue;
   nai_status_t status;
   int32_t MaxModule, MaxChannel;
   uint32_t moduleID;

   *iscanAB = FALSE;

   /* Query user on the Card and Module to use for this example */
   bQuit = naiapp_query_CardIndex(naiapp_GetBoardCnt(), defcard, cardIndex);
   if (!bQuit)
   {
      status = check_status(naibrd_GetModuleCount(*cardIndex, &MaxModule));
      if (status == NAI_SUCCESS)
      {
         bContinue = TRUE;
         while (bContinue)
         {
            bQuit = naiapp_query_ModuleNumber(MaxModule, defmod, module);
            if (!bQuit)
            {
               /* Get the number of CAN channels on the module */
               moduleID = naibrd_GetModuleID(*cardIndex, *module);
               if (IsCAN(moduleID))
               {
                  MaxChannel = naibrd_CAN_GetChannelCount(moduleID);
                  bQuit = naiapp_query_ChannelNumber(MaxChannel, defchan, canchan);
                  bContinue = FALSE;
                  if (moduleID == NAI_MODULE_ID_P6 ||
                     moduleID == NAI_MODULE_ID_CB1)
                  {
                     *iscanAB = TRUE;
                  }
                  else
                  {
                     *iscanAB = FALSE;
                  }
               }
               else
               {
                  printf("ERROR: Module selected does not support CAN Functionality\n");
                  bContinue = FALSE;
                  bQuit = TRUE;
               }
            }
            else
               bContinue = FALSE;
         }
      }
   }
   return bQuit;
}

bool_t QueryUserForTiming(int32_t cardIndex, int32_t module, int32_t channel, int32_t* prescaler, int32_t* sjw, int32_t* tseg1, int32_t* tseg2)
{
   bool_t bQuit = FALSE;
   bool_t bContinue = TRUE;
   int32_t defprescaler;
   int32_t defsjw;
   int32_t deftseg1;
   int32_t deftseg2;
   int8_t inputBuffer[80];
   int32_t inputResponseCnt;

   if (IsCAN_AB(cardIndex, module, channel))
   {
      defprescaler = PRESCALER_1MBit;
      defsjw = SJW_1MBit;
      deftseg1 = TSEG1_1MBit;
      deftseg2 = TSEG2_1MBit;
   }
   else
   {
      defprescaler = PRESCALER_500K;
      defsjw = SJW_500K;
      deftseg1 = TSEG1_500K;
      deftseg2 = TSEG2_500K;
   }
   while (bContinue)
   {
      printf("\nSet the Prescaler (0x0 to 0x3F) [default=0x%02X] ", defprescaler);
      bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
      if (!bQuit)
      {
         if (inputResponseCnt == 0)
         {
            *prescaler = defprescaler;
            bContinue = FALSE;
         }
         else
         {
            *prescaler = naiapp_utils_HexStrToDecInt32((int8_t *)inputBuffer);

            if (*prescaler >= 0 || *prescaler <= 63)
            {
               bContinue = FALSE;
            }
            else
            {
               printf("\nInvalid prescaler value.");
            }
         }
      }
   }

   if (!bQuit)
   {
      bContinue = TRUE;

      while (bContinue)
      {
         printf("\nSet the Synchronization Jump Width (0x0 to 0x3) [default=0x%01X] ", defsjw);
         bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
         if (!bQuit)
         {
            if (inputResponseCnt == 0)
            {
               *sjw = defsjw;
               bContinue = FALSE;
            }
            else
            {
               *sjw = naiapp_utils_HexStrToDecInt32((int8_t *)inputBuffer);

               if (*sjw >= 0 || *sjw <= 3)
               {
                  bContinue = FALSE;
               }
               else
               {
                  printf("\nInvalid SJW value.");
               }
            }
         }
      }

      if (!bQuit)
      {
         bContinue = TRUE;

         while (bContinue)
         {
            printf("\nSet the Time Segment Before the Sample Point (0x1 to 0xF) [default=0x%01X] ", deftseg1);
            bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
            if (!bQuit)
            {
               if (inputResponseCnt == 0)
               {
                  *tseg1 = deftseg1;
                  bContinue = FALSE;
               }
               else
               {
                  *tseg1 = naiapp_utils_HexStrToDecInt32((int8_t *)inputBuffer);

                  if (*tseg1 >= 1 || *tseg1 <= 0xF)
                  {
                     bContinue = FALSE;
                  }
                  else
                  {
                     printf("\nInvalid time segment value.");
                  }
               }
            }
         }

         if (!bQuit)
         {
            bContinue = TRUE;

            while (bContinue)
            {
               printf("\nSet the Time Segment After the Sample Point (0x0 to 0x7) [default=0x%01X] ", deftseg2);
               bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
               if (!bQuit)
               {
                  if (inputResponseCnt == 0)
                  {
                     *tseg2 = deftseg2;
                     bContinue = FALSE;
                  }
                  else
                  {
                     *tseg2 = naiapp_utils_HexStrToDecInt32((int8_t *)inputBuffer);

                     if (*tseg2 >= 1 || *tseg2 <= 0xF)
                     {
                        bContinue = FALSE;
                     }
                     else
                     {
                        printf("\nInvalid time segment value.");
                     }
                  }
               }
            }
         }
      }
   }

   return bQuit;
}

bool_t GetRxFiltering(int32_t cardIndex, int32_t module, int32_t canchan)
{
   bool_t bQuit = FALSE;
   bool_t bContinue = TRUE;
   int8_t inputBuffer[80];
   int32_t inputResponseCnt;

   while (bContinue)
   {
      printf("\nDo you want to receive CAN-A (A) or CAN-B (B) Messages, or Both (E) Messages? [default=E] ");
      bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
      if (!bQuit)
      {
         if (inputResponseCnt == 0 || (toupper(inputBuffer[0]) == 'E'))
         {
            check_status(naibrd_CAN_SetABFilterEn(cardIndex, module, canchan, DEF_ACCEPTANCE_FILTER, FALSE));
            bContinue = FALSE;
         }
         else if (toupper(inputBuffer[0]) == 'A')
         {
            check_status(naibrd_CAN_SetABFilterEn(cardIndex, module, canchan, DEF_ACCEPTANCE_FILTER, TRUE));
            check_status(naibrd_CAN_SetStdExtFilter(cardIndex, module, canchan, DEF_ACCEPTANCE_FILTER, TRUE));
            bContinue = FALSE;
         }
         else if (toupper(inputBuffer[0]) == 'B')
         {
            check_status(naibrd_CAN_SetABFilterEn(cardIndex, module, canchan, DEF_ACCEPTANCE_FILTER, TRUE));
            check_status(naibrd_CAN_SetStdExtFilter(cardIndex, module, canchan, DEF_ACCEPTANCE_FILTER, FALSE));
            bContinue = FALSE;
         }
         else
         {
            printf("\nInvalid Value. Please Enter a Valid Response (A, B or E): ");
         }
      }
   }

   return bQuit;
}

bool_t GetAccFiltering(int32_t cardIndex, int32_t module, int32_t canchan)
{
   bool_t bQuit = FALSE;
   bool_t bContinue = TRUE;
   int8_t inputBuffer[80];
   int32_t inputResponseCnt;

   while (bContinue)
   {
      printf("\nDo you want to enable Acceptance Mask/Code Filtering? [default=N]: ");
      bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
      if (!bQuit)
      {
         if (inputResponseCnt == 0 || (toupper(inputBuffer[0]) == 'N'))
         {
            check_status(naibrd_CAN_SetEnFilterCount(cardIndex, module, canchan, 0));
            check_status(naibrd_CAN_ClearFilter(cardIndex, module, canchan, DEF_ACCEPTANCE_FILTER));
            bContinue = FALSE;
         }
         else if (toupper(inputBuffer[0]) == 'Y')
         {
            /* Since changes are being made to filter set, let's make sure CAN module holds off from acting on changes until we are done with filter configuration */
            check_status(naibrd_CAN_StartFilterChanges(cardIndex, module, canchan));

            /* Enable only the 1st filter */
            check_status(naibrd_CAN_SetEnFilterCount(cardIndex, module, canchan, 1));
            check_status(naibrd_CAN_SetAcceptCodeEn(cardIndex, module, canchan, DEF_ACCEPTANCE_FILTER, TRUE));
            while (bContinue)
            {
               int32_t value;

               printf("\nPlease enter the value (in hex) of the Acceptance Mask [default=0xFFFFFFFF]: ");
               bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);

               if (!bQuit)
               {
                  if (inputResponseCnt == 0)
                  {
                     check_status(naibrd_CAN_SetAcceptMask(cardIndex, module, canchan, DEF_ACCEPTANCE_FILTER, 0xFFFFFFFF));
                     bContinue = FALSE;
                  }
                  else
                  {
                     value = naiapp_utils_HexStrToDecInt32((int8_t *)inputBuffer);
                     if (value != -1)
                     {
                        check_status(naibrd_CAN_SetAcceptMask(cardIndex, module, canchan, DEF_ACCEPTANCE_FILTER, value));
                        bContinue = FALSE;
                     }
                     else
                     {
                        printf("\nInvalid Value. Please Enter a Valid Response (32-bit hex value): ");
                     }
                  }
               }
            }

            bContinue = TRUE;

            while (bContinue)
            {
               int32_t value;

               printf("\nPlease enter the value (in hex) of the Acceptance Code [default=0xFFFFFFFF]: ");
               bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
               if (!bQuit)
               {
                  if (inputResponseCnt == 0)
                  {
                     check_status(naibrd_CAN_SetAcceptCode(cardIndex, module, canchan, DEF_ACCEPTANCE_FILTER, 0xFFFFFFFF));
                     bContinue = FALSE;
                  }
                  else
                  {
                     value = naiapp_utils_HexStrToDecInt32((int8_t *)inputBuffer);

                     if (value != -1)
                     {
                        check_status(naibrd_CAN_SetAcceptCode(cardIndex, module, canchan, DEF_ACCEPTANCE_FILTER, value));
                        bContinue = FALSE;
                     }
                     else
                     {
                        printf("\nInvalid Value. Please Enter a Valid Response (32-bit hex value): ");
                     }
                  }
               }
            }

            /* Now apply all filter changes */
            check_status(naibrd_CAN_ApplyFilterChanges(cardIndex, module, canchan));
         }
         else
         {
            printf("\nInvalid Value. Please Enter a Valid Response (Y or N): ");
         }
      }
      else
      {
         bContinue = FALSE;
      }
   }

   return bQuit;
}

/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/

void setCANTiming(int32_t cardIndex, int32_t module, nai_can_baud_rate_type_t can_timing, int32_t* channelList, int32_t channelListSize)
{
   int32_t channel;
   int32_t listIndex;
   int32_t prescaler, sjw, tseg1, tseg2;

   getCANTimingParameters(can_timing, &prescaler, &sjw, &tseg1, &tseg2);

   for (listIndex = 0; listIndex < channelListSize; listIndex++)
   {
      channel = channelList[listIndex];
      naibrd_CAN_StartConfigChanges(cardIndex, module, channel);
      check_status(naibrd_CAN_SetBitTiming(cardIndex, module, channel, prescaler, sjw, tseg1, tseg2));
      naibrd_CAN_ApplyConfigChanges(cardIndex, module, channel);
   }

}

void getCANTimingParameters(nai_can_baud_rate_type_t can_timing, int32_t* prescaler, int32_t* sjw, int32_t* tseg1, int32_t* tseg2) {

   switch (can_timing)
   {
      case NAI_CAN_250K_BAUD:
         *prescaler = PRESCALER_250K;
         *sjw = SJW_250K;
         *tseg1 = TSEG1_250K;
         *tseg2 = TSEG2_250K;
         break;

      case NAI_CAN_500K_BAUD:
         *prescaler = PRESCALER_500K;
         *sjw = SJW_500K;
         *tseg1 = TSEG1_500K;
         *tseg2 = TSEG2_500K;
         break;

      case NAI_CAN_1M_BAUD:
         *prescaler = PRESCALER_1MBit;
         *sjw = SJW_1MBit;
         *tseg1 = TSEG1_1MBit;
         *tseg2 = TSEG2_1MBit;
         break;
   }

}

/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/

char* getBaudRateString(nai_can_baud_rate_type_t baudRate)
{
   char* baudRate_S = NULL;
   switch (baudRate)
   {
      case NAI_CAN_BAUD_UNASSIGNED:
         baudRate_S = "UNASSIGNED";
         break;

      case NAI_CAN_1M_BAUD:
         baudRate_S = "1Mbit";
         break;
      case NAI_CAN_500K_BAUD:
         baudRate_S = "500K";
         break;

      case NAI_CAN_250K_BAUD:
         baudRate_S = "250K";
         break;

      case NAI_CAN_125K_BAUD:
         baudRate_S = "125K";
         break;
      case NAI_CAN_100K_BAUD:
         baudRate_S = "100K";
         break;
   }
   return baudRate_S;
}

/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/

char* getProtocolString(nai_can_protocol_type_t protocol)
{
   char*  protocol_S = NULL;
   switch (protocol)
   {
      case NAI_CAN_PROTOCOL_UNASSIGNED:
         protocol_S = "UNASSIGNED";
         break;
      case NAI_CAN_PROTOCOL_AB:
         protocol_S = "AB";
         break;
      case NAI_CAN_PROTOCOL_J1939:
         protocol_S = "J1939";
         break;
   }

   return protocol_S;
}

char* getFaultTypeString(nai_can_swt_fault_type_t faultType)
{
   char* faultType_s = "NONE";

   switch (faultType)
   {

      case NAI_CAN_WIRE_DISCONNECT:

         faultType_s = "WIRE DISCONNECT";

         break;

      case NAI_CAN_WIRE_OPEN:

         faultType_s = "WIRE_OPEN";

         break;
      case NAI_CAN_MAIN_BUS_SHORT:

         faultType_s = "MAIN BUS SHORT";

         break;
      default:
         /* just return default faultType_s */
         break;
   }

   return  faultType_s;
}

/**************************************************************************************************************/
/**
<summary>
Sets the channels' protocols in channelList to CAN J1939.
Only CB3 modules support this function.

</summary>
*/
/**************************************************************************************************************/
void setChannelToCANJ1939(int32_t cardIndex, int32_t module, int32_t modid, int32_t* channelList, int32_t channelListSize)
{
   int32_t channel;
   int32_t listIndex;
   channel = -1;
   if (modid == NAI_MODULE_ID_CB3)
   {
      for (listIndex = 0; listIndex < channelListSize; listIndex++)
      {
         channel = channelList[listIndex];
         check_status(naibrd_CAN_SetProtocol(cardIndex, module, channel, NAI_CAN_PROTOCOL_J1939));
      }
   }
   else
   {
      if (modid == NAI_MODULE_ID_CB2)
      {
         printf("\nFunction does not support CB2\n");
      }
      else if (modid == NAI_MODULE_ID_CB1)
      {
         printf("\nFunction does not support CB1\n");
      }
   }
}

/**************************************************************************************************************/
/**
<summary>
Sets the channels' protocols within channelList to CAN AB.
Only CB3 modules support this function.

</summary>
*/
/**************************************************************************************************************/
void setChannelToCANAB(int32_t cardIndex, int32_t module, int32_t modid, int32_t* channelList, int32_t channelListSize)
{
   int32_t channel;
   int32_t listIndex;
   channel = -1;
   if (modid == NAI_MODULE_ID_CB3)
   {
      for (listIndex = 0; listIndex < channelListSize; listIndex++)
      {
         channel = channelList[listIndex];
         check_status(naibrd_CAN_SetProtocol(cardIndex, module, channel, NAI_CAN_PROTOCOL_AB));
      }
   }
   else
   {
      if (modid == NAI_MODULE_ID_CB2)
      {
         printf("\nFunction does not support CB2 \n");
      }
      else if (modid == NAI_MODULE_ID_CB1)
      {
         printf("\nFunction does not support CB1 \n");
      }
   }
}

/**************************************************************************************************************/
/**
<summary>
Sets the channels' protocols within the range (min,max) to CAN J1939.
Only CB3 modules support this function.

</summary>
*/
/**************************************************************************************************************/
void setChannelToCANJ1939_R(int32_t cardIndex, int32_t module, int32_t modid, int32_t minChannel, int32_t maxChannel)
{
   int32_t channel;
   channel = -1;
   if (modid == NAI_MODULE_ID_CB3)
   {
      for (channel = minChannel; channel <= maxChannel; channel++)
      {
         check_status(naibrd_CAN_SetProtocol(cardIndex, module, channel, NAI_CAN_PROTOCOL_J1939));
      }
   }
   else
   {
      if (modid == NAI_MODULE_ID_CB2)
      {
         printf("\nFunction does not support CB2\n");
      }
      else if (modid == NAI_MODULE_ID_CB1)
      {
         printf("\nFunction does not support CB1\n");
      }
   }
}

/**************************************************************************************************************/
/**
<summary>
Sets the channels' protocols within the range (min,max) to CAN AB.
Only CB3 modules support this function.

</summary>
*/
/**************************************************************************************************************/
void setChannelToCANAB_R(int32_t cardIndex, int32_t module, int32_t modid, int32_t minChannel, int32_t maxChannel)
{
   int32_t channel;
   channel = -1;
   if (modid == NAI_MODULE_ID_CB3)
   {
      for (channel = minChannel; channel <= maxChannel; channel++)
      {
         check_status(naibrd_CAN_SetProtocol(cardIndex, module, channel, NAI_CAN_PROTOCOL_AB));
      }
   }
   else
   {
      if (modid == NAI_MODULE_ID_CB2)
      {
         printf("\nFunction does not support CB2 \n");
      }
      else if (modid == NAI_MODULE_ID_CB1)
      {
         printf("\nFunction does not support CB1 \n");
      }
   }
}

/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/
void setTxEnable(int32_t cardIndex, int32_t module, int32_t min, int32_t max, bool_t enable) {
   int32_t chan;
   for (chan = min; chan <= max; chan++) {
      naibrd_CAN_StartConfigChanges(cardIndex, module, chan);
      naibrd_CAN_SetTxEnable(cardIndex, module, chan, enable);
      naibrd_CAN_ApplyConfigChanges(cardIndex, module, chan);
   }
}

/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/
void setRxEnable(int32_t cardIndex, int32_t module, int32_t min, int32_t max, bool_t enable) {
   int32_t chan;
   for (chan = min; chan <= max; chan++) {
      naibrd_CAN_StartConfigChanges(cardIndex, module, chan);
      naibrd_CAN_SetRxEnable(cardIndex, module, chan, enable);
      naibrd_CAN_ApplyConfigChanges(cardIndex, module, chan);
   }
}

/**************************************************************************************************************/
/**
<summary>
This function configures the baud rate of the can channels in the minChannel,maxChannel range to the values set
in inputCANConfig. Also Enables the channels to Rx
</summary>
*/
/**************************************************************************************************************/
void Cfg_Rx_CAN(CanConfig inputCANConfig)
{
   int32_t cardIndex = inputCANConfig.cardIndex;
   int32_t module = inputCANConfig.module;
   int32_t channel;
   int32_t minChannel = inputCANConfig.minChannel;
   int32_t maxChannel = inputCANConfig.maxChannel;

   int32_t prescaler;
   int32_t sjw;
   int32_t tseg1;
   int32_t tseg2;

   for (channel = minChannel; channel <= maxChannel; channel++)
   {

      getCANTimingParameters(inputCANConfig.baudRate, &prescaler, &sjw, &tseg1, &tseg2);

      setCANFIFOStatusConditions(cardIndex, module, channel);

      check_status(naibrd_CAN_SetBitTiming(inputCANConfig.cardIndex, inputCANConfig.module, channel, prescaler, sjw, tseg1, tseg2));
      check_status(naibrd_CAN_SetRxEnable(cardIndex, module, channel, TRUE));
   }

}
/**************************************************************************************************************/
/**
<summary>
This function configures the baud rate of the can channels in the minChannel,maxChannel range to the values set
in inputCANConfig. Also Enables the channels to Tx.
</summary>
*/
/**************************************************************************************************************/
void Cfg_Tx_CAN(CanConfig inputCANConfig)
{
   int32_t cardIndex = inputCANConfig.cardIndex;
   int32_t module = inputCANConfig.module;
   int32_t channel = inputCANConfig.module;
   int32_t minChannel = inputCANConfig.minChannel;
   int32_t maxChannel = inputCANConfig.maxChannel;

   int32_t prescaler;
   int32_t sjw;
   int32_t tseg1;
   int32_t tseg2;

   for (channel = minChannel; channel <= maxChannel; channel++)
   {

      getCANTimingParameters(inputCANConfig.baudRate, &prescaler, &sjw, &tseg1, &tseg2);

      check_status(naibrd_CAN_SetBitTiming(cardIndex, module, channel, prescaler, sjw, tseg1, tseg2));
      check_status(naibrd_CAN_SetTxEnable(cardIndex, module, channel, TRUE));
   }

}

/**************************************************************************************************************/
/**
<summary>
Interprets and prints the contents of the FIFO status register.

</summary>
*/
/**************************************************************************************************************/
void printFIFOStatusRx(uint32_t fifoStatus, FILE* stream)
{
   uint32_t Rx_FIFO_ALMOST_FULL = 1;
   uint32_t Rx_EMPTY = 1 << 4;
   uint32_t Rx_HIGH_WATERMARK_REACHED = 1 << 2;
   uint32_t Rx_LOW_WATERMARK_REACHED = 1 << 3;

   if (Rx_FIFO_ALMOST_FULL & fifoStatus)
   {
      fprintf(stream, "fifo Status = FIFO ALMOST FULL");
   }
   else if (Rx_EMPTY & fifoStatus)
   {
      fprintf(stream, "fifo Status = RX EMPTY");
   }
   else if (Rx_HIGH_WATERMARK_REACHED & fifoStatus)
   {
      fprintf(stream, "fifo Status = RX HIGH WATERMARK REACHED");
   }
   else if (Rx_LOW_WATERMARK_REACHED & fifoStatus)
   {
      fprintf(stream, "fifo Status = RX LOW WATERMARK REACHED");
   }
   else
   {
      fprintf(stream, "fifo Status = %#x", fifoStatus);
   }
}

/**************************************************************************************************************/
/**
<summary>
Sets the thresholds for the status register of the passed in channel
</summary>
*/
/**************************************************************************************************************/

void setCANFIFOStatusConditions(int32_t cardIndex, int32_t module, int32_t channel)
{
   int32_t writeVal;

   writeVal = 100;

   naibrd_CAN_SetTxBufferAlmostEmpty(cardIndex, module, channel, writeVal);

   writeVal = 32667;

   naibrd_CAN_SetRxBufferAlmostFull(cardIndex, module, channel, writeVal);

   writeVal = 20000;

   naibrd_CAN_SetRxBufferHighWatermark(cardIndex, module, channel, writeVal);

   writeVal = 5000;
   naibrd_CAN_SetRxBufferLowWatermark(cardIndex, module, channel, writeVal);

}

/**************************************************************************************************************/
/**
<summary>
Prints the fifo data inside the buffer param. Groups the data into frames with bytesPerFrame size.
</summary>
*/
/**************************************************************************************************************/
void printFIFOChannelData(int32_t channel, CanDataFrame* frameData, int32_t numFramesOnFifo, FILE* stream)
{
   int32_t index;
   uint32_t byte;
   fprintf(stream, "channel %d fifo Data = ", channel);

   for (index = 0; index < numFramesOnFifo; index++)
   {
      fprintf(stream, "(");
      for (byte = 0; byte < frameData[index].length; byte++)
      {
         fprintf(stream, ",0x%02X", frameData[index].data[byte]);
      }
      fprintf(stream, ")||");
      fprintf(stream, "\n");
   }

   if (index == 0)
      fprintf(stream, "\n");

}

/**************************************************************************************************************/
/**
<summary>
Prints all the fifo data found in fifoData.

</summary>
*/
/**************************************************************************************************************/
void printAllFIFOData(FIFO* fifoData[NAI_GEN5_CAN_MAX_CHANNEL_COUNT], FILE* fifoDataFile, int32_t min, int32_t max)
{
   CanDataFrame * buffer;
   int32_t numOfFramesOnFifo;
   int32_t channel;

   for (channel = min; channel <= max && fifoData[channel - 1] != NULL; channel++)
   {
      buffer = fifoData[channel - 1]->buffer;
      numOfFramesOnFifo = fifoData[channel - 1]->numOfFramesOnFifo;
      printFIFOChannelData(channel, buffer, numOfFramesOnFifo, fifoDataFile);
   }

}

/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/

void baudRateToString(char baudRate[50], nai_can_baud_rate_type_t can_timing) {
   baudRate[0] = '\0';
   switch (can_timing) {
      case NAI_CAN_250K_BAUD:
         strcpy(baudRate, "250K");
         break;

      case NAI_CAN_500K_BAUD:
         strcpy(baudRate, "500K");
         break;

      case NAI_CAN_1M_BAUD:
         strcpy(baudRate, "1MBit");
         break;
   }
}
/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/

void protocolToString(char baudRate[50], nai_can_protocol_type_t protocol) {
   baudRate[0] = '\0';

   switch (protocol) {
      case  NAI_CAN_PROTOCOL_J1939:
         strcpy(baudRate, "J1939");
         break;

      case NAI_CAN_PROTOCOL_AB:
         strcpy(baudRate, "AB");
         break;
      case NAI_CAN_PROTOCOL_UNASSIGNED:
         strcpy(baudRate, "UNASSIGNED");
         break;
   }
}
/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/

void channelListToString(char channelListString[50], int32_t* channelList, int32_t channelListSize) {

   char channelString[10];
   int32_t listIndex;
   int32_t channel;
   channelListString[0] = '\0';
   strcat(channelListString, "{");
   for (listIndex = 0; listIndex < channelListSize - 1; listIndex++) {
      channel = channelList[listIndex];
      sprintf(channelString, "%d", channel);
      strcat(channelListString, channelString);
      strcat(channelListString, ",");
   }

   if (channelListSize > 0) {
      channel = channelList[listIndex];
      sprintf(channelString, "%d", channel);
      strcat(channelListString, channelString);
      strcat(channelListString, "}");
   }

}
/**************************************************************************************************************/
/**
<summary>
Reads all the frames off the FIFO of the passed in channel and stores them in a buffer.
Returns the amount of the fifo that was filled.
</summary>
*/
/**************************************************************************************************************/
int32_t getFIFOChannelData(int32_t cardIndex, int32_t module, int32_t channel, CanDataFrame* frameData, int32_t maxFramesOnFIFO)
{

   int32_t i;
   nai_status_t status = NAI_SUCCESS;
   bool_t bIsModeA;
   int32_t uiOutMsgId;
   uint32_t uiOutLength = 0;
   int32_t outcount;
   int32_t outPGN;
   int32_t outSource;
   int32_t outDestination;
   int32_t index = 0;

   naibrd_CAN_GetRxFrameCount(cardIndex, module, channel, &outcount);
   for (i = 0; i < outcount; i++)
   {
      if (index < maxFramesOnFIFO)
      {
         if (IsCAN_AB(cardIndex, module, channel)) {
            status = naibrd_CAN_Receive_Ex(cardIndex, module, channel, frameData[index].maxLength, &bIsModeA, &uiOutMsgId, 4, frameData[index].data, &uiOutLength);
         }
         else if (IsCAN_J1939(cardIndex, module, channel)) {
            status = naibrd_CAN_Receive_J1939_Ex(cardIndex, module, channel, frameData[index].maxLength, &outPGN, &outSource, &outDestination, 4, frameData[index].data, &uiOutLength);
         }
         frameData[index].length = uiOutLength;
         if (status == NAI_SUCCESS)
         {
            index++;
         }
      }
   }
   return index;
}

/**************************************************************************************************************/
/**
<summary>
Read the fifo for channels min through max, and store the content in fifoData

</summary>
*/
/**************************************************************************************************************/
void getAllFIFOData(int32_t cardIndex, int32_t module, FIFO* fifoData[NAI_GEN5_CAN_MAX_CHANNEL_COUNT], int32_t min, int32_t max)
{
   int32_t channel;
   for (channel = min; channel <= max && fifoData[channel - 1] != NULL; channel++)
   {
      fifoData[channel - 1]->numOfFramesOnFifo = getFIFOChannelData(cardIndex, module, channel, fifoData[channel - 1]->buffer, fifoData[channel - 1]->maxFramesOnFifo);
   }
}

/**************************************************************************************************************/
/**
<summary>
emptys the Rx fifo on the given channel. Returns false if the function fails

</summary>
*/
/**************************************************************************************************************/
bool_t clearRxFIFOChannel(int32_t cardIndex, int32_t module, int32_t channel)
{
   int32_t i;
   bool_t bIsModeA;
   int32_t uiOutMsgId;
   int32_t uiOutLength = 0;
   int32_t outcount;
   int32_t outPGN;
   int32_t outSource;
   int32_t outDestination;
   int32_t bufferLength;

   uint8_t buffer[NAI_J1939_MAX_DATA_LEN];
   bufferLength = NAI_J1939_MAX_DATA_LEN;

   naibrd_CAN_GetRxFrameCount(cardIndex, module, channel, &outcount);
   for (i = 0; i < outcount; i++)
   {

      if (IsCAN_AB(cardIndex, module, channel)) {
         naibrd_CAN_Receive(cardIndex, module, channel, bufferLength, &bIsModeA, &uiOutMsgId, buffer, &uiOutLength);
      }
      else if (IsCAN_J1939(cardIndex, module, channel)) {
         naibrd_CAN_Receive_J1939(cardIndex, module, channel, bufferLength, &outPGN, &outSource, &outDestination, buffer, &uiOutLength);
      }
   }
   naibrd_CAN_GetRxFrameCount(cardIndex, module, channel, &outcount);

   return !outcount;
}
/**************************************************************************************************************/
/**
<summary>
Transmits the FIFO data found on a given channel. The channels fifo buffer is frameData.

</summary>
*/
/**************************************************************************************************************/
void transmitFIFOChannelData(int32_t cardIndex, int32_t module, int32_t channel, CanDataFrame* frameData, int32_t numOfFramesOnFifo, int32_t maxNumOfFrames)
{
   bool_t txMsgWaiting;
   int32_t PGN = 0xFEBF;
   int32_t priority = 0;
   int32_t destination = 0xFF;
   int32_t frame;
   bool_t isModeA = FALSE;

   for (frame = 0; frame < numOfFramesOnFifo; frame++)
   {
      if (frame < maxNumOfFrames)
      {
         if (IsCAN_J1939(cardIndex, module, channel)) {

            naibrd_CAN_SetTxEnable(cardIndex, module, channel, FALSE);
            naibrd_CAN_QueueTransmit_J1939_Ex(cardIndex, module, channel, PGN, priority, destination, 4, frameData[frame].data, frameData[frame].length);
            naibrd_CAN_GetTxMessageWaiting(cardIndex, module, channel, &txMsgWaiting);

            if (txMsgWaiting)
               naibrd_CAN_SetTxEnable(cardIndex, module, channel, TRUE);
            else
               printf("message not ready!\n");

         }
         else if (IsCAN_AB(cardIndex, module, channel)) {

            naibrd_CAN_SetTxEnable(cardIndex, module, channel, FALSE);
            naibrd_CAN_QueueTransmit_Ex(cardIndex, module, channel, isModeA, PGN, 4, frameData[frame].data, frameData[frame].length);
            naibrd_CAN_GetTxMessageWaiting(cardIndex, module, channel, &txMsgWaiting);

            if (txMsgWaiting)
               naibrd_CAN_SetTxEnable(cardIndex, module, channel, TRUE);
            else
               printf("message not ready!\n");
         }
      }
   }

}

/**************************************************************************************************************/
/**
<summary>
Transmits the FIFO data found on a given channel. The channels fifo buffer is frameData.

</summary>
*/
/**************************************************************************************************************/
void transmitFIFOChannelData_PGN(int32_t cardIndex, int32_t module, int32_t channel, int32_t PGN, CanDataFrame* frameData, int32_t numOfFramesOnFifo, int32_t maxNumOfFrames)
{
   bool_t txMsgWaiting;
   int32_t priority = 0;
   int32_t destination = 0xFF;
   int32_t frame;
   bool_t isModeA = FALSE;

   for (frame = 0; frame < numOfFramesOnFifo; frame++)
   {
      if (frame < maxNumOfFrames)
      {
         if (IsCAN_J1939(cardIndex, module, channel)) {

            naibrd_CAN_SetTxEnable(cardIndex, module, channel, FALSE);
            naibrd_CAN_QueueTransmit_J1939_Ex(cardIndex, module, channel, PGN, priority, destination, 4, frameData[frame].data, frameData[frame].length);
            naibrd_CAN_GetTxMessageWaiting(cardIndex, module, channel, &txMsgWaiting);

            if (txMsgWaiting)
               naibrd_CAN_SetTxEnable(cardIndex, module, channel, TRUE);
            else
               printf("message not ready!\n");

         }
         else if (IsCAN_AB(cardIndex, module, channel)) {

            naibrd_CAN_SetTxEnable(cardIndex, module, channel, FALSE);
            naibrd_CAN_QueueTransmit_Ex(cardIndex, module, channel, isModeA, PGN, 4, frameData[frame].data, frameData[frame].length);
            naibrd_CAN_GetTxMessageWaiting(cardIndex, module, channel, &txMsgWaiting);

            if (txMsgWaiting)
               naibrd_CAN_SetTxEnable(cardIndex, module, channel, TRUE);
            else
               printf("message not ready!\n");
         }
      }
   }

}

/**************************************************************************************************************/
/**
<summary>
transmits all the data found on each fifo in the fifoCollection.

</summary>
*/
/**************************************************************************************************************/
void transmitAllFIFOData(int32_t cardIndex, int32_t module, FIFO* fifoData[NAI_GEN5_CAN_MAX_CHANNEL_COUNT], int32_t min, int32_t max)
{
   int32_t channel;
   CanDataFrame * buffer;
   int32_t numOfFramesOnFifo;
   int32_t maxNumOfFrames;
   for (channel = min; channel <= max && fifoData[channel - 1] != NULL; channel++)
   {
      buffer = fifoData[channel - 1]->buffer;
      numOfFramesOnFifo = fifoData[channel - 1]->numOfFramesOnFifo;
      maxNumOfFrames = fifoData[channel - 1]->maxFramesOnFifo;
      transmitFIFOChannelData(cardIndex, module, channel, buffer, numOfFramesOnFifo, maxNumOfFrames);
   }
}

/**************************************************************************************************************/
/**
<summary>
transmits all the data found on each fifo in the fifoCollection.

</summary>
*/
/**************************************************************************************************************/

void transmitAllFIFOData_PGN(int32_t cardIndex, int32_t module, int32_t PGN, FIFO* fifoData[NAI_GEN5_CAN_MAX_CHANNEL_COUNT], int32_t min, int32_t max)
{
   int32_t channel;
   CanDataFrame * buffer;
   int32_t numOfFramesOnFifo;
   int32_t maxNumOfFrames;
   for (channel = min; channel <= max && fifoData[channel - 1] != NULL; channel++)
   {
      buffer = fifoData[channel - 1]->buffer;
      numOfFramesOnFifo = fifoData[channel - 1]->numOfFramesOnFifo;
      maxNumOfFrames = fifoData[channel - 1]->maxFramesOnFifo;
      transmitFIFOChannelData_PGN(cardIndex, module, channel, PGN, buffer, numOfFramesOnFifo, maxNumOfFrames);
   }
}

/**************************************************************************************************************/
/**
<summary>
Enables transmit and Receive on all channels so the address claiming process can occur. Address claiming needs to happen in order
For the CAN channels to transmit and receive messages.

</summary>
*/
/**************************************************************************************************************/
void claimAddresses(int32_t card, int32_t mod, int32_t min, int32_t max)
{
   int32_t status = NAI_SUCCESS;
   int32_t chan;
   int32_t srcAddress = 0;
   int32_t claimStatus = 0;
   int32_t baseAddress = 192; /*0xC0*/

   int32_t numOfWaits = 0;

   for (chan = min; chan <= max; chan++)
   {
      naibrd_CAN_StartConfigChanges(card, mod, chan);

      naibrd_CAN_SetRxEnable(card, mod, chan, TRUE);
      naibrd_CAN_SetTxEnable(card, mod, chan, TRUE);

      naibrd_CAN_ApplyConfigChanges(card, mod, chan);
   }

   for (chan = min; chan <= max; chan++)
   {
      status = naibrd_CAN_SetAddress(card, mod, chan, (baseAddress + (chan - 1)));
      if (status == NAI_SUCCESS)
      {
         do
         {
            /* Wait for address to have a chance to be claimed. */
            naibrd_Wait(500000); /* 500 mS */
            numOfWaits++;
            status = naibrd_CAN_GetAddress(card, mod, chan, &srcAddress, &claimStatus);

         } while (claimStatus != 2 && numOfWaits <= 10);

         if (srcAddress != (baseAddress + (chan - 1)))
            printf("Failed to claim Source Address: 0x%x\n", (baseAddress + (chan - 1)));
         else
            printf("Channel %d succeeded in claiming Address 0x%x\n", chan, srcAddress);
      }
   }

   for (chan = min; chan <= max; chan++)
   {
      naibrd_CAN_StartConfigChanges(card, mod, chan);

      naibrd_CAN_SetRxEnable(card, mod, chan, FALSE);
      naibrd_CAN_SetTxEnable(card, mod, chan, FALSE);

      naibrd_CAN_ApplyConfigChanges(card, mod, chan);
   }
}

/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/

FIFO* allocateSpaceForFIFO(int32_t maxNumFramesOnFIFO, int32_t sizeOfFramePayload)
{
   FIFO* fifo;
   int32_t bufferIndex;
   int32_t numOfFramesAllocated = 0;
   fifo = (FIFO*)malloc(sizeof(FIFO));
   fifo->buffer = (CanDataFrame*)malloc(sizeof(CanDataFrame)* maxNumFramesOnFIFO);

   fifo->fifoStatus = 0;
   fifo->numOfFramesOnFifo = 0;

   for (bufferIndex = 0; bufferIndex < maxNumFramesOnFIFO; bufferIndex++)
   {
      numOfFramesAllocated++;
      fifo->buffer[bufferIndex].maxLength = sizeOfFramePayload;
      fifo->buffer[bufferIndex].length = 0;
      fifo->buffer[bufferIndex].data = (uint32_t*)malloc(sizeof(uint32_t) * sizeOfFramePayload);
   }
   fifo->maxFramesOnFifo = maxNumFramesOnFIFO;

   return fifo;

}

/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/

void deallocSpaceForFIFO(FIFO* fifo)
{
   int32_t bufferIndex;

   /* Dealloc frames */
   for (bufferIndex = 0; bufferIndex < fifo->maxFramesOnFifo; bufferIndex++)
   {
      free(fifo->buffer[bufferIndex].data);
   }
   /* dealloc fifo */
   free(fifo->buffer);
   free(fifo);

}

/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/

bool_t isInputValidChannel(int8_t inputBuffer[80], int32_t* channelOut)
{
   bool_t inputValid = FALSE;
   int32_t channel;
   if (isdigit(inputBuffer[0]))
   {
      channel = (int32_t)(inputBuffer[0] - '0');

      if (channel >= 1 && channel <= NAI_GEN5_CAN_MAX_CHANNEL_COUNT)
      {
         inputValid = TRUE;
         *channelOut = channel;
      }
      else
      {
         inputValid = FALSE;
         *channelOut = -1;
      }
   }

   return inputValid;
}

/**************************************************************************************************************/
/**
<summary>
Querys the user for a range defining the size of the payload in a can frame.

</summary>
*/
/**************************************************************************************************************/
bool_t QueryForPayloadRange(int32_t *min, int32_t *max, int32_t minPayload, int32_t maxPayload)
{
   bool_t bQuit = FALSE;
   int32_t minTemp = 0;
   int32_t maxTemp = 0;
   int8_t inputBuffer[80];
   int32_t inputResponseCnt;

   printf("\nPlease choose a minimum payload between (%d - %d). Default is (%d):", minPayload, maxPayload, minPayload);
   bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
   if (!bQuit)
   {
      naiapp_query_NumberFromResponse(&minTemp, inputBuffer, inputResponseCnt);

      if (minTemp >= minPayload && maxTemp <= maxPayload)
      {
         *min = minTemp;
      }
      else
      {
         *min = minPayload;
      }

      printf("\nPlease choose a maximum payload between (%d - %d). Default is (%d):", *min, maxPayload, maxPayload);
      bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
      if (!bQuit)
      {
         naiapp_query_NumberFromResponse(&maxTemp, inputBuffer, inputResponseCnt);

         if (maxTemp >= *min && maxTemp <= maxPayload)
         {
            *max = maxTemp;
         }
         else
         {
            *max = maxPayload;
         }
      }
   }

   return bQuit;
}

/**************************************************************************************************************/
/**
<summary>
Querys the user for the size of the payload in a can frame.

</summary>
*/
/**************************************************************************************************************/
bool_t QueryForPayload(int32_t *size, int32_t minPayload, int32_t maxPayload)
{
   bool_t bQuit = FALSE;
   int32_t sizeTemp = 0;
   int8_t inputBuffer[80];
   int32_t inputResponseCnt;

   printf("Please choose a payload size between (%d - %d). Default is (%d):", minPayload, maxPayload, maxPayload);
   bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
   if (!bQuit)
   {
      naiapp_query_NumberFromResponse(&sizeTemp, inputBuffer, inputResponseCnt);

      if ((sizeTemp >= minPayload && sizeTemp <= maxPayload))
      {
         *size = sizeTemp;
      }
      else
      {
         *size = maxPayload;
      }
      printf("\n");
   }

   return bQuit;
}
/**************************************************************************************************************/
/**
<summary>
Querys the user for the number of frames to send on a channel in a given transmission.

</summary>
*/
/**************************************************************************************************************/
bool_t QueryForNumOfFramesToTransmit(int32_t* frames, int32_t minFrame, int32_t maxFrame)
{
   bool_t bQuit = FALSE;
   int32_t temp = 0;
   int8_t inputBuffer[80];
   int32_t inputResponseCnt;

   printf("\nChoose the number of frames you wish to send in a given transmission. Choose between (%d - %d). Default is (%d):", minFrame, maxFrame, minFrame);
   bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
   if (!bQuit)
   {
      naiapp_query_NumberFromResponse(&temp, inputBuffer, inputResponseCnt);

      if (temp >= minFrame && temp <= maxFrame)
      {
         *frames = temp;
      }
      else
      {
         *frames = minFrame;
      }
   }
   return bQuit;
}

/**************************************************************************************************************/
/**
<summary>
Querys the user for the protocol to use.

</summary>
*/
/**************************************************************************************************************/
bool_t QueryForChannelProtocol(bool_t* isJ1939)
{
   bool_t bQuit = FALSE;
   int8_t inputBuffer[80];
   int32_t inputResponseCnt;

   printf("\nWould you like to use the J1939 protocol? No(N) or Yes(Y) (Default: Y): ");
   bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
   if (!bQuit)
   {
      if ((inputBuffer[0] == 'N') || (inputBuffer[0] == 'n'))
      {
         *isJ1939 = FALSE;
      }
      else
      {
         *isJ1939 = TRUE;
      }
   }
   return bQuit;
}

/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/

bool_t QueryUserForCANTiming(nai_can_baud_rate_type_t* baudRate, bool_t isJ1939)
{
   bool_t bQuit = FALSE;
   int8_t inputBuffer[80];
   int32_t inputResponseCnt;

   if (isJ1939)
   {
      printf("\nPlease select a Baud Rate. Options: 250K(1) , 500K(2). Default is 500K:");
      bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
      if (!bQuit)
      {
         if (inputBuffer[0] == '1')
         {
            *baudRate = NAI_CAN_250K_BAUD;
         }
         else
         {
            *baudRate = NAI_CAN_500K_BAUD;
         }
      }
   }
   else
   {
      printf("\nPlease select a Baud Rate. Options: 250K(1) , 500K(2) , 1Mbit(3). Default is 500K:");
      bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
      if (!bQuit)
      {
         if (inputBuffer[0] == '1')
         {
            *baudRate = NAI_CAN_250K_BAUD;
         }
         else if (inputBuffer[0] == '3')
         {
            *baudRate = NAI_CAN_1M_BAUD;
         }
         else
         {
            *baudRate = NAI_CAN_500K_BAUD;
         }
      }
   }

   return bQuit;
}

/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/

bool_t QueryUserForAddressClaiming(bool_t* claimAddresses)
{
   bool_t bQuit = FALSE;
   int8_t inputBuffer[80];
   int32_t inputResponseCnt;

   printf("\nWould you like to claim Addresses for channels? No(N) or Yes(Y) (Default: Y): ");
   bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
   if (!bQuit)
   {
      if ((inputBuffer[0] == 'N') || (inputBuffer[0] == 'n'))
      {
         *claimAddresses = FALSE;
      }
      else
      {
         *claimAddresses = TRUE;
      }
   }

   return bQuit;
}

/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/

bool_t QueryForPGN(uint32_t* PGN)
{
   bool_t bQuit = FALSE;
   uint32_t temp = 0;
   uint32_t minPGN = 0xFE00;
   uint32_t maxPGN = 0xFFFF;
   uint32_t defaultPGN = 0xFEBF;
   int8_t inputBuffer[80];
   int32_t inputResponseCnt;

   printf("\nChoose the PGN of the message you wish to transmit. Choose between (%X - %X). Default PGN is (%X):", minPGN, maxPGN, defaultPGN);
   bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
   if (!bQuit)
   {
      temp = naiapp_utils_HexStrToDecUInt32(inputBuffer);

      if (temp >= minPGN && temp <= maxPGN)
      {
         *PGN = temp;
      }
      else
      {
         *PGN = defaultPGN;
      }
   }
   return bQuit;
}

/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/

bool_t QueryChannelForTxEnable(bool_t* txEnable)
{

   bool_t bQuit = FALSE;
   int8_t inputBuffer[80];
   int32_t inputResponseCnt;

   printf("\nWould you like to enable transmissions? No(N) or Yes(Y) (Default: Y):");

   bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);

   if (!bQuit)
   {
      if ((inputBuffer[0] == 'N') || (inputBuffer[0] == 'n'))
      {
         *txEnable = FALSE;
      }
      else
      {
         *txEnable = TRUE;
      }
   }

   return bQuit;
}

/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/

bool_t QueryChannelForRxEnable(bool_t* rxEnable)
{
   bool_t bQuit = FALSE;
   int8_t inputBuffer[80];
   int32_t inputResponseCnt;

   printf("\nWould you like to enable receiving? No(N) or Yes(Y) (Default: Y):");

   bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);

   if (!bQuit)
   {
      if ((inputBuffer[0] == 'N') || (inputBuffer[0] == 'n'))
      {
         *rxEnable = FALSE;
      }
      else
      {
         *rxEnable = TRUE;
      }
   }

   return bQuit;

}

/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/

bool_t QueryForChannels(int32_t *minChannel, int32_t* maxChannel)
{
   bool_t bQuit;
   bool_t inputReceived = FALSE;
   int32_t channel;
   int8_t inputBuffer[80];
   int32_t inputResponseCnt;

   do
   {
      printf("\nEnter a channel [1-%d] or type A for ALL:", NAI_GEN5_CAN_MAX_CHANNEL_COUNT);
      bQuit = naiapp_query_ForQuitResponse(100, NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);

      if (!bQuit)
      {
         if (inputBuffer[0] != 'A' && inputBuffer[0] != 'a')
         {
            if (isInputValidChannel(inputBuffer, &channel) && !bQuit)
            {
               *minChannel = channel;
               *maxChannel = channel;
               inputReceived = TRUE;
            }
            else
            {
               printf("\nInvalid input try again");
            }
         }
         else
         {
            *minChannel = 1;
            *maxChannel = NAI_GEN5_CAN_MAX_CHANNEL_COUNT;
            inputReceived = TRUE;
         }
      }
   } while (!inputReceived && !bQuit);

   return bQuit;

}

/**************************************************************************************************************/
/**
<summary>

</summary>
*/
/**************************************************************************************************************/

void initializeCANConfigurations(int32_t cardIndex, int32_t module, int32_t modid, int32_t channel, int32_t maxChannel, int32_t minChannel, int32_t maxPayload, int32_t minPayload, nai_can_baud_rate_type_t baudRate)
{
   inputCANConfig.cardIndex = cardIndex;
   inputCANConfig.module = module;
   inputCANConfig.modid = modid;
   inputCANConfig.channel = channel;
   inputCANConfig.maxChannel = maxChannel;
   inputCANConfig.minChannel = minChannel;
   inputCANConfig.maxPayload = maxPayload;
   inputCANConfig.minPayload = minPayload;
   inputCANConfig.baudRate = baudRate;
}

Help Bot

X