/*DDK*************************************************************************/
/*                                                                           */
/* COPYRIGHT    Copyright (C) 1995 IBM Corporation                           */
/*                                                                           */
/*    The following IBM OS/2 WARP source code is provided to you solely for  */
/*    the purpose of assisting you in your development of OS/2 WARP device   */
/*    drivers. You may use this code in accordance with the IBM License      */
/*    Agreement provided in the IBM Device Driver Source Kit for OS/2. This  */
/*    Copyright statement may not be removed.                                */
/*                                                                           */
/*****************************************************************************/
/**********************************************************************/
/*                                                                    */
/*   File            = EDDEFLDB                                       */
/*                                                                    */
/*   Description     = Enable : subfunction Fill lDeviceBlock         */
/*                                                                    */
/*   Function        = FillLdb performs the required device driver    */
/*                     global functions                               */
/*                                                                    */
/*   Reference       = Winthorn Functional Specification              */
/*                     Device Driver Interface Specification          */
/*                     Display Device Driver Design Specification     */
/*                                                                    */
/*                                                                    */
/**********************************************************************/
/**********************************************************************/
/* Lots of include files because this module fills in the dispatch    */
/* table !!!                                                          */
/**********************************************************************/
#define INCL_WINSHELLDATA
#define INCL_GREALL
#define INCL_DOSDEVICES
#define INCL_DOSMODULEMGR
#define INCL_DDIMISC
#define INCL_DDIPATHS
#define INCL_WINSYS
#define INCL_DOSPROCESS
#define INCL_DOSRESOURCES
#define INCL_DOSERRORS
#include <eddinclt.h>

#include <eddvcone.h>
#include <eddecone.h>

#include <edddtypt.h>
#include <eddetypt.h>

#include <eddaextf.h>
#include <eddbextf.h>
#include <eddcextf.h>
#include <eddeextf.h>
#include <eddgextf.h>
#include <eddlextf.h>
#include <eddmextf.h>
#include <eddqextf.h>
#include <eddsextf.h>
#include <eddtextf.h>
#include <eddvextf.h>

#include <twozero.h>
#include <memman.h>
#ifdef VRAMPTR
#include <eddncach.h>
#endif /* VRAMPTR */

#ifdef INCL_PERFTEST
#include <perftest.h>
#endif

#ifdef DCAF                                                               //DCAF
#include <dcaf.h>                                                         //DCAF
#endif                                                                    //DCAF

#ifdef DBCS                                                 
#include <eddjdef.h>                                        
#include <eddjfm.h>                                         
#include <eddjinit.h>                                       
#include <eddjfont.h>                                       
extern ULONG                    ulSysFontId;                
#endif 

extern HMODULE              hModule;

extern AvioFontTableType    AvioBaseFont[NO_OF_AVIO_FONTS];

extern DDTType              DDT;

extern HMODULE              font_hmod;

ULONG   NotFirst = FALSE;
#if defined   MEMMAPIO || BPP24
ULONG   flVRAMFirst = 0;
ULONG   pVRAM = 0xffffffff;
HFILE    hSVGA;
ULONG    ulAction;
CHAR     szSQ[32] = "\\DEV\\SINGLEQ$";
#include <8514.h>
#endif

#ifdef FIREWALLS
CHAR achInts[2] = {'\0'};
#endif /* FIREWALLS */

#ifdef _8514
DDIENTRY anobody_home ( VOID );

#pragma
struct _OS2_PM_DRV_ENABLE_LEVELS
{
   UCHAR ring[17];
} _pascal OS2_PM_DRV_ENABLE_LEVELS = {2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,0};

struct _OS2_PM_DRV_RING_LEVELS
{
   UCHAR ring[257];
} _pascal OS2_PM_DRV_RING_LEVELS = {1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
                                    1,1,2,2,2,1,2,2,2,2,2,2,2,2,2,1,
                                    1,1,2,2,2,2,2,2,2,2,2,1,2,1,2,2,
                                    2,2,2,1,1,2,2,1,1,1,2,2,2,2,2,1,
                                    1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
                                    1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
                                    1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
                                    1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
                                    1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
                                    1,1,1,1,1,1,1,1,1,1,1,1,1,2,2,1,
                                    2,1,2,2,2,2,2,2,2,2,2,1,2,2,2,2,
                                    2,1,1,2,2,2,2,2,2,1,2,2,2,2,2,1,
                                    1,1,1,2,2,2,2,2,2,2,2,2,1,1,1,1,
                                    1,1,2,1,1,2,2,2,2,2,2,2,2,2,1,1,0};

#if defined   MEMMAPIO || BPP24
typedef struct  SCRNTX
{
        ULONG stx_Address;
        ULONG stx_Size;
        ULONG stx_flFlag;
} SCRNTX;

typedef struct  SCRNRX
{
        ULONG srx_ScrnPtr;
} SCRNRX;
#endif

#endif  // memmapio || bpp24

PPFNL   EnginesDispatchTable;
PFNL    DriversDispatchTable[] = {
    0,                               //GreGetArcParameters          0x4000
    0,                               //GreSetArcParameters          0x4001
    0,                               //GreArc                       0x4002
    0,                               //GrePartialArc                0x4003
    0,                               //GreFullArcInterior           0x4004
    0,                               //GreFullArcBoundary           0x4005
    0,                               //GreFullArcBoth               0x4006
    0,                               //GreBoxInterior               0x4007
    0,                               //GreBoxBoundary               0x4008
    0,                               //GreBoxBoth                   0x4009
    0,                               //GrePolyFillet                0x400A
    0,                               //GrePolyFilletSharp           0x400B
    0,                               //GrePolySpline                0x400C
    0,                               //GreDrawConicsInPath          0x400D
    0,                               //GreCookWholePath             0x400E
    0,                               //GreCookPathCurves            0x400F
    0,                               //                             0x4010
    0,                               //GreRenderPath                0x4011
#ifdef DCAF                                                               //DCAF
    OpenScreenChangeArea,            //GreOpenScreenChangeArea      0x4012//DCAF
    GetScreenChangeArea,             //GreGetScreenChangeArea       0x4013//DCAF
    CloseScreenChangeArea,           //GreCloseScreenChangeArea     0x4014//DCAF
#else                                                                     //DCAF
    0,                               //                             0x4012
    0,                               //                             0x4013
    0,                               //                             0x4014
#endif                                                                    //DCAF
    0,                               //                             0x4015
    eddl_PolyLine,                   //GreDisjointLines             0x4016
    eddl_GetCurrentPosition,         //GreGetCurrentPosition        0x4017
    eddl_SetCurrentPosition,         //GreSetCurrentPosition        0x4018
    eddl_PolyLine,                   //GrePolyLine                  0x4019
    eddl_DrawLinesInPath,            //GreDrawLinesInPath           0x401A
    eddl_PolyShortLine,              //GrePolyShortLine             0x401B
    edds_PolyScanLine,               //GrePolyScanline              0x401C
#ifdef DCAF                                                               //DCAF
    GetScreenBits,                   //GreGetScreenBits             0x401D//DCAF
    SetScreenBits,                   //GreSetScreenBits             0x401E//DCAF
#else                                                                     //DCAF
    0,                               //                             0x401D
    0,                               //                             0x401E
#endif                                                                    //DCAF
    0,                               //                             0x401F
    0,                               //                             0x4020
    0,                               //                             0x4021
    DrawBits,                        //GreDrawBits                  0x6022
    eddb_DeviceCreateBitmap,         //GreDeviceCreateBitmap        0x6023
    eddb_DeviceDeleteBitmap,         //GreDeviceDeleteBitmap        0x4024
    eddb_DeviceSelectBitmap,         //GreDeviceSelectBitmap        0x4025
    eddb_BitBlt,                     //GreBitblt                    0x6026
    eddb_GetPel,                     //GreGetPel                    0x6027
    eddb_SetPel,                     //GreSetPel                    0x4028
    eddb_ImageData,                  //GreImageData                 0x4029
    ScanLR,                          //GreScanLR                    0x602A
    0,                               //GreFloodFill                 0x602B
    eddm_SaveScreenBits,             //GreSaveScreenBits            0x402C
    0,                               //GreRestoreScreenBits         0x402D
    eddb_DrawBorder,                 //GreDrawBorder                0x602E
    eddm_DeviceSetCursor,            //GreDeviceSetCursor           0x402F
    GetBitmapBits,                   //GreGetBitmapBits             0x6030
    SetBitmapBits,                   //GreSetBitmapBits             0x6031
    eddm_SetColorCursor,             //GreSetColorCursor            0x4032
    0,                               //                             0x4033
    0,                               //                             0x4034
    eddt_CharString,                 //GreCharString                0x5035
    eddt_CharStringPos,              //GreCharStringPos             0x7036
#ifndef DBCS                                                
    0,                               //GreQueryTextBox              0x5037
    0,                               //GreQueryCharPositions        0x5038
    0,                               //GreQueryWidthTable           0x5039
#else 
    eddt_QueryTextBox,               //GreQueryTextBox              0x5037
    eddt_QueryCharPositions,         //GreQueryCharPositions        0x5038
    eddt_QueryWidthTable,            //GreQueryWidthTable           0x5039
#endif 
    eddb_PolyMarker,                 //GrePolyMarker                0x403A
    eddv_CharRect,                   //GreCharRect                  0x403B
    eddv_CharStr,                    //GreCharStr                   0x403C
    eddv_ScrollRect,                 //GreScrollRect                0x403D
    eddv_UpdateCursor,               //GreUpdateCursor              0x403E
    0,                               //                             0x403F
    0,                               //                             0x4040
    0,                               //                             0x4041
    0,                               //                             0x4042
    0,                               //                             0x4043
    0,                               //                             0x4044
    0,                               //                             0x4045
    0,                               //GreBeginArea                 0x4046
    0,                               //GreEndArea                   0x4047
    0,                               //GreBeginPath                 0x4048
    0,                               //GreEndPath                   0x4049
    0,                               //GreCloseFigure               0x404A
    0,                               //GreFillPath                  0x404B
    0,                               //GreOutlinePath               0x404C
    0,                               //GreModifyPath                0x404D
    0,                               //GreStrokePath                0x404E
    0,                               //GreSelectClipPath            0x404F
    0,                               //GreSavePath                  0x4050
    0,                               //GreRestorePath               0x4051
    0,                               //GreClip1DPath                0x4052
    0,                               //GreDrawRawPath               0x4053
    0,                               //GreDrawCookedPath            0x4054
    0,                               //GreAreaSetAttributes         0x6055
    0,                               //GrePolygon                   0x4056
    0,                               //GrePathToRegion              0x4057
    0,                               //GreDrawRLE                   0x4058
    0,                               //                             0x4059
    0,                               //                             0x405A
    0,                               //                             0x405B
    0,                               //                             0x405C
    0,                               //GreGetRegionBox              0x405D
    0,                               //GreGetRegionRects            0x405E
    0,                               //GreOffsetRegion              0x405F
    0,                               //GrePtInRegion                0x4060
    0,                               //GreRectInRegion              0x4061
    0,                               //GreCreateRectRegion          0x4062
    0,                               //GreDestroyRegion             0x4063
    0,                               //GreSetRectRegion             0x4064
    0,                               //GreCombineRegion             0x4065
    0,                               //GreCombineRectRegion         0x4066
    0,                               //GreCombineShortLineRegion    0x4067
    0,                               //GreEqualRegion               0x4068
    0,                               //GrePaintRegion               0x4069
    0,                               //GreSetRegionOwner            0x406A
    0,                               //GreFrameRegion               0x406B
    0,                               //                             0x406C
    0,                               //                             0x406D
    0,                               //GreGetClipBox                0x406E
    0,                               //GreGetClipRects              0x406F
    0,                               //GreOffsetClipRegion          0x4070
    0,                               //GrePtVisible                 0x4071
    0,                               //GreRectVisible               0x4072
    0,                               //GreQueryClipRegion           0x4073
    0,                               //GreSelectClipRegion          0x4074
    0,                               //GreIntersectClipRectangle    0x4075
    0,                               //GreExcludeClipRectangle      0x4076
    0,                               //GreSetXformRect              0x4077
    0,                               //                             0x4078
    0,                               //                             0x4079
    0,                               //                             0x407A
    0,                               //GreSaveRegion                0x407B
    0,                               //GreRestoreRegion             0x407C
    0,                               //GreClipPathCurves            0x407D
    0,                               //GreSelectPathRegion          0x407E
    0,                               //GreRegionSelectBitmap        0x407F
    0,                               //GreCopyClipRegion            0x4080
    0,                               //GreSetupDC                   0x4081
    0,                               //                             0x4082
    0,                               //GreGetPageUnits              0x4083
    0,                               //GreSetPageUnits              0x4084
    0,                               //GreGetModelXform             0x4085
    0,                               //GreSetModelXform             0x4086
    0,                               //GreGetWindowViewportXform    0x4087
    0,                               //GreSetWindowViewportXform    0x4088
    0,                               //GreGetGlobalViewingXform     0x4089
    0,                               //GreSetGlobalViewingXform     0x408A
    0,                               //GreSaveXformData             0x408B
    0,                               //GreRestoreXformData          0x408C
    0,                               //GreGetPageViewport           0x408D
    0,                               //GreSetPageViewport           0x408E
    0,                               //                             0x408F
    0,                               //                             0x4090
    0,                               //GreGetGraphicsField          0x4091
    0,                               //GreSetGraphicsField          0x4092
    0,                               //GreGetViewingLimits          0x4093
    0,                               //GreSetViewingLimits          0x4094
    0,                               //GreQueryViewportSize         0x4095
    0,                               //GreConvert                   0x4096
    0,                               //GreConvertPath               0x4097
    0,                               //GreSaveXform                 0x4098
    0,                               //GreRestoreXform              0x4099
    0,                               //GreMultiplyXforms            0x409A
    0,                               //GreConvertWithMatrix         0x409B
    0,                               //                             0x409C
    edda_DeviceGetAttributes,        //GreDeviceGetAttributes       0x609D
    eddv_DeviceSetAVIOFont2,         //GreDeviceSetAVIOFont2        0x409E
    0,                               //                             0x409F
    edda_GetPairKerningTable,        //GreGetPairKerningTable       0x40A0
    0,                               //GreDeviceSetAVIOFont         0x40A1
    edda_DeviceSetAttributes,        //GreDeviceSetAttributes       0x60A2
    edda_DeviceSetGlobalAttribute,   //GreDeviceSetGlobalAttribute  0x60A3
    edda_NotifyClipChange,           //GreNotifyClipChange          0x40A4
    eddm_NotifyTransformChange,      //GreNotifyTransformChange     0x40A5
    edda_RealizeFont,                //GreRealizeFont               0x40A6
    eddm_ErasePS,                    //GreErasePS                   0x40A7
    eddl_SetStyleRatio,              //GreSetStyleRatio             0x40A8
    edda_DeviceQueryFontAttributes,  //GreDeviceQueryFontAttributes 0x40A9
    edda_DeviceQueryFonts,           //GreDeviceQueryFonts          0x40AA
    edda_DeviceInvalidateVisRegion,  //GreDeviceInvalidateVisRegion 0x40AB
    eddg_GetPickWindow,              //GreGetPickWindow             0x40AC
    eddg_SetPickWindow,              //GreSetPickWindow             0x40AD
    eddg_ResetBounds,                //GreResetBounds               0x40AE
    eddg_GetBoundsData,              //GreGetBoundsData             0x40AF
    eddg_AccumulateBounds,           //GreAccumulateBounds          0x40B0
    0,                               //GreGetExtraError             0x40B1
    0,                               //GreSetExtraError             0x40B2
    edda_GetCodePage,                //GreGetCodePage               0x40B3
    edda_SetCodePage,                //GreSetCodePage               0x40B4
    eddm_LockDevice,                 //GreLockDevice                0x40B5
    eddm_UnlockDevice,               //GreUnlockDevice              0x40B6
    eddm_Death,                      //GreDeath                     0x40B7
    eddm_Resurrection,               //GreResurrection              0x40B8
    0,                               //                             0x40B9
    edda_GetDCOrigin,                //GreGetDCOrigin               0x40BA
    edda_DeviceSetDCOrigin,          //GreDeviceSetDCOrigin         0x40BB
    eddl_GetLineOrigin,              //GreGetLineOrigin             0x40BC
    eddl_SetLineOrigin,              //GreSetLineOrigin             0x40BD
    eddl_GetStyleRatio,              //GreGetStyleRatio             0x40BE
    0,                               //                             0x40BF
    0,                               //                             0x40C0
    0,                               //                             0x40C1
    0,                               //                             0x40C2
    eddc_QueryColorData,             //GreQueryColorData            0x60C3
    eddc_QueryLogColorTable,         //GreQueryLogColorTable        0x60C4
    eddc_CreateLogColorTable,        //GreCreateLogColorTable       0x60C5
    eddc_RealizeColorTable,          //GreRealizeColorTable         0x60C6
    eddc_UnrealizeColorTable,        //GreUnrealizeColorTable       0x60C7
    eddc_QueryRealColors,            //GreQueryRealColors           0x40C8
    eddc_QueryNearestColor,          //GreQueryNearestColor         0x40C9
    eddc_QueryColorIndex,            //GreQueryColorIndex           0x60CA
    eddc_QueryRGBColor,              //GreQueryRGBColor             0x60CB
    0,                               //                             0x40CC
    0,                               //                             0x40CD
    0,                               //                             0x40CE
    0,                               //                             0x40CF
    eddq_QueryDeviceBitmaps,         //GreQueryDeviceBitmaps        0x40D0
    eddq_QueryDeviceCaps,            //GreQueryDeviceCaps           0x40D1
    eddq_Escape,                     //GreEscape                    0x40D2
    eddq_QueryHardcopyCaps,          //GreQueryHardcopyCaps         0x40D3
    eddm_QueryDevResource,           //GreQueryDevResource2         0x40D4
    DeviceCreatePalette,             //GreDeviceCreatePalette       0x40D5
    DeviceDeletePalette,             //GreDeviceDeletePalette       0x40D6
    DeviceSetPaletteEntries,         //GreDeviceSetPaletteEntries   0x40D7
    DeviceAnimatePalette,            //GreDeviceAnimatePalette      0x40D8
    DeviceResizePalette,             //GreDeviceResizePalette       0x40D9
    RealizePalette,                  //GreRealizePalette            0x40DA
    QueryHWPaletteInfo,              //GreQueryHWPaletteInfo        0x40DB
    UpdateColors,                    //GreUpdateColors              0x40DC
    QueryPaletteRealization,         //GreQueryPaletteRealization   0x40DD
    0,                               //GreGetVisRects               0x40DE
    0                                //GreDevicePolySet             0x40DF
};

/**********************************************************************/
/* FillLdb performs the following operations:                         */
/*        Notify the DosExitList of the DD termination routine        */
/*        Create the global device driver heap                        */
/*        Put our function addresses in the engine's dispatch table   */
/*        Inform the engine about the type of the device driver       */
/**********************************************************************/

USHORT FillLdb (pFLParamsLst   param1,
                pFLReturnsLst  param2)

{
    /******************************************************************/
    /* Local variables                                                */
    /******************************************************************/
    ULONG           Result;            /* result of called functions  */
    ULONG           i;                 /* loop control variable       */
    ULONG           last_avio_font;
    CHAR               achFailName[128];
    PVOID           DummyAddress;      /* For the ret from DosGetRes2 */
    PPFNL           DispTab;            /* pointer to start of        */
                                                       /* engines dispatch table      */

#ifdef FIREWALLS
    if ( NEW_PROCESS_INT_ENABLED )
    {
       haltproc();
    }
#endif /* FIREWALLS */

    /******************************************************************/
    /* Add the Enable Termination routine to this application's       */
    /* DosExitList, so that this Dynamic Link Library gets control    */
    /* when the application terminates (normally or abnormally).      */
    /* The first exit list function is called immediately at          */
    /* termination so that semaphores locked by the terminating       */
    /* process can be freed.                                          */
    /* The second is called later after the application and engine    */
    /* exit lists to allow any necessary tidying up.                  */
    /******************************************************************/
    Result = DosExitList(EXLST_ADD | EXLST_PRTY_UNLOCK,
                         (PFNEXITLIST)Unlock_Termination);
    if ((Result != NO_ERROR) &&
        (Result != ERROR_ALREADY_EXISTS))
    {
        LogDosError(Result);
        goto FILLLDB_ERR_EXIT;
    }

    Result = DosExitList(EXLST_ADD | EXLST_PRTY_PMDRIVERS,
                         (PFNEXITLIST)TidyUp_Termination);
    if ((Result != NO_ERROR) &&
        (Result != ERROR_ALREADY_EXISTS))
    {
        LogDosError(Result);
        goto FILLLDB_ERR_EXIT;
    }

#ifdef  INCL_PERFTEST
    /******************************************************************/
    /* Performance testing required - get access to semaphores        */
    /******************************************************************/
    PTSemInit();
#endif /* INCL_PERFTEST */

    /******************************************************************/
    /* Get access to the driver semaphore.                            */
    /******************************************************************/
    OpenDriverSemaphore();


    /******************************************************************/
    /* We handle this call differently dependant on whether this      */
    /* is the first call to it or not.                                */
    /******************************************************************/
    if ( NotFirst )
    {
#ifdef MATROX
        /**************************************************************/
        /* Get access to the screen bitmap in VRAM for this process.  */
        /**************************************************************/
        AccessVRAMBitmap();
#endif /* MATROX */

        /**************************************************************/
        /* AVIO fonts have been loaded from resources.                */
        /* Give the process access to all of them.                    */
        /**************************************************************/
        /**************************************************************/
        /* Load the dll containing the fonts                          */
        /**************************************************************/
        Result = DosLoadModule(achFailName,
                               sizeof(achFailName),
                               RESOURCE_DLL,
                               &font_hmod);

        if ( Result != NO_ERROR )
        {
            DebugOutput("XGA: Unable to load font DLL\n\r");
            LogDosError(Result);
            return(ERROR_ZERO);
        }

#ifdef DBCS                                                 
        /*============================================================*/
        /* This font (SBCS Sys. Proportional) is the only SBCS font   */
        /* which is loaded and available even when the driver is      */
        /* working as DBCS driver.  See eddj_SetupDBCSFontInformation.*/
        /*============================================================*/
        DosGetResource(font_hmod,
                       1000,
                       ulSysFontId,
                       &DummyAddress);

        /*============================================================*/
        /* If this driver is running as DBCS-capable driver (even if  */
        /* system default CP is SBCS), all AVIO fonts are managed by  */
        /* DBCS Font Manager.   So we need to do different preparation*/
        /* in this case...                                            */
        /*============================================================*/
        if (CHECKENV(ENV_DBCS_CAPABLE))/* if DBCS suuport is enabled  */
        {
            eddj_ValidateSystemFont(); /* prepare DBCS FM/Fonts for   */
                                       /*   this process.             */
                                       /*   returns no error.         */
        }
        else                           /* or if running as pure       */
        {                              /*   SBCS driver...            */
#endif                                                      
        if ( DDT.ScreenWidth < HI_RES_WIDTH )
        {
          i = 0;
          last_avio_font = MAX_AVIO_FONTS_LOADED;
        }
        else
        {
          i = NO_OF_AVIO_FONTS - MAX_AVIO_FONTS_LOADED;
          last_avio_font = MAX_AVIO_FONTS_LOADED + i;
        }
        for ( ; i < last_avio_font; i++)
        {
            DosGetResource(font_hmod,
                           AvioBaseFont[i].ResourceType,
                           AvioBaseFont[i].ResourceName,
                           &DummyAddress );
        }

#ifdef DBCS                                                 
        }
#endif                                                      
    }
    else /* first time */
    {
#ifdef FIREWALLS
        PrfQueryProfileString( HINI_PROFILE,
                               "PM_IBMXGA",
                               "INT3",
                               "",
                               achInts,
                               2 );
        if ( FIRST_TIME_INT_ENABLED )
        {
           haltproc();
        }
#endif /* FIREWALLS */

#ifdef TMP                                                  
      {                                /* needed to define vars       */
        /**************************************************************/
        /* This is temporary fix for J200-47...                       */
        /**************************************************************/
        extern ULONG InitPID;          /* init time process ID        */

        PTIB ptib;                     /* ptr to thread info block    */
        PPIB ppib;                     /* ptr to process info block   */
        ULONG   ulOpenAction;

        DosGetInfoBlocks (&ptib, &ppib );/* get current process ID    */

        if (ppib->pib_ulpid != InitPID)/* if other process has loaded */
        {                              /* this DLL... This actually   */
                                       /* happend for J200-47...      */
          #ifndef _8514                                     
            OpenDriverSemaphore();

            DosOpen ("\\DEV\\$$$XGA20",
                     &aiXGAAdapter.hfDevHandle,
                     &ulOpenAction,
                     0L,
                     FILE_SYSTEM,
                     FILE_OPEN,
                     OPEN_FLAGS_WRITE_THROUGH | OPEN_SHARE_DENYNONE
                       | OPEN_ACCESS_READWRITE,
                     0L );
          #else 
            _asm
            {
            int 3
            }
          #endif 
        }
      }
#endif 

        /**************************************************************/
        /* We need to know the bitcount we are running at.            */
        /*                                                            */
        /* This used to be determined at FillPhysicalDeviceBlock      */
        /* time.                                                      */
        /*                                                            */
        /* However we need to know it now, so we will call the old    */
        /* routine from here, and FillPDB called by the engine will   */
        /* be able to return without doing anything!                  */
        /**************************************************************/
        FillPdb();

#ifdef VRAMPTR
        if ( !initialise_bm_cache() )
        {
            return(ERROR_ZERO);
        }
#endif /* VRAMPTR */

        /**************************************************************/
        /* We now have determined what configuration to run at, and   */
        /* can thus determine what entries in the dispatch table we   */
        /* dont actually wish to hook.                                */
        /**************************************************************/
        if (DDT.BitCount != 8)
        {
            /**********************************************************/
            /* We are not 8 bpp so we wont hook the palette manager   */
            /* entry points.                                          */
            /* We therefore null out the entries in our table.        */
            /**********************************************************/
            DriversDispatchTable[NGreDeviceCreatePalette     & 0xff] = 0;
            DriversDispatchTable[NGreDeviceDeletePalette     & 0xff] = 0;
            DriversDispatchTable[NGreDeviceSetPaletteEntries & 0xff] = 0;
            DriversDispatchTable[NGreDeviceAnimatePalette    & 0xff] = 0;
            DriversDispatchTable[NGreDeviceResizePalette     & 0xff] = 0;
            DriversDispatchTable[NGreRealizePalette          & 0xff] = 0;
            DriversDispatchTable[NGreQueryHWPaletteInfo      & 0xff] = 0;
            DriversDispatchTable[NGreUpdateColors            & 0xff] = 0;
            DriversDispatchTable[NGreQueryPaletteRealization & 0xff] = 0;
        }
    }

    #if defined   MEMMAPIO | BPP24
    GetVRAMPointer( MEMMAPADDR , MEMMAPLENGTH , &flVRAMFirst , &pVRAM );
    #endif

    DispTab = param2->DispTab;
    if (DispTab != NULL)
    {
        /**************************************************************/
        /* Take our copies of the entries we need for simulations     */
        /* before we change any of the values.                        */
        /**************************************************************/
        if ( NotFirst == FALSE)
        {
            /**********************************************************/
            /* Take a copy of all the entries the engine has passed   */
            /* us.                                                    */
            /* This table size may change, so we dont use static      */
            /* data for it.                                           */
            /**********************************************************/
            EnginesDispatchTable = AllocateMemory(param1->TableSize * 4,
                                                  MT_DISPATCH_TABLE,
                                                  MO_SHARED);
            for (i=0; i<param1->TableSize; i++)
            {
                EnginesDispatchTable[i] = DispTab[i];
            }
        }

        /**************************************************************/
        /* Find the number of entries in our table                    */
        /**************************************************************/
        i = sizeof(DriversDispatchTable) / sizeof(DriversDispatchTable[0]);

        /**************************************************************/
        /* We must only pass back as many entries as the caller       */
        /* wants                                                      */
        /**************************************************************/
        if (i > param1->TableSize)
        {
            i = param1->TableSize;
        }

        while(--i)
        {
            /**********************************************************/
            /* If we hook this, then pass back our address            */
            /**********************************************************/
            if (DriversDispatchTable[i])
            {
                DispTab[i] = DriversDispatchTable[i];
            }
        }
    }

    /******************************************************************/
    /* Ensure that we know we have been through the code at least     */
    /* once.                                                          */
    /******************************************************************/
    NotFirst = TRUE;

    /******************************************************************/
    /* Set the flags to show that we want:                            */
    /*   bit 0 = 0 => single physical device block required           */
    /*   bit 1 = 0 => an arbitary number of DCs can co-exist          */
    /*   bit 2 = 1 => the device and file name fields of OpenDevDc    */
    /*                are not significant, and should be ignored.     */
    /* All other bits are reserved and should not be modified.        */
    /******************************************************************/
    *(param2->Flags) &= 0xFFFFFFF8;
    *(param2->Flags) |= 0x00000004;

    return(OK);

FILLLDB_ERR_EXIT:
    return(ERROR_ZERO);
}

#ifdef _8514
/**********************************************************************/
/* FillLdb performs the following operations:                         */
/*        Notify the DosExitList of the DD termination routine        */
/*        Create the global device driver heap                        */
/*        Put our function addresses in the engine's dispatch table   */
/*        Inform the engine about the type of the device driver       */
/**********************************************************************/

DDIENTRY anobody_home ( VOID )
{
    _asm
    {
       mov ax,0
       int 3
       // might put in debug output
    }
    return(1L);
}

#if defined   MEMMAPIO | BPP24
/***************************************************************************
*
* FUNCTION NAME = GetVRAMPointer
*
* DESCRIPTION   = Uses an Ioctl to get a pointer to VRAM.
*
* INPUT         =
* OUTPUT        =
*
* RETURN-NORMAL =
* RETURN-ERROR  =
*
**************************************************************************/

ULONG GetVRAMPointer ( ULONG ulAddr , ULONG ulSize , PULONG pulFirst , PULONG  ppVRAM )
{

SCRNTX   scrnTx;
SCRNRX   scrnRx;
BOOL     fAttach;
USHORT   usAction;

   if (DosOpen( szSQ , &hSVGA , &ulAction , 0, 0, 1, 0x00c0, 0))
   {
      goto   getvram_exit;
   }

   scrnTx.stx_Address = ulAddr;
   scrnTx.stx_Size = ulSize;
   scrnTx.stx_flFlag = 0;

   if ( !*pulFirst ) {
      fAttach = 0;
      usAction = 0x007e;
      *pulFirst = 1;
   }
   else
   {
      usAction = 0x007f;
      scrnTx.stx_Address = *ppVRAM;
      fAttach = 1;
   }

   if ( !DosDevIOCtl( hSVGA, 3, usAction, &scrnTx, sizeof(SCRNTX),
                     0, &scrnRx, sizeof(SCRNRX), 0) )
   {
      if ( fAttach == 0)
      {
         *ppVRAM = scrnRx.srx_ScrnPtr;
      }
   }

   DosClose( hSVGA );

getvram_exit:
   return( 1L );

}
#endif
#endif
