For more detail have a look in MSDN
if still Problem let us know.
Thankyou
SuperKoko
April 14th, 2006, 01:48 PM
I want to start a discussion on why is it generally considered to be useless to check if the allocation done through new failed or not.
It is not useless.
IMHO, catching a potential bad_alloc exception is a requirement in a correct program.
But perhaps, you misunderstood what said some C++ programmers.
It is useless to check that the returned pointer is not NULL, because it can't be NULL.
new throws calls a handler, which, by default, throws a bad_alloc exception!
I am aware that a few old C++ compilers are not compliant on that point, and returns NULL in case of allocation failure. :(
Graham
April 14th, 2006, 03:38 PM
new (std::nothrow)
is a standard-compliant way of getting the same behaviour.
stober
April 14th, 2006, 04:32 PM
use set_new_handler it Installs a user function that is to be called when operator new fails in its attempt to allocate memory.
Your program didn't work on my computer. I'm running XP with 1 Gig RAM. I first compiled it with VC++ 6.0 and got (almost) immediate assertion failure and abnormal program termination. Then I compiled it the VC++ 2005 Pro, that program just kept attempting to allocate more and more memory -- eventually my computer slowed down to a crawl and I finally killed that program. It never did call that newhandler() function.
[edit]I debugged VC++ 6.0 and found out that it doesn't implement set_new_handler()., Here is the assertion in M$'s function :eek:
// cannot use stub to register a new handler
assert(new_p == 0);
[edit again]VC++ 6.0 uses _set_new_handler() instead of set_new_handler(). made that change and the program worked the same as it did with 2005 compiler.
MrViggy
April 14th, 2006, 04:42 PM
In general, I think the idea is that if your app is requesting small amounts of memory, and it fails to get any (which means, on Windows, you're probably getting close to the 2GB limit), there's not much more your applciation can do (can't continue).
Of course, if you have an app that is using this much memory, it might be time to think about using your own memory management, and develop some kind of cache system.
My $0.02...
Viggy
SuperKoko
April 14th, 2006, 05:06 PM
In general, I think the idea is that if your app is requesting small amounts of memory, and it fails to get any (which means, on Windows, you're probably getting close to the 2GB limit), there's not much more your applciation can do (can't continue).
I have experienced applications that supported very well out-of-memory conditions.
Simply, the current operation fail, but it is still possible to use the software, save, modify what I want, etc...
I have also seen applications crashing stupidly...
MrViggy
April 14th, 2006, 05:10 PM
It really depends on the application. Our applications just exit. The issue is that if we can't get the memory we need, then the design we are working on writing is hosed already. So, we delete the design, and inform the user to call the s/w hotline for some possible solutions.
Viggy
miteshpandey
April 14th, 2006, 09:04 PM
Here is a link to an article by Herb_Sutter on this matter.
Check out the moral #2
Link (http://www.gotw.ca/publications/mill16.htm)
Perhaps I misunderstood what he says. Maybe he meant is that there is no use in checking if new allocation succeeded or not in systems which commit memory long after the request for memory.
Maybe this doesn't happen in Windows system and we should check for new allocations.
What are your thoughts after reading the article?
Bornish
April 15th, 2006, 01:03 AM
If talking about non-POD objects, I believe best error handling is offered by a dummy interface instance (probably static) providing a default behaviour of the class. Overriding the creation of instances from a class, the reason for failure can be stored on per thread basis and retrieved by the client (caller of the allocation) through the dummy interface. In some cases, it is also useful to provide a mechanism for testing if the instance is a dummy or a real object. My personal favorite safety method is providing objects with a signature that gets overwritten on destruction, thus being able to test a pointer for validity when received through posted messages or shared by multiple threads.
exterminator
April 15th, 2006, 06:47 AM
Dissection - It is not necessary to check for successful memory allocations if you are using the non-nothrow version of new. It would throw std::bad_alloc exception. Work with exceptions instead of NULL checks all over the place unless that is the requirement (as for Graham working with the nothrow version).
There is a nothrow version of new ... and it returns NULL if the memory allocation fails. And a program should have checks for that. Atleast notifying the user about it, logging the failure.
There should be some precise reason about the failure so that the worries following it are directed rightly. If there are no checks, no logging and the program fails you are just left with no clues as to what should be done! What part of the program caused the abrupt failure? What should we tell the client? How must we target the situation? Start debugging from Line 1 on the client's machine? Totally inacceptible!
Lazy initialized or COW implementations (some implementations of std::string) are different. Let them be.. but you can not always program your applications based on assumptions about certain implementations. That is not the best practice. Moreover, if the handlers fail to give you proper diagnostic signals - that's the particular implementations problem - and not yours!
It is utter truth that there cannot really be much that can be done on new failure. I agree but a notification is something that should happen. new handlers do that. Use them. The ultimate goal of exception handling is to catch those exceptional conditions, do some diagnostics and try to recover.
Trying/Ability to recover is important. You should not always catch exceptions that you cannot do nothing about because in the end you are left with no other option than re-throwing the exception with a little log created which could also have had been done in the code that actually is capable of handling/recovering from the exception. If you consider from that point of view - handling new related exceptions is meaningless - because you really can't do anything about it... but this is an exceptional case - you program is going to end - and no other part of the code will be able to handle it. So, a little logging can always prove helpful in predicting the error to determine if this failure was because of new failure or some other exception that was left unhandled by a bad programmer! Be it done - using new handlers or exception catching mechanism.
Conclusion - use new handlers (set_new_handler) as well as catch std:bad_alloc exceptions. Herb Sutter's article in not suggesting against their usage but targets lazy initialization and how it makes our life tough (showing success when actually later the program fails) and standard conformance issues. He shows the practical significance of this exception - it is very rare true but it can happen! If they really felt they are un-necessary then may be the standards specifications could be made a few pages shorter. ;)
Suggestion - read the article again. :) - kidding, but its no harm you know! Use new handlers as well as exception handling depending upon the program's specifications as to what must be done in such cases.
SuperKoko
April 15th, 2006, 07:57 AM
It is utter truth that there cannot really be much that can be done on new failure. I agree but a notification is something that should happen. new handlers do that. Use them. The ultimate goal of exception handling is to catch those exceptional conditions, do some diagnostics and try to recover.
There are not much that can be done, but there is much that can be not undone....
I mean that a bad_alloc exception means only that the operation allocating this memory fails... no more.
For instance, a good video game that lacks memory for allocating a sprite (or model or texture) or playing a sound, will simply fail to display or play it.... not crash. If the game is really well written, it can even display a "default sprite" (or model, or texture).
It does little... but I claim that it is recovers properly from the exception.
Similarly, a MDI application (Word processor... or web brower), can have many open windows, and if a new one is created and there is not enough memory, instead of crashing, it is MUCH better to simply don't create the new window. Because as a user, I can't accept to see all of my browsing windows suddenly close with a message "Not enough memory... bye bye!".
And guys who think that there is enough memory are wrong. I experience often out-of-memory.
And there are many programs that crash... and others that recover properly. I always prefer to use programs that recover properly.
Furthermore, there are cases where we can really recover and make the operation success.
A simple example:
std::vector::push_back may use an exponential growth strategy (allocating 1.3 or 1.5 times the memory needed).
And, you know that, for a std::vector reallocation, you need twice the memory of the vector. That is much.
So, a std::bad_alloc is not so exceptionnal. In that case, one can recover by allocating exactly the needed memory (and not 1.5 times the needed memory).
Back to the web browser example : Many (all?) web browser keep in cache a lot of data. In fact, web browser would use a very very little amount of memory if they had no cache.
So, if there is an out-of-memory condition, it is very easy to free much memory.
But, for example, I admit that a C++ compiler can't do much when it has not enough memory, except exit cleanly.
miteshpandey
April 15th, 2006, 09:09 AM
From the above discussion, I have come to understand that:
Failure of allocation through new should be checked (whether bad_alloc is thrown or the nothrow version which returns null)
1. If the program can't do without that specific memory that could not be allocated through new, the program should log this and exit. The logging is for diagnostic purpose.
2. If the programmer has alternative strategies(like requesting for fewer bytes or etc.) then the program can take this alternative path instead of exiting the application.
Am I far from correct?
Mitsukai
April 15th, 2006, 09:27 AM
i would rather check if it returned 0 or not, throw has to much power of the application for me.
exterminator
April 15th, 2006, 09:35 AM
There are not much that can be done, but there is much that can be not undone....
I mean that a bad_alloc exception means only that the operation allocating this memory fails... no more.
For instance, a good video game that lacks memory for allocating a sprite (or model or texture) or playing a sound, will simply fail to display or play it.... not crash. If the game is really well written, it can even display a "default sprite" (or model, or texture)...... (and more......)Correct... I totally agree. In fact, I considered this case in my post as well when I said the following in the suggestions part:Use new handlers as well as exception handling depending upon the program's specifications as to what must be done in such cases.Am I far from correct?No. You are not incorrect. You are on right track! In fact, now just leave new failure away and think about any kind of exception. That is what you actually do for any other exception. Then why should new be given special treatment? Yeah, I agree they are all specific exceptional cases but still you have to handle them as far as you can and take remedial action specific to that exception, if you can. Otherwise - why would there be a need to write anything else except catch(...)?
Again, I put stress on this that the ability to recover is important if you are planning to put a catch block! How you are planning to recover depends on the programmer and the specifications that have been laid down in the design phase! Good examples are provided in SuperKoko's post above.
Regards.
exterminator
April 15th, 2006, 09:44 AM
i would rather check if it returned 0 or not, throw has to much power of the application for me.Mitsukai, this does not make sense? What are you trying to say? Please be explicit while explaining things. The way you have written your post - its too confusing and in fact does not make sense.
If you are suggesting not use exception handling and using the historical ways of catching errors then I guess you must go ahead with reading the following FAQs for a start.
It has been unanimously decided on Codeguru that people use exception handling and hence you should too... if you don't agree do a search for exception handling on this forum and come back with the arguments. We would like to settle this forever! ;) :D
codeguru.com
Copyright Internet.com Inc., All Rights Reserved.