|Deletions are marked like this.||Additions are marked like this.|
|Line 8:||Line 8:|
|[[http://www.x.org/releases/X11R7.7/doc/xorg-server/ddxDesign.html|DDX DESIGN documentation]] ([[ttp://www.x.org/releases/X11R7.7/doc/xorg-server/ddxDesign.pdf|PDF]]). It explains the design and the structure of the driver. Furthermore it contains||[[http://www.x.org/releases/X11R7.7/doc/xorg-server/ddxDesign.html|DDX DESIGN documentation]] ([[http://www.x.org/releases/X11R7.7/doc/xorg-server/ddxDesign.pdf|PDF]]). It explains the design and the structure of the driver. Furthermore it contains|
I want to develop an new driver - where do I start?
If you already have downloaded the Xserver sourcetree - which you have to do anyway - you can find the xml source for this file in the directory: hw/xfree86/doc/. You may also pick one of the existing drivers as a reference. (I personally like to use the neomagic driver, it is simple and I wrote it ).
My chipset supports more than one head - How can I implement that?
[Just a clipping from an email I wrote]
[Question - does this section still apply in this day and age? -MJT]
Basically both heads will be driven by different instances of the same driver. Each driver runs on a different 'entity' of the same device, since there is a different copy of the screen structures and driver structures for each driver for each entity this doesn't differ much from the same driver running two distinct chipsets. Still both instances of the driver can see each other, as they can share a driver private structure that can be used to pass information between the different instances. This structure is allocated during probing of the entity of this chipset which is the master.
To implement this there is a little overhead required:
The Probe() function needs to be able to distingquish between two heads. Take a look at the 'chips' driver: the CHIPSProbe() function has some special treatment for the 69030. This code is what you need. You can copy most of it verbatim.
To identify if the instance of the driver is running on the master or the slave you can check xf86IsPrimInitDone() in the PreInit() function. Before you return from this function for the master you should call xf86SetPrimInitDone() to set this variable.
If your driver supports both single head and dual head chipsets you can query xf86IsEntityShared() to find out if it is shared.
You can share data between the primary and the secondary screen in the private structure that you allocate in the Probe() function. To get to this structure you have to call xf86GetEntityPrivate().
What about the RandR 1.2 modesetting APIs?
[This is the information I gleaned trying to add DDX modesetting support to the VirtualBox video driver. I will update it as I go along. Please update if you know more/better! -MJT]
A useful piece of documentation for starting out is hw/xfree86/doc/README.modes in the server source code, which describes how to add the necessary information about crtcs and outputs (the main objects in DDX modesetting) to a driver. Information about the functions in the xf86OutputFuncs structure, which are not described in the README.modes file, can be found in the header file hw/xfree86/modes/xf86Crtc.h. randrproto.txt describes the protocol from a general and an X11 client point of view.
An omission in the README.modes document is that xf86OutputUseScreenMonitor() should be called after xf86OutputCreate() but before xf86InitialConfiguration(). Failing to do so can cause a server segfault.
The call to xf86CrtcSetSizeRange() with a valid maximum range is required. The maximum value must fit in a 16bit signed word.
In order to be able to expand the virtual resolution beyond its initial value, the resize function in the xf86CrtcConfigFuncsRec has to resize the screen pixmap as well as setting scrn->virtualX, scrn->virtualY and scrn->displayWidth. To obtain the screen pixmap, call pScreen->GetScreenPixmap(pScreen), and to change its values (there is no memory to reallocate, as it points to video RAM), call pScreen->ModifyPixmapHeader(). In this case the resize function should also set the new virtual resolution to the hardware.
A new mode type - M_T_PREFERRED - can be set instead of M_T_BUILTIN for at least one mode returned by get_modes in the xf86OutputFuncsRec structure. This corresponds to e.g. the native resolution of an LCD display. When the display is set up automatically this (or these) preferred modes will be given priority.
- In RandR 1.2, monitor hotplugging events are meant to be sent to the driver by a client daemon, using the RandR 1.2 client protocol. I believe this will be (was) changed as part of kernel mode setting.
- For working EDID information (used for instance by gnome-control-center to display monitor name) either don't implement the output set_property callback (given to xf86OutputCreate) or have it always return TRUE. This is because EDID information is stored as a property on each output.
See http://www.virtualbox.org/browser/trunk/src/VBox/Additions/x11/vboxvideo, particularly the file vboxvideo_13.c for a reasonably simple sample of a driver using RandR 1.2 modesetting.