C++ and a safe way to jump out of dynamically generated code - c++

My project is written in C++, and it makes use of dynamically generated code to glue some things together (using Fabrice Bellard's TCC and a bit of manually generated assembly thunks). Dynamically generated code sometimes jumps into "runtime helpers" implemented in C++ and back.
There's a feature that allows to abort dynamically generated code altogether, wherever it is, jumping back to C++ (the caller). To achieve that, I'm simply using C++ exceptions: a runtime helper (posing as a C function) simply throws a C++ exception, and it propagates through generated functions back to C++. I'm using SJLJ and everything works OK so far, but I don't want to depend on a particilar implementation (I read that that's safe only with SJLJ).
Other than the aborting scheme above, my C++ code uses exceptions mostly in critical situations, it's not used for general purpose control flow. However, I rely on RAII to automatically destruct objects on stack.
My question is: Is it theoretically and practically safe to use longjmp/setjmp instead, provided setjmp is set right before calling a dynamically generated function, and provided that longjmp never propagates through C++ functions that rely on RAII (I must make sure that none of runtime helpers implemented in C++ make use of it) and always lands in setjmp (set right before the function)?
Or C++ is so fragile that even this isn't guaranteed to work well and will corrupt something? Or maybe C++ breaks only if actual exceptions are thrown? What if the exceptions are thrown locally and caught immediatelly (in runtime helpers called by generated assembly), is it safe? Or maybe just because there are a few foreign frames up the stack, it will refuse to work?
EG:
jmp_buf buf; // thread-local
char* msg; // thread-local
// ... some C++ code here, potentially some RAII thingy
GeneratedFunc func = (GeneratedFunc)compile_stuff();
if (!setjmp(buf)) {
// somewhere deep inside, it calls longjmp to jump back to the top function in case a problem happens
func();
} else {
printf("error: %s\n", msg);
// do something about the error here
}
// some other C++ code

Is it theoretically and practically safe to use longjmp/setjmp instead, provided setjmp is set right before calling a dynamically generated function, and provided that longjmp never propagates through C++ functions that rely on RAII (I must make sure that none of runtime helpers implemented in C++ make use of it) and always lands in setjmp (set right before the function)?
The Standard's 18.10/4 says:
...longjmp(jmp_buf jbuf, int val) has more restricted behavior in this International Standard. A setjmp/longjmp call pair has undefined behavior if replacing the setjmp and longjmp by catch and throw would invoke any non-trivial destructors for any automatic objects.
So, it's not just RAII, but any stack-hosted objected with non-trivial destructors (i.e. "resources" might be acquired after construction but still need to be released during destruction, or there could be side effects of destruction other than resource release, such as logging).
Or C++ is so fragile that even this isn't guaranteed to work well and will corrupt something?
It should work subject to the caveat above about trivial destructors (which is quite a big restriction).
Or maybe C++ breaks only if actual exceptions are thrown? What if the exceptions are thrown locally and caught immediatelly (in runtime helpers called by generated assembly), is it safe?
That's unrelated to the setjmp / longjmp behaviour. If you throw and catch inside normal C++ compiler generated code there shouldn't be any residual/consequent issues with execution (re)entering the dynamically generated code. The same approach is used for wrapped C++ libraries called to/from C; exceptions may be caught on the boundaries of a C++ library and converted to error codes that C can handle.

Related

if map.insert fails how check its failure without using bad_alloc

If inside my code i am having a
class A;
A ob;
pair<map<int,A>::iterator,bool> ret;
ret=map.insert(pair<int,A>(1,ob));
If map fails to insert the ob because of out of memory, it will throw bad_alloc
but is there any other way to check whether insert failed or not because i have a restriction to not use namespace and exception handling.
Can't we use some kind of NULL pointer comparision statement?
The standard library reports failure to allocate memory by throwing std::bad_alloc. And while you are able to get around that with new(nothrow), you can't do that with standard library classes.
Exception handling is part of C++; it is not an optional part of C++. Exceptions are the standard C++ way of handling erroneous conditions. I understand that you're working in an environment that doesn't allow you to catch exceptions, but you then have to accept that you're working in an environment that doesn't allow you to use all of C++. So there will be limitations on what you can do.
It should be noted that, unless you're using a custom allocator, it's unlikely that recovering from an "unable to allocate" error would be something easy to implement. Being unable to allocate memory would only happen because your application ran out of memory. In that case, just let the exception be thrown; since you don't use exceptions, it will escape main and cause your program to crash. Which is exactly what you want to happen.
If you do have some way to survive running out of allocatable address space, there's not much you can do if you can't catch exceptions. C++ standard library classes are designed to work with C++, and that means all of it. Including exceptions.
You're not allowed to use exception handling? Reconsider this. Parts of the C++ standard library use exceptions internally - this means you can't turn off exceptions using a compiler switch. If exceptions are enabled, you might as well use them - or of course you can implement your own exception-free standard library.

C++ exception for null pointers

I have a little function (in a DLL) which looks like this:
int my_function(const char* const s)
{
try {
return my_object->do_something_with(s);
} catch (exception& e) {
return ERROR_CODE;
}
}
I thought that the try-catch block would prevent anything which might happen inside my_object from propagating to the outside. Unfortunately, I was wrong, and my program which calls this function (from VB) just stopped working because I had passed a null pointer argument.
So, why is my try-catch block not working as (I) expected? Is there a workaround? I used to program a lot in Java and I think it would have worked there ...
It would have worked in Java, because in Java a NullPointerException is thown. In C++, there's no such ubiquitous exception, dereferencing a null pointer will just give a segmentation fault.
Additionally, in C++ there is no enforced exception type hierarchy. An exception of any type may be thrown; exceptions don't have to derive from std::exception. (So even if someone had defined a class NullPointerException {};, but had not designated it to derive from std::exception, you still wouldn't be catching it.)
Dereferencing a null pointer in C++ is undefined behavior. This means the C++ standard doesn't put any limits on what may happen. Anything is permitted - a particular implementation might document its own behavior, or it might not. If it doesn't, the behavior might be consistent and predictable, or it might not.
In general it's best to assume that undefined behavior will cause your computer to catch fire (or format the hard disk). Just don't provoke it. Of course it's difficult to avoid errors in the first cut of your code, so when you do it by accident and your computer doesn't catch fire, then you were lucky, fix the bug and move on. Your function could be rewritten:
int my_function(const char* const s)
{
if (s == 0) return ERROR_CODE;
return my_object->do_something_with(s);
}
Alternatively you could fix the caller to not pass a null pointer in the first place, or you could fix do_something_with to accept a null pointer. C++ functions with pointer parameters should document whether or not null pointers are permitted.
Different people will write the test (s==0) differently - it could be (s==NULL) or (NULL==s) or (!s). Pick one you like.
In practice of course, compilers have good reasons not to set your computer on fire, and modern OSes try to ensure that badly-behaved apps don't massively inconvenience other apps. So on most systems, most of the time, when you dereference a null pointer you'll get some kind of hardware exception or signal, or your process will be killed, or perhaps on an embedded system the device will lock up and need a reboot.
You will not in general get a C++-style software exception that you can catch with any kind of catch clause, although Windows does have a feature called SEH which you can use to get that behavior.
In C++, anything can be thrown, and that anything does not necessarily derive from std::exception, which I'm assuming you're catching (using namespace std?).
If you want to catch everything that can possibly be thrown, you can use a catch-all, catch (...). This will catch any exception, but you won't know what the exception it caught is. It's always better to catch specific exceptions, where possible.
Note that normally, a catch all will not handle lower level exceptions such as access violations. If you're using Windows and Visual Studio, you can configure your project to make catch-all blocks handle these exceptions with /EHa, but doing this is often dangerous and not suggested.
c++ faq items regarding exceptions might help you understand c++ exceptions better.
Lots of people programming in java have a problem understanding pointers and references, so if the program stopped working, maybe it was due to a crash (segmentation fault due to dereferencing NULL?)
There is no NullPointerException in C++. If you really want to catch such an access, you must catch some signals (SIGSEGFAULT for example).
Take it with a grain of salt because I haven't touched a C++ compiler since 1999. So much has changed with the STL and C++ that maybe things have changed. However, this is what I recall.
The exception model in C++ is very different from the one in Java. You have to be a lot, lot, but lot more proactive in checking for errors (and in throwing your own custom exceptions).
In Java, a call to de-reference a reference is ultimately a bytecode instruction sent and interpreted by the JVM. The JVM always check (internally) if the reference is null , and when it finds that it is, it automatically throws a java.lang.NullPointerException.
If the JVM weren't programmed to do such a thing, an access to a null reference would cause the JVM to crash with a SEGFAULT - exactly the behavior one would expect with a compiled, unguarded language when encountering an unguarded null pointer de-referencing (not just C or C++ but also in Pascal, Ada, Assembly or even good old BASIC attempting to do a PEEK/POKE at an invalid address location.)
The way (at least in my time) in C++ (or in any of the languages I've mentioned) was to explicitly check if the pointer (or the address being assigned to a reference) was null. At that point, if the test returns true, you launch your exception. You don't blindly go after the pointer. You gotta explicitly test it for null (or have a very strongly guaranteed pre-condition that the pointer actually points to the thing you need to get access to) before de-referencing.
This is somewhat equivalent to the following Java pseudocode
if( myPossiblyBadReference == null )
{
throw java.lang.NullPointerException( "you suck!" );
// or throw my.own.NPEException(); // preferably a specialization of NullPointerException
}
else
{
doYourThingieWith( myPossiblyBadReference );
}
Things might be done differently now in C++, specially now with the C++0x stuff coming down the pipe (of which I have no clue about.) But at least, that's the behavior I had to deal with when coding in C++.
In other words, there is a lot more elbow grease involved in getting such things done. Remember that you are working at a lower level of abstraction from the one provided by the JVM.
The JVM is a barrier that gives you a lot of nice error-handling capabilities (one which we Java developers tend to rely too much on.) Those error-handling capabilities need to be explicitly be coded when you work at a lower level (not just in C++.)

Whats the right approach for error handling in C++

One is to use C++ exceptions: try catch blocks. But freeing dynamic memory will be an issue when an exception is raised.
Second is to use C style: errno variable
Third is just to return -1 on error and 0 on success :)
Which way should be chosen for a mid-size project and why? Any other better approach..?
But freeing dynamic memory will be an issue when an exception is raised.
No it's not. std::vector<int> v(100); Done.
The concept here is called Scope-Bound Resource Management (SBRM), also known by the much more common (and awkward) name Resource Acquisition Is Initialization (RAII). Basically, all resources are contained in some object which will clean up the resource in the destructor (which is always guaranteed to be run for an automatically allocated object). So whether or not the function exists normally or via exception, the destructor is run and your resource is cleaned up.
Never do an allocation where you need to free it explicitly, use containers and smart pointers.
Second is to use C style: errno variable
Third is just to return -1 on error and 0 on success :)
And how do they help solving your problem of freeing dynamic memory? They also use an early-exit strategy, same as throw.
So in summary, they don’t have an advantage over C++ exceptions (according to you).
In the first place, you should strive for a program with minimum error cases. (Because errors are not cool.)
Exceptions are a nice tool but should be used conservatively: reserve them for "exceptional cases", do not use them to control the flow of your program.
For example, do not use exceptions to test whether a user input is correct or not. (For such a case, return an error code.)
One is to use C++ exceptions: try
catch blocks. But freeing dynamic
memory will be an issue when an
exception is raised.
#see RAII.
Exceptions should be your preferred method of dealing with exceptional runtime situations like running out of memory. Note that something like std::map::find doesn't throw (and it shouldn't) because it's not necessarily an error or particularly exceptional case to search for a key that doesn't exist: the function can inform the client whether or not the key exists. It's not like a violation of a pre-condition or post-condition like requiring a file to exist for a program to operate correctly and finding that the file isn't there.
The beauty of exception-handling, if you do it correctly (again, #see RAII), is that it avoids the need to litter error-handling code throughout your system.
Let's consider a case where function A calls function B which calls C then D and so on, all the way up to 'Z'. Z is the only function that can throw, and A is the only one interested in recovering from an error (A is the entry point for a high-level operation, e.g., like loading an image). If you stick to RAII which will be helpful for more than exception-handling, then you only need to put a line of code in Z to throw an exception and a little try/catch block in A to catch the exception and, say, display an error message to the user.
Unfortunately a lot of people don't adhere to RAII as strictly as they should in practice, so a lot of real world code has more try/catch blocks than should be necessary to deal with manual resource cleanup (which shouldn't have to be manual). Nevertheless, this is the ideal you should strive to achieve in your code, and it's more practical if it's a mid-sized project. Likewise, in real world scenarios, people often ignore error codes returned by functions. if you're going to put the extra mile in favor of robustness, you might as well start with RAII because that will help your application regardless of whether you use exception handling or error code handling.
There is a caveat: you should not throw exceptions across module boundaries. If you do, you should consider a hybrid between error codes (as in returning error codes, not using a global error status like errno) and exceptions.
It is worth noting that if you use operator new in your code without specifying nothrow everywhere, ex:
int* p = new int(123); // can throw std::bad_alloc
int* p = new(std::nothrow) int(123); // returns a null pointer on failure
... then you already need to catch and handle bad_alloc exceptions in your code for it to be robust against out of memory exceptions.
Have a look at this comment by Herb Sutter on try catch for C++ GOTW. And do go through his whole set of articles. He does have a lot to say on when and how to check and save yourself from error conditions and how to handle them in the best ways possible.
Throw an exception. Destructors of variables are always called when an exception is thrown, and if your stack-based variables don't clean up after themselves (if for example you used a raw pointer when you need to delete the result), then you get what you deserve. Use smart pointers, no memory leaks.
But freeing dynamic memory will be an issue when an exception is raised.
Freeing memory (or any other resource for that matter) doesn't suddenly become a non-issue because you don't use exceptions. The techniques that make dealing with these problems while exceptions can be thrown easy, also make it easier when there can be "error conditions".
Exceptions are good for passing control from one context to another.
You let the compiler do the work of unrolling the stack between the contexts then in the new context compensate for the exception (and then hopefully continue).
If your error happens and can be corrected in the same context then error codes are a good method to do error handling and clean up (Don't take this to mean you should not be using RAII you still need that). But for example within a class an error occurs in a function and the calling function can correct for that type of error (then it probably is not an exceptional circumstance so no exceptions) then error code are useful.
You should not use error codes when you have to pass information out of a library or sub system as you are then relying on the developer using the code to actually check and handle the code to make sure it works correctly and more often than not they will ignore error codes.

How can I avoid using exceptions in C++?

What techniques can I use to avoid exceptions in C++, as mentioned in Google's style guide?
Don't throw exceptions.
Don't use STL (which relies heavily on exceptions).
Use only new(std::nothrow) or override ::operator new to return 0 on failure.
Note that by avoiding exceptions, you're effectively throwing out lots of useful libraries, including Boost. Basically, you'll have to program everything from scratch.
Not throwing exceptions in your own code is relatively easy: you just don't use the throw statement.
Not throwing exceptions from memory allocation failures is a little more painful: either you don't use normal new (use new(std::nothrow) or malloc or something instead), or you use some nonstandard compiler option to get it to do something nonstandard when it fails (e.g. immediately terminate your program, or return 0), or you override operator new to do something nonstandard when it fails.
If your chosen approach is to immediately terminate the program, you can implement this with set_new_handler(), which I had forgotten about until litb reminded me.
That leaves the problem of dealing with exceptions generated by C++ libraries you don't maintain. Generally you'll have to wrap library calls in a wrapper that looks something like this:
int DoSomething(int &output, const int input) throw() {
try {
output = library_do_something(input);
return 1;
} catch (...) {
return 0;
}
}
The catch (...) catches all possible C++ exceptions from library_do_something (as well as the assignment operator on output, which isn't relevant here), throws away all the information they may have contained, and then maps all those failures to 0.
Note that this style means that you can't use RAII at all, not even a little bit, because you have no way of signaling failure within a constructor. The whole point of RAII is that you acquire all your resources inside of constructors so that they will be properly released by a destructor during exception propagation. But resource acquisition is something that can essentially always fail. So you can't do that inside a constructor.
I'm interested to know why one would want to avoid exceptions in C++ and what mechanism one would replace them with to deal with the reality of unexpected failure while still maintaining decent structure.
Sure adding them to a existing codebase that doesn't use RAII type semantics is extremely costly - but if one is doing green field development then what alternative would you suggest and how are going to justify not using high quality libraries that do use exceptions vs. writing your own exception free / bug free alternatives?
The style guide says they "don't use exceptions" which is just that - they don't throw them and don't call anything that could throw them (for example, they would use the new(std::nothrow) instead of usual new because the latter will throw bad_alloc when it fails to allocate memory.
In some compilers, you may be able to turn off exception handling. This could cause unexpected results with external code though - it is not something I would want to try.
Other than that, the obvious first step would be to avoid throwing exceptions from your own code, probably with liberal use of the nothrow directive, and attempt to avoid throwing exceptions from external (3rd party) code through defensive programming.
That means that your code needs to be aware of possible external exceptional failure conditions all the time, such as running out of memory, out of disk space, loss of an internet connection, hardware failure, and any number of other circumstances that might cause code to throw...
In some cases you may be able to use exception-free versions of some code (such as throwing-new vs. non-throwing new).
What I do is to never throw exceptions with my own code, and to "translate" or wrap any external code that does that.

Is there a favored idiom for mimicing Java's try/finally in C++?

Been doing Java for number of years so haven't been tracking C++. Has finally clause been added to C++ exception handling in the language definition?
Is there a favored idiom that mimics Java's try/finally?
Am also bothered that C++ doesn't have an ultimate super type for all possible exceptions that could be thrown - like Java's Throwable class.
I can write:
try {
// do something
} catch(...) {
// alas, can't examine the exception
// can only do cleanup code and perhaps rethrow, ala:
throw;
}
ADDENDUM EDIT:
I ended up accepting the answer that
had the most up votes, i.e., use
destructors to do cleanup. Of course,
from my own comments, it is clear I
don't entirely agree with that.
However, C++ is what it is and so in
the application endeavor I have in
mind, I'm going to more or less strive
to adhere to common community
practice. I'll use template classes to
wrap resources that don't already have
a class destructor (i.e., C library
resources), thus bestowing on them
destructor semantics.
NEW ADDENDUM EDIT:
Hmm, instead of finally then a closure
feature perhaps? A closure combined with
ScopeGuard approach (see one of the
answers below) would be a way to
accomplish cleanup with arbitrary
actions and access to the cleanup
code's outer scope context. Cleanup could be done in the idiom fashion that is seen in Ruby programming where they supply cleanup blocks when a resource is being opened. Isn't a
closure feature being considered for
C++?
By making effective use of destructors. When an exception is thrown in a try block, any object created within it will be destroyed immediately (and hence its destructor called).
This is different from Java where you have no idea when an object's finalizer will be called.
UPDATE: Straight from the horse's mouth: Why doesn't C++ provide a "finally" construct?
My $.02. I've been programming in managed languages like C# and Java for years, but was forced to make the switch to C++ for the purposes of speed. At first I couldn't believe how I had to write out the method signature twice in the header file and then the cpp file, and I didn't like how there was no finally block, and no garbage collection meant tracking memory leaks everywhere - gosh I didn't like it at all!
However, as I said I was forced to use C++. So I was forced to seriously learn it, and now I've finally understood all the programming idioms like RAII and I get all the subtleties of the language and such. It took me a while but now I see just how different of a language it is compared to C# or Java.
These days I think C++ is the best language there is! Yes, I can understand that there is a little more what I call 'chaff' sometimes (seemingly unnecessary stuff to write), but after actually using the language seriously, I've changed my mind about it completely.
I used to have memory leaks all the time. I used to write all my code into the .h file because I hated the separation of code, I couldn't understand why they would do that! And I used to always end up with stupid cyclic include dependencies, and heaps more. I was really hung up on C# or Java, to me C++ was a huge step down. These days I get it. I almost never have memory leaks, I enjoy the separation of interface and implementation, and I don't have problems with cycle dependencies anymore.
And I don't miss the finally block either. To be honest, my opinion is that these C++ programmers that you talk about writing repeated cleanup actions in catch blocks just sound to me like they're just bad C++ programmers. I mean, it doesn't look like any of the other C++ programmers in this thread are having any of the problems you mention. RAII really does make finally redundant, and if anything, it's less work. You write one destructor and then you never have to write another finally ever! Well at least for that type.
With respect, what I think is going on is you're just used to Java now, just like I had been.
C++'s answer is RAII: The object's destructor will be executed when they go out of scope. Whether by a return, by an exception or whatever. If you handle the exception somewhere else, you can be sure all objects from the called function down to your handler will be properly destructed by having their destructor called. They will clean up for you.
Read http://en.wikipedia.org/wiki/Resource_acquisition_is_initialization
No finally has not been added to C++, nor is it likely to ever be added.
The way C++ uses constructor/destructor makes the need for finally unnecessary.
If you are using catch(...) to cleanup then you are not using C++ properly. The cleanup code should all be in the destructor.
Though it is not a requirement to use it C++ does have a std::exception.
Forcing developers to derive from a specific class to use exception goes against the keep it simple philosophy of C++. Its also why we don't require all classes to derive from Object.
Read: Does C++ support 'finally' blocks? (And what's this 'RAII' I keep hearing about?)
The use of finally is more error prone than destructors to do clean up.
This is because you are forcing the user of the object to do clean up rather than the designer/implementer of the class.
Ok, I have to add in an answer to the points you made in a separate answer post:
(It would be a lot more convenient if you'd edited this into the original question, so it doesn't end up at the bottom below the answers to it.
If all cleanup always gets done in
destructors then there wouldn't need
to be any cleanup code in a catch
block - yet C++ has catch blocks where
cleanup actions get done. Indeed it
has a block for catch(...) where it is
only possible to do cleanup actions
(well, certainly can't get at any
exception information to do any
logging).
catch has a completely separate purpose, and as a Java programmer you should be aware of that. The finally clause is for "unconditional" cleanup actions. No matter how the block is exited, this must be done. Catch is for conditional cleanup. If this type of exception is thrown, we need to perform a few extra actions.
The cleanup in a finally block will
get done whether there was an
exception thrown or not - which is
what one always wants to happen when
cleanup code does exist.
Really? If we want it to always happen for this type (say, we always want to close a database connection when we're done with it), then why don't we define it once? In the type itself? Make the database connection close itself, rather than having to put a try/finally around every single use of it?
That's the point in destructors. They guarantee that each type is able to take care of its own cleanup, every time it's used, without the caller having to think of it.
C++ developers from day one have been
plagued with having to repeat cleanup
actions that appear in catch blocks in
the code flow that occurs upon
successful exit from the try block.
Java and C# programmers just do it
once in the finally block.
No. C++ programmers have never been plagued by that. C programmers have. And C programmers who realized that c++ had classes, and then called themselves C++ programmers have.
I program in C++ and C# daily, and I feel I'm plagued by C#'s ridiculous insistence that I must supply a finally clause (or a using block) EVERY SINGLE TIME I use a database connection or something else that must be cleaned up.
C++ lets me specify once and for all that "whenever we're done with this type, it should perform these actions". I don't risk forgetting to release memory. I don't risk forgetting to close file handles, sockets or database connections. Because my memory, my handles, sockets and db connections do it themselves.
How can it ever be preferable to have to write duplicate cleanup code every time you use a type? If you need to wrap the type because it doesn't have a destructor itself, you have two easy options:
Look for a proper C++ library which provides this destructor (hint: Boost)
Use boost::shared_ptr to wrap it, and supply it with a custom functor at runtime, specifying the cleanup to be done.
When you write application server
software like Java EE app servers
Glassfish, JBoss, etc., you want to be
able to catch and log exception
information - as opposed to let it
fall on the floor. Or worse fall into
the runtime and cause a ungraceful
abrupt exit of the application server.
That's why it's very desirable to have
an overarching base class for any
possible exception.
And C++ has just such a class. std::exception.
Have done C++ since the CFront days
and Java/C# most of this decade. Is
clear to see there's just an enormous
culture gap in how fundamentally
similar things are approached.
No, you've never done C++. You've done CFront, or C with classes. Not C++. There's a huge difference. Quit calling the answers lame, and you might learn something about the language you thought you knew. ;)
Cleanup functions, themselves, are thoroughly lame. They have low cohesion, in that they are expected to perform a series of activities only related in when they happen. They have high coupling, in that they need to have their internals modified when the functions that actually do something are changed. Because of this, they're error-prone.
The try...finally construct is a framework for cleanup functions. It is a language-encouraged way to write lousy code. Moreover, since it encourages writing the same cleanup code over and over, it undermines the DRY principle.
The C++ way is far preferable for these purposes. The cleanup code for a resource is written precisely once, in the destructor. It's in the same place as the rest of the code for that resource, and therefore has good cohesiveness. The cleanup code doesn't have to be put into unrelated modules, and therefore this cuts down on coupling. It is written precisely once, when well designed.
Moreover, the C++ way is much more uniform. C++, with the smart pointer additions, handles all sorts of resources in the same way, while Java handles memory well and provides inadequate constructs to release other resources.
There are plenty of problems with C++, but this isn't one of them. There are ways in which Java is better than C++, but this isn't one of them.
Java would be much better off with a way to implement RAII instead of try...finally.
To avoid having to define a wrapper class for every releasable resource, you may be interested in ScopeGuard (http://www.ddj.com/cpp/184403758) which allows one to create "cleaners" on the fly.
For example:
FILE* fp = SomeExternalFunction();
// Will automatically call fclose(fp) when going out of scope
ScopeGuard file_guard = MakeGuard(fclose, fp);
An Example of how difficult it is to use finally correctly.
Open and closing two files.
Where you want to guarantee that the file is closed correctly.
Waiting for the GC is not an option as the files may be re-used.
In C++
void foo()
{
std::ifstream data("plop");
std::ofstream output("plep");
// DO STUFF
// Files closed auto-magically
}
In a language with no destructors but has a finally clause.
void foo()
{
File data("plop");
File output("plep");
try
{
// DO STUFF
}
finally
{
// Must guarantee that both files are closed.
try {data.close();} catch(Throwable e){/*Ignore*/}
try {output.close();}catch(Throwable e){/*Ignore*/}
}
}
This is a simple example and already the code is getting convoluted. Here we are only trying to marshal 2 simple resources. But as the number of resources that need to be managed increases and/or their complexity increases the use of a finally block becomes harder and harder to use correctly in the presence of exceptions.
The use of finally moves responsibility for correct usage onto the user of an object. By using constructor/destructor mechanism provided by C++ you move the responsibility of correct usage to the designer/implementer of the class. This is inheritanly safer as the designer only needs to do it correctly once at the class level (rather than have different users try and do it correctly in different ways).
Using C++11 with its lambda expressions, I've recently started using the following code to mimic finally:
class FinallyGuard {
private:
std::function<void()> f_;
public:
FinallyGuard(std::function<void()> f) : f_(f) { }
~FinallyGuard() { f_(); }
};
void foo() {
// Code before the try/finally goes here
{ // Open a new scope for the try/finally
FinallyGuard signalEndGuard([&]{
// Code for the finally block goes here
});
// Code for the try block goes here
} // End scope, will call destructor of FinallyGuard
// Code after the try/finally goes here
}
The FinallyGuard is an object which is constructed with a callable function-like argument, preferrably a lambda expression. It will simply remember that function until its destructor is called, which is the case when the object goes out of scope, either due to normal control flow or due to stack unwinding during exception handling. In both cases, the destructor will call the function, thus executing the code in question.
It is a bit strange that you have to write the code for the finally before the code for the try block, but apart from that it actually feels a lot like a genuine try/finally from Java. I guess one should not abuse this for situations where an object with its own proper destructor would be more appropriate, but there are cases where I consider this approach above more suitable. I discussed one such scenario in this question.
As far as I understand things, std::function<void()> will use some pointer indirection and at least one virtual function call to perform its type erasure, so there will be a performance overhead. Don't use this technique in a tight loop where performance is critical. In those cases, a specialized object whose destructor does one thing only would be more appropriate.
C++ destructors make finally redundant. You can get the same effect by moving the cleanup code from finally to corresponding destructors.
I think that you are missing the point of what catch (...) can do.
You say in your example "alas, can't examine the exception". Well, you have no information about the type of the exception. You don't even know if it's a polymorphic type so even if you had some sort of an untyped reference to it, you couldn't even safely attempt a dynamic_cast.
If you know about certain exceptions or exception hierarchies that you can do something with then this is the place for catch blocks with explicity named types.
catch (...) is not often useful in C++. It can be used in places which have to guarantee that they don't throw, or only throw certain contracted exceptions. If you are using catch (...) for cleanup then there is a very good chance that your code is not robustly exception safe in any case.
As mentioned in other answers, if you are using local objects to manage resources (RAII) then it can be surprising and enlightening how few catch blocks you need, often - if you don't need to do anything locally with an exception - even the try block can be redundant as you let the exceptions flow out to the client code that can respond to them while still guaranteeing no resource issues.
To answer your original question, if you need some piece of code to run at the end of a block, exception or no exception, then a recipe would be.
class LocalFinallyReplacement {
~LocalFinallyReplacement() { /* Finally code goes here */ }
};
// ...
{ // some function...
LocalFinallyReplacement lfr; // must be a named object
// do something
}
Note how we can completely do away with try, catch and throw.
If you had data in the function that was originally declared outside the try block that you needed access to in the "finally" block, then you may need to add that to the constructor of the helper class and store it until the destructor. However, at this point I would seriously reconsider whether the problem could be resolved by altering the design of the local resource handling objects as it would imply something awry in the design.
Not completetely offtopic.
Boiler Plating DB Resource Cleanup in Java
sarcasm mode: Isn't the Java idiom wonderful?
I've done plenty of class design and template wrapper design in C++ over those 15 years and done it all the C++ way in terms of destructors cleaning up. Every project, though, also invariably involved the use of C libraries that provided resources with the open it, use it, close it usage model. A try/finally would mean such a resource can just be consumed where it needs to be - in a completely robust manner - and be done with it. The least tedium approach to programming that situation. Could deal with all the other state going on during the logic of that cleanup without having to be scoped away in some wrapper destructor.
I did most of my C++ coding on Windows so could always resort to using Microsoft's __try/__finally for such situations. (Their structured exception handling has some powerful abilities for interacting with exceptions.) Alas, doesn't look like C language has ever ratified any portable exception handling constructs.
That wasn't ideal solution, though, because it was not straightforward to blend C and C++ code in a try block where either style of exception might get thrown. A finally block added to C++ would have been helpful for those situations and would enable portability.
Regarding your addendum-edit, yes closures are being considered for C++0x. They can be used with RAII scoped guards to provide an easy to use solution, check Pizer's weblog. They can also be used to mimic try-finally, see this answer ; but is this really a good idea ? .
Thought I'd add my own solution to this - a kind of smart pointer wrapper for when you have to deal with non-RAII types.
Used like this:
Finaliser< IMAPITable, Releaser > contentsTable;
// now contentsTable can be used as if it were of type IMAPITable*,
// but will be automatically released when it goes out of scope.
So here's the implementation of Finaliser:
/* Finaliser
Wrap an object and run some action on it when it runs out of scope.
(A kind of 'finally.')
* T: type of wrapped object.
* R: type of a 'releaser' (class providing static void release( T* object )). */
template< class T, class R >
class Finaliser
{
private:
T* object_;
public:
explicit Finaliser( T* object = NULL )
{
object_ = object;
}
~Finaliser() throw()
{
release();
}
Finaliser< T, R >& operator=( T* object )
{
if (object_ != object && object_ != NULL)
{
release();
}
object_ = object;
return *this;
}
T* operator->() const
{
return object_;
}
T** operator&()
{
return &object_;
}
operator T*()
{
return object_;
}
private:
void release() throw()
{
R::release< T >( object_ );
}
};
... and here's Releaser:
/* Releaser
Calls Release() on the object (for use with Finaliser). */
class Releaser
{
public:
template< class T > static void release( T* object )
{
if (object != NULL)
{
object->Release();
}
}
};
I have a few different kinds of releaser like this, including one for free() and one for CloseHandle().