1

I am writing an exception handling library in C and i ran into a bump:

#define TRY do{ jmp_buf ex_buf__; switch( setjmp(ex_buf__) ){ case 0:
#define FINALLY break; } default:
#define CATCH(x) break; case x:
#define ETRY } }while(0)
#define THROW(x) longjmp(ex_buf__, x)

In my current implementation of try catch throw, I won't be able to throw an exception from inside a method called from inside the try block because the jmp_buf variable is local. How would i make that possible? I thought about a global variable but that would not allow me to have nested try catch blocks.

Jean-Luc Nacif Coelho
  • 1,006
  • 3
  • 14
  • 30
  • Id on´t think this is possible without modifying *all* functions and function calls you have. C simply has no exceptions. – deviantfan Feb 28 '14 at 13:07

2 Answers2

4

You need to use a global jump buffer, because it needs to be visible to your "clients". You could, for example, save the old jump buffer in a try block, and restore it after its use.

In general, I would not recommend this approach at all, though. Trying to retrofit features into a language is fraught with peril, not the least of which would be the following code:

for ;; { 
  TRY {
    if (someVar) {
      break;
    }
  }
  FINALLY {
    doIt()
  }
  ETRY
}
Norwæ
  • 1,575
  • 8
  • 18
  • 2
    Agreed: it is not a good idea to try to implement Object-oriented specific features in `C`. If you "need" to do such a thing you probably had chosen the wrong language... – n0p Feb 28 '14 at 13:16
  • .. not that try/finally/catch has anything at all to do with object orientation. Which, incidentally, works just fine in C. – perh Feb 28 '14 at 13:33
  • Just a reminder that C++ is implemented in C.... Anyways this is a library for homework that I am making since it has to be done in C and i don't like C. Good approach though. Thanks a lot! – Jean-Luc Nacif Coelho Feb 28 '14 at 14:02
  • 2
    @Jean-LucNacifCoelho "C++ is implemented in C" - no. just no. – Andreas Grapentin Feb 28 '14 at 15:00
3

Use a stack of jmp_buf's. Or better yet, use the existing CII library, which has been designed, built, and tested for this purpose.

Norman Ramsey
  • 198,648
  • 61
  • 360
  • 533
  • 1- Creating a local variable within a newly created scope suffices to save the context, as the compiler allows you to reuse variable names in different scopes. 2- "Use this already implemented library" is never a good answer. – Jean-Luc Nacif Coelho Jan 01 '15 at 21:05