Ram Test for C3
RossH
Posts: 5,519
Hi,
Can someone with a C3 please try the enclosed binary and see if it works? - it's a simple RAM test for testing Catalina's 64kb SPI SRAM access code.
The program uses the serial port, and can be loaded by any suitable means (including the Parallax Propeller Tool or Catalina Payload).
When run, it prints Start? and waits for a y (this gives you time to start a serial terminal emulator). The first test is a trivial test which can be repeated by pressing y again. Or press n to go to the more complex test (which usually prints nothing).
If everything works ok, you should see something like:
Ross.
Can someone with a C3 please try the enclosed binary and see if it works? - it's a simple RAM test for testing Catalina's 64kb SPI SRAM access code.
The program uses the serial port, and can be loaded by any suitable means (including the Parallax Propeller Tool or Catalina Payload).
When run, it prints Start? and waits for a y (this gives you time to start a serial terminal emulator). The first test is a trivial test which can be repeated by pressing y again. Or press n to go to the more complex test (which usually prints nothing).
If everything works ok, you should see something like:
START?y A 00000000 00000000 DEADBEEF A 00000004 00000004 DEADBEEF A 00000008 00000008 DEADBEEF A 0000000C 0000000C DEADBEEF A 00000010 00000010 DEADBEEF A 00000014 00000014 DEADBEEF A 00000018 00000018 DEADBEEF A 0000001C 0000001C DEADBEEF A 00000020 00000020 DEADBEEF A 00000024 00000024 DEADBEEF A 00000028 00000028 DEADBEEF A 0000002C 0000002C DEADBEEF A 00000030 00000030 DEADBEEF A 00000034 00000034 DEADBEEF A 00000038 00000038 DEADBEEF A 0000003C 0000003C DEADBEEF AGAIN?n DONE AGAIN?Here is my XMM RAM access logic, in case anyone wants to check it:
'------------------------- C3 SPI XMM Support Routines ------------------------- ' ' XMM_Activate : Activate the XMM bus. ' XMM_Activate muxc XMM_Flags,#1 ' save C flag muxnz XMM_Flags,#2 ' save Z flag andn dira,MASK ' set I/O pins as inputs while initializing andn outa,MASK ' set all I/O pins zero ... or outa,CS_BOTH ' ... except CS_CLR and CL_CLK or dira,DIRN ' set pin directions mov XMM_Addr,BIT15 ' select ... call #XMM_BankSelect ' ... SPI SRAM bank 1 mov outx,#%0000_0001 ' set ... call #XMM_OutByte ' ... selected SPI SRAM ... mov outx,#%0100_0000 ' ... to sequential ... call #XMM_OutByte ' ... mode mov XMM_Addr,#0 ' select ... call #XMM_BankSelect ' ... SPI SRAM bank 0 mov outx,#%0000_0001 ' set ... call #XMM_OutByte ' ... selected SPI SRAM ... mov outx,#%0100_0000 ' ... to sequential ... call #XMM_OutByte ' ... mode shr XMM_Flags,#1 wz,wc ' restore C & Z flags, fall through to ... ' 'XMM_Tristate : Give up the XMM bus. Call this to allow other cogs to use microSD etc. ' To activate XMM again, call XMM_Activate. ' XMM_Tristate andn outa,CS_CLR ' Reset SPI channel ... or outa,CS_CLR ' ... to deselect SPI SRAMs XMM_Activate_ret XMM_Tristate_ret ret ' #ifdef NEED_XMM_READLONG ' ' XMM_ReadLong : Read long from XMM at address in XMM_Addr into the destination register ' set up in XMM_Dest. XMM_Activate should be called at least once before ' this routine is used. ' On entry: ' XMM_Addr : address to read (up to 16 bits) ' XMM_Dst : destination of this instruction set to destination register ' On exit: ' Destination register contains long read from XMM. ' ' ' XMM_ReadMult : Read multiple bytes in source register to XMM at address XMM_Addr. ' XMM_Activate should be called at least once before this routine is used. ' On entry: ' XMM_Addr : address to read (up to 16 bits) ' XMM_Dst : destination of this instruction set to destination register ' XMM_Len : number of bytes to read (usually 1, 2 or 4) ' On exit: ' Destination register contains bytes read from XMM. ' XMM_ReadLong mov XMM_Len,#4 ' read 4 bytes XMM_ReadMult muxc XMM_Flags,#1 ' save C flag muxnz XMM_Flags,#2 ' save Z flag mov outx,#%0000_0011 ' Set Command ... call #XMM_SetCmdAddr ' ... and Address (and lower CS) add XMM_Addr,XMM_Len ' update XMM_Addr mov XMM_Temp,#0 :ReadLoop call #XMM_InByte ' read next byte from SPI and outx,#$FF or XMM_Temp,outx ror XMM_Temp,#8 djnz XMM_Len,#:ReadLoop ' repeat while XMM_len <> 0 XMM_Dst mov 0-0,XMM_Temp ' save the result andn outa,CS_CLR ' reset SPI Channel ... or outa,CS_CLR ' ... to terminate read shr XMM_Flags,#1 wz,wc ' restore C & Z flags XMM_ReadLong_ret XMM_ReadMult_ret ret ' #endif ' #ifdef NEED_XMM_WRITELONG ' ' XMM_WriteLong : Write long in source register to XMM at address XMM_Addr. ' On entry: ' XMM_Addr : (32-bit) address to write (up to 16 bits) ' XMM_Src : source of this instruction set to source register ' On exit: ' XMM_Addr incremented by 4. ' ' ' XMM_WriteMult : Write multiple bytes in source register to XMM at address XMM_Addr. ' XMM_Activate should be called at least once before this routine is used. ' On entry: ' XMM_Addr : address to write (up to 16 bits) ' XMM_Src : source of this instruction set to source register ' XMM_Len : number of bytes to write (usually 1, 2 or 4) ' On exit: ' XMM_Addr incremented by 4. ' XMM_WriteLong mov XMM_Len,#4 ' write 4 bytes XMM_WriteMult muxc XMM_Flags,#1 ' save C flag muxnz XMM_Flags,#2 ' save Z flag mov outx,#%0000_0010 ' Set Command ... call #XMM_SetCmdAddr ' ... and Address (and lower CS) add XMM_Addr,XMM_Len ' update XMM_Addr XMM_Src mov XMM_Temp,0-0 ' save the value to write :WriteLoop mov outx,XMM_Temp and outx,#$FF call #XMM_OutByte ' write a byte to SPI ror XMM_Temp,#8 ' shift next byte down to prepare djnz XMM_Len,#:WriteLoop ' repeat while XMM_len <> 0 andn outa,CS_CLR ' reset SPI Channel ... or outa,CS_CLR ' ... to terminate read shr XMM_Flags,#1 wz,wc ' restore C & Z flags XMM_WriteLong_ret XMM_WriteMult_ret ret ' #endif ' #ifdef NEED_XMM_WRITEPAGE ' ' XMM_WritePage : Write bytes from Hub RAM to XMM RAM ' On entry: ' XMM_Addr (32-bit): destination address in sram, 16-bits used ' Hub_Addr (32-bit): source address in main memory, 16-bits used ' XMM_Len (32-bit): number of bytes to write. ' XMM_WritePage muxc XMM_Flags,#1 ' save C flag muxnz XMM_Flags,#2 ' save Z flag mov outx,#%0000_0010 ' Set Command ... call #XMM_SetCmdAddr ' ... and Address (and lower CS) :WriteLoop rdbyte outx,Hub_Addr ' get byte from source (Hub) call #XMM_OutByte ' write byte to SPI add Hub_Addr,#1 ' inc source address add XMM_Addr,#1 ' inc dest address djnz XMM_Len,#:WriteLoop ' repeat while XMM_len <> 0 andn outa,CS_CLR ' reset SPI Channel ... or outa,CS_CLR ' ... to terminate read shr XMM_Flags,#1 wz,wc ' restore C & Z flags XMM_WritePage_ret ret ' #endif ' #ifdef NEED_XMM_READPAGE ' ' XMM_ReadPage : Read bytes from XMM RAM to Hub RAM. ' On Entry: ' XMM_Addr (32-bit): source address in sram, 16-bits used ' Hub_Addr (32-bit): destination address in main memory, 16-bits used ' XMM_Len (32-bit): number of bytes to read. ' XMM_ReadPage muxc XMM_Flags,#1 ' save C flag muxnz XMM_Flags,#2 ' save Z flag mov outx,#%0000_0011 ' Set Command ... call #XMM_SetCmdAddr ' ... and Address (and lower CS) :ReadLoop call #XMM_InByte ' read byte from SPI wrbyte outx,Hub_Addr ' write byte to destination (Hub) add Hub_Addr,#1 ' inc dest address add XMM_Addr,#1 ' inc src address djnz XMM_Len,#:ReadLoop ' repeat while XMM_len <> 0 andn outa,CS_CLR ' reset SPI Channel ... or outa,CS_CLR ' ... to terminate read shr XMM_Flags,#1 wz,wc ' restore C & Z flags XMM_ReadPage_ret ret ' #endif ' 'XMM_SetCmdAddr : Set XMM command and address (and lower CS). XMM_Activate should be called ' at least once before this routine is used. 'On Entry: ' outx : Command (2 for read, 3 for write) ' XMM_Addr : address to set (up to 16 bits) 'On Exit: ' XMM_Addr : preserved ' C & Z flags destroyed! ' XMM_SetCmdAddr call #XMM_BankSelect ' select the SPI SRAM bank mov XMM_Test,#8 ' command is 8 bits rol outx,#24 ' put first bit in MSB :CmdLoop rol outx,#1 wc muxc outa,IBIT or outa,CLCK andn outa,CLCK djnz XMM_Test,#:CmdLoop mov XMM_Test,#16 ' 16 address bits rol XMM_Addr,#16 ' put first address bit in MSB :AddrLoop rol XMM_Addr,#1 wc muxc outa,IBIT or outa,CLCK andn outa,CLCK djnz XMM_Test,#:AddrLoop XMM_SetCmdAddr_ret ret ' ' XMM_OutByte - send a byte to the SPI RAM ' On entry: byte in outx (lower 8 bits) ' On exit: C flag destroyed! ' XMM_OutByte mov XMM_Test,#8 ' 8 bits rol outx,#24 ' put first bit in MSB :OutLoop rol outx,#1 wc muxc outa,IBIT or outa,CLCK andn outa,CLCK djnz XMM_Test,#:OutLoop XMM_OutByte_ret ret ' ' XMM_InByte - receive a byte from SPI RAM ' On exit: outx shifted left 8 bits, new byte in lower 8 bits ' On exit: Z flag destroyed! ' XMM_InByte mov XMM_Test,#8 ' 8 bits :InLoop test OBIT,ina wz shl outx,#1 muxnz outx,#1 or outa,CLCK andn outa,CLCK djnz XMM_Test,#:InLoop XMM_InByte_ret ret ' ' XMM_BankSelect - select appropriate SPI SRAM bank based on address ' On entry: XMM_Addr bit 15 determines SRAM bank to select (0 or 1) ' On exit: Z flag destroyed! ' XMM_BankSelect andn outa,CS_CLR ' Reset SPI Channel ... or outa,CS_CLR ' ... to deselect SPI SRAMs andn outa,CS_CLK ' toggle SPI Select Clock ... or outa,CS_CLK ' ... to select first SRAM (bank 0) test XMM_Addr,BIT15 wz ' if bit 15 set ... if_nz andn outa,CS_CLK ' ... toggle SPI Select Clock ... if_nz or outa,CS_CLK ' ... to select second SRAM (bank 1) XMM_BankSelect_ret ret ' ' XMM variables ' outx long $0 ' XMM_Flags long $0 XMM_Len long $0 XMM_Temp long $0 XMM_Test long $0 XMM_Addr long $0 HUB_Addr long $0 ' ' ' C3 Hardware Access: ' MASK long (|<Common#SPI_CS_CLK) | (|<Common#SPI_CS_CLR) | (|<Common#SPI_CLK) | (|<Common#SPI_SI) | (|<Common#SPI_SO) DIRN long (|<Common#SPI_CS_CLK) | (|<Common#SPI_CS_CLR) | (|<Common#SPI_CLK) | (|<Common#SPI_SI) CS_CLK long (|<Common#SPI_CS_CLK) CS_CLR long (|<Common#SPI_CS_CLR) CS_BOTH long (|<Common#SPI_CS_CLK) | (|<Common#SPI_CS_CLR) OBIT long (|<Common#SPI_SO) IBIT long (|<Common#SPI_SI) CLCK long (|<Common#SPI_CLK) BIT15 long $8000 ' '---------------------- End of C3 SPI XMM Support Routines ---------------------Thanks,
Ross.
Comments
I tried this on my prototype C3 and unfortunately it doesn't seem to work. Here is some of the transcript from my serial terminal (bst). I deleted a lot of blank lines to save space.
I've also attached the cache driver I use with ZOG on the C3. It has the same interface as jazzed's SDRAM cache driver.
Thanks,
David
Andre'
No, I haven't ordered a C3 yet - Parallax's shipping costs doubles the price of the board, so I thought I'd wait until I could investigate alternative methods of acquiring one.
Hi David,
Thanks, I'll check my code (and compare it with yours) and re-post an amended version.
Ross.
Aha! For a start, it seems I had my CLR and INC pins for selecting the SPI channel the wrong way round! If you get a chance, try the attached executable. But don't worry too much - my own C3 should arrive in a few days, so I'll fix it then.
Ross.
Looks much better this time. I think it's working. Congratulations!
Thanks! Yes, that's working. This means I can now execute C programs out of the 64Kb of SPI SRAM on the C3 (albeit a bit slowly!). Adding in the FLASH support should be easy. I'll do that over the next week or so, so by the time my C3 arrives, Catalina should be fully functional.
I'll also have a look at using your caching driver. It will be interesting to see the performance difference.
Ross.
One alternative is to enter the order with whatever shipping method you want and put in the notes "Please use the cheapest USPS method and credit me the difference charged by the on-line order system". - Ken
It will be faster even though the backstore choices (some SPI device) are slow. Of course the same interface is also used by the SDRAM cache driver which makes things interesting. The performance is different of course between SPI RAM and SDRAM. I'm looking into to doing a C3 8MB SDRAM add on module which at first glance seems possible..
Hi Ken. The UPS cost quoted by your online ordering system was US$65, so I opted for USPS instead (~US$38 from memory). I still thought was a bit steep considering USPS themselves only charge US$13 (I checked) - but I paid it, and as far as I know the order has been processed - certainly it has already been debited from my credit card.
Happy to get a credit if you can figure out a cheaper way to post it.
Ross.
Hi David,
The code I posted above is all that is required (the error was in the pin definitions, not in that code). This is the actual code I include in the XMM kernel. Of course, this is a pretty brain-dead implementation for a serial interface - it is cribbed from my parallel SRAM code. For serial SRAM it will be at least 10 times slower - but I expect a cache will speed things up quite a bit. Of course, the overhead of interacting with the cache (which will be in another cog) will slow it back down again, but you should still see better performance (at the cost of a cog).
I will also have to add a new option to the C3 target to tell it to put read/write segments in the SPI SRAM and read-only segments in the SPI FLASH, but that's fairly simple.
Ross.
Now THAT would be nice!
Ross.
Hi Ross,
Looks like the US Postal Service changed the link for 1st class international. Our IT manager is working on getting the correct link. We are dealing with the US post office, so it could take a bit to get this fixed. For now, customers can put a note in the comments section of the order to ship 1st class international, or call our sales department and place an order.
Sorry for the trouble and we hope to have this fixed soon.
Jim Carey
Parallax Sales