Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Вопросы к экзамену СМО(ответы. Еличева).doc
Скачиваний:
0
Добавлен:
01.07.2025
Размер:
8.96 Mб
Скачать
  1. Структурная обработка исключений.

Вторая особая архитектура, поддерживаемая и используемая Windows NT, назы­вается структурной обработкой исключений. Исключения (exceptions) — это синхронные ошибки или нетипичные события, вызывающие исполнение кода вне обычного потока управления. В отличие от прерываний, которые генериру­ются внешним источником, исключения возникают при исполнении програм­мой некоторого кода и могут быть воспроизведены.

Например, когда программа вызывает функцию С mallocQ, типичным ре­зультатом будет выделение памяти и возвращение указателя на нее. Исключи­тельная ситуация возникает тогда, когда из-за некоторой проблемы, например, недостатка свободной памяти, не удается выделить новый блок. При этом функ­ция возвращает указатель NULL

Возврат особого значения, указывающего на исключение — это обычная, но примитивная форма обработки исключений, и она имеет ряд недостатков. Во-первых, программист обязан скрупулезно соблюдать ритуал проверки воз­вращаемого значения и либо реагировать на ошибки, либо передавать их на более высокий уровень программы. Если на одном из уровней проверка не про­водится, то ошибки могут повлиять на не имеющие отношения к месту их воз­никновения части программы. Во-вторых, текст программы загромождается операторами If...Then...Else, обрабатывающими нетипичные случаи. В-третьих, информация о причине возникновения проблем не всегда легко доступна коду, который должен обработать ошибку.

Исключения могут обнаруживаться как программно, так и аппаратно. На­пример, аппаратура обнаруживает исключения "деление на 0", тогда как про­граммное обеспечение определяет нарушения защиты памяти. Структурная об­работка исключений — это метод, применяемый Windows NT для обработки как программных, так и аппаратных исключений, с использованием структур управ­ления (отсюда и название) некоторого языка программирования. Структурная обработка исключений позволяет любому блоку кода определить, от исключе­ний каких типов он хочет защищаться, и зарегистрировать специальный учас­ток кода — обработчик исключений (exception manager), который исполняется при возникновении исключений заданных типов в этом блоке.

Приводимый ниже код представляет собой пример процедуры на Microsoft С, в которую входит обработчик исключений. Функция является моди­фицированным вариантом стандартной библиотечной функции strlen(), воз­вращающей длину строки, которая заканчивается нулевым символом.

Обычная функция strlen() быстро просматривает память по одному симво­лу, до тех пор пока не найдет символ NULL. Но если строка не заканчивается нулем или указатель на строку неверен, то strlen() может внезапно завершиться с исключением "нарушение защиты памяти".

Приведенная здесь модифицированная версия перехватывает исключение и возвращает осмысленное значение (не обязательно верное, просто осмыслен­ное) вместо аварийного завершения программы. Новое ключевое слово try слу­жит отметкой начала блока кода, который может вызвать нарушение защиты. Если исключение возникает внутри этого блока, то управление передается на ключевое слово except, за которым в скобках следует фильтр исключений. Фильтр исключений дает возможность задать обработку только для некоторых типов исключений. Если значение фильтра равно EXCEPTION_EXECUTE_HANDLER, то исполняется обработчик исключения, в данном случае оператор return (count). Фильтры исключений — это достаточно мощное средство, так как они могут обращаться к локальным данным и иметь любую сложность. Применение филь­тров позволяет исполнять обработчик только при точном соблюдении задан­ных условий. Передача управления обработчику исключений называется воз­буждением исключения (raising an exception). Обратите внимание, что код обработки ошибок удален с основного пути выполнения программы.

Каждый блок кода может иметь собственный обработчик исключений, и обработчики могут быть вложены друг в друга. При возникновении исключения фильтр исключений может проверить его тип и по результатам проверки ука­зать ОС: выполнить обработчик исключений, продолжить выполнение програм­мы, завершить работу программы или продолжить поиск обработчика в охваты­вающем блоке кода.

Исключения ОС — не единственный тип исключений, которые может об­рабатывать приложение. Приложения сами могут генерировать исключения при помощи функции Win32 API RaiseException(), вызывая тем самым передачу-управления соответствующему обработчику исключений. Для поддержки этой операции ОС регистрирует обработчики исключений и просматривает их в надлежащем порядке в случае возбуждения исключения. Если ни один из обра­ботчиков не взялся за обработку проблемы, то ОС завершает программу, вызвав­шую ошибку. Средство обработки исключений Windows NT не зависит от ис­пользуемого языка программирования; один и тот же механизм используется для всех языков. Каждый язык определяет, каким образом в нем раскрывается этот механизм.

Другой тип обработчика исключений, известный как обработчик завер­шения (termination handler), позволяет приложению гарантировать выполнение некоторого блока кода, даже если защищенный блок завершается ненормально. Обработчики завершения часто содержат код, освобождающий ресурсы, чтобы в случае ненормального завершения процедуры выделенные ею ресурсы были возвращены системе. Следующий фрагмент кода иллюстрирует назначение об­работчика завершения:

Критическая секция — это синхронизационный объект Win32, который гарантирует, что данный блок кода будет исполняться одновременно не более чем одним потоком. В нашем примере поток получает доступ к критической секции, выделяет буфер, после чего модифицирует его содержимое. Если слу­чится что-то не то (например, произойдет необработанное исключение) и про­цедура завершится в тот момент, когда поток находится в критической секции, то остальные потоки, ожидающие доступ к этому ресурсу, будут заблокированы навсегда. Более того, буфер, выделенный потоком, будет потерян, так как ОС не сможет его освободить сама. (Разработчики часто называют такого рода ошиб­ки утечками памяти. Если их происходит слишком много, то память постепенно "утекает".) Обработчик завершения гарантирует, что поток освободит объект-критическую секцию и буфер. Обработчики завершения исполняются всегда, когда поток управления выходит из тела блока try...finally, независимо от способа, которым происходит этот выход.

Обработчики исключений и завершений могут использоваться для дости­жения устойчивой работы приложения как по отдельности, так и в комбинации. Windows NT использует оба типа обработчиков для обеспечения надежной ра­боты на всех уровнях системы.

Объектная модель Windows NT:

  1. Объекты. Использование объектов.

  2. Файловая и объектная модель.

  3. Структура и типы объектов.

  4. Управление объектами: имена, каталоги.

  5. Управление объектами: домены, символические связи.

Контроль доступа

к объектам WinNT:

  1. Описатели и удержание объектов. Учет использования ресурсов..

Хотя имена объектов важны для хранения и совместного использования объек­тов, они используются не часто. Процесс указывает имя объекта, когда он созда­ет объект или открывает его описатель. После этого процесс использует описа­тель объекта. Ссылка на объект при помощи его описателя выполняется быст­рее, чем по имени, так как диспетчер объекта может опустить поиск имени и найти объект непосредственно.

Описатель объекта NT — это индекс в специфичной для процесса таблице объектов (object table). Таблица объектов процесса содержит указатели на все объекты, описатели которых открыты процессом. Процесс может получить описатель объекта, создав объект, или открыв описатель существующего объек­та, или унаследовав описатель от другого процесса, или получив дубликат опи­сателя из другого процесса. На рис. 3-7 показана связь между процессом и его таблицей объектов.

Каждый вход таблицы объектов содержит предоставленные права доступа для соответствующего описателя и его режим наследования (inheritance designa­tion) — иными словами, получат ли процессы, созданные данным процессом, копию этого описателя в своих таблицах объектов. Хотя термин описатель (handle), строго говоря, относится только к индексу в таблице, разработчики используют этот термин и для обозначения данных, хранящихся в соответству­ющем входе таблицы.

Рис. 3-7. Структура таблицы объектов.

Два процесса совместно используют объект, если оба они открыли его опи­сатели. Каждый из этих описателей уникален, как показано на рис. 3-8.

Создатель объекта определяет, могут ли описатели объекта наследо­ваться из процесса теми процессами, которые он создал. Это средство по­зволяет поддерживать среды, включая Win32 и POSIX, разрешающие насле­дование ресурсов.

При завершении процесса соответствующий объект-процесс становится кандидатом на удаление из системы (в зависимости от того, используется ли он все еще другим процессом, как будет описано далее). Прежде чем удалить

Рис. 3-8. Совместное использование объекта.

объект-процесс, диспетчер объектов вызывает метод "удалить" для объектов-процессов, который закрывает все описатели в таблице объектов процесса.