LWN.net Weekly Edition for February 18, 2021
Welcome to the LWN.net Weekly Edition for February 18, 2021
This edition contains the following feature content:
- What goes into default Debian?: what sort of experience should the default install provide?
- Malware in open-source web extensions: the story of the corruption of the Great Suspender browser extension.
- kcmp() breaks loose: a little-known Linux system call starts to see wider use.
- Introducing maple trees: a new data structure to help the kernel keep track of memory areas.
- Development statistics for the 5.11 kernel: where the code in 5.11 came from.
This week's edition also includes these inner pages:
- Brief items: Brief news items from throughout the community.
- Announcements: Newsletters, conferences, security updates, patches, and more.
Please enjoy this week's edition, and, as always, thank you for supporting LWN.net.
What goes into default Debian?
The venerable locate
file-finding utility has long been available for Linux systems, though its
origins are in the BSD world. It is a generally useful tool, but does have
a cost beyond just the disk space it occupies in the filesystem; there is a
periodic daemon program (updatedb)
that runs to keep the file-name database up to date. As a recent
debian-devel discussion shows, though, people have differing ideas of
just how important the tool is—and whether it should be part of the default installation of Debian.
There are several variants of locate floating around at this point. The original is described in a ;login: article from 1983; a descendant of that code lives on in the GNU Find Utilities alongside find and xargs. After that came Secure Locate (slocate), which checks permissions to only show file names that users have access to, and its functional successor, mlocate, which does the same check but also merges new changes into the existing database, rather than recreating it, for efficiency and filesystem-cache preservation. On many Linux distributions these days, mlocate is the locate of choice.
But Steinar H. Gunderson has created another variant, plocate, which he has suggested should be the standard locate for the upcoming Debian 12 ("Bookworm") release. He said that plocate can completely supplant mlocate:
He pointed out that mlocate used to be installed by default, but that was changed for Debian 10 ("Buster"). He would like to see locate return as part of the default install, but to use plocate instead:
Bernd Zeimetz agreed
that plocate should be part of the default install, as
did Paul Wise, but Wise was concerned about the cost of keeping the
database updated. Gunderson said
that plocate (like mlocate) tries to be smarter than
simply walking the whole filesystem. "It keeps track of the mtime of
each directory, and doesn't do the
readdir()/getdents() if it hasn't changed.
" But Josh Triplett argued that while
plocate is a good choice for the default locate for
Debian, it should not be part of the default (or base) install:
Beyond that, he pointed out that desktop environments often provide similar
functionality, "typically based on a change-watching API (e.g. inotify)
rather than a regularly scheduled update
". Gunderson said
that the amount of wasted time generally amounts to "a few
seconds every night
". Triplett noted that there
was a counterexample to that figure in the thread, but he also made a broader point about
defaults in the distribution:
The defaults need to cater for 1) the broadest set of users, and 2) users who are less likely to change the defaults. Most users don't run locate, and those who do are more likely to be users who can and do change the defaults. `apt install plocate` isn't hard for someone who uses locate to do.
But, as Gunderson pointed
out, systems that are shared by multiple users could benefit from
having locate available—without having to ask an administrator to
install it. He suggested that locate is a standard tool for users
of the command line, as well. Adrian Bunk said that
shared systems are "pretty rare
", but Russ Allbery pointed out that
"rare" might not be the right characterization: "They've become
*rarer*, but they're still very common in the academic and
scientific research world.
"
Bunk also noted that many non-technical Linux users never actually touch
the shell. Gunderson wondered
why Debian installs a whole host of other utilities (e.g. netcat,
lsof, the PCI utilities) that are really only
useful for technical, shell-aware Linux users. Those utilities are
"expected to be on a typical Linux system by almost
every technically-knowledgeable Linux user
", Marvin Renich said,
but locate does not quite rise to that level.
Others disagreed, of course. Bjørn Mork drew the line
differently, noting that administrators can always add tools that they
need, but sometimes users cannot:
In addition,
not having locate available by default is "yet another step away from being a
proper Unix system
", Mork said. Holger Levsen suggested
that it was perhaps time for someone to create a package that installs a "proper Unix system".
There would, of course, be differing opinions on what constitutes such a
system, which is part of what is driving the question of a default locate
as well. One suspects that hair length
or color
would not actually play much of a role as was (jokingly) suggested, but
several
packages with different choices could be accommodated, as Levsen noted.
So it would seem that plocate will be the default locate for Debian, though mlocate will still be available, but neither will be installed by default. Or at least there was no huge groundswell of support to change the current practice. That is in keeping with the practice of other Linux distributions (Fedora, openSUSE, Ubuntu, and RHEL, at least), but it is understandable that locate might be missed. find is a reasonable substitute, but it lacks the instant feedback that locate provides. For me, that's worth installing an extra package and expending a few seconds per day—your mileage may vary.
Malware in open-source web extensions
On February 4, millions of browser tabs were suddenly terminated. Not everyone was surprised; the dozen people who spent the last four months waiting for this tragedy to occur watched in relief as the first in a rapid stream of GitHub comments began pouring in. The Great Suspender, a Chrome extension that suspended inactive tabs, with around two-million users, had been forcibly uninstalled because it contained malware. This was a serious problem for users, in part due to the difficulty in recovering the lost tabs, but the extension's malevolence had been painfully obvious to anyone who cared to investigate it.
Who owns the code?
This extension was compromised not because some cunning cracker had gotten into the build infrastructure or thanks to a failure to escape certain metacharacters. Instead it was due to an open question in free and open-source software communities: Who owns the code? The entire point of an open-source license is to divorce us from being restricted to one group controlling everything about the code. Rather, the code is owned by the community around it, as opposed to any one individual. However, that is only true in theory when it comes to many types of software.
The reason this theory breaks down in practice is that the code doesn't magically move from one member of the community to another: somewhere, there needs to be a canonical place for patches and pull requests to be unified into releases. Such a location needs an owner: a person to operate the server, hold the GitHub accounts, sign the releases, and push them to distributors.
But what happens when the original creator decides to move on? In the case of Python, we can see that play out in real time. Many projects are not titanic behemoths with a dedicated foundation and complete governance system, however; instead, they may just have a single maintainer who manages the occasional patch from the community. Sites that host code for open-source projects (e.g. GitHub) do allow for having a core team of maintainers and a collection of other contributors, each able to continue to evolve the project on their own. But some distribution systems, such as the Chrome Web Store or the Apple App Store, effectively require a single person to be responsible for the code and every one of its releases.
Since the original creator has exclusive control over the account for the distribution channel (which is typically the user's only gateway to the program), it logically follows that they are responsible for transferring control to future maintainers, despite the fact that they may only have the copyright on a portion of the software. Additionally, as the distribution-channel account is the property of the project owner, they can sell that account and the accompanying maintainership. After all, while the code of the extension might be owned by its larger community, the distributing account certainly isn't.
Such is what occurred for The Great Suspender, which was a Chrome extension on the Web Store that suspends inactive tabs, halting their scripts and releasing most of the resources from memory. In June 2020, Dean Oemcke, the creator and longtime maintainer, decided to move on from the project. He transferred the GitHub repository and the Web Store rights, announcing the change in a GitHub issue that said nothing about the identity of the new maintainer. The announcement even made a concerning mention of a purchase, which raises the question of who would pay money for a free extension, and why.
Of course, as the vast majority of the users of The Great Suspender were not interested in its open-source nature, few of them noticed until October, when the new maintainer made a perfectly ordinary release on the Chrome Web Store. Well, perfectly ordinary except for the minor details that the release did not match the contents of the Git repository, was not tagged on GitHub, and lacked a changelog.
Had I not been bored, I never would have searched for a changelog, found the GitHub repository, and seen the allegations that the new maintainer had included a malicious script in the release. Worse, the only reason I knew about the release was due to the nature of the extension itself: virtually every other browser extension gives no notice of updates. Because The Great Suspender needs to seize control of a tab's process to suspend it, it has a fairly elaborate mechanism to warn about and conduct updates, which is a direct result of the problems that otherwise occur.
Investigating
What followed from that October discovery was a roller-coaster ride: only a few security amateurs had decided to take a look at the update and we had no idea what to do. The extension now seemed to be downloading and executing a JavaScript file from an unrelated third-party domain. That domain appeared to be Open Web Analytics, a perfectly legitimate alternative to the Google Analytics already used by the extension: crisis averted. Well, until we discovered that the domain was utterly unrelated and was actually delivering a script that would be linked to other malicious browser extensions. While the JavaScript of Chrome extensions is required to be distributed in unobfuscated form, remote scripts are (clearly) not verified. Since discovering the function of a minified JavaScript file is a difficult task, and the actual script served could have varied, the exact details of what the extension did remain unclear.
While some suspect that the remote script was committing advertising fraud by rewriting referral headers, those suspicions are based on analysis of other malicious extensions that use the same analytics ID as the loaded script. Shortly before the update, the new owner made some minor changes in order to justify the addition of request-intercepting permissions. Thus, it is feared that the remote script was harvesting the logins from HTTP forms, as well as authentication cookies. Unfortunately, confirming those suspicions is difficult: the server serves an innocent version of Open Web Analytics to direct requests (i.e. those sent by directly visiting the page), and likely performed multiple levels of verification to make the true version hard to capture. Since Google has removed the extension as malware, the malicious version of the JavaScript code has likely stopped being served altogether. The investigators, having proven that the extension was not running Open Web Analytics despite the clear efforts to masquerade as such, simply concluded that it was malicious and moved on.
That release, which granted the power to inspect and modify all the HTTP(S) requests of over a million browsers to a malicious domain, happened in October 2020. A follow-up release, which removed the malicious code, was published after a month, but it appears that the original version had disabled auto-updating, since most existing installations kept the malicious version until it was forcibly removed. Four months passed before that time, during which the extension's entire user base wasn't just vulnerable, but was effectively already hacked.
This shows another problem: how the extension's malware nature faded from sight. The progression of experiences for each user who discovered the malevolent behavior was clear: following a brief period of outrage, possibly paired with a report to Google, the user would uninstall the Web Store version and sideload a safe version from source (which is the only way to prevent Chrome from automatically updating to the compromised version). As a result, they would move on from the discussion, resulting in long periods of silence where all involved parties decided that, since they were now safe from the malware, it was no longer their problem. Meanwhile, new GitHub issues continued to be opened, driving the dire warnings of immediate security compromise further and further away from even a suspicious investigator. Spikes in activity were few and far between: following a month of silence, a few Twitter accounts raised the issue in early January, leading to some reporting of the malware, but more weeks of silence would pass before Google's eventual ban.
Other examples
The Great Suspender had been compromised before, as have numerous other extensions. The ability to inspect the complete browsing activity of millions of users is worth a fortune, even if the attacker makes no effort to actually compromise any of their accounts. This makes web extensions an excellent target for the enterprising attacker. An eerily similar case is that of the paired extensions Nano Adblocker and Nano Defender, which were forked from uBlock Origin.
UBlock Origin is a widely-distributed, open-source ad-blocking extension intended to be fast, lightweight, and reasonably user-friendly, while still offering advanced filtering capabilities. UBlock Origin was itself forked from the original uBlock by its original creator, Raymond Hill, after (you guessed it) he transferred ownership of uBlock to a new, untrustworthy maintainer, Chris Aljoudi. In addition to creating a website solely to solicit donations, Aljoudi began reducing blocking features, eventually choosing to permit certain ads via the "acceptable ads" program. This effectively meant that large ad providers could easily pay to have their ads not be blocked: in short, the original uBlock joined the long list of ad-blockers that do the exact opposite.
As a result, Hill created a fork, now called uBlock Origin, which reverted the changes. When Hugo Xu later created Nano Adblocker, it was based on uBlock Origin, adding additional functionality to let users submit reports of unblocked ads for later review and fixes. Xu also created an extension to protect against websites that try to block users of uBlock-based ad-blockers, called Nano Defender. However, the massive strain of needing to triage the ever-changing web sites that were working to get through the filters led Xu to sell both extensions to an undisclosed group of Turkish developers. Nano Defender and its 200,000+ users, upon their recent acquisition, immediately began having their personal data mined.
These two examples are only part of a larger problem with browser extensions, even those that are open source. These extensions are available for free, subject to minimal review, and are easily published in the same locations as legitimate extensions. As a result, browser extensions with explicitly malicious practices appear all the time and are one of the most popular methods of modern malware delivery.
It is often quite simple to convince an inexperienced user that this extension will improve their searching experience, or that one will block malicious domains. The developer then buries some code in the extension that turns the user's computer into an ad-viewing, money-making machine. Furthermore, since there is only minimal communication with users after they install, the acquisition of login credentials can turn even a existing, open-source extension with an established basis of trust into a security risk. The fact that the Chrome Web Store requires unobfuscated JavaScript in the extension is of little assistance when extensions can simply load a payload from what seems to be an innocent analytics provider, or even just rely on the rarity of JavaScript developers willing to install and examine large numbers of extensions to check for malware.
While both Nano Defender and The Great Suspender have been removed from the Web Store, and users have changed their work habits or moved to other extensions (uBlock Origin and The Marvellous Suspender, respectively), the underlying issues remain. Chrome's extensions platform has a long history of being understaffed, and moves slowly. This is reflected in the four months it took for Google to remove The Great Suspender, including a full month after news outlets reported on the problems. To prevent these issues from occurring again in the future, Google has been pushing a "Manifest V3", which (among other, more controversial requirements) bans the practice of executing any JavaScript loaded from a remote server. While this wouldn't block the Nano Defender attack, it would prevent the levels of indirection that were employed by The Great Suspender, which would make it much easier to identify and remove the malware. Other questions raised by this issue are the inability for extension authors to communicate with their users and the risks of automatically updating extensions for all users. While automatic updates are a useful feature, there are also some concerns with them, as these incidents have shown.
kcmp() breaks loose
Given the large set of system calls implemented by the Linux kernel, it would not be surprising for most people to be unfamiliar with a few of them. Not everybody needs to know the details of setresgid(), modify_ldt(), or lookup_dcookie(), after all. But even developers who have a wide understanding of the Linux system-call set may be surprised by kcmp(), which is not enabled by default in the kernel build. It would seem, though, that the word has gotten out, leading to an effort to make kcmp() more widely available.The kcmp() system call was added in 2012 to address a problem encountered by the checkpoint/restore in user space (CRIU) effort. The CRIU developers are working (with some success) toward the goal of being able to record the complete state of a set of processes to persistent storage, then restart those processes at some future time, possibly on a different machine. This would be challenging in the best of times, but the CRIU developers have taken on an additional handicap: doing the entire job from user space. Over the years attempts have been made to implement a kernel-based checkpoint mechanism, but none have even come close to being considered for merging. The user-space approach appears to be the only realistic way of solving the checkpoint/restore problem.
CRIU may be banished to user space, but the kernel community has still allowed the addition of features where needed to get the job done. For example, userfaultfd() helps in the migration of process memory, and various features of the clone() system call help with recreating processes that look the same as they did at checkpoint time. These helpers have made the checkpoint/restore job doable while still keeping most of the work out of the kernel.
One problem the CRIU developers encountered early on was determining whether two open file descriptors (possibly found in different processes) refer to the same open file within the kernel. Creating such file descriptors can be done with dup() or clone(); they can be spread across unrelated processes by sending SCM_RIGHTS datagrams. It was easy enough for CRIU to determine that two file descriptors refer to the same file by looking at the relevant entries in /proc; at restore time, that file can be opened again in both places to recreate the situation at checkpoint time.
If, however, two file descriptors refer to the same open file — if, in other words, they refer to the same file structure within the kernel — then replacing them with two independent descriptors at restore time may break the application. CRIU can do the right thing to restore these descriptors correctly, but only if it can detect that they are related at checkpoint time. That detection was not something that the kernel supported at the time.
Querying the provenance of file descriptors is, at its core, asking about the kernel's internal data structures; making that information available must be done with great care. One idea that was discussed early on was to have the kernel export the address of the file structure behind each descriptor; if two descriptors show the same address, then they are entangled and should be recreated in the same mode. But the kernel goes to some length to hide the addresses of its data structures to make attacks harder; this effort is not always successful, but it is deemed worth doing. So exposing addresses in this way is not something that will fly.
Instead, the developers finally added a system call to answer the actual question: are these two descriptors the same? That was kcmp():
int kcmp(pid_t pid1, pid_t pid2, int type, unsigned long idx1,
unsigned long idx2);
If type is KCMP_FILE, then the kernel will check whether file descriptor idx1 in the process whose ID is pid1 is the same as descriptor idx2 in pid2. There are a number of other resources that can be queried in the same way, but the question is always the same: are these two the same thing? This is a much safer question for the kernel to answer, but there are still restrictions; in particular, the calling process must have the privilege to use ptrace() on both of the target processes, and all processes involved must be in the same PID namespace.
Even with those restrictions, kcmp() made some people nervous. As a way of containing any possible damage, this system call was only built into kernels configured for checkpoint/restore functionality. If it was absent on most kernels, it could not be used to exploit those kernels, after all.
In the real world, though, the choices made by kernel developers about configuration options mean relatively little. Most users run kernels built by distributors, and distributors have an incentive to enable as many features as possible, even if relatively few users will need them. Most people will not complain about unneeded code in their kernels — code they probably do not even know is there — but they will definitely complain if some feature they need does not work. So, while checkpoint/restore users are relatively rare, distributors (Fedora and Ubuntu, for example) have enabled the feature for those who need it. That has made kcmp() widely available as well.
If you make a feature available, somebody will come along and use it, probably in some way you didn't anticipate. And so, it seems, the Mesa graphics library found a use for kcmp() that has nothing to do with checkpointing. At times, the library can find itself dealing with multiple file descriptors referring to the same underlying DRM devices; in this case, making changes to one will affect the other, probably in unsatisfying ways. To avoid this problem, Mesa checks (with kcmp()) to ensure that file descriptors are independent when needed.
That check will only work properly if kcmp() is actually available in the running kernel, though, and that is not the case on all distributions. Asking those distributors to enable the full checkpoint/restore functionality for kcmp() seems like overkill, so Chris Wilson instead submitted a patch to make kcmp() selectable independently. Describing the need for the patch, Daniel Vetter said:
Michel Dänzer, who implemented this functionality, defended
the use of kcmp() and expressed surprise that it wasn't
universally available. He asked what other solution he should have chosen,
but got no answer. Kees Cook noted that
kcmp() "is a really powerful syscall
", but that its
use is constrained and it's already widely available, "so it may be
okay to expose this
".
The first version of the patch enabled kcmp() by default, but that runs counter to normal practice even in the absence of any residual security concerns so, by the third version, the default was changed to "no". The system call will still be enabled, though, if either checkpoint/restore or graphics are enabled, meaning that it will be available on most kernels going forward. It would be fairly surprising if this patch were not merged for 5.12, and distributors may well backport it to older kernels as well.
Introducing maple trees
Seen from outside, the internals of the Linux kernel appear to be stable, especially in subsystems like the memory-management subsystem. However, from time to time, developers need to replace an internal interface to solve a longstanding problem. One such issue is contention on the lock used to protect essential memory-management structures, including the page tables and virtual memory areas (VMAs). Liam Howlett and Matthew Wilcox have been developing a new data structure, called a "maple tree", to replace the data structures currently used for VMAs. This potentially big change in internal kernel structures has been recently posted for a review in a massive patch set.
Linux is a virtual-memory system. The address space for each process contains multiple virtual memory areas represented by vm_area_struct structures. Each VMA represents a contiguous block of address space and represents a range of memory of the same type, which may be anonymous memory (not backed by a file), a memory-mapped file, or even device memory. A virtual memory area, as seen from the process, is contiguous, while the supporting physical memory may not be. In addition, the address space contains holes between the VMAs; the kernel fills those empty blocks (leaving space for unmapped "guard" pages to catch buffer overflows) when it needs to add a new mapped area, for example when loading a library or in a response to an mmap() call.
Almost anything one can do in the system involves memory, so the operations on the structures representing the VMAs must be fast. These operations include lookups (finding out which VMA corresponds to a given virtual address, finding out if the memory is mapped, or locating an empty gap for a new memory area), and modifications (growing a stack, for example).
VMAs are currently stored in a modified red-black tree (rbtree) with an additional, doubly-linked list that allows the kernel to traverse all of the VMAs in a process's address space. Kernel developers have been unhappy with this data structure for some time, for a number of reasons: rbtrees do not support ranges well, they are difficult to handle in a lockless manner (the balancing operation of the rbtree affects multiple items at the same time), and rbtree traversal is inefficient, which is why the additional linked list exists.
Operations on VMAs are protected by a lock (specifically a reader/writer semaphore), which is contained in struct mm_struct. This lock was called mmap_sem until it was renamed to mmap_lock for the 5.8 release in June 2020. This renaming was a part of an effort to wrap the lock in an API, hoping to ease its replacement in the future.
Users, especially those with threaded applications in large systems, often experience contention on this lock. The problem has been discussed by kernel developers numerous times, with at least three sessions discussing it at the 2019 Linux Storage, Filesystem, and Memory-Management Summit (LFSMM). The core of the problem is that the lock is required for many operations, including almost anything involving page tables and VMAs. There are other related structures that are effectively protected by mmap_lock (with the additional difficulty of lack of documentation of this fact). In addition to splitting the unrelated structures out from under mmap_lock, the developers were considering either using a structure that would allow lockless access to the VMAs or using some type of range lock. The maple tree was proposed as one of the solutions at that time, but at that time it was in an early state of development and the code was not available yet.
Introducing maple trees
Maple trees (the name might refer to the shape of the maple leaf, leading in multiple directions) differ in important aspects from rbtrees. They belong to the B-tree family, so their nodes can contain more than two elements — up to 16 elements in leaf nodes, or ten elements in internal nodes. The use of B-trees also means that there is less need to create new nodes, as nodes may include empty slots that can be filled over time without additional allocations. Each node requires at most 256 bytes, which is a multiple of popular cache line sizes. The increased number of elements in a node and the cache-aligned size means fewer cache misses when traversing the tree.
The improved support for searching in maple trees also comes from the B-tree structure. In a B-tree, each node holds keys, called "pivots", that separate the node into subtrees. A subtree before a given key contains only values lower or equal to the key, while subtree after the key contains only values higher than the key (and lower than the next key).
Of course, maple trees were designed to work in a lockless manner, using read-copy-update (RCU). The maple tree is a generic structure that can be used in different kernel subsystems; the first usage is replacing the rbtrees and linked lists to manage VMAs. One of the authors, Liam Howlett, explained the reasons for the design in a blog post.
Maple trees offer two APIs: the simple one and the advanced one. The simple API uses the mtree_ prefix for its functions, with the main structure, struct maple_tree, defined as follows:
struct maple_tree {
spinlock_t ma_lock;
unsigned int ma_flags;
void __rcu *ma_root;
};
The static initializers are DEFINE_MTREE(name) and MTREE_INIT(name, flags), with the latter taking a bitmask of flags from the two defined currently. MAPLE_ALLOC_RANGE indicates that the tree will be used to allocate ranges and that it should manage gaps between the allocations; MAPLE_USE_RCU activates the RCU mode for the case of multiple readers. Dynamic initialization is possible with the same flags using mtree_init():
void mtree_init(struct maple_tree *mt, unsigned int ma_flags);
Developers can free the whole tree with:
void mtree_destroy(struct maple_tree *mt);
Three functions exist to add entries to the tree; mtree_insert(), mtree_insert_range(), and mtree_store_range(). The first two functions only add an entry if it does not previously exist, while the third function can overwrite an existing entry. They are defined as follows:
int mtree_insert(struct maple_tree *mt, unsigned long index,
void *entry, gfp_t gfp);
int mtree_insert_range(struct maple_tree *mt, unsigned long first,
unsigned long last, void *entry, gfp_t gfp);
int mtree_store_range(struct maple_tree *mt, unsigned long first,
unsigned long last, void *entry, gfp_t gfp);
mtree_insert() takes a pointer to the tree mt, the integer key of the entry index, the pointer to the entry entry, and the memory allocation flags gfp for new tree nodes (if needed). mtree_insert_range() inserts a range from first to last with the given data entry. These functions return zero on success, and a negative value otherwise, including -EEXIST if the key already exists. Finally, mtree_store_range() takes the same arguments as mtree_insert_range(); the difference is that it replaces any existing entries for the corresponding keys.
Two functions exist to get an entry from the tree or remove an entry:
void *mtree_load(struct maple_tree *mt, unsigned long index);
void *mtree_erase(struct maple_tree *mt, unsigned long index);
To read an entry, the developer should use mtree_load(), which takes a pointer to the tree mt and the key of the requested value index. The function returns a pointer to the entry, or NULL if the key was not found in the tree. The same syntax is used to remove an entry from the tree using mtree_erase(). It removes the given key from the tree and returns the associated entry, returning NULL if no such value was found.
There is more to the simple API than the above, including mtree_alloc_range() to allocate a range from the key space. The advanced API (which uses the mas_ prefix) adds iterator functions for the traversal of the whole tree, or to access next and previous elements using a state variable. With this fine-grained control, developers can resume a search as needed. The API also allows developers to find empty areas or duplicate the tree.
Replacing the VMA rbtree (and more)
The patch set contains more than just the introduction of maple trees. It is worth noting that a big part of the set adds and updates tests, a welcome addition given the impact of the changes and the future importance of the new data structure.
In the 70 patches in this set, maple trees are used to replace rbtrees in all operations on VMAs, and one of the patches removes the usage of rbtrees from VMAs. Another part of the patch set leads to the removal of the VMA linked list. This removal requires modifications in various places in the kernel code that were using the VMA list directly: the architecture code, core dump and program loading routines, some device drivers, and of course the memory-management code. The patch set also removes the VMA cache (which tracks the VMAs that are most recently accessed by each process to speed lookup), as the implementation with maple trees is faster and the cache is no longer needed.
The cover letter includes some performance results, which are somewhat hard to interpret. Some microbenchmarks show a performance increase, and some (a smaller number) a decrease. Kernel compilation time is similar to that with the vanilla 5.10 kernel, with a few more instructions executed (probably linked to the added code). Howlett requested insights from developers into the results.
Current status and next steps
Maple trees are currently at the RFC stage, with limitations; the implementation does not support 32-bit systems or non-MMU platforms, for example. However, the code is functional and kernel developers may look into it to decide if it is the direction they want to go on the quest of removing mmap_lock (as the lock was not removed in this patch set). Based on the size of the patch set, it may take time until the review is finished.
Development statistics for the 5.11 kernel
The 5.11 kernel was released on February 14 — the most romantic sort of Valentine's day gift one could hope for. This kernel saw the merging of 14,340 changesets from 1,912 developers; it is certainly not the busiest development cycle we have seen recently, but it still saw a lot of activity. Read on for our traditional look at where the code merged for 5.11 came from.The history of the 5.x kernels to date looks like this:
Release Changesets Developers 5.0 12,808 1,760 5.1 13,034 1,727 5.2 14,024 1,784 5.3 14,605 1,882 5.4 14,619 1,877 5.5 14,350 1,885 5.6 12,665 1,712 5.7 13,901 1,878 5.8 16,306 1,991 5.9 14,858 1,917 5.10 16,174 1,971 5.11 14,340 1,912
The 5.11 development cycle, thus, looks fairly average and unremarkable in general — a middle-of-the road 5.x kernel. That said, the number of developers involved remains over 1,900; 280 of those developers made their first kernel contribution during the 5.11 cycle. The 5.11 kernel contains 608,000 more lines of code than 5.10 did.
The most active 5.11 developers were:
Most active 5.11 developers
By changesets Lee Jones 497 3.5% Krzysztof Kozlowski 195 1.4% Thomas Gleixner 148 1.0% Christophe Leroy 135 0.9% Chuck Lever 133 0.9% Christoph Hellwig 132 0.9% Sakari Ailus 126 0.9% Arnd Bergmann 119 0.8% Ville Syrjälä 119 0.8% Jonathan Cameron 115 0.8% Gustavo A. R. Silva 93 0.6% Tom Rix 90 0.6% Andy Shevchenko 89 0.6% Geert Uytterhoeven 87 0.6% Johannes Berg 86 0.6% Alex Elder 83 0.6% Takashi Iwai 83 0.6% Christian König 82 0.6% Colin Ian King 81 0.6% Trond Myklebust 81 0.6%
By changed lines Huang Rui 269436 28.0% Bhawanpreet Lakha 81661 8.5% Lee Jones 17973 1.9% Oded Gabbay 14281 1.5% Jiaxin Yu 13408 1.4% Johannes Berg 9764 1.0% Sakari Ailus 9305 1.0% Ilya Dryomov 7528 0.8% Srinivas Kandagatla 6072 0.6% Jonathan Cameron 5958 0.6% Fabio Estevam 5913 0.6% Christian König 5789 0.6% Roman Li 5370 0.6% Arnd Bergmann 5084 0.5% Chuck Lever 4681 0.5% Thomas Gleixner 4672 0.5% Christoph Hellwig 4612 0.5% Jin Yao 4577 0.5% Jarkko Sakkinen 4575 0.5% Peter Geis 4521 0.5%
Lee Jones was the contributor of the largest number of changesets this time around; the bulk of that work went into fixing compiler warnings throughout the tree. Krzysztof Kozlowski continues to contribute cleanups and small improvements to drivers and devicetree files. Thomas Gleixner worked on a lot of low-level improvements, including the kmap_local() mechanism. Christophe Leroy did a lot of work in the PowerPC architecture code, and Chuck Lever contributed a large number of (mostly) NFS-server changes.
The largest code addition — by far — was by Huang Rui, who added yet another set of massive amdgpu header files; Bhawanpreet Lakha also worked on the AMD graphics drivers. Oded Gabbay added support for the Habana "Gaudi" processor, which inevitably included a set of large header files, and Jiaxin Yu added the mt8192 audio driver.
Work on the 5.11 kernel was supported by 225 companies that we were able to identify; that is a typical number. The most active of those companies were:
Most active 5.11 employers
By changesets Intel 1364 9.5% (Unknown) 1106 7.7% Linaro 1050 7.3% Red Hat 836 5.8% AMD 825 5.8% Huawei Technologies 766 5.3% 698 4.9% (None) 523 3.6% SUSE 451 3.1% IBM 432 3.0% NVIDIA 400 2.8% 390 2.7% Arm 313 2.2% Samsung 288 2.0% NXP Semiconductors 284 2.0% (Consultant) 255 1.8% Oracle 250 1.7% Linutronix 233 1.6% Renesas Electronics 222 1.5% Code Aurora Forum 205 1.4%
By lines changed AMD 382664 39.7% Intel 94102 9.8% Linaro 47288 4.9% (Unknown) 39747 4.1% (None) 28334 2.9% 25976 2.7% Red Hat 24926 2.6% MediaTek 19657 2.0% NVIDIA 18029 1.9% Huawei Technologies 17853 1.9% NXP Semiconductors 15108 1.6% IBM 14767 1.5% SUSE 14337 1.5% 13033 1.4% (Consultant) 12716 1.3% Code Aurora Forum 12491 1.3% Arm 10065 1.0% BayLibre 9688 1.0% Linutronix 8843 0.9% Texas Instruments 7916 0.8%
As usual, there are few surprises here. If there is any sort of trend to point out in these results, it is that contributions from hardware companies are slowly growing in proportion relative to those from software and support companies.
Drilling down
The above numbers are all relative to the kernel source tree as a whole. If one looks at specific subsystems, the picture changes a bit. The results at this level tend to be more variable from one release to the next, so it makes sense to look over a long time period. The following numbers, thus, are accumulated over the time since the 5.5 release in January 2020; they are, in other words, a first approximation of the work that was merged last year.
Much of the core kernel code lives in the kernel directory. The developers and companies most actively working in that directory during 2020 were:
Most active (kernel)
Developers Paul E. McKenney 250 9.0% Peter Zijlstra 140 5.1% Christoph Hellwig 110 4.0% Thomas Gleixner 105 3.8% Steven Rostedt 98 3.5% Yonghong Song 59 2.1% Marco Elver 58 2.1% Masami Hiramatsu 56 2.0% Eric W. Biederman 44 1.6% Andrii Nakryiko 40 1.4%
Companies 486 17.6% Intel 294 10.6% 274 9.9% Red Hat 228 8.2% Linutronix 161 5.8% (Unknown) 141 5.1% Linaro 121 4.4% (Consultant) 112 4.0% VMware 98 3.5% Arm 97 3.5%
Over the last few years, Facebook has become the home to an increasing number of core-kernel developers, to the point that the company contributes far more patches to the kernel directory than any other.
The picture shifts a bit if one looks at patches to the memory-management code, found in the mm subdirectory.
Most active (mm)
Developers Christoph Hellwig 82 5.4% Matthew Wilcox 65 4.3% David Hildenbrand 60 4.0% Wei Yang 57 3.8% Roman Gushchin 51 3.4% Andrey Konovalov 48 3.2% Johannes Weiner 45 3.0% Vlastimil Babka 36 2.4% John Hubbard 34 2.2% Alex Shi 30 2.0% Mike Rapoport 30 2.0%
Companies Red Hat 162 10.7% 156 10.3% 121 8.0% (Unknown) 117 7.7% Oracle 95 6.3% (Consultant) 85 5.6% (None) 75 5.0% SUSE 73 4.8% Alibaba 73 4.8% Huawei Technologies 71 4.7% Intel 68 4.5%
The picture for filesystems looks like this:
Most active (fs)
Developers Pavel Begunkov 343 5.8% Christoph Hellwig 322 5.4% Jens Axboe 264 4.4% Darrick J. Wong 244 4.1% Josef Bacik 228 3.8% Trond Myklebust 207 3.5% Nikolay Borisov 199 3.3% Al Viro 174 2.9% Eric Biggers 154 2.6% Qu Wenruo 145 2.4%
Companies Red Hat 1043 17.5% SUSE 788 13.2% 690 11.6% Oracle 547 9.2% Huawei Technologies 389 6.5% (Consultant) 365 6.1% 347 5.8% (None) 314 5.3% (Unknown) 285 4.8% Hammerspace 207 3.5%
Much of the "filesystem" work over last year has been focused on the rapidly developing io_uring subsystem and on core infrastructural work. Beyond that, XFS, Btrfs, and NFS were all areas of active development.
And if one looks at the networking subsystem, the results are:
Most active (net)
Developers Chuck Lever 188 4.1% Christoph Hellwig 169 3.7% Paolo Abeni 136 3.0% Florian Westphal 124 2.7% Eric Dumazet 115 2.5% Karsten Graul 106 2.3% Pablo Neira Ayuso 105 2.3% Johannes Berg 100 2.2% Vladimir Oltean 83 1.8% Xin Long 77 1.7%
Companies Red Hat 573 12.5% 430 9.4% Intel 383 8.3% (None) 308 6.7% (Unknown) 303 6.6% (Consultant) 238 5.2% Oracle 219 4.8% Mellanox 183 4.0% IBM 179 3.9% Huawei Technologies 172 3.7%
There are a couple of interesting results here. Chuck Lever shows up for his work on the RPC code used by the NFS filesystem, for example, while Christoph Hellwig's work was mostly driven by improvements he was making elsewhere in the tree; neither is normally seen as a core networking developer. Paolo Abeni and Florian Westphal both worked on the mostly under-the-radar upstreaming of the multipath TCP code, which has been long in coming.
One conclusion that can be drawn here is that core-kernel work is somewhat concentrated in a relatively small number of companies. That said, it is much less so than it was some years ago. It would appear that more companies working within Linux have come to the conclusion that their interests lie in working beyond the specific subsystems needed to make their own hardware work. That seems like a good thing for the long-term sustainability of the kernel.
Brief items
Kernel development
Kernel release status
The 5.11 kernel was released on February 14. In the announcement, Linus said: "I know it's Valentine's Day here in the US - maybe give this release a good testing before you go back and play with development kernels. All right? Because I'm sure your SO will understand."
Headline features in 5.11 include Intel SGX support, a new system-call interception mechanism, the seccomp() constant-action bitmap optimization, the internal kmap_local() API, the epoll_pwait2() system call, and much more. See the LWN merge-window articles (part 1, part 2) and the (under development) KernelNewbies 5.11 page for more information.
Stable updates: 5.10.16, 5.4.98, and 4.19.176 were released on February 13, followed by 5.10.17 and 5.4.99 on February 17.
5.12 Merge window delayed
Those of us who are watching the mainline kernel repository may have been wondering why it appears that no pull requests for the 5.12 merge window have yet been acted upon. The problem, it seems, is power outages caused by the severe winter weather in the US Pacific northwest. Until that gets resolved, which could take a few days, the 5.12 merge window is likely to remain on hold.
Distributions
Gentoo mourns the loss of Kent Fredric
A brief post on the Gentoo site is in memory of Kent "kent\n" Frederic. "Kent was an active member of the Gentoo community for many years. He tirelessly managed Gentoo’s Perl support, and was active in the Rust project as well as in many other corners. We all remember him as an enthusiastic, bright person, with lots of eye for detail and constant willingness to help out and improve things. On behalf of the world-wide Gentoo community, our heartfelt condolences go out to his family and friends."
Development
Go 1.16 released
Version 1.16 of the Go language is available. New features include an "embed" package, Apple Arm64 support, use of modules by default, and build-performance improvements; see the release notes for details.Rust 1.50.0 released
Version 1.50.0 of the Rust language has been released. "For this release, we have improved array indexing, expanded safe access to union fields, and added to the standard library."
Development quote of the week
When you put together the lessons from each of the research exercises we've done, the result is a picture of different user segments having somewhat different interests and requirements. On the one hand, we have the large number of people who have never used GNOME or an open source desktop, to whom a familiar design is one that is generally preferable. On the other hand, there are users who don't want a carbon copy of the proprietary desktops, and there are (probably more technical) users who are particularly interested in a more minimal, pared back experience which doesn't distract them from their work.
The best way for the GNOME project to navigate this landscape is a tricky question, and it involves a difficult balancing act. However, with the changes that are coming in GNOME 40, we hope that we are starting out on that path, with an approach that both adopts some familiar conventions from other platforms, while developing and refining GNOME's unique strengths.
Page editor: Jake Edge
Announcements
Newsletters
Distributions and system administration
- DistroWatch Weekly (February 15)
- Lunar Linux Weekly News (February 12)
- openSUSE Tumbleweed Review of the Week (February 12)
- Tails Report (January)
- Ubuntu Weekly Newsletter (February 13)
Development
- Emacs News (February 15)
- What's cooking in git.git (February 10)
- LXC/LXD/LXCFS Weekly Status (February 15)
- OCaml Weekly News (February 16)
- Perl Weekly (February 15)
- PostgreSQL Weekly News (February 14)
- Python Weekly Newsletter (February 11)
- Racket News (February 15)
- Weekly Rakudo News (February 15)
- Ruby Weekly News (February 11)
- This Week in Rust (February 10)
Meeting minutes
- Fedora FESCO meeting minutes (February 17)
- Perl Steering Council meeting minutes (February 05)
- Perl Steering Council meeting minutes (February 12)
Calls for Presentations
CFP Deadlines: February 18, 2021 to April 19, 2021
The following listing of CFP deadlines is taken from the LWN.net CFP Calendar.
| Deadline | Event Dates | Event | Location |
|---|---|---|---|
| February 28 | June 15 June 16 |
stackconf online 2021 | Online |
| March 1 | May 2 May 3 |
PyCon Israel 2021 | Online |
| March 15 | May 13 May 15 |
Linux App Summit | online |
| March 19 | May 4 May 6 |
sambaXP 2021 | Online |
| March 22 | July 21 July 25 |
GUADEC | Online |
If the CFP deadline for your event does not appear here, please tell us about it.
Upcoming Events
Events: February 18, 2021 to April 19, 2021
The following event listing is taken from the LWN.net Calendar.
| Date(s) | Event | Location |
|---|---|---|
| February 18 February 20 |
DevConf.CZ | Online |
| March 20 March 21 |
LibrePlanet 2021 | Online |
| March 30 | Open Source 101 | Online |
| April 9 April 10 |
Grazer Linuxtage 2021 | Online |
If your event does not appear here, please tell us about it.
Security updates
Alert summary February 11, 2021 to February 17, 2021
| Dist. | ID | Release | Package | Date |
|---|---|---|---|---|
| Arch Linux | ASA-202102-9 | ansible | 2021-02-12 | |
| Arch Linux | ASA-202102-6 | chromium | 2021-02-12 | |
| Arch Linux | ASA-202102-13 | cups | 2021-02-12 | |
| Arch Linux | ASA-202102-12 | docker | 2021-02-12 | |
| Arch Linux | ASA-202102-1 | firefox | 2021-02-12 | |
| Arch Linux | ASA-202102-11 | gitlab | 2021-02-12 | |
| Arch Linux | ASA-202102-17 | glibc | 2021-02-12 | |
| Arch Linux | ASA-202102-22 | helm | 2021-02-12 | |
| Arch Linux | ASA-202102-16 | lib32-glibc | 2021-02-12 | |
| Arch Linux | ASA-202102-10 | minio | 2021-02-12 | |
| Arch Linux | ASA-202102-7 | nextcloud | 2021-02-12 | |
| Arch Linux | ASA-202102-8 | opendoas | 2021-02-12 | |
| Arch Linux | ASA-202102-5 | opera | 2021-02-12 | |
| Arch Linux | ASA-202102-15 | php | 2021-02-12 | |
| Arch Linux | ASA-202102-14 | php7 | 2021-02-12 | |
| Arch Linux | ASA-202102-21 | privoxy | 2021-02-12 | |
| Arch Linux | ASA-202102-18 | python-django | 2021-02-12 | |
| Arch Linux | ASA-202102-19 | python-jinja | 2021-02-12 | |
| Arch Linux | ASA-202102-20 | python2-jinja | 2021-02-12 | |
| Arch Linux | ASA-202102-2 | thunderbird | 2021-02-12 | |
| Arch Linux | ASA-202102-4 | vivaldi | 2021-02-12 | |
| Arch Linux | ASA-202102-3 | wireshark-cli | 2021-02-12 | |
| Debian | DLA-2559-1 | LTS | busybox | 2021-02-15 |
| Debian | DLA-2554-1 | LTS | firejail | 2021-02-11 |
| Debian | DLA-2557-1 | LTS | linux-4.19 | 2021-02-12 |
| Debian | DLA-2555-1 | LTS | netty | 2021-02-11 |
| Debian | DSA-4855-1 | stable | openssl | 2021-02-17 |
| Debian | DSA-4852-1 | stable | openvswitch | 2021-02-15 |
| Debian | DLA-2561-1 | LTS | ruby-mechanize | 2021-02-17 |
| Debian | DSA-4853-1 | stable | spip | 2021-02-16 |
| Debian | DSA-4851-1 | stable | subversion | 2021-02-13 |
| Debian | DLA-2556-1 | LTS | unbound1.9 | 2021-02-12 |
| Debian | DLA-2558-1 | LTS | xterm | 2021-02-14 |
| Fedora | FEDORA-2021-8aaccdbb5f | F33 | audacity | 2021-02-15 |
| Fedora | FEDORA-2021-7fb30b9381 | F32 | chromium | 2021-02-17 |
| Fedora | FEDORA-2021-b1d1655cef | F32 | community-mysql | 2021-02-15 |
| Fedora | FEDORA-2021-db50ab62d3 | F33 | community-mysql | 2021-02-15 |
| Fedora | FEDORA-2021-7716e59d84 | F32 | jasper | 2021-02-17 |
| Fedora | FEDORA-2021-0c18ee6369 | F33 | jasper | 2021-02-12 |
| Fedora | FEDORA-2021-4cebc3aff9 | F32 | java-1.8.0-openjdk | 2021-02-11 |
| Fedora | FEDORA-2021-09272cf059 | F33 | java-1.8.0-openjdk | 2021-02-11 |
| Fedora | FEDORA-2021-555c9aef71 | F32 | java-11-openjdk | 2021-02-11 |
| Fedora | FEDORA-2021-f8ede2fdfc | F32 | kernel | 2021-02-14 |
| Fedora | FEDORA-2021-76aaa904e2 | F33 | kernel | 2021-02-14 |
| Fedora | FEDORA-2021-ebc1c35c5d | F33 | libzypp | 2021-02-13 |
| Fedora | FEDORA-2021-98841e94ff | F33 | linux-firmware | 2021-02-12 |
| Fedora | FEDORA-2021-b1d1655cef | F32 | mysql-connector-odbc | 2021-02-15 |
| Fedora | FEDORA-2021-db50ab62d3 | F33 | mysql-connector-odbc | 2021-02-15 |
| Fedora | FEDORA-2021-ae5a54ba78 | F32 | php | 2021-02-12 |
| Fedora | FEDORA-2021-8e36e7ed1a | F33 | python-cryptography | 2021-02-12 |
| Fedora | FEDORA-2021-5329c680f7 | F33 | python-django | 2021-02-13 |
| Fedora | FEDORA-2021-d5cde50865 | F32 | python3.10 | 2021-02-13 |
| Fedora | FEDORA-2021-aef54ec149 | F32 | roundcubemail | 2021-02-17 |
| Fedora | FEDORA-2021-434b65378a | F33 | roundcubemail | 2021-02-17 |
| Fedora | FEDORA-2021-24fdc228e4 | F32 | rubygem-mechanize | 2021-02-11 |
| Fedora | FEDORA-2021-db8ebc547e | F33 | rubygem-mechanize | 2021-02-11 |
| Fedora | FEDORA-2021-510977db25 | F32 | spice-vdagent | 2021-02-17 |
| Fedora | FEDORA-2021-09ce0cdfac | F33 | spice-vdagent | 2021-02-12 |
| Fedora | FEDORA-2021-a3a0273cb2 | F33 | subversion | 2021-02-12 |
| Fedora | FEDORA-2021-93149af72b | F32 | thunderbird | 2021-02-12 |
| Fedora | FEDORA-2021-ab674d56bc | F33 | webkit2gtk3 | 2021-02-17 |
| Fedora | FEDORA-2021-4a437fe032 | F32 | xpdf | 2021-02-11 |
| Fedora | FEDORA-2021-013d9a30e0 | F33 | xpdf | 2021-02-11 |
| Fedora | FEDORA-2021-ebc1c35c5d | F33 | zypper | 2021-02-13 |
| Mageia | MGASA-2021-0083 | 7 | chromium-browser | 2021-02-15 |
| Mageia | MGASA-2021-0081 | 7 | gssproxy | 2021-02-11 |
| Mageia | MGASA-2021-0079 | 7 | gstreamer1.0-plugins-bad | 2021-02-10 |
| Mageia | MGASA-2021-0084 | 7 | kernel | 2021-02-15 |
| Mageia | MGASA-2021-0085 | 7 | kernel-linus | 2021-02-15 |
| Mageia | MGASA-2021-0077 | 7 | nethack | 2021-02-10 |
| Mageia | MGASA-2021-0078 | 7 | perl-Email-MIME and perl-Email-MIME-ContentType | 2021-02-10 |
| Mageia | MGASA-2021-0080 | 7 | phpldapadmin | 2021-02-11 |
| Mageia | MGASA-2021-0082 | 7 | trojita | 2021-02-15 |
| openSUSE | openSUSE-SU-2021:0276-1 | oSB SLE-15-SP2 | chromium | 2021-02-11 |
| openSUSE | openSUSE-SU-2021:0276-1 | oSB SLE-15-SP2 | chromium | 2021-02-11 |
| openSUSE | openSUSE-SU-2021:0278-1 | 15.2 | containerd, docker, docker-runc, | 2021-02-12 |
| openSUSE | openSUSE-SU-2021:0278-1 | 15.2 | containerd, docker, docker-runc, | 2021-02-12 |
| openSUSE | openSUSE-SU-2021:0271-1 | 15.2 | firejail | 2021-02-10 |
| openSUSE | openSUSE-SU-2021:0269-1 | 15.2 | java-11-openjdk | 2021-02-10 |
| openSUSE | openSUSE-SU-2021:0295-1 | librepo | 2021-02-15 | |
| openSUSE | openSUSE-SU-2021:0277-1 | 15.2 | librepo | 2021-02-12 |
| openSUSE | openSUSE-SU-2021:0277-1 | 15.2 | librepo | 2021-02-12 |
| openSUSE | openSUSE-SU-2021:0300-1 | 15.2 | mumble | 2021-02-16 |
| openSUSE | openSUSE-SU-2021:0274-1 | oSB SLE-15-SP2 | nextcloud | 2021-02-11 |
| openSUSE | openSUSE-SU-2021:0274-1 | oSB SLE-15-SP2 | nextcloud | 2021-02-11 |
| openSUSE | openSUSE-SU-2021:0283-1 | 15.2 | openvswitch | 2021-02-13 |
| openSUSE | openSUSE-SU-2021:0296-1 | 15.2 | opera | 2021-02-15 |
| openSUSE | openSUSE-SU-2021:0279-1 | oSB SLE-15-SP2 | privoxy | 2021-02-12 |
| openSUSE | openSUSE-SU-2021:0279-1 | oSB SLE-15-SP2 | privoxy | 2021-02-12 |
| openSUSE | openSUSE-SU-2021:0270-1 | 15.2 | python | 2021-02-10 |
| openSUSE | openSUSE-SU-2021:0302-1 | 15.2 | python-bottle | 2021-02-16 |
| openSUSE | openSUSE-SU-2021:0272-1 | oSB SLE-15-SP2 | rclone | 2021-02-11 |
| openSUSE | openSUSE-SU-2021:0272-1 | oSB SLE-15-SP2 | rclone | 2021-02-11 |
| openSUSE | openSUSE-SU-2021:0280-1 | 15.2 | subversion | 2021-02-12 |
| openSUSE | openSUSE-SU-2021:0284-1 | 15.2 | wpa_supplicant | 2021-02-13 |
| Oracle | ELSA-2021-0474 | OL8 | dotnet | 2021-02-16 |
| Oracle | ELSA-2021-9051 | OL6 | kernel | 2021-02-16 |
| Oracle | ELSA-2021-9053 | OL7 | kernel | 2021-02-16 |
| Oracle | ELSA-2021-9051 | OL7 | kernel | 2021-02-16 |
| Oracle | ELSA-2021-9053 | OL8 | kernel | 2021-02-16 |
| Oracle | ELSA-2021-9053 | OL8 | kernel | 2021-02-16 |
| Oracle | ELSA-2021-9057 | OL7 | kernel-container | 2021-02-16 |
| Oracle | ELSA-2021-9057 | OL8 | kernel-container | 2021-02-16 |
| Red Hat | RHSA-2021:0603-01 | EL7 | RHDM | 2021-02-17 |
| Red Hat | RHSA-2021:0600-01 | EL7 | RHPAM | 2021-02-17 |
| Red Hat | RHSA-2021:0531-01 | EL8 | container-tools:rhel8 | 2021-02-16 |
| Red Hat | RHSA-2021:0474-01 | EL8 | dotnet | 2021-02-10 |
| Red Hat | RHSA-2021:0471-01 | EL8 | dotnet3.1 | 2021-02-10 |
| Red Hat | RHSA-2021:0476-01 | EL8 | dotnet5.0 | 2021-02-10 |
| Red Hat | RHSA-2021:0530-01 | EL8 | java-1.8.0-ibm | 2021-02-16 |
| Red Hat | RHSA-2021:0526-01 | EL7.7 | kernel | 2021-02-16 |
| Red Hat | RHSA-2021:0558-01 | EL8 | kernel | 2021-02-16 |
| Red Hat | RHSA-2021:0537-01 | EL8 | kernel-rt | 2021-02-16 |
| Red Hat | RHSA-2021:0525-01 | EL7.7 | net-snmp | 2021-02-16 |
| Red Hat | RHSA-2021:0548-01 | EL8 | nodejs:10 | 2021-02-16 |
| Red Hat | RHSA-2021:0549-01 | EL8 | nodejs:12 | 2021-02-16 |
| Red Hat | RHSA-2021:0551-01 | EL8 | nodejs:14 | 2021-02-16 |
| Red Hat | RHSA-2021:0538-01 | EL8 | nss | 2021-02-16 |
| Red Hat | RHSA-2021:0557-01 | EL8 | perl | 2021-02-16 |
| Red Hat | RHSA-2021:0528-01 | EL7.7 | python | 2021-02-16 |
| Red Hat | RHSA-2021:0599-01 | EL8 | redhat-ds:11 | 2021-02-16 |
| Red Hat | RHSA-2021:0521-01 | SCL | rh-nodejs10-nodejs | 2021-02-15 |
| Red Hat | RHSA-2021:0485-01 | RHSC | rh-nodejs12-nodejs | 2021-02-11 |
| Red Hat | RHSA-2021:0507-01 | EL8 | subversion:1.10 | 2021-02-15 |
| Red Hat | RHSA-2021:0509-01 | EL8.1 | subversion:1.10 | 2021-02-15 |
| Red Hat | RHSA-2021:0508-01 | EL8.2 | subversion:1.10 | 2021-02-15 |
| SUSE | SUSE-SU-2021:0435-1 | MP4.0 SLE15 SES6 | containerd, docker, docker-runc, golang-github-docker-libnetwork | 2021-02-11 |
| SUSE | SUSE-SU-2021:0445-1 | SLE12 | containerd, docker, docker-runc, golang-github-docker-libnetwork | 2021-02-12 |
| SUSE | SUSE-SU-2021:0431-1 | SLE12 | firefox | 2021-02-11 |
| SUSE | SUSE-SU-2021:0430-1 | SLE15 | firefox | 2021-02-11 |
| SUSE | SUSE-SU-2021:0488-1 | MP4.0 SLE15 SES6 | jasper | 2021-02-16 |
| SUSE | SUSE-SU-2021:0489-1 | OS7 OS8 OS9 SLE12 | jasper | 2021-02-16 |
| SUSE | SUSE-SU-2021:14627-1 | SLE11 | jasper | 2021-02-16 |
| SUSE | SUSE-SU-2021:0437-1 | OS7 SLE12 | kernel | 2021-02-11 |
| SUSE | SUSE-SU-2021:0452-1 | OS8 SLE12 SES5 | kernel | 2021-02-12 |
| SUSE | SUSE-SU-2021:0434-1 | OS9 SLE12 | kernel | 2021-02-11 |
| SUSE | SUSE-SU-2021:14630-1 | SLE11 | kernel | 2021-02-16 |
| SUSE | SUSE-SU-2021:0433-1 | SLE12 | kernel | 2021-02-11 |
| SUSE | SUSE-SU-2021:0427-1 | SLE15 | kernel | 2021-02-10 |
| SUSE | SUSE-SU-2021:0438-1 | SLE15 | kernel | 2021-02-11 |
| SUSE | SUSE-SU-2021:0439-1 | MP4.0 SLE15 SES6 | openvswitch | 2021-02-11 |
| SUSE | SUSE-SU-2021:0451-1 | OS7 SLE12 | openvswitch | 2021-02-12 |
| SUSE | SUSE-SU-2021:0446-1 | OS8 SLE12 SES5 | openvswitch | 2021-02-12 |
| SUSE | SUSE-SU-2021:0479-1 | OS9 SLE12 | openvswitch | 2021-02-15 |
| SUSE | SUSE-SU-2021:0440-1 | SLE15 | openvswitch | 2021-02-11 |
| SUSE | SUSE-SU-2021:0436-1 | SLE15 | openvswitch | 2021-02-11 |
| SUSE | SUSE-SU-2021:0449-1 | SLE12 | perl-File-Path | 2021-02-12 |
| SUSE | SUSE-SU-2021:0432-1 | OS7 OS8 OS9 SLE12 SES5 | python | 2021-02-11 |
| SUSE | SUSE-SU-2021:0483-1 | SLE15 | python-bottle | 2021-02-16 |
| SUSE | SUSE-SU-2021:0486-1 | OS7 | python-urllib3 | 2021-02-16 |
| SUSE | SUSE-SU-2021:0428-1 | SLE12 | python36 | 2021-02-10 |
| SUSE | SUSE-SU-2021:0492-1 | MP4.0 SLE15 SES6 | screen | 2021-02-17 |
| SUSE | SUSE-SU-2021:0491-1 | OS7 OS8 OS9 SLE12 | screen | 2021-02-17 |
| SUSE | SUSE-SU-2021:0425-1 | MP4.0 SLE15 SES6 | subversion | 2021-02-10 |
| SUSE | SUSE-SU-2021:0424-1 | SLE12 | subversion | 2021-02-10 |
| SUSE | SUSE-SU-2021:0443-1 | MP4.0 SLE15 SES6 | wpa_supplicant | 2021-02-11 |
| SUSE | SUSE-SU-2021:0478-1 | OS7 OS8 OS9 SLE12 | wpa_supplicant | 2021-02-15 |
| SUSE | SUSE-SU-2021:0477-1 | SLE12 | wpa_supplicant | 2021-02-15 |
| Ubuntu | USN-4733-1 | 18.04 20.04 20.10 | gnome-autoar | 2021-02-11 |
| Ubuntu | USN-4731-1 | 16.04 18.04 20.04 20.10 | junit4 | 2021-02-10 |
| Ubuntu | USN-4729-1 | 16.04 18.04 20.04 20.10 | openvswitch | 2021-02-10 |
| Ubuntu | USN-4735-1 | 20.04 20.10 | postgresql-12 | 2021-02-15 |
| Ubuntu | USN-4730-1 | 18.04 | postsrsd | 2021-02-10 |
| Ubuntu | USN-4732-1 | 20.10 | sqlite3 | 2021-02-11 |
| Ubuntu | USN-4736-1 | 20.10 | thunderbird | 2021-02-16 |
| Ubuntu | USN-4734-2 | 14.04 | wpa | 2021-02-16 |
| Ubuntu | USN-4734-1 | 16.04 18.04 20.04 20.10 | wpa | 2021-02-11 |
Kernel patches of interest
Kernel releases
Architecture-specific
Core kernel
Development tools
Device drivers
Device-driver infrastructure
Documentation
Filesystems and block layer
Memory management
Networking
Security-related
Miscellaneous
Page editor: Rebecca Sobol
