Michael Kerrisk is a trainer, author, and programmer who has a passion for investigating and explaining software systems. He is the author of "The Linux Programming Interface", a widely acclaimed book on Linux (and UNIX) system programming. He has been actively involved in the Linux development community since 2000, operating mainly in the area of testing, design review, and documentation of kernel-user-space interfaces. Since 2004, he has maintained the Linux "man-pages" project, which provides the primary documentation for Linux system calls and C library functions. Michael is a New Zealander, living in Munich, Germany, from where he operates a training business (man7.org) providing low-level Linux programming courses in Europe, North America, and occasionally further afield.
Strace is a tool for monitoring the "system-call conversation" that takes place between applications and the Linux kernel. At the simplest level, it can be used to display the entire conversation, and--crucially--that conversation is displayed symbolically (without the need for application source code). Thus, one sees the names of system calls, the symbolic representation of each of bit-mask argument (using the names shown in the manual pages), structure arguments broken out into individual fields, and so on.
In this presentation, we'll examine the output produced by strace (including some subtle details) and look at the rich set of options it provides for limiting the trace to specific systems calls and signals, as well as accesses to specific files.
This two-day workshop provides a solid understanding of the operating system architecture and low-level interfaces (principally, system calls and library functions) that are required to build system-level applications on Linux (and UNIX) systems. By completion of the workshop, participants will have a good understanding of the construction of many common Linux and UNIX programs (e.g., the shell, ls(1), and cp(1))
(+) Topics marked with a plus sign will be covered as time permits.
1. Fundamental concepts
* System calls and library functions
* Error handling
* System data types
2. File I/O
* File descriptors
* I/O system calls: open(), close(), read(), write()
* Seeking to a file offset: lseek(); file holes
* Relationship between file descriptors and open files
* Duplicating file descriptors
* Open file status flags
* I/O buffering in stdio and the kernel
3. File attributes
* Retrieving file information: stat()
* File ownership and permissions
* Changing file attributes
4. Directories and links (+)
* Hard and soft (symbolic) links
* Current working directory
* System calls and library functions for working with directories and links
* Process ID and parent process ID
* Memory layout of a process
* Command-line arguments
* Environment list
6. Process Credentials
* Password and group file
* User and group IDs
* Process credentails: real and effective IDs; supplementary group IDs
* Retrieving process credentials
* Signal types and default actions
* Setting signal dispositions
* Signal handlers
* Blocking signals (the signal mask); pending signals
* Designing signal handler functions
* Reentrant and async-signal-safe functions
8. Process lifecycle
* Process creation: fork()
* File descriptors and fork()
* Process termination: exit(3) and _exit(2)
* Monitoring child processes: wait(), waitpid()
* Orphans and zombies
* The SIGCHLD signal
9. Executing programs
* Executing a program: execve()
* The exec() library functions
* File descriptors and exec()
10. Privileged programs (+)
* Set-user-ID and set-group-ID programs
* Changing process credentials
11. Using pipes and FIFOs for interprocess communication (+)
* Creating and using pipes
* Using pipes to connect filters
* Semantics of I/O on pipes and FIFOs
The following people are likely to find the workshop of particular benefit:
* Programmers developing system-level applications for Linux systems, or programmers porting such applications from other operating systems (e.g., Windows) to Linux.
* Embedded programmers developing applications for Linux, or porting embedded applications from systems such as VxWorks or QNX to Linux.
* DevOps engineers and sytem administrators who want to gain a greater insight into the oepration of Linux applications.
The workshop consists of a mixture of detailed presentations coupled with many coding exercises that allow participants to apply the knowledge learned in the presentations.
* You should have a good reading knowledge of C or C++. For the practical sessions, templates will be provided to relieve you of the need to type in tedious boilerplate code. The templates are in C, but if you wish, it is also possible to complete the exercises in another suitable language such as D, Rust, or of course C++.
* You should have a basic familiarity with the Linux/UNIX command line to do tasks such as listing directories, editing files, and compiling programs.
* No previous system programming experience is assumed.
You'll need a laptop with Linux installed--either as a native install or inside a virtual machine (VM). In the latter case, you should ensure that the VM has working Internet access. The system should have a C compiler (e.g., gcc) and "make" installed. (It's likely that both of these are provided as part of the default install, if you are setting up a new system.)
Seccomp (secure computing) is a means to limit the system calls a program may make to the Linux kernel. It can be used to select exactly which system calls are permitted (or denied) and to restrict the arguments that may be passed to those system calls. System call filtering is achieved by writing BPF programs--programs written for a small in-kernel virtual machine that is able to examine system call numbers and arguments.
In this session, I'll examine the BPF virtual machine and look at some illustrative examples of filter programs that restrict the set of permitted system calls. I'll also briefly mention some of the productivity aids available for writing BPF filters and consider some caveats regarding its use. The goal is to provide a solid understanding of a tool that has found use in a wide range of applications running on Linux, including Docker, LXC, various web browsers, systemd, Flatpak, and Firejail.