vbscript: Added VBScript.RegExp version 1.0 typelib.
[wine] / dlls / vbscript / vbscript.h
index 3f55b40..2ce93b6 100644 (file)
 #include "wine/list.h"
 #include "wine/unicode.h"
 
+typedef struct {
+    void **blocks;
+    DWORD block_cnt;
+    DWORD last_block;
+    DWORD offset;
+    struct list custom_blocks;
+} vbsheap_t;
+
+void vbsheap_init(vbsheap_t*) DECLSPEC_HIDDEN;
+void *vbsheap_alloc(vbsheap_t*,size_t) __WINE_ALLOC_SIZE(2) DECLSPEC_HIDDEN;
+void vbsheap_free(vbsheap_t*) DECLSPEC_HIDDEN;
+
 typedef struct _function_t function_t;
 typedef struct _vbscode_t vbscode_t;
 typedef struct _script_ctx_t script_ctx_t;
+typedef struct _vbdisp_t vbdisp_t;
 
 typedef struct named_item_t {
     IDispatch *disp;
@@ -43,43 +56,204 @@ typedef struct named_item_t {
     struct list entry;
 } named_item_t;
 
+typedef enum {
+    VBDISP_CALLGET,
+    VBDISP_LET,
+    VBDISP_SET,
+    VBDISP_ANY
+} vbdisp_invoke_type_t;
+
+typedef struct {
+    BOOL is_public;
+    const WCHAR *name;
+} vbdisp_prop_desc_t;
+
 typedef struct {
+    const WCHAR *name;
+    BOOL is_public;
+    function_t *entries[VBDISP_ANY];
+} vbdisp_funcprop_desc_t;
+
+#define BP_GET      1
+#define BP_GETPUT   2
+
+typedef struct {
+    DISPID id;
+    HRESULT (*proc)(vbdisp_t*,VARIANT*,unsigned,VARIANT*);
+    DWORD flags;
+    unsigned min_args;
+    unsigned max_args;
+} builtin_prop_t;
+
+typedef struct _class_desc_t {
+    const WCHAR *name;
+    script_ctx_t *ctx;
+
+    unsigned class_initialize_id;
+    unsigned class_terminate_id;
+    unsigned func_cnt;
+    vbdisp_funcprop_desc_t *funcs;
+
+    unsigned prop_cnt;
+    vbdisp_prop_desc_t *props;
+
+    unsigned builtin_prop_cnt;
+    const builtin_prop_t *builtin_props;
+    ITypeInfo *typeinfo;
+    function_t *value_func;
+
+    struct _class_desc_t *next;
+} class_desc_t;
+
+struct _vbdisp_t {
     IDispatchEx IDispatchEx_iface;
 
     LONG ref;
-} vbdisp_t;
+    BOOL terminator_ran;
+    struct list entry;
+
+    const class_desc_t *desc;
+    VARIANT props[1];
+};
+
+typedef struct _ident_map_t ident_map_t;
+
+typedef struct {
+    IDispatchEx IDispatchEx_iface;
+    LONG ref;
+
+    ident_map_t *ident_map;
+    unsigned ident_map_cnt;
+    unsigned ident_map_size;
+
+    script_ctx_t *ctx;
+} ScriptDisp;
+
+HRESULT create_vbdisp(const class_desc_t*,vbdisp_t**) DECLSPEC_HIDDEN;
+HRESULT disp_get_id(IDispatch*,BSTR,vbdisp_invoke_type_t,BOOL,DISPID*) DECLSPEC_HIDDEN;
+HRESULT vbdisp_get_id(vbdisp_t*,BSTR,vbdisp_invoke_type_t,BOOL,DISPID*) DECLSPEC_HIDDEN;
+HRESULT disp_call(script_ctx_t*,IDispatch*,DISPID,DISPPARAMS*,VARIANT*) DECLSPEC_HIDDEN;
+HRESULT disp_propput(script_ctx_t*,IDispatch*,DISPID,DISPPARAMS*) DECLSPEC_HIDDEN;
+void collect_objects(script_ctx_t*) DECLSPEC_HIDDEN;
+HRESULT create_procedure_disp(script_ctx_t*,vbscode_t*,IDispatch**) DECLSPEC_HIDDEN;
+HRESULT create_script_disp(script_ctx_t*,ScriptDisp**) DECLSPEC_HIDDEN;
 
-HRESULT disp_get_id(IDispatch*,BSTR,DISPID*);
-HRESULT disp_call(script_ctx_t*,IDispatch*,DISPID,DISPPARAMS*,VARIANT*);
+static inline unsigned arg_cnt(const DISPPARAMS *dp)
+{
+    return dp->cArgs - dp->cNamedArgs;
+}
+
+static inline VARIANT *get_arg(DISPPARAMS *dp, DWORD i)
+{
+    return dp->rgvarg + dp->cArgs-i-1;
+}
+
+typedef struct _dynamic_var_t {
+    struct _dynamic_var_t *next;
+    VARIANT v;
+    const WCHAR *name;
+    BOOL is_const;
+} dynamic_var_t;
 
 struct _script_ctx_t {
     IActiveScriptSite *site;
     LCID lcid;
 
+    IInternetHostSecurityManager *secmgr;
+    DWORD safeopt;
+
     IDispatch *host_global;
 
-    vbdisp_t *script_obj;
+    ScriptDisp *script_obj;
 
+    class_desc_t global_desc;
+    vbdisp_t *global_obj;
+
+    class_desc_t err_desc;
+    vbdisp_t *err_obj;
+
+    dynamic_var_t *global_vars;
+    function_t *global_funcs;
+    class_desc_t *classes;
+    class_desc_t *procs;
+
+    vbsheap_t heap;
+
+    struct list objects;
     struct list code_list;
     struct list named_items;
 };
 
-HRESULT init_global(script_ctx_t*);
+HRESULT init_global(script_ctx_t*) DECLSPEC_HIDDEN;
+HRESULT init_err(script_ctx_t*) DECLSPEC_HIDDEN;
+
+IUnknown *create_ax_site(script_ctx_t*) DECLSPEC_HIDDEN;
 
 typedef enum {
     ARG_NONE = 0,
     ARG_STR,
     ARG_BSTR,
     ARG_INT,
-    ARG_UINT
+    ARG_UINT,
+    ARG_ADDR,
+    ARG_DOUBLE
 } instr_arg_type_t;
 
 #define OP_LIST                                   \
+    X(add,            1, 0,           0)          \
+    X(and,            1, 0,           0)          \
+    X(assign_ident,   1, ARG_BSTR,    ARG_UINT)   \
+    X(assign_member,  1, ARG_BSTR,    ARG_UINT)   \
     X(bool,           1, ARG_INT,     0)          \
+    X(case,           0, ARG_ADDR,    0)          \
+    X(concat,         1, 0,           0)          \
+    X(const,          1, ARG_BSTR,    0)          \
+    X(div,            1, 0,           0)          \
+    X(double,         1, ARG_DOUBLE,  0)          \
+    X(empty,          1, 0,           0)          \
+    X(enumnext,       0, ARG_ADDR,    ARG_BSTR)   \
+    X(equal,          1, 0,           0)          \
+    X(errmode,        1, ARG_INT,     0)          \
+    X(eqv,            1, 0,           0)          \
+    X(exp,            1, 0,           0)          \
+    X(gt,             1, 0,           0)          \
+    X(gteq,           1, 0,           0)          \
+    X(icall,          1, ARG_BSTR,    ARG_UINT)   \
     X(icallv,         1, ARG_BSTR,    ARG_UINT)   \
+    X(idiv,           1, 0,           0)          \
+    X(imp,            1, 0,           0)          \
+    X(incc,           1, ARG_BSTR,    0)          \
+    X(is,             1, 0,           0)          \
+    X(jmp,            0, ARG_ADDR,    0)          \
+    X(jmp_false,      0, ARG_ADDR,    0)          \
+    X(jmp_true,       0, ARG_ADDR,    0)          \
+    X(long,           1, ARG_INT,     0)          \
+    X(lt,             1, 0,           0)          \
+    X(lteq,           1, 0,           0)          \
+    X(mcall,          1, ARG_BSTR,    ARG_UINT)   \
+    X(mcallv,         1, ARG_BSTR,    ARG_UINT)   \
+    X(me,             1, 0,           0)          \
+    X(mod,            1, 0,           0)          \
+    X(mul,            1, 0,           0)          \
+    X(neg,            1, 0,           0)          \
+    X(nequal,         1, 0,           0)          \
+    X(new,            1, ARG_STR,     0)          \
+    X(newenum,        1, 0,           0)          \
     X(not,            1, 0,           0)          \
+    X(nothing,        1, 0,           0)          \
+    X(null,           1, 0,           0)          \
+    X(or,             1, 0,           0)          \
+    X(pop,            1, ARG_UINT,    0)          \
     X(ret,            0, 0,           0)          \
-    X(string,         1, ARG_STR,     0)
+    X(set_ident,      1, ARG_BSTR,    ARG_UINT)   \
+    X(set_member,     1, ARG_BSTR,    ARG_UINT)   \
+    X(short,          1, ARG_INT,     0)          \
+    X(step,           0, ARG_ADDR,    ARG_BSTR)   \
+    X(stop,           1, 0,           0)          \
+    X(string,         1, ARG_STR,     0)          \
+    X(sub,            1, 0,           0)          \
+    X(val,            1, 0,           0)          \
+    X(xor,            1, 0,           0)
 
 typedef enum {
 #define X(x,n,a,b) OP_##x,
@@ -93,6 +267,7 @@ typedef union {
     BSTR bstr;
     unsigned uint;
     LONG lng;
+    double *dbl;
 } instr_arg_t;
 
 typedef struct {
@@ -101,9 +276,36 @@ typedef struct {
     instr_arg_t arg2;
 } instr_t;
 
+typedef struct {
+    const WCHAR *name;
+    BOOL by_ref;
+} arg_desc_t;
+
+typedef enum {
+    FUNC_GLOBAL,
+    FUNC_FUNCTION,
+    FUNC_SUB,
+    FUNC_PROPGET,
+    FUNC_PROPLET,
+    FUNC_PROPSET,
+    FUNC_DEFGET
+} function_type_t;
+
+typedef struct {
+    const WCHAR *name;
+} var_desc_t;
+
 struct _function_t {
+    function_type_t type;
+    const WCHAR *name;
+    BOOL is_public;
+    arg_desc_t *args;
+    unsigned arg_cnt;
+    var_desc_t *vars;
+    unsigned var_cnt;
     unsigned code_off;
     vbscode_t *code_ctx;
+    function_t *next;
 };
 
 struct _vbscode_t {
@@ -112,21 +314,51 @@ struct _vbscode_t {
 
     BOOL option_explicit;
 
-    BOOL global_executed;
-    function_t global_code;
+    BOOL pending_exec;
+    function_t main_code;
 
     BSTR *bstr_pool;
     unsigned bstr_pool_size;
     unsigned bstr_cnt;
+    vbsheap_t heap;
 
     struct list entry;
 };
 
 void release_vbscode(vbscode_t*) DECLSPEC_HIDDEN;
-HRESULT compile_script(script_ctx_t*,const WCHAR*,vbscode_t**) DECLSPEC_HIDDEN;
-HRESULT exec_script(script_ctx_t*,function_t*) DECLSPEC_HIDDEN;
+HRESULT compile_script(script_ctx_t*,const WCHAR*,const WCHAR*,vbscode_t**) DECLSPEC_HIDDEN;
+HRESULT exec_script(script_ctx_t*,function_t*,IDispatch*,DISPPARAMS*,VARIANT*) DECLSPEC_HIDDEN;
+void release_dynamic_vars(dynamic_var_t*) DECLSPEC_HIDDEN;
+
+#define TID_LIST \
+    XDIID(ErrObj) \
+    XDIID(GlobalObj)
+
+typedef enum {
+#define XDIID(iface) iface ## _tid,
+TID_LIST
+#undef XDIID
+    LAST_tid
+} tid_t;
+
+HRESULT get_typeinfo(tid_t,ITypeInfo**) DECLSPEC_HIDDEN;
+
+#ifndef INT32_MIN
+#define INT32_MIN (-2147483647-1)
+#endif
+
+#ifndef INT32_MAX
+#define INT32_MAX (2147483647)
+#endif
+
+static inline BOOL is_int32(double d)
+{
+    return INT32_MIN <= d && d <= INT32_MAX && (double)(int)d == d;
+}
+
+HRESULT WINAPI VBScriptFactory_CreateInstance(IClassFactory*,IUnknown*,REFIID,void**) DECLSPEC_HIDDEN;
 
-HRESULT WINAPI VBScriptFactory_CreateInstance(IClassFactory*,IUnknown*,REFIID,void**);
+const char *debugstr_variant(const VARIANT*) DECLSPEC_HIDDEN;
 
 static inline void *heap_alloc(size_t len)
 {