Gesprekssynchronisatie
COM-toepassingen moeten correct kunnen omgaan met gebruikersinvoer tijdens het verwerken van een of meer aanroepen van COM of het besturingssysteem. COM biedt alleen gesprekssynchronisatie voor appartementen met één thread. Multithreaded appartementen (met gratis threads) ontvangen geen oproepen tijdens het plaatsen van oproepen (op dezelfde thread). Multithreaded appartementen kunnen geen gesynchroniseerde invoergesprekken voeren. Asynchrone oproepen worden geconverteerd naar synchrone oproepen in multithreaded appartementen. Het berichtfilter wordt niet aangeroepen voor een thread in een multithreaded appartement. Zie Processen, Threads en Appartementenvoor meer informatie over threadingproblemen.
COM-aanroepen tussen processen vallen als volgt in drie categorieën:
-
synchrone aanroepen
-
De meeste communicatie die binnen COM plaatsvindt, is synchroon. Bij het maken van synchrone oproepen wacht de beller op het antwoord voordat deze doorgaat en kan deze binnenkomende berichten ontvangen terwijl er wordt gewacht. COM voert een modale lus in om te wachten op het antwoord, het ontvangen en verzenden van andere berichten op een gecontroleerde manier.
-
Asynchrone meldingen
-
Bij het verzenden van asynchrone meldingen wacht de beller niet op het antwoord. COM gebruikt PostMessage of gebeurtenissen op hoog niveau om asynchrone meldingen te verzenden, afhankelijk van het platform. COM definieert vijf asynchrone methoden van IAdviseSink:
- OnDataChange-
- OnViewChange-
- OnRename-
- opslaan
- OnClose-
Notitie
Hoewel COM een asynchrone aanroep verwerkt, kunnen synchrone aanroepen niet worden uitgevoerd. De implementatie van een containertoepassing van OnDataChange- kan bijvoorbeeld geen aanroep naar IPersistStorage::Savebevatten. Deze aanroepen zijn de enige asynchrone aanroepen die door COM worden ondersteund. Er is op dit moment geen manier om een aangepaste interface te maken die asynchroon is.
-
met invoer gesynchroniseerde aanroepen
-
Wanneer invoersynchroneerde aanroepen worden gedaan, moet het aangeroepen object de aanroep voltooien voordat het besturingselement wordt opgehaald. Dit helpt ervoor te zorgen dat focusbeheer correct werkt en dat de gegevens die door de gebruiker zijn ingevoerd, correct worden verwerkt. Deze aanroepen worden gedaan door COM via de functie SendMessage, zonder een modale lus in te voeren. Tijdens het verwerken van een door invoer gesynchroniseerde aanroep mag het object dat wordt aangeroepen geen functie of methode aanroepen (inclusief synchrone methoden) die controle kunnen opleveren. De volgende methoden zijn gesynchroniseerd met invoer
- IOleWindow::GetWindow
- IOleInPlaceActiveObject::OnFrameWindowActivate
- IOleInPlaceActiveObject::OnDocWindowActivate
- IOleInPlaceActiveObject::ResizeBorder-
- IOleInPlaceUIWindow::GetBorder
- IOleInPlaceUIWindow::RequestBorderSpace
- IOleInPlaceUIWindow::SetBorderSpace
- IOleInPlaceFrame::SetMenu
- IOleInPlaceFrame::SetStatusText
- IOleInPlaceObject::SetObjectRects
Om problemen te minimaliseren die kunnen ontstaan door asynchrone berichtverwerking, zijn de meeste COM-methodeaanroepen synchroon. Met synchrone communicatie is er geen speciale code nodig om binnenkomende berichten te verzenden en te verwerken. Wanneer een toepassing een synchrone methodeaanroep doet, voert COM een modale wachtlus in waarmee de vereiste antwoorden worden verwerkt en binnenkomende berichten worden verzonden naar toepassingen die deze kunnen verwerken.
COM beheert methodeaanroepen door een id toe te wijzen die een logische thread-idwordt genoemd. Er wordt een nieuwe toegewezen wanneer een gebruiker een menuopdracht selecteert of wanneer de toepassing een nieuwe COM-bewerking start. Volgende aanroepen die betrekking hebben op de eerste COM-aanroep, krijgen dezelfde logische thread-id toegewezen als de eerste aanroep.