FBDRI can run independant of any 2D windowing system. You don't have to load 2D windowing and user interface code if you don't need it. OpenGL programs that use FBDRI instead of XF86DRI require much less memory since Xlib, the XServer, and all the X extensions are removed. FBDRI programs can have larger visuals and textures than X because no offscreen memory is reserved for anything else and we can easily kludge the memory manager. FBDRI can potentially be much easier to configure than X. Although the current draft has a lot of hard coding, all you need to theoretically worry about is the framebuffer modeline and color depth. We can do lots of strange and unusual things much more easily under FBDRI than under X, like directly writing to texture memory over mmio, overlapping texture buffers to simulate more memory than we really have, implementing 2D windowing systems inside textures.
Rather we reused the GLX and XF86DRI code and performed significant modifications to run it independantly of a 2D windowing system. Despite the modifications, the reuse of XF86DRI makes it possible to support 3D in the framebuffer console shortly after any new X windows driver comes out.
Although the current FBDRI draft relies on SDL for visual initialization and user input, FBDRI is designed to function independant and parallel of the windowing system, thus there are no SDL dependancies in it. You could easily write your own initialization calls to the framebuffer device and transfer control to pure FBDRI in less than 64k of memory.
Currently FBDRI only works with the following chipset:
ATI Radeon with 64MB
ATI Radeon with 32MB
Since we're not planning to use any other chipset at the office, further ports would have to come from outside.
Either way, our installation directions are specific to radeon.
Sourcecode to download:
This contains an SDL and a DRI directory. They should both get uncomressed side by side somewhere. Then you should make in SDL and make in DRI.
Once the top level Makefiles are finished, go into dri/os-support/linux/drm/kernel and run make again.
So now you have four important objects:
sdl/src/.libs/libSDL* - SDL windowing system hacked for FBDRI.
dri/i686/libglfb.so - OpenGL implementation using FBDRI.
dri/i686/kernel/radeonfb.o - kernel framebuffer driver hacked to enable bus mastering.
dri/os-support/linux/drm/kernel/radeon.o - kernel DRI/DRM driver hacked for FBDRI.
If it succeeded in building a test program, congratulations, otherwise you'll have to write your own test program.
To run the test program you need to load some kernel modules.
insmod i686/kernel/radeonfb.o This probably depends on packed pixel modules in your /lib/modules directory. Obviously your kernel needs support for framebuffer devices enabled.
insmod os-support/linux/drm/kernel/radeon.o
Edit the LD_LIBRARY_PATH in runtest to point to your sdl/src/.libs and your dri/i686 directories. Then run runtest preferrably by remote login from another computer.
Hit a key to quit the program. It doesn't restore the console so you'll have to reboot to get it back.
081201: Initial release. 64MB Radeon only.
082201: This should theoretically support Radeons with 32MB as
well as 64MB. C++ as well as C programs should now compile for FBDRI. Some
functions not implemented in 081201 should now work. Also the waiting
and cache flushing was disabled from the DRM kernel module. This speeds
it up by 10% without appearing to cause any problems.
If you plan to develop for FBDRI the include directories are different:
sdl/include - SDL header files
dri/include/GL - OpenGL header files
You must use these include files instead of the traditional system includes because the SDL structures are different sizes to support FBDRI and the GL functions were mapped directly to FBDRI using macros, not assembly language symbol redirection like X Windows.
You must link the following libraries:
dri/i686/libglfb.so
sdl/src/.libs/libSDL.so
Unlike XF86DRI where you had a lot of functions to pointers indirecting 95% of the calls, FBDRI ports should rely on symbol reuse. Future FBDRI ports should rename the RADEON*, drmRadeon, etc calls to generic DRIVER, and drmDriver calls, thus by linking different object files for DRIVER and drmDriver functions you eliminate indirection and make the code much easier to read. The FBMesa calls already do this.
We've taken all the relevant DRI code from the XFree86 tree and assembled it in the dri directory. A single top-level Makefile compiles everything in all the dri subdirectories except os-support/linux/drm/kernel/.
"FBDRI_Main *dpy" replaces all "Display *dpy" and most of the visual/screen/drawable instances for now.
Currently some of the variables are hard coded to speed up the FB porting. Variables like PCI bus ID.
Wherever an X structure is needed, values are set in the FBDRI_Main structure, to be initialized in the FBDRIScreenInit command. This is called by whatever initializes the framebuffer console, in our case SDL.
All X11 dependancies which can't be removed have to be implemented in the FBDRI_Main object.
Spagetti for sending requests to the X Server are gone.
Version checking is gone, probably to be reintroduced later.
The kernel level driver is straight from xc/programs/Xserver/hw/xfree86/os-support/linux/drm/kernel. Minor changes are done to improve verbosity and work around some X Server dependancies.
Mappings between the X11 dri directories and the FB dri directories.
We try to adhere to the original directory structure to minimize confusion.
xc/include/GL | -> | include/GL |
xc/extras/Mesa/include/GL | -> | include/GL |
xc/lib/GL/dri | -> | lib/GL/dri |
xc/lib/GL/glx | -> | lib/GL/glfb |
xc/lib/GL/mesa/src/drv/ | -> | lib/GL/mesa/src/drv/ |
xc/lib/GL/mesa/dri/ | -> | lib/GL/mesa/dri |
xc/programs/Xserver/hw/xfree86/os-support | -> | os-support |
xc/programs/Xserver/hw/xfree86/os-support/linux/drm/kernel | -> | os-support/linux/drm/kernel |
xc/programs/Xserver/hw/xfree86/drivers/ati | -> | drivers/ati/ |
xc/programs/Xserver/GL/dri/ | -> | dri/ |
You'll find that the driver specific definitions tend to stay in
dri/lib/GL/mesa/src/drv - user-space XF86DRI driver
dri/os-support/linux/drm/kernel - kernel-space XF86DRI driver
dri/drivers/ - segments of the XFree86 2D driver required by DRI
The dri source code documentation, except for the Jens Owen parts, is pretty bad, with many indirections making it hard to follow. Most of the indirections should be eliminated in FB dri and a monolithic libglfb.so binary created for each card.
Rough idea of the control flow in the X Server DRI:
X Server initialization calls this
radeon_driver.c: RADEONScreenInit
radeon_dri.c: RADEONDRIScreenInit
dri.c: DRIScreenInit
dri.c: DRICreateContextPrivFromHandle
dri.c: RADEONDRIMapInit
dri.c: RADEONInitVisualConfigs
SDL_video.c: SDL_SetVideoMode
SDL_x11video.c: X11_SetVideoMode
SDL_x11video.c: X11_CreateWindow
SDL_x11gl.c: X11_GL_CreateContext
glxcmds.c: CreateContext (glXCreateContext)
glxext.c: __glXInitialize
dri_glx.c: driCreateDisplay // Bind the __driCreateScreen functions to pointers
glxext.c: AllocAndFetchScreenConfigs
dri_mesa.c: __driCreateScreen (createScreen)
dri_mesa.c: driMesaCreateScreen
radeon_xmesa.c: XMesaCreateVisual
radeon_xmesa.c: XMesaInitDriver
radeon_screen.c: radeonCreateScreen
dri_mesa.c: driMesaCreateContext (createContext) // The dri context.
gl_create_context // The mesa GL context inside the dri context
radeon_xmesa.c: XMesaCreateContext (CreateContext)
radeon_context.c: radeonCreateContext
SDL_x11gl.c: X_GL_MakeCurrent (GL_MakeCurrent)
glxext.c: glXMakeCurrent
dri_mesa.c: driMesaBindContext
dri_mesa.c:driMesaCreateDrawable
radeon_xmesa.c: XMesaCreateWindowBuffer
Rough idea of the control flow in FB DRI. Most of these calls should
be direct:
SDL_video.c: SDL_SetVideoMode
SDL_fbvideo.c: FB_SetVideoMode
dri.c DRIExtensionInit
fbdrimain.c: FBDRIScreenInit
radeon_dri.c: RADEONPreInitDRI
radeon_dri.c: RADEONDRIScreenInit
dri.c: DRIScreenInit
dri.c: DRICreateContextPrivFromHandle
dri.c: RADEONDRIMapInit
dri.c: RADEONInitVisualConfigs
radeon_dri.c: RADEONDRITexturesInit
radeon_dri.c: RADEONDRIFinishScreenInit
glfbcmds.c: glFBCreateContext
glfbext.c: __glFBInitialize
dri_glfb.c: driCreateDisplay // Bind the __driCreateScreen functions to pointers
glfbext.c: AllocAndFetchScreenConfigs
dri_mesa.c: __driCreateScreen (createScreen)
dri_mesa.c: driMesaCreateScreen
radeon_fbmesa.c: FBMesaCreateVisual
radeon_fbmesa.c: FBMesaInitDriver
radeon_screen.c: radeonCreateScreen
dri_mesa.c: driMesaCreateContext (createContext) // The dri context.
gl_create_context // The mesa GL context inside the dri context
radeon_fbmesa.c: FBMesaCreateContext (CreateContext)
radeon_context.c: radeonCreateContext
glfbext.c: glFBMakeCurrent
dri_mesa.c: driMesaBindContext (bindContext)
dri_mesa.c:driMesaCreateDrawable
radeon_fbmesa.c: FBMesaCreateWindowBuffer
radeon_fbmesa.c: FBMesaMakeCurrent (MakeCurrent)
radeon_context.c: radeonMakeCurrent
glfbext.c: __glFBSetCurrentContext
radeon_driver.c: RADEONCloseScreen
radeon_dri.c: RADEONDRICloseScreen
dri.c: DRICloseScreen
glfbclient.h: GLFBcontext
fbdrimain.h: FBDRI_Main
fbdri.c: These were previously client side requests in
lib/GL/dri/XF86dri.c, later received by a server side xf86dri.c and
then dispatched to pure DRI calls. These should be replaced by the
pure DRI calls.
radeon_dri.c: Initializes the hardware.
SDL_fbvideo.c: Initializes the function that initializes the hardware.
glfbcmds.c, glfbext.c: Front end to the GL subsystem. Functions
usually start with "glFB" Initializes the OpenGL specific stuff.
dri_mesa.c: the front end to the front end of the GL subsystem. Entry
points used to initialize the system. Functions usually start with
"dri"
radeon_fbmesa.c: Entry points initializing card specific portions of
the DRI objects. Usually start with "FBMesa"