Aplicativo MFC pára de responder quando você inicializar o aplicativo como um apartamento multithreaded no Visual C++ .NET ou no Visual C++ 2005

IMPORTANTE: Este artigo foi traduzido por um sistema de tradução automática (também designado por Machine Translation ou MT), não tendo sido portanto traduzido ou revisto por pessoas. A Microsoft possui artigos traduzidos por aplicações (MT) e artigos traduzidos por tradutores profissionais, com o objetivo de oferecer em português a totalidade dos artigos existentes na base de dados de suporte. No entanto, a tradução automática não é sempre perfeita, podendo conter erros de vocabulário, sintaxe ou gramática. A Microsoft não é responsável por incoerências, erros ou prejuízos ocorridos em decorrência da utilização dos artigos MT por parte dos nossos clientes. A Microsoft realiza atualizações freqüentes ao software de tradução automática (MT). Obrigado.

Clique aqui para ver a versão em Inglês deste artigo: 828643
Sintomas
Quando você usar a seguinte chamada de método CoInitializeEx para inicializar um aplicativo Microsoft Foundation Class Library (MFC) como um apartamento multithreaded (MTA), o aplicativo pode parar de responder:
CoInitializeEx(NULL, COINIT_MULTITHREADED)
Causa
Um aplicativo MFC usa muita de armazenamento local de thread para armazenar informações de estado do segmento e processar informações de estado. Portanto, um aplicativo MFC não é compatível com um modelo de programação thread livre. Por exemplo, se você escrever um aplicativo que exibe uma interface do usuário (UI) e que também usa alguns objetos COM (Component Object Model) remoto, durante a quaisquer chamadas de método para os objetos COM remotos, a interface do usuário pode parar de responder. Esse comportamento ocorre porque o thread da interface do usuário que você inicializa como um MTA thread usando o método CoInitializeEx(..., COINIT_MULTITHREADED) torna bloquear chamadas de procedimento remoto (RPCs) para compartimento COM outro. Enquanto aguarda o segmento de interface do usuário para a mensagem de resposta RPC, as mensagens de janela que são lançadas a fila do thread da interface do usuário são acumuladas. Portanto, janelas que foram criadas pelo segmento de interface do usuário podem parar de responder. Este comportamento pode causar aos usuários finais prematuramente encerra o aplicativo.
Resolução
Para contornar este problema, execute o aplicativo MFC (interface do usuário thread) em um apartment STA (Single Threaded). Para fazer isso, inicialize o MFC aplicativo usando o método CoIntializeEx(..., COINIT_APARTMENTTHREADED) . Quando uma STA thread faz uma chamada RPC, o thread cai em um loop de mensagem COM gerenciados (para distribuir mensagens de janela) e COM cria outro segmento para receber o RPC mensagem de resposta. Como o loop de COM gerenciados mensagem oferece suporte a expedição das mensagens de janela, a interface do usuário pode manter em execução.
Situação
Esse comportamento é por design.
Mais Informações

Passos para reproduzir o problema

  1. Criar e, em seguida, criar um aplicativo MFC Single Document Interface (SDI) ou um aplicativo MFC Multiple Document Interface (MDI) usando AppWizard MFC. Para fazer isso, execute as seguintes etapas:
    1. Inicie o Microsoft Visual Studio .NET ou Microsoft Visual Studio 2005.
    2. No menu arquivo , aponte para novo e, em seguida, clique em Project .
    3. Clique em Projetos do Visual c++ em Tipos de projeto e, em seguida, clique em Aplicativo MFC em modelos .

      Observação No Visual Studio 2005, clique em Visual C++ em Tipos de projeto e clique em MFC Application em modelos .
    4. Na caixa de texto nome , digite teste e, em seguida, clique em OK .
    5. Na caixa de diálogo MFC Application Wizard , clique em Application Type no painel esquerdo.
    6. Em Tipo de aplicativo , clique em documento único ou vários documentos e em seguida, clique em Concluir .
  2. No método de arquivo Test.cpp CWinAppEx , localize o código a seguir:
    return TRUE;
  3. Adicione o seguinte código antes do código que você localizado na etapa anterior:
    HRESULT hr = CoInitializeEx( NULL, COINIT_MULTITHREADED );if ( FAILED( hr ) ){	AfxMessageBox("CoInitializeEx initialization failed");	return FALSE;}
    Observação Visual Studio 2005, use o seguinte código.
    HRESULT hr = CoInitializeEx( NULL, COINIT_MULTITHREADED );if ( FAILED( hr ) ){    AfxMessageBox(L"CoInitializeEx initialization failed"); return FALSE;}
  4. Crie o aplicativo.
  5. Pressione CTRL + F5 para executar o aplicativo. Você percebe o comportamento mencionado na seção "Sintomas" deste artigo.

Propriedades

ID do Artigo: 828643 - Última Revisão: 01/17/2006 00:51:14 - Revisão: 2.0

Microsoft Visual C++ 2005 Express Edition, Microsoft Visual C++ .NET 2003 Standard Edition, Microsoft Visual C++ .NET 2002 Standard Edition

  • kbmt kbthread kbbug KB828643 KbMtpt
Comentários