in krabs/krabs/ut.hpp [124:202]
inline void ut::enable_providers(
const krabs::trace<krabs::details::ut> &trace)
{
if (trace.registrationHandle_ == INVALID_PROCESSTRACE_HANDLE)
return;
provider_filter_settings provider_flags;
// This function essentially takes the union of all the provider flags
// for a given provider GUID. This comes about when multiple providers
// for the same GUID are provided and request different provider flags.
// TODO: Only forward the calls that are requested to each provider.
for (auto &provider : trace.providers_) {
auto& settings = provider_flags[provider.get().guid_];
settings.filter_flags_.level_ |= provider.get().level_;
settings.filter_flags_.any_ |= provider.get().any_;
settings.filter_flags_.all_ |= provider.get().all_;
settings.filter_flags_.trace_flags_ |= provider.get().trace_flags_;
settings.rundown_enabled_ |= provider.get().rundown_enabled_;
for (const auto& filter : provider.get().filters_) {
settings.provider_filter_event_ids_.insert(
filter.provider_filter_event_ids().begin(),
filter.provider_filter_event_ids().end());
}
}
for (auto &provider : provider_flags) {
ENABLE_TRACE_PARAMETERS parameters;
parameters.ControlFlags = 0;
parameters.Version = ENABLE_TRACE_PARAMETERS_VERSION_2;
parameters.SourceId = provider.first;
GUID guid = provider.first;
auto& settings = provider.second;
parameters.EnableProperty = settings.filter_flags_.trace_flags_;
parameters.EnableFilterDesc = nullptr;
parameters.FilterDescCount = 0;
EVENT_FILTER_DESCRIPTOR filterDesc{};
std::vector<BYTE> filterEventIdBuffer;
auto filterEventIdCount = settings.provider_filter_event_ids_.size();
if (filterEventIdCount > 0) {
//event filters existing, set native filters using API
parameters.FilterDescCount = 1;
filterDesc.Type = EVENT_FILTER_TYPE_EVENT_ID;
//allocate + size of expected events in filter
DWORD size = FIELD_OFFSET(EVENT_FILTER_EVENT_ID, Events[filterEventIdCount]);
filterEventIdBuffer.resize(size, 0);
auto filterEventIds = reinterpret_cast<PEVENT_FILTER_EVENT_ID>(&(filterEventIdBuffer[0]));
filterEventIds->FilterIn = TRUE;
filterEventIds->Count = static_cast<USHORT>(filterEventIdCount);
auto index = 0;
for (auto filter : settings.provider_filter_event_ids_) {
filterEventIds->Events[index] = filter;
index++;
}
filterDesc.Ptr = reinterpret_cast<ULONGLONG>(filterEventIds);
filterDesc.Size = size;
parameters.EnableFilterDesc = &filterDesc;
}
ULONG status = EnableTraceEx2(trace.registrationHandle_,
&guid,
EVENT_CONTROL_CODE_ENABLE_PROVIDER,
settings.filter_flags_.level_,
settings.filter_flags_.any_,
settings.filter_flags_.all_,
0,
¶meters);
error_check_common_conditions(status);
}
}