AD FifoMenu
Edit this on GitLab
AD FifoMenu Sample Application (SSK 1.x)
Overview
The AD FifoMenu sample application demonstrates how to configure and use FIFO-based continuous data capture on analog-to-digital channels using the NAI Software Support Kit (SSK 1.x). Where the AD BasicOps sample performs single-shot reads of instantaneous channel values, AD FifoMenu shows you how to set up buffered, continuous sampling — capturing a stream of AD conversions into a hardware FIFO that your application drains at its own pace.
FIFO capture provides several advantages over single-shot reads:
-
Continuous sampling — the module converts at a configurable sample rate without host intervention, so you capture data at precise intervals regardless of software timing jitter.
-
Buffered data — samples accumulate in a per-channel hardware FIFO. You read them in bulk when convenient rather than polling one value at a time.
-
Configurable thresholds — high, low, almost-full, and almost-empty thresholds let you trigger interrupts or poll intelligently so your application knows when data is ready or when the buffer is about to overflow.
-
Timestamped samples — an optional timestamp word accompanies each sample, giving you a hardware-generated time reference for every conversion.
This sample supports the following AD module types: AD1 through AD6 and ADE through ADG. It also works with combination modules that include AD functionality: CME, CMF, and CMG. It serves as a practical API reference — each menu command maps directly to one or more naibrd_AD_*() API calls that you can lift into your own code.
Prerequisites
Before running this sample, make sure you have:
-
An NAI board with an AD module installed (AD1-AD6 or ADE-ADG).
-
SSK 1.x installed on your development host.
-
The sample applications built. Refer to the SSK 1.x build instructions for your platform if you have not already compiled them.
How to Run
Launch the AD_FifoMenu executable from your build output directory. On startup the application looks for a configuration file (default_ADFifoMenu.txt). On the first run, this file will not exist — the application will present an interactive board menu where you configure a board connection, card index, and module slot. You can save this configuration so that subsequent runs skip the menu and connect automatically. Once connected, a channel status display and command menu let you exercise each FIFO operation.
Board Connection and Module Selection
|
Note
|
This startup sequence is common to all NAI sample applications. The board connection and module selection code shown here is not specific to AD. |
The main() function follows a standard SSK 1.x startup flow:
-
Call
naiapp_RunBoardMenu()to load a saved configuration file (if one exists) or present the interactive board menu. The configuration file (default_ADFifoMenu.txt) is not included with the SSK — it is created when the user saves their connection settings from the board menu. On the first run, the menu will always appear. -
Query the user for a card index with
naiapp_query_CardIndex(). -
Query for a module slot with
naiapp_query_ModuleNumber(). -
Retrieve the module ID with
naibrd_GetModuleID()so downstream code can adapt to the specific AD variant installed.
#if defined (__VXWORKS__)
int32_t AD_FifoMenu(void)
#else
int32_t main(void)
#endif
{
bool_t stop = FALSE;
int32_t cardIndex;
int32_t moduleCnt;
int32_t module;
uint32_t moduleID = 0;
int8_t inputBuffer[80];
int32_t inputResponseCnt;
if (naiapp_RunBoardMenu(CONFIG_FILE) == TRUE)
{
while (stop != TRUE)
{
stop = naiapp_query_CardIndex(naiapp_GetBoardCnt(), 0, &cardIndex);
if (stop != TRUE)
{
check_status(naibrd_GetModuleCount(cardIndex, &moduleCnt));
stop = naiapp_query_ModuleNumber(moduleCnt, 1, &module);
if (stop != TRUE)
{
moduleID = naibrd_GetModuleID(cardIndex, module);
if ((moduleID != 0))
{
RunMenu(cardIndex, module, moduleID);
}
}
}
printf("\nType Q to quit or Enter key to restart application:\n");
stop = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR,
inputBuffer, &inputResponseCnt);
}
}
naiapp_access_CloseAllOpenCards();
return 0;
}
|
Important
|
Common connection errors you may encounter at this stage:
|
Program Structure
Application Parameters
Once connected, the sample populates an naiapp_AppParameters_t struct that every command function receives:
ad_fifoOps_params.cardIndex = cardIndex;
ad_fifoOps_params.module = module;
ad_fifoOps_params.channel = 1;
ad_fifoOps_params.modId = modid;
ad_fifoOps_params.maxChannels = naibrd_AD_GetChannelCount(modid);
In your own application, you will need to track the same values: card index, module number, active channel, module ID, and channel count. The naibrd_AD_GetChannelCount() call returns the number of AD channels available on the installed module variant.
Command Menu
The RunMenu() function displays the current channel configuration, then presents a command menu. The menu system is a sample convenience — in your own code, call these API functions directly.
| Command | Shortcut | Description |
|---|---|---|
Software Trigger |
|
Issue a software trigger to start FIFO sampling |
Read FIFO |
|
Read a specified number of samples from a channel’s FIFO |
Display FIFO Status |
|
Show the FIFO status register flags for all channels |
Clear FIFO |
|
Empty a channel’s FIFO buffer |
Configure FIFO |
|
Set up a channel’s range, thresholds, sample rate, buffer control, and trigger control |
Before each command prompt, the sample displays a channel configuration summary showing the current state of every channel: words in FIFO, thresholds, sample delay, FIFO size, sample rate, break frequency, buffer control, trigger control, and the status register. This display calls naibrd_AD_GetFIFO*() functions for each channel and gives you a snapshot of the module’s FIFO state.
FIFO Configuration (CFG)
The Configure FIFO command sets up all parameters needed for FIFO-based capture on a single channel. This is the most important step — the FIFO will not collect data until the channel is properly configured and a trigger is issued.
Channel State
To enable or disable a channel for FIFO capture, call naibrd_AD_SetChannelState(). An inactive channel (state 0) does not participate in sampling.
naibrd_AD_SetChannelState(cardIndex, module, channel, chanState);
|
Important
|
AD4 bank constraint: On AD4 modules, channels are divided into two banks (channels 1-8 and channels 9-16). Both banks must have the same number of active channels. If the banks are mismatched, the sample prints an error. Ensure you activate the same count of channels in each bank when working with AD4 modules. |
Range and Polarity
To configure the input voltage range and polarity on your channel, call naibrd_AD_SetRange():
if ((Range & NAI_AD_RANGE_BIPOLAR) == NAI_AD_RANGE_BIPOLAR)
mode = NAI_AD_RANGE_MODE_BIPOLAR;
else
mode = NAI_AD_RANGE_MODE_UNIPOLAR;
naibrd_AD_SetRange(cardIndex, module, channel, mode, Range);
The Range parameter is a numeric code that encodes both voltage range and polarity. Bit 4 selects bipolar (1) or unipolar (0). The lower bits select the voltage range. Available ranges vary by module type — consult your module’s manual for the supported values. For a detailed explanation of AD range and polarity configuration, see the AD BasicOps guide.
FIFO Thresholds
Thresholds control when the module signals that the FIFO has reached significant fill levels. To set the low and high thresholds, call:
naibrd_AD_SetFIFOLoThreshold(cardIndex, module, channel, LoThreshold);
naibrd_AD_SetFIFOHiThreshold(cardIndex, module, channel, HiThreshold);
-
LoThreshold— the FIFO count below which the low-threshold status flag is set. The sample defaults to 10. -
HiThreshold— the FIFO count above which the high-threshold status flag is set. The sample defaults to 15.
Both values must be between 0 and the maximum FIFO count for your module, which the sample retrieves with naibrd_AD_GetMaxFIFOCount(modid).
On Gen 5 boards, two additional threshold registers are available:
naibrd_AD_SetFIFOAlmostEmpty(cardIndex, module, channel, AlmostEmpty);
naibrd_AD_SetFIFOAlmostFull(cardIndex, module, channel, AlmostFull);
These provide finer-grained buffer management. The sample defaults to 5 for almost-empty and 18 for almost-full.
Sample Rate and Timing
To set the conversion rate, call naibrd_AD_SetFIFORate():
naibrd_AD_SetFIFORate(cardIndex, module, channel, SampleRate);
The valid range depends on your board generation:
-
Gen 5 boards — 0 to 250,000 samples per second.
-
Gen 3 boards — 0 to 65,535.
To introduce a delay before sampling begins after a trigger, call:
naibrd_AD_SetFIFODelay(cardIndex, module, channel, SampleDelay);
On Gen 5 boards, you can also set a skip count to decimate the sample stream:
naibrd_AD_SetFIFOSkip(cardIndex, module, channel, SkipCount);
Break Frequency
To set the analog filter break frequency, call:
naibrd_AD_SetBreakFrequency(cardIndex, module, channel, BreakFreq);
-
Gen 5 boards — 0 to 250,000 Hz.
-
Gen 3 boards — 0 to 10,000 Hz.
A value of 0 typically disables the filter. Consult your module’s manual for the supported break frequencies on your specific AD variant.
FIFO Size
To set how many samples the FIFO collects per trigger, call:
naibrd_AD_SetFIFOSize(cardIndex, module, channel, SamplesPerTrigger);
The maximum value is determined by naibrd_AD_GetMaxFIFOCount(modid). The sample defaults to 20.
Buffer Control
The buffer control register determines what data words are stored in the FIFO for each sample. To configure it, call:
naibrd_AD_SetFIFOCtrl(cardIndex, module, channel, BufferControl);
The register is a bitmapped value. The available bits differ by board generation:
Gen 5 boards:
-
Bit 2 — Filter: store filtered data (1) or unfiltered data (0).
-
Bit 4 — Timestamp: append a 16-bit timestamp counter to each sample.
Valid combinations: 0, 4, 16, 20.
Gen 3 boards:
-
Bit 0 — 16-bit high data word.
-
Bit 1 — 8-bit low data word (combine with bit 0 for 24-bit resolution).
-
Bit 2 — Filter: store filtered data (1) or unfiltered data (0).
-
Bit 4 — Timestamp: append a 16-bit timestamp counter to each sample.
Valid combinations: 1, 3, 5, 7, 16, 17, 19, 21, 23.
The buffer control setting directly affects how many FIFO words each sample consumes, which determines how many complete samples fit in the FIFO. The GetSamplesInFifo() helper in the sample calculates this by dividing the FIFO word count by the words-per-sample.
Trigger Control
The trigger control register determines how FIFO sampling is initiated. To configure it, call:
naibrd_AD_SetFIFOTrigCtrl(cardIndex, module, channel, TriggerControl);
Gen 5 boards (bitmapped):
-
Bits 0-1 — Trigger type:
0x0= continuous,0x1= single sample. -
Bits 4-5 — Trigger edge:
0x00= hardware positive edge,0x10= hardware negative edge,0x20= hardware either edge,0x30= software trigger. -
Bit 8 — Trigger enable:
0x000= disabled,0x100= enabled.
Default: 0x130 (single sample, software trigger, enabled).
Gen 3 boards (bitmapped):
-
Bits 0-1 — Source select:
0x00= external trigger 2,0x01= external trigger 1,0x02= software trigger. -
Bit 4 —
0x10= negative slope. -
Bit 5 —
0x20= trigger pulse enable. -
Bit 6 —
0x40= trigger pulse/trigger enable select. -
Bit 7 —
0x80= trigger clear.
Default: 0x22 (software trigger with trigger pulse enable).
Interrupt Masking
Before configuring a channel, the sample disables FIFO interrupts for that channel since the sample uses polling rather than interrupt-driven reads:
naibrd_AD_SetFIFOInterruptEnable(cardIndex, module, channel, 0);
In your own application, you may want to enable interrupts and register a handler instead of polling. Consult the Interrupts API Guide for details on interrupt-driven FIFO operations.
|
Important
|
Common Errors
|
Software Trigger (TRG)
To start FIFO sampling, issue a software trigger by calling naibrd_AD_SoftwareTrigger(). This triggers all configured channels on the module simultaneously:
check_status(naibrd_AD_SoftwareTrigger(cardIndex, module));
After the trigger fires, the module begins sampling at the configured rate. Samples accumulate in each active channel’s FIFO until the FIFO size limit is reached (for single-sample trigger mode) or until the FIFO is full (for continuous mode).
You must configure at least one channel (via the CFG command) before triggering. If no channels are active, the trigger has no effect.
|
Important
|
Common Errors
|
Read FIFO (RD)
To read captured samples from a channel’s FIFO, the sample first checks how many words are available, calculates the number of complete samples, then reads and displays them.
Checking FIFO Contents
The sample retrieves the current word count and computes how many complete samples are available:
naibrd_AD_GetFIFOCount(cardIndex, module, channel, &count);
if (count == 0)
{
printf("FIFO buffer is empty! No words to read!\n");
return NAI_ERROR_UNKNOWN;
}
The GetSamplesInFifo() helper divides the raw word count by the words-per-sample (determined by the buffer control setting):
naibrd_AD_GetFIFOCtrl(cardIndex, module, channel, &bufferCtrl);
/* Gen 5: 1 word per sample, +1 if timestamp enabled */
/* Gen 3: count 16-bit, 8-bit, and timestamp words */
if (0 != wordsPerSample)
*samplesInFifo = count / wordsPerSample;
Reading and Converting Samples
Each sample word is read with naibrd_AD_ReadFIFORaw32() and converted to a voltage with naibrd_AD_ConvertToVoltage():
naibrd_AD_ReadFIFORaw32(cardIndex, module, channel, 1, &Data16Hi, &read);
Data = Data16Hi;
naibrd_AD_ConvertToVoltage(modid, RawRange, Data, &Voltage);
For 24-bit resolution (Gen 3 with both 16-bit and 8-bit data enabled), the sample reads two words and combines them:
naibrd_AD_ReadFIFORaw32(cardIndex, module, channel, 1, &Data16Hi, &read);
naibrd_AD_ReadFIFORaw32(cardIndex, module, channel, 1, &Data8Lo, &read);
Data = (Data16Hi << 16) | Data8Lo;
naibrd_AD_ConvertToVoltage(modid, RawRange, Data, &Voltage);
If timestamps are enabled in the buffer control, an additional word is read after the data word(s):
if (Buffer_Controls[TIME_STAMP])
{
naibrd_AD_ReadFIFORaw32(cardIndex, module, channel, 1, &Data16Hi, &read);
printf(" %d ", Data16Hi);
}
The voltage conversion requires the current range setting, which the sample retrieves with naibrd_AD_GetRange() and converts to a raw range code with naibrd_AD_ConvertToVoltageRangeRaw().
|
Important
|
Common Errors
|
Display FIFO Status (STAT)
To check the status of all channel FIFOs, use the Display FIFO Status command. It reads the FIFO status register for every channel and decodes the individual flag bits:
naibrd_AD_GetFIFOStatus(cardIndex, module, channel, NAI_AD_FIFO_STATUS_REALTIME, &fifoStatus);
The NAI_AD_FIFO_STATUS_REALTIME parameter requests the live status (as opposed to latched status).
Gen 5 status flags:
| Flag | Meaning |
|---|---|
Sample Done |
The FIFO has collected the configured number of samples |
FIFO Full |
The FIFO buffer is completely full |
High Limit |
The word count has exceeded the high threshold |
Low Limit |
The word count is below the low threshold |
Empty |
The FIFO contains no data |
Almost Empty |
The word count is at or below the almost-empty threshold |
Almost Full |
The word count is at or above the almost-full threshold |
Gen 3 status flags:
| Flag | Meaning |
|---|---|
Sample Done |
The FIFO has collected the configured number of samples |
FIFO Full |
The FIFO buffer is completely full |
High Limit |
The word count has exceeded the high threshold |
Low Limit |
The word count is below the low threshold |
Empty |
The FIFO contains no data |
Use these flags to determine when to read the FIFO. In a production application, you would typically poll for Sample Done or High Limit (or register an interrupt) rather than reading blindly.
|
Important
|
Common Errors
|
Clear FIFO (CL)
To empty a channel’s FIFO buffer and reset its word count, call naibrd_AD_ClearFIFO():
check_status(naibrd_AD_ClearFIFO(cardIndex, module, channel));
Clearing the FIFO discards all unread samples. This is useful when you want to start a fresh capture without old data in the buffer. After clearing, you will need to issue a new software trigger to begin sampling again.
|
Important
|
Common Errors
|
Troubleshooting Reference
The following table summarizes errors and symptoms you may encounter while using the AD FifoMenu sample. Consult your module’s manual for hardware-specific diagnostics.
| Error / Symptom | Possible Causes | Suggested Resolution |
|---|---|---|
No board found |
Board not powered on; incorrect interface or address in config file. |
Verify physical connection and configuration file settings. Delete |
Connection timeout |
Network misconfiguration; firewall blocking traffic; wrong IP address. |
Confirm Ethernet settings or PCI/PCIe bus configuration. Check firewalls. |
Invalid card or module index |
Zero-based card index or one-based module index mismatch. |
Cards are zero-based, modules are one-based. Verify your values match the hardware. |
Module not present at selected slot |
No AD module in the chosen slot. |
Use the board menu to verify which slots are populated. |
FIFO stays empty after trigger |
Channel inactive; trigger not enabled; trigger source not set to software. |
Verify channel state is active (1), trigger enable bit is set, and trigger source is software trigger. |
FIFO Full — data overflow |
Reading too slowly for the configured sample rate. |
Increase read frequency, reduce sample rate, or increase FIFO size. Clear the FIFO and re-trigger. |
Incorrect voltage readings |
Range mismatch between configuration and conversion; buffer control changed between capture and read. |
Ensure the range and buffer control settings have not changed since the trigger was issued. |
|
Module does not support the requested FIFO feature. |
Verify your module type supports FIFO operations. Check the module manual. |
AD4 bank mismatch error |
Unequal number of active channels in bank 1 (ch 1-8) and bank 2 (ch 9-16). |
Activate the same number of channels in each bank on AD4 modules. |
Illegal buffer control value |
Unsupported bit combination entered for buffer control register. |
Use only the documented valid combinations for your board generation (Gen 3 or Gen 5). |
Sample count does not match expected |
Single-sample vs. continuous trigger mode confusion; FIFO size configured too small. |
Check trigger type (continuous vs. single) and FIFO size setting. |
Full Source
Full Source — AD_FifoMenu.c (SSK 1.x)
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include <ctype.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"
/* naibrd include files */
#include "nai.h"
#include "naibrd.h"
#include "functions/naibrd_ad.h"
#include "advanced/nai_ether_adv.h"
static const int8_t *CONFIG_FILE = (int8_t *)"default_ADFifoMenu.txt";
/* Function prototypes */
static bool_t RunMenu(int32_t cardIndex, int32_t module, uint32_t modid);
static void AD_displayChannelCfg(int32_t cardIndex, int32_t module, int32_t MAX_CHANNELS);
/* AD FIFO Command Functions */
static nai_status_t AD_SwTrigger(int32_t paramCount, int32_t* p_params);
static nai_status_t AD_ReadFifo(int32_t paramCount, int32_t* p_params);
static nai_status_t AD_DisplayFifoStatus(int32_t paramCount, int32_t* p_params);
static nai_status_t AD_ClearFifo(int32_t paramCount, int32_t* p_params);
static nai_status_t AD_ConfigChannel(int32_t paramCount, int32_t* p_params);
/* Additional Helper Functions */
static bool_t AD_getInput(uint32_t *value);
static void printRangeRequest();
static void printBufferRequest(int32_t cardIndex);
static void printTriggerCtrlRequest(int32_t cardIndex);
static void GetSamplesInFifo(int32_t cardIndex, int32_t module, int32_t channel, uint32_t count, uint32_t *samplesInFifo);
static void GetBufferControls(int32_t cardIndex, int32_t module, int32_t channel, bool_t Buffer_Controls[]);
static void PrintSamplesInFifo(int32_t cardIndex, int32_t module, int32_t channel, uint32_t samplesToRead, bool_t Buffer_Controls[]);
/****** Buffer Controls *******/
enum ad_buffer_options {DATA_16BIT, DATA_8BIT, DATA_RAW, TIME_STAMP, BUFFER_OPTIONS };
/****** Command Table *******/
/*** Invariant: enumeration of cmd table starts from 0 and increments by 1 ***/
enum ad_fifo_commands
{
AD_FIFO_CMD_SW_TRIGGER,
AD_FIFO_CMD_READ_FIFO,
AD_FIFO_CMD_DISPLAY_FIFO_STATUS,
AD_FIFO_CMD_CLEAR_FIFO,
AD_FIFO_CMD_CONFIG,
AD_FIFO_CMD_COUNT
};
naiapp_cmdtbl_params_t AD_FifoMenuCmds[] = {
{"TRG", "Execute Software Trigger", AD_FIFO_CMD_SW_TRIGGER, AD_SwTrigger},
{"RD", "Read data from the FIFO", AD_FIFO_CMD_READ_FIFO, AD_ReadFifo},
{"STAT", "Display FIFO Status", AD_FIFO_CMD_DISPLAY_FIFO_STATUS, AD_DisplayFifoStatus},
{"CL", "Clear FIFO", AD_FIFO_CMD_CLEAR_FIFO, AD_ClearFifo},
{"CFG", "Configure FIFO", AD_FIFO_CMD_CONFIG, AD_ConfigChannel},
};
/**************************************************************************************************************/
/**
<summary>
The purpose of the AD_FifoMenu is to illustrate the methods to call in the naibrd library to perform FIFO
operations with the AD modules for configuration setup and reading the channels.
The following system configuration routines from the nai_sys_cfg.c file are called to assist with the configuration
setup for this program prior to calling the naibrd DT routines.
- ClearDeviceCfg
- QuerySystemCfg
- DisplayDeviceCfg
- GetBoardSNModCfg
- SaveDeviceCfg
</summary>
*/
/**************************************************************************************************************/
#if defined (__VXWORKS__)
int32_t AD_FifoMenu(void)
#else
int32_t main(void)
#endif
{
bool_t stop = FALSE;
int32_t cardIndex;
int32_t moduleCnt;
int32_t module;
uint32_t moduleID = 0;
int8_t inputBuffer[80];
int32_t inputResponseCnt;
if (naiapp_RunBoardMenu(CONFIG_FILE) == TRUE)
{
while (stop != TRUE)
{
/* Query the user for the card index */
stop = naiapp_query_CardIndex(naiapp_GetBoardCnt(), 0, &cardIndex);
if (stop != TRUE)
{
check_status(naibrd_GetModuleCount(cardIndex, &moduleCnt));
/* Query the user for the module number */
stop = naiapp_query_ModuleNumber(moduleCnt, 1, &module);
if (stop != TRUE)
{
moduleID = naibrd_GetModuleID(cardIndex, module);
if ((moduleID != 0))
{
RunMenu(cardIndex, module, moduleID);
}
}
}
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>
RunMenu illustrates the channel configuration and prepares the menu which will handle user command requests.
Returns TRUE if the user enters the Quit Command at any point within its scope.
</summary>
*/
/**************************************************************************************************************/
static bool_t RunMenu(int32_t cardIndex, int32_t module, uint32_t modid)
{
bool_t bQuit = FALSE;
int8_t inputBuffer[80];
int32_t inputResponseCnt;
bool_t bCmdFound = FALSE;
naiapp_AppParameters_t ad_fifoOps_params;
int32_t cmd;
ad_fifoOps_params.cardIndex = cardIndex;
ad_fifoOps_params.module = module;
ad_fifoOps_params.channel = 1;
ad_fifoOps_params.modId = modid;
ad_fifoOps_params.maxChannels = naibrd_AD_GetChannelCount(modid);
naiapp_utils_LoadParamMenuCommands(AD_FIFO_CMD_COUNT, AD_FifoMenuCmds);
do
{
AD_displayChannelCfg(cardIndex, module, ad_fifoOps_params.maxChannels);
naiapp_display_ParamMenuCommands((int8_t*)"A/D FIFO MENU");
printf("\n\nPlease enter a command or 'q' to quit:");
bQuit = naiapp_query_ForQuitResponse(sizeof(inputBuffer), NAI_QUIT_CHAR, inputBuffer, &inputResponseCnt);
if (inputResponseCnt > 0)
{
bCmdFound = naiapp_utils_GetParamMenuCmdNum(inputResponseCnt, inputBuffer, &cmd);
if (bCmdFound)
{
AD_FifoMenuCmds[cmd].func(APP_PARAM_COUNT, (int32_t*)&ad_fifoOps_params);
}
else
{
printf("Invalid command entered\n");
}
}
} while (!bQuit);
return bQuit;
}
/**************************************************************************************************************/
/**
<summary>
AD_displayChannelCfg display each channel's settings and values for:
words in fifo, high threshold, low threshold, sample delay, size of fifo, sample rate,
break frequency, buffer control, trigger control, and the status register.
</summary>
*/
/**************************************************************************************************************/
static void AD_displayChannelCfg(int32_t cardIndex, int32_t module, int32_t MAX_CHANNELS)
{
uint32_t LoThreshold, HiThreshold, WordsInFifo, SampleDelay, AlmostEmpty, AlmostFull;
uint32_t FifoSize, SampleRate, BreakFreq, BufferControl, TriggerControl, SkipCount;
nai_ad_fifo_status_t StatusReg;
nai_ad_state_t chanState = NAI_AD_STATE_ACTIVE;
int32_t channel;
uint32_t modid, modver, modrev, special, boardgen;
naibrd_GetModuleInfo(cardIndex, module, &modid, &modver, &modrev, &special);
naibrd_GetBoardGen(cardIndex, &boardgen);
if ( NAI_XILINX_GEN5_ID == boardgen )
{
uint32_t bank1ActiveChannels = 0, bank2ActiveChannels = 0;
printf( "\n Words High Low Almost Almost Size");
printf( "\n in Thres- Thres- Empty Full Sample Skip of Sample Break Buffer Trig Status");
printf( "\nChan Active Fifo hold hold Delay Count FIFO Rate Freq Ctrl Ctrl Register");
printf( "\n------------------------------------------------------------------------------------------------------------------");
for ( channel = 1; channel <= MAX_CHANNELS; channel++ )
{
if ( channel <= 8 )
{
if ( 0 < chanState )
bank1ActiveChannels++;
}
else
{
if ( 0 < chanState )
bank2ActiveChannels++;
}
naibrd_AD_GetFIFOCount(cardIndex, module, channel, &WordsInFifo);
naibrd_AD_GetFIFOLoThreshold(cardIndex, module, channel, &LoThreshold);
naibrd_AD_GetFIFOHiThreshold(cardIndex, module, channel, &HiThreshold);
naibrd_AD_GetFIFOAlmostEmpty(cardIndex, module, channel, &AlmostEmpty);
naibrd_AD_GetFIFOAlmostFull(cardIndex, module, channel, &AlmostFull);
naibrd_AD_GetFIFODelay(cardIndex, module, channel, &SampleDelay);
naibrd_AD_GetFIFOSkip(cardIndex, module, channel, &SkipCount);
naibrd_AD_GetFIFOSize(cardIndex, module, channel, &FifoSize);
naibrd_AD_GetFIFORate(cardIndex, module, channel, &SampleRate);
naibrd_AD_GetBreakFrequency(cardIndex, module, channel, &BreakFreq);
naibrd_AD_GetFIFOCtrl(cardIndex, module, channel, &BufferControl);
naibrd_AD_GetFIFOTrigCtrl(cardIndex, module, channel, &TriggerControl);
naibrd_AD_GetFIFOStatus(cardIndex, module, channel, NAI_AD_FIFO_STATUS_REALTIME, &StatusReg);
printf( "\n %2d %d %-6u %-5d %-5d %-5d %-5d %-5d %-5d %-5d %-5d %-5d 0x%02X 0x%02X 0x%02X",
channel, chanState, WordsInFifo, HiThreshold, LoThreshold, AlmostEmpty, AlmostFull, SampleDelay,
SkipCount, FifoSize, SampleRate, BreakFreq, BufferControl, TriggerControl, StatusReg );
}
if (modid == NAI_MODULE_ID_AD4)
{
if ( (bank1ActiveChannels == 0) || (bank2ActiveChannels == 0) )
{
printf( "\n\n**ERROR - At least 1 channel per bank MUST be active!\n" );
printf( " - Bank 1 = channels 1..8, Bank 2 = channels 9..16\n" );
}
else if ( bank1ActiveChannels != bank2ActiveChannels )
{
printf( "\n\n**ERROR - Same number of channels MUST be active in both banks!\n" );
printf( " - Bank 1 (channels 1..8) Active Channels: %d, Bank 2 (channels 9..16) Active Channels: %d\n", bank1ActiveChannels, bank2ActiveChannels);
}
}
}
else
{
printf( "\n Words High Low Size");
printf( "\n in Thres- Thres- Sample of Sample Break Buffer Trig Status");
printf( "\nChan Active Fifo hold hold Delay FIFO Rate Freq Ctrl Ctrl Register");
printf( "\n----------------------------------------------------------------------------------------");
for ( channel = 1; channel <= MAX_CHANNELS; channel++ )
{
naibrd_AD_GetChannelState(cardIndex, module, channel, &chanState);
naibrd_AD_GetFIFOCount(cardIndex, module, channel, &WordsInFifo);
naibrd_AD_GetFIFOLoThreshold(cardIndex, module, channel, &LoThreshold);
naibrd_AD_GetFIFOHiThreshold(cardIndex, module, channel, &HiThreshold);
naibrd_AD_GetFIFODelay(cardIndex, module, channel, &SampleDelay);
naibrd_AD_GetFIFOSize(cardIndex, module, channel, &FifoSize);
naibrd_AD_GetFIFORate(cardIndex, module, channel, &SampleRate);
naibrd_AD_GetBreakFrequency(cardIndex, module, channel, &BreakFreq);
naibrd_AD_GetFIFOCtrl(cardIndex, module, channel, &BufferControl);
naibrd_AD_GetFIFOTrigCtrl(cardIndex, module, channel, &TriggerControl);
naibrd_AD_GetFIFOStatus(cardIndex, module, channel, NAI_AD_FIFO_STATUS_REALTIME, &StatusReg);
printf( "\n %2d %d %-6u %-5d %-5d %-5d %-5d %-5d %-5d 0x%02X 0x%02X 0x%02X",
channel, chanState, WordsInFifo, HiThreshold, LoThreshold, SampleDelay, FifoSize, SampleRate,
BreakFreq, BufferControl, TriggerControl, StatusReg );
}
}
}
/**************************************************************************************************************/
/**
<summary>
AD_configChannel initiates all the channels for writing and handles the user requests to configure the channels.
</summary>
*/
/**************************************************************************************************************/
static nai_status_t AD_ConfigChannel(int32_t paramCount, int32_t* p_params)
{
p_naiapp_AppParameters_t p_ad_params = (p_naiapp_AppParameters_t)p_params;
int32_t cardIndex = p_ad_params->cardIndex;
int32_t module = p_ad_params->module;
int32_t channel = p_ad_params->channel;
uint32_t Range = 0, LoThreshold = 0, HiThreshold = 0, SamplesPerTrigger = 0, SampleDelay = 0, AlmostEmpty = 0, AlmostFull = 0;
uint32_t SkipCount = 0, SampleRate = 0, BreakFreq = 0, BufferControl = 0, TriggerControl = 0, MAX_FIFO_COUNT;
nai_ad_range_mode_t mode;
nai_ad_state_t chanState;
bool_t success = FALSE;
uint32_t modid, modver, modrev, special, boardgen;
#if defined (WIN32)
UNREFERENCED_PARAMETER(paramCount);
#endif
naibrd_GetModuleInfo(cardIndex, module, &modid, &modver, &modrev, &special);
MAX_FIFO_COUNT = naibrd_AD_GetMaxFIFOCount(modid);
/* Query the user for the channel number */
naiapp_query_ChannelNumber(p_ad_params->maxChannels, 1, &channel);
naibrd_AD_SetFIFOInterruptEnable(cardIndex, module, channel, 0);
naibrd_AD_SetRaw(cardIndex, module, NAI_AD_RAW_CLK_RATE_ADDER_HI, 0x0000);
naibrd_AD_SetRaw(cardIndex, module, NAI_AD_RAW_CLK_RATE_ADDER_LO, 0xAC44);
naibrd_GetBoardGen(cardIndex, &boardgen);
if ( NAI_BLACKFIN_GEN3_ID == boardgen )
{
}
do
{
printf("Set channel %d to Active(1) or Inactive(0)?", channel);
success = AD_getInput(&chanState);
} while ( !success || ((chanState != 0) && (chanState != 1)) );
if ( 0 != chanState )
{
do
{
printRangeRequest();
success = AD_getInput(&Range);
if ( TRUE != success )
Range = 16;
success = TRUE;
} while ( !(success) || !(( Range <= 3) || (Range >= 9 && Range <= 10) ||
(Range >= 16 && Range <= 19) || (Range >=25 && Range <= 26 )) );
if ((Range & NAI_AD_RANGE_BIPOLAR) == NAI_AD_RANGE_BIPOLAR)
mode = NAI_AD_RANGE_MODE_BIPOLAR;
else
mode = NAI_AD_RANGE_MODE_UNIPOLAR;
do
{
printf( "\nPlease enter low threshold (0-%d) [default=10]:\n>>", MAX_FIFO_COUNT);
success = AD_getInput(&LoThreshold);
if ( TRUE != success )
LoThreshold = 10;
success=TRUE;
} while (!success || (LoThreshold > MAX_FIFO_COUNT));
do
{
printf( "\nPlease enter high threshold (0-%d) [default=15]:\n>>", MAX_FIFO_COUNT);
success = AD_getInput(&HiThreshold);
if ( TRUE != success )
HiThreshold = 15;
success= TRUE;
} while (!success || (HiThreshold > MAX_FIFO_COUNT));
if ( NAI_XILINX_GEN5_ID == boardgen )
{
do
{
printf( "\nPlease enter Almost Empty threshold (0-%d) [default=5]:\n>>", MAX_FIFO_COUNT);
success = AD_getInput(&AlmostEmpty);
if ( TRUE != success )
AlmostEmpty = 5;
success = TRUE;
} while (!success || (AlmostFull > MAX_FIFO_COUNT));
do
{
printf( "\nPlease enter Almost Full threshold (0-%d) [default=18]:\n>>", MAX_FIFO_COUNT);
success = AD_getInput(&AlmostFull);
if ( TRUE != success )
AlmostFull = 18;
success = TRUE;
} while (!success || (AlmostFull > MAX_FIFO_COUNT));
do
{
printf( "\nPlease enter the sample rate (0-250000) [default=250000]:\n>>");
success = AD_getInput(&SampleRate);
if ( TRUE != success )
SampleRate = 250000;
success = TRUE;
} while (!success || (SampleRate > 250000));
do
{
printf( "\nPlease enter the delay (0-4294967295 (0xFFFFFFFF)) [default=0]:\n>>");
success = AD_getInput(&SampleDelay);
if ( TRUE != success )
SampleDelay = 0;
success = TRUE;
} while (!success || (SampleDelay > 4294967295U));
do
{
printf( "\nPlease enter the Break Frequency (0-250000) [default=0]:\n>>");
success = AD_getInput(&BreakFreq);
if ( TRUE != success )
BreakFreq = 0;
success = TRUE;
} while (!success || (BreakFreq > 250000));
do
{
printf( "\nPlease enter the Skip Count (0-4294967295 (0xFFFFFFFF)) [default=0]:\n>>");
success = AD_getInput(&SkipCount);
if ( TRUE != success )
SkipCount = 0;
success = TRUE;
} while (!success || (SkipCount > 4294967295U));
}
else
{
do
{
printf( "\nPlease enter the sample rate (0-65,535) [default=65535]:\n>>");
success = AD_getInput(&SampleRate);
if ( TRUE != success )
SampleRate = 65535;
success = TRUE;
} while (!success || (SampleRate > 65535));
do
{
printf( "\nPlease enter the delay (0-65,535) [default=0]:\n>>");
success = AD_getInput(&SampleDelay);
if ( TRUE != success )
SampleDelay = 0;
success = TRUE;
} while (!success || (SampleDelay > 65535));
do
{
printf( "\nPlease enter the Break Frequency (0-10,000) [default=0]:\n>>");
success = AD_getInput(&BreakFreq);
if ( TRUE != success )
BreakFreq = 0;
success = TRUE;
} while (!success || (BreakFreq > 10000));
}
do
{
printf( "\nPlease enter the fifo size (0-%d) [default=20]:\n>>", MAX_FIFO_COUNT);
success = AD_getInput(&SamplesPerTrigger);
if ( TRUE != success )
SamplesPerTrigger = 20;
success = TRUE;
} while (!success || (SamplesPerTrigger > MAX_FIFO_COUNT));
do
{
printBufferRequest(cardIndex);
success = AD_getInput(&BufferControl);
if ( NAI_XILINX_GEN5_ID == boardgen )
{
if ( TRUE != success )
BufferControl = 0;
success = (BufferControl == 0 || BufferControl == 4 || BufferControl == 16 ||
BufferControl == 20);
}
else
{
if ( TRUE != success )
BufferControl = 1;
success = (BufferControl == 1 || BufferControl == 3 || BufferControl == 5 || BufferControl == 7) ||
(BufferControl == 16 || BufferControl == 17 || BufferControl == 19 || BufferControl == 21) ||
(BufferControl == 23);
}
} while (!success);
do
{
printTriggerCtrlRequest(cardIndex);
success = AD_getInput(&TriggerControl);
if ( TRUE != success )
{
if ( NAI_XILINX_GEN5_ID == boardgen )
TriggerControl = 0x130;
else
TriggerControl = 0x22;
success = TRUE;
}
} while (!success);
naibrd_AD_SetChannelState(cardIndex, module, channel, chanState);
naibrd_AD_SetRange(cardIndex, module, channel, mode, Range);
naibrd_AD_SetFIFOLoThreshold(cardIndex, module, channel, LoThreshold);
naibrd_AD_SetFIFOHiThreshold(cardIndex, module, channel, HiThreshold);
naibrd_AD_SetFIFODelay(cardIndex, module, channel, SampleDelay);
naibrd_AD_SetFIFOSize(cardIndex, module, channel, SamplesPerTrigger);
naibrd_AD_SetFIFORate(cardIndex, module, channel, SampleRate);
naibrd_AD_SetBreakFrequency(cardIndex, module, channel, BreakFreq);
naibrd_AD_SetFIFOCtrl(cardIndex, module, channel, BufferControl);
naibrd_AD_SetFIFOTrigCtrl(cardIndex, module, channel, TriggerControl);
if ( NAI_XILINX_GEN5_ID == boardgen )
{
naibrd_AD_SetFIFOAlmostEmpty(cardIndex, module, channel, AlmostEmpty);
naibrd_AD_SetFIFOAlmostFull(cardIndex, module, channel, AlmostFull);
naibrd_AD_SetFIFOSkip(cardIndex, module, channel, SkipCount );
}
}
else
naibrd_AD_SetChannelState(cardIndex, module, channel, chanState);
return NAI_SUCCESS;
}
/**************************************************************************************************************/
/**
<summary>
AD_SwTrigger calls the SoftwareTrigger API which causes the FIFO to start sampling.
</summary>
*/
/**************************************************************************************************************/
static nai_status_t AD_SwTrigger(int32_t paramCount, int32_t* p_params)
{
p_naiapp_AppParameters_t p_ad_params = (p_naiapp_AppParameters_t)p_params;
int32_t cardIndex = p_ad_params->cardIndex;
int32_t module = p_ad_params->module;
#if defined (WIN32)
UNREFERENCED_PARAMETER(paramCount);
#endif
check_status(naibrd_AD_SoftwareTrigger(cardIndex, module));
return NAI_SUCCESS;
}
/**************************************************************************************************************/
/**
<summary>
AD_DisplayFifoStatus illustrates which of the following flags have been raised:
Sample Done, FIFO Full, High Limit, Low Limit, Empty.
</summary>
*/
/**************************************************************************************************************/
static nai_status_t AD_DisplayFifoStatus(int32_t paramCount, int32_t* p_params)
{
uint32_t modid, modver, modrev, special, boardgen;
nai_ad_fifo_status_t fifoStatus;
int32_t MAX_CHANNELS;
p_naiapp_AppParameters_t p_ad_params = (p_naiapp_AppParameters_t)p_params;
int32_t cardIndex = p_ad_params->cardIndex;
int32_t module = p_ad_params->module;
int32_t channel = p_ad_params->channel;
#if defined (WIN32)
UNREFERENCED_PARAMETER(paramCount);
#endif
naibrd_GetModuleInfo(cardIndex, module, &modid, &modver, &modrev, &special);
naibrd_GetBoardGen(cardIndex, &boardgen);
MAX_CHANNELS = naibrd_AD_GetChannelCount(modid);
printf( "\n\n\n" );
if ( NAI_XILINX_GEN5_ID == boardgen )
{
uint16_t SampleDone, FifoFull, HiLimit, LoLimit, Empty, AlmostEmpty, AlmostFull;
printf( "| Ch | Status Register| Sample Done | FIFO Full | Hi Limit | Lo Limit | Empty | Almost | Almost |\n" );
printf( "| | (hex value) | | | | | | empty | full |\n" );
printf( "|----|----------------|-------------|-----------|----------|----------|-------|--------|--------|\n" );
for ( channel = 1; channel <= MAX_CHANNELS; channel++ )
{
naibrd_AD_GetFIFOStatus(cardIndex, module, channel, NAI_AD_FIFO_STATUS_REALTIME, &fifoStatus);
Empty = (NAI_AD_GEN5_FIFO_STATUS_EMPTY == (fifoStatus & NAI_AD_GEN5_FIFO_STATUS_EMPTY));
AlmostEmpty = (NAI_AD_GEN5_FIFO_STATUS_ALMOSTEMPTY == (fifoStatus & NAI_AD_GEN5_FIFO_STATUS_ALMOSTEMPTY));
LoLimit = (NAI_AD_GEN5_FIFO_STATUS_LOWMARK == (fifoStatus & NAI_AD_GEN5_FIFO_STATUS_LOWMARK));
HiLimit = (NAI_AD_GEN5_FIFO_STATUS_HIGHMARK == (fifoStatus & NAI_AD_GEN5_FIFO_STATUS_HIGHMARK));
AlmostFull = (NAI_AD_GEN5_FIFO_STATUS_ALMOSTFULL == (fifoStatus & NAI_AD_GEN5_FIFO_STATUS_ALMOSTFULL));
FifoFull = (NAI_AD_GEN5_FIFO_STATUS_FULL == (fifoStatus & NAI_AD_GEN5_FIFO_STATUS_FULL));
SampleDone = (NAI_AD_GEN5_FIFO_STATUS_DONE == (fifoStatus & NAI_AD_GEN5_FIFO_STATUS_DONE));
printf( "| %2d | 0x%02X | %d | %d | %d | %d | %d | %d | %d |\n",
channel, fifoStatus, SampleDone, FifoFull, HiLimit, LoLimit, Empty, AlmostEmpty, AlmostFull );
}
}
else
{
uint16_t SampleDone, FifoFull, HiLimit, LoLimit, Empty;
printf( "| Ch | Status Register| Sample Done | FIFO Full | Hi Limit | Lo Limit | Empty |\n" );
printf( "| | (hex value) | | | | | |\n" );
printf( "|----|----------------|-------------|-----------|----------|----------|-------|\n" );
for ( channel = 1; channel <= MAX_CHANNELS; channel++ )
{
naibrd_AD_GetFIFOStatus(cardIndex, module, channel, NAI_AD_FIFO_STATUS_REALTIME, &fifoStatus);
Empty = (NAI_AD_GEN3_FIFO_STATUS_EMPTY == (fifoStatus & NAI_AD_GEN3_FIFO_STATUS_EMPTY));
LoLimit = (NAI_AD_GEN3_FIFO_STATUS_LOW == (fifoStatus & NAI_AD_GEN3_FIFO_STATUS_LOW));
HiLimit = (NAI_AD_GEN3_FIFO_STATUS_HIGH == (fifoStatus & NAI_AD_GEN3_FIFO_STATUS_HIGH));
FifoFull = (NAI_AD_GEN3_FIFO_STATUS_FULL == (fifoStatus & NAI_AD_GEN3_FIFO_STATUS_FULL));
SampleDone = (NAI_AD_GEN3_FIFO_STATUS_DONE == (fifoStatus & NAI_AD_GEN3_FIFO_STATUS_DONE));
printf( "| %2d | 0x%02X | %d | %d | %d | %d | %d |\n",
channel, fifoStatus, SampleDone, FifoFull, HiLimit, LoLimit, Empty );
}
}
return NAI_SUCCESS;
}
/**************************************************************************************************************/
/**
<summary>
AD_ClearFifo empties the specified channel's FIFO buffer.
</summary>
*/
/**************************************************************************************************************/
static nai_status_t AD_ClearFifo(int32_t paramCount, int32_t* p_params)
{
p_naiapp_AppParameters_t p_ad_params = (p_naiapp_AppParameters_t)p_params;
int32_t cardIndex = p_ad_params->cardIndex;
int32_t module = p_ad_params->module;
int32_t channel = p_ad_params->channel;
#if defined (WIN32)
UNREFERENCED_PARAMETER(paramCount);
#endif
check_status(naibrd_AD_ClearFIFO(cardIndex, module, channel));
return NAI_SUCCESS;
}
/**************************************************************************************************************/
/**
<summary>
AD_ReadFifo handles the user request to read a certain number of samples from the FIFO.
</summary>
*/
/**************************************************************************************************************/
static nai_status_t AD_ReadFifo(int32_t paramCount, int32_t* p_params)
{
uint32_t count, samplesInFifo, samplesToRead;
bool_t BufferControls[BUFFER_OPTIONS] = {FALSE, FALSE, FALSE, FALSE};
uint32_t modid, modver, modrev, special;
p_naiapp_AppParameters_t p_ad_params = (p_naiapp_AppParameters_t)p_params;
int32_t cardIndex = p_ad_params->cardIndex;
int32_t module = p_ad_params->module;
int32_t channel = p_ad_params->channel;
#if defined (WIN32)
UNREFERENCED_PARAMETER(paramCount);
#endif
naibrd_GetModuleInfo( cardIndex, module, &modid, &modver, &modrev, &special);
naibrd_AD_GetFIFOCount(cardIndex, module, channel, &count);
if (count == 0)
{
printf("FIFO buffer is empty! No words to read!\n");
return NAI_ERROR_UNKNOWN;
}
GetSamplesInFifo(cardIndex, module, channel, count, &samplesInFifo);
GetBufferControls(cardIndex, module, channel, BufferControls);
do
{
printf( "\nHow many samples would you like to read from the FIFO? Enter\n" );
printf( "a number less than or equal to %d:\n>>", samplesInFifo);
AD_getInput(&samplesToRead);
} while (samplesToRead == 0 || (samplesToRead > samplesInFifo));
PrintSamplesInFifo(cardIndex, module, channel, samplesToRead, BufferControls);
return NAI_SUCCESS;
}
static void GetSamplesInFifo(int32_t cardIndex, int32_t module, int32_t channel, uint32_t count, uint32_t *samplesInFifo)
{
uint32_t wordsPerSample = 0, bufferCtrl, boardgen;
naibrd_AD_GetFIFOCtrl(cardIndex, module, channel, &bufferCtrl);
naibrd_GetBoardGen(cardIndex, &boardgen);
if ( NAI_XILINX_GEN5_ID == boardgen )
{
wordsPerSample = 1;
if ((bufferCtrl & NAI_AD_FIFO_CTRL_TIMESTAMP) == NAI_AD_FIFO_CTRL_TIMESTAMP)
wordsPerSample++;
}
else
{
if ((bufferCtrl & NAI_AD_FIFO_CTRL_TIMESTAMP) == NAI_AD_FIFO_CTRL_TIMESTAMP)
wordsPerSample++;
if ((bufferCtrl & NAI_AD_FIFO_CTRL_8BIT) == NAI_AD_FIFO_CTRL_8BIT)
wordsPerSample++;
if ((bufferCtrl & NAI_AD_FIFO_CTRL_16BIT) == NAI_AD_FIFO_CTRL_16BIT)
wordsPerSample++;
}
if ( 0 != wordsPerSample )
*samplesInFifo = count / wordsPerSample;
else
printf( "BufferControl is %d, which is an illegal value! Please re-enter a value for BufferControl via the CFG selection.\n",
bufferCtrl);
}
static void GetBufferControls(int32_t cardIndex, int32_t module, int32_t channel, bool_t BufferControls[])
{
uint32_t bufferCtrl;
naibrd_AD_GetFIFOCtrl(cardIndex, module, channel, &bufferCtrl);
if ((bufferCtrl & NAI_AD_FIFO_CTRL_TIMESTAMP) == NAI_AD_FIFO_CTRL_TIMESTAMP)
BufferControls[TIME_STAMP] = TRUE;
if ((bufferCtrl & NAI_AD_FIFO_CTRL_8BIT) == NAI_AD_FIFO_CTRL_8BIT)
BufferControls[DATA_8BIT] = TRUE;
if ((bufferCtrl & NAI_AD_FIFO_CTRL_16BIT) == NAI_AD_FIFO_CTRL_16BIT)
BufferControls[DATA_16BIT] = TRUE;
}
static void PrintSamplesInFifo(int32_t cardIndex, int32_t module, int32_t channel, uint32_t samplesToRead, bool_t Buffer_Controls[])
{
uint32_t modid, modver, modrev, special, boardgen;
float64_t range;
nai_ad_range_mode_t mode;
nai_ad_range_t RawRange;
naibrd_GetModuleInfo(cardIndex, module, &modid, &modver, &modrev, &special);
naibrd_GetBoardGen(cardIndex, &boardgen);
naibrd_AD_GetRange(cardIndex, module, channel, &mode, &range);
naibrd_AD_ConvertToVoltageRangeRaw(modid, mode, range, &RawRange);
printf( "DATA\t\tVOLTAGE\t\t" );
if(Buffer_Controls[TIME_STAMP])
printf( "TIME_STAMP" );
printf("\n");
do
{
float64_t Voltage = 0;
uint32_t Data16Hi = 0, Data8Lo = 0;
uint32_t read, Data = 0;
if (Buffer_Controls[DATA_16BIT] && Buffer_Controls[DATA_8BIT])
{
naibrd_AD_ReadFIFORaw32(cardIndex, module, channel, 1, &Data16Hi, &read);
naibrd_AD_ReadFIFORaw32(cardIndex, module, channel, 1, &Data8Lo, &read);
Data = (Data16Hi << 16) | Data8Lo;
naibrd_AD_ConvertToVoltage(modid, RawRange, Data, &Voltage);
}
else if ( Buffer_Controls[DATA_16BIT] || (NAI_XILINX_GEN5_ID == boardgen) )
{
naibrd_AD_ReadFIFORaw32(cardIndex, module, channel, 1, &Data16Hi, &read);
Data = Data16Hi;
naibrd_AD_ConvertToVoltage(modid, RawRange, Data, &Voltage);
}
printf("0x%08X\t%+7.6f\t", Data, Voltage);
if (Buffer_Controls[TIME_STAMP])
{
naibrd_AD_ReadFIFORaw32(cardIndex, module, channel, 1, &Data16Hi, &read);
printf(" %d ", Data16Hi);
}
printf("\n");
samplesToRead--;
} while (samplesToRead > 0);
}
static bool_t AD_getInput(uint32_t *value)
{
int8_t sUserInput[15];
memset( sUserInput, 0x00, sizeof( sUserInput ) );
fgets( (char *)sUserInput, sizeof(sUserInput), stdin);
if ('\n' != sUserInput[0])
{
sscanf((const char*)sUserInput, "%d", value);
return TRUE;
}
else
return FALSE;
}
static void printRangeRequest()
{
printf( "\nPlease select the range an polarity for this channel. Refer to the table\n" );
printf( " below for valid values: \n\n");
printf( " BIT | D4 | D3 | D2 | D1 | D0 |\n" );
printf( "MODULE | C4 | C2 | C1 | | | | | | Bipolar/Unipolar\n" );
printf( "-----------------------------------------------------------------------------\n");
printf( "RANGE | 50.0V | 40.0V | N/A | * | 1 | 0 | 1 | 0 | (decimal: 26/10)\n" );
printf( " | 25.0V | 20.0V | N/A | * | 1 | 0 | 0 | 1 | (decimal: 25/9)\n" );
printf( " | 12.5V | 10.0V | 10.0V | * | 0 | 0 | 0 | 0 | (decimal: 16/0)\n" );
printf( " | 6.25V | 5.00V | 5.00V | * | 0 | 0 | 0 | 1 | (decimal: 17/1)\n" );
printf( " | N/A | N/A | 2.50V | * | 0 | 0 | 1 | 0 | (decimal: 18/2)\n" );
printf( " | N/A | N/A | 1.25V | * | 0 | 0 | 1 | 1 | (decimal: 19/3)\n" );
printf( "-----------------------------------------------------------------------------\n");
printf( " KA | AD4 | AD5 | AD6 | | | | | | \n");
printf( "-----------------------------------------------------------------------------\n");
printf( " N/A | N/A | N/A | N/A | * | 1 | 0 | 1 | 0 | (decimal: 26/10)\n");
printf( " N/A | N/A | N/A | N/A | * | 1 | 0 | 0 | 1 | (decimal: 25/9)\n" );
printf( "10.00 | 10.00 | 50.00 |100.00 | * | 0 | 0 | 0 | 0 | (decimal: 16/0)\n" );
printf( " 5.00 | 5.00 | 25.00 | 50.00 | * | 0 | 0 | 0 | 1 | (decimal: 17/1)\n" );
printf( " N/A | 2.50 | 12.50 | 25.00 | * | 0 | 0 | 1 | 0 | (decimal: 18/2)\n" );
printf( " N/A | 1.25 | 6.25 | 12.50 | * | 0 | 0 | 1 | 1 | (decimal: 19/3)\n" );
printf( "-----------------------------------------------------------------------------\n");
printf( "\n\n * For bipolar/unipolar selection, program D4 as '0' for unipolar and '1' for\n bipolar\n\n" );
printf( "Please enter in decimal (26,10,25,9,16,0,17,1,18,2,19,3) [default=16]: \n>>");
}
static void printBufferRequest(int32_t cardIndex)
{
uint32_t boardgen;
naibrd_GetBoardGen(cardIndex, &boardgen);
if ( NAI_XILINX_GEN5_ID == boardgen )
{
printf( "\nPlease enter a value for the Buffer Control register. Refer to the\n" );
printf( "bit-map table below:\n\n" );
printf( "B0 = Reserved\n" );
printf( "B1 = Reserved\n" );
printf( "B2 = Filter. Filter Data (1) or Unfiltered data (0)\n" );
printf( "B3 = Reserved\n" );
printf( "B4 = Time Stamp. An integer counter that counts from 0 to 65,535 and wraps\n" );
printf( " around when it overflows.\n" );
printf( "B5 = Reserved\n" );
printf( "B6 = Reserved\n" );
printf( "B7 = Reserved\n" );
printf( "\nPlease enter the Buffer Control (0,4,16,20 ?) [default=0]:\n>>");
}
else
{
printf( "\nPlease enter a value for the Buffer Control register. Refer to the\n" );
printf( "bit-map table below:\n\n" );
printf( "B0 = Data (16 Bit Hi). 16 bit resolution data for unipolar and bipolar.\n" );
printf( "B1 = Data (8 Bit Lo). Combine with B0 to form a 24 bit resolution for unipolar\n" );
printf( " and bipolar data.\n" );
printf( "B2 = Filter. Filter Data (1) or Unfiltered data (0)\n" );
printf( "B3 = Reserved\n" );
printf( "B4 = Time Stamp. An integer counter that counts from 0 to 65,535 and wraps\n" );
printf( " around when it overflows.\n" );
printf( "B5 = Reserved\n" );
printf( "B6 = Reserved\n" );
printf( "B7 = Reserved\n" );
printf( "\nPlease enter the Buffer Control (1,3,5,7,16,17,19,21,23 ?) [default=1]:\n>>");
}
}
static void printTriggerCtrlRequest(int32_t cardIndex)
{
uint32_t boardgen;
naibrd_GetBoardGen(cardIndex, &boardgen);
if ( NAI_XILINX_GEN5_ID == boardgen )
{
printf( "\nTrigger Control- Please refer to the bit map below:\n\n" );
printf( "B0-B1 = Trigger Type (choose one only)\n" );
printf( " 0xXXX0 = Continuos\n" );
printf( " 0xXXX1 = Single Sample\n" );
printf( "B2-B3 = Reserved\n" );
printf( "B4-B5 = Trigger Edge (Choose one only)\n" );
printf( " 0xXX0X = RESERVED for Hardware Trigger (Positive Edge)\n" );
printf( " 0xXX1X = RESERVED for Hardware Trigger (Negative Edge)\n" );
printf( " 0xXX2X = RESERVED for Hardware Trigger (Either Edge)\n" );
printf( " 0xXX3X = Software Trigger\n" );
printf( "B6-B7 = Reserved\n" );
printf( "B8 = Trigger Enable (choose one only)\n" );
printf( " 0xX0XX = Disable/Stop Trigger\n" );
printf( " 0xX1XX = Enable\n" );
printf( "B9-B31 = Reserved\n" );
printf( "\nBy default, we will set the Trigger Control to:\n" );
printf( "304 (0x0130) - Single Sample | Software Trigger | Enable.");
printf( "Press 'Enter' to continue or enter a new value in decimal.\n" );
}
else
{
printf( "\nTrigger Control- Please refer to the bit map below:\n\n" );
printf( "B0-B1 = Source Select (choose one only)\n" );
printf( " 0x00 = Ext. Trigger 2\n" );
printf( " 0x01 = Ext. Trigger 1\n" );
printf( " 0x02 = Software Trigger\n" );
printf( "B3 = Reserved\n" );
printf( "B4-B7 = Trigger Type (Choose one only)\n" );
printf( " 0x10 = Negative Slope\n" );
printf( " 0x20 = Trigger Pulse Enable\n" );
printf( " 0x40 = Trigger Pulse/Trigger Enable Select\n" );
printf( " 0x80 = Trigger Clear\n" );
printf( "\nBy defualt, we will set the Trigger Control to:\n" );
printf( "34 (0x22) - Software Trigger. Press 'Enter' to continue or enter a new value in decimal.\n" );
}
}