Wrong ADC values in every other position of the buffer array

Post discussions on projects you are working on
JavaChips
Newbie
Posts: 0
Joined: Wed Jun 01, 2022 5:40 pm

Wrong ADC values in every other position of the buffer array

Post by JavaChips »

Hi all,

I'm currently writing a Java program to run a 2206B PicoScope in block mode. Something very bizarre is happening: every other value in the buffer array is incorrect. To work around this, I skip these wrong values by incrementing the index by 2 when I read from the buffer array. But I would still like to know why this happens because this workaround essentially reduces my sampling rate in half.
I appreciate any help I can get.

Best,
JavaChips

bennog
Advanced User
Advanced User
Posts: 206
Joined: Mon Nov 26, 2012 9:16 am
Location: Netherlands

Re: Wrong ADC values in every other position of the buffer array

Post by bennog »

You probably have 2 channels enabled during configuration, or channel B not disabled during setup.

Benno

Martyn
Site Admin
Site Admin
Posts: 4491
Joined: Fri Jun 10, 2011 8:15 am
Location: St. Neots

Re: Wrong ADC values in every other position of the buffer array

Post by Martyn »

It would be useful to see your code, either post here or send to support@picotech.com

Please note that even though the PicoScope 2206B is an 8 bit scope the values returned to the application are 16 bit.
Martyn
Technical Support Manager

JavaChips
Newbie
Posts: 0
Joined: Wed Jun 01, 2022 5:40 pm

Re: Wrong ADC values in every other position of the buffer array

Post by JavaChips »

Thanks for the replies.

Regarding configuration of channels, I have configured both channels and enabled them, and yet, both buffers have wrong values in every other position.

I have also noted that the values returned are 16 bits, so I believe my conversion formula is correct (cannot use the method given from the sdk as it mixes different data types so it ends up giving me incorrect values).

I think it may have something to do with how I configured the channels, or how I used the getValues function since the scope is giving me wrong ADC values. Here are snippets of my code that may reveal why this is the issue:

Setting channels

Code: Select all

                //Set up channel A
                
                int channelA = PS2000ACLibrary.PS2000A_CHANNEL.PS2000A_CHANNEL_A.ordinal();
                short enabledA = 1;
                int typeA = PS2000ACLibrary.PS2000A_COUPLING.PS2000A_DC.ordinal();
                int rangeA = PS2000ACLibrary.PS2000A_RANGE.PS2000A_2V.ordinal();
                float analogOffsetA = 0.0f;

                int setChannelReturnA = PS2000ACLibrary.INSTANCE.ps2000aSetChannel(handle, channelA, enabledA, typeA, rangeA, analogOffsetA);
                
                //Set channel B

                int channelB = PS2000ACLibrary.PS2000A_CHANNEL.PS2000A_CHANNEL_B.ordinal();
                short enabledB = 1;
                int typeB = PS2000ACLibrary.PS2000A_COUPLING.PS2000A_DC.ordinal();
                int rangeB = PS2000ACLibrary.PS2000A_RANGE.PS2000A_2V.ordinal();
                float analogOffsetB = 0.0f;

                int setChannelReturnB = PS2000ACLibrary.INSTANCE.ps2000aSetChannel(handle, channelB, enabledB, typeB, rangeB, analogOffsetB);
Get timebase

Code: Select all


                // Get timebase 

                // If we want 40 Hz => 1/40KHz = 25000 ns
                // 2500 ns * 62500000 + 2 = 1564.5 ns

                int timebase = 760;
                int noOfPreTriggerSamples = 5000;
                int noOfPostTriggerSamples = 5000;
                int noSamples = noOfPreTriggerSamples + noOfPostTriggerSamples;

                FloatByReference timeIntervalNsRef = new FloatByReference();
                timeIntervalNsRef.setValue((float) 0.0);

                short oversample = 0;

                IntByReference maxSamplesRef = new IntByReference();
                maxSamplesRef.setValue(0);

                int segmentIndex = 0;

                int getTimebase2Status = PicoStatus.PICO_INVALID_TIMEBASE;

                // Loop until a valid timebase has been found 

                while (getTimebase2Status != PicoStatus.PICO_OK) {
                    getTimebase2Status = PS2000ACLibrary.INSTANCE.ps2000aGetTimebase2(handle, timebase, noSamples, timeIntervalNsRef, oversample, maxSamplesRef, segmentIndex);

                    if (getTimebase2Status == PicoStatus.PICO_OK) {
                        break;
                    } else {
                        timebase = timebase + 1;
                    }
                }
 
Run block and wait until data collection is complete

Code: Select all

                // Running block 

                IntByReference timeIndisposedMs = new IntByReference();

                int runBlockStatus = PS2000ACLibrary.INSTANCE.ps2000aRunBlock(handle, noOfPreTriggerSamples, noOfPostTriggerSamples, timebase, oversample, timeIndisposedMs, segmentIndex, null, null);

                // Wait until the oscilloscope is ready 

                System.out.println("Collecting data...");

                ShortByReference ready = new ShortByReference();
                while (ready.getValue() == 0) // 1 for data collection done 
                {
                    int isReadyStatus = PS2000ACLibrary.INSTANCE.ps2000aIsReady(handle, ready);
                }
   
Set buffers

Code: Select all

                // Set bufferA

                Pointer bufferAMax = new Memory(noSamples * Native.getNativeSize(Short.TYPE));
                Pointer bufferAMin = new Memory(noSamples * Native.getNativeSize(Short.TYPE));

                for (int n = 0; n < noSamples; n++) {
                    bufferAMax.setShort(n * Native.getNativeSize(Short.TYPE), (short) 0);
                    bufferAMin.setShort(n * Native.getNativeSize(Short.TYPE), (short) 0);
                }

                int ratioModeA = PS2000ACLibrary.PS2000A_MODE.PS2000A_RATIO_MODE_NONE.ordinal();

                int setDataBuffersStatusA = PS2000ACLibrary.INSTANCE.ps2000aSetDataBuffers(handle, channelA, bufferAMax, bufferAMin, noSamples, segmentIndex, ratioModeA);

                // Set bufferB

                Pointer bufferBMax = new Memory(noSamples * Native.getNativeSize(Short.TYPE));
                Pointer bufferBMin = new Memory(noSamples * Native.getNativeSize(Short.TYPE));

                for (int n = 0; n < noSamples; n++) {
                    bufferBMax.setShort(n * Native.getNativeSize(Short.TYPE), (short) 0);

                }

                int ratioModeB = PS2000ACLibrary.PS2000A_MODE.PS2000A_RATIO_MODE_NONE.ordinal();

                int setDataBuffersStatusB = PS2000ACLibrary.INSTANCE.ps2000aSetDataBuffers(handle, channelB, bufferBMax, bufferBMin, noSamples, segmentIndex, ratioModeB);
 
Get values

Code: Select all

                // Get values
                
                int startIndex = 0; 
                IntByReference noOfSamples = new IntByReference(noSamples); 
                int downSampleRatio = 0; 
                int downSampleRatioMode = PS2000ACLibrary.PS2000A_MODE.PS2000A_RATIO_MODE_NONE.ordinal();
                ShortByReference overflow = new ShortByReference();
                
                int getValueReturn = PS2000ACLibrary.INSTANCE.ps2000aGetValues(handle, startIndex, noOfSamples, downSampleRatio, downSampleRatioMode, segmentIndex, overflow);

   
Thank you,
JavaChips

Martyn
Site Admin
Site Admin
Posts: 4491
Joined: Fri Jun 10, 2011 8:15 am
Location: St. Neots

Re: Wrong ADC values in every other position of the buffer array

Post by Martyn »

In our C# example

https://github.com/picotech/picosdk-c-s ... Console.cs

the GetValues call on line 401 uses a DownSampleRatio of 1, you are using 0.
Martyn
Technical Support Manager

JavaChips
Newbie
Posts: 0
Joined: Wed Jun 01, 2022 5:40 pm

Re: Wrong ADC values in every other position of the buffer array

Post by JavaChips »

Unfortunately that does not help. Still getting the same results.

-JavaChips

Martyn
Site Admin
Site Admin
Posts: 4491
Joined: Fri Jun 10, 2011 8:15 am
Location: St. Neots

Re: Wrong ADC values in every other position of the buffer array

Post by Martyn »

I would suggest simplifying your code as you are not using data aggregation.

Firstly change to using one channel, until you get it working, and then switch to using the ps2000aSetDataBuffer call not the dual buffer aggregation call ps2000aSetDataBuffers as you don't need the MinMax buffers.

If this works correctly you can then add in the second channel.
Martyn
Technical Support Manager

JavaChips
Newbie
Posts: 0
Joined: Wed Jun 01, 2022 5:40 pm

Re: Wrong ADC values in every other position of the buffer array

Post by JavaChips »

Thanks for the suggestion Martyn, but that was the original setup I had and I was getting the same results.

Only Channel A was set up and I used ps2000aSetDataBuffer instead.

-JavaChips

Martyn
Site Admin
Site Admin
Posts: 4491
Joined: Fri Jun 10, 2011 8:15 am
Location: St. Neots

Re: Wrong ADC values in every other position of the buffer array

Post by Martyn »

With the simplified version of code I would suggest using a known DC voltage at half of the chosen range, and then post the values you are getting back so we can see what you are receiving.
Martyn
Technical Support Manager

JavaChips
Newbie
Posts: 0
Joined: Wed Jun 01, 2022 5:40 pm

Re: Wrong ADC values in every other position of the buffer array

Post by JavaChips »

I've switched back to the simplified version of the code. The chosen range for now is 2V, so using a wave generator, I fed a 1V DC signal into Channel A.

Here are the ADC values I am getting. The correct ADC value is 16488. As you can see, every other value is incorrect.
https://imgur.com/a/eFt8Esu

bennog
Advanced User
Advanced User
Posts: 206
Joined: Mon Nov 26, 2012 9:16 am
Location: Netherlands

Re: Wrong ADC values in every other position of the buffer array

Post by bennog »

I find it hard to believe the value is exact 16488 every sample.
If you input a sin wave and post al the samples on wetransfer or here as attachment.
also for a square wave.

Benno

JavaChips
Newbie
Posts: 0
Joined: Wed Jun 01, 2022 5:40 pm

Re: Wrong ADC values in every other position of the buffer array

Post by JavaChips »

Hi Benno,

It's not 16488 every sample -- the values I showed in the picture were only of the first few. There were definitely noise spikes here and there.

I inputted a 300Hz 1Vpp sine and square waves. Here are the results. As you can see, every other value seems continuous...the other ones are incorrect.

-JavaChips
Attachments
square_wave_300hz_1vpp_adc.txt
(58.54 KiB) Downloaded 264 times
sine_wave_300hz_1vpp_adc.txt
(54.94 KiB) Downloaded 270 times

bennog
Advanced User
Advanced User
Posts: 206
Joined: Mon Nov 26, 2012 9:16 am
Location: Netherlands

Re: Wrong ADC values in every other position of the buffer array

Post by bennog »

It looks like you are getting min-max values.
2022-08-03_07-45-36.png
Ch-A from the 1st sample and every other sample
Ch-B from the 2nd sample and every other sample
They both show square and a sine wave only the Ch-B value is about 30% higher than the Ch-A values.

So what Martyn said about MIN/MAX is probably the case.

Benno
Attachments
pico-adc-values.xlsx
(801.59 KiB) Downloaded 266 times

JavaChips
Newbie
Posts: 0
Joined: Wed Jun 01, 2022 5:40 pm

Re: Wrong ADC values in every other position of the buffer array

Post by JavaChips »

Thanks for organizing the data and noticing this pattern!

I also had a feeling this may have to do with Min/Max buffers, which is why I used ps2000aSetDataBuffers() at the time of posting this topic in hopes that either the Max or the Min buffer would give me the correct values. But I found that the Max buffer still had alternating values...

I'm wondering if this is because my enumeration of PS2000A_MODE is missing a mode. I included all of the ones listed in the Programmer's Guide, but can never be too sure.
(See topic41920.html?&p=147882#p147882).

Code: Select all

        public enum PS2000A_MODE
        {
            PS2000A_RATIO_MODE_NONE, 
            PS2000A_MODE_AGGREGATE, 
            PS2000A_RATIO_MODE_AVERAGE, 
            PS2000A_RATIO_MODE_DECIMATE
        }
-JavaChips

Martyn
Site Admin
Site Admin
Posts: 4491
Joined: Fri Jun 10, 2011 8:15 am
Location: St. Neots

Re: Wrong ADC values in every other position of the buffer array

Post by Martyn »

This is the correct enumeration for the ps2000a devices, note it is not a straight enum and the order is different to yours. However as you are using None this would be the same anyway.

Code: Select all

/// 
/// Various methods of data reduction.
/// Note that a single call to setting the buffers (ie. ps2000aSetDataBuffer) can only
/// associate one buffer with one downsampling mode. If you intend to retrieve more than one
/// downsampling mode from the get values functions, you must call set data buffer several
///	times to associate a separate buffer with each channel and downsampling mode.
/// 
typedef enum enPS2000ARatioMode
{
	/// 
	/// No downsampling. Returns the raw data values.
	/// 
	PS2000A_RATIO_MODE_NONE,
	/// 
	/// Reduces every block of n values to just two values: a minimum and a maximum.
	/// The minimum and maximum values are returned in two separate buffers.
	/// 
	PS2000A_RATIO_MODE_AGGREGATE = 1,
	/// 
	/// Reduces every block of n values to a single value representing the
	/// average (arithmetic mean) of all the values.
	/// 
	PS2000A_RATIO_MODE_DECIMATE = 2,
	/// 
	/// Reduces every block of n values to just the first value in the block,
	/// discarding all the other values.
	/// 
	PS2000A_RATIO_MODE_AVERAGE = 4,
} PS2000A_RATIO_MODE;

This doesn't look like Min/Max data, it is too regular, and would be equivalent to having a square wave with 30% continuous noise on the peaks and troughs. Can you use PicoScope 6 or PicoScope 7 and post a data file or screen shot of the same square wave signal. If we know what the signal should look like then we can possibly work out what is happening to the data in the arrays.
Martyn
Technical Support Manager

Post Reply