32x: new SH2 memory handling, hopefully faster
[picodrive.git] / pico / memory.h
CommitLineData
af37bca8 1// memory map related stuff
2
3typedef unsigned char u8;
4typedef unsigned short u16;
5typedef unsigned int u32;
bcf65fd6 6typedef unsigned long uptr; // unsigned pointer-sized int
af37bca8 7
8#define M68K_MEM_SHIFT 16
45f2f245 9// minimum size we can map
10#define M68K_BANK_SIZE (1 << M68K_MEM_SHIFT)
11#define M68K_BANK_MASK (M68K_BANK_SIZE - 1)
af37bca8 12
bcf65fd6 13extern uptr m68k_read8_map [0x1000000 >> M68K_MEM_SHIFT];
14extern uptr m68k_read16_map [0x1000000 >> M68K_MEM_SHIFT];
15extern uptr m68k_write8_map [0x1000000 >> M68K_MEM_SHIFT];
16extern uptr m68k_write16_map[0x1000000 >> M68K_MEM_SHIFT];
af37bca8 17
bcf65fd6 18extern uptr s68k_read8_map [0x1000000 >> M68K_MEM_SHIFT];
19extern uptr s68k_read16_map [0x1000000 >> M68K_MEM_SHIFT];
20extern uptr s68k_write8_map [0x1000000 >> M68K_MEM_SHIFT];
21extern uptr s68k_write16_map[0x1000000 >> M68K_MEM_SHIFT];
af37bca8 22
bcf65fd6 23void z80_map_set(uptr *map, int start_addr, int end_addr,
0ace9b9a 24 const void *func_or_mh, int is_func);
bcf65fd6 25void cpu68k_map_set(uptr *map, int start_addr, int end_addr,
0ace9b9a 26 const void *func_or_mh, int is_func);
af37bca8 27void cpu68k_map_all_ram(int start_addr, int end_addr, void *ptr, int is_sub);
28void m68k_map_unmap(int start_addr, int end_addr);
29
30// top-level handlers that cores can use
31// (or alternatively build them into themselves)
32// XXX: unhandled: *16 and *32 might cross the bank boundaries
33typedef u32 (cpu68k_read_f)(u32 a);
34typedef void (cpu68k_write_f)(u32 a, u32 d);
35
36#define MAKE_68K_READ8(name, map) \
37u32 name(u32 a) \
38{ \
bcf65fd6 39 uptr v; \
af37bca8 40 a &= 0x00ffffff; \
41 v = map[a >> M68K_MEM_SHIFT]; \
42 if (v & 0x80000000) \
43 return ((cpu68k_read_f *)(v << 1))(a); \
44 else \
45 return *(u8 *)((v << 1) + (a ^ 1)); \
46}
47
48#define MAKE_68K_READ16(name, map) \
49u32 name(u32 a) \
50{ \
bcf65fd6 51 uptr v; \
af37bca8 52 a &= 0x00fffffe; \
53 v = map[a >> M68K_MEM_SHIFT]; \
54 if (v & 0x80000000) \
55 return ((cpu68k_read_f *)(v << 1))(a); \
56 else \
57 return *(u16 *)((v << 1) + a); \
58}
59
60#define MAKE_68K_READ32(name, map) \
61u32 name(u32 a) \
62{ \
bcf65fd6 63 uptr v, vs; \
af37bca8 64 u32 d; \
65 a &= 0x00fffffe; \
66 v = map[a >> M68K_MEM_SHIFT]; \
67 vs = v << 1; \
68 if (v & 0x80000000) { \
69 d = ((cpu68k_read_f *)vs)(a) << 16; \
70 d |= ((cpu68k_read_f *)vs)(a + 2); \
71 } \
72 else { \
73 u16 *m = (u16 *)(vs + a); \
74 d = (m[0] << 16) | m[1]; \
75 } \
76 return d; \
77}
78
79#define MAKE_68K_WRITE8(name, map) \
80void name(u32 a, u8 d) \
81{ \
bcf65fd6 82 uptr v; \
af37bca8 83 a &= 0x00ffffff; \
84 v = map[a >> M68K_MEM_SHIFT]; \
85 if (v & 0x80000000) \
86 ((cpu68k_write_f *)(v << 1))(a, d); \
87 else \
88 *(u8 *)((v << 1) + (a ^ 1)) = d; \
89}
90
91#define MAKE_68K_WRITE16(name, map) \
92void name(u32 a, u16 d) \
93{ \
bcf65fd6 94 uptr v; \
af37bca8 95 a &= 0x00fffffe; \
96 v = map[a >> M68K_MEM_SHIFT]; \
97 if (v & 0x80000000) \
98 ((cpu68k_write_f *)(v << 1))(a, d); \
99 else \
100 *(u16 *)((v << 1) + a) = d; \
101}
102
103#define MAKE_68K_WRITE32(name, map) \
104void name(u32 a, u32 d) \
105{ \
bcf65fd6 106 uptr v, vs; \
af37bca8 107 a &= 0x00fffffe; \
108 v = map[a >> M68K_MEM_SHIFT]; \
109 vs = v << 1; \
110 if (v & 0x80000000) { \
111 ((cpu68k_write_f *)vs)(a, d >> 16); \
112 ((cpu68k_write_f *)vs)(a + 2, d); \
113 } \
114 else { \
115 u16 *m = (u16 *)(vs + a); \
116 m[0] = d >> 16; \
117 m[1] = d; \
118 } \
119}
120