Kernel Extension

This document describes how to implement a device driver as a kernel extension.

Device drivers can also be kernel extensions, which means that they are loaded by the Kernel when it boots. They are used for extending the Kernel, as the name suggests. Generally, kernel extensions provide early initialisation of devices that must be permanently available, such as LCD, DMA, and I2C and other peripheral bus controllers. Because kernel extensions are loaded by the Kernel, they are never unloaded and so their destructors are never called.

The DECLARE_STANDARD_EXTENSION macro is used to provide an entry point for a kernel extension (see Entry Points).

Extensions are built into the ROM image, by specifying the extension keyword in the .iby file. This enables the ROM build tool to build the ROM header. The extensions are loaded in the order specified in the kernel.iby file.

extension[VARID]=\Epoc32\Release\<assp>\urel\KDEBUG.DLL \System\Bin\kdebug.dll

A kernel extension's interface to other Kernel side components is usually exported using a static interface. Clients can access this interface by using the global instance of the object created and initialised in the DECLARE_STANDARD_EXTENSION entry point. They then use this object to call the exported API.

Kernel extensions can also be implemented that let user code open channels on them to use the interface. This model is used for devices where initialisation has to be done at system boot up, but which can then be used by the clients, for example, the media driver elocd.ldd.

To do this, drivers have to declare DECLARE_EXTENSION_LDD in addition to the DECLARE_STANDARD_EXTENSION macro. In this model, extensions generally call Kernel::InstallLogicalDevice() /Kernel::InstallPhysicalDevice() to install the logical device. Later clients can open channels on this driver and use the interface in the same way as a standard driver.

DECLARE_STANDARD_EXTENSION()
    {
    ...
    // Create factory object
    DExDriverLogicalDevice* device = new DExDriverLogicalDevice;
    if (device==NULL)
        r=KErrNoMemory;
    else
        {
        // Installs the logical device by calling the second
        // phase constructor
        r=Kern::InstallLogicalDevice(device);
        }
    return r;
    }

DECLARE_EXTENSION_LDD()
    {
    return new DExDriverLogicalDevice;
    }