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

RLY Interrupt

RLY Interrupt

Explanation

About RLY_Interrupt Sample Application Code

This sample application code demonstrates how to perform an interrupt when a single channel receives a relay (RLY) message using North Atlantic Industries' Single-Slot Kit (SSK) and their naibrd library. This demonstration includes user interaction for configuring settings and supports handling multiple interrupts as well as offboard interrupts. Below is a detailed walk-through and explanation of the code.

Include Declarations The application includes necessary standard library headers like stdio.h, stdlib.h, string.h, and time.h, along with specific headers for relay interrupt handling and general board access from the North Atlantic Industries' libraries: - nai_rly_int.h - nai_rly_cfg.h - nai_rly_int_ether.h - naiapp_interrupt.h - naiapp_interrupt_ether.h - naiapp_boardaccess_menu.h - naiapp_boardaccess_query.h - naiapp_boardaccess_access.h - naiapp_boardaccess_display.h - naiapp_boardaccess_utils.h - nai.h - naibrd.h - naibrd_rly.h

Global Configuration and Prototypes The application uses a global constant for the configuration file:

static const int8_t *CONFIG_FILE = (const int8_t *)"default_RLY_Interrupt.txt";

And a prototype for the internal function Run_RLY_Interrupt():

static bool_t Run_RLY_Interrupt();

Main Routine This is the entry point of the application, designed to assist in accessing and configuring the board.

#if defined (__VXWORKS__)
int32_t RLY_Interrupt(void)
#else
int32_t main(void)
#endif

Initialization: The program initializes relay and interrupt configurations using the initializeRLYConfigurations and initializeInterruptConfigurations functions.

Board Menu: It calls naiapp_RunBoardMenu with the configuration file to display a menu for board access. If successful, the program enters a loop to query the user for the card index and module number and sets the configuration accordingly.

Interrupt Handling: If the user does not choose to quit, the program calls Run_RLY_Interrupt() to handle the relay interruptions.

Exit: Finally, the program waits for the user to hit the Enter key to exit and closes all open card connections.

Run_RLY_Interrupt Function The function handles all steps required for setting up, processing, and clearing relay interrupts:

static bool_t Run_RLY_Interrupt()

Main Steps:

  1. Query for Channels:

    • It queries the user to set channel ranges using naiapp_query_ForChannelRange.

  2. Interrupt Trigger Status:

    • The function queries for the edge trigger status using GetRLYLatchStatusTriggerMode.

  3. Clear Interrupt Prompts:

    • Whether the user wants prompts for clearing interrupts using QueryUserForClearingInterruptPrompts.

  4. Onboard/Offboard Interrupts:

    • Queries if interrupts should be processed onboard or offboard using QueryUserForOnboardOffboardInterrupts.

  5. Interrupt Steering:

    • Queries where the interrupt should be sent out to using GetIntSteeringTypeFromUser.

  6. Install ISR:

    • Based on the user configurations, installs the ISR using naibrd_InstallISR either for onboard or offboard processing.

  7. Configure RLY interrupt:

    • Calls configureRLYToInterruptOnRx to configure the module for interrupting on RX.

  8. Initialize Message Queue:

    • Initializes message queues and threads for handling the interrupts with InitInterruptAppThread and UpdateThreadState.

  9. Enable Interrupts:

    • Enables interrupts on the configured module with enableRLYInterrupts.

  10. Handle and Display:

    • Processes the actual interrupt using handleRLYInterrupt while waiting for user-triggered interrupts.

  11. Clear Configuration:

    • Clears module and board configurations by calling enableRLYInterrupts with false and naibrd_UninstallISR.

API Functions and Callbacks Some specific API functions and callbacks utilized in the code include: - naibrd_InstallISR - naibrd_RLY_SetInterruptEdgeLevel - naibrd_RLY_SetIntVector - naibrd_RLY_SetInterruptSteering - naibrd_RLY_SetIntEnable - naibrd_RLY_ClearStatus - naibrd_RLY_SetRxEnable - naibrd_UninstallISR

These functions handle everything from installing the ISR, configuring the interrupt vectors, enabling and clearing interrupts, to eventually uninstalling the ISR after processing.

This sample application gives a comprehensive demonstration on setting up and handling relay-based interrupts using the North Atlantic Industries' libraries and tools.

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

The RLY_Interrupt program demonstrates how to perform an interrupt when a single channel receives
a rly message. The purpose of this program is to demonstrate the method calls in the naibrd library for performing
the interrupt. More information on this process can be found in the naibrd SSK Quick Guide(Interrupts) file.

This application differs from RLY_Interrupt_Basic in that it could handle multiple interrupts at once.
It also queries the user for the edge trigger value and whether the user should be prompted to clear an interrupt.
The application also has support for offboard interrupts.

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

/************************/
/* Include Declarations */
/************************/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
/*Common Module Specific Sample Program include files*/
#include "nai_rly_int.h"
#include "nai_rly_cfg.h"
#include "nai_rly_int_ether.h"
/* Common Sample Program include files */
#include "include/naiapp_interrupt.h"
#include "include/naiapp_interrupt_ether.h"
#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"

/* naibrd include files */
#include "nai.h"
#include "naibrd.h"

/* Module Specific NAI Board Library files */
#include "functions/naibrd_rly.h"

/*********************************************/
/* Application Name and Revision Declaration */
/*********************************************/
/*
static const int8_t *App_Name = "RLY Interrupt Basic";
static const int8_t *App_Rev = "1.0";
*/

static const int8_t *CONFIG_FILE = (const int8_t *)"default_RLY_Interrupt.txt";

/********************************/
/* Internal Function Prototypes */
/********************************/
static bool_t Run_RLY_Interrupt();

/**************************************************************************************************************/
/*****                                     Main Routine                                                   *****/
/**************************************************************************************************************/
/**************************************************************************************************************/
/**
<summary>

The main routine assists in gaining access to the board.

The following routines from the nai_sys_cfg.c file are
called to assist with accessing and configuring the board.

 - ConfigDevice
 - DisplayDeviceCfg
 - GetBoardSNModCfg
 - CheckModule

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

#if defined (__VXWORKS__)
int32_t RLY_Interrupt(void)
#else
int32_t main(void)
#endif
{
   bool_t stop = FALSE;
   int32_t cardIndex;
   int32_t moduleCnt;
   int32_t module;
   int8_t inputBuffer[80];
   int32_t inputResponseCnt;

   initializeRLYConfigurations(0, 0, 0, 0, 0, 0);
   initializeInterruptConfigurations(FALSE, FALSE, FALSE, 0, 0, 0, 0);

   if (naiapp_RunBoardMenu(CONFIG_FILE) == TRUE)
   {
      while (stop != TRUE)
      {
         /* Query the user for the card index */
         stop = naiapp_query_CardIndex(naiapp_GetBoardCnt(), 0, &cardIndex);
         inputRLYConfig.cardIndex = cardIndex;
         if (stop != TRUE)
         {
            check_status(naibrd_GetModuleCount(cardIndex, &moduleCnt));

            /* Query the user for the module number */
            stop = naiapp_query_ModuleNumber(moduleCnt, 1, &module);
            inputRLYConfig.module = module;
            if (stop != TRUE)
            {
               inputRLYConfig.modid = naibrd_GetModuleID(cardIndex, module);
               if ((inputRLYConfig.modid != 0))
               {
                  Run_RLY_Interrupt();
               }
            }
         }
         printf("\nType Q to quit or Enter key to restart application:\n");
         stop = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
      }
   }

   printf("\nType the Enter key to exit the program: ");
   naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
   naiapp_access_CloseAllOpenCards();

   return 0;
}
/**************************************************************************************************************/
/**
<summary>

This function is broken into the following major steps. These steps correspond with the steps provided
in the naibrd SSK Quick Guide(Interrupts) file.

2. Bus Interrupt Handling - Install ISR

   API CALLS - naibrd_InstallISR

3. Enable Module Interrupts- Configures module to interrupter when channel receives RLY message.

   API CALLS - naibrd_RLY_SetInterruptEdgeLevel, naibrd_RLY_SetIntVector, naibrd_RLY_SetInterruptSteering, naibrd_RLY_SetIntEnable

4. Not applicable to RLY module

5. Show Interrupt Handling - Check the mailbox to see if any interrupts occurred.

6. Re-arming Interrupts - Clear the status register to allow interrupts to occur again. This is done by writing to the status register.
   In this program, we use an API call to do this.

   API CALLS - naibrd_RLY_ClearStatus

7. Clear Module Configurations

   API CALLS - naibrd_RLY_SetRxEnable

8. Clear Board Configurations

   API CALLS - naibrd_UninstallISR

</summary>
*/
/**************************************************************************************************************/
static bool_t Run_RLY_Interrupt()
{
   bool_t bQuit = FALSE;

   int32_t minChannel;
   int32_t maxChannel;

   minChannel = 1;
   maxChannel = naibrd_RLY_GetChannelCount(inputRLYConfig.modid);

   /* Query for Channels to Operate on */
   bQuit = naiapp_query_ForChannelRange(&inputRLYConfig.minChannel, &inputRLYConfig.maxChannel, minChannel, maxChannel);

   /* Query for Trigger Status of interrupts */
   if (!bQuit)
   {
      bQuit = GetRLYLatchStatusTriggerMode(&inputInterruptConfig.interrupt_Edge_Trigger);
   }
   /* Query user if they'd like to be prompted for clearing interrupts */
   if (!bQuit) {
      bQuit = QueryUserForClearingInterruptPrompts(&inputInterruptConfig.bPromptForInterruptClear);
   }
   if (!bQuit) {
      bQuit = QueryUserForOnboardOffboardInterrupts(&inputInterruptConfig.bProcessOnboardInterrupts);
   }

   /* Query user for location interrupt will be sent out to */
   if (!bQuit)
   {
      bQuit = GetIntSteeringTypeFromUser(&inputInterruptConfig.steering);
   }

   if (!bQuit)
   {

      /**** 2. Implement Bus Interrupt Handling****/
      setIRQ(inputInterruptConfig.steering, &inputInterruptConfig.irq);
      inputInterruptConfig.cardIndex = inputRLYConfig.cardIndex;

      if (inputInterruptConfig.bProcessOnboardInterrupts == TRUE)
      {
         check_status(naibrd_InstallISR(inputInterruptConfig.cardIndex, inputInterruptConfig.irq, (nai_isr_t)IntOnboardIsr, NULL));
      }
      else
      {
         check_status(naibrd_InstallISR(inputInterruptConfig.cardIndex, inputInterruptConfig.irq, (nai_isr_t)IntOffboardIsr, (void*)&inputRLYConfig.cardIndex));
      }
      /****3. configure Module to perform interrupts****/
      configureRLYToInterruptOnRx(inputInterruptConfig, inputRLYConfig);

      /****Initialize Message Queue ****/
      InitInterruptAppThread(ONBOARD_INT, 0);
      nai_msDelay(10);
      UpdateThreadState(RUN);

      /****Enable Interrupts****/
      enableRLYInterrupts(inputRLYConfig, TRUE);

      /***5. Show Interrupt Handling (contains step 6) ***/
      rlyIntProcessFunc = handleRLYInterrupt;

      /***Request user triggers interrupt ***/
      DisplayMessage_RLYInterrupt(MSG_USER_TRIGGER_RLY_INT);

      /****Wait on program threads****/
      while (!isThreadStateTerminated()) {
      }
      bQuit = TRUE;

      /*****7. Clear Module Configurations*****/
      enableRLYInterrupts(inputRLYConfig, FALSE);

      /*****8. Clear Board Configurations *****/
      check_status(naibrd_UninstallISR(inputInterruptConfig.cardIndex));
   }

   return bQuit;
}

Help Bot

X