| OLD | NEW |
| 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 #include "vm/globals.h" | 5 #include "vm/globals.h" |
| 6 #if defined(TARGET_ARCH_X64) | 6 #if defined(TARGET_ARCH_X64) |
| 7 | 7 |
| 8 #include "vm/assembler.h" | 8 #include "vm/assembler.h" |
| 9 #include "vm/cpu.h" | 9 #include "vm/cpu.h" |
| 10 #include "vm/heap.h" | 10 #include "vm/heap.h" |
| (...skipping 436 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 447 | 447 |
| 448 | 448 |
| 449 void Assembler::leaq(Register dst, const Address& src) { | 449 void Assembler::leaq(Register dst, const Address& src) { |
| 450 AssemblerBuffer::EnsureCapacity ensured(&buffer_); | 450 AssemblerBuffer::EnsureCapacity ensured(&buffer_); |
| 451 EmitOperandREX(dst, src, REX_W); | 451 EmitOperandREX(dst, src, REX_W); |
| 452 EmitUint8(0x8D); | 452 EmitUint8(0x8D); |
| 453 EmitOperand(dst & 7, src); | 453 EmitOperand(dst & 7, src); |
| 454 } | 454 } |
| 455 | 455 |
| 456 | 456 |
| 457 void Assembler::cmoveq(Register dst, Register src) { |
| 458 AssemblerBuffer::EnsureCapacity ensured(&buffer_); |
| 459 Operand operand(src); |
| 460 EmitOperandREX(dst, operand, REX_W); |
| 461 EmitUint8(0x0F); |
| 462 EmitUint8(0x44); |
| 463 EmitOperand(dst & 7, operand); |
| 464 } |
| 465 |
| 466 |
| 457 void Assembler::cmovgeq(Register dst, Register src) { | 467 void Assembler::cmovgeq(Register dst, Register src) { |
| 458 AssemblerBuffer::EnsureCapacity ensured(&buffer_); | 468 AssemblerBuffer::EnsureCapacity ensured(&buffer_); |
| 459 Operand operand(src); | 469 Operand operand(src); |
| 460 EmitOperandREX(dst, operand, REX_W); | 470 EmitOperandREX(dst, operand, REX_W); |
| 461 EmitUint8(0x0F); | 471 EmitUint8(0x0F); |
| 462 EmitUint8(0x4D); | 472 EmitUint8(0x4D); |
| 463 EmitOperand(dst & 7, operand); | 473 EmitOperand(dst & 7, operand); |
| 464 } | 474 } |
| 465 | 475 |
| 466 | 476 |
| (...skipping 2858 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3325 } | 3335 } |
| 3326 | 3336 |
| 3327 | 3337 |
| 3328 void Assembler::CompareClassId(Register object, intptr_t class_id) { | 3338 void Assembler::CompareClassId(Register object, intptr_t class_id) { |
| 3329 LoadClassId(TMP, object); | 3339 LoadClassId(TMP, object); |
| 3330 cmpl(TMP, Immediate(class_id)); | 3340 cmpl(TMP, Immediate(class_id)); |
| 3331 } | 3341 } |
| 3332 | 3342 |
| 3333 | 3343 |
| 3334 void Assembler::LoadTaggedClassIdMayBeSmi(Register result, Register object) { | 3344 void Assembler::LoadTaggedClassIdMayBeSmi(Register result, Register object) { |
| 3335 Label load, done; | 3345 ASSERT(object != TMP); |
| 3336 testq(object, Immediate(kSmiTagMask)); | 3346 ASSERT(result != TMP); |
| 3337 j(NOT_ZERO, &load, Assembler::kNearJump); | 3347 |
| 3338 LoadImmediate(result, Immediate(Smi::RawValue(kSmiCid)), PP); | 3348 // Make a copy of object since result and object can be the same register. |
| 3339 jmp(&done); | 3349 movq(TMP, object); |
| 3340 Bind(&load); | 3350 // Load up a null object. We only need it so we can use LoadClassId on it in |
| 3341 LoadClassId(result, object); | 3351 // the case that object is a Smi. |
| 3352 LoadObject(result, Object::null_object(), PP); |
| 3353 // Check if the object is a Smi. |
| 3354 testq(TMP, Immediate(kSmiTagMask)); |
| 3355 // If the object *is* a Smi, load the null object into tmp. o/w leave alone. |
| 3356 cmoveq(TMP, result); |
| 3357 // Loads either the cid of the object if it isn't a Smi, or the cid of null |
| 3358 // if it is a Smi, which will be ignored. |
| 3359 LoadClassId(result, TMP); |
| 3360 |
| 3361 movq(TMP, Immediate(kSmiCid)); |
| 3362 // If object is a Smi, move the Smi cid into result. o/w leave alone. |
| 3363 cmoveq(result, TMP); |
| 3364 // Finally, tag the result. |
| 3342 SmiTag(result); | 3365 SmiTag(result); |
| 3343 Bind(&done); | |
| 3344 } | 3366 } |
| 3345 | 3367 |
| 3346 | 3368 |
| 3347 static const char* cpu_reg_names[kNumberOfCpuRegisters] = { | 3369 static const char* cpu_reg_names[kNumberOfCpuRegisters] = { |
| 3348 "rax", "rcx", "rdx", "rbx", "rsp", "rbp", "rsi", "rdi", | 3370 "rax", "rcx", "rdx", "rbx", "rsp", "rbp", "rsi", "rdi", |
| 3349 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15" | 3371 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15" |
| 3350 }; | 3372 }; |
| 3351 | 3373 |
| 3352 | 3374 |
| 3353 const char* Assembler::RegisterName(Register reg) { | 3375 const char* Assembler::RegisterName(Register reg) { |
| 3354 ASSERT((0 <= reg) && (reg < kNumberOfCpuRegisters)); | 3376 ASSERT((0 <= reg) && (reg < kNumberOfCpuRegisters)); |
| 3355 return cpu_reg_names[reg]; | 3377 return cpu_reg_names[reg]; |
| 3356 } | 3378 } |
| 3357 | 3379 |
| 3358 | 3380 |
| 3359 static const char* xmm_reg_names[kNumberOfXmmRegisters] = { | 3381 static const char* xmm_reg_names[kNumberOfXmmRegisters] = { |
| 3360 "xmm0", "xmm1", "xmm2", "xmm3", "xmm4", "xmm5", "xmm6", "xmm7", | 3382 "xmm0", "xmm1", "xmm2", "xmm3", "xmm4", "xmm5", "xmm6", "xmm7", |
| 3361 "xmm8", "xmm9", "xmm10", "xmm11", "xmm12", "xmm13", "xmm14", "xmm15" | 3383 "xmm8", "xmm9", "xmm10", "xmm11", "xmm12", "xmm13", "xmm14", "xmm15" |
| 3362 }; | 3384 }; |
| 3363 | 3385 |
| 3364 | 3386 |
| 3365 const char* Assembler::FpuRegisterName(FpuRegister reg) { | 3387 const char* Assembler::FpuRegisterName(FpuRegister reg) { |
| 3366 ASSERT((0 <= reg) && (reg < kNumberOfXmmRegisters)); | 3388 ASSERT((0 <= reg) && (reg < kNumberOfXmmRegisters)); |
| 3367 return xmm_reg_names[reg]; | 3389 return xmm_reg_names[reg]; |
| 3368 } | 3390 } |
| 3369 | 3391 |
| 3370 } // namespace dart | 3392 } // namespace dart |
| 3371 | 3393 |
| 3372 #endif // defined TARGET_ARCH_X64 | 3394 #endif // defined TARGET_ARCH_X64 |
| OLD | NEW |