Shop OBEX P1 Docs P2 Docs Learn Events
SPI Flash spin2 code - Page 2 — Parallax Forums

SPI Flash spin2 code

2»

Comments

  • I still don't get it. :( My first guess was that Spi_Init() or Spi_Cmd32() would corrupt the stack so that size would be modified. So I inserted checks
    PUB Read (hubAdr, flashAdr, size)
    ' read any number of bytes
      test[0]:= size
      Spi_Init ()
      test[1]:= size
      Spi_Cmd32 (Read_Data, flashAdr)
      test[2]:= size
      repeat size
        byte[hubAdr++]:= Spi_RdByte ()
      ORG
        drvh        #spi_cs
      END
    
    But when I read out test[] later it's always correct, 3 times 80 for example. So I looked at the generated assembler code.
    '   test[2]:= size
    	add	objptr, #8
    	wrlong	local03, objptr
    	sub	objptr, #8
    '   repeat size
    	mov	local06, local03 wz
     if_e	jmp	#LR__0036
    LR__0035
    '     byte[hubAdr++]:= Spi_RdByte ()
    	calla	#_SpiFlash_Spi_RdByte
    	mov	local05, local01
    	mov	local07, local01
    	add	local07, #1
    	mov	local01, local07
    	wrbyte	result1, local05
    	mov	local04, local06
    	sub	local04, #1
    	mov	local06, local04 wz
     if_ne	jmp	#LR__0035
    LR__0036
    
    Not optimized very well but looks correct. Size (local3, local4 and local6) is decremented by only #1 per loop iteration.
  • ManAtWorkManAtWork Posts: 2,080
    edited 2020-07-13 12:42
    Doh! facepalm.gif
    The buffer in FlashDemo.spin2 is declared long!
    VAR
      long buffer[4096]
    
    So actually 256 bytes are read but only every fourth is displayed. You don't notice the gaps because also only every fourth byte is set to some meaningful value
      repeat i from 0 to 255
        buffer[i]:= i
    
    This sets byte 0, byte 4, byte 8 etc. to 1, 2, 3 etc. and the rest to 0.
  • Doh! Doh! Doh!

    will check it again with VAR byte buffer[256] and report back later !

    adding debug output of the buffer content, prior to flashWrite, may have also been a good idea earlier!. Extra Doh!



  • ...and I found out that the REP is no good idea. It works with Fastspin and -O1 optimization because the code is automatically copied to LUT RAM. But with no optimization or other compilers it fails because the jump-back of REP confuses the FIFO in hubexec mode and the timing is corrupted.

    I'll fix it and make another pull request for GIT.
  • A tip: the generated code for Read() will get much better if you replace
      ORG
        drvh #spi_cs
      END
    
    with
      pinh(spi_cs)
    
    The ORG is inhibiting a number of optimizations -- too many, it seems, and I need to dig into that, but in general the fewer ORGs in your code the better the compiler can do. In fastspin, at least, the pinh(spi_cs) will directly translate into drvh #spi_cs.
  • I have to confess that this object is one of the first things I wrote for the P2. There was very little documentation available about Spin2 and most examples were in pure assembler. So I took what I could get. Suggestions for improvements are welcome. I've seen that the situation is becoming better.
  • I think you did a great job @ManAtWork, especially considering the documentation situation.
  • Eric, I have played a little bit with the Spin2 pin commands after reading the new documentation. The commands are quite powerful and the predefined constants help making the code more clear by avoiding using literal bit patterns. But the optimization is not as good as it could be. Example:
    '   PinStart (pinRef , modePulse, $2000<<16 + $4000, 1)
    	mov	arg01, #32
    	mov	arg02, #72
    	mov	arg03, ##536887296
    	mov	arg04, #1
    	mov	local02, #32
    	calla	#__system___pinsetup
    	dirh	local02
    '   WrPin (pinSclk, modeTrans)
    	mov	arg02, #74
    	wrpin	arg02, #24
    '   WxPin (pinSclk, 90)  ' 1MHz
    	mov	arg02, #90
    	wxpin	arg02, #24
    
    Inlining the PinStart code would be better than a call. It executes faster and consumes less memory as it could be translated to only 4 instructions (WRPIN, WXPIN, WYPIN, DIRH) instead of 6. WRPIN() could also be translated to one single instruction instead of MOV + WRPIN.
  • Thanks for the suggestions. Here's a version of fastspin that should have much better optimizations (still not perfect, of course!)
Sign In or Register to comment.