internal override void Process(ProfilerSession sess)
        {
            Tracing.PacketTrace("HEAP COMPACTION BEGIN >>>");

            sess.HeapBytesFree = m_freeBytes;

            HeapCompactionBegin hc = new HeapCompactionBegin();
            sess.AddEvent(hc);
        }
        internal override void Process(ProfilerSession sess)
        {
            Tracing.PacketTrace("<<< HEAP COMPACTION END");

            // on CLR Profiler side: Need to preserve objects not relocated.

            sess.HeapBytesFree = m_freeBytes;

            HeapCompactionEnd hc = new HeapCompactionEnd();
            sess.AddEvent(hc);
        }
        internal override void Process(ProfilerSession sess)
        {
            Tracing.PacketTrace("GARBAGE COLLECTION BEGIN >>>");

            sess.HeapBytesFree = m_freeBytes;

            GarbageCollectionBegin gc = new GarbageCollectionBegin();
            sess.AddEvent(gc);
        }
        internal override void Process(ProfilerSession sess)
        {
            Tracing.PacketTrace("<<< GARBAGE COLLECTION BEGIN");

            sess.HeapBytesFree = m_freeBytes;

            GarbageCollectionEnd gc = new GarbageCollectionEnd();
            gc.liveObjects = new List<uint>(sess.m_liveObjectTable);
            sess.AddEvent(gc);
        }
        internal override void Process(ProfilerSession sess)
        {
            Tracing.PacketTrace("ALLOC: Objects relocated");

            List<uint> newTable = new List<uint>();
            for (int i = 0; i < sess.m_liveObjectTable.Count; i++ )
            {
                uint ptr = sess.m_liveObjectTable[i];
                uint j;
                for (j = 0; j < reloc.Length; j++)
                {
                    if (ptr >= reloc[j].m_start && ptr <= reloc[j].m_end)
                    {
                        newTable.Add(ptr + reloc[j].m_offset);
                        break;
                    }
                }
                if (j == reloc.Length)
                {
                    //No relocation for this object.
                    newTable.Add(ptr);
                }
            }
            newTable.Sort();
            sess.m_liveObjectTable = newTable;

            ObjectRelocation or = new ObjectRelocation();
            or.m_relocationRegions = reloc;
            sess.AddEvent(or);
        }
        internal override void Process(ProfilerSession sess)
        {
            Tracing.PacketTrace("ALLOC: Object freed from address {0}", m_address);

            int objIndex = sess.m_liveObjectTable.BinarySearch(m_address);
            if (objIndex > -1)
            {
                sess.m_liveObjectTable.RemoveAt(objIndex);

                ObjectDeletion delete = new ObjectDeletion();
                delete.address = m_address;
                sess.AddEvent(delete);
            }
        }
        internal override void Process(ProfilerSession sess)
        {
            Tracing.PacketTrace("ALLOC: Object allocated at address {0}", m_address);
            ObjectAllocation alloc = new ObjectAllocation();
            alloc.m_thread = sess.m_currentThreadPID;
            alloc.m_address = m_address;
            alloc.m_size = m_size;
            if (!sess.m_threadCallStacks.ContainsKey(sess.m_currentThreadPID))
            {
                sess.m_threadCallStacks.Add(sess.m_currentThreadPID, new Stack<uint>());
            }
            alloc.m_callStack = sess.m_threadCallStacks[sess.m_currentThreadPID].ToArray();
            Array.Reverse(alloc.m_callStack);
            sess.ResolveTypeName(m_type);   //Cache type name.

            if (sess.m_liveObjectTable.BinarySearch(m_address) < 0)
            {
                sess.m_liveObjectTable.Add(m_address);
                sess.m_liveObjectTable.Sort();
            }

            alloc.m_objectType = new ObjectType(m_type, m_rank);
            sess.AddEvent(alloc);
        }
 internal override void Process(ProfilerSession sess)
 {
     Tracing.PacketTrace("CALLS: Switched to thread {0}", m_thread);
     ContextSwitch c = new ContextSwitch();
     c.m_thread = m_thread;
     sess.m_currentThreadPID = m_thread;
     sess.AddEvent(c);
 }
        internal override void Process(ProfilerSession sess)
        {
            Tracing.PacketTrace("CALLS: Function returned on thread {0}", sess.m_currentThreadPID);

            if (sess.m_threadCallStacks.ContainsKey(sess.m_currentThreadPID))
            {
                Debug.Assert(sess.m_threadCallStacks[sess.m_currentThreadPID].Count > 0);
                sess.m_threadCallStacks[sess.m_currentThreadPID].Pop();
            }

            FunctionReturn f = new FunctionReturn();
            f.m_thread = sess.m_currentThreadPID;
            f.duration = m_duration;
            sess.AddEvent(f);
        }
        internal override void Process(ProfilerSession sess)
        {
            m_thread = sess.m_currentThreadPID;

            if (m_assembly == 0)
            {
                m_assembly = sess.m_currentAssembly;
            }
            else
            {
                sess.m_currentAssembly = m_assembly;
            }

            uint md = m_assembly << Packets.Commands.Bits.AssemblyShift | m_method;

            Tracing.PacketTrace("CALLS: Thread {0} called function {1}", m_thread, md);
            if (!sess.m_threadCallStacks.ContainsKey(m_thread))
            {
                sess.m_threadCallStacks.Add(m_thread, new Stack<uint>());
            }
            sess.m_threadCallStacks[m_thread].Push(md);

            FunctionCall f = new FunctionCall();
            f.m_thread = m_thread;
            f.m_callStack = sess.m_threadCallStacks[m_thread].ToArray();
            Array.Reverse(f.m_callStack);
            sess.m_engine.GetMethodName(md, true);    //Cache method name information while we still have a device.
            sess.AddEvent(f);
        }
        internal override void Process(ProfilerSession sess)
        {
            if (sess.m_currentHeapDump == null) { return; } //No heap dump to finish

            sess.HeapBytesUsed = m_heapBytesUsed;
            sess.AddEvent(sess.m_currentHeapDump);
            sess.m_currentHeapDump = null;
            Tracing.PacketTrace("<======================HEAP DUMP END");
        }