snippet to learn about the cordic solver

Hello forumists,
before I get my P2 silicon, I'm learning a bit of P2 theory. I am particularly interested in the Cordic solver.
That's why I write a few lines to learn the function. Maybe it is useful for others too.
The easy use of the cordic excites me.

Reinhard

Comments

  • Duane DegnDuane Degn Posts: 10,007
    edited 2019-12-02 - 16:52:30
    I'm just trying to figure out P2 stuff myself.

    I was under the impressing 90 was $4000_0000 instead of $3FFF_FFFF.
    I believe I saw a post from Chip where he used $2000_0000 for 45 degrees.
    I think a full 360 angle can't be stored in 32-bits. The way I understand it, $FFFF_FFFF is one bit less than a full circle.

    Edit: Forgot a zero in $4000_0000.
  • @Duane Degn

    Long time no see!
    Re-inventing the wheel is not a waste of time if, when you are done, you understand why it is round.
  • Chip lists some angles in this post: https://forums.parallax.com/discussion/comment/1179680/#Comment_1179680

    Here's the section of code listing some degrees.
    QSINCOS/QARCTAN/QROTATE usage:
    
    For the circular functions, angles are 32-bits and roll over at 360-degrees:
    
        $00000000 = 0 degrees                (360 * $00000000 / $1_00000000)
        $00000001 = ~0.000000083819 degrees  (360 * $00000001 / $1_00000000)
        $00B60B61 = ~1 degree                (360 * $00B60B61 / $1_00000000)
        $20000000 = 45 degrees               (360 * $20000000 / $1_00000000)
        $40000000 = 90 degrees               (360 * $40000000 / $1_00000000)
        $80000000 = 180 degrees              (360 * $80000000 / $1_00000000)
        $C0000000 = 270 degrees              (360 * $C0000000 / $1_00000000)
        $FFFFFFFF = ~359.9999999162 degrees  (360 * $FFFFFFFF / $1_00000000)
    
  • Long time no see!

    Life has been crazy busy.

    I'm trying to figure out how to use the P2 so I'll likely be on the forum a lot more than I have the last few years.
  • Duane Degn wrote: »
    I'm just trying to figure out P2 stuff myself.

    I was under the impressing 90 was $4000_0000 instead of $3FFF_FFFF.
    I believe I saw a post from Chip where he used $2000_0000 for 45 degrees.
    I think a full 360 angle can't be stored in 32-bits. The way I understand it, $FFFF_FFFF is one bit less than a full circle.

    Edit: Forgot a zero in $4000_0000.

    360 degrees is the same as 0 degrees, so you store it as $0000_0000. The beauty of binary radians is that equivalent angles have equivalent representations.
  • If you want to synthesize some frequency, you just add the frequency-proportional value into an accumulator and use the accumulator as the angle each time. Rollover is welcome.
  • Thank's to all for the helpfull tips.
    in my learning snippet i make following modifications:

    mov x,#100
    mov y,#100
    the vector is obviously 100*sqrt(2) long and the angle is 45°

    now i ask the cordic
    ' (X,Y) in polar coordinates
    qvector x,y
    getqx _abs '-> show me $8D ... exact...
    getqy _arg '-> show me $2000_0000 ... exact...
    now the rotation
    rot90 'rotate (X,Y) 90 Degrees counterclockwise, math. positive
    setq y 'Y = 100
    qrotate x,angle 'X = 100 angle = $4000_0000
    getqx x ' show me $FFFF_FF9C = -$64 ... exact...
    getqy y ' show me $63 ...small error...
    'show (X,Y) in polar coordinates
    qvector x,y
    getqx _abs '-> $8D ... exact...
    getqy _arg '-> $603469DC = 135,2879° ...small error...

    I think the small errors are not important in a real application.
    Best regards
    Reinhard
  • cgraceycgracey Posts: 11,954
    edited 2019-12-04 - 01:26:44
    Reinhard, I'm not seeing that small error in $63. I'm getting $64:
    dat		org
    
    		setq	#100
    		qrotate	#100,##$4000_0000
    		getqy	x
    		setbyte	outb,x,#3
    		setbyte	dirb,#$FF,#3
    		jmp	 #$
    
    x		res	1
    

    Also, this produces the correct angle of $6000_0000:
    dat		org
    
    		qvector	##-100,#100
    		getqy	x
    		shr	x,#24
    		setbyte	outb,x,#3
    		setbyte	dirb,#$FF,#3
    		jmp	 #$
    
    x		res	1
    

    Could you check your setup and confirm you are getting errors? It's working correctly for me.
  • currently i test only with spinsim

    if i code this:
    dat
    	org
    
    set_point
    	mov	x,#100
    	mov	y,#100
    
    
    rot90					'rotate (X,Y) 90 Degrees counterclockwise, math. positive
    	setq	y		
    	qrotate	x,angle
    	getqx	x		  
    	getqy	y		
    
    loop	jmp	#loop
    
    
    angle	       long	 $4000_0000	
    
    _abs		res	1
    _arg		res	1
    x		res	1
    y		res	1
    

    i get this
    Cog  0: 00000037 0004 fd601418                 getqx   $a, cram[a] = ffffff9c
    Cog  0: 00000038 0005 fd601619 F               getqy   $b
    Cog  0: 00000039 0005 fd601619                 getqy   $b, cram[b] = 63
    
    

    if i code this
    dat
    	org
    
    set_point
    	mov	x,#100
    	mov	y,#100
    
    
    rot90					'rotate (X,Y) 90 Degrees counterclockwise, math. positive
    	setq	y		
    	qrotate	x,##$4000_0000	  
    	getqx	x		  
    	getqy	y		
    
    
    	
    loop	jmp	#loop
    
    
    angle	long	$4000_0000	
    
    _abs		res	1
    _arg		res	1
    x		res	1
    y		res	1
    
    

    i get this
    Cog  0: 00000037 0005 fd601618                 getqx   $b, cram[b] = 0
    Cog  0: 00000038 0006 fd601819 F               getqy   $c
    Cog  0: 00000039 0006 fd601819                 getqy   $c, cram[c] = 64
    
  • @Reinhard : I don't think spinsim's cordic implementation has been tested to be bit-accurate with the actual hardware. So I wouldn't read too much into small differences.

    Do you have a real P2 to test with?

    FlexGUI, a GUI for programming the P1 and P2 in Spin, PASM, BASIC, and C.
    Help support its development at Patreon or PayPal.
  • I have not a real P2 at the moment.
    But i hope to get one soon.
    I know that I can only test correctly if I have a P2.
    Until then, I try to get into programming with spinsim.

    Thanks
    Reinhard
  • cgraceycgracey Posts: 11,954
    edited 2019-12-04 - 06:08:27
    Reinhard wrote: »
    I have not a real P2 at the moment.
    But i hope to get one soon.
    I know that I can only test correctly if I have a P2.
    Until then, I try to get into programming with spinsim.

    Thanks
    Reinhard

    Man, I didn't catch that you were using a simulator. I spent years fiddling with CORDIC stuff to get it working as bit-perfectly as I could, so I was surprised you were seeing the $63, instead of the $64.

    That's great we've got a simulator, anyway.
  • Sorry about the excitement.
    But I wrote at the very beginning of the post I use a simulator.

    I admire your performance.
    I think the P2 is a great processor.
    Unfortunately, at the moment I only have the opportunity to test with a simulator.
    sorry again.
    Reinhard
  • Spinsim uses C floating point functions to simulate the cordic instructions. This causes the results to be slightly different. I could make spinsim bit-exact if I implemented the cordic resolver the same way it is implemented in the chip. However, I don't recall whether the precise implementation has ever been published.
  • Dave, I have seen the cordic-implementation in the spinsim sources.
    I think you must not do the effort to implement it bit-exact.
    It's precise enough how it is.
    I did not want to do a big drama about it either.
    By the way, the spinsim is (not only for me) the only way to see what is going on in the P2.
    Thank you for this helpful tool.
    Reinhard
Sign In or Register to comment.