Home | History | Annotate | Download | only in src
      1 // Copyright 2010 the V8 project authors. All rights reserved.
      2 // Redistribution and use in source and binary forms, with or without
      3 // modification, are permitted provided that the following conditions are
      4 // met:
      5 //
      6 //     * Redistributions of source code must retain the above copyright
      7 //       notice, this list of conditions and the following disclaimer.
      8 //     * Redistributions in binary form must reproduce the above
      9 //       copyright notice, this list of conditions and the following
     10 //       disclaimer in the documentation and/or other materials provided
     11 //       with the distribution.
     12 //     * Neither the name of Google Inc. nor the names of its
     13 //       contributors may be used to endorse or promote products derived
     14 //       from this software without specific prior written permission.
     15 //
     16 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
     17 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
     18 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
     19 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
     20 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
     21 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
     22 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
     23 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
     24 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     25 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
     26 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     27 
     28 #ifndef V8_FACTORY_H_
     29 #define V8_FACTORY_H_
     30 
     31 #include "globals.h"
     32 #include "handles.h"
     33 #include "heap.h"
     34 
     35 namespace v8 {
     36 namespace internal {
     37 
     38 // Interface for handle based allocation.
     39 
     40 class Factory {
     41  public:
     42   // Allocate a new fixed array with undefined entries.
     43   Handle<FixedArray> NewFixedArray(
     44       int size,
     45       PretenureFlag pretenure = NOT_TENURED);
     46 
     47   // Allocate a new fixed array with non-existing entries (the hole).
     48   Handle<FixedArray> NewFixedArrayWithHoles(
     49       int size,
     50       PretenureFlag pretenure = NOT_TENURED);
     51 
     52   Handle<NumberDictionary> NewNumberDictionary(int at_least_space_for);
     53 
     54   Handle<StringDictionary> NewStringDictionary(int at_least_space_for);
     55 
     56   Handle<DescriptorArray> NewDescriptorArray(int number_of_descriptors);
     57   Handle<DeoptimizationInputData> NewDeoptimizationInputData(
     58       int deopt_entry_count,
     59       PretenureFlag pretenure);
     60   Handle<DeoptimizationOutputData> NewDeoptimizationOutputData(
     61       int deopt_entry_count,
     62       PretenureFlag pretenure);
     63 
     64   Handle<String> LookupSymbol(Vector<const char> str);
     65   Handle<String> LookupAsciiSymbol(Vector<const char> str);
     66   Handle<String> LookupTwoByteSymbol(Vector<const uc16> str);
     67   Handle<String> LookupAsciiSymbol(const char* str) {
     68     return LookupSymbol(CStrVector(str));
     69   }
     70 
     71 
     72   // String creation functions.  Most of the string creation functions take
     73   // a Heap::PretenureFlag argument to optionally request that they be
     74   // allocated in the old generation.  The pretenure flag defaults to
     75   // DONT_TENURE.
     76   //
     77   // Creates a new String object.  There are two String encodings: ASCII and
     78   // two byte.  One should choose between the three string factory functions
     79   // based on the encoding of the string buffer that the string is
     80   // initialized from.
     81   //   - ...FromAscii initializes the string from a buffer that is ASCII
     82   //     encoded (it does not check that the buffer is ASCII encoded) and
     83   //     the result will be ASCII encoded.
     84   //   - ...FromUtf8 initializes the string from a buffer that is UTF-8
     85   //     encoded.  If the characters are all single-byte characters, the
     86   //     result will be ASCII encoded, otherwise it will converted to two
     87   //     byte.
     88   //   - ...FromTwoByte initializes the string from a buffer that is two
     89   //     byte encoded.  If the characters are all single-byte characters,
     90   //     the result will be converted to ASCII, otherwise it will be left as
     91   //     two byte.
     92   //
     93   // ASCII strings are pretenured when used as keys in the SourceCodeCache.
     94   Handle<String> NewStringFromAscii(
     95       Vector<const char> str,
     96       PretenureFlag pretenure = NOT_TENURED);
     97 
     98   // UTF8 strings are pretenured when used for regexp literal patterns and
     99   // flags in the parser.
    100   Handle<String> NewStringFromUtf8(
    101       Vector<const char> str,
    102       PretenureFlag pretenure = NOT_TENURED);
    103 
    104   Handle<String> NewStringFromTwoByte(
    105       Vector<const uc16> str,
    106       PretenureFlag pretenure = NOT_TENURED);
    107 
    108   // Allocates and partially initializes an ASCII or TwoByte String. The
    109   // characters of the string are uninitialized. Currently used in regexp code
    110   // only, where they are pretenured.
    111   Handle<String> NewRawAsciiString(
    112       int length,
    113       PretenureFlag pretenure = NOT_TENURED);
    114   Handle<String> NewRawTwoByteString(
    115       int length,
    116       PretenureFlag pretenure = NOT_TENURED);
    117 
    118   // Create a new cons string object which consists of a pair of strings.
    119   Handle<String> NewConsString(Handle<String> first,
    120                                Handle<String> second);
    121 
    122   // Create a new string object which holds a substring of a string.
    123   Handle<String> NewSubString(Handle<String> str,
    124                               int begin,
    125                               int end);
    126 
    127   // Creates a new external String object.  There are two String encodings
    128   // in the system: ASCII and two byte.  Unlike other String types, it does
    129   // not make sense to have a UTF-8 factory function for external strings,
    130   // because we cannot change the underlying buffer.
    131   Handle<String> NewExternalStringFromAscii(
    132       ExternalAsciiString::Resource* resource);
    133   Handle<String> NewExternalStringFromTwoByte(
    134       ExternalTwoByteString::Resource* resource);
    135 
    136   // Create a global (but otherwise uninitialized) context.
    137   Handle<Context> NewGlobalContext();
    138 
    139   // Create a function context.
    140   Handle<Context> NewFunctionContext(int length,
    141                                      Handle<JSFunction> closure);
    142 
    143   // Create a 'with' context.
    144   Handle<Context> NewWithContext(Handle<Context> previous,
    145                                  Handle<JSObject> extension,
    146                                  bool is_catch_context);
    147 
    148   // Return the Symbol matching the passed in string.
    149   Handle<String> SymbolFromString(Handle<String> value);
    150 
    151   // Allocate a new struct.  The struct is pretenured (allocated directly in
    152   // the old generation).
    153   Handle<Struct> NewStruct(InstanceType type);
    154 
    155   Handle<AccessorInfo> NewAccessorInfo();
    156 
    157   Handle<Script> NewScript(Handle<String> source);
    158 
    159   // Proxies are pretenured when allocated by the bootstrapper.
    160   Handle<Proxy> NewProxy(Address addr,
    161                          PretenureFlag pretenure = NOT_TENURED);
    162 
    163   // Allocate a new proxy.  The proxy is pretenured (allocated directly in
    164   // the old generation).
    165   Handle<Proxy> NewProxy(const AccessorDescriptor* proxy);
    166 
    167   Handle<ByteArray> NewByteArray(int length,
    168                                  PretenureFlag pretenure = NOT_TENURED);
    169 
    170   Handle<ExternalArray> NewExternalArray(
    171       int length,
    172       ExternalArrayType array_type,
    173       void* external_pointer,
    174       PretenureFlag pretenure = NOT_TENURED);
    175 
    176   Handle<JSGlobalPropertyCell> NewJSGlobalPropertyCell(
    177       Handle<Object> value);
    178 
    179   Handle<Map> NewMap(InstanceType type, int instance_size);
    180 
    181   Handle<JSObject> NewFunctionPrototype(Handle<JSFunction> function);
    182 
    183   Handle<Map> CopyMapDropDescriptors(Handle<Map> map);
    184 
    185   // Copy the map adding more inobject properties if possible without
    186   // overflowing the instance size.
    187   Handle<Map> CopyMap(Handle<Map> map, int extra_inobject_props);
    188 
    189   Handle<Map> CopyMapDropTransitions(Handle<Map> map);
    190 
    191   Handle<Map> GetFastElementsMap(Handle<Map> map);
    192 
    193   Handle<Map> GetSlowElementsMap(Handle<Map> map);
    194 
    195   Handle<Map> GetExternalArrayElementsMap(Handle<Map> map,
    196                                           ExternalArrayType array_type,
    197                                           bool safe_to_add_transition);
    198 
    199   Handle<FixedArray> CopyFixedArray(Handle<FixedArray> array);
    200 
    201   // Numbers (eg, literals) are pretenured by the parser.
    202   Handle<Object> NewNumber(double value,
    203                            PretenureFlag pretenure = NOT_TENURED);
    204 
    205   Handle<Object> NewNumberFromInt(int value);
    206   Handle<Object> NewNumberFromUint(uint32_t value);
    207 
    208   // These objects are used by the api to create env-independent data
    209   // structures in the heap.
    210   Handle<JSObject> NewNeanderObject();
    211 
    212   Handle<JSObject> NewArgumentsObject(Handle<Object> callee, int length);
    213 
    214   // JS objects are pretenured when allocated by the bootstrapper and
    215   // runtime.
    216   Handle<JSObject> NewJSObject(Handle<JSFunction> constructor,
    217                                PretenureFlag pretenure = NOT_TENURED);
    218 
    219   // Global objects are pretenured.
    220   Handle<GlobalObject> NewGlobalObject(Handle<JSFunction> constructor);
    221 
    222   // JS objects are pretenured when allocated by the bootstrapper and
    223   // runtime.
    224   Handle<JSObject> NewJSObjectFromMap(Handle<Map> map);
    225 
    226   // JS arrays are pretenured when allocated by the parser.
    227   Handle<JSArray> NewJSArray(int capacity,
    228                              PretenureFlag pretenure = NOT_TENURED);
    229 
    230   Handle<JSArray> NewJSArrayWithElements(
    231       Handle<FixedArray> elements,
    232       PretenureFlag pretenure = NOT_TENURED);
    233 
    234   Handle<JSFunction> NewFunction(Handle<String> name,
    235                                  Handle<Object> prototype);
    236 
    237   Handle<JSFunction> NewFunctionWithoutPrototype(
    238       Handle<String> name,
    239       StrictModeFlag strict_mode);
    240 
    241   Handle<JSFunction> NewFunction(Handle<Object> super, bool is_global);
    242 
    243   Handle<JSFunction> BaseNewFunctionFromSharedFunctionInfo(
    244       Handle<SharedFunctionInfo> function_info,
    245       Handle<Map> function_map,
    246       PretenureFlag pretenure);
    247 
    248   Handle<JSFunction> NewFunctionFromSharedFunctionInfo(
    249       Handle<SharedFunctionInfo> function_info,
    250       Handle<Context> context,
    251       PretenureFlag pretenure = TENURED);
    252 
    253   Handle<Code> NewCode(const CodeDesc& desc,
    254                        Code::Flags flags,
    255                        Handle<Object> self_reference,
    256                        bool immovable = false);
    257 
    258   Handle<Code> CopyCode(Handle<Code> code);
    259 
    260   Handle<Code> CopyCode(Handle<Code> code, Vector<byte> reloc_info);
    261 
    262   Handle<Object> ToObject(Handle<Object> object);
    263   Handle<Object> ToObject(Handle<Object> object,
    264                           Handle<Context> global_context);
    265 
    266   // Interface for creating error objects.
    267 
    268   Handle<Object> NewError(const char* maker, const char* type,
    269                           Handle<JSArray> args);
    270   Handle<Object> NewError(const char* maker, const char* type,
    271                           Vector< Handle<Object> > args);
    272   Handle<Object> NewError(const char* type,
    273                           Vector< Handle<Object> > args);
    274   Handle<Object> NewError(Handle<String> message);
    275   Handle<Object> NewError(const char* constructor,
    276                           Handle<String> message);
    277 
    278   Handle<Object> NewTypeError(const char* type,
    279                               Vector< Handle<Object> > args);
    280   Handle<Object> NewTypeError(Handle<String> message);
    281 
    282   Handle<Object> NewRangeError(const char* type,
    283                                Vector< Handle<Object> > args);
    284   Handle<Object> NewRangeError(Handle<String> message);
    285 
    286   Handle<Object> NewSyntaxError(const char* type, Handle<JSArray> args);
    287   Handle<Object> NewSyntaxError(Handle<String> message);
    288 
    289   Handle<Object> NewReferenceError(const char* type,
    290                                    Vector< Handle<Object> > args);
    291   Handle<Object> NewReferenceError(Handle<String> message);
    292 
    293   Handle<Object> NewEvalError(const char* type,
    294                               Vector< Handle<Object> > args);
    295 
    296 
    297   Handle<JSFunction> NewFunction(Handle<String> name,
    298                                  InstanceType type,
    299                                  int instance_size,
    300                                  Handle<Code> code,
    301                                  bool force_initial_map);
    302 
    303   Handle<JSFunction> NewFunction(Handle<Map> function_map,
    304       Handle<SharedFunctionInfo> shared, Handle<Object> prototype);
    305 
    306 
    307   Handle<JSFunction> NewFunctionWithPrototype(Handle<String> name,
    308                                               InstanceType type,
    309                                               int instance_size,
    310                                               Handle<JSObject> prototype,
    311                                               Handle<Code> code,
    312                                               bool force_initial_map);
    313 
    314   Handle<JSFunction> NewFunctionWithoutPrototype(Handle<String> name,
    315                                                  Handle<Code> code);
    316 
    317   Handle<DescriptorArray> CopyAppendProxyDescriptor(
    318       Handle<DescriptorArray> array,
    319       Handle<String> key,
    320       Handle<Object> value,
    321       PropertyAttributes attributes);
    322 
    323   Handle<String> NumberToString(Handle<Object> number);
    324 
    325   enum ApiInstanceType {
    326     JavaScriptObject,
    327     InnerGlobalObject,
    328     OuterGlobalObject
    329   };
    330 
    331   Handle<JSFunction> CreateApiFunction(
    332       Handle<FunctionTemplateInfo> data,
    333       ApiInstanceType type = JavaScriptObject);
    334 
    335   Handle<JSFunction> InstallMembers(Handle<JSFunction> function);
    336 
    337   // Installs interceptors on the instance.  'desc' is a function template,
    338   // and instance is an object instance created by the function of this
    339   // function template.
    340   void ConfigureInstance(Handle<FunctionTemplateInfo> desc,
    341                          Handle<JSObject> instance,
    342                          bool* pending_exception);
    343 
    344 #define ROOT_ACCESSOR(type, name, camel_name)                                  \
    345   inline Handle<type> name() {                                                 \
    346     return Handle<type>(BitCast<type**>(                                       \
    347         &isolate()->heap()->roots_[Heap::k##camel_name##RootIndex]));          \
    348   }
    349   ROOT_LIST(ROOT_ACCESSOR)
    350 #undef ROOT_ACCESSOR_ACCESSOR
    351 
    352 #define SYMBOL_ACCESSOR(name, str)                                             \
    353   inline Handle<String> name() {                                               \
    354     return Handle<String>(BitCast<String**>(                                   \
    355         &isolate()->heap()->roots_[Heap::k##name##RootIndex]));                \
    356   }
    357   SYMBOL_LIST(SYMBOL_ACCESSOR)
    358 #undef SYMBOL_ACCESSOR
    359 
    360   Handle<String> hidden_symbol() {
    361     return Handle<String>(&isolate()->heap()->hidden_symbol_);
    362   }
    363 
    364   Handle<SharedFunctionInfo> NewSharedFunctionInfo(
    365       Handle<String> name,
    366       int number_of_literals,
    367       Handle<Code> code,
    368       Handle<SerializedScopeInfo> scope_info);
    369   Handle<SharedFunctionInfo> NewSharedFunctionInfo(Handle<String> name);
    370 
    371   Handle<JSMessageObject> NewJSMessageObject(
    372       Handle<String> type,
    373       Handle<JSArray> arguments,
    374       int start_position,
    375       int end_position,
    376       Handle<Object> script,
    377       Handle<Object> stack_trace,
    378       Handle<Object> stack_frames);
    379 
    380   Handle<NumberDictionary> DictionaryAtNumberPut(
    381       Handle<NumberDictionary>,
    382       uint32_t key,
    383       Handle<Object> value);
    384 
    385 #ifdef ENABLE_DEBUGGER_SUPPORT
    386   Handle<DebugInfo> NewDebugInfo(Handle<SharedFunctionInfo> shared);
    387 #endif
    388 
    389   // Return a map using the map cache in the global context.
    390   // The key the an ordered set of property names.
    391   Handle<Map> ObjectLiteralMapFromCache(Handle<Context> context,
    392                                         Handle<FixedArray> keys);
    393 
    394   // Creates a new FixedArray that holds the data associated with the
    395   // atom regexp and stores it in the regexp.
    396   void SetRegExpAtomData(Handle<JSRegExp> regexp,
    397                          JSRegExp::Type type,
    398                          Handle<String> source,
    399                          JSRegExp::Flags flags,
    400                          Handle<Object> match_pattern);
    401 
    402   // Creates a new FixedArray that holds the data associated with the
    403   // irregexp regexp and stores it in the regexp.
    404   void SetRegExpIrregexpData(Handle<JSRegExp> regexp,
    405                              JSRegExp::Type type,
    406                              Handle<String> source,
    407                              JSRegExp::Flags flags,
    408                              int capture_count);
    409 
    410  private:
    411   Isolate* isolate() { return reinterpret_cast<Isolate*>(this); }
    412 
    413   Handle<JSFunction> NewFunctionHelper(Handle<String> name,
    414                                        Handle<Object> prototype);
    415 
    416   Handle<JSFunction> NewFunctionWithoutPrototypeHelper(
    417       Handle<String> name,
    418       StrictModeFlag strict_mode);
    419 
    420   Handle<DescriptorArray> CopyAppendCallbackDescriptors(
    421       Handle<DescriptorArray> array,
    422       Handle<Object> descriptors);
    423 
    424   // Create a new map cache.
    425   Handle<MapCache> NewMapCache(int at_least_space_for);
    426 
    427   // Update the map cache in the global context with (keys, map)
    428   Handle<MapCache> AddToMapCache(Handle<Context> context,
    429                                  Handle<FixedArray> keys,
    430                                  Handle<Map> map);
    431 };
    432 
    433 
    434 } }  // namespace v8::internal
    435 
    436 #endif  // V8_FACTORY_H_
    437