summaryrefslogtreecommitdiffstats
path: root/presentation/presentation.tex
blob: b86129c101c2af1df12024d46b76a2d90191473a (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
%-------------------------------------------------------------------------------
% presentation.tex - presentation of the QCOW2 in-kernel project
%-------------------------------------------------------------------------------
% author   : Manuel Bentele
% date     : Aug 26, 2019
% copyright: (c) 2019 Manuel Bentele
%-------------------------------------------------------------------------------

\documentclass[english]{beamer}

%-------------------------------------------------------------------------------
% Presentation theme settings
%-------------------------------------------------------------------------------
\usetheme{Malmoe}
\usecolortheme{beaver}
\useinnertheme{rounded}

%-------------------------------------------------------------------------------
% Used packages
%-------------------------------------------------------------------------------
\usepackage{colortbl}
\usepackage{xcolor}
\usepackage{hyperref}
\usepackage{tikz}
\usetikzlibrary{positioning, calc, arrows}
\usepackage{pgfplots}
\usepackage{pgfplotstable}
\pgfplotsset{compat = newest}
\usepackage{pifont}

%-------------------------------------------------------------------------------
% Custom macros and definitions
%-------------------------------------------------------------------------------
\makeatletter\let\frametextheight\beamer@frametextheight\makeatother

\newcommand{\cmark}{\ding{51}}
\newcommand{\xmark}{\ding{55}}

\colorlet{hdr}{green!15}
\colorlet{ret}{yellow!15}
\colorlet{reb}{orange!15}
\colorlet{l1t}{red!15}
\colorlet{l2t}{violet!15}
\colorlet{dat}{cyan!15}

%-------------------------------------------------------------------------------
% General definitions
%-------------------------------------------------------------------------------
\title{QCOW2 in the Linux kernel}
\author[M. Bentele]{Manuel Bentele}
\institute{University of Freiburg}
\date{September 2, 2019}

\begin{document}

\begin{frame}
    \maketitle
\end{frame}

\section{Analysis}
\subsection{Requirements}
\begin{frame}{What has to be done?}
    \begin{block}{Implement the QCOW (QEMU Copy On Write) disk file format version~2 in the Linux kernel such that \dots}
        \vspace*{0.5cm}
        \begin{itemize}
            \item reading of the normal QCOW2 disk file format is possible
            \item compressed \& sparse QCOW2 disk files are supported as well
            \item the disk file format is exposed as block device
            \item the implementation compiles \& runs under Linux kernel 5 later
            \item the performance is better than using qemu-nbd
        \end{itemize} 
    \end{block}
\end{frame}

\subsection{Linux storage stack}
\begin{frame}{How does the Linux storage stack looks like?}
    \begin{center}
        \resizebox{!}{0.775\textheight}{
            \input{images/linux_storage_stack}
        }
    \end{center}
\end{frame}

\subsection{Implementation approaches}
\begin{frame}{How can the implementation be achieved?}
    \begin{block}{\xmark\ FUSE (Filesystem in Userspace) driver}
        \begin{itemize}
            \item implement reading of QCOW2 file format as user space driver
        \end{itemize}
    \end{block}
    \begin{block}{\xmark\ Device mapper target}
        \begin{itemize}
            \item implement reading of QCOW2 file format as mapped target
        \end{itemize}
    \end{block}
    \begin{block}{\xmark\ Custom block driver}
        \begin{itemize}
            \item create block driver \& configuration utility for reading QCOW2
        \end{itemize}
    \end{block}
    \begin{block}{\cmark\ Loop device module extension}
        \begin{itemize}
            \item extend the loop device module \& configuration utility by a file format subsystem to implement QCOW2 as additional file format driver
        \end{itemize}
    \end{block}
\end{frame}

\section{Implementation}
\subsection{Loop device module extension}
\begin{frame}{How is the file format subsystem integrated?}
    \resizebox{\textwidth}{!}{%
        \input{images/file_fmt_subsystem_integration}
    }
    \vfill
    \begin{itemize}
        \item file format subsystem abstracts the direct access to backing files to implement various file formats
        \item file formats are implemented as file format drivers
        \item drivers are registered at the subsystem
        \item subsystem supports (asynchronous) reads, (asynchronous) writes, flushes and virtual disk sizes
    \end{itemize}
\end{frame}

\begin{frame}[fragile, shrink=35]{How does a file format driver look like?}
\begin{verbatim}
#include "loop_file_fmt.h"

static int drv_file_fmt_read(struct loop_file_fmt *lo_fmt,
                             struct request *rq) {
    /* TODO: implement reading of file format */
    return -EIO;
}

static struct loop_file_fmt_ops drv_file_fmt_ops = {
    .read = drv_file_fmt_read
};
    
static struct loop_file_fmt_driver drv_file_fmt = {
    .name = "DRV",
    .file_fmt_type = LO_FILE_FMT_RAW,
    .ops = &drv_file_fmt_ops,
    .owner = THIS_MODULE
};

// register driver with loop_file_fmt_register_driver(&drv_file_fmt)
// unregister driver with loop_file_fmt_unregister_driver(&drv_file_fmt)
\end{verbatim}
\end{frame}

\subsection{QCOW2 file format driver}
\begin{frame}{How is the QCOW2 disk file format structured?}
    \begin{columns}
        \begin{column}[c]{0.25\textwidth}
            \resizebox{\textwidth}{!}{%
                \input{images/qcow2_structure}
            }
        \end{column}
        \begin{column}[c]{0.75\textwidth}
            \begin{itemize}
                \item data is saved in data clusters of equal size (512\,B -- 2\,MB)
                \item header provides offsets to 1st level tables
                \item two-level lookup of data clusters (L1 \& L2~tables)
                \item two-level reference count for copy on write (Refcount \& Refcount block tables)
                \item numbers are stored in big-endian order
                \item data clusters can be compressed or encrypted
                \item support of embedded snapshots by use of internal copy on write
            \end{itemize}
        \end{column}
    \end{columns}
\end{frame}

\begin{frame}{How does QCOW2 addresses data clusters?}
    \begin{itemize}
        \item QCOW2 header stores an offset in the file to the L1~table
        \item L1~table stores offsets in the file to L2 tables
        \item L2~tables stores offsets in the file to the data clusters
    \end{itemize}
    \begin{center}
        \resizebox{!}{0.55\textheight}{%
            \input{images/qcow2_addressing}
        }
    \end{center}
\end{frame}

\begin{frame}{How does the QCOW2 driver read data?}
    \begin{columns}
        \begin{column}[c]{0.4\textwidth}
            \resizebox{\textwidth}{!}{%
                \input{images/qcow2_reading}
            }
        \end{column}
        \begin{column}[c]{0.6\textwidth}
            Given a Linux IO read request with size $S$ and block device offset $O$:
            \begin{enumerate}
                \item calculate cluster $C$ and position $P$ for $O$ using cached L1 \& L2~tables
                \item decompress the data of $C$ if $C$ is compressed
                \item read data from $P$ into IO read request until $S$ bytes or the end of $C$ is reached
                \item repeat steps 1 -- 3 until IO read request is filled with $S$ bytes
            \end{enumerate}
        \end{column}
    \end{columns}
\end{frame}

\subsection{Performance of the driver}
\begin{frame}{How does the implementation perform compared to qemu-nbd?}
    \resizebox{\textwidth}{!}{
        \input{images/qcow2_performance}
    }
\end{frame}

\section{Outlook}
\subsection{Further work}
\begin{frame}{What can be done in the future?}
    \begin{block}{File format subsystem}
        \begin{itemize}
            \item implement other file formats, e.g. VDI, VMDK, \dots
            \item extend the API to support snapshots \& encryption
        \end{itemize}
    \end{block}
    \begin{block}{QCOW2 file format driver}
        \begin{itemize}
            \item implement write operations
            \item implement encryption \& snapshot support
            \item improve performance by hardware aligned cache allocation
            \item add a QCOW2 L2 cache clean interval
        \end{itemize}
    \end{block}
\end{frame}

\end{document}