comparison m68k_util.c @ 2666:38c281ef57b0

Memory access optimizaiton in new 68K core that gives a modest speed bump on average and will allow low-cost watchpoints
author Michael Pavone <pavone@retrodev.com>
date Fri, 07 Mar 2025 23:40:58 -0800
parents ec02a08196d5
children 7e86ec94c899
comparison
equal deleted inserted replaced
2665:54ac5fe14cf9 2666:38c281ef57b0
4 { 4 {
5 context->cycles += 4 * context->opts->gen.clock_divider; 5 context->cycles += 4 * context->opts->gen.clock_divider;
6 #ifdef DEBUG_DISASM 6 #ifdef DEBUG_DISASM
7 uint32_t tmp = context->scratch1; 7 uint32_t tmp = context->scratch1;
8 #endif 8 #endif
9 context->scratch1 = read_byte(context->scratch1, (void**)context->mem_pointers, &context->opts->gen, context); 9 uint32_t address = context->scratch1 & context->opts->gen.address_mask;
10 uint32_t index = address >> 16;
11 context->scratch1 = context->read8[index](address, context, context->read8_data[index]);
10 #ifdef DEBUG_DISASM 12 #ifdef DEBUG_DISASM
11 printf("Read.b %05X: %02X\n", tmp, context->scratch1); 13 printf("Read.b %05X: %02X\n", tmp, context->scratch1);
12 #endif 14 #endif
13 } 15 }
14 16
24 { 26 {
25 context->cycles += 4 * context->opts->gen.clock_divider; 27 context->cycles += 4 * context->opts->gen.clock_divider;
26 #ifdef DEBUG_DISASM 28 #ifdef DEBUG_DISASM
27 uint32_t tmp = context->scratch1; 29 uint32_t tmp = context->scratch1;
28 #endif 30 #endif
29 context->scratch1 = read_word(context->scratch1, (void**)context->mem_pointers, &context->opts->gen, context); 31 uint32_t address = context->scratch1 & context->opts->gen.address_mask;
32 uint32_t index = address >> 16;
33 context->scratch1 = context->read16[index](address, context, context->read16_data[index]);
30 #ifdef DEBUG_DISASM 34 #ifdef DEBUG_DISASM
31 if (tmp == context->pc) { 35 if (tmp == context->pc) {
32 m68kinst inst; 36 m68kinst inst;
33 m68k_decode(debug_disasm_fetch, context, &inst, tmp); 37 m68k_decode(debug_disasm_fetch, context, &inst, tmp);
34 static char disasm_buf[256]; 38 static char disasm_buf[256];
44 } 48 }
45 49
46 void m68k_write_8(m68k_context *context) 50 void m68k_write_8(m68k_context *context)
47 { 51 {
48 context->cycles += 4 * context->opts->gen.clock_divider; 52 context->cycles += 4 * context->opts->gen.clock_divider;
49 write_byte(context->scratch2, context->scratch1, (void**)context->mem_pointers, &context->opts->gen, context); 53 uint32_t address = context->scratch2 & context->opts->gen.address_mask;
54 uint32_t index = address >> 16;
55 context->write8[index](address, context, context->scratch1, context->write8_data[index]);
50 #ifdef DEBUG_DISASM 56 #ifdef DEBUG_DISASM
51 printf("Write.b %05X: %02X\n", context->scratch2, context->scratch1); 57 printf("Write.b %05X: %02X\n", context->scratch2, context->scratch1);
52 #endif 58 #endif
53 } 59 }
54 60
55 void m68k_rmw_writeback(m68k_context *context) 61 void m68k_rmw_writeback(m68k_context *context)
56 { 62 {
57 if (context->opts->gen.flags & M68K_OPT_BROKEN_READ_MODIFY) { 63 if (context->opts->gen.flags & M68K_OPT_BROKEN_READ_MODIFY) {
58 context->cycles += 4 * context->opts->gen.clock_divider; 64 context->cycles += 4 * context->opts->gen.clock_divider;
59 } else { 65 } else {
60 write_byte(context->scratch2, context->scratch1, (void**)context->mem_pointers, &context->opts->gen, context); 66 m68k_write_8(context);
61 } 67 }
62 } 68 }
63 69
64 void m68k_write_16(m68k_context *context) 70 void m68k_write_16(m68k_context *context)
65 { 71 {
66 context->cycles += 4 * context->opts->gen.clock_divider; 72 context->cycles += 4 * context->opts->gen.clock_divider;
67 write_word(context->scratch2, context->scratch1, (void**)context->mem_pointers, &context->opts->gen, context); 73 int32_t address = context->scratch2 & context->opts->gen.address_mask;
74 uint32_t index = address >> 16;
75 context->write16[index](address, context, context->scratch1, context->write16_data[index]);
68 #ifdef DEBUG_DISASM 76 #ifdef DEBUG_DISASM
69 printf("Write %05X: %04X\n", context->scratch2, context->scratch1); 77 printf("Write %05X: %04X\n", context->scratch2, context->scratch1);
70 #endif 78 #endif
71 } 79 }
72 80
220 opts->gen.address_mask = 0xFFFFFF; 228 opts->gen.address_mask = 0xFFFFFF;
221 opts->gen.byte_swap = 1; 229 opts->gen.byte_swap = 1;
222 opts->gen.max_address = 0x1000000; 230 opts->gen.max_address = 0x1000000;
223 opts->gen.bus_cycles = 4; 231 opts->gen.bus_cycles = 4;
224 opts->gen.clock_divider = clock_divider; 232 opts->gen.clock_divider = clock_divider;
233 opts->gen.mem_ptr_off = offsetof(m68k_context, mem_pointers);
225 sync_comp_tmp = sync_components; 234 sync_comp_tmp = sync_components;
226 int_ack_tmp = int_ack; 235 int_ack_tmp = int_ack;
227 } 236 }
228 237
229 m68k_context *init_68k_context(m68k_options * opts, m68k_reset_handler *reset_handler) 238 m68k_context *init_68k_context(m68k_options * opts, m68k_reset_handler *reset_handler)
232 context->opts = opts; 241 context->opts = opts;
233 context->reset_handler = reset_handler; 242 context->reset_handler = reset_handler;
234 context->int_cycle = 0xFFFFFFFFU; 243 context->int_cycle = 0xFFFFFFFFU;
235 context->int_pending = 255; 244 context->int_pending = 255;
236 context->sync_components = sync_comp_tmp; 245 context->sync_components = sync_comp_tmp;
246 for (uint32_t i = 0; i < 256; i++)
247 {
248 context->read16[i] = get_interp_read_16(context, &opts->gen, i << 16, (i + 1) << 16, context->read16_data + i);
249 context->read8[i] = get_interp_read_8(context, &opts->gen, i << 16, (i + 1) << 16, context->read8_data + i);
250 context->write16[i] = get_interp_write_16(context, &opts->gen, i << 16, (i + 1) << 16, context->write16_data + i);
251 context->write8[i] = get_interp_write_8(context, &opts->gen, i << 16, (i + 1) << 16, context->write8_data + i);
252 }
237 sync_comp_tmp = NULL; 253 sync_comp_tmp = NULL;
238 context->int_ack_handler = int_ack_tmp; 254 context->int_ack_handler = int_ack_tmp;
239 int_ack_tmp = NULL; 255 int_ack_tmp = NULL;
240 return context; 256 return context;
241 } 257 }