Оригинальный DVD-ROM: eXeL@B DVD !
eXeL@B ВИДЕОКУРС !

ВИДЕОКУРС ВЗЛОМ
выпущен 12 ноября!


УЗНАТЬ БОЛЬШЕ >>
Домой | Статьи | RAR-cтатьи | FAQ | Форум | Скачать | Видеокурс
Новичку | Ссылки | Программирование | Интервью | Архив | Связь

О платформе .Net

Обсудить статью на форуме

Массу крэкерских инструментов, видеоуроков и статей вы сможете найти на видеокурсе от нашего сайта. Подробнее здесь.

Автор: n|m{iNT3 TEAM} <nim@int3.ru>

Main


В определенный момент времени исторически сложилась ситуация, когда на рынке высоких компьютерных технологий появились процессоры не совмистымые с x86 или совместимые, но ценой большой потери производительности, например например процессоры стандарта ia64. Так же появились процессоры, архитектура которых давала бы больший прирост производительности если бы компиляторы учитывали особенностиили этих процессоров, например процессоры ia32(64bit) или AMD(3DNOW и т.п.). Для того, что бы извлечь наибольшую производительность, разработчики делали несколько копий исполняемых файлов, откомпелированных под разное железо. Точно такая же ситуация ждала разработчиков, если программа должна была выполняться на разных операционных системах или на все возможных мобильных устройствах. В связи с этим было несколько больших минусов. Во первых увеличивался обьем дистрибутива, в одном дистрибутиве были файлы для разного железа и таких дистрибутивов было несколько, для разных операционных систем. Во вторых это увеличивало время и стоимость разработки, что естественно влияло на стоимость программы. Для решения данных проблем, была предложенна замечательная идея компиляции программы в два этапа. Первый этап компиляции заключался в переводе исходного кода программы в некий байт-код. Второй этап компеляции, при котором будет создан машинный код, должен происходить непосредственно на платформе, на которой эта программа и будет работать. Преимущества данного метода очевидно. Программа будет компилироваться непосредственно в машинный код, с учетом всех особенностей железа и операционной системы. За счет этого достигается наивысшая производительность программы, сокращат размер дистрибутива и избавляет разработчиков от головной боли. Воплощением данной идеи стала платформа .Net, которая была разработанна компанией Microsoft. Программа написанная для платформы .Net может работать везде где установленна эта платформа, например .Net программа работающая в операционной системе Windows, может с таким же успехом работать в любой операционной системе семейства юникс или на мобильном телефоне, однако управляемый код будет выполняться только под определенной операционной системой, если он вызывает специфические для платформы внутренние API или специфическую для платформы библиотеку классов. Изначально Microsoft выпустила три языка программирования для платформы .Net, это C#, Visual Basic и managed C++, они входят в поставку Visual Studio .Net. (см. картинку vs.bmp). Visual Basic .Net (VB.NET) является продолжением VB6, но честно признаться все что от него осталось это знакомый синтаксис. Когда я стал знакомиться с VB.NET мне показалось, что язык VB сделал такой же качественный скачок как и при переходе с QBasic на VB1. На данный момент VB активно развивается и имеет уже девятую версию. C++ претерпел не лучшие изменения на мой взгляд, когда его интегрировали в Visual Studio .Net, ужасный синтаксис стал еще ужасней, но у managed C++ есть единственное большое преимущество, это единственный язык платформы .Net который поддерживает ассемблерные вставки, в остальном одни недостатки. C# это новый язык и лучший на мой взгляд. Он вобрал в себя лушие стороны простоты VB и профессионализма С++. Познее было написанно множество языков для платформы .Net, по некоторым данным на сегодняшний день существует уже 40 таких языков. Итак программа написанная для платформы .Net компилируется в некий псевдо-код, который называется MSIL. Он включает в себя всю необходимую информацию о коде. Это обстоятельство позволяет платформе целиком и полностью управлять программой, именно по этому такие программы называют еще управляемыми. Разработчикам предоставленны средства, с помощью которых они могут повышать безопастность кода. Например они могут запретить доступ своей программы к реестру или к файлам, с помощью атрибутов доступа. Эти атрибуты могут быть применены как к программе целиком так и к отдельным ее частям. Контроль этих ограничений происходит на уровне платформы .Net. Второй этап компеляции программы(в машинный код) происходит при запуске программы. Но есть определенная особенность этой компеляции, программа не компилируется целиком! Компелируется только тот код, который должен выполнятся в данный момент. Это реализовывается за счет заглушек, при старте программы создаются заглушки на все методы программы, когда один из таких методов будет вызванн заглушка вызовет компелятор, который в свою очередь скомпелирует тело метода. На это соответственно требуется время, но это происходит только один раз т.е. после компеляции компелятор изменяет заглушку так, что выполнение передается в расположение машинного кода. Последующие вызовы метода, откомпилированного по требованию, передаются прямо в ранее созданный машинный код, что уменьшает время, необходимое для выполнения кода. Эта технология получила название JIT (Just In Time) если по русски, то отложенная компиляция или компеляция по требованию. Важным преимуществом платформы .Net является возможность разработки программ на разных .Net языках программирования. Это достигается за счет того , что платформа предоставляет систему общих типов, определенных средой выполнения, и следующих правилам среды выполнения при определении новых типов, а также при создании, использовании, сохранении и привязки к типам.

О сборках


Сборки предназначены для упрощения развертывания приложений и для решения вопросов, связанных с отслеживанием версий, которые могут возникнуть при использовании приложений, основанных на компонентах. Многие пользователи и разработчики знакомы с вопросами отслеживания версий и развертывания, которые возникли в сегодняшних системах, основанных на компонентах. Речь идет о так называемом DLLHALL. Некоторые пользователи были безумно счастливы, когда после установки одной программы пара других начинали работать неправильно или переставали работать вовсе. Многие разработчики потратили бесчисленные часы, пытаясь для активации COM-класса сохранить в целостности все необходимые данные системного реестра.

Для приложений Win32 при отслеживании версий существуют две проблемы:
1. Правила отслеживания версий не могут быть определены между частями приложения; они задаются операционной системой. Существующий подход основывается на обратной совместимости, которую часто трудно гарантировать. Определения интерфейсов должны быть статическими и публикуемыми однократно, а единая часть кода должна обеспечивать обратную совместимость с предыдущими версиями. Следовательно, код обычно создается таким образом, что в любой заданный момент времени на компьютере может присутствовать и выполняться только одна версия кода.
2. Не существует пути поддержки целостности между наборами компонентов, собранных вместе, и набором, присутствующим на компьютере в момент выполнения.
Эти два вопроса отслеживания версий вместе порождают конфликты DLL, когда установка одного приложения может непредумышленно нарушить работу другого существующего приложения, поскольку определенный устанавливаемый программный компонент или DLL не полностью совместим с предыдущей версией. При возникновении данной ситуации в системе отсутствуют средства поддержки, направленные на диагностику и исправление ошибки.


Многие проблемы разработки были решены с помощью сборок .NET Framework. Поскольку сборки являются самодокументирующимися компонентами, не зависящими от данных системного реестра, они не оказывают никакого влияния на установку приложений. Кроме того, сборки упрощают удаление и копирование приложений. Посути для установки любого .Net приложения требуется просто скопирывать папку с программой и создать ярлык на рабочем столе :). Физический смысл сборки заключается в том, что одна сборка это один исполняемый файл, либо exe либо dll. Так же существует системный кеш сборок, он распологается по адресу %WINDIR%\assembly\. В этом кеше хранятся сборки которые не имеет смысла распространять вместе с программой т.к. эти сборки входят в стандартную поставку дистрибутива .Net Framework.

В общем случае статическая сборка может состоять из четырех элементов:


-Манифест сборки, содержащий ее метаданные.
-Метаданные типов.
-Реализующий типы код на промежуточном языке MSIL.
-Набор ресурсов.


Обязательным является лишь манифест сборки, однако остальные типы ресурсов необходимы для обеспечения требуемой функциональности сборки. Существует несколько способов группировки этих элементов в сборку. Все эти элементы могут быть сгруппированы в единый физический файл, как показано на следующей иллюстрации. (смотри картинку assemblyover1.gif ) Кроме того, элементы сборки могут содержаться в нескольких файлах. Эти файлы могут быть модулями откомпилированного кода (.netmodule), ресурсами (например, файлами .bmp или .jpg) или другими файлами, которые необходимы приложению. Сборка из нескольких файлов создается, если необходимо собрать модули, написанные на различных языках, и оптимизировать загрузку приложения, выделяя редко используемые пользовательские типы в модуль, который будет загружаться только при необходимости. На следующей иллюстрации разработчик гипотетического приложения выделил в отдельный модуль некоторый вспомогательный код, а ресурс большого объема (.bmp-рисунок) оставил в первоначальном файле. При использовании .NET Framework загрузка файла выполняется только при ссылке; размещение в отдельном файле кода, ссылки на который используются редко, оптимизирует процесс загрузки кода. (смотри картинку assemblyover2.gif) На этой иллюстрации все три принадлежащих сборке файла описаны в манифесте сборки, который содержится в файле MyAssembly.dll. Для файловой системы они являются тремя различными файлами. Стоит отметить, что файл Util.netmodule был откомпилирован как модуль, поскольку он не содержит данных о сборке. При создании сборки ее манифест был добавлен к файлу MyAssembly.dll, что указывает на связь сборки с файлами Util.netmodule и Graphic.bmp.При проектировании исходного кода необходимо принять определенные решения о способе разделения функций приложения между одним или несколькими файлами. При проектировании кода .NET Framework необходимо принять аналогичные решения о способе разделения функций между одной или несколькими сборками.


Домены приложений


Операционные системы и исполняющие среды обычно содержат определенные средства изоляции приложений друг от друга Эта изоляция необходима, чтобы гарантировать, что код, выполняемый одним приложением, не сможет в процессе своей работы на работу других, не связанных с ним приложений. Домены приложений предоставляют платформе .NET безопасные и гибкие блоки обработки, которые могут использоваться для изоляции отдельных приложений. Домены приложений обычно создаются хостами исполняющей среды, которые отвечают за загрузку общеязыковой среды выполнения перед запуском приложения. Исторически сложилось так, что для разделения приложений, выполняющихся на одном компьютере, используются границы процессов. Каждое приложение загружается в отдельный процесс, который отделяет его от других приложений, выполняющихся на том же самом компьютере. Приложения оказываются отделенными друг от друга, поскольку адреса в памяти привязаны к приложению; бессмысленно использовать в процессе указатель, передаваемый ему из другого процесса. Кроме того, прямые вызовы между процессами невозможны. Вместо этого необходимо использовать прокси, который позволяет реализовать межпроцессные вызовы. Перед запуском управляемый код должен пройти процесс проверки. В процессе проверки определяется, может ли код предпринимать попытки обращения к неверным адресам памяти или осуществлять другие действия, которые могут привести к нарушению правильной работы процесса, в котором выполняется этот код. Код, прошедший проверку, называется строго типизированным. Возможность проверки кода на строгую типизацию позволяет платформе .Net обеспечивать такой же высокий уровень изоляции процессов друг от друга, как при использовании границ процессов, при значительно более низких затратах по производительности. В одном процессе можно запустить несколько доменов приложений с таким же уровнем изоляции, какой обеспечивают отдельные процессы, но без дополнительных издержек на межпроцессные вызовы или переключение между процессами. Возможность выполнения нескольких приложений в одном процессе значительно повышает масштабируемость серверов. Изоляция приложений также играет важную роль в обеспечении безопасности. Так, например, можно запустить элементы управления нескольких веб-приложений в одном процессе обозревателя так, что эти элементы управления не смогут получить доступ к данным и ресурсам друг друга. Изоляция приложений при помощи доменов приложений имеет следующие преимущества:

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

2. Можно прекратить выполнение отдельных приложений, не останавливая процесс целиком. Использование доменов приложений позволяет выгружать код, используемый отдельным приложением. Выгружать отдельные сборки или типы невозможно. Выгрузить можно только домен целиком.

3. Код, используемый одним приложением, не может иметь непосредственного доступа к коду или ресурсам другого приложения. Общеязыковая среда выполнения реализует это разделение, предотвращая прямые вызовы между объектами в различных доменах приложений. Объекты, передаваемые от домена к домену, копируются или взаимодействуют через прокси. Если объект копируется, вызов этого объекта становится локальным. Таким образом, вызывающая программа и объект, с которым она взаимодействует, находятся в одном домене приложения. Если доступ к объекту осуществляется через прокси, осуществляется удаленный вызов объекта. В этом случае вызывающая программа и объект, с которым она взаимодействует, находятся в разных доменах приложений. Междоменные вызовы используют ту же инфраструктуру удаленных вызовов, что и вызовы между двумя разными процессами или двумя разными машинами. По существу, для поддержки правильной JIT-компиляции вызова метода метаданные используемого объекта должны быть доступны для обоих доменов приложений. Если вызывающий домен не имеет доступа к метаданным вызываемого объекта, компиляция может привести к сбою с генерацией исключения типа System.IO.FileNotFound. Механизм определения способов междоменного доступа для объекта зависит от объекта. Если ты хочешь получить дополнительные сведения смотри описание класса MarshalByRefObject.


Библиотека классов .NET Framework


Библиотека классов включает в себя средства для решения практически для любой задачи. Я сделаю краткий обзор этой библиотеки. Пространство имен System.IO содержит классы, позволяющие осуществлять чтение и запись в файлы и потоки данных, а также классы для работы с файлами и папками. Пространство имен(Namespace) это логическая группировка классов в единую группу классов, которые решают схожие по назначению задачи. Что бы продемонстрировать все простоту написания кода на C#, приведу пример метода который сохраняет, переданный в виде параметра, байтовый массив в файл:


void SaveByteArray (byte[] buffer)
{
	SaveFileDialog sfd = new SaveFileDialog();
	if (sfd.ShowDialog() == DialogResult.OK)
	{
		System.IO.FileStream fs = sfd.OpenFile();
		fs.Write(buffer, 0, buffer.Length);
		fs.Close();
	}
}


Пространство имен System.Collections содержит интерфейсы и классы, которые определяют различные коллекции объектов, такие как списки, очереди, двоичные массивы, хеш-таблицы и словари. Пространство имен System.Diagnostics предоставляет классы, позволяющие работать с системными процессами, журналами событий и счетчиками производительности. Пространство имен System.Reflection содержит классы и интерфейсы, обеспечивающие управляемое представление загруженных типов, методов и полей с возможностью динамического создания объектов и вызова методов. Пространство имен System.Security.Cryptography предоставляет службы криптографии, содержащие безопасную кодировку и декодировку данных, а также многие другие операции, например хеширование, генерирование случайных чисел и проверку подлинности сообщений. Пространство имен System.Security.Permissions определяет классы, которые управляют доступом к действиям и ресурсам на основании политики. Пространство имен System.Threading содержит классы и интерфейсы, которые дают возможность программировать в многопоточном режиме. Пространство имен System.Windows.Forms содержит классы для создания приложений Windows, которые получают преимущество при применении возможностей пользовательского интерфейса, доступных в операционной системе Microsoft Windows. Также это пространство имен содержит основные элементы управления, например Button, ListBox, Combobox, CheckBox, Textbox, etc.. Пространство имен System.Resources предоставляет классы и интерфейсы, позволяющие разработчику создавать, сохранять и управлять различными зависящими от культуры ресурсами, используемыми в приложении. Одним из наиболее важных классов в пространстве имен System.Resources является класс ResourceManager. Класс ResourceManager предоставляет пользователю доступ и управление ресурсами, содержащимися в главной сборке, также как и ресурсами сопутствующих сборок. Методы ResourceManager.GetObject и ResourceManager.GetString используются для получения объектов и строк, принятых в данной культуре. System.Data Пространство имен состоит в основном из классов, входящих в архитектуру ADO.NET. Архитектура ADO.NET позволяет выполнять сборку компонентов, эффективно работающих с данными из различных источников. В случае отключенного сценария (например, Internet) ADO.NET предоставляет средства, позволяющие запрашивать, обновлять и согласовывать данные в многоуровневых системах. Архитектура ADO.NET также применена в приложениях клиента, таких как Windows Forms или страницы HTML, созданных ASP.NET. System.Web осуществляет поддержку классов и интерфейсов, которые обеспечивают взаимодействие между обозревателем и сервером. Пространство имен включает класс HttpRequest, предоставляющий развернутые сведения о текущем запросе HTTP, класс HttpResponse, управляющий выводом данных HTTP для клиента, и класс HttpServerUtility, с помощью которого можно получить доступ к программам и процедурам сервера. System.Web также включает классы для операций с файлами cookie, передачи файлов, исключения сведений и управления выходными данными кэширования. И это далеко не полный список (смотри картикуEnumNamespaces.GIF).

Взломо устойчивость кода

.NET программ довольно высока. Разработчикам больше нет необходимости делать проверки на переполнение буфера. Недавно один мой знакомый спросил меня: "Каким образом в .Net программах подсчитывается длинна(Length) строки, так же как в программах С++, по 00-байту?", на что я ответил что длинну строки определяет свойство Length, а не строка определяет его ;). Этот ответ его не обрадовал :). Поскольку данное обстоятельство делает невозможным переполнение буфера, в .NET под любую строку будет созданн буфер соответствующий любому размеру строки в независимости от ее содержания. Даже если и будет найден способ внедрения шелл-кода, то потенциального хакера ждут определенные сложности т.к. в .Net программах запрещенно выполнение кода в хипах(heaps) и в стеке, что делает саму возможность переполнения бессмысленной. Кроме того есть дополнительные средства защиты, о них я уже говорил в начале статьи, это атрибуты привелегий кода, с помощью которых можно запретить программе выполнять потенциально опастные действия, например можно запретить доступ программы к реестру поставив атрибут:[System.Security.Permissions.RegistryPermission(System.Security.Permissions.SecurityAction.Deny)]. Если гипотический шелл-код попробует обратится к реестру в контексте данной прогрыммы, то возникнет исключение. Более того запретив обращение к реестру во всей прорамме, можно определить атрибут для класса или метода, которым все же будет разрешенн доступ к реестру и то только к определенным ключам :), [RegistryPermissionAccess.Write Or RegistryPermissionAccess.Read, "HKEY_LOCAL_MACHINE\HARDWARE\DESCRIPTION\System\FloatingPointProcessor\0")]


В заключение

хотел бы сказать, что платформа .Net все больше захватывает расположение разработчиков. По не проверенным данным следующая после Windows Vista будет целиком написанна на .Net. Уже сейчас ведутся эксперементальные разработки в этом направлении, что бы ознакомиться с ними посмотри http://research.microsoft.com/os/singularity/ . Программирование в .Net исключает большое количество ошибок, за счет хорошо продуманного ООП, а принудительно-рекомендательный характер платформы, делает код более понятным и соответственно облегчает его поддержку в будующем. Я уже забыл о тех временах, когда добавляя незначительную деталь в программе, можно было получить целую серию багов, для отладки которых приходится неделю отлаживать программу, и нередко появлялось желание переписать все с нуля. В общем, потратив немного времени на ее изучения, ты врятли останешься разочарованным.




Обсуждение статьи: О платформе .Net >>>


Комментарии к статье: О платформе .Net


Материалы находятся на сайте https://exelab.ru



Оригинальный DVD-ROM: eXeL@B DVD !


Вы находитесь на EXELAB.rU
Проект ReactOS