Unusual SAR DMA Results

Tip / Sign in to post questions, reply, level up, and achieve exciting badges. Know more

cross mob
lock attach
Attachments are accessible only for community members.
Anonymous
Not applicable

Hello,

   

A while back I followed an example on how to set the DMA unit up to work with a SAR. What I am trying to do is to specify, with a constant, an N number of samples to capture from the SAR. When it is done capturing the samples, an interrupt fires, telling the main routine to write the results to the terminal. It is writing incorrect results to the terminal. I verified that my analog front end is working with a loop. It works flawlessly. The problem has something to do with the DMA configuration.

   

Can someone assist me in tracking it down. The project is attached.

   

Thanks,

   

Ben

0 Likes
19 Replies
Bob_Marlowe
Level 10
Level 10
First like given 50 questions asked 10 questions asked

current_data_flag must be declared as volatile because it is changed in an interrupt handler.

   

The TdSetConfiguration specifies a transfer count of 4 times NO_OF_SAMPLES, but your target array is only half of that size.

   

 

   

Bob

0 Likes
Anonymous
Not applicable

I changed the flag to volatile as well as the CyDmaTdSetConfiguration to 2 * NO_OF_SAMPLES.

   

It still is printing incorrect results. Something else is happening as well.

0 Likes
lock attach
Attachments are accessible only for community members.
Bob_Marlowe
Level 10
Level 10
First like given 50 questions asked 10 questions asked

I took the liberty to change some lines in your project.

   

Your main issue will be that you generate 100,000 samples/s which you cannot send over the uart wire with that speed. While sending, new values get generated...

   

There was an error within your Global.h -file where you included more than once the same declarations. This is usually done using the extern keyword. As a rule of thumb: Only declarations in a .h-file, no definitions/instantiations of variables or procedures.

   

I changed the interrupt handling, so that you can keep the handler within your own files and not within a generated file. Have a look into the "System Reference Guide" under Creator -> Help, search for "CY_ISR"

   

 

   

Bob

0 Likes
Anonymous
Not applicable

This problem is being stubborn. Your updated firmware is definately better C programming, but the DAC is still displaying the same old garbage when I run it. I fooled around with the array size constant and making it big (above 2048) changes the nature of the garbage. I think it is something to do with the configuration of that DMA. Either that or I maxed out the memory.

0 Likes
Bob_Marlowe
Level 10
Level 10
First like given 50 questions asked 10 questions asked

What are the results you get and what are the values you expect?

   

 

   

Bob

0 Likes
Anonymous
Not applicable

No matter what appears on the input it always spits out between 1.02V and 1.04V. It should, with my current setup spit out between around 0V and 0.16V.

0 Likes
Bob_Marlowe
Level 10
Level 10
First like given 50 questions asked 10 questions asked

Well, and what do you get when you read the result directly (after disabling DMA) from your ADC?

   

 

   

Bob

0 Likes
Anonymous
Not applicable

  Have a look into the "System Reference Guide" under Creator -> Help, search for "CY_ISR"

0 Likes
Anonymous
Not applicable

Quote

   

What do you get when you read the result directly (after disabling DMA) from your ADC?

   

 

   

The results are what they are supposed to be.

0 Likes
Bob_Marlowe
Level 10
Level 10
First like given 50 questions asked 10 questions asked

@Haroon

   

You are copying my post!

   

 

   

Bob

0 Likes
Anonymous
Not applicable

I have the differential inputs shorted at present. This should yield 0 volts. WIthout DMA usage, it does. With it, it spits out the incorrect results. Instead it bounces between 1.01 and 1.05 volts, clearly incorrect.

0 Likes
Anonymous
Not applicable

I also checked my power supplies with the scope, all are clean.

0 Likes
lock attach
Attachments are accessible only for community members.
EvPa_264126
Level 7
Level 7
500 replies posted 250 replies posted 100 likes received

Bob already told you: you are limited by time of sending data (UART)
You'll have to wait until the transmission in UART before starting a new measurement.
Check out my project,  I strongly reduced data rate.
I hope you have already done a search on the forum:
http://www.cypress.com/search.cfm?q=DMA+ADC+UART&sa.x=11&sa.y=4
http://www.cypress.com/?rID=46895

0 Likes
Bob_Marlowe
Level 10
Level 10
First like given 50 questions asked 10 questions asked

Shorting the +- inputs together does not mean that you read a zero as input, compare your setting to the explanation on page 6 of the SAR-datasheet. so the values 0x07ff are not unusual.

   

 

   

Bob

0 Likes
Anonymous
Not applicable

I am confused. Reading straight off the converter outputs the proper results (near zeros) when the input is shorted. When the input is not shorted, it displays the proper differential reading (or does it?). Your description and Page 6 somehow does not make it seem proper. The DMA and direct reads are giving different results bottom line. I would think they would square up.

   

Weird. What is really happening? Is the direct read somehow reading single ended?

0 Likes
Bob_Marlowe
Level 10
Level 10
First like given 50 questions asked 10 questions asked

I just went through the sources and found out that there IS a difference when reading via GetResult16() or using DMA. GetResult16() subtracts a variable named "_shift" which aligns the measured result to 2's complement. This cannot be done in DMA (no operations possible) and so the difference in the values. Look at page 17 of the SAR's datasheet.

   

 

   

Bob

0 Likes
Anonymous
Not applicable

Ah, that explains it.

   

Right now I am just subtracting the average of a bunch of values that appear on UART with the input shorted from the differential reading.

   

Is this the way it is usually done?

0 Likes
Bob_Marlowe
Level 10
Level 10
First like given 50 questions asked 10 questions asked

Not necessarily this way. The variable CURRENT_SENSE_shift is set during the initialization and has the value of 0x0800 for your configuration, but you may check for yourself.

   

 

   

Bob

0 Likes
EvPa_264126
Level 7
Level 7
500 replies posted 250 replies posted 100 likes received


Sorry for the stupid advice ....
Bob, thanks for the tip about page 17
it works:
CURRENT_SENSOR_SetOffset (0x800);

0 Likes