Re: How to tell when all kexts are loaded
Re: How to tell when all kexts are loaded
- Subject: Re: How to tell when all kexts are loaded
- From: Terry Lambert <email@hidden>
- Date: Wed, 30 Nov 2005 14:21:20 -0800
On Nov 30, 2005, at 2:21 AM, Stephane Sudre wrote:
Le 30 Nov 2005, à 01:41, Terry Lambert a écrit :
On Nov 29, 2005, at 4:14 PM, Stephane Sudre wrote:
On mercredi, novembre 30, 2005, at 12:31 AM, Terry Lambert wrote:
(1) Your kext would need to be loaded and interfaced with the
networking stack before the network was in fact enabled, so that
no packets were permitted to pass through the networking interace
to a potentially vulenrable program on the host system, until the
defensive software was in place.
For this requirement, the kext must load at system startup.
To achieve this, you would have to use IOKit matching - the KEXT
would need to implement an IOKit device driver, and that driver
would have to always claim that it had discovered matching
hardware.
For this requirement, you would also need to ensure that the kext
was loaded before network startup.
To achieve this, you would need to claim that the device driver
was a "Root" device - that is, it was required in order to mount
the Root volume so that the OS was capable of booting; note that
making this requirement endangers the system: a bug in this
device driver could result in an unrecoverable boot failure
requiring either a reinstall, or a boot from install media and an
escape to a shell or a boot from an alternate partition.
Your point on "Root" device is not exactly right AFAIK. "Root"
device startup can be prevented. With some code, the I/O Kernel
extension can know that the boot was made in Safe mode and so
perform differently or return failure on loading.
This is incorrect. In an earlier response, I made the statement
that setting "OSBundleRequired" to "Root" was sufficient; I was
mistaken, and corrected by Dean; it's *necessary*, but not
*sufficient*. To be sufficient, it needs to also be an IOKit
driver that claims it has found matching hardware, i.e.:
(a) Be an IOKit driver
(b) Follow the IOKit matching rules
(c) Claim to have matched hardware
(d) Have an "OSBundleRequired" of "Root" in its "Info.plist" file
(e) *NOT* have a non-zero value for "IOKitDebug" in its
"Info.plist" file
See:
<http://developer.apple.com/documentation/Darwin/Conceptual/KEXTConcept/KEXTConceptLoading/loading_kexts.html#//apple_ref/doc/uid/20002369-97330-BABDIDAF
>
You mean that PE_parse_boot_arg("-x", &dummy) is not working?
Actually, all it does is add a "-x" to init (launchd) arguments, and
set the IOKit global safeBoot.
If you'd clicked on the link, you would have read:
During a safe boot, BootX loads the KEXTs required to mount the
root file
system just as in other modes of booting. Then kextd starts and
examines
all the drivers on the system. If this is a safe boot, however,
kextd will
only consider loading a KEXT if the OSBundleRequired property is
present
in its Info.plist file. This preserves the integrity of the safe
boot by
ensuring that only drivers necessary for mounting root or
operating the
system’s user interface are loaded.
Safe booting helps protect the system from the possible panic of
a driver.
If a driver’s OSBundleRequired property is set to “Root”, it will
always be
loaded by BootX, even in single-user or safe-boot modes. If this
driver
panics, the system itself may panic, requiring reinstallation of
the
operating system or booting off a CD.
In other words, the driver is loaded by BootX, not by kextd, and it's
always loaded if the property is "Root", even in single user or safe
boot situations.
The IOKit matching is required to ensure that the driver is
*activated* because it is a required driver that has found hardware.
Consider the case of a safe boot of a generic MacOS X that can run on
several platforms - for example, a G4 machine with an ATA disk
controller and a G5 machine with a SATA disk controller. Both the ATA
and SATA controller drivers are marked as "Root", meaning that they
are required for the machine to boot, even in safe or single user
situations, BUT the driver is only active after that if it has found
matching hardware.
Consider also the case of a machine where the OpenFirmware devices in
the device tree know how to read the boot disk, but the kernel itself
doesn't - until the drivers have been loaded from the boot disk. In
that case, the OpenFirmware drivers are used to load the KEXT drivers
into memory from the disk prior to activating the kernel, and
OpenFirmware being deactivated.
This is all in the technical notes on developer.apple.com.
Concerning the point of being loaded before the network stack is
enabled, there's a problem in Tiger where the callback which could
be used to be loaded before the stack is enabled (so that for
instance you can attach socket filters the sooner possible) is
never called before the stack is enabled. At least, that's been my
experience. This is a known problem AFAIK.
I really can't parse:
"the callback which could be used to be loaded before the stack
is enabled"
If "used to be" means "formerly was", it doesn't match the verb
tense of "is" (should be "was"?), and if "be used" means "carry out
a purpose or action", then "to be" probably should have been "is").
Simpler syntax:
the callback you need to support to be informed that the network
stack has just been loaded & initialized.
C syntax:
net_init_add always returns EALREADY
In other words, you are saying that the callback AST that calls
bsd_init() (which is what calls net_init_run() and sets the valued of
list_head to LIST_RAN in bsd/net/init.c) has already been called.
Your interpretation of the sequence of events is incorrect, in the
case that I'm specifically describing:
(1) You have an IOKit driver
(2) It's OSBundleRequired property is Root
(3) It claims to match hardware
The reason for this is that it will get initialized when
kernel_bootstrap_thread() is run; in kernel_bootstrap_thread(), the
sequence of events is:
...
PE_init_iokit();
...
bsd_init();
That is, if your driver is started by PE_init_iokit() because it's a
Root driver that matches hardware (and it doesn't have a non-zero
IOKitDebug), then you get initialized *before* net_init_run() gets
called.
If it's the former, I'm not sure I understand why it's a problem to
not call a callback ona disabled stack, since disabled stacks don't
have any activity on them; if it's the latter, I'm not sure why
loading the network extension before enabling the stack is a
problem, either, since it seems to be the desired behavior.
Do you have a radar # for a problem report that better explains why
the Tiger behavior is a problem for you?
The problem is that this method is supposed to allow someone to add
a callback but this callback is currently useless IMHO since the
network stack is always initialized when you call net_init_add.
See above. Your KEXT simply doesn't match the criteria necessary to
get it initialized by the call into PE_init_iokit() - change that
attribute of your KEXT, and your objection goes away.
I actually think this is a strawman argument in any case, since the
network interfaces are not changed from state "down" to state "up"
until after configd runs, in any case (configd is run after launchd),
so as long as you are loaded at startup before configd runs, it should
matter whether net_init_run() has already happened yet or not.
-- Terry _______________________________________________
Do not post admin requests to the list. They will be ignored.
Darwin-kernel mailing list (email@hidden)
Help/Unsubscribe/Update your Subscription:
This email sent to email@hidden