XPCOM component not being registered by regxpcom
Damien O'Brien
Mon, 04 Apr 2005 17:54:21 -0700
--
Hej,
zbudowałem komponent XPCOM, który używa interfejsu nsIContentPolicy. Funkcja z nsIContentPolicy, której używam to ShouldLoad (zostaje wywołana tuż przed tym, jak nowa strona kończy się ładować). Rejestruję mój komponent używając regxpcom wg. instrukcji z "Creating XPCOM Components", ale z jakiegoś powodu wydaje się to nie działać. Właściwie, mimo że regxpcom twierdzi, iż komponent się zarejestrował, nie jestem przekonany, że tak jest. Gdy używam przeglądarki komponentów (component viewer) w Mozilli, mój komponent się nie pojawia na liście tych zarejestrowanych. Czy ktoś ma jakiś pomysł, dlaczego jest on niewidoczny? Używam regxpcom w ten sposób:
regxpcom -x "C:\gecko-sdk\bin" "C:\Program Files\Common Files\mozilla.org\GRE\1.7.6_2005031907\components\TestPageLoad.dll"
Czy umieściłem swoją dllkę we właściwym miejscu?
Gdy zaglądam do compreg.dat są tam nowe informacje związane z komponentem i używanymi przez niego interfejsami. Xpti.dat zmieniła się data modyfikacji, ale z tego, co widzę, nie zmieniła się jego zawartość. Więc, jak już wspominałem, mój kod wydaje się nie być wywoływany, gdy startuje Mozilla i nie widzę mojego komponentu w przeglądarce komponentów.
Powinienem też dodać, że mój komponent jest rejestrowany jako obserwator zdarzenia xpcom-startup, by ładował się razem z XPCOM (użyłem do tego przykładowego kodu z "Creating XPCOM Components").
Wszelka pomoc mile widziana.
--
Gangadhar NPK
Tue, 05 Apr 2005 11:41:25 -0700
--
Damien,
ja też zmierzyłem się z tym problemem, ale po daremnych próbach jego rozwiązania zaniechałem dalszych prób.
Ale muszę dodać, że widziałem swój komponent w przeglądarce komponentów i poza tym się ładował (potwierdziłem to używając przeglądarki procesów). Możesz spróbować usuwając pliki compreg.dat i xpti.dat (nie zapomnij zrobić kopii zapasowej) i wtedy uruchomić Mozillę. Zobacz, czy komponent jest rejestrowany. O ile pamiętam, xpti.dat i compreg.dat są aktualizowane, jeśli komponent jest we właściwym miejscu (folder components). Podziel się proszę swoimi obserwacjami w tej kwestii, bo być może przyda się to jeszcze komuś,
dzięki,
Gangadhar
--
Damien O'Brien
Wed, 06 Apr 2005 09:48:28 -0700
--
Cześć Gangadhar,
dzięki za pomoc. Mogę potwierdzić, że wszystko, co trzeba zrobić, by komponent został zarejestrowany, to umieścić pliki .dll i .xpt w folderze components Mozilli (u mnie: "C:\Program
Files\mozilla.org\Mozilla\components"). Jeśli następnie uruchomisz ponownie Mozillę i zajrzysz do compreg.dat oraz xpti.dat, zobaczysz odwołania do twojego komponentu oraz kategorie, interfejsy itp., do których się zarejestrował.
Możesz wtedy użyć przeglądarki komponentów, by zobaczyć swój komponent na liście.
Jednakże, wydaje mi się, że mylisz się co do faktu ładowania twojego komponentu przez Mozillę. Po tym jak wykonałem wszystkie powyższe instrukcje, mój komponent nadal nie był ładowany. Przetestowałem to ustawiając breakpoint na początku DllMain w moim komponencie i podłączając się do wątku w debuggerze VS.Net. Mój breakpoint nie został osiągnięty, co wskazywałoby na to, że dllka nie została załadowana.
Następnie przyjrzałem się mozilli w przeglądarce procesów tak, jak ty. Okazało się, że mozilla dostaje się do dllki. Ale fakt, że DllMain nie została wywołana podczas debugowania, wskazuje na to, że dllka nie została załadowana. Wg. instrukcji do przeglądarki procesów, dllka pojawia się na liście, gdy jest ładowana LUB otwierana. Następnie użyłem FileMon (file monitor), by sprawdzić, co dzieje się z moją dllką, gdy startuje Mozilla. Widoczna była jedynie operacja otwarcia pliku.
Więc... w tej chwili wnioskuję, że moja dllka jest otwierana przez mozillę, ale nie ładowana. Być może ja (my ;-)) pominąłem coś w mojej dllce, co powoduje jej nieładowanie.
Jakieś pomysły?
> [...]
>the matter to rest.
Czy masz na myśli to, że również próbujesz użyć ShouldLoad w swoim komponencie, ale nie jest ona wywoływana?
Dzięki,
Damien
--
Jean-Marc Desperrier
Fri, 08 Apr 2005 02:04:33 -0700
--
Wygląda na to, że nie eksportujesz właściwych nazw funkcji. Sprawdź narzędziem Dependency Walker (przeglądanie zależności), co zostaje wyeksportowane.
--
Damien O'Brien
Fri, 08 Apr 2005 05:28:26 -0700
--
Cześć Jean-Marc,
Dzięki za odpowiedź :)
Zrobiłem, co zasugerowałeś i przyjrzałem się mojej dllce przy pomocy Dependency Walkera. Jedyną eksportowaną funkcją jest NSGetModule. Czy powinienem, eksportować coś jeszcze, czego szuka XPCOM zanim załaduje dllkę.
Dzięki,
Damo
Oops - jeszcze jedna sprawa...
Przyjrzałem się bliżej również compreg.dat i xpti.dat, myśląc że znajdę tam jakieś wskazówki co do przyczyny nieładowania komponentu. Poniżej znajdują się wpisy z tych plików dot. mojego komponentu.
Jedno, co zauważyłem w sekcji CLASSIDS, to że pozostałe wpisy, choć łudząco podobne, na końcu fragmentu contractID jest ;1 lub ;2, np. porównując z GoogleDesktop
[CLASSIDS]
{b23cb38b-b82e-4f6a-9769-d8b37a3c05f5},@google/googledesktopwebcapture;1,,GoogleDesktopWebCapture,rel:GoogleDesktopMozilla.dll
{82b9ab1d-7169-43b6-b6bb-9870ed36f7c7},@dobrien/testpageload,,TestPageLoad,rel:TestPageLoad.dll
Mój wpis nie ma tego ;1. Jakieś pomysły, co to znaczy? Czy brak tego elementu u mnie oznacza błąd? Czy może dlatego moja dllka nie jest ładowana?
Podobnie w sekcjach categories i contractids. Większość wpisów ma to ;1, ale mój nie, np.
[CONTRACTIDS]
@google/googledesktopmozilla;1,{b088432c-b090-4223-bbe5-90b040fb1fc8}
@dobrien/testpageload,{82b9ab1d-7169-43b6-b6bb-9870ed36f7c7}
[CATEGORIES]
xpcom-startup,GoogleDesktopMozilla,@google/googledesktopmozilla;1
xpcom-startup,TestPageLoad,@dobrien/testpageload
Dzięki,
Damo
wpisy compreg.dat dla mojego komponentu
------------------------------------
[COMPONENTS]
rel:TestPageLoad.dll,1112888214197
[CLASSIDS]
{82b9ab1d-7169-43b6-b6bb-9870ed36f7c7},@dobrien/testpageload,,TestPageLo
ad,rel:TestPageLoad.dll
[CONTRACTIDS]
@dobrien/testpageload,{82b9ab1d-7169-43b6-b6bb-9870ed36f7c7}
[CATEGORIES]
content-policy,TestPageLoad,@dobrien/testpageload
xpcom-startup,TestPageLoad,@dobrien/testpageload
wpisy xpti.dat dla mojego komponentu
----------------------------------
[Files,74]
2,TestPageLoad.xpt,0,122,1112893396439
[Interfaces,998]
667,iTestPageLoad,{82b9ab1d-7169-43b6-b6bb-9870ed36f7c7},2,-1,0
--
Jason DeArte
Tue, 19 Apr 2005 15:31:07 -0700
--
> [...] actually being loaded.
Nie wiem, jak tam VS.NET, ale w starszych wersjach DevStudio (6 na moim PC), jeśli podpinało się do debugowanego procesu, nie można ustawić breakpointa na module, który jeszcze nie został załadowany.
Teraz możesz WYMUSIĆ breakpoint gdziekolwiek w twoim kodzie dodając "_asm {int 3}". Jest to jednak coś, czego zdecydowanie nie chcesz zostawić w ostatecznej wersji kodu ;-)