libgadu  1.12.2
Struktury danych | Funkcje
Połączenia bezpośrednie do wersji Gadu-Gadu 6.x
Diagram współpracy dla Połączenia bezpośrednie do wersji Gadu-Gadu 6.x:

Struktury danych

struct  gg_dcc
 Połączenie bezpośrednie do wersji Gadu-Gadu 6.x. Więcej...
 

Funkcje

int gg_dcc_request (struct gg_session *sess, uin_t uin)
 Wysyła żądanie zwrotnego połączenia bezpośredniego. Więcej...
 
int gg_dcc_fill_file_info (struct gg_dcc *d, const char *filename)
 Wypełnia pola struktury gg_dcc niezbędne do wysłania pliku. Więcej...
 
int gg_dcc_fill_file_info2 (struct gg_dcc *d, const char *filename, const char *local_filename)
 Wypełnia pola struktury gg_dcc niezbędne do wysłania pliku. Więcej...
 
struct gg_dccgg_dcc_get_file (uint32_t ip, uint16_t port, uin_t my_uin, uin_t peer_uin)
 Rozpoczyna odbieranie pliku przez zwrotne połączenie bezpośrednie. Więcej...
 
struct gg_dccgg_dcc_send_file (uint32_t ip, uint16_t port, uin_t my_uin, uin_t peer_uin)
 Rozpoczyna wysyłanie pliku. Więcej...
 
struct gg_dccgg_dcc_voice_chat (uint32_t ip, uint16_t port, uin_t my_uin, uin_t peer_uin)
 Rozpoczyna połączenie głosowe. Więcej...
 
void gg_dcc_set_type (struct gg_dcc *d, int type)
 Ustawia typ przychodzącego połączenia bezpośredniego. Więcej...
 
struct gg_dccgg_dcc_socket_create (uin_t uin, uint16_t port)
 Tworzy gniazdo nasłuchujące dla połączeń bezpośrednich. Więcej...
 
int gg_dcc_voice_send (struct gg_dcc *d, char *buf, int length)
 Wysyła ramkę danych połączenia głosowego. Więcej...
 
struct gg_eventgg_dcc_watch_fd (struct gg_dcc *h)
 Funkcja wywoływana po zaobserwowaniu zmian na deskryptorze połączenia. Więcej...
 
void gg_dcc_free (struct gg_dcc *d)
 Zwalnia zasoby używane przez połączenie bezpośrednie. Więcej...
 

Opis szczegółowy

Nota
Funkcje opisane poniżej są zgodne ze starą wersją Gadu-Gadu. Nowy sposób przesyłania plików i przeprowadzania rozmów głosowych, wprowadzony w Gadu-Gadu 7.x, obsługiwany jest innymi funkcjami.

Gadu-Gadu, w przeciwieństwie do protokołów takich jak IRC, umożliwia połączenia w obie strony, bez względu na to, który klient nadaje, a który odbiera. Do tego, jeśli obie strony łączą się do serwera z tego samego publicznego adresu IP, serwer przesyła im ich adresy lokalne.

Ze względu na kierunek i sposób połączenia, wyróżniamy kilka sytuacji:

To, czy możemy się z kimś połączyć widać po porcie połączeń bezpośrednich drugiej strony, jaki dostajemy w zdarzeniach o zmianie statusu. Jeśli port jest niższy od 10, połączenie nie jest możliwe i należy wysłać specjalną wiadomość za pomocą funkcji gg_dcc_request().

Każde połączenie bezpośrednie i gniazdo nasłuchujące opisywane jest przez strukturę gg_dcc. To ostatnie możemy stworzyć za pomocą:

struct gg_dcc *gniazdo;
gniazdo = gg_dcc_socket_create(numer_gg, port_nasłuchujący);
if (!gniazdo)
błąd("Nie można utworzyć gniazda");
dodaj_do_obserwowanych(gniazdo);
struct gg_dcc * gg_dcc_socket_create(uin_t uin, uint16_t port)
Tworzy gniazdo nasłuchujące dla połączeń bezpośrednich.
Definition: dcc.c:387
Połączenie bezpośrednie do wersji Gadu-Gadu 6.x.
Definition: libgadu.h:438

Jeśli podamy port 0, libgadu spróbuje znaleźć pierwszy wolny port w okolicy domyślnego portu połączeń bezpośrednich. W przypadku powodzenia zwraca zaalokowaną strukturę gg_dcc, której najbardziej interesującym polem port zawierające numer przyznanego portu. Jeśli zwróci NULL, w zmiennej systemowej errno znajdzie się powód błędu: EINVAL to niewłaściwie parametry, ENOMEM to brak pamięci, a reszta możliwych błędów to błędy związane z gniazdami, np. EADDRINUSE gdy nie można znaleźć wolnego portu.

Następnie należy w zmiennej globalnej gg_dcc_port ustawić zaalokowany port, do zmiennej gg_dcc_ip wpisać publiczny adres IP i połączyć się z serwerem, żeby poinformować świat o swoich namiarach. Jeśli publiczny adres IP to 255.255.255.255, automatycznie jest przypisywany adres IP, z którego wychodzi połączenie do serwera. Należy pamiętać, że wartości tych zmiennych są używane przez gg_login(), więc ich wartości trzeba ustawić przez połączeniem.

Po połączeniu obserwujemy deskryptor gniazda nasłuchującego i gdy coś się pojawi, wywołujemy:

struct gg_event *zdarzenie;
zdarzenie = gg_dcc_watch_fd(gniazdo);
if (!zdarzenie) {
usuń_z_obserwowanych(gniazdo);
gg_dcc_free(gniazdo);
błąd("Poważny błąd!");
}
void gg_dcc_free(struct gg_dcc *d)
Zwalnia zasoby używane przez połączenie bezpośrednie.
Definition: dcc.c:1386
struct gg_event * gg_dcc_watch_fd(struct gg_dcc *h)
Funkcja wywoływana po zaobserwowaniu zmian na deskryptorze połączenia.
Definition: dcc.c:573
Opis zdarzenia.
Definition: libgadu.h:1369

Błąd jest zwracany tylko w naprawdę krytycznych sytuacjach, gdy brakuje pamięci, lub nie powiodła się operacja na gniazdach, która nie miała się nie powieść (i przy okazji dalsza praca jest kompletnie bezcelowa).

Jeśli błędu nie będzie, dostaniemy informacje o zdarzeniu. W przypadku GG_SESSION_DCC_SOCKET mogą to być:

W każdym z tych wypadków należy po sprawdzeniu zdarzenia wywołać funkcję...

gg_event_free(zdarzenie);
void gg_event_free(struct gg_event *e)
Zwalnia pamięć zajmowaną przez informację o zdarzeniu.
Definition: events.c:66

...by zwolnić pamięć po zdarzeniu.

Gdy nadejdzie połączenie i dopiszemy je do listy obserwowanych, należy zwracać uwagę na następujące zdarzenia:

Tutaj również należy pamiętać o wywoływaniu gg_event_free().

Jeśli chcemy sami wysłać plik, sprawdzamy najpierw, czy druga strona może przyjąć połączenie, patrząc na jej port. Jeśli jest wyższy niż 10, możemy śmiało wywołać funkcję:

struct gg_dcc *dcc;
dcc = gg_dcc_send_file(adres_odbiorcy, port_odbiorcy, numer_wlasny, numer_odbiorcy);
if (!dcc)
błąd("Nie można ustanowić połączenia");
struct gg_dcc * gg_dcc_send_file(uint32_t ip, uint16_t port, uin_t my_uin, uin_t peer_uin)
Rozpoczyna wysyłanie pliku.
Definition: dcc.c:308

Zaraz potem możemy wywołać funkcję gg_dcc_fill_file_info(), by uzupełnić informację o pliku...

gg_dcc_fill_file_info(conn, filename);

...ale jeśli tego nie zrobimy teraz, biblioteka poprosi nas o to w odpowiedniej za pomocą zdarzenia GG_EVENT_DCC_NEED_FILE_INFO.

Jeśli port jest podejrzanie niski, znaczy że połączenie jest niemożliwe i wtedy wywołujemy funkcję:

gg_dcc_request(sesja, numer_odbiorcy);
int gg_dcc_request(struct gg_session *sess, uin_t uin)
Wysyła żądanie zwrotnego połączenia bezpośredniego.
Definition: dcc.c:69

gdzie session to nasza sesja Gadu-Gadu (musi być połączona), a peer_uin to numer drugiej strony. Wiadomość spowoduje, że druga strona spróbuje się z nami połączyć, jeśli ma taką możliwość.

Gdy otrzymamy wiadomość klasy GG_CLASS_CTCP o treści składającej się z bajtu 0x02 znaczy, że ktoś chce nam coś przesłać i mamy się z nim połączyć. Wywołujemy wtedy:

struct gg_dcc *dcc;
dcc = gg_dcc_get_file(adres_nadawcy, port_nadawcy, numer_wlasny, numer_nadawcy);
if (!dcc)
błąd("Nie można ustanowić połączenia");
struct gg_dcc * gg_dcc_get_file(uint32_t ip, uint16_t port, uin_t my_uin, uin_t peer_uin)
Rozpoczyna odbieranie pliku przez zwrotne połączenie bezpośrednie.
Definition: dcc.c:289

Dalej tak samo, jak przy zwykłym odbieraniu pliku.

Dokumentacja funkcji

◆ gg_dcc_request()

int gg_dcc_request ( struct gg_session sess,
uin_t  uin 
)

Wysyła żądanie zwrotnego połączenia bezpośredniego.

Funkcję wykorzystuje się, jeśli nie ma możliwości połączenia się z odbiorcą pliku lub rozmowy głosowej. Po otrzymaniu żądania druga strona spróbuje nawiązać zwrotne połączenie bezpośrednie z nadawcą. gg_dcc_request()

Parametry
sessStruktura sesji
uinNumer odbiorcy
Zwraca
Patrz gg_send_message_ctcp()

◆ gg_dcc_fill_file_info()

int gg_dcc_fill_file_info ( struct gg_dcc d,
const char *  filename 
)

Wypełnia pola struktury gg_dcc niezbędne do wysłania pliku.

Nota
Większą funkcjonalność zapewnia funkcja gg_dcc_fill_file_info2().
Parametry
dStruktura połączenia
filenameNazwa pliku
Zwraca
0 jeśli się powiodło, -1 w przypadku błędu

◆ gg_dcc_fill_file_info2()

int gg_dcc_fill_file_info2 ( struct gg_dcc d,
const char *  filename,
const char *  local_filename 
)

Wypełnia pola struktury gg_dcc niezbędne do wysłania pliku.

Parametry
dStruktura połączenia
filenameNazwa pliku zapisywana w strukturze
local_filenameNazwa pliku w lokalnym systemie plików
Zwraca
0 jeśli się powiodło, -1 w przypadku błędu

◆ gg_dcc_get_file()

struct gg_dcc* gg_dcc_get_file ( uint32_t  ip,
uint16_t  port,
uin_t  my_uin,
uin_t  peer_uin 
)

Rozpoczyna odbieranie pliku przez zwrotne połączenie bezpośrednie.

Parametry
ipAdres IP nadawcy
portPort nadawcy
my_uinWłasny numer
peer_uinNumer nadawcy
Zwraca
Struktura gg_dcc lub NULL w przypadku błędu

◆ gg_dcc_send_file()

struct gg_dcc* gg_dcc_send_file ( uint32_t  ip,
uint16_t  port,
uin_t  my_uin,
uin_t  peer_uin 
)

Rozpoczyna wysyłanie pliku.

Parametry
ipAdres IP odbiorcy
portPort odbiorcy
my_uinWłasny numer
peer_uinNumer odbiorcy
Zwraca
Struktura gg_dcc lub NULL w przypadku błędu

◆ gg_dcc_voice_chat()

struct gg_dcc* gg_dcc_voice_chat ( uint32_t  ip,
uint16_t  port,
uin_t  my_uin,
uin_t  peer_uin 
)

Rozpoczyna połączenie głosowe.

Parametry
ipAdres IP odbiorcy
portPort odbiorcy
my_uinWłasny numer
peer_uinNumer odbiorcy
Zwraca
Struktura gg_dcc lub NULL w przypadku błędu

◆ gg_dcc_set_type()

void gg_dcc_set_type ( struct gg_dcc d,
int  type 
)

Ustawia typ przychodzącego połączenia bezpośredniego.

Funkcję należy wywołać po otrzymaniu zdarzenia GG_EVENT_DCC_CALLBACK.

Parametry
dStruktura połączenia
typeRodzaj połączenia (GG_SESSION_DCC_SEND lub GG_SESSION_DCC_VOICE)

◆ gg_dcc_socket_create()

struct gg_dcc* gg_dcc_socket_create ( uin_t  uin,
uint16_t  port 
)

Tworzy gniazdo nasłuchujące dla połączeń bezpośrednich.

Funkcja przywiązuje gniazdo do pierwszego wolnego portu TCP.

Parametry
uinWłasny numer
portPreferowany port (jeśli równy 0 lub -1, próbuje się domyślnego)
Nota
Ze względu na możliwość podania wartości -1 do parametru będącego 16-bitową liczbą bez znaku, port 65535 nie jest dostępny.
Zwraca
Struktura gg_dcc lub NULL w przypadku błędu

◆ gg_dcc_voice_send()

int gg_dcc_voice_send ( struct gg_dcc d,
char *  buf,
int  length 
)

Wysyła ramkę danych połączenia głosowego.

Parametry
dStruktura połączenia
bufBufor z danymi
lengthDługość bufora z danymi
Zwraca
0 jeśli się powiodło, -1 w przypadku błędu

◆ gg_dcc_watch_fd()

struct gg_event* gg_dcc_watch_fd ( struct gg_dcc h)

Funkcja wywoływana po zaobserwowaniu zmian na deskryptorze połączenia.

Funkcja zwraca strukturę zdarzenia gg_event. Jeśli rodzaj zdarzenia to GG_EVENT_NONE, nie wydarzyło się jeszcze nic wartego odnotowania. Strukturę zdarzenia należy zwolnić funkcja gg_event_free.

Parametry
hStruktura połączenia
Zwraca
Struktura zdarzenia lub NULL jeśli wystąpił błąd

◆ gg_dcc_free()

void gg_dcc_free ( struct gg_dcc d)

Zwalnia zasoby używane przez połączenie bezpośrednie.

Parametry
dStruktura połączenia