Программирование для Windows NT

       

Определения и глобальные переменные


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

В глобальных переменных hInst, szAppName и szAppTitle хранится, соответственно, идентификатор приложения, полученный при запуске через параметр hInstance функции WinMain, имя и заголовок главного окна приложения.

Глобальная переменная lpMemoryBuffer содержит указатель на блок виртуальной памяти размером MEMBLOCK_SIZE байт. Это именно тот блок памяти, с которым в нашем приложении выполняются все операции.

И, наконец, в глобальной переменной hSetMenu хранится идентификатор меню Set protection, который необходим для выполнения операции отметки строк этого меню.


Помимо обычных include-файлов, характерных для наших приложений, в приложении MultiSDI используется файл process.h. Этот файл содержит прототип функции _beginthread, с помощью которой наше приложение создает задачи.

Для синхронизации задач, выполняющих рисование в окне приложения, мы определили глобальную структуру csWindowPaint типа CRITICAL_SECTION, которая будет использоваться в качестве критической секции:

CRITICAL_SECTION csWindowPaint;

В глобальной переменной fTerminate хранится  флаг, установка которого в состояние TRUE вызывает завершение всех трех задач рисования.

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




Так как для запуска задач в приложении MultiMDI мы пользуемся функцией CreateThread, нам не нужно включать файл process.h.



В глобальных переменных szFrameClassName и szChildClassName хранятся указатели, соответственно, на имена классов для окна Frame Window и окна Child Window.

Адрес заголовка приложения хранится в глобальной переменной szWindowTitle.

Переменная hInst используется для хранения идентификатора приложения.

Переменные hwndFrame, hwndClient и hwndChild используются, соответственно, для хранения идентификаторов окон Frame Window, Client Window и дочернего окна (в момент его создания).

Для каждого дочернего MDI-окна мы создаем структуру типа CHILD_WINDOW_TAG,  в которой сохраняем такую информацию, как признак активности задачи, запущенной для этого окна, критическую секцию для рисования в окне, а также идентификатор задачи, запущенной для окна:

typedef struct _CHILD_WINDOW_TAG

{

  BOOL fActive;

  CRITICAL_SECTION csChildWindowPaint;

  HANDLE hThread;

} CHILD_WINDOW_TAG;

Кроме того, мы определили указатель на эту структуру:

typedef CHILD_WINDOW_TAG *LPCHILD_WINDOW_TAG;




Для работы со стандартной диалоговой панелью, с помощью которой выбирается запускаемый программный файл, в исходный текст приложения включается файл commctrl.h.

В области глобальных переменных нашего приложения определены переменные dwCreationFlags и fWaitTermination. Первая из них содержит флаги создания процессов, которые настраиваются при помощи диалоговой панели Start Options и используются при запуске процессов функцией CreateProcess. Во второй переменной хранится признак необходимости ожидания завершения процессов. Содержимое этой переменной изменяется также при помощи диалоговой панели Start Options.




Приложение SEMMDI сделано на базе описанного ранее приложения MultiMDI, поэтому здесь мы приведем сокращенное описание определений, глобальных переменных и функций.

Для каждого дочернего MDI-окна в приложении MultiMDI мы создавали структуру типа CHILD_WINDOW_TAG,  в которой хранилась такая информация, как признак активности задачи, запущенной для этого окна, критическая секция для рисования в окне, а также идентификатор задачи, запущенной для окна. Создавая приложение SEMMDI, мы добавили в эту структуру поле fWaiting:

typedef struct _CHILD_WINDOW_TAG

{

  BOOL fActive;

  BOOL fWaiting;

  CRITICAL_SECTION csChildWindowPaint;

  HANDLE hThread;

} CHILD_WINDOW_TAG;

typedef CHILD_WINDOW_TAG *LPCHILD_WINDOW_TAG;

В поле fWaiting записывается значение TRUE, когда соответствующая задача находится в состоянии ожидания семафора. Проверяя содержимое этого поля, мы запрещаем пользователю удалять окна, если соответствующие им задачи находятся в состоянии ожидания семафора.



Содержание раздела