Przeglądaj źródła

Backport make EsprimaExtensions.TryGetKey more resilient to missing execution context (#1919)

Co-authored-by: Thrasha <[email protected]>
Marko Lahma 1 rok temu
rodzic
commit
91c2cd4ccc

+ 14 - 0
Jint.Tests/Runtime/EvaluationContextTests.cs

@@ -0,0 +1,14 @@
+namespace Jint.Tests.Runtime;
+
+public class EvaluationContextTests
+{
+    [Fact]
+    public void ShouldThrowJavaScriptException()
+    {
+        var mockedEngine = new Engine();
+
+        Expression expression = new Identifier(NodeType.MemberExpression.ToString());
+
+        Assert.Throws<Jint.Runtime.JavaScriptException>(() => AstExtensions.TryGetComputedPropertyKey(expression, mockedEngine));
+    }
+}

+ 2 - 2
Jint/AstExtensions.cs

@@ -58,7 +58,7 @@ namespace Jint
             return key;
         }
 
-        private static JsValue TryGetComputedPropertyKey<T>(T expression, Engine engine)
+        internal static JsValue TryGetComputedPropertyKey<T>(T expression, Engine engine)
             where T : Expression
         {
             if (expression.Type is NodeType.Identifier
@@ -75,7 +75,7 @@ namespace Jint
                 or NodeType.YieldExpression
                 or NodeType.TemplateLiteral)
             {
-                var context = engine._activeEvaluationContext;
+                var context = engine._activeEvaluationContext ?? new EvaluationContext(engine);
                 return JintExpression.Build(expression).GetValue(context!);
             }
 

+ 3 - 3
Jint/Engine.cs

@@ -61,7 +61,7 @@ namespace Jint
         internal readonly Dictionary<string, Type?> TypeCache = new(StringComparer.Ordinal);
 
         // we use registered type reference as prototype if it's known
-        internal Dictionary<Type,TypeReference>? _typeReferences;
+        internal Dictionary<Type, TypeReference>? _typeReferences;
 
         // cache for already wrapped CLR objects to keep object identity
         internal ConditionalWeakTable<object, ObjectInstance>? _objectWrapperCache;
@@ -462,7 +462,7 @@ namespace Jint
                 // TODO what about callstack and thrown exceptions?
                 RunAvailableContinuations();
 
-               return this;
+                return this;
             }
             finally
             {
@@ -1258,7 +1258,7 @@ namespace Jint
             {
                 foreach (var name in pointer.Names)
                 {
-                    privateIdentifiers??= new HashSet<PrivateIdentifier>(PrivateIdentifierNameComparer._instance);
+                    privateIdentifiers ??= new HashSet<PrivateIdentifier>(PrivateIdentifierNameComparer._instance);
                     privateIdentifiers.Add(name.Key);
                 }
 

+ 4 - 1
Jint/Native/Function/EvalFunction.cs

@@ -1,6 +1,7 @@
 using Jint.Runtime;
 using Jint.Runtime.Descriptors;
 using Jint.Runtime.Environments;
+using Jint.Runtime.Interpreter;
 using Jint.Runtime.Interpreter.Statements;
 using Environment = Jint.Runtime.Environments.Environment;
 
@@ -172,7 +173,9 @@ public sealed class EvalFunction : Function
                 Engine.EvalDeclarationInstantiation(script, varEnv, lexEnv, privateEnv, strictEval);
 
                 var statement = new JintScript(script);
-                var result = statement.Execute(_engine._activeEvaluationContext!);
+                var context = _engine._activeEvaluationContext ?? new EvaluationContext(_engine);
+                var result = statement.Execute(context);
+
                 var value = result.GetValueOrDefault();
 
                 if (result.Type == CompletionType.Throw)

+ 1 - 1
Jint/Runtime/Interpreter/Expressions/JintExpression.cs

@@ -132,7 +132,7 @@ namespace Jint.Runtime.Interpreter.Expressions
                     : new JintMemberExpression((MemberExpression) ((ChainExpression) expression).Expression),
                 NodeType.AwaitExpression => new JintAwaitExpression((AwaitExpression) expression),
                 NodeType.YieldExpression => new JintYieldExpression((YieldExpression) expression),
-                _ =>  null
+                _ => null
             };
 
             if (result is null)