private static Completion Parse(IValue thisObj, IReadOnlyList <IValue> arguments) { var argComp = arguments.At(0); if (argComp.IsAbrupt()) { return(argComp); } var dateComp = argComp.value !.ToJsString(); if (dateComp.IsAbrupt()) { return(dateComp); } var date = (dateComp.value as StringValue) !.@string; if (!DateTime.TryParseExact(date, DefaultFormats, CultureInfo.InvariantCulture, DateTimeStyles.AdjustToUniversal | DateTimeStyles.AssumeUniversal, out var result)) { if (!DateTime.TryParseExact(date, SecondaryFormats, CultureInfo.InvariantCulture, DateTimeStyles.AdjustToUniversal, out result)) { if (!DateTime.TryParse(date, Interpreter.Instance().Culture, DateTimeStyles.AdjustToUniversal, out result)) { if (!DateTime.TryParse(date, CultureInfo.InvariantCulture, DateTimeStyles.AdjustToUniversal, out result)) { // unrecognized dates should return NaN (15.9.4.2) return(Completion.NormalCompletion(NumberValue.DoubleNaN)); } } } } return(Completion.NormalCompletion(new NumberValue(FromDateTime(result)))); }
private static Completion getOwnPropertyDescriptor(IValue @this, IReadOnlyList <IValue> arguments) { var argCheck = Utils.CheckArguments(arguments, 2); if (argCheck.IsAbrupt()) { return(argCheck); } var obj = arguments[0].ToObject(); if (obj.IsAbrupt()) { return(obj); } var key = arguments[1].ToPropertyKey(); if (key.IsAbrupt()) { return(key); } var desc = (obj.value as Object) !.GetOwnProperty(key.Other !); if (desc.IsAbrupt()) { return(desc); } return(Completion.NormalCompletion(desc.Other?.ToObject() as IValue ?? UndefinedValue.Instance)); }
public static Completion CopyDataProperties(Object target, IValue source, IReadOnlyList <string> excludedItems) { if (source is UndefinedValue || source is NullValue) { return(Completion.NormalCompletion(target)); } var from = (source.ToObject().value as Object) !; IReadOnlyList <string> keys = from.OwnPropertyKeys(); foreach (var nextKey in keys) { var excluded = excludedItems.Contains(nextKey); if (!excluded) { var descComp = from.GetOwnProperty(nextKey); if (descComp.IsAbrupt()) { return(descComp); } var desc = descComp.Other; if (desc != null && desc.Enumerable.HasValue && desc.Enumerable.Value) { var propValue = from.Get(nextKey); if (propValue.IsAbrupt()) { return(propValue); } CreateDataProperty(target, nextKey, propValue.value !); } } } return(Completion.NormalCompletion(target)); }
private static Completion charAt(IValue thisValue, IReadOnlyList <IValue> arguments) { var O = thisValue.RequireObjectCoercible(); if (O.IsAbrupt()) { return(O); } var sComp = O.value !.ToJsString(); if (sComp.IsAbrupt()) { return(sComp); } var S = (sComp.value as StringValue) !.@string; var pos = arguments.At(0, UndefinedValue.Instance); var positionComp = pos.ToInteger(); if (positionComp.IsAbrupt()) { return(positionComp); } var position = positionComp.Other; var size = S.Length; if (position < 0 || position >= size) { return(Completion.NormalCompletion(StringValue.Empty)); } return(Completion.NormalCompletion(new StringValue(S.Substring(position, 1)))); }
public override Completion InternalCall(IValue @this, IReadOnlyList <IValue> arguments) { if (FunctionKind == FunctionKind.ClassConstructor) { throw new InvalidOperationException("FunctionObject.Call: Spec 9.2.1 step 2"); } var callerContext = Interpreter.Instance().RunningExecutionContext(); var calleeContext = PrepareForOrdinaryCall(UndefinedValue.Instance); if (Interpreter.Instance().RunningExecutionContext() != calleeContext) { throw new InvalidOperationException("FunctionObject.Call: FunctionObject.PrepareForOrdinaryCall did not perform as expected."); } OrdinaryCallBindThis(calleeContext, @this); var result = OrdinaryCallEvaluateBody(arguments); Interpreter.Instance().PopExecutionStack(calleeContext); if (callerContext != Interpreter.Instance().RunningExecutionContext()) { throw new InvalidOperationException("Interpreter.PopExecutionStack did not perform as expected."); } if (result.completionType == CompletionType.Return) { return(Completion.NormalCompletion(result.value)); } if (result.IsAbrupt()) { return(result); } return(Completion.NormalCompletion(UndefinedValue.Instance)); }
public Completion CreateGlobalVarBinding(string n, bool d) { var hasProperty = ObjectRecord.BindingObject.HasOwnProperty(n); if (hasProperty.IsAbrupt()) { return(hasProperty); } var extensible = ObjectRecord.BindingObject.IsExtensible; if (hasProperty.Other == false && extensible == true) { var comp = ObjectRecord.CreateMutableBinding(n, d); if (comp.IsAbrupt()) { return(comp); } comp = ObjectRecord.InitializeBinding(n, UndefinedValue.Instance); if (comp.IsAbrupt()) { return(comp); } } if (!VarNames.Contains(n)) { VarNames.Add(n); } return(Completion.NormalCompletion()); }
public override Completion InternalConstruct(IReadOnlyList <IValue> arguments, Object?newTarget) { if (arguments.Count == 0) { return(Completion.NormalCompletion(Utils.ObjectCreate(Interpreter.Instance().CurrentRealm().Intrinsics.ObjectPrototype))); } return(InternalCall(this, arguments)); }
public static Completion At(this IReadOnlyList <IValue> arguments, int index) { if (arguments.Count <= index) { return(Completion.ThrowTypeError($"At least {index + 1} arguments are required")); } return(Completion.NormalCompletion(arguments[index])); }
private Completion OrdinaryCallEvaluateBody(IReadOnlyList <IValue> arguments) { if (Code != null) { return(Code.EvaluateBody(this, arguments)); } return(Completion.NormalCompletion()); }
public override Completion InternalCall(IValue thisValue, IReadOnlyList <IValue> arguments) { if (arguments.Count == 0) { return(Completion.NormalCompletion(NumberValue.PositiveZero)); } return(arguments[0].ToNumber()); }
public override Completion CreateMutableBinding(string name, bool deletable) { if (bindings.ContainsKey(name)) { throw new InvalidOperationException("Spec 8.1.1.1.2 step 2"); } bindings.Add(name, BindingRecord.Mutable(canDelete: deletable)); return(Completion.NormalCompletion()); }
public override Completion CreateImmutableBinding(string name, bool strict) { if (bindings.ContainsKey(name)) { throw new InvalidOperationException("Spec 8.1.1.1.3 step 2"); } bindings.Add(name, BindingRecord.Immutable(strict: strict)); return(Completion.NormalCompletion()); }
public override Completion InitializeBinding(string name, IValue value) { if (!bindings.ContainsKey(name) || bindings[name].Value != null) { throw new InvalidOperationException("Spec 8.1.1.1.4 step 2"); } bindings[name].Value = value; return(Completion.NormalCompletion()); }
public override Completion InternalConstruct(IReadOnlyList <IValue> arguments, Object?newTarget) { var callerContext = Interpreter.Instance().RunningExecutionContext(); IValue?thisArgument = null; if (ConstructorKind == ConstructorKind.Base) { var thisComp = Utils.OrdinaryCreateFromConstructor(newTarget, i => i.ObjectPrototype); if (thisComp.IsAbrupt()) { return(thisComp); } thisArgument = thisComp.value; } ExecutionContext calleeContext = PrepareForOrdinaryCall(newTarget); if (calleeContext != Interpreter.Instance().RunningExecutionContext()) { throw new InvalidOperationException("FunctionObject.PrepareForOrdinaryCall did not perform as expected."); } if (ConstructorKind == ConstructorKind.Base) { OrdinaryCallBindThis(calleeContext, thisArgument); } var constructorEnv = calleeContext.LexicalEnvironment; var envRec = (constructorEnv.EnvironmentRecord as FunctionEnvironmentRecord) !; var result = OrdinaryCallEvaluateBody(arguments); Interpreter.Instance().PopExecutionStack(calleeContext); if (callerContext != Interpreter.Instance().RunningExecutionContext()) { throw new InvalidOperationException("Interpreter.PopExecutionStack did not perform as expected."); } if (result.completionType == CompletionType.Return) { if (result.value is Object) { return(Completion.NormalCompletion(result.value)); } if (ConstructorKind == ConstructorKind.Base) { return(Completion.NormalCompletion(thisArgument)); } if (!(result.value is UndefinedValue)) { throw new InvalidCastException("FunctionObject.InternalConstruct: Spec 9.2.2 step 13c"); } } else if (result.IsAbrupt()) { return(result); } return(envRec.GetThisBinding()); }
public Completion GetSuperBase() { if (HomeObject == UndefinedValue.Instance) { return(Completion.NormalCompletion(UndefinedValue.Instance)); } if (!(HomeObject is Object o)) { throw new InvalidOperationException("Spec 8.1.1.3.5 step 4"); } return(o.GetPrototypeOf()); }
public Completion GetThisBinding() { if (ThisBindingStatus == ThisBindingStatus.Lexical) { throw new InvalidOperationException("Spec 8.1.1.3.4 step 2"); } if (ThisBindingStatus == ThisBindingStatus.Uninitialized) { return(Completion.ThrowReferenceError("'this' value is not initialized")); } return(Completion.NormalCompletion(ThisValue)); }
public static Completion toString(IValue @this, IReadOnlyList <IValue> arguments) { if (@this is StringValue) { return(Completion.NormalCompletion(@this)); } if (@this is StringObject s) { return(Completion.NormalCompletion(s.value)); } return(Completion.ThrowTypeError("Must be called on a string")); }
public override Completion GetBindingValue(string name, bool strict) { if (!bindings.ContainsKey(name)) { throw new InvalidOperationException("Spec 8.1.1.1.6 step 2"); } if (bindings[name].Value == null) { return(Completion.ThrowReferenceError($"binding {name} does not exist.")); } return(Completion.NormalCompletion(bindings[name].Value)); }
public override Completion InternalConstruct(IReadOnlyList <IValue> arguments, Object?newTarget) { var booleanLiteral = InternalCall(UndefinedValue.Instance, arguments); if (booleanLiteral.IsAbrupt()) { return(booleanLiteral); } var O = new BooleanObject((booleanLiteral.value as BooleanValue) !); return(Completion.NormalCompletion(O)); }
public static Completion valueOf(IValue @this, IReadOnlyList <IValue> arguments) { if (!(@this is DateObject d)) { return(Completion.ThrowTypeError("this is not a Date object")); } if (double.IsNaN(d.PrimitiveValue)) { return(Completion.NormalCompletion(new StringValue("Invalid Date"))); } return(Completion.NormalCompletion(new NumberValue(d.PrimitiveValue))); }
internal static Completion OrdinaryCreateFromConstructor(Object?constructor, Func <Intrinsics, Object> intrinsicDefaultProto) { var protoComp = GetPrototypeFromConstructor(constructor, intrinsicDefaultProto); if (protoComp.IsAbrupt()) { return(protoComp); } var proto = protoComp.value !; return(Completion.NormalCompletion(ObjectCreate(proto))); }
public static Completion getTimeZoneOffset(IValue @this, IReadOnlyList <IValue> arguments) { if (!(@this is DateObject d)) { return(Completion.ThrowTypeError("this is not a Date object")); } var t = d.PrimitiveValue; if (!IsFinite(t)) { return(Completion.NormalCompletion(NumberValue.DoubleNaN)); } return(Completion.NormalCompletion(new NumberValue((int)(t - LocalTime(t)) / MsPerMinute))); }
public static Completion getMonth(IValue @this, IReadOnlyList <IValue> arguments) { if (!(@this is DateObject d)) { return(Completion.ThrowTypeError("this is not a Date object")); } var t = d.PrimitiveValue; if (!IsFinite(t)) { return(Completion.NormalCompletion(NumberValue.DoubleNaN)); } return(Completion.NormalCompletion(new NumberValue(MonthFromTime(LocalTime(t))))); }
public Completion BindThisValue(IValue value) { if (ThisBindingStatus == ThisBindingStatus.Lexical) { throw new InvalidOperationException("FunctionEnvironmentRecord.BindThisValue: ThisBindingStatus must not be Lexical"); } if (ThisBindingStatus == ThisBindingStatus.Initialized) { return(Completion.ThrowReferenceError("'this' value is already initialized")); } ThisValue = value; ThisBindingStatus = ThisBindingStatus.Initialized; return(Completion.NormalCompletion(value)); }
private static Completion isNaN(IValue thisValue, IReadOnlyList <IValue> arguments) { var number = arguments.At(0, UndefinedValue.Instance); if (!(number is NumberValue n)) { return(Completion.NormalCompletion(BooleanValue.False)); } if (double.IsNaN(n.number)) { return(Completion.NormalCompletion(BooleanValue.True)); } return(Completion.NormalCompletion(BooleanValue.False)); }
public Completion ResolveThisBinding() { var env = GetThisEnvironment(); if (env is FunctionEnvironmentRecord functionEnvironmentRecord) { return(functionEnvironmentRecord.GetThisBinding()); } if (env is GlobalEnvironmentRecord globalEnvironmentRecord) { return(Completion.NormalCompletion(globalEnvironmentRecord.GetThisBinding())); } throw new InvalidOperationException("env has no This Binding"); }
private static Completion ObjectDefineProperties(Object O, IValue Properties) { var propsComp = Properties.ToObject(); if (propsComp.IsAbrupt()) { return(propsComp); } var props = propsComp.value as Object; var keys = props !.OwnPropertyKeys(); var descriptors = new List <(string, PropertyDescriptor)>(); foreach (var nextKey in keys) { var propDesc = props.GetOwnProperty(nextKey); if (propDesc.IsAbrupt()) { return(propDesc); } if (propDesc.Other != null && propDesc.Other.Enumerable.GetValueOrDefault() == true) { var descObj = props.Get(nextKey); if (descObj.IsAbrupt()) { return(descObj); } if (!(descObj.value is Object o)) { return(Completion.ThrowTypeError("properties of the property argument must be objects.")); } var desc = PropertyDescriptor.FromObject(o); if (desc.IsAbrupt()) { return(desc); } descriptors.Add((nextKey, desc.Other !)); } } foreach (var(P, desc) in descriptors) { var comp = O.DefinePropertyOrThrow(P, desc); if (comp.IsAbrupt()) { return(comp); } } return(Completion.NormalCompletion(O)); }
private Completion InitializeHostDefinedRealm() { var realm = JSInterpreter.Realm.CreateRealm(); var newContext = new ExecutionContext(realm); PushExecutionStack(newContext); realm.SetRealmGlobalObject(null, null); Completion globalObj = realm.SetDefaultGlobalBindings(); if (globalObj.IsAbrupt()) { return(globalObj); } // implementation-defined global object properties return(Completion.NormalCompletion()); }
public override Completion InternalCall(IValue thisValue, IReadOnlyList <IValue> arguments) { if (arguments.Count == 0) { return(Completion.NormalCompletion(StringValue.Empty)); } var arg = arguments[0].ToJsString(); if (arg.IsAbrupt()) { return(arg); } return(Completion.NormalCompletion(arg.value)); }
private static Completion source(IValue thisValue, IReadOnlyList <IValue> arguments) { if (!(thisValue is Object)) { return(Completion.ThrowTypeError("Not valid RegExp object")); } if (!(thisValue is RegExpObject o)) { if (thisValue == Interpreter.Instance().CurrentRealm().Intrinsics.RegExpPrototype) { return(Completion.NormalCompletion(new StringValue("(?:)"))); } return(Completion.ThrowTypeError("Not valid RegExp object")); } return(Completion.NormalCompletion(new StringValue(EscapeRegExpPattern(o.OriginalSource)))); }