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

Side by Side Diff: src/ia32/codegen-ia32.cc

Issue 6529055: [Isolates] Merge crankshaft (r5922 from bleeding_edge). (Closed)
Patch Set: Win32 port Created 9 years, 10 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
« no previous file with comments | « src/ia32/codegen-ia32.h ('k') | src/ia32/cpu-ia32.cc » ('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 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 86 matching lines...) Expand 10 before | Expand all | Expand 10 after
97 void VirtualFrameRuntimeCallHelper::BeforeCall(MacroAssembler* masm) const { 97 void VirtualFrameRuntimeCallHelper::BeforeCall(MacroAssembler* masm) const {
98 frame_state_->Save(masm); 98 frame_state_->Save(masm);
99 } 99 }
100 100
101 101
102 void VirtualFrameRuntimeCallHelper::AfterCall(MacroAssembler* masm) const { 102 void VirtualFrameRuntimeCallHelper::AfterCall(MacroAssembler* masm) const {
103 frame_state_->Restore(masm); 103 frame_state_->Restore(masm);
104 } 104 }
105 105
106 106
107 void ICRuntimeCallHelper::BeforeCall(MacroAssembler* masm) const { 107 void StubRuntimeCallHelper::BeforeCall(MacroAssembler* masm) const {
108 masm->EnterInternalFrame(); 108 masm->EnterInternalFrame();
109 } 109 }
110 110
111 111
112 void ICRuntimeCallHelper::AfterCall(MacroAssembler* masm) const { 112 void StubRuntimeCallHelper::AfterCall(MacroAssembler* masm) const {
113 masm->LeaveInternalFrame(); 113 masm->LeaveInternalFrame();
114 } 114 }
115 115
116 116
117 // ------------------------------------------------------------------------- 117 // -------------------------------------------------------------------------
118 // CodeGenState implementation. 118 // CodeGenState implementation.
119 119
120 CodeGenState::CodeGenState(CodeGenerator* owner) 120 CodeGenState::CodeGenState(CodeGenerator* owner)
121 : owner_(owner), 121 : owner_(owner),
122 destination_(NULL), 122 destination_(NULL),
(...skipping 7273 matching lines...) Expand 10 before | Expand all | Expand 10 after
7396 7396
7397 7397
7398 void CodeGenerator::GenerateRegExpExec(ZoneList<Expression*>* args) { 7398 void CodeGenerator::GenerateRegExpExec(ZoneList<Expression*>* args) {
7399 ASSERT_EQ(4, args->length()); 7399 ASSERT_EQ(4, args->length());
7400 7400
7401 // Load the arguments on the stack and call the stub. 7401 // Load the arguments on the stack and call the stub.
7402 Load(args->at(0)); 7402 Load(args->at(0));
7403 Load(args->at(1)); 7403 Load(args->at(1));
7404 Load(args->at(2)); 7404 Load(args->at(2));
7405 Load(args->at(3)); 7405 Load(args->at(3));
7406
7406 RegExpExecStub stub; 7407 RegExpExecStub stub;
7407 Result result = frame_->CallStub(&stub, 4); 7408 Result result = frame_->CallStub(&stub, 4);
7408 frame_->Push(&result); 7409 frame_->Push(&result);
7409 } 7410 }
7410 7411
7411 7412
7412 void CodeGenerator::GenerateRegExpConstructResult(ZoneList<Expression*>* args) { 7413 void CodeGenerator::GenerateRegExpConstructResult(ZoneList<Expression*>* args) {
7413 // No stub. This code only occurs a few times in regexp.js.
7414 const int kMaxInlineLength = 100;
7415 ASSERT_EQ(3, args->length()); 7414 ASSERT_EQ(3, args->length());
7415
7416 Load(args->at(0)); // Size of array, smi. 7416 Load(args->at(0)); // Size of array, smi.
7417 Load(args->at(1)); // "index" property value. 7417 Load(args->at(1)); // "index" property value.
7418 Load(args->at(2)); // "input" property value. 7418 Load(args->at(2)); // "input" property value.
7419 {
7420 VirtualFrame::SpilledScope spilled_scope;
7421 7419
7422 Label slowcase; 7420 RegExpConstructResultStub stub;
7423 Label done; 7421 Result result = frame_->CallStub(&stub, 3);
7424 __ mov(ebx, Operand(esp, kPointerSize * 2)); 7422 frame_->Push(&result);
7425 __ test(ebx, Immediate(kSmiTagMask));
7426 __ j(not_zero, &slowcase);
7427 __ cmp(Operand(ebx), Immediate(Smi::FromInt(kMaxInlineLength)));
7428 __ j(above, &slowcase);
7429 // Smi-tagging is equivalent to multiplying by 2.
7430 STATIC_ASSERT(kSmiTag == 0);
7431 STATIC_ASSERT(kSmiTagSize == 1);
7432 // Allocate RegExpResult followed by FixedArray with size in ebx.
7433 // JSArray: [Map][empty properties][Elements][Length-smi][index][input]
7434 // Elements: [Map][Length][..elements..]
7435 __ AllocateInNewSpace(JSRegExpResult::kSize + FixedArray::kHeaderSize,
7436 times_half_pointer_size,
7437 ebx, // In: Number of elements (times 2, being a smi)
7438 eax, // Out: Start of allocation (tagged).
7439 ecx, // Out: End of allocation.
7440 edx, // Scratch register
7441 &slowcase,
7442 TAG_OBJECT);
7443 // eax: Start of allocated area, object-tagged.
7444
7445 // Set JSArray map to global.regexp_result_map().
7446 // Set empty properties FixedArray.
7447 // Set elements to point to FixedArray allocated right after the JSArray.
7448 // Interleave operations for better latency.
7449 __ mov(edx, ContextOperand(esi, Context::GLOBAL_INDEX));
7450 __ mov(ecx, Immediate(FACTORY->empty_fixed_array()));
7451 __ lea(ebx, Operand(eax, JSRegExpResult::kSize));
7452 __ mov(edx, FieldOperand(edx, GlobalObject::kGlobalContextOffset));
7453 __ mov(FieldOperand(eax, JSObject::kElementsOffset), ebx);
7454 __ mov(FieldOperand(eax, JSObject::kPropertiesOffset), ecx);
7455 __ mov(edx, ContextOperand(edx, Context::REGEXP_RESULT_MAP_INDEX));
7456 __ mov(FieldOperand(eax, HeapObject::kMapOffset), edx);
7457
7458 // Set input, index and length fields from arguments.
7459 __ pop(FieldOperand(eax, JSRegExpResult::kInputOffset));
7460 __ pop(FieldOperand(eax, JSRegExpResult::kIndexOffset));
7461 __ pop(ecx);
7462 __ mov(FieldOperand(eax, JSArray::kLengthOffset), ecx);
7463
7464 // Fill out the elements FixedArray.
7465 // eax: JSArray.
7466 // ebx: FixedArray.
7467 // ecx: Number of elements in array, as smi.
7468
7469 // Set map.
7470 __ mov(FieldOperand(ebx, HeapObject::kMapOffset),
7471 Immediate(FACTORY->fixed_array_map()));
7472 // Set length.
7473 __ mov(FieldOperand(ebx, FixedArray::kLengthOffset), ecx);
7474 // Fill contents of fixed-array with the-hole.
7475 __ SmiUntag(ecx);
7476 __ mov(edx, Immediate(FACTORY->the_hole_value()));
7477 __ lea(ebx, FieldOperand(ebx, FixedArray::kHeaderSize));
7478 // Fill fixed array elements with hole.
7479 // eax: JSArray.
7480 // ecx: Number of elements to fill.
7481 // ebx: Start of elements in FixedArray.
7482 // edx: the hole.
7483 Label loop;
7484 __ test(ecx, Operand(ecx));
7485 __ bind(&loop);
7486 __ j(less_equal, &done); // Jump if ecx is negative or zero.
7487 __ sub(Operand(ecx), Immediate(1));
7488 __ mov(Operand(ebx, ecx, times_pointer_size, 0), edx);
7489 __ jmp(&loop);
7490
7491 __ bind(&slowcase);
7492 __ CallRuntime(Runtime::kRegExpConstructResult, 3);
7493
7494 __ bind(&done);
7495 }
7496 frame_->Forget(3);
7497 frame_->Push(eax);
7498 } 7423 }
7499 7424
7500 7425
7501 class DeferredSearchCache: public DeferredCode { 7426 class DeferredSearchCache: public DeferredCode {
7502 public: 7427 public:
7503 DeferredSearchCache(Register dst, Register cache, Register key) 7428 DeferredSearchCache(Register dst, Register cache, Register key)
7504 : dst_(dst), cache_(cache), key_(key) { 7429 : dst_(dst), cache_(cache), key_(key) {
7505 set_comment("[ DeferredSearchCache"); 7430 set_comment("[ DeferredSearchCache");
7506 } 7431 }
7507 7432
(...skipping 2577 matching lines...) Expand 10 before | Expand all | Expand 10 after
10085 case ILLEGAL: 10010 case ILLEGAL:
10086 UNREACHABLE(); 10011 UNREACHABLE();
10087 } 10012 }
10088 } 10013 }
10089 10014
10090 10015
10091 #undef __ 10016 #undef __
10092 10017
10093 #define __ masm. 10018 #define __ masm.
10094 10019
10020
10021 static void MemCopyWrapper(void* dest, const void* src, size_t size) {
10022 memcpy(dest, src, size);
10023 }
10024
10025
10095 MemCopyFunction CreateMemCopyFunction() { 10026 MemCopyFunction CreateMemCopyFunction() {
10096 size_t actual_size; 10027 HandleScope scope;
10097 byte* buffer = static_cast<byte*>(OS::Allocate(Assembler::kMinimalBufferSize, 10028 MacroAssembler masm(NULL, 1 * KB);
10098 &actual_size,
10099 true));
10100 CHECK(buffer);
10101 HandleScope handles;
10102 MacroAssembler masm(buffer, static_cast<int>(actual_size));
10103 10029
10104 // Generated code is put into a fixed, unmovable, buffer, and not into 10030 // Generated code is put into a fixed, unmovable, buffer, and not into
10105 // the V8 heap. We can't, and don't, refer to any relocatable addresses 10031 // the V8 heap. We can't, and don't, refer to any relocatable addresses
10106 // (e.g. the JavaScript nan-object). 10032 // (e.g. the JavaScript nan-object).
10107 10033
10108 // 32-bit C declaration function calls pass arguments on stack. 10034 // 32-bit C declaration function calls pass arguments on stack.
10109 10035
10110 // Stack layout: 10036 // Stack layout:
10111 // esp[12]: Third argument, size. 10037 // esp[12]: Third argument, size.
10112 // esp[8]: Second argument, source pointer. 10038 // esp[8]: Second argument, source pointer.
(...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after
10186 __ add(Operand(src), Immediate(0x10)); 10112 __ add(Operand(src), Immediate(0x10));
10187 __ movdqa(Operand(dst, 0), xmm0); 10113 __ movdqa(Operand(dst, 0), xmm0);
10188 __ add(Operand(dst), Immediate(0x10)); 10114 __ add(Operand(dst), Immediate(0x10));
10189 __ bind(&move_less_16); 10115 __ bind(&move_less_16);
10190 10116
10191 // At most 15 bytes to copy. Copy 16 bytes at end of string. 10117 // At most 15 bytes to copy. Copy 16 bytes at end of string.
10192 __ and_(count, 0xF); 10118 __ and_(count, 0xF);
10193 __ movdqu(xmm0, Operand(src, count, times_1, -0x10)); 10119 __ movdqu(xmm0, Operand(src, count, times_1, -0x10));
10194 __ movdqu(Operand(dst, count, times_1, -0x10), xmm0); 10120 __ movdqu(Operand(dst, count, times_1, -0x10), xmm0);
10195 10121
10122 __ mov(eax, Operand(esp, stack_offset + kDestinationOffset));
10196 __ pop(esi); 10123 __ pop(esi);
10197 __ pop(edi); 10124 __ pop(edi);
10198 __ ret(0); 10125 __ ret(0);
10199 } 10126 }
10200 __ Align(16); 10127 __ Align(16);
10201 { 10128 {
10202 // Copy loop for unaligned source and aligned destination. 10129 // Copy loop for unaligned source and aligned destination.
10203 // If source is not aligned, we can't read it as efficiently. 10130 // If source is not aligned, we can't read it as efficiently.
10204 __ bind(&unaligned_source); 10131 __ bind(&unaligned_source);
10205 __ IncrementCounter(COUNTERS->memcopy_unaligned(), 1); 10132 __ IncrementCounter(COUNTERS->memcopy_unaligned(), 1);
(...skipping 26 matching lines...) Expand all
10232 __ add(Operand(src), Immediate(0x10)); 10159 __ add(Operand(src), Immediate(0x10));
10233 __ movdqa(Operand(dst, 0), xmm0); 10160 __ movdqa(Operand(dst, 0), xmm0);
10234 __ add(Operand(dst), Immediate(0x10)); 10161 __ add(Operand(dst), Immediate(0x10));
10235 __ bind(&move_less_16); 10162 __ bind(&move_less_16);
10236 10163
10237 // At most 15 bytes to copy. Copy 16 bytes at end of string. 10164 // At most 15 bytes to copy. Copy 16 bytes at end of string.
10238 __ and_(count, 0x0F); 10165 __ and_(count, 0x0F);
10239 __ movdqu(xmm0, Operand(src, count, times_1, -0x10)); 10166 __ movdqu(xmm0, Operand(src, count, times_1, -0x10));
10240 __ movdqu(Operand(dst, count, times_1, -0x10), xmm0); 10167 __ movdqu(Operand(dst, count, times_1, -0x10), xmm0);
10241 10168
10169 __ mov(eax, Operand(esp, stack_offset + kDestinationOffset));
10242 __ pop(esi); 10170 __ pop(esi);
10243 __ pop(edi); 10171 __ pop(edi);
10244 __ ret(0); 10172 __ ret(0);
10245 } 10173 }
10246 10174
10247 } else { 10175 } else {
10248 __ IncrementCounter(COUNTERS->memcopy_noxmm(), 1); 10176 __ IncrementCounter(COUNTERS->memcopy_noxmm(), 1);
10249 // SSE2 not supported. Unlikely to happen in practice. 10177 // SSE2 not supported. Unlikely to happen in practice.
10250 __ push(edi); 10178 __ push(edi);
10251 __ push(esi); 10179 __ push(esi);
(...skipping 23 matching lines...) Expand all
10275 __ mov(edx, count); 10203 __ mov(edx, count);
10276 count = edx; 10204 count = edx;
10277 __ shr(ecx, 2); // Make word count instead of byte count. 10205 __ shr(ecx, 2); // Make word count instead of byte count.
10278 __ rep_movs(); 10206 __ rep_movs();
10279 10207
10280 // At most 3 bytes left to copy. Copy 4 bytes at end of string. 10208 // At most 3 bytes left to copy. Copy 4 bytes at end of string.
10281 __ and_(count, 3); 10209 __ and_(count, 3);
10282 __ mov(eax, Operand(src, count, times_1, -4)); 10210 __ mov(eax, Operand(src, count, times_1, -4));
10283 __ mov(Operand(dst, count, times_1, -4), eax); 10211 __ mov(Operand(dst, count, times_1, -4), eax);
10284 10212
10213 __ mov(eax, Operand(esp, stack_offset + kDestinationOffset));
10285 __ pop(esi); 10214 __ pop(esi);
10286 __ pop(edi); 10215 __ pop(edi);
10287 __ ret(0); 10216 __ ret(0);
10288 } 10217 }
10289 10218
10290 CodeDesc desc; 10219 CodeDesc desc;
10291 masm.GetCode(&desc); 10220 masm.GetCode(&desc);
10292 // Call the function from C++. 10221 ASSERT(desc.reloc_size == 0);
10293 return FUNCTION_CAST<MemCopyFunction>(buffer); 10222
10223 // Copy the generated code into an executable chunk and return a pointer
10224 // to the first instruction in it as a C++ function pointer.
10225 LargeObjectChunk* chunk = LargeObjectChunk::New(desc.instr_size, EXECUTABLE);
10226 if (chunk == NULL) return &MemCopyWrapper;
10227 memcpy(chunk->GetStartAddress(), desc.buffer, desc.instr_size);
10228 CPU::FlushICache(chunk->GetStartAddress(), desc.instr_size);
10229 return FUNCTION_CAST<MemCopyFunction>(chunk->GetStartAddress());
10294 } 10230 }
10295 10231
10296 #undef __ 10232 #undef __
10297 10233
10298 } } // namespace v8::internal 10234 } } // namespace v8::internal
10299 10235
10300 #endif // V8_TARGET_ARCH_IA32 10236 #endif // V8_TARGET_ARCH_IA32
OLDNEW
« no previous file with comments | « src/ia32/codegen-ia32.h ('k') | src/ia32/cpu-ia32.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698