May 30th, 2010, 23:05 Posted By: wraggster
Pate has posted more news of his WIP Dos Emulator for the Nintendo DS:
Firstly, in case you haven't noticed this yet, DSx86 now has a Compatibility WIKI page where each of you can mark games that work or don't work on the current DSx86 version. Special thanks to Master_Thief for setting up that wiki page and for testing the majority of games on it! With the wiki in place there is no need for you to report working games to me any more. :-) Please send me bug reports about games that don't work, though, especially with a debug log if applicable, so that I can attempt to fix the problems before releasing the next version.
The past week was mainly spent fixing various bugs in the emulation code. I also added several missing (mainly graphics) opcodes that have been mentioned in the debug logs I have received, thanks again for those! The biggest (and scariest) change was that I rewrote the IRQ handling (again!) to fix a problem that was revealed by a game called Galactix.
The problem in Galactix was that it usually only played the first note of the game music, and then later it would hang at a random time during the intro. I had noticed that when it did hang, it was always running a tight loop that checked whether a certain memory location had a zero. It obviously expected this memory location to change value (based on a timer, most likely), but when it had hung the memory location value never changed. After some debugging and tracing the memory access I got a pretty clear understanding of the timer handling behaviour of Galactix, and after some thought I suddenly got an idea (or rather a theory) about what might be wrong in DSx86.
Galactix uses a "Task Service Manager" (that is part of an error string very close to the memory location it checked, so I believe that is the name of the utility code that handles the timer interrupt in the game) which works by incrementing a variable every time a timer interrupt occurs, and then calling various functions in a function pointer table, each of which have their own incrementing variables, with adders that are not always one. For example, one of the functions might only get called every tenth timer interrupt. Now, the main timer interrupt increments the overall timer interrupt counter at the very start of the timer interrupt, and then each of these functions test if their counters are equal to the global counter value, and if they are, this functions get called and gets it's counter incremented by the adder value, to be ready for the next call etc.
Every time I use something similar in my own code, I have a habit of checking whether the counter value is equal or larger than the value I am waiting for, just to be sure I don't miss a timer increment. This then brings us to my theory, I thought that perhaps some of those functions take such a long time to run that a new timer interrupt happens and starts again running the timer code, first incrementing the global counter. In this situation it would be possible for the functions to miss their next timer tick, and stay waiting for it for the next (almost) 65536 timer ticks.
I decided to implement a new feature to the DSx86 debugger with which you can change the byte in the memory using a syntax E AAAA:BBBB CC where AAAA:BBBB is the segment and offset of the byte and CC is the new byte value. I used this new debugger feature to change the JE opcode to JAE opcode in Galactix, and indeed, after this change the music played fine and the intro did not crash. (Well, not immediately, it crashed after a couple of loops, but that was not unexpected as the IRQ handlers are not meant to be re-entrant.) This test did prove my theory that I did not handle the "End-Of-Interrupt" command properly, but instead allow new interrupts to re-enter the interrupt routine.
So, I spent some time implementing proper IRQ handling to avoid this situation in the DSx86 IRQ code, and I also (finally) moved all the interrupt-related stuff to a new source code file. Now it is not scattered around the emulator code but in a single place, so if I still need to make changes to it, it will be easier (and not as scary!). After this rewritten IRQ handling Galactix looks to be running fine.
I also fixed the graphics problems in Catacomb Abyss. I had not implemented the split screen handling in the EGA modes, only in the Mode-X graphics modes, and Catacomb Abyss wanted to use a split screen for the low part of the screen. I also found a problem in the EGA Write Mode 2 handling with 16-bit opcodes. After these fixes Catacomb Abyss began to look correct. Also, the LOADFIX command I added into the previous version only worked with EXE programs (silly me), which is why it did not help with Ultima 4, for example. I implemented it also for COM programs and now Ultima 4 goes to the actual game properly.
Finally, I managed to fix the problems preventing the Sysinfo program from Norton Utilities 8.0 to start. I had used Sysinfo 5.0 in my own tests, which did not need some of the additional DOS functions that Sysinfo 8.0 needed. In the next version Sysinfo 8.0 will also run. The picture below is actually here so you can see why I don't plan to support 386/486 opcodes with DSx86. :-) There is not much point when the games will run that slowly. Well, I might support some of the 386 opcodes that can "accidentally" be left in the 286 programs, like long conditional jumps, but I won't add support for 32-bit registers, for example.
I have recently been using the iDeaS emulator to test DSx86 on my PC, with the R4 DLDI patch so I can actually run the DOS games in it. The emulator is pretty slow, but I have now learned to use it's debugger so it has helped me in debugging the problems in DSx86. It does have some bugs, though, which I have reported to the author. Hopefully the next version will run better.
Finally, in case you are interested (and even if you aren't :-), here is a picture of the access statistics for my DSx86 pages. Quite a steady increase of visits, and as I have a 15GB monthly bandwidth limit by my web provider, I soon need to start keeping an eye on the bandwidth, and then perhaps start zipping the files hosted here if the limit starts approaching. Looking at the logs is of course one motivation boost to keep working on DSx86, it is nice to see how more and more people find DSx86 interesting. :-)
For more information and downloads, click here!
There are 0 comments - Join In and Discuss Here