Coclass support.
This commit is contained in:
parent
80829db067
commit
c2c87daf4a
|
@ -259,6 +259,7 @@ static struct keyword {
|
||||||
/* ... */
|
/* ... */
|
||||||
{"module", tMODULE},
|
{"module", tMODULE},
|
||||||
/* ... */
|
/* ... */
|
||||||
|
{"noncreatable", tNONCREATABLE},
|
||||||
{"object", tOBJECT},
|
{"object", tOBJECT},
|
||||||
{"odl", tODL},
|
{"odl", tODL},
|
||||||
{"oleautomation", tOLEAUTOMATION},
|
{"oleautomation", tOLEAUTOMATION},
|
||||||
|
|
|
@ -157,6 +157,7 @@ static type_t std_uhyper = { "MIDL_uhyper" };
|
||||||
%token tLONG
|
%token tLONG
|
||||||
%token tMETHODS
|
%token tMETHODS
|
||||||
%token tMODULE
|
%token tMODULE
|
||||||
|
%token tNONCREATABLE
|
||||||
%token tOBJECT tODL tOLEAUTOMATION
|
%token tOBJECT tODL tOLEAUTOMATION
|
||||||
%token tOPTIONAL
|
%token tOPTIONAL
|
||||||
%token tOUT
|
%token tOUT
|
||||||
|
@ -360,6 +361,7 @@ attribute:
|
||||||
| tINPUTSYNC { $$ = make_attr(ATTR_INPUTSYNC); }
|
| tINPUTSYNC { $$ = make_attr(ATTR_INPUTSYNC); }
|
||||||
| tLENGTHIS '(' m_exprs ')' { $$ = make_attrp(ATTR_LENGTHIS, $3); }
|
| tLENGTHIS '(' m_exprs ')' { $$ = make_attrp(ATTR_LENGTHIS, $3); }
|
||||||
| tLOCAL { $$ = make_attr(ATTR_LOCAL); }
|
| tLOCAL { $$ = make_attr(ATTR_LOCAL); }
|
||||||
|
| tNONCREATABLE { $$ = make_attr(ATTR_NONCREATABLE); }
|
||||||
| tOBJECT { $$ = make_attr(ATTR_OBJECT); }
|
| tOBJECT { $$ = make_attr(ATTR_OBJECT); }
|
||||||
| tODL { $$ = make_attr(ATTR_ODL); }
|
| tODL { $$ = make_attr(ATTR_ODL); }
|
||||||
| tOLEAUTOMATION { $$ = make_attr(ATTR_OLEAUTOMATION); }
|
| tOLEAUTOMATION { $$ = make_attr(ATTR_OLEAUTOMATION); }
|
||||||
|
|
|
@ -205,22 +205,12 @@ void add_interface(type_t *iface)
|
||||||
|
|
||||||
void add_coclass(class_t *cls)
|
void add_coclass(class_t *cls)
|
||||||
{
|
{
|
||||||
ifref_t *lcur = cls->ifaces;
|
|
||||||
ifref_t *cur;
|
|
||||||
typelib_entry_t *entry;
|
typelib_entry_t *entry;
|
||||||
|
|
||||||
if (lcur) {
|
|
||||||
while (NEXT_LINK(lcur)) lcur = NEXT_LINK(lcur);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!typelib) return;
|
if (!typelib) return;
|
||||||
|
|
||||||
/* install interfaces the coclass depends on */
|
chat("add coclass: %s\n", cls->name);
|
||||||
cur = lcur;
|
|
||||||
while (cur) {
|
|
||||||
add_interface(cur->iface);
|
|
||||||
cur = PREV_LINK(cur);
|
|
||||||
}
|
|
||||||
entry = xmalloc(sizeof(*entry));
|
entry = xmalloc(sizeof(*entry));
|
||||||
entry->kind = TKIND_COCLASS;
|
entry->kind = TKIND_COCLASS;
|
||||||
entry->u.class = cls;
|
entry->u.class = cls;
|
||||||
|
|
|
@ -83,6 +83,7 @@ enum attr_type
|
||||||
ATTR_INPUTSYNC,
|
ATTR_INPUTSYNC,
|
||||||
ATTR_LENGTHIS,
|
ATTR_LENGTHIS,
|
||||||
ATTR_LOCAL,
|
ATTR_LOCAL,
|
||||||
|
ATTR_NONCREATABLE,
|
||||||
ATTR_OBJECT,
|
ATTR_OBJECT,
|
||||||
ATTR_ODL,
|
ATTR_ODL,
|
||||||
ATTR_OLEAUTOMATION,
|
ATTR_OLEAUTOMATION,
|
||||||
|
|
|
@ -1590,6 +1590,9 @@ static msft_typeinfo_t *create_msft_typeinfo(msft_typelib_t *typelib, enum type_
|
||||||
|
|
||||||
typeinfo->typekind |= kind | 0x20;
|
typeinfo->typekind |= kind | 0x20;
|
||||||
|
|
||||||
|
if(kind == TKIND_COCLASS)
|
||||||
|
typeinfo->flags |= 0x2; /* TYPEFLAG_FCANCREATE */
|
||||||
|
|
||||||
for( ; attr; attr = NEXT_LINK(attr)) {
|
for( ; attr; attr = NEXT_LINK(attr)) {
|
||||||
switch(attr->type) {
|
switch(attr->type) {
|
||||||
case ATTR_HELPCONTEXT:
|
case ATTR_HELPCONTEXT:
|
||||||
|
@ -1615,6 +1618,10 @@ static msft_typeinfo_t *create_msft_typeinfo(msft_typelib_t *typelib, enum type_
|
||||||
typeinfo->flags |= 0x10; /* TYPEFLAG_FHIDDEN */
|
typeinfo->flags |= 0x10; /* TYPEFLAG_FHIDDEN */
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case ATTR_NONCREATABLE:
|
||||||
|
typeinfo->flags &= ~0x2; /* TYPEFLAG_FCANCREATE */
|
||||||
|
break;
|
||||||
|
|
||||||
case ATTR_ODL:
|
case ATTR_ODL:
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
@ -1819,7 +1826,6 @@ static void add_enum_typeinfo(msft_typelib_t *typelib, type_t *enumeration)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static void add_typedef_typeinfo(msft_typelib_t *typelib, var_t *tdef)
|
static void add_typedef_typeinfo(msft_typelib_t *typelib, var_t *tdef)
|
||||||
{
|
{
|
||||||
msft_typeinfo_t *msft_typeinfo;
|
msft_typeinfo_t *msft_typeinfo;
|
||||||
|
@ -1837,6 +1843,86 @@ static void add_typedef_typeinfo(msft_typelib_t *typelib, var_t *tdef)
|
||||||
msft_typeinfo->typeinfo->typekind |= (alignment << 11 | alignment << 6);
|
msft_typeinfo->typeinfo->typekind |= (alignment << 11 | alignment << 6);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void add_coclass_typeinfo(msft_typelib_t *typelib, class_t *cls)
|
||||||
|
{
|
||||||
|
msft_typeinfo_t *msft_typeinfo;
|
||||||
|
ifref_t *iref;
|
||||||
|
int num_ifaces = 0, offset, i;
|
||||||
|
MSFT_RefRecord *ref, *first = NULL, *first_source = NULL;
|
||||||
|
int have_default = 0, have_default_source = 0;
|
||||||
|
attr_t *attr;
|
||||||
|
|
||||||
|
msft_typeinfo = create_msft_typeinfo(typelib, TKIND_COCLASS, cls->name, cls->attrs,
|
||||||
|
typelib->typelib_header.nrtypeinfos);
|
||||||
|
|
||||||
|
if((iref = cls->ifaces)) {
|
||||||
|
num_ifaces++;
|
||||||
|
while(NEXT_LINK(iref)) {
|
||||||
|
iref = NEXT_LINK(iref);
|
||||||
|
num_ifaces++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
offset = msft_typeinfo->typeinfo->datatype1 = ctl2_alloc_segment(typelib, MSFT_SEG_REFERENCES,
|
||||||
|
num_ifaces * sizeof(*ref), 0);
|
||||||
|
for(i = 0; i < num_ifaces; i++) {
|
||||||
|
if(iref->iface->typelib_idx == -1)
|
||||||
|
add_interface_typeinfo(typelib, iref->iface);
|
||||||
|
ref = (MSFT_RefRecord*) (typelib->typelib_segment_data[MSFT_SEG_REFERENCES] + offset + i * sizeof(*ref));
|
||||||
|
ref->reftype = typelib->typelib_typeinfo_offsets[iref->iface->typelib_idx];
|
||||||
|
ref->flags = 0;
|
||||||
|
ref->oCustData = -1;
|
||||||
|
ref->onext = -1;
|
||||||
|
if(i < num_ifaces - 1)
|
||||||
|
ref->onext = offset + (i + 1) * sizeof(*ref);
|
||||||
|
|
||||||
|
for(attr = iref->attrs; attr; attr = NEXT_LINK(attr)) {
|
||||||
|
switch(attr->type) {
|
||||||
|
case ATTR_DEFAULT:
|
||||||
|
ref->flags |= 0x1; /* IMPLTYPEFLAG_FDEFAULT */
|
||||||
|
break;
|
||||||
|
case ATTR_RESTRICTED:
|
||||||
|
ref->flags |= 0x4; /* IMPLTYPEFLAG_FRESTRICTED */
|
||||||
|
break;
|
||||||
|
case ATTR_SOURCE:
|
||||||
|
ref->flags |= 0x2; /* IMPLTYPEFLAG_FSOURCE */
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
warning("add_coclass_typeinfo: unhandled attr %d\n", attr->type);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if(ref->flags & 0x1) { /* IMPLTYPEFLAG_FDEFAULT */
|
||||||
|
if(ref->flags & 0x2) /* IMPLTYPEFLAG_SOURCE */
|
||||||
|
have_default_source = 1;
|
||||||
|
else
|
||||||
|
have_default = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* If the interface is non-restricted and we haven't already had one then
|
||||||
|
remember it so that we can use it as a default later */
|
||||||
|
if((ref->flags & 0x4) == 0) { /* IMPLTYPEFLAG_FRESTRICTED */
|
||||||
|
if(ref->flags & 0x2) { /* IMPLTYPEFLAG_FSOURCE */
|
||||||
|
if(!first_source)
|
||||||
|
first_source = ref;
|
||||||
|
}
|
||||||
|
else if(!first)
|
||||||
|
first = ref;
|
||||||
|
}
|
||||||
|
iref = PREV_LINK(iref);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* If we haven't had a default interface, then set the default flags on the
|
||||||
|
first ones */
|
||||||
|
if(!have_default && first)
|
||||||
|
first->flags |= 0x1;
|
||||||
|
if(!have_default_source && first_source)
|
||||||
|
first_source->flags |= 0x1;
|
||||||
|
|
||||||
|
msft_typeinfo->typeinfo->cImplTypes = num_ifaces;
|
||||||
|
msft_typeinfo->typeinfo->size = 4;
|
||||||
|
msft_typeinfo->typeinfo->typekind |= 0x2200;
|
||||||
|
}
|
||||||
|
|
||||||
static void add_entry(msft_typelib_t *typelib, typelib_entry_t *entry)
|
static void add_entry(msft_typelib_t *typelib, typelib_entry_t *entry)
|
||||||
{
|
{
|
||||||
switch(entry->kind) {
|
switch(entry->kind) {
|
||||||
|
@ -1856,6 +1942,10 @@ static void add_entry(msft_typelib_t *typelib, typelib_entry_t *entry)
|
||||||
add_typedef_typeinfo(typelib, entry->u.tdef);
|
add_typedef_typeinfo(typelib, entry->u.tdef);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case TKIND_COCLASS:
|
||||||
|
add_coclass_typeinfo(typelib, entry->u.class);
|
||||||
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
error("add_entry: unhandled type %d\n", entry->kind);
|
error("add_entry: unhandled type %d\n", entry->kind);
|
||||||
break;
|
break;
|
||||||
|
|
Loading…
Reference in New Issue