MonitorSpec

From Amiga Coding
Jump to: navigation, search

MonitorSpec

This is the main structure representing a single display driver in AmigaOS.

Originally Amiga graphics.library can work only with chipset. So there are actually no video drivers, the library is a driver itself. However monitor drivers really exist.

A monitor driver is responsible for setting up synchronization signal rates and describing the physical layout of the display field. Monitor driver consists of mandatory MonitorSpec data structure, optional SpecialMonitor data structure, and optional code part. Display drivers can be either built-in into ROM or loaded from DEVS:Monitors drawer during system startup.

There is no support for display driver removal. Once it was installed it will live in your system forever.

There is support for library-alike opening and closing MonitorSpec. ms_OpenCount is incremented by every OpenMonitor() call and decremented by every CloseMonitor() call. No other actions on drivers are taken by these routines.

struct	MonitorSpec
{
    struct	ExtendedNode	ms_Node;            /* A common header to all graphics.library structures */
    UWORD	ms_Flags;                           /* Flags, see below */
    LONG	ratioh;
    LONG	ratiov;
    UWORD	total_rows;                         /* Total number of lines drawn. This includes border and vertical retrace */
    UWORD	total_colorclocks;                  /* Total number of color clocks per one line. This includes border and horizontal retrace */
    UWORD	DeniseMaxDisplayColumn;
    UWORD	BeamCon0;                           /* Value for beamcon0 register, written directly */
    UWORD	min_row;
    struct	SpecialMonitor	*ms_Special;        /* A pointer to optional structure describing variable display timings */
    UWORD	ms_OpenCount;                       /* Open count. Exact purpose is yet unknown */
    LONG	(*ms_transform)();
    LONG	(*ms_translate)();
    LONG	(*ms_scale)();
    UWORD	ms_xoffset;
    UWORD	ms_yoffset;
    struct Rectangle ms_LegalView;                  /* A valid range of positions for top-left corner of the view. Bottom-right point is included */
    LONG	(*ms_maxoscan)();	            /* maximum legal overscan */
    LONG	(*ms_videoscan)();	            /* video display overscan */
    UWORD	DeniseMinDisplayColumn;
    ULONG	DisplayCompatible;
    struct	List DisplayInfoDataBase;
    struct	SignalSemaphore DisplayInfoDataBaseSemaphore;
    LONG	(*ms_MrgCop)();                     /* Three optional pointers to driver-specific implementations                  */
    LONG	(*ms_LoadView)();                   /* of named routines. New for v39. Note that in v36 two of these               */
    LONG	(*ms_KillView)();                   /* three fields were simply reserved ULONGs, and ms_KillView was absent at all */
};

/* ms_Flags */
#define MSB_REQUEST_NTSC	0 /* This driver uses NTSC preset mode */
#define MSB_REQUEST_PAL		1 /* This driver uses PAL preset mode  */
#define MSB_REQUEST_SPECIAL	2 /* This driver uses custom scan rates, ms_Special is supplied */
#define MSB_REQUEST_A2024	3
#define MSB_DOUBLE_SPRITES	4
#define	MSF_REQUEST_NTSC	(1 << MSB_REQUEST_NTSC)
#define	MSF_REQUEST_PAL		(1 << MSB_REQUEST_PAL)
#define	MSF_REQUEST_SPECIAL	(1 << MSB_REQUEST_SPECIAL)
#define	MSF_REQUEST_A2024	(1 << MSB_REQUEST_A2024)
#define MSF_DOUBLE_SPRITES	(1 << MSB_DOUBLE_SPRITES)

/* obsolete, v37 compatible definitions follow */
#define	REQUEST_NTSC		(1 << MSB_REQUEST_NTSC)
#define	REQUEST_PAL		(1 << MSB_REQUEST_PAL)
#define	REQUEST_SPECIAL		(1 << MSB_REQUEST_SPECIAL)
#define	REQUEST_A2024		(1 << MSB_REQUEST_A2024)

Since v39 graphics.library started supporting RTG by itself. In order to provide an ability to completely replace chipset programming with own code. three fields exist for this purpose: ms_MrgCop, ms_LoadView and ms_KillView.

ms_MrgCop and ms_LoadView are there to provide replacements to corresponding functions in graphics.library. If these pointers are not NULLs, MrgCop() and LoadView() in graphics.library will simply jump to these vectors with original parameters, and do nothing more. Display driver's code will be fully responsible for setting up whatever hardware is used.

ms_KillView is called by graphics.library internal LoadView() implementation when current display driver is switched. This can be used, for example, for switching back from graphics card display to chipset display. In this case ms_KillView routine can be supplied which turns of card's display and enables chipset passthrough (for example). Chipset display drivers do not supply ms_KillView, for them internal blanking routine is used (which is equal to LoadView(NULL)).

For chipset display driver the following fields in this structure are taken into account (currently this follows LoadView() behavior):

  • ms_Flags is checked against MSF_REQUEST_SPECIAL. If this flag is set, the driver is expected to supply SpecialMonitor structure. See its description for further details.
  • total_rows is put into GfxBase->current_tot_rows
  • total_rows-1 is put into GfxBase->MaxDisplayRow
  • total_colorclocks is put into GfxBase->current_tot_cclks
  • DeniseMaxDisplayColumn is put into GfxBase->MaxDisplayColumn
  • BeamCon0 is written into beamcon0 chipset register. graphics.library does this itself only for standard displays (if MSF_SPECIAL is not set)
  • DeniseMinDisplayColumn is put into GfxBase->MinDisplayColumn