diff --git a/dlls/vbscript/lex.c b/dlls/vbscript/lex.c index d8c5ed30045..f78eee4ff91 100644 --- a/dlls/vbscript/lex.c +++ b/dlls/vbscript/lex.c @@ -72,9 +72,11 @@ static const struct { {L"on", tON}, {L"option", tOPTION}, {L"or", tOR}, + {L"preserve", tPRESERVE}, {L"private", tPRIVATE}, {L"property", tPROPERTY}, {L"public", tPUBLIC}, + {L"redim", tREDIM}, {L"rem", tREM}, {L"resume", tRESUME}, {L"select", tSELECT}, diff --git a/dlls/vbscript/parse.h b/dlls/vbscript/parse.h index f4f8a5e5e2b..4bf82cbedb3 100644 --- a/dlls/vbscript/parse.h +++ b/dlls/vbscript/parse.h @@ -120,6 +120,7 @@ typedef enum { STAT_FUNC, STAT_IF, STAT_ONERROR, + STAT_REDIM, STAT_SELECT, STAT_SET, STAT_STOP, @@ -165,6 +166,13 @@ typedef struct _dim_statement_t { dim_decl_t *dim_decls; } dim_statement_t; +typedef struct { + statement_t stat; + const WCHAR *identifier; + BOOL preserve; + expression_t *dims; +} redim_statement_t; + typedef struct _arg_decl_t { const WCHAR *name; BOOL by_ref; diff --git a/dlls/vbscript/parser.y b/dlls/vbscript/parser.y index 8bb99f9f9a4..46af0b16bea 100644 --- a/dlls/vbscript/parser.y +++ b/dlls/vbscript/parser.y @@ -51,6 +51,7 @@ static statement_t *new_call_statement(parser_ctx_t*,BOOL,expression_t*); static statement_t *new_assign_statement(parser_ctx_t*,expression_t*,expression_t*); static statement_t *new_set_statement(parser_ctx_t*,member_expression_t*,expression_t*,expression_t*); static statement_t *new_dim_statement(parser_ctx_t*,dim_decl_t*); +static statement_t *new_redim_statement(parser_ctx_t*,const WCHAR*,BOOL,expression_t*); static statement_t *new_while_statement(parser_ctx_t*,statement_type_t,expression_t*,statement_t*); static statement_t *new_forto_statement(parser_ctx_t*,const WCHAR*,expression_t*,expression_t*,expression_t*,statement_t*); static statement_t *new_foreach_statement(parser_ctx_t*,const WCHAR*,expression_t*,statement_t*); @@ -112,7 +113,8 @@ static statement_t *link_statements(statement_t*,statement_t*); %token tTRUE tFALSE %token tNOT tAND tOR tXOR tEQV tIMP %token tIS tMOD -%token tCALL tDIM tSUB tFUNCTION tGET tLET tCONST +%token tCALL tSUB tFUNCTION tGET tLET tCONST +%token tDIM tREDIM tPRESERVE %token tIF tELSE tELSEIF tEND tTHEN tEXIT %token tWHILE tWEND tDO tLOOP tUNTIL tFOR tTO tEACH tIN %token tSELECT tCASE tWITH @@ -133,7 +135,7 @@ static statement_t *link_statements(statement_t*,statement_t*); %type ConstExpression NumericLiteralExpression %type MemberExpression %type Arguments Arguments_opt ArgumentList ArgumentList_opt Step_opt ExpressionList -%type OptionExplicit_opt DoType +%type OptionExplicit_opt DoType Preserve_opt %type ArgumentsDecl_opt ArgumentDeclList ArgumentDecl %type FunctionDecl PropertyDecl %type ElseIfs_opt ElseIfs ElseIf @@ -194,6 +196,8 @@ SimpleStatement | CallExpression '=' Expression { $$ = new_assign_statement(ctx, $1, $3); CHECK_ERROR; } | tDIM DimDeclList { $$ = new_dim_statement(ctx, $2); CHECK_ERROR; } + | tREDIM Preserve_opt tIdentifier '(' ArgumentList ')' + { $$ = new_redim_statement(ctx, $3, $2, $5); CHECK_ERROR; } | IfStatement { $$ = $1; } | tWHILE Expression StSep StatementsNl_opt tWEND { $$ = new_while_statement(ctx, STAT_WHILE, $2, $4); CHECK_ERROR; } @@ -231,6 +235,10 @@ MemberExpression | tDOT DotIdentifier { expression_t *dot_expr = new_expression(ctx, EXPR_DOT, sizeof(*dot_expr)); CHECK_ERROR; $$ = new_member_expression(ctx, dot_expr, $2); CHECK_ERROR; } +Preserve_opt + : /* empty */ { $$ = FALSE; } + | tPRESERVE { $$ = TRUE; } + DimDeclList : DimDecl { $$ = $1; } | DimDecl ',' DimDeclList { $1->next = $3; $$ = $1; } @@ -537,6 +545,8 @@ DotIdentifier | tRESUME { $$ = $1; } | tGOTO { $$ = $1; } | tWITH { $$ = $1; } + | tREDIM { $$ = $1; } + | tPRESERVE { $$ = $1; } /* Most statements accept both new line and ':' as separators */ StSep @@ -864,6 +874,20 @@ static statement_t *new_dim_statement(parser_ctx_t *ctx, dim_decl_t *decls) return &stat->stat; } +static statement_t *new_redim_statement(parser_ctx_t *ctx, const WCHAR *identifier, BOOL preserve, expression_t *dims) +{ + redim_statement_t *stat; + + stat = new_statement(ctx, STAT_REDIM, sizeof(*stat)); + if(!stat) + return NULL; + + stat->identifier = identifier; + stat->preserve = preserve; + stat->dims = dims; + return &stat->stat; +} + static elseif_decl_t *new_elseif_decl(parser_ctx_t *ctx, expression_t *expr, statement_t *stat) { elseif_decl_t *decl;