PERFORCE change 209637 for review

Robert Watson rwatson at FreeBSD.org
Sun Apr 15 18:41:37 UTC 2012


http://p4web.freebsd.org/@@209637?ac=10

Change 209637 by rwatson at rwatson_svr_ctsrd_mipsbuild on 2012/04/15 18:40:34

	Implement d_read and d_write methods, not just d_mmap method, for
	the Terasic Multi-touch LCD display driver.  I/O must be 32-bit
	aligned and a multiple of 32 bits in size in order to meet the
	requirements of the underlying bus (in most cases), so this is
	enforced by the driver.  This should allow tools such as dd to be
	used to set screen contents easily, even though the preferred
	usage pattern will be for frame buffer libraries to memory map
	the buffer and perform I/O directly (without kernel intervention).
	
	While here, fix two issues in the d_mmap method: properly include
	the requested mapping offset when calculating the physical
	address, and use ENODEV rather than EINVAL to be consistent with
	the read and write methods.

Affected files ...

.. //depot/projects/ctsrd/beribsd/src/sys/dev/terasic/mtllcd/terasic_mtllcd.c#4 edit
.. //depot/projects/ctsrd/beribsd/src/sys/dev/terasic/mtllcd/terasic_mtllcd_nexus.c#3 edit

Differences ...

==== //depot/projects/ctsrd/beribsd/src/sys/dev/terasic/mtllcd/terasic_mtllcd.c#4 (text+ko) ====

@@ -37,6 +37,7 @@
 #include <sys/lock.h>
 #include <sys/mutex.h>
 #include <sys/rman.h>
+#include <sys/uio.h>
 
 #include <machine/bus.h>
 #include <machine/resource.h>
@@ -44,16 +45,82 @@
 
 #include <dev/terasic/mtllcd/terasic_mtllcd.h>
 
-static d_mmap_t mtllcd_mmap;
+static d_mmap_t terasic_mtllcd_mmap;
+static d_read_t terasic_mtllcd_read;
+static d_write_t terasic_mtllcd_write;
 
 static struct cdevsw mtllcd_cdevsw = {
 	.d_version =	D_VERSION,
-	.d_mmap =	mtllcd_mmap,
+	.d_mmap =	terasic_mtllcd_mmap,
+	.d_read =	terasic_mtllcd_read,
+	.d_write =	terasic_mtllcd_write,
 	.d_name =	"terasic_mtllcd",
 };
 
+/*
+ * All I/O to/from the mtllcd device must be 32-bit, and aligned to 32-bit.
+ */
 static int
-mtllcd_mmap(struct cdev *dev, vm_ooffset_t offset, vm_paddr_t *paddr,
+terasic_mtllcd_read(struct cdev *dev, struct uio *uio, int flag)
+{
+	struct terasic_mtllcd_softc *sc;
+	u_long offset, size;
+	uint32_t v;
+	int error;
+
+	if (uio->uio_offset < 0 || uio->uio_offset % 4 != 0 ||
+	    uio->uio_resid % 4 != 0)
+		return (ENODEV);
+	sc = dev->si_drv1;
+	TERASIC_MTLLCD_LOCK(sc);
+	size = rman_get_size(sc->mtl_res);
+	TERASIC_MTLLCD_UNLOCK(sc);
+	error = 0;
+	if ((uio->uio_offset + uio->uio_resid < 0) ||
+	    (uio->uio_offset + uio->uio_resid > size))
+		return (ENODEV);
+	while (uio->uio_resid > 0) {
+		offset = uio->uio_offset;
+		if (offset + sizeof(v) > size)
+			return (ENODEV);
+		v = bus_read_4(sc->mtl_res, offset);
+		error = uiomove(&v, sizeof(v), uio);
+		if (error)
+			return (error);
+	}
+	return (error);
+}
+
+static int
+terasic_mtllcd_write(struct cdev *dev, struct uio *uio, int flag)
+{
+	struct terasic_mtllcd_softc *sc;
+	u_long offset, size;
+	uint32_t v;
+	int error;
+
+	if (uio->uio_offset < 0 || uio->uio_offset % 4 != 0 ||
+	    uio->uio_resid % 4 != 0)
+		return (ENODEV);
+	sc = dev->si_drv1;
+	TERASIC_MTLLCD_LOCK(sc);
+	size = rman_get_size(sc->mtl_res);
+	TERASIC_MTLLCD_UNLOCK(sc);
+	error = 0;
+	while (uio->uio_resid > 0) {
+		error = uiomove(&v, sizeof(v), uio);
+		if (error)
+			return (error);
+		offset = uio->uio_offset;
+		if (offset + sizeof(v) > size)
+			return (ENODEV);
+		bus_write_4(sc->mtl_res, offset, v);
+	}
+	return (error);
+}
+
+static int
+terasic_mtllcd_mmap(struct cdev *dev, vm_ooffset_t offset, vm_paddr_t *paddr,
     int nprot, vm_memattr_t *memattr)
 {
 	struct terasic_mtllcd_softc *sc;
@@ -64,10 +131,10 @@
 	error = 0;
 	if (trunc_page(offset) == offset &&
 	    rman_get_size(sc->mtl_res) >= offset + PAGE_SIZE) {
-		*paddr = rman_get_start(sc->mtl_res);
+		*paddr = rman_get_start(sc->mtl_res) + offset;
 		*memattr = VM_MEMATTR_UNCACHED;
 	} else
-		error = EINVAL;
+		error = ENODEV;
 	TERASIC_MTLLCD_UNLOCK(sc);
 	return (error);
 }

==== //depot/projects/ctsrd/beribsd/src/sys/dev/terasic/mtllcd/terasic_mtllcd_nexus.c#3 (text+ko) ====

@@ -56,10 +56,6 @@
  *
  * TODO:
  *
- * 1. Allow read(2) and write(2) to work on MTL frame buffer / input memory so
- *    that dd(1), etc, can be used to paint the touch screen conveniently
- *    when there is no windowing system running.
- *
  * 2. Allow different portions of the MTL memory space to be exported via
  *    different device nodes -- text frame buffer, graphics frame buffer,
  *    touch screen input.


More information about the p4-projects mailing list