OLD | NEW |
1 // Copyright 2013 the V8 project authors. All rights reserved. | 1 // Copyright 2013 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 552 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
563 // ----------------------------------------------------------------------------- | 563 // ----------------------------------------------------------------------------- |
564 // Operands. | 564 // Operands. |
565 const int kSmiShift = kSmiTagSize + kSmiShiftSize; | 565 const int kSmiShift = kSmiTagSize + kSmiShiftSize; |
566 const uint64_t kSmiShiftMask = (1UL << kSmiShift) - 1; | 566 const uint64_t kSmiShiftMask = (1UL << kSmiShift) - 1; |
567 | 567 |
568 // Represents an operand in a machine instruction. | 568 // Represents an operand in a machine instruction. |
569 class Operand { | 569 class Operand { |
570 // TODO(all): If necessary, study more in details which methods | 570 // TODO(all): If necessary, study more in details which methods |
571 // TODO(all): should be inlined or not. | 571 // TODO(all): should be inlined or not. |
572 public: | 572 public: |
573 // #<immediate> | |
574 // where <immediate> is int64_t. | |
575 // GCC complains about ambiguous aliasing if we don't explicitly declare the | |
576 // variants. | |
577 // The simple literal-value wrappers are allowed to be implicit constructors | |
578 // because Operand is a wrapper class that doesn't normally perform any type | |
579 // conversion. | |
580 inline Operand(int64_t immediate, | |
581 RelocInfo::Mode rmode = RelocInfo::NONE64); // NOLINT(runtime/explicit) | |
582 inline Operand(uint64_t immediate, | |
583 RelocInfo::Mode rmode = RelocInfo::NONE64); // NOLINT(runtime/explicit) | |
584 inline Operand(int32_t immediate, | |
585 RelocInfo::Mode rmode = RelocInfo::NONE32); // NOLINT(runtime/explicit) | |
586 inline Operand(uint32_t immediate, | |
587 RelocInfo::Mode rmode = RelocInfo::NONE32); // NOLINT(runtime/explicit) | |
588 | |
589 | |
590 // rm, {<shift> {#<shift_amount>}} | 573 // rm, {<shift> {#<shift_amount>}} |
591 // where <shift> is one of {LSL, LSR, ASR, ROR}. | 574 // where <shift> is one of {LSL, LSR, ASR, ROR}. |
592 // <shift_amount> is uint6_t. | 575 // <shift_amount> is uint6_t. |
593 // This is allowed to be an implicit constructor because Operand is | 576 // This is allowed to be an implicit constructor because Operand is |
594 // a wrapper class that doesn't normally perform any type conversion. | 577 // a wrapper class that doesn't normally perform any type conversion. |
595 inline Operand(Register reg, | 578 inline Operand(Register reg, |
596 Shift shift = LSL, | 579 Shift shift = LSL, |
597 unsigned shift_amount = 0); // NOLINT(runtime/explicit) | 580 unsigned shift_amount = 0); // NOLINT(runtime/explicit) |
598 | 581 |
599 // rm, <extend> {#<shift_amount>} | 582 // rm, <extend> {#<shift_amount>} |
600 // where <extend> is one of {UXTB, UXTH, UXTW, UXTX, SXTB, SXTH, SXTW, SXTX}. | 583 // where <extend> is one of {UXTB, UXTH, UXTW, UXTX, SXTB, SXTH, SXTW, SXTX}. |
601 // <shift_amount> is uint2_t. | 584 // <shift_amount> is uint2_t. |
602 inline Operand(Register reg, | 585 inline Operand(Register reg, |
603 Extend extend, | 586 Extend extend, |
604 unsigned shift_amount = 0); | 587 unsigned shift_amount = 0); |
605 | 588 |
606 inline explicit Operand(Smi* value); | 589 template<typename T> |
607 explicit Operand(const ExternalReference& f); | 590 inline explicit Operand(Handle<T> handle); |
608 explicit Operand(Handle<Object> handle); | 591 |
| 592 // Implicit constructor for all int types, ExternalReference, and Smi. |
| 593 template<typename T> |
| 594 inline Operand(T t); // NOLINT(runtime/explicit) |
| 595 |
| 596 // Implicit constructor for int types. |
| 597 template<typename int_t> |
| 598 inline Operand(int_t t, RelocInfo::Mode rmode); |
609 | 599 |
610 inline bool IsImmediate() const; | 600 inline bool IsImmediate() const; |
611 inline bool IsShiftedRegister() const; | 601 inline bool IsShiftedRegister() const; |
612 inline bool IsExtendedRegister() const; | 602 inline bool IsExtendedRegister() const; |
613 inline bool IsZero() const; | 603 inline bool IsZero() const; |
614 | 604 |
615 // This returns an LSL shift (<= 4) operand as an equivalent extend operand, | 605 // This returns an LSL shift (<= 4) operand as an equivalent extend operand, |
616 // which helps in the encoding of instructions that use the stack pointer. | 606 // which helps in the encoding of instructions that use the stack pointer. |
617 inline Operand ToExtendedRegister() const; | 607 inline Operand ToExtendedRegister() const; |
618 | 608 |
619 inline int64_t immediate() const; | 609 inline int64_t immediate() const; |
620 inline Register reg() const; | 610 inline Register reg() const; |
621 inline Shift shift() const; | 611 inline Shift shift() const; |
622 inline Extend extend() const; | 612 inline Extend extend() const; |
623 inline unsigned shift_amount() const; | 613 inline unsigned shift_amount() const; |
624 | 614 |
625 // Relocation information. | 615 // Relocation information. |
626 RelocInfo::Mode rmode() const { return rmode_; } | 616 RelocInfo::Mode rmode() const { return rmode_; } |
627 void set_rmode(RelocInfo::Mode rmode) { rmode_ = rmode; } | 617 void set_rmode(RelocInfo::Mode rmode) { rmode_ = rmode; } |
628 bool NeedsRelocation() const; | 618 bool NeedsRelocation() const; |
629 | 619 |
630 // Helpers | 620 // Helpers |
631 inline static Operand UntagSmi(Register smi); | 621 inline static Operand UntagSmi(Register smi); |
632 inline static Operand UntagSmiAndScale(Register smi, int scale); | 622 inline static Operand UntagSmiAndScale(Register smi, int scale); |
633 | 623 |
634 private: | 624 private: |
| 625 void initialize_handle(Handle<Object> value); |
635 int64_t immediate_; | 626 int64_t immediate_; |
636 Register reg_; | 627 Register reg_; |
637 Shift shift_; | 628 Shift shift_; |
638 Extend extend_; | 629 Extend extend_; |
639 unsigned shift_amount_; | 630 unsigned shift_amount_; |
640 RelocInfo::Mode rmode_; | 631 RelocInfo::Mode rmode_; |
641 }; | 632 }; |
642 | 633 |
643 | 634 |
644 // MemOperand represents a memory operand in a load or store instruction. | 635 // MemOperand represents a memory operand in a load or store instruction. |
(...skipping 1398 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2043 class EnsureSpace BASE_EMBEDDED { | 2034 class EnsureSpace BASE_EMBEDDED { |
2044 public: | 2035 public: |
2045 explicit EnsureSpace(Assembler* assembler) { | 2036 explicit EnsureSpace(Assembler* assembler) { |
2046 assembler->CheckBuffer(); | 2037 assembler->CheckBuffer(); |
2047 } | 2038 } |
2048 }; | 2039 }; |
2049 | 2040 |
2050 } } // namespace v8::internal | 2041 } } // namespace v8::internal |
2051 | 2042 |
2052 #endif // V8_A64_ASSEMBLER_A64_H_ | 2043 #endif // V8_A64_ASSEMBLER_A64_H_ |
OLD | NEW |