Index: src/libcfa/Makefile.am
===================================================================
--- src/libcfa/Makefile.am	(revision cd17862cca0dd2992a5f5a031b06b60cff940efb)
+++ src/libcfa/Makefile.am	(revision 67fa9f99aebe68e73094bddc3ebf1c0d1c2d7844)
@@ -50,5 +50,5 @@
 
 libobjs = ${headers:=.o}
-libsrc = libcfa-prelude.c interpose.c libhdr/libdebug.c ${headers:=.c}
+libsrc = libcfa-prelude.c interpose.c libhdr/libdebug.c ${headers:=.c} exception.c
 
 # not all platforms support concurrency, add option do disable it
Index: src/libcfa/Makefile.in
===================================================================
--- src/libcfa/Makefile.in	(revision cd17862cca0dd2992a5f5a031b06b60cff940efb)
+++ src/libcfa/Makefile.in	(revision 67fa9f99aebe68e73094bddc3ebf1c0d1c2d7844)
@@ -102,5 +102,5 @@
 	containers/pair.c containers/result.c containers/vector.c \
 	concurrency/coroutine.c concurrency/thread.c \
-	concurrency/kernel.c concurrency/monitor.c \
+	concurrency/kernel.c concurrency/monitor.c exception.c \
 	concurrency/CtxSwitch-@MACHINE_TYPE@.S concurrency/alarm.c \
 	concurrency/invoke.c concurrency/preemption.c
@@ -126,5 +126,5 @@
 	libcfa_d_a-interpose.$(OBJEXT) \
 	libhdr/libcfa_d_a-libdebug.$(OBJEXT) $(am__objects_2) \
-	$(am__objects_3)
+	libcfa_d_a-exception.$(OBJEXT) $(am__objects_3)
 am_libcfa_d_a_OBJECTS = $(am__objects_4)
 libcfa_d_a_OBJECTS = $(am_libcfa_d_a_OBJECTS)
@@ -136,5 +136,5 @@
 	containers/pair.c containers/result.c containers/vector.c \
 	concurrency/coroutine.c concurrency/thread.c \
-	concurrency/kernel.c concurrency/monitor.c \
+	concurrency/kernel.c concurrency/monitor.c exception.c \
 	concurrency/CtxSwitch-@MACHINE_TYPE@.S concurrency/alarm.c \
 	concurrency/invoke.c concurrency/preemption.c
@@ -158,5 +158,5 @@
 	libcfa_a-interpose.$(OBJEXT) \
 	libhdr/libcfa_a-libdebug.$(OBJEXT) $(am__objects_6) \
-	$(am__objects_7)
+	libcfa_a-exception.$(OBJEXT) $(am__objects_7)
 am_libcfa_a_OBJECTS = $(am__objects_8)
 libcfa_a_OBJECTS = $(am_libcfa_a_OBJECTS)
@@ -328,5 +328,5 @@
 libobjs = ${headers:=.o}
 libsrc = libcfa-prelude.c interpose.c libhdr/libdebug.c ${headers:=.c} \
-	$(am__append_4)
+	exception.c $(am__append_4)
 libcfa_a_SOURCES = ${libsrc}
 libcfa_a_CFLAGS = -nodebug -O2
@@ -514,4 +514,5 @@
 
 @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libcfa_a-assert.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libcfa_a-exception.Po@am__quote@
 @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libcfa_a-fstream.Po@am__quote@
 @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libcfa_a-interpose.Po@am__quote@
@@ -524,4 +525,5 @@
 @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libcfa_a-stdlib.Po@am__quote@
 @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libcfa_d_a-assert.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libcfa_d_a-exception.Po@am__quote@
 @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libcfa_d_a-fstream.Po@am__quote@
 @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libcfa_d_a-interpose.Po@am__quote@
@@ -850,4 +852,11 @@
 @am__fastdepCC_FALSE@	$(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libcfa_d_a_CFLAGS) $(CFLAGS) -c -o concurrency/libcfa_d_a-monitor.obj `if test -f 'concurrency/monitor.c'; then $(CYGPATH_W) 'concurrency/monitor.c'; else $(CYGPATH_W) '$(srcdir)/concurrency/monitor.c'; fi`
 
+libcfa_d_a-exception.obj: exception.c
+@am__fastdepCC_TRUE@	$(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libcfa_d_a_CFLAGS) $(CFLAGS) -MT libcfa_d_a-exception.obj -MD -MP -MF $(DEPDIR)/libcfa_d_a-exception.Tpo -c -o libcfa_d_a-exception.obj `if test -f 'exception.c'; then $(CYGPATH_W) 'exception.c'; else $(CYGPATH_W) '$(srcdir)/exception.c'; fi`
+@am__fastdepCC_TRUE@	$(AM_V_at)$(am__mv) $(DEPDIR)/libcfa_d_a-exception.Tpo $(DEPDIR)/libcfa_d_a-exception.Po
+@AMDEP_TRUE@@am__fastdepCC_FALSE@	$(AM_V_CC)source='exception.c' object='libcfa_d_a-exception.obj' libtool=no @AMDEPBACKSLASH@
+@AMDEP_TRUE@@am__fastdepCC_FALSE@	DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
+@am__fastdepCC_FALSE@	$(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libcfa_d_a_CFLAGS) $(CFLAGS) -c -o libcfa_d_a-exception.obj `if test -f 'exception.c'; then $(CYGPATH_W) 'exception.c'; else $(CYGPATH_W) '$(srcdir)/exception.c'; fi`
+
 concurrency/libcfa_d_a-alarm.o: concurrency/alarm.c
 @am__fastdepCC_TRUE@	$(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libcfa_d_a_CFLAGS) $(CFLAGS) -MT concurrency/libcfa_d_a-alarm.o -MD -MP -MF concurrency/$(DEPDIR)/libcfa_d_a-alarm.Tpo -c -o concurrency/libcfa_d_a-alarm.o `test -f 'concurrency/alarm.c' || echo '$(srcdir)/'`concurrency/alarm.c
@@ -1143,4 +1152,11 @@
 @AMDEP_TRUE@@am__fastdepCC_FALSE@	DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
 @am__fastdepCC_FALSE@	$(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libcfa_a_CFLAGS) $(CFLAGS) -c -o concurrency/libcfa_a-monitor.obj `if test -f 'concurrency/monitor.c'; then $(CYGPATH_W) 'concurrency/monitor.c'; else $(CYGPATH_W) '$(srcdir)/concurrency/monitor.c'; fi`
+
+libcfa_a-exception.obj: exception.c
+@am__fastdepCC_TRUE@	$(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libcfa_a_CFLAGS) $(CFLAGS) -MT libcfa_a-exception.obj -MD -MP -MF $(DEPDIR)/libcfa_a-exception.Tpo -c -o libcfa_a-exception.obj `if test -f 'exception.c'; then $(CYGPATH_W) 'exception.c'; else $(CYGPATH_W) '$(srcdir)/exception.c'; fi`
+@am__fastdepCC_TRUE@	$(AM_V_at)$(am__mv) $(DEPDIR)/libcfa_a-exception.Tpo $(DEPDIR)/libcfa_a-exception.Po
+@AMDEP_TRUE@@am__fastdepCC_FALSE@	$(AM_V_CC)source='exception.c' object='libcfa_a-exception.obj' libtool=no @AMDEPBACKSLASH@
+@AMDEP_TRUE@@am__fastdepCC_FALSE@	DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
+@am__fastdepCC_FALSE@	$(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libcfa_a_CFLAGS) $(CFLAGS) -c -o libcfa_a-exception.obj `if test -f 'exception.c'; then $(CYGPATH_W) 'exception.c'; else $(CYGPATH_W) '$(srcdir)/exception.c'; fi`
 
 concurrency/libcfa_a-alarm.o: concurrency/alarm.c
Index: src/libcfa/exception.c
===================================================================
--- src/libcfa/exception.c	(revision cd17862cca0dd2992a5f5a031b06b60cff940efb)
+++ src/libcfa/exception.c	(revision 67fa9f99aebe68e73094bddc3ebf1c0d1c2d7844)
@@ -44,16 +44,16 @@
 // RESUMPTION ================================================================
 
-void __cfaehm__throw_resume(exception except) {
-
-	// DEBUG
-	printf("Throwing resumption exception %d\n", except);
-
-	struct __try_resume_node * original_head = shared_stack.current_resume;
-	struct __try_resume_node * current =
+void __cfaehm__throw_resumption(exception * except) {
+
+	// DEBUG
+	printf("Throwing resumption exception %d\n", *except);
+
+	struct __cfaehm__try_resume_node * original_head = shared_stack.current_resume;
+	struct __cfaehm__try_resume_node * current =
 		(original_head) ? original_head->next : shared_stack.top_resume;
 
 	for ( ; current ; current = current->next) {
 		shared_stack.current_resume = current;
-		if (current->try_to_handle(except)) {
+		if (current->handler(except)) {
 			shared_stack.current_resume = original_head;
 			return;
@@ -61,9 +61,9 @@
 	}
 
-	printf("Unhandled exception %d\n", except);
+	printf("Unhandled exception %d\n", *except);
 	shared_stack.current_resume = original_head;
 
 	// Fall back to termination:
-	__cfaehm__throw_terminate(except);
+	__cfaehm__throw_termination(except);
 	// TODO: Default handler for resumption.
 }
@@ -73,12 +73,12 @@
  * after the node is built but before it is made the top node.
  */
-void __try_resume_setup(struct __try_resume_node * node,
-                        bool (*handler)(exception except)) {
+void __cfaehm__try_resume_setup(struct __cfaehm__try_resume_node * node,
+                        int (*handler)(exception * except)) {
 	node->next = shared_stack.top_resume;
-	node->try_to_handle = handler;
+	node->handler = handler;
 	shared_stack.top_resume = node;
 }
 
-void __try_resume_cleanup(struct __try_resume_node * node) {
+void __cfaehm__try_resume_cleanup(struct __cfaehm__try_resume_node * node) {
 	shared_stack.top_resume = node->next;
 }
@@ -111,10 +111,10 @@
 }
 
-void __cfaehm__throw_terminate( int val ) {
+void __cfaehm__throw_termination( exception * val ) {
 	// Store the current exception
-	shared_stack.current_exception = val;
-
-	// DEBUG
-	printf("Throwing termination exception %d\n", val);
+	shared_stack.current_exception = *val;
+
+	// DEBUG
+	printf("Throwing termination exception %d\n", *val);
 
 	// Call stdlibc to raise the exception
@@ -147,9 +147,9 @@
 
 // Nesting this the other way would probably be faster.
-void __cfaehm__rethrow_terminate(void) {
+void __cfaehm__rethrow_termination(void) {
 	// DEBUG
 	printf("Rethrowing termination exception\n");
 
-	__cfaehm__throw_terminate(shared_stack.current_exception);
+	__cfaehm__throw_termination(&shared_stack.current_exception);
 }
 
@@ -322,7 +322,7 @@
 // for details
 __attribute__((noinline))
-void __try_terminate(void (*try_block)(),
-		void (*catch_block)(int index, exception except),
-		__attribute__((unused)) int (*match_block)(exception except)) {
+void __cfaehm__try_terminate(void (*try_block)(),
+		void (*catch_block)(int index, exception * except),
+		__attribute__((unused)) int (*match_block)(exception * except)) {
 	//! volatile int xy = 0;
 	//! printf("%p %p %p %p\n", &try_block, &catch_block, &match_block, &xy);
@@ -364,5 +364,5 @@
 	// Exception handler
 	catch_block(shared_stack.current_handler_index,
-	            shared_stack.current_exception);
+	            &shared_stack.current_exception);
 }
 
@@ -384,11 +384,11 @@
 	// Body uses language specific data and therefore could be modified arbitrarily
 	".LLSDACSBCFA2:\n"						// BODY start
-	"	.uleb128 .TRYSTART-__try_terminate\n"		// Handled area start  (relative to start of function)
+	"	.uleb128 .TRYSTART-__cfaehm__try_terminate\n"		// Handled area start  (relative to start of function)
 	"	.uleb128 .TRYEND-.TRYSTART\n"				// Handled area length
-	"	.uleb128 .CATCH-__try_terminate\n"				// Hanlder landing pad adress  (relative to start of function)
+	"	.uleb128 .CATCH-__cfaehm__try_terminate\n"				// Hanlder landing pad adress  (relative to start of function)
 	"	.uleb128 1\n"						// Action code, gcc seems to use always 0
 	".LLSDACSECFA2:\n"						// BODY end
 	"	.text\n"							// TABLE footer
-	"	.size	__try_terminate, .-__try_terminate\n"
+	"	.size	__cfaehm__try_terminate, .-__cfaehm__try_terminate\n"
 	"	.ident	\"GCC: (Ubuntu 6.2.0-3ubuntu11~16.04) 6.2.0 20160901\"\n"
 //	"	.section	.note.GNU-stack,\"x\",@progbits\n"
Index: src/libcfa/exception.h
===================================================================
--- src/libcfa/exception.h	(revision cd17862cca0dd2992a5f5a031b06b60cff940efb)
+++ src/libcfa/exception.h	(revision 67fa9f99aebe68e73094bddc3ebf1c0d1c2d7844)
@@ -38,13 +38,13 @@
 // Data structure creates a list of resume handlers.
 struct __cfaehm__try_resume_node {
-    __cfaehm__try_resume_node * next;
+    struct __cfaehm__try_resume_node * next;
     int (*handler)(exception * except);
 };
 
 void __cfaehm__try_resume_setup(
-    __cfaehm__try_resume_node * node,
+    struct __cfaehm__try_resume_node * node,
     int (*handler)(exception * except));
 void __cfaehm__try_resume_cleanup(
-    __cfaehm__try_resume_node * node);
+    struct __cfaehm__try_resume_node * node);
 
 // Check for a standard way to call fake deconstructors.
Index: src/libcfa/fstream
===================================================================
--- src/libcfa/fstream	(revision cd17862cca0dd2992a5f5a031b06b60cff940efb)
+++ src/libcfa/fstream	(revision 67fa9f99aebe68e73094bddc3ebf1c0d1c2d7844)
@@ -10,6 +10,6 @@
 // Created On       : Wed May 27 17:56:53 2015
 // Last Modified By : Peter A. Buhr
-// Last Modified On : Mon May 15 18:11:09 2017
-// Update Count     : 104
+// Last Modified On : Sat Jul  1 16:37:53 2017
+// Update Count     : 112
 //
 
@@ -24,4 +24,5 @@
 	_Bool sepDefault;
 	_Bool sepOnOff;
+	_Bool lastSepOn;
 	const char * sepCur;
 	char separator[separateSize];
@@ -35,4 +36,5 @@
 const char * sepGetCur( ofstream * );
 void sepSetCur( ofstream *, const char * );
+_Bool lastSepOn( ofstream * );
 
 // public
Index: src/libcfa/fstream.c
===================================================================
--- src/libcfa/fstream.c	(revision cd17862cca0dd2992a5f5a031b06b60cff940efb)
+++ src/libcfa/fstream.c	(revision 67fa9f99aebe68e73094bddc3ebf1c0d1c2d7844)
@@ -10,6 +10,6 @@
 // Created On       : Wed May 27 17:56:53 2015
 // Last Modified By : Peter A. Buhr
-// Last Modified On : Mon May 15 18:11:11 2017
-// Update Count     : 234
+// Last Modified On : Sat Jul  1 16:37:54 2017
+// Update Count     : 242
 //
 
@@ -33,4 +33,5 @@
 	this->sepDefault = sepDefault;
 	this->sepOnOff = sepOnOff;
+	this->lastSepOn = false;
 	sepSet( this, separator );
 	sepSetCur( this, sepGet( this ) );
@@ -39,5 +40,6 @@
 
 // private
-_Bool sepPrt( ofstream * os ) { return os->sepOnOff; }
+_Bool lastSepOn( ofstream * os ) { return os->lastSepOn; }
+_Bool sepPrt( ofstream * os ) { os->lastSepOn = false; return os->sepOnOff; }
 void sepReset( ofstream * os ) { os->sepOnOff = os->sepDefault; }
 void sepReset( ofstream * os, _Bool reset ) { os->sepDefault = reset; os->sepOnOff = os->sepDefault; }
@@ -46,10 +48,11 @@
 
 // public
-void sepOn( ofstream * os ) { os->sepOnOff = 1; }
-void sepOff( ofstream * os ) { os->sepOnOff = 0; }
+void sepOn( ofstream * os ) { os->lastSepOn = true; os->sepOnOff = true; }
+void sepOff( ofstream * os ) { os->lastSepOn = false; os->sepOnOff = 0; }
 
 _Bool sepDisable( ofstream *os ) {
 	_Bool temp = os->sepDefault;
 	os->sepDefault = false;
+	os->lastSepOn = false;
 	sepReset( os );
 	return temp;
@@ -92,5 +95,5 @@
 		exit( EXIT_FAILURE );
 	} // if
-	?{}( os, file, 1, 0, " ", ", " );
+	?{}( os, file, true, false, " ", ", " );
 } // open
 
@@ -132,7 +135,7 @@
 } // fmt
 
-static ofstream soutFile = { (FILE *)(&_IO_2_1_stdout_), 1, 0, " ", ", " };
+static ofstream soutFile = { (FILE *)(&_IO_2_1_stdout_), true, false, " ", ", " };
 ofstream *sout = &soutFile;
-static ofstream serrFile = { (FILE *)(&_IO_2_1_stderr_), 1, 0, " ", ", " };
+static ofstream serrFile = { (FILE *)(&_IO_2_1_stderr_), true, false, " ", ", " };
 ofstream *serr = &serrFile;
 
Index: src/libcfa/iostream
===================================================================
--- src/libcfa/iostream	(revision cd17862cca0dd2992a5f5a031b06b60cff940efb)
+++ src/libcfa/iostream	(revision 67fa9f99aebe68e73094bddc3ebf1c0d1c2d7844)
@@ -10,6 +10,6 @@
 // Created On       : Wed May 27 17:56:53 2015
 // Last Modified By : Peter A. Buhr
-// Last Modified On : Mon May 15 18:08:44 2017
-// Update Count     : 105
+// Last Modified On : Sun Jul  2 08:42:56 2017
+// Update Count     : 110
 //
 
@@ -26,4 +26,5 @@
 	const char * sepGetCur( ostype * );					// get current separator string
 	void sepSetCur( ostype *, const char * );			// set current separator string
+	_Bool lastSepOn( ostype * );						// last manipulator is setOn (context sensitive)
 	// public
 	void sepOn( ostype * );								// turn separator state on
@@ -43,9 +44,9 @@
 	ostype * write( ostype *, const char *, unsigned long int );
 	int fmt( ostype *, const char fmt[], ... );
-};
+}; // ostream
 
 trait writeable( otype T ) {
 	forall( dtype ostype | ostream( ostype ) ) ostype * ?|?( ostype *, T );
-};
+}; // writeable
 
 // implement writable for intrinsic types
@@ -103,9 +104,9 @@
 	istype * ungetc( istype *, char );
 	int fmt( istype *, const char fmt[], ... );
-};
+}; // istream
 
 trait readable( otype T ) {
 	forall( dtype istype | istream( istype ) ) istype * ?|?( istype *, T );
-};
+}; // readable
 
 forall( dtype istype | istream( istype ) ) istype * ?|?( istype *, char * );
Index: src/libcfa/iostream.c
===================================================================
--- src/libcfa/iostream.c	(revision cd17862cca0dd2992a5f5a031b06b60cff940efb)
+++ src/libcfa/iostream.c	(revision 67fa9f99aebe68e73094bddc3ebf1c0d1c2d7844)
@@ -10,6 +10,6 @@
 // Created On       : Wed May 27 17:56:53 2015
 // Last Modified By : Peter A. Buhr
-// Last Modified On : Mon May  8 18:24:23 2017
-// Update Count     : 369
+// Last Modified On : Sun Jul  2 08:54:02 2017
+// Update Count     : 375
 //
 
@@ -201,6 +201,6 @@
 forall( dtype ostype, otype T, ttype Params | ostream( ostype ) | writeable( T ) | { ostype * ?|?( ostype *, Params ); } )
 ostype * ?|?( ostype * os, T arg, Params rest ) {
+	os | arg;											// print first argument
 	sepSetCur( os, sepGetTuple( os ) );					// switch to tuple separator
-	os | arg;											// print first argument
 	os | rest;											// print remaining arguments
 	sepSetCur( os, sepGet( os ) );						// switch to regular separator
@@ -217,4 +217,5 @@
 forall( dtype ostype | ostream( ostype ) )
 ostype * endl( ostype * os ) {
+	if ( lastSepOn( os ) ) fmt( os, "%s", sepGetCur( os ) );
 	os | '\n';
 	flush( os );
Index: src/libcfa/lsda.h
===================================================================
--- src/libcfa/lsda.h	(revision 67fa9f99aebe68e73094bddc3ebf1c0d1c2d7844)
+++ src/libcfa/lsda.h	(revision 67fa9f99aebe68e73094bddc3ebf1c0d1c2d7844)
@@ -0,0 +1,262 @@
+//This code was stolen from gcc to read exception tables
+
+
+/* If using C++, references to abort have to be qualified with std::.  */
+#if __cplusplus
+#define __gxx_abort std::abort
+#else
+#define __gxx_abort abort
+#endif
+
+/* Pointer encodings, from dwarf2.h.  */
+#define DW_EH_PE_absptr         0x00
+#define DW_EH_PE_omit           0xff
+
+#define DW_EH_PE_uleb128        0x01
+#define DW_EH_PE_udata2         0x02
+#define DW_EH_PE_udata4         0x03
+#define DW_EH_PE_udata8         0x04
+#define DW_EH_PE_sleb128        0x09
+#define DW_EH_PE_sdata2         0x0A
+#define DW_EH_PE_sdata4         0x0B
+#define DW_EH_PE_sdata8         0x0C
+#define DW_EH_PE_signed         0x08
+
+#define DW_EH_PE_pcrel          0x10
+#define DW_EH_PE_textrel        0x20
+#define DW_EH_PE_datarel        0x30
+#define DW_EH_PE_funcrel        0x40
+#define DW_EH_PE_aligned        0x50
+
+#define DW_EH_PE_indirect	0x80
+
+
+
+int handler_found = 0;
+
+/* Given an encoding, return the number of bytes the format occupies.
+This is only defined for fixed-size encodings, and so does not
+include leb128.  */
+static unsigned int size_of_encoded_value (unsigned char encoding) __attribute__ ((unused));
+
+static unsigned int size_of_encoded_value (unsigned char encoding)
+{
+	if (encoding == DW_EH_PE_omit) return 0;
+
+	switch (encoding & 0x07) {
+		case DW_EH_PE_absptr: return sizeof (void *);
+		case DW_EH_PE_udata2: return 2;
+		case DW_EH_PE_udata4: return 4;
+		case DW_EH_PE_udata8: return 8;
+	}
+	__gxx_abort ();
+}
+
+/* Given an encoding and an _Unwind_Context, return the base to which
+the encoding is relative.  This base may then be passed to
+read_encoded_value_with_base for use when the _Unwind_Context is
+not available.  */
+static _Unwind_Ptr base_of_encoded_value (unsigned char encoding, struct _Unwind_Context *context)
+{
+	if (encoding == DW_EH_PE_omit) return 0;
+
+	switch (encoding & 0x70) {
+		case DW_EH_PE_absptr:
+		case DW_EH_PE_pcrel:
+		case DW_EH_PE_aligned:
+			return 0;
+		case DW_EH_PE_textrel:
+			return _Unwind_GetTextRelBase (context);
+		case DW_EH_PE_datarel:
+			return _Unwind_GetDataRelBase (context);
+		case DW_EH_PE_funcrel:
+			return _Unwind_GetRegionStart (context);
+	}
+	__gxx_abort ();
+}
+
+/* Read an unsigned leb128 value from P, store the value in VAL, return
+P incremented past the value.  We assume that a word is large enough to
+hold any value so encoded; if it is smaller than a pointer on some target,
+pointers should not be leb128 encoded on that target.  */
+static const unsigned char * read_uleb128 (const unsigned char *p, _uleb128_t *val)
+{
+	unsigned int shift = 0;
+	unsigned char byte;
+	_uleb128_t result;
+
+	result = 0;
+	do
+	{
+		byte = *p++;
+		result |= ((_uleb128_t)byte & 0x7f) << shift;
+		shift += 7;
+	}
+	while (byte & 0x80);
+
+	*val = result;
+	return p;
+}
+
+/* Similar, but read a signed leb128 value.  */
+static const unsigned char * read_sleb128 (const unsigned char *p, _sleb128_t *val)
+{
+	unsigned int shift = 0;
+	unsigned char byte;
+	_uleb128_t result;
+
+	result = 0;
+	do
+	{
+		byte = *p++;
+		result |= ((_uleb128_t)byte & 0x7f) << shift;
+		shift += 7;
+	}
+	while (byte & 0x80);
+
+	/* Sign-extend a negative value.  */
+	if (shift < 8 * sizeof(result) && (byte & 0x40) != 0) result |= -(((_uleb128_t)1L) << shift);
+
+	*val = (_sleb128_t) result;
+	return p;
+}
+
+/* Load an encoded value from memory at P.  The value is returned in VAL;
+The function returns P incremented past the value.  BASE is as given
+by base_of_encoded_value for this encoding in the appropriate context.  */
+
+static const unsigned char * read_encoded_value_with_base (unsigned char encoding, _Unwind_Ptr base, const unsigned char *p, _Unwind_Ptr *val)
+{
+	union unaligned
+	{
+		void *ptr;
+		unsigned u2 __attribute__ ((mode (HI)));
+		unsigned u4 __attribute__ ((mode (SI)));
+		unsigned u8 __attribute__ ((mode (DI)));
+		signed s2 __attribute__ ((mode (HI)));
+		signed s4 __attribute__ ((mode (SI)));
+		signed s8 __attribute__ ((mode (DI)));
+	} __attribute__((__packed__));
+
+	const union unaligned *u = (const union unaligned *) p;
+	_Unwind_Internal_Ptr result;
+
+	if (encoding == DW_EH_PE_aligned)
+	{
+		_Unwind_Internal_Ptr a = (_Unwind_Internal_Ptr) p;
+		a = (a + sizeof (void *) - 1) & - sizeof(void *);
+		result = *(_Unwind_Internal_Ptr *) a;
+		p = (const unsigned char *) (_Unwind_Internal_Ptr) (a + sizeof (void *));
+	}
+	else
+	{
+		switch (encoding & 0x0f)
+		{
+			case DW_EH_PE_absptr:
+				result = (_Unwind_Internal_Ptr) u->ptr;
+				p += sizeof (void *);
+				break;
+			case DW_EH_PE_uleb128:
+			{
+				_uleb128_t tmp;
+				p = read_uleb128 (p, &tmp);
+				result = (_Unwind_Internal_Ptr) tmp;
+			}
+			break;
+
+			case DW_EH_PE_sleb128:
+			{
+				_sleb128_t tmp;
+				p = read_sleb128 (p, &tmp);
+				result = (_Unwind_Internal_Ptr) tmp;
+			}
+			break;
+
+			case DW_EH_PE_udata2:
+				result = u->u2;
+				p += 2;
+				break;
+			case DW_EH_PE_udata4:
+				result = u->u4;
+				p += 4;
+				break;
+			case DW_EH_PE_udata8:
+				result = u->u8;
+				p += 8;
+				break;
+			case DW_EH_PE_sdata2:
+				result = u->s2;
+				p += 2;
+				break;
+			case DW_EH_PE_sdata4:
+				result = u->s4;
+				p += 4;
+				break;
+			case DW_EH_PE_sdata8:
+				result = u->s8;
+				p += 8;
+				break;
+			default:
+				__gxx_abort();
+		}
+
+		if (result != 0)
+		{
+			result += ((encoding & 0x70) == DW_EH_PE_pcrel ? (_Unwind_Internal_Ptr) u : base);
+			
+			if (encoding & DW_EH_PE_indirect) result = *(_Unwind_Internal_Ptr *) result;
+		}
+	}
+
+	*val = result;
+	return p;
+}
+
+/* Like read_encoded_value_with_base, but get the base from the context
+rather than providing it directly.  */
+static inline const unsigned char * read_encoded_value (struct _Unwind_Context *context, unsigned char encoding, const unsigned char *p, _Unwind_Ptr *val)
+{
+	return read_encoded_value_with_base (encoding, base_of_encoded_value (encoding, context), p, val);
+}
+
+typedef struct
+{
+	_Unwind_Ptr Start;
+	_Unwind_Ptr LPStart;
+	_Unwind_Ptr ttype_base;
+	const unsigned char *TType;
+	const unsigned char *action_table;
+	unsigned char ttype_encoding;
+	unsigned char call_site_encoding;
+} lsda_header_info;
+
+static const unsigned char * parse_lsda_header (struct _Unwind_Context *context, const unsigned char *p, lsda_header_info *info)
+{
+	_uleb128_t tmp;
+	unsigned char lpstart_encoding;
+
+	info->Start = (context ? _Unwind_GetRegionStart (context) : 0);
+
+	/* Find @LPStart, the base to which landing pad offsets are relative.  */
+	lpstart_encoding = *p++;
+	if (lpstart_encoding != DW_EH_PE_omit) p = read_encoded_value (context, lpstart_encoding, p, &info->LPStart);
+
+	else info->LPStart = info->Start;
+
+	/* Find @TType, the base of the handler and exception spec type data.  */
+	info->ttype_encoding = *p++;
+	if (info->ttype_encoding != DW_EH_PE_omit)
+	{
+		p = read_uleb128 (p, &tmp);
+		info->TType = p + tmp;
+	}
+	else info->TType = 0;
+
+	/* The encoding and length of the call-site table; the action table
+	immediately follows.  */
+	info->call_site_encoding = *p++;
+	p = read_uleb128 (p, &tmp);
+	info->action_table = p + tmp;
+
+	return p;
+}
