BindFunctionInstance.cs 2.3 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980
  1. using Jint.Native.Object;
  2. using Jint.Runtime;
  3. namespace Jint.Native.Function
  4. {
  5. public sealed class BindFunctionInstance : FunctionInstance, IConstructor
  6. {
  7. public BindFunctionInstance(
  8. Engine engine,
  9. Realm realm)
  10. : base(engine, realm, name: null, thisMode: FunctionThisMode.Strict)
  11. {
  12. }
  13. public JsValue TargetFunction { get; set; }
  14. public JsValue BoundThis { get; set; }
  15. public JsValue[] BoundArgs { get; set; }
  16. public override JsValue Call(JsValue thisObject, JsValue[] arguments)
  17. {
  18. var f = TargetFunction as FunctionInstance;
  19. if (f is null)
  20. {
  21. ExceptionHelper.ThrowTypeError(_realm);
  22. }
  23. var args = CreateArguments(arguments);
  24. var value = f.Call(BoundThis, args);
  25. _engine._jsValueArrayPool.ReturnArray(args);
  26. return value;
  27. }
  28. public ObjectInstance Construct(JsValue[] arguments, JsValue newTarget)
  29. {
  30. var target = TargetFunction as IConstructor;
  31. if (target is null)
  32. {
  33. ExceptionHelper.ThrowTypeError(_realm);
  34. }
  35. var args = CreateArguments(arguments);
  36. if (ReferenceEquals(this, newTarget))
  37. {
  38. newTarget = TargetFunction;
  39. }
  40. var value = target.Construct(args, newTarget);
  41. _engine._jsValueArrayPool.ReturnArray(args);
  42. return value;
  43. }
  44. internal override bool OrdinaryHasInstance(JsValue v)
  45. {
  46. var f = TargetFunction as FunctionInstance;
  47. if (f is null)
  48. {
  49. ExceptionHelper.ThrowTypeError(_realm);
  50. }
  51. return f.OrdinaryHasInstance(v);
  52. }
  53. private JsValue[] CreateArguments(JsValue[] arguments)
  54. {
  55. var combined = _engine._jsValueArrayPool.RentArray(BoundArgs.Length + arguments.Length);
  56. System.Array.Copy(BoundArgs, combined, BoundArgs.Length);
  57. System.Array.Copy(arguments, 0, combined, BoundArgs.Length, arguments.Length);
  58. return combined;
  59. }
  60. internal override bool IsConstructor => TargetFunction.IsConstructor;
  61. public override string ToString() => "function () { [native code] }";
  62. }
  63. }