Save file fixes, more games booting, and a better Android frontend!

What a month! Thank you all so much for the heartwarming words and support. Mikage's website had around 20k unique visits, there have been lots of videos and blog articles on the project (including one on wololo), and we had a strong start with our Patreon page bringing in more than $400 in its first month.

All this positive reception has been very promising, and I'm excited to see how the next months turn out! Now without further ado, let's talk about what I've been up to in July.

Fix graphics on Mali GPUs

Mikage hadn't really received a lot of user-testing before its announcement: I merely tested three devices, all of which run Qualcomm GPUs, so it was no surprise my first patrons quickly reported issues with Mali-based phones.

Luckily, and thanks to the kind help of some members of our Discord server lent me a hand in testing, I was able to narrow down the issue to the memory management logic in Mikage's Vulkan code. Fixing this wasn't a big deal, so I was able to release a followup release working with both Qualcomm and Mali GPUs only three days after the original release.

What a shame: Mali users would see a blank screen with Mikage's initial release. Luckily, one fix later everything works just fine!

Fix corner case in DMA transfers

When trying to boot Super Mario 3D Land, the user would be greeted by an error message box about an implemented corner case in SVCStartInterprocessDMA. Implementing this wasn't too hard, so I took the chance to clean up and future-proof the code a little so similar errors won't be hunting us too soon.

Believe it or not, this little fix and some stubbing work in the MIC module were actually enough to get the game to reach its title screen!

Another game reaches the title screen!

Implement ExtData

ExtData is the name for a mechanism using which the 3DS stores game-specific data, separate from the save data created by the game. On a technical level, ExtData and SaveData are very similar but emulating ExtData requires a few specific tweaks for accurate emulation. Luckily, Mikage features an extensive test suite using which the differences between the two mechanisms were easily identified, and as such implementing ExtData in the code wasn't too much trouble either.

This feature was a major blocker that prevented a lot of games from booting very early on. I'm glad it's finally out of the way, and it already paid off: Bravely Default now boots and even creates save data!

Thanks to the ExtData implementation, Bravely Default now boots!

Fix various save file issues

While working on the tests for ExtData, I also found a minor issue in the SaveData implementation. When a game boots for the first time, Mikage implicitly created save data but instead it should have returned a "SaveData is not formatted" error to the application, so that the game can set up the save data itself instead.

This makes the "Creating save file data" texts show up on Ocarina of Time 3D, which previously would silently omit this information. While the game never had any trouble creating the save file, it's cool to see this work as intended now.

Yay for accuracy: OoT now tells us what's up

In other news, erasing the game's save files wasn't supported since I hadn't actually implemented DeleteFile. This wasn't by accident: A broken implementation could accidentally delete sensitive user data! To prevent such unintended side effects, I shipped the first alpha release without any deletion support. I'm now confident that the path validation in DeleteFile is correct and robust, so the August release will finally allow you to delete your ingame saves. You know, just in case you wanted to sit through those lengthy intro cutscenes again ;)

Android User Experience

A lot of people liked the look'n feel of the app, but early adopters will be able to confirm it could be somewhat rough to use at times.

This starts with actually loading games: Due to Android's Content Provider system, it could become difficult for Mikage to find games in the user-selected folders. Loading content from external SD cards was outright not supported. Once you managed to tell Mikage where your games are, it would sometimes fail to show you their thumbnails.

And as you've seen in the screenshots at the top, upon starting a game you would be greeted with a botton overlay that was squeezed together on the left side on most displays. That's okay for a quick try, but not if you want to do anything interesting.

I knew about these issues when I announced the project, but I felt it was more important to get the word out in the open than provide a perfectly polished experience from day 1. Nevertheless, it is one of the declared project goals to have a user interface that is both pleasant and intuitive to use, so fixing these rough edges had high priority to me.

Luckily, starting with the August release users won't need to worry about these quirks anymore. Loading your games from any storage location works just fine now, and the button overlay position dynamically adapts to your display size!

What's next?

The next Patreon-exclusive alpha release is scheduled for 11 August, featuring all of the improvements outlined above. Of course, my job isn't done; here's a couple of things I want to do in August:

Improve the ResourceManager cache for Vulkan render targets: This will fix a couple of issues such as the green water in OoT 3D and the flickering graphics in Cubic Ninja, and it also turned out to be a blocker for getting some games to boot

Implement Shared Font functionality: This is another commonly feature, and I want to implement the shared font at least to the point we can get the games that need it booting properly

Open-source blobify, a utility library used in Mikage to handle binary serialization. This will be interesting for programmers, and should serve as a reaffirmation of my intent to open-source Mikage eventually

As usual, if you want to support Mikage's development to get the official release ready as soon as possible, becoming a member on Patreon is the best way of doing so.

Once again, thanks for all of your support!

This post was originally released to Patreon members on 28 July