2009-09-16 2 views
4

나는 의심의 여지가있다. COM을 초기화하고, CoCreateInstance를 수행하고, 일부 인터페이스를 사용합니다. 릴리스를 호출하지 않고 CoUninitialize를 호출 할 수 있습니까? 메모리/리소스 유출이 발생합니까?COM : Release를 호출하지 않고 CoUninitialize를 호출 할 수 있습니까?

미리 감사드립니다. -Mani. MSDN에서

+0

완벽하게 유효한 질문이지만 질문하는 이유를 자세히 설명해주십시오. 단지 호기심이 있거나 문제를 적절하게 해제하는 데 문제가 있습니까? – sharptooth

답변

3

:

http://msdn.microsoft.com/en-us/library/ms688715%28VS.85%29.aspx

의 주요 창을 숨기고 통해 떨어지는 신청 후 COM 라이브러리에 수행 된 마지막 호출 로

CoUninitialize는 응용 프로그램 종료시 호출 할 필요는 주요 메시지 루프. 열린 대화 이 남아 있으면 CoUninitialize가 모달 메시지 루프를 시작하고 컨테이너 또는이 COM 응용 프로그램의 서버에서 보류중인 메시지를 전달합니다. 메시지를 디스 패칭하면 CoUninitialize는 응용 프로그램이 대기중인 모든 메시지를 수신하기 전에 을 종료하지 않도록합니다. COM이 아닌 메시지는 무시됩니다.

종료시 CoUninitialize를 호출해야하며 그때까지 메모리 누수가 있더라도 상관 없습니다.

+2

"종료 할 때 CoUninitialize 만 호출하면됩니다". 이것은 전적으로 사실입니다. CoInitialized 된 스레드를 파괴 할 때 호출해야합니다. 종종 이러한 스레드는 종료 전에 오래 죽습니다. – Goz

+0

사실,이 컨텍스트에서 사용한 적이 없다고 생각합니다. –

0

AFAIK, CoUninitialize는 현재 스레드에서 사용중인 모든 COM 리소스를 해제한다고 가정합니다. 나는 그것에 의지하지 않을 것이다. 오히려 내가 초기화되지 않은 것을 호출하기 전에 모든 것을 해제하는지 확인하고 싶습니다.

1

CoUninitialize() 대신 (IUnknown::Release())을 개체에 사용하면 안됩니다.이 개체는 매우 다른 기능입니다.

IUnknown::Release()은 개체의 참조 횟수를 줄이고 파괴 가능성이 있습니다. 마샬링이 사용되지 않는 경우이 호출은 vtable (컨트롤이 COM 서버 코드로 직접 전달됨)을 통해 올바르게 수행되며 COM 하위 시스템은 아무 것도 수행하지 않습니다.

CoUninitialize()는 마샬링 관련 객체라고 생각되는 호출 스레드에 대한 COM 관련 리소스를 해제합니다. 마샬링이 사용되지 않는 경우 개체는 코드 만 알고 있으므로 릴리스되지 않은 상태로 유지됩니다.

그래서 다른 대신 하나를 사용하지 않아야합니다.

+0

감사합니다. 만약 내가 실제로 tat, CoUninitialize Release를 호출하지 않고 사용한다면? 누출로 인해 해를 입니까? 나는 ur 대답에 따라 변경해야하기 때문에 이것에서 흥미 롭습니다 –

+0

마샬링이 비활성화되면 객체가 유출됩니다. 질문을 편집하고 변경하려는 내용, 방법 및 이유에 대해 자세히 설명해주십시오. – sharptooth

2

COM 초기화 여부에 관계없이 릴리스에 대한 호출을 생략하면 개체가 서버 측에서 활성 상태로 유지되어 서비스가 실행되지 않는 경우 전체 서버를 아무런 이유없이 유지할 수 있습니다. 즉, 서버 측에서 메모리 누수가 발생하며 COM 서버를 다시 시작해야만이를 제거 할 수 있습니다.

COM을 처음 사용하기 시작할 때 비슷한 질문을 한 적이 있습니다. 내가 작업하고 있던 클라이언트는 많은 쓰레드를 사용하고 있었으며, 각 쓰레드가 수행하는 다른 작업을 위해 인터페이스를 재사용하려고했습니다. 이로 인해 인터페이스 캐시 관리가 상당히 어려워졌습니다. 결국에는 바로 가기가 없었습니다. MTA, GIT 또는 인터페이스 마샬링을 사용하지 않는 한 인터페이스를 만든 스레드는 인터페이스를 해제해야합니다.

더 쉽게 만들려면 CComPtr을 사용하여 만든 인터페이스를 관리하십시오. 일반 포인터와 마찬가지로 스마트 포인터를 사용하면 때로는 훨씬 쉬워집니다.

+0

늦은 코멘트에 대해 사과드립니다. CComPtr을 사용하여 문제를 해결했습니다. 모든 관심을 가져 주셔서 감사합니다. -Mani. –

관련 문제