使用atl_com建立第一個本機伺服器

來源:互聯網
上載者:User

使用atl_com建立第一個本機伺服器
vc6
1.file-->new-->project--->atl com project
設定工程名:LocalServer

2.在server type 下選擇 executable ,之後選擇 finish

3.系統自動產生了一些檔案其中比較重要的有:
localserver.idl// 介面定義檔案
localserver.cpp// 可執行檔(編譯串連後產生 localserver.exe )
LocalServerps.mk// makefile

3.在 localserver.idl 加入新的介面定義

//如果不知道上面的東西的含義那麼去補補idl
//注意你可以使用想到來產生一個介面,而且想到還會產生和這個介面對應的組件(實現這個介面的類)
//使用方式如下:insert-->new atl object -->選擇object 中的simple object-->
之後會彈出一個對話方塊atl object wizard properties,選擇names,在Shortname裡填入Mathb別的框會自動產生。
之後選擇attribute,選擇appartment ,custom, yes ,support isuppoerterrorinfo
選擇ok,我們成功地在idl中加入了一個新的介面IMath,並且定義了一個新的組件CMath,這個組件實現了IMath,之後我們會讓這個組件實現更多的介面。。
這時系統新組建檔案math.h .cMath的標頭檔。
math.cpp  CMath的實現檔案。
Math.rgs  math組件的registar指令檔。有了他你就不用自己寫把組件註冊到註冊表的東西了

4.為IMath加入函數Add
  在Classview中,游標放在IMath點又建選擇Add method .之後填入傳回值,函數名,參數
選擇確定,同時系統還在CMath加入了相應的代碼
//到這裡系統為idl檔案加入了如下內容:
 [
  object,
  uuid(73DEDCFD-C87B-4E68-B6D1-A36FA3316DCD),
 
  helpstring("IMath Interface"),
  pointer_default(unique)
 ]
 interface IMath : IUnknown
 {
  [helpstring("method Add")] HRESULT Add([in]int ipara1,[in]int ipara2,[out]int *pResult);
 };
//為math.h加入了如下內容
// CMath
class ATL_NO_VTABLE CMath :
 public CComObjectRootEx<CComSingleThreadModel>,
 public CComCoClass<CMath, &CLSID_Math>,
 public ISupportErrorInfo,
 public IMath,//...........
 public IAdvancedMath//.....................
{
public:
 CMath()
 {
 }

DECLARE_REGISTRY_RESOURCEID(IDR_MATH)

DECLARE_PROTECT_FINAL_CONSTRUCT()

BEGIN_COM_MAP(CMath)
 COM_INTERFACE_ENTRY(IMath)
 COM_INTERFACE_ENTRY(IAdvancedMath)
 COM_INTERFACE_ENTRY(ISupportErrorInfo)
END_COM_MAP()

// ISupportsErrorInfo
 STDMETHOD(InterfaceSupportsErrorInfo)(REFIID riid);

// IMath
public:
 STDMETHOD(Add)(/*[in]*/int ipara1,/*[in]*/int ipara2,/*[out]*/int *pResult);//。,。。。。

public:
 //IAdvancedMath
 //手動加入的介面
 STDMETHOD(AdvancedAdd)(/*in*/int ipara1,/*[in]*/int ipara2,/*[out]*/int *pResult);
};

//對math.cpp加入的內容
STDMETHODIMP CMath::Add(int ipara1, int ipara2, int *pResult)
{
 // TODO: Add your implementation code here
 *pResult = ipara1 +ipara2;
 cout<<"CMath::Add/n";
 return S_OK;
}
5.手動加入新介面IAdvancedMath(上面使用的嚮導就是每次定義一個介面,同時為他弄一個組件。所以不能利用嚮導來為一個組件加入多個介面)。並加入一個函數
在localserver.idl中加入:
//add manual
 [
  object,
  uuid(63FFA301-5BB0-4e0a-95CF-92C22FF1B796),
 
  helpstring("IAdvancedMath Interface"),
  pointer_default(unique)
 ]
 interface IAdvancedMath : IUnknown
 {
//加入的函數
  [helpstring("method Add")] HRESULT AdvancedAdd([in]int ipara1,[in]int ipara2,[out]int *pResult);
 };

 

[
 uuid(0C01D7A4-D53A-4DF2-9D7A-1F76140E1C04),
 version(1.0),
 helpstring("LocalServer 1.0 Type Library")
]
library LOCALSERVERLib
{
 importlib("stdole32.tlb");
 importlib("stdole2.tlb");

 [
  uuid(82139624-D5FF-4418-8A11-EAA7EF381147),
  helpstring("Math Class")
 ]
 coclass Math
 {
  [default] interface IMath;//使用想到自動加入的
  interface IAdvancedMath;//我們加入的
 };
};
為CMath加入 public IAdvancedMath,使之繼承IAdvancedMath,//...........如上。
為CMath加入
public:
 //IAdvancedMath
 STDMETHOD(AdvancedAdd)(/*in*/int ipara1,/*[in]*/int ipara2,/*[out]*/int *pResult);

及其實現:
STDMETHODIMP CMath::AdvancedAdd(/*in*/int ipara1,/*[in]*/int ipara2,/*[out]*/int *pResult)
{
 *pResult = ipara1 +ipara2;
 
 cout<<"CMath::AdvancedAdd/n";
 return S_OK;
}
6.建立localserver.exe
7.在目前的目錄下進入命令列。
執行命令:midl localserver.idl//這一步可以省略
執行命令:nmake -f LocalServerps.mk//效果是產生proxy_stub.dll//可能dll的名字不一樣這裡只是例子
執行命令:regsvr32.exe proxy_stub.dll//註冊存根代理dll

//.............
在以上的步驟中 :主要的就是加入介面和實現介面(組件)
同時註冊代理存根。
注意我們需要修改的檔案並不多!·!!!··
//////////////////////////////////////////////////////////
//。。。。。。。。。。。。
產生用戶端:
建立一個簡單的控制台程式:

#include "stdafx.h"
//下面兩個包含檔案的順序重要
#include "../LocalServer.h"
#include "../LocalServer_i.c"

#include <iostream>
using namespace std;

int main(int argc, char* argv[])
{
 cout<<"in  client:init com/n";
 if(FAILED(::CoInitialize(NULL)) )//。。。。。。
 {
  cout<<"init com error /n";
  return 0;
 }
 IMath *pm;
 HRESULT hr;

 hr = ::CoCreateInstance( CLSID_Math ,//。。。。。。。。。。
     NULL,CLSCTX_LOCAL_SERVER, IID_IMath, (void **)&pm );
 if ( FAILED(hr))
 {
  cout<<" get pimath error  hr="<<hr<<"/n";
  if ( hr== REGDB_E_CLASSNOTREG )
  {
   cout<<"REGDB_E_CLASSNOTREG "<<endl;
  }
  if ( hr ==CLASS_E_NOAGGREGATION)
  {
   cout<<"CLASS_E_NOAGGREGATION "<<endl;
  }
  ::CoUninitialize();
  return 0;
 }
 int rs=0;
 pm->Add( 10 ,20 , &rs);
 cout<<"result  is :"<<rs<<endl;
 IAdvancedMath *pam;
 hr=pm->QueryInterface(IID_IAdvancedMath ,(void **)&pam);
 if ( FAILED(hr))
 {
  cout<<" get pam error  hr="<<hr<<"/n";
  if ( hr== REGDB_E_CLASSNOTREG )
  {
   cout<<"REGDB_E_CLASSNOTREG "<<endl;
  }
  if ( hr ==CLASS_E_NOAGGREGATION)
  {
   cout<<"CLASS_E_NOAGGREGATION "<<endl;
  }
  pm->Release();
  ::CoUninitialize();
  return 0;
 }
 pam->AdvancedAdd(50,100, &rs);
 cout<<"result  is :"<<rs<<endl;
 pm->Release();
 pam->Release();
 ::CoUninitialize();
 return 0;
}
建立之後 直接運行用戶端就可以了。。
(如果伺服器還沒有啟動則, 用戶端會通過某種方式來讓伺服器啟動的。。) 

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.