OLD | NEW |
1 // Copyright 2011 the V8 project authors. All rights reserved. | 1 // Copyright 2011 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 19 matching lines...) Expand all Loading... |
30 | 30 |
31 #include "ic-inl.h" | 31 #include "ic-inl.h" |
32 | 32 |
33 | 33 |
34 namespace v8 { | 34 namespace v8 { |
35 namespace internal { | 35 namespace internal { |
36 | 36 |
37 | 37 |
38 // Compute a transcendental math function natively, or call the | 38 // Compute a transcendental math function natively, or call the |
39 // TranscendentalCache runtime function. | 39 // TranscendentalCache runtime function. |
40 class TranscendentalCacheStub: public CodeStub { | 40 class TranscendentalCacheStub: public PlatformCodeStub { |
41 public: | 41 public: |
42 enum ArgumentType { | 42 enum ArgumentType { |
43 TAGGED = 0 << TranscendentalCache::kTranscendentalTypeBits, | 43 TAGGED = 0 << TranscendentalCache::kTranscendentalTypeBits, |
44 UNTAGGED = 1 << TranscendentalCache::kTranscendentalTypeBits | 44 UNTAGGED = 1 << TranscendentalCache::kTranscendentalTypeBits |
45 }; | 45 }; |
46 | 46 |
47 TranscendentalCacheStub(TranscendentalCache::Type type, | 47 TranscendentalCacheStub(TranscendentalCache::Type type, |
48 ArgumentType argument_type) | 48 ArgumentType argument_type) |
49 : type_(type), argument_type_(argument_type) { } | 49 : type_(type), argument_type_(argument_type) { } |
50 void Generate(MacroAssembler* masm); | 50 void Generate(MacroAssembler* masm); |
51 private: | 51 private: |
52 TranscendentalCache::Type type_; | 52 TranscendentalCache::Type type_; |
53 ArgumentType argument_type_; | 53 ArgumentType argument_type_; |
54 void GenerateCallCFunction(MacroAssembler* masm, Register scratch); | 54 void GenerateCallCFunction(MacroAssembler* masm, Register scratch); |
55 | 55 |
56 Major MajorKey() { return TranscendentalCache; } | 56 Major MajorKey() { return TranscendentalCache; } |
57 int MinorKey() { return type_ | argument_type_; } | 57 int MinorKey() { return type_ | argument_type_; } |
58 Runtime::FunctionId RuntimeFunction(); | 58 Runtime::FunctionId RuntimeFunction(); |
59 }; | 59 }; |
60 | 60 |
61 | 61 |
62 class StoreBufferOverflowStub: public CodeStub { | 62 class StoreBufferOverflowStub: public PlatformCodeStub { |
63 public: | 63 public: |
64 explicit StoreBufferOverflowStub(SaveFPRegsMode save_fp) | 64 explicit StoreBufferOverflowStub(SaveFPRegsMode save_fp) |
65 : save_doubles_(save_fp) { } | 65 : save_doubles_(save_fp) { } |
66 | 66 |
67 void Generate(MacroAssembler* masm); | 67 void Generate(MacroAssembler* masm); |
68 | 68 |
69 virtual bool IsPregenerated(); | 69 virtual bool IsPregenerated(); |
70 static void GenerateFixedRegStubsAheadOfTime(); | 70 static void GenerateFixedRegStubsAheadOfTime(); |
71 virtual bool SometimesSetsUpAFrame() { return false; } | 71 virtual bool SometimesSetsUpAFrame() { return false; } |
72 | 72 |
73 private: | 73 private: |
74 SaveFPRegsMode save_doubles_; | 74 SaveFPRegsMode save_doubles_; |
75 | 75 |
76 Major MajorKey() { return StoreBufferOverflow; } | 76 Major MajorKey() { return StoreBufferOverflow; } |
77 int MinorKey() { return (save_doubles_ == kSaveFPRegs) ? 1 : 0; } | 77 int MinorKey() { return (save_doubles_ == kSaveFPRegs) ? 1 : 0; } |
78 }; | 78 }; |
79 | 79 |
80 | 80 |
81 class UnaryOpStub: public CodeStub { | 81 class UnaryOpStub: public PlatformCodeStub { |
82 public: | 82 public: |
83 UnaryOpStub(Token::Value op, | 83 UnaryOpStub(Token::Value op, |
84 UnaryOverwriteMode mode, | 84 UnaryOverwriteMode mode, |
85 UnaryOpIC::TypeInfo operand_type = UnaryOpIC::UNINITIALIZED) | 85 UnaryOpIC::TypeInfo operand_type = UnaryOpIC::UNINITIALIZED) |
86 : op_(op), | 86 : op_(op), |
87 mode_(mode), | 87 mode_(mode), |
88 operand_type_(operand_type) { | 88 operand_type_(operand_type) { |
89 } | 89 } |
90 | 90 |
91 private: | 91 private: |
(...skipping 121 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
213 // Omit left string check in stub (left is definitely a string). | 213 // Omit left string check in stub (left is definitely a string). |
214 NO_STRING_CHECK_LEFT_IN_STUB = 1 << 0, | 214 NO_STRING_CHECK_LEFT_IN_STUB = 1 << 0, |
215 // Omit right string check in stub (right is definitely a string). | 215 // Omit right string check in stub (right is definitely a string). |
216 NO_STRING_CHECK_RIGHT_IN_STUB = 1 << 1, | 216 NO_STRING_CHECK_RIGHT_IN_STUB = 1 << 1, |
217 // Omit both string checks in stub. | 217 // Omit both string checks in stub. |
218 NO_STRING_CHECK_IN_STUB = | 218 NO_STRING_CHECK_IN_STUB = |
219 NO_STRING_CHECK_LEFT_IN_STUB | NO_STRING_CHECK_RIGHT_IN_STUB | 219 NO_STRING_CHECK_LEFT_IN_STUB | NO_STRING_CHECK_RIGHT_IN_STUB |
220 }; | 220 }; |
221 | 221 |
222 | 222 |
223 class StringAddStub: public CodeStub { | 223 class StringAddStub: public PlatformCodeStub { |
224 public: | 224 public: |
225 explicit StringAddStub(StringAddFlags flags) : flags_(flags) {} | 225 explicit StringAddStub(StringAddFlags flags) : flags_(flags) {} |
226 | 226 |
227 private: | 227 private: |
228 Major MajorKey() { return StringAdd; } | 228 Major MajorKey() { return StringAdd; } |
229 int MinorKey() { return flags_; } | 229 int MinorKey() { return flags_; } |
230 | 230 |
231 void Generate(MacroAssembler* masm); | 231 void Generate(MacroAssembler* masm); |
232 | 232 |
233 void GenerateConvertArgument(MacroAssembler* masm, | 233 void GenerateConvertArgument(MacroAssembler* masm, |
234 int stack_offset, | 234 int stack_offset, |
235 Register arg, | 235 Register arg, |
236 Register scratch1, | 236 Register scratch1, |
237 Register scratch2, | 237 Register scratch2, |
238 Register scratch3, | 238 Register scratch3, |
239 Register scratch4, | 239 Register scratch4, |
240 Label* slow); | 240 Label* slow); |
241 | 241 |
242 const StringAddFlags flags_; | 242 const StringAddFlags flags_; |
243 }; | 243 }; |
244 | 244 |
245 | 245 |
246 class SubStringStub: public CodeStub { | 246 class SubStringStub: public PlatformCodeStub { |
247 public: | 247 public: |
248 SubStringStub() {} | 248 SubStringStub() {} |
249 | 249 |
250 private: | 250 private: |
251 Major MajorKey() { return SubString; } | 251 Major MajorKey() { return SubString; } |
252 int MinorKey() { return 0; } | 252 int MinorKey() { return 0; } |
253 | 253 |
254 void Generate(MacroAssembler* masm); | 254 void Generate(MacroAssembler* masm); |
255 }; | 255 }; |
256 | 256 |
257 | 257 |
258 class StringCompareStub: public CodeStub { | 258 class StringCompareStub: public PlatformCodeStub { |
259 public: | 259 public: |
260 StringCompareStub() { } | 260 StringCompareStub() { } |
261 | 261 |
262 // Compare two flat ASCII strings and returns result in v0. | 262 // Compare two flat ASCII strings and returns result in v0. |
263 static void GenerateCompareFlatAsciiStrings(MacroAssembler* masm, | 263 static void GenerateCompareFlatAsciiStrings(MacroAssembler* masm, |
264 Register left, | 264 Register left, |
265 Register right, | 265 Register right, |
266 Register scratch1, | 266 Register scratch1, |
267 Register scratch2, | 267 Register scratch2, |
268 Register scratch3, | 268 Register scratch3, |
(...skipping 20 matching lines...) Expand all Loading... |
289 Register scratch1, | 289 Register scratch1, |
290 Register scratch2, | 290 Register scratch2, |
291 Register scratch3, | 291 Register scratch3, |
292 Label* chars_not_equal); | 292 Label* chars_not_equal); |
293 }; | 293 }; |
294 | 294 |
295 | 295 |
296 // This stub can convert a signed int32 to a heap number (double). It does | 296 // This stub can convert a signed int32 to a heap number (double). It does |
297 // not work for int32s that are in Smi range! No GC occurs during this stub | 297 // not work for int32s that are in Smi range! No GC occurs during this stub |
298 // so you don't have to set up the frame. | 298 // so you don't have to set up the frame. |
299 class WriteInt32ToHeapNumberStub : public CodeStub { | 299 class WriteInt32ToHeapNumberStub : public PlatformCodeStub { |
300 public: | 300 public: |
301 WriteInt32ToHeapNumberStub(Register the_int, | 301 WriteInt32ToHeapNumberStub(Register the_int, |
302 Register the_heap_number, | 302 Register the_heap_number, |
303 Register scratch, | 303 Register scratch, |
304 Register scratch2) | 304 Register scratch2) |
305 : the_int_(the_int), | 305 : the_int_(the_int), |
306 the_heap_number_(the_heap_number), | 306 the_heap_number_(the_heap_number), |
307 scratch_(scratch), | 307 scratch_(scratch), |
308 sign_(scratch2) { | 308 sign_(scratch2) { |
309 ASSERT(IntRegisterBits::is_valid(the_int_.code())); | 309 ASSERT(IntRegisterBits::is_valid(the_int_.code())); |
(...skipping 23 matching lines...) Expand all Loading... |
333 return IntRegisterBits::encode(the_int_.code()) | 333 return IntRegisterBits::encode(the_int_.code()) |
334 | HeapNumberRegisterBits::encode(the_heap_number_.code()) | 334 | HeapNumberRegisterBits::encode(the_heap_number_.code()) |
335 | ScratchRegisterBits::encode(scratch_.code()) | 335 | ScratchRegisterBits::encode(scratch_.code()) |
336 | SignRegisterBits::encode(sign_.code()); | 336 | SignRegisterBits::encode(sign_.code()); |
337 } | 337 } |
338 | 338 |
339 void Generate(MacroAssembler* masm); | 339 void Generate(MacroAssembler* masm); |
340 }; | 340 }; |
341 | 341 |
342 | 342 |
343 class NumberToStringStub: public CodeStub { | 343 class NumberToStringStub: public PlatformCodeStub { |
344 public: | 344 public: |
345 NumberToStringStub() { } | 345 NumberToStringStub() { } |
346 | 346 |
347 // Generate code to do a lookup in the number string cache. If the number in | 347 // Generate code to do a lookup in the number string cache. If the number in |
348 // the register object is found in the cache the generated code falls through | 348 // the register object is found in the cache the generated code falls through |
349 // with the result in the result register. The object and the result register | 349 // with the result in the result register. The object and the result register |
350 // can be the same. If the number is not found in the cache the code jumps to | 350 // can be the same. If the number is not found in the cache the code jumps to |
351 // the label not_found with only the content of register object unchanged. | 351 // the label not_found with only the content of register object unchanged. |
352 static void GenerateLookupNumberStringCache(MacroAssembler* masm, | 352 static void GenerateLookupNumberStringCache(MacroAssembler* masm, |
353 Register object, | 353 Register object, |
354 Register result, | 354 Register result, |
355 Register scratch1, | 355 Register scratch1, |
356 Register scratch2, | 356 Register scratch2, |
357 Register scratch3, | 357 Register scratch3, |
358 bool object_is_smi, | 358 bool object_is_smi, |
359 Label* not_found); | 359 Label* not_found); |
360 | 360 |
361 private: | 361 private: |
362 Major MajorKey() { return NumberToString; } | 362 Major MajorKey() { return NumberToString; } |
363 int MinorKey() { return 0; } | 363 int MinorKey() { return 0; } |
364 | 364 |
365 void Generate(MacroAssembler* masm); | 365 void Generate(MacroAssembler* masm); |
366 }; | 366 }; |
367 | 367 |
368 | 368 |
369 class RecordWriteStub: public CodeStub { | 369 class RecordWriteStub: public PlatformCodeStub { |
370 public: | 370 public: |
371 RecordWriteStub(Register object, | 371 RecordWriteStub(Register object, |
372 Register value, | 372 Register value, |
373 Register address, | 373 Register address, |
374 RememberedSetAction remembered_set_action, | 374 RememberedSetAction remembered_set_action, |
375 SaveFPRegsMode fp_mode) | 375 SaveFPRegsMode fp_mode) |
376 : object_(object), | 376 : object_(object), |
377 value_(value), | 377 value_(value), |
378 address_(address), | 378 address_(address), |
379 remembered_set_action_(remembered_set_action), | 379 remembered_set_action_(remembered_set_action), |
(...skipping 125 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
505 | 505 |
506 private: | 506 private: |
507 Register object_; | 507 Register object_; |
508 Register address_; | 508 Register address_; |
509 Register scratch0_; | 509 Register scratch0_; |
510 Register scratch1_; | 510 Register scratch1_; |
511 | 511 |
512 Register GetRegThatIsNotOneOf(Register r1, | 512 Register GetRegThatIsNotOneOf(Register r1, |
513 Register r2, | 513 Register r2, |
514 Register r3) { | 514 Register r3) { |
515 for (int i = 0; i < Register::kNumAllocatableRegisters; i++) { | 515 for (int i = 0; i < Register::NumAllocatableRegisters(); i++) { |
516 Register candidate = Register::FromAllocationIndex(i); | 516 Register candidate = Register::FromAllocationIndex(i); |
517 if (candidate.is(r1)) continue; | 517 if (candidate.is(r1)) continue; |
518 if (candidate.is(r2)) continue; | 518 if (candidate.is(r2)) continue; |
519 if (candidate.is(r3)) continue; | 519 if (candidate.is(r3)) continue; |
520 return candidate; | 520 return candidate; |
521 } | 521 } |
522 UNREACHABLE(); | 522 UNREACHABLE(); |
523 return no_reg; | 523 return no_reg; |
524 } | 524 } |
525 friend class RecordWriteStub; | 525 friend class RecordWriteStub; |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
564 RememberedSetAction remembered_set_action_; | 564 RememberedSetAction remembered_set_action_; |
565 SaveFPRegsMode save_fp_regs_mode_; | 565 SaveFPRegsMode save_fp_regs_mode_; |
566 Label slow_; | 566 Label slow_; |
567 RegisterAllocation regs_; | 567 RegisterAllocation regs_; |
568 }; | 568 }; |
569 | 569 |
570 | 570 |
571 // Enter C code from generated RegExp code in a way that allows | 571 // Enter C code from generated RegExp code in a way that allows |
572 // the C code to fix the return address in case of a GC. | 572 // the C code to fix the return address in case of a GC. |
573 // Currently only needed on ARM and MIPS. | 573 // Currently only needed on ARM and MIPS. |
574 class RegExpCEntryStub: public CodeStub { | 574 class RegExpCEntryStub: public PlatformCodeStub { |
575 public: | 575 public: |
576 RegExpCEntryStub() {} | 576 RegExpCEntryStub() {} |
577 virtual ~RegExpCEntryStub() {} | 577 virtual ~RegExpCEntryStub() {} |
578 void Generate(MacroAssembler* masm); | 578 void Generate(MacroAssembler* masm); |
579 | 579 |
580 private: | 580 private: |
581 Major MajorKey() { return RegExpCEntry; } | 581 Major MajorKey() { return RegExpCEntry; } |
582 int MinorKey() { return 0; } | 582 int MinorKey() { return 0; } |
583 | 583 |
584 bool NeedsImmovableCode() { return true; } | 584 bool NeedsImmovableCode() { return true; } |
585 }; | 585 }; |
586 | 586 |
587 // Trampoline stub to call into native code. To call safely into native code | 587 // Trampoline stub to call into native code. To call safely into native code |
588 // in the presence of compacting GC (which can move code objects) we need to | 588 // in the presence of compacting GC (which can move code objects) we need to |
589 // keep the code which called into native pinned in the memory. Currently the | 589 // keep the code which called into native pinned in the memory. Currently the |
590 // simplest approach is to generate such stub early enough so it can never be | 590 // simplest approach is to generate such stub early enough so it can never be |
591 // moved by GC | 591 // moved by GC |
592 class DirectCEntryStub: public CodeStub { | 592 class DirectCEntryStub: public PlatformCodeStub { |
593 public: | 593 public: |
594 DirectCEntryStub() {} | 594 DirectCEntryStub() {} |
595 void Generate(MacroAssembler* masm); | 595 void Generate(MacroAssembler* masm); |
596 void GenerateCall(MacroAssembler* masm, | 596 void GenerateCall(MacroAssembler* masm, |
597 ExternalReference function); | 597 ExternalReference function); |
598 void GenerateCall(MacroAssembler* masm, Register target); | 598 void GenerateCall(MacroAssembler* masm, Register target); |
599 | 599 |
600 private: | 600 private: |
601 Major MajorKey() { return DirectCEntry; } | 601 Major MajorKey() { return DirectCEntry; } |
602 int MinorKey() { return 0; } | 602 int MinorKey() { return 0; } |
(...skipping 129 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
732 FPURegister dst, | 732 FPURegister dst, |
733 Register dst1, | 733 Register dst1, |
734 Register dst2, | 734 Register dst2, |
735 Register heap_number_map, | 735 Register heap_number_map, |
736 Register scratch1, | 736 Register scratch1, |
737 Register scratch2, | 737 Register scratch2, |
738 Label* not_number); | 738 Label* not_number); |
739 }; | 739 }; |
740 | 740 |
741 | 741 |
742 class StringDictionaryLookupStub: public CodeStub { | 742 class StringDictionaryLookupStub: public PlatformCodeStub { |
743 public: | 743 public: |
744 enum LookupMode { POSITIVE_LOOKUP, NEGATIVE_LOOKUP }; | 744 enum LookupMode { POSITIVE_LOOKUP, NEGATIVE_LOOKUP }; |
745 | 745 |
746 explicit StringDictionaryLookupStub(LookupMode mode) : mode_(mode) { } | 746 explicit StringDictionaryLookupStub(LookupMode mode) : mode_(mode) { } |
747 | 747 |
748 void Generate(MacroAssembler* masm); | 748 void Generate(MacroAssembler* masm); |
749 | 749 |
750 static void GenerateNegativeLookup(MacroAssembler* masm, | 750 static void GenerateNegativeLookup(MacroAssembler* masm, |
751 Label* miss, | 751 Label* miss, |
752 Label* done, | 752 Label* done, |
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
785 | 785 |
786 class LookupModeBits: public BitField<LookupMode, 0, 1> {}; | 786 class LookupModeBits: public BitField<LookupMode, 0, 1> {}; |
787 | 787 |
788 LookupMode mode_; | 788 LookupMode mode_; |
789 }; | 789 }; |
790 | 790 |
791 | 791 |
792 } } // namespace v8::internal | 792 } } // namespace v8::internal |
793 | 793 |
794 #endif // V8_MIPS_CODE_STUBS_ARM_H_ | 794 #endif // V8_MIPS_CODE_STUBS_ARM_H_ |
OLD | NEW |