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 3838 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3849 | 3849 |
3850 CHECK(r->IsFunction()); | 3850 CHECK(r->IsFunction()); |
3851 CHECK_EQ(1, break_point_hit_count); | 3851 CHECK_EQ(1, break_point_hit_count); |
3852 | 3852 |
3853 // Get rid of the debug event listener. | 3853 // Get rid of the debug event listener. |
3854 v8::Debug::SetDebugEventListener(NULL); | 3854 v8::Debug::SetDebugEventListener(NULL); |
3855 CheckDebuggerUnloaded(); | 3855 CheckDebuggerUnloaded(); |
3856 } | 3856 } |
3857 | 3857 |
3858 | 3858 |
| 3859 static void DebugEventCounterCheck(int caught, int uncaught, int message) { |
| 3860 CHECK_EQ(caught, exception_hit_count); |
| 3861 CHECK_EQ(uncaught, uncaught_exception_hit_count); |
| 3862 CHECK_EQ(message, message_callback_count); |
| 3863 } |
| 3864 |
| 3865 |
3859 // Test break on exceptions. For each exception break combination the number | 3866 // Test break on exceptions. For each exception break combination the number |
3860 // of debug event exception callbacks and message callbacks are collected. The | 3867 // of debug event exception callbacks and message callbacks are collected. The |
3861 // number of debug event exception callbacks are used to check that the | 3868 // number of debug event exception callbacks are used to check that the |
3862 // debugger is called correctly and the number of message callbacks is used to | 3869 // debugger is called correctly and the number of message callbacks is used to |
3863 // check that uncaught exceptions are still returned even if there is a break | 3870 // check that uncaught exceptions are still returned even if there is a break |
3864 // for them. | 3871 // for them. |
3865 TEST(BreakOnException) { | 3872 TEST(BreakOnException) { |
3866 DebugLocalContext env; | 3873 DebugLocalContext env; |
3867 v8::HandleScope scope(env->GetIsolate()); | 3874 v8::HandleScope scope(env->GetIsolate()); |
3868 env.ExposeDebug(); | 3875 env.ExposeDebug(); |
3869 | 3876 |
3870 // Create functions for testing break on exception. | 3877 // Create functions for testing break on exception. |
3871 CompileFunction(&env, "function throws(){throw 1;}", "throws"); | 3878 CompileFunction(&env, "function throws(){throw 1;}", "throws"); |
3872 v8::Local<v8::Function> caught = | 3879 v8::Local<v8::Function> caught = |
3873 CompileFunction(&env, | 3880 CompileFunction(&env, |
3874 "function caught(){try {throws();} catch(e) {};}", | 3881 "function caught(){try {throws();} catch(e) {};}", |
3875 "caught"); | 3882 "caught"); |
3876 v8::Local<v8::Function> notCaught = | 3883 v8::Local<v8::Function> notCaught = |
3877 CompileFunction(&env, "function notCaught(){throws();}", "notCaught"); | 3884 CompileFunction(&env, "function notCaught(){throws();}", "notCaught"); |
| 3885 v8::Local<v8::Function> notCaughtFinally = CompileFunction( |
| 3886 &env, "function notCaughtFinally(){try{throws();}finally{}}", |
| 3887 "notCaughtFinally"); |
| 3888 // In this edge case, even though this finally does not propagate the |
| 3889 // exception, the debugger considers this uncaught, since we want to break |
| 3890 // at the first throw for the general case where finally implicitly rethrows. |
| 3891 v8::Local<v8::Function> edgeCaseFinally = CompileFunction( |
| 3892 &env, "function caughtFinally(){L:try{throws();}finally{break L;}}", |
| 3893 "caughtFinally"); |
3878 | 3894 |
3879 v8::V8::AddMessageListener(MessageCallbackCount); | 3895 v8::V8::AddMessageListener(MessageCallbackCount); |
3880 v8::Debug::SetDebugEventListener(DebugEventCounter); | 3896 v8::Debug::SetDebugEventListener(DebugEventCounter); |
3881 | 3897 |
3882 // Initial state should be no break on exceptions. | 3898 // Initial state should be no break on exceptions. |
3883 DebugEventCounterClear(); | 3899 DebugEventCounterClear(); |
3884 MessageCallbackCountClear(); | 3900 MessageCallbackCountClear(); |
3885 caught->Call(env->Global(), 0, NULL); | 3901 caught->Call(env->Global(), 0, NULL); |
3886 CHECK_EQ(0, exception_hit_count); | 3902 DebugEventCounterCheck(0, 0, 0); |
3887 CHECK_EQ(0, uncaught_exception_hit_count); | |
3888 CHECK_EQ(0, message_callback_count); | |
3889 notCaught->Call(env->Global(), 0, NULL); | 3903 notCaught->Call(env->Global(), 0, NULL); |
3890 CHECK_EQ(0, exception_hit_count); | 3904 DebugEventCounterCheck(0, 0, 1); |
3891 CHECK_EQ(0, uncaught_exception_hit_count); | 3905 notCaughtFinally->Call(env->Global(), 0, NULL); |
3892 CHECK_EQ(1, message_callback_count); | 3906 DebugEventCounterCheck(0, 0, 2); |
| 3907 edgeCaseFinally->Call(env->Global(), 0, NULL); |
| 3908 DebugEventCounterCheck(0, 0, 2); |
3893 | 3909 |
3894 // No break on exception | 3910 // No break on exception |
3895 DebugEventCounterClear(); | 3911 DebugEventCounterClear(); |
3896 MessageCallbackCountClear(); | 3912 MessageCallbackCountClear(); |
3897 ChangeBreakOnException(false, false); | 3913 ChangeBreakOnException(false, false); |
3898 caught->Call(env->Global(), 0, NULL); | 3914 caught->Call(env->Global(), 0, NULL); |
3899 CHECK_EQ(0, exception_hit_count); | 3915 DebugEventCounterCheck(0, 0, 0); |
3900 CHECK_EQ(0, uncaught_exception_hit_count); | |
3901 CHECK_EQ(0, message_callback_count); | |
3902 notCaught->Call(env->Global(), 0, NULL); | 3916 notCaught->Call(env->Global(), 0, NULL); |
3903 CHECK_EQ(0, exception_hit_count); | 3917 DebugEventCounterCheck(0, 0, 1); |
3904 CHECK_EQ(0, uncaught_exception_hit_count); | 3918 notCaughtFinally->Call(env->Global(), 0, NULL); |
3905 CHECK_EQ(1, message_callback_count); | 3919 DebugEventCounterCheck(0, 0, 2); |
| 3920 edgeCaseFinally->Call(env->Global(), 0, NULL); |
| 3921 DebugEventCounterCheck(0, 0, 2); |
3906 | 3922 |
3907 // Break on uncaught exception | 3923 // Break on uncaught exception |
3908 DebugEventCounterClear(); | 3924 DebugEventCounterClear(); |
3909 MessageCallbackCountClear(); | 3925 MessageCallbackCountClear(); |
3910 ChangeBreakOnException(false, true); | 3926 ChangeBreakOnException(false, true); |
3911 caught->Call(env->Global(), 0, NULL); | 3927 caught->Call(env->Global(), 0, NULL); |
3912 CHECK_EQ(0, exception_hit_count); | 3928 DebugEventCounterCheck(0, 0, 0); |
3913 CHECK_EQ(0, uncaught_exception_hit_count); | |
3914 CHECK_EQ(0, message_callback_count); | |
3915 notCaught->Call(env->Global(), 0, NULL); | 3929 notCaught->Call(env->Global(), 0, NULL); |
3916 CHECK_EQ(1, exception_hit_count); | 3930 DebugEventCounterCheck(1, 1, 1); |
3917 CHECK_EQ(1, uncaught_exception_hit_count); | 3931 notCaughtFinally->Call(env->Global(), 0, NULL); |
3918 CHECK_EQ(1, message_callback_count); | 3932 DebugEventCounterCheck(2, 2, 2); |
| 3933 edgeCaseFinally->Call(env->Global(), 0, NULL); |
| 3934 DebugEventCounterCheck(3, 3, 2); |
3919 | 3935 |
3920 // Break on exception and uncaught exception | 3936 // Break on exception and uncaught exception |
3921 DebugEventCounterClear(); | 3937 DebugEventCounterClear(); |
3922 MessageCallbackCountClear(); | 3938 MessageCallbackCountClear(); |
3923 ChangeBreakOnException(true, true); | 3939 ChangeBreakOnException(true, true); |
3924 caught->Call(env->Global(), 0, NULL); | 3940 caught->Call(env->Global(), 0, NULL); |
3925 CHECK_EQ(1, exception_hit_count); | 3941 DebugEventCounterCheck(1, 0, 0); |
3926 CHECK_EQ(0, uncaught_exception_hit_count); | |
3927 CHECK_EQ(0, message_callback_count); | |
3928 notCaught->Call(env->Global(), 0, NULL); | 3942 notCaught->Call(env->Global(), 0, NULL); |
3929 CHECK_EQ(2, exception_hit_count); | 3943 DebugEventCounterCheck(2, 1, 1); |
3930 CHECK_EQ(1, uncaught_exception_hit_count); | 3944 notCaughtFinally->Call(env->Global(), 0, NULL); |
3931 CHECK_EQ(1, message_callback_count); | 3945 DebugEventCounterCheck(3, 2, 2); |
| 3946 edgeCaseFinally->Call(env->Global(), 0, NULL); |
| 3947 DebugEventCounterCheck(4, 3, 2); |
3932 | 3948 |
3933 // Break on exception | 3949 // Break on exception |
3934 DebugEventCounterClear(); | 3950 DebugEventCounterClear(); |
3935 MessageCallbackCountClear(); | 3951 MessageCallbackCountClear(); |
3936 ChangeBreakOnException(true, false); | 3952 ChangeBreakOnException(true, false); |
3937 caught->Call(env->Global(), 0, NULL); | 3953 caught->Call(env->Global(), 0, NULL); |
3938 CHECK_EQ(1, exception_hit_count); | 3954 DebugEventCounterCheck(1, 0, 0); |
3939 CHECK_EQ(0, uncaught_exception_hit_count); | |
3940 CHECK_EQ(0, message_callback_count); | |
3941 notCaught->Call(env->Global(), 0, NULL); | 3955 notCaught->Call(env->Global(), 0, NULL); |
3942 CHECK_EQ(2, exception_hit_count); | 3956 DebugEventCounterCheck(2, 1, 1); |
3943 CHECK_EQ(1, uncaught_exception_hit_count); | 3957 notCaughtFinally->Call(env->Global(), 0, NULL); |
3944 CHECK_EQ(1, message_callback_count); | 3958 DebugEventCounterCheck(3, 2, 2); |
| 3959 edgeCaseFinally->Call(env->Global(), 0, NULL); |
| 3960 DebugEventCounterCheck(4, 3, 2); |
3945 | 3961 |
3946 // No break on exception using JavaScript | 3962 // No break on exception using JavaScript |
3947 DebugEventCounterClear(); | 3963 DebugEventCounterClear(); |
3948 MessageCallbackCountClear(); | 3964 MessageCallbackCountClear(); |
3949 ChangeBreakOnExceptionFromJS(env->GetIsolate(), false, false); | 3965 ChangeBreakOnExceptionFromJS(env->GetIsolate(), false, false); |
3950 caught->Call(env->Global(), 0, NULL); | 3966 caught->Call(env->Global(), 0, NULL); |
3951 CHECK_EQ(0, exception_hit_count); | 3967 DebugEventCounterCheck(0, 0, 0); |
3952 CHECK_EQ(0, uncaught_exception_hit_count); | |
3953 CHECK_EQ(0, message_callback_count); | |
3954 notCaught->Call(env->Global(), 0, NULL); | 3968 notCaught->Call(env->Global(), 0, NULL); |
3955 CHECK_EQ(0, exception_hit_count); | 3969 DebugEventCounterCheck(0, 0, 1); |
3956 CHECK_EQ(0, uncaught_exception_hit_count); | 3970 notCaughtFinally->Call(env->Global(), 0, NULL); |
3957 CHECK_EQ(1, message_callback_count); | 3971 DebugEventCounterCheck(0, 0, 2); |
| 3972 edgeCaseFinally->Call(env->Global(), 0, NULL); |
| 3973 DebugEventCounterCheck(0, 0, 2); |
3958 | 3974 |
3959 // Break on uncaught exception using JavaScript | 3975 // Break on uncaught exception using JavaScript |
3960 DebugEventCounterClear(); | 3976 DebugEventCounterClear(); |
3961 MessageCallbackCountClear(); | 3977 MessageCallbackCountClear(); |
3962 ChangeBreakOnExceptionFromJS(env->GetIsolate(), false, true); | 3978 ChangeBreakOnExceptionFromJS(env->GetIsolate(), false, true); |
3963 caught->Call(env->Global(), 0, NULL); | 3979 caught->Call(env->Global(), 0, NULL); |
3964 CHECK_EQ(0, exception_hit_count); | 3980 DebugEventCounterCheck(0, 0, 0); |
3965 CHECK_EQ(0, uncaught_exception_hit_count); | |
3966 CHECK_EQ(0, message_callback_count); | |
3967 notCaught->Call(env->Global(), 0, NULL); | 3981 notCaught->Call(env->Global(), 0, NULL); |
3968 CHECK_EQ(1, exception_hit_count); | 3982 DebugEventCounterCheck(1, 1, 1); |
3969 CHECK_EQ(1, uncaught_exception_hit_count); | 3983 notCaughtFinally->Call(env->Global(), 0, NULL); |
3970 CHECK_EQ(1, message_callback_count); | 3984 DebugEventCounterCheck(2, 2, 2); |
| 3985 edgeCaseFinally->Call(env->Global(), 0, NULL); |
| 3986 DebugEventCounterCheck(3, 3, 2); |
3971 | 3987 |
3972 // Break on exception and uncaught exception using JavaScript | 3988 // Break on exception and uncaught exception using JavaScript |
3973 DebugEventCounterClear(); | 3989 DebugEventCounterClear(); |
3974 MessageCallbackCountClear(); | 3990 MessageCallbackCountClear(); |
3975 ChangeBreakOnExceptionFromJS(env->GetIsolate(), true, true); | 3991 ChangeBreakOnExceptionFromJS(env->GetIsolate(), true, true); |
3976 caught->Call(env->Global(), 0, NULL); | 3992 caught->Call(env->Global(), 0, NULL); |
3977 CHECK_EQ(1, exception_hit_count); | 3993 DebugEventCounterCheck(1, 0, 0); |
3978 CHECK_EQ(0, message_callback_count); | |
3979 CHECK_EQ(0, uncaught_exception_hit_count); | |
3980 notCaught->Call(env->Global(), 0, NULL); | 3994 notCaught->Call(env->Global(), 0, NULL); |
3981 CHECK_EQ(2, exception_hit_count); | 3995 DebugEventCounterCheck(2, 1, 1); |
3982 CHECK_EQ(1, uncaught_exception_hit_count); | 3996 notCaughtFinally->Call(env->Global(), 0, NULL); |
3983 CHECK_EQ(1, message_callback_count); | 3997 DebugEventCounterCheck(3, 2, 2); |
| 3998 edgeCaseFinally->Call(env->Global(), 0, NULL); |
| 3999 DebugEventCounterCheck(4, 3, 2); |
3984 | 4000 |
3985 // Break on exception using JavaScript | 4001 // Break on exception using JavaScript |
3986 DebugEventCounterClear(); | 4002 DebugEventCounterClear(); |
3987 MessageCallbackCountClear(); | 4003 MessageCallbackCountClear(); |
3988 ChangeBreakOnExceptionFromJS(env->GetIsolate(), true, false); | 4004 ChangeBreakOnExceptionFromJS(env->GetIsolate(), true, false); |
3989 caught->Call(env->Global(), 0, NULL); | 4005 caught->Call(env->Global(), 0, NULL); |
3990 CHECK_EQ(1, exception_hit_count); | 4006 DebugEventCounterCheck(1, 0, 0); |
3991 CHECK_EQ(0, uncaught_exception_hit_count); | |
3992 CHECK_EQ(0, message_callback_count); | |
3993 notCaught->Call(env->Global(), 0, NULL); | 4007 notCaught->Call(env->Global(), 0, NULL); |
3994 CHECK_EQ(2, exception_hit_count); | 4008 DebugEventCounterCheck(2, 1, 1); |
3995 CHECK_EQ(1, uncaught_exception_hit_count); | 4009 notCaughtFinally->Call(env->Global(), 0, NULL); |
3996 CHECK_EQ(1, message_callback_count); | 4010 DebugEventCounterCheck(3, 2, 2); |
| 4011 edgeCaseFinally->Call(env->Global(), 0, NULL); |
| 4012 DebugEventCounterCheck(4, 3, 2); |
3997 | 4013 |
3998 v8::Debug::SetDebugEventListener(NULL); | 4014 v8::Debug::SetDebugEventListener(NULL); |
3999 CheckDebuggerUnloaded(); | 4015 CheckDebuggerUnloaded(); |
4000 v8::V8::RemoveMessageListeners(MessageCallbackCount); | 4016 v8::V8::RemoveMessageListeners(MessageCallbackCount); |
4001 } | 4017 } |
4002 | 4018 |
4003 | 4019 |
| 4020 static void try_finally_original_message(v8::Handle<v8::Message> message, |
| 4021 v8::Handle<v8::Value> data) { |
| 4022 CHECK_EQ(2, message->GetLineNumber()); |
| 4023 CHECK_EQ(2, message->GetStartColumn()); |
| 4024 message_callback_count++; |
| 4025 } |
| 4026 |
| 4027 |
| 4028 TEST(TryFinallyOriginalMessage) { |
| 4029 // Test that the debugger plays nicely with the pending message. |
| 4030 message_callback_count = 0; |
| 4031 DebugEventCounterClear(); |
| 4032 v8::V8::AddMessageListener(try_finally_original_message); |
| 4033 v8::Debug::SetDebugEventListener(DebugEventCounter); |
| 4034 ChangeBreakOnException(true, true); |
| 4035 DebugLocalContext env; |
| 4036 v8::Isolate* isolate = CcTest::isolate(); |
| 4037 v8::HandleScope scope(isolate); |
| 4038 CompileRun( |
| 4039 "try {\n" |
| 4040 " throw 1;\n" |
| 4041 "} finally {\n" |
| 4042 "}\n"); |
| 4043 DebugEventCounterCheck(1, 1, 1); |
| 4044 v8::Debug::SetDebugEventListener(NULL); |
| 4045 v8::V8::RemoveMessageListeners(try_finally_original_message); |
| 4046 } |
| 4047 |
| 4048 |
4004 TEST(EvalJSInDebugEventListenerOnNativeReThrownException) { | 4049 TEST(EvalJSInDebugEventListenerOnNativeReThrownException) { |
4005 DebugLocalContext env; | 4050 DebugLocalContext env; |
4006 v8::HandleScope scope(env->GetIsolate()); | 4051 v8::HandleScope scope(env->GetIsolate()); |
4007 env.ExposeDebug(); | 4052 env.ExposeDebug(); |
4008 | 4053 |
4009 // Create functions for testing break on exception. | 4054 // Create functions for testing break on exception. |
4010 v8::Local<v8::Function> noThrowJS = CompileFunction( | 4055 v8::Local<v8::Function> noThrowJS = CompileFunction( |
4011 &env, "function noThrowJS(){var a=[1]; a.push(2); return a.length;}", | 4056 &env, "function noThrowJS(){var a=[1]; a.push(2); return a.length;}", |
4012 "noThrowJS"); | 4057 "noThrowJS"); |
4013 | 4058 |
(...skipping 3586 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
7600 "let y = 2; \n" | 7645 "let y = 2; \n" |
7601 "debugger; \n" | 7646 "debugger; \n" |
7602 "x * y", | 7647 "x * y", |
7603 30); | 7648 30); |
7604 ExpectInt32( | 7649 ExpectInt32( |
7605 "x = 1; y = 2; \n" | 7650 "x = 1; y = 2; \n" |
7606 "debugger;" | 7651 "debugger;" |
7607 "x * y", | 7652 "x * y", |
7608 30); | 7653 30); |
7609 } | 7654 } |
OLD | NEW |