6502.org Forum  Projects  Code  Documents  Tools  Forum
It is currently Mon May 13, 2024 12:06 pm

All times are UTC




Post new topic Reply to topic  [ 23 posts ]  Go to page Previous  1, 2
Author Message
PostPosted: Fri Aug 11, 2023 7:24 am 
Offline

Joined: Mon Jan 19, 2004 12:49 pm
Posts: 684
Location: Potsdam, DE
Honeywell Aerospace SPI/Parallel eeprom. For Aerospace, Deep Earth, and High Temperature applications and (was) priced accordingly... https://aerospace.honeywell.com/content ... asheet.pdf

(I used to work in the Deep Earth development, making steering robots for oil drills. It gets a bit warm down there; we used to design to operate from -40 to +150C, and were looking at +225C when I left.)

Neil


Top
 Profile  
Reply with quote  
PostPosted: Fri Aug 11, 2023 7:43 am 
Offline

Joined: Tue Jul 05, 2005 7:08 pm
Posts: 993
Location: near Heidelberg, Germany
I see you're all way more creative than I am.

I used a large CPLD in the Micro-PET and part of it boots from an SPI ROM, by copying over the first page of the ROM into 6502 page $ffxx, while keepinh phi2 stopped. After that the SPI interface - incl ROM is available as peripheral to the CPU.

My approach would still be a CPLD to do just that. If you want a smaller one you could generate the lower 8 address bits only and pull the upper 8 bits high using other means.

André

_________________
Author of the GeckOS multitasking operating system, the usb65 stack, designer of the Micro-PET and many more 6502 content: http://6502.org/users/andre/


Top
 Profile  
Reply with quote  
PostPosted: Fri Aug 11, 2023 7:54 am 
Offline

Joined: Tue Jul 05, 2005 7:08 pm
Posts: 993
Location: near Heidelberg, Germany
If you want to do away with the address line generation, you could stream out the exact code sequence the CPU requires while booting - completely ignoring the address lines.

However that quickly gets complicated. Stores need to go to parallel RAM. But I don't think you can use zeropage or stack as this would need detection when to allow reading it instead of getting the value from SPI ROM.
Also you cannot use the same SPI ROM to load the second stage boot code from - as it is busy streaming out the initial boot code to the CPU, you would need a second storage medium.
Also, no wait loops are allowed as the executed code is fixed in ROM. - no dynamic second stage boot program storage can be used. You might get away with an SD card but I don't know enough of its protocol. An SD Card actually requires a second SPI core as the first one is busy streaming the initial boot code...

So, would maybe work, in the category 'because I can', but I doubt it would less resources than a small CPLD that counts addresses, and can be even used to hold the second stage boot code.

_________________
Author of the GeckOS multitasking operating system, the usb65 stack, designer of the Micro-PET and many more 6502 content: http://6502.org/users/andre/


Top
 Profile  
Reply with quote  
PostPosted: Fri Aug 11, 2023 7:59 am 
Offline

Joined: Tue Jul 05, 2005 7:08 pm
Posts: 993
Location: near Heidelberg, Germany
Michael wrote:
gfoot wrote:
Michael wrote:
Ok. Since you've pretty much dis'ed using a microcontroller, how about using an 8K 74AHCTXL18426 "boot loader" IC in a DIP-14 package (~$1.50)?

I'm afraid I don't know what you mean - yes I'm not keen on using a microcontroller for this, and I'm not sure what 74AHCTXL18426 is, did you mean PIC16F18426, or is it the same thing?

Yeah, it's a PIC microcontroller and it simply takes advantage of a simple novel interface method to appear to the 6502 as a 'smart' phantom ROM of sorts. Using it to copy an image of your boot loader into memory at startup is one of many ways you might use it. I use it to copy a full 64K image from a slow ROM at a nice leisurely 1-MHz rate into RAM on a 64K RAM system before switching to a fast clock.

Good luck on your project...


How does the copying work with only 14 pins minus two for power supply, to generate addresses to store data to?

Edit: that's probably exactly what described in my post above when ignoring address lines completely. And using a microcontroller you are more flexible - you can even run a 'shadow ' program to see if data read from IO causes branches and then just stream out the right code branch. Nice!

_________________
Author of the GeckOS multitasking operating system, the usb65 stack, designer of the Micro-PET and many more 6502 content: http://6502.org/users/andre/


Top
 Profile  
Reply with quote  
PostPosted: Fri Aug 11, 2023 10:54 am 
Offline

Joined: Mon Jan 19, 2004 12:49 pm
Posts: 684
Location: Potsdam, DE
Same approach as mine, I think: let the processor generate the addresses it wants, but ignore them except when writing.

Though I wouldn't expect to execute loops and branches; no need if all you're doing is loading the ram with a bootloader.

Neil


Top
 Profile  
Reply with quote  
PostPosted: Fri Aug 11, 2023 9:32 pm 
Offline
User avatar

Joined: Tue Oct 25, 2016 8:56 pm
Posts: 360
Yes, a CPLD would be "easier" - if you already have the knowledge and infrastructure to program one. Not everyone does, nor is it trivial to get to that position. For this reason I feel like booting from an SPI EEPROM still has a place if it can be made to work. The solution is far from ideal, but it has less "up-front barriers" than a CPLD does.

_________________
Want to design a PCB for your project? I strongly recommend KiCad. Its free, its multiplatform, and its easy to learn!
Also, I maintain KiCad libraries of Retro Computing and Arduino components you might find useful.


Top
 Profile  
Reply with quote  
PostPosted: Fri Aug 11, 2023 11:28 pm 
Offline
User avatar

Joined: Wed Feb 13, 2013 1:38 pm
Posts: 586
Location: Michigan, USA
fachat wrote:
Michael wrote:
gfoot wrote:
Michael wrote:
Ok. Since you've pretty much dis'ed using a microcontroller, how about using an 8K 74AHCTXL18426 "boot loader" IC in a DIP-14 package (~$1.50)?

I'm afraid I don't know what you mean - yes I'm not keen on using a microcontroller for this, and I'm not sure what 74AHCTXL18426 is, did you mean PIC16F18426, or is it the same thing?

Yeah, it's a PIC microcontroller and it simply takes advantage of a simple novel interface method to appear to the 6502 as a 'smart' phantom ROM of sorts. Using it to copy an image of your boot loader into memory at startup is one of many ways you might use it. I use it to copy a full 64K image from a slow ROM at a nice leisurely 1-MHz rate into RAM on a 64K RAM system before switching to a fast clock.

Good luck on your project...
Quote:

How does the copying work with only 14 pins minus two for power supply, to generate addresses to store data to?

Edit: that's probably exactly what described in my post above when ignoring address lines completely. And using a microcontroller you are more flexible - you can even run a 'shadow ' program to see if data read from IO causes branches and then just stream out the right code branch. Nice!

The microcontroller presents to the 6502 as a smart ROM of sorts. It simply provides LDA <imm>, LDA <abs>, STA <abs>, and JMP <abs> instructions while turning on ROM or RAM during the correct cycle within each instruction.

A hardware analogy might look something like the drawing below where you're setting clock and data switches during each half clock cycle to mimick the microcontroller single-cycle Push() and Pull() functions. I'm working on a demo project.
Attachment:
blind interface #2.png
blind interface #2.png [ 356.42 KiB | Viewed 1756 times ]

Code:
  /******************************************************************************
   *  core 'blind interface' functions                                          *
   *                                                                            */
   void uReset()                      // ****************************************
   { clk(1);                          // clock = 1                              *
     res(0);                          // reset = 0  ~~~~~~~~~~~~~~~~~~~~~~~~~~  *
     _delay_us(100);                  //                                        *
     uPull(ram);                      //                                   (1)  *
     uPull(ram);                      //                                   (2)  *
     res(1);                          // reset = 1  ~~~~~~~~~~~~~~~~~~~~~~~~~~  *
     uPull(ram);                      //                                   (1)  *
     uPull(ram);                      //                                   (2)  *
     uPull(ram);                      //                                   (3)  *
     uPull(ram);                      //                                   (4)  *
     uPull(ram);                      //                                   (5)  *
     uPush(lo(0x8000));               // address $FFFC (reset vector lo)   (6)  *
     uPush(hi(0x8000));               // address $FFFD (reset vector hi)   (7)  *
   }                                  // ****************************************

   void wrROM(u16 addr,byte data)     // ****************************************
   { uPush(0xA9);                     //  lda <imm>                             *
     uPush(data);                     //   "                                    *
     uPush(0x8D);                     //  sta <abs>                             *
     uPush(lo(addr));                 //   "         address lo                 *
     uPush(hi(addr));                 //   "         address hi                 *
     uPull(rom);                      //   "         6502 write op'             *
   }                                  // ****************************************

   void wrRAM(byte data)              // ****************************************
   { uPush(0xA9);                     //  lda <imm>                             *
     uPush(data);                     //   "                                    *
     uPush(0x8D);                     //  sta <abs>                             *
     uPush(lo(addr));                 //   "         abs address lo             *
     uPush(hi(addr));                 //   "         abs address hi             *
     uPull(ram);                      //   "         6502 write op'             *
   }                                  // ****************************************

   byte rdMEM(byte mem)               // ****************************************
   { uPush(0x4C);                     //  jmp $8000  reset PC (avoid I/O area)  *
     uPush(lo(0x8000));               //   "         abs address lo             *
     uPush(hi(0x8000));               //   "         abs address hi             *
     uPush(0xAD);                     //  lda <abs>                             *
     uPush(lo(addr));                 //   "         abs address lo             *
     uPush(hi(addr));                 //   "         abs address hi             *
     return uPull(mem);               //   "         6502 read op'              *
   }                                  // ****************************************
Simply build off of those core functions (loader, programmer, etc.)...
Code:
  /******************************************************************************
   *  load 64K RAM from 64K 'A' or 'B' half of ROM at 'power-up' or 'reset' at  *
   *  a nice liesurely 1-MHz rate.                                              *
   *                                                                            */
   void loader()                      // ****************************************
   { addr = 0x0000; x15(0);           // start address $0000, ROM A15 = 0       *
     uReset();                        // reset CPU (synchronize micro to cpu)   *
     do                               // copy 64K ROM minus 8K I/O area to RAM  *
     { wrRAM(rdMEM(rom));             // ROM -> RAM (0000..5FFF & 8000..FFFF)   *
       if(++addr == 0x6000)           // if I/O area ($6000..$7FFF)             *
       { addr = 0x8000; x15(1);       //   skip, ROM A15 = 1 ($8000..$FFFF)     *
       }                              //                                        *
     } while(addr);                   // until roll-over to 0 (full 64K range)  *
   }                                  // ****************************************
Code:
  /******************************************************************************
   *  programming 64K RAM image onto 64K 'A' or 'B' half of the 128K Flash ROM  *
   *  takes about 7 seconds.                                                    */
   void flash()                       // ****************************************
   { addr = 0x0000; x15(0);           // start address $0000, ROM A15 = 0       *
     uReset();                        // reset 6502 (synchronize uC to cpu)     *
     do                               //                                        *
     { if((addr & 0x0FFF) == 0)       // if 4K sector boundary                  *
       { wrROM(0x5555,0xAA);          // erase sector sequence                  *
         wrROM(0x2AAA,0x55);          //  "                                     *
         wrROM(0x5555,0x80);          //  "                                     *
         wrROM(0x5555,0xAA);          //  "                                     *
         wrROM(0x2AAA,0x55);          //  "                                     *
         wrROM(addr,0x30);            //  "                                     *
         _delay_ms(25);               // required delay                         *
         putSer('.');                 // indicate progress                      *
       }                              //                                        *
       wrROM(0x5555,0xAA);            // write byte 'unlock' sequence           *
       wrROM(0x2AAA,0x55);            //  "                                     *
       wrROM(0x5555,0xA0);            //  "                                     *
       wrROM(addr,rdMEM(ram));        // write byte                             *
       _delay_us(20);                 // required write delay                   *
       if(++addr == 0x6000)           // if I/O area ($6000..$7FFF)             *
       { addr = 0x8000; x15(1);       //   skip, ROM A15 = 1 ($8000..$FFFF)     *
       }                              //                                        *
     } while(addr);                   // until roll-over to 0 (full 64K range)  *
   }                                  // ****************************************
Code:
  /******************************************************************************
   *  hex file download to RAM (ROM emulator mode, 115200 baud)                 *
   *                                                                            */
   char loadHex()                     // ****************************************
   { char bytecnt;                    // hex record length                      *
     char type;                       // hex record type                        *
     char data;                       //                                        *
     char cksum;                      // hex record checksum                    *
     char error = 0;                  //                                        *
     do                               // process hex file                       *
     { do                             // process hex record                     *
       { putSer(data = getSer());     // echo & flush <cr> and <lf> chars       *
       } while(data != ':');          // until we see a ':' record header       *
       cksum = (bytecnt = getByte()); // get 'byte' (not character) count       *
       cksum += (data = getByte());   // get address hi                         *
       addr = (data << 8);            //  "                                     *
       cksum += (data = getByte());   // get address lo                         *
       addr += data;                  //  "                                     *
       cksum += (type = getByte());   // get record type (0, 1, or 4)           *
       if(type == 4)                  // if <extended address> record           *
       { cksum += getByte();          //                                        *
         cksum += getByte();          //                                        *
       }                              //                                        *
       if(type == 0)                  // if <data> record                       *
       { while(bytecnt--)             //                                        *
         { data = getByte();          //                                        *
           cksum += data;             //                                        *
           wrRAM(data); addr++;       // write byte to RAM, bump address        *
         }                            //                                        *
       }                              //                                        *
       data = getByte();              // get record checksum byte               *
       if(-data != cksum) error = 1;  // test for error                         *
     } while(type != 1);              // loop until <end-of-file> record        *
     return error;                    //                                        *
   }                                  // ****************************************


Last edited by Michael on Sat Aug 12, 2023 10:20 am, edited 5 times in total.

Top
 Profile  
Reply with quote  
PostPosted: Sat Aug 12, 2023 4:25 am 
Offline
User avatar

Joined: Fri Aug 30, 2002 1:09 am
Posts: 8433
Location: Southern California
What I did was similar to what barnacle describes.  It's described at viewtopic.php?p=91876#p91876 and my next two posts on that page.  It's finished and tests fine, but I've been slow to make the system it's made to plug into.  I can provide them, and I do show them on the front page of my site, but I have not finished the documentation.

_________________
http://WilsonMinesCo.com/ lots of 6502 resources
The "second front page" is http://wilsonminesco.com/links.html .
What's an additional VIA among friends, anyhow?


Top
 Profile  
Reply with quote  
Display posts from previous:  Sort by  
Post new topic Reply to topic  [ 23 posts ]  Go to page Previous  1, 2

All times are UTC


Who is online

Users browsing this forum: No registered users and 8 guests


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot post attachments in this forum

Search for:
Jump to: