15 July 2004

Asserts, error codes, and exceptions

Herb Sutter has a poorly written, but well-intentioned and informative, article on error reporting in the August 2004 C/C++ Users Journal. In it, he summarizes the difference between asserts, error codes, and exceptions. He also defines the three (and only three) types of errors that occur.

Three types of errors:

  • A condition that prevents the function from meeting a precondition (for example, a parameter restriction) of another function that must be called.

  • A condition that prevents the function from establishing one of its own postconditions. If the function has a return value, then producing a valid return value object is a postcondition.

  • A condition that prevents the function from reestablishing an invariant that it is responsible for maintaining. This is a special kind of postcondition that applies particularly to member functions; an essential postcondition of every nonprivate member function is that it must reestablish its class's invariants.

He emphasizes the preconditions, postconditions, and invariants, and says that any other condition is not an error and should not be reported as an error.

So, consider a function that opens a file with a specific name and remembers the last file opened (my example):

std::string g_currentFile;
void OpenFile(const std::string& name, std::ifstream& file);
  • An empty name string is a precondition error,
  • A name that has no matching file is a postcondition error (if the function was not intended to be a search function),
  • Altering g_currentFile when the function is not successful is an invariant error

Programming mistakes are guarded using assertions. This mean that anything outside the errors described above should be asserted.

Functions must provide one of three safety guarantees. These were originally defined by Dave Abrahams here.

  • Basic guarantee: leave your program in a valid state,
  • Strong guarantee: leave your program in the intended final state, or in the original state,
  • Nofail (nothrow) guarantee: the function will never fail

Finally, the benefits of exceptions over error codes:

  • Exceptions can't be silently ignored. You must explicity catch them.
  • Exceptions propagate automatically.
  • Exception handling removes error handling and recovery from the main line of control flow.
  • Exception handling is better than the alternatives for reporting errors from constructors and operators.
[ posted by sstrader on 15 July 2004 at 11:29:23 AM in Programming ]