T.R | Title | User | Personal Name | Date | Lines |
---|
3466.1 | more info needed | DECC::SEIGEL | | Wed Feb 26 1997 13:04 | 8 |
| > In MS C++ it's possible to create an own exception wrapper
> function by using the _set_se_translator (trans_func)
> function.
Could you explain in more detail what is meant by one's oen
excpetion wrapper function ?
THanks, Harold
|
3466.2 | | DECC::OUELLETTE | | Wed Feb 26 1997 14:09 | 134 |
| I'm still out of my league on this question, but perhaps the VC++
documentation for _set_se_translator will help. Here it is:
_set_se_translator
Handles Win32 exceptions (C structured exceptions) as C++ typed exceptions.
typedef void (*_se_translator_function)( unsigned int, struct
_EXCEPTION_POINTERS* );
_se_translator_function _set_se_translator( _se_translator_function
se_trans_func );
Routine Required Header Compatibility
_set_se_translator <eh.h> Win 95, Win NT
For additional compatibility information, see Compatibility in the
Introduction.
Libraries
LIBC.LIB Single thread static library, retail version
LIBCMT.LIB Multithread static library, retail version
MSVCRT.LIB Import library for MSVCRT.DLL, retail version
Return Value
_set_se_translator returns a pointer to the previous translator function
registered by _set_se_translator, so that the previous function can be
restored later. If no previous function has been set, the return value may
be used to restore the default behavior; this value may be NULL.
Parameter
se_trans_func Pointer to a C structured exception translator function that
you write
Remarks
The _set_se_translator function provides a way to handle Win32 exceptions
(C structured exceptions) as C++ typed exceptions. To allow each C
exception to be handled by a C++ catch handler, first define a C exception
"wrapper" class that can be used, or derived from, in order to attribute a
specific class type to a C exception. To use this class, install a custom C
exception translator function that is called by the internal
exception-handling mechanism each time a C exception is raised. Within your
translator function, you can throw any typed exception that can be caught
by a matching C++ catch handler.
To specify a custom translation function, call _set_se_translator with the
name of your translation function as its argument. The translator function
that you write is called once for each function invocation on the stack
that has try blocks. There is no default translator function.
In a multithreaded environment, translator functions are maintained
separately for each thread. Each new thread gets a copy of the new
translator function of the calling thread. Thus, each thread is in charge
of its own translation handling.
The se_trans_func function that you write must take an unsigned integer and
a pointer to a Win32 _EXCEPTION_POINTERS structure as arguments. The
arguments are the return values of calls to the Win32 API GetExceptionCode
and GetExceptionInformation functions, respectively.
Example
/* SETRANS.CPP
*/
#include <stdio.h>
#include <windows.h>
#include <eh.h>
void SEFunc();
void trans_func( unsigned int, EXCEPTION_POINTERS* );
class SE_Exception
{
private:
unsigned int nSE;
public:
SE_Exception() {}
SE_Exception( unsigned int n ) : nSE( n ) {}
~SE_Exception() {}
unsigned int getSeNumber() { return nSE; }
};
void main( void )
{
try
{
_set_se_translator( trans_func );
SEFunc();
}
catch( SE_Exception e )
{
printf( "Caught a __try exception with SE_Exception.\n" );
}
}
void SEFunc()
{
__try
{
int x, y=0;
x = 5 / y;
}
__finally
{
printf( "In finally\n" );
}
}
void trans_func( unsigned int u, EXCEPTION_POINTERS* pExp )
{
printf( "In trans_func.\n" );
throw SE_Exception();
}
Output
In finally.
In trans_func.
Caught a __try exception with SE_Exception.
See Also set_terminate, set_unexpected, terminate, unexpected
Exception Handling Routines
|
3466.3 | some info | DECC::SEIGEL | | Wed Feb 26 1997 17:00 | 7 |
| Unlike Digital Unix, DEC C does not support C structured exceptions on VMS.
However, on VMS, you can catch non-C++ exceptions using the type
struct & chf$signal_array, as discussed in the DEC C++ manual. The caught
object is actually a SIGARGS structure.
Harold
|
3466.4 | MAny thanks! | ATZIS3::EHRLICH_K | Never met a Lady like her before! | Thu Feb 27 1997 08:15 | 7 |
| Hi Harold,
yes, many thanks, that's it. I'll try your comments and be back
with the results.
Cheers
Charly
|
3466.5 | Testprogram with 2 different results... | ATZIS2::EHRLICH_K | Never met a Lady like her before! | Fri Feb 28 1997 04:27 | 161 |
| Hi,
Below you can find a short testprogram which returns 2 different results on
WNT and AVMS.
MTIA for your kind support.
Cheers
Charly
#ifdef __VMS
#include <chfdef.h>
//#include <exc_handling.h>
#include <cxx_exception.h>
#include <lib$routines.h>
#include <ssdef.h>
#endif
#include <iostream.h>
#include <string.h>
#include <stdio.h>
class cError
{
public:
cError () { cErrorText[0] = '\0';};
char cErrorText[150];
};
#ifdef _WIN32
#include <eh.h>
#include <windows.h>
void trans_func( unsigned int u, _EXCEPTION_POINTERS* pExp );
void trans_func( unsigned int u, _EXCEPTION_POINTERS* pExp )
{
cError Error;
cout << "In trans_func." << endl;
sprintf (Error.cErrorText, "Code: %X", u);
throw Error;
}
#endif
#ifdef __VMS
int wandler (void *sigarr, void *mecharr);
#endif
main ()
{
char *pName;
char cName[] = "String String String";
cout << cName << endl;
pName = NULL;
#ifdef _WIN32
_set_se_translator( trans_func );
#endif
#ifdef __VMS
//VAXC$ESTABLISH (wandler); // Don't work with cxx/excep
#endif
try
{
#ifdef __VMS
//lib$signal (666); //this work with chf$signal_array
#endif
strcpy ( pName , "Neu"); // --> AccessViolation
}
catch ( char *pName )
{
cout << pName << endl;
}
#ifdef __VMS
catch ( struct chf$signal_array *obj)
{
cout <<"chf$signal_array: "<< obj->chf$l_sig_name << endl;
}
#endif
catch (cError Error)
{
cout << Error.cErrorText << endl;
}
catch (unsigned int Code)
{
cout << "Unsigned int: " << Code << endl;
}
catch (int Code)
{
cout << "Unsigned int: " << Code << endl;
}
catch ( ... )
{
cout << "catch(...)" << endl;
}
cout.flush();
return 1;
}
#ifdef __VMS
int wandler (void *sigarr, void *mecharr)
{
cError Error;
cout << "Im Wander" << endl;
cout.flush();
strcpy (Error.cErrorText, "Das ist vom Wandler");
return SS$_CONTINUE;
}
#endif
Output on WNT:
G:\PROG\EXC\WINNT\DEBUG>winnt
String String String
In trans_func.
Code: C0000005
This Code means:
Searching for 'c0000005'...
D:\MSDEV\include\WINNT.H(791):#define STATUS_ACCESS_VIOLATION
((DWORD )0xC0000005L)
1 occurrence(s) have been found.
On OpenVMS ALPHA V6.2 and with CXX V5.5 doesn't look fine:
GESP39> r test_exception
String String String
%SYSTEM-F-ACCVIO, access violation, reason mask=00, virtual
address=00000000, PC
=80566388, PS=0000001B
%TRACE-F-TRACEBACK, symbolic stack dump follows
image module routine line rel PC abs
PC
0 0000000000000000
FFFFFFFF80566388
TEST_EXCEPTION TEST_EXCEPTION main 9357 0000000000000198
0000000000030198
TEST_EXCEPTION TEST_EXCEPTION __main
0 0000000000000064
0000000000030064
0 FFFFFFFF836CE170
FFFFFFFF836CE170
The chf$signal_array function is included in the test-program.
It works, but runs into an ACCVIO. Seems there's no LIB$SIGNAL!!!
Is it possible to handle such an ACCVIO and not to terminate the
program.
Cheers
Charly
|
3466.6 | | SPECXN::DERAMO | Dan D'Eramo | Fri Feb 28 1997 11:13 | 20 |
| >The chf$signal_array function is included in the test-program.
>It works, but runs into an ACCVIO. Seems there's no LIB$SIGNAL!!!
By default, OpenVMS exceptions that are used to implement UNIX
style signals are not caught by
catch (struct chf$signal_array *p)
SS$_ACCVIO corresponds to the UNIX style SIGBUS signal. So to
catch it with the above, you first need to call
cxxl$set_condition(cxx_exception);
(use #include <cxx_exception.h> for all the needed
definitions). To revert back to letting those "signal"'s
go through, call
cxxl$set_condition (unix_signal);
Dan
|
3466.7 | Wow, Great! | ATZIS2::EHRLICH_K | Never met a Lady like her before! | Tue Mar 04 1997 07:02 | 7 |
| Hi Dan,
many thanks for your very good explanation. That's exactly what
I needed to understand the difference. Everything's fine, now.
Cheers
Charly
|