JsWeakMap.cs 1.6 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374
  1. using System.Runtime.CompilerServices;
  2. using Jint.Native.Object;
  3. using Jint.Runtime;
  4. namespace Jint.Native;
  5. internal sealed class JsWeakMap : ObjectInstance
  6. {
  7. private readonly ConditionalWeakTable<JsValue, JsValue> _table;
  8. public JsWeakMap(Engine engine) : base(engine)
  9. {
  10. _table = new ConditionalWeakTable<JsValue, JsValue>();
  11. }
  12. internal bool WeakMapHas(JsValue key)
  13. {
  14. return _table.TryGetValue(key, out _);
  15. }
  16. internal bool WeakMapDelete(JsValue key)
  17. {
  18. return _table.Remove(key);
  19. }
  20. internal void WeakMapSet(JsValue key, JsValue value)
  21. {
  22. if (!key.CanBeHeldWeakly(_engine.GlobalSymbolRegistry))
  23. {
  24. Throw.TypeError(_engine.Realm, "WeakMap key must be an object, got " + key);
  25. }
  26. #if SUPPORTS_WEAK_TABLE_ADD_OR_UPDATE
  27. _table.AddOrUpdate(key, value);
  28. #else
  29. _table.Remove(key);
  30. _table.Add(key, value);
  31. #endif
  32. }
  33. internal JsValue WeakMapGet(JsValue key)
  34. {
  35. if (!_table.TryGetValue(key, out var value))
  36. {
  37. return Undefined;
  38. }
  39. return value;
  40. }
  41. internal JsValue GetOrInsert(JsValue key, JsValue value)
  42. {
  43. if (_table.TryGetValue(key, out var temp))
  44. {
  45. return temp;
  46. }
  47. _table.Add(key, value);
  48. return value;
  49. }
  50. internal JsValue GetOrInsertComputed(JsValue key, ICallable callbackfn)
  51. {
  52. if (_table.TryGetValue(key, out var temp))
  53. {
  54. return temp;
  55. }
  56. var value = callbackfn.Call(Undefined, key);
  57. _table.Add(key, value);
  58. return value;
  59. }
  60. }