The XLL+ Function Wizard creates three C++ functions for each add-in function. One is the wrapper function called by Excel 2003 and below, another is the wrapper function called by Excel 2007 and above, and the third is the common implementation function called by both wrapper functions.
The wrapper functions call the implementation function within a try-catch block, which catches exceptions of type CXlRuntimeException. While validating user input, the implementation function calls a number of XLL+ library functions which may throw exceptions of type CXlRuntimeException.
In the wrapper function the application-level method CXllApp::DisplayException() is called, which converts the caught exception into an error result to be returned to Excel.
The pseudo-code below illustrates this exception flow.
If your code raises an exception which is derived from CXlRuntimeException, then you do not need to handle it specially - the wrapper function will handle and translate it for you.
If your code raises exceptions of some other type, then you must catch them. Depending on your preference in programming style, you can deal with them in one of two ways.
Examples of the two techniques are shown below.
The first block of code below was used in the
HISTVOL
add-in function, to trap a C++ exception and translate immediately to
#NUM!
.
CXlOper* HISTVOL_Impl(CXlOper& xloResult, const CXlOper* Prices_op, const CXlOper* DaysPerYear_op) { ... //}}XLP_SRC try { xloResult = CalcHistVol(Prices, DaysPerYear); } catch(const char*) { xloResult = xlerrNum; } return xloResult.Ret(); }
Another approach could have been used: to catch the error and rethrow it with a rich error message.
CXlOper* HISTVOL_Impl(CXlOper& xloResult, const CXlOper* Prices_op, const CXlOper* DaysPerYear_op) { ... //}}XLP_SRC try { xloResult = CalcHistVol(Prices, DaysPerYear); } catch(const char* ex) { throw CXlRuntimeException(ex); } return xloResult.Ret(); }
With this approach, the error string originally thrown by
CalcHistVol()
is caught by the wrapper function
and passed to CXllApp::DisplayException(), so you
get errors such as:
#ERROR: zero value #ERROR: negative value #ERROR: too few points