5 #include "src/runtime/runtime-utils.h" 7 #include "src/arguments-inl.h" 8 #include "src/counters.h" 9 #include "src/elements.h" 10 #include "src/heap/factory.h" 11 #include "src/isolate-inl.h" 13 #include "src/objects-inl.h" 14 #include "src/objects/module.h" 25 MaybeHandle<HeapObject> Enumerate(Isolate* isolate,
26 Handle<JSReceiver> receiver) {
27 JSObject::MakePrototypesFast(receiver, kStartAtReceiver, isolate);
28 FastKeyAccumulator accumulator(isolate, receiver,
29 KeyCollectionMode::kIncludePrototypes,
30 ENUMERABLE_STRINGS,
true);
32 if (!accumulator.is_receiver_simple_enum()) {
33 Handle<FixedArray> keys;
34 ASSIGN_RETURN_ON_EXCEPTION(
35 isolate, keys, accumulator.GetKeys(GetKeysConversion::kConvertToString),
38 if (!accumulator.is_receiver_simple_enum())
return keys;
40 DCHECK(!receiver->IsJSModuleNamespace());
41 return handle(receiver->map(), isolate);
46 MaybeHandle<Object> HasEnumerableProperty(Isolate* isolate,
47 Handle<JSReceiver> receiver,
50 Maybe<PropertyAttributes> result = Just(ABSENT);
52 LookupIterator::PropertyOrElement(isolate, receiver, key, &success);
53 if (!success)
return isolate->factory()->undefined_value();
54 for (; it.IsFound(); it.Next()) {
56 case LookupIterator::NOT_FOUND:
57 case LookupIterator::TRANSITION:
59 case LookupIterator::JSPROXY: {
61 result = JSProxy::GetPropertyAttributes(&it);
62 if (result.IsNothing())
return MaybeHandle<Object>();
63 if (result.FromJust() == ABSENT) {
65 Handle<JSProxy> proxy = it.GetHolder<JSProxy>();
66 Handle<Object> prototype;
67 ASSIGN_RETURN_ON_EXCEPTION(isolate, prototype,
68 JSProxy::GetPrototype(proxy), Object);
69 if (prototype->IsNull(isolate)) {
70 return isolate->factory()->undefined_value();
73 return HasEnumerableProperty(
74 isolate, Handle<JSReceiver>::cast(prototype), key);
75 }
else if (result.FromJust() & DONT_ENUM) {
76 return isolate->factory()->undefined_value();
81 case LookupIterator::INTERCEPTOR: {
82 result = JSObject::GetPropertyAttributesWithInterceptor(&it);
83 if (result.IsNothing())
return MaybeHandle<Object>();
84 if (result.FromJust() != ABSENT)
return it.GetName();
87 case LookupIterator::ACCESS_CHECK: {
88 if (it.HasAccess())
continue;
89 result = JSObject::GetPropertyAttributesWithFailedAccessCheck(&it);
90 if (result.IsNothing())
return MaybeHandle<Object>();
91 if (result.FromJust() != ABSENT)
return it.GetName();
92 return isolate->factory()->undefined_value();
94 case LookupIterator::INTEGER_INDEXED_EXOTIC:
96 return isolate->factory()->undefined_value();
97 case LookupIterator::ACCESSOR: {
98 if (it.GetHolder<Object>()->IsJSModuleNamespace()) {
99 result = JSModuleNamespace::GetPropertyAttributes(&it);
100 if (result.IsNothing())
return MaybeHandle<Object>();
101 DCHECK_EQ(0, result.FromJust() & DONT_ENUM);
105 case LookupIterator::DATA:
109 return isolate->factory()->undefined_value();
115 RUNTIME_FUNCTION(Runtime_ForInEnumerate) {
116 HandleScope scope(isolate);
117 DCHECK_EQ(1, args.length());
118 CONVERT_ARG_HANDLE_CHECKED(JSReceiver, receiver, 0);
119 RETURN_RESULT_OR_FAILURE(isolate, Enumerate(isolate, receiver));
123 RUNTIME_FUNCTION(Runtime_ForInHasProperty) {
124 HandleScope scope(isolate);
125 DCHECK_EQ(2, args.length());
126 CONVERT_ARG_HANDLE_CHECKED(JSReceiver, receiver, 0);
127 CONVERT_ARG_HANDLE_CHECKED(Object, key, 1);
128 Handle<Object> result;
129 ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
130 isolate, result, HasEnumerableProperty(isolate, receiver, key));
131 return isolate->heap()->ToBoolean(!result->IsUndefined(isolate));