Live data from Hacker News

Why I Write Games in C (yes, C)

jonathanwhiting.com

241–250 of 556 posts

Re: Why I Write Games in C (yes, C)

#241
post #46

> The stop-the-world garbage collection is a big pain for games, stopping the world is something you can't really afford to do. I love this opinion from games programmers because they never qualify it and talk about what their latency budgets are and what they do in lieu of a garbage collector. They just hand wave and say "GC can't work". The reality is you still have to free resources, so it's not like the garbage c…

Disclaimer: I'm not a game developer; but, I've worked on a lot of projects with tight frame time requirements in my time at Netflix on the TVUI team. I also have no experience in Go so I can't comment on the specifics of that garbage collector vs. V8. I don't think it's necessarily that it "can't" work as much as it takes away a critical element of control from the game developers and the times you find yourself "at…

> it was generally non-deterministic

This is basically it. People who have never worked on actual real-time systems just never seem to get that in those environments determinism often matters more than raw performance. I don't know about "soft" real-time (e.g. games, or audio/video) but in "hard" real-time (e.g. avionics, industrial control) it's pretty routine to do things like disable caches and take a huge performance hit for the sake of determinism. If you can run 10% faster but miss deadlines 0.1% more often, that's a fail. It's too easy for tyros to say pauses don't matter. In many environments they do.

Re: Why I Write Games in C (yes, C)

#242
post #46

> The stop-the-world garbage collection is a big pain for games, stopping the world is something you can't really afford to do. I love this opinion from games programmers because they never qualify it and talk about what their latency budgets are and what they do in lieu of a garbage collector. They just hand wave and say "GC can't work". The reality is you still have to free resources, so it's not like the garbage c…

> The reality is you still have to free resources, so it's not like the garbage collector is doing work that doesn't need to be done.

As others have pointed out, this isn't true for many video games. People write things so they're allocated upfront as much as possible and reuse the memory. A lot of old games had fixed addresses for everything as they used all available memory (this allowed for things like Gameshark cheats).

But there's a secondary issue. A GC imposes costs for the memory you never free. It doesn't know the data will never be freed, so it'll periodically check to see if the data is still reachable. Some applications have work arounds for this like using array offsets instead of pointers/references (fewer pointers to follow).

Re: Why I Write Games in C (yes, C)

#243
post #46

> The stop-the-world garbage collection is a big pain for games, stopping the world is something you can't really afford to do. I love this opinion from games programmers because they never qualify it and talk about what their latency budgets are and what they do in lieu of a garbage collector. They just hand wave and say "GC can't work". The reality is you still have to free resources, so it's not like the garbage c…

Could you maybe phrase this in a less snarky and condescending tone? It's a great comment if you take out only the first two sentences.

Re: Why I Write Games in C (yes, C)

#244

Earlier quoted context omitted.

That's not entirely true. If you only rely on RAII you may end up with millions of shared pointers, each of which needs to be managed independently and having its own overhead. They may also be independently allocated, which means they will be fragmented in memory. Not so simple.

I think it’s safe to say for the general case that if you have millions of widely-shared smart pointers you are not following RAII principles. At that point you are left with poorly-implemented reference counting, with a ton of synchronization overhead.

[deleted]

Re: Why I Write Games in C (yes, C)

#245

Earlier quoted context omitted.

That's not entirely true. If you only rely on RAII you may end up with millions of shared pointers, each of which needs to be managed independently and having its own overhead. They may also be independently allocated, which means they will be fragmented in memory. Not so simple.

I think it’s safe to say for the general case that if you have millions of widely-shared smart pointers you are not following RAII principles. At that point you are left with poorly-implemented reference counting, with a ton of synchronization overhead.

Which RAII principle would you say would be broken in this scenario?

Re: Why I Write Games in C (yes, C)

#246
> The strongest thing on my desired, but not required list is simplicity. I find looking up language features, and quirky 'clever' api's incredibly tiring.

Indeed. Clever apis are a disease endemic to the JavaScript community. expect(me).to.puke.when(i.see.shit.like.this());

> The ideal language would be one I can memorize, and then never have to look things up.

You can't memorize C. The idea that you can "hold C in your head" is a myth, and propaganda repeated by C pushers. In reality, the gotchas surrounding undefined behavior are so numerous and subtle that you're much better off using something else, even if it means accepting the complexity that is C++. (In reality, what you want is a language such as Rust that has well-defined behavior.)

> I need a platform that I am confident will be around for a while.

Don't get your hopes up. The closest we've had is POSIX, but POSIX is showing its age, and in the modern era churn is the rule, rather than the exception. More than a decade old? Rewrite it! New framework came out? Rewrite it! Developer fell in love with some flashy new technique? Rewrite it! Not enough nonbinary PoCs on the dev team? Rewrite it!

Re: Why I Write Games in C (yes, C)

#247
post #46

> The stop-the-world garbage collection is a big pain for games, stopping the world is something you can't really afford to do. I love this opinion from games programmers because they never qualify it and talk about what their latency budgets are and what they do in lieu of a garbage collector. They just hand wave and say "GC can't work". The reality is you still have to free resources, so it's not like the garbage c…

I know this subject quite well and I will later publish a detailed article. The real run-time cost of memory management done well in a modern game engine written without OOP features is extremely low. We usually use a few very simple specialized memory allocators, you'd probably be surprised by how simple memory management can be. The trick is to not use the same allocator when the lifetime is different. Some resourc…

This is exactly what's continually drawing me to Zig for this sort of thing. Any function that requires memory allocation has to either create a new allocator for itself or explicitly accept an existing one as an argument, which seems to make it a lot easier/clearer to manage multiple allocators for this exact use case.

Re: Why I Write Games in C (yes, C)

#248

> [C++] is high performance, and it offers but features I don't want, and at a great complexity cost. 1. Complexity of implementation is not complexity of use. Example: Take std::array vs a plain C array. std::array is a few hundreds of lines of code. But - it's about as inutitive to use; has more convenience features; easier for the compiler to optimize; and doesn't let you should yourself in the foot that easily. 2…

Some people just like writing code. You can't say that C's features are insufficient, when you can implement the vast majority of C++ features in native C, and all of 'em with tooling. What's wrong with having direct control of only the features you need? What's wrong with code generation? Not to trample on C++, I like it (albeit less than C). I would definitely create C++ if it didn't exist.

> when you can implement the vast majority of C++ features in native C

No, you absolutely cannot, even in principle. C++ is not "C with classes" and some syntactic sugar like it started out. That's not been the case for many years already.

Also, even the features you can implement - you won't; you don't have the person-years for that. You will have to, need to, use libraries. For those you need to compare the libraries available for C and for C++, and C comes up quite short (not just because C libraries are also usable in C++...)

Re: Why I Write Games in C (yes, C)

#249
post #98

Earlier quoted context omitted.

I know this subject quite well and I will later publish a detailed article. The real run-time cost of memory management done well in a modern game engine written without OOP features is extremely low. We usually use a few very simple specialized memory allocators, you'd probably be surprised by how simple memory management can be. The trick is to not use the same allocator when the lifetime is different. Some resourc…

as an example point, the Go garbage collector clears heaps of 18gb in sub-millisecond latencies. If I'm understanding the problem at hand (maybe I'm not!), given an engine running at a target framerate of 144 frames per second, you're working with a latency budget of about 7ms per frame. Do you always use all 7ms, or do you sometimes sleep or spin until the next frame to await user input? We can also look at it from…

> as an example point, the Go garbage collector clears heaps of 18gb in sub-millisecond latencies.

The trick here is to double the heap size, which would be completely unacceptable for a game that's making use of what the hardware offers.

Re: Why I Write Games in C (yes, C)

#250

I’m not sure why but programmers like to reject entire languages instead of just rejecting the features they don’t like. A lot of stuff in C++ is entirely avoidable. Protocol-oriented programming is extremely useful for games and I like Objective-C for that reason. (Objective-C doesn’t meet his mentioned goal of portability but this is an example where C++ could be used to gain “light” inheritance without having to o…

Compilation times even for simple C++ programs are far too long and it's not like you can reject this "feature" unless you basically write C code compiled with C++ compiler. For instance: simple hello world with iostreams takes 280ms to compile vs 40ms for C equivalent with stdio. And it only gets exponentially worse with bigger programs.
Post reply on HN