Как я могу получить исходный файл скомпилированного метода? - PullRequest
6 голосов
/ 09 апреля 2010

Я действительно озадачен этим!

Объект StackFrame ( MSDN Link ) имеет метод GetFileName, который возвращает исходный путь к исходному файлу, который скомпилировал метод выполнения (при условии, что символы были сгенерированы и включены в исполняющие сборки). Похоже, эта информация используется для генерации полного текста исключения.

Я пытаюсь найти способ получить эту информацию, если метод в данный момент не выполняется. Я копался в API отражений и не видел способа получить эту информацию. Я предполагаю, что это должно быть где-то там.

Кто-нибудь еще знает метод, основанный на отражении (или вообще любой другой метод), который может дать мне имя файла кода?

Любые идеи, комментарии или оскорбления принимаются с благодарностью.

Большое спасибо!

Ответы [ 3 ]

4 голосов
/ 09 апреля 2010

Reflection может предоставлять информацию о типе только из метаданных сборки. Для получения адреса требуется файл отладки .pdb и адрес функции в памяти, скомпилированный компилятором JIT. Вы не можете получить адрес без метода StackFrame.GetNativeOffset () или интерфейсов отладчика, предполагая, что метод даже скомпилирован. Последний подход не может работать в процессе, программа не может отлаживать себя.

CLR не имеет никаких проблем, потому что он может извлечь адрес метода из стековых фреймов, когда обрабатывает исключение. Это все еще несовершенное искусство, оно не может видеть адреса методов, которые были встроены. Наличие этих кадров стека является обязательным первым шагом.

1 голос
/ 25 мая 2014

Вы можете прочитать информацию из файла .pdb и оценить ее самостоятельно. Она содержит все необходимые данные. Я не закончил читать код, но мое понимание таково:

  • Вы получаете токен метаданных из рассматриваемого метода путем отражения
  • Вы запрашиваете данные pdb для этого токена
  • Запись pdb содержит имя исходного файла и номер строки

Маркер метаданных - это 32-разрядное число, состоящее из байта типа и серийного номера. Этот токен описывает каждую отдельную сущность в файле сборки .NET: типы, ссылки на типы, методы, поля и так далее. Это число стоит больше, чем полное пространство имен, тип, имя метода и сигнатура метода, и его легче обрабатывать. Но имейте в виду, что он генерируется компилятором и может отличаться в каждой сборке, поэтому вам всегда нужен файл .pdb из той же сборки.

Файл pdb содержит записи о том, какое смещение IL в каком методе происходит из какого исходного местоположения. Если у вас нет StackFrame, а есть только метод, вы, вероятно, найдете несколько записей о методе, так что вы можете использовать один из них с наименьшим смещением или описать весь диапазон в исходном коде, который определяет метод.

Вот несколько ссылок для дальнейшего чтения, поисковый термин «pdb2xml» - это старый пример кода от Microsoft:

Поскольку .NET API для чтения файлов .pdb требует наличия файлов сборки, это преобразование следует выполнять непосредственно после сборки, чтобы сгенерированный файл XML был действительно переносимым.

Я на самом деле строю этот метод в своем решении для ведения журналов .NET, FieldLog , чтобы разрешить разрешение исходного местоположения из журналов сбоев из сборок релизов и де-обфусцировать следы стека от запутанных сборок. *

0 голосов
/ 09 апреля 2010

Используйте декомпилятор RedGate Reflector для проверки сборки, содержащей класс.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...