3357 lines
103 KiB
C
3357 lines
103 KiB
C
/*/****************************************************************************
|
|
* name: mtxinit.c
|
|
*
|
|
* description: Routines to initialise MGA board
|
|
*
|
|
* designed: Benoit Leblanc
|
|
* last modified: $Author: ctoutant $, $Date: 94/09/28 13:22:46 $
|
|
*
|
|
* version: $Id: MTXINIT.C 1.91 94/09/28 13:22:46 ctoutant Exp $
|
|
*
|
|
*
|
|
* HwData * mtxCheckHwAll(void)
|
|
* bool mtxSelectHw(HwData *pHardware)
|
|
* HwModeData * mtxGetHwModes(void)
|
|
* bool mtxSelectHwMode(HwModeData *pHwModeSelect)
|
|
* bool mtxSetDisplayMode(HwModeData *pDisplayModeSelect, dword Zoom)
|
|
*
|
|
* dword mtxGetMgaSel(void)
|
|
* void mtxGetInfo(HwModeData *pCurHwMode, HwModeData *pCurDispMode,
|
|
* byte *InitBuffer, byte *VideoBuffer)
|
|
* bool mtxSetLUT(word index, mtxRGB color)
|
|
* void mtxClose(void)
|
|
*
|
|
******************************************************************************/
|
|
|
|
#include "switches.h"
|
|
|
|
#ifdef WINDOWS_NT
|
|
#if defined(ALLOC_PRAGMA)
|
|
#pragma alloc_text(PAGE,mtxCheckHwAll)
|
|
#pragma alloc_text(PAGE,mtxSelectHw)
|
|
#pragma alloc_text(PAGE,mtxGetHwModes)
|
|
#pragma alloc_text(PAGE,mtxSelectHwMode)
|
|
#pragma alloc_text(PAGE,mtxSetDisplayMode)
|
|
#pragma alloc_text(PAGE,overScan)
|
|
#pragma alloc_text(PAGE,mapPciVl)
|
|
#pragma alloc_text(PAGE,MapBoard)
|
|
#pragma alloc_text(PAGE,adjustDefaultVidset)
|
|
#pragma alloc_text(PAGE,selectMgaInfoBoard)
|
|
#pragma alloc_text(PAGE,UpdateHwModeTable)
|
|
// #pragma alloc_text(PAGE,mtxGetMgaSel)
|
|
#pragma alloc_text(PAGE,mtxGetInfo)
|
|
#pragma alloc_text(PAGE,InitHwStruct)
|
|
#pragma alloc_text(PAGE,mtxSetLUT)
|
|
#pragma alloc_text(PAGE,mtxClose)
|
|
#endif
|
|
|
|
//Not to be paged out:
|
|
// Hw
|
|
// pMgaBaseAddr
|
|
// iBoard
|
|
// mtxVideoMode
|
|
// pMgaDeviceExtension
|
|
//#if defined(ALLOC_PRAGMA)
|
|
//#pragma data_seg("PAGE")
|
|
//#endif
|
|
|
|
#else /* #ifdef WINDOWS_NT */
|
|
|
|
#include <stdlib.h>
|
|
#include <string.h>
|
|
#include <stdio.h>
|
|
#include <dos.h>
|
|
#include <time.h>
|
|
|
|
#endif /* #ifdef WINDOWS_NT */
|
|
|
|
#ifdef OS2
|
|
#include <os2.h>
|
|
#pragma intrinsic(strcat, strcpy)
|
|
#endif
|
|
|
|
#ifdef WINDOWS
|
|
#include "windows.h"
|
|
#endif
|
|
|
|
#include "bind.h"
|
|
#include "defbind.h"
|
|
#include "sxci.h"
|
|
#include "def.h"
|
|
#include "mga.h"
|
|
#include "mgai_c.h"
|
|
#include "mgai.h"
|
|
#include "caddi.h"
|
|
#include "mtxpci.h"
|
|
#include "mtxvpro.h"
|
|
#include "vidfile.h"
|
|
|
|
#if ((!defined (WINDOWS_NT)) || (USE_DDC_CODE))
|
|
/*********** DDC CODE ****************/
|
|
#include "edid.h"
|
|
/*********** DDC CODE ****************/
|
|
#endif
|
|
|
|
/* Externals from mgainfo.c (which used to be mgainfo.h) */
|
|
/* #include "mgainfo.h" */ /* Default video parameters */
|
|
#ifdef WINDOWS_NT
|
|
extern UCHAR DefaultVidset[];
|
|
extern word configSpace;
|
|
#else
|
|
extern char DefaultVidset[];
|
|
#endif
|
|
|
|
/* Externals from tables.c (which used to be tables.h) */
|
|
/* #include "tables.h" */
|
|
extern OffScrData OffScrFBM_000_A[];
|
|
extern OffScrData iOffScrFBM_000_A[];
|
|
extern OffScrData OffScrFBM_010_A[];
|
|
extern OffScrData iOffScrFBM_010_A[];
|
|
extern OffScrData OffScrFBM_010_B[];
|
|
extern OffScrData iOffScrFBM_010_B[];
|
|
extern OffScrData OffScrFBM_011_A[];
|
|
extern OffScrData iOffScrFBM_011_A[];
|
|
extern OffScrData OffScrFBM_101_B[];
|
|
extern OffScrData iOffScrFBM_101_B[];
|
|
extern OffScrData OffScrFBM_111_A[];
|
|
extern OffScrData iOffScrFBM_111_A[];
|
|
extern OffScrData OffAth2[];
|
|
extern OffScrData iOffAth2[];
|
|
extern OffScrData OffAth4[];
|
|
extern OffScrData iOffAth4[];
|
|
extern HwModeData HwModesFBM_000_A[21];
|
|
extern HwModeInterlace iHwModesFBM_000_A[21];
|
|
extern HwModeData HwModesFBM_010_A[34];
|
|
extern HwModeInterlace iHwModesFBM_010_A[34];
|
|
extern HwModeData HwModesFBM_010_B[48];
|
|
extern HwModeInterlace iHwModesFBM_010_B[48];
|
|
extern HwModeData HwModesFBM_011_A[55];
|
|
extern HwModeInterlace iHwModesFBM_011_A[55];
|
|
extern HwModeData HwModesFBM_101_B[8];
|
|
extern HwModeInterlace iHwModesFBM_101_B[8];
|
|
extern HwModeData HwModesFBM_111_A[15];
|
|
extern HwModeInterlace iHwModesFBM_111_A[15];
|
|
extern HwModeData ModesAth2[63];
|
|
extern HwModeInterlace iModesAth2[63];
|
|
extern HwModeData ModesAth4[98];
|
|
extern HwModeInterlace iModesAth4[98];
|
|
|
|
|
|
|
|
#ifdef _WINDOWS_DLL16
|
|
|
|
/*** Definition for pool memory ***/
|
|
#define PAN_X 0
|
|
#define PAN_Y 1
|
|
#define PAN_DISP_WIDTH 2
|
|
#define PAN_DISP_HEIGHT 3
|
|
#define DB_SCALE 4
|
|
#define PAN_BOUND_LEFT 5
|
|
#define PAN_BOUND_TOP 6
|
|
#define PAN_BOUND_RIGHT 7
|
|
#define PAN_BOUND_BOTTOM 8
|
|
|
|
|
|
HINSTANCE hsxci=0;
|
|
HINSTANCE huser=0;
|
|
typedef long (FAR PASCAL *FARPROC2)();
|
|
static FARPROC2 fp1;
|
|
word NbSxciLoaded=0;
|
|
word FAR *pDllMem;
|
|
#endif
|
|
|
|
|
|
#ifdef PRINT_DEBUG
|
|
extern int debug_printf( char *fmt, ... );
|
|
extern void openDebugfFile(char *s);
|
|
extern void reOpenDebugfFile();
|
|
extern void closeDebugfFile(char *s);
|
|
extern void imprimeBuffer(byte *InitBuf, byte *VideoBuf);
|
|
#endif
|
|
|
|
dword MgaSel;
|
|
|
|
#ifdef WINDOWS_NT
|
|
|
|
extern INTERFACE_TYPE NtInterfaceType;
|
|
extern UCHAR MgaBusType[];
|
|
|
|
#define MGA_BUS_INVALID 0
|
|
#define MGA_BUS_PCI 1
|
|
#define MGA_BUS_ISA 2
|
|
|
|
ULONG PciSlot;
|
|
PVOID pMgaDeviceExtension;
|
|
PUCHAR pMgaBaseAddr;
|
|
PUCHAR pciBiosRoutine;
|
|
PUCHAR pMgaPciIo, pMgaPciConfigSpace;
|
|
|
|
#define PCI_LEN 0x00000004
|
|
#define CONFIG_SPACE 0x0000c000
|
|
#define CONFIG_LEN 0x00000100
|
|
|
|
VIDEO_ACCESS_RANGE MgaPciCseAccessRange =
|
|
{PCI_CSE, 0x00000000, PCI_LEN, 1, 0, 1};
|
|
|
|
VIDEO_ACCESS_RANGE MgaPciConfigAccessRange =
|
|
{CONFIG_SPACE, 0x00000000, CONFIG_LEN, 1, 0, 1};
|
|
|
|
VIDEO_ACCESS_RANGE VideoProAccessRange =
|
|
{0x00000240, 0x00000000, 0x20, 1, 1, 1};
|
|
|
|
typedef struct _MULTI_MODE
|
|
{
|
|
ULONG MulModeNumber; // unique mode Id
|
|
ULONG MulWidth; // total width of mode
|
|
ULONG MulHeight; // total height of mode
|
|
ULONG MulPixWidth; // pixel depth of mode
|
|
ULONG MulRefreshRate; // refresh rate of mode
|
|
USHORT MulArrayWidth; // number of boards arrayed along X
|
|
USHORT MulArrayHeight; // number of boards arrayed along Y
|
|
UCHAR MulBoardNb[NB_BOARD_MAX]; // board numbers of required boards
|
|
USHORT MulBoardMode[NB_BOARD_MAX]; // mode required from each board
|
|
HwModeData *MulHwModes[NB_BOARD_MAX]; // pointers to required HwModeData
|
|
} MULTI_MODE, *PMULTI_MODE;
|
|
|
|
|
|
/*--------------------------------------------------------------------------*\
|
|
| HW_DEVICE_EXTENSION
|
|
|
|
|
| Define device extension structure. This is device dependant/private
|
|
| information.
|
|
|
|
|
\*--------------------------------------------------------------------------*/
|
|
typedef struct _MGA_DEVICE_EXTENSION {
|
|
ULONG SuperModeNumber; // Current mode number
|
|
ULONG NumberOfSuperModes; // Total number of modes
|
|
PMULTI_MODE pSuperModes; // Array of super-modes structures
|
|
// For each board:
|
|
ULONG NumberOfModes[NB_BOARD_MAX]; // Number of available modes
|
|
ULONG NumberOfValidModes[NB_BOARD_MAX];
|
|
// Number of valid modes
|
|
ULONG ModeFlags2D[NB_BOARD_MAX]; // 2D modes supported by each board
|
|
ULONG ModeFlags3D[NB_BOARD_MAX]; // 3D modes supported by each board
|
|
USHORT ModeFreqs[NB_BOARD_MAX][64]; // Refresh rates bit fields
|
|
UCHAR ModeList[NB_BOARD_MAX][64]; // Valid hardware modes list
|
|
HwModeData *pMgaHwModes[NB_BOARD_MAX]; // Array of mode information structs.
|
|
BOOLEAN bUsingInt10; // May need this later
|
|
PVOID KernelModeMappedBaseAddress[NB_BOARD_MAX];
|
|
// Kern-mode virt addr base of MGA regs
|
|
PVOID UserModeMappedBaseAddress[NB_BOARD_MAX];
|
|
// User-mode virt addr base of MGA regs
|
|
PVOID MappedAddress[]; // NUM_MGA_COMMON_ACCESS_RANGES elements
|
|
} MGA_DEVICE_EXTENSION, *PMGA_DEVICE_EXTENSION;
|
|
|
|
//#define ADDR_46E8_PORT (PVOID) ((ULONG)(((PMGA_DEVICE_EXTENSION)pMgaDeviceExtension)->MappedAddress[5]) + (0x46e8 - 0x46e8))
|
|
#define ADDR_46E8_PORT 0x46e8
|
|
|
|
#else /* #ifdef WINDOWS_NT */
|
|
|
|
volatile byte _Far *pMgaBaseAddr;
|
|
|
|
#endif /* #ifdef WINDOWS_NT */
|
|
|
|
/* Global parameters */
|
|
byte iBoard=0; /* index of current selected board */
|
|
byte NbBoard=0; /* total board detected */
|
|
|
|
bool CheckHwAllDone=FALSE;
|
|
bool SpecialModeOn = FALSE;
|
|
/*VIDEOPRO*/
|
|
bool VAFCconnector;
|
|
extern bool initVideoMode(word mode, byte pwidth);
|
|
extern bool initVideoPro(byte mode, byte dactype);
|
|
|
|
#ifdef OS2
|
|
word mtxVideoMode = mtxPASSTHRU;
|
|
#else
|
|
word mtxVideoMode;
|
|
#endif
|
|
|
|
long setTVP3026Freq ( volatile byte _Far *pDeviceParam, long fout, long reg, byte pWidth );
|
|
|
|
#ifndef __DDK_SRC__
|
|
extern dword BindingRC[NB_BOARD_MAX];
|
|
extern dword BindingCL[NB_BOARD_MAX];
|
|
#endif
|
|
|
|
#if( !defined(_WINDOWS_DLL16) && !defined(INIT_ONLY))
|
|
#ifndef OS2
|
|
dword _Far *BufBind;
|
|
SYSPARMS *sp;
|
|
|
|
#ifndef __DDK_SRC__
|
|
byte* CaddiInit(byte *InitBuf, byte *VideoBuf);
|
|
#else
|
|
byte* InitDDK(byte *InitBuf, byte *VideoBuf);
|
|
byte* ReInitDDK(byte *InitBuf, byte *VideoBuf);
|
|
#endif
|
|
|
|
|
|
void setTVP3026(volatile byte _Far *pDevice, long fout_voulue, long reg, word pWidth);
|
|
|
|
#endif
|
|
#endif
|
|
|
|
HwData Hw[NB_BOARD_MAX+1];
|
|
dword presentMclk[NB_BOARD_MAX+1] = {0}; /* MCLK currently in use */
|
|
dword Dst0, Dst1;
|
|
|
|
dword ProductMGA[NB_BOARD_MAX];
|
|
HwModeData *FirstMode[NB_BOARD_MAX];
|
|
|
|
byte InitBuf[NB_BOARD_MAX][INITBUF_S] = {0};
|
|
byte VideoBuf[NB_BOARD_MAX][VIDEOBUF_S] = {0};
|
|
extern dword crtcTab[NB_CRTC_PARAM];
|
|
extern vid vidtab[24];
|
|
char *mgainf = (char *)0;
|
|
|
|
/*** PROTOTYPES ***/
|
|
|
|
bool MapBoard(void);
|
|
static void overScan(void);
|
|
void UpdateHwModeTable (char *,HwModeData *,HwModeInterlace *,bool);
|
|
bool ProgrammeClock(byte Chip, dword Dst1, dword InfoDac);
|
|
extern dword getmgasel(void);
|
|
extern programme_reg_icd ( volatile byte _Far *pDevice, short reg, dword data );
|
|
#if 0
|
|
extern word detectVideoBoard(void);
|
|
#endif
|
|
|
|
void mtxMapVLBSpace();
|
|
bool mtxSetVLB(dword sel);
|
|
bool mtxIsVLBBios ();
|
|
void delay_us(dword delai);
|
|
|
|
#ifndef WINDOWS_NT
|
|
void setPciOptionReg();
|
|
#endif
|
|
|
|
#ifdef WINDOWS_NT
|
|
|
|
extern PUCHAR setmgasel(dword MgaSel, dword phyadr, dword limit);
|
|
extern PVOID AllocateSystemMemory(ULONG NumberOfBytes);
|
|
extern BOOLEAN bConflictDetected(ULONG ulAddressToVerify);
|
|
extern PUCHAR pciBiosCallAddr();
|
|
|
|
#else /* #ifdef WINDOWS_NT */
|
|
|
|
#ifdef OS2
|
|
extern volatile byte _Far *setmgasel(dword MgaSel, dword phyadr, word limit);
|
|
extern HWIsSelected(dword, dword , dword, dword, byte);
|
|
#else
|
|
extern volatile byte _Far *setmgasel(dword MgaSel, dword phyadr, dword limit);
|
|
#endif
|
|
|
|
#endif /* #ifdef WINDOWS_NT */
|
|
|
|
extern void GetMGAConfiguration(volatile byte _Far *pMgaBaseAddr,
|
|
dword *Dst0, dword *Dst1, dword *InfoHardware);
|
|
extern void MGASysInit(byte *);
|
|
|
|
#ifdef OS2
|
|
extern char *selectMgaInfoBoard();
|
|
#else
|
|
char *selectMgaInfoBoard();
|
|
#endif
|
|
|
|
extern bool loadVidPar(dword Zoom, HwModeData *HwMode, HwModeData *DisplayMode);
|
|
extern void calculCrtcParam(void);
|
|
extern void MoveToVideoBuffer(byte *vidtab, byte *crtcTab, byte *VideoBuf);
|
|
extern void MGAVidInit(byte *, byte *);
|
|
dword mtxGetMgaSel(void);
|
|
bool mtxLectureMgaInf(void);
|
|
bool InitHwStruct(byte CurBoard, HwModeData *pHwModeData, word sizeArray,
|
|
dword VramAvailable, dword DramAvailable);
|
|
extern char *mtxConvertMgaInf( char * );
|
|
|
|
|
|
#ifdef _WINDOWS_DLL16
|
|
extern void FAR *memalloc(dword size);
|
|
extern dword memfree(void FAR **mem);
|
|
extern void AdjustDBWindow(void);
|
|
#endif
|
|
|
|
|
|
#ifdef WINDOWS
|
|
dword ValMSec;
|
|
|
|
int _Far pascal LibMain(HANDLE hInstance, WORD wDataSeg, WORD wHeapSize, LPSTR lpszCmdLine)
|
|
{
|
|
if (wHeapSize > 0)
|
|
UnlockData(0);
|
|
|
|
return 1;
|
|
}
|
|
#endif
|
|
|
|
|
|
|
|
/*-----------------------------------------------------
|
|
* mtxCheckHwAll
|
|
*
|
|
* This function returns the pointer to an array of MGA
|
|
* hardware devices found in the system
|
|
*
|
|
* Return value:
|
|
* >0 = Pointer to HwData structure
|
|
* 0 = Error ; No MGA device found
|
|
*-----------------------------------------------------*/
|
|
|
|
HwData * mtxCheckHwAll(void)
|
|
{
|
|
dword TmpDword;
|
|
byte Board, TmpByte, DUB_SEL, ChipSet;
|
|
dword PcbRev, TitanRev, DubRev;
|
|
dword RamBanks;
|
|
dword InfoHardware;
|
|
void *pMgaInfo;
|
|
bool dacSupportHires;
|
|
|
|
#ifndef WINDOWS_NT
|
|
byte i;
|
|
|
|
// Modified for Windows NT:
|
|
// Since we can't open files in the kernel-mode driver, MGA.INF
|
|
// is read in the user-mode driver instead; so, prior to calling
|
|
// _mtxCheckHwAll, mgainf already points to MGA.INF data and
|
|
// all the MGA boards have been mapped already...so we don't have
|
|
// to call MapBoard or mtxLectureMgaInf here.
|
|
|
|
if (! CheckHwAllDone)
|
|
{
|
|
/*** Figure number of iteration in one tick (55 millisecond) ***/
|
|
#ifdef WINDOWS
|
|
{
|
|
dword _Far *tick = MAKELP(0x40, 0x6c);
|
|
dword t;
|
|
|
|
_asm{ pushf
|
|
sti } /* enable the interrupt because of a hang bug */
|
|
ValMSec = 0;
|
|
t = *tick + 1;
|
|
|
|
while(t > *tick);
|
|
|
|
t++;
|
|
while(t > *tick)
|
|
ValMSec++;
|
|
_asm popf
|
|
}
|
|
#endif
|
|
|
|
#ifdef PRINT_DEBUG
|
|
openDebugfFile("\\SXCIEXT.LOG");
|
|
debug_printf(" ---- Premier appel CheckHwAll\n");
|
|
#endif
|
|
|
|
if (! MapBoard())
|
|
{
|
|
#ifdef PRINT_DEBUG
|
|
debug_printf("MapBoard Fail\n");
|
|
#endif
|
|
return(mtxFAIL);
|
|
}
|
|
}
|
|
|
|
#ifdef PRINT_DEBUG
|
|
else
|
|
{
|
|
reOpenDebugfFile();
|
|
debug_printf(" ---- appel (pas le premier) CheckHwAll\n");
|
|
}
|
|
#endif
|
|
|
|
if (! mtxLectureMgaInf())
|
|
{
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("mtxLectureMgaInf Fail");
|
|
#endif
|
|
return(mtxFAIL);
|
|
}
|
|
|
|
#endif /* #ifndef WINDOWS_NT */
|
|
|
|
/* Initialize Hw[] structure for each board */
|
|
for (Board=0; Board<NbBoard; Board++)
|
|
{
|
|
|
|
#if ((!defined (WINDOWS_NT)) || (USE_DDC_CODE))
|
|
/*********** DDC COMPAQ CODE ****************/
|
|
|
|
if (NbBoard == 1)
|
|
if (ReportDDCcapabilities())
|
|
SupportDDC = (byte)ReadEdid();
|
|
|
|
/*********** DDC COMPAQ CODE ****************/
|
|
#endif
|
|
|
|
#ifdef PRINT_DEBUG
|
|
{
|
|
debug_printf("BOARD No %d\n", Board);
|
|
}
|
|
#endif
|
|
if (! mtxSelectHw(&Hw[Board]))
|
|
{
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("mtxSelectHw Fail");
|
|
#endif
|
|
return(mtxFAIL);
|
|
}
|
|
mtxMapVLBSpace();
|
|
pMgaInfo = selectMgaInfoBoard();
|
|
if (! pMgaInfo)
|
|
{
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("selectMgaInfoBoard Fail");
|
|
#endif
|
|
return(mtxFAIL);
|
|
}
|
|
|
|
/* Initialize according to Vgaen switch (strapping conf.) */
|
|
|
|
mgaReadDWORD(*(pMgaBaseAddr+TITAN_OFFSET+TITAN_CONFIG),TmpDword);
|
|
if (TmpDword&TITAN_VGAEN_M)
|
|
Hw[Board].VGAEnable = 1;
|
|
else
|
|
{
|
|
Hw[Board].VGAEnable = 0;
|
|
if (! CheckHwAllDone)
|
|
{
|
|
/*----- SoftReset (need for PCI IMPRSESSION+ with high freq --*/
|
|
mgaWriteDWORD(*(pMgaBaseAddr + TITAN_OFFSET + TITAN_RST), TITAN_SOFTRESET_SET);
|
|
delay_us(2);
|
|
mgaWriteDWORD(*(pMgaBaseAddr + TITAN_OFFSET + TITAN_RST), TITAN_SOFTRESET_CLR);
|
|
delay_us(2);
|
|
}
|
|
}
|
|
|
|
#if ((!defined (WINDOWS_NT)) || (USE_DDC_CODE))
|
|
/*********** DDC COMPAQ CODE ****************/
|
|
|
|
if (SupportDDC && Hw[0].VGAEnable)
|
|
Hw[0].PortCfg = 0x01;
|
|
|
|
if (SupportDDC && (!Hw[0].VGAEnable || mgainf != DefaultVidset))
|
|
SupportDDC = FALSE;
|
|
|
|
/*********** DDC COMPAQ CODE ****************/
|
|
#endif
|
|
|
|
if (TmpDword&0x00000001)
|
|
Hw[Board].Device8_16 = 1; /* mode 16-bit */
|
|
else
|
|
Hw[Board].Device8_16 = 0; /* mode 8-bit */
|
|
|
|
#ifdef WINDOWS_NT
|
|
if ((Hw[iBoard].pHwMode != NULL) &&
|
|
(NbBoard > 1))
|
|
{
|
|
// pHwMode has been initialized to NULL in MgaFindAdapter.
|
|
// If it's not NULL here, it means we've been here before.
|
|
// If we have more than one board, then InitHwStruct has allocated
|
|
// memory for pHwMode, and we'll release it here.
|
|
|
|
VideoPortReleaseBuffer(pMgaDeviceExtension, Hw[iBoard].pHwMode);
|
|
Hw[iBoard].pHwMode = NULL;
|
|
}
|
|
#endif
|
|
|
|
Hw[iBoard].pCurrentHwMode = NULL;
|
|
Hw[iBoard].pCurrentDisplayMode = NULL;
|
|
Hw[iBoard].CurrentZoomFactor = 0;
|
|
Hw[iBoard].CurrentXStart = 0;
|
|
Hw[iBoard].CurrentYStart = 0;
|
|
mtxSetVideoMode(mtxADV_MODE);
|
|
|
|
GetMGAConfiguration(pMgaBaseAddr, &Dst0, &Dst1, &InfoHardware);
|
|
|
|
#ifdef PRINT_DEBUG
|
|
{
|
|
debug_printf("DST0 = 0x%08lx, DST1 = 0x%08lx InfoHardware = 0x%x\n", Dst0, Dst1, InfoHardware);
|
|
}
|
|
#endif
|
|
|
|
/* Verify if DAC support resolution above 1280 */
|
|
dacSupportHires = !(Dst1 & TITAN_DST1_ABOVE1280_M); /* Test bit Above1280 */
|
|
|
|
Hw[Board].ProductType = (Dst0 & TITAN_DST0_PRODUCT_M) >> TITAN_DST0_PRODUCT_A;
|
|
|
|
PcbRev = (Dst0 & TITAN_DST0_PCBREV_M) >> TITAN_DST0_PCBREV_A;
|
|
|
|
mgaReadDWORD(*(pMgaBaseAddr+TITAN_OFFSET+TITAN_REV), TitanRev);
|
|
TitanRev = (TitanRev & 0x000000ff) << 4;
|
|
DubRev = 0 << 8;
|
|
|
|
if( ((TitanRev >> 4) & 0x0000000f) < ATHENA_CHIP)
|
|
PcbRev = 0xf - (PcbRev & 0xf); /* 4 bits for TITAN and ATLAS */
|
|
else
|
|
PcbRev = 7 - (PcbRev & 0x7); /* 3 bits for ATHENA */
|
|
|
|
Hw[Board].ProductRev = PcbRev+TitanRev+DubRev;
|
|
|
|
#if 0
|
|
/*** status presence of the VideoPro board ***/
|
|
if( detectVideoBoard() )
|
|
Hw[Board].ProductRev |= 0x1000; /* Set bit 12 to 1 */
|
|
else
|
|
Hw[Board].ProductRev &= 0xffffefff; /* Set bit 12 to 0 */
|
|
#endif
|
|
if( ((Hw[iBoard].ProductRev >> 4) & 0x0000000f) == ATHENA_CHIP)
|
|
{
|
|
|
|
/*------ Strap added for ATHENA ------------------------------*/
|
|
mgaReadDWORD(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_CONFIG), TmpDword);
|
|
|
|
|
|
/** BEN we add this condition to fix bug shift left **/
|
|
/* For Impression Lite we force regular operation */
|
|
if ((Dst1 & TITAN_DST1_ABOVE1280_M) && (Dst1 & TITAN_DST1_200MHZ_M) &&
|
|
((Hw[iBoard].ProductRev >> 4) & 0x0000000f) == ATHENA_CHIP )
|
|
{
|
|
TmpDword = TmpDword & 0xfffffffb; /* bit 2=0: Board supports regular (135MHz/170MHz) operation */
|
|
}
|
|
else
|
|
{
|
|
if((Dst1 & TITAN_DST1_200MHZ_M) >> TITAN_DST1_200MHZ_A)
|
|
TmpDword = TmpDword & 0xfffffffb; /* bit 2=0: Board supports regular (135MHz/170MHz) operation */
|
|
else
|
|
TmpDword = TmpDword | 0x00000004; /* bit 2=1: Board supports 200MHz operation */
|
|
}
|
|
|
|
mgaWriteDWORD(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_CONFIG), TmpDword);
|
|
|
|
if (
|
|
( (InfoHardware == Info_Dac_ViewPoint) ||
|
|
(InfoHardware == Info_Dac_TVP3026)
|
|
) &&
|
|
(TmpDword & 0x00000004)
|
|
) /* support 200MHz */
|
|
dacSupportHires = 1;
|
|
else
|
|
dacSupportHires = 0;
|
|
/*------ Strap added for ATHENA ------------------------------*/
|
|
|
|
/*** BEN I add this condition to prevent to program NOMUX for
|
|
board MGA-PCI/2+ and MGA-VLB/2+ because the bit NOMUX
|
|
is used to set the clock ***/
|
|
if (
|
|
(InfoHardware == Info_Dac_BT485) ||
|
|
(InfoHardware == Info_Dac_ATT2050) ||
|
|
(InfoHardware == Info_Dac_PX2085)
|
|
)
|
|
{
|
|
/*------ Strap added for ATHENA --------------------------*/
|
|
mgaReadDWORD(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_CONFIG), TmpDword);
|
|
|
|
if((Dst1 & TITAN_DST1_NOMUXES_M) >> TITAN_DST1_NOMUXES_A)
|
|
TmpDword = TmpDword & 0xffffffdf; /* bit 5=0: */
|
|
else
|
|
TmpDword = TmpDword | 0x00000020; /* bit 5=1: */
|
|
|
|
mgaWriteDWORD(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_CONFIG), TmpDword);
|
|
/*------ Strap added for ATHENA --------------------------*/
|
|
}
|
|
}
|
|
|
|
/*** BEN open issue */
|
|
Hw[Board].ShellRev = 0;
|
|
Hw[Board].BindingRev = BINDING_REV;
|
|
|
|
|
|
/*** ----- DUBIC PATCH Disable mouse IRQ and proceed ------ ***/
|
|
mgaWriteBYTE(*(pMgaBaseAddr + DUBIC_OFFSET + DUBIC_NDX_PTR), 0x08);
|
|
mgaReadBYTE(*(pMgaBaseAddr + DUBIC_OFFSET + DUBIC_DUB_SEL), DUB_SEL);
|
|
mgaWriteBYTE(*(pMgaBaseAddr + DUBIC_OFFSET + DUBIC_DUB_SEL), 0x00);
|
|
/*** ------------------------------------------------------ ***/
|
|
|
|
mgaWriteBYTE(*(pMgaBaseAddr+DUBIC_OFFSET + DUBIC_NDX_PTR), DUBIC_DUB_CTL2);
|
|
mgaReadBYTE(*(pMgaBaseAddr+DUBIC_OFFSET + DUBIC_DATA), TmpByte);
|
|
|
|
|
|
/*** ----- DUBIC PATCH ReEnable mouse IRQ ----------------- ***/
|
|
mgaWriteBYTE(*(pMgaBaseAddr + DUBIC_OFFSET + DUBIC_NDX_PTR), 0x08);
|
|
mgaWriteBYTE(*(pMgaBaseAddr + DUBIC_OFFSET + DUBIC_DUB_SEL), DUB_SEL);
|
|
/*** ------------------------------------------------------ ***/
|
|
|
|
Hw[Board].Sync = TmpByte & 0x1;
|
|
|
|
#if 0
|
|
mgaReadDWORD(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_OPMODE), TmpDword);
|
|
if (TmpDword & 0x00000100)
|
|
Hw[Board].PortCfg = 1; /* Mouse enable */
|
|
else if (TmpByte & 0x04)
|
|
Hw[Board].PortCfg = 2; /* Laser enable */
|
|
else
|
|
Hw[Board].PortCfg = 0; /* Port disable */
|
|
#endif
|
|
|
|
/* Interrupt number for the mouse or the laser port */
|
|
mgaReadBYTE(*(pMgaBaseAddr+DUBIC_OFFSET + DUBIC_DUB_SEL), TmpByte);
|
|
TmpByte = (TmpByte & 0x18) >> 3;
|
|
switch (TmpByte)
|
|
{
|
|
case 0:
|
|
Hw[Board].PortIRQ = (byte)-1;
|
|
break;
|
|
case 1:
|
|
Hw[Board].PortIRQ = 3;
|
|
break;
|
|
case 2:
|
|
Hw[Board].PortIRQ = 4;
|
|
break;
|
|
case 3:
|
|
Hw[Board].PortIRQ = 5;
|
|
break;
|
|
}
|
|
|
|
mgaReadDWORD(*(pMgaBaseAddr+TITAN_OFFSET+TITAN_OPMODE),TmpDword);
|
|
if (TmpDword & TITAN_MOUSEMAP_M)
|
|
Hw[Board].MouseMap = 0x238;
|
|
else
|
|
Hw[Board].MouseMap = 0x23c;
|
|
|
|
mgaReadBYTE(*(pMgaBaseAddr+DUBIC_OFFSET + DUBIC_DUB_SEL), TmpByte);
|
|
TmpByte = (TmpByte & 0x70) >> 5;
|
|
switch (TmpByte)
|
|
{
|
|
case 0:
|
|
Hw[Board].MouseIRate = 0;
|
|
break;
|
|
case 1:
|
|
Hw[Board].MouseIRate = 25;
|
|
break;
|
|
case 2:
|
|
Hw[Board].MouseIRate = 50;
|
|
break;
|
|
case 3:
|
|
Hw[Board].MouseIRate = 100;
|
|
break;
|
|
case 4:
|
|
Hw[Board].MouseIRate = 200;
|
|
break;
|
|
}
|
|
|
|
|
|
/*Hw[Board].DacType = InfoHardware & 0x00000003; */
|
|
|
|
/*** BEN Temporary translate code ***/
|
|
#if 0
|
|
/*VIDEOPRO*/
|
|
VAFCconnector = 0;
|
|
#endif
|
|
switch(InfoHardware)
|
|
{
|
|
case Info_Dac_BT481:
|
|
case Info_Dac_BT482:
|
|
Hw[Board].DacType = BT482;
|
|
break;
|
|
|
|
case Info_Dac_Sierra:
|
|
Hw[Board].DacType = SIERRA;
|
|
break;
|
|
|
|
case Info_Dac_ViewPoint:
|
|
Hw[Board].DacType = VIEWPOINT;
|
|
break;
|
|
|
|
case Info_Dac_TVP3026:
|
|
Hw[Board].DacType = TVP3026;
|
|
break;
|
|
|
|
case Info_Dac_BT484:
|
|
Hw[Board].DacType = BT484;
|
|
break;
|
|
|
|
case Info_Dac_BT485:
|
|
case Info_Dac_ATT2050:
|
|
Hw[Board].DacType = BT485;
|
|
break;
|
|
|
|
case Info_Dac_Chameleon:
|
|
Hw[Board].DacType = CHAMELEON;
|
|
break;
|
|
|
|
case Info_Dac_PX2085:
|
|
#if 0
|
|
/*VIDEOPRO*/
|
|
VAFCconnector = 1;
|
|
#endif
|
|
#ifndef WINDOWS_NT
|
|
Hw[Board].DacType = BT485;
|
|
#else
|
|
Hw[Board].DacType = PX2085;
|
|
#endif /* #ifndef WINDOWS_NT */
|
|
|
|
break;
|
|
|
|
default:
|
|
return(mtxFAIL);
|
|
}
|
|
|
|
#ifdef PRINT_DEBUG
|
|
{
|
|
debug_printf("Dactype[%d] = %x\n", Board, Hw[Board].DacType);
|
|
}
|
|
#endif
|
|
|
|
/*** Cursor info init ***/
|
|
switch(Hw[Board].DacType)
|
|
{
|
|
case BT482:
|
|
Hw[Board].cursorInfo.MaxWidth = 32;
|
|
Hw[Board].cursorInfo.MaxHeight = 32;
|
|
Hw[Board].cursorInfo.MaxDepth = 2;
|
|
Hw[Board].cursorInfo.MaxColors = 2;
|
|
break;
|
|
|
|
case BT485:
|
|
case PX2085:
|
|
case VIEWPOINT:
|
|
Hw[Board].cursorInfo.MaxWidth = 64;
|
|
Hw[Board].cursorInfo.MaxHeight = 64;
|
|
Hw[Board].cursorInfo.MaxDepth = 2;
|
|
Hw[Board].cursorInfo.MaxColors = 2;
|
|
break;
|
|
|
|
case TVP3026:
|
|
Hw[Board].cursorInfo.MaxWidth = 64;
|
|
Hw[Board].cursorInfo.MaxHeight = 64;
|
|
Hw[Board].cursorInfo.MaxDepth = 2;
|
|
Hw[Board].cursorInfo.MaxColors = 3;
|
|
break;
|
|
|
|
default:
|
|
Hw[Board].cursorInfo.MaxWidth = 0;
|
|
Hw[Board].cursorInfo.MaxHeight = 0;
|
|
Hw[Board].cursorInfo.MaxDepth = 0;
|
|
Hw[Board].cursorInfo.MaxColors = 0;
|
|
break;
|
|
|
|
}
|
|
|
|
Hw[Board].cursorInfo.CurWidth = 0;
|
|
Hw[Board].cursorInfo.CurHeight = 0;
|
|
Hw[Board].cursorInfo.HotSX = 0;
|
|
Hw[Board].cursorInfo.HotSY = 0;
|
|
|
|
|
|
|
|
/* Form Rambank value */
|
|
RamBanks = ((Dst1 & TITAN_DST1_RAMBANK_M) << 8L) |
|
|
((Dst0 & 0xfe000000) >> 24L) |
|
|
((Dst1 & TITAN_DST1_RAMBANK0_M) >> TITAN_DST1_RAMBANK0_A);
|
|
|
|
|
|
/*** Check the ZTAG bit ***/
|
|
if (RamBanks & (dword)0x40)
|
|
*((byte*) (InitBuf[Board] + INITBUF_ZTagFlag)) = TRUE;
|
|
else
|
|
*((byte*) (InitBuf[Board] + INITBUF_ZTagFlag)) = FALSE;
|
|
|
|
RamBanks = RamBanks & 0x1bf; /* Mask le ZTAG et bits dont care */
|
|
|
|
#ifdef PRINT_DEBUG
|
|
{
|
|
debug_printf("RamBank = %x\n", RamBanks);
|
|
}
|
|
#endif
|
|
|
|
switch((Hw[iBoard].ProductRev >> 4) & 0x0000000f)
|
|
{
|
|
case TITAN_CHIP:
|
|
ChipSet = TITAN_CHIP;
|
|
break;
|
|
|
|
case ATLAS_CHIP:
|
|
ChipSet = ATLAS_CHIP;
|
|
|
|
/* Check if VLB2 board */
|
|
mgaReadDWORD(*(pMgaBaseAddr+0x2000),TmpDword);
|
|
if (TmpDword == (dword)0x0518102b) /* ID Matrox */
|
|
mgaWriteBYTE(*(pMgaBaseAddr+0x2040),0x01); /* Program option reg */
|
|
#ifndef WINDOWS_NT
|
|
else /* PCI bus */
|
|
/* If PCI disable PCI posted write feature
|
|
if system use Ares chipset */
|
|
disPostedWFeature();
|
|
break;
|
|
#endif /* #ifndef WINDOWS_NT */
|
|
|
|
case ATHENA_CHIP:
|
|
ChipSet = ATHENA_CHIP;
|
|
|
|
/*** BEN se programme maintenant par le clock synthetiser ***/
|
|
/* Check if VLB2 board */
|
|
mgaReadDWORD(*(pMgaBaseAddr+0x2000),TmpDword);
|
|
if (TmpDword == (dword)0x0518102b) /* ID Matrox */
|
|
mgaWriteBYTE(*(pMgaBaseAddr+0x2040),0x01); /* Program option reg */
|
|
break;
|
|
}
|
|
|
|
/*** Define ProductMGA ***/
|
|
|
|
if (RamBanks == (dword)0x001 && ChipSet == TITAN_CHIP)
|
|
ProductMGA[Board] = MGA_ULT_1M;
|
|
|
|
else if (RamBanks == (dword)0x004 && ChipSet == TITAN_CHIP)
|
|
ProductMGA[Board] = MGA_ULT_2M;
|
|
|
|
else if (RamBanks == (dword)0x005 && ChipSet == TITAN_CHIP)
|
|
ProductMGA[Board] = MGA_IMP_3M;
|
|
|
|
else if (RamBanks == (dword)0x025 && ChipSet == TITAN_CHIP)
|
|
ProductMGA[Board] = MGA_IMP_3M_Z;
|
|
|
|
else if (RamBanks == (dword)0x09C && ChipSet == TITAN_CHIP)
|
|
ProductMGA[Board] = MGA_PRO_4M5;
|
|
|
|
else if (RamBanks == (dword)0x13C && ChipSet == TITAN_CHIP)
|
|
ProductMGA[Board] = MGA_PRO_4M5_Z;
|
|
|
|
else if (RamBanks == (dword)0x004 && (ChipSet == ATLAS_CHIP || ChipSet == ATHENA_CHIP))
|
|
ProductMGA[Board] = MGA_PCI_2M;
|
|
|
|
else if (RamBanks == (dword)0x005 && (ChipSet == ATLAS_CHIP || ChipSet == ATHENA_CHIP))
|
|
ProductMGA[Board] = MGA_PCI_4M;
|
|
|
|
else
|
|
{
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("RamBanks Inconnue");
|
|
#endif
|
|
return(mtxFAIL);
|
|
}
|
|
|
|
/*** Define Product type for external use ***/
|
|
if( ChipSet == TITAN_CHIP )
|
|
{
|
|
if( ProductMGA[Board]==MGA_ULT_1M || ProductMGA[Board]==MGA_ULT_2M )
|
|
Hw[Board].ProductType |= (dword)MGA_ULTIMA<<16;
|
|
|
|
else if( ProductMGA[Board]==MGA_PRO_4M5 || ProductMGA[Board]==MGA_PRO_4M5_Z )
|
|
Hw[Board].ProductType |= (dword)MGA_IMPRESSION_PRO<<16;
|
|
|
|
else
|
|
Hw[Board].ProductType |= (dword)MGA_IMPRESSION<<16;
|
|
}
|
|
else if( ChipSet == ATLAS_CHIP )
|
|
{
|
|
if( InfoHardware == Info_Dac_PX2085 )
|
|
Hw[Board].ProductType |= (dword)MGA_ULTIMA_VAFC<<16;
|
|
|
|
else if( (Dst1 & TITAN_DST1_200MHZ_M) && !(Dst1 & TITAN_DST1_ABOVE1280_M))
|
|
Hw[Board].ProductType |= (dword)MGA_ULTIMA_PLUS_200<<16;
|
|
|
|
else if( InfoHardware == Info_Dac_ViewPoint )
|
|
Hw[Board].ProductType |= (dword)MGA_ULTIMA_PLUS<<16;
|
|
|
|
else
|
|
Hw[Board].ProductType |= (dword)MGA_ULTIMA<<16;
|
|
|
|
}
|
|
else /* Athena */
|
|
{
|
|
if ((Dst1 & TITAN_DST1_ABOVE1280_M) && (Dst1 & TITAN_DST1_200MHZ_M))
|
|
Hw[Board].ProductType |= (dword)MGA_IMPRESSION_LTE<<16;
|
|
|
|
else if( InfoHardware == Info_Dac_TVP3026)
|
|
Hw[Board].ProductType |= (dword)MGA_IMPRESSION_PLUS<<16;
|
|
|
|
else if( InfoHardware == Info_Dac_ViewPoint )
|
|
Hw[Board].ProductType |= (dword)MGA_ULTIMA_PLUS<<16;
|
|
|
|
else
|
|
Hw[Board].ProductType |= (dword)MGA_ULTIMA<<16;
|
|
|
|
}
|
|
|
|
#ifdef PRINT_DEBUG
|
|
{
|
|
debug_printf("ProductMGA[%d] = %x\n", Board, ProductMGA[Board]);
|
|
}
|
|
#endif
|
|
|
|
if(! ProgrammeClock(ChipSet, Dst1, InfoHardware))
|
|
return(mtxFAIL);
|
|
|
|
switch (ProductMGA[Board])
|
|
{
|
|
case MGA_ULT_1M:
|
|
if(!(InitHwStruct(Board, HwModesFBM_000_A,
|
|
sizeof(HwModesFBM_000_A), 1048576, 0)))
|
|
{
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("MGA_ULT_1M : InitHwStruct Fail");
|
|
#endif
|
|
return(mtxFAIL);
|
|
}
|
|
UpdateHwModeTable (pMgaInfo, FirstMode[Board],
|
|
iHwModesFBM_000_A, dacSupportHires);
|
|
break;
|
|
|
|
case MGA_ULT_2M:
|
|
if(!(InitHwStruct(Board, HwModesFBM_010_A,
|
|
sizeof(HwModesFBM_010_A), 2097152, 0)))
|
|
{
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("MGA_ULT_2M : InitHwStruct Fail");
|
|
#endif
|
|
return(mtxFAIL);
|
|
}
|
|
UpdateHwModeTable (pMgaInfo, FirstMode[Board],
|
|
iHwModesFBM_010_A, dacSupportHires);
|
|
break;
|
|
|
|
case MGA_IMP_3M:
|
|
if(!(InitHwStruct(Board, HwModesFBM_010_B,
|
|
sizeof(HwModesFBM_010_B), 3145728, 0)))
|
|
{
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("MGA_IMP_3M : InitHwStruct Fail");
|
|
#endif
|
|
return(mtxFAIL);
|
|
}
|
|
UpdateHwModeTable (pMgaInfo, FirstMode[Board],
|
|
iHwModesFBM_010_B, dacSupportHires);
|
|
break;
|
|
|
|
case MGA_IMP_3M_Z:
|
|
if(!(InitHwStruct(Board, HwModesFBM_011_A,
|
|
sizeof(HwModesFBM_011_A), 3145728, 2097152)))
|
|
{
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("MGA_IMP_3M_Z : InitHwStruct Fail");
|
|
#endif
|
|
return(mtxFAIL);
|
|
}
|
|
UpdateHwModeTable (pMgaInfo, FirstMode[Board],
|
|
iHwModesFBM_011_A, dacSupportHires);
|
|
break;
|
|
|
|
case MGA_PRO_4M5:
|
|
if(!(InitHwStruct(Board, HwModesFBM_101_B,
|
|
sizeof(HwModesFBM_101_B), 4718592, 0)))
|
|
{
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("MGA_PRO_4M5 : InitHwStruct Fail");
|
|
#endif
|
|
return(mtxFAIL);
|
|
}
|
|
UpdateHwModeTable (pMgaInfo, FirstMode[Board],
|
|
iHwModesFBM_101_B, dacSupportHires);
|
|
break;
|
|
|
|
case MGA_PRO_4M5_Z:
|
|
if(!(InitHwStruct(Board, HwModesFBM_111_A,
|
|
sizeof(HwModesFBM_111_A), 4718592, 4194304)))
|
|
{
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("MGA_PRO_4M5_Z : InitHwStruct Fail");
|
|
#endif
|
|
return(mtxFAIL);
|
|
}
|
|
UpdateHwModeTable (pMgaInfo, FirstMode[Board],
|
|
iHwModesFBM_111_A, dacSupportHires);
|
|
break;
|
|
|
|
case MGA_PCI_2M:
|
|
if(!(InitHwStruct(Board, ModesAth2,
|
|
sizeof(ModesAth2), 2097152, 0)))
|
|
return(mtxFAIL);
|
|
UpdateHwModeTable (pMgaInfo, FirstMode[Board], iModesAth2,
|
|
dacSupportHires);
|
|
break;
|
|
|
|
case MGA_PCI_4M:
|
|
if(!(InitHwStruct(Board, ModesAth4,
|
|
sizeof(ModesAth4), 4194304, 0)))
|
|
return(mtxFAIL);
|
|
UpdateHwModeTable (pMgaInfo, FirstMode[Board], iModesAth4,
|
|
dacSupportHires);
|
|
break;
|
|
|
|
default:
|
|
{
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("Produit Inconnue");
|
|
#endif
|
|
return(mtxFAIL);
|
|
}
|
|
}
|
|
|
|
if (Hw[Board].VGAEnable == 1)
|
|
mtxSetVideoMode(mtxVGA);
|
|
|
|
#ifdef WINDOWS_NT
|
|
// Do not free this now, since we do not use setmgasel in mtxSelectHw.
|
|
// VideoPortFreeDeviceBase(pMgaDeviceExtension, pMgaBaseAddr);
|
|
#endif
|
|
} /*** for loop Board... ***/
|
|
|
|
/* Set the OPTION register for ATLAS PCI */
|
|
#ifndef WINDOWS_NT
|
|
setPciOptionReg();
|
|
#endif
|
|
|
|
/* Indicates end of array */
|
|
Hw[Board].MapAddress = (dword)-1;
|
|
|
|
/* Default initialisation */
|
|
Hw[iBoard].pCurrentDisplayMode = Hw[iBoard].pCurrentHwMode;
|
|
|
|
#if( !defined( _WINDOWS_DLL16) && !defined(OS2) && !defined(INIT_ONLY))
|
|
#ifndef WINDOWS_NT
|
|
|
|
if (! CheckHwAllDone)
|
|
{
|
|
/* Allocate a static buffer for the command (C-Binding -> CADDI) */
|
|
#ifndef __DDK_SRC__
|
|
BufBind = mtxAllocBuffer(BUF_BIND_SIZE);
|
|
#endif
|
|
/* Allocate a static RC and a clip list for each MGA device */
|
|
for (i=0; Hw[i].MapAddress != (dword)-1 ; i++)
|
|
{
|
|
if (! mtxSelectHw(&Hw[i]))
|
|
{
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("mtxSelectHw(&Hw[]) == 0\n");
|
|
#endif
|
|
return(mtxFAIL);
|
|
}
|
|
#ifndef __DDK_SRC__
|
|
BindingRC[i] = (dword)NULL;
|
|
/***
|
|
*** _tDDK_STATE needs to be NULL'ed here if you want the DDK
|
|
*** to behave exactly like the SDK
|
|
***/
|
|
#endif
|
|
if (!mtxSelectHwMode(Hw[iBoard].pCurrentHwMode))
|
|
{
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("mtxSelectHwMode(Hw[].pCurrentHwMode == 0");
|
|
#endif
|
|
return(mtxFAIL);
|
|
}
|
|
|
|
#ifndef __DDK_SRC__
|
|
BindingRC[i] = (dword)mtxAllocRC(NULL);
|
|
BindingCL[i] = (dword)mtxAllocCL(1);
|
|
#endif
|
|
mtxSetVideoMode(mtxVGA);
|
|
}
|
|
}
|
|
|
|
#endif /* #ifndef WINDOWS_NT */
|
|
#endif /* #if( !defined( _WINDOWS_DLL16) && !defined(OS2))... */
|
|
|
|
CheckHwAllDone = TRUE;
|
|
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("Sortie Ok CheckHwAll");
|
|
#endif
|
|
return(&Hw[0]);
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/*------------------------------------------------
|
|
* mtxSelectHw
|
|
*
|
|
* Select the MGA device to be used for subsequent
|
|
* drawing operations
|
|
*
|
|
* Return:
|
|
* mtxOK : Hardware select successful
|
|
* mtxFAIL : Hardware select failure
|
|
*------------------------------------------------*/
|
|
|
|
bool mtxSelectHw(HwData *pHardware)
|
|
{
|
|
HwData *pScanHwData;
|
|
bool FlagFoundHwData;
|
|
|
|
|
|
/*** VALIDATE pHardware and set iBoard ***/
|
|
|
|
FlagFoundHwData = FALSE;
|
|
iBoard = 0;
|
|
|
|
for (pScanHwData = &Hw[0]; pScanHwData->MapAddress != (dword)-1;
|
|
pScanHwData++, iBoard++)
|
|
{
|
|
if (pScanHwData == pHardware)
|
|
{
|
|
FlagFoundHwData = TRUE;
|
|
break;
|
|
}
|
|
}
|
|
|
|
if (! FlagFoundHwData)
|
|
return(mtxFAIL);
|
|
|
|
#ifdef WINDOWS_NT
|
|
pMgaBaseAddr = Hw[iBoard].BaseAddress;
|
|
#else
|
|
pMgaBaseAddr = setmgasel(MgaSel, Hw[iBoard].MapAddress, 4);
|
|
#endif
|
|
|
|
#ifdef OS2
|
|
HWIsSelected(ProductMGA[iBoard], Hw[iBoard].ProductType,
|
|
Hw[iBoard].ProductRev, Hw[iBoard].MapAddress, Hw[iBoard].DacType);
|
|
#endif
|
|
|
|
#if( !defined(WINDOWS) && !defined(OS2) && !defined(WINDOWS_NT) && !defined(INIT_ONLY))
|
|
#ifndef __DDK_SRC__
|
|
CaddiReInit(InitBuf[iBoard], VideoBuf[iBoard]);
|
|
#else
|
|
ReInitDDK(InitBuf[iBoard], VideoBuf[iBoard]);
|
|
#endif
|
|
#endif
|
|
|
|
return(mtxOK);
|
|
}
|
|
|
|
|
|
|
|
/*------------------------------------------------------
|
|
* mtxGetHwModes
|
|
*
|
|
* This function returns a pointer to a list of hardware
|
|
* modes available for the current MGA device
|
|
* as selected by mtxSelectHw()
|
|
*
|
|
* Return:
|
|
* HwModes = 0 : MGA device not found
|
|
* HwModes != 0 : Pointer to HwModes array
|
|
*------------------------------------------------------*/
|
|
|
|
HwModeData *mtxGetHwModes(void)
|
|
{
|
|
if (NbBoard == 0)
|
|
return(0);
|
|
return(FirstMode[iBoard]);
|
|
}
|
|
|
|
|
|
/*------------------------------------------------------
|
|
* mtxGetRefreshRates
|
|
*
|
|
* This function returns a word that contains a bit field
|
|
* of possible frequency for a specific resolution and
|
|
* pixel depth.
|
|
*
|
|
* Return:
|
|
*------------------------------------------------------*/
|
|
|
|
word mtxGetRefreshRates(HwModeData *pHwModeSelect)
|
|
{
|
|
word FreqRes,i;
|
|
|
|
for (FreqRes = 0,i = 0; ResParam[i].DispWidth != (word) -1; i++)
|
|
{
|
|
if ((ResParam[i].DispWidth == pHwModeSelect->DispWidth) && (ResParam[i].PixDepth == pHwModeSelect->PixWidth))
|
|
{
|
|
switch (ResParam[i].RefreshRate)
|
|
{
|
|
// bit 0: 43 Hz interlaced
|
|
// bit 1: 56 Hz
|
|
// bit 2: 60 Hz
|
|
// bit 3: 66 Hz
|
|
// bit 4: 70 Hz
|
|
// bit 5: 72 Hz
|
|
// bit 6: 75 Hz
|
|
// bit 7: 76 Hz
|
|
// bit 8: 80 Hz
|
|
// bit 9: 85 Hz
|
|
// bit 10: 90 Hz
|
|
// bit 11: 100 Hz
|
|
// bit 12: 120 Hz
|
|
|
|
case 43:
|
|
FreqRes |= 0x0001;
|
|
break;
|
|
case 56:
|
|
FreqRes |= 0x0002;
|
|
break;
|
|
case 60:
|
|
FreqRes |= 0x0004;
|
|
break;
|
|
case 66:
|
|
FreqRes |= 0x0008;
|
|
break;
|
|
case 70:
|
|
FreqRes |= 0x0010;
|
|
break;
|
|
case 72:
|
|
FreqRes |= 0x0020;
|
|
break;
|
|
case 75:
|
|
FreqRes |= 0x0040;
|
|
break;
|
|
case 76:
|
|
FreqRes |= 0x0080;
|
|
break;
|
|
case 80:
|
|
FreqRes |= 0x0100;
|
|
break;
|
|
case 85:
|
|
FreqRes |= 0x0200;
|
|
break;
|
|
case 90:
|
|
FreqRes |= 0x0400;
|
|
break;
|
|
case 100:
|
|
FreqRes |= 0x0800;
|
|
break;
|
|
case 120:
|
|
FreqRes |= 0x1000;
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
return(FreqRes);
|
|
}
|
|
|
|
/*----------------------------------------------------------
|
|
* mtxSelectHwMode
|
|
*
|
|
* Select from the list of available hardware modes returned
|
|
* by mtxGetHwModes()
|
|
*
|
|
* Return:
|
|
* mtxOK : HwMode select successfull
|
|
* mtxFAIL : HwMode select failure
|
|
*
|
|
*----------------------------------------------------------*/
|
|
|
|
bool mtxSelectHwMode(HwModeData *pHwModeSelect)
|
|
{
|
|
bool FlagFindMode;
|
|
byte TmpByte;
|
|
HwModeData *pScanHwMode;
|
|
general_info *generalInfo;
|
|
dword DST0, DST1, Info;
|
|
|
|
generalInfo = (general_info *)selectMgaInfoBoard();
|
|
|
|
FlagFindMode = FALSE;
|
|
|
|
for ( pScanHwMode = FirstMode[iBoard]; pScanHwMode->DispWidth != (word)-1;
|
|
pScanHwMode++)
|
|
{
|
|
if (pScanHwMode == pHwModeSelect)
|
|
{
|
|
FlagFindMode = TRUE;
|
|
break;
|
|
}
|
|
}
|
|
|
|
if (NbBoard == 0 || FlagFindMode == FALSE)
|
|
return(mtxFAIL);
|
|
|
|
Hw[iBoard].pCurrentHwMode = NULL;
|
|
Hw[iBoard].pCurrentDisplayMode = NULL;
|
|
mtxSetVideoMode(mtxADV_MODE);
|
|
|
|
Hw[iBoard].pCurrentHwMode = pHwModeSelect;
|
|
|
|
if(pHwModeSelect->DispType & 0x04) /* LUT mode */
|
|
{
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_LUTMode)) = TRUE;
|
|
}
|
|
else
|
|
{
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_LUTMode)) = FALSE;
|
|
}
|
|
|
|
/* Initialize a init buffer for CADDI */
|
|
if (pHwModeSelect->PixWidth == 24) /* PACK PIXEL */
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_PWidth)) = 0x12;
|
|
else
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_PWidth)) =
|
|
pHwModeSelect->PixWidth >> 4;
|
|
|
|
*((word*) (InitBuf[iBoard] + INITBUF_ScreenWidth)) =
|
|
pHwModeSelect->FbPitch;
|
|
*((word*) (InitBuf[iBoard] + INITBUF_ScreenHeight)) =
|
|
pHwModeSelect->DispHeight;
|
|
|
|
#ifdef WINDOWS_NT
|
|
*((UINT_PTR*)(InitBuf[iBoard] + INITBUF_MgaOffset)) = (UINT_PTR)pMgaBaseAddr;
|
|
#else
|
|
#ifdef __WATCOMC__
|
|
#ifdef __WATCOM_PHAR__ /* Watcom & Phar Lap */
|
|
*((dword*)(InitBuf[iBoard] + INITBUF_MgaOffset)) = 0;
|
|
#else /* Watcom & Rational */
|
|
*((dword*)(InitBuf[iBoard] + INITBUF_MgaOffset)) = (dword)pMgaBaseAddr;;
|
|
#endif
|
|
#elif __MICROSOFTC600__
|
|
*((dword*)(InitBuf[iBoard] + INITBUF_MgaOffset)) = (dword)pMgaBaseAddr;;
|
|
#else /* High C & Phar Lap */
|
|
*((dword*)(InitBuf[iBoard] + INITBUF_MgaOffset)) = 0;
|
|
#endif
|
|
*((word*) (InitBuf[iBoard] + INITBUF_MgaSegment)) = MgaSel >> 16;
|
|
#endif /* #ifdef WINDOWS_NT */
|
|
|
|
/* Default setting */
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_ZBufferFlag)) = FALSE;
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_ZinDRAMFlag)) = FALSE;
|
|
*((dword*)(InitBuf[iBoard] + INITBUF_ZBufferHwAddr)) = 0;
|
|
|
|
switch(generalInfo->BitOperation8_16)
|
|
{
|
|
case BIT8:
|
|
*((byte*)(InitBuf[iBoard] + INITBUF_16)) = 2;
|
|
break;
|
|
|
|
case BIT16:
|
|
*((byte*)(InitBuf[iBoard] + INITBUF_16)) = 1;
|
|
break;
|
|
|
|
case BITNARROW16:
|
|
*((byte*)(InitBuf[iBoard] + INITBUF_16)) = 3;
|
|
break;
|
|
|
|
default:
|
|
*((byte*)(InitBuf[iBoard] + INITBUF_16)) = 0;
|
|
break;
|
|
}
|
|
|
|
/* If on top of VGA, we must program in 16bit narrow absolutely */
|
|
|
|
if ((Hw[iBoard].ProductType & BOARD_MGA_VL_M) == BOARD_MGA_VL)
|
|
{
|
|
*((byte*)(InitBuf[iBoard] + INITBUF_16)) = 2; /* 8-bit mode */
|
|
}
|
|
else
|
|
{
|
|
if (Hw[iBoard].MapAddress == MGA_ISA_BASE_1)
|
|
*((byte*)(InitBuf[iBoard] + INITBUF_16)) = 1;
|
|
}
|
|
|
|
/* Transfer DMA informations from mga.inf */
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_DMAEnable)) = (byte)generalInfo->DmaEnable;
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_DMAChannel)) = (byte)generalInfo->DmaChannel;
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_DMAType)) = (byte)generalInfo->DmaType;
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_DMAXferWidth)) = (byte)generalInfo->DmaXferWidth;
|
|
|
|
/* Special case for MGA_IMP_3M_Z at 1024x768x32: we act like an MGA_IMP_3M */
|
|
if (ProductMGA[iBoard] == MGA_IMP_3M_Z &&
|
|
pHwModeSelect->DispWidth == 1024 &&
|
|
pHwModeSelect->PixWidth == 32)
|
|
{
|
|
ProductMGA[iBoard] = MGA_IMP_3M;
|
|
SpecialModeOn = TRUE;
|
|
}
|
|
|
|
/* Reset to the real value of FBM when the flag is on and this is not the
|
|
special mode */
|
|
if (SpecialModeOn == TRUE && (pHwModeSelect->DispWidth != 1024 ||
|
|
pHwModeSelect->PixWidth != 32))
|
|
{
|
|
ProductMGA[iBoard] = MGA_IMP_3M_Z;
|
|
SpecialModeOn = FALSE;
|
|
}
|
|
|
|
switch (ProductMGA[iBoard])
|
|
{
|
|
case MGA_ULT_1M:
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_FBM)) = 0;
|
|
break;
|
|
|
|
case MGA_ULT_2M:
|
|
case MGA_IMP_3M:
|
|
case MGA_PCI_4M:
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_FBM)) = 2;
|
|
break;
|
|
|
|
case MGA_IMP_3M_Z:
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_FBM)) = 3;
|
|
break;
|
|
|
|
case MGA_PRO_4M5:
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_FBM)) = 5;
|
|
break;
|
|
|
|
case MGA_PRO_4M5_Z:
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_FBM)) = 7;
|
|
break;
|
|
|
|
case MGA_PCI_2M:
|
|
if (pHwModeSelect->ZBuffer)
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_FBM)) = 10;
|
|
else
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_FBM)) = 2;
|
|
break;
|
|
|
|
default:
|
|
return(mtxFAIL);
|
|
}
|
|
|
|
if (pHwModeSelect->ZBuffer)
|
|
{
|
|
switch (ProductMGA[iBoard])
|
|
{
|
|
case MGA_IMP_3M: /* We can do Z-buffer in VRAM */
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_ZBufferFlag)) = TRUE;
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_ZinDRAMFlag)) = FALSE;
|
|
*((dword*)(InitBuf[iBoard] + INITBUF_ZBufferHwAddr)) =
|
|
0x200000;
|
|
break;
|
|
|
|
case MGA_IMP_3M_Z:
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_ZBufferFlag)) = TRUE;
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_ZinDRAMFlag)) = TRUE;
|
|
*((dword*)(InitBuf[iBoard] + INITBUF_ZBufferHwAddr)) =
|
|
0x400000;
|
|
break;
|
|
|
|
case MGA_PRO_4M5_Z:
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_ZBufferFlag)) = TRUE;
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_ZinDRAMFlag)) = TRUE;
|
|
*((dword*)(InitBuf[iBoard] + INITBUF_ZBufferHwAddr)) =
|
|
0x600000;
|
|
break;
|
|
|
|
case MGA_PCI_4M:
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_ZBufferFlag)) = TRUE;
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_ZinDRAMFlag)) = FALSE;
|
|
*((dword*)(InitBuf[iBoard] + INITBUF_ZBufferHwAddr)) =
|
|
0x200000;
|
|
break;
|
|
|
|
case MGA_PCI_2M:
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_ZBufferFlag)) = TRUE;
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_ZinDRAMFlag)) = FALSE;
|
|
*((dword*)(InitBuf[iBoard] + INITBUF_ZBufferHwAddr)) =
|
|
0x100000;
|
|
break;
|
|
}
|
|
}
|
|
|
|
/* This blank is used before setting TITAN_FBM bit */
|
|
/* (done in GetMGAConfiguration and MGASysInit) */
|
|
/* Blank the screen */
|
|
mgaWriteBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_SEQ_ADDR), 0x01);
|
|
mgaReadBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_SEQ_DATA), TmpByte);
|
|
TmpByte |= 0x20; /* screen off */
|
|
mgaWriteBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_SEQ_DATA), TmpByte);
|
|
|
|
GetMGAConfiguration(pMgaBaseAddr, &DST0, &DST1, &Info);
|
|
|
|
*((dword*) (InitBuf[iBoard] + INITBUF_DST0)) = DST0;
|
|
*((dword*) (InitBuf[iBoard] + INITBUF_DST1)) = DST1;
|
|
*((dword*) (InitBuf[iBoard] + INITBUF_DACType)) = Info;
|
|
|
|
/** Default setting **/
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_DB_SideSide)) = FALSE;
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_DB_FrontBack)) = FALSE;
|
|
|
|
/*** CALCULATION OF YDSTORG FOR MGA_PCI_4M ***/
|
|
if (ProductMGA[iBoard] == MGA_PCI_4M)
|
|
{
|
|
{
|
|
dword NbBytes, PixelTransit, lines, offset;
|
|
dword Width, Height, PixelWidth, FbPitch;
|
|
|
|
if (pHwModeSelect->PixWidth == 24) /* PACK PIXEL */
|
|
{
|
|
Width = (dword)((pHwModeSelect->DispWidth * 3) >> 2);
|
|
FbPitch = (dword)(pHwModeSelect->FbPitch * 3) >> 2;
|
|
PixelWidth = 4;
|
|
}
|
|
else
|
|
{
|
|
Width = (dword)pHwModeSelect->DispWidth;
|
|
PixelWidth = (dword)((pHwModeSelect->PixWidth)/8);
|
|
FbPitch = (dword)pHwModeSelect->FbPitch;
|
|
}
|
|
Height = (dword)pHwModeSelect->DispHeight;
|
|
NbBytes = Width * Height * PixelWidth;
|
|
if (NbBytes > (dword)2097152)
|
|
{
|
|
PixelTransit = (dword)2097152 / PixelWidth;
|
|
lines = (dword)(PixelTransit / FbPitch);
|
|
offset = (PixelTransit - (FbPitch * lines)) * PixelWidth;
|
|
|
|
if (pHwModeSelect->PixWidth == 24) /* PACK PIXEL */
|
|
*((dword*) (InitBuf[iBoard] + INITBUF_YDSTORG)) = offset;
|
|
else
|
|
*((dword*) (InitBuf[iBoard] + INITBUF_YDSTORG)) =
|
|
offset / PixelWidth;
|
|
}
|
|
else
|
|
{
|
|
*((dword*) (InitBuf[iBoard] + INITBUF_YDSTORG)) = 0;
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
*((dword*) (InitBuf[iBoard] + INITBUF_YDSTORG)) = 0;
|
|
}
|
|
|
|
|
|
/*--------------------------------------------------------------*/
|
|
/** If Double Buffering mode (software) **/
|
|
|
|
if((pHwModeSelect->DispType & 0x10) && /* DB mode */
|
|
!(pHwModeSelect->DispType & 0x04) ) /* not LUT mode */
|
|
{
|
|
/* Check for exception case: DB mode 16 bit with Z for PCI/2M */
|
|
if( (ProductMGA[iBoard]==MGA_PCI_2M) &&
|
|
pHwModeSelect->ZBuffer &&
|
|
pHwModeSelect->PixWidth == 8 &&
|
|
Hw[iBoard].DacType == TVP3026)
|
|
{
|
|
*((dword*) (InitBuf[iBoard] + INITBUF_DB_YDSTORG)) =
|
|
*((dword*) (InitBuf[iBoard] + INITBUF_YDSTORG));
|
|
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_DB_FrontBack)) = TRUE;
|
|
/** Caddi has to work in 16-bit **/
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_PWidth)) = 16 >> 4;
|
|
}
|
|
else
|
|
{
|
|
if(ProductMGA[iBoard]==MGA_PCI_2M)
|
|
{
|
|
*((dword*) (InitBuf[iBoard] + INITBUF_DB_YDSTORG)) =
|
|
(dword)((dword)pHwModeSelect->DispWidth *
|
|
(dword)pHwModeSelect->DispHeight);
|
|
}
|
|
else
|
|
{
|
|
if (pHwModeSelect->ZBuffer && pHwModeSelect->PixWidth==8)
|
|
{
|
|
/*** Must start on a boundary of 1M (for Z buffer alignment) ***/
|
|
*((dword*) (InitBuf[iBoard] + INITBUF_DB_YDSTORG)) =
|
|
0x100000 / (pHwModeSelect->PixWidth / 8);
|
|
}
|
|
else
|
|
{
|
|
*((dword*) (InitBuf[iBoard] + INITBUF_DB_YDSTORG)) =
|
|
(dword)((dword)pHwModeSelect->DispWidth *
|
|
(dword)pHwModeSelect->DispHeight);
|
|
}
|
|
}
|
|
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_DB_SideSide)) = TRUE;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
*((dword*) (InitBuf[iBoard] + INITBUF_DB_YDSTORG)) =
|
|
*((dword*) (InitBuf[iBoard] + INITBUF_YDSTORG));
|
|
}
|
|
|
|
/*--------------------------------------------------------------*/
|
|
|
|
|
|
/* To communicate the information to WINDOWS */
|
|
Hw[iBoard].YDstOrg = *((dword*) (InitBuf[iBoard] + INITBUF_YDSTORG));
|
|
|
|
/*** Program YDSTORG ***/
|
|
mgaWriteDWORD(*(pMgaBaseAddr + TITAN_OFFSET + TITAN_YDSTORG), Hw[iBoard].YDstOrg );
|
|
|
|
switch((Hw[iBoard].ProductRev >> 4) & 0x0000000f)
|
|
{
|
|
case TITAN_CHIP:
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_ChipSet)) = TITAN_CHIP;
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_DubicPresent)) = 1;
|
|
break;
|
|
|
|
case ATLAS_CHIP:
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_ChipSet)) = ATLAS_CHIP;
|
|
mgaReadBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_CONFIG), TmpByte);
|
|
mgaWriteBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_CONFIG), TmpByte | TITAN_NODUBIC_M);
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_DubicPresent)) = 0;
|
|
break;
|
|
|
|
case ATHENA_CHIP:
|
|
default:
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_ChipSet)) = ATHENA_CHIP;
|
|
mgaReadBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_CONFIG), TmpByte);
|
|
mgaWriteBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_CONFIG), TmpByte | TITAN_NODUBIC_M);
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_DubicPresent)) = 0;
|
|
break;
|
|
}
|
|
|
|
MGASysInit(InitBuf[iBoard]);
|
|
|
|
/* Unblank the screen */
|
|
mgaWriteBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_SEQ_ADDR), 0x01);
|
|
mgaReadBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_SEQ_DATA), TmpByte);
|
|
TmpByte &= 0xdf; /* screen on */
|
|
mgaWriteBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_SEQ_DATA), TmpByte);
|
|
|
|
#if( !defined(_WINDOWS_DLL16) && !defined(OS2) && !defined(INIT_ONLY))
|
|
#ifndef WINDOWS_NT
|
|
#ifndef __DDK_SRC__
|
|
sp = (SYSPARMS *)CaddiInit(InitBuf[iBoard], VideoBuf[iBoard]);
|
|
if(BindingRC[iBoard] != (dword)NULL)
|
|
{
|
|
dword _Far *pBufBind;
|
|
|
|
pBufBind = BufBind;
|
|
*pBufBind++ = INITRC;
|
|
*pBufBind++ = (dword)BindingRC[iBoard];
|
|
|
|
*pBufBind++ = SETENDPOINT + (0x1 << 16);
|
|
*pBufBind++ = (dword)BindingRC[iBoard];
|
|
*pBufBind++ = DONE;
|
|
if (!mtxPostBuffer (BufBind, DONT_CARE, DONT_CARE))
|
|
return(mtxFAIL);
|
|
}
|
|
#else
|
|
sp = (SYSPARMS *)InitDDK(InitBuf[iBoard], VideoBuf[iBoard]);
|
|
/***
|
|
*** _tDDK_STATE needs to be re-initialized here if you want the DDK
|
|
*** to behave exactly like the SDK
|
|
***/
|
|
|
|
#endif /* __DDK_SRC__ */
|
|
#endif /* #ifndef WINDOWS_NT */
|
|
#endif /* #if( !defined(_WINDOWS_DLL16) && !defined(OS2))... */
|
|
|
|
return(mtxOK);
|
|
}
|
|
|
|
/*----------------------------------------------------------
|
|
* blkModeSupported
|
|
*
|
|
* Check if board support 8-bit block mode.
|
|
* Condition: i) chip set ATHENA
|
|
* ii) IMP+ PCB rev 2 or more
|
|
* iii)
|
|
*
|
|
* Return:
|
|
* mtxOK : 8-bit block mode supported
|
|
* mtxFAIL : 8-bit block mode not supported
|
|
*
|
|
*----------------------------------------------------------*/
|
|
bool blkModeSupported()
|
|
{
|
|
dword TramDword;
|
|
|
|
/* Test if ATHENA chip */
|
|
if( ((Hw[iBoard].ProductRev >> 4) & 0x0000000f) < ATHENA_CHIP)
|
|
return mtxFAIL;
|
|
|
|
/* Special case */
|
|
if( ((Hw[iBoard].ProductType & 0x0f) == BOARD_MGA_RESERVED) &&
|
|
(Hw[iBoard].DacType != TVP3026 )
|
|
) return mtxFAIL;
|
|
|
|
|
|
/* Test IMP+ with PCB rev < 2, we read TramDword to find IMP+ /p4 */
|
|
mgaReadDWORD(*(pMgaBaseAddr+TITAN_OFFSET+TITAN_OPMODE),TramDword);
|
|
TramDword &= TITAN_TRAM_M;
|
|
|
|
/* PCB rev < 2 and not a /p4 */
|
|
if( (((Hw[iBoard].ProductRev & 0xf) < 2) && !TramDword))
|
|
return mtxFAIL;
|
|
|
|
|
|
return mtxOK;
|
|
}
|
|
|
|
/*----------------------------------------------------------
|
|
* mtxSetDisplayMode
|
|
*
|
|
* Select the display mode
|
|
*
|
|
* Return:
|
|
* ptr != 0 : Start address of the vidset buffer
|
|
* ptr = 0 : SetDisplayMode select failure
|
|
*
|
|
*----------------------------------------------------------*/
|
|
|
|
bool mtxSetDisplayMode(HwModeData *pDisplayModeSelect, dword Zoom)
|
|
{
|
|
|
|
byte TmpByte, vsyncPresent;
|
|
dword TmpDword;
|
|
dword Dst0, Dst1, i;
|
|
dword InfoHardware;
|
|
|
|
|
|
|
|
|
|
/*-----------------------------------------------------------*/
|
|
|
|
#ifdef PRINT_DEBUG
|
|
{
|
|
reOpenDebugfFile();
|
|
debug_printf("****** SetDisplayMode\n");
|
|
}
|
|
#endif
|
|
|
|
if (Hw[iBoard].pCurrentHwMode == NULL)
|
|
{
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("Hw[iBoard].pCurrentHwMode == NULL Fail\n");
|
|
#endif
|
|
return(mtxFAIL);
|
|
}
|
|
|
|
/* Validate Display mode to see if it is <= Hard Mode */
|
|
if (pDisplayModeSelect->DispWidth > Hw[iBoard].pCurrentHwMode->DispWidth)
|
|
{
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("pDisplayModeSelect->DispWidth > Hw[iBoard].pCurrentHwMode->DispWidth Fail\n");
|
|
#endif
|
|
return(mtxFAIL);
|
|
}
|
|
|
|
/* Validate pDisplayModeSelect to see if it is displayable */
|
|
if (pDisplayModeSelect->DispType & DISP_NOT_SUPPORT)
|
|
{
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("DISPLAY_NOT_SUPPORT Fail\n");
|
|
#endif
|
|
return(mtxFAIL);
|
|
}
|
|
|
|
if(pDisplayModeSelect->DispType & 0x08) /* 565 mode */
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_565Mode)) = TRUE;
|
|
else
|
|
*((byte*) (InitBuf[iBoard] + INITBUF_565Mode)) = FALSE;
|
|
|
|
|
|
Hw[iBoard].pCurrentDisplayMode = NULL;
|
|
mtxSetVideoMode(mtxADV_MODE);
|
|
|
|
|
|
/* begin programmation of display in vsynch */
|
|
|
|
/* Test blank screen */
|
|
mgaWriteBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_SEQ_ADDR), 0x01);
|
|
mgaReadBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_SEQ_DATA), vsyncPresent);
|
|
vsyncPresent = !(vsyncPresent & 0x20);
|
|
|
|
/* Test if valide horizontal parameters in CRTC */
|
|
if (vsyncPresent)
|
|
{
|
|
mgaWriteBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_1_CRTC_ADDR), 0x00);
|
|
mgaReadBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_1_CRTC_DATA), TmpByte);
|
|
mgaWriteBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_1_CRTC_ADDR), 0x01);
|
|
mgaReadBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_1_CRTC_DATA), vsyncPresent);
|
|
/* Compare Hdisplay Htotal */
|
|
vsyncPresent = vsyncPresent < TmpByte;
|
|
}
|
|
|
|
|
|
|
|
|
|
if (vsyncPresent)
|
|
{
|
|
for (i = 0; i < 1000000L; i++)
|
|
{
|
|
mgaReadDWORD(*(pMgaBaseAddr + TITAN_OFFSET + TITAN_STATUS), TmpDword);
|
|
if ( !(TmpDword & TITAN_VSYNCSTS_M) ) break;
|
|
}
|
|
for (i = 0; i < 1000000L; i++)
|
|
{
|
|
mgaReadDWORD(*(pMgaBaseAddr + TITAN_OFFSET + TITAN_STATUS), TmpDword);
|
|
if ( (TmpDword & TITAN_VSYNCSTS_M) ) break;
|
|
}
|
|
}
|
|
|
|
|
|
/*------ Strap added in ATHENA For max clock dac support ----*/
|
|
GetMGAConfiguration(pMgaBaseAddr, &Dst0, &Dst1, &InfoHardware);
|
|
|
|
mgaReadDWORD(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_CONFIG), InfoHardware);
|
|
|
|
if(!((Dst1 & TITAN_DST1_200MHZ_M) >> TITAN_DST1_200MHZ_A))
|
|
InfoHardware = InfoHardware & 0xfffffffb; /* bit 2=0: Board supports regular (135MHz/170MHz) operation */
|
|
else
|
|
InfoHardware = InfoHardware | 0x00000004; /* bit 2=1: Board supports 200MHz operation */
|
|
|
|
|
|
mgaWriteDWORD(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_CONFIG), InfoHardware);
|
|
|
|
/*------ Strap added for ATHENA ------------------------------*/
|
|
if ( blkModeSupported() )
|
|
{
|
|
mgaReadDWORD(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_OPMODE), InfoHardware);
|
|
|
|
if(Dst0 & TITAN_DST0_BLKMODE_M)
|
|
InfoHardware = InfoHardware & 0xf7ffffff; /* bit 27=0: VRAM 4 bit block mode */
|
|
else
|
|
InfoHardware = InfoHardware | 0x08000000; /* bit 27=1: VRAM 8 bit block mode */
|
|
mgaWriteDWORD(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_OPMODE), InfoHardware);
|
|
}
|
|
|
|
/* Blank the screen */
|
|
mgaWriteBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_SEQ_ADDR), 0x01);
|
|
mgaReadBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_SEQ_DATA), TmpByte);
|
|
TmpByte |= 0x20; /* screen off */
|
|
mgaWriteBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_SEQ_DATA), TmpByte);
|
|
|
|
Hw[iBoard].pCurrentDisplayMode = pDisplayModeSelect;
|
|
Hw[iBoard].CurrentZoomFactor = (Zoom & 0x000f000f);
|
|
|
|
/*** Load video parameters, load values in vidtab[] ***/
|
|
loadVidPar(Zoom, Hw[iBoard].pCurrentHwMode, Hw[iBoard].pCurrentDisplayMode);
|
|
|
|
/*** Calculate register values of the CRTC and put in crtcTab[] ***/
|
|
calculCrtcParam();
|
|
|
|
MoveToVideoBuffer((byte *)vidtab, (byte *)crtcTab, (byte *)VideoBuf[iBoard]);
|
|
|
|
#ifdef PRINT_DEBUG
|
|
imprimeBuffer(InitBuf[iBoard], VideoBuf[iBoard]);
|
|
#endif
|
|
|
|
#if 0
|
|
/*VIDEOPRO Init if TV MODE*/
|
|
if (pDisplayModeSelect->DispType & 0x02)
|
|
{
|
|
switch(pDisplayModeSelect->DispWidth)
|
|
{
|
|
default:
|
|
case 640:
|
|
if (VAFCconnector)
|
|
initVideoMode(NTSC_STD | VAFC,
|
|
(byte)pDisplayModeSelect->PixWidth);
|
|
else
|
|
initVideoMode(NTSC_STD,
|
|
(byte)pDisplayModeSelect->PixWidth);
|
|
break;
|
|
|
|
case 768:
|
|
if (VAFCconnector)
|
|
initVideoMode(PAL_STD | VAFC,
|
|
(byte)pDisplayModeSelect->PixWidth);
|
|
else
|
|
initVideoMode(PAL_STD,
|
|
(byte)pDisplayModeSelect->PixWidth);
|
|
break;
|
|
}
|
|
}
|
|
#endif
|
|
|
|
MGAVidInit(InitBuf[iBoard], VideoBuf[iBoard]);
|
|
|
|
#if 0
|
|
/*VIDEOPRO Make on if TV mode off sinon */
|
|
if (pDisplayModeSelect->DispType & 0x02)
|
|
{
|
|
if (VAFCconnector)
|
|
initVideoPro(1, PX2085);
|
|
else
|
|
initVideoPro(1, Hw[iBoard].DacType);
|
|
}
|
|
else
|
|
{
|
|
initVideoPro(0, Hw[iBoard].DacType);
|
|
}
|
|
#endif
|
|
#ifdef SCRAP
|
|
/*** BEN TEST SPECIAL POUR VIDEOPRO ***/
|
|
mgaReadBYTE(*(pMgaBaseAddr+TITAN_OFFSET+TITAN_MISC_OUT_R), TmpByte);
|
|
TmpByte = TmpByte & 0xfb; /* force bit 2 a 0 (clock) */
|
|
mgaWriteBYTE(*(pMgaBaseAddr+TITAN_OFFSET+TITAN_MISC_OUT_W), TmpByte);
|
|
|
|
mgaReadBYTE(*(pMgaBaseAddr+TITAN_OFFSET+TITAN_CRT_CTRL),TmpByte);
|
|
TmpByte |= 0xc0; /* Set vertical and horizontal reset */
|
|
mgaWriteBYTE(*(pMgaBaseAddr+TITAN_OFFSET+TITAN_CRT_CTRL),TmpByte);
|
|
|
|
if(pDisplayModeSelect->DispType & 0x02 ) /* mode TV */
|
|
initVideoPro(1);
|
|
else
|
|
initVideoPro(0);
|
|
#endif
|
|
|
|
/*** BEN pour Pedro ***/
|
|
/* Flag to avoid multiple initialisation of lvid[0:2] and lvidfield */
|
|
*((byte*)(VideoBuf[iBoard] + VIDEOBUF_LvidInitFlag)) |= 0x80;
|
|
|
|
#if( !defined(_WINDOWS_DLL16) && !defined(OS2) && !defined(INIT_ONLY))
|
|
#ifndef WINDOWS_NT
|
|
/*** BEN Permet de determiner DBWindowXOffset et DBWindowYOffset ***/
|
|
#ifndef __DDK_SRC__
|
|
sp = (SYSPARMS *)CaddiInit(InitBuf[iBoard], VideoBuf[iBoard]);
|
|
#else
|
|
sp = (SYSPARMS *)InitDDK(InitBuf[iBoard], VideoBuf[iBoard]);
|
|
#endif
|
|
#endif
|
|
#endif
|
|
|
|
#ifdef _WINDOWS_DLL16
|
|
if(NbSxciLoaded)
|
|
{
|
|
fp1 = (FARPROC2)GetProcAddress(hsxci, "Win386LibEntry");
|
|
(*fp1)((byte _Far *)InitBuf[iBoard], (byte _Far *)VideoBuf[iBoard],
|
|
Hw[iBoard].pCurrentHwMode->FbPitch, ID_CallCaddiInit);
|
|
}
|
|
#endif
|
|
|
|
/* Unblank the screen */
|
|
mgaWriteBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_SEQ_ADDR), 0x01);
|
|
mgaReadBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_SEQ_DATA), TmpByte);
|
|
TmpByte &= 0xdf; /* screen on */
|
|
mgaWriteBYTE(*(pMgaBaseAddr+TITAN_OFFSET + TITAN_SEQ_DATA), TmpByte);
|
|
|
|
/* Wait for start of vertical sync */
|
|
mgaPollDWORD(*(pMgaBaseAddr + TITAN_OFFSET + TITAN_STATUS),
|
|
TITAN_VSYNCSTS_SET, TITAN_VSYNCSTS_M);
|
|
|
|
/* Need 16 ms for be sure we are one retrace make */
|
|
/* ------------------------------ Remplace par un delai de 16 ms */
|
|
/* delay_us(16000); */
|
|
|
|
/*** Calculation of CurrentOverScanX and CurrentOverScanY in structure HwData ***/
|
|
if ( ((Hw[iBoard].ProductRev >> 4) & 0x0000000f) > 0 ) /* NOT TITAN */
|
|
{
|
|
Hw[iBoard].CurrentOverScanX = 0;
|
|
Hw[iBoard].CurrentOverScanY = 0;
|
|
}
|
|
else
|
|
{
|
|
overScan();
|
|
}
|
|
|
|
#if( !defined(WINDOWS) && !defined(OS2) && !defined(WINDOWS_NT) && !defined(INIT_ONLY))
|
|
mtxScClip(0, 0, pDisplayModeSelect->DispWidth, pDisplayModeSelect->DispHeight);
|
|
#endif
|
|
|
|
#ifdef _WINDOWS_DLL16
|
|
if(NbSxciLoaded)
|
|
{
|
|
*(pDllMem+PAN_DISP_WIDTH) = Hw[iBoard].pCurrentDisplayMode->DispWidth-1;
|
|
*(pDllMem+PAN_DISP_HEIGHT) = Hw[iBoard].pCurrentDisplayMode->DispHeight-1;
|
|
|
|
switch((Zoom & 0x000f000f))
|
|
{
|
|
case(0x00010001):
|
|
*(pDllMem+DB_SCALE) = (word)1;
|
|
break;
|
|
|
|
case(0x00020002):
|
|
*(pDllMem+DB_SCALE) = (word)2;
|
|
break;
|
|
|
|
case(0x00040004):
|
|
*(pDllMem+DB_SCALE) = (word)4;
|
|
break;
|
|
|
|
default:
|
|
*(pDllMem+DB_SCALE) = (word)1;
|
|
}
|
|
AdjustDBWindow();
|
|
}
|
|
#endif /* #ifdef _WINDOWS_DLL16 */
|
|
|
|
#ifdef PRINT_DEBUG
|
|
closeDebugfFile("Fin Set Display Mode\n");
|
|
#endif
|
|
|
|
return(mtxOK);
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/*----------------------- Ajustement overscan ------------------------------
|
|
hblank_e n'a que 6 bits de resolution. On le construit comme suit
|
|
5 bits Lsb dans reg 3 <4:0> et 6ieme bit dans reg 5 <7>
|
|
|
|
horizontal blank end = (reg 3 & 0x1f) | ((reg 5 >> 2) & 0x20)
|
|
|
|
On complete les bits manquant de BlankEnd en utilisant les bits
|
|
<7:6> de BLANK START.
|
|
SI les 6 bits LSBs de BLANK START sont superieur a ceux du BLANK END
|
|
alors ceci veu dire les deux les plus significatif de BLANK END sont egale
|
|
a ceux du BLANK START + 1, sinon il sont egaux.
|
|
|
|
Une fois qu'on a le BLANK END complet on peut le comparer au horizontal Total
|
|
pour connaitre l'overscan a gauche.
|
|
|
|
0.......Blank End....Htotal - 1.
|
|
|
|
Note: On compare a Htotal -1. si il y 10 caractere alors on va de 0...9
|
|
|
|
Idem pour l'overscan vertical ou il manque les 2 bits MSBs <9:8>.
|
|
|
|
Note: Il y a un cas special ou le HBLANKE est a zero, dans ce cas
|
|
l'overscan doit-etre a zero.
|
|
----------------------------------------------------------------------------*/
|
|
|
|
static void overScan(void)
|
|
{
|
|
word total, blank_s, blank_e, mask;
|
|
|
|
/* Overlay to left of screen */
|
|
/* Htotal = reg(0) + 5 donc Htotal - 1 = reg(0) + 4 */
|
|
|
|
total = (word)(crtcTab[0] + 4);
|
|
blank_s = (word)crtcTab[2];
|
|
blank_e = (word)((crtcTab[3] & 0x1f) | ( (crtcTab[5] >> 2) & 0x20 ));
|
|
|
|
if (blank_e != 0) /* We verify for the special case where blank_e == 0 */
|
|
{
|
|
mask = blank_s >> 6;
|
|
if ((blank_s & 0x3f) > blank_e) mask++;
|
|
blank_e |= mask << 6;
|
|
Hw[iBoard].CurrentOverScanX = (total - blank_e) << 3; /* 8 pixel per cell */
|
|
}
|
|
else
|
|
{
|
|
Hw[iBoard].CurrentOverScanX = 0;
|
|
}
|
|
|
|
/* Overlay on top of screen */
|
|
/* Vtotal = reg(6,7) + 2 donc Vtotal - 1 = reg(6,7) + 1 */
|
|
|
|
total = (word)crtcTab[6] + 1;
|
|
mask = (word)crtcTab[7];
|
|
total |= ((mask << 4) & 0x200) | ((mask << 8) & 0x100);
|
|
blank_s = (word)crtcTab[21] |
|
|
( ((word)crtcTab[9] << 4) & 0x200 ) |
|
|
( ((word)crtcTab[7] << 5) & 0x100 ) ;
|
|
blank_e = (word)crtcTab[22];
|
|
|
|
mask = blank_s >> 8;
|
|
if ((blank_s & 0x7f) > blank_e)
|
|
mask++;
|
|
blank_e |= mask << 8;
|
|
|
|
Hw[iBoard].CurrentOverScanY = (total - blank_e);
|
|
|
|
/* Test if we double the scan lines (Horizontal retrace divide select) */
|
|
if (crtcTab[23] & 0x04)
|
|
Hw[iBoard].CurrentOverScanY <<= 1;
|
|
|
|
/* We modify the overscan, must recalculate the HotSpot */
|
|
if (Hw[iBoard].cursorInfo.CurWidth > 0)
|
|
mtxCursorSetHotSpot(Hw[iBoard].cursorInfo.cHotSX,
|
|
Hw[iBoard].cursorInfo.cHotSX);
|
|
}
|
|
|
|
|
|
|
|
|
|
void mapPciVl(dword addr)
|
|
{
|
|
byte TmpByte;
|
|
dword pci_id, TmpDword;
|
|
mgaReadDWORD(*(pMgaBaseAddr+0x2000),pci_id);
|
|
if ((pci_id == (dword)0x0518102b) || (pci_id == (dword)0x0d10102b))
|
|
{
|
|
mgaWriteDWORD(*(pMgaBaseAddr+0x2010),addr);
|
|
mgaReadBYTE(*(pMgaBaseAddr+0x2004), TmpByte);
|
|
mgaWriteBYTE(*(pMgaBaseAddr+0x2004), TmpByte | 2);
|
|
|
|
mgaReadDWORD(*(pMgaBaseAddr+TITAN_OFFSET+TITAN_CONFIG),TmpDword);
|
|
|
|
if (TmpDword&TITAN_VGAEN_M)
|
|
{
|
|
#ifndef WINDOWS_NT
|
|
_outp(0x46e8, 0x08);
|
|
#else
|
|
_outp(ADDR_46E8_PORT, 0x08);
|
|
#endif
|
|
}
|
|
|
|
}
|
|
}
|
|
|
|
|
|
/*-------------------------------------------------------------------
|
|
* MapBoard
|
|
*
|
|
* Map all MGA devices in systems
|
|
*
|
|
* Set global variables:
|
|
* - Hw[].MapAddress
|
|
* - MgaSel : Board selector
|
|
*-------------------------------------------------------------------*/
|
|
bool MapBoard(void)
|
|
{
|
|
dword val_id, ba;
|
|
|
|
#if USE_VP_GET_ACCESS_RANGES
|
|
|
|
VIDEO_ACCESS_RANGE MgaDriverPciAccessRange[14];
|
|
ULONG ulNbPciAccessRanges = 14;
|
|
VP_STATUS status;
|
|
USHORT VendorId = MATROX_VENDOR_ID;
|
|
USHORT DeviceId[] = { MGA_DEVICE_ID_ATH, MGA_DEVICE_ID_ATL };
|
|
ULONG ulNbDeviceIds = 2;
|
|
ULONG ulDeviceCnt = 0;
|
|
ULONG k;
|
|
BOOLEAN bRangeFound;
|
|
|
|
#endif
|
|
|
|
//[dlee] For now, we'll just check base addresses AC000 and C8000 on Alpha
|
|
//#ifndef MGA_ALPHA
|
|
dword ScanAddr[] = { MGA_ISA_BASE_1, MGA_ISA_BASE_2, MGA_ISA_BASE_3,
|
|
MGA_ISA_BASE_4, MGA_ISA_BASE_5, MGA_ISA_BASE_6,
|
|
MGA_ISA_BASE_7 };
|
|
//#else
|
|
// dword ScanAddr[] = { MGA_ISA_BASE_2, MGA_ISA_BASE_1 };
|
|
//#endif
|
|
|
|
word i, j, b_exist;
|
|
PciBiosInfo bi;
|
|
|
|
#ifndef WINDOWS_NT
|
|
NbBoard = 0;
|
|
#endif
|
|
|
|
MgaSel = getmgasel();
|
|
mtxSetVLB(MgaSel);
|
|
|
|
#ifdef WINDOWS_NT
|
|
// Special
|
|
if (NtInterfaceType == PCIBus)
|
|
{
|
|
#endif
|
|
|
|
#if USE_VP_GET_ACCESS_RANGES
|
|
|
|
#define PCI_SLOT_MAX 32
|
|
|
|
for (i = 0; i < (word)ulNbPciAccessRanges; i++)
|
|
{
|
|
MgaDriverPciAccessRange[i].RangeStart.LowPart = 0xffffffff;
|
|
}
|
|
|
|
// DbgBreakPoint();
|
|
// _asm {int 3}
|
|
|
|
PciSlot = 0;
|
|
|
|
status = VideoPortGetAccessRanges(pMgaDeviceExtension,
|
|
0,
|
|
(PIO_RESOURCE_DESCRIPTOR) NULL,
|
|
ulNbPciAccessRanges,
|
|
MgaDriverPciAccessRange,
|
|
&VendorId,
|
|
&DeviceId[ulDeviceCnt],
|
|
&PciSlot);
|
|
if (status == NO_ERROR)
|
|
{
|
|
VideoDebugPrint((1, "MGA: no_error on DeviceId %d\n",
|
|
ulDeviceCnt));
|
|
i = 0;
|
|
while ((i < (word)ulNbPciAccessRanges) &&
|
|
(NbBoard < 7) &&
|
|
((ba = MgaDriverPciAccessRange[i].RangeStart.LowPart) !=
|
|
0xffffffff))
|
|
{
|
|
if (MgaDriverPciAccessRange[i].RangeLength == 0x4000)
|
|
{
|
|
// This is a control aperture.
|
|
// Do we already know about it?
|
|
bRangeFound = FALSE;
|
|
for (k = 0; k < NbBoard; k++)
|
|
{
|
|
if (Hw[k].MapAddress == ba)
|
|
{
|
|
bRangeFound = TRUE;
|
|
break;
|
|
}
|
|
}
|
|
if (!bRangeFound)
|
|
{
|
|
// This is a new memory-space range.
|
|
if ((pMgaBaseAddr = setmgasel(MgaSel, ba, 4)) != NULL)
|
|
{
|
|
mgaReadDWORD(*(pMgaBaseAddr+TITAN_OFFSET+TITAN_REV),
|
|
val_id);
|
|
if ( (val_id & (~TITAN_CHIPREV_M)) == TITAN_ID)
|
|
{
|
|
// This is one of ours!
|
|
Hw[NbBoard].MapAddress = ba;
|
|
Hw[NbBoard].BaseAddress = pMgaBaseAddr;
|
|
MgaBusType[NbBoard] = MGA_BUS_PCI;
|
|
NbBoard++;
|
|
}
|
|
else
|
|
{
|
|
// We don't know what this was! Free the range.
|
|
VideoPortFreeDeviceBase(pMgaDeviceExtension,
|
|
pMgaBaseAddr);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
MgaDriverPciAccessRange[i].RangeStart.LowPart = 0xffffffff;
|
|
i++;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if (status == ERROR_MORE_DATA)
|
|
VideoDebugPrint((1, "MGA: error_more_data on DeviceId %d\n", ulDeviceCnt));
|
|
else if (status == ERROR_DEV_NOT_EXIST)
|
|
VideoDebugPrint((1, "MGA: error_dev_not_exist on DeviceId %d\n", ulDeviceCnt));
|
|
else
|
|
VideoDebugPrint((1, "MGA: unknown error on DeviceId %d\n", ulDeviceCnt));
|
|
}
|
|
|
|
#else /* #if USE_VP_GET_ACCESS_RANGES */
|
|
|
|
#ifdef WINDOWS_NT /* For WinNT3.1 and WinNT3.5/Intel */
|
|
// Get access to ports before calling pciFindFirstMGA_2.
|
|
//if (VideoPortVerifyAccessRanges(pMgaDeviceExtension,
|
|
// 1,
|
|
// &MgaPciCseAccessRange) == NO_ERROR &&
|
|
// (pMgaPciIo = VideoPortGetDeviceBase(pMgaDeviceExtension,
|
|
// MgaPciCseAccessRange.RangeStart,
|
|
// MgaPciCseAccessRange.RangeLength,
|
|
// MgaPciCseAccessRange.RangeInIoSpace)) != NULL)
|
|
if ((pMgaPciIo = VideoPortGetDeviceBase(pMgaDeviceExtension,
|
|
MgaPciCseAccessRange.RangeStart,
|
|
MgaPciCseAccessRange.RangeLength,
|
|
MgaPciCseAccessRange.RangeInIoSpace)) != NULL)
|
|
{
|
|
#endif /* #ifdef MGA_WINNT31 */
|
|
|
|
#ifndef OS2
|
|
if ( (ba = (dword)pciFindFirstMGA_2()) != (dword)-1)
|
|
{
|
|
while ( (ba != (dword)-1 ) && (NbBoard < 7) )
|
|
{
|
|
#ifdef WINDOWS_NT
|
|
b_exist = 0;
|
|
for (j = 0; j < NbBoard; j++)
|
|
{
|
|
if (Hw[j].MapAddress == ba)
|
|
{
|
|
b_exist = 1;
|
|
break;
|
|
}
|
|
}
|
|
if (!b_exist)
|
|
{
|
|
// This is a new range.
|
|
#endif
|
|
pMgaBaseAddr = setmgasel(MgaSel, ba, 4);
|
|
if (pMgaBaseAddr != NULL)
|
|
{
|
|
mgaReadDWORD(*(pMgaBaseAddr+TITAN_OFFSET+TITAN_REV),val_id);
|
|
if ( (val_id & (~TITAN_CHIPREV_M)) == TITAN_ID)
|
|
{
|
|
Hw[NbBoard].MapAddress = ba;
|
|
#ifdef WINDOWS_NT
|
|
Hw[NbBoard].BaseAddress = pMgaBaseAddr;
|
|
MgaBusType[NbBoard] = MGA_BUS_PCI;
|
|
Hw[NbBoard].ConfigSpace = configSpace - 0x100;
|
|
if (configSpace > 0xd000)
|
|
Hw[NbBoard].ConfigSpace = 0;
|
|
|
|
#if 0 // TO BE COMPLETED
|
|
if (Hw[NbBoard].ConfigSpace != 0)
|
|
{
|
|
MgaPciConfigAccessRange.RangeStart.LowPart = (ULONG)configSpace;
|
|
if (VideoPortVerifyAccessRanges(pMgaDeviceExtension,
|
|
1,
|
|
&MgaPciConfigAccessRange) == NO_ERROR &&
|
|
(pMgaPciConfigSpace = VideoPortGetDeviceBase(pMgaDeviceExtension,
|
|
MgaPciConfigAccessRange.RangeStart,
|
|
MgaPciConfigAccessRange.RangeLength,
|
|
MgaPciConfigAccessRange.RangeInIoSpace)) != NULL)
|
|
{
|
|
Hw[NbBoard].ConfigSpaceAddress = pMgaPciConfigSpace;
|
|
}
|
|
}
|
|
#endif
|
|
#endif
|
|
NbBoard++;
|
|
}
|
|
#ifdef WINDOWS_NT
|
|
else
|
|
{
|
|
// We don't know what that was!
|
|
VideoPortFreeDeviceBase(pMgaDeviceExtension,
|
|
pMgaBaseAddr);
|
|
}
|
|
#endif
|
|
}
|
|
#ifdef WINDOWS_NT
|
|
}
|
|
#endif
|
|
ba = (dword)pciFindNextMGA_2();
|
|
}
|
|
}
|
|
|
|
#ifdef WINDOWS_NT
|
|
// Free access to ports after calling pciFindFirst/NextMGA_2.
|
|
VideoPortFreeDeviceBase(pMgaDeviceExtension,pMgaPciIo);
|
|
}
|
|
#endif /* #ifdef WINDOWS_NT */
|
|
|
|
else
|
|
{
|
|
#ifdef WINDOWS_NT
|
|
if ((pciBiosRoutine = pciBiosCallAddr()) != NULL)
|
|
{
|
|
VideoDebugPrint((1, "pciBiosRoutine = 0x%x\n", pciBiosRoutine));
|
|
#endif
|
|
if ( pciBiosPresent( &bi ) )
|
|
{
|
|
#endif /* #ifndef OS2 */
|
|
|
|
ba = (dword)pciFindFirstMGA();
|
|
while ( (ba != (dword)-1 ) && (NbBoard < 7) )
|
|
{
|
|
#ifdef WINDOWS_NT
|
|
b_exist = 0;
|
|
for (j = 0; j < NbBoard; j++)
|
|
{
|
|
if (Hw[j].MapAddress == ba)
|
|
{
|
|
b_exist = 1;
|
|
break;
|
|
}
|
|
}
|
|
if (!b_exist)
|
|
{
|
|
// This is a new range.
|
|
#endif
|
|
pMgaBaseAddr = setmgasel(MgaSel, ba, 4);
|
|
if (pMgaBaseAddr != NULL)
|
|
{
|
|
mgaReadDWORD(*(pMgaBaseAddr+TITAN_OFFSET+TITAN_REV),
|
|
val_id);
|
|
if ( (val_id & (~TITAN_CHIPREV_M)) == TITAN_ID)
|
|
{
|
|
Hw[NbBoard].MapAddress = ba;
|
|
#ifdef WINDOWS_NT
|
|
Hw[NbBoard].BaseAddress = pMgaBaseAddr;
|
|
MgaBusType[NbBoard] = MGA_BUS_PCI;
|
|
#endif
|
|
NbBoard++;
|
|
}
|
|
#ifdef WINDOWS_NT
|
|
else
|
|
{
|
|
// We don't know what that was!
|
|
VideoPortFreeDeviceBase(pMgaDeviceExtension,
|
|
pMgaBaseAddr);
|
|
}
|
|
#endif
|
|
}
|
|
#ifdef WINDOWS_NT
|
|
}
|
|
#endif
|
|
|
|
ba = (dword)pciFindNextMGA();
|
|
|
|
}
|
|
#ifndef OS2
|
|
}
|
|
|
|
#ifdef WINDOWS_NT
|
|
}
|
|
#endif
|
|
}
|
|
#endif /* #ifndef OS2 */
|
|
#endif /* #if USE_VP_GET_ACCESS_RANGES */
|
|
|
|
#ifdef WINDOWS_NT
|
|
// Special
|
|
}
|
|
else
|
|
{
|
|
#endif
|
|
/* Search ISA BUS */
|
|
if ( mtxIsVLBBios() )
|
|
{
|
|
#ifndef WINDOWS_NT
|
|
_outp(0x46e8, 0x00);
|
|
#else
|
|
_outp(ADDR_46E8_PORT, 0x00);
|
|
#endif
|
|
}
|
|
|
|
//#ifndef MGA_ALPHA
|
|
for (i=0; (i < 7) && (NbBoard < 7); i++)
|
|
//#else
|
|
// for (i=0; (i < 2) && (NbBoard < 2); i++)
|
|
//#endif
|
|
{
|
|
b_exist = 0;
|
|
for (j = 0; j < NbBoard; j++)
|
|
{
|
|
if (Hw[j].MapAddress == ScanAddr[i])
|
|
{
|
|
b_exist = 1;
|
|
break;
|
|
}
|
|
}
|
|
|
|
#ifdef WINDOWS_NT
|
|
// On Windows NT, we have to verify that the range we're about to map
|
|
// does not conflict with a range that has already been mapped by
|
|
// another driver.
|
|
//if ((!b_exist) && (!bConflictDetected(ScanAddr[i])))
|
|
if (!b_exist)
|
|
{
|
|
#endif
|
|
|
|
pMgaBaseAddr = setmgasel(MgaSel, ScanAddr[i], 4);
|
|
if (pMgaBaseAddr != NULL)
|
|
{
|
|
mapPciVl(ScanAddr[i]);
|
|
mgaReadDWORD(*(pMgaBaseAddr+TITAN_OFFSET+TITAN_REV),val_id);
|
|
if ( !b_exist && ((val_id & (~TITAN_CHIPREV_M)) == TITAN_ID))
|
|
{
|
|
Hw[NbBoard].MapAddress = ScanAddr[i];
|
|
#ifdef WINDOWS_NT
|
|
Hw[NbBoard].BaseAddress = pMgaBaseAddr;
|
|
MgaBusType[NbBoard] = MGA_BUS_ISA;
|
|
Hw[NbBoard].ConfigSpace = 0;
|
|
#endif
|
|
if ( mtxIsVLBBios() && (ScanAddr[i] == MGA_ISA_BASE_1) )
|
|
mgaWriteDWORD(*(pMgaBaseAddr+0x2010), (dword)0x80000000 |
|
|
(dword)MGA_ISA_BASE_1);
|
|
NbBoard++;
|
|
}
|
|
#ifdef WINDOWS_NT
|
|
else
|
|
{
|
|
// We don't know what that was!
|
|
VideoPortFreeDeviceBase(pMgaDeviceExtension, pMgaBaseAddr);
|
|
}
|
|
#endif
|
|
}
|
|
#ifdef WINDOWS_NT
|
|
}
|
|
#endif
|
|
}
|
|
|
|
#ifdef WINDOWS_NT
|
|
// Special
|
|
}
|
|
#endif
|
|
|
|
/* Indicates end of array */
|
|
Hw[NbBoard].MapAddress = (dword)-1;
|
|
|
|
if (NbBoard == 0)
|
|
return(mtxFAIL);
|
|
else
|
|
return(mtxOK);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/*-----------------------------------------------------
|
|
* adjustDefaultVidset
|
|
*
|
|
* Return default Vidset for the select board
|
|
*------------------------------------------------------*/
|
|
char *adjustDefaultVidset()
|
|
{
|
|
general_info *generalInfo;
|
|
|
|
mgainf = DefaultVidset;
|
|
generalInfo = (general_info *)selectMgaInfoBoard();
|
|
generalInfo->MapAddress = Hw[iBoard].MapAddress;
|
|
|
|
#ifdef WINDOWS_NT
|
|
generalInfo->BitOperation8_16 = -1;
|
|
#else
|
|
generalInfo->BitOperation8_16 = (short)0xffff;
|
|
#endif
|
|
|
|
return(mgainf);
|
|
}
|
|
|
|
|
|
//[dlee] Modified for Windows NT
|
|
// This is not called for Windows NT because we can't open files in
|
|
// kernel mode. (MGA.INF is new read in the user-mode driver instead)
|
|
|
|
#ifndef WINDOWS_NT
|
|
/*--------------------------------------------------------------
|
|
* mtxLectureMgaInf
|
|
*
|
|
* Read file mga.inf and put data in buffer mgainf
|
|
* or take DefaultVidset
|
|
*
|
|
*--------------------------------------------------------------*/
|
|
bool mtxLectureMgaInf(void)
|
|
{
|
|
#ifdef WINDOWS
|
|
LPSTR lpszEnv;
|
|
bool findMGA;
|
|
#endif
|
|
|
|
#ifdef OS2
|
|
HFILE hFile;
|
|
USHORT usAction;
|
|
USHORT usInfoLevel = 1;
|
|
FILESTATUS status;
|
|
USHORT bytesRead;
|
|
ULONG fn_ID;
|
|
char mgaName[] = "MGA";
|
|
char far *mgaPathPtr;
|
|
char mgaPath[300];
|
|
USHORT fileSize;
|
|
#else
|
|
FILE *pFile;
|
|
char *env, path[128];
|
|
long fileSize;
|
|
#endif
|
|
int i;
|
|
|
|
#ifndef OS2
|
|
/*** Reading file MGA.INF ***/
|
|
/*** Put values in global array mgainf ***/
|
|
strcpy(path, "mga.inf");
|
|
if ((pFile = fopen(path, "rb")) == NULL)
|
|
{
|
|
#endif
|
|
|
|
#ifdef WINDOWS
|
|
/*** Find MGA variable ***/
|
|
findMGA = FALSE;
|
|
lpszEnv = GetDOSEnvironment();
|
|
|
|
while(*lpszEnv != '\0')
|
|
{
|
|
if (! (strncmp("MGA=", lpszEnv, 4)) )
|
|
{
|
|
findMGA = TRUE;
|
|
break;
|
|
}
|
|
|
|
lpszEnv += lstrlen(lpszEnv) + 1;
|
|
}
|
|
|
|
if (findMGA)
|
|
{
|
|
strcpy(path, lpszEnv+4);
|
|
i = strlen(path);
|
|
if (path[i-1] != '\\')
|
|
strcat(path, "\\");
|
|
strcat(path, "mga.inf");
|
|
|
|
if ((pFile = fopen(path, "rb")) == NULL)
|
|
{
|
|
mgainf = adjustDefaultVidset();
|
|
return mtxOK;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
mgainf = adjustDefaultVidset();
|
|
return mtxOK;
|
|
}
|
|
#endif /* #ifdef WINDOWS */
|
|
|
|
#if( !defined(WINDOWS) && !defined(OS2) && !defined(WINDOWS_NT) )
|
|
|
|
/* Check environment variable MGA */
|
|
if ( (env = getenv("MGA")) != NULL )
|
|
{
|
|
strcpy(path, env);
|
|
i = strlen(path);
|
|
if (path[i-1] != '\\')
|
|
strcat(path, "\\");
|
|
strcat(path, "mga.inf");
|
|
if ((pFile = fopen(path, "rb")) == NULL)
|
|
{
|
|
mgainf = adjustDefaultVidset();
|
|
return mtxOK;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
mgainf = adjustDefaultVidset();
|
|
return mtxOK;
|
|
}
|
|
#endif /* #if( !defined(WINDOWS) && !defined(OS2) && !defined(WINDOWS_NT) ) */
|
|
|
|
#ifdef OS2
|
|
/* Position of mga.inf defined by the environnement variable MGA */
|
|
/* if it is not defined, we will use the setup by defaut */
|
|
|
|
if(DosScanEnv(mgaName, &mgaPathPtr))
|
|
{
|
|
mgainf = adjustDefaultVidset();
|
|
return(mtxOK);
|
|
}
|
|
strcpy(mgaPath, mgaPathPtr);
|
|
strcat(mgaPath, "\\mga.inf");
|
|
|
|
if(DosOpen2(mgaPath, &hFile, &usAction, 0L, FILE_NORMAL, FILE_OPEN,
|
|
OPEN_ACCESS_READONLY | OPEN_SHARE_DENYREADWRITE, NULL, 0L))
|
|
{
|
|
mgainf = adjustDefaultVidset();
|
|
return(mtxOK);
|
|
}
|
|
|
|
DosQFileInfo(hFile, usInfoLevel, &status, (USHORT)sizeof(FILESTATUS));
|
|
fileSize = (USHORT)status.cbFile;
|
|
#else
|
|
}
|
|
fseek(pFile, 0, SEEK_END);
|
|
fileSize = ftell(pFile);
|
|
rewind(pFile);
|
|
#endif
|
|
|
|
if (CheckHwAllDone && (mgainf != DefaultVidset))
|
|
free( (void *)mgainf);
|
|
|
|
if ( (mgainf = (char *)malloc(fileSize * sizeof(char))) == 0 )
|
|
{
|
|
#ifdef OS2
|
|
DosClose(hFile);
|
|
#else
|
|
fclose(pFile);
|
|
#endif
|
|
mgainf = adjustDefaultVidset();
|
|
/*** BEN setter un warning code ici ***/
|
|
return(mtxOK);
|
|
}
|
|
|
|
#ifdef OS2
|
|
if ( DosRead(hFile, (PVOID)mgainf, fileSize, &bytesRead) ||
|
|
(bytesRead != fileSize))
|
|
#else
|
|
if ( fread(mgainf, sizeof(char), fileSize, pFile) < fileSize )
|
|
#endif
|
|
{
|
|
#ifdef OS2
|
|
DosClose(hFile);
|
|
#else
|
|
fclose(pFile);
|
|
#endif
|
|
free(mgainf);
|
|
mgainf = adjustDefaultVidset();
|
|
/*** BEN setter un warning code ici ***/
|
|
return(mtxOK);
|
|
}
|
|
|
|
if ( ((header *)mgainf)->Revision != (short)VERSION_NUMBER)
|
|
{
|
|
/* Conversion of old mga.inf file to the current revision */
|
|
if ( !(mgainf = mtxConvertMgaInf( mgainf )))
|
|
{
|
|
#ifdef OS2
|
|
DosClose(hFile);
|
|
#else
|
|
fclose(pFile);
|
|
#endif
|
|
mgainf = adjustDefaultVidset();
|
|
/*** BEN setter un warning code ici ***/
|
|
return(mtxOK);
|
|
}
|
|
}
|
|
|
|
#ifdef OS2
|
|
DosClose(hFile);
|
|
#else
|
|
fclose(pFile);
|
|
#endif
|
|
|
|
if ( (general_info *)selectMgaInfoBoard() == NULL)
|
|
{
|
|
free(mgainf);
|
|
mgainf = adjustDefaultVidset();
|
|
/*** BEN setter un warning code ici ***/
|
|
return(mtxOK);
|
|
}
|
|
|
|
if (strncmp(mgainf, "Matrox MGA Setup file", 21))
|
|
{
|
|
free(mgainf);
|
|
mgainf = adjustDefaultVidset();
|
|
}
|
|
|
|
return(mtxOK);
|
|
}
|
|
#endif /* #ifndef WINDOWS_NT */
|
|
|
|
|
|
|
|
|
|
|
|
/*-----------------------------------------------------
|
|
* selectMgaInfoBoard
|
|
*
|
|
* Return a pointer at the first information for the
|
|
* selected board
|
|
*------------------------------------------------------
|
|
*
|
|
* Algorithme de recherche
|
|
* mga.inf support 7 card in the system. We have to fit the MapAdress
|
|
* of the card whith the one specified in structure general_info. If
|
|
* no one of the seven general_info fit, we pick the first valid one.
|
|
* Note : The map adresse of the structure is not updated, we must not use
|
|
* this adress outside this function.
|
|
*
|
|
*------------------------------------------------------*/
|
|
|
|
|
|
char *selectMgaInfoBoard()
|
|
{
|
|
word IndexBoard, DefaultBoard;
|
|
header *pHeader = (header *)mgainf;
|
|
general_info *genInfo = NULL;
|
|
|
|
DefaultBoard = NB_BOARD_MAX;
|
|
for (IndexBoard = 0; !genInfo && (IndexBoard < NB_BOARD_MAX); IndexBoard++)
|
|
{
|
|
if ( pHeader->BoardPtr[IndexBoard] > 0 )
|
|
{
|
|
if ( DefaultBoard == NB_BOARD_MAX) DefaultBoard = IndexBoard;
|
|
genInfo = (general_info *)(mgainf + pHeader->BoardPtr[IndexBoard]);
|
|
if (Hw[iBoard].MapAddress != genInfo->MapAddress) genInfo = NULL;
|
|
}
|
|
}
|
|
|
|
if ( !genInfo) /*** BEN setter un warning code ici ***/
|
|
{
|
|
if (DefaultBoard < NB_BOARD_MAX)
|
|
{
|
|
genInfo = (general_info *)(mgainf + pHeader->BoardPtr[DefaultBoard]);
|
|
}
|
|
else
|
|
{
|
|
mgainf = adjustDefaultVidset();
|
|
pHeader = (header *)mgainf;
|
|
genInfo = (general_info *)(mgainf + pHeader->BoardPtr[0]);
|
|
}
|
|
}
|
|
|
|
return (char *)genInfo;
|
|
}
|
|
|
|
|
|
|
|
|
|
/*-----------------------------------------------------
|
|
* UpdateHwModeTable
|
|
*
|
|
* Update hardware mode table with interlace informations
|
|
* if we are in interlace mode
|
|
*
|
|
*------------------------------------------------------*/
|
|
|
|
void UpdateHwModeTable (char *pMgaInfo,
|
|
HwModeData *pHwMode,
|
|
HwModeInterlace *piHwMode,
|
|
bool dacSupportHires )
|
|
{
|
|
|
|
short FlagMonitorSupport;
|
|
word TmpRes;
|
|
HwModeData *pHwMode1;
|
|
general_info *generalInfo = (general_info *)pMgaInfo;
|
|
|
|
if (CheckHwAllDone)
|
|
{
|
|
for (pHwMode1 = pHwMode ; pHwMode1->DispWidth != (word)-1; pHwMode1++)
|
|
{
|
|
pHwMode1->DispType &= 0x5e; /* force interlaced = 0 and monitor limited = 0 */
|
|
|
|
if (pHwMode1->DispType & 0x40) /* Hw limited */
|
|
pHwMode1->DispType |= 0x80; /* force not displayable bit on */
|
|
}
|
|
}
|
|
|
|
for ( ; pHwMode->DispWidth != (word)-1; piHwMode++, pHwMode++)
|
|
{
|
|
/* Determine TmpRes for compatibility with spec mga.inf */
|
|
switch (pHwMode->DispWidth)
|
|
{
|
|
case 640: if (pHwMode->DispType & 0x02)
|
|
TmpRes = RESNTSC;
|
|
else
|
|
TmpRes = RES640;
|
|
break;
|
|
|
|
case 768: TmpRes = RESPAL;
|
|
break;
|
|
|
|
case 800: TmpRes = RES800;
|
|
break;
|
|
|
|
case 1024: TmpRes = RES1024;
|
|
break;
|
|
|
|
case 1152: TmpRes = RES1152;
|
|
break;
|
|
|
|
case 1280: TmpRes = RES1280;
|
|
break;
|
|
|
|
case 1600: TmpRes = RES1600;
|
|
break;
|
|
}
|
|
|
|
FlagMonitorSupport = generalInfo ->MonitorSupport[TmpRes];
|
|
|
|
/*** Update of the pHwMode table if I (interlace) ***/
|
|
switch ( FlagMonitorSupport )
|
|
{
|
|
case MONITOR_I:
|
|
if(piHwMode->FbPitch)
|
|
{
|
|
pHwMode->FbPitch = piHwMode->FbPitch;
|
|
pHwMode->DispType = piHwMode->DispType;
|
|
pHwMode->NumOffScr = piHwMode->NumOffScr;
|
|
pHwMode->pOffScr = piHwMode->pOffScr;
|
|
}
|
|
pHwMode->DispType |= DISP_SUPPORT_I; /* Interlace */
|
|
break;
|
|
|
|
case MONITOR_NA:
|
|
pHwMode->DispType |= DISP_SUPPORT_NA; /* monitor limited */
|
|
break;
|
|
}
|
|
|
|
/* Not displayable, hw limited */
|
|
if ((pHwMode->DispWidth > 1280) && !dacSupportHires)
|
|
pHwMode->DispType |= DISP_SUPPORT_HWL;
|
|
|
|
#if ((!defined (WINDOWS_NT)) || (USE_DDC_CODE))
|
|
if (SupportDDC && !(byte)InDDCTable(pHwMode->DispWidth))
|
|
pHwMode->DispType |= DISP_SUPPORT_NA; /* monitor limited */
|
|
#endif
|
|
|
|
/*** For ATLAS chip we can't do Z buffering ***/
|
|
if( ((Hw[iBoard].ProductRev >> 4) & 0x0000000f) == ATLAS_CHIP &&
|
|
pHwMode->ZBuffer )
|
|
pHwMode->DispType |= DISP_SUPPORT_HWL;
|
|
|
|
/*** For an Ultima board we can't do Z-buffer ***/
|
|
|
|
if( !((Dst1 & TITAN_DST1_ABOVE1280_M) && (Dst1 & TITAN_DST1_200MHZ_M)) &&
|
|
(ProductMGA[iBoard] == MGA_PCI_2M || ProductMGA[iBoard] == MGA_PCI_4M) &&
|
|
((Hw[iBoard].ProductRev >> 4) & 0x0000000f) == ATHENA_CHIP &&
|
|
pHwMode->ZBuffer && Hw[iBoard].DacType != TVP3026)
|
|
{
|
|
pHwMode->DispType |= DISP_SUPPORT_HWL;
|
|
}
|
|
|
|
/* For Impression Lite we can't do double buffering */
|
|
if ((Dst1 & TITAN_DST1_ABOVE1280_M) && (Dst1 & TITAN_DST1_200MHZ_M) &&
|
|
((Hw[iBoard].ProductRev >> 4) & 0x0000000f) == ATHENA_CHIP &&
|
|
(pHwMode->DispType & 0x10) && pHwMode->ZBuffer)
|
|
{
|
|
pHwMode->DispType |= DISP_SUPPORT_HWL;
|
|
}
|
|
|
|
|
|
/* PACK PIXEL ON TVP and Windows only */
|
|
|
|
#ifdef _WINDOWS_DLL16
|
|
if ((pHwMode->PixWidth == 24) && (Hw[iBoard].DacType != TVP3026))
|
|
pHwMode->DispType |= DISP_SUPPORT_HWL;
|
|
#else
|
|
if (pHwMode->PixWidth == 24)
|
|
pHwMode->DispType |= DISP_SUPPORT_HWL;
|
|
#endif
|
|
|
|
}
|
|
}
|
|
|
|
/*-----------------------------------------------------
|
|
* mtxGetMgaSel
|
|
*
|
|
* Return the selector
|
|
* (Called by the driver)
|
|
*------------------------------------------------------*/
|
|
|
|
dword mtxGetMgaSel(void)
|
|
{
|
|
return(MgaSel);
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/*-----------------------------------------------------
|
|
* mtxGetInfo
|
|
*
|
|
* Return useful informations to Open GL and Windows
|
|
*------------------------------------------------------*/
|
|
|
|
void mtxGetInfo(HwModeData **pCurHwMode, HwModeData **pCurDispMode, byte **InitBuffer, byte **VideoBuffer)
|
|
{
|
|
*pCurHwMode = Hw[iBoard].pCurrentHwMode;
|
|
*pCurDispMode = Hw[iBoard].pCurrentDisplayMode;
|
|
*InitBuffer = InitBuf[iBoard];
|
|
*VideoBuffer = VideoBuf[iBoard];
|
|
}
|
|
|
|
|
|
#ifdef WINDOWS
|
|
/*-----------------------------------------------------
|
|
* mtxGetHwData
|
|
*
|
|
* Return useful informations to Open GL and Windows
|
|
* Return value:
|
|
* - null pointer : no MGA board
|
|
* - valid pointer: pointer to HwData structure
|
|
*------------------------------------------------------*/
|
|
|
|
HwData *mtxGetHwData(void)
|
|
{
|
|
if(Hw[iBoard].MapAddress == (dword)-1)
|
|
return 0;
|
|
else
|
|
return(&Hw[iBoard]);
|
|
}
|
|
#endif /* #ifdef WINDOWS */
|
|
|
|
|
|
|
|
|
|
/*-----------------------------------------------------
|
|
* InitHwStruct
|
|
*
|
|
* Initialize: Hw[].pCurrentHwMode
|
|
* Hw[].VramAvailable
|
|
* Hw[].DramAvailable
|
|
*------------------------------------------------------*/
|
|
|
|
bool InitHwStruct(byte CurBoard, HwModeData *pHwModeData, word sizeArray,
|
|
dword VramAvailable, dword DramAvailable)
|
|
{
|
|
/* Dynamic allocation of memory if we have more than 1 board */
|
|
|
|
if (NbBoard == 1)
|
|
{
|
|
Hw[CurBoard].pCurrentHwMode = pHwModeData;
|
|
}
|
|
else
|
|
{
|
|
#ifdef WINDOWS_NT
|
|
if(! (Hw[CurBoard].pCurrentHwMode = AllocateSystemMemory(sizeArray)))
|
|
return mtxFAIL;
|
|
Hw[CurBoard].pHwMode = Hw[CurBoard].pCurrentHwMode;
|
|
#else
|
|
if(! (Hw[CurBoard].pCurrentHwMode = malloc(sizeArray)))
|
|
return mtxFAIL;
|
|
#endif
|
|
memcpy(Hw[CurBoard].pCurrentHwMode, pHwModeData, sizeArray);
|
|
}
|
|
|
|
FirstMode[CurBoard] = Hw[CurBoard].pCurrentHwMode;
|
|
Hw[CurBoard].VramAvail = VramAvailable;
|
|
Hw[CurBoard].DramAvail = DramAvailable;
|
|
|
|
return mtxOK;
|
|
}
|
|
|
|
|
|
|
|
|
|
/*-------------------------------------------------------------------
|
|
* mtxSetLUT
|
|
*
|
|
* Initialize RAMDAC LUT
|
|
*
|
|
* Return value:
|
|
* mtxOK - successfull
|
|
* mtxFAIL - failed (not in a LUT mode
|
|
*-------------------------------------------------------------------*/
|
|
bool mtxSetLUT(word index, mtxRGB color)
|
|
{
|
|
|
|
if(! (Hw[iBoard].pCurrentHwMode->DispType & 0x04))
|
|
return mtxFAIL;
|
|
|
|
switch(Hw[iBoard].DacType)
|
|
{
|
|
case BT482:
|
|
mgaWriteBYTE(*(pMgaBaseAddr + RAMDAC_OFFSET + BT482_WADR_PAL),
|
|
(byte)index);
|
|
mgaWriteBYTE(*(pMgaBaseAddr + RAMDAC_OFFSET + BT482_COL_PAL),
|
|
(byte)color);
|
|
mgaWriteBYTE(*(pMgaBaseAddr + RAMDAC_OFFSET + BT482_COL_PAL),
|
|
(byte)(color >> 8));
|
|
mgaWriteBYTE(*(pMgaBaseAddr + RAMDAC_OFFSET + BT482_COL_PAL),
|
|
(byte)(color >> 16));
|
|
break;
|
|
|
|
case BT485:
|
|
case PX2085:
|
|
case VIEWPOINT:
|
|
case TVP3026:
|
|
mgaWriteBYTE(*(pMgaBaseAddr + RAMDAC_OFFSET + BT484_WADR_PAL),
|
|
(byte)index);
|
|
mgaWriteBYTE(*(pMgaBaseAddr + RAMDAC_OFFSET + BT484_COL_PAL),
|
|
(byte)color);
|
|
mgaWriteBYTE(*(pMgaBaseAddr + RAMDAC_OFFSET + BT484_COL_PAL),
|
|
(byte)(color >> 8));
|
|
mgaWriteBYTE(*(pMgaBaseAddr + RAMDAC_OFFSET + BT484_COL_PAL),
|
|
(byte)(color >> 16));
|
|
break;
|
|
|
|
default:
|
|
return mtxFAIL;
|
|
}
|
|
return mtxOK;
|
|
}
|
|
|
|
|
|
|
|
/*---------------------------------------------
|
|
* mtxClose
|
|
* Supported for compatibility. Nothing done
|
|
*---------------------------------------------*/
|
|
void mtxClose(void)
|
|
{
|
|
}
|
|
|
|
|
|
|
|
#ifdef _WINDOWS_DLL16
|
|
/*----------------------------------------------------------
|
|
* mtxLoadSXCI
|
|
*
|
|
* Load SXCI.DLL
|
|
*
|
|
* Return: (mtxOK or mtxFAIL)
|
|
*
|
|
*----------------------------------------------------------*/
|
|
|
|
HANDLE FAR PASCAL _export mtxLoadSXCI(word mode, word FAR *ErrorCode)
|
|
{
|
|
char cBuffer[20];
|
|
|
|
|
|
GetPrivateProfileString("mga.drv","3D","",cBuffer,sizeof(cBuffer),
|
|
"SYSTEM.INI");
|
|
if( (strcmp(cBuffer,"OFF")== 0) && mode == SXCI_3D &&
|
|
(((Hw[iBoard].ProductRev >> 4) & 0x0000000f) == 0) ) /* TITAN */
|
|
{
|
|
*ErrorCode = 101;
|
|
return(0);
|
|
}
|
|
|
|
GetPrivateProfileString("boot","display.drv","",cBuffer,sizeof(cBuffer),
|
|
"SYSTEM.INI");
|
|
if( (strcmp(cBuffer,"mga16.drv")== 0) && mode == SXCI_3D )
|
|
{
|
|
*ErrorCode = 103; /* driver not supported */
|
|
return(0);
|
|
}
|
|
|
|
if( (Hw[iBoard].pCurrentHwMode->ZBuffer == FALSE) && mode == SXCI_3D)
|
|
{
|
|
*ErrorCode = 102;
|
|
return(0);
|
|
}
|
|
|
|
|
|
/*** If pack pixel mode: can't load sxci.dll ***/
|
|
if( Hw[iBoard].pCurrentHwMode->PixWidth == 24)
|
|
{
|
|
*ErrorCode = 104;
|
|
return(0);
|
|
}
|
|
|
|
|
|
|
|
hsxci = LoadLibrary("sxci.dll");
|
|
if(hsxci > 32)
|
|
{
|
|
fp1 = (FARPROC2)GetProcAddress(hsxci, "Win386LibEntry");
|
|
}
|
|
else
|
|
{
|
|
*ErrorCode = 100;
|
|
return(0);
|
|
}
|
|
|
|
pDllMem = (word FAR *)memalloc(30);
|
|
(*fp1)(pDllMem, 31); /* Call PassPoolMem */
|
|
|
|
*(pDllMem+PAN_X) = 0;
|
|
*(pDllMem+PAN_Y) = 0;
|
|
*(pDllMem+PAN_DISP_WIDTH) = Hw[iBoard].pCurrentDisplayMode->DispWidth-1;
|
|
*(pDllMem+PAN_DISP_HEIGHT) = Hw[iBoard].pCurrentDisplayMode->DispHeight-1;
|
|
*(pDllMem+PAN_BOUND_LEFT) = 0;
|
|
*(pDllMem+PAN_BOUND_RIGHT) = 0;
|
|
*(pDllMem+PAN_BOUND_TOP) = 0;
|
|
*(pDllMem+PAN_BOUND_BOTTOM) = 0;
|
|
*(pDllMem+DB_SCALE) = (word)1;
|
|
|
|
*ErrorCode = hsxci;
|
|
NbSxciLoaded++;
|
|
return(hsxci);
|
|
}
|
|
|
|
|
|
|
|
/*----------------------------------------------------------
|
|
* mtxUnloadSXCI
|
|
*
|
|
* Unload SXCI.DLL
|
|
*
|
|
* Return: void
|
|
*
|
|
*----------------------------------------------------------*/
|
|
|
|
void FAR PASCAL _export mtxUnloadSXCI(void)
|
|
{
|
|
if(NbSxciLoaded)
|
|
{
|
|
if(NbSxciLoaded == 1)
|
|
memfree((void FAR **)&pDllMem);
|
|
FreeLibrary(hsxci);
|
|
NbSxciLoaded--;
|
|
}
|
|
}
|
|
|
|
#endif /* #ifdef _WINDOWS_DLL16 */
|
|
|
|
|
|
|
|
|
|
/*----------------------------------------------------------
|
|
* ProgrammeClock
|
|
*
|
|
* Set clock according of new strapping: (50MHz, 55MHz or 60MHz)
|
|
* VD34, VD33 -> MGA-PCI/2 and MGA-VLB/2
|
|
* VD49, VD36 -> MGA-PCI/2+ and MGA-VLB/2+
|
|
*
|
|
* For TITAN -> 45MHz
|
|
*----------------------------------------------------------*/
|
|
|
|
bool ProgrammeClock(byte Chip, dword Dst1, dword InfoDac)
|
|
{
|
|
dword Value;
|
|
dword ValClock;
|
|
byte TmpByte;
|
|
|
|
if( (Chip == ATLAS_CHIP) || (Chip == ATHENA_CHIP))
|
|
{
|
|
if ((Hw[iBoard].ProductType & 0x0f) == BOARD_MGA_RESERVED)
|
|
{
|
|
ValClock = 0x065AC3D; /* 50MHz */
|
|
}
|
|
|
|
/*** Detect if MGA-PCI/2+ or MGA-VLB/2+ ***/
|
|
else if( ((ProductMGA[iBoard] == MGA_PCI_2M) ||
|
|
(ProductMGA[iBoard] == MGA_PCI_4M)) &&
|
|
(InfoDac == Info_Dac_ViewPoint))
|
|
{
|
|
Value = ((Dst1 & TITAN_DST1_NOMUXES_M) >>
|
|
(TITAN_DST1_NOMUXES_A-1)) |
|
|
((Dst1 & TITAN_DST1_ABOVE1280_M) >>
|
|
TITAN_DST1_ABOVE1280_A);
|
|
|
|
switch(Value)
|
|
{
|
|
case 3:
|
|
ValClock = 0x065AC3D; /* 50MHz */
|
|
break;
|
|
case 2:
|
|
ValClock = 0x068A413; /* 60MHz */
|
|
break;
|
|
case 0:
|
|
ValClock = 0x067D83D; /* 55MHz */
|
|
break;
|
|
default:
|
|
return(mtxFAIL);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
Value = (Dst1 & TITAN_DST1_RAMSPEED_M) >> TITAN_DST1_RAMSPEED_A;
|
|
|
|
switch(Value)
|
|
{
|
|
case 0:
|
|
ValClock = 0x065AC3D; /* 50MHz */
|
|
break;
|
|
case 1:
|
|
ValClock = 0x068A413; /* 60MHz */
|
|
break;
|
|
case 3:
|
|
ValClock = 0x067D83D; /* 55MHz */
|
|
break;
|
|
default:
|
|
return(mtxFAIL);
|
|
}
|
|
}
|
|
}
|
|
else /* TITAN */
|
|
{
|
|
ValClock = 0x0063AC44; /* 45MHz */
|
|
}
|
|
|
|
/* Lookup for find real frequency to progrmming */
|
|
switch( ValClock )
|
|
{
|
|
case 0x063AC44: presentMclk[iBoard] = 45000000L; /* 45Mhz */
|
|
break;
|
|
|
|
case 0x065AC3D: presentMclk[iBoard] = 50000000L; /* 50Mhz */
|
|
break;
|
|
|
|
case 0x067D83D: presentMclk[iBoard] = 55000000L; /* 55Mhz */
|
|
break;
|
|
|
|
case 0x068A413: presentMclk[iBoard] = 60000000L; /* 60Mhz */
|
|
break;
|
|
|
|
case 0x06d4423: presentMclk[iBoard] = 65000000L; /* 65Mhz */
|
|
break;
|
|
|
|
case 0x06ea410: presentMclk[iBoard] = 70000000L; /* 70Mhz */
|
|
break;
|
|
|
|
case 0x06ed013: presentMclk[iBoard] = 75000000L; /* 75Mhz */
|
|
break;
|
|
|
|
case 0x06f7020: presentMclk[iBoard] = 80000000L; /* 80Mhz */
|
|
break;
|
|
|
|
case 0x071701e: presentMclk[iBoard] = 85000000L; /* 85Mhz */
|
|
break;
|
|
|
|
case 0x074fc13: presentMclk[iBoard] = 90000000L; /* 90Mhz */
|
|
break;
|
|
|
|
default: ValClock = 0x065AC3D;
|
|
presentMclk[iBoard] = 50000000L; /* 50Mhz */
|
|
}
|
|
|
|
if(InfoDac == Info_Dac_TVP3026)
|
|
{
|
|
setTVP3026Freq(pMgaBaseAddr, presentMclk[iBoard] / 1000L, 3, 0);
|
|
}
|
|
else
|
|
{
|
|
/*** Program MCLOCK ***/
|
|
mgaReadBYTE(*(pMgaBaseAddr+TITAN_OFFSET+TITAN_MISC_OUT_R), TmpByte);
|
|
programme_reg_icd ( pMgaBaseAddr, 3, ValClock );
|
|
mgaWriteBYTE(*(pMgaBaseAddr+TITAN_OFFSET+TITAN_MISC_ISTAT0), TmpByte);
|
|
delay_us(10000);
|
|
}
|
|
|
|
return(mtxOK);
|
|
}
|