msvcp: Fix failure class layout and exception information data.

Signed-off-by: Piotr Caban <piotr@codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
Piotr Caban 2017-12-06 18:25:49 +01:00 committed by Alexandre Julliard
parent 5f5f9974f5
commit 7ff10d348f
2 changed files with 130 additions and 23 deletions

View file

@ -111,22 +111,26 @@ const rtti_object_locator name ## _rtti = { \
&name ## _hierarchy \
};
#define DEFINE_CXX_DATA(type, base_no, cl1, cl2, dtor) \
\
#define DEFINE_CXX_TYPE_INFO(type) \
static const cxx_type_info type ## _cxx_type_info = { \
0, \
& type ##_type_info, \
{ 0, -1, 0 }, \
sizeof(type), \
(cxx_copy_ctor)THISCALL(MSVCP_ ## type ##_copy_ctor) \
}; \
};
#define DEFINE_CXX_DATA(type, base_no, cl1, cl2, cl3, cl4, dtor) \
DEFINE_CXX_TYPE_INFO(type) \
\
static const cxx_type_info_table type ## _cxx_type_table = { \
base_no+1, \
{ \
& type ## _cxx_type_info, \
cl1, \
cl2 \
cl2, \
cl3, \
cl4 \
} \
}; \
\
@ -203,8 +207,7 @@ static void init_ ## name ## _rtti(char *base) \
name ## _rtti.object_locator = (char*)&name ## _rtti - base; \
}
#define DEFINE_CXX_DATA(type, base_no, cl1, cl2, dtor) \
\
#define DEFINE_CXX_TYPE_INFO(type) \
static cxx_type_info type ## _cxx_type_info = { \
0, \
0xdeadbeef, \
@ -213,9 +216,21 @@ static cxx_type_info type ## _cxx_type_info = { \
0xdeadbeef \
}; \
\
static void init_ ## type ## _cxx_type_info(char *base) \
{ \
type ## _cxx_type_info.type_info = (char *)&type ## _type_info - base; \
type ## _cxx_type_info.copy_ctor = (char *)MSVCP_ ## type ## _copy_ctor - base; \
}
#define DEFINE_CXX_DATA(type, base_no, cl1, cl2, cl3, cl4, dtor) \
\
DEFINE_CXX_TYPE_INFO(type) \
\
static cxx_type_info_table type ## _cxx_type_table = { \
base_no+1, \
{ \
0xdeadbeef, \
0xdeadbeef, \
0xdeadbeef, \
0xdeadbeef, \
0xdeadbeef \
@ -231,11 +246,12 @@ static cxx_exception_type type ##_cxx_type = { \
\
static void init_ ## type ## _cxx(char *base) \
{ \
type ## _cxx_type_info.type_info = (char *)&type ## _type_info - base; \
type ## _cxx_type_info.copy_ctor = (char *)MSVCP_ ## type ## _copy_ctor - base; \
init_ ## type ## _cxx_type_info(base); \
type ## _cxx_type_table.info[0] = (char *)&type ## _cxx_type_info - base; \
type ## _cxx_type_table.info[1] = (char *)cl1 - base; \
type ## _cxx_type_table.info[2] = (char *)cl2 - base; \
type ## _cxx_type_table.info[3] = (char *)cl3 - base; \
type ## _cxx_type_table.info[4] = (char *)cl4 - base; \
type ## _cxx_type.destructor = (char *)dtor - base; \
type ## _cxx_type.type_info_table = (char *)&type ## _cxx_type_table - base; \
}
@ -258,11 +274,15 @@ static void init_ ## type ## _cxx(char *base) \
DEFINE_RTTI_DATA(name, off, 9, cl1, cl2, cl3, cl4, cl5, cl6, cl7, cl8, cl9, mangled_name)
#define DEFINE_CXX_DATA0(name, dtor) \
DEFINE_CXX_DATA(name, 0, NULL, NULL, dtor)
DEFINE_CXX_DATA(name, 0, NULL, NULL, NULL, NULL, dtor)
#define DEFINE_CXX_DATA1(name, cl1, dtor) \
DEFINE_CXX_DATA(name, 1, cl1, NULL, dtor)
DEFINE_CXX_DATA(name, 1, cl1, NULL, NULL, NULL, dtor)
#define DEFINE_CXX_DATA2(name, cl1, cl2, dtor) \
DEFINE_CXX_DATA(name, 2, cl1, cl2, dtor)
DEFINE_CXX_DATA(name, 2, cl1, cl2, NULL, NULL, dtor)
#define DEFINE_CXX_DATA3(name, cl1, cl2, cl3, dtor) \
DEFINE_CXX_DATA(name, 3, cl1, cl2, cl3, NULL, dtor)
#define DEFINE_CXX_DATA4(name, cl1, cl2, cl3, cl4, dtor) \
DEFINE_CXX_DATA(name, 4, cl1, cl2, cl3, cl4, dtor)
#ifdef __i386__
@ -380,7 +400,7 @@ typedef struct
typedef struct
{
UINT count;
const cxx_type_info *info[3];
const cxx_type_info *info[5];
} cxx_type_info_table;
typedef struct
@ -436,7 +456,7 @@ typedef struct
typedef struct
{
UINT count;
unsigned int info[3];
unsigned int info[5];
} cxx_type_info_table;
typedef struct

View file

@ -56,6 +56,8 @@ extern const vtable_ptr MSVCP_out_of_range_vtable;
extern const vtable_ptr MSVCP_invalid_argument_vtable;
/* ??_7runtime_error@std@@6B@ */
extern const vtable_ptr MSVCP_runtime_error_vtable;
extern const vtable_ptr MSVCP__System_error_vtable;
extern const vtable_ptr MSVCP_system_error_vtable;
extern const vtable_ptr MSVCP_failure_vtable;
/* ??_7bad_cast@std@@6B@ */
extern const vtable_ptr MSVCP_bad_cast_vtable;
@ -656,13 +658,24 @@ DEFINE_RTTI_DATA1(runtime_error, 0, &exception_rtti_base_descriptor, ".?AVruntim
DEFINE_CXX_DATA1(runtime_error, &exception_cxx_type_info, MSVCP_runtime_error_dtor)
/* failure class data */
typedef runtime_error failure;
typedef struct {
runtime_error base;
#if _MSVCP_VER > 90
int err;
#endif
} system_error;
typedef system_error _System_error;
typedef system_error failure;
static failure* MSVCP_failure_ctor( failure *this, exception_name name )
{
TRACE("%p %s\n", this, EXCEPTION_STR(name));
MSVCP_runtime_error_ctor(this, name);
this->e.vtable = &MSVCP_failure_vtable;
MSVCP_runtime_error_ctor(&this->base, name);
#if _MSVCP_VER > 90
/* FIXME: set err correctly */
this->err = 0;
#endif
this->base.e.vtable = &MSVCP_failure_vtable;
return this;
}
@ -671,8 +684,11 @@ failure* __thiscall MSVCP_failure_copy_ctor(
failure *this, failure *rhs)
{
TRACE("%p %p\n", this, rhs);
MSVCP_runtime_error_copy_ctor(this, rhs);
this->e.vtable = &MSVCP_failure_vtable;
MSVCP_runtime_error_copy_ctor(&this->base, &rhs->base);
#if _MSVCP_VER > 90
this->err = rhs->err;
#endif
this->base.e.vtable = &MSVCP_failure_vtable;
return this;
}
@ -680,7 +696,7 @@ DEFINE_THISCALL_WRAPPER(MSVCP_failure_dtor, 4)
void __thiscall MSVCP_failure_dtor(failure *this)
{
TRACE("%p\n", this);
MSVCP_runtime_error_dtor(this);
MSVCP_runtime_error_dtor(&this->base);
}
DEFINE_THISCALL_WRAPPER(MSVCP_failure_vector_dtor, 8)
@ -688,18 +704,67 @@ void* __thiscall MSVCP_failure_vector_dtor(
failure *this, unsigned int flags)
{
TRACE("%p %x\n", this, flags);
return MSVCP_runtime_error_vector_dtor(this, flags);
return MSVCP_runtime_error_vector_dtor(&this->base, flags);
}
DEFINE_THISCALL_WRAPPER(MSVCP_failure_what, 4)
const char* __thiscall MSVCP_failure_what(failure *this)
{
TRACE("%p\n", this);
return MSVCP_runtime_error_what(this);
return MSVCP_runtime_error_what(&this->base);
}
DEFINE_RTTI_DATA2(failure, 0, &runtime_error_rtti_base_descriptor, &exception_rtti_base_descriptor, ".?AVfailure@std@@")
DEFINE_CXX_DATA2(failure, &runtime_error_cxx_type_info, &exception_cxx_type_info, MSVCP_runtime_error_dtor)
#if _MSVCP_VER > 90
DEFINE_THISCALL_WRAPPER(MSVCP_system_error_copy_ctor, 8)
system_error* __thiscall MSVCP_system_error_copy_ctor(
system_error *this, system_error *rhs)
{
MSVCP_failure_copy_ctor(this, rhs);
this->base.e.vtable = &MSVCP_system_error_vtable;
return this;
}
#endif
#if _MSVCP_VER > 110
DEFINE_THISCALL_WRAPPER(MSVCP__System_error_copy_ctor, 8)
_System_error* __thiscall MSVCP__System_error_copy_ctor(
_System_error *this, _System_error *rhs)
{
MSVCP_failure_copy_ctor(this, rhs);
this->base.e.vtable = &MSVCP__System_error_vtable;
return this;
}
#endif
#if _MSVCP_VER > 110
DEFINE_RTTI_DATA2(_System_error, 0, &runtime_error_rtti_base_descriptor,
&exception_rtti_base_descriptor, ".?AV_System_error@std@@")
DEFINE_RTTI_DATA3(system_error, 0, &_System_error_rtti_base_descriptor,
&runtime_error_rtti_base_descriptor, &exception_rtti_base_descriptor,
".?AVsystem_error@std@@")
DEFINE_RTTI_DATA4(failure, 0, &system_error_rtti_base_descriptor,
&_System_error_rtti_base_descriptor, &runtime_error_rtti_base_descriptor,
&exception_rtti_base_descriptor, ".?AVfailure@ios_base@std@@")
DEFINE_CXX_TYPE_INFO(_System_error)
DEFINE_CXX_TYPE_INFO(system_error);
DEFINE_CXX_DATA4(failure, &system_error_cxx_type_info,
&_System_error_cxx_type_info, &runtime_error_cxx_type_info,
&exception_cxx_type_info, MSVCP_runtime_error_dtor)
#elif _MSVCP_VER > 90
DEFINE_RTTI_DATA2(system_error, 0, &runtime_error_rtti_base_descriptor,
&exception_rtti_base_descriptor, ".?AVsystem_error@std@@")
DEFINE_RTTI_DATA3(failure, 0, &system_error_rtti_base_descriptor,
&runtime_error_rtti_base_descriptor, &exception_rtti_base_descriptor,
".?AVfailure@ios_base@std@@")
DEFINE_CXX_TYPE_INFO(system_error);
DEFINE_CXX_DATA3(failure, &system_error_cxx_type_info, &runtime_error_cxx_type_info,
&exception_cxx_type_info, MSVCP_runtime_error_dtor)
#else
DEFINE_RTTI_DATA2(failure, 0, &runtime_error_rtti_base_descriptor,
&exception_rtti_base_descriptor, ".?AVfailure@ios_base@std@@")
DEFINE_CXX_DATA2(failure, &runtime_error_cxx_type_info,
&exception_cxx_type_info, MSVCP_runtime_error_dtor)
#endif
/* bad_cast class data */
typedef exception bad_cast;
@ -911,6 +976,16 @@ void __asm_dummy_vtables(void) {
EXCEPTION_VTABLE(runtime_error,
VTABLE_ADD_FUNC(MSVCP_runtime_error_vector_dtor)
VTABLE_ADD_FUNC(MSVCP_runtime_error_what));
#if _MSVCP_VER > 110
EXCEPTION_VTABLE(_System_error,
VTABLE_ADD_FUNC(MSVCP_failure_vector_dtor)
VTABLE_ADD_FUNC(MSVCP_failure_what));
#endif
#if _MSVCP_VER > 90
EXCEPTION_VTABLE(system_error,
VTABLE_ADD_FUNC(MSVCP_failure_vector_dtor)
VTABLE_ADD_FUNC(MSVCP_failure_what));
#endif
EXCEPTION_VTABLE(failure,
VTABLE_ADD_FUNC(MSVCP_failure_vector_dtor)
VTABLE_ADD_FUNC(MSVCP_failure_what));
@ -996,6 +1071,12 @@ void init_exception(void *base)
init_out_of_range_rtti(base);
init_invalid_argument_rtti(base);
init_runtime_error_rtti(base);
#if _MSVCP_VER > 110
init__System_error_rtti(base);
#endif
#if _MSVCP_VER > 90
init_system_error_rtti(base);
#endif
init_failure_rtti(base);
init_bad_cast_rtti(base);
init_range_error_rtti(base);
@ -1007,6 +1088,12 @@ void init_exception(void *base)
init_out_of_range_cxx(base);
init_invalid_argument_cxx(base);
init_runtime_error_cxx(base);
#if _MSVCP_VER > 110
init__System_error_cxx_type_info(base);
#endif
#if _MSVCP_VER > 90
init_system_error_cxx_type_info(base);
#endif
init_failure_cxx(base);
init_bad_cast_cxx(base);
init_range_error_cxx(base);