2009-04-04 3 views
3

이것은 Register implementation of a com interface의 연속입니다. 지금은 디버깅이 필요한 실제 코드가 있습니다.깨진 COM 개체 등록

IAudioSessionEvents를 구현하는 COM 개체와 IClassFactory를 구현하고 첫 번째 개체를 생성하는 COM 개체가 두 가지 있습니다. 내가 RegisterKeyValue (...)를 생략 한

BOOL RegisterClassManually(WCHAR* szGuid, WCHAR* szDllPath) 
{ 
WCHAR szKeyName[1024]; 
wsprintf(szKeyName, TEXT("Software\\Classes\\CLSID\\%s"), szGuid); 

if(!RegisterKeyValue(HKEY_CURRENT_USER, szKeyName, NULL, TEXT(DESCRIPTION_CONST))) return false; 

wsprintf(szKeyName, TEXT("Software\\Classes\\CLSID\\%s\\InprocServer32"), szGuid); 

if(!RegisterKeyValue(HKEY_CURRENT_USER, szKeyName, NULL, szDllPath)) return false; 
if(!RegisterKeyValue(HKEY_CURRENT_USER, szKeyName, TEXT("ThreadingModel"), TEXT("Apartment"))) return false; 

return true; 
} 

STDAPI DllRegisterServer() 
{ 
//Write data to HKEY_CURRENT_USER\\Software\\Classes\\CLSID\\{GUID} 
// Also ""\\InProcServer32 
// Also "".ThreadingModel = "Apartment" 

WCHAR* szGuid; 
WCHAR szDllPath[512]; 
StringFromCLSID(CLSID_AudioEventsFactory, &szGuid); 

if(g_dllModule == NULL) return SELFREG_E_CLASS; 

GetModuleFileName(g_dllModule, szDllPath, 512); 

if(!RegisterClassManually(szGuid, szDllPath)) return SELFREG_E_CLASS; 

StringFromCLSID(CLSID_AudioEvents, &szGuid); 

if(!RegisterClassManually(szGuid, szDllPath)) return SELFREG_E_CLASS; 

return S_OK; 
} 

, 간단한 레지스트리 코드 나는 등의 작품을 확인했습니다

다음 코드 (COM 등록에 대한 이해에 따라) 그 객체를 등록 예정된.

이 코드는 이러한 COM 객체를 사용하려고 시도합니다 :

IAudioSessionEvents* listener = NULL; 

IClassFactory* factory = NULL; 

//Fails on this call 
hr = CoGetClassObject(CLSID_AudioEventsFactory, CLSCTX_ALL, NULL, __uuidof(IClassFactory), (void**)&factory); 

if(hr != S_OK) 
{ 
    ... Report Error ... 
} 

hr = factory->CreateInstance(NULL, __uuidof(IAudioSessionEvents), (void**)&listener); 

CoGetClassObject를에 대한 호출 (...)이 시간의 =의 0x80040111를 반환 (ClassFactory 요청한 클래스를 제공 할 수 없음).

STDAPI DllGetClassObject(const CLSID& clsid, 
        const IID& iid, 
        void** ppv) 
{ 

if (clsid == __uuidof(IClassFactory)) 
{ 
    AudioEventsFactory *pFact = new AudioEventsFactory; 
    if (pFact == NULL) 
     return E_OUTOFMEMORY; 
    else 
    { 
     return pFact->QueryInterface(iid , ppv); 
    } 
} 

return CLASS_E_CLASSNOTAVAILABLE; 
} 

내가 잘못 여기서 뭐하는 거지 :

DllGetClassObject의 구현

는 (1800 정보 당 ommision을 지적)? 나는 그 COM 등록에 의심 스럽지만 실제로 레지스트리에서 요구되는 것을 정확히 나열하는 것을 찾을 수 없습니다. 저는 지금 리버스 엔지니어링을했습니다.

답변

2

이 문서 COM in plain C에는 ATL을 사용하지 않고 COM dll을 구현하는 방법에 대한 설명이 있습니다. 1800에서 지적한대로 DllGetClassObject는 COM 개체를 만들기 위해 호출됩니다. 또한 The COM Programmer's Cookbook은 COM에 대한 좋은 참고 자료입니다.