Udostępnij przez


IDirectWriterLock — implementacja pliku złożonego

Implementacja pliku złożonego IDirectWriterLock umożliwia otwarcie pliku złożonego w trybie bezpośrednim z jednym zapisem i wieloma czytnikami.

Pliki złożone można otwierać w trybie bezpośrednim przy użyciu flagi STGM_DIRECT. InterfejsIDirectWriterLockustawia STGM_READWRITE|STGM_SHARE_DENY_WRITE flaga jako prawidłowa w trybie bezpośrednim bez konieczności narzutowania kopii migawki.

Po otwarciu pliku złożonego w trybie transakcyjnym przy użyciu flagi STGM_TRANSACTED można również mieć wielu czytników i pojedynczy moduł zapisywania przy użyciu STGM_READWRITE|STGM_SHARE_DENY_WRITE flaga. Jednak w tym przypadku kopia migawki pliku jest wykonana dla czytelników. Często wiąże się to z obciążeniem kopii tymczasowej.

Kiedy należy używać

Użyj dostarczonej przez system implementacji IDirectWriterLock podczas otwierania magazynu w trybie bezpośrednim (STGM_DIRECT) przy użyciu STGM_READWRITE|STGM_SHARE_DENY_WRITE flagi.

Aby uzyskać wskaźnik IDirectWriterLock, wywołaj QueryInterface w IStorage, aby uzyskać główny obiekt magazynu dla pliku złożonego.

Wywołaj IDirectWriterLock::WaitForWriteAccess, aby uzyskać wyłączny dostęp do zapisu w pliku złożonym. Wywołaj IDirectWriterLock::ReleaseWriteAccess, aby zwolnić wyłączny dostęp do zapisu.

IDirectWriterLock::HaveWriteAccess wskazuje, czy plik jest obecnie zablokowany.

Uwagi

Implementacja pliku złożonego funkcji pojedynczego modułu zapisywania z wieloma czytnikami jest oparta na blokadzie zakresu. Składnik zapisywania uzyskuje wyłączny dostęp do magazynu do zapisu po zamknięciu magazynu przez wszystkich bieżących czytelników. Mimo że składnik zapisywania jest aktywny, kolejni czytelnicy nie mogą otworzyć magazynu. Składnik zapisywania wywołuje IDirectWriterLock::WaitForWriteAccess w celu uzyskania wyłącznego dostępu do zapisu. Składnik zapisywania musi następnie wywołać IDirectWriterLock::ReleaseWriteAccess, aby zwolnić magazyn.

Wywołanie IDirectWriterLock::WaitForWriteAccess jest wymagane przed zapisaniem w tym trybie wielokrotnego zapisywania pojedynczego czytnika. Próbuje zapisać w pliku bez wywoływania IDirectWriterLock::WaitForWriteAccess pierwszego wyniku w STG_E_ACCESSDENIED. Ten błąd jest zwracany nawet wtedy, gdy składnik zapisywania początkowo otworzył plik, a żaden czytelnik nie ma obecnie otwartego pliku.

Zagadnienia dotyczące marshalingu

Przeprowadzanie marshalingu niestandardowego jest zwykle używane, gdy plik złożony jest marshaling do innego procesu na tym samym komputerze. Podczas marshalingu magazynów prawa dostępu nie są brane pod uwagę, a wskaźnik IStorage jest przekazywany do nowego procesu z tymi samymi trybami dostępu i prawami co oryginalny proces marshalingu. Aby uzyskać więcej informacji na temat trybów dostępu, zobacz stałe STGM. Podczas marshalingu żadne blokady nie są pobierane ani weryfikowane w celu zapewnienia wyłącznego dostępu do zapisu. W tym przypadku nie ma wymuszania zasad pojedynczego zapisywania dla plików złożonych otwartych w trybie pojedynczego zapisywania wielokrotnego. Zamiast tego wymuszanie jest obsługiwane wewnętrznie przez implementację pliku złożonego.

Ponieważ wskaźnik IStorage jest przekazywany do innego procesu podczas marshalingu, możliwe jest, że dwa procesy mają równoczesny dostęp do tego samego pliku złożonego. Mimo że obiekt wywołujący mógł uzyskać wyłączny dostęp do zapisu do magazynu przez wywołanie IDirectWriterLock::WaitForWriteAccess, wersja marshaled może również mieć dostęp jednocześnie. Wersje marshaled nie są wymuszane do zamknięcia, gdy pojedynczy składnik zapisywania uzyskuje dostęp do pliku. W takim przypadku implementacja pliku złożonego synchronizuje operacje zapisu wewnętrznie.

Jeśli pojedynczy składnik zapisywania uzyskuje wyłączny dostęp przez wywołanie metody , IDirectWriterLock::WaitForWriteAccess, magazyn marshalowany ma również dostęp do zapisu i nie musi wywoływać IDirectWriterLock::WaitForWriteAccess. Oba procesy mają dostęp do zapisu, a synchronizacja jest kontrolowana przez wewnętrzną implementację pliku złożonego.

IDirectWriterLock