Kiedy używać tabeli interfejsu globalnego
Jeśli odpakowujesz wskaźnik interfejsu wielokrotnie między apartamentami w procesie, możesz użyć interfejsu IGlobalInterfaceTable. W przypadku innych technik należy za każdym razem ponownie marshalować.
Notatka
Jeśli wskaźnik interfejsu jest unmarshaled tylko raz, możesz użyć funkcji CoMarshalInterThreadInterfaceInStream. Może również służyć do przekazywania wskaźnika interfejsu z jednego wątku do innego wątku w tym samym procesie.
Interfejs IGlobalInterfaceTable sprawia również, że inny wcześniej trudny problem jest prostszy dla programisty. Ten problem występuje, gdy obowiązują następujące warunki:
- W procesie obiekt agile agreguje swobodnowątkowy marshaler.
- Ten sam obiekt agile przechowuje również (jako zmienne składowe) wskaźniki interfejsu do innych obiektów, które nie są zwinne i nie agregują marshalera bez wątkowego.
W takiej sytuacji, jeśli obiekt zewnętrzny jest przesyłany do innego mieszkania i aplikacja go wywołuje, a obiekt próbuje użyć wskaźników interfejsu swoich zmiennych składowych, które nie są bezpieczne dla wielowątkowości lub są serwerami proxy dla obiektów w innych mieszkaniach, może to prowadzić do nieprawidłowych wyników lub błędu RPC_E_WRONG_THREAD. Ten błąd występuje, ponieważ interfejs wewnętrzny jest przeznaczony do wywoływania tylko z mieszkania, w którym był najpierw przechowywany w zmiennej składowej.
Aby rozwiązać ten problem, obiekt zewnętrzny agregujący bezwątkowy marshaler powinien wywołać IGlobalInterfaceTable::RegisterInterfaceInGlobal w interfejsie wewnętrznym i zapisać wynikowy plik cookie w zmiennej składowej, zamiast przechowywać rzeczywisty wskaźnik interfejsu. Gdy obiekt zewnętrzny chce wywołać wskaźnik interfejsu obiektu wewnętrznego, powinien wywołać IGlobalInterfaceTable::GetInterfaceFromGlobal, użyj zwróconego wskaźnika interfejsu, a następnie zwolnij go. Gdy obiekt zewnętrzny zniknie, powinien wywołać metodę IGlobalInterfaceTable::RevokeInterfaceFromGlobal, aby usunąć interfejs z tabeli interfejsu globalnego.
Tematy pokrewne