initrd와 initramfs의 차이점은 무엇입니까?
내가 아는 initrd
한 블록 장치 역할을하므로 파일 시스템 드라이버 (예 :)가 필요합니다 ext2
. 커널에는의 파일 시스템을 감지하기위한 하나 이상의 내장 모듈이 있어야합니다 initrd
. 이 기사, Introducing initramfs, 초기 RAM 디스크의 새 모델 에서는 다음과 같이 작성되었습니다.
그러나 램 디스크는 실제로 캐싱으로 인해 더 많은 메모리를 낭비합니다. Linux는 블록 장치에서 읽거나 쓰는 모든 파일 및 디렉토리 항목을 캐시하도록 설계되었으므로 Linux는 ramdisk에서 데이터를 "페이지 캐시"(파일 데이터의 경우) 및 "dentry 캐시"(디렉토리 항목의 경우)로 복사합니다. . 블록 장치 인 것처럼 가장하는 램 디스크의 단점은 블록 장치처럼 취급된다는 것입니다.
무엇 page cache
과 dentry cache
? 단락에서 데이터가 ramdisk
블록 장치로 취급되어 모든 데이터가 캐시되어 복제되었음을 의미 합니까?
constrast에서 ramfs
:
몇 년 전 Linus Torvalds는 깔끔한 아이디어를 가지고있었습니다. Linux의 캐시가 파일 시스템처럼 마운트 될 수 있다면 어떨까요? 파일을 캐시에 보관하고 파일이 삭제되거나 시스템이 재부팅 될 때까지 절대 제거하지 마십시오. Linus는 "ramfs"라는 캐시 주변에 작은 래퍼를 작성했으며 다른 커널 개발자는 "tmpfs"라는 개선 된 버전을 만들었습니다 (데이터를 스왑 공간에 쓸 수 있고 지정된 마운트 지점의 크기를 제한하여 소비하기 전에 채워질 수 있음). 사용 가능한 모든 메모리). Initramfs는 tmpfs의 인스턴스입니다.
이러한 램 기반 파일 시스템은 포함 된 데이터의 크기에 맞게 자동으로 확장 또는 축소됩니다. ramfs에 파일을 추가 (또는 기존 파일 확장)하면 자동으로 더 많은 메모리가 할당되고 파일을 삭제하거나 자르면 해당 메모리가 해제됩니다. 블록 장치가 없기 때문에 블록 장치와 캐시간에 중복이 없습니다. 캐시의 사본은 데이터의 유일한 사본입니다. 무엇보다도 이것은 새로운 코드가 아니라 기존 Linux 캐싱 코드를위한 새로운 애플리케이션입니다. 즉, 크기가 거의 추가되지 않고 매우 간단하며 매우 잘 테스트 된 인프라를 기반으로합니다.
요컨대, ramfs
파일이 열리고 메모리에로드되지 않습니까?
initrd
와 둘 다 ramfs
컴파일 타임에 압축되지만 차이점은 initrd
부팅시 커널에 의해 마운트되도록 압축 해제 된 블록 장치 ramfs
이며 cpio를 통해 메모리에 압축 해제된다는 것 입니다. 나 맞아? 아니면 ramfs
최소한의 파일 시스템입니까?
마지막으로, 오늘까지 initrd
이미지는 여전히 최신 커널에 표시됩니다. 그러나 그것은 initrd
실제로 ramfs
오늘날 사용되는 것이고 그 이름은 단지 역사적 목적을위한 것입니까?
Dentry (및 inode) 캐시
Linux의 파일 시스템 하위 시스템에는 세 개의 계층이 있습니다. 시스템 호출 인터페이스를 구현하고 교차 마운트 지점과 기본 권한 및 제한 검사를 처리하는 VFS (가상 파일 시스템). 그 아래에는 개별 파일 시스템 용 드라이버와 블록 장치 (디스크, 메모리 카드 등, 네트워크 인터페이스는 예외) 용 드라이버에 대한 인터페이스가 있습니다.
VFS와 파일 시스템 간의 인터페이스는 여러 클래스입니다 (일반 C이므로 함수에 대한 포인터를 포함하는 구조이지만 개념적으로는 객체 지향 인터페이스입니다). 세 가지 주요 클래스는 inode
파일 시스템의 모든 객체 (파일 또는 디렉토리) dentry
를 설명하는, 디렉토리의 항목 file
을 설명하는, 프로세스에 의해 열린 파일을 설명하는입니다. 마운트되면 파일 시스템 드라이버가 생성 inode
되고 dentry
루트에 대해 프로세스가 파일에 액세스하고 결국 만료 될 때 요청시 다른 드라이버 가 생성됩니다. 그것은 dentry 및 inode 캐시입니다.
네, 열려있는 모든 파일을 루트 디렉토리 아래로에 대한 있어야만한다는 것을 의미하지 inode
와 dentry
구조를 나타내는 커널 메모리에 할당.
페이지 캐시
Linux에서 사용자 영역 데이터를 포함하는 각 메모리 페이지는 통합 page
구조 로 표시됩니다 . 이것은 페이지를 익명 (사용 가능한 경우 스왑 공간으로 교체 할 수 있음)으로 표시하거나 inode
일부 파일 시스템에서 연결 (파일 시스템에 다시 쓰고 다시 읽을 수 있음) 할 수 있으며 여러 메모리 맵의 일부가 될 수 있습니다. 즉, 일부 프로세스의 주소 공간에서 볼 수 있습니다. 현재 메모리에로드 된 모든 페이지의 합계가 페이지 캐시입니다.
페이지는 mmap 인터페이스를 구현하는 데 사용되며 일반적인 읽기 및 쓰기 시스템 호출은 다른 방법으로 파일 시스템에 의해 구현 될 수 있지만 대부분의 인터페이스는 페이지를 사용하는 일반 함수를 사용합니다. 파일 읽기가 요청 될 때 페이지를 할당하고 파일 시스템을 호출하여 하나씩 채우는 일반적인 함수가 있습니다. 블록 장치 기반 파일 시스템의 경우 적절한 주소를 계산하고이 채우기를 블록 장치 드라이버에 위임합니다.
ramdev (ramdisk)
Ramdev는 일반 블록 장치입니다. 이를 통해 모든 파일 시스템을 계층화 할 수 있지만 블록 장치 인터페이스에 의해 제한됩니다. 그리고 그것은 호출자가 할당 한 페이지를 채우고 그것을 다시 쓰는 방법을 가지고 있습니다. 이것이 바로 디스크, 메모리 카드, USB 대용량 저장 장치 등과 같은 실제 블록 장치에 필요한 것이지만, ramdisk의 경우 데이터가 메모리에 두 번, 한 번은 ramdev의 메모리에, 한 번은 메모리에 방문객.
이것은 initrd
. initrd가 드물고 이국적인 사건이었던 시대부터.
tmpfs
Tmpfs는 다릅니다. 더미 파일 시스템입니다. VFS에 제공하는 방법은 작동을위한 최소한의 방법입니다 (이는 inode, dentry 및 파일 방법이 무엇을해야하는지에 대한 훌륭한 문서입니다). 파일은 inode 캐시에 해당 inode 및 dentry가있는 경우에만 존재하며 파일이 생성 될 때 생성되고 파일이 삭제되지 않는 한 만료되지 않습니다. 페이지는 데이터가 기록 될 때 파일에 연결되고 그렇지 않으면 익명으로 동작합니다 (데이터는 스왑에 저장 될 수 있으며 page
구조는 파일이 존재하는 한 계속 사용됨).
이것은 메모리에 데이터의 추가 사본이 없다는 것을 의미하며 전체가 훨씬 간단하고 약간 더 빠릅니다. 기본 스토리지 인 다른 파일 시스템의 캐시 역할을하는 데이터 구조를 사용합니다.
이것은 새로운 구현 방법입니다 initrd
( initramfs
이지만 이미지는 여전히라고 initrd
합니다.).
또한 (단지에 장착의 tmpfs를 의미한다 "POSIX 공유 메모리"구현하는 방법 /dev/shm
도 최근에하고, 간단하고 효율적인 및 응용 프로그램이 파일을 작성하고이를 메모리 매핑 자유롭게을) /tmp
및 /run
(또는 /var/run
) 자주의 tmpfs는 노트북에 특히 장착이 디스크가 회전하지 않도록하거나 SSD의 경우 일부 마모를 방지합니다.
나는 당신이 모두 옳다고 생각합니다.
부팅 할 때 필요한 단계를 따르면 차이를 쉽게 알 수 있습니다.
initrd
ramdev
블록 장치가 생성된다. 실제 디스크 대신 메모리를 사용하는 시뮬레이션 된 하드 디스크 인 램 기반 블록 장치입니다.- The
initrd
file is read and unzipped into the device, as if you didzcat initrd | dd of=/dev/ram0
or something similar. - The
initrd
contains an image of a filesystem, so now you can mount the filesystem as usual:mount /dev/ram0 /root
. Naturally, filesystems need a driver, so if you use ext2, the ext2 driver has to be compiled in-kernel. - Done!
initramfs
- A
tmpfs
is mounted:mount -t tmpfs nodev /root
. The tmpfs doesn't need a driver, it is always on-kernel. No device needed, no additional drivers. - The
initramfs
is uncompressed directly into this new filesystem:zcat initramfs | cpio -i
, or similar. - Done!
And yes, it is still called initrd
in many places although it is a initramfs
, particularly in boot loaders, as for them it is just a BLOB. The difference is made by the OS when it boots.
To add another noteworthy difference between initrd
and initramfs
not mentioned in the excellent answer above.
- With
initrd
the kernel by default hands over to userspacepid 1
at/sbin/init
- Newer initramfs however changes things up and executes
pid 1
at/init
as it could become a pitfall (see https://unix.stackexchange.com/a/147688/24394)
Minimal runnable QEMU examples and newbie explanation
In this answer, I will:
- provide a minimal runnable Buildroot + QEMU example for you to test things out
- explain the most fundamental difference between both for the very beginners who are likely googling this
Hopefully these will serve as a basis to verify and understand the more internals specifics details of the difference.
The minimal setup is fully automated here, and this is the corresponding getting started.
The setup prints out the QEMU commands as they are run, and as explained in that repo, we can easily produce the three following working types of boots:
root filesystem is in an ext2 "hard disk":
qemu-system-x86_64 -kernel normal/bzImage -drive file=rootfs.ext2
root filesystem is in initrd:
qemu-system-x86_64 -kernel normal/bzImage -initrd rootfs.cpio
-drive
is not given.rootfs.cpio
contains the same files asrootfs.ext2
, except that they are in CPIO format, which is similar to.tar
: it serializes directories without compressing them.root filesystem is in initramfs:
qemu-system-x86_64 -kernel with_initramfs/bzImage
Neither
-drive
nor-initrd
are given.with_initramfs/bzImage
is a kernel compiled with options identical tonormal/bzImage
, except for one:CONFIG_INITRAMFS_SOURCE=rootfs.cpio
pointing to the exact same CPIO as from the-initrd
example.
By comparing the setups, we can conclude the most fundamental properties of each:
in the hard disk setup, QEMU loads bzImage into memory.
This work is normally done by bootloaders / firmware do in real hardware such as GRUB.
The Linux kernel boots, then using its drivers reads the root filesystem from disk.
in the initrd setup, QEMU does some further bootloader work besides loading the kernel into memory: it also:
- loads the
rootfs.cpio
into memory - informs the kernel about it: https://unix.stackexchange.com/questions/89923/how-does-linux-load-the-initrd-image
This time then, the kernel just uses the
rootfs.cpio
from memory directly, since no hard disk is present.Writes are not persistent across reboots, since everything is in memory
- loads the
in the initramfs setup, we build the kernel a bit differently: we also give the
rootfs.cpio
to the kernel build system.The kernel build system then knows how to stick the kernel image and the CPIO together into a single image.
Therefore, all we need to do is to pass the bzImage to QEMU. QEMU loads it into image, just like it did for the other setups, but nothing else is required: the CPIO also gets loaded into memory since it is glued to the kernel image!
ReferenceURL : https://stackoverflow.com/questions/10603104/the-difference-between-initrd-and-initramfs
'program tip' 카테고리의 다른 글
Flask와 함께 Google OAuth2 사용 (0) | 2021.01.07 |
---|---|
Python 람다의 로컬 값 바인딩 (0) | 2021.01.07 |
ArrayList와 LinkedList의 성능 차이 (0) | 2021.01.07 |
연결된 서버에서 비 xml 데이터를 쿼리 할 때 "Xml 데이터 형식은 분산 쿼리에서 지원되지 않습니다"라는 오류가 발생하는 이유는 무엇입니까? (0) | 2021.01.07 |
CSS 표시 테이블 셀에는 백분율 너비가 필요합니다. (0) | 2021.01.07 |