На этой странице возможны любые операции
|
PAGE_WRITECOPY
|
Попытки исполнения содержимого памяти на этой странице
выбывают нарушение доступа, попытка записи приводит к тому, что процессу
предоставляется "личная" копия данной страницы
|
PAGE_EXECUTE_WRITECOPY
|
На этой странице возможны любые операции, попытка записи
приводит к тому, что процессу предоставляется "личная" копия данной
страницы
|
Защита типа "копирование при записи"
Атрибуты
защиты, перечисленные в предыдущей таблице, достаточно понятны, кроме двух
последних: PAGE_WRITECOPY и PAGE_EXECUTE_WRITECOPY. Они предназначены
специально для экономного расходования оперативной памяти и места в страничном
файле. Windows поддерживает мехянизм, позволяющий двум и более процессам
разделять один и тот же блок памяти. Например, если Вы запустите 10 экземпляров
программы Notepad, все экземпляры будут совместно использовать одни и те же
страницы с кодом и данными этой программы. И обычно никяких проблем не
возникает — пока процессы ничего не записывают в общие блоки памяти. Только
представьте, что творилось бы в системе, если потоки из разных процессов начали
бы одновременно записывать в один и тот же блок памяти!
Чтобы
предотвратить этот хаос, операционная система присваивает общему блоку памяти
атрибут защиты "копирование при записи" (copy-on-write). Когда поток
в одном процессе попытается что-нибудь записать в общий блок памяти, в дело тут
же вступит система и проделает следующие операции:
Найдет
свободную страницу в оперативной памяти. Заметьте, что при первом проецировании
модуля на адресное пространство процесса эта страница будет скопирована на одну
из страниц, выделенных в страничном файле. Поскольку система выделяет нужное
пространство в страничном файле еще при первом проецировании модуля, сбои на
этом этапе маловероятны.
Скопирует
страницу с данными, которые поток пытается записать в общий блок памяти, на
свободную страницу оперативной памяти, полученную на этапе 1. Последней
присваивается атрибут защиты PAGE_WRITECOPY или PAGE_EXECUTE_WRITECOPY. Атрибут
защиты и содержимое исходной страницы не меняются.
Отобразит
виртуальный адрес этой страницы в процессе на новую страницу в оперативной
памяти.
Когда
система выполнит эти операции, процесс получит свою копию нужной страницы
памяти.
Кроме
того, при резервировании адресного пространства или передаче физической памяти
через VirtualAlloc нельзя указывать атрибуты PAGE_WRITECOPY или
PAGE_EXECUTE_WRITECOPY. Иначе вызов VirtualAlloc даст ошибку, a GetLastError вернет код ERROR_INVALID_PARAMETER. Дело в том, что эти два атрибута
используются операционной системой, только когда она проецирует образы EXE- или
DLL-файлов.