← Documents Documentation/admin-guide/device-mapper/dm-pcache.rst GitHub 원문 ↗

Linux 6.18.37 · Administration / Device Mapper

dm-pcache — Persistent Cache

DAX PMem을 crash-persistent write-back cache로 사용하는 dm-pcache의 구조, status, GC와 복구 동작입니다.

Source pathDocumentation/admin-guide/device-mapper/dm-pcache.rst
Source versionLinux v6.18.37
TranslationDUJINLABS 전문 번역 + 해설

요약·해설과 원문, 전문 번역을 서로 분리했습니다. API 이름, symbol, source path는 원문 표기를 사용합니다.

1. 요약·해설

원문의 핵심 논리와 kernel programming 관점의 보충 설명입니다. 아래의 전문 번역과는 별도로 작성했습니다.

구조와 생성

dm-pcache.rst:1-60

DAX cache 아키텍처, crash-safe metadata와 constructor·최초 format을 설명합니다.

상태와 data path

dm-pcache.rst:61-155

세 cursor, segment·kset 구조, write-back·GC·CRC 흐름을 정리합니다.

Failure와 workflow

dm-pcache.rst:156-202

Media 오류·cache full·crash 복구, 현재 제약과 운영 예제를 설명합니다.

2. 영어 원문 전체

번역 기준이 된 Linux v6.18.37 원문입니다. 줄 번호는 이 버전의 파일 좌표입니다.

원문 전체 펼치기
1 .. SPDX-License-Identifier: GPL-2.0
2
3 =================================
4 dm-pcache — Persistent Cache
5 =================================
6
7 *Author: Dongsheng Yang <dongsheng.yang@linux.dev>*
8
9 This document describes *dm-pcache*, a Device-Mapper target that lets a
10 byte-addressable *DAX* (persistent-memory, “pmem”) region act as a
11 high-performance, crash-persistent cache in front of a slower block
12 device. The code lives in `drivers/md/dm-pcache/`.
13
14 Quick feature summary
15 =====================
16
17 * *Write-back* caching (only mode currently supported).
18 * *16 MiB segments* allocated on the pmem device.
19 * *Data CRC32* verification (optional, per cache).
20 * Crash-safe: every metadata structure is duplicated (`PCACHE_META_INDEX_MAX
21 == 2`) and protected with CRC+sequence numbers.
22 * *Multi-tree indexing* (indexing trees sharded by logical address) for high PMem parallelism
23 * Pure *DAX path* I/O – no extra BIO round-trips
24 * *Log-structured write-back* that preserves backend crash-consistency
25
26
27 Constructor
28 ===========
29
30 ::
31
32 pcache <cache_dev> <backing_dev> [<number_of_optional_arguments> <cache_mode writeback> <data_crc true|false>]
33
34 ========================= ====================================================
35 ``cache_dev`` Any DAX-capable block device (``/dev/pmem0``…).
36 All metadata *and* cached blocks are stored here.
37
38 ``backing_dev`` The slow block device to be cached.
39
40 ``cache_mode`` Optional, Only ``writeback`` is accepted at the
41 moment.
42
43 ``data_crc`` Optional, default to ``false``
44
45 * ``true`` – store CRC32 for every cached entry
46 and verify on reads
47 * ``false`` – skip CRC (faster)
48 ========================= ====================================================
49
50 Example
51 -------
52
53 .. code-block:: shell
54
55 dmsetup create pcache_sdb --table \
56 "0 $(blockdev --getsz /dev/sdb) pcache /dev/pmem0 /dev/sdb 4 cache_mode writeback data_crc true"
57
58 The first time a pmem device is used, dm-pcache formats it automatically
59 (super-block, cache_info, etc.).
60
61
62 Status line
63 ===========
64
65 ``dmsetup status <device>`` (``STATUSTYPE_INFO``) prints:
66
67 ::
68
69 <sb_flags> <seg_total> <cache_segs> <segs_used> \
70 <gc_percent> <cache_flags> \
71 <key_head_seg>:<key_head_off> \
72 <dirty_tail_seg>:<dirty_tail_off> \
73 <key_tail_seg>:<key_tail_off>
74
75 Field meanings
76 --------------
77
78 =============================== =============================================
79 ``sb_flags`` Super-block flags (e.g. endian marker).
80
81 ``seg_total`` Number of physical *pmem* segments.
82
83 ``cache_segs`` Number of segments used for cache.
84
85 ``segs_used`` Segments currently allocated (bitmap weight).
86
87 ``gc_percent`` Current GC high-water mark (0-90).
88
89 ``cache_flags`` Bit 0 – DATA_CRC enabled
90 Bit 1 – INIT_DONE (cache initialised)
91 Bits 2-5 – cache mode (0 == WB).
92
93 ``key_head`` Where new key-sets are being written.
94
95 ``dirty_tail`` First dirty key-set that still needs
96 write-back to the backing device.
97
98 ``key_tail`` First key-set that may be reclaimed by GC.
99 =============================== =============================================
100
101
102 Messages
103 ========
104
105 *Change GC trigger*
106
107 ::
108
109 dmsetup message <dev> 0 gc_percent <0-90>
110
111
112 Theory of operation
113 ===================
114
115 Sub-devices
116 -----------
117
118 ==================== =========================================================
119 backing_dev Any block device (SSD/HDD/loop/LVM, etc.).
120 cache_dev DAX device; must expose direct-access memory.
121 ==================== =========================================================
122
123 Segments and key-sets
124 ---------------------
125
126 * The pmem space is divided into *16 MiB segments*.
127 * Each write allocates space from a per-CPU *data_head* inside a segment.
128 * A *cache-key* records a logical range on the origin and where it lives
129 inside pmem (segment + offset + generation).
130 * 128 keys form a *key-set* (kset); ksets are written sequentially in pmem
131 and are themselves crash-safe (CRC).
132 * The pair *(key_tail, dirty_tail)* delimit clean/dirty and live/dead ksets.
133
134 Write-back
135 ----------
136
137 Dirty keys are queued into a tree; a background worker copies data
138 back to the backing_dev and advances *dirty_tail*. A FLUSH/FUA bio from the
139 upper layers forces an immediate metadata commit.
140
141 Garbage collection
142 ------------------
143
144 GC starts when ``segs_used >= seg_total * gc_percent / 100``. It walks
145 from *key_tail*, frees segments whose every key has been invalidated, and
146 advances *key_tail*.
147
148 CRC verification
149 ----------------
150
151 If ``data_crc is enabled`` dm-pcache computes a CRC32 over every cached data
152 range when it is inserted and stores it in the on-media key. Reads
153 validate the CRC before copying to the caller.
154
155
156 Failure handling
157 ================
158
159 * *pmem media errors* – all metadata copies are read with
160 ``copy_mc_to_kernel``; an uncorrectable error logs and aborts initialisation.
161 * *Cache full* – if no free segment can be found, writes return ``-EBUSY``;
162 dm-pcache retries internally (request deferral).
163 * *System crash* – on attach, the driver replays ksets from *key_tail* to
164 rebuild the in-core trees; every segment’s generation guards against
165 use-after-free keys.
166
167
168 Limitations & TODO
169 ==================
170
171 * Only *write-back* mode; other modes planned.
172 * Only FIFO cache invalidate; other (LRU, ARC...) planned.
173 * Table reload is not supported currently.
174 * Discard planned.
175
176
177 Example workflow
178 ================
179
180 .. code-block:: shell
181
182 # 1. Create devices
183 dmsetup create pcache_sdb --table \
184 "0 $(blockdev --getsz /dev/sdb) pcache /dev/pmem0 /dev/sdb 4 cache_mode writeback data_crc true"
185
186 # 2. Put a filesystem on top
187 mkfs.ext4 /dev/mapper/pcache_sdb
188 mount /dev/mapper/pcache_sdb /mnt
189
190 # 3. Tune GC threshold to 80 %
191 dmsetup message pcache_sdb 0 gc_percent 80
192
193 # 4. Observe status
194 watch -n1 'dmsetup status pcache_sdb'
195
196 # 5. Shutdown
197 umount /mnt
198 dmsetup remove pcache_sdb
199
200
201 ``dm-pcache`` is under active development; feedback, bug reports and patches
202 are very welcome!
203

3. 한국어 전문 번역

영어 원문의 문단 순서와 의미를 유지한 전체 번역입니다. 코드, 함수명, symbol과 URL은 원문 표기를 유지합니다.

DAX persistent cache 구조와 기능

1-25

저자는 Dongsheng Yang `<dongsheng.yang@linux.dev>`입니다. `dm-pcache`는 byte-addressable DAX persistent-memory, 즉 pmem 영역을 느린 block device 앞의 고성능 crash-persistent cache로 사용하는 Device-Mapper target입니다. 구현은 `drivers/md/dm-pcache/`에 있습니다.

dm-pcache I/O 경로
Upper-layer I/ODevice-Mapper `dm-pcache`Pure DAX pathPMem cacheBackground write-backBacking device

빠른 DAX pmem이 느린 backing block device 앞에서 write-back cache로 동작합니다.

빠른 기능 요약
기능내용
Cache mode현재는 write-back만 지원
AllocationPMem 장치에서 16 MiB segment 단위 할당
Data 검증Cache별 선택 가능한 CRC32
Metadata crash-safety모든 metadata 구조를 두 벌로 복제(`PCACHE_META_INDEX_MAX == 2`)하고 CRC와 sequence number로 보호
IndexingLogical address로 sharding한 multi-tree indexing으로 PMem 병렬성 향상
I/O path추가 BIO 왕복이 없는 pure DAX path
Write-backBackend crash-consistency를 보존하는 log-structured 방식

현재 구현의 cache 정책, 배치, 검증과 crash-safety 특성입니다.

Target constructor와 최초 format

26-60

Target constructor 형식은 다음과 같습니다.

    pcache <cache_dev> <backing_dev> [<number_of_optional_arguments> <cache_mode writeback> <data_crc true|false>]
dm-pcache constructor 인자
인자의미
`cache_dev`DAX-capable block device, 예: `/dev/pmem0`. 모든 metadata와 cached block 저장
`backing_dev`Cache할 느린 block device
`cache_mode`선택 인자. 현재는 `writeback`만 허용
`data_crc`선택 인자, 기본 `false`. `true`면 각 cached entry의 CRC32를 저장하고 read에서 검증하며, `false`면 더 빠른 비검증 경로 사용
undefinedundefined

Cache 장치, backing 장치와 optional key/value 인자를 지정합니다.

=========================  ====================================================
``cache_dev``               Any DAX-capable block device (``/dev/pmem0``…).
                            All metadata *and* cached blocks are stored here.

``backing_dev``             The slow block device to be cached.

``cache_mode``              Optional, Only ``writeback`` is accepted at the
                            moment.

``data_crc``                Optional, default to ``false``

                            * ``true``  – store CRC32 for every cached entry
			      and verify on reads
                            * ``false`` – skip CRC (faster)
=========================  ====================================================

다음 예는 `/dev/pmem0`를 `/dev/sdb`의 write-back cache로 사용하고 data CRC를 활성화합니다.

   dmsetup create pcache_sdb --table \
     "0 $(blockdev --getsz /dev/sdb) pcache /dev/pmem0 /dev/sdb 4 cache_mode writeback data_crc true"

PMem 장치를 처음 사용하면 `dm-pcache`가 superblock과 `cache_info` 등을 자동으로 format합니다.

Status line과 세 개의 log cursor

61-101

`dmsetup status <device>`의 `STATUSTYPE_INFO` 출력 형식은 다음과 같습니다.

   <sb_flags> <seg_total> <cache_segs> <segs_used> \
   <gc_percent> <cache_flags> \
   <key_head_seg>:<key_head_off> \
   <dirty_tail_seg>:<dirty_tail_off> \
   <key_tail_seg>:<key_tail_off>
dm-pcache status 필드
필드의미
`sb_flags`Endian marker 등을 포함한 superblock flag
`seg_total`물리 pmem segment 수
`cache_segs`Cache에 사용하는 segment 수
`segs_used`현재 할당된 segment 수, 즉 bitmap weight
`gc_percent`현재 GC high-water mark, 0~90
`cache_flags`Bit 0 DATA_CRC, bit 1 INIT_DONE, bits 2~5 cache mode(0은 WB)
`key_head`새 key-set을 기록하는 위치
`dirty_tail`Backing device에 아직 write-back해야 하는 첫 dirty key-set
`key_tail`GC가 회수할 수 있는 첫 key-set

용량, GC 임계값, cache 상태와 log cursor 위치를 보여 줍니다.

===============================  =============================================
``sb_flags``                     Super-block flags (e.g. endian marker).

``seg_total``                    Number of physical *pmem* segments.

``cache_segs``                   Number of segments used for cache.

``segs_used``                    Segments currently allocated (bitmap weight).

``gc_percent``                   Current GC high-water mark (0-90).

``cache_flags``                  Bit 0 – DATA_CRC enabled
                                 Bit 1 – INIT_DONE (cache initialised)
                                 Bits 2-5 – cache mode (0 == WB).

``key_head``                     Where new key-sets are being written.

``dirty_tail``                   First dirty key-set that still needs
                                 write-back to the backing device.

``key_tail``                     First key-set that may be reclaimed by GC.
===============================  =============================================
Key-set cursor 관계
`key_tail`GC 가능 live/dead 경계`dirty_tail`Clean/dirty 경계`key_head`새 key-set 기록

세 cursor가 새 기록, dirty write-back 경계와 GC 회수 경계를 나눕니다.

GC trigger runtime message

102-111

Runtime message로 GC가 시작되는 사용률 임계값을 0부터 90 사이에서 변경할 수 있습니다.

   dmsetup message <dev> 0 gc_percent <0-90>
GC 임계값 변경
`dmsetup message <dev> 0``gc_percent <0-90>`새 GC high-water mark

Target sector 0에 message를 보내 새 high-water mark를 적용합니다.

Sub-device, segment와 key-set

112-133

`backing_dev`는 SSD, HDD, loop, LVM 등을 포함한 임의의 block device입니다. `cache_dev`는 direct-access memory를 노출하는 DAX 장치여야 합니다.

dm-pcache sub-device
장치요건과 역할
`backing_dev`원본 data를 보관하는 임의의 block device
`cache_dev`Direct-access memory를 제공하는 DAX PMem 장치

Cache data path의 두 저장 계층입니다.

====================  =========================================================
backing_dev             Any block device (SSD/HDD/loop/LVM, etc.).
cache_dev               DAX device; must expose direct-access memory.
====================  =========================================================

PMem 공간은 16 MiB segment로 나뉩니다. 각 write는 segment 안의 per-CPU `data_head`에서 공간을 할당합니다. `cache-key`는 origin의 logical range와 PMem 내 위치인 segment, offset, generation을 기록합니다.

Key 128개가 하나의 key-set, 즉 kset을 이룹니다. Kset은 PMem에 순차 기록되고 자체 CRC로 crash-safe하게 보호됩니다. `(key_tail, dirty_tail)` 쌍은 clean/dirty kset과 live/dead kset의 경계를 정합니다.

Segment와 key-set 배치
16 MiB PMem segmentPer-CPU `data_head`Cached data range`cache-key` = logical range + segment + offset + generation128 keysCRC-protected kset

Per-CPU append 위치에서 data를 할당하고 key를 128개씩 crash-safe kset으로 묶습니다.

Write-back, garbage collection과 CRC 검증

134-155

Dirty key는 tree에 queue됩니다. Background worker가 data를 `backing_dev`로 복사하고 `dirty_tail`을 전진시킵니다. Upper layer의 FLUSH 또는 FUA bio는 metadata를 즉시 commit하도록 강제합니다.

Background write-back
Cached writeDirty key treeBackground worker`backing_dev`로 data 복사`dirty_tail` 전진
FLUSH/FUA bio즉시 metadata commit

Dirty tree를 순회해 backing device에 반영하고 clean 경계를 이동합니다.

GC는 `segs_used >= seg_total * gc_percent / 100`일 때 시작합니다. `key_tail`부터 순회해 모든 key가 invalidate된 segment를 해제하고 `key_tail`을 전진시킵니다.

Garbage collection
Segment 사용률 계산`gc_percent` 이상`key_tail`부터 scan모든 key invalidated?Segment free`key_tail` 전진

High-water mark를 넘으면 가장 오래된 kset부터 완전히 죽은 segment를 회수합니다.

`data_crc`를 활성화하면 cached data range를 삽입할 때마다 CRC32를 계산해 on-media key에 저장합니다. Read에서는 caller에게 복사하기 전에 CRC를 검증합니다.

Data CRC 경로
Cache insertData range CRC32 계산On-media key에 저장Cached readCRC 재검증Caller로 복사

삽입 시 저장한 CRC32와 read 시 재계산 값을 비교합니다.

Failure 처리와 현재 제약

156-175
Failure 처리
상황처리
PMem media error모든 metadata copy를 `copy_mc_to_kernel`로 읽고 uncorrectable error를 log한 뒤 초기화 중단
Cache fullFree segment가 없으면 write에 `-EBUSY`; request deferral로 내부 재시도
System crashAttach 시 `key_tail`부터 kset을 replay해 in-core tree 재구축; segment generation으로 use-after-free key 방지

Media 오류, cache 부족과 crash 재부착 상황의 동작입니다.

현재 limitation과 TODO
항목현재 상태
Cache modeWrite-back만 지원, 다른 mode 계획
InvalidationFIFO만 지원, LRU·ARC 등 계획
Table reload현재 미지원
Discard계획됨

문서 시점에 지원하지 않거나 계획된 기능입니다.

생성부터 종료까지의 예제 workflow

176-202

다음 workflow는 target 생성, filesystem 생성과 mount, GC 임계값 조정, status 관찰, 안전한 unmount와 제거 순서를 보여 줍니다.

   # 1.  Create devices
   dmsetup create pcache_sdb --table \
     "0 $(blockdev --getsz /dev/sdb) pcache /dev/pmem0 /dev/sdb 4 cache_mode writeback data_crc true"

   # 2.  Put a filesystem on top
   mkfs.ext4 /dev/mapper/pcache_sdb
   mount /dev/mapper/pcache_sdb /mnt

   # 3.  Tune GC threshold to 80 %
   dmsetup message pcache_sdb 0 gc_percent 80

   # 4.  Observe status
   watch -n1 'dmsetup status pcache_sdb'

   # 5.  Shutdown
   umount /mnt
   dmsetup remove pcache_sdb
dm-pcache 운영 workflow
`dmsetup create pcache_sdb``mkfs.ext4``mount /mnt``gc_percent 80``dmsetup status` 관찰`umount``dmsetup remove`

Cache 장치를 만든 뒤 filesystem을 사용하고 GC를 조정한 다음 순서대로 종료합니다.

`dm-pcache`는 활발히 개발 중이며 feedback, bug report와 patch를 환영합니다.