Shop OBEX P1 Docs P2 Docs Learn Events
Quad Unipoler stepper driver, in progress. — Parallax Forums

Quad Unipoler stepper driver, in progress.

davidsaundersdavidsaunders Posts: 1,559
edited 2017-03-01 20:47 in Propeller 1
About an hour ago I decided to redo my stepper driver, to use PASM and just worry about how to control one stepper, then implement simple Ping Pong Pang Pow multitasking to get it up to four.

This has not been tested yet, as I need to rewrite my simple command interpreter to put in values for use with the new layout, as was easiest from PASM.

For my use this will be tied to an RPi using a simple clocked bi-directional three wire serial implementation based on that used by the Game Boy. In my use there is a command interpreter to take commands from a program running on the RPi.

The unimplemented 5th task will end up updating the current position information in hub ram for access by spin, as well as sending back to whatever else may want to know about it.

Here is where it is, while untested, if you add code to put useful values into the variables used by the PASM driver it should work so long as I did not miss something obvious (this is a quickly thrown together this afternoon, as a better way).

It is in next post, this one turned out to be to long with the code

Also note that the comment at the beginning does mention the command language that I use for my command interpreter.


As long as I did not miss something obvious it should be useful. Do not have much time this afternoon.

Comments

  • davidsaundersdavidsaunders Posts: 1,559
    edited 2017-03-01 21:46
    'Concept of usage, for stepper controller.
    'Uses a simple command sequence to control steppers.  Current version
    '  recieves its commands custom data link, from a control program
    '  running on a Raspberry Pi under Raspbian Linux.
    
    'All commands recieved are a long, where the high byte is the command
    '  and the lower 24-bits are the data for that command.
    'Speed is given in steps per second, in the range of 0 to 2048.  The
    '  direction flag indicates a reverse direction when set.  Distance is
    '  measured in steps, and is always taken as a positive number.
    'The supported commands are:
    ' $D0   Set the distance to move stepper A, distance is in bits 0..11,
    '        max speed is in bits 12..22, and direction in bit 23.
    ' $D1   Set the distance move for stepper B, same format as $10.
    ' $D2   Set the distance to move for stepper C, same format as $10.
    ' $D3   Set the distance to move for stepper D, same format as $10.
    ' $E0   Set the accelleration rate, for stepper B.
    ' $E1   Set the accelleration rate, for stepper C.
    ' $E2   Set the accelleration rate, for stepper D.
    ' $E3   Set the accelleration rate, for stepper A.
    ' $F0   Request status.
    'Any other value in the high byte is just ignored.
    'NOTICE: ACCELERATION NOT YET IMPLEMENTED, SORRY.
    
    CON
      _CLCKMODE XTAL1+PLL16
      _XINFREQ 5_000_000
    
    
    VAR
      long StpDrA      'Direction of movement for stepper A.
      long StpDlyA     'Time between steps for stepper A.
      long StpDstA     'Distance to move for Stepper A.
      long StpShftA    'Output Shift for stepper A.
      
      long StpDrB      'Direction of movement for stepper B.
      long StpDlyB     'Time between steps for stepper B.
      long StpDstB     'Distance to move for Stepper B.
      long StpShftB    'Output Shift for stepper B.
    
      long StpDrC      'Direction of movement for stepper C.
      long StpDlyC     'Time between steps for stepper C.
      long StpDstC     'Distance to move for Stepper C.
      long StpShftC    'Output Shift for stepper C.
    
      long StpDrD      'Direction of movement for stepper D.
      long StpDlyD     'Time between steps for stepper D.
      long StpDstD     'Distance to move for Stepper D.
      long StpShftD    'Output Shift for stepper D.
      
      long APos         'Current Position of Stepper A.
      long BPos         'Current Position of Stepper A.
      long CPos         'Current Position of Stepper A.
      long DPos         'Current Position of Stepper A.
    
    
    '***********************************************************
    DAT
       ORG 0
    Stepper
    
    '*** Initialize for task 1 *************
    
            MOV     dta,PAR            'Only need Shift val once.
            ADD     dta,#8
            RDLONG  StpShft1,dta
            ROL     Msk1,StpShft1      'Set up some masks.
            ROL     NMsk1,StpShft1
    
            SUB     dta, #4
            RDLONG  StpDly1,dta
            MOV     wt1,StpDly1         'need an initial time.
            ADD     wt1,CNT
    
    '*** Initialize for task 2 *************
            MOV     TASK2,#FtchLp2
            
            ADD     dta,#24
            RDLONG  StpShft2,dta
            ROL     Msk2,StpShft2      'Set up some masks.
            ROL     NMsk2,StpShft2
    
            SUB     dta, #4
            RDLONG  StpDly2,dta
            MOV     wt2,StpDly2         'need an initial time.
            ADD     wt2,CNT
    
    '*** Initialize for task 3 *************
            MOV     TASK3,#FtchLp3
            
            ADD     dta,#40
            RDLONG  StpShft3,dta
            ROL     Msk3,StpShft3      'Set up some masks.
            ROL     NMsk3,StpShft3
    
            SUB     dta, #4
            RDLONG  StpDly3,dta
            MOV     wt3,StpDly3         'need an initial time.
            ADD     wt3,CNT
    
    '*** Initialize for task 4 *************
            MOV     TASK4,#FtchLp4
            
            ADD     dta,#56
            RDLONG  StpShft4,dta
            ROL     Msk4,StpShft4      'Set up some masks.
            ROL     NMsk4,StpShft4
    
            SUB     dta, #4
            RDLONG  StpDly4,dta
            MOV     wt4,StpDly4         'need an initial time.
            ADD     wt4,CNT
    
    
    '***********************************************************
    '**** Task 1 Code ******************************************
    '***********************************************************
    FtchLp1
            JUMPRET TASK1,TASK2
    
            MOV     dta,PAR            'Grabbing parameters from the HUB.
            RDLONG  StpDr1,dta
            ADD     dta,#4
            RDLONG  StpDly1,dta
            ADD     dta,#4
            RDLONG  StpDst1,dta
    
    
     
    StpLp1
            MOV     scrt1,Step         'Get the value of the step.
            ROR     scrt1,cstp
            ROL     scrt1,StpShft1     'Line up for the output pins.
            AND     scrt1,NMsk1        'Be clean
    
            ADD     cstp1,StpDr1       'Get read for next step,
            AND     cstp1,#3           '  remember to keep bound 0, 3
    
            'WAITCNT wt1,StpDly1        'Time it correctly.
            MOV      tmp1,wt1           'And be able to ping pong pang pow.
    Wlp1    JUMPRET TASK1,TASK2
            SUB      tmp1,CNT
            CMP      tmp1,CVal     WC    'Maximum time to get back here is
      IF_C  JMP      #Wlp1              '  716 clocks, we use 1024.
            MOV      wt1,CNT
            ADD      wt1,StpDly1
            
            AND     OUTA,Msk1
            OR      OUTA,scrt1         'Change only our pins.
    
            SUB     StpDst1,1    WZ    'Are we done with this move?
      IF_Z  JMP     #StpLp1            '  if not keep on,
            JMP     #FtchLp1           '  if we are, get next movement.
          
          
    
      dta1      long 0             'Index into hub RAM, to get parameters.
      wt1       long 0             'How long to wait till next step.
      cstp1     long 0             'Current step index.
      scrt1     long 0             'Working scratch pad.
      Msk1      long $FFFFFFF0     'Pin mask.
      NMsk1     long $0000000F     'Inverted Pin mask.
      
      StpDr1    long 0
      StpDly1   long 0
      StpDst1   long 0
      StpShft1  long 0
    
    
    
    '***********************************************************
    '**** Task 2 Code ******************************************
    '***********************************************************
    FtchLp2
            JMPRET  TASK2,TASK3
    
            MOV     dta,PAR            'Grabbing parameters from the HUB.
            ADD     dta,#16
            RDLONG  StpDr2,dta
            ADD     dta,#4
            RDLONG  StpDly2,dta
            ADD     dta,#4
            RDLONG  StpDst2,dta
    
    
            JMPRET  TASK2,TASK3
     
    StpLp2
            MOV     scrt2,Step         'Get the value of the step.
            ROR     scrt2,cstp
            ROL     scrt2,StpShft2     'Line up for the output pins.
            AND     scrt2,NMsk2        'Be clean
    
            ADD     cstp2,StpDr2       'Get read for next step,
            AND     cstp2,#3           '  remember to keep bound 0, 3
    
            'WAITCNT wt2,StpDly2        'Time it correctly.
            MOV      tmp2,wt2           'And be able to ping pong pang pow.
    Wlp2    JMPRET  TASK2,TASK3
            SUB      tmp2,CNT
            CMP      tmp2,CVal     WC   'Maximum time to get back here is
      IF_C  JMP      #Wlp2              '  716 clocks, we use 1024.
            MOV      wt2,CNT
            ADD      wt2,StpDly2
            
            AND     OUTA,Msk2
            OR      OUTA,scrt2         'Change only our pins.
    
            SUB     StpDst2,1    WZ    'Are we done with this move?
      IF_Z  JMP     #StpLp2            '  if not keep on,
            JMP     #FtchLp2           '  if we are, get next movement.
          
          
    
      dta2      long 0             'Index into hub RAM, to get parameters.
      wt2       long 0             'How long to wait till next step.
      cstp2     long 0             'Current step index.
      scrt2     long 0             'Working scratch pad.
      Msk2      long $FFFFFFF0     'Pin mask.
      NMsk2     long $0000000F     'Inverted Pin mask.
      
      StpDr2    long 0
      StpDly2   long 0
      StpDst2   long 0
      StpShft2  long 0
    
    
    '***********************************************************
    '**** Task 3 Code ******************************************
    '***********************************************************
    FtchLp3
            JMPRET  TASK3,TASK4
    
            MOV     dta,PAR            'Grabbing parameters from the HUB.
            ADD     dta,#32
            RDLONG  StpDr3,dta
            ADD     dta,#4
            RDLONG  StpDly3,dta
            ADD     dta,#4
            RDLONG  StpDst3,dta
    
    
            JMPRET  TASK3,TASK4
     
    StpLp3
            MOV     scrt3,Step         'Get the value of the step.
            ROR     scrt3,cstp
            ROL     scrt3,StpShft3     'Line up for the output pins.
            AND     scrt3,NMsk3        'Be clean
    
            ADD     cstp3,StpDr3       'Get read for next step,
            AND     cstp3,#3           '  remember to keep bound 0, 3
    
            'WAITCNT wt3,StpDly3        'Time it correctly.
            MOV      tmp3,wt3           'And be able to ping pong pang pow.
    Wlp3    JMPRET  TASK3,TASK4
            SUB      tmp3,CNT
            CMP      tmp3,CVal     WC   'Maximum time to get back here is
      IF_C  JMP      #Wlp3              '  716 clocks, we use 1024.
            MOV      wt3,CNT
            ADD      wt3,StpDly3
            
            AND     OUTA,Msk3
            OR      OUTA,scrt3         'Change only our pins.
    
            SUB     StpDst3,1    WZ    'Are we done with this move?
      IF_Z  JMP     #StpLp3            '  if not keep on,
            JMP     #FtchLp3           '  if we are, get next movement.
          
          
    
      wt3       long 0             'How long to wait till next step.
      cstp3     long 0             'Current step index.
      scrt3     long 0             'Working scratch pad.
      Msk3      long $FFFFFFF0     'Pin mask.
      NMsk3     long $0000000F     'Inverted Pin mask.
      
      StpDr3    long 0
      StpDly3   long 0
      StpDst3   long 0
      StpShft3  long 0
    
    
    '***********************************************************
    '**** Task 4 Code ******************************************
    '***********************************************************
    FtchLp4
            JMPRET  TASK4,TASK1
    
            MOV     dta,PAR            'Grabbing parameters from the HUB.
            ADD     dta,#48
            RDLONG  StpDr4,dta
            ADD     dta,#4
            RDLONG  StpDly4,dta
            ADD     dta,#4
            RDLONG  StpDst4,dta
    
    
            JMPRET  TASK4,TASK1
     
    StpLp4
            MOV      scrt4,Step         'Get the value of the step.
            ROR      scrt4,cstp4
            ROL      scrt4,StpShft4     'Line up for the output pins.
            AND      scrt4,NMsk4        'Be clean
    
            ADD      cstp4,StpDr4       'Get read for next step,
            AND      cstp4,#3           '  remember to keep bound 0, 3
    
            'WAITCNT wt4,StpDly4        'Time it correctly.
            MOV      tmp4,wt4           'And be able to ping pong pang pow.
    Wlp4    JMPRET   TASK4,TASK1
            SUB      tmp4,CNT
            CMP      tmp4,CVal     WC   'Maximum time to get back here is
      IF_C  JMP      #Wlp4              '  716 clocks, we use 1024.
            MOV      wt4,CNT
            ADD      wt4,StpDly4
            
            AND      OUTA,Msk4
            OR       OUTA,scrt4         'Change only our pins.
    
            SUB      StpDst4,1    WZ    'Are we done with this move?
      IF_Z  JMP      #StpLp4            '  if not keep on,
            JMP      #FtchLp4           '  if we are, get next movement.
          
          
    
      wt4       long 0             'How long to wait till next step.
      cstp4     long 0             'Current step index.
      scrt4     long 0             'Working scratch pad.
      Msk4      long $FFFFFFF0     'Pin mask.
      NMsk4     long $0000000F     'Inverted Pin mask.
      
      StpDr4    long 0
      StpDly4   long 0
      StpDst4   long 0
      StpShft4  long 0
    
    
    '***********************************************************
    '**** Task 5 Code ******************************************
    '***********************************************************
    
    '***********************************************************
    '**** Values used by all tasks *****************************
    '***********************************************************
    
    
      Step   long %0011_0110_1100_1001
    
      dta      long 0             'Index into hub RAM, to get parameters.
      
      CVal   long 1024             'Value for comparing remaining time.
    
      TASK1  LONG 0
      TASK2  LONG 0
      TASK3  LONG 0
      TASK4  LONG 0
    
    {{
    ┌──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────┐
    │                                                   TERMS OF USE: MIT License                                                  │                                                            
    ├──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────┤
    │Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation    │ 
    │files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy,    │
    │modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software│
    │is furnished to do so, subject to the following conditions:                                                                   │
    │                                                                                                                              │
    │The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.│
    │                                                                                                                              │
    │THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE          │
    │WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR         │
    │COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,   │
    │ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.                         │
    └──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────┘
    }}
    
    Edit: Corrected one bug I noticed while looking at the code.
Sign In or Register to comment.