public LineNumberTable GetLineNumberTable()
        {
            lock (SymbolFile) {
                if (lnt != null)
                {
                    return(lnt);
                }

                if (LineNumberTableOffset == 0)
                {
                    return(null);
                }

                MyBinaryReader reader  = SymbolFile.BinaryReader;
                long           old_pos = reader.BaseStream.Position;
                reader.BaseStream.Position = LineNumberTableOffset;

                lnt = LineNumberTable.Read(SymbolFile, reader, (flags & Flags.ColumnsInfoIncluded) != 0, (flags & Flags.EndInfoIncluded) != 0);

                reader.BaseStream.Position = old_pos;
                return(lnt);
            }
        }
Exemple #2
0
        MonoSymbolFile(Stream stream)
        {
            reader = new MyBinaryReader(stream);

            try {
                long magic         = reader.ReadInt64();
                int  major_version = reader.ReadInt32();
                int  minor_version = reader.ReadInt32();

                if (magic != OffsetTable.Magic)
                {
                    throw new MonoSymbolFileException("Symbol file is not a valid");
                }
                if (major_version != OffsetTable.MajorVersion)
                {
                    throw new MonoSymbolFileException(
                              "Symbol file has version {0} but expected {1}", major_version, OffsetTable.MajorVersion);
                }
                if (minor_version != OffsetTable.MinorVersion)
                {
                    throw new MonoSymbolFileException("Symbol file has version {0}.{1} but expected {2}.{3}",
                                                      major_version, minor_version,
                                                      OffsetTable.MajorVersion, OffsetTable.MinorVersion);
                }

                MajorVersion = major_version;
                MinorVersion = minor_version;
                guid         = new Guid(reader.ReadBytes(16));

                ot = new OffsetTable(reader, major_version, minor_version);
            } catch (Exception e) {
                throw new MonoSymbolFileException("Cannot read symbol file", e);
            }

            source_file_hash  = new Dictionary <int, SourceFileEntry> ();
            compile_unit_hash = new Dictionary <int, CompileUnitEntry> ();
        }
 internal ScopeVariable(MyBinaryReader reader)
 {
     Scope = reader.ReadLeb128();
     Index = reader.ReadLeb128();
 }
 internal CapturedScope(MyBinaryReader reader)
 {
     Scope        = reader.ReadLeb128();
     CapturedName = reader.ReadString();
 }
 internal CapturedVariable(MyBinaryReader reader)
 {
     Name         = reader.ReadString();
     CapturedName = reader.ReadString();
     Kind         = (CapturedKind)reader.ReadByte();
 }
 internal LocalVariableEntry(MonoSymbolFile file, MyBinaryReader reader)
 {
     Index      = reader.ReadLeb128();
     Name       = reader.ReadString();
     BlockIndex = reader.ReadLeb128();
 }
        void DoRead(MonoSymbolFile file, MyBinaryReader br, bool includesColumns, bool includesEnds)
        {
            var lines = new List <LineNumberEntry> ();

            bool is_hidden = false, modified = false;
            int  stm_line = 1, stm_offset = 0, stm_file = 1;

            while (true)
            {
                byte opcode = br.ReadByte();

                if (opcode == 0)
                {
                    byte size    = br.ReadByte();
                    long end_pos = br.BaseStream.Position + size;
                    opcode = br.ReadByte();

                    if (opcode == DW_LNE_end_sequence)
                    {
                        if (modified)
                        {
                            lines.Add(new LineNumberEntry(
                                          stm_file, stm_line, -1, stm_offset, is_hidden));
                        }
                        break;
                    }
                    else if (opcode == DW_LNE_MONO_negate_is_hidden)
                    {
                        is_hidden = !is_hidden;
                        modified  = true;
                    }
                    else if ((opcode >= DW_LNE_MONO__extensions_start) &&
                             (opcode <= DW_LNE_MONO__extensions_end))
                    {
                        ;                         // reserved for future extensions
                    }
                    else
                    {
                        throw new MonoSymbolFileException("Unknown extended opcode {0:x}", opcode);
                    }

                    br.BaseStream.Position = end_pos;
                    continue;
                }
                else if (opcode < OpcodeBase)
                {
                    switch (opcode)
                    {
                    case DW_LNS_copy:
                        lines.Add(new LineNumberEntry(
                                      stm_file, stm_line, -1, stm_offset, is_hidden));
                        modified = false;
                        break;

                    case DW_LNS_advance_pc:
                        stm_offset += br.ReadLeb128();
                        modified    = true;
                        break;

                    case DW_LNS_advance_line:
                        stm_line += br.ReadLeb128();
                        modified  = true;
                        break;

                    case DW_LNS_set_file:
                        stm_file = br.ReadLeb128();
                        modified = true;
                        break;

                    case DW_LNS_const_add_pc:
                        stm_offset += MaxAddressIncrement;
                        modified    = true;
                        break;

                    default:
                        throw new MonoSymbolFileException(
                                  "Unknown standard opcode {0:x} in LNT",
                                  opcode);
                    }
                }
                else
                {
                    opcode -= OpcodeBase;

                    stm_offset += opcode / LineRange;
                    stm_line   += LineBase + (opcode % LineRange);
                    lines.Add(new LineNumberEntry(
                                  stm_file, stm_line, -1, stm_offset, is_hidden));
                    modified = false;
                }
            }

            _line_numbers = lines.ToArray();

            if (includesColumns)
            {
                for (int i = 0; i < _line_numbers.Length; ++i)
                {
                    var ln = _line_numbers[i];
                    if (ln.Row >= 0)
                    {
                        ln.Column = br.ReadLeb128();
                    }
                }
            }
            if (includesEnds)
            {
                for (int i = 0; i < _line_numbers.Length; ++i)
                {
                    var ln = _line_numbers[i];

                    int row = br.ReadLeb128();
                    if (row == 0xffffff)
                    {
                        ln.EndRow    = -1;
                        ln.EndColumn = -1;
                    }
                    else
                    {
                        ln.EndRow    = ln.Row + row;
                        ln.EndColumn = br.ReadLeb128();
                    }
                }
            }
        }