Happy New Year 2017 Roundup – CHIP-8, Rust, and more

Lately, I’ve been more interested in learning about emulators and interpreters, down to the way that CPUs work at a low level. In university, the furthest down we got was C++ and we didn’t spend that much time there, so everything under that has always felt a little like black magic to me. To overcome that, I took a look into what it would take to write a toy emulator.

After briefly considering an NES emulator as my first project, I discovered the CHIP-8 VM and decided that would make a really neat first project. There are lots of resources for the CHIP-8 and it’s also a simple implementation, which means it can be done over a weekend or even faster.

I decided to write the emulator using Rust, a systems programming language that I’ve been dabbling in on and off whenever I feel like taking a break from Java. In the past, I would have dabbled in C or C++ but as time goes by, I feel that it makes more sense to focus on Rust.

Why?

Like C and C++, Rust compiles down to native code and runs without the overhead of a VM while also giving you full access to the platform underneath. Unlike C and C++, it also has some nice features that make it feel modern and fresh, like memory safety without garbage collection, super-charged enums, and a great build system that has built-in support for dependencies, unit testing, and more.

In fact, the only real beef I have with Rust is that it’s still young, so its support for mobile development is not quite up to par with the C and C++ support provided by Apple and Google. I’m sure this will improve with time. (After spending some time with Swift, I would also wish for no semicolons and maybe nicer optional unwrapping, but, at least with the semicolons, that ship has probably already sailed. :))

By writing the interpreter in Rust and taking advantage of the unit test features, it was very easy to build up the CHIP-8 VM, and I only ended up with a couple of pesky logic bugs due to being unsure about the implementation in a couple of places and due to a misuse of the slicing syntax.

Once I was done with the Rust implementation, I just copy-pasted the whole thing into Javascript, which you can check out at the end of this post. The code is available on GitHub, and here are a couple of other implementations you can also check out:

Kotlin CHIP-8 (badlogic) (Let’s write a Chip8 emulator in Kotlin)
Rust CHIP-8 (Notch)

I would also recommend checking out nand2tetris, a really interesting course which teaches you how to build your own toy CPU from NAND gates. The course can be audited for free on Coursera.

In the future, instead of copy/pasting to JS, I might be able to just compile straight to WebAssembly:

Compiling Rust to your Browser
Compiling Rust to WebAssembly Guide

I really like where Rust is going and hope to see a lot more progress in 2017. Happy New Year, and here’s to a great 2017 for all. 🙂

Site Updates, and Thoughts on Native Development for the Web

I’ve recently been spending time travelling overseas, taking a bit of a break after reaching an important milestone with the book, and also taking a bit of a rest from working for myself! The trip has been good so far, and I’ve even been keeping up to date with items from the RSS feed. Here is some of the news that I wanted to share with y’all, as well as to get your thoughts:

Book nearing production

OpenGL ES for Android: A Quick-Start Guide reached its final beta a couple of weeks ago, and is now being readied to be sent off to the printers. I would like to thank everyone again for their feedback and support; I am so grateful for it, and happy that the book is now going out the door. I’d also like to give a special thanks to Mario Zechner, the creator behind libgdx and Beginning Android Games, for generously contributing his foreword and a lot of valuable feedback!

Site news

Not too long ago, I decided to add a new forums section to the site to hopefully build up some more community involvement and get a two-way dialogue going; unfortunately, things didn’t quite take off. The forums have also suffered from spam and some technical issues, and recently I was even locked out of the forum administration. I have no idea what happened or how to fix it, so since the posting rate was low, I am just putting the forums on ice for now.

I’d still love to find a way to have some more discussions happening on the site. In which other ways do you believe that I could improve the site so that I could encourage this? I’d love to hear your thoughts.

Topics to explore further

I’ve also been thinking about new topics to explore and write about, as a lot of exciting things are happening with 3D on the mobile and web. One big trend that seems to be taking place: Native is making a comeback.

For many years,  C and C++ were proclaimed to be dead languages, lingering around only for legacy reasons, and soon to be replaced by the glorious world of managed languages. Having started out my own development career in Java, I can agree that the Java world does have a lot of advantages. The language is easier to learn than a behemoth like C++, and, at least on the desktop, the performance on the JVM can even come close to rivalling native languages.

So, why the resurgence in C and C++? Here are some of my thoughts:

  • The world is not just limited to the desktop anymore, and there are more important platforms to target than ever before. C and C++ excel at cross-platform portability, as just about every platform has a C/C++ compiler. By contrast, the JVM and .NET runtimes are limited to certain platforms, and Android’s Dalvik VM is not as good as the JVM in producing fast, efficient JIT compiled code. Yes, there are bytecode translators and commercial alternatives such as Xamarin’s Mono platforms for mobile, but this comes with its own set of disadvantages.
  • Resource usage can be more important than programmer productivity. This is true in big, expensive data centers, and it’s also true on mobile, where smaller downloads and lower battery usage can lead to happier customers.
  • C and C++ are still king when it comes to fast, efficient compiled code that can be compiled almost anywhere. Other native would-be competitors lose out because they are either not as fast or not as widely available on the different platforms. When productivity becomes more important than performance, these alternatives also get squeezed out by the managed and scripting languages.

As much as C and C++ excel at the things they’re good at, they also come with a lot of legacy cruft. C++ is a huge language, and it gets larger with each new standard. On the other hand, at least the compilers give you some freedom. Don’t want to use the STL? Roll out your own custom containers. Don’t want the cost/limitations of exception handling and RTTI? Compile with -fno-exceptions and -fno-rtti. Undefined behavior is another nasty issue which can rear its head, though compilers like Clang now feature additional tools to help catch and fix these errors. With data-oriented design and sensible error handling, C++ code can be both fast and maintainable.

Compiling C and C++ to the web

With tools like emscripten, you can now compile your C/C++ code to JavaScript and run it in a browser, and if you use the asm.js subset, it can actually run with very good performance, enough to run a modern 3D game using JavaScript and WebGL. I’ve always been skeptical of the whole “JavaScript everywhere” meme, because how can the web truly become an open computing platform by forcing the use of one language for everything? There’s no way a single language can be equally suitable for all tasks, and why would I want to develop a second code base just for the web? For this reason, I used to believe that Google’s Native Client held more promise, since it can run native code with almost no speed loss. Why use JavaScript when you can just execute directly on the CPU and bring your existing code over?

Now I see things a bit differently and I think that the asm.js approach has a lot of merit to it. NaCl has been around for years now, and it still only runs in Google Chrome, and then only on certain platforms and only if the software is distributed through the Chrome store, or if the user enables a developer flag. The asm.js approach, on the other end, can run on every browser that supports modern JavaScript. This approach is also portable, meaning it will work into the foreseeable future, even on new device architectures. NaCl, on the other hand, is limited to what was compiled. Portable NaCl is supposed to fix this, but it’s been a work-in-progress for years now, and given the experience with NaCl, it may never find its way to another browser besides Google Chrome. Combined with WebGL, compiling to JavaScript really opens up the web to a lot of new possibilities, one where you can deploy across the web without being tied to a single browser or plugin. The BananaBread demo shows just some of what is possible.

I’d like to learn more about writing OpenGL apps that can run on Android, iOS, and the web, all with a single code base in C++. I know that this is also possible with Java by using Google’s Web Toolkit and bytecode translators (after all, this is how libgdx does it), but I’d like to learn something different, outside of the Java sphere. Is this something that you guys would be interested in reading more of? This is all relatively new to me and I’m currently exploring, so as always, looking forward to your feedback. 🙂

Update: I am now developing an air hockey project here: Developing a Simple Game of Air Hockey Using C++ and OpenGL ES 2 for Android, iOS, and the Web