/*
 #########################################################################
 ## Driver installation program for Windows 95/98/NT/2000               ##
 ##                 Dialog module ( linked with INSTDRV.C )             ##
 ##                                             (C) Aktiv Co. 1997-2001 ##
 #########################################################################
*/

#include <windows.h>
#include <stdio.h>
#include <ctype.h>

#include "instdrv.h"
#include "inststr.h"
#include "instdrvs.h"
#include "instdrvf.h"


#define PORT_PRESENT(a)  (bPort&(1<<a))

extern void TryToExitWindows        ( void );
extern BOOL IsXDigitStr				(char *szStr, BYTE byLen);
extern char* RS                     ( int  );

int          CheckDriver            ( void );
void         SetPortSettings        ( HWND, int );
void         SetAvailiblePorts      ( HWND );
void         EnableChecks           ( HWND, int, int );
BOOL         CheckEditBox           ( HWND, int, float, float, float*, int );
BOOL         CheckEditBoxInt        ( HWND, int, int, int, int*, int );
BOOL 		 CheckEditBoxIntHex	    (HWND hWnd,int IDC,int min,int max,int * Res,int MsgID);
BOOL         SetupFriendlyLPTNames  ( void );
void         ShowAlert              ( HWND, int );
void         CheckRadio             ( HWND, int );
void         EnableRadios           ( HWND, int, int, int );

BOOL _export CALLBACK ConfigDlgProc95     ( HWND, UINT, WPARAM, LPARAM);
BOOL _export CALLBACK ConfigDlgProcNT     ( HWND, UINT, WPARAM, LPARAM);
BOOL _export CALLBACK AdvancedDlgProc     ( HWND, UINT, WPARAM, LPARAM);
BOOL _export CALLBACK MsgDlgProc          ( HWND, UINT, WPARAM, LPARAM);


struct _CFG_CRC    // Structure for storing driver configuration

{
 DWORD Timeout;
 DWORD M1,M2,M3;
 BYTE  I1,I2,I3;
 BYTE  Port;
 DWORD CfgFlags;
 BYTE  byUSBCheck;
 BYTE  byLPTAuto;
 WORD  LPTA1,LPTA2,LPTA3;
 BYTE  byMultiProc;
} CfgCrc;


// Macro for updating the driver configuration structure
#define MAKE_CFG_CRC {CfgCrc.Timeout=dwTimeOut;CfgCrc.M1=Prt[0].Method;CfgCrc.M2=Prt[1].Method;\
                      CfgCrc.M3=Prt[2].Method;CfgCrc.Port=bPort;CfgCrc.I1=Prt[0].Irql;\
                      CfgCrc.I2=Prt[1].Irql;CfgCrc.I3=Prt[2].Irql;CfgCrc.CfgFlags=dwConfigFlags;\
					  CfgCrc.LPTA1=Prt[0].Base;CfgCrc.LPTA2=Prt[1].Base;CfgCrc.LPTA3=Prt[2].Base;\
                      CfgCrc.byUSBCheck=byUSBCheck;CfgCrc.byLPTAuto=byLPTAuto;\
                      CfgCrc.byMultiProc=byConfigMultiProc;}
// Macro for detecting changes in driver configuration
#define _CRC_CHECK  ((CfgCrc.Timeout==dwTimeOut)&&(CfgCrc.Port==bPort)&& \
                     (CfgCrc.M1==Prt[0].Method)&&(CfgCrc.M2==Prt[1].Method)&&(CfgCrc.M3==Prt[2].Method)&& \
                     (CfgCrc.I1==Prt[0].Irql)&&(CfgCrc.I2==Prt[1].Irql)&&(CfgCrc.I3==Prt[2].Irql)&&\
                     (CfgCrc.LPTA1==Prt[0].Base)&&(CfgCrc.LPTA2==Prt[1].Base)&&(CfgCrc.LPTA3==Prt[2].Base)&&\
                     (CfgCrc.CfgFlags==dwConfigFlags)&&(CfgCrc.byUSBCheck==byUSBCheck)&&\
                     (CfgCrc.byLPTAuto==byLPTAuto)&&(CfgCrc.byMultiProc==(BYTE)bMultiProc))

extern int  CurDrvVer;
extern BOOL bRus;
extern BOOL bWinNT2000;
extern BOOL bMultiProc;			// Multiprocessor mode flag (from GetSystemInfo())
extern BOOL bInfo;
extern HINSTANCE hMainInstance;
extern TDriverState DrvState;

extern BOOL bUSBPresent;		//Defined in INSTDRV.C

static char szText[0x100];         	//String for general use

//char szMyIcon[] = {"IDI_ICON1"};

// Variables for configuration dialog
TLPTinfo Prt[4];                   // Information structure (for printer and USB ports)
BYTE  bPort = 7;                   // Bit mask of ports to be used
int   nCur = 0;                    // Current port number (0 means LPT1 etc.)
DWORD dwConfigFlags = 0x8000;      // Driver configuration flags
DWORD dwTimeOut = 10000;           // Current TimeOut value
WORD  wTimers = gd_TIMELOOP_AUTO;  // Current Timer and Delay methods
HWND  hCfgWnd;                     // Handle of configuration window
BYTE  byUSBCheck;		   		   // =1, if USB port is to be used

BYTE  byLPTAuto;				   // "Autodetect LPT Arrdesses" mode
WORD  awAutoLPTAddr[3];			   // Autodetected LPT Addresses
BYTE  byConfigMultiProc; 		   // Multiprocessor mode flag (from registry)	

GD_DRIVER_INFO DI;                 // Driver Info structure

//******************************************************************
// This routine checks driver by GD_CheckDriver() and
// fills the DrvState structure with driver state information

int CheckDriver()
{
 int nRet;
 switch (nRet = GD_CheckDriver(&DI,sizeof(DI)))
 {
    case ge_NO_ERROR:
       DrvState.Present = 1;
       DrvState.Age     = DRIVER_AGE_EQUAL;
    break;
    case ge_DRIVER_BUSY:
        GD_GetLastErrorDescription ( szText, 0x100 );
        DrvState.Present = 1;
        DrvState.Age     = DRIVER_AGE_EQUAL;
    break;
    case ge_DRIVER_NOT_FOUND:
       DrvState.Present = 0;
    break;
    case ge_DRIVER_NEWER_VERSION:
       DrvState.Present = 1;
       DrvState.Age     = DRIVER_AGE_NEWER;
    break;
    case ge_DIOCTL_FAIL:
    case ge_DRIVER_OLD_VERSION:
       DrvState.Present = 1;
       DrvState.Age     = DRIVER_AGE_OLDER;
    break;
    case ge_REBOOT_NEEDED:
       DrvState.RebootNeeded = 1;
       DrvState.Present = 1;
    break;
 }
 return nRet;
}
//******************************************************************
// This routine sets up the 'FRIENDLY NAMES' - strings with friendly
// description of the port. These strings come from registry.
// Registry keys come from driver.
// Friendly names supported for Windows 95 for the time.
BOOL SetupFriendlyLPTNames()
{
 int i;
 BOOL bPresent = 0;
 DWORD size=100;

	for (i=0;i<3;i++){
   		if (!RegQueryValueEx((HKEY)Prt[i].RegKey,"FRIENDLYNAME",NULL,NULL,(void*)szText,&size)) // == SUCCESS
   		{
      		memccpy (Prt[i].FriendlyName,szText,0,100);
      		bPresent = 1;
   		}
 	}
 	if(bUSBPresent){
        sprintf( szText, RS(S_USB_NAME));
   		memccpy (Prt[3].FriendlyName,szText,0,100);
 	}


 return bPresent;
}
//******************************************************************
// This routine sets 'YES-NO' radio button state and friendly name for port
void SetPortSettings(HWND hWnd,int PortNum)
{
 if (PORT_PRESENT(PortNum) || (PortNum == 3 && byUSBCheck))	//If LPTx or USB is available
 {
    CheckDlgButton(hWnd,IDC_RADIOBUTTON_YES,1);
    CheckDlgButton(hWnd,IDC_RADIOBUTTON_NO ,0);
    SendMessage(hWnd,WM_COMMAND,IDC_RADIOBUTTON_YES,0);
 }
 else
 {
    CheckDlgButton(hWnd,IDC_RADIOBUTTON_NO ,1);
    CheckDlgButton(hWnd,IDC_RADIOBUTTON_YES,0);
    SendMessage(hWnd,WM_COMMAND,IDC_RADIOBUTTON_NO ,0);
 }
 SetWindowText(GetDlgItem(hWnd,IDC_STATICTEXT_FR_NAME),Prt[PortNum].FriendlyName);
}
//******************************************************************
//  This routine fills listbox with available port names
//
void SetAvailiblePorts(HWND hWnd)
{
 int i,f=0;

 for (i=0;i<3;i++)
 {
    Prt[i].Base = DI.di_awBase[i];
    Prt[i].RegKey = DI.di_adwHKey[i];

    if (Prt[i].Base)
    {
       f = 1;
       sprintf( szText, "LPT%d  ( %03Xh )", i+1, Prt[i].Base );
       SendMessage(GetDlgItem(hWnd,IDC_LISTBOX1),LB_ADDSTRING,0,(LPARAM)szText);
    }
    else
       bPort &= (BYTE)((1<<i)^0xFF); // Clear this bit because this port does not exist!
 }
 if(bUSBPresent){
       f = 1;
       sprintf( szText, "USB");
       SendMessage(GetDlgItem(hWnd,IDC_LISTBOX1),LB_ADDSTRING,0,(LPARAM)szText);
 }

 if (!f)
 {
    MessageBox(hWnd,RS(S_NOLPTFOUND),"Error",MB_);
    EndDialog(hWnd,RET_CANCEL);
 }


}
//***************************************************************************
//  This routine enables and checks all method checkboxes for current port
//
void EnableChecks(HWND hWnd,int notAuto,int nOff)
{
// notAuto is negative for Auto method:
//                      if TRUE  -> Auto is off and we need to show all
//                      if FALSE -> Auto is on and only grayed default needed
// nOff is for unused port. If it's 0, then all checks are off.
 EnableWindow(GetDlgItem(hWnd,IDC_STATICTEXT_METHODS), nOff );
 EnableWindow(GetDlgItem(hWnd,IDC_CHECK_STEAL   ),notAuto & DI.di_Flags.mSteal );
 EnableWindow(GetDlgItem(hWnd,IDC_CHECK_ACQUIRE ),notAuto & DI.di_Flags.mAquire );
 EnableWindow(GetDlgItem(hWnd,IDC_CHECK_CS      ),notAuto & DI.di_Flags.mCrSect );
 EnableWindow(GetDlgItem(hWnd,IDC_CHECK_MASK    ),notAuto & DI.di_Flags.mMask );
 EnableWindow(GetDlgItem(hWnd,IDC_CHECK_CLI     ),notAuto & DI.di_Flags.mCli );
 EnableWindow(GetDlgItem(hWnd,IDC_CHECK_ALLOC   ),notAuto & DI.di_Flags.mAlloc );
 EnableWindow(GetDlgItem(hWnd,IDC_CHECK_IRQL    ),notAuto & DI.di_Flags.mIrql );
 if ( bWinNT2000 )
 {
    sprintf(szText,"%d",Prt[nCur].Irql);
    SetWindowText(GetDlgItem(hWnd,IDC_EDIT_IRQL),szText);
 }
 if (notAuto)
 {  // Then check the box we consider with following parameters:
    //  Is this method used for this port? and
    //  Is this method supported by driver?

    CheckDlgButton(hWnd,IDC_CHECK_STEAL  ,(Prt[nCur].Method & gd_METHOD_STEAL  )&& DI.di_Flags.mSteal );
    CheckDlgButton(hWnd,IDC_CHECK_ACQUIRE,(Prt[nCur].Method & gd_METHOD_ACQUIRE)&& DI.di_Flags.mAquire );
    CheckDlgButton(hWnd,IDC_CHECK_CS     ,(Prt[nCur].Method & gd_METHOD_CS     )&& DI.di_Flags.mCrSect );
    CheckDlgButton(hWnd,IDC_CHECK_MASK   ,(Prt[nCur].Method & gd_METHOD_MASK   )&& DI.di_Flags.mMask );
    CheckDlgButton(hWnd,IDC_CHECK_CLI    ,(Prt[nCur].Method & gd_METHOD_CLI    )&& DI.di_Flags.mCli );
    CheckDlgButton(hWnd,IDC_CHECK_ALLOC  ,(Prt[nCur].Method & gd_METHOD_ALLOC  )&& DI.di_Flags.mAlloc );
    CheckDlgButton(hWnd,IDC_CHECK_IRQL   ,(Prt[nCur].Method & gd_METHOD_IRQL   )&& DI.di_Flags.mIrql );
    if (( Prt[nCur].Method & gd_METHOD_IRQL   )&& DI.di_Flags.mIrql )
        EnableWindow  (GetDlgItem(hWnd,IDC_EDIT_IRQL),1);
    else
        EnableWindow  (GetDlgItem(hWnd,IDC_EDIT_IRQL),0);
 }
 else
 {
    CheckDlgButton(hWnd,IDC_CHECK_STEAL  ,(gd_METHOD_AUTO_95 & gd_METHOD_STEAL   & nOff )&& DI.di_Flags.mSteal );
    CheckDlgButton(hWnd,IDC_CHECK_ACQUIRE,(gd_METHOD_AUTO_95 & gd_METHOD_ACQUIRE & nOff )&& DI.di_Flags.mAquire );
    CheckDlgButton(hWnd,IDC_CHECK_CS     ,(gd_METHOD_AUTO_95 & gd_METHOD_CS      & nOff )&& DI.di_Flags.mCrSect );
    CheckDlgButton(hWnd,IDC_CHECK_MASK   ,(gd_METHOD_AUTO_95 & gd_METHOD_MASK    & nOff )&& DI.di_Flags.mMask );
    CheckDlgButton(hWnd,IDC_CHECK_CLI    ,(gd_METHOD_AUTO_95 & gd_METHOD_CLI     & nOff )&& DI.di_Flags.mCli );
    CheckDlgButton(hWnd,IDC_CHECK_ALLOC  ,(gd_METHOD_AUTO_NT & gd_METHOD_ALLOC   & nOff )&& DI.di_Flags.mAlloc );
    CheckDlgButton(hWnd,IDC_CHECK_IRQL   ,(gd_METHOD_AUTO_NT & gd_METHOD_IRQL    & nOff )&& DI.di_Flags.mIrql );
    EnableWindow  (GetDlgItem(hWnd,IDC_EDIT_IRQL    ),0);
 }
}
//*****************************************************************************
//   This routine checks FLOAT value in the given editbox
//   It takes Dialog,Item,Ranges(Min & Max), Result and Error message ID
//
BOOL CheckEditBox(HWND hWnd,int IDC,float min,float max,float * Res,int MsgID)
{
 HWND EditItem = GetDlgItem(hWnd,IDC);
 GetWindowText(EditItem,szText,10);
 if ((sscanf(szText,"%g",Res)!=1)||(*Res < min)||(*Res > max))
 {
    if (MsgID>=0)
    {
       sprintf(szText,RS(MsgID),min,max);
       MessageBox(hWnd,szText,"Error",MB_);
    }
    else
       SetFocus(hWnd);
    SetFocus(EditItem);
    SendMessage(EditItem,EM_SETSEL,0,-1);
    return 0;
 }
 return 1;
}
//*****************************************************************************
//  This routine is the same as previous but checks INTEGER value
//
BOOL CheckEditBoxInt(HWND hWnd,int IDC,int min,int max,int * Res,int MsgID)
{
 HWND EditItem = GetDlgItem(hWnd,IDC);
 int i;

 GetWindowText(EditItem,szText,10);

 for(i=0; i < 10; i++){
 	if(szText[i] == 0x0)
    	break;
	if(!isdigit(szText[i]))
    	goto CheckErr;
 }

 if ((sscanf(szText,"%d",Res)!=1)||(*Res < min)||(*Res > max))
 {
CheckErr:
    if (MsgID>=0)
    {
       sprintf(szText,RS(MsgID),min,max);
       MessageBox(hWnd,szText,"Error",MB_);
    }
    else
       SetFocus(hWnd);
    SetFocus(EditItem);
    SendMessage(EditItem,EM_SETSEL,0,-1);
    return 0;
 }
 sprintf(szText,"%d",*Res);
 SetWindowText(EditItem,szText);
 return 1;
}
//*****************************************************************************
//  This routine is the same as previous but checks INTEGER HEX value
//
BOOL CheckEditBoxIntHex(HWND hWnd,int IDC,int min,int max,int * Res,int MsgID)
{
 HWND 	EditItem = GetDlgItem(hWnd,IDC);

 GetWindowText(EditItem,szText,10);

 if ((!IsXDigitStr(szText, 10)) || (sscanf(szText,"%X",Res)!=1)||(*Res < min)||(*Res > max))
 {
    if (MsgID>=0)
    {
       sprintf(szText,RS(MsgID),min,max);
       MessageBox(hWnd,szText,"Error",MB_);
    }
    else
       SetFocus(hWnd);
    SetFocus(EditItem);
    SendMessage(EditItem,EM_SETSEL,0,-1);
    return 0;
 }
 sprintf(szText,"%X",*Res);
 SetWindowText(EditItem,szText);
 return 1;
}
//*****************************************************************************
//(((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((
//)))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))
//(((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((
//)))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))
//(((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((
//)))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))
//*****************************************************************************
//   This is DialogProc for main dialog
//
//extern int WINAPI GD_ConfigMultiprocMode( BOOL bMulti ); // Undocumented function.


BOOL _export CALLBACK MsgDlgProc( HWND hWnd, UINT uMsg,
                                  WPARAM wParam, LPARAM lParam )
{
 RECT rc;
 DWORD s1;
 static int DlgX=-600,DlgY;  // -600 used as a flag of first usage

 switch( uMsg )
 {
   case WM_INITDIALOG:

//   		hIcon = LoadIcon(hMainInstance, szMyIcon);

       // Print version at left lower corner of the dialog.
       // Version 1.10 appears like '1.1';  1.12 appears as is
       sprintf (szText,"v %d.%d", CurDrvVer>>8,((CurDrvVer&0xFF)%10)?CurDrvVer&0xff:(CurDrvVer&0xff)/10);
/******
		if((CurDrvVer&0xFF)%10)
			sprintf (szText,"v %d.%02d", CurDrvVer>>8,CurDrvVer&0xff);
        else
			sprintf (szText,"v %d.%d", CurDrvVer>>8,(CurDrvVer&0xff)/10);
******/
       SetWindowText(GetDlgItem(hWnd,IDC_STATICTEXT2),szText);
       SetWindowText(hWnd,RS(S_TITLE));
       SetWindowText(GetDlgItem(hWnd,IDC_STATICTEXT1),RS(S_WELCOME));
       SetWindowText(GetDlgItem(hWnd,IDEXIT),RS(S_BTNEXIT));
       SetWindowText(GetDlgItem(hWnd,IDINSTALL),RS(S_BTNINSTALL));
       SetWindowText(GetDlgItem(hWnd,IDREMOVE),RS(S_BTNUNINSTALL));
       SetWindowText(GetDlgItem(hWnd,IDCONFIG),RS(S_BTNCONFIG));
       GetWindowRect(hWnd,&rc);
       s1 = rc.right - rc.left;
/*********
       GetWindowRect(GetDlgItem(hWnd,IDC_STATICBITMAP1),&rc);
       if (DlgX!=-600) // Not the first time!
          SetWindowPos(hWnd,HWND_BOTTOM,DlgX,DlgY,0,0,SWP_NOSIZE+SWP_NOZORDER);
       SetWindowPos(GetDlgItem(hWnd,IDC_STATICBITMAP1),HWND_BOTTOM,
          (int)(s1-(rc.right - rc.left)-5),-10,0,0,SWP_NOSIZE+SWP_NOZORDER);
*********/

       // The rest of operations we will perform after the dialog appears:
       PostMessage(hWnd,WM_COMMAND,345,0);
       break;

   case WM_DESTROY:
       {
         RECT rc;
         GetWindowRect(hWnd,&rc);
         DlgX = rc.left;
         DlgY = rc.top;
       }
       break;

   case WM_COMMAND:
       switch( wParam )
       {
       // User-defined message. To allow the dialog to be shown.
       case 345:
            if (!DrvState.Present)
            {
                SetWindowText(GetDlgItem(hWnd,IDINSTALL),RS(S_BTNINSTALL));
                EnableWindow(GetDlgItem(hWnd,IDCONFIG),0);
                EnableWindow(GetDlgItem(hWnd,IDREMOVE),0);
                EnableWindow(GetDlgItem(hWnd,IDINSTALL),1);
            }
            else
            {
                SetWindowText(GetDlgItem(hWnd,IDINSTALL),RS(S_BTNREINSTALL));
                if (!DI.di_Flags.fConfigurable)
                    EnableWindow(GetDlgItem(hWnd,IDCONFIG),0);
                else{
                    EnableWindow(GetDlgItem(hWnd,IDCONFIG),1);
                    if(DI.di_byMultiProc != (BYTE)bMultiProc){
//						GD_ConfigMultiprocMode(bMultiProc);
                        GD_ReconfigureDriver();
                        CheckDriver();
					}
				}
                EnableWindow(GetDlgItem(hWnd,IDREMOVE),1);
                EnableWindow(GetDlgItem(hWnd,IDINSTALL),1);

                if (DrvState.Age != DRIVER_AGE_EQUAL)
                {
                   GD_GetLastErrorDescription  ( szText, 0x100 );
                   if (!bInfo) // else message appears from DLL
                      MessageBox(NULL, szText, RS(S_TITLE),MB_);
                }

            }
            break;

       case IDINSTALL:
            GD_PrintLog(" ==== Install Button pressed ====");
            EndDialog(hWnd,0);
            break;

       case IDREMOVE:
            GD_PrintLog(" ==== Remove Button pressed ====");
            EndDialog(hWnd,COMMAND_UNINST);
            break;

       case IDCONFIG:
            GD_PrintLog(" ==== Config Button pressed ====");
            if ( bWinNT2000 )
                 DialogBox(hMainInstance,MAKEINTRESOURCE(IDD_CONFIG_NT),hWnd,(DLGPROC)ConfigDlgProcNT);
            else
                 DialogBox(hMainInstance,MAKEINTRESOURCE(IDD_CONFIG),hWnd,(DLGPROC)ConfigDlgProc95);
            break;

       case IDEXIT:
            GD_PrintLog(" ==== Exit Button pressed ====");
            EndDialog(hWnd,COMMAND_EXIT);
            break;
       }
       break;
 default: return FALSE;
 }
 return (BOOL)DefWindowProc(hWnd,uMsg,wParam,lParam);
}
//*****************************************************************************
//(((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((
//))))  #    #  ##### ))))))))))))))))))))))))))))))))))))))))))))))))))))))))
//((((  ##   #    #   ((((((((((((((((((((((((((((((((((((((((((((((((((((((((
//))))  # #  #    #   ))))))))))))))))))))))))))))))))))))))))))))))))))))))))
//((((  #  # #    #   ((((((((((((((((((((((((((((((((((((((((((((((((((((((((
//))))  #   ##    #   ))))))))))))))))))))))))))))))))))))))))))))))))))))))))
//(((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((
//*****************************************************************************
//   This is DialogProc for configuration dialog.  Windows NT variant
//
BOOL _export CALLBACK ConfigDlgProcNT( HWND hWnd, UINT uMsg,
                                     WPARAM wParam, LPARAM lParam )
{
 float fTimeOut;
 int   iIRQL,i;

 switch( uMsg )
 {
   case WM_INITDIALOG:

       hCfgWnd = hWnd;
       // Initialize: Title
       SetWindowText(hWnd,RS(S_TITLE_CFG));
       // Static text
       SetWindowText(GetDlgItem(hWnd,IDC_STATICTEXT2),RS(S_CONFIGTEXT));
       SetWindowText(GetDlgItem(hWnd,IDC_STATICTEXT3),RS(S_TIMEOUT));
       SetWindowText(GetDlgItem(hWnd,IDC_STATICTEXT4),RS(S_SEC));
       SetWindowText(GetDlgItem(hWnd,IDC_STATICTEXT_METHODS),RS(S_STEALTYPE));
       SetWindowText(GetDlgItem(hWnd,IDC_STATICTEXT_USE),RS(S_USEPORT));
       // Radio buttons and check boxes
       if (bRus)
       {
             SetWindowText(GetDlgItem(hWnd,IDC_RADIOBUTTON_YES),"Да");
             SetWindowText(GetDlgItem(hWnd,IDC_RADIOBUTTON_NO ),"Нет");
             SetWindowText(GetDlgItem(hWnd,IDC_BUTTON_CANCEL  ),"Отмена");
             SetWindowText(GetDlgItem(hWnd,IDC_CHECK_ALLOC    ),"Захват LPT порта");
             SetWindowText(GetDlgItem(hWnd,IDC_CHECK_IRQL     ),"Изменить IRQL на");
             SetWindowText(GetDlgItem(hWnd,IDC_BUTTON_ADVANCED),"Дополнительно");
       }
       else
       {
             SetWindowText(GetDlgItem(hWnd,IDC_RADIOBUTTON_YES),"Yes");
             SetWindowText(GetDlgItem(hWnd,IDC_RADIOBUTTON_NO ),"No");
             SetWindowText(GetDlgItem(hWnd,IDC_BUTTON_CANCEL  ),"Cancel");
             SetWindowText(GetDlgItem(hWnd,IDC_CHECK_ALLOC    ),"Capture LPT port");
             SetWindowText(GetDlgItem(hWnd,IDC_CHECK_IRQL     ),"Change IRQL to");
             SetWindowText(GetDlgItem(hWnd,IDC_BUTTON_ADVANCED),"Advanced");
       }

       // Ports ------------------------------
       bPort = DI.di_bPort;
       // Methods and IRQLs ------------------
       for (i=0;i<3;i++)
       {
          Prt[i].Method = DI.di_adwMethod[i];
          Prt[i].Irql   = DI.di_abIrql[i];
       }
       // TimeOut ----------------------------
       dwTimeOut = DI.di_dwTimeout;
       sprintf(szText,"%lg",dwTimeOut/1000.0);
       SetWindowText(GetDlgItem(hWnd,IDC_EDIT1),szText);
       // Configuration Flags ----------------
       dwConfigFlags = DI.di_dwConfigFlags;
       wTimers = (WORD)(DI.di_dwTimeLoop & 0xFFFF) ;

       // USB Check Mode ---------------------
       byUSBCheck = DI.di_byUSBCheck;

       // "LPT addresses Autodetect" mode ----
       byLPTAuto = DI.di_byLPTAuto;

       	// Autodetected LPT addresses --------
       	for (i=0;i<3;i++)
        	awAutoLPTAddr[i] = DI.di_awAutoLPTAddr[i];

       // Port list
       SetAvailiblePorts(hWnd);
       SendMessage(GetDlgItem(hWnd,IDC_LISTBOX1),LB_SETCURSEL,0,0);
       SendMessage(hWnd,WM_COMMAND,IDC_LISTBOX1 | 0x10000,0);
       MAKE_CFG_CRC;

       break;
   case WM_COMMAND:

       switch( LOWORD(wParam) )
       {
       case IDC_LISTBOX1:
           if (HIWORD(wParam)==1) // Item changes...
           {
               nCur=SendMessage(GetDlgItem(hWnd,IDC_LISTBOX1),LB_GETCURSEL,0,0);
               SendMessage(GetDlgItem(hWnd,IDC_LISTBOX1),LB_GETTEXT,nCur,(LPARAM)szText);
               if(!bUSBPresent || !strstr(szText, "USB"))
               		nCur=szText[3]-'1';
			   else
               		nCur=3;	//For USB - set index to last item of Prt[] array
////               nCur=szText[3]-'1';
               SetPortSettings(hWnd,nCur);
               return 0;
            }
            break;
       case IDC_EDIT1:
           if (HIWORD(wParam)==EN_KILLFOCUS)
           {
              if (CheckEditBox(hWnd,IDC_EDIT1,MIN_TIMEOUT,MAX_TIMEOUT,&fTimeOut,S_TIMEOUTMSG))
                 fTimeOut=fTimeOut*1000.0+0.5;
                 dwTimeOut=(DWORD)(fTimeOut);
           }
           break;
       case IDC_EDIT_IRQL:
           if (HIWORD(wParam)==EN_KILLFOCUS)
           {
              if (CheckEditBoxInt(hWnd,IDC_EDIT_IRQL,MIN_IRQL,MAX_IRQL,&iIRQL,S_IRQLOUTOFRANGE))
                 Prt[nCur].Irql=(BYTE)(iIRQL);
           }
           break;
       case IDC_RADIOBUTTON_YES:
       		///////////
       		if(nCur == 3){		//If "USB" field exists in listbox
                byUSBCheck = 1;
                EnableWindow(GetDlgItem(hWnd,IDC_CHECK_AUTO),FALSE);
                CheckDlgButton(hWnd,IDC_CHECK_AUTO,FALSE);
                EnableChecks(hWnd,FALSE,0);
       			EnableWindow(GetDlgItem(hWnd,IDC_BUTTON_ADVANCED), FALSE);
                EnableWindow(GetDlgItem(hWnd,IDC_EDIT1),FALSE);
       			EnableWindow(GetDlgItem(hWnd,IDC_STATICTEXT3),FALSE);
       			EnableWindow(GetDlgItem(hWnd,IDC_STATICTEXT4),FALSE);
			}
			else{
            //////////
	            bPort=(BYTE)(bPort|(1<<nCur));
       			EnableWindow ( GetDlgItem(hWnd,IDC_BUTTON_ADVANCED), DI.di_Flags.cTimers );///////
                EnableWindow(GetDlgItem(hWnd,IDC_EDIT1),TRUE);	///////
       			EnableWindow(GetDlgItem(hWnd,IDC_STATICTEXT3),TRUE);	//////
       			EnableWindow(GetDlgItem(hWnd,IDC_STATICTEXT4),TRUE);	//////
    	        EnableWindow(GetDlgItem(hWnd,IDC_CHECK_AUTO),TRUE);
        	    if (Prt[nCur].Method & gd_METHOD_AUTO)
            	   CheckDlgButton(hWnd,IDC_CHECK_AUTO,TRUE);
	            else
    	           CheckDlgButton(hWnd,IDC_CHECK_AUTO,FALSE);
        	    SendMessage(hWnd,WM_COMMAND,IDC_CHECK_AUTO,0);
			}	/////
            return 0;

       case IDC_RADIOBUTTON_NO:
       		///////////
       		if(nCur == 3){		//If "USB" field exists in listbox
                byUSBCheck = 0;
       			EnableWindow(GetDlgItem(hWnd,IDC_BUTTON_ADVANCED), FALSE);
                EnableWindow(GetDlgItem(hWnd,IDC_EDIT1),FALSE);
       			EnableWindow(GetDlgItem(hWnd,IDC_STATICTEXT3),FALSE);
       			EnableWindow(GetDlgItem(hWnd,IDC_STATICTEXT4),FALSE);
			}
            else{
       		///////////
	            bPort=(BYTE)(bPort&((1<<nCur)^(0xFF)));
	       		EnableWindow ( GetDlgItem(hWnd,IDC_BUTTON_ADVANCED), DI.di_Flags.cTimers );/////
                EnableWindow(GetDlgItem(hWnd,IDC_EDIT1),TRUE);	///////
       			EnableWindow(GetDlgItem(hWnd,IDC_STATICTEXT3),TRUE);	//////
       			EnableWindow(GetDlgItem(hWnd,IDC_STATICTEXT4),TRUE);	//////
			}////
   	        EnableWindow(GetDlgItem(hWnd,IDC_CHECK_AUTO),FALSE);
       	    CheckDlgButton(hWnd,IDC_CHECK_AUTO,FALSE);
           	EnableChecks(hWnd,FALSE,0);
            return 0;
       case IDC_CHECK_AUTO:
            if (IsDlgButtonChecked(hWnd,IDC_CHECK_AUTO)==BST_CHECKED)
            {
               Prt[nCur].Method |= gd_METHOD_AUTO;
               Prt[nCur].Irql = gd_IRQL_AUTO;
               EnableChecks(hWnd,FALSE,0xFF);
            }
            else
            {
               EnableChecks(hWnd,TRUE,0xFF);
               Prt[nCur].Method &= (0xFFFF ^ gd_METHOD_AUTO);
            }
            return 0;
       case IDC_CHECK_ALLOC:
            if (IsDlgButtonChecked(hWnd,IDC_CHECK_ALLOC)==BST_CHECKED)
               Prt[nCur].Method |= gd_METHOD_ALLOC;
            else
               Prt[nCur].Method &= (0xFFFF ^ gd_METHOD_ALLOC);
            return 0;
       case IDC_CHECK_IRQL:
            if (IsDlgButtonChecked(hWnd,IDC_CHECK_IRQL)==BST_CHECKED)
            {
               Prt[nCur].Method |= gd_METHOD_IRQL;
               EnableWindow(GetDlgItem(hWnd,IDC_EDIT_IRQL),TRUE);
            }
            else
            {
               Prt[nCur].Method &= (0xFFFF ^ gd_METHOD_IRQL);
               EnableWindow(GetDlgItem(hWnd,IDC_EDIT_IRQL),FALSE);
            }
            return 0;
        case IDC_BUTTON_ADVANCED:
         {
            DWORD dwTmp;
            dwTmp = wTimers | ( DI.di_dwTimeLoop & 0xFFFF0000 );
            GD_PrintLog(" ==== Advanced Button pressed ====");
            wTimers = (WORD)DialogBoxParam(hMainInstance,MAKEINTRESOURCE(IDD_ADVANCED),hWnd,(DLGPROC)AdvancedDlgProc, dwTmp );
            break;
         }
       case IDC_BUTTON_OK:

            GD_PrintLog(" ==== Config Dialog OK pressed ====");
            if ( CheckEditBox ( hWnd, IDC_EDIT1, MIN_TIMEOUT, MAX_TIMEOUT, &fTimeOut, S_TIMEOUTMSG ) )
            {
                 fTimeOut = fTimeOut * 1000.0 + 0.5;
                 dwTimeOut = ( DWORD )( fTimeOut );
            }
            else
                return 0;

            if (CheckEditBoxInt(hWnd,IDC_EDIT_IRQL,MIN_IRQL,MAX_IRQL,&iIRQL,S_IRQLOUTOFRANGE))
                Prt[nCur].Irql=(BYTE)(iIRQL);
            else
                return 0;

            dwConfigFlags = wTimers;

            if ( !_CRC_CHECK )
            {
                GD_ConfigPortsUse(bPort);
                GD_ConfigTimeOut(dwTimeOut);
                GD_ConfigFlags(dwConfigFlags);
                GD_ConfigUSBUse(byUSBCheck);
                GD_ConfigPortsAddr(byLPTAuto, Prt[0].Base, Prt[1].Base, Prt[2].Base);
                for ( i=0; i<3; i++ )
                {
                    GD_ConfigIrql((BYTE)i,Prt[i].Irql);
                    GD_ConfigPortAlloc((BYTE)i,Prt[i].Method);
                }
                i = GD_ReconfigureDriver();
                if ( i != ge_NO_ERROR)
                {
                   GD_GetLastErrorDescription(szText,0x100);
                   if (i!=ge_PORTS_NOT_USED) //YES-NO dialog in DLL always
                     if (!bInfo)// else message appears from DLL
                        MessageBox(NULL,szText,"Error",MB_);

                   // if driver is busy we ignore OK button to avoid
                   // loss of the new configuration
                      return 0;

                }
                CheckDriver();
                EndDialog(hWnd,RET_OK);
            }
            else
            {
                GD_PrintLog("      Config Dialog is closed with NO CHANGES ====");
                EndDialog(hWnd,RET_CANCEL);
            }
            return 0;

       case IDC_BUTTON_CANCEL:
            GD_PrintLog(" ==== Config Dialog is cancelled... ====");
            EndDialog(hWnd,RET_CANCEL);
            return 0;
       }
       break;
 default: return FALSE;
 }
return (BOOL)DefWindowProc(hWnd,uMsg,wParam,lParam);
}
//*****************************************************************************
//(((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((
//)))))))))))MMMM)))MMMMM))))))))))))))))))))))))))))))))))))))))))))))))))))))
//((((((((((MM((MM((M((((((((((((((((((((((((((((((((((((((((((((((((((((((((((
//)))))))))))MMMMM))MMMM)))))))))))))))))))))))))))))))))))))))))))))))))))))))
//(((((((((((((MM((((((M(((((((((((((((((((((((((((((((((((((((((((((((((((((((
//)))))))))MMMMM)))MMMM))))))))))))))))))))))))))))))))))))))))))))))))))))))))
//*****************************************************************************
//   This is DialogProc for configuration dialog.  Windows 95/98 variant
//
BOOL _export CALLBACK ConfigDlgProc95 ( HWND hWnd, UINT uMsg,
                                        WPARAM wParam, LPARAM lParam )
{
 float fTimeOut;
 int i;

 switch( uMsg )
 {
   case WM_INITDIALOG:
       hCfgWnd = hWnd;
       // Initialize: Title
       SetWindowText(hWnd,RS(S_TITLE_CFG));
       // All static texts
       SetWindowText(GetDlgItem(hWnd,IDC_STATICTEXT2),RS(S_CONFIGTEXT));
       SetWindowText(GetDlgItem(hWnd,IDC_STATICTEXT3),RS(S_TIMEOUT));
       SetWindowText(GetDlgItem(hWnd,IDC_STATICTEXT4),RS(S_SEC));
       SetWindowText(GetDlgItem(hWnd,IDC_STATICTEXT_METHODS),RS(S_STEALTYPE));
       SetWindowText(GetDlgItem(hWnd,IDC_STATICTEXT_USE),RS(S_USEPORT));
       // Radio buttons
       if (bRus)
       {
           SetWindowText(GetDlgItem(hWnd,IDC_RADIOBUTTON_YES),"Да");
           SetWindowText(GetDlgItem(hWnd,IDC_RADIOBUTTON_NO ),"Нет");
           SetWindowText(GetDlgItem(hWnd,IDC_BUTTON_CANCEL  ),"Отмена");
           SetWindowText(GetDlgItem(hWnd,IDC_CHECK_AUTO     ),"Автоматический");
           SetWindowText(GetDlgItem(hWnd,IDC_CHECK_STEAL    ),"Захват LPT порта");
           SetWindowText(GetDlgItem(hWnd,IDC_CHECK_ACQUIRE  ),"Захват I/O диапазона");
           SetWindowText(GetDlgItem(hWnd,IDC_CHECK_CS       ),"Критическая секция");
           SetWindowText(GetDlgItem(hWnd,IDC_CHECK_MASK     ),"Маскирование прерываний");
           SetWindowText(GetDlgItem(hWnd,IDC_CHECK_CLI      ),"Запрет прерываний");
           SetWindowText(GetDlgItem(hWnd,IDC_BUTTON_ADVANCED),"Дополнительно");
       }
       else
       {
           SetWindowText(GetDlgItem(hWnd,IDC_RADIOBUTTON_YES),"Yes");
           SetWindowText(GetDlgItem(hWnd,IDC_RADIOBUTTON_NO ),"No");
           SetWindowText(GetDlgItem(hWnd,IDC_BUTTON_CANCEL  ),"Cancel");
           SetWindowText(GetDlgItem(hWnd,IDC_CHECK_AUTO     ),"Auto");
           SetWindowText(GetDlgItem(hWnd,IDC_CHECK_STEAL    ),"Capture LPT port");
           SetWindowText(GetDlgItem(hWnd,IDC_CHECK_ACQUIRE  ),"Capture I/O range");
           SetWindowText(GetDlgItem(hWnd,IDC_CHECK_CS       ),"Critical section");
           SetWindowText(GetDlgItem(hWnd,IDC_CHECK_MASK     ),"Interrupts masking");
           SetWindowText(GetDlgItem(hWnd,IDC_CHECK_CLI      ),"Interupts disabling");
           SetWindowText(GetDlgItem(hWnd,IDC_BUTTON_ADVANCED),"Advanced");
       }
       EnableWindow ( GetDlgItem(hWnd,IDC_BUTTON_ADVANCED), DI.di_Flags.cTimers );

       // Ports ------------------------------
       bPort = DI.di_bPort;
       // Methods ----------------------------
       Prt[0].Method = DI.di_adwMethod[0];
       Prt[1].Method = DI.di_adwMethod[1];
       Prt[2].Method = DI.di_adwMethod[2];
       // TimeOut ----------------------------
       dwTimeOut = DI.di_dwTimeout;
       // Configuration Flags ------------------
       dwConfigFlags = DI.di_dwConfigFlags;

       // Timer / Delay method
       wTimers = (WORD)(DI.di_dwTimeLoop & 0xFFFF) ;

       // USB Check Mode -------------------
       byUSBCheck = DI.di_byUSBCheck;

       // "LPT addresses Autodetect" mode ----
       byLPTAuto = DI.di_byLPTAuto;

       	// Autodetected LPT addresses --------
       	for (i=0;i<3;i++)
        	awAutoLPTAddr[i] = DI.di_awAutoLPTAddr[i];

		// Processors ------------------------
        byConfigMultiProc = DI.di_byMultiProc;

       // Display Current TimeOut
       sprintf(szText,"%lg",dwTimeOut/1000.0);
       SetWindowText(GetDlgItem(hWnd,IDC_EDIT1),szText);
       // Port list
       SetAvailiblePorts(hWnd);
       SetupFriendlyLPTNames();
       SendMessage(GetDlgItem(hWnd,IDC_LISTBOX1),LB_SETCURSEL,0,0);
       SendMessage(hWnd,WM_COMMAND,IDC_LISTBOX1 | 0x10000,0);
       MAKE_CFG_CRC;

       break;
   case WM_COMMAND:

       switch( LOWORD(wParam) )
       {

       case IDC_LISTBOX1:
           if (HIWORD(wParam)==1) // Item changes...
           {
               nCur=SendMessage(GetDlgItem(hWnd,IDC_LISTBOX1),LB_GETCURSEL,0,0);
               SendMessage(GetDlgItem(hWnd,IDC_LISTBOX1),LB_GETTEXT,nCur,(LPARAM)szText);
               if(!bUSBPresent || !strstr(szText, "USB"))
               		nCur=szText[3]-'1';
			   else
               		nCur=3;	//For USB - set index to last item of Prt[] array
               SetPortSettings(hWnd,nCur);
               return 0;
           }
           break;
       case IDC_EDIT1:
           if (HIWORD(wParam)==EN_KILLFOCUS)
              if (CheckEditBox(hWnd, IDC_EDIT1, MIN_TIMEOUT,MAX_TIMEOUT, &fTimeOut, S_TIMEOUTMSG))
              {
                  fTimeOut=fTimeOut*1000.0+0.5;
                  dwTimeOut=(DWORD)(fTimeOut);
              }
           break;
       case IDC_RADIOBUTTON_YES:
       		///////////
       		if(nCur == 3){		//If "USB" field exists in listbox
                byUSBCheck = 1;
                EnableWindow(GetDlgItem(hWnd,IDC_CHECK_AUTO),FALSE);
                CheckDlgButton(hWnd,IDC_CHECK_AUTO,FALSE);
                EnableChecks(hWnd,FALSE,0);
       			EnableWindow(GetDlgItem(hWnd,IDC_BUTTON_ADVANCED), FALSE);
                EnableWindow(GetDlgItem(hWnd,IDC_EDIT1),FALSE);
       			EnableWindow(GetDlgItem(hWnd,IDC_STATICTEXT3),FALSE);
       			EnableWindow(GetDlgItem(hWnd,IDC_STATICTEXT4),FALSE);
			}
			else{
            //////////
	            bPort=(BYTE)(bPort| (1<<nCur));
       			EnableWindow ( GetDlgItem(hWnd,IDC_BUTTON_ADVANCED), DI.di_Flags.cTimers );///////
                EnableWindow(GetDlgItem(hWnd,IDC_EDIT1),TRUE);	///////
       			EnableWindow(GetDlgItem(hWnd,IDC_STATICTEXT3),TRUE);	//////
       			EnableWindow(GetDlgItem(hWnd,IDC_STATICTEXT4),TRUE);	//////
	            EnableWindow(GetDlgItem(hWnd,IDC_CHECK_AUTO),TRUE);
    	        if (Prt[nCur].Method & gd_METHOD_AUTO)
        	       	CheckDlgButton(hWnd,IDC_CHECK_AUTO,TRUE);
            	else
                	CheckDlgButton(hWnd,IDC_CHECK_AUTO,FALSE);
            	SendMessage(hWnd,WM_COMMAND,IDC_CHECK_AUTO,0);
			}	//////
            return 0;

       case IDC_RADIOBUTTON_NO:
       		///////////
       		if(nCur == 3){		//If "USB" field exists in listbox
                byUSBCheck = 0;
       			EnableWindow(GetDlgItem(hWnd,IDC_BUTTON_ADVANCED), FALSE);
                EnableWindow(GetDlgItem(hWnd,IDC_EDIT1),FALSE);
       			EnableWindow(GetDlgItem(hWnd,IDC_STATICTEXT3),FALSE);
       			EnableWindow(GetDlgItem(hWnd,IDC_STATICTEXT4),FALSE);
			}
            else{
       		///////////
	            bPort=(BYTE)(bPort&( (1<<nCur) ^ 0xFF ));
	       		EnableWindow ( GetDlgItem(hWnd,IDC_BUTTON_ADVANCED), DI.di_Flags.cTimers );/////
                EnableWindow(GetDlgItem(hWnd,IDC_EDIT1),TRUE);	///////
       			EnableWindow(GetDlgItem(hWnd,IDC_STATICTEXT3),TRUE);	//////
       			EnableWindow(GetDlgItem(hWnd,IDC_STATICTEXT4),TRUE);	//////
			}
   	        EnableWindow(GetDlgItem(hWnd,IDC_CHECK_AUTO),FALSE);
       	    CheckDlgButton(hWnd,IDC_CHECK_AUTO,FALSE);
           	EnableChecks(hWnd,FALSE,0);
            return 0;
       case IDC_CHECK_AUTO:
            if (IsDlgButtonChecked(hWnd,IDC_CHECK_AUTO)==BST_CHECKED)
            {
               EnableChecks(hWnd,FALSE,0xFF);
               Prt[nCur].Method |= gd_METHOD_AUTO;
            }
            else
            {
               EnableChecks(hWnd,TRUE,0xFF);
               Prt[nCur].Method &= (0xFFFF ^ gd_METHOD_AUTO);
            }
            return 0;
       case IDC_CHECK_STEAL:
            if (IsDlgButtonChecked(hWnd,IDC_CHECK_STEAL)==BST_CHECKED)
               Prt[nCur].Method |= gd_METHOD_STEAL;
            else
               Prt[nCur].Method &= (0xFFFF ^ gd_METHOD_STEAL);
            return 0;
       case IDC_CHECK_ACQUIRE:
            if (IsDlgButtonChecked(hWnd,IDC_CHECK_ACQUIRE)==BST_CHECKED)
               Prt[nCur].Method |= gd_METHOD_ACQUIRE;
            else
               Prt[nCur].Method &= (0xFFFF ^ gd_METHOD_ACQUIRE);
            return 0;
       case IDC_CHECK_CS:
            if (IsDlgButtonChecked(hWnd,IDC_CHECK_CS)==BST_CHECKED)
               Prt[nCur].Method |= gd_METHOD_CS;
            else
               Prt[nCur].Method &= (0xFFFF ^ gd_METHOD_CS);
            return 0;
       case IDC_CHECK_MASK:
            if (IsDlgButtonChecked(hWnd,IDC_CHECK_MASK)==BST_CHECKED)
               Prt[nCur].Method |= gd_METHOD_MASK;
            else
               Prt[nCur].Method &= (0xFFFF ^ gd_METHOD_MASK);
            return 0;
       case IDC_CHECK_CLI:
            if (IsDlgButtonChecked(hWnd,IDC_CHECK_CLI)==BST_CHECKED)
               Prt[nCur].Method |=  gd_METHOD_CLI;
            else
               Prt[nCur].Method &=  (0xFFFF ^ gd_METHOD_CLI);
            return 0;
       case IDC_BUTTON_ADVANCED:
         {
            DWORD dwTmp;
            dwTmp = wTimers | ( DI.di_dwTimeLoop & 0xFFFF0000 );

///            dwTmp &= 0xeeeeeeee

            GD_PrintLog(" ==== Advanced Button pressed ====");
            wTimers = (WORD) DialogBoxParam(hMainInstance,MAKEINTRESOURCE(IDD_ADVANCED),hWnd,(DLGPROC)AdvancedDlgProc, dwTmp );
            break;
         }
        case IDC_BUTTON_OK:
            GD_PrintLog(" ==== Config Dialog OK pressed ====");
            if (CheckEditBox(hWnd, IDC_EDIT1, MIN_TIMEOUT,MAX_TIMEOUT, &fTimeOut, -1))
            {
                fTimeOut=fTimeOut*1000.0+0.5;
                dwTimeOut=(DWORD)(fTimeOut);
            }
            else
                break;
            dwConfigFlags = wTimers;
            if ( !_CRC_CHECK )
            {

                GD_ConfigPortsUse(bPort);
                GD_ConfigTimeOut(dwTimeOut);
                GD_ConfigFlags(dwConfigFlags);
                GD_ConfigUSBUse(byUSBCheck);
                GD_ConfigPortsAddr(byLPTAuto, Prt[0].Base, Prt[1].Base, Prt[2].Base);
                for ( i=0; i<3; i++ )
                {
                    GD_ConfigPortAlloc((BYTE)i,Prt[i].Method);
                }
                i = GD_ReconfigureDriver();
                if ( i != ge_NO_ERROR)
                {
                   GD_GetLastErrorDescription(szText,0x100);
                   if (i!=ge_PORTS_NOT_USED) //YES-NO dialog in DLL always
                     if (!bInfo)// else message appears from DLL
                        MessageBox(NULL,szText,"Error",MB_);

                   // if driver is busy we ignore OK button to avoid
                   // loss of the new configuration
                      return 0;
                }
                CheckDriver();
                EndDialog(hWnd,RET_OK);

            }
            else
            {
                GD_PrintLog("      Config Dialog is closed with NO CHANGES ====");
                EndDialog(hWnd,RET_CANCEL);
            }
            return 0;

       case IDC_BUTTON_CANCEL:
            GD_PrintLog(" ==== Config Dialog canceled... ====");
            EndDialog(hWnd,RET_CANCEL);
            return 0;
       }
       break;
 default: return FALSE;
 }
return (BOOL)DefWindowProc(hWnd,uMsg,wParam,lParam);
}

//*****************************************************************************
//(((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((
//)))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))
//(((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((
//)))))))   A D V A N C E D      C o n f i g u r a t i o n   ))))))))))))))))))
//(((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((((
//)))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))))
//*****************************************************************************
void EnableRadios (HWND hDlg, int i, int w, int s)
{ // Parameters are:
  //  i : On/Off flag
  //  w : State
  //  s : Support

 // Enable group boxes
 EnableWindow ( GetDlgItem ( hDlg, IDC_GROUPBOX1 ), i );
 EnableWindow ( GetDlgItem ( hDlg, IDC_GROUPBOX2 ), i );

 // Enable radio buttons
 EnableWindow ( GetDlgItem ( hDlg, IDC_RADIOBUTTON1 ), i && ( w & gd_TIME_SYSTEM ) );
 EnableWindow ( GetDlgItem ( hDlg, IDC_RADIOBUTTON2 ), i && ( w & gd_TIME_TRADITIONAL ) );
 EnableWindow ( GetDlgItem ( hDlg, IDC_RADIOBUTTON3 ), i && ( w & gd_TIME_SECONDARY ) );
 EnableWindow ( GetDlgItem ( hDlg, IDC_RADIOBUTTON4 ), i && ( w & gd_LOOP_PENTIUM ));
 EnableWindow ( GetDlgItem ( hDlg, IDC_RADIOBUTTON5 ), i && ( w & gd_LOOP_BSF ));
 EnableWindow ( GetDlgItem ( hDlg, IDC_RADIOBUTTON6 ), i && ( w & gd_LOOP_TRADITIONAL ));
 EnableWindow ( GetDlgItem ( hDlg, IDC_RADIOBUTTON7 ), i && ( w & gd_LOOP_SECONDARY ));

 // Show '!' pictures
 s = i ? (( s ^ 0xFFFF ) & w) : 0 ;

 ShowWindow   ( GetDlgItem ( hDlg, IDC_STATICBITMAP1 ), (s & gd_TIME_SYSTEM)?1:0 );
 ShowWindow   ( GetDlgItem ( hDlg, IDC_STATICBITMAP2 ), (s & gd_TIME_TRADITIONAL)?1:0 );
 ShowWindow   ( GetDlgItem ( hDlg, IDC_STATICBITMAP3 ), (s & gd_TIME_SECONDARY)?1:0 );
 ShowWindow   ( GetDlgItem ( hDlg, IDC_STATICBITMAP4 ), (s & gd_LOOP_PENTIUM)?1:0 );
 ShowWindow   ( GetDlgItem ( hDlg, IDC_STATICBITMAP5 ), (s & gd_LOOP_BSF)?1:0 );
 ShowWindow   ( GetDlgItem ( hDlg, IDC_STATICBITMAP6 ), (s & gd_LOOP_TRADITIONAL)?1:0 );
 ShowWindow   ( GetDlgItem ( hDlg, IDC_STATICBITMAP7 ), (s & gd_LOOP_SECONDARY)?1:0 );
}
//*****************************************************************************
//  Checks given timer radio button and delay radio button
//
void CheckRadio (HWND hDlg, int mask )
{
 int timer =  mask & 0x00FF;
 int loop  = (mask & 0xFF00);

 if (timer != 0xFF)
 {
   CheckDlgButton ( hDlg, IDC_RADIOBUTTON1, 0 );
   CheckDlgButton ( hDlg, IDC_RADIOBUTTON2, 0 );
   CheckDlgButton ( hDlg, IDC_RADIOBUTTON3, 0 );
   switch ( timer )
   {
     case gd_TIME_SYSTEM:
          CheckDlgButton ( hDlg, IDC_RADIOBUTTON1, 1 );
     break;
     case gd_TIME_TRADITIONAL:
          CheckDlgButton ( hDlg, IDC_RADIOBUTTON2, 1 );
     break;
     case gd_TIME_SECONDARY:
          CheckDlgButton ( hDlg, IDC_RADIOBUTTON3, 1 );
     break;
   }
 }
 if (loop != 0xFF00)
 {
   CheckDlgButton ( hDlg, IDC_RADIOBUTTON4, 0 );
   CheckDlgButton ( hDlg, IDC_RADIOBUTTON5, 0 );
   CheckDlgButton ( hDlg, IDC_RADIOBUTTON6, 0 );
   CheckDlgButton ( hDlg, IDC_RADIOBUTTON7, 0 );
   switch ( loop )
   {
     case gd_LOOP_PENTIUM:
          CheckDlgButton ( hDlg, IDC_RADIOBUTTON4, 1 );
     break;
     case gd_LOOP_BSF:
          CheckDlgButton ( hDlg, IDC_RADIOBUTTON5, 1 );
     break;
     case gd_LOOP_TRADITIONAL:
          CheckDlgButton ( hDlg, IDC_RADIOBUTTON6, 1 );
          SendMessage    ( hDlg, WM_COMMAND, IDC_RADIOBUTTON6, 0 );
     break;
     case gd_LOOP_SECONDARY:
          CheckDlgButton ( hDlg, IDC_RADIOBUTTON7, 1 );
     break;
   }
 }
}
//*****************************************************************************
//  Shows warning about possible damages that could be caused by unsupported timers
//
void ShowAlert ( HWND hDlg, int nShow )
{
   ShowWindow ( GetDlgItem ( hDlg, IDC_STATICBITMAP_DOWN ), nShow );
   ShowWindow ( GetDlgItem ( hDlg, IDC_STATICTEXT_WARN ), nShow );
}
//*****************************************************************************
//*****************************************************************************


extern int WINAPI GD_GetAutoTimeMethods( WORD * wTimers ); // Undocumented function.
// Gets the best timer/delay method directly from driver.
// Returns corresponding bits in wTimers
// See gd_TIME_XXXXXX & gd_LOOP_XXXXXX constants for details

//*****************************************************************************
//   This is DialogProc for Advanced options dialog
//
BOOL _export CALLBACK AdvancedDlgProc( HWND hDlg, UINT uMsg,
                                      WPARAM wParam, LPARAM lParam )
{
int i;
static int wSupp;   // Supported by system
static int wCur;    // Currently selected
static int wState;  // Currently availible
static int wInitial;
static int iLPTAddr;
static BYTE byLPTAutoInit;
static WORD awBaseInit[3];
//static WORD awBaseCur[3];
HCURSOR hCur;
// Listed above variables' type actualy is WORD, but int declaration is used to
// prevent "Conversion may loose significant digits" warning
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

 // lParam is a bit mask:
 //             Byte
 //             0 (low)   Current timer
 //             1         Current delay
 //             2         Supported timers
 //             3         Supported delay
 switch( uMsg )
 {

   case WM_INITDIALOG:
       wSupp = (WORD)( lParam >> 16 );

       // If no Pentium processor found, "Pentium counter" method is disabled
       wState = wSupp | ( 0xFFFF ^ gd_LOOP_PENTIUM );

       wInitial = wCur  = (WORD)(lParam & 0xFFFF);

       SetWindowText ( hDlg, RS ( S_ADVANCEDOPTIONS ));
       SetWindowText ( GetDlgItem ( hDlg, IDC_STATICTEXT_WARN ), RS ( S_TIMEREXCLAM ));
       SetWindowText ( GetDlgItem ( hDlg, IDC_STATICTEXT1 ), RS ( S_TIMELOOPTITLE ));
       SetWindowText ( GetDlgItem ( hDlg, IDC_LPTAUTO_STATICTEXT1 ), RS ( S_LPTADDRTITLE ));
       SetWindowText ( GetDlgItem ( hDlg, IDC_LPT1_STATICTEXT1 ), "LPT1:");
       SetWindowText ( GetDlgItem ( hDlg, IDC_LPT2_STATICTEXT1 ), "LPT2:");
       SetWindowText ( GetDlgItem ( hDlg, IDC_LPT3_STATICTEXT1 ), "LPT3:");
       ShowAlert ( hDlg, ( wCur & wSupp ) != (wCur & 0x7FFF) );

       EnableRadios  ( hDlg, 1, wState, wSupp );
////       if ( wCur & gd_TIMELOOP_AUTO ) // Auto mode
       if ((wCur & gd_TIMELOOP_AUTO) || bMultiProc) // Auto mode
       {
          wCur |= gd_TIMELOOP_AUTO;	////
          CheckDlgButton (  hDlg, IDC_CHECKBOX_AUTO, 1 );
          SendMessage ( hDlg, WM_COMMAND, IDC_CHECKBOX_AUTO, 0 );
       }
       else
          CheckRadio ( hDlg, wCur );

       if (bRus)
       {
           SetWindowText(GetDlgItem(hDlg,IDCANCEL          ),"Отмена");
           SetWindowText(GetDlgItem(hDlg,IDC_CHECKBOX_AUTO ),"Авто");
           SetWindowText(GetDlgItem(hDlg,IDC_GROUPBOX1     ),"Таймер");
           SetWindowText(GetDlgItem(hDlg,IDC_GROUPBOX2     ),"Метод задержек");
           SetWindowText(GetDlgItem(hDlg,IDC_RADIOBUTTON1  ),"Системный");
           SetWindowText(GetDlgItem(hDlg,IDC_RADIOBUTTON2  ),"Традиционный");
           SetWindowText(GetDlgItem(hDlg,IDC_RADIOBUTTON3  ),"Дополнительный");
           SetWindowText(GetDlgItem(hDlg,IDC_RADIOBUTTON4  ),"Счетчик Pentium");
           SetWindowText(GetDlgItem(hDlg,IDC_RADIOBUTTON5  ),"Счетчик BSF");
           SetWindowText(GetDlgItem(hDlg,IDC_RADIOBUTTON6  ),"Традиционный");
           SetWindowText(GetDlgItem(hDlg,IDC_RADIOBUTTON7  ),"Дополнительный");
           SetWindowText(GetDlgItem(hDlg,IDC_CHECKBOX_LPTAUTO ),"Авто");
           SetWindowText(GetDlgItem(hDlg,IDC_LPTAUTO_GROUPBOX1),"Адреса LPT-портов, hex");
       }
       else
       {
           SetWindowText(GetDlgItem(hDlg,IDC_BUTTON_CANCEL ),"Cancel");
           SetWindowText(GetDlgItem(hDlg,IDC_CHECKBOX_AUTO ),"Auto");
           SetWindowText(GetDlgItem(hDlg,IDC_GROUPBOX1     ),"Timer");
           SetWindowText(GetDlgItem(hDlg,IDC_GROUPBOX2     ),"Delay method");
           SetWindowText(GetDlgItem(hDlg,IDC_RADIOBUTTON1  ),"System");
           SetWindowText(GetDlgItem(hDlg,IDC_RADIOBUTTON2  ),"Traditional");
           SetWindowText(GetDlgItem(hDlg,IDC_RADIOBUTTON3  ),"Secondary");
           SetWindowText(GetDlgItem(hDlg,IDC_RADIOBUTTON4  ),"Pentium counter");
           SetWindowText(GetDlgItem(hDlg,IDC_RADIOBUTTON5  ),"BSF tick");
           SetWindowText(GetDlgItem(hDlg,IDC_RADIOBUTTON6  ),"Traditional");
           SetWindowText(GetDlgItem(hDlg,IDC_RADIOBUTTON7  ),"Secondary");
           SetWindowText(GetDlgItem(hDlg,IDC_CHECKBOX_LPTAUTO ),"Auto");
           SetWindowText(GetDlgItem(hDlg,IDC_LPTAUTO_GROUPBOX1),"LPT ports addresses, hex");
       }

       	byLPTAutoInit = byLPTAuto;
        for(i=0; i < 3; i++)
        	awBaseInit[i] = Prt[i].Base;

		if(Prt[0].Base){
	   		sprintf(szText,"%X",(WORD)Prt[0].Base);
    	   	SetWindowText(GetDlgItem(hDlg,IDC_EDIT_LPT1),szText);
		}
		if(Prt[1].Base){
	   		sprintf(szText,"%X",(WORD)Prt[1].Base);
    	   	SetWindowText(GetDlgItem(hDlg,IDC_EDIT_LPT2),szText);
		}
		if(Prt[2].Base){
	   		sprintf(szText,"%X",(WORD)Prt[2].Base);
    	   	SetWindowText(GetDlgItem(hDlg,IDC_EDIT_LPT3),szText);
		}

	   	if(byLPTAuto)	//LPT Auto mode
          	CheckDlgButton(hDlg, IDC_CHECKBOX_LPTAUTO, 1);
		else
          	CheckDlgButton(hDlg, IDC_CHECKBOX_LPTAUTO, 0);
       	SendMessage ( hDlg, WM_COMMAND, IDC_CHECKBOX_LPTAUTO, 0 );

/**************
       // Display Current LPT1 Address
       if(Prt[0].Base){
	       	sprintf(szText,"%X",(WORD)Prt[0].Base);
    	   	SetWindowText(GetDlgItem(hDlg, IDC_EDIT_LPT1), szText);
		}
        else{
        	EnableWindow(GetDlgItem(hDlg, IDC_EDIT_LPT1), FALSE);
        }

       // Display Current LPT2 Address
       if(Prt[1].Base){
	       	sprintf(szText,"%X",(WORD)Prt[1].Base);
    	   	SetWindowText(GetDlgItem(hDlg, IDC_EDIT_LPT2), szText);
		}
        else{
        	EnableWindow(GetDlgItem(hDlg, IDC_EDIT_LPT2), FALSE);
        }

       // Display Current LPT3 Address
       if(Prt[2].Base){
	       	sprintf(szText,"%X",(WORD)Prt[2].Base);
    	   	SetWindowText(GetDlgItem(hDlg, IDC_EDIT_LPT3), szText);
		}
        else{
        	EnableWindow(GetDlgItem(hDlg, IDC_EDIT_LPT3), FALSE);
        }
*****************/
   break;

   case WM_COMMAND:
       	switch( wParam )
       	{
       	case IDC_CHECKBOX_LPTAUTO:
       ////////////////////////////////////
	       	//Disable all Edit Boxes
   			EnableWindow(GetDlgItem(hDlg, IDC_EDIT_LPT1), FALSE);
   			EnableWindow(GetDlgItem(hDlg, IDC_EDIT_LPT2), FALSE);
	   		EnableWindow(GetDlgItem(hDlg, IDC_EDIT_LPT3), FALSE);
    	   	if(IsDlgButtonChecked(hDlg, IDC_CHECKBOX_LPTAUTO))
       		{
                // Disable Groupbox & texts
				EnableWindow(GetDlgItem(hDlg, IDC_LPTAUTO_GROUPBOX1), FALSE);
				EnableWindow(GetDlgItem(hDlg, IDC_LPT1_STATICTEXT1), FALSE);
				EnableWindow(GetDlgItem(hDlg, IDC_LPT2_STATICTEXT1), FALSE);
				EnableWindow(GetDlgItem(hDlg, IDC_LPT3_STATICTEXT1), FALSE);
		       	// Display Autodetected LPT Addresses
    	   		if(awAutoLPTAddr[0]){
	    	   		sprintf(szText,"%X",awAutoLPTAddr[0]);
	    		   	SetWindowText(GetDlgItem(hDlg, IDC_EDIT_LPT1), szText);
		        }
		       	if(awAutoLPTAddr[1]){
	    	   		sprintf(szText,"%X",awAutoLPTAddr[1]);
    	   			SetWindowText(GetDlgItem(hDlg, IDC_EDIT_LPT2), szText);
	        	}
    	   		if(awAutoLPTAddr[2]){
			       	sprintf(szText,"%X",awAutoLPTAddr[2]);
    			   	SetWindowText(GetDlgItem(hDlg, IDC_EDIT_LPT3), szText);
	        	}
    	        byLPTAuto = 1;
			}
	        else{
                // Enable Groubbox & texts
				EnableWindow(GetDlgItem(hDlg, IDC_LPTAUTO_GROUPBOX1), TRUE);
    	   		if(Prt[0].Base){
					EnableWindow(GetDlgItem(hDlg, IDC_LPT1_STATICTEXT1), TRUE);
   					EnableWindow(GetDlgItem(hDlg, IDC_EDIT_LPT1), TRUE);
	       			sprintf(szText,"%X",(WORD)Prt[0].Base);
	    	   		SetWindowText(GetDlgItem(hDlg, IDC_EDIT_LPT1), szText);
				}
	    	   	if(Prt[1].Base){
					EnableWindow(GetDlgItem(hDlg, IDC_LPT2_STATICTEXT1), TRUE);
   					EnableWindow(GetDlgItem(hDlg, IDC_EDIT_LPT2), TRUE);
	       			sprintf(szText,"%X",(WORD)Prt[1].Base);
	    	   		SetWindowText(GetDlgItem(hDlg, IDC_EDIT_LPT2), szText);
        		}
       			if(Prt[2].Base){
					EnableWindow(GetDlgItem(hDlg, IDC_LPT3_STATICTEXT1), TRUE);
   					EnableWindow(GetDlgItem(hDlg, IDC_EDIT_LPT3), TRUE);
			       	sprintf(szText,"%X",(WORD)Prt[2].Base);
    			   	SetWindowText(GetDlgItem(hDlg, IDC_EDIT_LPT3), szText);
        		}
		        byLPTAuto = 0;
    	    }
        	break;

       	case IDC_EDIT_LPT1:
        	if (HIWORD(wParam)==EN_KILLFOCUS){
            	if (CheckEditBoxIntHex(hDlg,IDC_EDIT_LPT1,MIN_LPT,MAX_LPT,&iLPTAddr,S_LPTADDROUTOFRANGE))
                	Prt[0].Base=(WORD)(iLPTAddr);
        	}
           	break;

       	case IDC_EDIT_LPT2:
        	if (HIWORD(wParam)==EN_KILLFOCUS){
            	if (CheckEditBoxIntHex(hDlg,IDC_EDIT_LPT2,MIN_LPT,MAX_LPT,&iLPTAddr,S_LPTADDROUTOFRANGE))
                	Prt[1].Base=(WORD)(iLPTAddr);
        	}
           	break;

       	case IDC_EDIT_LPT3:
        	if (HIWORD(wParam)==EN_KILLFOCUS){
            	if (CheckEditBoxIntHex(hDlg,IDC_EDIT_LPT3,MIN_LPT,MAX_LPT,&iLPTAddr,S_LPTADDROUTOFRANGE))
                	Prt[2].Base=(WORD)(iLPTAddr);
        	}
           	break;

       case IDC_CHECKBOX_AUTO:
       	if ( IsDlgButtonChecked ( hDlg, IDC_CHECKBOX_AUTO ) )
       	{
           WORD wTMAuto;

           if(bMultiProc)
	           EnableWindow(GetDlgItem(hDlg, IDC_CHECKBOX_AUTO), FALSE);

           EnableRadios ( hDlg, 0, wState, wSupp );
           ShowAlert ( hDlg, 0 );
           wCur |= gd_TIMELOOP_AUTO;

           hCur = SetCursor(LoadCursor(NULL,IDC_WAIT));

           if ( GD_GetAutoTimeMethods( &wTMAuto ) != ge_NO_ERROR )//Also Correct methods if MultiProc
           {
               GD_GetLastErrorDescription ( szText, 0x100 );
               if (!bInfo) // else message appears from DLL
                   MessageBox  ( NULL, szText, "Error", MB_ );
               PostMessage ( hDlg, WM_COMMAND, IDCANCEL, 0 );
           }

           CheckRadio ( hDlg, wTMAuto );

           SetCursor(hCur);
       	}
       	else
       	{
           EnableRadios ( hDlg, 1, wState, wSupp );
           wCur &= 0xFFFF ^ gd_TIMELOOP_AUTO;
           CheckRadio ( hDlg, wCur );
           ShowAlert ( hDlg, ( wCur & wSupp ) != wCur );
		}
		break;

       case IDC_RADIOBUTTON6:
            if ( IsDlgButtonChecked ( hDlg, IDC_RADIOBUTTON6 ) )
            {
               wState = wState & ( 0xFF02 );
               wCur = gd_TIME_TRADITIONAL + gd_LOOP_TRADITIONAL;
               CheckRadio ( hDlg, 0xFF02 );
               ShowAlert ( hDlg, ( wCur & wSupp ) != wCur ); // This uses same 3ch as timer method
            }

            EnableRadios (hDlg, !IsDlgButtonChecked(hDlg, IDC_CHECKBOX_AUTO), wState, wSupp );
       break;

       case IDC_RADIOBUTTON1:
            wCur = (wCur & 0xFF00) + gd_TIME_SYSTEM;
            ShowAlert ( hDlg, ( wCur & wSupp ) != wCur );
            goto TotalEnable;

       case IDC_RADIOBUTTON2:
            wCur = (wCur & 0xFF00) + gd_TIME_TRADITIONAL;
            ShowAlert ( hDlg, ( wCur & wSupp ) != wCur );
            if ( !IsDlgButtonChecked(hDlg, IDC_RADIOBUTTON6) )
               goto TotalEnable;
            break;

       case IDC_RADIOBUTTON3:
            wCur = (wCur & 0xFF00) + gd_TIME_SECONDARY;
            ShowAlert ( hDlg, ( wCur & wSupp ) != wCur );
            goto TotalEnable;

       case IDC_RADIOBUTTON4:
            wCur = (wCur & 0xFF  ) + gd_LOOP_PENTIUM;
            goto TotalEnable;

       case IDC_RADIOBUTTON5:
            wCur = (wCur & 0xFF  ) + gd_LOOP_BSF;
            goto TotalEnable;

       case IDC_RADIOBUTTON7:
            wCur = (wCur & 0xFF  ) + gd_LOOP_SECONDARY;
            ShowAlert ( hDlg, ( wCur & wSupp ) != wCur ); // This uses same 0ch as timer method
TotalEnable:

            wState = wSupp | ( 0xFFFF ^ gd_LOOP_PENTIUM );
            EnableRadios (hDlg, !IsDlgButtonChecked(hDlg, IDC_CHECKBOX_AUTO), wState, wSupp );
       break;

       case IDOK:
			if(!byLPTAuto){
            	//If Port i present - check User value
	           	if(awAutoLPTAddr[0]){
                	if(CheckEditBoxIntHex(hDlg,IDC_EDIT_LPT1,MIN_LPT,MAX_LPT,&iLPTAddr,S_LPTADDROUTOFRANGE))
	    	           	Prt[0].Base=(WORD)(iLPTAddr);
					else
                    	break;
//               			PostMessage(hDlg, WM_COMMAND, IDC_EDIT_LPT1, 0);
				}
        	   	if(awAutoLPTAddr[1]){
                	if(CheckEditBoxIntHex(hDlg,IDC_EDIT_LPT2,MIN_LPT,MAX_LPT,&iLPTAddr,S_LPTADDROUTOFRANGE))
	            	   	Prt[1].Base=(WORD)(iLPTAddr);
					else
                    	break;
//               			PostMessage(hDlg, WM_COMMAND, IDC_EDIT_LPT2, 0);
				}
	           	if(awAutoLPTAddr[2]){
                	if(CheckEditBoxIntHex(hDlg,IDC_EDIT_LPT3,MIN_LPT,MAX_LPT,&iLPTAddr,S_LPTADDROUTOFRANGE))
    	           		Prt[2].Base=(WORD)(iLPTAddr);
					else
                    	break;
//               			PostMessage(hDlg, WM_COMMAND, IDC_EDIT_LPT3, 0);
				}
			}
            else{
 	           	for(i=0; i < 3; i++){
            		Prt[i].Base = awAutoLPTAddr[i];
            	}
            }
            i = ( IsDlgButtonChecked ( hDlg, IDC_RADIOBUTTON1 ) ? gd_TIME_SYSTEM : 0 )      |
                ( IsDlgButtonChecked ( hDlg, IDC_RADIOBUTTON2 ) ? gd_TIME_TRADITIONAL : 0 ) |
                ( IsDlgButtonChecked ( hDlg, IDC_RADIOBUTTON3 ) ? gd_TIME_SECONDARY : 0 )   |
                ( IsDlgButtonChecked ( hDlg, IDC_RADIOBUTTON4 ) ? gd_LOOP_PENTIUM : 0 )       |
                ( IsDlgButtonChecked ( hDlg, IDC_RADIOBUTTON5 ) ? gd_LOOP_BSF : 0 )         |
                ( IsDlgButtonChecked ( hDlg, IDC_RADIOBUTTON6 ) ? gd_LOOP_TRADITIONAL : 0 ) |
                ( IsDlgButtonChecked ( hDlg, IDC_RADIOBUTTON7 ) ? gd_LOOP_SECONDARY : 0 )   |
                ( IsDlgButtonChecked ( hDlg, IDC_CHECKBOX_AUTO) ? gd_TIMELOOP_AUTO : 0 );
            sprintf(szText," ==== Advanced Dialog is closed by OK button with flags==0x%08lX ====",i);
            GD_PrintLog(szText);
            EndDialog ( hDlg, i );
       break;

       case IDCANCEL:
       		byLPTAuto = byLPTAutoInit;
        	for(i=0; i < 3; i++)
        		Prt[i].Base = awBaseInit[i];
            GD_PrintLog(" ==== Advanced Dialog is cancelled... ====");
            EndDialog ( hDlg, wInitial );
       break;
       }
       break;
 default: return FALSE;
 }
 return (BOOL)DefWindowProc(hDlg,uMsg,wParam,lParam);
}
