Pages: 1 [2]
  Print  
Author Topic: C++0x and garbage collection  (Read 2341 times)
Offline (Female) serprex
Reply #15 Posted on: November 18, 2010, 07:06:36 PM
Smooth ER
Developer
Joined: Apr 2008
Posts: 106

View Profile WWW
Stack variables are allocated all together. Static variables are not faster than the stack. The stack let's different code reuse the same memory. Keeping variables declared at the inner most scope is best, as it gets reused rather than redefined (Register allocation.) Those two kinds of memory don't suffer fragmentation, and don't have to deal with runtime allocation. This limits pretty close to malloc/free, which becomes close to mmap if you use large blocks which are then partitioned by one's own means. See things like arenas and pools. To understand more about malloc/free, read about free lists

Rusky contends that GC helps cache locality, but preferably one designs their objects to maintain locality by explicitly putting them together in memory, which resolves the issue also. That's the issue I have with people saying that JITs are going to bypass C: In Java, the JIT proves that array bounds are safe, and stops checking. In C, the compiler assumes the array bounds are safe, and doesn't check. One has a JIT to deal with, the other doesn't

Also, Rusky, LLVM doesn't have very good mechanisms for GC. They have some hooks to facillitate a shadow stack, but that says nothing of how much C++'s semantics fail to facillitate garbage collection. Hence Boehm admits that it cannot be standard compliant, only implementation friendly

And at that last part of I still don't know enough about it: Neither is ever always the right. Hence D allows the programmer to disable the GC for some things
Logged
Offline (Male) Rusky
Reply #16 Posted on: November 19, 2010, 12:34:44 AM

Resident Troll
Joined: Feb 2008
Posts: 961
MSN Messenger - rpjohnst@gmail.com
View Profile WWW Email
The stack is indeed a much better way to allocate memory in terms of cache usage and runtime overhead - memory access is minimized, fragmentation is impossible and there's no runtime mechanisms to keep track of what's allocated beyond a couple of registers that are heavily optimized within the processor. However, when you can't use the stack for whatever reason (dynamic size, data's scope doesn't follow the stack's behavior nicely, small stack, etc.) you need some kind of dynamic allocation.

Using malloc/free for each object is the least efficient, because each object can be a different size, each uses a few bytes to keep track of size/usage and eventually you end up with a fragmented heap without a lot of contiguous free memory. Allocating larger chunks for memory pools and free lists can help alleviate this problem and is often a good idea. However, you can still get bad cache usage with objects from different pools or far apart in their pools.

You can manually put objects together in memory by carefully tuning allocation, but (compacting/generational) garbage collection is sometimes a better way to do this because it automatically puts things allocated close together in the same chunk of memory. It also has the ability to rearrange the heap, so that even when the original assumption that objects allocated together are used together is wrong, objects that stay in use and do get accessed together get placed close together after a collection or two.

The tradeoffs between GC and manual memory management should always be taken into consideration - besides the end result of performance, which is complicated enough, there's also the cost in programmer time. In the real world it's often worth it to have somewhat sub-optimal performance rather than pay programmers more than that extra performance would earn you with extra sales. The same applies to scripting languages - people are willing to trade runtime performance for ease of use because overall the task gets done much more quickly.

---

LLVM supports more than a shadow stack - that's just the simplest way to do it because it's already 90% set up. Their garbage collector documentation explains what's possible beyond that. The Boehm collector has to work around a lot of limitations in C++'s semantics, but some of these could be removed by compiler support. While it's impossible to find all the pointers in a C++ program because of its weak typing, it is possible to be completely sure about things that stay within the type system.

Finally, JIT has nothing to do with bounds checking. The issue here is that people confuse JIT with all the type checking that most JIT languages include - you could easily write a JIT for C that could improve performance over statically compiled programs. Also, startup time is only a problem for some types of applications. Servers that are designed to stay running forever may start out slower but will just keep getting better and better as they run. Better system designs can help avoid repeating startup delays for normal desktop applications as well. By itself, JIT really can improve performance, not just "keep up."
Logged
Offline (Male) Josh @ Dreamland
Reply #17 Posted on: November 19, 2010, 10:48:26 AM

Prince of all Goldfish
Developer
Location: Ohio, United States
Joined: Feb 2008
Posts: 2950

View Profile Email
Quote
when you can't use the stack for whatever reason (dynamic size
alloca() :troll:
Logged
"That is the single most cryptic piece of code I have ever seen." -Master PobbleWobble
"I disapprove of what you say, but I will defend to the death your right to say it." -Evelyn Beatrice Hall, Friends of Voltaire
Offline (Male) Rusky
Reply #18 Posted on: November 19, 2010, 11:48:10 AM

Resident Troll
Joined: Feb 2008
Posts: 961
MSN Messenger - rpjohnst@gmail.com
View Profile WWW Email
Which is non-standard, doesn't always work the way you want or the same across platforms and is only one reason. :)
Logged
Offline (Female) serprex
Reply #19 Posted on: November 19, 2010, 12:57:23 PM
Smooth ER
Developer
Joined: Apr 2008
Posts: 106

View Profile WWW
It's standard in C99
« Last Edit: November 19, 2010, 01:00:27 PM by serprex » Logged
Offline (Unknown gender) luiscubal
Reply #20 Posted on: November 19, 2010, 02:11:54 PM
Member
Joined: Jun 2009
Posts: 452

View Profile Email
If you need to create a pointer and have it outlive the function, alloca won't work.
That said, it's still a good function to know about.
Logged
Pages: 1 [2]
  Print