ReactOS  0.4.13-dev-551-gf37fb1f
typelib.c
Go to the documentation of this file.
1 /*
2  * IDL Compiler
3  *
4  * Copyright 2004 Ove Kaaven
5  * Copyright 2006 Jacek Caban for CodeWeavers
6  *
7  * This library is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU Lesser General Public
9  * License as published by the Free Software Foundation; either
10  * version 2.1 of the License, or (at your option) any later version.
11  *
12  * This library is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15  * Lesser General Public License for more details.
16  *
17  * You should have received a copy of the GNU Lesser General Public
18  * License along with this library; if not, write to the Free Software
19  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
20  */
21 
22 #include "config.h"
23 #include "wine/port.h"
24 #include "wine/wpp.h"
25 
26 #include <stdio.h>
27 #include <stdlib.h>
28 #include <stdarg.h>
29 #ifdef HAVE_UNISTD_H
30 # include <unistd.h>
31 #endif
32 #include <string.h>
33 #include <ctype.h>
34 
35 #ifdef __REACTOS__
36 #include <typedefs.h>
37 #else
38 #include "windef.h"
39 #include "winbase.h"
40 #endif
41 
42 #include "widl.h"
43 #include "utils.h"
44 #include "parser.h"
45 #include "header.h"
46 #include "typelib.h"
47 #include "widltypes.h"
48 #include "typelib_struct.h"
49 #include "typetree.h"
50 
51 #ifdef __REACTOS__
52 static typelib_t *typelib;
53 #endif
54 
55 /* List of oleauto types that should be recognized by name.
56  * (most of) these seem to be intrinsic types in mktyplib.
57  * This table MUST be alphabetically sorted on the kw field.
58  */
59 static const struct oatype {
60  const char *kw;
61  unsigned short vt;
62 } oatypes[] = {
63  {"BSTR", VT_BSTR},
64  {"CURRENCY", VT_CY},
65  {"DATE", VT_DATE},
66  {"DECIMAL", VT_DECIMAL},
67  {"HRESULT", VT_HRESULT},
68  {"LPSTR", VT_LPSTR},
69  {"LPWSTR", VT_LPWSTR},
70  {"SCODE", VT_ERROR},
71  {"VARIANT", VT_VARIANT},
72  {"VARIANT_BOOL", VT_BOOL}
73 };
74 #define NTYPES (sizeof(oatypes)/sizeof(oatypes[0]))
75 #define KWP(p) ((const struct oatype *)(p))
76 
77 static int kw_cmp_func(const void *s1, const void *s2)
78 {
79  return strcmp(KWP(s1)->kw, KWP(s2)->kw);
80 }
81 
82 static unsigned short builtin_vt(const type_t *t)
83 {
84  const char *kw = t->name;
85  struct oatype key;
86  const struct oatype *kwp;
87  key.kw = kw;
88 #ifdef KW_BSEARCH
89  kwp = bsearch(&key, oatypes, NTYPES, sizeof(oatypes[0]), kw_cmp_func);
90 #else
91  {
92  unsigned int i;
93  for (kwp=NULL, i=0; i < NTYPES; i++)
94  if (!kw_cmp_func(&key, &oatypes[i])) {
95  kwp = &oatypes[i];
96  break;
97  }
98  }
99 #endif
100  if (kwp) {
101  return kwp->vt;
102  }
103  if (is_string_type (t->attrs, t))
104  {
105  const type_t *elem_type;
106  if (is_array(t))
107  elem_type = type_array_get_element(t);
108  else
109  elem_type = type_pointer_get_ref(t);
110  if (type_get_type(elem_type) == TYPE_BASIC)
111  {
112  switch (type_basic_get_type(elem_type))
113  {
114  case TYPE_BASIC_CHAR: return VT_LPSTR;
115  case TYPE_BASIC_WCHAR: return VT_LPWSTR;
116  default: break;
117  }
118  }
119  }
120  return 0;
121 }
122 
123 static int match(const char*n, const char*m)
124 {
125  if (!n) return 0;
126  return !strcmp(n, m);
127 }
128 
129 unsigned short get_type_vt(type_t *t)
130 {
131  unsigned short vt;
132 
133  chat("get_type_vt: %p type->name %s\n", t, t->name);
134  if (t->name) {
135  vt = builtin_vt(t);
136  if (vt) return vt;
137  }
138 
139  if (type_is_alias(t) && is_attr(t->attrs, ATTR_PUBLIC))
140  return VT_USERDEFINED;
141 
142  switch (type_get_type(t)) {
143  case TYPE_BASIC:
144  switch (type_basic_get_type(t)) {
145  case TYPE_BASIC_BYTE:
146  return VT_UI1;
147  case TYPE_BASIC_CHAR:
148  case TYPE_BASIC_INT8:
149  if (type_basic_get_sign(t) > 0)
150  return VT_UI1;
151  else
152  return VT_I1;
153  case TYPE_BASIC_WCHAR:
154  return VT_I2; /* mktyplib seems to parse wchar_t as short */
155  case TYPE_BASIC_INT16:
156  if (type_basic_get_sign(t) > 0)
157  return VT_UI2;
158  else
159  return VT_I2;
160  case TYPE_BASIC_INT:
161  if (type_basic_get_sign(t) > 0)
162  return VT_UINT;
163  else
164  return VT_INT;
165  case TYPE_BASIC_INT32:
166  case TYPE_BASIC_LONG:
168  if (type_basic_get_sign(t) > 0)
169  return VT_UI4;
170  else
171  return VT_I4;
172  case TYPE_BASIC_INT64:
173  case TYPE_BASIC_HYPER:
174  if (type_basic_get_sign(t) > 0)
175  return VT_UI8;
176  else
177  return VT_I8;
178  case TYPE_BASIC_INT3264:
179  if (pointer_size == 8)
180  {
181  if (type_basic_get_sign(t) > 0)
182  return VT_UI8;
183  else
184  return VT_I8;
185  }
186  else
187  {
188  if (type_basic_get_sign(t) > 0)
189  return VT_UI4;
190  else
191  return VT_I4;
192  }
193  case TYPE_BASIC_FLOAT:
194  return VT_R4;
195  case TYPE_BASIC_DOUBLE:
196  return VT_R8;
197  case TYPE_BASIC_HANDLE:
198  error("handles can't be used in typelibs\n");
199  }
200  break;
201 
202  case TYPE_POINTER:
203  return VT_PTR;
204 
205  case TYPE_ARRAY:
207  {
208  if (match(type_array_get_element(t)->name, "SAFEARRAY"))
209  return VT_SAFEARRAY;
210  return VT_PTR;
211  }
212  else
213  return VT_CARRAY;
214 
215  case TYPE_INTERFACE:
216  if(match(t->name, "IUnknown"))
217  return VT_UNKNOWN;
218  if(match(t->name, "IDispatch"))
219  return VT_DISPATCH;
220  return VT_USERDEFINED;
221 
222  case TYPE_ENUM:
223  case TYPE_STRUCT:
224  case TYPE_COCLASS:
225  case TYPE_MODULE:
226  case TYPE_UNION:
228  return VT_USERDEFINED;
229 
230  case TYPE_VOID:
231  return VT_VOID;
232 
233  case TYPE_ALIAS:
234  /* aliases should be filtered out by the type_get_type call above */
235  assert(0);
236  break;
237 
238  case TYPE_FUNCTION:
239  error("get_type_vt: functions not supported\n");
240  break;
241 
242  case TYPE_BITFIELD:
243  error("get_type_vt: bitfields not supported\n");
244  break;
245  }
246  return 0;
247 }
248 
249 #ifdef __REACTOS__
250 void start_typelib(typelib_t *typelib_type)
251 {
252  if (!do_typelib) return;
253  typelib = typelib_type;
254 }
255 
256 void end_typelib(void)
257 {
258  if (!typelib) return;
259 
261 }
262 #endif
263 
264 static void tlb_read(int fd, void *buf, int count)
265 {
266  if(read(fd, buf, count) < count)
267  error("error while reading importlib.\n");
268 }
269 
270 static void tlb_lseek(int fd, off_t offset)
271 {
272  if(lseek(fd, offset, SEEK_SET) == -1)
273  error("lseek failed\n");
274 }
275 
276 static void msft_read_guid(int fd, MSFT_SegDir *segdir, int offset, GUID *guid)
277 {
278  tlb_lseek(fd, segdir->pGuidTab.offset+offset);
279  tlb_read(fd, guid, sizeof(GUID));
280 }
281 
283 {
285  MSFT_SegDir segdir;
286  int *typeinfo_offs;
287  int i;
288 
289  importlib->allocated = 0;
290 
291  tlb_lseek(fd, 0);
292  tlb_read(fd, &header, sizeof(header));
293 
294  importlib->version = header.version;
295 
296  typeinfo_offs = xmalloc(header.nrtypeinfos*sizeof(INT));
297  tlb_read(fd, typeinfo_offs, header.nrtypeinfos*sizeof(INT));
298  tlb_read(fd, &segdir, sizeof(segdir));
299 
300  msft_read_guid(fd, &segdir, header.posguid, &importlib->guid);
301 
302  importlib->ntypeinfos = header.nrtypeinfos;
303  importlib->importinfos = xmalloc(importlib->ntypeinfos*sizeof(importinfo_t));
304 
305  for(i=0; i < importlib->ntypeinfos; i++) {
307  MSFT_NameIntro nameintro;
308  int len;
309 
310  tlb_lseek(fd, sizeof(MSFT_Header) + header.nrtypeinfos*sizeof(INT) + sizeof(MSFT_SegDir)
311  + typeinfo_offs[i]);
312  tlb_read(fd, &base, sizeof(base));
313 
314  importlib->importinfos[i].importlib = importlib;
315  importlib->importinfos[i].flags = (base.typekind&0xf)<<24;
316  importlib->importinfos[i].offset = -1;
317  importlib->importinfos[i].id = i;
318 
319  if(base.posguid != -1) {
320  importlib->importinfos[i].flags |= MSFT_IMPINFO_OFFSET_IS_GUID;
321  msft_read_guid(fd, &segdir, base.posguid, &importlib->importinfos[i].guid);
322  }
323  else memset( &importlib->importinfos[i].guid, 0, sizeof(importlib->importinfos[i].guid));
324 
325  tlb_lseek(fd, segdir.pNametab.offset + base.NameOffset);
326  tlb_read(fd, &nameintro, sizeof(nameintro));
327 
328  len = nameintro.namelen & 0xff;
329 
330  importlib->importinfos[i].name = xmalloc(len+1);
331  tlb_read(fd, importlib->importinfos[i].name, len);
332  importlib->importinfos[i].name[len] = 0;
333  }
334 
335  free(typeinfo_offs);
336 }
337 
338 static int open_typelib(const char *name)
339 {
340  char *file_name;
341  int fd;
342 
344  if(!file_name)
345  return open(name, O_RDONLY | O_BINARY );
346 
348  free(file_name);
349  return fd;
350 }
351 
353 {
354  int fd;
355  INT magic;
356 
357  fd = open_typelib(importlib->name);
358 
359  /* widl extension: if importlib name has no .tlb extension, try using .tlb */
360  if(fd < 0) {
361  const char *p = strrchr(importlib->name, '.');
362  size_t len = p ? p - importlib->name : strlen(importlib->name);
363  if(strcmp(importlib->name + len, ".tlb")) {
364  char *tlb_name = xmalloc(len + 5);
365  memcpy(tlb_name, importlib->name, len);
366  strcpy(tlb_name + len, ".tlb");
367  fd = open_typelib(tlb_name);
368  free(tlb_name);
369  }
370  }
371 
372  if(fd < 0)
373  error("Could not find importlib %s.\n", importlib->name);
374 
375  tlb_read(fd, &magic, sizeof(magic));
376 
377  switch(magic) {
378  case MSFT_MAGIC:
380  break;
381  default:
382  error("Wrong or unsupported typelib magic %x\n", magic);
383  };
384 
385  close(fd);
386 }
387 
388 #ifdef __REACTOS__
389 void add_importlib(const char *name)
390 #else
391 void add_importlib(const char *name, typelib_t *typelib)
392 #endif
393 {
395 
396  if(!typelib) return;
397 
399  if(!strcmp(name, importlib->name))
400  return;
401 
402  chat("add_importlib: %s\n", name);
403 
404  importlib = xmalloc(sizeof(*importlib));
405  memset( importlib, 0, sizeof(*importlib) );
406  importlib->name = xstrdup(name);
407 
409  list_add_head( &typelib->importlibs, &importlib->entry );
410 }
struct S2 s2
Definition: compat.h:1939
Definition: compat.h:1955
#define error(str)
Definition: mkdosfs.c:1605
Definition: compat.h:1951
#define open
Definition: acwin.h:71
ACPI_SIZE strlen(const char *String)
Definition: utclib.c:269
GLenum GLuint GLenum GLsizei const GLchar * buf
Definition: glext.h:7751
#define MSFT_IMPINFO_OFFSET_IS_GUID
Definition: typelib.h:174
static void read_importlib(importlib_t *importlib)
Definition: typelib.c:352
GLuint GLuint GLsizei count
Definition: gl.h:1545
static type_t * type_array_get_element(const type_t *type)
Definition: typetree.h:253
#define free
Definition: debug_ros.c:5
__kernel_off_t off_t
Definition: linux.h:201
char * wpp_find_include(const char *name, const char *parent_name)
Definition: preproc.c:509
Definition: typelib.c:59
GLintptr offset
Definition: glext.h:5920
__WINE_SERVER_LIST_INLINE void list_add_head(struct list *list, struct list *elem)
Definition: list.h:96
GLdouble n
Definition: glext.h:7729
static ITypeLib * typelib
Definition: apps.c:105
GLdouble GLdouble t
Definition: gl.h:2047
u32_t magic(void)
#define assert(x)
Definition: debug.h:53
static int fd
Definition: io.c:51
_Check_return_opt_ _CRTIMP long __cdecl lseek(_In_ int _FileHandle, _In_ long _Offset, _In_ int _Origin)
_Check_return_ _CRTIMP _CONST_RETURN char *__cdecl strrchr(_In_z_ const char *_Str, _In_ int _Ch)
static enum type_basic_type type_basic_get_type(const type_t *type)
Definition: typetree.h:73
IUnknownVtbl vt
Definition: typelib.c:6130
static void tlb_read(int fd, void *buf, int count)
Definition: typelib.c:264
int32_t INT
Definition: typedefs.h:56
const GLfloat * m
Definition: glext.h:10848
static type_t * type_pointer_get_ref(const type_t *type)
Definition: typetree.h:292
#define LIST_FOR_EACH_ENTRY(elem, list, type, field)
Definition: list.h:198
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
const GUID * guid
void * xmalloc(int size)
Definition: uimain.c:747
unsigned short vt
Definition: typelib.c:61
GLuint base
Definition: 3dtext.c:35
importlib("stdole2.tlb")
static void msft_read_guid(int fd, MSFT_SegDir *segdir, int offset, GUID *guid)
Definition: typelib.c:276
static int type_is_alias(const type_t *type)
Definition: typetree.h:274
smooth NULL
Definition: ftsmooth.c:416
static int is_array(const type_t *t)
Definition: header.h:64
void add_importlib(const char *name, typelib_t *typelib)
Definition: typelib.c:391
int do_typelib
Definition: widl.c:117
#define MSFT_MAGIC
static int open_typelib(const char *name)
Definition: typelib.c:338
static int kw_cmp_func(const void *s1, const void *s2)
Definition: typelib.c:77
INT offset
Definition: typelib.h:89
static const struct oatype oatypes[]
#define SEEK_SET
Definition: jmemansi.c:26
int create_msft_typelib(typelib_t *typelib)
Definition: write_msft.c:2657
MSFT_pSeg pNametab
Definition: typelib.h:109
static int is_string_type(const attr_list_t *attrs, const type_t *type)
Definition: header.h:94
static enum type_type type_get_type(const type_t *type)
Definition: typetree.h:68
struct S1 s1
static int match(const char *n, const char *m)
Definition: typelib.c:123
const char * kw
Definition: typelib.c:60
Definition: compat.h:1940
uint32_t entry
Definition: isohybrid.c:63
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
GLenum GLsizei len
Definition: glext.h:6722
#define close
Definition: acwin.h:74
Definition: compat.h:1942
unsigned int pointer_size
Definition: widl.c:158
#define KWP(p)
Definition: typelib.c:75
#define O_BINARY
Definition: acwin.h:83
void chat(const char *s,...)
Definition: utils.c:131
static LPCWSTR file_name
Definition: protocol.c:146
MSFT_pSeg pGuidTab
Definition: typelib.h:105
Definition: name.c:36
char * strcpy(char *DstString, const char *SrcString)
Definition: utclib.c:388
static int type_basic_get_sign(const type_t *type)
Definition: typetree.h:80
static int type_array_is_decl_as_ptr(const type_t *type)
Definition: typetree.h:260
int strcmp(const char *String1, const char *String2)
Definition: utclib.c:469
int is_attr(const attr_list_t *list, enum attr_type t)
Definition: header.c:99
GLfloat GLfloat p
Definition: glext.h:8902
char * xstrdup(const char *s)
Definition: uimain.c:768
#define memset(x, y, z)
Definition: compat.h:39
static void tlb_lseek(int fd, off_t offset)
Definition: typelib.c:270
unsigned short get_type_vt(type_t *t)
Definition: typelib.c:129
struct CFHEADER header
Definition: fdi.c:109
Definition: compat.h:1941
Definition: compat.h:1938
_CRTIMP int __cdecl read(_In_ int _FileHandle, _Out_writes_bytes_(_MaxCharCount) void *_DstBuf, _In_ unsigned int _MaxCharCount)
static unsigned short builtin_vt(const type_t *t)
Definition: typelib.c:82
static void read_msft_importlib(importlib_t *importlib, int fd)
Definition: typelib.c:282
Definition: path.c:42
#define O_RDONLY
Definition: acwin.h:82
#define bsearch
#define NTYPES
Definition: typelib.c:74