| OLD | NEW |
| 1 // Copyright 2007-2008 the V8 project authors. All rights reserved. | 1 // Copyright 2007-2008 the V8 project authors. All rights reserved. |
| 2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
| 3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
| 4 // met: | 4 // met: |
| 5 // | 5 // |
| 6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
| 7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
| 8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
| 9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
| 10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
| (...skipping 4000 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4011 " if (str.indexOf('#<a Fun>') == -1) return 3;" | 4011 " if (str.indexOf('#<a Fun>') == -1) return 3;" |
| 4012 " return 0;" | 4012 " return 0;" |
| 4013 " }" | 4013 " }" |
| 4014 " return 4;" | 4014 " return 4;" |
| 4015 "}" | 4015 "}" |
| 4016 "test();"); | 4016 "test();"); |
| 4017 CHECK_EQ(0, value->Int32Value()); | 4017 CHECK_EQ(0, value->Int32Value()); |
| 4018 } | 4018 } |
| 4019 | 4019 |
| 4020 | 4020 |
| 4021 THREADED_TEST(Eval) { |
| 4022 v8::HandleScope scope; |
| 4023 LocalContext current; |
| 4024 |
| 4025 // Test that un-aliased eval uses local context. |
| 4026 Local<Script> script = |
| 4027 Script::Compile(v8_str("foo = 0;" |
| 4028 "(function() {" |
| 4029 " var foo = 2;" |
| 4030 " return eval('foo');" |
| 4031 "})();")); |
| 4032 Local<Value> result = script->Run(); |
| 4033 CHECK_EQ(2, result->Int32Value()); |
| 4034 |
| 4035 // Test that un-aliased eval has right this. |
| 4036 script = |
| 4037 Script::Compile(v8_str("function MyObject() { this.self = eval('this'); }" |
| 4038 "var o = new MyObject();" |
| 4039 "o === o.self")); |
| 4040 result = script->Run(); |
| 4041 CHECK(result->IsTrue()); |
| 4042 } |
| 4043 |
| 4044 |
| 4021 THREADED_TEST(CrossEval) { | 4045 THREADED_TEST(CrossEval) { |
| 4022 v8::HandleScope scope; | 4046 v8::HandleScope scope; |
| 4023 LocalContext other; | 4047 LocalContext other; |
| 4024 LocalContext current; | 4048 LocalContext current; |
| 4025 | 4049 |
| 4026 Local<String> token = v8_str("<security token>"); | 4050 Local<String> token = v8_str("<security token>"); |
| 4027 other->SetSecurityToken(token); | 4051 other->SetSecurityToken(token); |
| 4028 current->SetSecurityToken(token); | 4052 current->SetSecurityToken(token); |
| 4029 | 4053 |
| 4030 // Setup reference from current to other. | 4054 // Setup reference from current to other. |
| 4031 current->Global()->Set(v8_str("other"), other->Global()); | 4055 current->Global()->Set(v8_str("other"), other->Global()); |
| 4032 | 4056 |
| 4033 // Check that new variables are introduced in other context. | 4057 // Check that new variables are introduced in other context. |
| 4034 Local<Script> script = | 4058 Local<Script> script = |
| 4035 Script::Compile(v8_str("other.eval('var foo = 1234')")); | 4059 Script::Compile(v8_str("other.eval('var foo = 1234')")); |
| 4036 script->Run(); | 4060 script->Run(); |
| 4037 Local<Value> foo = other->Global()->Get(v8_str("foo")); | 4061 Local<Value> foo = other->Global()->Get(v8_str("foo")); |
| 4038 CHECK_EQ(1234, foo->Int32Value()); | 4062 CHECK_EQ(1234, foo->Int32Value()); |
| 4039 CHECK(!current->Global()->Has(v8_str("foo"))); | 4063 CHECK(!current->Global()->Has(v8_str("foo"))); |
| 4040 | 4064 |
| 4041 // Check that writing to non-existing properties introduces them in | 4065 // Check that writing to non-existing properties introduces them in |
| 4042 // the current context. | 4066 // the other context. |
| 4043 script = | 4067 script = |
| 4044 Script::Compile(v8_str("other.eval('na = 1234')")); | 4068 Script::Compile(v8_str("other.eval('na = 1234')")); |
| 4045 script->Run(); | 4069 script->Run(); |
| 4046 CHECK_EQ(1234, current->Global()->Get(v8_str("na"))->Int32Value()); | 4070 CHECK_EQ(1234, other->Global()->Get(v8_str("na"))->Int32Value()); |
| 4047 CHECK(!other->Global()->Has(v8_str("na"))); | 4071 CHECK(!current->Global()->Has(v8_str("na"))); |
| 4048 | 4072 |
| 4049 // Check that variables in current context are visible in other | 4073 // Check that global variables in current context are not visible in other |
| 4050 // context. This must include local variables. | 4074 // context. |
| 4075 v8::TryCatch try_catch; |
| 4051 script = | 4076 script = |
| 4052 Script::Compile(v8_str("var bar = 42;" | 4077 Script::Compile(v8_str("var bar = 42; other.eval('bar');")); |
| 4053 "(function() { " | |
| 4054 " var baz = 87;" | |
| 4055 " return other.eval('bar + baz');" | |
| 4056 "})();")); | |
| 4057 Local<Value> result = script->Run(); | 4078 Local<Value> result = script->Run(); |
| 4058 CHECK_EQ(42 + 87, result->Int32Value()); | 4079 CHECK(try_catch.HasCaught()); |
| 4080 try_catch.Reset(); |
| 4081 |
| 4082 // Check that local variables in current context are not visible in other |
| 4083 // context. |
| 4084 script = |
| 4085 Script::Compile(v8_str("(function() { " |
| 4086 " var baz = 87;" |
| 4087 " return other.eval('baz');" |
| 4088 "})();")); |
| 4089 result = script->Run(); |
| 4090 CHECK(try_catch.HasCaught()); |
| 4091 try_catch.Reset(); |
| 4059 | 4092 |
| 4060 // Check that global variables in the other environment are visible | 4093 // Check that global variables in the other environment are visible |
| 4061 // when evaluting code. | 4094 // when evaluting code. |
| 4062 other->Global()->Set(v8_str("bis"), v8_num(1234)); | 4095 other->Global()->Set(v8_str("bis"), v8_num(1234)); |
| 4063 script = Script::Compile(v8_str("other.eval('bis')")); | 4096 script = Script::Compile(v8_str("other.eval('bis')")); |
| 4064 CHECK_EQ(1234, script->Run()->Int32Value()); | 4097 CHECK_EQ(1234, script->Run()->Int32Value()); |
| 4098 CHECK(!try_catch.HasCaught()); |
| 4065 | 4099 |
| 4066 // Check that the 'this' pointer isn't touched as a result of | 4100 // Check that the 'this' pointer points to the global object evaluating |
| 4067 // calling eval across environments. | 4101 // code. |
| 4102 other->Global()->Set(v8_str("t"), other->Global()); |
| 4103 script = Script::Compile(v8_str("other.eval('this == t')")); |
| 4104 result = script->Run(); |
| 4105 CHECK(result->IsTrue()); |
| 4106 CHECK(!try_catch.HasCaught()); |
| 4107 |
| 4108 // Check that variables introduced in with-statement are not visible in |
| 4109 // other context. |
| 4068 script = | 4110 script = |
| 4069 Script::Compile(v8_str("var t = this; other.eval('this == t')")); | 4111 Script::Compile(v8_str("with({x:2}){other.eval('x')}")); |
| 4070 result = script->Run(); | 4112 result = script->Run(); |
| 4071 CHECK(result->IsBoolean()); | 4113 CHECK(try_catch.HasCaught()); |
| 4072 CHECK(result->BooleanValue()); | 4114 try_catch.Reset(); |
| 4073 | 4115 |
| 4074 // Check that doing a cross eval works from within a global | 4116 // Check that you cannot use 'eval.call' with another object than the |
| 4075 // with-statement. | 4117 // current global object. |
| 4076 script = | 4118 script = |
| 4077 Script::Compile(v8_str("other.y = 1;" | 4119 Script::Compile(v8_str("other.y = 1; eval.call(other, 'y')")); |
| 4078 "with({x:2}){other.eval('x+y')}")); | |
| 4079 result = script->Run(); | 4120 result = script->Run(); |
| 4080 CHECK_EQ(3, result->Int32Value()); | 4121 CHECK(try_catch.HasCaught()); |
| 4081 } | 4122 } |
| 4082 | 4123 |
| 4083 | 4124 |
| 4084 THREADED_TEST(CrossLazyLoad) { | 4125 THREADED_TEST(CrossLazyLoad) { |
| 4085 v8::HandleScope scope; | 4126 v8::HandleScope scope; |
| 4086 LocalContext other; | 4127 LocalContext other; |
| 4087 LocalContext current; | 4128 LocalContext current; |
| 4088 | 4129 |
| 4089 Local<String> token = v8_str("<security token>"); | 4130 Local<String> token = v8_str("<security token>"); |
| 4090 other->SetSecurityToken(token); | 4131 other->SetSecurityToken(token); |
| (...skipping 1116 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 5207 LocalContext context; | 5248 LocalContext context; |
| 5208 Local<ObjectTemplate> templ = ObjectTemplate::New(); | 5249 Local<ObjectTemplate> templ = ObjectTemplate::New(); |
| 5209 templ->SetAccessCheckCallbacks(NamedSetAccessBlocker, | 5250 templ->SetAccessCheckCallbacks(NamedSetAccessBlocker, |
| 5210 IndexedSetAccessBlocker); | 5251 IndexedSetAccessBlocker); |
| 5211 templ->Set(v8_str("x"), v8::True()); | 5252 templ->Set(v8_str("x"), v8::True()); |
| 5212 Local<v8::Object> instance = templ->NewInstance(); | 5253 Local<v8::Object> instance = templ->NewInstance(); |
| 5213 context->Global()->Set(v8_str("obj"), instance); | 5254 context->Global()->Set(v8_str("obj"), instance); |
| 5214 Local<Value> value = CompileRun("obj.x"); | 5255 Local<Value> value = CompileRun("obj.x"); |
| 5215 CHECK(value->BooleanValue()); | 5256 CHECK(value->BooleanValue()); |
| 5216 } | 5257 } |
| 5258 |
| 5259 |
| 5260 static String::ExternalStringResource* SymbolCallback(const char* chars, |
| 5261 size_t length) { |
| 5262 uint16_t* buffer = i::NewArray<uint16_t>(length + 1); |
| 5263 for (size_t i = 0; i < length; i++) { |
| 5264 buffer[i] = chars[i]; |
| 5265 } |
| 5266 buffer[length] = '\0'; |
| 5267 return new TestResource(buffer); |
| 5268 } |
| 5269 |
| 5270 |
| 5271 static v8::Handle<Value> ExternalSymbolGetter(Local<String> name, |
| 5272 const AccessorInfo& info) { |
| 5273 ApiTestFuzzer::Fuzz(); |
| 5274 CHECK(!name->Equals(v8_str("externalSymbol722")) || name->IsExternal()); |
| 5275 return v8::True(); |
| 5276 } |
| 5277 |
| 5278 |
| 5279 static void ExternalSymbolSetter(Local<String> name, |
| 5280 Local<Value> value, |
| 5281 const AccessorInfo&) { |
| 5282 ApiTestFuzzer::Fuzz(); |
| 5283 CHECK(!name->Equals(v8_str("externalSymbol722")) || name->IsExternal()); |
| 5284 } |
| 5285 |
| 5286 |
| 5287 THREADED_TEST(ExternalSymbols) { |
| 5288 TestResource::dispose_count = 0; |
| 5289 v8::V8::SetExternalSymbolCallback(SymbolCallback); |
| 5290 v8::HandleScope scope; |
| 5291 LocalContext context; |
| 5292 Local<ObjectTemplate> templ = ObjectTemplate::New(); |
| 5293 // Use a bizare name so that the name does not clash with names used |
| 5294 // in natives files. If running with snapshots enabled, variable |
| 5295 // names used in the native files will be normal symbols instead of |
| 5296 // external ones. Also, make sure that the bizare name is used from |
| 5297 // JavaScript code before using it from C++ code. |
| 5298 Local<Value> value = |
| 5299 CompileRun("var o = { externalSymbol722: 42 }; o.externalSymbol722"); |
| 5300 CHECK_EQ(42, value->Int32Value()); |
| 5301 templ->SetAccessor(v8_str("externalSymbol722"), |
| 5302 ExternalSymbolGetter, |
| 5303 ExternalSymbolSetter); |
| 5304 context->Global()->Set(v8_str("obj"), templ->NewInstance()); |
| 5305 value = CompileRun("obj.externalSymbol722"); |
| 5306 CHECK_EQ(true, value->BooleanValue()); |
| 5307 value = CompileRun("obj.externalSymbol722 = 42"); |
| 5308 v8::V8::SetExternalSymbolCallback(NULL); |
| 5309 } |
| 5310 |
| 5311 |
| 5312 // This test verifies that pre-compilation (aka preparsing) can be called |
| 5313 // without initializing the whole VM. Thus we cannot run this test in a |
| 5314 // multi-threaded setup. |
| 5315 TEST(PreCompile) { |
| 5316 // TODO(155): This test would break without the initialization of V8. This is |
| 5317 // a workaround for now to make this test not fail. |
| 5318 v8::V8::Initialize(); |
| 5319 const char *script = "function foo(a) { return a+1; }"; |
| 5320 v8::ScriptData *sd = v8::ScriptData::PreCompile(script, strlen(script)); |
| 5321 CHECK_NE(sd->Length(), 0); |
| 5322 CHECK_NE(sd->Data(), NULL); |
| 5323 } |
| OLD | NEW |