Implementing pulse setup/hold time monitoring device

I need an instrument that can monitor two signals from a stepper motor controller.

Namely STEP and DIR.

For the STEP signal I want to monitor the step pulse length and time between pulses recording min and max.
For the DIR signal I want to record the minimum setup/hold time in relation to rising edge of the STEP pulse.

The STEP signal frequency is max 150 kHz and the minimum pulse length (both more or less
guaranteed by design because it is software generated) is 500 nsec.

Required accuracy is 2 usec.

I happen to have Parallax Propeller dev kit that I've never used so I figure out, maybe this is something that
could be relatively easily implemented on it.

Is this feasible?

Where should I start?

Pointers to 'closest similar' ready made project to get me started?

I've never programmed Propeller but have close to 40 years of experience in embedded stuff with
all the usual suspect CPUs working with assembler and C.

Any comments welcome.

cheers Kusti

Comments

  • iseriesiseries Posts: 399
    edited 2018-03-15 - 10:43:42
    While what you are asking for is simple enough, coding it is a different story.

    Here is some sample code that records how long a signal is high and low using some hardware counters.
    #include "simpletools.h"
    
    #define DIR 1
    #define STEP 2
    
    void doRecord(void *);
    
    long volatile Low;
    long volatile High;
    int *cog;
    
    
    int main()
    {
    
      cog = cog_run(&doRecord, 50);
      
     
      while(1)
      {
        print("Low: %d, High: %d", Low, High);
        pause(1000);    
      }  
    }
    
    void doRecord(void *par)
    {
      CTRA = 0x30000000 | STEP;  //Count when high
      CTRB = 0x20000000 | STEP;  //Count when low
      FRQA = 1;                  //Count by 1
      FRQB = 1;                  //Count by 1
      
      input(STEP);
      
      while (1)
      {
        while (get_state(STEP) == 0);  //Wait for pin to go low
        PHSA = 0;                      //Clear high counter
        while (PHSA == 0);             //Wait for counter to start
        PHSB = 0;                      //Clear low counter
        while (get_state(STEP) == 0);  //Wait for pin to go low
        Low = PHSA;                    //How many counts was that
        while (get_state(STEP) == 1);  //Wait for pin to go high
        High = PHSB;                   //How many counts was that
      }
    }
    

    To convert counter values to microseconds you need to divide by 80 as the processer is running at 80 Mhz.

    Here is a link to the hardware manual and also about counters.
    https://parallax.com/downloads/propeller-p8x32a-documentation

    Mike
  • Thanks!!

    Looks simple enough to get me started, I will dug out the dev kit tonight and see what happens ;)

    Funny, I was not expecting C, my mind set was spin and stuff though I had read about C on Propeller when bought the kit some years ago.


    cheers Kusti
  • Actually never picked up SPIN. Long time seasoned C coder.

    Love the propeller as it's straight forward and simple to program.

    STM on the other hand is a head banger.

    Mike
  • jmgjmg Posts: 13,928
    edited 2018-03-15 - 19:10:42
    nyholku wrote: »
    ..
    Namely STEP and DIR.

    For the STEP signal I want to monitor the step pulse length and time between pulses recording min and max.
    For the DIR signal I want to record the minimum setup/hold time in relation to rising edge of the STEP pulse.

    The STEP signal frequency is max 150 kHz and the minimum pulse length (both more or less
    guaranteed by design because it is software generated) is 500 nsec.

    Required accuracy is 2 usec.
    A 2us accuracy is going to give 0 on 500ns ?
    As above, gated counters can measure Hi or Lo times, to 12.5ns, but you may need care to capture a single pulse before the next one arrives.

    One easy sanity check there, would be to allocate one COG CTRA,CTRB pair, and have one Pulse-Width gated, and the other Edge counting.
    Reading both, without clearing either, will roughly indicate cases where multiple pulses were averaged.

    Roughly is because you cannot capture both values on the same sysclk, nearest possible capture is 50ns, so there can be small phase creep of the two.
    If you are ok with averages, you could measure many pulses in HLL.

    setup/hold time is not so simple... but timers can do LOGIC A & !B etc on two pins, so that can assist :
    STEP   ___/===\_______/===\_______/===\_______/===\_______/===\_______
    DIR   ________________________/======================\________________
              ^w          ^w          ^w
    DIR & !STEP   ________________/===\____/======\____/==\___________________
                          ^cT1        ^cT2 CTRA
    !DIR & !STEP _/======\____/==\___________________
                          ^cT3        ^cT4 CTRB
       
    

    Here you track STEP edge using wait and save gated timers (cT1,cT3 points), then when DIR has _/= since last save, wait for next STEP, and cT2-cT1 is th, and cT4-CT3 is tsu
  • Hi, thanks for input, I'm back on this project after a period of hiatus.

    I have some hurdles on the way but I will make a second thread on those.
  • Some basics first.
    Most instructions (pasm) are 4 clocks so at 80MHz thats 50ns per instruction. However you can overclock the prop. Most of Parallax P1 boards have pluggable xtals and Parallax sell (currently?) 6.25MHz crystals. That would give you 100MHz or 40ns per instruction. The waitpxx instructions can get 1 clock resolution after setup.
    Then there are two counters that can be programmed in each cog.
    You biggest problem will be seeing the results on a monitor. Youll need to do some averaging.

    Start with something simple. Wait for the start of the step pulse, time the length, output it, wait a little for the output, and repeat.
    My Prop boards: P8XBlade2, RamBlade, CpuBlade, TriBlade
    Prop OS (also see Sphinx, PropDos, PropCmd, Spinix)
    Website: www.clusos.com
    Prop Tools (Index) , Emulators (Index) , ZiCog (Z80)
  • So, if I understand correctly, you want to determine the timing of an actual stepper controller with output signals "Step" and "Dir". There should be a reason to do this. Can you tell about that reason?
    Fakt is (not Fake), that for some reason step/direction signals exist, while it would be much better to only have quadrature signals to drive a stepper. But it is, as is is. The problem is: if there is a "dir" signal, it makes only sense to change dir of a stepper at low speed, that is, step pulses have low frequency. A good idea is the change direction in the middle of two step pulses. But in a control loop you might be forced to change direction very quickly (if for example the loop runs at 20kHz). So you create more decisions than you can execute. In this case: just do nothing, wait until you decision settles.

    So my advice: before you solve the problem to measure a problem, try to eliminate the underlying problem. You could e.g. easily take the output of the stepper controller, filter any glitch and create new step/dir signals to drive your motor driver.
    no reason to reason if you feel feelings: in love with the propeller

    How-2-TACHYON
  • Cluso99Cluso99 Posts: 15,409
    edited 2019-10-06 - 22:01:47
    Most likely the DIR only has to be set prior to the STEP going active as it is probably latched on the rising edge of STEP (presuming active is high). So anything from >=0ns is probably fine. It may need to remain stable thru the STEP width although again its not likely. This does presume that the device has an electronic interface which is most likely these days.
    So for your testing, you could just use a simple program to wait for Step to go hi, read the time CNT, read the DIR pin, then wait for Step to go low, read CNT, sub the first CNT value from the new CNT value, and output the results to hub for another cog to process at its leisure, and go back to the start. You could add for the first wait to subtract its CNT from the previous CNT when STEP went low to give the time of the low part of Step. All this is easy in pasm.

    Here is a simple example (untested and not complete)
    con
      pinstep  = 3  ' the pin number for STEP
      pindir   = 4  ' the pin number for DIR
    
    pub start
    
    dat
                    org     0
    entry
    loop            waitpeq pinhi,stepmask                  ' wait for STEP to go hi
                    mov     timehi,cnt                      ' save the time
                    mov     direction,ina                   ' read all pins
                    and     direction,dirmask               ' extract DIR pin
                    wrlong  direction,ptrdir                ' save in hub
                    sub     timelo,timehi                   ' get the STEP low time (not valid first time)
                    wrlong  timelo,ptrsteplo                ' save in hub
    
                    waitpeq pinlo,stepmask                  ' wait for STEP to go lo
                    mov     timelo,cnt                      ' save the time
                    sub     timehi,timelo                   ' get the STEP high time
                    wrlong  timehi,ptrstephi                ' save in hub
                    jmp     #loop
    
    pinhi           long    1<<pinstep                      ' 
    pinlo           long    0<<pinstep                      ' will always be 0
    stepmask        long    1<<pinstep                      ' same as pinhi
    dirmask         long    1<<pindir
    direction       long    0
    timehi          long    0
    timelo          long    0
    
    ptrdir          long    @dirhub                         ' pointer to the location in hub for the DIR pin value
    ptrstephi       long    @stephi                         ' pointer to the location in hub for the STEP high time count (clocks)
    ptrsteplo       long    @steplo                         ' pointer to the location in hub for the STEP low time count (clocks)
    
    dat
                    org     0
    ' hub locations...
    dirhub          long    0
    stephi          long    0
    steplo          long    0
    
    My Prop boards: P8XBlade2, RamBlade, CpuBlade, TriBlade
    Prop OS (also see Sphinx, PropDos, PropCmd, Spinix)
    Website: www.clusos.com
    Prop Tools (Index) , Emulators (Index) , ZiCog (Z80)
  • jmgjmg Posts: 13,928
    edited 2019-10-06 - 22:40:52
    Cluso99 wrote: »
    Most likely the DIR only has to be set prior to the STEP going active as it is probably latched on the rising edge of STEP (presuming active is high). So anything from >=0ns is probably fine. It may need to remain stable thru the STEP width although again its not likely...
    From the OP's initial wording, they needed DIR setup and hold (relative to Step _/=), so I think they suspect issues that may need trouble shooting.
    However, that is easy to add to your example loop, if they configure the CTRA, CTRB to be 2-pin gated from STEP, DIR, they can also be read and MIN values collected.
  • Surely what you are trying to do you would do with a scope or logic analyzer? The only reason you would do it with a Prop is because you want it to be a permanent instrument, a one-off or a production item itself. If you are lacking basic test equipment but you have a Prop then why not try SPLAT, it is a logic analyzer for the Prop that you can view on a serial terminal.

    Either way, Tachyon Forth itself can easily do what you want including the VGA display and even data-logging to an SD if there is some reason for that.

    Tachyon Forth - compact, fast, forthwright and interactive
    useforthlogo-s.png
    --->CLICK THE LOGO for more links<---
    P2 +++++ TAQOZ INTRO & LINKS +++++ P2 SHORTFORM DATASHEET
    P1 +++++ Latest Tachyon includes EASYFILE +++++ Tachyon Forth News Blog
    Brisbane, Australia
Sign In or Register to comment.