Skip site navigation (1)Skip section navigation (2)
Date:      Tue, 19 Apr 2005 22:56:40 +0000 (GMT)
From:      wpaul@FreeBSD.ORG (Bill Paul)
To:        current@freebsd.org
Subject:   New driver loading scheme for Project Evil, need input
Message-ID:  <20050419225640.7B92816A4CF@hub.freebsd.org>

next in thread | raw e-mail | index | archive | help

For a while now I've been thinking about streamlining the process of
installing NDIS drivers, mainly so that people no longer have to compile
if_ndis.ko every time. After no small amount of head scratching, I've
finally come up with a way to do it. There are a few aesthetic details
left to work out though, for which I thought I'd solicit some opinions.

As it stands now, you have to go through the following steps to
load a new NDIS driver:

- Find the .SYS and .INF files for your card
- Use ndiscvt(8) to convert them into an ndis_driver_data.h file
- Copy this file to /sys/modules/if_ndis
- Compile if_ndis.ko

The main problems with this are:

- if_ndis.ko can't be pre-compiled and shipped with the system
- the kernel source must be installed
- using ndiscvt(8) is a little confusing

The new system I've cooked up works like this:

- ndis.ko and if_ndis.ko are both pre-built for you.
- A new installation screipt, tentatively named wintobsd.sh, and
  a small C file, windrv_stub.c are installed with the base OS.
- The wintobsd.sh script is interactive and prompts you to enter
  the path for both your .INF and .SYS files.
- If necessary, the script will run iconv(1) on .INF files that
  are actually in unicode format (people often forget to do this
  and then wonder why ndiscvt(8) doesn't work)
- The script will run ndiscvt(8), but use the -O option to convert
  the .SYS file directly into a .o file (via the magic of objcopy(1))
  and produce a stripped down .h file with just the device ID and
  registry info in it (rather than the usual giant .h file with
  an encoded byte array containing the .SYS image).
- Lastly, the script will compile the windrv_stub.c file and link
  it against the converted .o file, producing a .ko file that
  can be kldloaded into the system.
- Optionally, the script can also produce a non-shared .o file that
  can be statically linked into the kernel, for those who need/want
  static kernel images.

The objcopy(1) trick basically produces an ELF file that has the
Windows .SYS file encapsulated with in it. Two symbols are created
to denote the start end end of the image so that it can be loaded later.
The windrv_stub.o module linked with the Windows image provides a
small FreeBSD modevent handler that hooks the driver into Project
Evil and eventually causes a bus-reprobe. This means that all you
have to do is kldload this one module into the kernel, and presto!
a new ndisX networking interface appears.

The end result is that installing a Windows driver should be as simple
as:

- run the script
- give it your foo.inf and foo.sys files when it asks you
- it spits out a foo_sys.ko module and you kldload it
- the end

You still end up needing the C compiler, objcopy, ndiscvt and (optionally)
iconv, but the script automates the use of all these tooks and explains
to the user what's going on while it's working.

Anyway. The things I have yet to determine are:

- Where should windrv_stub.c ultimately be installed? I'm thinking it
  should go in /usr/share/misc.

- What should the script be called? wintobsd.sh sounds kind of lame.

Any suggestions or comments on my mad scheme would be welcome.

-Bill

--
=============================================================================
-Bill Paul            (510) 749-2329 | Senior Engineer, Master of Unix-Fu
                 wpaul@windriver.com | Wind River Systems
=============================================================================
              <adamw> you're just BEGGING to face the moose
=============================================================================



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?20050419225640.7B92816A4CF>