Topic: Stack vs. Heap allocation (dynamic arrays or what happend to alloca)
Author: Jacob Rief <jacob@reality2.com>
Date: 1997/04/23 Raw View
Joe Buck wrote:
> Just write (ignoring namespace issues)
>
> #include <vector>
>
> void foo(int i)
> {
> vector<AnyType> array(i);
> ...
> }
>
> It does exactly what you want and you can use array[index], etc just
> as if it were an array. If you insist that the memory for your vector
> be on the stack, I suppose you could write a special allocator.
Yes, but on the heap not on the stack. Thats the way how vector is
implemented
in the STL, but not the way I asked for.
----------------------
Phil Edwards wrote:
> [cc'd to poster]
>
> Jacob Rief <jacob@reality2.com> wrote:
> [snip]
> + AnyType array[i]; // allocate memory on the stack and call
> + // i - times the default constructur of AnyType
> [snip]
>
> The Standard does allow a placement new, in order to construct an
> object at a specific location. Pass a pointer address as the first
> argument to new in order to get this functionality. The example given
> is something like (assuming a class Foo with a default ctor):
>
> char the_place_to_be[sizeof(Foo)];
> Foo *ptr = new (the_place_to_be) Foo;
And who calls the delete operator? The destructor would have
to be called manually at the end of the function. Objects on the
stack are destructed automatically.
--------------------
jfs@frontiernet.net wrote:
>
> Phil,
>
> You need to be careful about using placement new to construct objects
> in shared memory.
>
> Any class you place in shared memory CAN NOT have virtual functions
> or pointer-type instance variables. (i.e. map or multimap) since
> the base address the O/S chooses for a shared memory segment can
> vary from process to process. i.e. Process #1 can map it 0x04000000
> and process #2 can map it 0x06000000
Assuming You are talking about UNIX:
Only if You start two different processes from the shell. If You fork
Your
task there is no need to build a virtual-function-emulating class.
I use classes with virtual function inside shared memory with different
tasks acessing them. However these tasks must be spitted with fork
(or pthreads which I never used) rather than starting them seperately.
You also must initialize shared memory before forking!
---------------------
Preston Pfarner wrote:
[ snip ]
> Why do you want stack allocation, anyway? Automatic destruction
> and deallocation? If so, perhaps a smart pointer-to-array would
> be appropriate solution (or smart pointer to Vector template).
Stack allocation is faster and safer than heap allocation. On some
robust or real-time applications heap allocation is not even allowed.
Even if You dont have to remember to free up the memory with
auto_ptr<...> and vector<...> the allocation itself is done on the
heap.
In C++ the responsability of heap-allocation and dellocation is often
encapsulated and so the programmer might forget where his data really is
stored. This can result in strange behaviour on long-term-running
systems
with strong heap fragmentation.
Unfortunately there is no standard library for a garbage collecting heap
in C++.
---
[ comp.std.c++ is moderated. To submit articles: try just posting with ]
[ your news-reader. If that fails, use mailto:std-c++@ncar.ucar.edu ]
[ FAQ: http://reality.sgi.com/employees/austern_mti/std-c++/faq.html ]
[ Policy: http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu ]
Author: Preston Pfarner <presto@dapper.caltech.edu>
Date: 1997/04/12 Raw View
Jacob Rief <jacob@reality2.com> writes:
> Why does C++ not allow any default dynamic array allocation on the
> stack just as the following example demonstrates?
[ snip ]
While (as was mentioned) you can use placement new to create an object
into this location, you still must remember to explicitly call the
destructor yourself (a la "pointer->~ClassType()"). This might not
be consistent your goals.
Why do you want stack allocation, anyway? Automatic destruction
and deallocation? If so, perhaps a smart pointer-to-array would
be appropriate solution (or smart pointer to Vector template).
---
[ comp.std.c++ is moderated. To submit articles: Try just posting with your
newsreader. If that fails, use mailto:std-c++@ncar.ucar.edu
comp.std.c++ FAQ: http://reality.sgi.com/austern/std-c++/faq.html
Moderation policy: http://reality.sgi.com/austern/std-c++/policy.html
Comments? mailto:std-c++-request@ncar.ucar.edu
]
Author: jfs@frontiernet.net
Date: 1997/04/13 Raw View
Phil,
You need to be careful about using placement new to construct objects
in shared memory.
Any class you place in shared memory CAN NOT have virtual functions
or pointer-type instance variables. (i.e. map or multimap) since
the base address the O/S chooses for a shared memory segment can
vary from process to process. i.e. Process #1 can map it 0x04000000
and process #2 can map it 0x06000000
Ran into the problem myself. I had to use POD structs to contain each
class's instance data, place them in shared memory, and use indirction
to acess them.
class ShmClass {
struct Data {
int x_;
int y_;
} * impl;
public:
inline int x() const { return impl->x_; }
inline void x(int val) { impl->x_ = val; }
inline int y() const { return impl->y_; }
inline void y(int val) { impl->y_ = val; }
};
If you need pointer instance data, then you need to write all your
algorithms in terms of offsets into a shared memory base address and
perform pointer arithmetic to form a valid pointer before accessing
them.
Also, don't forget to synchronize access to the shared data using
something like a semaphore.
Good luck,
John.
---
[ comp.std.c++ is moderated. To submit articles: Try just posting with your
newsreader. If that fails, use mailto:std-c++@ncar.ucar.edu
comp.std.c++ FAQ: http://reality.sgi.com/austern/std-c++/faq.html
Moderation policy: http://reality.sgi.com/austern/std-c++/policy.html
Comments? mailto:std-c++-request@ncar.ucar.edu
]
Author: Eric Gindrup <gindrup@okway.okstate.edu>
Date: 1997/04/14 Raw View
Preston Pfarner wrote:
> Why do you want stack allocation, anyway? Automatic destruction
> and deallocation? If so, perhaps a smart pointer-to-array would
> be appropriate solution (or smart pointer to Vector template).
Sometimes the heap is empty but the stack is not.
-- Eric Gindrup ! gindrup@okway.okstate.edu
---
[ comp.std.c++ is moderated. To submit articles: Try just posting with your
newsreader. If that fails, use mailto:std-c++@ncar.ucar.edu
comp.std.c++ FAQ: http://reality.sgi.com/austern/std-c++/faq.html
Moderation policy: http://reality.sgi.com/austern/std-c++/policy.html
Comments? mailto:std-c++-request@ncar.ucar.edu
]
Author: Jacob Rief <jacob@reality2.com>
Date: 1997/04/10 Raw View
In C there is a nice but rarely used function to allocate a chunk of
memory from the stack (alloca) instead of the heap (malloc).
In C++ there is no counterpart. If I call 'alloca' instead of 'new'
no constructors are called.
Why does C++ not allow any default dynamic array allocation on the
stack just as the following example demonstrates?
void foo(int i)
{
AnyType array[i]; // allocate memory on the stack and call
// i - times the default constructur of AnyType
...
...
// call i - times destructor of AnyType
// reset the stackpointer
}
Is there any reason why this shoud not be allowed in any future
C++ standard. I heard that dynamic stack allocation is a built in
language feature in Modula 2.
---
[ comp.std.c++ is moderated. To submit articles: try just posting with ]
[ your news-reader. If that fails, use mailto:std-c++@ncar.ucar.edu ]
[ FAQ: http://reality.sgi.com/employees/austern_mti/std-c++/faq.html ]
[ Policy: http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu ]
Author: Matt Austern <austern@isolde.mti.sgi.com>
Date: 1997/04/10 Raw View
Jacob Rief <jacob@reality2.com> writes:
> In C there is a nice but rarely used function to allocate a chunk of
> memory from the stack (alloca) instead of the heap (malloc).
> In C++ there is no counterpart. If I call 'alloca' instead of 'new'
> no constructors are called.
Except that C doesn't have the alloca function. It isn't part of the
C standard. (I'm not sure whether it's even part of the POSIX
standard. I don't think so, but I don't have a copy of the POSIX
standard handy.)
---
[ comp.std.c++ is moderated. To submit articles: try just posting with ]
[ your news-reader. If that fails, use mailto:std-c++@ncar.ucar.edu ]
[ FAQ: http://reality.sgi.com/employees/austern_mti/std-c++/faq.html ]
[ Policy: http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu ]
Author: pedwards@cs.wright.edu (Phil Edwards)
Date: 1997/04/10 Raw View
[cc'd to poster]
Jacob Rief <jacob@reality2.com> wrote:
[snip]
+ AnyType array[i]; // allocate memory on the stack and call
+ // i - times the default constructur of AnyType
[snip]
The Standard does allow a placement new, in order to construct an
object at a specific location. Pass a pointer address as the first
argument to new in order to get this functionality. The example given
is something like (assuming a class Foo with a default ctor):
char the_place_to_be[sizeof(Foo)];
Foo *ptr = new (the_place_to_be) Foo;
I envision myself making copious use of placement new in a current
project, in order to place an object into shared memory -- I'll just
use the address returned by shmget(2) in the call to placement new.
If you alloca'ed the proper amount of space, you could then use that
pointer in the call to new.
I don't know what would happen if you tried using array new and
placement new simultaneously. I suspect that any reasonably intelligent
implementation that supports placement new would implement "placement
array" new and delete, but I'm just a student so they don't consult
with me before doing these things. :-)
The relevent Standard clause is [lib.new.delete.placement], which in
the December96 release was 18.4.1.3. There's a pointer to the HTML
version of the Standard in the signature block appended by the
moderators of this group, and I've got a copy (for another several
months at least) at http://www.cs.wright.edu/people/students/pedwards/ .
---
[ comp.std.c++ is moderated. To submit articles: try just posting with ]
[ your news-reader. If that fails, use mailto:std-c++@ncar.ucar.edu ]
[ FAQ: http://reality.sgi.com/employees/austern_mti/std-c++/faq.html ]
[ Policy: http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu ]
Author: jbuck@Synopsys.COM (Joe Buck)
Date: 1997/04/10 Raw View
Jacob Rief <jacob@reality2.com> writes:
>In C there is a nice but rarely used function to allocate a chunk of
>memory from the stack (alloca) instead of the heap (malloc).
>In C++ there is no counterpart. If I call 'alloca' instead of 'new'
>no constructors are called.
The main use of alloca in C is as a convenient way of getting
variable-length arrays that are automatically cleaned up when the function
exits. C++ users can use vector<T> for this purpose (valarray<T>
may be a better choice in some cases).
>Why does C++ not allow any default dynamic array allocation on the
>stack just as the following example demonstrates?
>void foo(int i)
>{
> AnyType array[i]; // allocate memory on the stack and call
> // i - times the default constructur of AnyType
> ...
> ...
>
> // call i - times destructor of AnyType
> // reset the stackpointer
>}
Just write (ignoring namespace issues)
#include <vector>
void foo(int i)
{
vector<AnyType> array(i);
...
}
It does exactly what you want and you can use array[index], etc just
as if it were an array. If you insist that the memory for your vector
be on the stack, I suppose you could write a special allocator.
--
-- Joe Buck http://www.synopsys.com/pubs/research/people/jbuck.html
Help stamp out Internet spam: see http://www.vix.com/spam/
---
[ comp.std.c++ is moderated. To submit articles: try just posting with ]
[ your news-reader. If that fails, use mailto:std-c++@ncar.ucar.edu ]
[ FAQ: http://reality.sgi.com/employees/austern_mti/std-c++/faq.html ]
[ Policy: http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu ]
Author: Christopher Eltschka <celtschk@physik.tu-muenchen.de>
Date: 1997/04/11 Raw View
Jacob Rief wrote:
>
> In C there is a nice but rarely used function to allocate a chunk of
> memory from the stack (alloca) instead of the heap (malloc).
> In C++ there is no counterpart. If I call 'alloca' instead of 'new'
> no constructors are called.
>
> Why does C++ not allow any default dynamic array allocation on the
> stack just as the following example demonstrates?
> void foo(int i)
> {
> AnyType array[i]; // allocate memory on the stack and call
> // i - times the default constructur of AnyType
> ...
> ...
>
> // call i - times destructor of AnyType
> // reset the stackpointer
> }
>
> Is there any reason why this shoud not be allowed in any future
> C++ standard. I heard that dynamic stack allocation is a built in
> language feature in Modula 2.
g++ has it as extension, so it is obviously possible (on all platforms
g++ has been ported to). I don't know if it is completely portable,
though (although I don't see any problem, as the standard would only
need to give the semantics; there would be no need that it is *really*
created on the stack)
Unfortunately, even on systems which have alloca, it is not even
possible to write an operator new, so you can do it like
new(execution_stack) T[25] or s.th. like this, as the memory
allocated with alloca would be local to the allocator, and therefore
released on it's return. So the only option to do it now
"semi-portable" (i.e. portable to all C++ compilers that have alloca)
is to use alloca, followed by placement new. BTW, you would obviously
have to call the destructor yourself, as the compiler can't know that
your placement-newed object is just an automatic one.
---
[ comp.std.c++ is moderated. To submit articles: Try just posting with your
newsreader. If that fails, use mailto:std-c++@ncar.ucar.edu
comp.std.c++ FAQ: http://reality.sgi.com/austern/std-c++/faq.html
Moderation policy: http://reality.sgi.com/austern/std-c++/policy.html
Comments? mailto:std-c++-request@ncar.ucar.edu
]