Synchronisation des appels
Les applications COM doivent être en mesure de traiter correctement les entrées utilisateur lors du traitement d’un ou plusieurs appels à partir de COM ou du système d’exploitation. COM fournit la synchronisation des appels pour les appartements à thread unique uniquement. Les appartements multithreads (contenant des threads à threads libres) ne reçoivent pas d’appels lors de l’exécution d’appels (sur le même thread). Les appartements multithreads ne peuvent pas effectuer d’appels synchronisés d’entrée. Les appels asynchrones sont convertis en appels synchrones dans des appartements multithreads. Le filtre de messages n’est appelé pour aucun thread dans un appartement multithread. Pour plus d’informations sur les problèmes de threading, consultez Processus, threads et appartements.
Les appels COM entre les processus se répartissent en trois catégories , comme suit :
-
Appels synchrones
-
La plupart des communications qui ont lieu dans COM sont synchrones. Lors d’appels synchrones, l’appelant attend la réponse avant de continuer et peut recevoir des messages entrants pendant l’attente. COM entre dans une boucle modale pour attendre la réponse, en recevant et en dispatchant d’autres messages de manière contrôlée.
-
Notifications asynchrones
-
Lors de l’envoi de notifications asynchrones, l’appelant n’attend pas la réponse. COM utilise PostMessage ou des événements de haut niveau pour envoyer des notifications asynchrones, selon la plateforme. COM définit cinq méthodes asynchrones de IAdviseSink :
Notes
Pendant que COM traite un appel asynchrone, les appels synchrones ne peuvent pas être effectués. Par exemple, l’implémentation d’OnDataChange par une application conteneur ne peut pas contenir d’appel à IPersistStorage::Save. Ces appels sont les seuls appels asynchrones pris en charge par COM. Il n’existe aucun moyen de créer une interface personnalisée asynchrone pour l’instant.
-
Appels synchronisés en entrée
-
Lorsque vous effectuez des appels synchronisés en entrée, l’objet appelé doit terminer l’appel avant de générer le contrôle. Cela permet de garantir que la gestion des focus fonctionne correctement et que les données entrées par l’utilisateur sont traitées de manière appropriée. Ces appels sont effectués par COM via la fonction SendMessage , sans entrer de boucle modale. Lors du traitement d’un appel synchronisé en entrée, l’objet appelé ne doit appeler aucune fonction ou méthode (y compris les méthodes synchrones) susceptible de produire un contrôle. Les méthodes suivantes sont synchronisées en entrée
- IOleWindow::GetWindow
- IOleInPlaceActiveObject::OnFrameWindowActivate
- IOleInPlaceActiveObject::OnDocWindowActivate
- IOleInPlaceActiveObject::ResizeBorder
- IOleInPlaceUIWindow::GetBorder
- IOleInPlaceUIWindow::RequestBorderSpace
- IOleInPlaceUIWindow::SetBorderSpace
- IOleInPlaceFrame::SetMenu
- IOleInPlaceFrame::SetStatusText
- IOleInPlaceObject::SetObjectRects
Pour réduire les problèmes qui peuvent survenir du traitement asynchrone des messages, la majorité des appels de méthode COM sont synchrones. Avec la communication synchrone, il n’est pas nécessaire de disposer d’un code spécial pour distribuer et gérer les messages entrants. Lorsqu’une application effectue un appel de méthode synchrone, COM entre dans une boucle d’attente modale qui gère les réponses requises et distribue les messages entrants aux applications capables de les traiter.
COM gère les appels de méthode en affectant un identificateur appelé ID de thread logique. Un nouveau est attribué lorsqu’un utilisateur sélectionne une commande de menu ou lorsque l’application lance une nouvelle opération COM. Les appels suivants qui se rapportent à l’appel COM initial se voient attribuer le même ID de thread logique que l’appel initial.