CodeGuru Home VC++ / MFC / C++ .NET / C# Visual Basic VB Forums Developer.com
Results 1 to 9 of 9
  1. #1
    Join Date
    May 2002
    Posts
    1,798

    What is the best way to exit from a dll function when an error is encountered?

    I apologize for bringing this up again, but I still have a major problem with it.

    Say I have a dll that performs some mathematical parsing and calculations. The calling function is only a single C -linkage wrapper function in the dll. I can anticipate likely errors and program the dll methods to do several things when an anticipated error is encountered. (For now, let's not worry about unanticipated errors).
    1 - send an error message to the user application using WM_COPYDATA
    2 - throw an exception (assuming the calling app has used the try catch scenario)
    3 - try to gracefully recover from the error within the dll and keep on going (jump to some safe place - but how ??)
    4 - don't throw an exception from within the dll but halt the program (not very nice - the user won't know what happened)

    Previous discussions on the matter have predominantly expressed the opinion that it is a 'bad idea' to throw exceptions from within a dll.

    Long ago there was in use setjmp.h and something like
    Code:
    if(setjmp(e_buf)) return -1;
    , but I believe this was only for old C applications - I'm not really sure. But at least someone back then recognized the need for getting back to a safe place in a process.

    Anyway, I'm throwing (no pun intended) this out again for your thoughts. Your ideas, no matter how far out, will be greatly appreciated.
    Last edited by Mike Pliam; October 23rd, 2012 at 09:44 PM.
    mpliam

  2. #2
    Join Date
    Nov 2000
    Location
    Voronezh, Russia
    Posts
    6,620

    Re: What is the best way to exit from a dll function when an error is encountered?

    Quote Originally Posted by Mike Pliam View Post
    The calling function is only a single C -linkage wrapper function in the dll
    No exception should be let out of the dll, though inside you may use whatever you prefer. The wrapper function should catch all probable exceptions and based on those return error codes explanatory enough, possibly along with some error context data (whatever it really means) which should be optional depending on whether client wants it or not.

    Of course this scenario implies the client makes a synchronous call to the dll function. If this is not the case, and the dll runs its tasks in background, there must be some mechanism for indication/notification of task completion as well as some mechanism of per-task information retrieval. Which means the tasks are identified by some unique id, and this id lets client to query for task context information any time it needs that.
    Best regards,
    Igor

  3. #3
    Join Date
    May 2002
    Posts
    1,798

    Re: What is the best way to exit from a dll function when an error is encountered?

    Quote Originally Posted by Igor Vartanov View Post
    No exception should be let out of the dll, though inside you may use whatever you prefer.
    Do you think then that it is acceptable to use throw/catch mechanism entirely within the dll ? This might allow for a better organized handling of errors within the dll and some orderly exit portal.
    mpliam

  4. #4
    Join Date
    Nov 2000
    Location
    Voronezh, Russia
    Posts
    6,620

    Re: What is the best way to exit from a dll function when an error is encountered?

    If it really does allow, then yes, absolutely. What makes you think it might be not?
    Best regards,
    Igor

  5. #5
    Join Date
    Apr 2000
    Location
    Belgium (Europe)
    Posts
    4,626

    Re: What is the best way to exit from a dll function when an error is encountered?

    1) No. This is an oldfashioned way for making 2 different process communicate with eachother. Since a DLL is loaded in the process space of the host process, no such thing is needed.

    Windows API typically solves this by having the API functions return a bool. You can then use GetLastError() to obtain the actual error message.

    Note that you will also need to formally decide how memory for return strings needs to be deallocated, new/delete/malloc/free won't work because you cannot asssume the dll host has the same runtime you have.

    if you insist on using new/malloc to allocate the string, you will also need to export a string deallocation routine from your dll.
    Alternatively you can use one of the windows API's to allocate the memory, and document that users need to use the appropriate API function to clean up the memory. common in this are returning BSTR's (Ole strings) which have dedicated allocation/deallocation, or use a generic localalloc/globalalloc, ...

    2) exposing exceptions from a dll is possible but ONLY if the DLL host has been created with the same compiler (brand and version) as the host application. Typically this is only a feasible scenario when you create both yourself, or when you have released the DLL in source code form and expect clients to build their own version. Even in this scenario it requires matching builds and an assurance that the dll uses the same runtime library as the dll host. This in effect means the runtime will need to be a dll also, and it means both the dll and the dll host need to be built as a unit by you.

    Otherwise all bets are off, there is no 'standard' for dll's to "export thrown exceptions", every compiler does it their way, even different versions may do it differently, and some languages that may use your dll may not even have an exception handling mechanism.

    the same thisn is true for the 'old' setjmp() approach. This will only work if the dll and the dll host are built as a unit and are built specifically around that approach).


    3) This may be an option. You'll have to decide if continuing "graceful" is at all possible or desired. I have at least one dll where somethign like this is being done. On error, all following actions on the object that failed will simply do nothing and return a special error number indicating the call could not continue due to a previous error that hasn't been resolved yet.
    While possible, it requires extra effor on the part of the party making the dll.

    4) A very very bad idea
    While you can blatantly terminate the process, this will leave the process aborting in an undefined state. All sorts of resources may have been allocated that don't automatically get freed. (network connections, database connections, cache entries, ...) depending on the sort of program using your dll, this could be anything from merely annoying to catastrophic (oops you just crashed the program handling the cooling rods in a nuclear power plant, the plant overheats, you just killed thousands of people and poisoned the environment for thousands of years (yes I exagerate, you get the point I hope)).

    The only time a termination should be considered is inside the program code (or if you make both the dll and the program as a unit, the dll not to be used for anything else) and only if you're writing the program and even in that case it is sign of poor handling.


    ---
    TLDR: a lot of this depends on who makes the dll and who makes the hosting program and/or how strictly you can control how they are built.

  6. #6
    Join Date
    Apr 2000
    Location
    Belgium (Europe)
    Posts
    4,626

    Re: What is the best way to exit from a dll function when an error is encountered?

    basically:
    if you make both yourself: do whatever you want that works. Anything else is "guidelines".

    If you make the dll, and users/clients of this dll still need to make their programs:
    do whatever you want that is as compatible as possible with all the compilers you want to support, then document how users are required to respond to your way of handling errors.

    If you make an addon dll that needs to work in a preexisting program:
    do whatever method the preexisting program prescribes.

    ...

  7. #7
    Join Date
    May 2002
    Posts
    1,798

    Re: What is the best way to exit from a dll function when an error is encountered?

    Thank you for taking the time to share your ideas.

    I am disappointed with your views on using WM_COPYDATA mechanism to generate error and warning messages from the dll. I have gotten this to work quite well. The problem I have with this as that I have not figured out what to do after the error has been encountered and the message sent. But I still like the idea because if one has several hundred possible anticipated errors, it is relatively simple to fashion specific error messages for each, whereas, if all the errors were sent as integers via the wrapper, the burden of deciphering them would be on the caller.

    I had not really planned to distribute the dll under consideration separate from an application, but that approach has considerable attraction in general, so that the more independent the client code is from the dll, the easier it should be to use.

    Anyway, you've given me alot to think about and I plan to experiment with using the wrapper to return an error code integer. Or if I was really clever, I might try to fashion a GetLastError method for the client to use.
    mpliam

  8. #8
    Join Date
    Oct 2008
    Posts
    1,456

    Re: What is the best way to exit from a dll function when an error is encountered?

    Quote Originally Posted by Mike Pliam View Post
    Say I have a dll that performs some mathematical parsing and calculations.
    if those messages are so many and <so> commonly occuring then it could make sense to setup some true comunication mechanims between the "parser" and the client code.

    I mean, if I understood you correctly, those "anticipated errors" are similar to, say, a compiler output, or the messages/warnings output of one of those symbolic mathematical programs ( like Mathematica, Maple, etc... ), aren't they ? if yes, then are they really <errors> ? or do they just represent a specific state of the parser and the client to which both should react accordingly ?
    I don't know because I'm just guessing ... but, if I'm right then it could be the time to think a better and more coordinated way of managing the relative states of the caller and the parser, from a more general POV than mere error handling.

  9. #9
    Join Date
    Nov 2000
    Location
    Voronezh, Russia
    Posts
    6,620

    Re: What is the best way to exit from a dll function when an error is encountered?

    Quote Originally Posted by Mike Pliam View Post
    I am disappointed with your views on using WM_COPYDATA mechanism to generate error and warning messages from the dll. I have gotten this to work quite well. The problem I have with this as that I have not figured out what to do after the error has been encountered and the message sent. But I still like the idea because if one has several hundred possible anticipated errors, it is relatively simple to fashion specific error messages for each, whereas, if all the errors were sent as integers via the wrapper, the burden of deciphering them would be on the caller.
    Mike, the worst thing about WM_COPYDATA is that client is obliged to provide a receiver window to be able to catch dll errors. Too pushy design, I would say, from dll client standpoint. Another point was already mentioned by OReubens: the message is intended to transfer data block between two processes, and using it inside the same process is obviously an overkill.

    As for the client's burden of deciphering, typically DLLs provide string resources for FormatMessage mechanism, this way making the burden be all DLL's. If you never want to mess with message compiler, your DLL can provide some function like GetErrorCodeText to translate the code to a formatted string. Please note, this translation is required for error logging only, but app may be guided by properly designed error codes alright, without any need in deciphering.

    I had not really planned to distribute the dll under consideration separate from an application, but that approach has considerable attraction in general, so that the more independent the client code is from the dll, the easier it should be to use.
    Let me confirm this with you, you mean sending WM_COPYDATA should provide more independence to client in your situation? If you really think that, you're definitely wrong. The real independence is being able to have some options in workflow control, and wasting no memory on unnecessary data copy when the latter is not mandatory for decision making.

    Please analyze Windows API or CRT functions design in their most. Those return error codes and let client to omit receiver buffer passing when it's optional. They allow deferred error code refinement (by means of GetLastError or errno) and further translation of the code to text. They provide descriptive error code sets. See anything common with what I said above?
    Last edited by Igor Vartanov; October 28th, 2012 at 01:40 PM.
    Best regards,
    Igor

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  





Click Here to Expand Forum to Full Width

Featured