--- parser3/src/main/execute.C 2013/10/04 21:21:55 1.371 +++ parser3/src/main/execute.C 2015/05/07 18:27:35 1.374 @@ -21,7 +21,7 @@ #include "pa_vimage.h" #include "pa_wwrapper.h" -volatile const char * IDENT_EXECUTE_C="$Id: execute.C,v 1.371 2013/10/04 21:21:55 moko Exp $" IDENT_PA_OPCODE_H IDENT_PA_OPERATION_H IDENT_PA_VCODE_FRAME_H IDENT_PA_WWRAPPER_H; +volatile const char * IDENT_EXECUTE_C="$Id: execute.C,v 1.374 2015/05/07 18:27:35 moko Exp $" IDENT_PA_OPCODE_H IDENT_PA_OPERATION_H IDENT_PA_VCODE_FRAME_H IDENT_PA_WWRAPPER_H; //#define DEBUG_EXECUTE @@ -76,6 +76,10 @@ char *opcode_name[]={ "WITH_SELF__VALUE__CONSTRUCT_VALUE", #endif +#ifdef OPTIMIZE_BYTECODE_GET_ELEMENT__SPECIAL + "GET_ELEMENT__SPECIAL", + "GET_ELEMENT__SPECIAL__WRITE", +#endif // expression ops: unary "NEG", "INV", "NOT", "DEF", "IN", "FEXISTS", "DEXISTS", // expression ops: binary @@ -263,8 +267,7 @@ void Request::execute(ArrayOperation& op wcontext->set_somebody_entered_some_class(); debug_origin=i.next().origin; - Value& value=*i.next().value; - const String& name=*value.get_string(); debug_name=&name; + const String& name=*i.next().value->get_string(); debug_name=&name; DEBUG_PRINT_STRING(name) @@ -277,6 +280,38 @@ void Request::execute(ArrayOperation& op stack.push(*class_value); break; } + +#ifdef OPTIMIZE_BYTECODE_GET_ELEMENT__SPECIAL + case OP::OP_GET_ELEMENT__SPECIAL: + case OP::OP_GET_ELEMENT__SPECIAL__WRITE: + { + const String& name=stack.pop().string(); debug_name=&name; + Value& ncontext=stack.pop().value(); + + Value* value=0; + if(VStateless_class* vclass=ncontext.get_class()){ + if(name==class_element_name){ + value=vclass; + } else if(name==class_name_element_name){ + value=new VString(vclass->name()); + } + } else { + // Value + if(name==class_element_name){ + value=&ncontext; + }else if(name==class_name_element_name){ + value=new VString(*new String(ncontext.type())); + } + }; + if(opcode==OP::OP_GET_ELEMENT__SPECIAL){ + stack.push(*value); + } else { + write_assign_lang(*value); + } + break; + } +#endif + // OP_WITH case OP::OP_WITH_ROOT: { @@ -1359,7 +1394,9 @@ StringOrValue Request::process(Value& in Junction* junction=input_value.get_junction(); if(junction) { if(junction->is_getter) { // is it a getter-junction? - return process_getter(*junction); + StringOrValue result=process_getter(*junction); + Value *value=result.get_value(); + return value ? process(*value, intercept_string) : result; } if(junction->code) { // is it a code-junction? @@ -1422,7 +1459,9 @@ void Request::process_write(Value& input Junction* junction=input_value.get_junction(); if(junction) { if(junction->is_getter) { // is it a getter-junction? - write_pass_lang(process_getter(*junction)); + StringOrValue result=process_getter(*junction); + Value *value=result.get_value(); + value ? process_write(*value) : write_pass_lang(result); return; } @@ -1594,6 +1633,7 @@ const String* Request::get_method_filena origin=i.next().origin; break; } + default: break; } if(origin.file_no) return get_used_filename(origin.file_no);