abcmem.c 1.9 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768
  1. #include "common.h"
  2. #include "io.h"
  3. #include "abcio.h"
  4. #include "sys.h"
  5. #include "console.h"
  6. #include "config.h"
  7. /* Configure ABC memory map */
  8. struct abc_mem_init {
  9. unsigned int addr;
  10. uint16_t len;
  11. uint8_t flags;
  12. enum sysvar_enum enable;
  13. const char *data; /* May not be const, but... */
  14. };
  15. #define RD (ABCMEMMAP_RD >> 24)
  16. #define WR (ABCMEMMAP_WR >> 24)
  17. extern const char rom_ufddos80[];
  18. extern const char rom_ufddos800[];
  19. extern const char rom_print80_29[];
  20. /* Not really NV, but matches NVRAM in some expansions */
  21. static char __dram_bss __aligned(512) abc80_nvram[2 << 10];
  22. /* 16K external memory to expand to 512K */
  23. static char __dram_bss __aligned(512) abc80_extmem[16 << 10];
  24. /* These MUST be sorted! */
  25. static const struct abc_mem_init mem_init_abc80[] = {
  26. { 0x5000, 2 << 10, RD|WR, config_abc_mem_abc80_nvram, abc80_nvram },
  27. { 0x6000, 4 << 10, RD, config_abc_mem_abc80_ufddos, rom_ufddos80 },
  28. { 0x7400, 1 << 10, RD, config_abc_mem_abc80_pun80, rom_print80_29 },
  29. { 0x8000, 16 << 10, RD|WR, config_abc_mem_abc80_ram, abc80_extmem },
  30. { -1U, 0, 0, sysvar_null, NULL }
  31. };
  32. static const struct abc_mem_init mem_init_abc800[] = {
  33. { 0x6000, 4 << 10, RD, config_abc_mem_abc800_ufddos, rom_ufddos800 },
  34. { -1U, 0, 0, sysvar_null, NULL }
  35. };
  36. static const struct abc_mem_init *
  37. get_next(const struct abc_mem_init *curr, unsigned int addr)
  38. {
  39. while (addr >= curr->addr + curr->len ||
  40. !(!curr->enable || getvar_bool(curr->enable)))
  41. curr++;
  42. return curr;
  43. }
  44. void __cold abc_init_memmap(void)
  45. {
  46. volatile uint32_t *pg = &ABCMEMMAP_PAGE(0);
  47. const struct abc_mem_init *next;
  48. next = is_abc800() ? mem_init_abc800 : mem_init_abc80;
  49. for (unsigned int addr = 0; addr < 0x10000; addr += 512) {
  50. next = get_next(next, addr);
  51. if (addr < next->addr) {
  52. *pg++ = 0;
  53. } else {
  54. *pg++ = ((size_t)(next->data + (addr - next->addr))
  55. & SDRAM_MASK) | (next->flags << 24);
  56. }
  57. }
  58. }