NetBSD-Bugs archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

re: kern/41715



OK, the problem is that mmio regs are being access when the device
isn't open by the vblank callout.

i've stopped it from doing that, and now i can't seem to get any
crashes.

my patch is below.  it inclues a work-around for drm_ioctl.c to
get past a -current issue.  it also contains additional code to
call drm_rmmap() when these mappings are throw away.. (this was
the key to the dev_priv->mmio changing issue i was seeing.  there
was no corruption.)


there's a couple of other changes in there as well.  i need to
look more closely at the callout_drain() change, and possible
make it use the dev->vbl_lock.  and the callout* usage in
vblank_disable_fn() could use some looking at.


.mrg.


Index: bsd-core/drmP.h
===================================================================
RCS file: /cvsroot/src/sys/external/bsd/drm/dist/bsd-core/drmP.h,v
retrieving revision 1.12
diff -p -r1.12 drmP.h
*** bsd-core/drmP.h     20 Jun 2009 01:07:09 -0000      1.12
--- bsd-core/drmP.h     7 Aug 2009 01:45:49 -0000
*************** struct drm_file;
*** 133,139 ****
  #define DRM_KASSERT(x,y)    KASSERT(x)
  #define device_get_softc(x)   device_private(x)
  #define callout_deactivate(x) callout_stop(x)
! #define callout_drain(x)      callout_stop(x)
  #endif
  
  #if defined(DRM_LINUX) && DRM_LINUX && !defined(__amd64__)
--- 133,139 ----
  #define DRM_KASSERT(x,y)    KASSERT(x)
  #define device_get_softc(x)   device_private(x)
  #define callout_deactivate(x) callout_stop(x)
! #define callout_drain(x)      callout_halt(x, NULL)
  #endif
  
  #if defined(DRM_LINUX) && DRM_LINUX && !defined(__amd64__)
*************** struct drm_file {
*** 582,590 ****
        int               minor;
        pid_t             pid;
        uid_t             uid;
- #if defined(__NetBSD__)
-       int refs;
- #endif
        drm_magic_t       magic;
        unsigned long     ioctl_count;
        void             *driver_priv;
--- 582,587 ----
Index: bsd-core/drm_fops.c
===================================================================
RCS file: /cvsroot/src/sys/external/bsd/drm/dist/bsd-core/drm_fops.c,v
retrieving revision 1.5
diff -p -r1.5 drm_fops.c
*** bsd-core/drm_fops.c 20 Jun 2009 01:07:09 -0000      1.5
--- bsd-core/drm_fops.c 7 Aug 2009 01:45:49 -0000
*************** int drm_open_helper(dev_t kdev, int flag
*** 70,78 ****
  
        DRM_LOCK();
        priv = drm_find_file_by_proc(dev, p);
!       if (priv) {
!               priv->refs++;
!       } else {
                priv = malloc(sizeof(*priv), DRM_MEM_FILES, M_NOWAIT | M_ZERO);
                if (priv == NULL) {
                        DRM_UNLOCK();
--- 70,76 ----
  
        DRM_LOCK();
        priv = drm_find_file_by_proc(dev, p);
!       if (!priv) {
                priv = malloc(sizeof(*priv), DRM_MEM_FILES, M_NOWAIT | M_ZERO);
                if (priv == NULL) {
                        DRM_UNLOCK();
*************** int drm_open_helper(dev_t kdev, int flag
*** 81,87 ****
                priv->uid               = kauth_cred_getsvuid(p->p_cred);
                priv->pid               = p->p_pid;
  
-               priv->refs              = 1;
                priv->minor             = m;
                priv->ioctl_count       = 0;
  
--- 79,84 ----
Index: bsd-core/drm_ioctl.c
===================================================================
RCS file: /cvsroot/src/sys/external/bsd/drm/dist/bsd-core/drm_ioctl.c,v
retrieving revision 1.4
diff -p -r1.4 drm_ioctl.c
*** bsd-core/drm_ioctl.c        20 Jun 2009 01:07:09 -0000      1.4
--- bsd-core/drm_ioctl.c        7 Aug 2009 01:45:49 -0000
*************** drm_set_busid(struct drm_device *dev)
*** 135,142 ****
--- 135,147 ----
                return ENOMEM;
        }
  
+ #if 0
        snprintf(dev->unique, dev->unique_len, "pci:%04x:%02x:%02x.%1x",
            dev->pci_domain, dev->pci_bus, dev->pci_slot, dev->pci_func);
+ #else
+       snprintf(dev->unique, dev->unique_len, "pci:%04x:%02x:%02x.%1x",
+           dev->pci_bus, dev->pci_bus, dev->pci_slot, dev->pci_func);
+ #endif
  
        DRM_UNLOCK();
  
Index: bsd-core/drm_irq.c
===================================================================
RCS file: /cvsroot/src/sys/external/bsd/drm/dist/bsd-core/drm_irq.c,v
retrieving revision 1.10
diff -p -r1.10 drm_irq.c
*** bsd-core/drm_irq.c  20 Jun 2009 01:07:09 -0000      1.10
--- bsd-core/drm_irq.c  7 Aug 2009 01:45:49 -0000
*************** void drm_vblank_cleanup(struct drm_devic
*** 139,144 ****
--- 139,148 ----
  
        vblank_disable_fn((void *)dev);
  
+ #if defined(__NetBSD__)
+       callout_destroy(&dev->vblank_disable_timer);
+ #endif
+ 
        free(dev->vblank, DRM_MEM_DRIVER);
  
        dev->num_crtcs = 0;
*************** void drm_vblank_put(struct drm_device *d
*** 366,372 ****
  #if defined(__FreeBSD__)
                (timeout_t *)
  #endif
!         vblank_disable_fn, (void *)dev);
        DRM_SPINUNLOCK_IRQRESTORE(&dev->vbl_lock, irqflags);
  }
  
--- 370,376 ----
  #if defined(__FreeBSD__)
                (timeout_t *)
  #endif
!                            vblank_disable_fn, (void *)dev);
        DRM_SPINUNLOCK_IRQRESTORE(&dev->vbl_lock, irqflags);
  }
  
Index: bsd-core/drm_scatter.c
===================================================================
RCS file: /cvsroot/src/sys/external/bsd/drm/dist/bsd-core/drm_scatter.c,v
retrieving revision 1.3
diff -p -r1.3 drm_scatter.c
*** bsd-core/drm_scatter.c      20 Jun 2009 01:07:09 -0000      1.3
--- bsd-core/drm_scatter.c      7 Aug 2009 01:45:49 -0000
*************** drm_sg_alloc(struct drm_device *dev, str
*** 127,132 ****
--- 127,133 ----
  
        dmah->tag = dev->pa.pa_dmat;
  
+       DRM_DEBUG("going to bus_dmamem_alloc size=%lx pages=%lx\n", 
request->size, pages);
        if ((ret = bus_dmamem_alloc(dmah->tag, request->size, PAGE_SIZE, 0,
                                    dmah->segs, pages, &nsegs,
                                    BUS_DMA_WAITOK) != 0)) {
Index: shared-core/radeon_cp.c
===================================================================
RCS file: /cvsroot/src/sys/external/bsd/drm/dist/shared-core/radeon_cp.c,v
retrieving revision 1.5
diff -p -r1.5 radeon_cp.c
*** shared-core/radeon_cp.c     20 Jun 2009 01:07:10 -0000      1.5
--- shared-core/radeon_cp.c     7 Aug 2009 01:45:49 -0000
*************** static int radeon_do_cleanup_cp(struct d
*** 1401,1406 ****
--- 1401,1412 ----
                        dev_priv->gart_info.addr = 0;
                }
        }
+ 
+       if (dev_priv->mmio)
+               drm_rmmap(dev, dev_priv->mmio);
+       if (dev_priv->fb_map)
+               drm_rmmap(dev, dev_priv->fb_map);
+ 
        /* only clear to the start of flags */
        memset(dev_priv, 0, offsetof(drm_radeon_private_t, flags));
  
*************** int radeon_driver_load(struct drm_device
*** 2021,2027 ****
  int radeon_driver_firstopen(struct drm_device *dev)
  {
        int ret;
-       drm_local_map_t *map;
        drm_radeon_private_t *dev_priv = dev->dev_private;
  
        dev_priv->gart_info.table_size = RADEON_PCIGART_TABLE_SIZE;
--- 2027,2032 ----
*************** int radeon_driver_firstopen(struct drm_d
*** 2035,2041 ****
        dev_priv->fb_aper_offset = drm_get_resource_start(dev, 0);
        ret = drm_addmap(dev, dev_priv->fb_aper_offset,
                         drm_get_resource_len(dev, 0), _DRM_FRAME_BUFFER,
!                        _DRM_WRITE_COMBINING, &map);
        if (ret != 0)
                return ret;
  
--- 2040,2046 ----
        dev_priv->fb_aper_offset = drm_get_resource_start(dev, 0);
        ret = drm_addmap(dev, dev_priv->fb_aper_offset,
                         drm_get_resource_len(dev, 0), _DRM_FRAME_BUFFER,
!                        _DRM_WRITE_COMBINING, &dev_priv->fb_map);
        if (ret != 0)
                return ret;
  
Index: shared-core/radeon_drv.h
===================================================================
RCS file: /cvsroot/src/sys/external/bsd/drm/dist/shared-core/radeon_drv.h,v
retrieving revision 1.5
diff -p -r1.5 radeon_drv.h
*** shared-core/radeon_drv.h    19 Jun 2009 03:50:05 -0000      1.5
--- shared-core/radeon_drv.h    7 Aug 2009 01:45:49 -0000
*************** typedef struct drm_radeon_private {
*** 296,301 ****
--- 296,302 ----
  
        drm_local_map_t *sarea;
        drm_local_map_t *mmio;
+       drm_local_map_t *fb_map;
        drm_local_map_t *cp_ring;
        drm_local_map_t *ring_rptr;
        drm_local_map_t *gart_textures;
Index: shared-core/radeon_irq.c
===================================================================
RCS file: /cvsroot/src/sys/external/bsd/drm/dist/shared-core/radeon_irq.c,v
retrieving revision 1.2
diff -p -r1.2 radeon_irq.c
*** shared-core/radeon_irq.c    19 Jun 2009 03:50:05 -0000      1.2
--- shared-core/radeon_irq.c    7 Aug 2009 01:45:49 -0000
*************** int radeon_enable_vblank(struct drm_devi
*** 65,70 ****
--- 65,73 ----
  {
        drm_radeon_private_t *dev_priv = dev->dev_private;
  
+       if (!dev_priv->mmio)
+               return 0;
+ 
        if ((dev_priv->flags & RADEON_FAMILY_MASK) >= CHIP_RS600) {     
                switch (crtc) {
                case 0:
*************** void radeon_disable_vblank(struct drm_de
*** 100,105 ****
--- 103,111 ----
  {
        drm_radeon_private_t *dev_priv = dev->dev_private;
  
+       if (!dev_priv->mmio)
+               return;
+ 
        if ((dev_priv->flags & RADEON_FAMILY_MASK) >= CHIP_RS600) {     
                switch (crtc) {
                case 0:
*************** u32 radeon_get_vblank_counter(struct drm
*** 289,294 ****
--- 295,302 ----
                DRM_ERROR("called with no initialization\n");
                return -EINVAL;
        }
+       if (!dev_priv->mmio)
+               return 0;
  
        if (crtc < 0 || crtc > 1) {
                DRM_ERROR("Invalid crtc %d\n", crtc);
*************** int radeon_irq_emit(struct drm_device *d
*** 322,327 ****
--- 330,337 ----
                DRM_ERROR("called with no initialization\n");
                return -EINVAL;
        }
+       if (!dev_priv->mmio)
+               return 0;
  
        result = radeon_emit_irq(dev);
  
*************** int radeon_irq_wait(struct drm_device *d
*** 344,349 ****
--- 354,361 ----
                DRM_ERROR("called with no initialization\n");
                return -EINVAL;
        }
+       if (!dev_priv->mmio)
+               return 0;
  
        return radeon_wait_irq(dev, irqwait->irq_seq);
  }


Home | Main Index | Thread Index | Old Index