| OLD | NEW |
| 1 // Copyright (c) 1994-2006 Sun Microsystems Inc. | 1 // Copyright (c) 1994-2006 Sun Microsystems Inc. |
| 2 // All Rights Reserved. | 2 // All Rights Reserved. |
| 3 // | 3 // |
| 4 // Redistribution and use in source and binary forms, with or without | 4 // Redistribution and use in source and binary forms, with or without |
| 5 // modification, are permitted provided that the following conditions are | 5 // modification, are permitted provided that the following conditions are |
| 6 // met: | 6 // met: |
| 7 // | 7 // |
| 8 // - Redistributions of source code must retain the above copyright notice, | 8 // - Redistributions of source code must retain the above copyright notice, |
| 9 // this list of conditions and the following disclaimer. | 9 // this list of conditions and the following disclaimer. |
| 10 // | 10 // |
| (...skipping 235 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 246 enum ScaleFactor { | 246 enum ScaleFactor { |
| 247 times_1 = 0, | 247 times_1 = 0, |
| 248 times_2 = 1, | 248 times_2 = 1, |
| 249 times_4 = 2, | 249 times_4 = 2, |
| 250 times_8 = 3 | 250 times_8 = 3 |
| 251 }; | 251 }; |
| 252 | 252 |
| 253 | 253 |
| 254 class Operand BASE_EMBEDDED { | 254 class Operand BASE_EMBEDDED { |
| 255 public: | 255 public: |
| 256 // reg | |
| 257 INLINE(explicit Operand(Register reg)); | |
| 258 | |
| 259 // MemoryOperand | |
| 260 INLINE(explicit Operand()) { UNIMPLEMENTED(); } | |
| 261 | |
| 262 // Returns true if this Operand is a wrapper for the specified register. | |
| 263 bool is_reg(Register reg) const; | |
| 264 | |
| 265 // These constructors have been moved to MemOperand, and should | |
| 266 // be removed from Operand as soon as all their uses use MemOperands instead. | |
| 267 // [disp/r] | |
| 268 INLINE(explicit Operand(intptr_t disp, RelocInfo::Mode rmode)) { | |
| 269 UNIMPLEMENTED(); | |
| 270 } | |
| 271 // disp only must always be relocated | |
| 272 | |
| 273 // [base + disp/r] | 256 // [base + disp/r] |
| 274 explicit Operand(Register base, int32_t disp, | 257 INLINE(Operand(Register base, int32_t disp)); |
| 275 RelocInfo::Mode rmode = RelocInfo::NONE); | |
| 276 | 258 |
| 277 // [base + index*scale + disp/r] | 259 // [base + index*scale + disp/r] |
| 278 explicit Operand(Register base, | 260 Operand(Register base, |
| 279 Register index, | 261 Register index, |
| 280 ScaleFactor scale, | 262 ScaleFactor scale, |
| 281 int32_t disp, | 263 int32_t disp); |
| 282 RelocInfo::Mode rmode = RelocInfo::NONE); | |
| 283 | 264 |
| 284 // [index*scale + disp/r] | 265 // [index*scale + disp/r] |
| 285 explicit Operand(Register index, | 266 Operand(Register index, |
| 286 ScaleFactor scale, | 267 ScaleFactor scale, |
| 287 int32_t disp, | 268 int32_t disp); |
| 288 RelocInfo::Mode rmode = RelocInfo::NONE); | |
| 289 | |
| 290 // End of constructors and methods that have been moved to MemOperand. | |
| 291 | 269 |
| 292 private: | 270 private: |
| 293 byte rex_; | 271 byte rex_; |
| 294 byte buf_[10]; | 272 byte buf_[10]; |
| 295 // The number of bytes in buf_. | 273 // The number of bytes in buf_. |
| 296 unsigned int len_; | 274 unsigned int len_; |
| 297 // Only valid if len_ > 4. | |
| 298 RelocInfo::Mode rmode_; | 275 RelocInfo::Mode rmode_; |
| 299 | 276 |
| 300 // Set the ModRM byte without an encoded 'reg' register. The | 277 // Set the ModRM byte without an encoded 'reg' register. The |
| 301 // register is encoded later as part of the emit_operand operation. | 278 // register is encoded later as part of the emit_operand operation. |
| 279 // set_modrm can be called before or after set_sib and set_disp*. |
| 302 inline void set_modrm(int mod, Register rm); | 280 inline void set_modrm(int mod, Register rm); |
| 303 | 281 |
| 282 // Set the SIB byte if one is needed. Sets the length to 2 rather than 1. |
| 304 inline void set_sib(ScaleFactor scale, Register index, Register base); | 283 inline void set_sib(ScaleFactor scale, Register index, Register base); |
| 305 inline void set_disp8(int8_t disp); | 284 |
| 306 inline void set_disp32(int32_t disp); | 285 // Adds operand displacement fields (offsets added to the memory address). |
| 286 // Needs to be called after set_sib, not before it. |
| 287 inline void set_disp8(int disp); |
| 288 inline void set_disp32(int disp); |
| 307 | 289 |
| 308 friend class Assembler; | 290 friend class Assembler; |
| 309 }; | 291 }; |
| 310 | 292 |
| 311 class MemOperand : public Operand { | |
| 312 public: | |
| 313 // [disp/r] | |
| 314 INLINE(explicit MemOperand(int32_t disp, RelocInfo::Mode rmode)) : | |
| 315 Operand() { | |
| 316 UNIMPLEMENTED(); | |
| 317 } | |
| 318 // disp only must always be relocated | |
| 319 | |
| 320 // [base + disp/r] | |
| 321 explicit MemOperand(Register base, int32_t disp, | |
| 322 RelocInfo::Mode rmode = RelocInfo::NONE); | |
| 323 | |
| 324 // [base + index*scale + disp/r] | |
| 325 explicit MemOperand(Register base, | |
| 326 Register index, | |
| 327 ScaleFactor scale, | |
| 328 int32_t disp, | |
| 329 RelocInfo::Mode rmode = RelocInfo::NONE); | |
| 330 | |
| 331 // [index*scale + disp/r] | |
| 332 explicit MemOperand(Register index, | |
| 333 ScaleFactor scale, | |
| 334 int32_t disp, | |
| 335 RelocInfo::Mode rmode = RelocInfo::NONE); | |
| 336 }; | |
| 337 | |
| 338 // ----------------------------------------------------------------------------- | |
| 339 // A Displacement describes the 32bit immediate field of an instruction which | |
| 340 // may be used together with a Label in order to refer to a yet unknown code | |
| 341 // position. Displacements stored in the instruction stream are used to describe | |
| 342 // the instruction and to chain a list of instructions using the same Label. | |
| 343 // A Displacement contains 2 different fields: | |
| 344 // | |
| 345 // next field: position of next displacement in the chain (0 = end of list) | |
| 346 // type field: instruction type | |
| 347 // | |
| 348 // A next value of null (0) indicates the end of a chain (note that there can | |
| 349 // be no displacement at position zero, because there is always at least one | |
| 350 // instruction byte before the displacement). | |
| 351 // | |
| 352 // Displacement _data field layout | |
| 353 // | |
| 354 // |31.....2|1......0| | |
| 355 // [ next | type | | |
| 356 | |
| 357 class Displacement BASE_EMBEDDED { | |
| 358 public: | |
| 359 enum Type { | |
| 360 UNCONDITIONAL_JUMP, | |
| 361 CODE_RELATIVE, | |
| 362 OTHER | |
| 363 }; | |
| 364 | |
| 365 int data() const { return data_; } | |
| 366 Type type() const { return TypeField::decode(data_); } | |
| 367 void next(Label* L) const { | |
| 368 int n = NextField::decode(data_); | |
| 369 n > 0 ? L->link_to(n) : L->Unuse(); | |
| 370 } | |
| 371 void link_to(Label* L) { init(L, type()); } | |
| 372 | |
| 373 explicit Displacement(int data) { data_ = data; } | |
| 374 | |
| 375 Displacement(Label* L, Type type) { init(L, type); } | |
| 376 | |
| 377 void print() { | |
| 378 PrintF("%s (%x) ", (type() == UNCONDITIONAL_JUMP ? "jmp" : "[other]"), | |
| 379 NextField::decode(data_)); | |
| 380 } | |
| 381 | |
| 382 private: | |
| 383 int data_; | |
| 384 | |
| 385 class TypeField: public BitField<Type, 0, 2> {}; | |
| 386 class NextField: public BitField<int, 2, 32-2> {}; | |
| 387 | |
| 388 void init(Label* L, Type type); | |
| 389 }; | |
| 390 | |
| 391 | |
| 392 | 293 |
| 393 // CpuFeatures keeps track of which features are supported by the target CPU. | 294 // CpuFeatures keeps track of which features are supported by the target CPU. |
| 394 // Supported features must be enabled by a Scope before use. | 295 // Supported features must be enabled by a Scope before use. |
| 395 // Example: | 296 // Example: |
| 396 // if (CpuFeatures::IsSupported(SSE2)) { | 297 // if (CpuFeatures::IsSupported(SSE2)) { |
| 397 // CpuFeatures::Scope fscope(SSE2); | 298 // CpuFeatures::Scope fscope(SSE2); |
| 398 // // Generate SSE2 floating point code. | 299 // // Generate SSE2 floating point code. |
| 399 // } else { | 300 // } else { |
| 400 // // Generate standard x87 floating point code. | 301 // // Generate standard x87 floating point code. |
| 401 // } | 302 // } |
| (...skipping 441 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 843 | 744 |
| 844 void emit_operand(Register reg, const Operand& adr); | 745 void emit_operand(Register reg, const Operand& adr); |
| 845 | 746 |
| 846 void emit_farith(int b1, int b2, int i); | 747 void emit_farith(int b1, int b2, int i); |
| 847 | 748 |
| 848 // labels | 749 // labels |
| 849 void print(Label* L); | 750 void print(Label* L); |
| 850 void bind_to(Label* L, int pos); | 751 void bind_to(Label* L, int pos); |
| 851 void link_to(Label* L, Label* appendix); | 752 void link_to(Label* L, Label* appendix); |
| 852 | 753 |
| 853 // displacements | |
| 854 inline Displacement disp_at(Label* L); | |
| 855 inline void disp_at_put(Label* L, Displacement disp); | |
| 856 inline void emit_disp(Label* L, Displacement::Type type); | |
| 857 | |
| 858 // record reloc info for current pc_ | 754 // record reloc info for current pc_ |
| 859 void RecordRelocInfo(RelocInfo::Mode rmode, intptr_t data = 0); | 755 void RecordRelocInfo(RelocInfo::Mode rmode, intptr_t data = 0); |
| 860 | 756 |
| 861 friend class CodePatcher; | 757 friend class CodePatcher; |
| 862 friend class EnsureSpace; | 758 friend class EnsureSpace; |
| 863 | 759 |
| 864 // Code buffer: | 760 // Code buffer: |
| 865 // The buffer into which code and relocation info are generated. | 761 // The buffer into which code and relocation info are generated. |
| 866 byte* buffer_; | 762 byte* buffer_; |
| 867 int buffer_size_; | 763 int buffer_size_; |
| (...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 908 private: | 804 private: |
| 909 Assembler* assembler_; | 805 Assembler* assembler_; |
| 910 #ifdef DEBUG | 806 #ifdef DEBUG |
| 911 int space_before_; | 807 int space_before_; |
| 912 #endif | 808 #endif |
| 913 }; | 809 }; |
| 914 | 810 |
| 915 } } // namespace v8::internal | 811 } } // namespace v8::internal |
| 916 | 812 |
| 917 #endif // V8_X64_ASSEMBLER_X64_H_ | 813 #endif // V8_X64_ASSEMBLER_X64_H_ |
| OLD | NEW |