1// Copyright 2006-2008 the V8 project authors. All rights reserved. 2// Use of this source code is governed by a BSD-style license that can be 3// found in the LICENSE file. 4 5"use strict"; 6 7// This file contains infrastructure used by the API. See 8// v8natives.js for an explanation of these files are processed and 9// loaded. 10 11 12function CreateDate(time) { 13 var date = new $Date(); 14 date.setTime(time); 15 return date; 16} 17 18 19var kApiFunctionCache = new InternalArray(); 20var functionCache = kApiFunctionCache; 21 22 23function Instantiate(data, name) { 24 if (!%IsTemplate(data)) return data; 25 var tag = %GetTemplateField(data, kApiTagOffset); 26 switch (tag) { 27 case kFunctionTag: 28 return InstantiateFunction(data, name); 29 case kNewObjectTag: 30 var Constructor = %GetTemplateField(data, kApiConstructorOffset); 31 // Note: Do not directly use a function template as a condition, our 32 // internal ToBoolean doesn't handle that! 33 var result = typeof Constructor === 'undefined' ? 34 {} : new (Instantiate(Constructor))(); 35 ConfigureTemplateInstance(result, data); 36 result = %ToFastProperties(result); 37 return result; 38 default: 39 throw 'Unknown API tag <' + tag + '>'; 40 } 41} 42 43 44function InstantiateFunction(data, name) { 45 // We need a reference to kApiFunctionCache in the stack frame 46 // if we need to bail out from a stack overflow. 47 var cache = kApiFunctionCache; 48 var serialNumber = %GetTemplateField(data, kApiSerialNumberOffset); 49 var isFunctionCached = 50 (serialNumber in cache) && (cache[serialNumber] != kUninitialized); 51 if (!isFunctionCached) { 52 try { 53 var flags = %GetTemplateField(data, kApiFlagOffset); 54 var prototype; 55 if (!(flags & (1 << kRemovePrototypeBit))) { 56 var template = %GetTemplateField(data, kApiPrototypeTemplateOffset); 57 prototype = typeof template === 'undefined' 58 ? {} : Instantiate(template); 59 60 var parent = %GetTemplateField(data, kApiParentTemplateOffset); 61 // Note: Do not directly use a function template as a condition, our 62 // internal ToBoolean doesn't handle that! 63 if (typeof parent !== 'undefined') { 64 var parent_fun = Instantiate(parent); 65 %SetPrototype(prototype, parent_fun.prototype); 66 } 67 } 68 var fun = %CreateApiFunction(data, prototype); 69 if (name) %FunctionSetName(fun, name); 70 var doNotCache = flags & (1 << kDoNotCacheBit); 71 if (!doNotCache) cache[serialNumber] = fun; 72 ConfigureTemplateInstance(fun, data); 73 if (doNotCache) return fun; 74 } catch (e) { 75 cache[serialNumber] = kUninitialized; 76 throw e; 77 } 78 } 79 return cache[serialNumber]; 80} 81 82 83function ConfigureTemplateInstance(obj, data) { 84 var properties = %GetTemplateField(data, kApiPropertyListOffset); 85 if (!properties) return; 86 // Disable access checks while instantiating the object. 87 var requires_access_checks = %DisableAccessChecks(obj); 88 try { 89 for (var i = 1; i < properties[0];) { 90 var length = properties[i]; 91 if (length == 3) { 92 var name = properties[i + 1]; 93 var prop_data = properties[i + 2]; 94 var attributes = properties[i + 3]; 95 var value = Instantiate(prop_data, name); 96 %SetProperty(obj, name, value, attributes); 97 } else if (length == 5) { 98 var name = properties[i + 1]; 99 var getter = properties[i + 2]; 100 var setter = properties[i + 3]; 101 var attribute = properties[i + 4]; 102 var access_control = properties[i + 5]; 103 %SetAccessorProperty( 104 obj, name, getter, setter, attribute, access_control); 105 } else { 106 throw "Bad properties array"; 107 } 108 i += length + 1; 109 } 110 } finally { 111 if (requires_access_checks) %EnableAccessChecks(obj); 112 } 113} 114