Hooking versus Punting

The terms hooking and punting refer to driver decisions concerning how standard bitmap drawing operations are implemented. If the driver requests GDI to create a surface with a standard DIB format, GDI can handle all drawing and text operations. A driver can, however, hook out and implement functions if its hardware provides faster operation. A driver hooks a DrvXxx function when it has implemented that function's operation. Punting means that the driver wants GDI to handle the operation.

There are some situations in which the operation must be implemented in the driver. For example, if you are dealing with a device-managed surface, or you are drawing on a nonstandard bitmap, certain drawing functions must be implemented in the display driver. Display drivers must also handle the management of banked memory, although they can callback for each bank and have GDI do the drawing.

Hooking

By default, when a drawing surface is an engine-managed surface, GDI handles the drawing (rendering) operation. For a driver to take advantage of hardware that offers acceleration for some or all of these drawing functions for a given surface, or to make use of special block transfer hardware, it can hook these functions from GDI. To hook calls, the driver specifies the hooks as flags of the flHook parameter of the EngAssociateSurface function.

If the driver hooks a call, it must implement that call. The driver can optimize the operation where there is hardware support; or it can implement the operation in highly optimized assembler code when portability is not an issue. Such a driver might handle only certain cases on a hooked call. For example, if complicated graphics are requested on a call that is hooked, it may still be more efficient to punt the call back to GDI, allowing GDI to handle the operation.

Another example of a driver choosing whether or not to handle a hooked call is a driver that supports hardware that can handle bit-block-transfer calls with certain ROPs, but otherwise is just a frame buffer. Such a driver will return a handle to the bitmap surface for the frame buffer as the surface for its PDEV, but it will hook the DrvBitBlt call for itself. When GDI calls DrvBitBlt, the driver can check the ROP to see if it is one of those supported by the hardware. If not, the driver can pass the operation back to GDI with a call to EngBitBlt.

Drivers that support device-managed surfaces must hook out some of the drawing functions; namely DrvPaint, DrvCopyBits, DrvTextOut, and DrvStrokePath. Although GDI simulations can handle other drawing functions, it is recommended for performance reasons that drivers of this type hook out other functions, such as DrvBitBlt and DrvRealizeBrush, because simulation requires drawing from and to the surface.

Punting

Punting the call back to GDI means to put in a call to the corresponding GDI simulation. In general, for every DrvXxx graphics output call, there is a corresponding GDI EngXxx simulation call that takes the same arguments. Object parameters, such as a SURFOBJ, PATHOBJ, or CLIPOBJ, can be passed without change to GDI simulation. When the driver punts a call back to GDI, the size of the driver is reduced (since the code for that functionality can be omitted). However, because the engine owns the call, the driver does not have control over the execution speed. For some complicated cases, there may be no real advantage to providing support in the driver.

Hookable GDI Graphics Output Functions

The graphics output functions that the driver can hook and the corresponding GDI simulations are listed in the following table.

Driver Graphics Output Function Corresponding GDI Simulation
DrvBitBlt EngBitBlt
DrvCopyBits EngCopyBits
DrvStretchBlt EngStretchBlt
DrvFillPath EngFillPath
DrvStrokeAndFillPath EngStrokeAndFillPath
DrvTextOut EngTextOut
DrvPaint EngPaint
DrvStrokePath EngStrokePath
DrvLineTo EngLineTo