on
JAVA - JVM
Java
Java 공부를 정리 tag
JVM (Java Virtual Machine)
Advanced Java
스터디를 위해, 그리고 부족했던 언어에 대한 이해를 높이고자 작성하게 됐습니다.
JVM이란?
The Java Virtual Machine is the cornerstone of the Java platform. It is the component of the technology responsible for its hardware- and operating system-independence, the small size of its compiled code, and its ability to protect users from malicious programs.
The Java Virtual Machine is an abstract computing machine. Like a real computing machine, it has an instruction set and manipulates various memory areas at run time. It is reasonably common to implement a programming language using a virtual machine; the best-known virtual machine may be the P-Code machine of UCSD Pascal. - JVM Spec
공식문서에서 JVM에 대해 위와 같이 적혀있다. 다시 정리를 하자면,
JVM은 실제 컴퓨터처럼
instruction set
을 가지며 Runtime에 다양한 메모리 영역을 조작한다. HW와 OS의 독립성을 보장해주며 Java bytecode를 읽고 해석하고 실행한다.
그러니깐 실제 컴퓨터 처럼 보이는 가상의 기계(Virtual Machine)라는 것이다. 더 쉽게 말하자면 Java로 작성된 프로그램이 실행되도록 만들어주는 Virtual Machine이라고 생각하면 된다.
왜?? JVM…? 그냥 인텔, ARM CPU 써서 든든하게 컴파일하면 되지 않냐?
여기서 JVM의 탄생 배경이 나온다.
-
Java는
Sun Microsystems
에서 가전제품 내 탑재해 동작하는 프로그램을 위해 탄생-
왜? 그냥 있던거 쓰지?
-
C/C++의 문제점은
compile-platform
과target-platform
이 다를 경우, 프로그램이 동작하지 않는다. → 하지만 이 문제는target-platform
에 맞춰 컴파일하는Cross Compile
으로 해결 가능하다. -
기존의 객체지향 언어였던 C++은 HW(CPU)와 OS에 맞는 컴파일러가 필요했다. → 가전제품용 컴파일러를 만들기엔 너무 많은 자원이 소모됨. 이게 문제. 그리고 계속 다른 디바이스가 나오게 되면, 거기에 맞는 컴파일러를 만들어야 될수도 있음.
-
-
??? 그러면
Cross Compile
해서 C++쓰면 되는거 아닌가? JVM 굳이 왜 쓰냐?Java가 탄생할 때 즈음 웹이 등장. C/C++는 플랫폼 마다 컴파일을 해줬어야 했지만, 매번 컴파일을 할 수는 없었다. 그리고 다양한 디바이스에 대한 컴파일도 지원했어야 한다. 따라서 Java의 경우 java compiler로
class file
을 만들어서 해당class file
만을 네트워크를 통해 전달하여 ‘웹 브라우저에 JVM이 설치되어 있다면’ 실행시킬 수 있었다.class file
을 읽어서 실행시키는 것이 JVM이다.→ 현재
Javascript
을 생각하면 비슷할 것 같다.
-
-
결국 플랫폼에 상관없이 코드 한번만 적으면 어디서든 실행될 수 있는 Cross Platform 언어가 필요했다. 따라서 Java 개발 시작.
Cross Platform language
: programming language가 여러 종류의 컴퓨터 플랫폼에서 동작할 수 있는 것 - 출처:wiki
-
그러던 와중 WWW이 출현했다. ‘이식 가능한 언어’를 요구하는 웹의 출현으로 Java가 당시 컴퓨터 언어 설계 프로젝트의 선두로 부상하게 됐다.
-
왜? 이식 가능한 언어를 요구했는가?
그 예전에는 웹이 처음 등장했을 시기여서 다양한 컴퓨터에서 실행되어야 했기에 이식 가능한 언어를 요구했다. 그리고 Java의 플랫폼에 독립적인 ‘이식가능하다는 자체’가 그 니즈를 충족했던 것이다.
-
-
따라서! Java를 CPU, OS 바로 위가 아닌, JVM 위에서 실행시킴으로써 플랫폼에 독립적일 수 있었고 독집적으로 실행시키는 것을 구현하기 위해 JVM이 탄생한 것이다.
Java code 실행 과정 (간단)
Java code 의 실행과정에 대해 간단하고 보고 가도록 하자.
-
Java source code 작성
public class Main { public static void main(String[] args) { System.out.println("Hello Java!!"); } }
-
$ javac Main.java
명령어를 사용하여 Java source code를 bytecode로 변환시킨다.
$ ls Main.java Main.class
Main.class
라는 class file이 생성된다. 이 파일을 JVM이 읽어서 실행시키는 것. -
$ java Main Hello Java!!
만들어진 class file은 어느 플랫폼이라도 해당 플랫폼에 맞게 설치된 JVM만 있다면 동일하게 실행될 수 있다.
특징
-
stack 기반 VM
-
Intel x86, ARM architecture 는 register 기반으로 동작한다. 그러나 Java는 stack 기반으로 동작한다.
-
why? 왜 자바는 스택을 기반으로 동작할까? 그냥 똑같이 register기반으로 동작하면 안되는가?
device마다 register의 수가 다르기 때문이다. 이게 뭐?? 라고 생각할 수도 있다. 따라서 우리는 다시 한번 되새겨야 한다.
Java는 플랫폼에 독립적인 언어 입니다.
device또한 플랫폼이다. 그렇기에 register 기반으로 동작하게 되면, 디바이스마다 다른 register의 상황을 고려해야하기 때문에 이는 플랫폼 독립을 보장하지 못하게 된다.
-
-
플랫폼에 독립적이다 → 위에서 열심히 설명했다.
- 컴퓨터의 HW바로 위에서 동작하는 것이 아닌, JVM 위에서 동작하기 때문에 Java는 플랫폼에 독립적이다.
- JVM은 OS, HW에 맞게 만들어줘야 한다. → HW위에서 동작하는 것이 JVM이기 때문이다. 따라서 JVM만큼은 플랫폼에 독립적이지 못하다.
-
Symbolic Reference :
primitive data type
을 제외한 모든 타입(클래스와 인터페이스)을 명시적인 메모리 주소 기반의 레퍼런스가 아니라 심볼릭 레퍼런스를 통해 참조한다. → 이게 정확히 무엇을 뜻하는지 잘 모르겠습니다. 더 알아봐야 할 것 같습니다. -
Garbage Collection (향후 포스팅에서 자세히 다루겠다)
-
Primitive type 을 명확하게 정의 → 플랫폼의 독립성 보장
The primitive data types supported by the Java Virtual Machine are the numeric types, the
boolean
type (§2.3.4), and thereturnAddress
type (§2.3.3). - JVM SpecJava
는 C언어처럼 플랫폼 마다primitive type
의 크기가 변하지 않는다. 따라서 Java는 그 크기를 정확히 정의해줌으로써 플랫폼의 독립성을 보장한다. - Long vs Int size in C -
network byte order 사용 → intel과 ARM 사이에서 플랫폼의 독립성을 유지하기 위해 고정된 byte order를 유지해야 하기 위함.
byte order
: 컴퓨터의 메모리와 같은 1차원의 공간에 여러 갱의 연속된 대상을 배열하는 방법을 뜻하며byte
를 배열하는 방법을 특히Byte Order
라고 한다. - wiki- 표현 방식에는
Little Endian
,Big Endian
2가지가 있는데 현재 JVM에 대해 다루고 있기에 설명은 생략할 것이다. - OS 시스템이 내부적으로 데이터를 표현하는 방법이다. 따라서 플랫폼과 관련됐기에 Java는 플랫폼의 독립성을 유지하기 위해 ‘고정된 byte order’를 유지하는 것이다.
- 표현 방식에는
- network byte order 는
Big Endian
방식을 사용한다.
그러면 JVM만 있으면 되는데 설치할 때 JRE, JDK는 뭐냐
Ubuntu20.04 를 쓰면서, 그리고 현재 Mac OS를 사용하면서 당연하게도 Java를 설치한 경험이 있다. 그럴 때 마다 JRE
, JDK
라는 것도 같이 설치됐는데 지금 위 설명만 들으면 얘네들은 꼭 필요할까?? 라는 생각이 들어서 한번 조사해봤다.
JRE (Java Runtime Environment)
Java Runtime Environment 또는 JRE는 컴퓨터의 운영체제 소프트웨어 상에서 실행되고 클래스 라이브러리 및 특정 Java 프로그램이 실행해야 하는 기타 리소스를 제공하는 소프트웨어 계층입니다. - IBM
JVM 은 우리가 컴파일한 .class
파일이 작동할 수 있는 환경을 제공해 준다. 그 환경이 JRE
이다.
-
구성 요소
-
JVM
JRE를 구성하는게 바로 JVM!!
-
Java Class Libraries
The Java Class Library (JCL) is a set of dynamically loadable libraries that Java Virtual Machine (JVM) languages can call at run time. - wiki
Java 실행을 위한 필수적인 라이브러리이다.
-
Java Class Loader : 실행에 필요한 Class를 JVM에 loading해주는 역할. 아래에서 자세히 다룰 것이다.
-
이러한 구성요소들로 JVM이 원활하게 작동 가능한 것이다.
BUT!! JRE는 실제 프로그램을 구동 시키는 것에 집중한다. 따라서 실제 Java code가 주어져도 이를 분석하거나 .class
file로 변환하는 일은 할 수가 없다. 위의 설명도
JVM은 우리가 컴파일한
.class
파일이 작동할 수 있는 환경을 제공…
이라고 말했었다. 따라서 우리는 컴파일을 하지 않은 순수 Java code와 JRE만으로 코드를 실행시킬 수가 없다.
JDK (Java Development Kit)
그래서!! 우리는 Java Compiler 등등 개발에 필요한 요소들이 필요하다!
It implements the Java Language Specification (JLS) and the Java Virtual Machine Specification (JVMS) and provides the Standard Edition (SE) of the Java Application Programming Interface (API). - wiki
쉽게 말하자면, Java를 활용하여 개발할 때 필요한 도구의 모음이라고 생각하면 된다. 때문에 실행도 시킬 수 있어야 하기에 JRE
도 포함되어 있다.
javac
, jdb
와 같은 기능들을 갖고 있다.
- Java EE vs Java SE
- Java EE : 기본 기능에 다른 기능들을 추가한 버전
- Java SE : 기본 기능만 있는 버전
Rerference
Wikipedia 참고