Problems while lowering the sampling rate

Post your MATLAB discussions here
Post Reply
tei
Newbie
Posts: 0
Joined: Fri Jun 17, 2016 8:06 am

Problems while lowering the sampling rate

Post by tei »

I need a configuration that triggers on channel D at 200mV captures 17 microsseconds of data at a sampling rate of 10ns on channel A and delivers it, then restarts. I calculated that 17microseconds with a sampling rate of 10ns should be 1700 postsamples.

I have problems to catch the trigger when setting the sampling rate to 10ns. Also I don't know how to restart the whole process.

Here is what I have got till now:

Code: Select all

classdef Test < handle
    
    properties
        %===Other==============                     
        picoScope;
        
        %===PicoScope==========       
        picoEnums;
        picoStreamGroup;
        picoBufferSize  = 1e6; 
        picoStatus;
        picoBufferDriver;        
        picoBufferApp;        
        picoChannelRangeMV;                
        picoNumSamplesTriggerPre = 0;
        picoNumSamplesTriggerPost = 2e5;
        picoStreamingInterval = 50e-9;
        picoTriggerTreshMV = 200;
    end
    
    methods     
        
        function main(this)
            try                   
       

          PS6000Config;
          this.picoEnums = ps6000Enuminfo;
          this.picoScope = icdevice('picotech_ps6000_generic.mdd');
          connect(this.picoScope);

          this.picoScopeChannelSetup();
          this.picoScopeBufferSetup();
          this.picoScopeTriggerSetup();
          this.picoScopeMiscealousSetup();

                     
                
            this.picoScopeStartMeasure();
            catch ex
               disp(ex.message);                          
            end
        
          
            this.picoScopeCleanUp();
        end

        function picoScopeStartMeasure(this)
            downSampleRatio     = 1;
            downSampleRatioMode = this.picoEnums.enPS6000RatioMode.PS6000_RATIO_MODE_NONE;            
            maxADCCount = double(get(this.picoScope, 'maxADCValue'));
            
            maxSamples = get(this.picoScope, 'numPreTriggerSamples') + get(this.picoScope, 'numPostTriggerSamples');
            
            pBufferChAFinal = libpointer('int16Ptr', zeros(maxSamples, 1, 'int16'));                        
            
            [this.picoStatus.runStreaming, actualSampleInterval, sampleIntervalTimeUnitsStr] = ...
                invoke(this.picoStreamGroup, 'ps6000RunStreaming', downSampleRatio, ...
                downSampleRatioMode, this.picoBufferSize);
            
            exitLoop = PicoConstants.FALSE; % Indicates if the device has stopped automatically.
            totalSamples        = 0; % Total number of samples captured by the device.            
            this.picoStatus.getStreamingLatestValues = PicoStatus.PICO_OK; % OK
            count = 0;
            countNull = 0;   
            
            while exitLoop == PicoConstants.FALSE && this.picoStatus.getStreamingLatestValues == PicoStatus.PICO_OK
                                
                ready = PicoConstants.FALSE;
   
                while(ready == PicoConstants.FALSE)

                   this.picoStatus.getStreamingLatestValues = invoke(this.picoStreamGroup, 'getStreamingLatestValues');

                   ready = invoke(this.picoStreamGroup, 'isReady');                 
                end
                
                hasAutoStopOccurred = invoke(this.picoStreamGroup, 'autoStopped');

              
             
                                
                % Check for new data values
                [newSamples, startIndex] = invoke(this.picoStreamGroup, 'availableData');
                
                 if(hasAutoStopOccurred == PicoConstants.TRUE)

                  disp('AutoStop: TRUE - exiting loop.');  
                  break;
   %Restart Process?
             %     [this.picoStatus.runStreaming, actualSampleInterval, sampleIntervalTimeUnitsStr] = ...
                 %           invoke(this.picoStreamGroup, 'ps6000RunStreaming', downSampleRatio, ...
                  %            downSampleRatioMode, this.picoBufferSize);
                 end
                 
                 if(newSamples > 0)                    
                    
                    firstValuePosn = startIndex + 1;
                    lastValuePosn = startIndex + newSamples; 
                    
                    % Check if the scope has triggered
                    [triggered, triggeredAt] = invoke(this.picoStreamGroup, 'isTriggerReady');

                    if (triggered == PicoConstants.TRUE)
                       disp('Triggered');
                        % Adjust trigger position as MATLAB does not use zero-based
                        % indexing.
                       bufferTriggerPosition = triggeredAt + 1;

                       triggeredAtIndex = totalSamples + bufferTriggerPosition;       
                       count = count +1;
                        
                     %  bufferChAmV = adc2mv(this.picoBufferApp.Value(triggeredAtIndex:lastValuePosn), this.picoChannelRangeMV, maxADCCount);
                       
                       if count >= 2                           
                           exitLoop = PicoConstants.TRUE;                                             
                       end
                    end

                   totalSamples  = totalSamples + newSamples;
                   
                     % Convert data values to millivolts from the application buffer(s).

                  
                    clear bufferChAmV;                    
                    clear firstValuePosn;
                    clear lastValuePosn;
                    clear startIndex;
                    clear triggered;
                    clear triggerAt;                   
                 else
                   countNull = countNull +1;
                 end                      
                 
                 if (countNull == 10)
                     break;
                 end           
            end                           
        end
            
        function picoScopeTriggerSetup(this)
          triggerGroupObj = get(this.picoScope, 'Trigger');
          triggerGroupObj = triggerGroupObj(1);       
          
            
            set(triggerGroupObj, 'autoTriggerMs', 0);         
            
            [status.setSimpleTrigger] = ...
                invoke(triggerGroupObj, 'setSimpleTrigger', ...
                this.picoEnums.enPS6000Channel.PS6000_CHANNEL_D, ...
                this.picoTriggerTreshMV, this.picoEnums.enPS6000ThresholdDirection.PS6000_RISING);                                   

        end
        
        function picoScopeMiscealousSetup(this)
            set(this.picoScope, 'numPreTriggerSamples', this.picoNumSamplesTriggerPre);
            set(this.picoScope, 'numPostTriggerSamples', this.picoNumSamplesTriggerPost);            
            set(this.picoStreamGroup, 'streamingInterval', this.picoStreamingInterval);
        end
        
        function picoScopeChannelSetup(this)
            
             this.picoStatus.setChannelStatus(1) = invoke(...
                this.picoScope, 'ps6000SetChannel', 0, PicoConstants.TRUE, ...
                this.picoEnums.enPS6000Coupling.PS6000_DC_1M, this.picoEnums.enPS6000Range.PS6000_500MV,...
                0.0, this.picoEnums.enPS6000BandwidthLimiter.PS6000_BW_FULL);
            
            this.picoChannelRangeMV = PicoConstants.SCOPE_INPUT_RANGES(this.picoEnums.enPS6000Range.PS6000_500MV + 1);

            this.picoStatus.setChannelStatus(4) = invoke(...
                this.picoScope, 'ps6000SetChannel', 3, PicoConstants.TRUE, ...
                this.picoEnums.enPS6000Coupling.PS6000_DC_1M, this.picoEnums.enPS6000Range.PS6000_1V,...
                0.0, this.picoEnums.enPS6000BandwidthLimiter.PS6000_BW_FULL);          
        end

        function picoScopeBufferSetup(this)
            segmentIndex        = 0;   
            ratioMode           = this.picoEnums.enPS6000RatioMode.PS6000_RATIO_MODE_NONE;
            channelA            = this.picoEnums.enPS6000Channel.PS6000_CHANNEL_A;            
           
            % Initialisiere den Application und den Driver Buffer            
            this.picoBufferDriver = libpointer('int16Ptr', zeros(this.picoBufferSize, 1, 'int16'));            
            this.picoBufferApp = libpointer('int16Ptr', zeros(this.picoBufferSize, 1)); 
            
            % Übergebe Driver-Buffer an das PicoScope
            this.picoStatus.setDataBufferChA = invoke( this.picoScope, 'ps6000SetDataBuffer', ...
                channelA, this.picoBufferDriver, this.picoBufferSize, segmentIndex, ratioMode);            
            
            % Hole Streaming Group
            this.picoStreamGroup = get(this.picoScope, 'Streaming');
            this.picoStreamGroup = this.picoStreamGroup(1);

            % Verbinde Application und Driver Buffer mit Streaming Group
            this.picoStatus.setAppAndDriverBuffers = invoke(this.picoStreamGroup, 'setAppAndDriverBuffers', ...
                channelA, this.picoBufferApp, this.picoBufferDriver, this.picoBufferSize);            
        end        
    
        function picoScopeCleanUp(this)
           if (isempty(this.picoScope))
               return;
           end
           
           [status.stop] = invoke(this.picoScope, 'ps6000Stop');
           disconnect(this.picoScope);
           delete(this.picoScope);
        end
    end
end

Hitesh

Re: Problems while lowering the sampling rate

Post by Hitesh »

Hi tei,

Given the period of time over which you are collecting data, I would recommend collecting data using a block mode capture rather than trying to use streaming mode.

The device is unable to sample at 10 ns (refer to the Timebases section in the Programmer's Guide, so if you are only using channels A and D you can collect data using a sampling interval of 400 ps and then downsample (decimate) by a factor of 25 to retrieve the 1700 samples at 10 ns intervals.

Here's a suggested code flow:

Code: Select all

icdevice()
connect()

% Configure channels and trigger

% Set the timebase property of the device object

% Set number of pre-trigger and post-trigger samples

% Loop

[status.runBlock] = invoke(blockGroupObj, 'runBlock', 0);

% Retrieve data values:
%
% start index       : 0
% segment index     : 0
% downsampling ratio: 25
% downsampling mode : 4 (ps6000Enuminfo.enPS6000RatioMode.PS6000_RATIO_MODE_DECIMATE)

% Provide additional output arguments for the remaining channels e.g. chB
% for Channel B.
[numSamples, overflow, chA, ~, ~, ~] = invoke(blockGroupObj, 'getBlockData', 0, 0, 25, 4);

% End Loop

% Stop

% Disconnect
Regards,

tei
Newbie
Posts: 0
Joined: Fri Jun 17, 2016 8:06 am

Re: Problems while lowering the sampling rate

Post by tei »

Thank you.

I'm now trying to invoke "ps6000RunBlock" but I can't determine how to call it in the right way. I took 1 as the timebase to set it to 400ps and oversampling-rate to 1. I set timIndisposedMs to null and segementIndex to 1. What do I have to insert for lpReady and pParameter. The exception I got is "Not enough input arguments.".

Code: Select all

%              PICO_STATUS ps6000RunBlock
% (
% short handle,
% unsigned long noOfPreTriggerSamples,
% unsigned long noOfPostTriggerSamples,
% unsigned long timebase,
% short oversample,
% long * timeIndisposedMs,
% unsigned long segmentIndex,
% ps6000BlockReady lpReady,
% void * pParameter
% )
           [this.picoStatus.runBlock] = ...
                 invoke(blockGroupObj, 'ps6000RunBlock', this.picoNumSamplesTriggerPre, this.picoNumSamplesTriggerPost, ...
                1, 1, null, 1, null, null);

Hitesh

Re: Problems while lowering the sampling rate

Post by Hitesh »

Hi tei,

Try passing the empty matrix '[]' instead of null for your arguments or alternatively use the 'runBlock' function where you only need to pass in the segmentIndex parameter.

Regards,

tei
Newbie
Posts: 0
Joined: Fri Jun 17, 2016 8:06 am

Re: Problems while lowering the sampling rate

Post by tei »

Unfortunately thats not working.
Now I get the error: "No method with matching signature."

Code: Select all

  [this.picoStatus.runBlock] = ...
                 invoke(blockGroupObj, 'ps6000RunBlock', this.picoNumSamplesTriggerPre, this.picoNumSamplesTriggerPost, ...
                1, 1, [], 1, [], []);
I have to call ps6000RunBlock because I want to invoke commands on a different device as stated in your example:

Code: Select all

%%
% This example uses the _runBlock_ function in order to collect a block of
% data - if other code needs to be executed while waiting for the device to
% indicate that it is ready, use the _ps6000RunBlock_ function and poll
% the _ps6000IsReady_ function.

% Capture a block of data:
%
% segment index: 0 (The buffer memory is not segmented in this example)

[status.runBlock] = invoke(blockGroupObj, 'runBlock', 0);

Hitesh

Re: Problems while lowering the sampling rate

Post by Hitesh »

Hi tei,

Please e-mail support@picotech.com and I can provide you with an updated Instrument Driver file which has the ps6000RunBlock function.

Regards,

Post Reply