TTSnapshotExtractor.h 4.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106
  1. //-------------------------------------------------------------------------------------------------------
  2. // Copyright (C) Microsoft. All rights reserved.
  3. // Licensed under the MIT license. See LICENSE.txt file in the project root for full license information.
  4. //-------------------------------------------------------------------------------------------------------
  5. #pragma once
  6. #if ENABLE_TTD
  7. namespace TTD
  8. {
  9. //A class that is in charge of extracting a snapshot of the heap
  10. class SnapshotExtractor
  11. {
  12. private:
  13. //The mark table for all pure objects that we have seen (filled in during walk used during extract)
  14. MarkTable m_marks;
  15. //A worklist for processing the objects as we find them during the mark
  16. JsUtil::Queue<Js::RecyclableObject*, HeapAllocator> m_worklist;
  17. TTDIdentifierDictionary<TTD_PTR_ID, NSSnapType::SnapHandler*> m_idToHandlerMap;
  18. TTDIdentifierDictionary<TTD_PTR_ID, NSSnapType::SnapType*> m_idToTypeMap;
  19. //The snapshot that is being constructed
  20. SnapShot* m_pendingSnap;
  21. ////////
  22. //Mark code
  23. //Visit a handler/type during the walk-mark phase
  24. void MarkVisitHandler(Js::DynamicTypeHandler* handler);
  25. void MarkVisitType(Js::Type* type);
  26. //Visit all the named and dynamic indexed properties that can appear on any object
  27. void MarkVisitStandardProperties(Js::RecyclableObject* obj);
  28. //Ensure that a handler/type has been extracted
  29. void ExtractHandlerIfNeeded(Js::DynamicTypeHandler* handler, ThreadContext* threadContext);
  30. void ExtractTypeIfNeeded(Js::Type* jstype, ThreadContext* threadContext);
  31. //Ensure that a slot/scope has been extracted
  32. void ExtractSlotArrayIfNeeded(Js::ScriptContext* ctx, Field(Js::Var)* scope);
  33. void ExtractScopeIfNeeded(Js::ScriptContext* ctx, Js::FrameDisplay* environment);
  34. void ExtractScriptFunctionEnvironmentIfNeeded(Js::ScriptFunction* function);
  35. ////
  36. //Performance info
  37. uint32 m_snapshotsTakenCount;
  38. double m_totalMarkMillis;
  39. double m_totalExtractMillis;
  40. double m_maxMarkMillis;
  41. double m_maxExtractMillis;
  42. double m_lastMarkMillis;
  43. double m_lastExtractMillis;
  44. void UnloadDataFromExtractor();
  45. //
  46. //TODO: In the case of weak* types (WeakMap & WeakSet) the results of a snapshot -- and potentially later execution depends on when a GC has been run.
  47. // I *think* we want to keep track of the number of weak types that *may* be live here and, if there are any, then always do a GC before doing a snapshot to put things in a uniform state.
  48. //
  49. public:
  50. SnapshotExtractor();
  51. ~SnapshotExtractor();
  52. //Get the current pending snapshot
  53. SnapShot* GetPendingSnapshot();
  54. //Return the slab allocatorr for the current active snapshot
  55. SlabAllocator& GetActiveSnapshotSlabAllocator();
  56. //Visit a variable value during the walk-mark phase, marking it and adding it to the appropriate worklist as needed
  57. void MarkVisitVar(Js::Var var);
  58. //Mark the function body
  59. void MarkFunctionBody(Js::FunctionBody* fb);
  60. //Mark/Extract the scope information for a function
  61. void MarkScriptFunctionScopeInfo(Js::FrameDisplay* environment);
  62. ////////
  63. //Do the actual snapshot extraction
  64. //Begin the snapshot by initializing the snapshot information
  65. void BeginSnapshot(ThreadContext* threadContext, double gcTime);
  66. //Do the walk of all objects caller need to to call MarkWalk on roots to initialize the worklist
  67. void DoMarkWalk(ThreadContext* threadContext);
  68. //Evacuate all the marked javascript objects into the snapshot (can do lazily/incrementally if desired)
  69. //All of the external elements are evacuated during the mark phase while propertyRecords and primitiveObjects are evacuated during the complete phase
  70. void EvacuateMarkedIntoSnapshot(ThreadContext* threadContext, JsUtil::BaseHashSet<Js::FunctionBody*, HeapAllocator>& liveTopLevelBodies);
  71. //Tidy up and save the snapshot return the completed snapshot
  72. SnapShot* CompleteSnapshot();
  73. //On replay we do a walk of the heap and re-populate the weak collection pin sets
  74. void DoResetWeakCollectionPinSet(ThreadContext* threadContext);
  75. };
  76. }
  77. #endif