#define _X86_
#include <windows.h>
#include <stdio.h>
#include <wdm.h>
int main()
{
// переменные для хранения счетчика времени
LARGE_INTEGER time1;
LARGE_INTEGER time2;
// переменная для хранения старого IRQL
KIRQL oldirql;
// поднимаем IRQL до DISPATCH_LEVEL
KeRaiseIrql(DISPATCH_LEVEL, &oldirql);
// считываем таймер
QueryPerformanceCounter(&time1);
// работает функция
printf("IRQL raised! \n");
// считываем таймер
QueryPerformanceCounter(&time2);
// возвращаем IRQL к прежнему уровню
KeLowerIrql(oldirql);
return 0;
}
IRQL. Таймер. Конфликт SDK и DDK (WDK).
Первая версия:
Код:
Для работы QueryPerformanceCounter подключается windows.h, для KeRaiseIrql и KeLowerIrql, соответственно wdm.h Поскольку windows.h и wdm.h в свою очередь подключают различные (но содержащие сходные определения) header-файлы, при компиляции происходят многократные переопределения, что ведет к дальнейшим ошибкам:
Цитата:
1>c:\winddk\7600.16385.0\inc\api\ntdef.h(128) : warning C4005: MAX_NATURAL_ALIGNMENT: изменение макроопределения
1> c:\program files\microsoft sdks\windows\v7.0\include\winnt.h(109): см. предыдущее определение 'MAX_NATURAL_ALIGNMENT'
1>c:\winddk\7600.16385.0\inc\api\ntdef.h(161) : warning C4005: PROBE_ALIGNMENT: изменение макроопределения
1> c:\program files\microsoft sdks\windows\v7.0\include\winnt.h(142): см. предыдущее определение 'PROBE_ALIGNMENT'
1>c:\winddk\7600.16385.0\inc\api\ntdef.h(614) : error C2011: _PROCESSOR_NUMBER: переопределение типа "struct"
1> c:\program files\microsoft sdks\windows\v7.0\include\winnt.h(493): см. объявление '_PROCESSOR_NUMBER'
1>c:\winddk\7600.16385.0\inc\api\ntdef.h(625) : error C2011: _GROUP_AFFINITY: переопределение типа "struct"
1> c:\program files\microsoft sdks\windows\v7.0\include\winnt.h(504): см. объявление '_GROUP_AFFINITY'
1>c:\winddk\7600.16385.0\inc\api\ntdef.h(882) : error C2011: _FLOAT128: переопределение типа "struct"
1> c:\program files\microsoft sdks\windows\v7.0\include\winnt.h(630): см. объявление '_FLOAT128'
1>c:\winddk\7600.16385.0\inc\api\ntdef.h(933) : error C2011: _LARGE_INTEGER: переопределение типа "union"
1> c:\program files\microsoft sdks\windows\v7.0\include\winnt.h(677): см. объявление '_LARGE_INTEGER'
1>c:\winddk\7600.16385.0\inc\api\ntdef.h(951) : error C2011: _ULARGE_INTEGER: переопределение типа "union"
1> c:\program files\microsoft sdks\windows\v7.0\include\winnt.h(695): см. объявление '_ULARGE_INTEGER'
1>c:\winddk\7600.16385.0\inc\api\ntdef.h(973) : error C2011: _LUID: переопределение типа "struct"
1> c:\program files\microsoft sdks\windows\v7.0\include\winnt.h(717): см. объявление '_LUID'
1>c:\winddk\7600.16385.0\inc\api\ntdef.h(1070) : error C2084: функция "ULONGLONG
...
Поскольку у нас консольное приложение, выход я нашел: заменил QueryPerformanceCounter на KeQueryPerformanceCounter. Таким образом исключил необходимый вначале windows.h
Вторая версия:
Код:
#define _X86_
#include <wdm.h>
#include <stdio.h>
int main()
{
LARGE_INTEGER time1;
LARGE_INTEGER time2;
KIRQL oldirql;
KeRaiseIrql(DISPATCH_LEVEL, &oldirql);
time1 = KeQueryPerformanceCounter(NULL);
printf("IRQL raised! \n");
time2 = KeQueryPerformanceCounter(NULL);
KeLowerIrql(oldirql);
return 0;
}
#include <wdm.h>
#include <stdio.h>
int main()
{
LARGE_INTEGER time1;
LARGE_INTEGER time2;
KIRQL oldirql;
KeRaiseIrql(DISPATCH_LEVEL, &oldirql);
time1 = KeQueryPerformanceCounter(NULL);
printf("IRQL raised! \n");
time2 = KeQueryPerformanceCounter(NULL);
KeLowerIrql(oldirql);
return 0;
}
Но при компоновке выдается следующее:
Цитата:
1>TestIrql.obj : error LNK2001: неразрешенный внешний символ "__imp_@KfRaiseIrql@4"
1>TestIrql.obj : error LNK2001: неразрешенный внешний символ "__imp_@KfLowerIrql@4"
1>TestIrql.obj : error LNK2001: неразрешенный внешний символ "__imp__KeQueryPerformanceCounter"
1>TestIrql.obj : error LNK2001: неразрешенный внешний символ "__imp_@KfLowerIrql@4"
1>TestIrql.obj : error LNK2001: неразрешенный внешний символ "__imp__KeQueryPerformanceCounter"
Такие ошибки возникают, когда не подключены какие-либо библиотеки.. Подключаем wdm.lib Теперь ошибка всего одна:
Цитата:
1>TestIrql.obj : error LNK2001: неразрешенный внешний символ "__imp__KeQueryPerformanceCounter"
Попробуем исключить измерение времени и посмотреть, что получится.
Третья (урезанная до предела) версия:
Код:
#define _X86_
#include <stdio.h>
#include <wdm.h>
int main()
{
KIRQL oldirql;
KeRaiseIrql(DISPATCH_LEVEL, &oldirql);
printf("IRQL raised! \n");
KeLowerIrql(oldirql);
return 0;
}
#include <stdio.h>
#include <wdm.h>
int main()
{
KIRQL oldirql;
KeRaiseIrql(DISPATCH_LEVEL, &oldirql);
printf("IRQL raised! \n");
KeLowerIrql(oldirql);
return 0;
}
Вроде бы все скомпилировалось и собралось, запускаем.. И получаем: "Ошибка при инициализации приложения (0xc0000005). Для выхода из приложения нажмите кнопку "ОК".
Вопросы к людям, которые имеют опыт в использовании данных функций ядра:
1) Как исправить ошибку компоновки?
2) Почему возникает ошибка инициализации приложения?
3) Как быть, если в Windows-приложении (или консольном, использующим Win32 API) необходимо пользоваться функциями ядра? Можно ли подружить SDK и WDK (DDK)?
Просьба ко всем остальным (у кого может и нет опыта, но зато есть WDK (DDK)): пожалуйста, попробуйте запустить вторую версию кода на своих машинах и напишите их конфигурацию.
Заранее спасибо за ответы.
Версия SDK: 7
Версия DDK (WDK): 7
Операционная система: Windows XP SP2
Среда разработки: Visual C++ Express 2008
Компиляция кода: как C++
P.S. Вообще в требованиях к WDK написано Windows XP SP3, но при установке на SP2 никаких протестов у инсталлера не возникало.
Данная иллюстрация мне знакома. Но она не отвечает ни на один из поставленных вопросов.
Windows SDK
WDK
Полагаю неестественность ваших манипуляций вас не озадачила, так же как и описания объектов манипуляций, так же как и разница между голубеньким и фиолетовым.
Господа, учим мат. часть.
WDK
Полагаю неестественность ваших манипуляций вас не озадачила, так же как и описания объектов манипуляций, так же как и разница между голубеньким и фиолетовым.
Господа, учим мат. часть.
Ладно, еще сам подумаю..