Haskell For Games!

I've been head-down in a big stack of papers since around March this year. That was the point at which I first started to get excited about the idea of Haskell becoming a plausible language for use in games development. More recently I decided to start doing something about it and gave a talk to a group of dedicated Haskellers at AngloHaskell 2009. The event turned out to be a lot of fun and I think it's safe to say the talk went pretty well. Here's the abstract.

Functional Languages in Games: Plotting the Coup

[Slides as PDF]

As a games developer by trade, my experience of the industry leads me to suspect games development is approaching a tipping point where functional languages could enact a successful coup. The revolution would claim a chunk of C++-owned territory for the victor and mark an important milestone in the development of functional languages. It will not be easy. Games development is notoriously demanding and the successful functional language would need to meet stringent performance requirements, have clearly demonstrable 'killer apps', jump through hoops of fire and tell jokes at parties. This talk will discuss how close Haskell is to meeting these demands, the challenges that remain, evidence of functional languages already in games, and how Haskell compares against its nearest competitors.

Haskell For Games!

At first glance it sounds like a crazy idea. One to file away with the other crazy ideas to replace C++ with Java/C#/Python/etc. Most alternatives to C++ are so unlikely to succeed in practice that they appear to taint the very idea of replacing C++. I've written before about my high regard for C++,  but as powerful and effective as it is for games development, it does not represent an impossible challenge and we don't have to look to replace it entirely. Finding it a suitable companion would be a major step forward and is the goal I'd choose to focus on.

Multi-core

There are powerful currents moving in modern computer hardware, pulling us inevitably into murky multi-core waters. However this movement also begins to make the idea of doing games development in an alternative language more plausible. What do we do when large multi-core systems become a standard hardware platform? (A reality that I note is only a handful of years away.) I have yet to see a parallelisation option that don't make me think life in this new age in C++ will be rather hard. And would it be any easier in C# or Java? No. Multi-core life there will likely be just as tough. However, these aren't the only options.

Functional languages

I'm far from the first to notice this, but pure functional languages - as opposed to the imperative languages most of us are used to - do at least have a theoretical advantage. Pure functional code does not have side effects. If you call it with the same parameters you will always get the same answer. It is thread-safe at a fundamental level giving opportunities for optimisation and parallel evaluation that are either infeasible or impossible with imperative code. They aren't so alien as you may immediately think. You may well already work with such a language without really realising it. Ignoring some syntactical obfuscations, both CG and HLSL are essentially pure, referentially transparent languages. Neither language can wipe your hardrive or save state in global variables, and it's no coincidence that they both optimise exceptionally well.

As you can well imagine, this is not an open-and-shut success case. Achieving good parallelism, even from a functional starting point, is still hard. In the previous example of CG/HLSL, the hard parallelism work is still done by the programmer by setting up the GPU pipeline, rather than magically derived from the CG/HLSL. Doing complicated, dependent operations in a GPU architecture is tricky and the subject of many GPGPU articles, although to be fair many of these obstacles are due to the current GPU architecture than the more fundamental issues in utilising parallelism.

Achieving parallel code that includes grubby details like nesting and runtime data dependencies are hard problems. But in the long term I think it's more plausible to turn these problems into successes in functional languages than anywhere else. Compiler-parallelised code, even if partly programmer controlled, would be a Killer App for any alternative language, and one feature that C++ is unlikely to ever have. Without this feature, there are many other benefits for games development to adopt a functional sister-language, but the cost of doing so may cancel out the cost of the adoption.

Multi-core Haskell

I'm championing Haskell from the functional language pack for a variety of reasons, several of which are noted briefly in my talk and the rest I'll expand on further in the future. I hope many of the benefits of Haskell will be apparent to anyone prepared to spend the time learning it, and I'd urge anyone interested to get stuck in immediately. There are several decent tutorials referenced from the Haskell Wiki, and I can highly recommend, "Learn You A Haskell For Great Good!", as a great starting point. One other very notable highlight is the on-going research into extending the language to support Nested Data Parallelism. Although not complete, this research does look very promising and where I'm hoping some of the magic may take place.

Haskell for Games is by no means a done deal, but my enthusiasm for this project has at least withstood it's first challenge - presenting these ideas to members of the Haskell community - and if anything has grown as a result.


Comments

  1. Quote

    Great talk & post Sam!

  2. Quote
    Artyom Shalkhakov said 12 August, 2009, 2:49 am:

    Very interesting, but a lot of hand-waving. :)

    I suppose that more practical solution would be to adopt a language like ATS, which allows one to work on a very low level but still maintaining safety (you can statically guarantee termination if you wish, for example -- not that you'd want to :) and you can get rid of any "free freed memory" errors, etc.). It has many interesting features regarding it's type system (that is far more expressive than Haskell's).

    Haskell OTOH is so beautiful. :)

  3. Quote

    In case you haven't seen the related work in this area. Something like the Jane Street Summer of Code project?

    * LambdaCube - Haskell: Lambda Cube 3D Engine, http://www.haskell.org/haskellwiki/LambdaCubeEngine

    * hpysics. http://www.youtube.com/watch?v=uziCn2SBbxs - the Google SoC project using data parallelism for a physics engine

    Just demos of using a) reactive programming, and b) data parallelism, to write game engines. Proof of concept stuff.

  4. Quote

    @Artyom I haven't spent much time looking at ATS yet, but it does look interesting. Thanks.

    @dons Thanks, I haven't see either before. I'll check them out.

    I'm still reading through most of the FRP material online. It appears to be well suited to modelling mixed discrete/continuous systems, such as real world robots, but I'm not yet sure that this translates very well to games or graphics in practice. Games are really quite discrete systems at heart. The concept of a frame is fairly deeply embedded, and I'm not sure if the FRP style of doing thing would obfuscate this.

    Conal Elliotts ideas for how to apply it to rendering were interesting though.

  5. Quote

    I've been trying to push Haskell games forward a little lately: http://hackage.haskell.org/package/boomslang

  6. Quote

    I’m still reading through most of the FRP material online. It appears to be well suited to modelling mixed discrete/continuous systems, such as real world robots, but I’m not yet sure that this translates very well to games or graphics in practice. Games are really quite discrete systems at heart. The concept of a frame is fairly deeply embedded, and I’m not sure if the FRP style of doing thing would obfuscate this.

    Yes, FRP intentionally obfuscates the discrete nature of typical game implementations. Or put differently, the intent that led to FRP is to unobfuscate the essence of the interactive behavior that typically gets implemented discretely (and imperatively) in applications like games.

    A question to meditate over: Are games purely discrete systems at heart? Or maybe are programmers so in the habit of implementing games in a purely discrete fashion that we've come to think of games as being purely discrete at heart?

  7. Quote
    Mbrodersen said 14 April, 2012, 7:55 pm:

    I am currently working on a game written in Haskell with a bit of C++ to deal with DirectX. With more than 15 years of experience in game development behind me I can clearly say that using C++ to write all of your game code is just crazy. C++ is excellent for low level manipulation of vertices etc. but it is not even close to being the most productive anguage when it comes to the more important code: the actual game. I have seriously looked at many languages to use instead of C++ for the non-vertex fiddle code including Java, C#, Clojure, Common lisp, Scheme, Scala, Standard ML, Ruby and Haskell. Haskell and ML were the clear winners. The productivity speed of those two languages compared with C++ just blew me away. And the speed was impressive too. Haskell is about 50% of C++ speed running REAL game code including path finding etc. Which is dramatically faster than LUA and other known game programming languages. However learning Haskell if you are a traditional C++ developer is HARD. You have to unlearn years of bad habits while expanding your understanding of how to write solid code. But it is absolutely worth it. It is like upgrading from being an average Army soldier to joining the Navy Seals. Hard work but worth it if you can.

  8. Quote
    Mbrodersen said 14 April, 2012, 8:01 pm:

    Oh by the way: I am not using FRP in my game. Writing games using "normal" Haskell is easy enough already. I find FRP to be too "academic" for practical usage: great for getting papers published but not a great choice for coding real games.

Leave a Comment

(required)

(required)

Formatting Your Comment

The following XHTML tags are available for use:

<a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>

URLs are automatically converted to hyperlinks.