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

Side by Side Diff: src/x64/assembler-x64.cc

Issue 115920: X64: Added jmp and call and nop(n) to X64 assembler. (Closed)
Patch Set: Addressed more review comments. Created 11 years, 6 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
OLDNEW
1 // Copyright 2009 the V8 project authors. All rights reserved. 1 // Copyright 2009 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 253 matching lines...) Expand 10 before | Expand all | Expand 10 after
264 if (*p != 0) { // 0 means uninitialized. 264 if (*p != 0) { // 0 means uninitialized.
265 *p += pc_delta; 265 *p += pc_delta;
266 } 266 }
267 } 267 }
268 } 268 }
269 269
270 ASSERT(!overflow()); 270 ASSERT(!overflow());
271 } 271 }
272 272
273 273
274 void Assembler::emit_operand(Register reg, const Operand& adr) { 274 void Assembler::emit_operand(int rm, const Operand& adr) {
275 ASSERT_EQ(rm & 0x07, rm);
William Hesse 2009/05/29 13:08:00 I think that rm should be anded with 0x7 always, s
Lasse Reichstein 2009/05/29 13:13:29 I'd rather fail than silently correct errors. The
275 const unsigned length = adr.len_; 276 const unsigned length = adr.len_;
276 ASSERT(length > 0); 277 ASSERT(length > 0);
277 278
278 // Emit updated ModRM byte containing the given register. 279 // Emit updated ModRM byte containing the given register.
279 pc_[0] = (adr.buf_[0] & ~0x38) | ((reg.code() && 0x7) << 3); 280 pc_[0] = (adr.buf_[0] & ~0x38) | (rm << 3);
280 281
281 // Emit the rest of the encoded operand. 282 // Emit the rest of the encoded operand.
282 for (unsigned i = 1; i < length; i++) pc_[i] = adr.buf_[i]; 283 for (unsigned i = 1; i < length; i++) pc_[i] = adr.buf_[i];
283 pc_ += length; 284 pc_ += length;
284 } 285 }
285 286
286 287
287 // Assembler Instruction implementations 288 // Assembler Instruction implementations
288 289
289 void Assembler::arithmetic_op(byte opcode, Register reg, const Operand& op) { 290 void Assembler::arithmetic_op(byte opcode, Register reg, const Operand& op) {
(...skipping 65 matching lines...) Expand 10 before | Expand all | Expand 10 after
355 L->link_to(pc_offset() - sizeof(int32_t)); 356 L->link_to(pc_offset() - sizeof(int32_t));
356 } else { 357 } else {
357 ASSERT(L->is_unused()); 358 ASSERT(L->is_unused());
358 int32_t current = pc_offset(); 359 int32_t current = pc_offset();
359 emitl(current); 360 emitl(current);
360 L->link_to(current); 361 L->link_to(current);
361 } 362 }
362 } 363 }
363 364
364 365
366 void Assembler::call(Register adr) {
367 EnsureSpace ensure_space(this);
368 last_pc_ = pc_;
369 // Opcode: FF /2 r64
370 if (!is_uint3(adr.code())) {
371 emit_rex_64(adr);
372 }
373 emit(0xFF);
374 emit(0xD0 | (adr.code() & 0x07));
375 }
376
377
365 void Assembler::dec(Register dst) { 378 void Assembler::dec(Register dst) {
366 EnsureSpace ensure_space(this); 379 EnsureSpace ensure_space(this);
367 last_pc_ = pc_; 380 last_pc_ = pc_;
368 emit_rex_64(dst); 381 emit_rex_64(dst);
369 emit(0xFF); 382 emit(0xFF);
370 emit(0xC8 | (dst.code() & 0x7)); 383 emit(0xC8 | (dst.code() & 0x7));
371 } 384 }
372 385
373 386
374 void Assembler::dec(const Operand& dst) { 387 void Assembler::dec(const Operand& dst) {
(...skipping 97 matching lines...) Expand 10 before | Expand all | Expand 10 after
472 // 1110 1001 #32-bit disp 485 // 1110 1001 #32-bit disp
473 ASSERT(L->is_unused()); 486 ASSERT(L->is_unused());
474 emit(0xE9); 487 emit(0xE9);
475 int32_t current = pc_offset(); 488 int32_t current = pc_offset();
476 emitl(current); 489 emitl(current);
477 L->link_to(current); 490 L->link_to(current);
478 } 491 }
479 } 492 }
480 493
481 494
495 void Assembler::jmp(Register target) {
496 EnsureSpace ensure_space(this);
497 last_pc_ = pc_;
498 // Opcode FF/4 r64
499 if (!is_uint3(target.code())) {
500 emit_rex_64(target);
501 }
502 emit(0xFF);
503 emit(0xE0 | target.code() & 0x07);
504 }
505
506
482 void Assembler::movq(Register dst, const Operand& src) { 507 void Assembler::movq(Register dst, const Operand& src) {
483 EnsureSpace ensure_space(this); 508 EnsureSpace ensure_space(this);
484 last_pc_ = pc_; 509 last_pc_ = pc_;
485 emit_rex_64(dst, src); 510 emit_rex_64(dst, src);
486 emit(0x8B); 511 emit(0x8B);
487 emit_operand(dst, src); 512 emit_operand(dst, src);
488 } 513 }
489 514
490 515
491 void Assembler::movq(Register dst, Register src) { 516 void Assembler::movq(Register dst, Register src) {
(...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after
552 577
553 void Assembler::not_(const Operand& dst) { 578 void Assembler::not_(const Operand& dst) {
554 EnsureSpace ensure_space(this); 579 EnsureSpace ensure_space(this);
555 last_pc_ = pc_; 580 last_pc_ = pc_;
556 emit_rex_64(dst); 581 emit_rex_64(dst);
557 emit(0xF7); 582 emit(0xF7);
558 emit_operand(2, dst); 583 emit_operand(2, dst);
559 } 584 }
560 585
561 586
587 void Assembler::nop(int n) {
588 // The recommended muti-byte sequences of NOP instructions from the Intel 64
589 // and IA-32 Architectures Software Developer's Manual.
590 //
591 // Length Assembly Byte Sequence
592 // 2 bytes 66 NOP 66 90H
593 // 3 bytes NOP DWORD ptr [EAX] 0F 1F 00H
594 // 4 bytes NOP DWORD ptr [EAX + 00H] 0F 1F 40 00H
595 // 5 bytes NOP DWORD ptr [EAX + EAX*1 + 00H] 0F 1F 44 00 00H
596 // 6 bytes 66 NOP DWORD ptr [EAX + EAX*1 + 00H] 66 0F 1F 44 00 00H
597 // 7 bytes NOP DWORD ptr [EAX + 00000000H] 0F 1F 80 00 00 00 00H
598 // 8 bytes NOP DWORD ptr [EAX + EAX*1 + 00000000H] 0F 1F 84 00 00 00 00 00H
599 // 9 bytes 66 NOP DWORD ptr [EAX + EAX*1 + 66 0F 1F 84 00 00 00 00
600 // 00000000H] 00H
601
602 ASSERT(1 <= n);
603 ASSERT(n <= 9);
604 EnsureSpace ensure_space(this);
605 last_pc_ = pc_;
606 switch (n) {
607 case 1:
608 emit(0x90);
609 return;
610 case 2:
611 emit(0x66);
612 emit(0x90);
613 return;
614 case 3:
615 emit(0x0f);
616 emit(0x1f);
617 emit(0x00);
618 return;
619 case 4:
620 emit(0x0f);
621 emit(0x1f);
622 emit(0x40);
623 emit(0x00);
624 return;
625 case 5:
626 emit(0x0f);
627 emit(0x1f);
628 emit(0x44);
629 emit(0x00);
630 emit(0x00);
631 return;
632 case 6:
633 emit(0x66);
634 emit(0x0f);
635 emit(0x1f);
636 emit(0x44);
637 emit(0x00);
638 emit(0x00);
639 return;
640 case 7:
641 emit(0x0f);
642 emit(0x1f);
643 emit(0x80);
644 emit(0x00);
645 emit(0x00);
646 emit(0x00);
647 emit(0x00);
648 return;
649 case 8:
650 emit(0x0f);
651 emit(0x1f);
652 emit(0x84);
653 emit(0x00);
654 emit(0x00);
655 emit(0x00);
656 emit(0x00);
657 emit(0x00);
658 return;
659 case 9:
660 emit(0x66);
661 emit(0x0f);
662 emit(0x1f);
663 emit(0x84);
664 emit(0x00);
665 emit(0x00);
666 emit(0x00);
667 emit(0x00);
668 emit(0x00);
669 return;
670 }
671 }
672
673
562 void Assembler::pop(Register dst) { 674 void Assembler::pop(Register dst) {
563 EnsureSpace ensure_space(this); 675 EnsureSpace ensure_space(this);
564 last_pc_ = pc_; 676 last_pc_ = pc_;
565 if (dst.code() & 0x8) { 677 if (dst.code() & 0x8) {
566 emit_rex_64(dst); 678 emit_rex_64(dst);
567 } 679 }
568 emit(0x58 | (dst.code() & 0x7)); 680 emit(0x58 | (dst.code() & 0x7));
569 } 681 }
570 682
571 683
(...skipping 431 matching lines...) Expand 10 before | Expand all | Expand 10 after
1003 UNIMPLEMENTED(); 1115 UNIMPLEMENTED();
1004 return NULL; 1116 return NULL;
1005 } 1117 }
1006 1118
1007 byte* JavaScriptFrame::GetCallerStackPointer() const { 1119 byte* JavaScriptFrame::GetCallerStackPointer() const {
1008 UNIMPLEMENTED(); 1120 UNIMPLEMENTED();
1009 return NULL; 1121 return NULL;
1010 } 1122 }
1011 1123
1012 } } // namespace v8::internal 1124 } } // namespace v8::internal
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698