OLD | NEW |
1 // Copyright 2010 the V8 project authors. All rights reserved. | 1 // Copyright 2010 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 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
44 return; \ | 44 return; \ |
45 } while (false) | 45 } while (false) |
46 | 46 |
47 | 47 |
48 #define CHECK_BAILOUT \ | 48 #define CHECK_BAILOUT \ |
49 do { \ | 49 do { \ |
50 if (!has_supported_syntax_) return; \ | 50 if (!has_supported_syntax_) return; \ |
51 } while (false) | 51 } while (false) |
52 | 52 |
53 | 53 |
54 void FastCodeGenSyntaxChecker::Check(FunctionLiteral* fun, | 54 void FastCodeGenSyntaxChecker::Check(CompilationInfo* info) { |
55 CompilationInfo* info) { | |
56 info_ = info; | 55 info_ = info; |
57 | 56 |
58 // We do not specialize if we do not have a receiver or if it is not a | 57 // We do not specialize if we do not have a receiver or if it is not a |
59 // JS object with fast mode properties. | 58 // JS object with fast mode properties. |
60 if (!info->has_receiver()) BAILOUT("No receiver"); | 59 if (!info->has_receiver()) BAILOUT("No receiver"); |
61 if (!info->receiver()->IsJSObject()) BAILOUT("Receiver is not an object"); | 60 if (!info->receiver()->IsJSObject()) BAILOUT("Receiver is not an object"); |
62 Handle<JSObject> object = Handle<JSObject>::cast(info->receiver()); | 61 Handle<JSObject> object = Handle<JSObject>::cast(info->receiver()); |
63 if (!object->HasFastProperties()) BAILOUT("Receiver is in dictionary mode"); | 62 if (!object->HasFastProperties()) BAILOUT("Receiver is in dictionary mode"); |
64 | 63 |
65 // We do not support stack or heap slots (both of which require | 64 // We do not support stack or heap slots (both of which require |
66 // allocation). | 65 // allocation). |
67 Scope* scope = fun->scope(); | 66 Scope* scope = info->scope(); |
68 if (scope->num_stack_slots() > 0) { | 67 if (scope->num_stack_slots() > 0) { |
69 BAILOUT("Function has stack-allocated locals"); | 68 BAILOUT("Function has stack-allocated locals"); |
70 } | 69 } |
71 if (scope->num_heap_slots() > 0) { | 70 if (scope->num_heap_slots() > 0) { |
72 BAILOUT("Function has context-allocated locals"); | 71 BAILOUT("Function has context-allocated locals"); |
73 } | 72 } |
74 | 73 |
75 VisitDeclarations(scope->declarations()); | 74 VisitDeclarations(scope->declarations()); |
76 CHECK_BAILOUT; | 75 CHECK_BAILOUT; |
77 | 76 |
78 // We do not support empty function bodies. | 77 // We do not support empty function bodies. |
79 if (fun->body()->is_empty()) BAILOUT("Function has an empty body"); | 78 if (info->function()->body()->is_empty()) { |
80 VisitStatements(fun->body()); | 79 BAILOUT("Function has an empty body"); |
| 80 } |
| 81 VisitStatements(info->function()->body()); |
81 } | 82 } |
82 | 83 |
83 | 84 |
84 void FastCodeGenSyntaxChecker::VisitDeclarations( | 85 void FastCodeGenSyntaxChecker::VisitDeclarations( |
85 ZoneList<Declaration*>* decls) { | 86 ZoneList<Declaration*>* decls) { |
86 if (!decls->is_empty()) BAILOUT("Function has declarations"); | 87 if (!decls->is_empty()) BAILOUT("Function has declarations"); |
87 } | 88 } |
88 | 89 |
89 | 90 |
90 void FastCodeGenSyntaxChecker::VisitStatements(ZoneList<Statement*>* stmts) { | 91 void FastCodeGenSyntaxChecker::VisitStatements(ZoneList<Statement*>* stmts) { |
(...skipping 234 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
325 void FastCodeGenSyntaxChecker::VisitThisFunction(ThisFunction* expr) { | 326 void FastCodeGenSyntaxChecker::VisitThisFunction(ThisFunction* expr) { |
326 BAILOUT("ThisFunction"); | 327 BAILOUT("ThisFunction"); |
327 } | 328 } |
328 | 329 |
329 #undef BAILOUT | 330 #undef BAILOUT |
330 #undef CHECK_BAILOUT | 331 #undef CHECK_BAILOUT |
331 | 332 |
332 | 333 |
333 #define __ ACCESS_MASM(masm()) | 334 #define __ ACCESS_MASM(masm()) |
334 | 335 |
335 Handle<Code> FastCodeGenerator::MakeCode(FunctionLiteral* fun, | 336 Handle<Code> FastCodeGenerator::MakeCode(CompilationInfo* info) { |
336 Handle<Script> script, | |
337 bool is_eval, | |
338 CompilationInfo* info) { | |
339 // Label the AST before calling MakeCodePrologue, so AST node numbers are | 337 // Label the AST before calling MakeCodePrologue, so AST node numbers are |
340 // printed with the AST. | 338 // printed with the AST. |
341 AstLabeler labeler; | 339 AstLabeler labeler; |
342 labeler.Label(fun); | 340 labeler.Label(info); |
343 info->set_has_this_properties(labeler.has_this_properties()); | |
344 | 341 |
345 CodeGenerator::MakeCodePrologue(fun); | 342 CodeGenerator::MakeCodePrologue(info); |
346 | 343 |
347 const int kInitialBufferSize = 4 * KB; | 344 const int kInitialBufferSize = 4 * KB; |
348 MacroAssembler masm(NULL, kInitialBufferSize); | 345 MacroAssembler masm(NULL, kInitialBufferSize); |
349 | 346 |
350 // Generate the fast-path code. | 347 // Generate the fast-path code. |
351 FastCodeGenerator fast_cgen(&masm, script, is_eval); | 348 FastCodeGenerator fast_cgen(&masm); |
352 fast_cgen.Generate(fun, info); | 349 fast_cgen.Generate(info); |
353 if (fast_cgen.HasStackOverflow()) { | 350 if (fast_cgen.HasStackOverflow()) { |
354 ASSERT(!Top::has_pending_exception()); | 351 ASSERT(!Top::has_pending_exception()); |
355 return Handle<Code>::null(); | 352 return Handle<Code>::null(); |
356 } | 353 } |
357 | 354 |
358 // Generate the full code for the function in bailout mode, using the same | 355 // Generate the full code for the function in bailout mode, using the same |
359 // macro assembler. | 356 // macro assembler. |
360 CodeGenerator cgen(&masm, script, is_eval); | 357 CodeGenerator cgen(&masm); |
361 CodeGeneratorScope scope(&cgen); | 358 CodeGeneratorScope scope(&cgen); |
362 cgen.Generate(fun, CodeGenerator::SECONDARY, info); | 359 cgen.Generate(info, CodeGenerator::SECONDARY); |
363 if (cgen.HasStackOverflow()) { | 360 if (cgen.HasStackOverflow()) { |
364 ASSERT(!Top::has_pending_exception()); | 361 ASSERT(!Top::has_pending_exception()); |
365 return Handle<Code>::null(); | 362 return Handle<Code>::null(); |
366 } | 363 } |
367 | 364 |
368 Code::Flags flags = Code::ComputeFlags(Code::FUNCTION, NOT_IN_LOOP); | 365 Code::Flags flags = Code::ComputeFlags(Code::FUNCTION, NOT_IN_LOOP); |
369 return CodeGenerator::MakeCodeEpilogue(fun, &masm, flags, script); | 366 return CodeGenerator::MakeCodeEpilogue(&masm, flags, info); |
370 } | 367 } |
371 | 368 |
372 | 369 |
373 void FastCodeGenerator::VisitDeclaration(Declaration* decl) { | 370 void FastCodeGenerator::VisitDeclaration(Declaration* decl) { |
374 UNREACHABLE(); | 371 UNREACHABLE(); |
375 } | 372 } |
376 | 373 |
377 | 374 |
378 void FastCodeGenerator::VisitBlock(Block* stmt) { | 375 void FastCodeGenerator::VisitBlock(Block* stmt) { |
379 VisitStatements(stmt->statements()); | 376 VisitStatements(stmt->statements()); |
(...skipping 206 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
586 | 583 |
587 | 584 |
588 void FastCodeGenerator::VisitThisFunction(ThisFunction* expr) { | 585 void FastCodeGenerator::VisitThisFunction(ThisFunction* expr) { |
589 UNREACHABLE(); | 586 UNREACHABLE(); |
590 } | 587 } |
591 | 588 |
592 #undef __ | 589 #undef __ |
593 | 590 |
594 | 591 |
595 } } // namespace v8::internal | 592 } } // namespace v8::internal |
OLD | NEW |