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
|
% The Linux Kernel
[back](index.md)
TODO: A word about how the kernel is in charge of enforcing security
TODO: Talk about `dmesg`
Role
----
A kernel is a piece of software that is loaded at boot time. It is a
component that is responsible for "orchestrating" the OS in different
manners. There are different types of kernel in this world, and they may
have different responsibilities. We will be focusing solely on the role
of the Linux kernel here.
### Hardware control and abstraction
One goal for a kernel is to be the "glue" between the hardware and
other software.
For example, let's suppose two pieces of software want to store data in
a hard drive. Without hardware control, if these two softwares were to
run concurrently, they both would try to control the spinning hard
drive, potentially trying to make it go in different directions.
Without hardware control, each software would have to consciously and
constantly collaborate with each other to avoid conflict when accessing
each piece of hardware.
With the Linux kernel accessing the hardware is gated by an API: each
software that wants to access the hard drive has to go use system calls
(e.g.: `read(2)` / `write(2)`), and the kernel will then schedule
these tasks sequentially.
Another important point, is that without the Linux kernel, each piece of
software would have to care if the hard drive is a spinning disk, an
SSD, or a USB stick, or if is connected using a SATA cable, a USB cable,
etc.
The Linux kernel allows us to not care about this, and provides us with
the filesystem abstraction, and mount points. To the software developer
doing a `read` on a file doesn't change if the file is stored on an
SSD or even on a network filesystem, because the kernel will check that
for us, and apply the appropriate logic.
### Multitasking
Another big role of the Linux kernel is to allow multiple programs to
run concurrently: the CPU doesn't have knowledge of processes or
threads, it just runs binary code.
Let's say we have a CPU with 4 cores. That means that the CPU can truly run
only 4 tasks in parallel.
As a user with this CPU, this doesn't impact me that I'm running a graphical
interface, a web browser, a mail client, a terminal window, and a video player.
Each of these 5 applications feels responsive even if the CPU can only run 4 of
them at the time.
This is because the kernel is responsible for switching the tasks that the CPU
runs (a.k.a. scheduling). Theses tasks / applications are switched quickly and
in such a way that they feel responsive to the user.
The Linux kernel also provides developers with another abstraction to
execute tasks concurrently: threads. Threads are akin to having multiple
processes, except that when scheduled, they keep the same memory region
for their heap.
Without the kernel, the software developer would have to care about the
CPU architecture, how much cores it has, and would have to find the
right assembly instructions for the given CPU to run code in parallel,
and if they want to run more tasks concurrently than the amount of
available CPU cores, they would have to implement their own task
scheduler.
Thankfully we do not have to care about that, because the Linux kernel
cares about it for us instead.
Sources
-------
The official sources of the Linux kernel can be found in
[kernel.org](https://www.kernel.org)[^distrib-patches].
[^distrib-patches]:
Note that these are the *original* sources. Lots of GNU/Linux distributions
incorporate additional patches to the source of their Linux kernel.
This might be done for various reasons, like for security, performance, or
additional experimental features (e.g.
[Debian](https://sources.debian.org/patches/linux/5.7.6-1/),
[Gentoo](https://gitweb.gentoo.org/proj/linux-patches.git/tree/?h=5.7))
The official programming language of the Linux kernel is C. It is
heavily documented in the `Documentation` subdirectory, using the
sphinx documentation system.
Versioning
----------
TODO: this section
Dependencies
------------
To compile a Linux kernel whose version is greater than 5.2, one needs
the following dependencies:
<!--
A C compiler:: GCC, or Clang Perl 5:: An old scripting language bc:: A
command line calculator net-tools:: Some networking-related command-line
tools (contains for example the `ifconfig` command) openssl:: A well
known cryptography library rsync:: A command line utility to copy /
synchronize files and directories gmp:: A library for doing arithmetic
with arbitrary precision mpc:: A library for doing complex arithmetic
with arbitrary precision mpfr:: A library for doing floating-point
arithmetic with arbitrary precision libelf:: A library for reading ELF
file. ELF is the standard executable format used for Linux. utillinux::
A set of system utilities for Linux (contains for example the `dmesg`
command) bison:: A parser generator flex:: A lexical analyser generator
cpio:: A command-line utility for CPIO compressed archives
-->
TODO: Also refer to their Debian, Ubuntu, etc. packages.
Configuring the kernel
----------------------
```sh
make nconfig
```
Building the kernel
-------------------
```sh
make -j8
```
Running the kernel
------------------
TODO: link the QEMU article
```c
#include <stdio.h>
/**
* \brief The entry point of the program.
*
* \param argc the number of command line arguments
* \param argv the command line argument, as an array of NULL terminated strings
*/
int main(int argc, char** argv) {
for(int i = 0; i < argc; ++i) {
printf("Argument %i: %s\n", i, argv[i]);
}
}
```
|