[Java] JVM은 무엇이며 자바 코드는 어떻게 실행하는 것인가.
Web/Java

[Java] JVM은 무엇이며 자바 코드는 어떻게 실행하는 것인가.

목차 (클릭시 해당 목차로 이동)


     

     

     

    백기선님 Java 스터디를 뒤늦게 시작합니다.

    https://github.com/whiteship/live-study/issues?q=is%3Aissue+is%3Aclosed 

     

    whiteship/live-study

    온라인 스터디. Contribute to whiteship/live-study development by creating an account on GitHub.

    github.com

     

     

     

     

    Java


    운영체제에 독립적

     

    Java가 나오기 전 기존의 언어는 다른 운영체제에 적용하려면 많은 노력이 필요했지만, Java는 운영체제에 독립적이기 때문에 운영체제가 바뀌어도 같은 코드 그대로 동작할 수 있습니다.

     

     

    Java는 다른언어와 무엇이 다르기 때문에 Java로 작성된 프로그램은 운영체제와 하드웨어에 관계없이 실행가능한

     

    "Write once, run anywhere" 가 가능할까요?

     

     

     

     

     

     

    JVM


    JVM. Java Virtual Machine 덕분입니다.

    (직역. 자바 가상 컴퓨터. (Machine을 기계가 아닌 컴퓨터로 이해하면 좋음) Virtual Machine은 보통 소프트웨어로 구현된 하드웨어를 뜻한다.)

     

    자바 응용프로그램은 운영체제나 하드웨어가 아닌 JVM하고만 통신하고, JVM은 해당 운영체제가 이해할 수 있도록 변환하여 전달합니다.

     

    Java애플리케이션과 일반 애플리케이션의 비교

     

     

     

     

    JVM이 OS와 상호작용하기 때문에 특정 OS마다 종속적인 JVM들이 존재합니다.

     

    정리하면,

    • Java 애플리케이션은 OS에 종속적이지 않다.
    • JVM은 OS에 종속적이다. (각 OS에 맞는 JVM이 필요하다)

     

    Windows, Linux, Mac 각 운영체제마다 필요한 JVM이 다릅니다.

    다양한 OS용 JVM

     

     

     

     

    JVM 구성요소


     

    JVM의 구성요소 4가지에 대해 알아봅니다.

     

    1. Class Loader
    2. Excecution Engine
    3. Garbage Collector
    4. Runtime Data Area

     

    Class Loader


     

    자바 애플리케이션이 실행중일때, 아래작업이 수행됩니다.

     

    1. Java에서  소스를 작성하면 .java 파일이 생성됩니다.
    2. jdk에 있는 javac가 .java 파일을 .class 파일(바이트코드)로 컴파일합니다.
    3. 이렇게 생성된 클래스파일들을 엮어서 JVM의 메모리 영역(Runtime Data Area)에 적재하는 역할을 하는 것이 Class Loader 입니다.

     

     

     

     

     

    Execution Engine


    최초의 JVM은 Class Loader에 의해 메모리에 적재된 .class파일(바이트코드)들을 기계어로 번역해 Interpreter 방식으로 실행했습니다.

     

    Interpreter 방식

    프로그램 실행중 바이트 코드를 한 라인씩 읽고 해석하여 실행하는 방식입니다.

     

    JVM의 최초 버전에 사용된 Interpreter방식은 같은 함수가 여러 번 불릴 때 매번 기계어 코드를 생성하므로 속도가 느리다는 단점이 있습니다.

     

     

    JIT (Just In Time)

    최근에 JDK 1.3 이후 JIT가 도입되었습니다.

     

    JIT 컴파일러는 실행중 바이트 코드를 한 라인씩 읽고 해석하여 실행하는 방식까지는 Interpreter 방식과 같지만, 적절한 시점에서 바이트코드 전체를 컴파일하여 기계어 코드로 변경하고 이후에는 더 이상 인터프리팅 하지 않고 기계어 코드로 직접 실행합니다. 그래서 같은 함수가 여러 번 불릴 때 매번 기계어 코드를 생성하는 것을 방지합니다.

     

     

    정리

    자바 컴파일러가 자바 프로그램 코드를 바이트코드로 변환한 다음, 실제 바이트코드를 실행하는 시점에서 JVM이 바이트 코드를 JIT 컴파일을 통해 기계어로 변환합니다.

     

     

     

     

     

    Garbage Collector


    Heap 메모리 영역에 생성(적재)된 객체들 중에 참조하지 않는 객체들을 탐색 후 제거합니다.

     

    특징

    • Garbage Collector가 실행되는 시간은 언제인지 알 수 없습니다.
      (참조가 없어지자마자 해제되는 것을 보장하지 않습니다.)
    • Garbage Collector가 수행되는 동안 Garbage Collector를 수행하는 쓰레드가 아닌 다른 모든 쓰레드는 일시정지 됩니다.

     

     

     

     

    Runtime Data Area


    JVM의 메모리 영역으로 자바 애플리케이션을 실행할 때 사용되는 데이터들을 적재하는 영역입니다.

     

    응용프로그램이 실행되면 JVM은 시스템으로부터 프로그램을 수행하는데 필요한 메모를 할당받고, 이 메모리를 용도에 따라 여러 영역으로 나누어 관리합니다.

     

    영역들 중에서 3가지 주요 영역에 대해서만 알아봅니다.

     

    1. method area
    2. call stack
    3. heap

     

     

    JVM의 메모리 구조 (출처. anota-com.tistory.com)

     

    Method area

    Class Loader에 의해 생성(적재)되는 클래스에 대한 정보(클래스 데이터)와 클래스 변수들을 메서드 영역(method area)에 저장합니다.

     

    Heap

    인스턴스가 생성되는 공간.

    프로그램 실행 중 생성되는 (new 연산자 의해서 생성되는) 배열과 객체는 모두 이곳에 생성됩니다.

     

    Call Stack (호출 스택)

    메서드의 작업에 필요한 메모리 공간을 제공합니다.

    메서드가 호출되면, 호출스택에 호출된 메서드를 위한 메모리가 할당되며, (= 해당 메서드는 호출스택에서 메모리를 얻음)  이 메모리는 메서드가 작업을 수행하는 동안 지역변수(매개변수 포함)들과 연산의 중간결과 등을 저장하는데 사용됩니다.

    그리고 메서드가 작업을 마치면 할당되었던 메모리 공간은 반환되어 비워집니다.

     

     

     

     

    JDK와 JRE

     

    JDK (Java Develpopment Kit)


    Java로 프로그래밍을 하기 위해서는 JDK(Java Develpopment Kit)를 설치해야 합니다.

     

    JDK = (해당 OS의) JVM + Java API + 개발에 필요한 실행파일(javac.exe, java.exe, javap.exe 등)

     

     

     

    JRE (Java Runtime Environment)


    Java로 작성된 응용프로그램이 실행되기 위한 최소환경

     

    JRE = (해당 OS의) JVM + Java API

     

     

     

     

    JDK vs JRE


     

    JDK = JRE + 개발에 필요한 실행파일(javac.exe, java.exe, javap.exe 등)

     

    JRE는 Java로 작성된 응용프로그램이 실행되기 위한 최소환경이기 때문에 이미 Java로 작성되었다면 개발에 필요한 실행파일은 없어도 됩니다.

     

    즉, JDK에서 (개발에 필요한 실행파일)이 빠진 것이 JRE입니다.

     

     

     

     

     

    개발에 필요한 실행파일들


     

    javac.exe


    자바 컴파일러. 자바소스코드를 바이트코드로 컴파일합니다.

    > javac Hello.java

    Hello.java -> Hello.class

     

     

     

     

    바이트코드란?

    Virual Machine이 이해할 수 있는 이진 표현법입니다.

    "기계어" 보다는 더 추상적인 개념입니다.

    (자바 바이트코드는 기계가 바로 수행할 수 있는 언어(기계어) 보다는 비교적 인간이 보기 편한 형태로 기술되어 있습니다.)

     

     

     

     

     

    java.exe


    자바 인터프리터. 컴파일러가 생성한 바이트코드(Hello.class)를 해석하고 실행합니다.

    > java Hello

     

     

     

     

    javap.exe


    역 어셈블러. 컴파일된 클래스파일(Hello.class)을 원래의 소스로 변환합니다.

    > javap Hello

    Hello.class -> Hello.java

     

     

     

     

    이 외에도 여러 실행파일들이 존재합니다.

     

     

     

     

     

    'Web > Java' 카테고리의 다른 글

    [Java] GitHub API를 이용한 대시보드 만들기  (2) 2021.07.05
    [Java] JUnit5  (0) 2021.07.05
    [Java] 제어문  (0) 2021.07.05
    [Java] 연산자  (2) 2021.06.25
    [Java] 자바 데이터타입, 변수 그리고 배열  (2) 2021.06.10