OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 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 14454 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
14465 CHECK_EQ(is_eval, frame->IsEval()); | 14465 CHECK_EQ(is_eval, frame->IsEval()); |
14466 CHECK_EQ(is_constructor, frame->IsConstructor()); | 14466 CHECK_EQ(is_constructor, frame->IsConstructor()); |
14467 } | 14467 } |
14468 | 14468 |
14469 | 14469 |
14470 void AnalyzeStackInNativeCode(const v8::FunctionCallbackInfo<v8::Value>& args) { | 14470 void AnalyzeStackInNativeCode(const v8::FunctionCallbackInfo<v8::Value>& args) { |
14471 v8::HandleScope scope(args.GetIsolate()); | 14471 v8::HandleScope scope(args.GetIsolate()); |
14472 const char* origin = "capture-stack-trace-test"; | 14472 const char* origin = "capture-stack-trace-test"; |
14473 const int kOverviewTest = 1; | 14473 const int kOverviewTest = 1; |
14474 const int kDetailedTest = 2; | 14474 const int kDetailedTest = 2; |
| 14475 const int kFunctionName = 3; |
| 14476 const int kDisplayName = 4; |
| 14477 const int kFunctionNameAndDisplayName = 5; |
| 14478 const int kDisplayNameIsNotString = 6; |
| 14479 const int kFunctionNameIsNotString = 7; |
14475 | 14480 |
14476 DCHECK(args.Length() == 1); | 14481 DCHECK(args.Length() == 1); |
14477 | 14482 |
14478 int testGroup = args[0]->Int32Value(); | 14483 int testGroup = args[0]->Int32Value(); |
14479 if (testGroup == kOverviewTest) { | 14484 if (testGroup == kOverviewTest) { |
14480 v8::Handle<v8::StackTrace> stackTrace = v8::StackTrace::CurrentStackTrace( | 14485 v8::Handle<v8::StackTrace> stackTrace = v8::StackTrace::CurrentStackTrace( |
14481 args.GetIsolate(), 10, v8::StackTrace::kOverview); | 14486 args.GetIsolate(), 10, v8::StackTrace::kOverview); |
14482 CHECK_EQ(4, stackTrace->GetFrameCount()); | 14487 CHECK_EQ(4, stackTrace->GetFrameCount()); |
14483 checkStackFrame(origin, "bar", 2, 10, false, false, | 14488 checkStackFrame(origin, "bar", 2, 10, false, false, |
14484 stackTrace->GetFrame(0)); | 14489 stackTrace->GetFrame(0)); |
(...skipping 13 matching lines...) Expand all Loading... |
14498 stackTrace->GetFrame(0)); | 14503 stackTrace->GetFrame(0)); |
14499 checkStackFrame(origin, "baz", 8, 3, false, true, | 14504 checkStackFrame(origin, "baz", 8, 3, false, true, |
14500 stackTrace->GetFrame(1)); | 14505 stackTrace->GetFrame(1)); |
14501 bool is_eval = true; | 14506 bool is_eval = true; |
14502 // This is the source string inside the eval which has the call to baz. | 14507 // This is the source string inside the eval which has the call to baz. |
14503 checkStackFrame(NULL, "", 1, 1, is_eval, false, stackTrace->GetFrame(2)); | 14508 checkStackFrame(NULL, "", 1, 1, is_eval, false, stackTrace->GetFrame(2)); |
14504 // The last frame is an anonymous function which has the initial eval call. | 14509 // The last frame is an anonymous function which has the initial eval call. |
14505 checkStackFrame(origin, "", 10, 1, false, false, stackTrace->GetFrame(3)); | 14510 checkStackFrame(origin, "", 10, 1, false, false, stackTrace->GetFrame(3)); |
14506 | 14511 |
14507 CHECK(stackTrace->AsArray()->IsArray()); | 14512 CHECK(stackTrace->AsArray()->IsArray()); |
| 14513 } else if (testGroup == kFunctionName) { |
| 14514 v8::Handle<v8::StackTrace> stackTrace = v8::StackTrace::CurrentStackTrace( |
| 14515 args.GetIsolate(), 5, v8::StackTrace::kOverview); |
| 14516 CHECK_EQ(3, stackTrace->GetFrameCount()); |
| 14517 checkStackFrame(origin, "function.name", 2, 24, false, false, |
| 14518 stackTrace->GetFrame(0)); |
| 14519 } else if (testGroup == kDisplayName) { |
| 14520 v8::Handle<v8::StackTrace> stackTrace = v8::StackTrace::CurrentStackTrace( |
| 14521 args.GetIsolate(), 5, v8::StackTrace::kOverview); |
| 14522 CHECK_EQ(3, stackTrace->GetFrameCount()); |
| 14523 checkStackFrame(origin, "function.displayName", 2, 24, false, false, |
| 14524 stackTrace->GetFrame(0)); |
| 14525 } else if (testGroup == kFunctionNameAndDisplayName) { |
| 14526 v8::Handle<v8::StackTrace> stackTrace = v8::StackTrace::CurrentStackTrace( |
| 14527 args.GetIsolate(), 5, v8::StackTrace::kOverview); |
| 14528 CHECK_EQ(3, stackTrace->GetFrameCount()); |
| 14529 checkStackFrame(origin, "function.displayName", 2, 24, false, false, |
| 14530 stackTrace->GetFrame(0)); |
| 14531 } else if (testGroup == kDisplayNameIsNotString) { |
| 14532 v8::Handle<v8::StackTrace> stackTrace = v8::StackTrace::CurrentStackTrace( |
| 14533 args.GetIsolate(), 5, v8::StackTrace::kOverview); |
| 14534 CHECK_EQ(3, stackTrace->GetFrameCount()); |
| 14535 checkStackFrame(origin, "function.name", 2, 24, false, false, |
| 14536 stackTrace->GetFrame(0)); |
| 14537 } else if (testGroup == kFunctionNameIsNotString) { |
| 14538 v8::Handle<v8::StackTrace> stackTrace = v8::StackTrace::CurrentStackTrace( |
| 14539 args.GetIsolate(), 5, v8::StackTrace::kOverview); |
| 14540 CHECK_EQ(3, stackTrace->GetFrameCount()); |
| 14541 checkStackFrame(origin, "f", 2, 24, false, false, stackTrace->GetFrame(0)); |
14508 } | 14542 } |
14509 } | 14543 } |
14510 | 14544 |
14511 | 14545 |
14512 // Tests the C++ StackTrace API. | 14546 // Tests the C++ StackTrace API. |
14513 // TODO(3074796): Reenable this as a THREADED_TEST once it passes. | 14547 // TODO(3074796): Reenable this as a THREADED_TEST once it passes. |
14514 // THREADED_TEST(CaptureStackTrace) { | 14548 // THREADED_TEST(CaptureStackTrace) { |
14515 TEST(CaptureStackTrace) { | 14549 TEST(CaptureStackTrace) { |
14516 v8::Isolate* isolate = CcTest::isolate(); | 14550 v8::Isolate* isolate = CcTest::isolate(); |
14517 v8::HandleScope scope(isolate); | 14551 v8::HandleScope scope(isolate); |
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
14559 v8::Handle<v8::Integer> line_offset = v8::Integer::New(isolate, 3); | 14593 v8::Handle<v8::Integer> line_offset = v8::Integer::New(isolate, 3); |
14560 v8::Handle<v8::Integer> column_offset = v8::Integer::New(isolate, 5); | 14594 v8::Handle<v8::Integer> column_offset = v8::Integer::New(isolate, 5); |
14561 v8::ScriptOrigin detailed_origin(origin, line_offset, column_offset); | 14595 v8::ScriptOrigin detailed_origin(origin, line_offset, column_offset); |
14562 v8::ScriptCompiler::Source script_source2(detailed_src, detailed_origin); | 14596 v8::ScriptCompiler::Source script_source2(detailed_src, detailed_origin); |
14563 v8::Handle<v8::UnboundScript> detailed_script( | 14597 v8::Handle<v8::UnboundScript> detailed_script( |
14564 v8::ScriptCompiler::CompileUnbound(isolate, &script_source2)); | 14598 v8::ScriptCompiler::CompileUnbound(isolate, &script_source2)); |
14565 v8::Handle<Value> detailed_result( | 14599 v8::Handle<Value> detailed_result( |
14566 detailed_script->BindToCurrentContext()->Run()); | 14600 detailed_script->BindToCurrentContext()->Run()); |
14567 CHECK(!detailed_result.IsEmpty()); | 14601 CHECK(!detailed_result.IsEmpty()); |
14568 CHECK(detailed_result->IsObject()); | 14602 CHECK(detailed_result->IsObject()); |
| 14603 |
| 14604 // Test using function.name and function.displayName in stack trace |
| 14605 const char* function_name_source = |
| 14606 "function bar(function_name, display_name, testGroup) {\n" |
| 14607 " var f = function() { AnalyzeStackInNativeCode(testGroup); };\n" |
| 14608 " if (function_name) {\n" |
| 14609 " Object.defineProperty(f, 'name', { value: function_name });\n" |
| 14610 " }\n" |
| 14611 " if (display_name) {\n" |
| 14612 " f.displayName = display_name;" |
| 14613 " }\n" |
| 14614 " f()\n" |
| 14615 "}\n" |
| 14616 "bar('function.name', undefined, 3);\n" |
| 14617 "bar(undefined, 'function.displayName', 4);\n" |
| 14618 "bar('function.name', 'function.displayName', 5);\n" |
| 14619 "bar('function.name', 239, 6);\n" |
| 14620 "bar(239, undefined, 7);\n"; |
| 14621 v8::Handle<v8::String> function_name_src = |
| 14622 v8::String::NewFromUtf8(isolate, function_name_source); |
| 14623 v8::ScriptCompiler::Source script_source3(function_name_src, |
| 14624 v8::ScriptOrigin(origin)); |
| 14625 v8::Handle<Value> function_name_result( |
| 14626 v8::ScriptCompiler::CompileUnbound(isolate, &script_source3) |
| 14627 ->BindToCurrentContext() |
| 14628 ->Run()); |
| 14629 CHECK(!function_name_result.IsEmpty()); |
14569 } | 14630 } |
14570 | 14631 |
14571 | 14632 |
14572 static void StackTraceForUncaughtExceptionListener( | 14633 static void StackTraceForUncaughtExceptionListener( |
14573 v8::Handle<v8::Message> message, | 14634 v8::Handle<v8::Message> message, |
14574 v8::Handle<Value>) { | 14635 v8::Handle<Value>) { |
14575 report_count++; | 14636 report_count++; |
14576 v8::Handle<v8::StackTrace> stack_trace = message->GetStackTrace(); | 14637 v8::Handle<v8::StackTrace> stack_trace = message->GetStackTrace(); |
14577 CHECK_EQ(2, stack_trace->GetFrameCount()); | 14638 CHECK_EQ(2, stack_trace->GetFrameCount()); |
14578 checkStackFrame("origin", "foo", 2, 3, false, false, | 14639 checkStackFrame("origin", "foo", 2, 3, false, false, |
(...skipping 1513 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
16092 env->GetIsolate(), | 16153 env->GetIsolate(), |
16093 "var foo = { bar : { baz : function() {}}}; var f = foo.bar.baz;"); | 16154 "var foo = { bar : { baz : function() {}}}; var f = foo.bar.baz;"); |
16094 v8::Script::Compile(script, &origin)->Run(); | 16155 v8::Script::Compile(script, &origin)->Run(); |
16095 v8::Local<v8::Function> f = v8::Local<v8::Function>::Cast( | 16156 v8::Local<v8::Function> f = v8::Local<v8::Function>::Cast( |
16096 env->Global()->Get(v8::String::NewFromUtf8(env->GetIsolate(), "f"))); | 16157 env->Global()->Get(v8::String::NewFromUtf8(env->GetIsolate(), "f"))); |
16097 CHECK_EQ(0, | 16158 CHECK_EQ(0, |
16098 strcmp("foo.bar.baz", *v8::String::Utf8Value(f->GetInferredName()))); | 16159 strcmp("foo.bar.baz", *v8::String::Utf8Value(f->GetInferredName()))); |
16099 } | 16160 } |
16100 | 16161 |
16101 | 16162 |
| 16163 THREADED_TEST(FunctionGetDebugName) { |
| 16164 LocalContext env; |
| 16165 v8::HandleScope scope(env->GetIsolate()); |
| 16166 const char* code = |
| 16167 "var error = false;" |
| 16168 "function a() { this.x = 1; };" |
| 16169 "a.displayName = 'display_a';" |
| 16170 "var b = (function() {" |
| 16171 " var f = function() { this.x = 2; };" |
| 16172 " f.displayName = 'display_b';" |
| 16173 " return f;" |
| 16174 "})();" |
| 16175 "var c = function() {};" |
| 16176 "c.__defineGetter__('displayName', function() {" |
| 16177 " error = true;" |
| 16178 " throw new Error();" |
| 16179 "});" |
| 16180 "function d() {};" |
| 16181 "d.__defineGetter__('displayName', function() {" |
| 16182 " error = true;" |
| 16183 " return 'wrong_display_name';" |
| 16184 "});" |
| 16185 "function e() {};" |
| 16186 "e.displayName = 'wrong_display_name';" |
| 16187 "e.__defineSetter__('displayName', function() {" |
| 16188 " error = true;" |
| 16189 " throw new Error();" |
| 16190 "});" |
| 16191 "function f() {};" |
| 16192 "f.displayName = { 'foo': 6, toString: function() {" |
| 16193 " error = true;" |
| 16194 " return 'wrong_display_name';" |
| 16195 "}};" |
| 16196 "var g = function() {" |
| 16197 " arguments.callee.displayName = 'set_in_runtime';" |
| 16198 "}; g();" |
| 16199 "var h = function() {};" |
| 16200 "h.displayName = 'displayName';" |
| 16201 "Object.defineProperty(h, 'name', { value: 'function.name' });" |
| 16202 "var i = function() {};" |
| 16203 "i.displayName = 239;" |
| 16204 "Object.defineProperty(i, 'name', { value: 'function.name' });" |
| 16205 "var j = function() {};" |
| 16206 "Object.defineProperty(j, 'name', { value: 'function.name' });" |
| 16207 "var foo = { bar : { baz : function() {}}}; var k = foo.bar.baz;"; |
| 16208 v8::ScriptOrigin origin = |
| 16209 v8::ScriptOrigin(v8::String::NewFromUtf8(env->GetIsolate(), "test")); |
| 16210 v8::Script::Compile(v8::String::NewFromUtf8(env->GetIsolate(), code), &origin) |
| 16211 ->Run(); |
| 16212 v8::Local<v8::Value> error = |
| 16213 env->Global()->Get(v8::String::NewFromUtf8(env->GetIsolate(), "error")); |
| 16214 CHECK_EQ(false, error->BooleanValue()); |
| 16215 const char* functions[] = {"a", "display_a", |
| 16216 "b", "display_b", |
| 16217 "c", "c", |
| 16218 "d", "d", |
| 16219 "e", "e", |
| 16220 "f", "f", |
| 16221 "g", "set_in_runtime", |
| 16222 "h", "displayName", |
| 16223 "i", "function.name", |
| 16224 "j", "function.name", |
| 16225 "k", "foo.bar.baz"}; |
| 16226 for (size_t i = 0; i < sizeof(functions) / sizeof(functions[0]) / 2; ++i) { |
| 16227 v8::Local<v8::Function> f = |
| 16228 v8::Local<v8::Function>::Cast(env->Global()->Get( |
| 16229 v8::String::NewFromUtf8(env->GetIsolate(), functions[i * 2]))); |
| 16230 CHECK_EQ(0, strcmp(functions[i * 2 + 1], |
| 16231 *v8::String::Utf8Value(f->GetDebugName()))); |
| 16232 } |
| 16233 } |
| 16234 |
| 16235 |
16102 THREADED_TEST(FunctionGetDisplayName) { | 16236 THREADED_TEST(FunctionGetDisplayName) { |
16103 LocalContext env; | 16237 LocalContext env; |
16104 v8::HandleScope scope(env->GetIsolate()); | 16238 v8::HandleScope scope(env->GetIsolate()); |
16105 const char* code = "var error = false;" | 16239 const char* code = "var error = false;" |
16106 "function a() { this.x = 1; };" | 16240 "function a() { this.x = 1; };" |
16107 "a.displayName = 'display_a';" | 16241 "a.displayName = 'display_a';" |
16108 "var b = (function() {" | 16242 "var b = (function() {" |
16109 " var f = function() { this.x = 2; };" | 16243 " var f = function() { this.x = 2; };" |
16110 " f.displayName = 'display_b';" | 16244 " f.displayName = 'display_b';" |
16111 " return f;" | 16245 " return f;" |
(...skipping 5968 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
22080 env2->Global()->Set(v8_str("obj2"), object2); | 22214 env2->Global()->Set(v8_str("obj2"), object2); |
22081 ExpectString("typeof obj2.values", "function"); | 22215 ExpectString("typeof obj2.values", "function"); |
22082 CHECK_NE(*object->Get(v8_str("values")), *object2->Get(v8_str("values"))); | 22216 CHECK_NE(*object->Get(v8_str("values")), *object2->Get(v8_str("values"))); |
22083 | 22217 |
22084 auto values2 = Local<Function>::Cast(object2->Get(v8_str("values"))); | 22218 auto values2 = Local<Function>::Cast(object2->Get(v8_str("values"))); |
22085 auto fn2 = i::Handle<i::JSFunction>::cast(v8::Utils::OpenHandle(*values2)); | 22219 auto fn2 = i::Handle<i::JSFunction>::cast(v8::Utils::OpenHandle(*values2)); |
22086 auto ctx2 = v8::Utils::OpenHandle(*env2.local()); | 22220 auto ctx2 = v8::Utils::OpenHandle(*env2.local()); |
22087 CHECK_EQ(fn2->GetCreationContext(), *ctx2); | 22221 CHECK_EQ(fn2->GetCreationContext(), *ctx2); |
22088 } | 22222 } |
22089 } | 22223 } |
OLD | NEW |