[gaim-migrate @ 10202]
Make the firefox browser option with with firefox 0.9 when an
instance of firefox is already running. Fixes bug 976056.
This is backward compatible (with 0.8, at least).
committer: Tailor Script <tailor@pidgin.im>
--------------------------------------------------------------------------- Protok鶻 G*du-G*du 4.x (C) Copyright 2001 by Wojtek Kaniewski <wojtekka@irc.pl>, Robert J. Wo�ny <speedy@atman.pl>, Tomasz Jarzynka <tomee@cpi.pl>, Adam Ludwikowski <adam.ludwikowski@wp.pl>, Marek Kozina <klith@hybrid.art.pl>, Rafa� Florek <raf@regionet.regionet.pl>, Igor Popik <igipop@wsfiz.edu.pl>--- 0) disclaimer ---------------------------------------------------------opis protoko�u bazuj� na do�wiadczeniach przeprowadzonych na moimdomowym komputerze oraz informacjach przys�anych do mnie przez r鷽nychludzi. �aden klient g*du-g*du nie zosta� skrzywdzony podczasprzeprowadzania bada�, blabla.--- 1) transmisja, format wszystkich pakiet�w -----------------------------w przeciwie�stwie do zabawek typu icq, g*du-g*du korzysta z protoko�u tcp.ka�dy pakiet zawiera dwa sta�e pola: struct gg_header { int type; /* typ pakietu */ int length; /* d�ugo倶 reszty pakietu */ };dla u�atwienia przyjmuj� nast�puj�ce d�ugo�ci zmiennych: sizeof(char) = 1,sizeof(short) = 2, sizeof(int) = 4. oczywi�cie wszystkie liczby s� zgodniez intelowym endianem. zak�adam te�, �e wszystkie zmienne s� bez znaku. niechce mi si� wsz�dzie pisa� `unsigned'.pola, co do kt�rych znaczenia nie mam pewno�ci, lub w og�le nie mam poj�cia,sk�d si� tam wzi螻y, oznaczam `dunno'.--- 2) zanim si� po咳czymy -------------------------------------------------�eby wiedzie�, z jakim serwerem mamy si� po咳czy�, nale�y poudawa� przezchwil� Internet Explorera, po咳czy� si� z hostem `appmsg.gadu-gadu.pl'. GET /appsvc/appmsg.asp?fmnumber=<tutaj_numerek_gg> HTTP/1.0 Host: appmsg.gadu-gadu.pl User-Agent: Mozilla/4.7 [en] (Win98; I) Pragma: no-cacheoryginalny klient mo�e wys�a� jeden z podanych identyfikator�w przegl�darki: Mozilla/4.04 [en] (Win95; I ;Nav) Mozilla/4.7 [en] (Win98; I) Mozilla/4.0 (compatible; MSIE 5.0; Windows NT; DigExt) Mozilla/4.0 (compatible; MSIE 5.0; Windows NT) Mozilla/4.0 (compatible; MSIE 5.0; Windows 98; DigExt) Mozilla/4.0 (compatible; MSIE 5.0; Windows 98)nowsze wersje klienta do zapytania dodaj� r�wnie� `version=...' opisuj�ce,z jakim klientem serwer ma do czynienia. jednak ze wzgl�du na mo�liwer鷽nice w protokole, lepiej pomija� ten parametr i uwaga� GG 4.0. w ka�dymrazie na to zapytanie serwer powinien odpowiedzie�: HTTP/1.0 200 OK 0 1 0 217.17.33.21:8074 217.17.33.21 217.17.33.21co to oznacza? nie mam poj�cia ;) wygl�da na to, �e ca�y g*du-g*du jestprzemy�lany i w przysz�o�ci b�dzie mo�na u�ywa� r鷽nych serwer�w do r鷽nychrzeczy, typu szukanie, obs�uga klient�w itd. p�ki co, 咳czy� si� trzeba napierwszy adres (tak, ten z portem).Je�eli po咳czenie z portem 8074 nie wyjdzie z jaki� specyficznych powod�w -mo�na si� 咳czy� na port 443. --- 3) logowanie si� -------------------------------------------------------po po咳czeniu si� portem serwera g*du-g*du, dostajemy pakiet typu 0x0001,kt�ry na potrzeby tego dokumentu nazwiemy: #define GG_WELCOME 0x0001reszta pakietu zawiera liczb�, na podstawie kt�rej liczony jest hash z has�aklienta: struct gg_welcome { int key; /* klucz szyfrowania has�a */ };kiedy mamy ju� t� warto倶 mo�emy odes�a� pakiet logowania #define GG_LOGIN 0x000cmusimy poda� kilka informacji: struct gg_login { int uin; /* tw�j numerek */ int hash; /* hash has�a */ int status; /* status na dzie� dobry */ int version; /* wersja klienta */ int local_ip; /* m�j adres ip */ short local_port; /* port, na kt�rym s�ucham */ };jak obliczy� hash has�a? hmm... nic prostszego. do ka�dej literki has�adodaje si� jedynk�, mno�y wszystko razem, a potem przez liczb� podan� przezserwer. for (hash = 1; *passwd; passwd++) hash *= (*passwd) + 1;zrozumia�e, racja? liczba oznaczaj�ca wersj� mo�e by� jedn� z poni�szych: 0x11 - 4.6.1 0x10 - 4.5.22, 4.5.21, 4.5.19, 4.5.17, 4.5.15 0x0f - 4.5.12 0x0b - 4.0.30, 4.0.29, 4.0.28, 4.0.25oczywi�cie nie s� to wszystkie mo�liwe wersje klient�w, lecz te, kt�reuda�o si� sprawdzi�. najbezpieczniej b�dzie przedstawia� si� jako tawersja, kt�rej ficzer�w u�ywamy. wiadomo, �e 4.0.x nie obs�ugiwa�y trybuukrytego, ani tylko dla znajomych itd.je�li wszystko si� powiedzie, dostaniemy w odpowiedzi pakiet typu #define GG_LOGIN_OK 0x0003z polem header->length = 0, lub pakiet #define GG_LOGIN_FAILED 0x0009--- 4) zmiana statusu -----------------------------------------------------g*du-g*du przewiduje trzy stany klienta, kt�re zmieniamy pakietem #define GG_NEW_STATUS 0x0002 #define GG_STATUS_NOT_AVAIL 0x0001 /* roz咳czony */ #define GG_STATUS_AVAIL 0x0002 /* dost�pny */ #define GG_STATUS_BUSY 0x0003 /* zaj�ty */ #define GG_STATUS_INVISIBLE 0x0014 /* niewidoczny */ #define GG_STATUS_FRIENDS_MASK 0x8000 /* tylko dla przyjaci鶻 */ struct gg_new_status { int status; /* na jaki zmieni�? */ }nale�y pami�ta�, �eby przed roz咳czeniem si� z serwerem nale�y zmieni�stan na GG_STATUS_NOT_AVAIL. je�li ma by� widoczny tylko dla przyjaci鶻,nale�y doda� GG_STATUS_FRIENDS do normalnej warto�ci stanu.--- 5) ludzie przychodz�, ludzie odchodz� ---------------------------------zaraz po zalogowaniu mo�emy wys�a� serwerowi list� ludzik�w w naszej li�ciekontakt�w, �eby dowiedzie� si�, czy s� w tej chwili dost�pni. pakiet zawieradowoln� ilo倶 struktur gg_notify: #define GG_NOTIFY 0x0010 struct gg_notify { int uin; /* numerek danej osoby */ char dunno1; /* == 3 */ };je�li kto� jest, serwer odpowie pakietem zawieraj�cym jedn� lub wi�cejstruktur gg_notify_reply: #define GG_NOTIFY_REPLY 0x000c /* tak, to samo co GG_LOGIN */ struct gg_notify_reply { int uin; /* numerek */ int status; /* status danej osoby */ int remote_ip; /* adres ip delikwenta */ short remote_port; /* port, na kt�rym s�ucha klient */ int version; /* wersja klienta */ short dunno1; /* znowu port? */ };je�li klient nie obs�uguje po咳cze� mi�dzy klientami (np. g*du-g*du 3.x)zamiast adresu ip jest 0, zamiast portu mo�e by� 0, 1, 2... niewa�ne ;)port mo�e przyjmowa� warto倶 1, je�li klient znajduje si� za jakim�firewallem lub innym urz�dzeniem robi�cym NAT. w ka�dym razie, je�li kto�si� pojawi w trakcie pracy, r�wnie� zostanie przys�any ten pakiet.proste? proste :)�eby doda� kogo� do listy w trakcie pracy, trzeba wys�a� ni�ej opisanypakiet. jego format jest identyczny jak przy GG_NOTIFY. #define GG_ADD 0x000d struct gg_add { int uin; /* numerek */ char dunno1; /* == 3 */ };je�li kto� opu�ci g*du-g*du lub zmieni stan, otrzymamy pakiet #define GG_STATUS 0x0002 struct gg_status { int uin; /* numerek */ int status; /* nowy stan */ };--- 6) wysy�anie wiadomo�ci ------------------------------------------------przejd�my do sedna sprawy ;) #define GG_SEND_MSG 0x000b #define GG_CLASS_QUEUED 0x0001 /* tylko przy odbieraniu */ #define GG_CLASS_MSG 0x0004 #define GG_CLASS_CHAT 0x0008 #define GG_CLASS_UNKNOWN_1 0x0020 struct gg_send_msg { int recipient; int seq; int class; char message[]; };wiadomo, odbiorca. numer sekwencyjny, kt�ry wykorzystujemy potem dopotwierdzenia. nie wykluczone, �e w jakis spos�b odr鷽nia si� r鷽nerozmowy za pomoc� cz蟠ci bajt�w, ale raczej nie ma znaczenia. klasawiadomo�ci pozwala odr鷽ni�, czy wiadomo倶 ma si� pokaza� w osobymokienku czy jako kolejna linijka w okienku rozmowy. wygl�da na to,�e to jaka� bitmapa, wi�c najlepiej ola� inne bity ni� 0x0e. (czasemklienty wysy�aj� 0x04, czasem 0x24 -- widocznie 0x20 to te� jaka�flaga). je�li odbiorca by� niedost�pny podczas wysy�ania wiadomo�ci,zostanie zaznaczony bit 0x01.oryginalny klient wysy�aj�c wiadomo倶 do kilku u�ytkownik�w, wysy�a poprostu kilka takich samych pakiet�w z r鷽nymi numerkami odbiorc�w. niema osobnego pakietu do tego. natomiast je�li chodzi o ,,konferencyjn�''do pakietu doklejana jest za ,,char message[];'' nast�puj�ca struktura: struct gg_send_recipients { char flag; /* == 1 */ int count; /* ilo倶 odbiorc�w */ int recipients[]; /* tablica odbiorc�w */ };na przyk�ad, by wys�a� do trzech ludzi, nale�y wys�a� pakiet: - -- --- --+--+--+--+--+--+--+-----------+-----------+ tre倶 |\0|\1| 0x02 | uin1 | uin2 | - -- -- ---+--+--+--+--+--+--+--+--+--+--+--+--+--+--+serwer po otrzymaniu wiadomo�ci odsy�a informacj� o tym. przy okazjim�wi, czy wiadomo倶 dotar�a do odbiorcy (status == GG_ACK_DELIVERED),czy mo�e jest offline i zosta�a zakolejkowana (GG_ACK_QUEUED): #define GG_SEND_MSG_ACK 0x0005 #define GG_ACK_DELIVERED 0x0002 #define GG_ACK_QUEUED 0x0003 struct gg_send_msg_ack { int status; int recipient; int seq; };numer sekwencyjny i adresat ten sam, co przy wysy�aniu.--- 7) otrzymywanie wiadomo�ci ---------------------------------------------zbyt wiele wyja�nie� chyba nie trzeba. wiadomo od kogo. drugie pole tonajprawdopodobniej jaki� numerek sekwencyjny. trzecie oznacza czas nadaniawiadomo�ci. klasa wiadomo�ci taka sama jak przy wysy�aniu: #define GG_RECV_MSG 0x000a struct gg_recv_msg { int sender; int seq; int time; int class; char message[]; };w przypadku pakiet�w ,,konferencyjnych'' na koncu pakietu doklejona jeststruktura identyczna ze struct gg_send_recipients zawieraj�ca pozosta�ychrozm�wc�w.--- 8) ping/pong -----------------------------------------------------------od czasu do czasu klient wysy�a pakiet a'la ping do serwera i dostaje pust�odpowied�. o ile dobrze pami�tam, serwer roz咳cza si� po up�ywie 5 minut odotrzymania ostatniej informacji. #define GG_PING 0x0008 /* nie ma niczego */ #define GG_PONG 0x0007 /* nie ma niczego */--- 9) podzi�kowania -------------------------------------------------------sw�j wk�ad w poznanie protoko�u mieli: - Robert J. Wo�ny <speedy@atman.pl>: opis nowo�ci w protokole GG 4.6, - Tomasz Jarzynka <tomee@cpi.pl>: badanie timeout�w, - Adam Ludwikowski <adam.ludwikowski@wp.pl>: wiele r鷽nych poprawek do tekstu, badanie wersji, - Marek Kozina <klith@hybrid.art.pl>: czas otrzymania wiadomo�ci, - Rafa� Florek <raf@regionet.regionet.pl>: konferencje, - Igor Popik <igipop@wsfiz.edu.pl>: klasy wiadomo�ci przy odbieraniu zakolejkowanej.----------------------------------------------------------------------------$Id: protocol.txt 2819 2001-11-27 22:54:32Z warmenhoven $