Я работаю над двумя C ++ DLL-проектами, которые делятся большей частью своего кода.
Итак, у меня есть один базовый проект, который компилируется в Base.lib
и два «производных» проекта, которые компилируются в Derived1.dll
а также Derived2.dll
и ссылка против Base.lib
, Эти производные DLL должны быть отправлены независимо. Пользователь даже не знает, что они связаны.
Теперь я хочу, чтобы обе мои DLL были поставщики событий Windows. Все события, в которые я хочу войти, происходят в Base.lib
, Итак, я добавил Instrumentation.man
к этому проекту и сделал его частью сборки.
Его содержание выглядит примерно так:
<?xml version="1.0" encoding="UTF-16"?>
<instrumentationManifest xsi:schemaLocation="http://schemas.microsoft.com/win/2004/08/events eventman.xsd" xmlns="http://schemas.microsoft.com/win/2004/08/events" xmlns:win="http://manifests.microsoft.com/win/2004/08/windows/events" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:trace="http://schemas.microsoft.com/win/2004/08/events/trace">
<instrumentation>
<events>
<provider name="Company-Provider-Base" guid="{12345678-1234-1234-1234-1234567890ABCD}" symbol="provider" resourceFileName="some/path/to.dll" messageFileName="some/path/to.dll" message="$(string.provider.message)">
<events>
...
</events>
</provider>
</events>
</instrumentation>
<localization>
<resources culture="en-US">
<stringTable>
<string id="provider.message" value="Base Provider" />
...
</stringTable>
</resources>
</localization>
</instrumentationManifest>
я использую mc.exe
чтобы скомпилировать это в файл ресурсов и файл заголовка. Заголовочный файл включен другими исходными файлами моего Базового проекта.
Теперь это работает на удивление хорошо! Все события регистрируются правильно для обеих библиотек DLL.
Однако, конечно, обе библиотеки DLL теперь имеют одного и того же поставщика с одинаковыми именем, guid и сообщением.
Итак, мой актуальный вопрос заключается в следующем:
Как я могу сделать provider
элемент в Instrumentation.man
настраивается таким образом, чтобы мои DLL-проекты могли заполнять свои собственные name
, guid
, а также message
атрибуты?
Я использую WiX для создания своих установочных комплектов. WiX позволяет мне настроить resourceFileName
а также messageFileName
атрибуты provider
элемент (оба указывают на пустышки в исходном файле) только тогда, когда библиотеки DLL развернуты в целевой системе, чтобы на них можно было правильно ссылаться. Однако WIX не предлагает аналогичного способа (по крайней мере, я этого не вижу) для изменения других атрибутов столь же плавно, что было бы именно тем, что я хочу.
Я также заметил, что WiX предлагает настроить parameterFileName
приписывать. К сожалению, я не могу найти никакой информации, как эти параметры работают. Я понимаю что могу поставить %%n
в строки в манифесте, а затем параметр с идентификатором n
будет вставлен. Но я не понимаю, где и как объявлять эти параметры, и я не знаю, смогу ли я использовать их в атрибутах, которые я хочу настроить, чтобы они вообще мне не помогли.
В итоге я написал свой собственный инструмент для модификации XML (в C #, как описано Вот, но подойдет любой другой язык), который берет файл манифеста и имя решения и соответственно заменяет значения атрибута.
Чтобы сделать это автоматически, я добавил событие Pre-Build Event в базовый проект, который вызывает этот инструмент и передает ему файл манифеста и $(SolutionName)
,
Это решение не является ни привлекательным, ни легко масштабируемым, но оно работает.
Других решений пока нет …