Jacek Caban : vbscript: Added const statement compiler implementation.
Alexandre Julliard
julliard at winehq.org
Wed Sep 21 13:35:15 CDT 2011
Module: wine
Branch: master
Commit: a968166224439df300689ca8434f14532d7524a4
URL: http://source.winehq.org/git/wine.git/?a=commit;h=a968166224439df300689ca8434f14532d7524a4
Author: Jacek Caban <jacek at codeweavers.com>
Date: Wed Sep 21 14:03:38 2011 +0200
vbscript: Added const statement compiler implementation.
---
dlls/vbscript/compile.c | 78 ++++++++++++++++++++++++++++++++++++++++++++--
dlls/vbscript/interp.c | 7 ++++
dlls/vbscript/vbscript.h | 1 +
3 files changed, 83 insertions(+), 3 deletions(-)
diff --git a/dlls/vbscript/compile.c b/dlls/vbscript/compile.c
index 53b7f81..712d97d 100644
--- a/dlls/vbscript/compile.c
+++ b/dlls/vbscript/compile.c
@@ -46,6 +46,9 @@ typedef struct {
dim_decl_t *dim_decls;
dynamic_var_t *global_vars;
+ const_decl_t *const_decls;
+ const_decl_t *global_consts;
+
function_t *func;
function_t *funcs;
function_decl_t *func_decls;
@@ -302,6 +305,26 @@ static inline void label_set_addr(compile_ctx_t *ctx, unsigned label)
ctx->labels[label & ~LABEL_FLAG] = ctx->instr_cnt;
}
+static expression_t *lookup_const_decls(compile_ctx_t *ctx, const WCHAR *name, BOOL lookup_global)
+{
+ const_decl_t *decl;
+
+ for(decl = ctx->const_decls; decl; decl = decl->next) {
+ if(!strcmpiW(decl->name, name))
+ return decl->value_expr;
+ }
+
+ if(!lookup_global)
+ return NULL;
+
+ for(decl = ctx->global_consts; decl; decl = decl->next) {
+ if(!strcmpiW(decl->name, name))
+ return decl->value_expr;
+ }
+
+ return NULL;
+}
+
static HRESULT compile_args(compile_ctx_t *ctx, expression_t *args, unsigned *ret)
{
unsigned arg_cnt = 0;
@@ -325,6 +348,14 @@ static HRESULT compile_member_expression(compile_ctx_t *ctx, member_expression_t
unsigned arg_cnt = 0;
HRESULT hres;
+ if(ret_val && !expr->args) {
+ expression_t *const_expr;
+
+ const_expr = lookup_const_decls(ctx, expr->identifier, TRUE);
+ if(const_expr)
+ return compile_expression(ctx, const_expr);
+ }
+
hres = compile_args(ctx, expr->args, &arg_cnt);
if(FAILED(hres))
return hres;
@@ -627,7 +658,8 @@ static HRESULT compile_dim_statement(compile_ctx_t *ctx, dim_statement_t *stat)
dim_decl_t *dim_decl = stat->dim_decls;
while(1) {
- if(lookup_dim_decls(ctx, dim_decl->name) || lookup_args_name(ctx, dim_decl->name)) {
+ if(lookup_dim_decls(ctx, dim_decl->name) || lookup_args_name(ctx, dim_decl->name)
+ || lookup_const_decls(ctx, dim_decl->name, FALSE)) {
FIXME("dim %s name redefined\n", debugstr_w(dim_decl->name));
return E_FAIL;
}
@@ -643,6 +675,39 @@ static HRESULT compile_dim_statement(compile_ctx_t *ctx, dim_statement_t *stat)
return S_OK;
}
+static HRESULT compile_const_statement(compile_ctx_t *ctx, const_statement_t *stat)
+{
+ const_decl_t *decl, *next_decl = stat->decls;
+
+ do {
+ decl = next_decl;
+
+ if(lookup_const_decls(ctx, decl->name, FALSE) || lookup_args_name(ctx, decl->name)
+ || lookup_dim_decls(ctx, decl->name)) {
+ FIXME("%s redefined\n", debugstr_w(decl->name));
+ return E_FAIL;
+ }
+
+ if(ctx->func->type == FUNC_GLOBAL) {
+ HRESULT hres;
+
+ hres = compile_expression(ctx, decl->value_expr);
+ if(FAILED(hres))
+ return hres;
+
+ hres = push_instr_bstr(ctx, OP_const, decl->name);
+ if(FAILED(hres))
+ return hres;
+ }
+
+ next_decl = decl->next;
+ decl->next = ctx->const_decls;
+ ctx->const_decls = decl;
+ } while(next_decl);
+
+ return S_OK;
+}
+
static HRESULT compile_function_statement(compile_ctx_t *ctx, function_statement_t *stat)
{
if(ctx->func != &ctx->code->global_code) {
@@ -712,6 +777,9 @@ static HRESULT compile_statement(compile_ctx_t *ctx, statement_t *stat)
case STAT_CALL:
hres = compile_member_expression(ctx, ((call_statement_t*)stat)->expr, FALSE);
break;
+ case STAT_CONST:
+ hres = compile_const_statement(ctx, (const_statement_t*)stat);
+ break;
case STAT_DIM:
hres = compile_dim_statement(ctx, (dim_statement_t*)stat);
break;
@@ -815,6 +883,7 @@ static HRESULT compile_func(compile_ctx_t *ctx, statement_t *stat, function_t *f
ctx->func = func;
ctx->dim_decls = NULL;
+ ctx->const_decls = NULL;
hres = compile_statement(ctx, stat);
ctx->func = NULL;
if(FAILED(hres))
@@ -893,7 +962,7 @@ static HRESULT create_function(compile_ctx_t *ctx, function_decl_t *decl, functi
function_t *func;
HRESULT hres;
- if(lookup_dim_decls(ctx, decl->name) || lookup_funcs_name(ctx, decl->name)) {
+ if(lookup_dim_decls(ctx, decl->name) || lookup_funcs_name(ctx, decl->name) || lookup_const_decls(ctx, decl->name, FALSE)) {
FIXME("%s: redefinition\n", debugstr_w(decl->name));
return E_FAIL;
}
@@ -1019,7 +1088,7 @@ static HRESULT compile_class(compile_ctx_t *ctx, class_decl_t *class_decl)
static const WCHAR class_terminateW[] = {'c','l','a','s','s','_','t','e','r','m','i','n','a','t','e',0};
if(lookup_dim_decls(ctx, class_decl->name) || lookup_funcs_name(ctx, class_decl->name)
- || lookup_class_name(ctx, class_decl->name)) {
+ || lookup_const_decls(ctx, class_decl->name, FALSE) || lookup_class_name(ctx, class_decl->name)) {
FIXME("%s: redefinition\n", debugstr_w(class_decl->name));
return E_FAIL;
}
@@ -1247,6 +1316,7 @@ HRESULT compile_script(script_ctx_t *script, const WCHAR *src, vbscode_t **ret)
ctx.dim_decls = NULL;
ctx.classes = NULL;
ctx.labels = NULL;
+ ctx.global_consts = NULL;
ctx.labels_cnt = ctx.labels_size = 0;
hres = compile_func(&ctx, ctx.parser.stats, &ctx.code->global_code);
@@ -1255,6 +1325,8 @@ HRESULT compile_script(script_ctx_t *script, const WCHAR *src, vbscode_t **ret)
return hres;
}
+ ctx.global_consts = ctx.const_decls;
+
for(func_decl = ctx.func_decls; func_decl; func_decl = func_decl->next) {
hres = create_function(&ctx, func_decl, &new_func);
if(FAILED(hres)) {
diff --git a/dlls/vbscript/interp.c b/dlls/vbscript/interp.c
index aff7b91..232a582 100644
--- a/dlls/vbscript/interp.c
+++ b/dlls/vbscript/interp.c
@@ -644,6 +644,13 @@ static HRESULT interp_set_member(exec_ctx_t *ctx)
return hres;
}
+static HRESULT interp_const(exec_ctx_t *ctx)
+{
+ BSTR arg = ctx->instr->arg1.bstr;
+ FIXME("%s\n", debugstr_w(arg));
+ return E_NOTIMPL;
+}
+
static HRESULT interp_new(exec_ctx_t *ctx)
{
const WCHAR *arg = ctx->instr->arg1.bstr;
diff --git a/dlls/vbscript/vbscript.h b/dlls/vbscript/vbscript.h
index 5a968d1..73b0b86 100644
--- a/dlls/vbscript/vbscript.h
+++ b/dlls/vbscript/vbscript.h
@@ -184,6 +184,7 @@ typedef enum {
X(assign_member, 1, ARG_BSTR, 0) \
X(bool, 1, ARG_INT, 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) \
More information about the wine-cvs
mailing list