In each of my main functions, I would like to catch certain classes of exceptions and convert them to exit codes.
Is there a more elegant solution to this than starting and ending each main function with macros that will paste the implicit try {} catch
I want?
Can I somehow achieve this with the std::set_terminate
functionality?
Example:
int main(){
try { //<- insert this
/*
the business logic goes here
*/
//-> and insert this
}
catch(const Someclass1& e){ return 2; }
catch(const Someclass2& e){ return 3; }
//...
catch(...){ return 1; }
}
A clean way involves using a translation function with all of your exception boilerplate that returns the exit values for the corresponding exception.
template <typename Callable>
int call_and_translate_for_boundary(Callable&& func)
try {
func();
return 0;
}
catch(const Someclass1& e){ return 2; }
catch(const Someclass2& e){ return 3; }
//...
catch(...){ return 1; }
In your own code, you only concern yourself with wrapping your business logic with a lambda and passed that into the translation function so it can capture and translate for you.
int main() {
return call_and_translate_for_boundary([&]{
//business logic here
});
}
I guess you could do something with macros if you want to. Here's how:
#define MY_MAIN int main(int argc, char** argv) try // <- yes, try here
#define MY_CATCH catch (const Someclass1& e){ return 1; } \
catch (const Someclass2& e){ return 1; } \
... \
catch (...) { return -1; }
MY_MAIN
{
// usual business...
return 0;
}
MY_CATCH
The idea is to let the macro write a try catch "around" the main function body, which is all legal.
int main() try { throw 1; } catch (int i) { return 0; }
little example live
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With