New DRM driver model - gets rid of DRM() macros!

Jon Smirl jonsmirl at
Tue Sep 28 08:54:35 PDT 2004

I've checked two new directories into DRM CVS for Linux 2.6 -
linux-core, shared-core. This code implements a new model for DRM
where DRM is split into a core piece and personality modules that
share the core. The major reason for doing this is that it allows me
to remove all of the DRM() macros; something that is causing lot's of
complaints from the Linux kernel people.

cvs -z3 -d:pserver:anonymous at co drm 

The patch for this is quite large, 500K, and it will mess up the Linux
2.4/BSD DRM builds since it removes the DRM() macro. Instead of doing
this as a patch I made the new CVS directories.

I've checked radeon and r128 and they work. Everything else should
work except ffb, please check the other drivers and let me know. I've
probably made some typos with a edit this large.

ffb should work in principle but since I don't own one or a Sparc
machine so I can't compile the driver. I suspect ffb has compiler
errors but the are easily fixed just by copying similar code from one
of the working modules. Please send patches.

The API between the core and personalities doesn't look to be all that
huge. With work I'd guess that 10% of the entry points could be
eliminated. After another year of development we might be able to
specify a stable core API.

What are everyone's thoughts on this? There is no technical reason it
can't be implemented on Linux 2.4/BSD, although I don't see any reason
to do it for 2.4.

Any ideas on how to generate a unique identifier for the core? It
probably should be regenerated by the Makefile whenever the core
changes. Personalities would have to match the core identifier. This
would stop people from loading binary modules that don't match the

After sometime testing and fixing obvious problems I'll generate a
patch for the 2.6 kernel and lkml.

[root at smirl linux-2.6]# lsmod | more
Module                  Size  Used by
tdfx                    2816  0
sis                    10176  0
mga                    56704  0
i915                   16896  0
via                    19428  0
savage                  3840  0
r128                   44672  0
radeon                 70272  0
drm                    59684  8 tdfx,sis,mga,i915,via,savage,r128,radeon

The core provides these entry points....

[root at smirl linux-2.6]# grep EXPORT_SYMBOL *

Drivers provide these callbacks......

struct drm_driver_fn {
       u32 driver_features;
       int dev_priv_size;
       int permanent_maps;
       drm_ioctl_desc_t *ioctls;
       int num_ioctls;
       int (*preinit)(struct drm_device *, unsigned long flags);
       void (*prerelease)(struct drm_device *, struct file *filp);
       void (*pretakedown)(struct drm_device *);
       int (*postcleanup)(struct drm_device *);
       int (*presetup)(struct drm_device *);
       int (*postsetup)(struct drm_device *);
       int (*dma_ioctl)( DRM_IOCTL_ARGS );
       /* these are opposites at the moment */
       int (*open_helper)(struct drm_device *, drm_file_t *);
       void (*free_filp_priv)(struct drm_device *, drm_file_t *);

       void (*release)(struct drm_device *, struct file *filp);
       void (*dma_ready)(struct drm_device *);
       int (*dma_quiescent)(struct drm_device *);
       int (*context_ctor)(struct drm_device *dev, int context);
       int (*context_dtor)(struct drm_device *dev, int context);
       int (*kernel_context_switch)(struct drm_device *dev, int old, int new);
       int (*kernel_context_switch_unlock)(struct drm_device *dev);
       int (*vblank_wait)(struct drm_device *dev, unsigned int *sequence);
/* these have to be filled in */
       int (*postinit)(struct drm_device *, unsigned long flags);
       irqreturn_t (*irq_handler)( DRM_IRQ_ARGS );
       void (*irq_preinstall)(struct drm_device *dev);
       void (*irq_postinstall)(struct drm_device *dev);
       void (*irq_uninstall)(struct drm_device *dev);
       void (*reclaim_buffers)(struct file *filp);
       unsigned long (*get_map_ofs)(drm_map_t *map);
       unsigned long (*get_reg_ofs)(struct drm_device *dev);
       void (*set_version)(struct drm_device *dev, drm_set_version_t *sv);
       int (*version)(drm_version_t *version);

Jon Smirl
jonsmirl at

More information about the xorg mailing list