internal UnloadedBlock(Buffer raw, DirectivesBlock directives) : base(BlockCode.Unloaded) { kind = raw.ReadByte (); start_counter = raw.ReadUlong (); end_counter = raw.ReadUlong (); thread_id = raw.ReadUlong (); if (directives.LoadedElementsCarryId) id = raw.ReadUint (); item_name = raw.ReadString (); switch ((LoadedItemInfo) kind) { case LoadedItemInfo.APPDOMAIN: is_appdomain = true; break; case LoadedItemInfo.MODULE: is_module = true; break; case LoadedItemInfo.ASSEMBLY: is_assembly = true; break; default: throw new Exception (String.Format ("unknown load event kind {0}", kind)); } if (!raw.IsEmpty) throw new Exception ("Unexpected data remaining in block"); }
internal MappingBlock(Buffer raw, DirectivesBlock directives) : base(BlockCode.Mapping) { start_counter = raw.ReadUlong (); start_time = raw.ReadTime (); thread_id = raw.ReadUlong (); for (uint item_id = raw.ReadUint (); item_id != 0; item_id = raw.ReadUint ()) { uint assembly = 0; if (directives.ClassesCarryAssemblyId) assembly = raw.ReadUint (); string name = raw.ReadString (); classes.Add (new ClassInfo (item_id, assembly, name)); } for (uint item_id = raw.ReadUint (); item_id != 0; item_id = raw.ReadUint ()) { uint class_id = raw.ReadUint (); bool is_wrapper = false; if (directives.MethodsCarryWrapperFlag) is_wrapper = raw.ReadUint () != 0; string name = raw.ReadString (); methods.Add (new MethodInfo (item_id, class_id, is_wrapper, name)); } end_counter = raw.ReadUlong (); end_time = raw.ReadTime (); if (!raw.IsEmpty) throw new Exception ("Unexpected data remaining in block"); }
internal EventsBlock(Buffer raw, DirectivesBlock directives) : base(BlockCode.Events) { start_counter = raw.ReadUlong (); start_time = raw.ReadTime (); thread_id = raw.ReadUlong (); ulong base_counter = raw.ReadUlong (); for (byte event_code = raw.ReadByte (); event_code != 0; event_code = raw.ReadByte ()) { EventInfoType event_type = (EventInfoType) (event_code & 0x7); byte event_data = (byte) (event_code >> 3); switch (event_type) { case EventInfoType.Allocation: uint id = (raw.ReadUint () << 5) | (uint) event_data; uint size = raw.ReadUint (); uint caller = directives.AllocationsCarryCallerMethod ? raw.ReadUint () : 0; ulong object_id = directives.AllocationsCarryId ? raw.ReadUlong () : 0; events.Add (new AllocationInfo (id, size, caller, object_id)); break; case EventInfoType.Class: uint class_id = raw.ReadUint (); base_counter += raw.ReadUlong (); if ((event_data & 0x3) == 3) { uint lock_event = raw.ReadUint (); ulong oid = raw.ReadUlong (); events.Add (new LockEventInfo (class_id, base_counter, lock_event, oid)); } else events.Add (new ClassEventInfo (event_data, class_id, base_counter)); break; case EventInfoType.Enter: case EventInfoType.ExitExplicit: uint method_id = raw.ReadUint () << 5 | (uint) event_data; base_counter += raw.ReadUlong (); events.Add (new MethodEventInfo (event_type, method_id, base_counter, 0)); break; case EventInfoType.ExitImplicit: throw new Exception ("Implicit method exit events are unsupported."); case EventInfoType.Method: uint mid = raw.ReadUint (); base_counter += raw.ReadUlong (); events.Add (new MethodEventInfo (EventInfoType.Method, mid, base_counter, event_data)); break; case EventInfoType.Other: byte generic_code = (byte) (event_data & 0xf); switch (generic_code) { case 1: // Thread ulong tid = raw.ReadUlong (); base_counter += raw.ReadUlong (); events.Add (new ThreadEventInfo (tid, base_counter, event_data)); break; case 2: // GC Collection case 3: // GC Mark case 4: // GC Sweep case 6: // GC StopWorld case 7: // GC StartWorld uint collection = raw.ReadUint (); base_counter += raw.ReadUlong (); events.Add (new GCEventInfo (generic_code, collection, base_counter, event_data)); break; case 5: // GC Resize ulong new_size = raw.ReadUlong (); uint coll = raw.ReadUint (); events.Add (new GCEventInfo (generic_code, coll, new_size, event_data)); break; case 8: // Jit Time Allocation events.Add (new AllocationInfo (raw.ReadUint (), raw.ReadUint (), directives.AllocationsCarryCallerMethod ? raw.ReadUint () : 0, directives.AllocationsCarryId ? raw.ReadUlong () : 0)); break; case 9: // Stack Section //FIXME: for now, we are just reading the data to get to the end StackEventInfo stack_info = new StackEventInfo (raw.ReadUint ()); uint top_section_size = raw.ReadUint (); for (int i = 0; i < top_section_size; i++) { uint meth_id = raw.ReadUint (); bool is_jitting = (meth_id & 0x1) != 0; meth_id >>= 1; stack_info.StackItems.Add (new StackEventInfo.Item (meth_id, is_jitting)); } events.Add (stack_info); break; default: throw new Exception ("unknown 'Other' event code " + generic_code); } break; default: throw new Exception ("Unexpected event type " + event_type); } } end_counter = raw.ReadUlong (); end_time = raw.ReadTime (); if (!raw.IsEmpty) throw new Exception ("Unexpected data remaining in block"); }
void AddDirectivesBlock (DirectivesBlock block) { directives = block; UpdateCounterAndTime (block.EndCounter, block.EndTime); }
Block DecodeBlock(BlockCode code, uint length, byte[] data) { switch (code) { case BlockCode.Directives: directives = new DirectivesBlock (new Buffer (data, length)); return directives; case BlockCode.End: return new EndBlock (new Buffer (data, length)); case BlockCode.Events: return new EventsBlock (new Buffer (data, length), directives); case BlockCode.Intro: return new IntroBlock (new Buffer (data, length)); case BlockCode.Loaded: return new LoadedBlock (new Buffer (data, length), directives); case BlockCode.Mapping: return new MappingBlock (new Buffer (data, length), directives); case BlockCode.Statistical: return new StatBlock (new Buffer (data, length)); case BlockCode.Unloaded: return new UnloadedBlock (new Buffer (data, length), directives); default: Console.WriteLine ("Unsupported block code: " + code); break; } return null; }
internal LoadedBlock(Buffer raw, DirectivesBlock directives) : base(BlockCode.Loaded) { kind = raw.ReadByte (); start_counter = raw.ReadUlong (); end_counter = raw.ReadUlong (); thread_id = raw.ReadUlong (); if (directives.LoadedElementsCarryId) id = raw.ReadUint (); item_name = raw.ReadString (); success = ((kind & (byte)LoadedItemInfo.SUCCESS) != 0); kind &= (byte) (LoadedItemInfo.APPDOMAIN|LoadedItemInfo.ASSEMBLY|LoadedItemInfo.MODULE); switch ((LoadedItemInfo) kind) { case LoadedItemInfo.APPDOMAIN: is_appdomain = true; break; case LoadedItemInfo.MODULE: is_module = true; break; case LoadedItemInfo.ASSEMBLY: is_assembly = true; if (directives.ClassesCarryAssemblyId) assembly_info = new AssemblyInfo (raw.ReadString (), raw.ReadUint (), raw.ReadUint (), raw.ReadUint (), raw.ReadUint (), raw.ReadString (), raw.ReadString (), raw.ReadUint () != 0); else { int commaPosition = item_name.IndexOf (','); assembly_info = new AssemblyInfo (commaPosition > 0 ? item_name.Substring (0, commaPosition) : "UNKNOWN"); } break; default: throw new Exception (String.Format ("unknown load event kind {0}", kind)); } if (!raw.IsEmpty) throw new Exception ("Unexpected data remaining in block"); }