badline 0.12.0 → 0.13.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (516) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +25 -0
  3. data/CLAUDE.md +59 -31
  4. data/README.md +1 -1
  5. data/doc/library.md +9 -9
  6. data/doc/pinned-behaviour.md +105 -105
  7. data/doc/snapshots.md +1 -4
  8. data/lib/badline/audio/bare_player.rb +4 -4
  9. data/lib/badline/audio/cli.rb +6 -6
  10. data/lib/badline/audio/jukebox.rb +2 -2
  11. data/lib/badline/audio/machine_player.rb +2 -2
  12. data/lib/badline/{media → audio}/queue.rb +1 -1
  13. data/lib/badline/audio/queued_tune.rb +6 -6
  14. data/lib/badline/audio/renderer.rb +5 -5
  15. data/lib/badline/audio/stereo.rb +1 -1
  16. data/lib/badline/c128/{bus_state.rb → bus/saved_state.rb} +6 -6
  17. data/lib/badline/c128/bus.rb +30 -51
  18. data/lib/badline/c128/color_lines.rb +2 -2
  19. data/lib/badline/c128/cpu.rb +1 -1
  20. data/lib/badline/c128/drives.rb +10 -11
  21. data/lib/badline/c128/fast_serial.rb +5 -5
  22. data/lib/badline/c128/mmu_pages.rb +1 -1
  23. data/lib/badline/c128/modes.rb +2 -2
  24. data/lib/badline/c128/saved_state.rb +21 -47
  25. data/lib/badline/c128/z80.rb +2 -2
  26. data/lib/badline/c128.rb +18 -72
  27. data/lib/badline/{computer → c64}/attachments.rb +16 -47
  28. data/lib/badline/c64/banked_ram/banking.rb +32 -0
  29. data/lib/badline/c64/banked_ram/plus256k.rb +56 -0
  30. data/lib/badline/c64/banked_ram/plus60k.rb +45 -0
  31. data/lib/badline/c64/banked_ram/unexpanded.rb +30 -0
  32. data/lib/badline/c64/banked_ram.rb +23 -0
  33. data/lib/badline/c64/bus/extra_sids.rb +32 -0
  34. data/lib/badline/c64/bus/fittings.rb +40 -0
  35. data/lib/badline/c64/bus/pla.rb +149 -0
  36. data/lib/badline/c64/bus/roms.rb +41 -0
  37. data/lib/badline/c64/bus/saved_state.rb +68 -0
  38. data/lib/badline/c64/bus/sid_slots.rb +44 -0
  39. data/lib/badline/c64/bus.rb +218 -0
  40. data/lib/badline/c64/cartridge/action_replay.rb +128 -0
  41. data/lib/badline/c64/cartridge/atomic_power.rb +26 -0
  42. data/lib/badline/c64/cartridge/bank.rb +83 -0
  43. data/lib/badline/c64/cartridge/comal80.rb +52 -0
  44. data/lib/badline/c64/cartridge/dinamic.rb +36 -0
  45. data/lib/badline/c64/cartridge/easy_flash.rb +147 -0
  46. data/lib/badline/c64/cartridge/epyx_fastload.rb +81 -0
  47. data/lib/badline/c64/cartridge/final_cartridge3.rb +91 -0
  48. data/lib/badline/c64/cartridge/flash/saved_state.rb +40 -0
  49. data/lib/badline/c64/cartridge/flash.rb +279 -0
  50. data/lib/badline/c64/cartridge/freezer.rb +35 -0
  51. data/lib/badline/c64/cartridge/fun_play.rb +40 -0
  52. data/lib/badline/c64/cartridge/g_mod2.rb +76 -0
  53. data/lib/badline/c64/cartridge/game_system.rb +42 -0
  54. data/lib/badline/c64/cartridge/geo_ram.rb +81 -0
  55. data/lib/badline/c64/cartridge/kcs_power.rb +77 -0
  56. data/lib/badline/c64/cartridge/mach5.rb +34 -0
  57. data/lib/badline/c64/cartridge/magic_desk.rb +32 -0
  58. data/lib/badline/c64/cartridge/ocean.rb +37 -0
  59. data/lib/badline/c64/cartridge/pagefox.rb +70 -0
  60. data/lib/badline/c64/cartridge/retro_replay/saved_state.rb +47 -0
  61. data/lib/badline/c64/cartridge/retro_replay.rb +286 -0
  62. data/lib/badline/c64/cartridge/rex_utility.rb +31 -0
  63. data/lib/badline/c64/cartridge/rgcd.rb +60 -0
  64. data/lib/badline/c64/cartridge/saved_state.rb +63 -0
  65. data/lib/badline/c64/cartridge/simons_basic.rb +37 -0
  66. data/lib/badline/c64/cartridge/standard.rb +17 -0
  67. data/lib/badline/c64/cartridge/super_games.rb +50 -0
  68. data/lib/badline/c64/cartridge/westermann.rb +32 -0
  69. data/lib/badline/c64/cartridge/zaxxon.rb +68 -0
  70. data/lib/badline/c64/cartridge.rb +258 -0
  71. data/lib/badline/c64/color_memory.rb +27 -0
  72. data/lib/badline/c64/common.rb +34 -0
  73. data/lib/badline/c64/kernal_traps.rb +89 -0
  74. data/lib/badline/c64/reu/dma/saved_state.rb +52 -0
  75. data/lib/badline/c64/reu/dma.rb +275 -0
  76. data/lib/badline/c64/reu/ram.rb +109 -0
  77. data/lib/badline/c64/reu/saved_state.rb +55 -0
  78. data/lib/badline/c64/reu/trigger.rb +34 -0
  79. data/lib/badline/c64/reu.rb +291 -0
  80. data/lib/badline/{computer → c64}/saved_state.rb +13 -18
  81. data/lib/badline/{computer → c64}/true_drives.rb +20 -31
  82. data/lib/badline/{computer.rb → c64.rb} +22 -80
  83. data/lib/badline/chips/cia/fast_forward.rb +62 -0
  84. data/lib/badline/chips/cia/interrupt_register.rb +145 -0
  85. data/lib/badline/chips/cia/saved_state.rb +49 -0
  86. data/lib/badline/chips/cia/serial/saved_state.rb +45 -0
  87. data/lib/badline/chips/cia/serial.rb +250 -0
  88. data/lib/badline/chips/cia/time_of_day.rb +232 -0
  89. data/lib/badline/chips/cia/timer.rb +208 -0
  90. data/lib/badline/chips/cia.rb +281 -0
  91. data/lib/badline/chips/cpu/addressing.rb +133 -0
  92. data/lib/badline/chips/cpu/boundary.rb +56 -0
  93. data/lib/badline/chips/cpu/core.rb +167 -0
  94. data/lib/badline/chips/cpu/instruction.rb +338 -0
  95. data/lib/badline/chips/cpu/instruction_set/arithmetic.rb +118 -0
  96. data/lib/badline/chips/cpu/instruction_set/bitwise.rb +130 -0
  97. data/lib/badline/chips/cpu/instruction_set/branch.rb +83 -0
  98. data/lib/badline/chips/cpu/instruction_set/flag.rb +67 -0
  99. data/lib/badline/chips/cpu/instruction_set/illegal.rb +274 -0
  100. data/lib/badline/chips/cpu/instruction_set/inc_dec.rb +73 -0
  101. data/lib/badline/chips/cpu/instruction_set/stack.rb +56 -0
  102. data/lib/badline/chips/cpu/instruction_set/transfer.rb +141 -0
  103. data/lib/badline/chips/cpu/instruction_set.rb +59 -0
  104. data/lib/badline/chips/cpu/interrupts.rb +108 -0
  105. data/lib/badline/chips/cpu/microcode.rb +179 -0
  106. data/lib/badline/chips/cpu/operations.rb +90 -0
  107. data/lib/badline/chips/cpu/port.rb +116 -0
  108. data/lib/badline/chips/cpu/saved_state.rb +117 -0
  109. data/lib/badline/chips/cpu/stack_operations.rb +84 -0
  110. data/lib/badline/chips/cpu/traps.rb +23 -0
  111. data/lib/badline/chips/cpu.rb +12 -0
  112. data/lib/badline/chips/sid/catch_up.rb +122 -0
  113. data/lib/badline/chips/sid/decimator.rb +66 -0
  114. data/lib/badline/chips/sid/envelope/saved_state.rb +70 -0
  115. data/lib/badline/chips/sid/envelope.rb +241 -0
  116. data/lib/badline/chips/sid/filter/saved_state.rb +42 -0
  117. data/lib/badline/chips/sid/filter.rb +241 -0
  118. data/lib/badline/chips/sid/saved_state.rb +52 -0
  119. data/lib/badline/chips/sid/voice.rb +79 -0
  120. data/lib/badline/chips/sid/waveform/combined.rb +128 -0
  121. data/lib/badline/chips/sid/waveform/fast_forward.rb +107 -0
  122. data/lib/badline/chips/sid/waveform/noise_writeback.rb +124 -0
  123. data/lib/badline/chips/sid/waveform/saved_state.rb +68 -0
  124. data/lib/badline/chips/sid/waveform.rb +307 -0
  125. data/lib/badline/chips/sid.rb +265 -0
  126. data/lib/badline/{c128 → chips}/vdc/memory.rb +1 -1
  127. data/lib/badline/{c128 → chips}/vdc/painter.rb +1 -1
  128. data/lib/badline/{c128 → chips}/vdc/raster.rb +1 -1
  129. data/lib/badline/chips/vdc/saved_state.rb +36 -0
  130. data/lib/badline/{c128 → chips}/vdc/window.rb +1 -1
  131. data/lib/badline/{c128 → chips}/vdc.rb +7 -31
  132. data/lib/badline/chips/via/control_lines.rb +124 -0
  133. data/lib/badline/chips/via/fast_forward.rb +55 -0
  134. data/lib/badline/chips/via/interrupt_register.rb +69 -0
  135. data/lib/badline/chips/via/saved_state.rb +44 -0
  136. data/lib/badline/chips/via/shift_register.rb +182 -0
  137. data/lib/badline/chips/via/timer1.rb +133 -0
  138. data/lib/badline/chips/via/timer2.rb +135 -0
  139. data/lib/badline/chips/via.rb +268 -0
  140. data/lib/badline/chips/vic/bank.rb +135 -0
  141. data/lib/badline/chips/vic/border_mask.rb +88 -0
  142. data/lib/badline/chips/vic/collisions.rb +117 -0
  143. data/lib/badline/chips/vic/color_patches.rb +49 -0
  144. data/lib/badline/chips/vic/display_state.rb +187 -0
  145. data/lib/badline/chips/vic/graphics_mode.rb +166 -0
  146. data/lib/badline/chips/vic/graphics_shifter/saved_state.rb +40 -0
  147. data/lib/badline/chips/vic/graphics_shifter.rb +187 -0
  148. data/lib/badline/chips/vic/register_log.rb +83 -0
  149. data/lib/badline/chips/vic/registers.rb +197 -0
  150. data/lib/badline/chips/vic/saved_state.rb +82 -0
  151. data/lib/badline/chips/vic/sequencer/saved_state.rb +91 -0
  152. data/lib/badline/chips/vic/sequencer.rb +277 -0
  153. data/lib/badline/chips/vic/sequencer_output.rb +118 -0
  154. data/lib/badline/chips/vic/sprite/internal_bus.rb +70 -0
  155. data/lib/badline/chips/vic/sprite/saved_state.rb +66 -0
  156. data/lib/badline/chips/vic/sprite/shifter.rb +148 -0
  157. data/lib/badline/chips/vic/sprite/timing.rb +58 -0
  158. data/lib/badline/chips/vic/sprite.rb +339 -0
  159. data/lib/badline/chips/vic/sprites/saved_state.rb +59 -0
  160. data/lib/badline/chips/vic/sprites.rb +284 -0
  161. data/lib/badline/chips/vic.rb +783 -0
  162. data/lib/badline/chips/vic_i/painter/saved_state.rb +40 -0
  163. data/lib/badline/{vic20/vic → chips/vic_i}/painter.rb +6 -30
  164. data/lib/badline/{vic20/vic → chips/vic_i}/saved_state.rb +2 -2
  165. data/lib/badline/chips/vic_i/sound/output.rb +85 -0
  166. data/lib/badline/chips/vic_i/sound.rb +235 -0
  167. data/lib/badline/{vic20/vic → chips/vic_i}/text_window.rb +2 -2
  168. data/lib/badline/{vic20/vic.rb → chips/vic_i.rb} +5 -5
  169. data/lib/badline/chips/z80/arithmetic.rb +119 -0
  170. data/lib/badline/chips/z80/bit_page.rb +57 -0
  171. data/lib/badline/chips/z80/block_io.rb +60 -0
  172. data/lib/badline/chips/z80/block_transfers.rb +61 -0
  173. data/lib/badline/chips/z80/bus_cycles.rb +113 -0
  174. data/lib/badline/chips/z80/core.rb +115 -0
  175. data/lib/badline/chips/z80/exchanges.rb +52 -0
  176. data/lib/badline/chips/z80/extended_page.rb +91 -0
  177. data/lib/badline/chips/z80/flags.rb +39 -0
  178. data/lib/badline/chips/z80/interrupt_acceptance.rb +48 -0
  179. data/lib/badline/chips/z80/jumps.rb +84 -0
  180. data/lib/badline/chips/z80/loads.rb +100 -0
  181. data/lib/badline/chips/z80/main_page.rb +136 -0
  182. data/lib/badline/chips/z80/registers.rb +122 -0
  183. data/lib/badline/chips/z80/saved_state.rb +71 -0
  184. data/lib/badline/chips/z80/shifts.rb +66 -0
  185. data/lib/badline/chips/z80.rb +13 -0
  186. data/lib/badline/core.rb +27 -29
  187. data/lib/badline/drives/datasette/saved_state.rb +37 -0
  188. data/lib/badline/drives/datasette.rb +140 -0
  189. data/lib/badline/drives/engine/core.rb +149 -0
  190. data/lib/badline/drives/engine/fast_serial.rb +75 -0
  191. data/lib/badline/drives/engine/idle.rb +127 -0
  192. data/lib/badline/drives/engine/idle_cpu.rb +30 -0
  193. data/lib/badline/drives/engine/orbit.rb +81 -0
  194. data/lib/badline/drives/engine/serial_lines.rb +75 -0
  195. data/lib/badline/drives/engine/sleep.rb +114 -0
  196. data/lib/badline/drives/engine/vias.rb +86 -0
  197. data/lib/badline/drives/engine/watch.rb +152 -0
  198. data/lib/badline/drives/engine.rb +11 -0
  199. data/lib/badline/drives/model1541/bus.rb +88 -0
  200. data/lib/badline/drives/model1541/byte_ready.rb +50 -0
  201. data/lib/badline/drives/model1541/cpu.rb +13 -0
  202. data/lib/badline/drives/model1541/disk/saved_state.rb +88 -0
  203. data/lib/badline/drives/model1541/disk.rb +317 -0
  204. data/lib/badline/drives/model1541/disk_via.rb +38 -0
  205. data/lib/badline/drives/model1541/gcr.rb +59 -0
  206. data/lib/badline/drives/model1541/mechanism/saved_state.rb +72 -0
  207. data/lib/badline/drives/model1541/mechanism.rb +315 -0
  208. data/lib/badline/drives/model1541/rotation.rb +123 -0
  209. data/lib/badline/drives/model1541/saved_state.rb +44 -0
  210. data/lib/badline/drives/model1541/sector_reader.rb +78 -0
  211. data/lib/badline/drives/model1541/serial_port.rb +20 -0
  212. data/lib/badline/drives/model1541/track.rb +100 -0
  213. data/lib/badline/drives/model1541.rb +81 -0
  214. data/lib/badline/drives/model1571/bus.rb +113 -0
  215. data/lib/badline/drives/model1571/cpu.rb +13 -0
  216. data/lib/badline/drives/model1571/saved_state.rb +47 -0
  217. data/lib/badline/drives/model1571/serial_port.rb +39 -0
  218. data/lib/badline/drives/model1571/serial_via.rb +27 -0
  219. data/lib/badline/drives/model1571/wd1770.rb +122 -0
  220. data/lib/badline/drives/model1571.rb +142 -0
  221. data/lib/badline/drives/model1581/bus.rb +139 -0
  222. data/lib/badline/drives/model1581/cpu.rb +13 -0
  223. data/lib/badline/drives/model1581/disk/saved_state.rb +89 -0
  224. data/lib/badline/drives/model1581/disk.rb +137 -0
  225. data/lib/badline/drives/model1581/mechanism.rb +119 -0
  226. data/lib/badline/drives/model1581/saved_state.rb +42 -0
  227. data/lib/badline/drives/model1581/serial_port.rb +54 -0
  228. data/lib/badline/drives/model1581/slot.rb +79 -0
  229. data/lib/badline/drives/model1581/track.rb +102 -0
  230. data/lib/badline/drives/model1581/track_bytes.rb +77 -0
  231. data/lib/badline/drives/model1581/wd1772/registers.rb +91 -0
  232. data/lib/badline/drives/model1581/wd1772/saved_state.rb +68 -0
  233. data/lib/badline/drives/model1581/wd1772/sector_writes.rb +75 -0
  234. data/lib/badline/drives/model1581/wd1772/sectors.rb +152 -0
  235. data/lib/badline/drives/model1581/wd1772/stepping.rb +111 -0
  236. data/lib/badline/drives/model1581/wd1772/tracks.rb +127 -0
  237. data/lib/badline/drives/model1581/wd1772/turn.rb +75 -0
  238. data/lib/badline/drives/model1581/wd1772.rb +218 -0
  239. data/lib/badline/drives/model1581.rb +206 -0
  240. data/lib/badline/drives/serial_bus.rb +161 -0
  241. data/lib/badline/frontend/boot.rb +10 -61
  242. data/lib/badline/frontend/machine_window.rb +3 -1
  243. data/lib/badline/frontend/player/filter_view.rb +1 -1
  244. data/lib/badline/frontend/player/player_controller.rb +2 -2
  245. data/lib/badline/frontend/player/player_screen.rb +1 -0
  246. data/lib/badline/frontend/player/theme.rb +7 -7
  247. data/lib/badline/frontend/timeline.rb +3 -3
  248. data/lib/badline/input/control_ports.rb +78 -0
  249. data/lib/badline/input/joystick.rb +27 -0
  250. data/lib/badline/input/keyboard.rb +114 -0
  251. data/lib/badline/input.rb +3 -0
  252. data/lib/badline/kernal_trap/{drive → dos}/block_commands.rb +1 -1
  253. data/lib/badline/kernal_trap/dos/channel.rb +183 -0
  254. data/lib/badline/kernal_trap/{drive → dos}/channels.rb +1 -1
  255. data/lib/badline/kernal_trap/{drive → dos}/memory.rb +1 -1
  256. data/lib/badline/kernal_trap/{drive → dos}/parameters.rb +1 -1
  257. data/lib/badline/kernal_trap/{drive → dos}/status.rb +1 -1
  258. data/lib/badline/kernal_trap/{drive → dos}/write_file.rb +1 -1
  259. data/lib/badline/kernal_trap/{drive → dos}/writes.rb +1 -1
  260. data/lib/badline/kernal_trap/{drive.rb → dos.rb} +11 -10
  261. data/lib/badline/kernal_trap/{file.rb → file_routine.rb} +1 -1
  262. data/lib/badline/kernal_trap/load.rb +6 -6
  263. data/lib/badline/kernal_trap/save.rb +5 -5
  264. data/lib/badline/kernal_trap/serial.rb +7 -7
  265. data/lib/badline/kernal_trap.rb +2 -3
  266. data/lib/badline/machine/clocking.rb +50 -0
  267. data/lib/badline/machine.rb +63 -7
  268. data/lib/badline/media/boot_disk.rb +2 -2
  269. data/lib/badline/media/disk_list.rb +3 -3
  270. data/lib/badline/media/disk_set.rb +1 -1
  271. data/lib/badline/media/extensions.rb +33 -0
  272. data/lib/badline/media/program.rb +28 -0
  273. data/lib/badline/media/true_drive.rb +4 -3
  274. data/lib/badline/media/tune.rb +35 -0
  275. data/lib/badline/media/vic20_cartridge.rb +1 -7
  276. data/lib/badline/media/vic20_media.rb +38 -80
  277. data/lib/badline/media.rb +84 -81
  278. data/lib/badline/model.rb +1 -1
  279. data/lib/badline/options/event.rb +3 -1
  280. data/lib/badline/roms/README +6 -6
  281. data/lib/badline/sdl.rb +1 -0
  282. data/lib/badline/{storage/sid_file.rb → sid_tune/file.rb} +3 -3
  283. data/lib/badline/{storage → sid_tune}/hvsc.rb +7 -7
  284. data/lib/badline/{storage → sid_tune}/song_lengths.rb +2 -2
  285. data/lib/badline/{storage → sid_tune}/stil/credit.rb +1 -1
  286. data/lib/badline/{storage → sid_tune}/stil.rb +3 -3
  287. data/lib/badline/sid_tune.rb +6 -0
  288. data/lib/badline/snapshot/c128_setup.rb +43 -0
  289. data/lib/badline/snapshot/c64_setup.rb +79 -0
  290. data/lib/badline/snapshot/image.rb +5 -25
  291. data/lib/badline/snapshot/machine_state.rb +10 -2
  292. data/lib/badline/snapshot/setup.rb +22 -66
  293. data/lib/badline/snapshot/state.rb +8 -17
  294. data/lib/badline/snapshot/storage_setup.rb +68 -0
  295. data/lib/badline/snapshot/vic20_setup.rb +37 -0
  296. data/lib/badline/snapshot/vice/c64_mem.rb +1 -1
  297. data/lib/badline/snapshot/vice/restore.rb +1 -1
  298. data/lib/badline/snapshot/vice/reu1764.rb +1 -1
  299. data/lib/badline/snapshot/vice/reu_fields.rb +40 -0
  300. data/lib/badline/snapshot/vice.rb +7 -5
  301. data/lib/badline/snapshot.rb +13 -12
  302. data/lib/badline/storage/d64_image.rb +15 -9
  303. data/lib/badline/storage/d71_image.rb +0 -2
  304. data/lib/badline/storage/d81_image.rb +0 -2
  305. data/lib/badline/storage/disk_image/writing.rb +2 -2
  306. data/lib/badline/storage/disk_image.rb +3 -6
  307. data/lib/badline/storage/g64_image.rb +2 -2
  308. data/lib/badline/storage/host_directory.rb +0 -5
  309. data/lib/badline/storage/t64.rb +2 -8
  310. data/lib/badline/storage/unavailable.rb +1 -1
  311. data/lib/badline/storage.rb +0 -37
  312. data/lib/badline/support/c128_checkpoint.rb +39 -0
  313. data/lib/badline/support/checkpoint.rb +108 -0
  314. data/lib/badline/support/vic20_checkpoint.rb +38 -0
  315. data/lib/badline/support.rb +5 -0
  316. data/lib/badline/version.rb +1 -1
  317. data/lib/badline/vic20/attachments.rb +11 -81
  318. data/lib/badline/vic20/bus/saved_state.rb +35 -0
  319. data/lib/badline/vic20/bus.rb +3 -25
  320. data/lib/badline/vic20/cpu.rb +1 -1
  321. data/lib/badline/vic20/port_wiring.rb +4 -4
  322. data/lib/badline/vic20/saved_state.rb +16 -60
  323. data/lib/badline/vic20/user_via_ports.rb +2 -2
  324. data/lib/badline/vic20.rb +20 -51
  325. metadata +250 -221
  326. data/lib/badline/address_bus/extra_sids.rb +0 -30
  327. data/lib/badline/address_bus/fittings.rb +0 -38
  328. data/lib/badline/address_bus/pla.rb +0 -147
  329. data/lib/badline/address_bus/roms.rb +0 -39
  330. data/lib/badline/address_bus/saved_state.rb +0 -72
  331. data/lib/badline/address_bus/sid_slots.rb +0 -42
  332. data/lib/badline/address_bus.rb +0 -235
  333. data/lib/badline/cartridge/action_replay.rb +0 -126
  334. data/lib/badline/cartridge/atomic_power.rb +0 -24
  335. data/lib/badline/cartridge/bank.rb +0 -81
  336. data/lib/badline/cartridge/comal80.rb +0 -50
  337. data/lib/badline/cartridge/dinamic.rb +0 -34
  338. data/lib/badline/cartridge/easy_flash.rb +0 -145
  339. data/lib/badline/cartridge/epyx_fastload.rb +0 -79
  340. data/lib/badline/cartridge/final_cartridge3.rb +0 -89
  341. data/lib/badline/cartridge/flash.rb +0 -306
  342. data/lib/badline/cartridge/freezer.rb +0 -33
  343. data/lib/badline/cartridge/fun_play.rb +0 -38
  344. data/lib/badline/cartridge/g_mod2.rb +0 -74
  345. data/lib/badline/cartridge/game_system.rb +0 -40
  346. data/lib/badline/cartridge/geo_ram.rb +0 -79
  347. data/lib/badline/cartridge/kcs_power.rb +0 -75
  348. data/lib/badline/cartridge/mach5.rb +0 -32
  349. data/lib/badline/cartridge/magic_desk.rb +0 -30
  350. data/lib/badline/cartridge/ocean.rb +0 -35
  351. data/lib/badline/cartridge/pagefox.rb +0 -68
  352. data/lib/badline/cartridge/retro_replay.rb +0 -320
  353. data/lib/badline/cartridge/rex_utility.rb +0 -29
  354. data/lib/badline/cartridge/rgcd.rb +0 -58
  355. data/lib/badline/cartridge/simons_basic.rb +0 -35
  356. data/lib/badline/cartridge/standard.rb +0 -15
  357. data/lib/badline/cartridge/super_games.rb +0 -48
  358. data/lib/badline/cartridge/westermann.rb +0 -30
  359. data/lib/badline/cartridge/zaxxon.rb +0 -66
  360. data/lib/badline/cartridge.rb +0 -303
  361. data/lib/badline/checkpoint.rb +0 -98
  362. data/lib/badline/cia/fast_forward.rb +0 -60
  363. data/lib/badline/cia/interrupt_register.rb +0 -143
  364. data/lib/badline/cia/serial.rb +0 -275
  365. data/lib/badline/cia/state.rb +0 -47
  366. data/lib/badline/cia/timer.rb +0 -206
  367. data/lib/badline/cia.rb +0 -279
  368. data/lib/badline/color_memory.rb +0 -25
  369. data/lib/badline/computer/kernal_traps.rb +0 -29
  370. data/lib/badline/control_ports.rb +0 -76
  371. data/lib/badline/cpu/addressing.rb +0 -131
  372. data/lib/badline/cpu/boundary.rb +0 -54
  373. data/lib/badline/cpu/core.rb +0 -165
  374. data/lib/badline/cpu/microcode.rb +0 -177
  375. data/lib/badline/cpu/operations.rb +0 -88
  376. data/lib/badline/cpu/saved_state.rb +0 -115
  377. data/lib/badline/cpu/stack_operations.rb +0 -82
  378. data/lib/badline/cpu.rb +0 -10
  379. data/lib/badline/cycleable.rb +0 -38
  380. data/lib/badline/datasette.rb +0 -161
  381. data/lib/badline/drive/core.rb +0 -147
  382. data/lib/badline/drive/fast_serial.rb +0 -73
  383. data/lib/badline/drive/idle.rb +0 -125
  384. data/lib/badline/drive/idle_cpu.rb +0 -28
  385. data/lib/badline/drive/orbit.rb +0 -79
  386. data/lib/badline/drive/serial_lines.rb +0 -73
  387. data/lib/badline/drive/sleep.rb +0 -112
  388. data/lib/badline/drive/vias.rb +0 -84
  389. data/lib/badline/drive/watch.rb +0 -150
  390. data/lib/badline/drive.rb +0 -11
  391. data/lib/badline/drive1541/bus.rb +0 -86
  392. data/lib/badline/drive1541/byte_ready.rb +0 -48
  393. data/lib/badline/drive1541/cpu.rb +0 -11
  394. data/lib/badline/drive1541/disk.rb +0 -318
  395. data/lib/badline/drive1541/disk_state.rb +0 -94
  396. data/lib/badline/drive1541/disk_via.rb +0 -36
  397. data/lib/badline/drive1541/gcr.rb +0 -57
  398. data/lib/badline/drive1541/mechanism.rb +0 -313
  399. data/lib/badline/drive1541/mechanism_state.rb +0 -68
  400. data/lib/badline/drive1541/rotation.rb +0 -121
  401. data/lib/badline/drive1541/sector_reader.rb +0 -76
  402. data/lib/badline/drive1541/serial_port.rb +0 -18
  403. data/lib/badline/drive1541/track.rb +0 -98
  404. data/lib/badline/drive1541.rb +0 -111
  405. data/lib/badline/drive1571/bus.rb +0 -111
  406. data/lib/badline/drive1571/cpu.rb +0 -11
  407. data/lib/badline/drive1571/serial_port.rb +0 -37
  408. data/lib/badline/drive1571/serial_via.rb +0 -25
  409. data/lib/badline/drive1571/wd1770.rb +0 -120
  410. data/lib/badline/drive1571.rb +0 -175
  411. data/lib/badline/drive1581/bus.rb +0 -137
  412. data/lib/badline/drive1581/cpu.rb +0 -11
  413. data/lib/badline/drive1581/disk.rb +0 -135
  414. data/lib/badline/drive1581/disk_state.rb +0 -87
  415. data/lib/badline/drive1581/mechanism.rb +0 -117
  416. data/lib/badline/drive1581/serial_port.rb +0 -52
  417. data/lib/badline/drive1581/slot.rb +0 -78
  418. data/lib/badline/drive1581/track.rb +0 -100
  419. data/lib/badline/drive1581/track_bytes.rb +0 -75
  420. data/lib/badline/drive1581/wd1772/registers.rb +0 -89
  421. data/lib/badline/drive1581/wd1772/sector_writes.rb +0 -73
  422. data/lib/badline/drive1581/wd1772/sectors.rb +0 -150
  423. data/lib/badline/drive1581/wd1772/state.rb +0 -66
  424. data/lib/badline/drive1581/wd1772/stepping.rb +0 -109
  425. data/lib/badline/drive1581/wd1772/tracks.rb +0 -125
  426. data/lib/badline/drive1581/wd1772/turn.rb +0 -73
  427. data/lib/badline/drive1581/wd1772.rb +0 -216
  428. data/lib/badline/drive1581.rb +0 -233
  429. data/lib/badline/iec_bus.rb +0 -159
  430. data/lib/badline/instruction.rb +0 -334
  431. data/lib/badline/instruction_set/arithmetic.rb +0 -114
  432. data/lib/badline/instruction_set/bitwise.rb +0 -126
  433. data/lib/badline/instruction_set/branch.rb +0 -79
  434. data/lib/badline/instruction_set/flag.rb +0 -63
  435. data/lib/badline/instruction_set/illegal.rb +0 -270
  436. data/lib/badline/instruction_set/inc_dec.rb +0 -69
  437. data/lib/badline/instruction_set/stack.rb +0 -52
  438. data/lib/badline/instruction_set/transfer.rb +0 -137
  439. data/lib/badline/instruction_set.rb +0 -55
  440. data/lib/badline/interrupts.rb +0 -104
  441. data/lib/badline/joystick.rb +0 -25
  442. data/lib/badline/kernal_trap/channel.rb +0 -181
  443. data/lib/badline/keyboard.rb +0 -112
  444. data/lib/badline/ram_expansion/banking.rb +0 -30
  445. data/lib/badline/ram_expansion/plus256k.rb +0 -54
  446. data/lib/badline/ram_expansion/plus60k.rb +0 -43
  447. data/lib/badline/ram_expansion/unexpanded.rb +0 -28
  448. data/lib/badline/ram_expansion.rb +0 -21
  449. data/lib/badline/reu/dma/saved_state.rb +0 -50
  450. data/lib/badline/reu/dma.rb +0 -273
  451. data/lib/badline/reu/ram.rb +0 -107
  452. data/lib/badline/reu/saved_state.rb +0 -80
  453. data/lib/badline/reu/trigger.rb +0 -32
  454. data/lib/badline/reu.rb +0 -289
  455. data/lib/badline/sid/catch_up.rb +0 -120
  456. data/lib/badline/sid/decimator.rb +0 -64
  457. data/lib/badline/sid/envelope/state.rb +0 -68
  458. data/lib/badline/sid/envelope.rb +0 -239
  459. data/lib/badline/sid/filter.rb +0 -263
  460. data/lib/badline/sid/voice.rb +0 -77
  461. data/lib/badline/sid/waveform/combined.rb +0 -126
  462. data/lib/badline/sid/waveform/fast_forward.rb +0 -105
  463. data/lib/badline/sid/waveform/noise_writeback.rb +0 -122
  464. data/lib/badline/sid/waveform/state.rb +0 -66
  465. data/lib/badline/sid/waveform.rb +0 -305
  466. data/lib/badline/sid.rb +0 -303
  467. data/lib/badline/time_of_day.rb +0 -228
  468. data/lib/badline/traps.rb +0 -19
  469. data/lib/badline/via/control_lines.rb +0 -122
  470. data/lib/badline/via/fast_forward.rb +0 -53
  471. data/lib/badline/via/interrupt_register.rb +0 -67
  472. data/lib/badline/via/shift_register.rb +0 -180
  473. data/lib/badline/via/state.rb +0 -42
  474. data/lib/badline/via/timer1.rb +0 -131
  475. data/lib/badline/via/timer2.rb +0 -133
  476. data/lib/badline/via.rb +0 -266
  477. data/lib/badline/vic/bank.rb +0 -133
  478. data/lib/badline/vic/border_mask.rb +0 -86
  479. data/lib/badline/vic/collisions.rb +0 -115
  480. data/lib/badline/vic/color_patches.rb +0 -47
  481. data/lib/badline/vic/display_state.rb +0 -185
  482. data/lib/badline/vic/graphics_mode.rb +0 -164
  483. data/lib/badline/vic/graphics_shifter.rb +0 -207
  484. data/lib/badline/vic/register_log.rb +0 -81
  485. data/lib/badline/vic/registers.rb +0 -195
  486. data/lib/badline/vic/sequencer.rb +0 -275
  487. data/lib/badline/vic/sequencer_output.rb +0 -116
  488. data/lib/badline/vic/sequencer_state.rb +0 -89
  489. data/lib/badline/vic/sprite/internal_bus.rb +0 -68
  490. data/lib/badline/vic/sprite/saved_state.rb +0 -64
  491. data/lib/badline/vic/sprite/shifter.rb +0 -146
  492. data/lib/badline/vic/sprite/timing.rb +0 -56
  493. data/lib/badline/vic/sprite.rb +0 -337
  494. data/lib/badline/vic/sprites.rb +0 -282
  495. data/lib/badline/vic/sprites_state.rb +0 -57
  496. data/lib/badline/vic.rb +0 -852
  497. data/lib/badline/vic20/sound/output.rb +0 -83
  498. data/lib/badline/vic20/sound.rb +0 -233
  499. data/lib/badline/z80/arithmetic.rb +0 -117
  500. data/lib/badline/z80/bit_page.rb +0 -55
  501. data/lib/badline/z80/block_io.rb +0 -58
  502. data/lib/badline/z80/block_transfers.rb +0 -59
  503. data/lib/badline/z80/bus_cycles.rb +0 -111
  504. data/lib/badline/z80/core.rb +0 -113
  505. data/lib/badline/z80/exchanges.rb +0 -50
  506. data/lib/badline/z80/extended_page.rb +0 -89
  507. data/lib/badline/z80/flags.rb +0 -37
  508. data/lib/badline/z80/interrupt_acceptance.rb +0 -46
  509. data/lib/badline/z80/jumps.rb +0 -82
  510. data/lib/badline/z80/loads.rb +0 -98
  511. data/lib/badline/z80/main_page.rb +0 -134
  512. data/lib/badline/z80/registers.rb +0 -120
  513. data/lib/badline/z80/saved_state.rb +0 -69
  514. data/lib/badline/z80/shifts.rb +0 -64
  515. data/lib/badline/z80.rb +0 -11
  516. /data/lib/badline/snapshot/{fields.rb → vice/fields.rb} +0 -0
@@ -0,0 +1,275 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "badline/c64/reu/dma/saved_state"
4
+
5
+ module Badline
6
+ class C64
7
+ class REU
8
+ # One transfer between the C64 and the REU's RAM, clocked a cycle at a
9
+ # time while the REC holds the bus. The REC only reads the C64's bus
10
+ # while BA is high, so a read followed by BA low waits for BA to rise.
11
+ # After a write it goes on through the first BA-low cycle and stops at
12
+ # the second. See doc/pinned-behaviour.md, REU DMA.
13
+ class DMA
14
+ include SavedState
15
+
16
+ # Transfer types, as the command register's bottom two bits give
17
+ # them.
18
+ STASH = 0
19
+ FETCH = 1
20
+ SWAP = 2
21
+ VERIFY = 3
22
+
23
+ # What the REC did on the cycle before.
24
+ IDLE = 0
25
+ READ = 1
26
+ WRITE = 2
27
+
28
+ # Where the transfer stopped, what it left for the length register,
29
+ # and the status bits it ended with.
30
+ attr_reader :c64, :expansion, :length, :events
31
+
32
+ def initialize(ram, span, bus)
33
+ @ram = ram
34
+ @span = span
35
+ @bus = bus
36
+ @c64 = @expansion = @length = @events = 0
37
+ @holding = false
38
+ end
39
+
40
+ # Whether the REC held the bus on the last cycle clocked, which it
41
+ # does while it waits for BA too, since the CPU stays halted.
42
+ def holds_bus? = @holding
43
+
44
+ # A length of 0 moves 64K. control is the address control register,
45
+ # which can hold either address where it is.
46
+ def start(type, c64, expansion, length, control)
47
+ @type = type
48
+ @c64 = c64
49
+ @expansion = expansion
50
+ @length = length.zero? ? 0x10000 : length
51
+ @c64_step = control.anybits?(FIX_C64) ? 0 : 1
52
+ @expansion_step = control.anybits?(FIX_EXPANSION) ? 0 : 1
53
+ @events = 0
54
+ @holding = true
55
+ @last = IDLE
56
+ @waiting = false
57
+ @ba_low_after_writes = 0
58
+ @stopped_after_write = false
59
+ @swap_write_due = false
60
+ @swap_read_again = false
61
+ @swap_byte = 0
62
+ @held_read = 0
63
+ @moved_all = false
64
+ @extra_cycle = false
65
+ end
66
+
67
+ # Writes the byte a fetch from these addresses starts with, without
68
+ # counting it. Other transfers start with a read.
69
+ def write_ahead(type, c64, expansion)
70
+ return unless type == FETCH
71
+
72
+ @c64 = c64
73
+ byte = @ram.peek(expansion)
74
+ @ram.latch = byte
75
+ write_c64(byte)
76
+ end
77
+
78
+ # One cycle of the transfer. The cycle the REC lets go of the bus on
79
+ # is the CPU's. late says BA fell on this cycle but a REC that moved a
80
+ # byte on the last one doesn't see it yet (VIC#reu_ba_late?), and
81
+ # handed_on that BA runs on from a bad line's DMA into a sprite's
82
+ # here (VIC#reu_ba_handed_on?).
83
+ def cycle!(ba_low, late, handed_on)
84
+ note_ba(ba_low, late)
85
+ @swap_read_again ||= handed_on && @swap_write_due
86
+ settle_held_read(ba_low) if @held_read.positive?
87
+ return if @waiting && ba_low
88
+
89
+ @waiting = false
90
+ @moved_all ? wind_down : move(ba_low)
91
+ end
92
+
93
+ private
94
+
95
+ # The second BA-low cycle in a row after writes stops the REC, and so
96
+ # does any BA-low cycle after a read. It then waits for BA to rise.
97
+ def note_ba(ba_low, late)
98
+ seen = ba_low && !late
99
+ if @last == READ
100
+ note_ba_after_read(seen)
101
+ elsif @last == WRITE
102
+ note_ba_after_write(seen)
103
+ end
104
+ @last = IDLE
105
+ end
106
+
107
+ # A swap's read that BA stops before its write is made again.
108
+ def note_ba_after_read(ba_low)
109
+ @waiting = ba_low
110
+ @ba_low_after_writes = 0
111
+ @swap_read_again = ba_low && @swap_write_due && @held_read.zero?
112
+ end
113
+
114
+ # A fetch's last write doesn't go through the first BA-low cycle.
115
+ # Pinned by REU/reutiming2/d and d2.
116
+ def note_ba_after_write(ba_low)
117
+ @ba_low_after_writes = ba_low ? @ba_low_after_writes + 1 : 0
118
+ @stopped_after_write = @ba_low_after_writes == 2 || (ba_low && @type == FETCH && @length == 1)
119
+ return unless @stopped_after_write
120
+
121
+ @waiting = true
122
+ @ba_low_after_writes = 0
123
+ end
124
+
125
+ # A fetch or a swap whose last write ran into BA, or a verify that
126
+ # found a difference before its last byte, takes one more cycle before
127
+ # the REC lets go of the bus.
128
+ def wind_down
129
+ if @extra_cycle || (@stopped_after_write && (@type == FETCH || @type == SWAP))
130
+ @extra_cycle = @stopped_after_write = false
131
+ @last = READ
132
+ return
133
+ end
134
+
135
+ @holding = false
136
+ settle
137
+ end
138
+
139
+ def move(ba_low)
140
+ case @type
141
+ when STASH then stash
142
+ when FETCH then fetch
143
+ when SWAP then swap(ba_low)
144
+ else verify
145
+ end
146
+ end
147
+
148
+ # The REU's data bus latch keeps the last byte the REC stored.
149
+ def stash
150
+ byte = read_c64
151
+ @ram.poke(@expansion, byte)
152
+ @ram.latch = byte
153
+ step
154
+ @last = READ
155
+ end
156
+
157
+ def fetch
158
+ byte = @ram.peek(@expansion)
159
+ @ram.latch = byte
160
+ write_c64(byte)
161
+ step
162
+ @last = WRITE
163
+ end
164
+
165
+ # Two cycles a byte: the C64's byte is read and stored while the
166
+ # REU's is fetched, and the REU's is written to the C64 on the next.
167
+ def swap(ba_low)
168
+ return read_swap_again if @swap_read_again
169
+
170
+ if @swap_write_due
171
+ @swap_write_due = false
172
+ write_c64(@swap_byte)
173
+ step
174
+ @last = WRITE
175
+ return
176
+ end
177
+
178
+ @swap_byte = @ram.peek(@expansion)
179
+ @swap_write_due = true
180
+ @last = READ
181
+ return swap_read_on_ba if ba_low
182
+
183
+ @ram.poke(@expansion, read_c64)
184
+ end
185
+
186
+ # A swap's read on the first BA-low cycle after a write, while AEC is
187
+ # still high. On the last byte the read is made there, the write
188
+ # follows on the next cycle whatever BA does, and the REC lets go.
189
+ # Otherwise the read stays open and takes what is on the bus two
190
+ # cycles later, or on the cycle BA rises if that comes first. Pinned
191
+ # by REU/reutiming2/e5-m2, f3-m2 and f4-m2.
192
+ def swap_read_on_ba
193
+ return @held_read = 2 unless @length == 1
194
+
195
+ @ram.poke(@expansion, read_c64)
196
+ @last = IDLE
197
+ @ba_low_after_writes = 0
198
+ end
199
+
200
+ # A swap's read that BA cut off from its write is made again when BA
201
+ # rises, and the write follows it. Pinned by REU/reutiming2/e4-m2,
202
+ # e6-m2 and g3-m2.
203
+ def read_swap_again
204
+ @swap_read_again = false
205
+ @ram.poke(@expansion, read_c64)
206
+ @last = READ
207
+ end
208
+
209
+ def settle_held_read(ba_low)
210
+ @held_read -= 1
211
+ return if @held_read.positive? && ba_low
212
+
213
+ @held_read = 0
214
+ @ram.poke(@expansion, read_c64)
215
+ end
216
+
217
+ # A difference ends the transfer, with one cycle more if bytes were
218
+ # left to compare.
219
+ def verify
220
+ same = @ram.peek(@expansion) == read_c64
221
+ step
222
+ @last = READ
223
+ return if same
224
+
225
+ @events |= FAULT
226
+ @extra_cycle = @length.positive?
227
+ @moved_all = true
228
+ end
229
+
230
+ # The REC reaches C64 memory as the CPU sees it, but at $00 and $01
231
+ # it reaches the RAM under the CPU's port.
232
+ def read_c64
233
+ @c64 < 0x02 ? @bus.ram.peek(@c64) : @bus.peek(@c64)
234
+ end
235
+
236
+ def write_c64(byte)
237
+ @c64 < 0x02 ? @bus.ram.poke(@c64, byte) : @bus.poke(@c64, byte)
238
+ end
239
+
240
+ # The REC counts the expansion address in its 19 low bits, from the
241
+ # top of its span back to 0, and leaves the bank bits above them as
242
+ # they were.
243
+ def step
244
+ @c64 = (@c64 + @c64_step) & 0xffff
245
+ low = (@expansion & 0x7ffff) + @expansion_step
246
+ @expansion = (@expansion & 0xf80000) | (low == @span ? 0 : low)
247
+ @length -= 1
248
+ @moved_all = true if @length.zero?
249
+ end
250
+
251
+ # The length register is left at 1 after a whole block. A fetch has
252
+ # already fetched the byte after its last into the latch.
253
+ def settle
254
+ return settle_verify if @type == VERIFY
255
+
256
+ @length += 1
257
+ @events |= END_OF_BLOCK
258
+ @ram.latch = @ram.peek(@expansion) if @type == FETCH
259
+ end
260
+
261
+ # A verify that compared every byte ends the block. One that found a
262
+ # difference on the byte before the last compares the last too, and
263
+ # ends the block if that one is the same.
264
+ def settle_verify
265
+ if @length.zero?
266
+ @length = 1
267
+ @events |= END_OF_BLOCK
268
+ elsif @length == 1 && @ram.peek(@expansion) == read_c64
269
+ @events |= END_OF_BLOCK
270
+ end
271
+ end
272
+ end
273
+ end
274
+ end
275
+ end
@@ -0,0 +1,109 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Badline
4
+ class C64
5
+ class REU
6
+ # The REU's DRAM, as the REC addresses it. The REC counts 19 address
7
+ # bits, 17 on the 1700, and the 1764 fills only the first 256K of
8
+ # them: past that a read finds the latch on the REU's data bus, which
9
+ # holds the last byte the REC moved. A unit past 512K takes its upper
10
+ # address lines from the bank register.
11
+ class RAM
12
+ BANK_SIZE = 0x10000
13
+
14
+ # Where a bank of a 1764 that has just been switched on reads
15
+ # inverted, over the first 128K of each 256K. Over the second 128K
16
+ # it is the rest of the bank that reads inverted. Measured from
17
+ # REU/raminitpattern/dumpfile-256k-x1541.bin, a real 1764's dump.
18
+ INVERTED = [0x2a00...0x5400, 0x8000...0xac00, 0xd600...0x10000].freeze
19
+
20
+ attr_reader :size
21
+ attr_accessor :latch
22
+
23
+ def initialize(size, span)
24
+ @size = size
25
+ @mask = (size > 0x80000 ? size : span) - 1
26
+ @banks = Array.new(size / BANK_SIZE) { [] }
27
+ @power_on = [[], []]
28
+ @latch = 0xff
29
+ end
30
+
31
+ def peek(addr)
32
+ addr &= @mask
33
+ addr < @size ? bank(addr >> 16)[addr & 0xffff] : @latch
34
+ end
35
+
36
+ def poke(addr, value)
37
+ addr &= @mask
38
+ bank(addr >> 16)[addr & 0xffff] = value if addr < @size
39
+ end
40
+
41
+ # The latch, and each 64K bank the REC has touched. A bank it hasn't
42
+ # keeps its power-on contents until it does.
43
+ def save_state(out)
44
+ out.int(@latch)
45
+ @banks.each do |bank|
46
+ out.boolean(!bank.empty?)
47
+ out.blob(bank) unless bank.empty?
48
+ end
49
+ end
50
+
51
+ def load_state(input)
52
+ @latch = input.int
53
+ @banks.each_index { |number| @banks[number] = input.boolean? ? input.blob : [] }
54
+ end
55
+
56
+ # Every byte, as one string, with a bank the REC hasn't touched at
57
+ # its power-on contents.
58
+ def contents
59
+ power_on = power_on_strings
60
+ Array.new(@banks.length) do |number|
61
+ bank = @banks[number]
62
+ bank.empty? ? power_on[(number >> 1) & 1] : bank.pack("C*")
63
+ end.join
64
+ end
65
+
66
+ # Takes every byte from a string as long as the RAM. A bank that
67
+ # holds its power-on contents stays untouched.
68
+ def restore(bytes)
69
+ power_on = power_on_strings
70
+ @banks.each_index do |number|
71
+ slice = bytes.byteslice(number * BANK_SIZE, BANK_SIZE).to_s
72
+ @banks[number] = slice == power_on[(number >> 1) & 1] ? [] : slice.bytes
73
+ end
74
+ end
75
+
76
+ private
77
+
78
+ def power_on_strings
79
+ [0, 1].map do |half|
80
+ @power_on[half] = power_on_bank(half == 1) if @power_on[half].empty?
81
+ @power_on[half].pack("C*")
82
+ end
83
+ end
84
+
85
+ # A bank takes its power-on contents the first time it is touched,
86
+ # so an REU costs only the memory a program uses.
87
+ def bank(number)
88
+ bank = @banks[number]
89
+ return bank unless bank.empty?
90
+
91
+ half = (number >> 1) & 1
92
+ @power_on[half] = power_on_bank(half == 1) if @power_on[half].empty?
93
+ @banks[number] = @power_on[half].dup
94
+ end
95
+
96
+ # Pairs of $FF and $00 bytes, starting with a single $FF, and each
97
+ # odd page the inverse of the even one before it.
98
+ def power_on_bank(upper)
99
+ Array.new(BANK_SIZE) do |offset|
100
+ byte = (offset + 1).anybits?(2) ? 0x00 : 0xff
101
+ byte ^= 0xff if offset.anybits?(0x100)
102
+ inverted = INVERTED.any? { |range| range.cover?(offset) }
103
+ inverted == upper ? byte : byte ^ 0xff
104
+ end
105
+ end
106
+ end
107
+ end
108
+ end
109
+ end
@@ -0,0 +1,55 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Badline
4
+ class C64
5
+ class REU
6
+ # The REU's state for a snapshot: the REC's registers and the values
7
+ # its counters start from, an armed or running transfer, the IRQ line,
8
+ # the transfer's own state and the RAM. The size is the machine's
9
+ # setup (Snapshot::C64Setup), so a restore finds an REU of the same size.
10
+ module SavedState
11
+ def size_kb = @size_kb
12
+
13
+ def save_state(out)
14
+ out.marker("REU")
15
+ [@status, @command, @c64, @c64_start, @expansion, @expansion_start, @bank, @bank_start, @length,
16
+ @length_start, @interrupt_mask, @address_control].each { |value| out.int(value) }
17
+ out.boolean(@armed).boolean(@requested).boolean(@running).boolean(@irq).boolean(@ba_was_low)
18
+ @dma.save_state(out)
19
+ @ram.save_state(out)
20
+ end
21
+
22
+ # The IRQ line comes back as it was without calling back into the
23
+ # machine, which reads it again afterwards.
24
+ def load_state(input)
25
+ input.marker("REU")
26
+ load_registers(input)
27
+ @armed = input.boolean?
28
+ @requested = input.boolean?
29
+ @running = input.boolean?
30
+ @irq = input.boolean?
31
+ @ba_was_low = input.boolean?
32
+ @dma.load_state(input)
33
+ @ram.load_state(input)
34
+ end
35
+
36
+ private
37
+
38
+ def load_registers(input)
39
+ @status = input.int
40
+ @command = input.int
41
+ @c64 = input.int
42
+ @c64_start = input.int
43
+ @expansion = input.int
44
+ @expansion_start = input.int
45
+ @bank = input.int
46
+ @bank_start = input.int
47
+ @length = input.int
48
+ @length_start = input.int
49
+ @interrupt_mask = input.int
50
+ @address_control = input.int
51
+ end
52
+ end
53
+ end
54
+ end
55
+ end
@@ -0,0 +1,34 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Badline
4
+ class C64
5
+ class REU
6
+ # Stands in for the page at $FF00 in the write table, passing each
7
+ # write on to what is mapped there and telling the REC when $FF00 is
8
+ # written, which starts an armed transfer.
9
+ class Trigger
10
+ ADDRESS = 0xff00
11
+
12
+ def initialize(reu)
13
+ @reu = reu
14
+ @target = nil
15
+ end
16
+
17
+ # Puts the trigger in front of target and returns it.
18
+ def wrap(target)
19
+ @target = target
20
+ self
21
+ end
22
+
23
+ def peek(addr)
24
+ @target.peek(addr)
25
+ end
26
+
27
+ def poke(addr, value)
28
+ @target.poke(addr, value)
29
+ @reu.ff00_written if addr == ADDRESS
30
+ end
31
+ end
32
+ end
33
+ end
34
+ end