Dr. Dobb's is part of the Informa Tech Division of Informa PLC

This site is operated by a business or businesses owned by Informa PLC and all copyright resides with them. Informa PLC's registered office is 5 Howick Place, London SW1P 1WG. Registered in England and Wales. Number 8860726.


Channels ▼
RSS

Implementing Direct Memory Access (DMA) in C


May 1992/Implementing Direct Memory Access (DMA) in C/Listing 1

Listing 1 (adtest.c) Application for High-Speed Data Acquisition Using DMA on the Lab Master AD

/****************************************************

       Copyright Don Bradley, 1991.

       Permission is granted for used of these routines
       in any manner as long as this copyright notice is
       included.

       Tested using Quick C 2.5 and MSC 6.0 on a
       Toshiba T5200.

***********************************************/

#include <math.h>
#include <conio.h>
#include <stdio.h>
#include <stdlib.h>
#include <process.h>
#include <fcntl.h>
#include <io.h>
#include <sys\types.h>
#include <sys\stat.h>
#include <malloc.h>

#include "labmastr.h"
#include "dma.h"

#define ESC 0x1B
#define FILEBUFFSIZE 0x4000

#define OK_EXIT                      0
#define MISSING_PARAMETERS_ERROR     1
#define NOT_ENABLED_ERROR            2
#define CANT_OPEN_FILE_ERROR         3
#define CANT_INITIALIZE_ERROR        4

void main(int argc, char *argv[]);
void dma_handler(int value);

static int file_buffer[FILEBUFFSIZE];
static int file_handle;
static int file_buff_ptr = 0;
static int channel_buffer[MAX_CHANNELS];
static int channel_number = 0;


static double freq = 1000.0;
static long num_of_samples: = 6000L;
static int dma_channel = 5;
static int num_of_channels = 1;


void main(int argc, char *argv[])
       {
       unsigned long num_collected = 0L;
       long loop_count = 0l;
       int ch;

       if(argc < 4){
              printf("Format:\n\n");
              printf("   ADCTEST <number of channels> ");
              printf("<number of samples> <sampling ");
              printf("frequency (Hz)>\n\n");
              exit(MISSING_PARAMETERS_ERROR);
              }

       num_of_channels = atoi(argv[1]);
       num_of_samples = atol(argv[2]);
       freq = atof(argv[3]);

       if (!LabMasterAD_Enable()) {
              printf("LabMasterAD %u V%u was not enabled.\n",
                      LabMasterAD_Product(),
                      LabMasterAD_Version());
              exit(NOT_ENABLED_ERROR);
              }

       printf("\n\nLabMasterAD %u", LabMasterAD_Product());
       printf(" V%u Enabled for\n", LabMasterAD_Version());
       printf("%d channels, ", num_of_channels);
       printf("%ld samples at ", num_of_samples);
       printf("at %lf Hz.\n", freq);

       if((file_handle = open("DATAFILE.DAT", 0_BINARY |
                              0_WRONLY | 0_CREAT | 0 TRUNC, S_IWRITE)) < 0){
              printf("DATAFILE.DAT could not be opened.\n\n");
              exit(CANT_OPEN_FILE_ERROR);
              }

       timer_reset();
       if(!init_adc_dma(num_of_channels, num_of_samples,
                    &freq, dma_channel, dma_handler)){
              printf("Errors initializing DMA transfer.\n\n");
              exit(CANT_INITIALIZE_ERROR);
              }

       printf("\nPress SPACE bar to start.\n\n");

       while ((ch = getch()) != ' ' && ch != 0x1b)
              ;

       if(ch == ESC) {
              printf("Execution Prematurly Terminated.\n\n");
              exit(OK_EXIT);
              }

       printf("ADC DMA has been started.\n");
       printf("Press ESC to exit from ADC DMA.\n\n");

       enable_dma(dma_channel);
       enable_adc();

       while (!adc_dma_done()) {
              if (kbhit())
                     if (getch() == ESC)
                            terminate_adc_dma();

              get_next_adc_values();

              /*
              // Insert here required main loop processing.
              {
              int i;

              for(i=0; i<num_of_channels; i++)
                    printf("%4X    ", channel_buffer[i]);
              for(i=0; i<num_of_channels; i++)
                    printf("\b\b\b\b\b\b\b\b");
              }
              */

              loop_count++;
              }

       // Write remaining values in file buffer.
       write(file_handle, file_buffer, file_buff_ptr*
              sizeof(int));

       printf("\n\nADC DMA was initialized for\n");
       printf("\t%d channels, %ld samples at %lf Hz\n\n",
              num_of_channels, num_of_samples, freq);

       printf("    Status:%8X\n", adc_status());
       printf(" Collected:%8ld\n",
              adc_dma_conversion_count());
       printf("Loop Count:%8ld\n\n", loop_count);
       printf("Finished...    ");

       if(adc_dma_conversion_count() < num_of_channels *
                    num_of_samples)
              printf("OVERRUN ERROR\n\n");
       else
              printf("NO ERRORS\n\n");

       LabMasterAD_Disable();
       exit(OK_EXIT);
       }

void dma_handler(int value)
/*& DMA handler routine. Used for processing each piece
        of     data. */
       {

       file_buffer[file_buff_ptr] = value;

       if(++file_buff_ptr >= FILEBUFFSIZE) {

              write(file_handle, file_buffer,
                    FILEBUFFSIZE*sizeof(int));

              file_buff_ptr = 0;
              }

       channel_buffer[channel_number] = value;

       if(++channel_number >= num_of_channels)
              channel_number = 0;

       // Insert here any further process that may be
       // required.
       // Be carful that the new code does not cause the
       // duration of this routine to exceed the required
       // limits for the selected data acquisition
       // specification.
       }
/*  End of File */

Related Reading


More Insights






Currently we allow the following HTML tags in comments:

Single tags

These tags can be used alone and don't need an ending tag.

<br> Defines a single line break

<hr> Defines a horizontal line

Matching tags

These require an ending tag - e.g. <i>italic text</i>

<a> Defines an anchor

<b> Defines bold text

<big> Defines big text

<blockquote> Defines a long quotation

<caption> Defines a table caption

<cite> Defines a citation

<code> Defines computer code text

<em> Defines emphasized text

<fieldset> Defines a border around elements in a form

<h1> This is heading 1

<h2> This is heading 2

<h3> This is heading 3

<h4> This is heading 4

<h5> This is heading 5

<h6> This is heading 6

<i> Defines italic text

<p> Defines a paragraph

<pre> Defines preformatted text

<q> Defines a short quotation

<samp> Defines sample computer code text

<small> Defines small text

<span> Defines a section in a document

<s> Defines strikethrough text

<strike> Defines strikethrough text

<strong> Defines strong text

<sub> Defines subscripted text

<sup> Defines superscripted text

<u> Defines underlined text

Dr. Dobb's encourages readers to engage in spirited, healthy debate, including taking us to task. However, Dr. Dobb's moderates all comments posted to our site, and reserves the right to modify or remove any content that it determines to be derogatory, offensive, inflammatory, vulgar, irrelevant/off-topic, racist or obvious marketing or spam. Dr. Dobb's further reserves the right to disable the profile of any commenter participating in said activities.

 
Disqus Tips To upload an avatar photo, first complete your Disqus profile. | View the list of supported HTML tags you can use to style comments. | Please read our commenting policy.