dxd - dynax driver framework 2.1.0d48
cross platform open source driver development framework
Loading...
Searching...
No Matches
Kick off

Basics

  • Create an appropriate .inf file (for Windows) and a .plist (for OSX) matching the device or kernel node you want to create.
    Following skeleton creates everything needed for a fully working kernel driver node (including PNP and power event handling):
    #include "version.h"
    #include <dxd_device.h>
    #ifdef WIN32
    WDF_EXTERN_C::NTSTATUS DriverEntry(
    ::DRIVER_OBJECT* driver,
    ::UNICODE_STRING* registry){$
    return dxd::create<dxd::driver<>>(driver, registry, DX_GUID);
    }
    #endif //WIN32
    Add a version.h describing your product:
    #define DX_PRODUCT MyProduct
    #define DX_PRODUCT_ID com_mycompany_myproduct
    #define DX_PRODUCT_URID com.mycompany.myproduct
  • Change the plist to match your device name defined in version.h. In the above case this would be the generic device defined by dxd (there is some macro magic going on in dx_macros.h defining the concatenated strings):
    [...]
    <key>IOKitPersonalities</key>
    <dict>
    <key>DX_PRODUCT</key>
    <dict>
    <key>IOClass</key>
    <string>com_mycompany_myproduct_device</string>
    <key>CFBundleIdentifier</key>
    <string>DX_PRODUCT_URID</string>
    <key>IOProviderClass</key>
    <string>IODevice</string>
    <key>IOUserClientClass</key>
    <string>DX_CLIENT</string>
    </dict>
    </dict>
    [...]

Selecting a specific device type

  • Decide which device or bus types sweet your needs best.
    To simply add generic PCI device handling functionality change the above code fragment to:
    [...]
    WDF_EXTERN_C::NTSTATUS DriverEntry(
    ::DRIVER_OBJECT* driver,
    ::UNICODE_STRING* registry){$
    return dxd::create<dxd::driver<dxd::pci>>(driver, registry, DX_GUID);
    }
    [...]
    ... and change the plist to
    [...]
    <key>IOKitPersonalities</key>
    <dict>
    <key>DX_PRODUCT</key>
    <dict>
    [...]
    <key>IOClass</key>
    <string>com_mycompany_myproduct_pci</string>
    [...]
    </dict>
    </dict>
    [...]

Creating your own device

Adding a user client

  • An applications connects to the driver through the means of an user client. To be able to handle application requests you need to add a user_client:
    #ifdef __MACH__
    #define user_client DX_CLIENT
    #endif//__MACH__
    class user_client: public dxd::client{
    typedef dxd::client super;
    #ifdef __MACH__
    virtual bool start(::IOService* provider){
    device= OSDynamicCast(user_device, provider);
    if(!super::start(provider))
    return false;
    return true;
    }
    #endif//__MACH__
    user_device* device;
    dxd::os_result launch() override{
    // optionally overwrite to handle user client creation
    return super::launch();
    }
    void dxd::os_result conclude() override{
    // optionally overwrite to handle user client disconnection
    super::conclude();
    }
    unsigned int ioctl,
    const void* in,
    size_t size_in,
    void* out,
    size_t size_out,
    size_t& size
    )override{
    // optionally overwrite to handle user client request from application
    switch(ioctl){
    case my_namespace::version:{
    try(status= (!size_in && size_out==sizeof(unsigned int))? dxd::ok: dxd::invalid);
    // write data & return size of written data
    *reinterpret_cast<unsigned int*>(out)= DX_VERSION32;
    size= sizeof(uint32_t);
    trace(" my_namespace::version:" DX_STRINGIFY(DX_VERSION) "\n");
    break;
    }
    }
    }
    public:
    #ifdef WIN32
    user_client(user_device*device): device(device){}
    #endif//WIN32
    };
    #ifdef __MACH__
    OSDefineMetaClassAndStructors(user_client,user_client::super);
    #endif//__MACH__
    #ifdef WIN32
    dxd::client*user_device::client_create(){return new user_client(this);};
    #endif//WIN32
    Definition iokit/dxd_device.h:360
    #define DX_VERSION32
    Definition dx_macros.h:72
    #define device
    IOKit: generic device.
    Definition iokit/dxd_device.h:84
    ioctl
    DX IOCTLs convetion char namespace indentifier: lower case user mode: upper case kernel.
    Definition macOS/dx_platform.h:113
    void trace(std::ostream &os, const exception &exception, unsigned int indent=0)
    Definition dx_exception.h:246
    dynax driver framework kernel namespace
    Definition dxd_endian.h:29
    @ ok
    Definition iokit/dxd_base.h:104
    @ invalid
    Definition iokit/dxd_base.h:106
    @ out
    Definition iokit/dxd_memory.h:41
    unsigned int uint32_t
    Definition wdk/dxd_base.h:110
    The plist containing the user client magic:
    [...]
    <key>IOKitPersonalities</key>
    <dict>
    <key>DX_PRODUCT</key>
    <dict>
    [...]
    <key>IOUserClientClass</key>
    <string>DX_CLIENT</string>
    [...]
    </dict>
    </dict>
    [...]

(c) copyright 2009 dynamic acoustics e.U. generated on Fri Feb 23 2024

a closed source license may be obtained by requesting a written permission from dynamic acoustics e.U.
however - governmental use generally and military use especially is strictly prohibited though.