Я использовал С# в Visual Studio с .NET, и я немного поиграл с Mono на openSUSE Linux, но я действительно не понимаю, как это работает.
Если я пишу приложение в Windows на .NET, как это связано с Mono? Я не могу просто выполнить файл Windows.exe на Linux без Wine, так что это не помогает мне выполнять приложения, разработанные в Windows.
Является ли цель чисто иметь эквивалент библиотеки .NET для Linux (и других), чтобы упростить кросс-платформенную разработку? Например, если бы я был бизнесом и хотел связаться с клиентами Linux, но действительно хотел использовать .NET, то Моно должен быть моим выбором? Или есть что-то еще, что мне не хватает?
Ответ 2
Это старый вопрос (с уже выбранным ответом), но я не верю, что на этот вопрос действительно был дан ответ.
Сначала немного фона...
Как работает .NET?
Традиционный Windows.EXE файл представляет собой двоичный файл, который представляет собой серию инструкций машинного языка, которые понимает ваш компьютер, и который вызывает вызовы в API Win32, которые являются частями Windows, которые предоставляют услуги, которые могут использовать приложения. Используемый машинный язык очень специфичен для вашего компьютера, а вызовы Win32 делают исполняемый файл очень зависимым от Windows. Исполняемый .NET не такой.
Важно понимать, что исполняемый файл .NET(файл .EXE) на самом деле не является родным приложением Windows. Windows сама не понимает, как запустить код в исполняемом файле .NET. Ваш компьютер тоже не понимает.
Как и Java, приложение .NET составлено из инструкций на языке CIL (Common Intermediate Language), который вы можете представить как машинный язык для идеального компьютера, который на самом деле не существует. В .NET реализация программного обеспечения этой идеализированной машины называется Common Language Runtime (CLR). Эквивалент в Java-мире называется виртуальной машиной Java (JVM). В Java эквивалент CIL называется байт-кодом Java. CIL иногда называют MSIL (Microsoft Intermediate Language).
CIL предназначен для работы на CLR (идеализированной машине), но в остальном независим от платформы, что означает, что CIL не заботится о том, какой у вас компьютер или в какой операционной системе вы работаете.
Так же, как вам нужна собственная версия Java JVM на каждой платформе, на которой вы хотите запустить Java, вам нужна собственная версия CLR для запуска исполняемых файлов .NET CIL. CLR является родным приложением Windows, как и традиционные файлы Win32 EXE, описанные выше. Сама среда CLR специфична для реализации Windows и компьютерной архитектуры, на которой она была разработана для запуска.
Не имеет значения, с какого языка .NET вы начинаете (С#, VisualBasic, F #, IronPython, IronRuby, Boo и т.д.), все они скомпилируются до байт-кода CIL. Вы можете легко "разобрать" программу CIL в форме объектно-ориентированного языка ассемблера, который легко читается людьми. Вы можете написать программу непосредственно в CIL, но мало кто это делает.
В Windows CLR скомпилирует этот код CIL Just-in-Time (JIT) сразу при запуске исполняемого файла - непосредственно перед запуском кода. Это означает, что байт-код CIL преобразуется (скомпилирован) в фактический машинный код, который запускается изначально на вашем компьютере. Эта часть CLR называется компилятором JIT или часто просто JIT.
На сегодняшний день Microsoft выпустила четыре версии CLR: 1.0, 1.1, 2.0 и 4.0. Вы должны иметь правильную версию CLR, установленную на вашем компьютере, если вы хотите запустить исполняемые файлы .NET, предназначенные для этой среды выполнения. CLR 2.0 поддерживает приложения .NET 2.0, 3.0 и 3.5. Для других версий .NET версия .NET полностью соответствует версии CLR.
В дополнение к JIT/CLR.NET предоставляет множество библиотек (сборок), которые составляют остальную часть платформы .NET, и предоставляют множество возможностей и служб, к которым могут обращаться приложения .NET. Подавляющее большинство этих сборок - это чистый код CIL, который работает на CLR. В Windows некоторые выполняют вызовы в Win32 API. Когда вы устанавливаете .NET, вы устанавливаете CLR, библиотеки классов (фреймворк) и набор инструментов для разработки. Каждая версия CLR обычно требует полного набора этих "каркасных" сборок. В некоторых версиях .NET(например, 3.0 и 3.5) добавлены дополнительные сборки фреймов без обновления CLR или существующих сборок, связанных с этой CLR.
Формат файла Portable Executable (PE), который поставляется в файле .EXE Windows, содержит заголовок, который описывает исполняемый файл, и идентифицирует файл как файл .NET или собственный файл Win32. Когда Windows пытается запустить .NET файл, он видит этот заголовок и автоматически вызывает CLR от вашего имени. Вот почему .NET EXE файлы появляются изначально на Windows.
Хорошо, так как работает Mono?
Mono реализует CLR на Linux, Mac и других платформах. Время выполнения Mono (CLR) - это родное приложение, написанное в основном на языке C, и скомпилированное до кода машинного языка для компьютерной системы, на которой предназначен запуск. Как и в Windows, время выполнения Mono зависит от операционной системы и типа используемой вами машины.
Как и в Windows, среда выполнения Mono (CLR) компилирует байт-код CIL в исполняемом файле .NET. Собственный код, который ваш компьютер может понять и выполнить. Таким образом,.NET файл является таким же "родным" для Linux, как и для Windows.
Чтобы переносить Mono в новую архитектуру, вам необходимо портировать JIT/CLR. Это похоже на перенос любого родного приложения на новую платформу.
Насколько хорошо .NET-код работает на Linux или Mac, на самом деле просто вопрос о том, насколько хорошо CLR реализуется в этих системах. Теоретически Mono CLR может выполнять код .NET в этих системах намного лучше, чем версия MS.NET для Windows. На практике реализация MS обычно превосходит (хотя и не во всех случаях).
В дополнение к CLR, Mono предоставляет большинство остальных библиотек (сборок), которые составляют платформу .NET. Как и в случае с версией Microsoft.NET(на самом деле, более того), сборники Mono предоставляются как байт-код CIL. Это позволяет извлекать файл *.dll или *.exe из Mono и запускать его без изменений в Windows, Mac или Linux, поскольку CIL является "родным" языком реализации CLR в этих системах.
Как и в Windows, Mono поддерживает несколько версий CLR и связанных сборок:
Очень ранние версии Mono (до 1.2?) поддерживали только CLR 1.0 или 1.1.
Mono не поддерживала большие фрагменты версии 2.0 до версии 2.0.
Моно версии до версии 2.4 поддерживаются как приложениями CLR 1.1, так и CLR 2.0.
Начиная с Mono 2.6, был добавлен CLR 4.0, но CLR 2.0 по-прежнему по умолчанию.
Начиная с Mono 2.8, CLR 4.0 стал по умолчанию и CLR 1.1 больше не поддерживается.
Mono 2.10 продолжает использовать CLR 4.0 по умолчанию, а также поддерживает CLR 2.0.
Как и в случае с реальной .NET(но в гораздо меньших масштабах), есть некоторые сборки Mono, которые вызывают в родные библиотеки. Чтобы сделать сборку System.Drawing в Mono, команда Mono написала программу Linux для имитации части GDI + Win32 API в Linux. Эта библиотека называется "libgdiplus". Если вы скомпилируете Mono из исходного кода, вы заметите, что вам нужно собрать этот файл libgdiplus, прежде чем вы сможете построить "mono". Вам не нужно "libgdiplus" в Windows, потому что часть GDI + в Win32 API уже входит в состав Windows. Полный порт Mono для новых платформ требует, чтобы эта библиотека libgdiplus также была перенесена.
В тех областях, где дизайн библиотеки .NET слишком сильно зависит от дизайна Windows и плохо подходит для таких систем, как Mac или Linux, команда Mono написала расширения для платформы .NET. Расширения Mono также являются просто байт-кодом CIL и, как правило, отлично работают на .NET.
В отличие от Windows, Linux обычно не обнаруживает исполняемые файлы .NET и запускает CLR по умолчанию. Пользователь должен обычно запускать CLR напрямую, набрав "mono appname.exe" или что-то подобное. Здесь "mono" - это приложение, которое реализует CLR, а "appname.exe" - это EXE файл, который содержит исполняемый код .NET.
Чтобы пользователи стали проще, приложения Mono часто завертываются в оболочку script, которая запускает CLR. Это скрывает тот факт, что среда CLR используется так же, как в Windows. Также можно сказать, что Linux запускает CLR, когда встречается файл, использующий формат файла PE. Обычно это не делается, поскольку формат файла PE также используется для собственных исполняемых файлов Win32 Windows, которые, конечно же, не поддерживают CLR (Mono).
Нет никакой технической причины, по которой Linux-пусковая установка не может использоваться Linux, которая затем запускает либо систему, которая понимает собственный код Windows (например, Wine), либо CLR (Mono), если это необходимо. Это просто не было сделано, насколько мне известно.
Назад и вперед
Любой код .NET, который придерживается "полностью управляемого" кода, что означает, что он не вызывает код не-.NET, должен отлично работать на Mono на всех платформах. Я обычно использую скомпилированные сборки .NET из Windows (для которых у меня нет кода) на Linux и Mac.
Я также могу взять любой код, который я компилирую на Mono, и запустить его на .NET в Windows. Я могу предоставить клиенту некоторый код, который я скомпилировал с помощью Mono, и не волнуйтесь, например, если он находится на 32-битной или 64-битной Windows. Клиент должен иметь правильную версию .NET(право CLR), установленную для курса. CLR 2.0 работает очень долго, и вы можете поспорить, что почти все пользователи Windows установлены. Компиляторы Mono и другой код также являются просто исполняемыми файлами CIL, и поэтому они отлично работают в Windows, если хотите.
Моно совместимость достаточно хороша, что большие куски реального кода Microsoft, такие как ASP.NET MVC, могут быть приняты (если это законно) из реальной версии MS.NET и выполняются на Mac или Linux. В общем, команда Mono отлично справилась с реализацией как CLR, так и остальной части фреймворка (библиотеки классов/сборки).
ASP.NET
В Windows Internet Information Server (IIS) знает, как звонить в CLR для выполнения .NET как части веб-приложения. В Linux/Mac есть модуль Apache (mod_mono), который предоставляет аналогичные возможности веб-серверу Apache. Это приложение написано на C, а также должно быть перенесено на новые архитектуры.
Портирование моно
В этом обсуждении были обнаружены части Mono, которые создаются как "родные" исполняемые файлы и должны существовать в системе, на которой вы хотите запускать приложения .NET.
- CLR (включая JIT-компилятор) - обычно известный как Mono
- libgdiplus (для систем, которые не поддерживают API GDI + [только для Windows])
- mod_mono (чтобы Apache мог вызывать веб-приложения CLR для .NET)
Эти три компонента с добавлением библиотек классов предоставляют среду .NET, которая выглядит "родной" исполняемым файлам .NET, которые вам нужно запустить.
Так работает Mono.