Пишем игрушечную ОС на C#

image

Введение


Здравствуй, хабрасообщество! Не знаю, будет ли этот топик полезен кому-либо, но надеюсь, что вы почерпнете здесь для себя что-то новое. Цель данной статьи — познакомить хабраюзеров с проектом COSMOS и показать, как можно реализовать собственную ОС, заточенную под Ваши нужды. Кому интересно — прошу под кат.

Знакомимся с COSMOS

Вот что нам говорит википедия:
Cosmos является бэкронимом от C# Open Source Managed Operating System (рус. «Управляемая операционная система с открытым кодом на C#»). Cosmos в настоящее время не стремится стать полноценной операционной системой, а скорее набором инструментальных средств, позволяющим другим разработчикам легко и просто создавать свои собственные операционные системы, или, как сказал один из руководителей проекта, действовать в качестве «операционной системы типа Lego». Он также функционирует как абстракционный слой, скрывающий значительную часть работы внутренних аппаратных средств.
Cosmos является конструктором, который позволяет полностью отвлечься от низкоуровнего программирования и писать на чистом C#.

Что нам потребуется?

В первую очередь, нам понадобится Microsoft Visual Studio 2010, предпочтительно Pro. Если Вы используете Express-версию, то Вам понадобится установить Microsoft Visual Studio Shell. Скачать все это добро:

Так же нам потребуется скачать и установить сам Cosmos User Kit. Кроме того, нам потребуется любая виртуальная машина для тестирования нашей операционной системы. Лично я использую QEMU и Virtual Box.

Начинаем кодить


Расчехляем Visual Studio, жмем «Создать проект… » и видим такое окошечко:
Выбираем Cosmos C# Library и нажимаем ОК, после этого откроется окно со
стандартным кодом
using System;
using System.Collections.Generic;
using System.Text;
using Sys = Cosmos.System;

namespace CSharpKernel1
{
    public class Kernel : Sys.Kernel
    {
        protected override void BeforeRun()
        {
            Console.WriteLine("Cosmos booted successfully. Type a line of text to get it echoed back.");
        }

        protected override void Run()
        {
            Console.Write("Input: ");
            var input = Console.ReadLine();
            Console.Write("Text typed: ");
            Console.WriteLine(input);
        }
    }
}

Здесь мы будем писать логику нашей операционной системы. Для корректной работы вашей ОС требуется в каждом проекте выбрать конфигурацию Release! Иначе он просто не будет работать.
Стандартный код нам не понадобится, поэтому смело выпиливайте его! А теперь приступим непосредственно к написанию кода. Чуть не забыл упомянуть, что код может использовать любые объекты библиотек .NET Framework, которые поддерживает Cosmos (либо переводом объекта в машинный код, либо каждую из его частей). Он также может вызвать любую библиотеку, встроенную в Cosmos. Для начала разберемся с классом Kernel.
Kernel
using System;
using System.Collections.Generic;
using System.Text;
using Sys = Cosmos.System;

namespace CSharpKernel1
{
    public class Kernel : Sys.Kernel
    {
        protected override void BeforeRun() /*Этот метод вызывается самым первым и выполняется только один раз. Его удобно использовать для инициализации компонентов. */
        {
            Console.ForegroundColor = ConsoleColor.Green; 
            //Цвет текста - зеленый
            Console.WriteLine("Welcome to HabrOS! Type \"help\" and then press \"ENTER\" to get some help.");
            //Выводим на экран приветствие
            Console.ForegroundColor = ConsoleColor.White;
            //Цвет текста - белый, как и по умолчанию. ВНИМАНИЕ! Метод Console.ResetColor() НЕ будет работать!
        }

        protected override void Run() //Данный метод вызывается постоянно, в нем мы разместим логику.
        {
        }
    }
}

Это, так сказать, каркас нашей ОС. Теперь добавим в проект класс CommandPrompt, который будет отвечать за ввод и выполнение команд.
CommandPrompt
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace ScorpionOS
{
    class CommandPrompt
    {
        public static void Read() { //Этот метод будет считывать с клавиатуры вводимый юзером текст
            Console.Write("->");
            String ln = Console.ReadLine(); //Считываем введенный текст и записываем его в переменную ln
            switch (ln)
            {
                case "help": //Помощь
                    Console.ForegroundColor = ConsoleColor.Cyan; //Цвет текста - бирюзовый
                    Console.WriteLine("To run a program, type name of program and press enter.");
                    Console.WriteLine("The following commands are available:");
                    Console.WriteLine("help - get help\nabout - information about the operating system\nshutdown - power off the computer\nreboot - reboot the computer");
                    Console.ForegroundColor = ConsoleColor.White; //Не забываем вернуть стандартный цвет
                    break;
                case "about": //Об ОС
                    Console.WriteLine("HabrOS ver. 0.01 beta.");
                    break;
                case "shutdown": //Выключение компьютера
                    Cosmos.Sys.Plugs.Deboot.ShutDown();
                    break;
                case "reboot": //Перезагрузка
                    Cosmos.Sys.Plugs.Deboot.Reboot();
                    break;
                default: //Любая другая введенная строка
                    Console.ForegroundColor = ConsoleColor.Red; //Думаю, здесь уже все понятно
                    Console.WriteLine("ERROR: Command not found");
                    Console.ForegroundColor = ConsoleColor.White;
                    break;
            }
        }
    }
}

Для корректной работы данного класса нам требуется добавить ссылку на библиотеку Cosmos.Sys.Plugs.dll. Она находится здесь: С:\папка_установки_cosmosUserKit\\Build\VSIP.
Ну что же, осталась самая малость: добавляем в метод Run() класса Kernel вызов метода CommandPrompt.Read():
Run()
protected override void Run()
        {
            CommandPrompt.Read(); //Считываем введенные с клавиатуры данные
        }

Вот и все. Мы реализовали простейшие команды ОС, теперь остается только скомпилировать наш проект и запустить его на виртуальной машине.
Для этого жмем Построение->построить решение, сохраняем наш проект и открываем Visual Studio 2010 Shell. Нажимаем создать проект и видим данное окно:
Создаем Cosmos Project, и в References добавляем ссылку на .dll — файл, получившийся в результате построения проекта. Этот длл находится в папке нашего первого проекта\bin\debug. ВАЖНО! Если у вас не установлен VMWarePlayer или Workstation, то открываем свойства проекта и выбираем ISO Image, как показано ниже:image
После этого так же нажимаем построить решение, ждем, так как построение выполняется сравнительно долго, и после успешного построения закрываем Visual Studio Shell, не забыв при этом сохранить проект. В итоге в папке второго проекта\bin\debug мы найдем .iso — файл. Его можно записать на диск или на флешку и грузить нашу ОС на реальном железе. Можете запустить в виртуальной машине нашу ОС и полюбоваться результатом :)

Итог


Вот и все! Я надеюсь, что вы узнали что-то новое, прочитав эту статью. Постараюсь ответить на все Ваши вопросы в комментариях, если что-то будет непонятно.
Поделиться публикацией

Комментарии 30

    +3
    У меня сильное чувство дежавю, буквально с год назад уже была статья про ОС на C# так же с использованием .NET или C#, уже точно не помню. Или Вы решили повторить славу предыдущего топика?:)
      +6


      >> май 2012

      Каждый год .NET сообщество собирает шабаш и пишет свою OS на Cosmos-е.
      –4
        +1
        Не Cosmos? Ну ладно… простите
          +3
          Моя реакция на твой комментарий.

          0
          И сколько такая ОС занимает места на диске и сколько ест оперативки?
            0
            В данном случае iso-образ весит 1,87 мегабайта, а оперативки ест очень мало — меньше мегабайта.
              +7
              и при этом вообще ничего не умеет. Программисты встраиваемых железок смотрят как-то недоумённо.
                0
                Так это голяк, для обучения, к примеру. Только ядро.
                  +1
                  раскрою страшную тайну — в 2 мегабайта флеша при очень большом желании можно утрамбовать линукс и минимальный userland.

                  Хотя я могу побыть в роли адвоката дьявола и описать примерные преимущества ОС написанной на управляемом языке, но мне неохота…
                    0
                    Одно дело с нуля писать загрузчик, ядро и так далее, и все это на ассемблере — ясное дело, что такая ОС будет весит очень мало. И для этого надо не один месяц провозиться с изучением ассемблера и прочего. А здесь от программиста требуется только знание си шарпа. Так что, думаю, плата в виде лишнего мегабайта достаточно окупается.
                      +2
                      Я не вижу смысла в таком обучении. Я вижу смысл в использовании чего-то типа cosmos в качестве тонкого рантайма для развёртывании на AWS, например, чтобы сократить накладные расходы на работу инстанса.

                      Но возможность работать с C# вместо C, не отменяет необходимости понимания принципов низкоуровневой работы с железом. Даже хуже, C# скрывает в частности работу с памятью, а эта абстракция протекает очень быстро.

                      З.Ы. Программисты люди такие, они всегда придумают новый уровень абстракции, на который можно просрать появившиеся вычислительные мощности.
                        0
                        А толку то? Все равно без знания асма он ось не напишет.
                        0
                        Зачем? Еще раз повторю: она нужна для обучения, для спортивного интереса, вряд ли кому то захочется просто так копаться в ядре линукса, чтобы построить свой shell, да и на C#, объективно, писать проще, особенно новичкам.
                          +1
                          Для обучения чему? выше я написал один из видимых мной вариантов полезного использования подобной заготовки под ОС. Так сказать заточка virtual instance под конкретную задачу с экономией на накладных расходах связанных с ОС общего назначения.
                    0
                    iso-образ весит 1,87 мегабайта, а оперативки ест очень мало — меньше мегабайта

                    В печь, РусОС — наше всё.
                  +2
                  Его можно записать на диск или на флешку и грузить нашу ОС на реальном железе.

                  Ничего себе! Как это возможно? Я думал для исполнения C# (.Net) кода необходима хост ОС (Windows или Linux) и CLR-рантайм (.Net Framework или Mono).
                    0
                    Это ирония или Вы серьезно? :)
                      +2
                      Серьезно.
                        +1
                        Там всё «просто». Есть минимальное ядро, умеющее базовый ввод-вывод, управление памятью и IPC. На его основе разворачивается ограниченное подмножество CLR которое умеет выполнять байткод.
                      0
                      Да, это возможно, так как код С# переводится в ассемблерный код, с помощью NASM. К тому же иначе не было бы смысла создавать такой проект, легче было бы создать простое консольное приложение С#.
                        0
                        Тогда почему C# не используется для создания «нативных» приложений?
                          0
                          Wikipedia: C# разрабатывался как язык программирования прикладного уровня для CLR и, как таковой, зависит, прежде всего, от возможностей самой CLR.
                          В Cosmos специально реализовано преобразование кода С# в ассемблерный код, причем реализовано не майкрософтом, а разработчиками Cosmos. Так что все вопросы к майкрософту.
                            +1
                            man Ahead-of-time compilation.
                              0
                              Почему не используют? Используют, еще как, например Xamarin умеет создавать нативные приложения под Win/Mac/Android/iOS
                          0
                          А есть аналог на С\С++?
                            0
                            Насколько мне известно, к сожалению нет.
                              0
                              Есть любительские ядра, можно также свободно дописывать нужный функционал на C\C++. Единственное нет подобной интеграции в среду.
                              –2
                              А давайте сделаем уже ОС на Qt.
                                0
                                Хабр, зачем ты следишь за мной??? В понедельник только вспомнил про проект Singularity и интереса ради скачал исходники, а тут это…
                                Жаль что проект загнулся :(

                                Только полноправные пользователи могут оставлять комментарии. Войдите, пожалуйста.

                                Самое читаемое