# 가상 머신에서의 디버깅

가상 머신 환경에서 Yocto 프로젝트를 디버깅하는 과정은 물리적 하드웨어 환경에서의 디버깅과는 다소 다를 수 있다. 가상 머신은 디버깅을 위한 추가적인 유연성을 제공하지만, 고유한 도전 과제도 존재한다. 이 장에서는 가상 머신 내에서 Yocto 프로젝트를 효과적으로 디버깅하는 방법을 설명한다.

#### 기본 개요

가상 머신에서 디버깅을 하려면 먼저 개발 환경이 올바르게 설정되어 있어야 한다. 이는 완전한 Yocto 프로젝트 빌드 환경과 적절한 가상 머신 소프트웨어(예: QEMU)가 포함된다.

#### 가상 네트워크 설정

가상 머신과 호스트 시스템 간의 원활한 통신을 위해 가상 네트워크를 구성해야 한다. 이는 SSH를 통해 가상 머신에 접근하거나, 로컬 및 원격 디버깅 세션을 설정하는 데 필수적이다.

**네트워크 브리징**

가상 머신은 호스트 시스템과 동일한 네트워크에 존재하는 것처럼 보이게 할 수 있다. 이는 네트워크 브리징을 통해 가능한다.

1. **호스트 네트워크 인터페이스 확인:** 호스트 시스템의 네트워크 인터페이스 이름을 확인한다.

```sh
ip link show
```

2. **QEMU 네트워크 브리지 설정:** QEMU를 실행할 때 네트워크 브리지를 설정하여 가상 머신이 호스트 네트워크와 동일한 네트워크에 있게 한다.

```sh
qemu-system-x86_64 -enable-kvm -m 2048 -hda /path/to/your/image -net nic -net bridge,br=br0
```

#### SSH를 통한 디버깅

가상 머신 안에서 실행 중인 이미지를 디버깅 할 때, SSH를 사용하면 편리한다. 이는 특히 원격 디버깅 세션을 시작할 때 유용하다.

1. **SSH 서버 설정:** Yocto 프로젝트의 빌드에 SSH 서버를 포함시킨다. `local.conf` 파일에 다음을 추가한다.

```
IMAGE_INSTALL_append = " openssh-sshd openssh-scp openssh-sftp"
```

2. **가상 머신에서 SSH 서버 시작:** 가상 머신이 부팅된 후 SSH 서버를 시작한다.

```sh
/etc/init.d/ssh start
```

3. **호스트 시스템에서 가상 머신으로 SSH 연결:** 가상 머신의 IP 주소를 확인한 후, 호스트 시스템에서 SSH를 통해 연결한다.

```sh
ssh root@<vm-ip-address>
```

#### QEMU의 디버그 인터페이스 사용

QEMU는 GDB와 같은 디버깅 도구와 인터페이스할 수 있는 기능을 제공한다. 이를 통해 가상 머신의 내부 상태를 조사할 수 있다.

1. **QEMU CLI 옵션으로 GDB 서버 활성화:** QEMU를 시작할 때 GDB 서버를 활성화한다.

```sh
qemu-system-x86_64 -s -S -enable-kvm -m 2048 -hda /path/to/your/image
```

여기서 `-s` 옵션은 GDB 서버를 1234번 포트에서 실행하고, `-S` 옵션은 QEMU를 중단 상태로 시작한다.

2. **GDB 시작 및 연결:** 호스트 시스템에서 GDB를 시작하고 QEMU GDB 서버에 연결한다.

```sh
gdb
(gdb) target remote :1234
```

#### 원격 디버깅

더 복잡한 디버깅 작업이 필요할 경우, 원격 디버깅을 설정하여 원거리에서 디버깅을 수행할 수 있다.

**설정 단계**

1. **GDB 서버 실행:** 디버깅하고자 하는 애플리케이션을 GDB 서버 모드로 실행한다.

   ```sh
   gdbserver :2345 /path/to/application
   ```
2. **GDB 클라이언트 연결:** 호스트 시스템에서 GDB 클라이언트를 실행하고 GDB 서버에 연결한다.

   ```sh
   gdb /path/to/application
   (gdb) target remote <vm-ip-address>:2345
   ```

**활용 사례**

원격 디버깅은 특히 문제가 발생하는 시점을 정확히 알아내기 어려운 경우에 유용하다. 모니터링할 변수를 설정하고, 필요한 시점에서 중단점을 설정한 뒤, 애플리케이션의 동작을 세밀하게 분석할 수 있다.

#### 성능 프로파일링

가상 머신에서 애플리케이션의 성능을 프로파일링하는 것은 실제 물리적 환경에서 디버깅하는 것과 유사하지만, 몇 가지 가상화 특유의 요소들이 추가된다. 성능 프로파일링 도구들은 다양한 정보를 제공하며, 가상 머신 내에서도 효과적으로 사용할 수 있다.

**OProfile**

먼저, OProfile을 사용하여 시스템의 다양한 성능 측면을 분석할 수 있다.

1. **OProfile 설치:** Yocto 프로젝트의 이미지에 OProfile을 포함시킨다.

```sh
IMAGE_INSTALL_append = " oprofile"
```

2. **OProfile 구성:** 가상 머신 내부에서 OProfile을 구성하고 실행한다.

```sh
opcontrol --init
opcontrol --start
```

3. **애플리케이션 실행:** 성능을 프로파일링하고자 하는 애플리케이션을 실행한다.
4. **OProfile 데이터 분석:** 데이터를 수집한 후 OProfile을 종료하고 결과를 분석한다.

```sh
opcontrol --stop
opreport
```

**Perf**

Linux 성능 분석 도구인 perf도 유용한 정보를 제공한다.

1. **Perf 설치:** Yocto 이미지에 perf 툴을 추가한다.

```sh
IMAGE_INSTALL_append = " perf"
```

2. **Perf 프로파일링:** 애플리케이션 실행과 함께 perf를 사용하여 성능 데이터를 수집한다.

```sh
perf record -a -g ./your_application
```

3. **Perf 데이터 분석:** 수집된 데이터를 바탕으로 분석을 수행한다.

```sh
perf report
```

#### 커널 디버깅

가상 머신에서는 커널 디버깅 또한 가능한다. 특히, 가상 머신 환경에서는 디버깅에 필요한 특정 기능을 사용하여 더 효율적으로 커널 문제를 추적할 수 있다.

**Kdump 사용**

Kdump는 시스템 충돌 이후 덤프 파일을 캡처하여, 문제를 디버깅하는 데 매우 유용하다.

1. **Kdump 설치 및 설정:** Yocto 이미지에 Kdump를 추가하고 설정한다.

```sh
IMAGE_INSTALL_append = " kdump kexec-tools"
```

2. **Kdump 활성화:** 가상 머신 내부에서 Kdump를 활성화한다.

```sh
systemctl enable kdump
systemctl start kdump
```

3. **시스템 충돌 후 분석:** 충돌 시 발생하는 덤프 파일을 분석하여 문제의 원인을 파악한다.

**QEMU 가상 커널 디버깅**

QEMU를 사용하면 가상 머신에서 커널 디버깅을 실행할 수 있다. 다음은 그 절차이다.

1. **QEMU를 디버그 모드로 실행:** QEMU를 디버그 모드로 실행하여 커널 디버깅을 설정한다.

```sh
qemu-system-x86_64 -s -S -enable-kvm -m 2048 -kernel /path/to/kernel/Image -append "console=ttyS0"
```

2. **GDB로 커널 연결:** 호스트에서 GDB를 시작하고 QEMU의 GDB 서버에 연결한다.

```sh
gdb /path/to/kernel/vmlinux
(gdb) target remote :1234
```

#### 마치며

가상 머신 내에서 Yocto 프로젝트를 디버깅하는 것은 다양한 도구와 방법을 필요로 한다. 이 장에서는 가상 네트워크 설정, SSH를 통한 디버깅, QEMU 가상 디버그 인터페이스 사용, 원격 디버깅, 성능 프로파일링 도구(OProfile, Perf) 활용, 그리고 커널 디버깅(Kdump, QEMU 가상 커널 디버깅) 등 다양한 주제를 다루었다. 이 모든 기법을 통해 가상화된 환경에서도 Yocto 프로젝트를 효과적으로 디버깅할 수 있다.
