style(9) rules for nested includes

John Baldwin jhb at
Thu Mar 10 20:28:20 UTC 2011

On Thursday, March 10, 2011 3:10:58 pm mdf at wrote:
> On Thu, Mar 10, 2011 at 11:46 AM, John Baldwin <jhb at> wrote:
> > On Thursday, March 10, 2011 12:17:28 pm mdf at wrote:
> >> I recall a recent discussion/PR about nested includes in the context
> >> of <sys/linker_set.h> and <sys/queue.h> being a few of the only ones
> >> allowed.  However, I don't see anything in style(9) about this.
> >
> > bde@ is probably the most authoritative.  My understanding is that the only
> > nested includes allowed in sys/sys/*.h are the two listed above and any header
> > that starts with an underscore (sys/_mutex.h, etc.).  The underscore variants
> > were added to allow nested includes when absolutely necessary, but those
> > includes are the bare minimum required to define structures, etc.
> >
> >> Now we come to the reason I ask.  I'm working on a patch to change the
> >> static sysctl code to use the standard SYSININT/SYSUNINIT code rather
> >> than have special treatment in kern_linker.c, but to do this I need to
> >> either change quite a few places that include <sys/sysctl.h>, or
> >> include <sys/kernel.h> instead of <sys/linker_set.h> in sysctl.h, as
> >> the SI_SUB_SYSCTLS value isn't visible otherwise.
> >
> > Hmm, what is the reason to use SYSINIT's instead of a dedicated linker set?
> Mostly for consistency.  The DB_COMMAND linker set was changed to use
> SYSINITs for version 8, and AFIAK SYSCTL is the only global kernel
> thing using a separate linker set.

That was because DB commands in modules just didn't work at all before. :)

> There's also a minor bug in initialization ordering where a static
> SYSCTL_PROC could use a lock initialized by SX_SYSINIT or MTX_SYSINIT,
> but at runtime module load the sysctl is exposed before the
> SI_SUB_LOCK stage has run, so in theory someone doing sysctl -a would
> crash the kernel on an attempt to lock an uninitialized mtx/sx.  We
> saw this happen once at Isilon.

Hmm, this is a legitimate reason, though I'd be tempted to fix that by just
registering sysctls after sysinit's have been invoked and vice versa on
unload.  It seems that would be a simpler fix with far less code churn and
not having to deal with the nested include mess, etc.

One thing I often do, btw when dealing these sorts of interdependencies in a
loadable module, is to use a single SYSINIT or module event handler to do all
the setup and teardown of a single kld.  This lets you handle errors far
better (SYSINIT's don't allow for that at all) and more explicitly order the
set of operations.

John Baldwin

More information about the freebsd-arch mailing list