1 Обзор
Java, как известно, поддерживает платформу агностик, безопасность и мобильность сети. Платформа Java состоит из виртуальных машин Java и основных классов Java, которые обеспечивают унифицированный интерфейс программирования для программ Pure Java, независимо от более низкой операционной системы. Именно из -за виртуальной машины Java ее утверждают, что она будет «скомпилирована один раз, везде» может быть гарантировано.
1.1 Процесс выполнения программы Java
Выполнение программ Java зависит от обстановки компиляции и управляемой среды. Исходный код преобразуется в исполняемый машинный код, который завершается следующим процессом:
Основным ядром технологии Java является виртуальная машина Java, потому что все программы Java работают на виртуальной машине. Работа программ Java требует сотрудничества виртуальной машины Java, файлов Java API и класса Java. Экземпляр Java Virtual Machine отвечает за запуск программы Java. Когда начинается программа Java, рождается экземпляр виртуальной машины. Когда программа заканчивается, экземпляр виртуальной машины умирает.
Крестоплатформенная функция Java заключается в том, что она имеет виртуальные машины, нацеленные на различные платформы.
1.2 Виртуальная машина Java
Основной задачей виртуальной машины Java является загрузка файлов классов и выполнить его байткоды. Как видно из рисунка ниже, виртуальная машина Java содержит загрузчик класса, который может загружать файлы классов из программ и API. Только классы, необходимые для выполнения программы, будут загружены в Java API, а байт -код выполняется двигателем выполнения.
Когда виртуальная машина Java реализуется программным обеспечением в хост -операционной системе, программа Java взаимодействует с хостом, вызывая локальные методы. Методы Java написаны на языке Java, составлены в Bytecode и хранятся в файлах класса. Локальный метод записывается на языке C/C ++/сборки, составлен в машинный код, связанный с процессором, хранясь в библиотеке динамических ссылок, а формат является собственностью для каждой платформы. Таким образом, локальный метод состоит в том, чтобы подключить программы Java к базовой операционной системе хоста.
Поскольку виртуальная машина Java не знает, как был создан файл класса и был ли она подделана, она реализует детектор файла класса, чтобы гарантировать, что типы, определенные в файле класса, могут быть безопасно использовать. Проверка файла класса обеспечивает надежность программы через четыре независимых сканирования:
・ Сбор файла класса
・ Семантическая проверка данных типа
・ Проверка байт -кодов
・ Справочная проверка символа
При выполнении Bytecode виртуальные машины Java также выполняют другие встроенные механизмы безопасности. Они являются характеристиками обеспечения надежности программ Java в качестве языков программирования Java, а также являются характеристиками виртуальных машин Java:
・ Type-Safe Suppe Reference
・ Структурированный доступ к памяти
・ Автоматическая коллекция мусора
・ Массив. Проверка границы
・ Пустая проверка цитаты
1.3 Тип данных виртуальной машины Java
Виртуальные машины Java выполняют расчеты с помощью определенных типов данных. Типы данных можно разделить на два типа: основные типы и эталонные типы, как показано на рисунке ниже:
Но Boolean немного особенный. Когда компилятор собирает исходный код Java в Bytecode, он будет представлять логический с помощью Int или Byte. В виртуальных машинах Java False представлен 0, а True представлен всеми ненулевыми целыми числами. Как и Java Language, диапазон стоимости основного типа виртуальной машины Java является последовательным везде, независимо от того, что такое хост-платформа, длинное всегда является подписанным целым числом с дополнением 64-разрядного два в любой виртуальной машине.
Для returnaddress этот базовый тип используется для реализации пункта наконец -то в программе Java. Программисты Java не могут использовать этот тип, его значение указывает на Opcode инструкции виртуальной машины.
2архитектура
В спецификации виртуальной машины Java поведение экземпляра виртуальной машины описано с точки зрения подсистемы, области памяти, типа данных и инструкций, и эти компоненты вместе показывают внутреннюю архитектуру абстрактной виртуальной машины.
2.1Class файл
Файл Javaclass содержит всю информацию о классе или интерфейсе. «Базовый тип» файла класса заключается в следующем:
| U1 | 1 байт, без подписного типа |
| U2 | 2 байта, без подписного типа |
| U4 | 4 байта, без подписного типа |
| U8 | 8 байтов, без подписного типа |
Если вы хотите узнать больше, JVM SE7 от Oracle дает официальную спецификацию: спецификация виртуальной машины Java®
Содержимое файла класса:
ClassFile {U4 Magic; // Магический номер: 0xcafebabe, используемый для определения того, является ли это файл класса Java u2 minor_version; // незначительный номер версии u2 Major_version; // номер основной версии u2 constant_pool_count; // постоянный размер бассейна CP_INFO CONSTANT_POOL [CONSTANT_POOL_COUNT-1]; // постоянный пул u2 access_flags; // Доступ к флагам на уровнях класса и интерфейса (полученные через | операция) u2 this_class; // Индекс класса (указывая на константы класса в постоянном пуле) U2 Super_Class; // Присутствует индекс класса (указывая на константы класса в постоянном пуле) u2 interfaces_count; // интерфейсы интерфейсы u2 интерфейсы [interfaces_count]; // Индекс интерфейса набор u2 fields_count; // счетчик поля Counter Field_info Fields [fields_count]; // Таблица поля набор u2 methods_count; // метод счета метода метода_инфоо метода [methods_count]; // Таблица методов набор u2 attributes_count; // Количество атрибута атрибута_INFO атрибута [attributes_count]; // таблица атрибутов} 2.2 Подсистема загрузчика класса
Подсистема загрузчика класса отвечает за поиск и загрузку информации типа. На самом деле, существует два типа погрузчиков для виртуальных машин Java: системные погрузчики и пользовательские погрузчики. Первый является частью реализации виртуальной машины Java, а вторая - часть программы Java.
・ Bootstrapclassloader: он используется для загрузки основной библиотеки Java, реализованной в собственном коде и не унаследован от java.lang.classloader.
・ ExtensionClassloader: он используется для загрузки библиотек расширения Java. Реализация виртуальной машины Java предоставит каталог библиотеки расширения. Этот класс загрузчик ищет и загружает классы Java в этом каталоге.
・ Загрузчик класса приложения: загружает классы Java в соответствии с приложением Java ClassPath (ClassPath). Вообще говоря, классы приложений Java загружаются им. Его можно получить через classloader.getSystemClassloader ().
В дополнение к загрузчикам классов, предоставленным системой, разработчики могут реализовать свои собственные загрузки класса, унаследовав класс Java.lang.lasloader для удовлетворения некоторых особых потребностей.
Подсистема загрузчика класса включает в себя несколько других компонентов виртуальной машины Java и классов из библиотеки Java.lang. Метод, определенный ClassLoader, предоставляет интерфейс для программы для доступа к механизму загрузчика класса. Кроме того, для каждого загруженного типа виртуальная машина Java создает экземпляр класса java.lang.class для представления типа. Как и другие объекты, пользовательские загрузчики класса и экземпляры класса помещаются в область кучи в памяти, в то время как информация о загруженном типе находится в области метода.
В дополнение к поиску и импорту двоичных файлов классов, подсистема загрузчика класса также должна нести ответственность за проверку правильности импортированного класса, распределение и инициализацию памяти для переменных класса и символические ссылки. Эти действия также должны быть выполнены в следующем порядке:
・ Загрузка (найти и загрузить двоичные данные типа)
・ Соединение (Проверка выполнения: Убедитесь, что правильность импортированного типа; подготовка: распределить память для переменных класса и инициализировать их по значениям по умолчанию;
・ Инициализация (переменные класса инициализируются до правильного начального значения)
2.3 Метод зона
В виртуальной машине Java информация о загруженном типе хранится в памяти в области метода. Когда виртуальная машина загружает определенный тип, она использует загрузчик класса для поиска соответствующего файла класса, затем считывает файл класса и передает его на виртуальную машину. Затем виртуальная машина извлекает информацию о типе и хранит эту информацию в области метода. Области метода также могут быть собраны сборщиком мусора, потому что виртуальная машина позволяет динамическому расширению программ Java через пользовательские загрузчики классов.
Следующая информация хранится в области метода:
・ Этот тип полностью квалифицированного имени (например, полностью квалифицированное имя java.lang.object)
・ Полностью квалифицированное название этого типа прямого суперкласса
・ Это тип типа класса или тип интерфейса
・ Этот тип модификатора доступа (подмножество общественных, абстрактных, окончательных)
・ Сортированный список полностью квалифицированных имен для любой прямой гипертерфейной
・ Постоянный пул этого типа (упорядоченный сбор, включающий прямые константы [строка, целочисленное целое число и константы плавания] и символические ссылки на другие типы, поля и методы)
・ Информация о поле (имя поля, тип, модификатор)
・ Информация о методе (имя метода, тип возврата, количество параметров и типа, модификатор)
・ Все классные (статические) переменные, кроме констант
・ Ссылка на класс ClassLoader (когда каждый тип загружается, виртуальная машина должна отслеживать, загружается ли она загрузчиком класса запуска или пользовательским загрузчиком класса).
・ Ссылка на класс класса (для каждого загруженного типа, виртуальная машина будет создавать экземпляр класса Java.lang.class соответственно. Например, если у вас есть ссылка на объект класса Java.lang.integer, тогда вам нужно только вызвать метод GetClass (), ссылаясь на Integer Object, чтобы получить объект класса.
2.4 куча
Все экземпляры класса или массивы, созданные программами Java во время выполнения (массивы являются реальным объектом в виртуальной машине Java), помещаются в одну и ту же кучу. Поскольку экземпляры виртуальной машины Java имеют только одно пространство кучи, все потоки поделится этой кучей. Следует отметить, что у виртуальной машины Java есть инструкция по распределению объектов в куче, но у него нет инструкции по освобождению памяти, потому что виртуальная машина передала эту задачу коллекционеру мусора для обработки. Спецификация виртуальной машины Java не обеспечивает соблюдения коллекционеров мусора, требуется, чтобы реализации виртуальных машин каким -то образом управляли своим собственным пространством кучи. Например, реализация может иметь только пространство кучи фиксированного размера. Когда пространство заполнено, оно просто бросает исключение из перспективы, которое не учитывает проблему утилизации объектов мусора, но соответствует спецификациям.
Спецификация виртуальной машины Java не указывает, как объекты Java представлены в куче, что дает реализатору решений виртуальной машины о том, как проектировать. Возможный дизайн кучи заключается в следующем:
Бассейн ручки, бассейн объектов. Ссылка объекта - локальный указатель на бассейн ручки. Преимущества этого дизайна способствуют сортировке фрагментов кучи. При перемещении объектов в пуле объектов часть ручки должна только изменить новый адрес указателя, указывающего на объект. Недостатком является то, что каждый раз, когда доступ к переменной экземпляра объекта, она должна проходить через два указателя.
2.5 Java Stack
Всякий раз, когда запускается поток, виртуальная машина Java выделяет ему стек Java. Стек Java состоит из многих кадров стека, одна рамка стека содержит состояние вызова метода Java. Когда поток вызывает метод Java, виртуальная машина выдвигает новую карму стека в стек Java. Когда метод возвращается, рамка стека появляется из стека Java. Стек Java сохраняет состояние вызовов метода Java в потоках, включая локальные переменные, параметры, возвращаемые значения и промежуточные результаты операций и т. Д. Виртуальные машины Java не имеют регистров, а в их наборе инструкций используется стек Java для хранения промежуточных данных. Причиной этой конструкции является сохранение набора инструкций виртуальной машины Java максимально компактным, а также облегчить реализацию виртуальной машины Java на платформе с небольшим количеством общих регистров. Кроме того, архитектура на основе стека также помогает оптимизировать код динамических компиляторов и мгновенных компиляторов, реализованных определенными виртуальными машинами во время выполнения.
2.5.1 стека кадр
Кадр стека состоит из локальной области переменной, стека операнда и области данных кадры. Когда виртуальная машина вызывает метод Java, она получает локальную область переменной и размер стека операндов этого метода из типа информации соответствующего класса и выделяет память кадра стека в соответствии с этим, а затем встает в стек Java.
2.5.1.1 локальная переменная зона
Локальная переменная область организована в массив, подсчищенный от 0 в единицах длины слова. В инструкции по байт -коду используются данные в нем через индекс, начиная с 0. Значения типов, плавания, ссылки и returndress, занимают один элемент в массиве, в то время как значения типов байта, короткие и char преобразуются в значения int, прежде чем храниться в массиве, а также занимают один элемент. Но значения типов длинные и двойные занимают два последовательных термина в массиве.
2.5.1.2 Операнд стек
Как и локальная переменная область, стек операнда также организован в массив в длине слова. Он обращается через стандартные операции стека и складывается. Поскольку счетчик программы не может быть непосредственно доступен в соответствии с инструкциями по программе, инструкции виртуальной машины Java получают операнды из стека операнда, поэтому его операция основана на стеке, а не на регистрах. Виртуальная машина принимает стек операндов в качестве рабочей области, потому что большинство инструкций должны всплывать данные отсюда, выполнять операции, а затем отдать результат обратно в стек операнда.
2.5.1.3
В дополнение к локальной области переменной области и стека операнда, рамки стека Java также нуждаются в областях данных о рамках для поддержки постоянного анализа пула, нормального возврата метода и механизмов отправки исключений. Всякий раз, когда виртуальная машина хочет выполнить инструкцию, которая требует постоянных данных пула, она обращается к ней через указатель к постоянному пулу в области данных кадра. В дополнение к анализу постоянных пулов, область данных рамы также помогает виртуальной машине обрабатывать нормальный конец или ненормальное прерывание методов Java. Если возврат заканчивается нормально, виртуальная машина должна восстановить кадр стека метода, инициирующий вызов, включая установку счетчика программы, чтобы указать на следующую инструкцию, инициирующую метод вызова; Если метод имеет возвращаемое значение, виртуальная машина должна выдвинуть его в стек операнда метода, инициирующий вызов. Для обработки выходов исключений во время выполнения метода Java, область данных кадра также содержит ссылку на таблицу исключений этого метода.
2.6 Программный счетчик
Для запуска Java -программы у каждого потока есть счетчик программы. Счетчики программы также называются регистрами ПК. Счетчик программы может удерживать как локальный указатель, так и returnaddress. Когда поток выполняет метод Java, значение счетчика программы всегда является адресом следующей выполненной инструкции. Адрес здесь может быть локальным указателем или смещением в байт -коде метода относительно инструкции «Пуск» метода. Если поток выполняет локальный метод, значение счетчика программы «не определен».
2.7 локальный стек методов
Любой локальный интерфейс метода будет использовать какой -то локальный стек методов. Когда поток вызывает метод Java, виртуальная машина создает новую рамку стека и вталкивает его в стек Java. Когда он вызывает локальный метод, виртуальная машина сохраняет стек Java неизменным и больше не встает в новый стек в стеке с резьбой Java. Виртуальная машина просто подключается динамически и напрямую вызывает указанный локальный метод.
Область метода и куча передаются всеми потоками в экземпляре виртуальной машины. Когда виртуальная машина загружает файл класса, он анализирует информацию типа из двоичных данных, содержащихся в файле класса, а затем помещает информацию о типе в области метода. Когда программа работает, виртуальная машина помещает все объекты, созданные программой во время выполнения в кучу.
Как и другие области памяти времени выполнения, область памяти, занятая локальным стеком методов, может быть динамически расширена или сжимается по мере необходимости.
3 Двигатель выполнения
В спецификации виртуальной машины Java поведение двигателя выполнения определяется с использованием наборов инструкций. Дизайнер, внедряющий механизм выполнения, решит, как выполнить байт -код, реализацию можно интерпретировать, скомпилироваться на лету или выполнять непосредственно с помощью инструкций на чипе или их смеси.
Двигатель выполнения может быть понят как абстрактная спецификация, конкретная реализация или управляемый экземпляр. Абстрактные спецификации используют наборы инструкций, чтобы указать поведение двигателя выполнения. Конкретная реализация может использовать различные технологии, включая программное обеспечение, оборудование или комбинацию технологии деревьев. Двигатель выполнения в качестве экземпляра выполнения - это поток.
Каждый поток программы JAVA является экземпляром независимого механизма выполнения виртуальной машины. С начала до конца жизненного цикла потока он либо выполняет байт -код, либо выполняет локальный метод.
3.1 Набор инструкций
Поток байт -кодов метода состоит из последовательности инструкций из виртуальной машины Java. Каждая инструкция содержит одно байтовый OPCODE, за которым следует 0 или более операндов. OpCode представляет операцию, которая будет выполнена; Операнд предоставляет виртуальную машину Java дополнительную информацию, необходимую для выполнения OpCode. Когда виртуальная машина выполняет инструкцию, она может использовать элементы в текущем постоянном пуле, значения в локальной переменной текущей кадра или значения в верхней части стека операнда текущего кадра.
Абстрактный двигатель выполнения выполняет одну инструкцию по байт -коде за раз. Каждый поток (экземпляр движения выполнения) программы, работающей на виртуальной машине Java, выполняет эту операцию. Двигатель выполнения получает OpCode, и если OpCode имеет операнд, он получает свой операнд. Он выполняет действие, указанное OPCODE и The Follow Operand, а затем получает следующий OpCode. Этот процесс выполнения Bytecode будет продолжаться до тех пор, пока поток не будет завершен, а завершение потока может быть помечено путем возвращения из его начального метода или не поймать исключение, которое выбросило.
4 локальный интерфейс метода
Местный интерфейс Java, также называемый JNI (JavanativeInterface), подготовлен для переносимости. Интерфейс локального метода позволяет локальному методу выполнять следующее:
Передавать или вернуть данные
Операция переменных экземпляра
Управлять переменными класса или методов вызова класса
Операнд Массив
Заблокировать объект кучи
Загрузить новый класс
бросить исключение
Поймать исключение, брошенное локальным методом, вызывая метод Java
Захватить асинхронное исключение, брошенное виртуальной машиной
Указывает, что объект коллекционера мусора больше не нужен
Суммировать
Выше приведено все об этой статье о глубоком понимании архитектуры виртуальной машины Java, и я надеюсь, что это будет полезно для всех. Заинтересованные друзья могут продолжать ссылаться на другие связанные темы на этом сайте. Если есть какие -либо недостатки, пожалуйста, оставьте сообщение, чтобы указать это. Спасибо, друзья, за вашу поддержку на этом сайте!