Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(528)

Side by Side Diff: runtime/vm/class_finalizer.cc

Issue 8319020: Verify method overrides in checked mode only (fix issue 69). (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: '' Created 9 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « no previous file | tests/co19/co19-runtime.status » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 #include "vm/class_finalizer.h" 5 #include "vm/class_finalizer.h"
6 6
7 #include "vm/flags.h" 7 #include "vm/flags.h"
8 #include "vm/heap.h" 8 #include "vm/heap.h"
9 #include "vm/isolate.h" 9 #include "vm/isolate.h"
10 #include "vm/longjump.h" 10 #include "vm/longjump.h"
(...skipping 134 matching lines...) Expand 10 before | Expand all | Expand 10 after
145 // Lookup function in 'cls' and all its super classes. 145 // Lookup function in 'cls' and all its super classes.
146 Class& test_class = Class::Handle(cls.raw()); 146 Class& test_class = Class::Handle(cls.raw());
147 Function& class_function = 147 Function& class_function =
148 Function::Handle(test_class.LookupDynamicFunction(function_name)); 148 Function::Handle(test_class.LookupDynamicFunction(function_name));
149 while (class_function.IsNull()) { 149 while (class_function.IsNull()) {
150 test_class = test_class.SuperClass(); 150 test_class = test_class.SuperClass();
151 if (test_class.IsNull()) break; 151 if (test_class.IsNull()) break;
152 class_function = test_class.LookupDynamicFunction(function_name); 152 class_function = test_class.LookupDynamicFunction(function_name);
153 } 153 }
154 if (class_function.IsNull()) { 154 if (class_function.IsNull()) {
155 const String& class_name = String::Handle(cls.Name());
155 OS::Print("%s implements '%s' missing: '%s'\n", 156 OS::Print("%s implements '%s' missing: '%s'\n",
156 cls.ToCString(), 157 class_name.ToCString(),
157 interface_name.ToCString(), 158 interface_name.ToCString(),
158 function_name.ToCString()); 159 function_name.ToCString());
159 } else if (!class_function.IsAssignableTo(interface_function)) { 160 } else if (!class_function.IsSubtypeOf(interface_function)) {
160 // TODO(regis): Shouldn't this be IsSubtypeOf instead of IsAssignableTo? 161 const String& class_name = String::Handle(cls.Name());
161 OS::Print("%s implements '%s' with wrong result type, wrong number of " 162 OS::Print("The type of instance method '%s' in class '%s' is not a "
162 "parameters, or wrong parameter types: '%s'\n", 163 "subtype of the type of '%s' in interface '%s'\n",
163 cls.ToCString(), 164 function_name.ToCString(),
164 interface_name.ToCString(), 165 class_name.ToCString(),
165 function_name.ToCString()); 166 function_name.ToCString(),
167 interface_name.ToCString());
166 } 168 }
167 } 169 }
168 } 170 }
169 } 171 }
170 #else 172 #else
171 173
172 void ClassFinalizer::VerifyClassImplements(const Class& cls) {} 174 void ClassFinalizer::VerifyClassImplements(const Class& cls) {}
173 175
174 #endif 176 #endif
175 177
(...skipping 637 matching lines...) Expand 10 before | Expand all | Expand 10 after
813 visited->RemoveLast(); 815 visited->RemoveLast();
814 } 816 }
815 817
816 818
817 void ClassFinalizer::CheckForLegalOverrides(const Class& cls) { 819 void ClassFinalizer::CheckForLegalOverrides(const Class& cls) {
818 HANDLESCOPE(); 820 HANDLESCOPE();
819 const Class& super = Class::Handle(cls.SuperClass()); 821 const Class& super = Class::Handle(cls.SuperClass());
820 if (super.IsNull()) { 822 if (super.IsNull()) {
821 return; 823 return;
822 } 824 }
823 // Check functions. 825 if (FLAG_enable_type_checks) {
824 // TODO(regis): It is not clear from the spec that we should be checking this. 826 // Check functions.
825 const Array& functions_array = Array::Handle(cls.functions()); 827 const Array& functions_array = Array::Handle(cls.functions());
826 Function& function = Function::Handle(); 828 Function& function = Function::Handle();
827 String& function_name = String::Handle(); 829 String& function_name = String::Handle();
828 intptr_t len = functions_array.Length(); 830 const intptr_t len = functions_array.Length();
829 for (intptr_t i = 0; i < len; i++) { 831 for (intptr_t i = 0; i < len; i++) {
830 function ^= functions_array.At(i); 832 function ^= functions_array.At(i);
831 if (!function.is_static()) { 833 if (!function.is_static()) {
832 function_name ^= function.name(); 834 function_name ^= function.name();
833 Function& overridden_function = 835 Function& overridden_function =
834 Function::Handle(super.LookupDynamicFunction(function_name)); 836 Function::Handle(super.LookupDynamicFunction(function_name));
835 if (!overridden_function.IsNull() && 837 if (!overridden_function.IsNull() &&
836 !function.HasCompatibleParametersWith(overridden_function)) { 838 !function.IsSubtypeOf(overridden_function)) {
837 const String& class_name = String::Handle(cls.Name()); 839 const String& class_name = String::Handle(cls.Name());
838 ReportError("class '%s' overrides function '%s' with incompatible " 840 const String& super_class_name = String::Handle(
839 "parameters.\n", 841 Class::Handle(overridden_function.owner()).Name());
840 class_name.ToCString(), function_name.ToCString()); 842 ReportError("The type of instance method '%s' in class '%s' is "
843 "not a subtype of the type of overriden instance "
844 "method '%s' in class '%s'\n",
845 function_name.ToCString(),
846 class_name.ToCString(),
847 function_name.ToCString(),
848 super_class_name.ToCString());
849 }
841 } 850 }
842 // Function types are purposely not checked for assignability.
843 } 851 }
844 } 852 }
845 // Check fields. 853 // Check fields.
846 const Array& fields_array = Array::Handle(cls.fields()); 854 const Array& fields_array = Array::Handle(cls.fields());
847 Field& field = Field::Handle(); 855 Field& field = Field::Handle();
848 String& field_name = String::Handle(); 856 String& field_name = String::Handle();
849 len = fields_array.Length(); 857 const intptr_t len = fields_array.Length();
850 for (intptr_t i = 0; i < len; i++) { 858 for (intptr_t i = 0; i < len; i++) {
851 field ^= fields_array.At(i); 859 field ^= fields_array.At(i);
852 field_name ^= field.name(); 860 field_name ^= field.name();
853 Field& super_field = Field::Handle(super.LookupStaticField(field_name)); 861 Field& super_field = Field::Handle(super.LookupStaticField(field_name));
854 if (super_field.IsNull()) { 862 if (super_field.IsNull()) {
855 super_field = super.LookupInstanceField(field_name); 863 super_field = super.LookupInstanceField(field_name);
856 } 864 }
857 if (!super_field.IsNull()) { 865 if (!super_field.IsNull()) {
858 // A static field may "override" a static field. 866 // A static field may "override" a static field.
859 if (!super_field.is_static() || !field.is_static()) { 867 if (!super_field.is_static() || !field.is_static()) {
(...skipping 116 matching lines...) Expand 10 before | Expand all | Expand 10 after
976 ASSERT(msg_buffer != NULL); 984 ASSERT(msg_buffer != NULL);
977 va_list args; 985 va_list args;
978 va_start(args, format); 986 va_start(args, format);
979 OS::VSNPrint(msg_buffer, kBufferLength, format, args); 987 OS::VSNPrint(msg_buffer, kBufferLength, format, args);
980 va_end(args); 988 va_end(args);
981 isolate->long_jump_base()->Jump(1, msg_buffer); 989 isolate->long_jump_base()->Jump(1, msg_buffer);
982 UNREACHABLE(); 990 UNREACHABLE();
983 } 991 }
984 992
985 } // namespace dart 993 } // namespace dart
OLDNEW
« no previous file with comments | « no previous file | tests/co19/co19-runtime.status » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698