src/emu/cpu/mcs48/mcs48.c
| r3128 | r3129 | |
| 195 | 195 | |
| 196 | 196 | INLINE UINT8 opcode_fetch(offs_t address) |
| 197 | 197 | { |
| 198 | | /* fix me - need to figure out how to bypass internal ROM in this case */ |
| 199 | | if (mcs48.ea && address < mcs48.int_rom_size) |
| 200 | | return 0x00; |
| 201 | 198 | return cpu_readop(address); |
| 202 | 199 | } |
| 203 | 200 | |
| r3128 | r3129 | |
| 209 | 206 | |
| 210 | 207 | INLINE UINT8 argument_fetch(offs_t address) |
| 211 | 208 | { |
| 212 | | /* fix me - need to figure out how to bypass internal ROM in this case */ |
| 213 | | if (mcs48.ea && address < mcs48.int_rom_size) |
| 214 | | return 0x00; |
| 215 | 209 | return cpu_readop_arg(address); |
| 216 | 210 | } |
| 217 | 211 | |
| r3128 | r3129 | |
| 705 | 699 | static void mcs48_init(int index, int clock, const void *config, int (*irqcallback)(int), UINT16 romsize) |
| 706 | 700 | { |
| 707 | 701 | memset(&mcs48, 0, sizeof(mcs48)); |
| 702 | |
| 703 | /* External access line |
| 704 | * EA=1 : read from external rom |
| 705 | * EA=0 : read from internal rom |
| 706 | */ |
| 707 | |
| 708 | /* FIXME: Current implementation suboptimal */ |
| 709 | mcs48.ea = (romsize ? 0 : 1); |
| 708 | 710 | |
| 709 | 711 | mcs48.irq_callback = irqcallback; |
| 710 | 712 | mcs48.int_rom_size = romsize; |
| r3128 | r3129 | |
| 733 | 735 | |
| 734 | 736 | /*------------------------------------------------- |
| 735 | 737 | i8035_init - initialization for systems with |
| 736 | | 1k of internal ROM and 64 bytes of internal |
| 738 | 0k of internal ROM and 64 bytes of internal |
| 737 | 739 | RAM |
| 738 | 740 | -------------------------------------------------*/ |
| 739 | 741 | |
| 740 | | #if (HAS_I8035 || HAS_I8041 || HAS_I8048 || HAS_I8648 || HAS_I8748 || HAS_MB8884 || HAS_N7751) |
| 742 | #if (HAS_I8035 || HAS_MB8884) |
| 741 | 743 | static void i8035_init(int index, int clock, const void *config, int (*irqcallback)(int)) |
| 742 | 744 | { |
| 745 | mcs48_init(index, clock, config, irqcallback, 0x0); |
| 746 | } |
| 747 | #endif |
| 748 | |
| 749 | |
| 750 | /*------------------------------------------------- |
| 751 | i8041_init - initialization for systems with |
| 752 | 1k of internal ROM and 64 bytes of internal |
| 753 | RAM |
| 754 | -------------------------------------------------*/ |
| 755 | |
| 756 | #if (HAS_I8041 || HAS_I8048 || HAS_I8648 || HAS_I8748 || HAS_N7751) |
| 757 | static void i8041_init(int index, int clock, const void *config, int (*irqcallback)(int)) |
| 758 | { |
| 743 | 759 | mcs48_init(index, clock, config, irqcallback, 0x400); |
| 744 | 760 | } |
| 745 | 761 | #endif |
| r3128 | r3129 | |
| 747 | 763 | |
| 748 | 764 | /*------------------------------------------------- |
| 749 | 765 | i8039_init - initialization for systems with |
| 750 | | 2k of internal ROM and 128 bytes of internal |
| 766 | 0k of internal ROM and 128 bytes of internal |
| 751 | 767 | RAM |
| 752 | 768 | -------------------------------------------------*/ |
| 753 | 769 | |
| 754 | | #if (HAS_I8039 || HAS_I8049 || HAS_I8749 || HAS_M58715) |
| 770 | #if (HAS_I8039) |
| 755 | 771 | static void i8039_init(int index, int clock, const void *config, int (*irqcallback)(int)) |
| 756 | 772 | { |
| 773 | mcs48_init(index, clock, config, irqcallback, 0x0); |
| 774 | } |
| 775 | #endif |
| 776 | |
| 777 | |
| 778 | /*------------------------------------------------- |
| 779 | i8049_init - initialization for systems with |
| 780 | 2k of internal ROM and 128 bytes of internal |
| 781 | RAM |
| 782 | -------------------------------------------------*/ |
| 783 | |
| 784 | #if (HAS_I8049 || HAS_I8749 || HAS_M58715) |
| 785 | static void i8049_init(int index, int clock, const void *config, int (*irqcallback)(int)) |
| 786 | { |
| 757 | 787 | mcs48_init(index, clock, config, irqcallback, 0x800); |
| 758 | 788 | } |
| 759 | 789 | #endif |
| r3128 | r3129 | |
| 772 | 802 | bus_w(0xff); |
| 773 | 803 | mcs48.p1 = 0xff; |
| 774 | 804 | mcs48.p2 = 0xff; |
| 805 | port_w(1, mcs48.p1); |
| 806 | port_w(2, mcs48.p2); |
| 775 | 807 | mcs48.tirq_enabled = FALSE; |
| 776 | 808 | mcs48.xirq_enabled = FALSE; |
| 777 | 809 | mcs48.timecount_enabled = 0; |
| r3128 | r3129 | |
| 844 | 876 | /* if the timer is enabled, accumulate prescaler cycles */ |
| 845 | 877 | if (mcs48.timecount_enabled & TIMER_ENABLED) |
| 846 | 878 | { |
| 879 | UINT8 oldtimer = mcs48.timer; |
| 847 | 880 | mcs48.prescaler += count; |
| 848 | 881 | mcs48.timer += mcs48.prescaler >> 5; |
| 849 | 882 | mcs48.prescaler &= 0x1f; |
| 850 | | timerover = (mcs48.timer == 0); |
| 883 | timerover = (oldtimer != 0 && mcs48.timer == 0); |
| 851 | 884 | } |
| 852 | 885 | |
| 853 | 886 | /* if the counter is enabled, poll the T1 test input once for each cycle */ |
| r3128 | r3129 | |
| 920 | 953 | ADDRESS MAPS |
| 921 | 954 | ***************************************************************************/ |
| 922 | 955 | |
| 956 | /* FIXME: the memory maps should probably support rom banking for EA */ |
| 923 | 957 | static ADDRESS_MAP_START(program_10bit, ADDRESS_SPACE_PROGRAM, 8) |
| 924 | | AM_RANGE(0x00, 0x3ff) AM_ROM |
| 958 | AM_RANGE(0x00, 0x3ff) AM_ROMBANK(MCS48_INTERNAL_ROMBANK) |
| 925 | 959 | ADDRESS_MAP_END |
| 926 | 960 | |
| 927 | 961 | static ADDRESS_MAP_START(program_11bit, ADDRESS_SPACE_PROGRAM, 8) |
| 928 | | AM_RANGE(0x00, 0x7ff) AM_ROM |
| 962 | AM_RANGE(0x00, 0x7ff) AM_ROMBANK(MCS48_INTERNAL_ROMBANK) |
| 929 | 963 | ADDRESS_MAP_END |
| 930 | 964 | |
| 931 | 965 | static ADDRESS_MAP_START(data_6bit, ADDRESS_SPACE_DATA, 8) |
| r3128 | r3129 | |
| 981 | 1015 | { |
| 982 | 1016 | /* --- the following bits of info are set as 64-bit signed integers --- */ |
| 983 | 1017 | case CPUINFO_INT_INPUT_STATE + MCS48_INPUT_IRQ: mcs48.irq_state = (info->i != CLEAR_LINE); break; |
| 984 | | case CPUINFO_INT_INPUT_STATE + MCS48_INPUT_EA: mcs48.ea = info->i; break; |
| 1018 | case CPUINFO_INT_INPUT_STATE + MCS48_INPUT_EA: mcs48.ea = (info->i != CLEAR_LINE); |
| 1019 | memory_set_bank(MCS48_INTERNAL_ROMBANK, mcs48.ea); |
| 1020 | break; |
| 985 | 1021 | |
| 986 | 1022 | case CPUINFO_INT_PC: |
| 987 | 1023 | case CPUINFO_INT_REGISTER + MCS48_PC: PC = info->i; break; |
| r3128 | r3129 | |
| 1139 | 1175 | case CPUINFO_INT_ADDRBUS_WIDTH + ADDRESS_SPACE_DATA: info->i = 6; break; |
| 1140 | 1176 | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_PROGRAM: info->internal_map8 = address_map_program_10bit; break; |
| 1141 | 1177 | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_DATA: info->internal_map8 = address_map_data_6bit; break; |
| 1142 | | case CPUINFO_PTR_INIT: info->init = i8035_init; break; |
| 1178 | case CPUINFO_PTR_INIT: info->init = i8041_init; break; |
| 1143 | 1179 | case CPUINFO_STR_NAME: strcpy(info->s, "I8041"); break; |
| 1144 | 1180 | default: mcs48_get_info(state, info); break; |
| 1145 | 1181 | } |
| r3128 | r3129 | |
| 1155 | 1191 | case CPUINFO_INT_ADDRBUS_WIDTH + ADDRESS_SPACE_DATA: info->i = 6; break; |
| 1156 | 1192 | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_PROGRAM: info->internal_map8 = address_map_program_10bit; break; |
| 1157 | 1193 | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_DATA: info->internal_map8 = address_map_data_6bit; break; |
| 1158 | | case CPUINFO_PTR_INIT: info->init = i8035_init; break; |
| 1194 | case CPUINFO_PTR_INIT: info->init = i8041_init; break; |
| 1159 | 1195 | case CPUINFO_STR_NAME: strcpy(info->s, "I8048"); break; |
| 1160 | 1196 | default: mcs48_get_info(state, info); break; |
| 1161 | 1197 | } |
| r3128 | r3129 | |
| 1171 | 1207 | case CPUINFO_INT_ADDRBUS_WIDTH + ADDRESS_SPACE_DATA: info->i = 6; break; |
| 1172 | 1208 | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_PROGRAM: info->internal_map8 = address_map_program_10bit; break; |
| 1173 | 1209 | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_DATA: info->internal_map8 = address_map_data_6bit; break; |
| 1174 | | case CPUINFO_PTR_INIT: info->init = i8035_init; break; |
| 1210 | case CPUINFO_PTR_INIT: info->init = i8041_init; break; |
| 1175 | 1211 | case CPUINFO_STR_NAME: strcpy(info->s, "I8648"); break; |
| 1176 | 1212 | default: mcs48_get_info(state, info); break; |
| 1177 | 1213 | } |
| r3128 | r3129 | |
| 1187 | 1223 | case CPUINFO_INT_ADDRBUS_WIDTH + ADDRESS_SPACE_DATA: info->i = 6; break; |
| 1188 | 1224 | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_PROGRAM: info->internal_map8 = address_map_program_10bit; break; |
| 1189 | 1225 | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_DATA: info->internal_map8 = address_map_data_6bit; break; |
| 1190 | | case CPUINFO_PTR_INIT: info->init = i8035_init; break; |
| 1226 | case CPUINFO_PTR_INIT: info->init = i8041_init; break; |
| 1191 | 1227 | case CPUINFO_STR_NAME: strcpy(info->s, "I8748"); break; |
| 1192 | 1228 | default: mcs48_get_info(state, info); break; |
| 1193 | 1229 | } |
| r3128 | r3129 | |
| 1199 | 1235 | { |
| 1200 | 1236 | switch (state) |
| 1201 | 1237 | { |
| 1202 | | case CPUINFO_INT_ADDRBUS_WIDTH + ADDRESS_SPACE_PROGRAM: info->i = 10; break; |
| 1238 | case CPUINFO_INT_ADDRBUS_WIDTH + ADDRESS_SPACE_PROGRAM: info->i = 12; break; |
| 1203 | 1239 | case CPUINFO_INT_ADDRBUS_WIDTH + ADDRESS_SPACE_DATA: info->i = 6; break; |
| 1204 | | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_PROGRAM: info->internal_map8 = address_map_program_10bit; break; |
| 1205 | 1240 | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_DATA: info->internal_map8 = address_map_data_6bit; break; |
| 1206 | 1241 | case CPUINFO_PTR_INIT: info->init = i8035_init; break; |
| 1207 | 1242 | case CPUINFO_STR_NAME: strcpy(info->s, "MB8884"); break; |
| r3128 | r3129 | |
| 1219 | 1254 | case CPUINFO_INT_ADDRBUS_WIDTH + ADDRESS_SPACE_DATA: info->i = 6; break; |
| 1220 | 1255 | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_PROGRAM: info->internal_map8 = address_map_program_10bit; break; |
| 1221 | 1256 | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_DATA: info->internal_map8 = address_map_data_6bit; break; |
| 1222 | | case CPUINFO_PTR_INIT: info->init = i8035_init; break; |
| 1257 | case CPUINFO_PTR_INIT: info->init = i8041_init; break; |
| 1223 | 1258 | case CPUINFO_STR_NAME: strcpy(info->s, "N7751"); break; |
| 1224 | 1259 | default: mcs48_get_info(state, info); break; |
| 1225 | 1260 | } |
| r3128 | r3129 | |
| 1252 | 1287 | case CPUINFO_INT_ADDRBUS_WIDTH + ADDRESS_SPACE_DATA: info->i = 7; break; |
| 1253 | 1288 | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_PROGRAM: info->internal_map8 = address_map_program_11bit; break; |
| 1254 | 1289 | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_DATA: info->internal_map8 = address_map_data_7bit; break; |
| 1255 | | case CPUINFO_PTR_INIT: info->init = i8039_init; break; |
| 1290 | case CPUINFO_PTR_INIT: info->init = i8049_init; break; |
| 1256 | 1291 | case CPUINFO_STR_NAME: strcpy(info->s, "I8049"); break; |
| 1257 | 1292 | default: mcs48_get_info(state, info); break; |
| 1258 | 1293 | } |
| r3128 | r3129 | |
| 1268 | 1303 | case CPUINFO_INT_ADDRBUS_WIDTH + ADDRESS_SPACE_DATA: info->i = 7; break; |
| 1269 | 1304 | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_PROGRAM: info->internal_map8 = address_map_program_11bit; break; |
| 1270 | 1305 | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_DATA: info->internal_map8 = address_map_data_7bit; break; |
| 1271 | | case CPUINFO_PTR_INIT: info->init = i8039_init; break; |
| 1306 | case CPUINFO_PTR_INIT: info->init = i8049_init; break; |
| 1272 | 1307 | case CPUINFO_STR_NAME: strcpy(info->s, "I8749"); break; |
| 1273 | 1308 | default: mcs48_get_info(state, info); break; |
| 1274 | 1309 | } |
| r3128 | r3129 | |
| 1282 | 1317 | { |
| 1283 | 1318 | case CPUINFO_INT_ADDRBUS_WIDTH + ADDRESS_SPACE_PROGRAM: info->i = 12; break; |
| 1284 | 1319 | case CPUINFO_INT_ADDRBUS_WIDTH + ADDRESS_SPACE_DATA: info->i = 7; break; |
| 1320 | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_PROGRAM: info->internal_map8 = address_map_program_11bit; break; |
| 1285 | 1321 | case CPUINFO_PTR_INTERNAL_MEMORY_MAP + ADDRESS_SPACE_DATA: info->internal_map8 = address_map_data_7bit; break; |
| 1286 | | case CPUINFO_PTR_INIT: info->init = i8039_init; break; |
| 1322 | case CPUINFO_PTR_INIT: info->init = i8049_init; break; |
| 1287 | 1323 | case CPUINFO_STR_NAME: strcpy(info->s, "M58715"); break; |
| 1288 | 1324 | default: mcs48_get_info(state, info); break; |
| 1289 | 1325 | } |