OLD | NEW |
1 // Copyright 2011 the V8 project authors. All rights reserved. | 1 // Copyright 2011 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 222 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
233 } | 233 } |
234 } while (follow_context_chain); | 234 } while (follow_context_chain); |
235 | 235 |
236 if (FLAG_trace_contexts) { | 236 if (FLAG_trace_contexts) { |
237 PrintF("=> no property/slot found\n"); | 237 PrintF("=> no property/slot found\n"); |
238 } | 238 } |
239 return Handle<Object>::null(); | 239 return Handle<Object>::null(); |
240 } | 240 } |
241 | 241 |
242 | 242 |
243 bool Context::GlobalIfNotShadowedByEval(Handle<String> name) { | |
244 Context* context = this; | |
245 | |
246 // Check that there is no local with the given name in contexts | |
247 // before the global context and check that there are no context | |
248 // extension objects (conservative check for with statements). | |
249 while (!context->IsGlobalContext()) { | |
250 // Check if the context is a catch or with context, or has introduced | |
251 // bindings by calling non-strict eval. | |
252 if (context->has_extension()) return false; | |
253 | |
254 // Not a with context so it must be a function context. | |
255 ASSERT(context->IsFunctionContext()); | |
256 | |
257 // Check non-parameter locals. | |
258 Handle<ScopeInfo> scope_info(context->closure()->shared()->scope_info()); | |
259 VariableMode mode; | |
260 InitializationFlag init_flag; | |
261 int index = scope_info->ContextSlotIndex(*name, &mode, &init_flag); | |
262 ASSERT(index < 0 || index >= MIN_CONTEXT_SLOTS); | |
263 if (index >= 0) return false; | |
264 | |
265 // Check parameter locals. | |
266 int param_index = scope_info->ParameterIndex(*name); | |
267 if (param_index >= 0) return false; | |
268 | |
269 // Check context only holding the function name variable. | |
270 index = scope_info->FunctionContextSlotIndex(*name, &mode); | |
271 if (index >= 0) return false; | |
272 context = context->previous(); | |
273 } | |
274 | |
275 // No local or potential with statement found so the variable is | |
276 // global unless it is shadowed by an eval-introduced variable. | |
277 return true; | |
278 } | |
279 | |
280 | |
281 void Context::ComputeEvalScopeInfo(bool* outer_scope_calls_non_strict_eval) { | |
282 // Skip up the context chain checking all the function contexts to see | |
283 // whether they call eval. | |
284 Context* context = this; | |
285 while (!context->IsGlobalContext()) { | |
286 if (context->IsFunctionContext()) { | |
287 if (context->closure()->shared()->scope_info()->CallsNonStrictEval()) { | |
288 // No need to go further since the answers will not change from | |
289 // here. | |
290 *outer_scope_calls_non_strict_eval = true; | |
291 return; | |
292 } | |
293 } | |
294 context = context->previous(); | |
295 } | |
296 } | |
297 | |
298 | |
299 void Context::AddOptimizedFunction(JSFunction* function) { | 243 void Context::AddOptimizedFunction(JSFunction* function) { |
300 ASSERT(IsGlobalContext()); | 244 ASSERT(IsGlobalContext()); |
301 #ifdef DEBUG | 245 #ifdef DEBUG |
302 Object* element = get(OPTIMIZED_FUNCTIONS_LIST); | 246 Object* element = get(OPTIMIZED_FUNCTIONS_LIST); |
303 while (!element->IsUndefined()) { | 247 while (!element->IsUndefined()) { |
304 CHECK(element != function); | 248 CHECK(element != function); |
305 element = JSFunction::cast(element)->next_function_link(); | 249 element = JSFunction::cast(element)->next_function_link(); |
306 } | 250 } |
307 | 251 |
308 CHECK(function->next_function_link()->IsUndefined()); | 252 CHECK(function->next_function_link()->IsUndefined()); |
(...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
371 // During bootstrapping we allow all objects to pass as global | 315 // During bootstrapping we allow all objects to pass as global |
372 // objects. This is necessary to fix circular dependencies. | 316 // objects. This is necessary to fix circular dependencies. |
373 Isolate* isolate = Isolate::Current(); | 317 Isolate* isolate = Isolate::Current(); |
374 return isolate->heap()->gc_state() != Heap::NOT_IN_GC || | 318 return isolate->heap()->gc_state() != Heap::NOT_IN_GC || |
375 isolate->bootstrapper()->IsActive() || | 319 isolate->bootstrapper()->IsActive() || |
376 object->IsGlobalObject(); | 320 object->IsGlobalObject(); |
377 } | 321 } |
378 #endif | 322 #endif |
379 | 323 |
380 } } // namespace v8::internal | 324 } } // namespace v8::internal |
OLD | NEW |