@hkultala: the time a GC needs to spend isn't deterministic. That means: when it starts to work, there is no way to determine beforehand how long it's going to take to complete.
malloc()/free() are non-deterministic as well. The only way to guarantee deterministic is control memory policy yourself. In fact, many parts of game engines are non-deterministic, it's why we get frame-rate sputter, which clearly shows that the problem is not limited to GC, but in general, related to unpredictable workloads.
And when the time spend isn't deterministic, it can never be real-time.
And it is often impossible to prevent many dynamic allocations/deallocations on an object-oriented platform, unless you can allocate everything you'll ever need right at the start and re-use it: you can only allocate instances of classes (like, a simple string) by calling their constructor. And if you're not happy with how those constructors behave, you're out of luck, because in most GC languages it's simply impossible to specify where in memory that new class is to be created.
False on several fronts. First, in systems with real time components, determinism isn't a global requirement, critical tasks just need to be guaranteed to run. So for example, you could write 90% of the system with default memory behavior under lower priority, and 10% using an immortal heap. Determinism isn't an "either-or" requirement and probably 90% of games shipped aren't deterministic, because interactions between artistic workloads are almost never 100% within budget especially in games with physics engines and lots of shit being created and moved around.
Real time garbage collectors do exist and they work. RTSJ includes the Henriksson GC for example.
However, in most cases this isn't needed. Azul has been shipping GCs for years with radically better behavior than regular GCs due to explicit hardware support, their worse case behavior on HUGE heaps is 25ms. They're now starting to bring those over to the x86 vs Zing, see
http://www.google.com/url?sa=t&sour...1OTJDQ&usg=AFQjCNGw3hYPO9XZ8HTz4NrKRVHimn-50g
But beyond that, other options are scoped heaps, immortal heaps, and off-heaps. Scoped heaps are like allocation pools or stack allocoation, everything is freed when you're done. Immortal Heaps are heaps where the GC is turned off. It's for permanent datastructures where you know they will never need to be collected.
In any circumstance where you think you'd have a custom memory pool, you could equally well have a per-heap compacting GC. All GC is, is the ability to compute reachability. As long as you can bound the size of the search space, and the work that needs to be done, you have predictability. Moreover, just because you have a language with GC, doesn't mean everything you allocate has to be GC'ed.