www.pudn.com > GEOPC_modified_2005621145656299.rar > EXEMAIN.CPP, change:2005-06-21,size:10901b


// exemain.cpp 
// 
//  This source file contains the EXE Mainline code for  
//  this sample OPC server. 
// 
// 
// (c) COPYRIGHT 1996,1997 INTELLUTION INC. 
// ALL RIGHTS RESERVED 
// 
// Original Author: Al Chisholm 
// 
// Modification Log: 
//	Vers    Date   By    Notes 
//	----  -------- ---   ----- 
//	0.00  11/18/96 ACC 
// 0.90  04/08/97 ACC   add async logic 
//       09/11/97 ACC   move init/delete critical section to fix shutdown crash 
// 
 
#define INITGUID 
#define WIN32_LEAN_AND_MEAN 
//#include <afx.h> 
#include "windows.h" 
#include "OLE2.h" 
#include <stdio.h> 
#include <objbase.h> 
#include <assert.h> 
#include "OPCXXX.h" 
#include "OPCfact.h" 
#include "OPCTHRD.h" 
 
 
 
 
 
#define TimerRes	100		// This sample updates 1 per second max 
// Globals  
// 
DWORD			objectCount = 0;		// Number of servers created 
DWORD			lockCount = 0;			// Standard COM Server lock count 
HINSTANCE		serverInstance = 0;		// DLL instance (e.g. for LoadString) 
FILETIME		serverStartTime;		// OPC specific server start time 
IMalloc			*pIMalloc = 0;			// Common memory allocator 
CRITICAL_SECTION	CritSec;			// For compatability with DLL version 
 
HWND	serverWindow = NULL; 
UINT	TimerID; 
BOOL	Register( IUnknown *Fact, DWORD regCls); 
BOOL	Unregister( void); 
STDAPI	DllCanUnloadNow( void); 
 
HMENU hMenu; 
HMENU hMenuPopup; 
#define IDM_COUR    10 
const int CLSID_STRING_SIZE = 39 ; 
char		szMyPath[80]; 
// 
// The following code supports the EXE version  
//  of the OPC Sample server 
// 
 
 
// OPCWndProc() 
//   This is the main windows procedure for the OPC Sample LocalServer. 
void CLSIDtoString(const CLSID& clsid, 
                 char* szCLSID, 
                 int length) 
{ 
	assert(length >= CLSID_STRING_SIZE) ; 
	// Get CLSID 
	LPOLESTR wszCLSID = NULL ; 
	HRESULT hr = StringFromCLSID(clsid, &wszCLSID) ; 
	assert(SUCCEEDED(hr)) ; 
 
	// Covert from wide characters to non-wide. 
	wcstombs(szCLSID, wszCLSID, length) ; 
 
	// Free memory. 
	CoTaskMemFree(wszCLSID) ; 
} 
LONG DeleteKey(HKEY hKeyParent,           // Parent of key to delete 
               const char* lpszKeyChild)  // Key to delete 
{ 
	// Open the child. 
	HKEY hKeyChild ; 
	LONG lRes = RegOpenKeyEx(hKeyParent, lpszKeyChild, 0, 
	                         KEY_ALL_ACCESS, &hKeyChild) ; 
	if (lRes != ERROR_SUCCESS) 
	{ 
		return lRes ; 
	} 
 
	// Enumerate all of the decendents of this child. 
	FILETIME time ; 
	char szBuffer[256] ; 
	DWORD dwSize = 256 ; 
	while (RegEnumKeyEx(hKeyChild, 0, szBuffer, &dwSize, NULL, 
	                    NULL, NULL, &time) == S_OK) 
	{ 
		// Delete the decendents of this child. 
		lRes = DeleteKey(hKeyChild, szBuffer) ; 
		if (lRes != ERROR_SUCCESS) 
		{ 
			// Cleanup before exiting. 
			RegCloseKey(hKeyChild) ; 
			return lRes; 
		} 
		dwSize = 256 ; 
	} 
 
	// Close the child. 
	RegCloseKey(hKeyChild) ; 
 
	// Delete this child. 
	return RegDeleteKey(hKeyParent, lpszKeyChild) ; 
} 
 
// 
// Create a key and set its value. 
// 
BOOL SetKeyAndValue(const char* szKey, 
                    const char* szSubkey, 
                    const char* szValue) 
{ 
	HKEY hKey; 
	char szKeyBuf[1024] ; 
 
	// Copy keyname into buffer. 
	strcpy(szKeyBuf, szKey) ; 
 
	// Add subkey name to buffer. 
	if (szSubkey != NULL) 
	{ 
		strcat(szKeyBuf, "\\") ; 
		strcat(szKeyBuf, szSubkey ) ; 
	} 
 
	// Create and open key and subkey. 
	long lResult = RegCreateKeyEx(HKEY_CLASSES_ROOT , 
	                              szKeyBuf,  
	                              0, NULL, REG_OPTION_NON_VOLATILE, 
	                              KEY_ALL_ACCESS, NULL,  
	                              &hKey, NULL) ; 
	if (lResult != ERROR_SUCCESS) 
	{ 
		return FALSE ; 
	} 
 
	// Set the Value. 
	if (szValue != NULL) 
	{ 
		RegSetValueEx(hKey, NULL, 0, REG_SZ,  
		              (BYTE *)szValue,  
		              strlen(szValue)+1) ; 
	} 
 
	RegCloseKey(hKey) ; 
	return TRUE ; 
} 
 
 
void MyRegist() 
{ 
	char szCLSID[39] ; 
			 
			char szKey[300],szKey1[300],szKey0[300]; 
			 
			CLSIDtoString(CLSID_OPCSampleServer, szCLSID, sizeof(szCLSID)) ; 
 
			SetKeyAndValue("OPC.F.1", NULL, "XHOPC") ; 
			SetKeyAndValue("OPC.F.1", "CLSID", szCLSID) ; 
			SetKeyAndValue("OPC.F.1", "OPC", NULL) ; 
 
 
			strcpy(szKey, "CLSID\\") ; 
			strcat(szKey, szCLSID) ; 
			SetKeyAndValue(szKey, NULL, "XHOPC") ; 
			SetKeyAndValue(szKey, "ProgID", "OPC.F.1") ; 
		//	char		szMyPath[80]; 
			SetKeyAndValue(szKey, "LocalServer32", szMyPath) ; 
 
			strcpy(szKey1,"\\Implemented Categories"); 
			strcat(szKey,szKey1); 
			strcpy(szKey0,szKey); 
	 
 
			SetKeyAndValue(szKey, NULL, NULL) ; 
			strcpy(szKey1, "\\") ; 
			CLSIDtoString(IID_CATID_OPCDAServer20, szCLSID, sizeof(szCLSID)) ; 
			strcat(szKey1, szCLSID) ;			 
			strcat(szKey,szKey1);	 
			SetKeyAndValue(szKey, NULL, NULL) ; 
				 
			strcpy(szKey1, "\\") ; 
			CLSIDtoString(IID_CATID_OPCDAServer10, szCLSID, sizeof(szCLSID)) ; 
			strcat(szKey1, szCLSID) ; 
			strcat(szKey0,szKey1); 
			SetKeyAndValue(szKey0, NULL, NULL) ; 
} 
void MyUnRegist() 
{ 
	char szCLSID[CLSID_STRING_SIZE] ; 
	CLSIDtoString(CLSID_OPCSampleServer, szCLSID, sizeof(szCLSID)) ; 
 
	// Build the key CLSID\\{...} 
	char szKey[64] ; 
	strcpy(szKey, "CLSID\\") ; 
	strcat(szKey, szCLSID) ; 
 
	// Delete the CLSID Key - CLSID\{...} 
	DeleteKey(HKEY_CLASSES_ROOT, szKey) ; 
	DeleteKey(HKEY_CLASSES_ROOT, "OPC.F.1") ; 
 
} 
 
LRESULT CALLBACK OPCWndProc( HWND hWnd, UINT iMsg, WPARAM wParam, LPARAM lParam) 
{ 
	int xPos,yPos,uCmdType; 
	WORD wNotifyCode; 
	WORD        wID ; 
	HDC hDC; 
	 
	char cs[300]; 
  switch ( iMsg) { 
   
	 
 
    case WM_DESTROY: 
      KillTimer(serverWindow, TimerID); 
      PostQuitMessage( 0); 
      break; 
	case WM_TIMER: 
		UpdateServers(TimerRes); 
		break; 
	case  WM_COMMAND: 
		 wNotifyCode = HIWORD(wParam);  
		 wID = LOWORD(wParam);  
		 
		 switch(wID) 
		 { 
		 case IDM_COUR+0: 
			 MyRegist(); 
			 break; 
		 case IDM_COUR+1: 
			 MyUnRegist(); 
			 break; 
		 default: 
			 break; 
		 } 
		 return 0 ; 
		 break; 
	 
		  
	default: 
      return DefWindowProc( hWnd, iMsg, wParam, lParam); 
  } 
  return 0; 
} 
 
WORD DINUM,AINUM; 
 
LPOLESTR AxTags[500]; 
LPOLESTR DxTags[500]; 
 
 
BOOL   ReadCfg() 
{ 
	char szMyPath[128]; 
	char szTagName[128]; 
	char bSection[50]; 
	WORD i; 
 
	DINUM=10; 
	AINUM=10; 
	for(i=0;i<DINUM;i++) 
	{ 
		wsprintf((LPSTR)bSection,"DI%d",(i+1)); 
		 
		DxTags[i]=new WCHAR[strlen(bSection)*2 + 1]; 
		mbstowcs(DxTags[i],(const char *)bSection,100); 
				 
	} 
	for(i=0;i<AINUM;i++) 
	{ 
		wsprintf((LPSTR)bSection,"AI%d",(i+1)); 
		 
		AxTags[i]=new WCHAR[strlen(bSection)*2 + 1]; 
		mbstowcs(AxTags[i],(const char *)bSection,100); 
				 
	} 
	return TRUE; 
	 
 
 
} 
 
int WINAPI WinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpszCmdLine, int nCmdShow) 
{ 
  BOOL success = TRUE; 
  MSG  msg; 
 
  serverInstance = hInstance; 
  msg.wParam = 0; 
  InitializeCriticalSection(&CritSec); 
 
 
  GetModuleFileName((HMODULE)hInstance, szMyPath, 79); 
 
  if ( SUCCEEDED( CoInitialize( NULL)))  
  { 
//	  hr = CoInitializeSecurity(NULL, , , NULL); 
    IClassFactory* serverFactory = new OPCClassFactory( CLSID_OPCSampleServer); 
    if ( serverFactory != NULL && Register(serverFactory,REGCLS_MULTIPLEUSE))  
	{ 
      if ( !hPrevInstance)  
	  { 
        WNDCLASS wc; 
        wc.style = CS_HREDRAW | CS_VREDRAW; 
        wc.lpfnWndProc = OPCWndProc; 
        wc.cbClsExtra = 0; 
        wc.cbWndExtra = 0; 
        wc.hInstance = serverInstance; 
        wc.hIcon = 0; 
        wc.hCursor = LoadCursor( NULL, IDC_ARROW); 
        wc.hbrBackground = (HBRUSH)(COLOR_WINDOW+1); 
        wc.lpszMenuName = 0; 
        wc.lpszClassName = "XOPC"; 
 
        success = (RegisterClass( &wc) != 0); 
      } 
 
	  hMenu = CreateMenu () ; 
 
   
	 hMenuPopup = CreateMenu () ; 
        
	 AppendMenu (hMenuPopup, MF_STRING, IDM_COUR + 0, 
                      "Register") ; 
     AppendMenu (hMenuPopup, MF_STRING, IDM_COUR + 1, 
                      "UnRegister") ; 
 
	 AppendMenu (hMenu, MF_STRING | MF_POPUP, (int) hMenuPopup, 
                 "opc") ; 
   
	   
 
      if ( success && ( serverWindow = CreateWindow( "XOPC", "XOPCServer", WS_OVERLAPPEDWINDOW, 
                                                     CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, 
                                                     NULL, hMenu, serverInstance, NULL)) != NULL)  
	  { 
        CoGetMalloc(MEMCTX_TASK, &pIMalloc);	// 'TASK' ok for DLL use 
        ShowWindow( serverWindow, SW_MINIMIZE); 
        UpdateWindow( serverWindow); 
//		if(!XdbRegister(FALSE,serverWindow)) return -1; 
		if(!ReadCfg())   return -1; 
        CoFileTimeNow( &serverStartTime); 
 
		// Start a psuedo-thread for Async Handling 
		// 
		InitServerSlots(); 
		TimerID = SetTimer(serverWindow, 0, TimerRes, 0);	// timer could be faster... 
 
        while ( GetMessage( &msg, NULL, 0, 0))  
		{ 
          TranslateMessage( &msg); 
          DispatchMessage( &msg); 
        } 
 
        pIMalloc->Release(); 
//		XdbUnRegister(FALSE,serverWindow); 
      } 
      Unregister(); 
    } 
    else  
	{ 
      // Delete the factory if we did not successfully register it.  If it was registered, the factory 
      // will be deleted by the Unregister() function. 
      if ( serverFactory != NULL) 
        delete serverFactory; 
    } 
    CoUninitialize(); 
    DeleteCriticalSection(&CritSec); 
  } 
   
  return msg.wParam; 
} 
 
 
 
 
// OPCServerUnload() 
//   This function is called when an object inside the server is destroyed.  If the server 
//   can legally unload, this function posts a WM_QUIT message to the main window.   
 
void OPCServerUnload( void) 
{ 
  if ( serverWindow != NULL && DllCanUnloadNow() == S_OK) 
    PostMessage( serverWindow, WM_CLOSE, 0, 0); 
} 
 
 
 
 
DWORD mRegisterID; 
 
// Register() 
//   This function is called by the EXE version of the server to register this class factory 
//   with the OLE libraries.  It returns TRUE if it is successful. 
 
BOOL Register( IUnknown *Fact, DWORD regCls) 
{ 
  return SUCCEEDED( CoRegisterClassObject( CLSID_OPCSampleServer,  
				Fact, CLSCTX_LOCAL_SERVER, regCls, &mRegisterID)); 
} 
 
 
 
// Unregister() 
//   Unregisters this class factory with the OLE libraries. 
 
BOOL Unregister( void) 
{ 
  BOOL success = SUCCEEDED( CoRevokeClassObject( mRegisterID)); 
  mRegisterID = 0; 
  return success; 
} 
 
/////////////////////////////////////// 
// DllCanUnloadNow() 
//  This is the standard function that is called  
//  to determine whether or not this DLL is 
//  in use. 
// 
/////////////////////////////////////// 
STDAPI DllCanUnloadNow( void) 
{ 
	SCODE sc; 
	BOOL canUnload; 
 
	// If we have no objects and we are not locked 
	// then we can be unloaded (e.g. by VB). 
	// 
	canUnload = ( objectCount == 0 && lockCount == 0); 
	sc = canUnload ? S_OK : S_FALSE; 
	return sc; 
}