| 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 330 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  341  private: |  341  private: | 
|  342   int data_; |  342   int data_; | 
|  343  |  343  | 
|  344   class TypeField: public BitField<Type, 0, 2> {}; |  344   class TypeField: public BitField<Type, 0, 2> {}; | 
|  345   class NextField: public BitField<int,  2, 32-2> {}; |  345   class NextField: public BitField<int,  2, 32-2> {}; | 
|  346  |  346  | 
|  347   void init(Label* L, Type type); |  347   void init(Label* L, Type type); | 
|  348 }; |  348 }; | 
|  349  |  349  | 
|  350  |  350  | 
 |  351 class AssemblerData:public BasicAssemblerData { | 
 |  352  public: | 
 |  353   // A previously allocated buffer of kMinimalBufferSize bytes, or NULL. | 
 |  354   byte* spare_buffer_; | 
 |  355   // CPU features | 
 |  356   uint64_t supported_; | 
 |  357   uint64_t enabled_; | 
 |  358   uint64_t found_by_runtime_probing_; | 
 |  359  private: | 
 |  360   AssemblerData() | 
 |  361     :BasicAssemblerData(), | 
 |  362     spare_buffer_(NULL), | 
 |  363     // Safe default is no features. | 
 |  364     supported_(0), | 
 |  365     enabled_(0), | 
 |  366     found_by_runtime_probing_(0) { | 
 |  367   } | 
 |  368   ~AssemblerData() { delete spare_buffer_; } | 
 |  369   friend class Assembler; | 
 |  370   DISALLOW_COPY_AND_ASSIGN(AssemblerData); | 
 |  371 }; | 
|  351  |  372  | 
|  352 // CpuFeatures keeps track of which features are supported by the target CPU. |  373 // CpuFeatures keeps track of which features are supported by the target CPU. | 
|  353 // Supported features must be enabled by a Scope before use. |  374 // Supported features must be enabled by a Scope before use. | 
|  354 // Example: |  375 // Example: | 
|  355 //   if (CpuFeatures::IsSupported(SSE2)) { |  376 //   if (CpuFeatures::IsSupported(SSE2)) { | 
|  356 //     CpuFeatures::Scope fscope(SSE2); |  377 //     CpuFeatures::Scope fscope(SSE2); | 
|  357 //     // Generate SSE2 floating point code. |  378 //     // Generate SSE2 floating point code. | 
|  358 //   } else { |  379 //   } else { | 
|  359 //     // Generate standard x87 floating point code. |  380 //     // Generate standard x87 floating point code. | 
|  360 //   } |  381 //   } | 
|  361 class CpuFeatures : public AllStatic { |  382 class CpuFeatures : public AllStatic { | 
|  362  public: |  383  public: | 
|  363   // Detect features of the target CPU. Set safe defaults if the serializer |  384   // Detect features of the target CPU. Set safe defaults if the serializer | 
|  364   // is enabled (snapshots must be portable). |  385   // is enabled (snapshots must be portable). | 
|  365   static void Probe(); |  386   static void Probe(); | 
|  366   // Check whether a feature is supported by the target CPU. |  387   // Check whether a feature is supported by the target CPU. | 
|  367   static bool IsSupported(CpuFeature f) { |  388   static bool IsSupported(CpuFeature f) { | 
|  368     if (f == SSE2 && !FLAG_enable_sse2) return false; |  389     if (f == SSE2 && !FLAG_enable_sse2) return false; | 
|  369     if (f == SSE3 && !FLAG_enable_sse3) return false; |  390     if (f == SSE3 && !FLAG_enable_sse3) return false; | 
|  370     if (f == CMOV && !FLAG_enable_cmov) return false; |  391     if (f == CMOV && !FLAG_enable_cmov) return false; | 
|  371     if (f == RDTSC && !FLAG_enable_rdtsc) return false; |  392     if (f == RDTSC && !FLAG_enable_rdtsc) return false; | 
|  372     return (supported_ & (static_cast<uint64_t>(1) << f)) != 0; |  393     return (v8_context()->assembler_data_->supported_ & | 
 |  394             (static_cast<uint64_t>(1) << f)) != 0; | 
|  373   } |  395   } | 
|  374   // Check whether a feature is currently enabled. |  396   // Check whether a feature is currently enabled. | 
|  375   static bool IsEnabled(CpuFeature f) { |  397   static bool IsEnabled(CpuFeature f) { | 
|  376     return (enabled_ & (static_cast<uint64_t>(1) << f)) != 0; |  398     return (v8_context()->assembler_data_->enabled_ & | 
 |  399       (static_cast<uint64_t>(1) << f)) != 0; | 
|  377   } |  400   } | 
|  378   // Enable a specified feature within a scope. |  401   // Enable a specified feature within a scope. | 
|  379   class Scope BASE_EMBEDDED { |  402   class Scope BASE_EMBEDDED { | 
|  380 #ifdef DEBUG |  403 #ifdef DEBUG | 
|  381    public: |  404    public: | 
|  382     explicit Scope(CpuFeature f) { |  405     explicit Scope(CpuFeature f) { | 
|  383       uint64_t mask = static_cast<uint64_t>(1) << f; |  406       uint64_t mask = static_cast<uint64_t>(1) << f; | 
|  384       ASSERT(CpuFeatures::IsSupported(f)); |  407       ASSERT(CpuFeatures::IsSupported(f)); | 
|  385       ASSERT(!Serializer::enabled() || (found_by_runtime_probing_ & mask) == 0); |  408       AssemblerData* const data = v8_context()->assembler_data_; | 
|  386       old_enabled_ = CpuFeatures::enabled_; |  409       ASSERT(!Serializer::enabled() || | 
|  387       CpuFeatures::enabled_ |= mask; |  410         (data->found_by_runtime_probing_ & mask) == 0); | 
 |  411       old_enabled_ = data->enabled_; | 
 |  412       data->enabled_ |= mask; | 
|  388     } |  413     } | 
|  389     ~Scope() { CpuFeatures::enabled_ = old_enabled_; } |  414     ~Scope() { v8_context()->assembler_data_->enabled_ = old_enabled_; } | 
|  390    private: |  415    private: | 
|  391     uint64_t old_enabled_; |  416     uint64_t old_enabled_; | 
|  392 #else |  417 #else | 
|  393    public: |  418    public: | 
|  394     explicit Scope(CpuFeature f) {} |  419     explicit Scope(CpuFeature f) {} | 
|  395 #endif |  420 #endif | 
|  396   }; |  421   }; | 
|  397  private: |  | 
|  398   static uint64_t supported_; |  | 
|  399   static uint64_t enabled_; |  | 
|  400   static uint64_t found_by_runtime_probing_; |  | 
|  401 }; |  422 }; | 
|  402  |  423  | 
|  403  |  424  | 
|  404 class Assembler : public Malloced { |  425 class Assembler : public Malloced { | 
|  405  private: |  426  private: | 
|  406   // We check before assembling an instruction that there is sufficient |  427   // We check before assembling an instruction that there is sufficient | 
|  407   // space to write an instruction and its relocation information. |  428   // space to write an instruction and its relocation information. | 
|  408   // The relocation writer's position must be kGap bytes above the end of |  429   // The relocation writer's position must be kGap bytes above the end of | 
|  409   // the generated instructions. This leaves enough space for the |  430   // the generated instructions. This leaves enough space for the | 
|  410   // longest possible ia32 instruction, 15 bytes, and the longest possible |  431   // longest possible ia32 instruction, 15 bytes, and the longest possible | 
| (...skipping 435 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  846  |  867  | 
|  847   friend class CodePatcher; |  868   friend class CodePatcher; | 
|  848   friend class EnsureSpace; |  869   friend class EnsureSpace; | 
|  849  |  870  | 
|  850   // Code buffer: |  871   // Code buffer: | 
|  851   // The buffer into which code and relocation info are generated. |  872   // The buffer into which code and relocation info are generated. | 
|  852   byte* buffer_; |  873   byte* buffer_; | 
|  853   int buffer_size_; |  874   int buffer_size_; | 
|  854   // True if the assembler owns the buffer, false if buffer is external. |  875   // True if the assembler owns the buffer, false if buffer is external. | 
|  855   bool own_buffer_; |  876   bool own_buffer_; | 
|  856   // A previously allocated buffer of kMinimalBufferSize bytes, or NULL. |  | 
|  857   static byte* spare_buffer_; |  | 
|  858  |  877  | 
|  859   // code generation |  878   // code generation | 
|  860   byte* pc_;  // the program counter; moves forward |  879   byte* pc_;  // the program counter; moves forward | 
|  861   RelocInfoWriter reloc_info_writer; |  880   RelocInfoWriter reloc_info_writer; | 
|  862  |  881  | 
|  863   // push-pop elimination |  882   // push-pop elimination | 
|  864   byte* last_pc_; |  883   byte* last_pc_; | 
|  865  |  884  | 
|  866   // source position information |  885   // source position information | 
|  867   int current_statement_position_; |  886   int current_statement_position_; | 
|  868   int current_position_; |  887   int current_position_; | 
|  869   int written_statement_position_; |  888   int written_statement_position_; | 
|  870   int written_position_; |  889   int written_position_; | 
 |  890  | 
 |  891   static void PostConstruct(); | 
 |  892   static void PreDestroy(); | 
 |  893   friend class V8Context; | 
|  871 }; |  894 }; | 
|  872  |  895  | 
|  873  |  896  | 
|  874 // Helper class that ensures that there is enough space for generating |  897 // Helper class that ensures that there is enough space for generating | 
|  875 // instructions and relocation information.  The constructor makes |  898 // instructions and relocation information.  The constructor makes | 
|  876 // sure that there is enough space and (in debug mode) the destructor |  899 // sure that there is enough space and (in debug mode) the destructor | 
|  877 // checks that we did not generate too much. |  900 // checks that we did not generate too much. | 
|  878 class EnsureSpace BASE_EMBEDDED { |  901 class EnsureSpace BASE_EMBEDDED { | 
|  879  public: |  902  public: | 
|  880   explicit EnsureSpace(Assembler* assembler) : assembler_(assembler) { |  903   explicit EnsureSpace(Assembler* assembler) : assembler_(assembler) { | 
| (...skipping 13 matching lines...) Expand all  Loading... | 
|  894  private: |  917  private: | 
|  895   Assembler* assembler_; |  918   Assembler* assembler_; | 
|  896 #ifdef DEBUG |  919 #ifdef DEBUG | 
|  897   int space_before_; |  920   int space_before_; | 
|  898 #endif |  921 #endif | 
|  899 }; |  922 }; | 
|  900  |  923  | 
|  901 } }  // namespace v8::internal |  924 } }  // namespace v8::internal | 
|  902  |  925  | 
|  903 #endif  // V8_IA32_ASSEMBLER_IA32_H_ |  926 #endif  // V8_IA32_ASSEMBLER_IA32_H_ | 
| OLD | NEW |