summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--Makefile28
-rw-r--r--hardsid.c207
2 files changed, 235 insertions, 0 deletions
diff --git a/Makefile b/Makefile
new file mode 100644
index 0000000..6544d91
--- /dev/null
+++ b/Makefile
@@ -0,0 +1,28 @@
+# Copyright 2018 Ian Cowburn
+#
+# Redistribution and use in source and binary forms, with or without
+# modification, are permitted provided that the following conditions are met:
+#
+# 1. Redistributions of source code must retain the above copyright notice,
+# this list of conditions and the following disclaimer.
+#
+# 2. Redistributions in binary form must reproduce the above copyright notice,
+# this list of conditions and the following disclaimer in the documentation
+# and/or other materials provided with the distribution.
+#
+# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+# AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+# ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
+# LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+# SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+# POSSIBILITY OF SUCH DAMAGE.
+#
+SRCS=hardsid.c device_if.h bus_if.h pci_if.h
+KMOD=hardsid
+
+.include <bsd.kmod.mk>
diff --git a/hardsid.c b/hardsid.c
new file mode 100644
index 0000000..2b514c9
--- /dev/null
+++ b/hardsid.c
@@ -0,0 +1,207 @@
+/* Copyright 2018 Ian Cowburn
+
+ Redistribution and use in source and binary forms, with or without
+ modification, are permitted provided that the following conditions are met:
+
+ 1. Redistributions of source code must retain the above copyright notice,
+ this list of conditions and the following disclaimer.
+
+ 2. Redistributions in binary form must reproduce the above copyright notice,
+ this list of conditions and the following disclaimer in the documentation
+ and/or other materials provided with the distribution.
+
+ THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
+ LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ POSSIBILITY OF SUCH DAMAGE.
+*/
+#include <sys/param.h>
+#include <sys/module.h>
+#include <sys/systm.h>
+#include <sys/errno.h>
+#include <sys/kernel.h>
+#include <sys/conf.h>
+#include <sys/uio.h>
+#include <sys/malloc.h>
+#include <sys/bus.h>
+
+#include <machine/bus.h>
+#include <sys/rman.h>
+#include <machine/resource.h>
+
+#include <dev/pci/pcivar.h>
+#include <dev/pci/pcireg.h>
+
+/* The softc holds our per-instance data. */
+struct hardsid_softc
+{
+ device_t my_dev;
+ struct cdev *my_cdev;
+};
+
+/* Function prototypes
+*/
+static d_open_t hardsid_open;
+static d_close_t hardsid_close;
+static d_read_t hardsid_read;
+static d_write_t hardsid_write;
+
+/* Character device entry points
+*/
+static struct cdevsw hardsid_cdevsw =
+{
+ .d_version = D_VERSION,
+ .d_open = hardsid_open,
+ .d_close = hardsid_close,
+ .d_read = hardsid_read,
+ .d_write = hardsid_write,
+ .d_name = "hardsid",
+};
+
+/*
+ * In the cdevsw routines, we find our softc by using the si_drv1 member
+ * of struct cdev. We set this variable to point to our softc in our
+ * attach routine when we create the /dev entry.
+ */
+
+int hardsid_open(struct cdev *dev, int oflags, int devtype, struct thread *td)
+{
+ struct hardsid_softc *sc;
+
+ /* Look up our softc. */
+ sc = dev->si_drv1;
+ device_printf(sc->my_dev, "Opened successfully.\n");
+ return 0;
+}
+
+int hardsid_close(struct cdev *dev, int fflag, int devtype, struct thread *td)
+{
+ struct hardsid_softc *sc;
+
+ /* Look up our softc. */
+ sc = dev->si_drv1;
+ device_printf(sc->my_dev, "Closed.\n");
+ return 0;
+}
+
+int hardsid_read(struct cdev *dev, struct uio *uio, int ioflag)
+{
+ struct hardsid_softc *sc;
+
+ /* Look up our softc. */
+ sc = dev->si_drv1;
+ device_printf(sc->my_dev, "Asked to read %zd bytes.\n", uio->uio_resid);
+ return 0;
+}
+
+int hardsid_write(struct cdev *dev, struct uio *uio, int ioflag)
+{
+ struct hardsid_softc *sc;
+
+ /* Look up our softc. */
+ sc = dev->si_drv1;
+ device_printf(sc->my_dev, "Asked to write %zd bytes.\n", uio->uio_resid);
+ return 0;
+}
+
+/* PCI Support Functions */
+
+/*
+ * Compare the device ID of this device against the IDs that this driver
+ * supports. If there is a match, set the description and return success.
+ */
+static int hardsid_probe(device_t dev)
+{
+ if ((pci_get_vendor(dev) == 0x6581) && (pci_get_device(dev) == 0x8580))
+ {
+ device_set_desc(dev, "hardsid");
+ return BUS_PROBE_DEFAULT;
+ }
+
+ return ENXIO;
+}
+
+/* Attach function is only called if the probe is successful. */
+
+static int hardsid_attach(device_t dev)
+{
+ struct hardsid_softc *sc;
+
+ /* Look up our softc and initialize its fields. */
+ sc = device_get_softc(dev);
+ sc->my_dev = dev;
+
+ /*
+ * Create a /dev entry for this device. The kernel will assign us
+ * a major number automatically. We use the unit number of this
+ * device as the minor number and name the character device
+ * "hardsid<unit>".
+ */
+ sc->my_cdev = make_dev(&hardsid_cdevsw, device_get_unit(dev),
+ UID_ROOT, GID_WHEEL, 0666, "hardsid%u", device_get_unit(dev));
+ sc->my_cdev->si_drv1 = sc;
+
+ return 0;
+}
+
+/* Detach device. */
+
+static int hardsid_detach(device_t dev)
+{
+ struct hardsid_softc *sc;
+
+ /* Teardown the state in our softc created in our attach routine. */
+ sc = device_get_softc(dev);
+ destroy_dev(sc->my_cdev);
+
+ return 0;
+}
+
+/* Called during system shutdown after sync. */
+
+static int hardsid_shutdown(device_t dev)
+{
+ return 0;
+}
+
+/*
+ * Device suspend routine.
+ */
+static int hardsid_suspend(device_t dev)
+{
+ return 0;
+}
+
+/*
+ * Device resume routine.
+ */
+static int hardsid_resume(device_t dev)
+{
+ return 0;
+}
+
+static device_method_t hardsid_methods[] =
+{
+ /* Device interface */
+ DEVMETHOD(device_probe, hardsid_probe),
+ DEVMETHOD(device_attach, hardsid_attach),
+ DEVMETHOD(device_detach, hardsid_detach),
+ DEVMETHOD(device_shutdown, hardsid_shutdown),
+ DEVMETHOD(device_suspend, hardsid_suspend),
+ DEVMETHOD(device_resume, hardsid_resume),
+
+ DEVMETHOD_END
+};
+
+static devclass_t hardsid_devclass;
+
+DEFINE_CLASS_0(hardsid, hardsid_driver, hardsid_methods,
+ sizeof(struct hardsid_softc));
+DRIVER_MODULE(hardsid, pci, hardsid_driver, hardsid_devclass, 0, 0);