что такое виртуальная машина java

Национальная библиотека им. Н. Э. Баумана
Bauman National Library

Персональные инструменты

JVM (Java Virtual Machine)

Java Virtual Machine — виртуальная машина Java — основная часть исполняющей системы Java, так называемой Java Runtime Environment (JRE). Виртуальная машина Java исполняет байт-код Java, предварительно созданный из исходного текста Java-программы компилятором Java (javac). JVM может также использоваться для выполнения программ, написанных на других языках программирования. Например, исходный код на языке Ada может быть откомпилирован в байт-код Java, который затем может выполниться с помощью JVM.

JVM является ключевым компонентом платформы Java. Так как виртуальные машины Java доступны для многих аппаратных и программных платформ, Java может рассматриваться и как связующее программное обеспечение, и как самостоятельная платформа. Использование одного байт-кода для многих платформ позволяет описать Java как «скомпилировано однажды, запускается везде» (compile once, run anywhere).

Виртуальные машины Java обычно содержат Интерпретатор байт-кода, однако, для повышения производительности во многих машинах также применяется JIT-компиляция часто исполняемых фрагментов байт-кода в машинный код. [1]

Содержание

Спецификация JVM

В 1996-м году компания Sun выпустила первую версию документа «Голубая книга JVM», в котором описана спецификация виртуальной машины Java, ставшего де-факто отраслевым стандартом платформы Java. Благодаря этому документу появились альтернативные реализации JVM, являющиеся «разработками с чистого листа» (англ. clean room design). В качестве примера можно привести Kaffe.

Начиная с версии J2SE 5.0 изменения в спецификации JVM вырабатываются в соответствии с формализованными пожеланиями заинтересованных сторон. Процесс внесения изменений в спецификации JVM называется Java Community Process.

JVM, доступная в исходных текстах на Си от фирмы Sun, называется KVM (Kilo Virtual Machine) и доступна на их сайте.

что такое виртуальная машина java. Смотреть фото что такое виртуальная машина java. Смотреть картинку что такое виртуальная машина java. Картинка про что такое виртуальная машина java. Фото что такое виртуальная машина java

Конфликты

Конкуренция между Sun и Microsoft

что такое виртуальная машина java. Смотреть фото что такое виртуальная машина java. Смотреть картинку что такое виртуальная машина java. Картинка про что такое виртуальная машина java. Фото что такое виртуальная машина java

В начале развития платформы «Java», существовали две конкурирующие реализации Java VM:

Однако «Microsoft Java VM» не была полностью совместима со спецификацией, описанной Sun в «голубой книге JVM», и имела существенные проблемы с производительностью при работе под большими нагрузками (при большом числе одновременно выполняемых потоков) и с безопасностью.

Компания «Sun» посчитала такую ситуацию недопустимой и решила, что Microsoft занимается намеренной дискредитацией и профанацией платформы «Java» путём распространения своей версии виртуальной машины Java, обладающей вышеперечисленными недостатками. На этом основании, Sun неоднократно подавала в суд на Microsoft — и Microsoft была лишена следующих прав на реализацию:

Некоторые обозреватели компьютерных изданий полагают, что жёсткая позиция, занятая Sun по вопросу Java, могла послужить дополнительным стимулом для разработки компанией «Microsoft» собственного Windows-решения: «.NET Framework». [2]

Разногласия между Sun и IBM

В 2001 году, с целью разработки стандарта кросс-платформенных Desktop-приложений, IBM стартовала открытый проект: «Eclipse».

Фреймворк «Eclipse» был основан на предыдущей закрытой разработке: IBM «VisualAge». IBM удалось сбалансировать интересы свободного сообщества и интересы бизнеса (свои интересы) в лицензии «Eclipse Public License», признанной организацией «Free Software Foundation».

Проект успешно развивается, используется в индустрии, в значительной степени отделился от IBM в самостоятельный (см. «Eclipse Foundation»).

Sun остаётся в оппозиции к Eclipse Foundation, так же, как и к Microsoft. Формально основной причиной противоречий остаётся библиотека «Standard Widget Toolkit» (SWT), которая противоречит Sun-концепции виртуальной машины и переносимости Java-приложений.

Среда исполнения

Программы, предназначенные для запуска на JVM, должны быть скомпилированы в стандартизированном переносимом двоичном формате, который обычно представляется в виде файлов «.class». Программа может состоять из множества классов, размещённых в различных файлах. Для облегчения размещения больших программ, часть файлов вида «.class» может быть упакована вместе в так называемом «.jar»-файле (сокращение от «Java Archive»).

Виртуальная машина JVM исполняет файлы «.class» и «.jar», эмулируя данные в них инструкции следующими путями:

В наши дни, JIT-компиляция используется в большинстве JVM для достижения большей скорости. Существуют также ahead-of-time компиляторы, позволяющие разработчикам приложений перекомпилировать файлы классов в родной для конкретной платформы код.

Как и большинство виртуальных машин, Java Virtual Machine имеет stack-ориентированную архитектуру, свойственную микроконтроллерам и микропроцессорам.

JVM — экземпляр JRE (Java Runtime Environment), вступающий в действие при исполнении программ Java; по завершении исполнения, этот экземпляр удаляется сборщиком мусора. JIT — та часть виртуальной машины Java, которая используется для ускорения выполнения приложений; JIT одновременно компилирует те части байт-кода, функциональность которых аналогична, — что сокращает время, необходимое для проведения компиляции. [3]

Загрузка и установка виртуальной машины Java

Для программирования на Java можно подобрать себе IDE, хорошим выбором будет NetBeans или Eclipse.

Для начала проверим, установлена ли Java платформа на вашем компьютере. Для этого запустите удобным для вас способом утилиту для работы с командной строкой. Например, перейдите в меню «Пуск» пункт «Выполнить», в появившемся окошке введите команду «cmd» без кавычек и нажмите «ОК».

Если на компьютере уже установлена исполняемая среда Java, вывод будет примерно таким:

java version «1.6.0_18»

Java(TM) SE Runtime Environment (build 1.6.0_18-b07)

Java HotSpot(TM) Client VM (build 16.0-b13, mixed mode)

Если вывод будет сообщать об ошибке или неизвестной команде, вам безусловно необходима установка виртуальной машины. Также рекомендуется обновить установку, если версия Java на вашем компьютере ниже чем 1.6.

Есть два продукта для загрузки:

Источник

Виртуальная машина Java — что это?

что такое виртуальная машина java. Смотреть фото что такое виртуальная машина java. Смотреть картинку что такое виртуальная машина java. Картинка про что такое виртуальная машина java. Фото что такое виртуальная машина java

Все мы знакомы с понятием JVM (Java Virtual Machine). В статье мы рассмотрим, что же такое виртуальная машина Java, из чего состоит, как работает, какую имеет архитектуру. Для лучшего понимания этого вы вкратце узнаете, как устроен class-файл и каким образом виртуальная машин Java выполняет обработку и исполнение байт-кода.

JVM — это ключевой компонент платформы Java («Джава», «Ява»), который загружает, проверяет и выполняет код. Давайте вспомним, что главной задачей Java-разработчиков было создание переносимых приложений. И JVM в данном случае играет основную роль с точки зрения переносимости, так как именно она обеспечивает необходимый уровень абстракции между скомпилированной Java-программой, базовой аппаратной платформой и ОС. При этом, несмотря на такой дополнительный «слой», скорость работы приложений в Java является довольно высокой, так как байт-код, выполняемый JVM, да и она сама прекрасно оптимизированы.

Структура class-файла в Java VM

Начинается файл со стартового числа 0xCAFEBABE. Это число есть в каждом классе, и оно является обязательным флагом для Java Virtual Machine. Благодаря ему система понимает, что перед ней находится class-файл.

что такое виртуальная машина java. Смотреть фото что такое виртуальная машина java. Смотреть картинку что такое виртуальная машина java. Картинка про что такое виртуальная машина java. Фото что такое виртуальная машина javaПоследующие 4 байта class-файла включают младший и старший номера Java-версий. По сути, они идентифицируют версию формата определённого class-файла, позволяя Java VM проверять, возможна ли по отношению к нему поддержка и загрузка. При этом каждая Java VM содержит ограничение версии, которую может загрузить (более поздние версии игнорируются).

С 9-го байта идёт пул констант. В нём содержатся все константы, относящиеся к нашему классу. В каждом классе их бывает разное количество, поэтому перед массивом есть переменная, которая указывает на длину (по сути, пул констант — это массив переменной длины). А каждая константа занимает 1 элемент в массиве.

Идём дальше. Во всём class-файле константы обозначаются целочисленным индексом, а он указывает их положение в массиве. Начальной константе соответствует индекс 1, второй — 2 и т. п.

Каждый элемент из пула констант начинается с 1-байтового тега, который определяет его тип. Всё это позволяет Java VM понять, каким образом правильно обработать далее идущую константу. Для этого зарезервировано 14 типов констант.

что такое виртуальная машина java. Смотреть фото что такое виртуальная машина java. Смотреть картинку что такое виртуальная машина java. Картинка про что такое виртуальная машина java. Фото что такое виртуальная машина javaК примеру, когда тег указывает, что константа есть строка, Java VM получает значение тега № 1, обрабатывая число, следующее за тегом, как длину массива байт, которые нужно считать для получения нужной нам строки.

А прочитав блок с константами, Java VM перейдёт к следующим 2-м байтам (флагам доступа), определяющим, описывает данный файл класс либо интерфейс, является ли класс финальным.

При этом имена класса, а также имена его родительского класса сохраняются в массиве констант, и на них указывают последующие четыре байта в файле.
Чуть по-другому обстоит дело с интерфейсами. Мы знаем, что класс наследует одновременно от множества интерфейсов, поэтому хранить нужно массив ссылок на пул констант. Таким образом, за определением класса, а также его родительского класса идёт число, которое характеризует размер массива интерфейсов, плюс сам массив. И все возможные значения кодов вы можете увидеть в таблице ниже: что такое виртуальная машина java. Смотреть фото что такое виртуальная машина java. Смотреть картинку что такое виртуальная машина java. Картинка про что такое виртуальная машина java. Фото что такое виртуальная машина javaПодобную структуру имеет и очередной блок — Fields. Он начинается с 2-байтового параметра числа полей в данном интерфейсе либо классе. Далее следует массив структур переменной длины. И каждая структура включает данные об одном поле: тип, значение, имя поля. В списке отображены лишь те поля, которые объявлены классом либо интерфейсом, который определён в файле. А вот поля имплементированных интерфейсов и родительских классов здесь не присутствуют, так как задаются они в своих class-файлах.

Пришла пора поговорить о методах класса. Именно в них содержится вся логика любого приложения и весь исполняемый байт-код.

Здесь ситуация аналогична полям, описанным выше. Например, в массиве переменной длины есть структуры, в них включено полное описание сигнатуры метода: имя метода, его атрибуты, модификаторы доступа.

В последний блок включена дополнительная мета-информация, к примеру, имя скомпилированного файла. Эта информация может присутствовать, но может и не присутствовать. При каких-нибудь проблемах виртуальная машина Java просто игнорирует данный блок.

Загрузка классов

В нашем случае главный класс приложения всегда грузится системным загрузчиком. Остальные — разными пользовательскими загрузчиками. Имя загрузчика в Java VM создаёт уникальное пространство имён, потому в приложении могут находиться несколько классов, имеющих одно и то же полное имя, если их обрабатывали разные загрузчики. Именно поэтому каждый загрузчик делегирует полномочия родителю. Таким образом, перед поиском класса для загрузки он сначала пытается «понять», не был ли нужный класс загружен раньше.

Линковка в Java VM

После загрузки класса в Java VM наступает этап линковки, и делится он на 3 части: 1. Верификация байт-кода. Статический анализ кода, выполняемый один раз для класса. Происходит проверка ошибок в байт-коде. Например, проверяется корректность инструкций, переполнение стека и совместимость типов переменных. 2. Выделение памяти под статические поля с последующей их инициализацией. 3. Разрешение символьных ссылок — Java VM подставляет ссылки на другие классы, поля и методы.

Когда класс инициализируется, Java VM может начинать выполнять байт-код методов.

Итак, Java VM получает 1 поток байтовых кодов для каждого метода в классе. Сам байт-код выполняется, если данный метод вызывается во время работы приложения. Поток байт-кода метода — не что иное, как некая последовательность инструкций для Java VM. И каждая инструкция включает в себя 1-байтовый код операции, а за этим кодом могут следовать несколько операндов. Код операции обозначает действие, которое необходимо предпринять.

На данным момент в Java содержится больше 200 операций. Все коды занимают лишь 1 байт.

В основе работы Java VM — стек, т. к. основные инструкции работают именно с ним.

Приведём пример умножения 2 чисел: что такое виртуальная машина java. Смотреть фото что такое виртуальная машина java. Смотреть картинку что такое виртуальная машина java. Картинка про что такое виртуальная машина java. Фото что такое виртуальная машина javaОперации выполняются во фрейме стека метода (в главном потоке исполнения приложения создаётся множество подстеков). что такое виртуальная машина java. Смотреть фото что такое виртуальная машина java. Смотреть картинку что такое виртуальная машина java. Картинка про что такое виртуальная машина java. Фото что такое виртуальная машина javaВ каждом стек-фрейме — массив локальных переменных.

Вызовы методов

В Java VM есть 2 главных вида методов: методы класса и методы экземпляра. Первые применяют статическое (раннее) связывание, вторые динамическое (позднее) связывание.

Java VM вызывает метод класса и выбирает его на основании типа ссылки на объект (всегда известен в процессе компиляции). С другой стороны, когда виртуальная машина Java вызывает метод экземпляра, происходит выбор метода для вызова на основании фактического класса объекта, а его можно узнать лишь при выполнении.

Java VM при этом снимает необходимое число переменных со стека, передавая в метод. Значение, возвращаемое методом, кладётся на стек. Типы возвращаемых значений методов: что такое виртуальная машина java. Смотреть фото что такое виртуальная машина java. Смотреть картинку что такое виртуальная машина java. Картинка про что такое виртуальная машина java. Фото что такое виртуальная машина java

Циклы

Последний нюанс — циклы. Смотрим, каким станет код, представленный ниже: что такое виртуальная машина java. Смотреть фото что такое виртуальная машина java. Смотреть картинку что такое виртуальная машина java. Картинка про что такое виртуальная машина java. Фото что такое виртуальная машина javaКаждый раз на стеке появляются 2 числа, которые сравниваются. Если i > 9999, производится выход из цикла. Для создания цикла служит конструкция на основе goto.

Заключение

По умолчанию байт-код интерпретируется в большинстве Java VM. Но если система видит, что какой-нибудь код используется часто, подключается встроенный компилятор, компилирующий байт-коды в машинный код, что существенно ускоряет работу приложения.

Источник

Как работает виртуальная машина Java — взгляд изнутри

Авторизуйтесь

Как работает виртуальная машина Java — взгляд изнутри

что такое виртуальная машина java. Смотреть фото что такое виртуальная машина java. Смотреть картинку что такое виртуальная машина java. Картинка про что такое виртуальная машина java. Фото что такое виртуальная машина java

Рассказывает Роман Иванов

Каждому Java-разработчику будет очень полезно понимать, что из себя представляет JVM, как в неё попадает код и как он исполняется. Статья больше подойдёт новичкам, но найти в ней что-то новое смогут и более опытные программисты. В статье вкратце описано, как устроен class-файл и как виртуальная машина обрабатывает и исполняет байт-код.

Основной задачей разработчиков Java было создание переносимых приложений. JVM играет центральную роль в переносимости — она обеспечивает должный уровень абстракции между скомпилированной программой и базовой аппаратной платформой и операционной системой. Несмотря на этот дополнительный «слой», скорость работы приложений необычайно высока, потому что байт-код, который выполняет JVM, и она сама отлично оптимизированы.

Рассмотрим схему работы JVM более подробно.

Структура class-файла

Напишем простейшее приложение и скомпилируем его. Компилятор заботливо создаст файл с расширением class и поместит туда всю информацию о нашем мини-приложении для JVM. Что мы увидим внутри? Файл поделён на десять секций, последовательность которых строго задана и определяет всю структуру class-файла.

4–5 декабря, Онлайн, Беcплатно

Файл начинается со стартового (магического) числа: 0xCAFEBABE. Данное число присутствует в каждом классе и является обязательным флагом для JVM: с его помощью система понимает, что перед ней class-файл.

что такое виртуальная машина java. Смотреть фото что такое виртуальная машина java. Смотреть картинку что такое виртуальная машина java. Картинка про что такое виртуальная машина java. Фото что такое виртуальная машина java

С девятого байта идёт пул констант, в котором содержатся все константы нашего класса. Так как в каждом классе их может быть различное количество, то перед массивом находится переменная, указывающая на его длину, то есть пул констант представляет из себя массив переменной длины. Каждая константа занимает один элемент в массиве. Во всём class-файле константы указываются целочисленным индексом, который обозначает их положение в массиве. Начальная константа имеет индекс 1, вторая константа — 2 и т. д.

Каждый элемент пула констант начинается с однобайтового тега, определяющего его тип. Это позволяет JVM понять, как правильно обработать идущую далее константу. Всего зарезервировано 14 типов констант:

Тип константыЗначение тега
CONSTANT_Class7
CONSTANT_Fieldref9
CONSTANT_Methodref10
CONSTANT_InterfaceMethodref11
CONSTANT_String8
CONSTANT_Integer3
CONSTANT_Float4
CONSTANT_Long5
CONSTANT_Double6
CONSTANT_NameAndType12
CONSTANT_Utf81
CONSTANT_MethodHandle15
CONSTANT_MethodType16
CONSTANT_InvokeDynamic18

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

Прочитав блок с константами, JVM переходит к следующим двум байтам — флагам доступа, которые определяют, описывает этот файл класс или интерфейс, общедоступный или абстрактный, является ли класс финальным.

Имена класса и его родительского класса хранятся в массиве констант, на которые указывают последующие 4 байта в файле.

Немного иначе обстоят дела с интерфейсами. Так как класс может наследоваться от множества интерфейсов одновременно, то хранить необходимо массив ссылок на пул констант. То есть за определением класса и его родительского класса идёт число, характеризующее размер массива интерфейсов, и сам массив. Все возможные значения кодов представлены ниже.

Имя флагаКодОпределение
ACC_PUBLIC0x0001Объявлен публичным
ACC_FINAL0x0010Объявлен финальным
ACC_SUPER0x0020Специальный флаг, введённый в версии Java 1.1 для совместимости при вызове методов родителя
ACC_INTERFACE0x0200Объявлен интерфейсом
ACC_ABSTRACT0x0400Объявлен абстрактным
ACC_SYNTHETIC0x1000Зарезервированное определение
ACC_ANNOTATION0x2000Объявлен аннотацией
ACC_ENUM0x4000Объявлен перечислением

Подобную структуру имеет и следующий блок — Fields.

Этот блок начинается с двухбайтового параметра количества полей в этом классе или интерфейсе. За ним идёт массив структур переменной длины. Каждая структура содержит информацию об одном поле: имя поля, тип, значение, если это, например, финальная переменная. В списке отображаются только те поля, которые были объявлены классом или интерфейсом, определённым в файле. Поля от родительских классов и имплементированных интерфейсов здесь не присутствуют, они задаются в своих class-файлах.

Далее мы переходим к самому важному месту в любом классе — его методам, именно в них сосредоточена вся логика любой программы, весь исполняемый байт-код.

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

В последнем блоке идёт дополнительная мета-информация, например имя файла, который был скомпилирован. Она может присутствовать, а может и нет. В случае каких-то проблем JVM просто игнорирует этот блок.

Загрузка классов

Теперь, разобравшись с общей структурой файла, посмотрим, как JVM его обрабатывает.

Чтобы попасть в JVM, класс должен быть загружен. Для этого существуют специальные классы-загрузчики:

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

После загрузки класса начинается этап линковки, который делится на три части.

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

JVM получает один поток байтовых кодов для каждого метода в классе. Байт-код метода выполняется, когда этот метод вызывается в ходе работы программы. Поток байт-кода метода — это последовательность инструкций для виртуальной машины Java. Каждая инструкция состоит из однобайтового кода операции, за которым может следовать несколько операндов. Код операции указывает действие, которое нужно предпринять. Всего на данный момент в Java более 200 операций. Все коды операций занимают только 1 байт, так как они были разработаны компактными, поэтому их максимальное число не может превысить 256 штук.

В основе работы JVM находится стек — основные инструкции работают с ним.

Рассмотрим пример умножения двух чисел. Ниже представлен байт-код метода:

На Java это будет выглядеть так:

По листингу выше можно заметить, что коды операций сами по себе указывают тип и значение. Например, код операции iconst_1 указывает JVM на целочисленное значение, равное единице. Такие байт-коды определены для самых часто используемых констант. Эти инструкции занимают 1 байт и введены специально для повышения эффективности выполнения байт-кода и уменьшения размера его потока. Подобные короткие константы также присутствуют и для других типов данных.

Всего JVM поддерживает семь примитивных типов данных: byte, short, int, long, float, double и char.

Если бы мы хотели положить в переменную а другое значение, например 11112, то нам пришлось бы использовать инструкцию sipush :

Данные операции выполняются в так называемом фрейме стека метода. У каждого метода есть некоторая своя часть в общем стеке. Таким образом в нашем главном потоке исполнения программы создаются множество подстеков на каждый вызов метода. Более наглядно это представлено на картинке ниже:

что такое виртуальная машина java. Смотреть фото что такое виртуальная машина java. Смотреть картинку что такое виртуальная машина java. Картинка про что такое виртуальная машина java. Фото что такое виртуальная машина java

В каждом стек-фрейме хранится массив локальных переменных, который позволяет сохранять и доставать локальные переменные, как мы сделали в примере выше, поместив значения 1 и 5 в переменные 1 и 2. Стоить отметить, что здесь компилятор также оптимизировал байт-код, используя однобайтовые инструкции. Если бы переменных в нашем методе было много, использовался бы код операции сохранения значения вместе с указанием позиции переменной в массиве.

Вызовы методов

Java предоставляет два основных вида методов: методы экземпляра и методы класса. Методы экземпляра используют динамическое (позднее) связывание, тогда как методы класса используют статическое (раннее) связывание.

Возвращаемое методом значение кладётся на стек. Типы возвращаемых значений методов указаны ниже:

ОперацияОписание
ireturnПомещает на стек значение типа int
lreturnПомещает на стек значение long,
freturnПомещает на стек значение float
dreturnПомещает на стек значение double
areturnПомещает на стек значение object
returnНе изменяет стек

Циклы

Осталось рассмотреть последнюю часто используемую конструкцию языка — циклы. Посмотрим, во что превратится код, представленный ниже:

Заключение

Изначально байт-код интерпретируется в большинстве JVM, но как только система замечает, что некоторый код используется очень часто, она подключает встроенный компилятор, который компилирует байт-коды в машинный код, тем самым значительно ускоряя работу приложения.

Таким образом, мы поверхностно рассмотрели жизненный цикл байткода в JVM: class-файлы, их загрузку и выполнение байт-кода и базовые инструкции.

Источник

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *