On 8/29/25 12:54 PM, Siddharth Nayyar wrote: > Hi everyone, > > This patch series proposes a new, scalable mechanism to represent > boolean flags for exported kernel symbols. > > Problem Statement: > > The core architectural issue with kernel symbol flags is our reliance on > splitting the main symbol table, ksymtab. To handle a single boolean > property, such as GPL-only, all exported symbols are split across two > separate tables: __ksymtab and __ksymtab_gpl. > > This design forces the module loader to perform a separate search on > each of these tables for every symbol it needs, for vmlinux and for all > previously loaded modules. > > This approach is fundamentally not scalable. If we were to introduce a > second flag, we would need four distinct symbol tables. For n boolean > flags, this model requires an exponential growth to 2^n tables, > dramatically increasing complexity. > > Another consequence of this fragmentation is degraded performance. For > example, a binary search on the symbol table of vmlinux, that would take > only 14 comparison steps (assuming ~2^14 or 16K symbols) in a unified > table, can require up to 26 steps when spread across two tables > (assuming both tables have ~2^13 symbols). This performance penalty > worsens as more flags are added. > > Proposed Solution: > > This series introduces a __kflagstab section to store symbol flags in a > dedicated data structure, similar to how CRCs are handled in the > __kcrctab. > > The flags for a given symbol in __kflagstab will be located at the same > index as the symbol's entry in __ksymtab and its CRC in __kcrctab. This > design decouples the flags from the symbol table itself, allowing us to > maintain a single, sorted __ksymtab. As a result, the symbol search > remains an efficient, single lookup, regardless of the number of flags > we add in the future.
Merging __ksymtab and __ksymtab_gpl into a single section looks ok to me, and similarly for __kcrctab and __kcrtab_gpl. The __ksymtab_gpl support originally comes from commit 3344ea3ad4 ("[PATCH] MODULE_LICENSE and EXPORT_SYMBOL_GPL support") [1], where it was named __gpl_ksymtab. The commit doesn't mention why the implementation opts for using a separate section, but I suspect it was designed this way to reduce memory/disk usage. A question is whether the symbol flags should be stored in a new __kflagstab section, instead of adding a flag member to the existing __ksymtab. As far as I'm aware, no userspace tool (particularly kmod) uses the __ksymtab data, so we are free to update its format. Note that I believe that __kcrctab/__kcrtab_gpl is a separate section because the CRC data is available only if CONFIG_MODVERSIONS=y. Including the flags as part of __ksymtab would be obviously a simpler schema. On the other hand, an entry in __ksymtab has in the worst case a size of 24 bytes with an 8-byte alignment requirement. This means that adding a flag to it would require additional 8 bytes per symbol. > > The motivation for this change comes from the Android kernel, which uses > an additional symbol flag to restrict the use of certain exported > symbols by unsigned modules, thereby enhancing kernel security. This > __kflagstab can be implemented as a bitmap to efficiently manage which > symbols are available for general use versus those restricted to signed > modules only. I think it would be useful to explain in more detail how this protected schema is used in practice and what problem it solves. Who is allowed to provide these limited unsigned modules and if the concern is kernel security, can't you enforce the use of only signed modules? [1] https://git.kernel.org/pub/scm/linux/kernel/git/tglx/history.git/commit/?id=3344ea3ad4b7c302c846a680dbaeedf96ed45c02 -- Thanks, Petr