Understanding and Performing Analog to Digital Signal Conversion

Created by Alex Simpkins 1-19-05, updated 9-14-06

Introduction

What are 'analog' and 'digital' quantities?

There are two types of signals to be considered within the context of microprocessors:

  • Analog - a continuously variable quantity which has infinite resolution, and varies between a given range.
    • Example 1 : A water faucet which allows the volume flow rate of water flowing in your sink to be controlled with a twist produces a flow rate of water that is analog. If you want to slightly alter volume flow rate, you turn the knob just slightly clockwise or counterclockwise. The volume flow rate of water is an example of an ANALOG quantity.
    • Example 2 : A circuit involving a voltage divider where one resistance is variable by a potentiometer produces an analog voltage. The potentiometer allows you to control the voltage between some minimum and maximum determined by the input voltage and the other resistance in the circuit.

 

  • Digital - a quantity which is 'either-or.' In logic terms, this quantity either exists or does not exist, represented by a logical 'one' or a logical 'zero.'
    • Example 1 : Timezones are an example of a digital quantity. You are either in one time zone or another.
    • Example 2 : The basic stamp has 16 digital I/O pins which can output either 5 Volts or 0 Volts. This is a digital quantity.

Converting between analog and digital quantities

An analog quantity can be converted to a digital quantity, and vice-versa. Obviously, information is lost whenever this conversion happens. The digital quantity lacks the infinite information which is contained in the analog signal, but much of that information may be unnecessary, if the digital representation contains sufficient information.

 

For the world of electronics, analog and digital quantities generally exist in terms of voltages. Converting from analog to digital and digital to analog signals can be performed with the use of simple microchips. Many of these chips then communicate with a host computer or microprocessor by serial or parallel means. One advantage of this is that an analog signal can be converted to digital numbers, then sent across large distances in a way by which no more information is lost than the initial conversion. A long wire will tend to pick up ambient noise, which will then be measured as if part of the signal of interest. For example, common noise comes from AC power in a building. The AC power cycles as a sine wave at a frequency of 60 Hertz (60 times per second).

This sine wave then adds to the signal you are attempting to measure. If the sine wave amplitude is similar to your signal, you cannot measure your signal. This proportion is called the signal to noise ratio. There are many steps which may be taken to reduce noise, such as shielding bare wires from electromagnetism.

Each voltage signal which is measured is referred to as a channel. Many microchip analog to digital converters have more than one channel which can be measured. One such chip, which we shall discuss here is the ADC0838, manufactured by linear devices. Some of the important features of the ADC0838 (see the DATASHEET for more info) are:

  • 8 channels (when set up for single-ended measures, or 4 channels when setup as differential measures - more on that later),
  • a resolution of 8 bits (2^8 steps between 0 and Vref, 256 steps - more on that later).
  • communicates the digital measurements of analog signals serially
  • can perform an analog to digital conversion in 32 microseconds.

That's 0.000032 Seconds! One may think that is incredibly fast, and yes it certainly is far quicker than you can say 'convert,' but you will see that the speed is necessary. In order to be sure you are measuring what you think you are measuring, a few issues must be considered and dealt with. The first is the speed at which the signal you are trying to measure is changing. If you are trying to measure the temperature change in your coffee while you read this article, a sample rate of once every few seconds will be sufficient to measure the temperature variation. If you are trying to measure the acceleration experienced by a test vehicle colliding with a wall during a crash test, once every few seconds is far too slow, you need at least 1000 times per second (1 kHz) or perhaps faster! In order to measure a signal, and avoid problems, one must sample, or record data points, at twice the maximum rate of change you are interested in. This avoids what is referred to as aliasing. Aliasing is an undesirable phenomenon which can happen when a high frequency signal is sampled at a frequency less than twice as fast. The resulting signal which one thinks one has measured is not a true signal, as evidenced below:

Here we see that as our sample frequency drops below two times the frequency of the sine wave, our measured signal fails to reproduce the sine wave accurately. As we drop the frequency even more, the signal we measure is looks more like a triangle wave than a sine wave.

Filtering:

Low Pass filtersmay need to be implemented to remove higher frequency artifacts from your measurements. A low pass filter, as the name implies, allows low frequency data to pass through it, while 'attenuating' (reducing the amplitude of ) the high frequency aspects of the data. In other words, you measure only the signals you want to measure, and remove what you don't want. This is similar to drinking orange juice with no pulp. You get the juice, but if you don't want the pulp, you filter it out! A low pass filter is implemented as follows:

and the values can be computed from the equation:

f = 1/RC

f = desired cutoff frequency

R = resistance (Ohms)

C = capacitance (Farads)

How to implement A to D with a basic stamp II and an ADC0838:

 

The physical package of the ADC0838 which we will use is as follows:

Here is a pin diagram of the ADC0838.

And a description of each pin:

  • Ch0-7 are the analog input channels. We can configure them as single-ended or differential inputs.
  • Com - common connection of the analog inputs, treat as the '-' connection. In the current context of the basic stamp, this is connected to Vss
  • DGND - ground reference for digital communication. In the case of the basic stamp, this is Vss
  • AGND - ground reference for powering the chip. This can be different from the Com or DGND, but in the case of what we will do with this now, connect to the Vss.
  • Vref - used for a reference on AtoD conversion (the analog voltage is compared to this maximum)
  • SE - this controls the format of the data output - MSB first or LSB first (more on this later)
  • DO - the data output of the ADC0838. This and DO can be tied together, since the converter automatically 'stops listening' to the appropriate pin. This happens by the pin which is ignored becoming of very high 'impedance'
  • SARS - this line tells the stamp when the commands have all registered in the ADC0838 and it is ready with a number to send back out to the stamp. It is pulled low during the conversion and setup, and high when ready to send data out to the stamp.
  • CLK - the clock pin controls the rate of communication of the ADC0838. With each rising and falling edge of the clock pin, one piece of information is transmitted or recieved
  • DI - data input to the ADC0838. This and DO can be tied together, since the converter automatically 'stops listening' to the appropriate pin. This happens by the pin which is ignored becoming of very high 'impedance'
  • CS - chip select tells the ADC0838 when to initiate a conversion. This is done by a falling edge, ie pulsing the chip select pin high then low again
  • V+ - connect to Vdd (on stamp) or Vcc
  • Vcc - (5V) the voltage supply for the ADC0838, to power its internal circuitry. This must be a smooth supply without much ripple or noise. It should be as close to exactly 5 volts as possible

 

  • Single-ended - voltages are measured with respect to some ground
  • Differential - voltages are measured at two points and the difference is the measured value

A common connection for using the ADC0838 with the basic stamp II for analog to digital conversion is as follows (R1 is a 10 kOhm potentiometer, our 'variable' input which lets us give a voltage between 0 and maximum voltage drop), R2 and R3 form a voltage divider, dividing 5V in half ( Vo = Vi*R3/(R2+R3):

 

Note1 : +5V is the stamp Vdd, GND is stamp Vss, since in this case our sensors will be powered by the stamp. Consult the ADC0838 datasheet for more info for which ground to use for a separately powered or referenced analog signal source.

Note2 : the connector labelled 'to_stamp' refers to stamp pin connections to the basic stamp Digital I/O's (0-15). We will use 1-5 here

Note3 : We are only using channel 0 in this example, but all channels can be connected to different analog sources for different measurements

 

How to program the basic stamp II to read an analog signal from the ADC0838

There are a few things that must happen for a successful read from the ADC0838. These are the steps:

  1. The CS line must be pulled low from high, and held low for the duration of the sample
  2. We now setup the ADC0838 chip by telling it the type of conversion, and channel desired (NOTE: only one channel can be sampled at a time). We will use the SHIFTOUT command on the basic stamp to pulse the CLK line once per data bit, while making the DIO line high or low to indicate appropriate data. The MUX table bellow proivdes for all options for setting up the data converfsion; however we our examples all use single ended input. The first data bit is what is referred to as a start bit, and is not linked to the setup, but is required before sending the setup commands. In the datasheet, this is referred to as the 'MUX addressing.'
  3. Once the setup is complete, a small amount of time for the conversion takes place, and then the ADC0838 is ready to communicate the data back. We will use the SHIFTIN command to bring the converted value back into the stamp and store it in a variable.
  4. At this point the conversion is complete, and we can convert the data into a integer variable that represents voltage, force, velocity, etc. One must be very very careful at this step, since the stamp uses integer math, and variables have limited size as well. A general overview of integer math is that all values involved are integers, for example, 5/8 = 0.625 would come out as 0 on a stamp. Be careful about variables, since a byte variable is a number between 0 and 255, and a word is a 16 bit number, i.e. a number between 0 and 2^16 (65535).

Here is a timing diagram equivalent to what is in words above:

The following table is how we set up the adc0838 for which channel to use and whether to be single-ended or differential (the codes we are interested in are the mux addresses. So if you wanted to set up your sample for single-ended, channel 0, you would send 11000 with the shiftout command like this: SHIFTOUT DIO, CLK, 1, [%11000\5]):

 

A Quick Program to read the analog voltage across the potentiometer:

 

'declare variables and constants
SE CON 5 'Recall that CON defines a constant. The format is NAME CON number, then that number

'replaces that name everywhere in your code when you compile it

CS CON 3 'we are defining the basic stamp pin numbers for each line
DIO CON 4 'this is the data in/out line on the stamp
SAR CON 1 'this is a line the stamp can monitor which tells when the ADC0838 chip is ready to give the sample value
CLK CON 2 'this is a clock line on the stamp, used to time the communications between the stamp and ADC0838 chip

adcBits VAR BYTE 'we'll be putting the data read from the ADC0838 chip into this variable

volt_ch0 VAR WORD 'this is going to be the converted voltage read from the specified channel (channel 0)

volt_ch6 VAR WORD 'this is going to be the converted voltage read from the specified channel (channel 6)

 

main:

' ******* Step 1: setup AD chip

'reset clock to make sure it is ready to go and follow the correct form
LOW CLK
LOW SE

'pull CS low to tell the chip to initiate a conversion
'hold low for entire conversion

HIGH CS
LOW CS

' ********* Step 2: specify which channel to read

'The Basic Stamp communicates to the ADC0838 chip with the SHIFTOUT commands in the folloiwng format

'SHIFTOUT Data Pin, Clock Pin, 1 (for most signficant bit first), [Binary string that specfies channel]

' which typically looks like

' SHIFTOUT DIO, CLK, 1, [binary string]

' The binary string that specifes the channel to input, always has the first bit as 1 (a start bit)

' The folloiwng 4 bits are specfied in the first 4 columns in table 2, according to the channel being read

' The Binary String is prefaced with a % and ends with a \n, where n is the nubmer of bits. The whole string is inside [square brackets].

SHIFTOUT DIO, CLK, 1, [%11000\5] ' Request analog input on channel 0

'**********Step 3: Read the data back into the stamp, into the adcBits variable

'Get the sample, 8 bits expected, Most significant bit first
SHIFTIN DIO, CLK, MSBPOST, [adcBits\8]

'**********Step 4: Convert the data into a voltage. BE VERY CAREFUL HERE!!!! We are dealing with integer math,

'which means remainders are truncated, ie 5/10 = 0 on the stamp, and 0.75 = 0 on the stamp!

'convert to a 10x voltage and display on the debug screen, ie 00 to 50 would equal 0.0 to 5.0 Volts
volt_ch0 = adcBits*50/255
DEBUG CR, CR, "Decimal value, 10x the voltage on channel 0: ", DEC3 volt_ch0 '

'****************************************************************************

'****************************************************************************

'now we'll read the channel 6 voltage divider (repeat what was above with a different MUX setup

' ******* Step 1: setup AD chip

'reset clock to make sure it is ready to go and follow the correct form
LOW CLK
LOW SE

'pull CS low to tell the chip to initiate a conversion
'hold low for entire conversion

HIGH CS
LOW CS

' ********* Step 2: specify which channel to read

SHIFTOUT DIO, CLK, 1, [%11011\5] ' Request analog input on channel 0

'*********Step 3: Read the data into the stamp

'Get the sample, 8 bits expected, Most significant bit first
SHIFTIN DIO, CLK, MSBPOST, [adcBits\8]

'*********Step 4: convert the data to a voltage value. Be EXTRA careful here: we're dealing

'with integer math, so 4/5 = 0! There are not decimals, ie 0.5 is 0 in integer math

'convert to a 10x voltage and display on the debug screen, ie 00 to 50 would equal 0.0 to 5.0 Volts
volt_ch6 = adcBits*50/255
DEBUG CR, CR, "Decimal value, 10x the voltage on channel 0: ", DEC3 volt_ch6

'Start over
GOTO main

If you want to measure an analog voltage, just connect the analog signal to the appropriate pin, referenced to COM (ie, + signal to Ch#, analog ground to COM), or differential referenced to Ch-. Then program the ADC0838 with the appropriate setup codes.

'now we'll start generating a clock pulse, the first 1 on the DI line is a start bit
'all leading zeros are ignored

'Channel 0, single-ended measure, the first bit is a start bit, the last four
'are the mux addresses, telling which channel and so on

 

 

 

Important Issues when connecting a signal:

Impedance is a big issue. One can consider impedance to be similar to resistance. Problems can occur from various related issue to impedance. If the impedance of the signal passing through circuits is not matched properly, spurious readings can result from energy waves reflecting through the circuit. This is a similar phenomenon to a wave bouncing off the wall of a pool and reflecting back. Consider the signal you are measuring to be similar to a river. Your measurements are performed by drawing off some of the river to measure, say speed. If you draw 3/4 of the river for your measurements, the original signal of the river is affected, and your measure may not be valid (most likely not!). However, if you use a tube 1/10000th of the width of the river, the quantity of water removed by your measurement will not significantly affect the river, and your measure is more likely not invalid.

Check the voltage range of the input signal. It must be within the set-up of your chip, or you risk damaging your ADC0838 chip.

Don't forget to low pass filter your input. Decide on the fastest signal you'll need to measure and cut off the rest.

Realize that there is more happening than what is described here, consider this document as a simple introduction to data acquisition. It gives you the tools you need to get started, but please continue to expand your knowledge. Otherwise when problems arise, they may take a long time to understand when they may be simple issues.