summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--bsd-core/drmP.h7
-rw-r--r--bsd-core/drm_bufs.c55
-rw-r--r--bsd-core/drm_drv.c7
3 files changed, 42 insertions, 27 deletions
diff --git a/bsd-core/drmP.h b/bsd-core/drmP.h
index d5907355..751714b6 100644
--- a/bsd-core/drmP.h
+++ b/bsd-core/drmP.h
@@ -686,6 +686,9 @@ struct drm_driver_info {
unsigned use_mtrr :1;
};
+/* Length for the array of resource pointers for drm_get_resource_*. */
+#define DRM_MAX_PCI_RESOURCE 3
+
/**
* DRM device functions structure
*/
@@ -748,6 +751,10 @@ struct drm_device {
#endif
void *irqh; /* Handle from bus_setup_intr */
+ /* Storage of resource pointers for drm_get_resource_* */
+ struct resource *pcir[DRM_MAX_PCI_RESOURCE];
+ int pcirid[DRM_MAX_PCI_RESOURCE];
+
int pci_domain;
int pci_bus;
int pci_slot;
diff --git a/bsd-core/drm_bufs.c b/bsd-core/drm_bufs.c
index 5ce2d4de..1df0238d 100644
--- a/bsd-core/drm_bufs.c
+++ b/bsd-core/drm_bufs.c
@@ -31,6 +31,8 @@
*
*/
+#include "dev/pci/pcireg.h"
+
#include "drmP.h"
/*
@@ -49,46 +51,45 @@ int drm_order(unsigned long size)
return order;
}
-unsigned long drm_get_resource_start(drm_device_t *dev, unsigned int resource)
+/* Allocation of PCI memory resources (framebuffer, registers, etc.) for
+ * drm_get_resource_*. Note that they are not RF_ACTIVE, so there's no virtual
+ * address for accessing them. Cleaned up at lastclose.
+ */
+static int drm_alloc_resource(drm_device_t *dev, int resource)
{
- struct resource *bsr;
- unsigned long offset;
+ if (resource >= DRM_MAX_PCI_RESOURCE) {
+ DRM_ERROR("Resource %d too large\n", resource);
+ return 1;
+ }
+ if (dev->pcir[resource] != NULL)
+ return 0;
- resource = resource * 4 + 0x10;
+ dev->pcirid[resource] = PCIR_BAR(resource);
+ dev->pcir[resource] = bus_alloc_resource_any(dev->device,
+ SYS_RES_MEMORY, &dev->pcirid[resource], RF_SHAREABLE);
- bsr = bus_alloc_resource_any(dev->device, SYS_RES_MEMORY, &resource,
- RF_ACTIVE | RF_SHAREABLE);
- if (bsr == NULL) {
+ if (dev->pcir[resource] == NULL) {
DRM_ERROR("Couldn't find resource 0x%x\n", resource);
- return 0;
+ return 1;
}
- offset = rman_get_start(bsr);
+ return 0;
+}
- bus_release_resource(dev->device, SYS_RES_MEMORY, resource, bsr);
+unsigned long drm_get_resource_start(drm_device_t *dev, unsigned int resource)
+{
+ if (drm_alloc_resource(dev, resource) != 0)
+ return 0;
- return offset;
+ return rman_get_start(dev->pcir[resource]);
}
unsigned long drm_get_resource_len(drm_device_t *dev, unsigned int resource)
{
- struct resource *bsr;
- unsigned long len;
-
- resource = resource * 4 + 0x10;
-
- bsr = bus_alloc_resource_any(dev->device, SYS_RES_MEMORY, &resource,
- RF_ACTIVE | RF_SHAREABLE);
- if (bsr == NULL) {
- DRM_ERROR("Couldn't find resource 0x%x\n", resource);
- return ENOMEM;
- }
-
- len = rman_get_size(bsr);
-
- bus_release_resource(dev->device, SYS_RES_MEMORY, resource, bsr);
+ if (drm_alloc_resource(dev, resource) != 0)
+ return 0;
- return len;
+ return rman_get_size(dev->pcir[resource]);
}
int drm_addmap(drm_device_t * dev, unsigned long offset, unsigned long size,
diff --git a/bsd-core/drm_drv.c b/bsd-core/drm_drv.c
index c4ee39cb..63024132 100644
--- a/bsd-core/drm_drv.c
+++ b/bsd-core/drm_drv.c
@@ -474,6 +474,13 @@ static int drm_lastclose(drm_device_t *dev)
TAILQ_FOREACH_SAFE(map, &dev->maplist, link, mapsave) {
drm_rmmap(dev, map);
}
+ for (i = 0; i < DRM_MAX_PCI_RESOURCE; i++) {
+ if (dev->pcir[i] == NULL)
+ continue;
+ bus_release_resource(dev->device, SYS_RES_MEMORY,
+ dev->pcirid[i], dev->pcir[i]);
+ dev->pcir[i] = NULL;
+ }
drm_dma_takedown(dev);
if ( dev->lock.hw_lock ) {