Мне нужно получить имена файлов из файла PDB, которые соответствуют переменным в безымянных пространствах имен. Я использую VS2012 и C ++. Я собрал небольшой пример тривиального кода, чтобы проиллюстрировать проблему:
// file: unnamed_namespace1.cpp Minimal test for anonymous namespace symbols
namespace {
float x;
static float xx;
}
int unnamed_namespace1(int data) {
x = 1.0f;
if (data == 0) {
// Computation
xx = x;
} else {
xx = 0.0;
}
return 1;
}
// file unnamed_namespace2.cpp Minimal test for anonymous namespace symbols
namespace {
float x;
float y;
float z;
static float xx;
static float yy;
static float zz;
}
int unnamed_namespace2(int data) {
x = 1.0f;
if (data == 0) {
// Computation
xx = x;
} else {
xx = 0.0;
}
return 2;
}
// file main.cpp
#include <iostream>
using std::cout;
using std::endl;
int unnamed_namespace1(int data);
int unnamed_namespace2(int data);
int main(int /* argc */, char** /* argv */) {
int r1 = unnamed_namespace1(0);
cout << "r1=" << r1 << endl;
int r2 = unnamed_namespace2(1);
cout << "r2=" << r2 << endl;
}
Мне нужен какой-то способ заглянуть в файл PDB и получить достаточно информации, чтобы различить два экземпляра x и xx в отдельных компиляциях.
Я скачал и немного поиграл с проектом под названием dia2dump (из https://msdn.microsoft.com/en-us/library/b5ke49f5.aspx), что немного помогло в понимании того, как работает система DIA, в отличие от «документации» MSDN по IDiaSymbol, в которой в основном отсутствует какой-либо контекст, и очень мало значимых примеров кода.
Похоже, что нет хорошего способа связать символы x и xx с именами исходных файлов.
Я могу получить IDiaSymbol * pSymbol, но различные функции, которые выглядят так, как будто они действительно могут предоставить то, что мне нужно, возвращают S_FALSE: «Возвращаемое значение S_FALSE означает, что свойство недоступно для символа».
Вот фрагмент кода, который я вставил в dia2dump:
BSTR bstrFname;
if (pSymbol->get_sourceFileName(&bstrFname) == S_OK) {
wprintf(L"fn:%s ", bstrFname); // <== never gets here
SysFreeString(bstrFname);
}else{
wprintf(L"no fn "); // <== this is always printed
}
Мне не удалось найти какие-либо подсказки, почему get_sourceFileName () не возвращает ничего полезного.
Я предполагаю, что я либо 1) ищу не в том месте, либо 2) программисты, которые написали DLL-файл доступа к интерфейсу отладки, не считают это достаточно важным для реализации этой функции для символов в анонимных пространствах имен. Я надеюсь, что это # 1, так что кто-то там может указать на то, что мне удалось пропустить.
Можно даже смеяться над моим невежеством, если вы предоставляете полезную информацию …
Задача ещё не решена.