📄 swf5compiler.y
字号:
{ $$ = newBuffer(); bufferWriteOp($$, SWFACTION_GOTOLABEL); bufferWriteS16($$, strlen($3)+1); bufferWriteHardString($$, $3, strlen($3)+1); free($3); bufferWriteOp($$, SWFACTION_STOP); } | GOTOANDPLAY '(' expr ')' { $$ = $3; bufferWriteOp($$, SWFACTION_GOTOFRAME2); bufferWriteS16($$, 1); bufferWriteU8($$, 1); } /* XXX - and play */ | GOTOANDSTOP '(' expr ')' { $$ = $3; bufferWriteOp($$, SWFACTION_GOTOFRAME2); bufferWriteS16($$, 1); bufferWriteU8($$, 0); } /* XXX - and stop */ | SETTARGET '(' STRING ')' { $$ = newBuffer(); bufferWriteOp($$, SWFACTION_SETTARGET); bufferWriteS16($$, strlen($3)+1); bufferWriteHardString($$, $3, strlen($3)+1); free($3); } | SETTARGET '(' expr ')' { $$ = $3; bufferWriteOp($$, SWFACTION_SETTARGET2); } | SETPROPERTY '(' expr ',' property ',' expr ')' { $$ = $3; bufferWriteFloat($$, $5); bufferConcat($$, $7); bufferWriteOp($$, SWFACTION_SETPROPERTY); } ;function_call : IDENTIFIER '(' expr_list ')' {#ifdef DEBUG printf("function_call: %s '(' expr_list ')'\n", $1);#endif $$ = $3.buffer; bufferWriteInt($$, $3.count); bufferWriteString($$, $1, strlen($1)+1); bufferWriteOp($$, SWFACTION_CALLFUNCTION); free($1); } | TARGETPATH '(' IDENTIFIER ')' { $$ = newBuffer(); bufferWriteString($$, $3, strlen($3)+1); free($3); bufferWriteOp($$, SWFACTION_GETVARIABLE); bufferWriteOp($$, SWFACTION_TARGETPATH); } | EVAL '(' expr ')' { $$ = $3; bufferWriteOp($$, SWFACTION_GETVARIABLE); } | GETTIMER '(' ')' { $$ = newBuffer(); bufferWriteOp($$, SWFACTION_GETTIME); } | RANDOM '(' expr ')' { $$ = $3; bufferWriteOp($$, SWFACTION_RANDOMNUMBER); } | LENGTH '(' expr_or_obj ')' { $$ = $3; bufferWriteOp($$, SWFACTION_STRINGLENGTH); } | INT '(' expr ')' { $$ = $3; bufferWriteOp($$, SWFACTION_INT); } | ORD '(' expr ')' { $$ = $3; bufferWriteOp($$, SWFACTION_ORD); } | CHR '(' expr ')' { $$ = $3; bufferWriteOp($$, SWFACTION_CHR); } | CONCAT '(' expr ',' expr ')' { $$ = $3; bufferConcat($$, $5); bufferWriteOp($$, SWFACTION_STRINGCONCAT); } | SUBSTRING '(' expr ',' expr ',' expr ')' { $$ = $3; bufferConcat($$, $5); bufferConcat($$, $7); bufferWriteOp($$, SWFACTION_SUBSTRING); } | TYPEOF '(' expr_or_obj ')' {#ifdef DEBUG printf("function_call: TYPEOF '(' expr_or_obj ')'\n");#endif $$ = $3; bufferWriteOp($$, SWFACTION_TYPEOF); } | GETPROPERTY '(' expr ',' property ')' { $$ = newBuffer(); bufferConcat($$, $3); bufferWriteFloat($$, $5); bufferWriteOp($$, SWFACTION_GETPROPERTY); } ;/* legacy and built-in functions */delete_call : DELETE obj_ref_for_delete_only { $$ = $2; if($2->hasObject) bufferWriteOp($$, SWFACTION_DELETE); else bufferWriteOp($$, SWFACTION_DELETE2); } ;expr_list : /* empty */ { $$.buffer = newBuffer(); $$.count = 0; } | expr_or_obj { $$.buffer = $1; $$.count = 1; } /* goes backwards. rrgh. */ | expr_list ',' expr_or_obj { Buffer tmp = newBuffer(); bufferConcat(tmp, $3); bufferConcat(tmp, $$.buffer); $$.buffer = tmp; ++$$.count; } ;method_call : lvalue_expr '.' identifier '(' expr_list ')' { $$ = $5.buffer; bufferWriteInt($$, $5.count); bufferConcat($$, $1); bufferWriteString($$, $3, strlen($3)+1); bufferWriteOp($$, SWFACTION_CALLMETHOD); free($3); } | lvalue_expr '[' expr ']' '(' expr_list ')' { $$ = $6.buffer; bufferWriteInt($$, $6.count); bufferConcat($$, $1); bufferConcat($$, $3); bufferWriteOp($$, SWFACTION_CALLMETHOD); } ;objexpr : identifier ':' expr_or_obj { $$ = newBuffer(); bufferWriteString($$, $1, strlen($1)+1); bufferConcat($$, $3); free($1); } ;objexpr_list : objexpr { $$.buffer = $1; $$.count = 1; } | objexpr_list ',' objexpr { bufferConcat($$.buffer, $3); ++$$.count; } ;assignop : "+=" { $$ = SWFACTION_ADD2; } | "-=" { $$ = SWFACTION_SUBTRACT; } | "*=" { $$ = SWFACTION_MULTIPLY; } | "/=" { $$ = SWFACTION_DIVIDE; } | "%=" { $$ = SWFACTION_MODULO; } | "&=" { $$ = SWFACTION_BITWISEAND; } | "|=" { $$ = SWFACTION_BITWISEOR; } | "^=" { $$ = SWFACTION_BITWISEXOR; } | "<<=" { $$ = SWFACTION_SHIFTLEFT; } | ">>=" { $$ = SWFACTION_SHIFTRIGHT; } | ">>>=" { $$ = SWFACTION_SHIFTRIGHT2; } ;incdecop : "++" { $$ = SWFACTION_INCREMENT; } | "--" { $$ = SWFACTION_DECREMENT; } ;/* resolves an lvalue into a buffer */lvalue_expr : lvalue { if($1.obj) { $$ = $1.obj; if($1.ident) bufferConcat($$, $1.ident); else bufferConcat($$, $1.memexpr); bufferWriteOp($$, SWFACTION_GETMEMBER); } else { $$ = $1.ident; bufferWriteOp($$, SWFACTION_GETVARIABLE); } } | function_call | method_call ;/* lvalue - things you can assign to */lvalue : identifier { $$.ident = newBuffer(); bufferWriteString($$.ident, $1, strlen($1)+1); free($1); $$.obj = 0; $$.memexpr = 0; } | lvalue_expr '.' identifier %prec '.' { $$.obj = $1; $$.ident = newBuffer(); bufferWriteString($$.ident, $3, strlen($3)+1); free($3); $$.memexpr = 0; } | lvalue_expr '[' expr ']' %prec '.' { $$.obj = $1; $$.memexpr = $3; $$.ident = 0; } ;/* these leave a value on the stack */expr : primary | primary_constant | '-' expr %prec UMINUS { $$ = $2; bufferWriteInt($2, -1); bufferWriteOp($2, SWFACTION_MULTIPLY); } | '~' expr %prec UMINUS { $$ = $2; bufferWriteInt($2, 0xffffffff); bufferWriteOp($2, SWFACTION_BITWISEXOR); } | '!' expr { $$ = $2; bufferWriteOp($2, SWFACTION_LOGICALNOT); } | expr LAN expr { $$ = $1; bufferWriteOp($$, SWFACTION_PUSHDUP); bufferWriteOp($$, SWFACTION_LOGICALNOT); bufferWriteOp($$, SWFACTION_IF); bufferWriteS16($$, 2); bufferWriteS16($$, bufferLength($3)+1); bufferWriteOp($$, SWFACTION_POP); bufferConcatSimple($$, $3); } | expr LOR expr { $$ = $1; bufferWriteOp($$, SWFACTION_PUSHDUP); bufferWriteOp($$, SWFACTION_IF); bufferWriteS16($$, 2); bufferWriteS16($$, bufferLength($3)+1); bufferWriteOp($$, SWFACTION_POP); bufferConcatSimple($$, $3); } | expr '*' expr { $$ = $1; bufferConcat($$, $3); bufferWriteOp($$, SWFACTION_MULTIPLY); } | expr '/' expr { $$ = $1; bufferConcat($$, $3); bufferWriteOp($$, SWFACTION_DIVIDE); } | expr '%' expr { $$ = $1; bufferConcat($$, $3); bufferWriteOp($$, SWFACTION_MODULO); } | expr '+' expr { $$ = $1; bufferConcat($$, $3); bufferWriteOp($$, SWFACTION_ADD2); } | expr '-' expr { $$ = $1; bufferConcat($$, $3); bufferWriteOp($$, SWFACTION_SUBTRACT); } | expr '&' expr { $$ = $1; bufferConcat($$, $3); bufferWriteOp($$, SWFACTION_BITWISEAND); } | expr '|' expr { $$ = $1; bufferConcat($$, $3); bufferWriteOp($$, SWFACTION_BITWISEOR); } | expr '^' expr { $$ = $1; bufferConcat($$, $3); bufferWriteOp($$, SWFACTION_BITWISEXOR); } | expr '<' expr { $$ = $1; bufferConcat($$, $3); bufferWriteOp($$, SWFACTION_LESS2); } | expr '>' expr { $$ = $3; bufferConcat($$, $1); bufferWriteOp($$, SWFACTION_LESS2); } | expr "<=" expr { $$ = $3; bufferConcat($$, $1); bufferWriteOp($$, SWFACTION_LESS2); bufferWriteOp($$, SWFACTION_LOGICALNOT); } | expr ">=" expr { bufferConcat($1, $3); bufferWriteOp($1, SWFACTION_LESS2); bufferWriteOp($1, SWFACTION_LOGICALNOT); } | expr "==" expr { bufferConcat($1, $3); bufferWriteOp($1, SWFACTION_EQUALS2); } | expr "===" expr { bufferConcat($1, $3); bufferWriteOp($1, SWFACTION_STRICTEQUALS); } | expr "!=" expr { bufferConcat($1, $3); bufferWriteOp($1, SWFACTION_EQUALS2); bufferWriteOp($1, SWFACTION_LOGICALNOT); } | expr "!==" expr { bufferConcat($1, $3); bufferWriteOp($1, SWFACTION_STRICTEQUALS); bufferWriteOp($1, SWFACTION_LOGICALNOT); } | expr "<<" expr { bufferConcat($1, $3); bufferWriteOp($1, SWFACTION_SHIFTLEFT); } | expr ">>" expr { bufferConcat($1, $3); bufferWriteOp($1, SWFACTION_SHIFTRIGHT); } | expr ">>>" expr { bufferConcat($1, $3); bufferWriteOp($1, SWFACTION_SHIFTRIGHT2); } | expr '?' expr ':' expr { bufferWriteOp($1, SWFACTION_IF); bufferWriteS16($1, 2); bufferWriteS16($1, bufferLength($5)+5); bufferConcatSimple($1, $5); bufferWriteOp($1, SWFACTION_JUMP); bufferWriteS16($1, 2); bufferWriteS16($1, bufferLength($3)); bufferConcatSimple($1, $3); } | lvalue '=' expr_or_obj { if($1.obj) /* obj[memexpr] or obj.ident */ { $$ = $1.obj; if($1.ident) bufferConcat($$, $1.ident); else bufferConcat($$, $1.memexpr); bufferConcat($$, $3); bufferWriteSetRegister($$, 0); bufferWriteOp($$, SWFACTION_SETMEMBER); bufferWriteRegister($$, 0); } else /* just ident */ { $$ = $3; bufferWriteOp($$, SWFACTION_PUSHDUP); bufferConcat($$, $1.ident); bufferWriteOp($$, SWFACTION_STACKSWAP); bufferWriteOp($$, SWFACTION_SETVARIABLE); }/* tricky case missing here: lvalue ASSIGN expr *//* like in x = y += z; */ } | expr INSTANCEOF lvalue_expr { $$ = $1; bufferConcat($$, $3); bufferWriteOp($$, SWFACTION_INSTANCEOF); } ;expr_or_obj : expr | NEW identifier {#ifdef DEBUG printf("NEW %s\n", $2);#endif $$ = newBuffer(); bufferWriteInt($$, 0); bufferWriteString($$, $2, strlen($2)+1); free($2); bufferWriteOp($$, SWFACTION_NEWOBJECT); } | NEW IDENTIFIER '(' expr_list ')' {#ifdef DEBUG printf("NEW %s '(' expr_list ')'\n", $2);#endif $$ = $4.buffer; bufferWriteInt($$, $4.count); bufferWriteString($$, $2, strlen($2)+1); free($2); bufferWriteOp($$, SWFACTION_NEWOBJECT); } | NEW lvalue_expr '.' IDENTIFIER {#ifdef DEBUG printf("NEW lvalue_expr '.' %s\n", $4);#endif $$ = newBuffer(); bufferWriteInt($$, 0); bufferConcat($$, $2); bufferWriteString($$, $4, strlen($4)+1); free($4); bufferWriteOp($$, SWFACTION_NEWMETHOD); } | NEW lvalue_expr '[' expr ']' {#ifdef DEBUG printf("NEW lvalue_expr '[' expr ']'\n");#endif $$ = newBuffer(); bufferWriteInt($$, 0); bufferConcat($$, $2); bufferConcat($$, $4); bufferWriteOp($$, SWFACTION_NEWMETHOD); } | NEW lvalue_expr '.' IDENTIFIER '(' expr_list ')' {#ifdef DEBUG printf("NEW lvalue_expr '.' %s '(' expr_list ')'\n", $4);#endif $$ = $6.buffer; bufferWriteInt($$, $6.count); bufferConcat($$, $2); bufferWriteString($$, $4, strlen($4)+1); free($4); bufferWriteOp($$, SWFACTION_NEWMETHOD); } | NEW lvalue_expr '[' expr ']' '(' expr_list ')' {#ifdef DEBUG printf("NEW lvalue_expr '[' expr ']' '(' expr_list ')'\n");#endif $$ = $7.buffer; bufferWriteInt($$, $7.count); bufferConcat($$, $2); bufferConcat($$, $4); bufferWriteOp($$, SWFACTION_NEWMETHOD); } | '[' expr_list ']' { $$ = $2.buffer; bufferWriteInt($$, $2.count); bufferWriteOp($$, SWFACTION_INITARRAY); } | emptybraces { $$ = newBuffer(); bufferWriteInt($$, 0); bufferWriteOp($$, SWFACTION_INITOBJECT); } | '{' objexpr_list '}' { $$ = $2.buffer; bufferWriteInt($$, $2.count); bufferWriteOp($$, SWFACTION_INITOBJECT); } ;primary : function_decl { if($1->name != NULL) { swf5error("anonymous decl only. identifier not allowed"); YYABORT; } $$ = newBuffer(); if(swfVersion > 6) bufferWriteFunction($$, $1, 2); else bufferWriteFunction($$, $1, 1); } | lvalue_expr | delete_call | incdecop lvalue %prec "++" { if($2.obj) { if($2.ident) // expr . identifier { $$ = $2.obj; bufferWriteOp($$, SWFACTION_PUSHDUP); /* a, a */ bufferWriteBuffer($$, $2.ident); /* a, a, i */ bufferWriteOp($$, SWFACTION_STACKSWAP); /* a, i, a */ bufferConcat($$, $2.ident); /* a, i, a, i */ bufferWriteOp($$, SWFACTION_GETMEMBER); bufferWriteOp($$, $1); bufferWriteSetRegister($$, 0); bufferWriteOp($$, SWFACTION_SETMEMBER); /* a.i = a.i+1 */ bufferWriteRegister($$, 0); /* a.i+1 */ }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -