/********************************************************************* * * ANSI C Example program: * DigPulseTrain-Var.c * * Example Category: * CO * * Description: * This example demonstrates how to generate a continuous digital * pulse train from a Counter Output Channel. The Frequency, Duty * Cycle, and Idle State are all configurable. * * This example shows how to configure the pulse in terms of * Frequency/Duty Cycle, but can easily be modified to generate a * pulse in terms of Time or Ticks. * * Instructions for Running: * 1. Select the Physical Channel which corresponds to the counter * you want to output your signal to on the DAQ device. * 2. Enter the Frequency and Duty Cycle to define the pulse * parameters. You can also change the Idle State to determine * the beginning and end states of the output. If the Idle State * is High, the generation will use inverted logic. * Additionally, you can set the Initial Delay (in seconds) * which will delay the beginning of the pulse train from the * start call; this is currently set to 0.0 in the code. * Note: Use the Measure Period example to verify you are * outputting the pulse train on the DAQ device. * * Steps: * 1. Create a task. * 2. Create a Counter Output channel to produce a Pulse in terms * of Frequency. If the Idle State of the pulse is set to low, * the state of the line will begin low and remain low after the * generation is stopped. * 3. Call the timing function to configure the duration of the * pulse generation. * 4. Call the Start function to arm the counter and begin the * pulse * train generation. * 5. For continuous generation, the counter will continually * generate the pulse train until stop button is pressed. * 6. Call the Clear Task function to clear the Task. * 7. Display an error if any. * * I/O Connections Overview: * The counter will output the pulse train on the output terminal * of the counter specified in the Physical Channel I/O control. * * This example uses the default output terminal for the counter of * your device. To determine what the default counter pins for you * device are or to set a different output terminal, refer to the * Connecting Counter Signals topic in the NI-DAQmx Help (search * for "Connecting Counter Signals"). * *********************************************************************/ #define MIN_RATE (0.001) #define MAX_RATE (20.0e6) #define MIN_SLEEP 1 #define MAX_SLEEP 3600 #include #include #include #include #include #include #define DAQmxErrChk(functionCall) if( DAQmxFailed(error=(functionCall)) ) goto Error; else int32 CVICALLBACK DoneCallback(TaskHandle taskHandle, int32 status, void *callbackData); int main(int argc, char* argv[]) { int error=0; TaskHandle taskHandle=0; char errBuff[2048]={'\0'}; char* base_ptr = ""; char* range_ptr = ""; char* sleep_ptr = ""; double range = 1000.0; double base_rate = 0.0; int sleep_time = MAX_SLEEP; int idx = 1; char device[100] = "Dev1/Ctr1"; if (argc > idx && toupper(argv[idx][0]) == 'D' && toupper(argv[idx][1]) == 'E' && toupper(argv[idx][2]) == 'V') { strncpy(device, argv[idx], sizeof(device)); ++idx; } if (argc > idx) { range_ptr = argv[idx]; range = (double) atof(range_ptr); ++idx; } if (range < MIN_RATE) range = MIN_RATE; if (range > MAX_RATE) range = MAX_RATE; if (argc > idx) { base_ptr = range_ptr; base_rate = range; range_ptr = argv[idx]; range = (double) atof(range_ptr); if (base_rate + range > MAX_RATE) range = MAX_RATE - base_rate; ++idx; sleep_time = MIN_SLEEP; } printf("Input of '%s' gives base of %g\n", base_ptr, base_rate); printf("Input of '%s' gives range of %g\n", range_ptr, range); if (argc > idx) { sleep_ptr = argv[idx]; sleep_time = atoi(sleep_ptr); if (sleep_time < MIN_SLEEP) sleep_time = MIN_SLEEP; if (sleep_time > MAX_SLEEP) sleep_time = MAX_SLEEP; ++idx; } else if (range == 0) sleep_time = MAX_SLEEP; printf("Input of '%s' gives loop time of %d\n", sleep_ptr, sleep_time); /*********************************************/ // DAQmx Configure Code /*********************************************/ while (1) { double this_rate; double rval; rval = (double) random() / (double) RAND_MAX; this_rate = range * rval; this_rate += base_rate; if (this_rate < MIN_RATE) this_rate = MIN_RATE; printf("Pulse train on %s at %f Hz.\n", device, this_rate); DAQmxErrChk (DAQmxCreateTask("",&taskHandle)); DAQmxErrChk (DAQmxCreateCOPulseChanFreq(taskHandle, device, "", DAQmx_Val_Hz, DAQmx_Val_Low, 0.0, this_rate, 0.50)); DAQmxErrChk (DAQmxCfgImplicitTiming(taskHandle,DAQmx_Val_ContSamps,1000)); DAQmxErrChk (DAQmxRegisterDoneEvent(taskHandle,0,DoneCallback,NULL)); /*********************************************/ // DAQmx Start Code /*********************************************/ DAQmxErrChk (DAQmxStartTask(taskHandle)); do { sleep(sleep_time); } while (range == 0); DAQmxStopTask(taskHandle); DAQmxClearTask(taskHandle); taskHandle = 0; } Error: if( DAQmxFailed(error) ) DAQmxGetExtendedErrorInfo(errBuff,2048); if( taskHandle!=0 ) { /*********************************************/ // DAQmx Stop Code /*********************************************/ DAQmxStopTask(taskHandle); DAQmxClearTask(taskHandle); } if( DAQmxFailed(error) ) printf("DAQmx Error: %s\n",errBuff); printf("End of program, press Enter key to quit\n"); getchar(); return 0; } int32 CVICALLBACK DoneCallback(TaskHandle taskHandle, int32 status, void *callbackData) { int32 error=0; char errBuff[2048]={'\0'}; // Check to see if an error stopped the task. DAQmxErrChk (status); Error: if( DAQmxFailed(error) ) { DAQmxGetExtendedErrorInfo(errBuff,2048); DAQmxClearTask(taskHandle); printf("DAQmx Error: %s\n",errBuff); } return 0; }