Path: utzoo!censor!geac!torsqnt!news-server.csri.toronto.edu!cs.utexas.edu!ut-emx!nowhere!sking From: sking@nowhere.uucp (Steven King) Newsgroups: comp.lang.c++ Subject: Re: Overloaded operator new Message-ID: <1990Dec06.061537.22247@nowhere.uucp> Date: 6 Dec 90 06:15:37 GMT Organization: nowhere Lines: 86 In article <1990Dec5.155604.24463@sjsumcs.sjsu.edu> horstman@sjsumcs.sjsu.edu (Cay Horstmann) writes: >Yep, this is all very true. Indeed, operator new could place information >into a "header" area of the block which an overloaded operator delete could >find (by subtracting the header size from this...) > >My student was working on the idea of implementing several pools of memory, >and she passed the address of a pool descriptor into new. So there is a >possible use, I guess. > >I do realize that placement is useful. > >IF one agrees that new(p) X(...) is a good syntax for placement, then it is >indeed reasonable to implement the more general new(...) X(...). > >Personally, I don't think this is very elegant. I would much favor the symmetric >syntax p->X(...) to run X::X(...) on the preallocated p and p->~X(...) on the >destructor, and separately deal with the allocation and deallocation of p. > >Orthogonality of language features. (You know, like in Algol 68 :-)) > >I do realize that it is against the spirit of constructors to run them on >preallocated memory (but so is an explicit call to a destructor), and there- >fore a yucky syntax may discourage some from doing so. Don't bet on it, though. > >You'll begin to see plenty "new(this) X() // clear the state " in student's >code, I bet. > >Has anyone used the flexibility of operator new( size_t, ... ) for anything >BUT placement? A real world ;-} usage; An embedded system consisting of a central host and multiple coprocessors. Communication between the host and the copros are via dualport ram. Messages are of variable length, but of a common base format. class Message defines the common header shared by all derived messages and an operator new ( but not delete ), which is inherited by all derived message classes. Message::operator new is passed a reference to a "comm" which is an object containing the desired dualport area which itself exists as a "heap" object which has two methods, alloc and free ( actually void * heap::operator ( ) ( size_t ) and void heap::operator ( ) ( void * ) -- I have a lot of fun finding new uses of operator ( ) ( ) ;-). Operator message::new calls the heap alloc method which synchronizes access to the heap ( it is a shared resource in a multitasking system ) and actually allocates the space in the dualport. The delete operator is not defined because one of comm's methods that functions as an interrupt handler simply invokes the heap free method on the message -- by definition, if the comm interrupt handler services a message, it must belong to that comms heap. kinda nasty, but it gets around the limited delete syntax. And of course comm::operator new invokes the constructor for the dualport class which does a ram check on the dualport and initializes the coprocessor, returning the result code in the third arguement to comm::new, a reference to an int... I had lots of fun with this code. The placement form of new is also usefull if one wants to create an array of objects but doesnt want to use a default constructor. class A { public: A ( int ) ; } ; main() { char buf [ 10 * sizeof ( A ) ] ; int i = 0 ; for ( char *b = buf ; b < buf + 10 * sizeof ( A ) ; b+= sizeof ( A ) ) new ( b ) A ( i++ ) ; } I'm sure there are other ways to abuse overloading new that I havent thought of yet... -- sking@nowhere ..!cs.utexas.edu!ut-emx!nowhere!sking been dazed and confused for so long its true; wanted an OS, never bargined for you. Lotsa people hacking, few of them know, kernal of unix was created below...