[PATCH:libpciaccess] Solaris: Implement map_legacy & legacy_io functions

Alan Coopersmith alan.coopersmith at oracle.com
Wed Apr 18 18:52:54 PDT 2012


Signed-off-by: Alan Coopersmith <alan.coopersmith at oracle.com>
---
 src/solx_devfs.c |  137 +++++++++++++++++++++++++++++++++++++++++++++++++++++-
 1 file changed, 135 insertions(+), 2 deletions(-)

diff --git a/src/solx_devfs.c b/src/solx_devfs.c
index 2079df0..4069dc2 100644
--- a/src/solx_devfs.c
+++ b/src/solx_devfs.c
@@ -1,6 +1,6 @@
 /*
  * (C) Copyright IBM Corporation 2006
- * Copyright (c) 2007, 2009, 2011, Oracle and/or its affiliates.
+ * Copyright (c) 2007, 2009, 2011, 2012, Oracle and/or its affiliates.
  * All Rights Reserved.
  *
  * Permission is hereby granted, free of charge, to any person obtaining a
@@ -38,6 +38,11 @@
 #include <libdevinfo.h>
 #include "pci_tools.h"
 
+#ifdef __x86
+# include <sys/sysi86.h>
+# include <sys/psw.h>
+#endif
+
 #include "pciaccess.h"
 #include "pciaccess_private.h"
 
@@ -1122,7 +1127,125 @@ pci_device_solx_devfs_write( struct pci_device * dev, const void * data,
     return (err);
 }
 
+static struct pci_io_handle *
+pci_device_solx_devfs_open_legacy_io(struct pci_io_handle *ret,
+				     struct pci_device *dev,
+				     pciaddr_t base, pciaddr_t size)
+{
+#ifdef __x86
+    if (sysi86(SI86V86, V86SC_IOPL, PS_IOPL) == 0) {
+	ret->base = base;
+	ret->size = size;
+	return ret;
+    }
+#endif
+    return NULL;
+}
+
+static uint32_t
+pci_device_solx_devfs_read32(struct pci_io_handle *handle, uint32_t reg)
+{
+#ifdef __x86
+    uint16_t port = (uint16_t) (handle->base + reg);
+    uint32_t ret;
+    __asm__ __volatile__("inl %1,%0":"=a"(ret):"d"(port));
+    return ret;
+#else
+    return *(uint32_t *)((uintptr_t)handle->memory + reg);
+#endif
+}
 
+static uint16_t
+pci_device_solx_devfs_read16(struct pci_io_handle *handle, uint32_t reg)
+{
+#ifdef __x86
+    uint16_t port = (uint16_t) (handle->base + reg);
+    uint16_t ret;
+    __asm__ __volatile__("inw %1,%0":"=a"(ret):"d"(port));
+    return ret;
+#else
+    return *(uint16_t *)((uintptr_t)handle->memory + reg);
+#endif
+}
+
+static uint8_t
+pci_device_solx_devfs_read8(struct pci_io_handle *handle, uint32_t reg)
+{
+#ifdef __x86
+    uint16_t port = (uint16_t) (handle->base + reg);
+    uint8_t ret;
+    __asm__ __volatile__("inb %1,%0":"=a"(ret):"d"(port));
+    return ret;
+#else
+    return *(uint8_t *)((uintptr_t)handle->memory + reg);
+#endif
+}
+
+static void
+pci_device_solx_devfs_write32(struct pci_io_handle *handle, uint32_t reg,
+    uint32_t data)
+{
+#ifdef __x86
+      uint16_t port = (uint16_t) (handle->base + reg);
+      __asm__ __volatile__("outl %0,%1"::"a"(data), "d"(port));
+#else
+      *(uint16_t *)((uintptr_t)handle->memory + reg) = data;
+#endif
+}
+
+static void
+pci_device_solx_devfs_write16(struct pci_io_handle *handle, uint32_t reg,
+    uint16_t data)
+{
+#ifdef __x86
+      uint16_t port = (uint16_t) (handle->base + reg);
+      __asm__ __volatile__("outw %0,%1"::"a"(data), "d"(port));
+#else
+    *(uint8_t *)((uintptr_t)handle->memory + reg) = data;
+#endif
+}
+
+static void
+pci_device_solx_devfs_write8(struct pci_io_handle *handle, uint32_t reg,
+    uint8_t data)
+{
+#ifdef __x86
+      uint16_t port = (uint16_t) (handle->base + reg);
+      __asm__ __volatile__("outb %0,%1"::"a"(data), "d"(port));
+#else
+      *(uint32_t *)((uintptr_t)handle->memory + reg) = data;
+#endif
+}
+
+static int
+pci_device_solx_devfs_map_legacy(struct pci_device *dev, pciaddr_t base,
+				 pciaddr_t size, unsigned map_flags,
+				 void **addr)
+{
+    int err;
+    struct pci_device_mapping map = {
+	.base = base,
+	.size = size,
+	.flags = map_flags,
+    };
+
+    err = pci_device_solx_devfs_map_range(dev, &map);
+    if (err == 0)
+	*addr = map.memory;
+    return err;
+}
+
+static int
+pci_device_solx_devfs_unmap_legacy(struct pci_device *dev,
+				   void *addr, pciaddr_t size)
+{
+    struct pci_device_mapping map = {
+	.memory = addr,
+	.size = size,
+    };
+
+    return pci_device_generic_unmap_range(dev, &map);
+}
 
 static const struct pci_system_methods solx_devfs_methods = {
     .destroy = pci_system_solx_devfs_destroy,
@@ -1135,7 +1258,17 @@ static const struct pci_system_methods solx_devfs_methods = {
     .read = pci_device_solx_devfs_read,
     .write = pci_device_solx_devfs_write,
 
-    .fill_capabilities = pci_fill_capabilities_generic
+    .fill_capabilities = pci_fill_capabilities_generic,
+
+    .open_legacy_io = pci_device_solx_devfs_open_legacy_io,
+    .read32 = pci_device_solx_devfs_read32,
+    .read16 = pci_device_solx_devfs_read16,
+    .read8 = pci_device_solx_devfs_read8,
+    .write32 = pci_device_solx_devfs_write32,
+    .write16 = pci_device_solx_devfs_write16,
+    .write8 = pci_device_solx_devfs_write8,
+    .map_legacy = pci_device_solx_devfs_map_legacy,
+    .unmap_legacy = pci_device_solx_devfs_unmap_legacy,
 };
 
 /*
-- 
1.7.9.2



More information about the xorg-devel mailing list