OLD | NEW |
---|---|
1 // Copyright 2006-2008 the V8 project authors. All rights reserved. | 1 // Copyright 2006-2008 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 5240 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
5251 // ebp: frame pointer (restored after C call) | 5251 // ebp: frame pointer (restored after C call) |
5252 // esp: stack pointer (restored after C call) | 5252 // esp: stack pointer (restored after C call) |
5253 // edi: number of arguments including receiver (C callee-saved) | 5253 // edi: number of arguments including receiver (C callee-saved) |
5254 | 5254 |
5255 if (do_gc) { | 5255 if (do_gc) { |
5256 __ mov(Operand(esp, 0 * kPointerSize), eax); // Result. | 5256 __ mov(Operand(esp, 0 * kPointerSize), eax); // Result. |
5257 __ call(FUNCTION_ADDR(Runtime::PerformGC), runtime_entry); | 5257 __ call(FUNCTION_ADDR(Runtime::PerformGC), runtime_entry); |
5258 } | 5258 } |
5259 | 5259 |
5260 // Call C function. | 5260 // Call C function. |
5261 __ lea(eax, Operand(ebp, | |
5262 edi, | |
5263 times_4, | |
5264 StandardFrameConstants::kCallerSPOffset - kPointerSize)); | |
5265 __ mov(Operand(esp, 0 * kPointerSize), edi); // argc. | 5261 __ mov(Operand(esp, 0 * kPointerSize), edi); // argc. |
5266 __ mov(Operand(esp, 1 * kPointerSize), eax); // argv. | 5262 __ mov(Operand(esp, 1 * kPointerSize), esi); // argv. |
iposva
2008/09/23 07:51:28
Please add the definition of esi to the contract a
| |
5267 __ call(Operand(ebx)); | 5263 __ call(Operand(ebx)); |
5268 // Result is in eax or edx:eax - do not destroy these registers! | 5264 // Result is in eax or edx:eax - do not destroy these registers! |
5269 | 5265 |
5270 // Check for failure result. | 5266 // Check for failure result. |
5271 Label failure_returned; | 5267 Label failure_returned; |
5272 ASSERT(((kFailureTag + 1) & kFailureTagMask) == 0); | 5268 ASSERT(((kFailureTag + 1) & kFailureTagMask) == 0); |
5273 __ lea(ecx, Operand(eax, 1)); | 5269 __ lea(ecx, Operand(eax, 1)); |
5274 // Lower 2 bits of ecx are 0 iff eax has failure tag. | 5270 // Lower 2 bits of ecx are 0 iff eax has failure tag. |
5275 __ test(ecx, Immediate(kFailureTagMask)); | 5271 __ test(ecx, Immediate(kFailureTagMask)); |
5276 __ j(zero, &failure_returned, not_taken); | 5272 __ j(zero, &failure_returned, not_taken); |
5277 | 5273 |
5278 // Restore number of arguments to ecx and clear top frame. | |
5279 __ mov(ecx, Operand(edi)); | |
5280 ExternalReference c_entry_fp_address(Top::k_c_entry_fp_address); | |
5281 __ mov(Operand::StaticVariable(c_entry_fp_address), Immediate(0)); | |
5282 | |
5283 // Restore the memory copy of the registers by digging them out from | 5274 // Restore the memory copy of the registers by digging them out from |
5284 // the stack. | 5275 // the stack. |
5285 if (do_restore) { | 5276 if (do_restore) { |
5286 // Ok to clobber ebx and edi - function pointer and number of arguments not | 5277 // Ok to clobber ebx and edi - function pointer and number of arguments not |
5287 // needed anymore. | 5278 // needed anymore. |
5288 const int kCallerSavedSize = kNumJSCallerSaved * kPointerSize; | 5279 const int kCallerSavedSize = kNumJSCallerSaved * kPointerSize; |
5289 int kOffset = ExitFrameConstants::kDebugMarkOffset - kCallerSavedSize; | 5280 int kOffset = ExitFrameConstants::kDebugMarkOffset - kCallerSavedSize; |
5290 __ lea(ebx, Operand(ebp, kOffset)); | 5281 __ lea(ebx, Operand(ebp, kOffset)); |
5291 __ CopyRegistersFromStackToMemory(ebx, edi, kJSCallerSaved); | 5282 __ CopyRegistersFromStackToMemory(ebx, ecx, kJSCallerSaved); |
5292 } | 5283 } |
5293 | 5284 |
5294 // Exit C frame. | 5285 // Exit C frame. |
5295 __ lea(esp, Operand(ebp, -1 * kPointerSize)); | 5286 __ LeaveExitFrame(); |
5296 __ pop(ebx); | |
5297 __ pop(ebp); | |
5298 | |
5299 // Restore current context from top and clear it in debug mode. | |
5300 ExternalReference context_address(Top::k_context_address); | |
5301 __ mov(esi, Operand::StaticVariable(context_address)); | |
5302 if (kDebug) { | |
5303 __ mov(Operand::StaticVariable(context_address), Immediate(0)); | |
5304 } | |
5305 | |
5306 // Pop arguments from caller's stack and return. | |
5307 __ pop(ebx); // Ok to clobber ebx - function pointer not needed anymore. | |
5308 __ lea(esp, Operand(esp, ecx, times_4, 0)); | |
5309 __ push(ebx); | |
5310 __ ret(0); | 5287 __ ret(0); |
5311 | 5288 |
5312 // Handling of Failure. | 5289 // Handling of Failure. |
5313 __ bind(&failure_returned); | 5290 __ bind(&failure_returned); |
5314 | 5291 |
5315 Label retry; | 5292 Label retry; |
5316 // If the returned exception is RETRY_AFTER_GC continue at retry label | 5293 // If the returned exception is RETRY_AFTER_GC continue at retry label |
5317 ASSERT(Failure::RETRY_AFTER_GC == 0); | 5294 ASSERT(Failure::RETRY_AFTER_GC == 0); |
5318 __ test(eax, Immediate(((1 << kFailureTypeTagSize) - 1) << kFailureTagSize)); | 5295 __ test(eax, Immediate(((1 << kFailureTypeTagSize) - 1) << kFailureTagSize)); |
5319 __ j(zero, &retry, taken); | 5296 __ j(zero, &retry, taken); |
(...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
5399 // ebp: frame pointer (restored after C call) | 5376 // ebp: frame pointer (restored after C call) |
5400 // esp: stack pointer (restored after C call) | 5377 // esp: stack pointer (restored after C call) |
5401 // esi: current context (C callee-saved) | 5378 // esi: current context (C callee-saved) |
5402 // edi: caller's parameter pointer pp (C callee-saved) | 5379 // edi: caller's parameter pointer pp (C callee-saved) |
5403 | 5380 |
5404 // NOTE: Invocations of builtins may return failure objects | 5381 // NOTE: Invocations of builtins may return failure objects |
5405 // instead of a proper result. The builtin entry handles | 5382 // instead of a proper result. The builtin entry handles |
5406 // this by performing a garbage collection and retrying the | 5383 // this by performing a garbage collection and retrying the |
5407 // builtin once. | 5384 // builtin once. |
5408 | 5385 |
5409 // Enter C frame. | 5386 StackFrame::Type frame_type = is_debug_break ? |
5410 // Here we make the following assumptions and use them when setting | 5387 StackFrame::EXIT_DEBUG : |
5411 // up the top-most Frame. Adjust the code if these assumptions | 5388 StackFrame::EXIT; |
5412 // change. | |
5413 ASSERT(ExitFrameConstants::kPPDisplacement == +2 * kPointerSize); | |
5414 ASSERT(ExitFrameConstants::kCallerPCOffset == +1 * kPointerSize); | |
5415 ASSERT(ExitFrameConstants::kCallerFPOffset == 0 * kPointerSize); | |
5416 ASSERT(ExitFrameConstants::kSPOffset == -2 * kPointerSize); | |
5417 __ push(ebp); // caller fp | |
5418 __ mov(ebp, Operand(esp)); // C entry fp | |
5419 __ push(ebx); // C function | |
5420 __ push(Immediate(0)); // saved entry sp, set before call | |
5421 __ push(Immediate(is_debug_break ? 1 : 0)); | |
5422 | 5389 |
5423 // Remember top frame. | 5390 // Enter the exit frame that transitions from JavaScript to C++. |
5424 ExternalReference c_entry_fp(Top::k_c_entry_fp_address); | 5391 __ EnterExitFrame(frame_type); |
5425 ExternalReference context_address(Top::k_context_address); | |
5426 __ mov(Operand::StaticVariable(c_entry_fp), ebp); | |
5427 __ mov(Operand::StaticVariable(context_address), esi); | |
5428 | 5392 |
5429 if (is_debug_break) { | 5393 if (is_debug_break) { |
5430 // Save the state of all registers to the stack from the memory | 5394 // Save the state of all registers to the stack from the memory |
5431 // location. | 5395 // location. |
5432 | 5396 |
5433 // TODO(1243899): This should be symmetric to | 5397 // TODO(1243899): This should be symmetric to |
5434 // CopyRegistersFromStackToMemory() but it isn't! esp is assumed | 5398 // CopyRegistersFromStackToMemory() but it isn't! esp is assumed |
5435 // correct here, but computed for the other call. Very error | 5399 // correct here, but computed for the other call. Very error |
5436 // prone! FIX THIS. Actually there are deeper problems with | 5400 // prone! FIX THIS. Actually there are deeper problems with |
5437 // register saving than this asymmetry (see the bug report | 5401 // register saving than this asymmetry (see the bug report |
5438 // associated with this issue). | 5402 // associated with this issue). |
5439 __ PushRegistersFromMemory(kJSCallerSaved); | 5403 __ PushRegistersFromMemory(kJSCallerSaved); |
5440 } | 5404 } |
5441 | 5405 |
5442 // Move number of arguments (argc) into callee-saved register. Note | |
5443 // that edi is only available after remembering the top frame. | |
5444 __ mov(edi, Operand(eax)); | |
5445 | |
5446 // Allocate stack space for 2 arguments (argc, argv). | 5406 // Allocate stack space for 2 arguments (argc, argv). |
5447 GenerateReserveCParameterSpace(masm, 2); | 5407 GenerateReserveCParameterSpace(masm, 2); |
5448 __ mov(Operand(ebp, ExitFrameConstants::kSPOffset), esp); // save entry sp | 5408 __ mov(Operand(ebp, ExitFrameConstants::kSPOffset), esp); // save entry sp |
5449 | 5409 |
5450 // eax: result parameter for PerformGC, if any (setup below) | 5410 // eax: result parameter for PerformGC, if any (setup below) |
5451 // ebx: pointer to builtin function (C callee-saved) | 5411 // ebx: pointer to builtin function (C callee-saved) |
5452 // ebp: frame pointer (restored after C call) | 5412 // ebp: frame pointer (restored after C call) |
5453 // esp: stack pointer (restored after C call) | 5413 // esp: stack pointer (restored after C call) |
5454 // edi: number of arguments including receiver (C callee-saved) | 5414 // edi: number of arguments including receiver (C callee-saved) |
5455 | 5415 |
(...skipping 127 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
5583 bool is_eval) { | 5543 bool is_eval) { |
5584 Handle<Code> code = Ia32CodeGenerator::MakeCode(fun, script, is_eval); | 5544 Handle<Code> code = Ia32CodeGenerator::MakeCode(fun, script, is_eval); |
5585 if (!code.is_null()) { | 5545 if (!code.is_null()) { |
5586 Counters::total_compiled_code_size.Increment(code->instruction_size()); | 5546 Counters::total_compiled_code_size.Increment(code->instruction_size()); |
5587 } | 5547 } |
5588 return code; | 5548 return code; |
5589 } | 5549 } |
5590 | 5550 |
5591 | 5551 |
5592 } } // namespace v8::internal | 5552 } } // namespace v8::internal |
OLD | NEW |