JintLiteralExpression.cs 2.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475
  1. using System;
  2. using Esprima;
  3. using Esprima.Ast;
  4. using Jint.Native;
  5. namespace Jint.Runtime.Interpreter.Expressions
  6. {
  7. internal class JintLiteralExpression : JintExpression
  8. {
  9. private JintLiteralExpression(Engine engine, Literal expression) : base(engine, expression)
  10. {
  11. }
  12. internal static JintExpression Build(Engine engine, Literal expression)
  13. {
  14. var constantValue = ConvertToJsValue(expression);
  15. if (!(constantValue is null))
  16. {
  17. return new JintConstantExpression(engine, expression, constantValue);
  18. }
  19. return new JintLiteralExpression(engine, expression);
  20. }
  21. internal static JsValue ConvertToJsValue(Literal literal)
  22. {
  23. if (literal.TokenType == TokenType.BooleanLiteral)
  24. {
  25. return literal.NumericValue > 0.0 ? JsBoolean.True : JsBoolean.False;
  26. }
  27. if (literal.TokenType == TokenType.NullLiteral)
  28. {
  29. return JsValue.Null;
  30. }
  31. if (literal.TokenType == TokenType.NumericLiteral)
  32. {
  33. var intValue = (int) literal.NumericValue;
  34. return literal.NumericValue == intValue
  35. && (intValue != 0 || BitConverter.DoubleToInt64Bits(literal.NumericValue) != JsNumber.NegativeZeroBits)
  36. ? JsNumber.Create(intValue)
  37. : JsNumber.Create(literal.NumericValue);
  38. }
  39. if (literal.TokenType == TokenType.StringLiteral)
  40. {
  41. return JsString.Create((string) literal.Value);
  42. }
  43. return null;
  44. }
  45. public override JsValue GetValue()
  46. {
  47. // need to notify correct node when taking shortcut
  48. _engine._lastSyntaxNode = _expression;
  49. return ResolveValue();
  50. }
  51. protected override object EvaluateInternal() => ResolveValue();
  52. private JsValue ResolveValue()
  53. {
  54. var expression = (Literal) _expression;
  55. if (expression.TokenType == TokenType.RegularExpression)
  56. {
  57. return _engine.RegExp.Construct((System.Text.RegularExpressions.Regex) expression.Value, expression.Regex.Flags);
  58. }
  59. return JsValue.FromObject(_engine, expression.Value);
  60. }
  61. }
  62. }