widl #35: coclasses
Huw D M Davies
h.davies1 at physics.ox.ac.uk
Thu Feb 3 06:19:41 CST 2005
Huw Davies <huw at codeweavers.com>
Coclass support
--
Huw Davies
huw at codeweavers.com
Index: tools/widl/parser.l
===================================================================
RCS file: /home/wine/wine/tools/widl/parser.l,v
retrieving revision 1.25
diff -u -p -r1.25 parser.l
--- tools/widl/parser.l 1 Feb 2005 18:48:25 -0000 1.25
+++ tools/widl/parser.l 3 Feb 2005 12:16:51 -0000
@@ -259,6 +259,7 @@ static struct keyword {
/* ... */
{"module", tMODULE},
/* ... */
+ {"noncreatable", tNONCREATABLE},
{"object", tOBJECT},
{"odl", tODL},
{"oleautomation", tOLEAUTOMATION},
Index: tools/widl/parser.y
===================================================================
RCS file: /home/wine/wine/tools/widl/parser.y,v
retrieving revision 1.39
diff -u -p -r1.39 parser.y
--- tools/widl/parser.y 2 Feb 2005 19:10:02 -0000 1.39
+++ tools/widl/parser.y 3 Feb 2005 12:16:51 -0000
@@ -157,6 +157,7 @@ static type_t std_uhyper = { "MIDL_uhype
%token tLONG
%token tMETHODS
%token tMODULE
+%token tNONCREATABLE
%token tOBJECT tODL tOLEAUTOMATION
%token tOPTIONAL
%token tOUT
@@ -360,6 +361,7 @@ attribute:
| tINPUTSYNC { $$ = make_attr(ATTR_INPUTSYNC); }
| tLENGTHIS '(' m_exprs ')' { $$ = make_attrp(ATTR_LENGTHIS, $3); }
| tLOCAL { $$ = make_attr(ATTR_LOCAL); }
+ | tNONCREATABLE { $$ = make_attr(ATTR_NONCREATABLE); }
| tOBJECT { $$ = make_attr(ATTR_OBJECT); }
| tODL { $$ = make_attr(ATTR_ODL); }
| tOLEAUTOMATION { $$ = make_attr(ATTR_OLEAUTOMATION); }
Index: tools/widl/typelib.c
===================================================================
RCS file: /home/wine/wine/tools/widl/typelib.c,v
retrieving revision 1.11
diff -u -p -r1.11 typelib.c
--- tools/widl/typelib.c 2 Feb 2005 19:10:02 -0000 1.11
+++ tools/widl/typelib.c 3 Feb 2005 12:16:51 -0000
@@ -205,22 +205,12 @@ void add_interface(type_t *iface)
void add_coclass(class_t *cls)
{
- ifref_t *lcur = cls->ifaces;
- ifref_t *cur;
typelib_entry_t *entry;
- if (lcur) {
- while (NEXT_LINK(lcur)) lcur = NEXT_LINK(lcur);
- }
-
if (!typelib) return;
- /* install interfaces the coclass depends on */
- cur = lcur;
- while (cur) {
- add_interface(cur->iface);
- cur = PREV_LINK(cur);
- }
+ chat("add coclass: %s\n", cls->name);
+
entry = xmalloc(sizeof(*entry));
entry->kind = TKIND_COCLASS;
entry->u.class = cls;
Index: tools/widl/widltypes.h
===================================================================
RCS file: /home/wine/wine/tools/widl/widltypes.h,v
retrieving revision 1.26
diff -u -p -r1.26 widltypes.h
--- tools/widl/widltypes.h 2 Feb 2005 19:10:02 -0000 1.26
+++ tools/widl/widltypes.h 3 Feb 2005 12:16:51 -0000
@@ -83,6 +83,7 @@ enum attr_type
ATTR_INPUTSYNC,
ATTR_LENGTHIS,
ATTR_LOCAL,
+ ATTR_NONCREATABLE,
ATTR_OBJECT,
ATTR_ODL,
ATTR_OLEAUTOMATION,
Index: tools/widl/write_msft.c
===================================================================
RCS file: /home/wine/wine/tools/widl/write_msft.c,v
retrieving revision 1.28
diff -u -p -r1.28 write_msft.c
--- tools/widl/write_msft.c 2 Feb 2005 19:10:02 -0000 1.28
+++ tools/widl/write_msft.c 3 Feb 2005 12:16:51 -0000
@@ -1590,6 +1590,9 @@ static msft_typeinfo_t *create_msft_type
typeinfo->typekind |= kind | 0x20;
+ if(kind == TKIND_COCLASS)
+ typeinfo->flags |= 0x2; /* TYPEFLAG_FCANCREATE */
+
for( ; attr; attr = NEXT_LINK(attr)) {
switch(attr->type) {
case ATTR_HELPCONTEXT:
@@ -1615,6 +1618,10 @@ static msft_typeinfo_t *create_msft_type
typeinfo->flags |= 0x10; /* TYPEFLAG_FHIDDEN */
break;
+ case ATTR_NONCREATABLE:
+ typeinfo->flags &= ~0x2; /* TYPEFLAG_FCANCREATE */
+ break;
+
case ATTR_ODL:
break;
@@ -1819,7 +1826,6 @@ static void add_enum_typeinfo(msft_typel
}
}
-
static void add_typedef_typeinfo(msft_typelib_t *typelib, var_t *tdef)
{
msft_typeinfo_t *msft_typeinfo;
@@ -1837,6 +1843,86 @@ static void add_typedef_typeinfo(msft_ty
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)
{
switch(entry->kind) {
@@ -1854,6 +1940,10 @@ static void add_entry(msft_typelib_t *ty
case TKIND_ALIAS:
add_typedef_typeinfo(typelib, entry->u.tdef);
+ break;
+
+ case TKIND_COCLASS:
+ add_coclass_typeinfo(typelib, entry->u.class);
break;
default:
More information about the wine-patches
mailing list