Download presentation
Presentation is loading. Please wait.
Published byΚανδάκη Μιχαλολιάκος Modified over 6 years ago
1
2006m 4 Paskaita 2006 Sarafinienė Nijolė
2
Aplikacinių programų sąsaja(API)
Aplikacinių programų sąsaja(API) tai sąsaja, kurią teikia op. sistema, biblioteka ar aplikacija. Jos tikslas-leisti kitoms kompiuterinėms programoms kreiptis tam tikro serviso atlikimo ar duomenų apsikeitimo. Vienas iš pagrindinių API tikslų yra aprašyti tai, kaip pasiekiamas tam tikras funkcijų rinkinys. Pavyzdžiui, API gali aprašyti, kaip nupiešiami langai ar ikonos ekrane naudojant biblioteką, kuri skirta šiam tikslui. API, kaip ir dauguma sąsajų yra tam tikra abstrakcija. API- tai rinkinys protokolų, procedūrų bei įrankių, skirtų programinėms aplikacijoms kurti. API palengvina programų sukūrimą, nes teikia paruoštus programų blokus, skirtus tam tikrų veiksmų realizavimui. Dauguma operacinių aplinkų teikia vartotojams API, kurias naudodami programuotojai gali kurti aplikacines programas, suderinamas su operacine aplinka. Sarafinienė Nijolė
3
Sąsajos Sarafinienė Nijolė
4
Aplikacinių programų sąsaja
API – tai tam tikra kalba, pranešimų formatai, kurie nusako tai, kaip programos bendrauja su operacine sistema, su kitų programų vykdomomis funkcijomis, su komunikacinėmis sistemomis ar įrenginių tvarkyklėmis. Pavyzdžiui, operacinė sistema gali turėti eilę standartinių API, kuriuos vartotojas gali panaudoti vartotojo įvedamų duomenų priėmimui, informacijos išvedimui į ekraną ar failų valdymui. Atskira API gali būti skirta palengvinimui programuotojui kuriant langų sistemą, su jų įvairiais elementais (iššokančiais meniu, slankikliais,...) API gali būti orientuojama kaip sąsaja skirta tinklinei komunikacijai – duomenų siuntimui per tinklą API gali būti orientuojama ir į darbą skirtingose techninėse platformose ar skirtingose operacinėse sistemose. Sarafinienė Nijolė
5
Aplikacinių programų sąsaja(API)
API apsprendžia, kaip programuotojai pasinaudoja tam tikra kompiuterio savybe. API egzistuoja tiek “Windows” sistemose, tiek failų sistemose, duomenų bazių sistemose, ir, be abejo, tinklinėse sistemose. UNIX-orientuotas, su Internetu surištas programavimas naudojasi trimis API: Berkeley Sockets, System V TLI, ir RPC. Soketai ir TLI teikia labai panašų funkcionalumą (priėjimą prie TCP ir UDP) , jie naudojami skirtingose UNIX versijose. RPC' API (RPC kalba) palaiko tinklines procedūras pasinaudojant Sun's RPC protokolu. Microsoft Windows turi į Soketų API panašų API. Sarafinienė Nijolė
6
Berkeley Soketai Soketai tai originali tinklinė sąsaja, sukurta BSD-serijos UNIX operacinėms sistemoms. Soketas tai galinis komunikavimo taškas, sukuriamas naudojant socket() funkciją, kuri naudoja du raktinius argumentus – domeną (domain) ir tipą. Domenas (domain), kuris leidžia bendrauti tinkle yra Internetinis AF_INET. Naudojami du pagrindiniai Internetinių soketų tipai - STREAM (TCP) ir DGRAM (UDP), kurie nusako skirtingus bendravimo būdus. UDP komunikacijoms, kurių metu sujungimas nėra vykdomas, yra naudojami DGRAM soketai. Sukūrus DGRAM soketą, jis iš karto gali būti panaudojamas perdavimui UDP paketų, naudojant sendto() funkciją. Norint priimti UDP paketus soketas turi būti pririšamas prie lokalaus porto adreso Pririšus DGRAM soketą prie UDP porto, jis gali būti naudojamas tiek persiuntimui informacijos( sendto()), tiek priėmimui (recvfrom()). TCP komunikacijoms, orientuotoms į susijungimus, STREAM naudojami soketai. STREAM soketas negali nei siųsti nei priimti duomenų, kol susijungimas nėra įkuriamas. Susijungimas įkuriamas naudojant connect() funkciją , kurios pagalba aktyvi susijungimo dalyvė bando sukurti susijungimą. Sudarius susijungimą, TCP soketai veikia taip kaip UNIX failų deskriptoriai, jie naudojami read(), write(), ir close() funkcijose. TCP susijungimas yra nusakomas dviejų galinių taškų pora, o kiekvieną tašką nusako IP adresas bei portas. Daug aktyvių soketų gali būti susijungę su tuo pačiu pasyviu soketu. Soketų API tui bibliotekines funkcijas, skirtas paieškai DNS serveriuose tam kad kompiuterių vardus pakeisti į Ip adresus ( gethostbyname() funkcija) Sarafinienė Nijolė
7
System V TLI System V's Transport Layer Interface (TLI) teikia beveik identišką funkcionalumą kaip ir Berkeley soketai. naudoja standartinius Interneto protokolus, taigi TLI aplikacijos gali bendrauti su Soket API ir atvirkščiai. t_open funkcija sukuria transportinį galinį komunikavimo tašką, kuriuo gali manipuliuoti tokios funkcijos kaip t_bind, t_connect, t_snd ir t_rcv, kurios yra analogiškos atitinkamoms Soketų API f-joms, skirsis tik sintaksė. Normalios UNIX operacijos su failais gali būti naudojamos operuojant transportiniais galinio komunikavimo taškais. “\begin{soapbox} TLI's main claim to superiority is its support for OSI, but there seems no compelling reason why Sockets couldn't also operate in an OSI environment, if anyone really wanted it to do so. AT&T's desire for a more proprietary networking interface is probably the real driving force behind TLI. Berkeley Sockets remains the API of choice for almost all UNIX-based Internet code. \end{soapbox} “ Sarafinienė Nijolė
8
RPC kalba RPC kalba leidžia programuotojui apibrėžti funkcionalią sąsają RPC programai, tada sukompiliuoti tai į kelis C kalbos failus naudojant rpcgen programą. Vienas iš šių failų yra serveris-shell’as. Kodas gali būti pridedamas tam, kad šis shell’as vykdytų norimas funkcijas. Serveris-shellas yra tada kompiliuojamas siekiant gauti dirbantį serverį. Kitas iš šių failų apibrėžia klientą, jis kompiliuojamas į klientinę programą, kuri vykdo tinklines RPC(remote process call) operacijas, naudojant tam tikras funkcijas . RPC servisai sukonstruojami reliatyviai paprastai “A major drawback of the method described above is the inability to re-create the server shell after it has been modified. This problem can be circumvented by using rpcgen's ability to conditionally include escaped C code in the original source.” Sarafinienė Nijolė
9
Tinklinių programų sąsaja
Jos tikslas – leisti vartotojams kurti tinklines aplikacijas, kurios bendrauja tarpusavyje. Vartotojui nereikia rūpintis tokiais klausimais: Kaip veikia tinklai, kaip siunčiami duomenys tinklu, Kaip duomenys paruošiami persiuntimui tinklu. Programuotojo dispozicijoj rinkinys funkcijų, kurios sudaro aplikacinių programų sąsają su žemesniais lygiais ir nusako pagrindinius veiksmus, reikalingus procesų bendravimui tinkle. Sarafinienė Nijolė
10
Tinklinių aplikacinių programų sąsaja
Sąsaja tarp aplikacijos ir tinklo Aplikacija gali siųsti/gauti duomenis į/iš tinklo, t.y. komunikuoti. Aplikacija Tinklinių programų sąsaja( API ) Protokolas A Protokolas B Protokolas C Sarafinienė Nijolė
11
Sąsajos uždaviniai Priskirti komunikacijai reikalingus lokalius resursus. Nusakyti lokalų bei nutolusį galinius komunikavimo taškus. Inicijuoti susijungimą (klientinėje pusėje) Laukti ateinančių susijungimų (serverio pusėje) Siųsti ar priimti duomenis. Nustatyti, kada duomenys pasirodė. Generuoti skubius duomenis. Apdoroti atėjusius skubius duomenis. Tvarkingai užbaigti susijungimą. Apdoroti susijungimo nutraukimą atėjusį iš nutolusio hosto. Nutraukti komunikacijas, įvykus klaidingai situacijai. Atlaisvinti resursus pasibaigus susijungimui. Sarafinienė Nijolė
12
Sisteminiai kreipiniai
Aplikacija 1 Aplikacija n Aplikacija 2 Aplikacijų kviečiamos sisteminės funkcijos Operacinės sistemos branduolys, turintis TCP/IP programinę įrangą Sarafinienė Nijolė
13
4.3BSD Pirmi bandymai susiję su UNIX 4.2 BSD – kaip “pipe” mechanizmo išplėtimas. Tarp-procesinio bendravimo pradžia galima laikyti UNIX 4.3 BSD , kuri turi posistemę, skirtą tarp-procesiniam bendravimui. Soketų mechanizmas buvo sukurtas tikslu užtikrinti procesų tarpusavio bendravimą tinkle. Soketai apibrėžti kaip galiniai komunikavimo taškai. Sarafinienė Nijolė
14
Portai Kiekvienas hostas turi 65,536 portus
Kai kurie portai yra rezervuoti specialioms aplikacijoms 20,21: FTP 23: Telnet 80: HTTP Port 1 Port 65535 Soketas užtikrina sąsają adresinei porai IP:portas Sarafinienė Nijolė
15
Failai ir srautai Pagrindinė abstrakcija – failas – arba nuosekli baitų seka – baitų srautas. Pavyzdys : Skaitymas iš klaviatūros, mainai su tinkline korta, rašymas į ekraną, komunikacija su kitu procesu naudojant “pipe” mechanizmą, ir visa kita – tai veiksmai su failais. Sarafinienė Nijolė
16
Bazinės UNIX funkcijos
open Paruošti įrenginį ar failą įvedimo /išvedimo oper. close Baigt naudoti anksčiau atidarytą įrenginį ar failą. read Paimti duomenis iš įvedimo įrenginio ar failo ir padėti juos į aplikacinės programos atmintį. Write Perduoti duomenis iš aplikacinės programos atminties į išvedimo įrenginį ar failą. lseek Pasislinkti iki specialios pozicijos faile ar įrenginyje. (ši operacija taikoma failams ar įrenginiams, kurie surišti su disku). Ioctl Kontroliuoti įrenginį ar progr. įrangą, kuri kreipiasi į jį (pavyzdžiui, nusakyti buferio dydį) Sarafinienė Nijolė
17
Soketo apibrėžimas Soketas yra tam tikra abstrakcija, atitinkanti galinius komunikavimo taškus. Dauguma aplikacijų, naudojančių TCP/IP sukuria atitinkamo tipo soketą ir vykdo seriją operacijų su soketais. Operacijos, kurios yra vykdomos su soketais: kontrolės operacijos( tai porto numerio surišimas su soketu, ryšio inicijavimas arba priėmimas sokete arba soketo suardymas) duomenų perdavimo operacijas(duomenų rašymas / skaitymas per soketą kitai aplikacijai). Statusą nusakančios operacijos(Tokios kaip kad IP adreso susijusio su soketu suradimas). Visuma operacijų, kurios gali būti vykdomos su soketais sudaro Soketų API (Aplikacijų programinį interfeisą-Application Programming Interface). Sarafinienė Nijolė
18
Soketo sukūrimas C: socket()
int s = socket(domain, type, protocol); s: soketo deskriptorius (sveikas skaičius (kaip ir failų-atveju) domain: komunikacinis domenas pav., AF_INET (IPv4 protokolui) – dažniausiai naudojama type: komunikacijų tipas SOCK_STREAM: patikimas, 2-krypčių sujungimu pagrįstas susijungimas SOCK_DGRAM: nepatikimas, be sujungimo. SOCK_RAW : teikia priėjimą prie vidinio tinklinio protokolo bei sąsajos. Prieinamas tik “root” vartotojui. protocol: nusakomas protokolas (faile /etc/protocols ) – paprastai nurodomas 0 Kreipinys socket() grąžina failų deskriptorių, kurį galima naudoti tolimesniuose veiksmuose Sarafinienė Nijolė
19
Deskriptorių lentelė Nors soketai turi tam tikrų specifinių savybių, jie yra labai panašūs į jums gerai pažįstamus failų deskriptorius. Pavyzdžiui, kai panaudojate open() kreipinį, šis jums gražina failų deskriptorių, kurį vėliau galima panaudoti programose operacijose read(), write() lseek() close()su šiuo failu. Sukūrus soketą, jis yra panašus į failo deskriptorių, jūs galite naudoti tas pačias I/O funkcijas- skaitymui, rašymui ar soketo uždarymui . Sarafinienė Nijolė
20
Failų deskriptorių lentelė
Sarafinienė Nijolė
21
Socketo deskriptoriaus duomenų struktūra
Deskriptorių lentelė Family: PF_INET Service: SOCK_STREAM Local IP: Remote IP: Local Port: 2249 Remote Port: 3726 1 2 3 4 Sarafinienė Nijolė
22
skirtumai tarp soketų bei atidarytų failų
Negalima naudoti lseek(2) funkcijos su soketais(kaip ir su pipe) Soketai gali turėti adresus, susijusius su jais. Failai ir pipe neturi tinklinių adresų. Soketai turi būti tinkamam būvyje norint vykdyti įvedimą/išvedimą. Atidaryti failai atvirkščiai gali būti tiek skaitomi tiek į juos galima rašyti. Sarafinienė Nijolė
23
Soketų charakteristikos:
Soketais nusakomas dviejų krypčių komunikacinis kelias. Soketas apibrėžiamas nusakant jo tipą Soketas egzistuoja tam tikrame domene. Soketai nereikalauja bendrų protėvių komunikavimo užtikrinimui tarp procesų. Aplikacinė programa užprašo operacinės sistemos sukurti soketą kai jai jo prireikia. Operacinė sist sukurdama soketą grąžina sveiką skaičių. Sukuriant soketą, jis gali būti nepririštas prie specifinio nutolusio adreso. Aplikacijų programai leidžiama pateikti paskirties adresą kiekvieną kartą panaudojant soketą. Sarafinienė Nijolė
24
Veiksmai su soketais Sukurti soketą ir surišti jį su vardu.
Sudaryti sujungimus ir priimti susijungimus. Siųsti ir priimti duomenis Nutraukti soketų operacijas Transliuoti tinklinius adresus Sarafinienė Nijolė
25
Soketų komunikaciniai domenai
Soketai, kurie pasižymi bendrom komunikacinėmis savybėmis, tokiomis kaip bendrai priimtini vardai, protokolai, adresų formatai, yra grupuojami į atskirus komunikacinius domenus. Komunikacinis domenas kartais interpretuojamas kaip vardų ar adresų erdvė. Komunikacinis domenas apima: Vardų manipuliavimo ir interpretavimo taisykles. Adresų formatų rinkinį, nusakantį adresų šeimą. Rinkinį protokolų, sudarantį protokolų šeimą. Sarafinienė Nijolė
26
Adresų formatas Adresų formatas nusako kokios taisyklės yra naudojamos sukuriant atitinkamo formato tinklinius adresus. Pavyzdžiui, Interneto komunikaciniame domene 32 bitų reikšmė, žyminti tinklinį hosto adresą yra sudaroma pagal taisykles, kurios įvertina tai, kokiame tinkle hostas randasi. Kiekvienas komunikacinis domenas turi skirtingas taisykles, kurios nusako, koks soketo vardas yra teisingas ir kaip šis vardas turi būti interpretuojamas. Soketą sukūrus, jam gali būti suteikiamas vardas, kuris sudaromas pagal konkretaus domeno taisykles. Pavyzdžiui, UNIX komunikaciniame domene gali būti /dev/pav. Soketai gali keistis duomenimis tik su to paties domeno soketais. Sarafinienė Nijolė
27
Komunikacinis domenas
4.3BSD soketų sąsajoje yra palaikomi trys skirtingi komunikaciniai domenai: UNIX domenas, skirtas komunikacijoms pačioje sistemoje palaikyti, Internet domenas, kuris naudojamas procesams komunikuojant Internete, NS domenas, kuris naudojamas kai procesai komunikuoja remdamiesi Xerox standartiniais komunikaciniais protokolais. Sarafinienė Nijolė
28
Domenas – adresų šeima Pasirinktas domenas nusako atitinkamą, sąsajoje naudojamą adresų šeimą: /usr/include/sys/socket.h faile nurodomos šios dažniausiai naudojamos adresų šeimos: AF_UNIX Žymi UNIX operacinėje sistemoje įprastus kelio vardus. AF_INET Žymi ARPA Interneto adresus. AF_NS Skirtas XEROX Network Systems protokolui. Sarafinienė Nijolė
29
Pavyzdys #include <sys/types.h> #include <sys/socket.h>
s1 = socket(AF_UNIX, SOCK_DGRAM,0); s2 = socket(AF_INET, SOCK_STREAM, 0); Jei protokolas nėra nusakomas ( 0 ), tai sistema parinks tinkamą protokolą, iš tų kurie tinka pagal komunikacinį domeną bei soketo tipą. “/usr/include/sys/types.h file defines data types used in system source code” “ /usr/include/sys/socket.h Socket header files contain data definitions, structures, constants, macros, and options used by socket subroutines. An application program must include the appropriate header file to make use of structures or other information a particular socket subroutine requires”. Sarafinienė Nijolė
30
Adresų šeimos Pirmas iš socket ()kreipinyje nurodomų parametrų yra komunikacinis domenas, kuris kartu žymi ir adresų šeimą. Adresų šeima nusako operacinei sistemai kaip interpretuoti pateikiamus adresus. Kreipinyje socket kaip adresinės šeimos (AF) gali būti naudojamos AF_UNIX (UNIX), AF_INET (Internet), AF_NS (Xerox Network Systems), ar AF_NDD (AIX Network Device Drivers) . Sarafinienė Nijolė
31
UNIX adresų šeima AF_UNIX
Ji užtikrina komunikacijas tarp procesų, kurie sukasi toje pačioje operacinėje sistemoje. Adresų šeima specifikuojama kaip AF_UNIX. Soketo vardas- tai ASCII simbolių eilutė, kurios max ilgį apsprendžia naudojama mašina. UNIX domene soketui suteikiamas kelio vardas failų sistemos vardų erdvėje. Failų sistemoje sukuriamas soketui mazgas ir kiti procesai gali kreiptis į soketą pateikdami tinkamą kelio vardą. UNIX domenų vardai leidžia komunikuoti bet kuriems dviems procesams, kurie dirba toje pačioje failų sistemoje. Sarafinienė Nijolė
32
Interneto adresų šeima
Uždavus adresų šeima AF_INET yra užtikrinamos komunikacijos tarp lokalaus proceso ir proceso , besisukančio nutolusiame hoste. Interneto domenas reikalauja, kad TCP/IP protokolai būtų instaliuoti sistemoje. Interneto domene soketo vardą sudaro 32 bitų IP adresas ir 16 bitų porto adresas. Interneto domenas remiasi standartiniais protokolais IP/TCP/UDP. Interneto domenas leidžia komunikacijas tarp dviejų mašinų. Sarafinienė Nijolė
33
Protokolų šeima Komunikacinis domenas indikuoja protokolų šeimą (PF), kuri bus naudojama su sukurtu soketu. Kai kurios protokolų šeimos turi keletą protokolų, nusakančių tą patį serviso tipą. Programuotojas turi turėt žinių apie protokolų šeimas ir apie tai kokį servisą teikia atitinkamas protokolas. PF_UNIX UNIX sistemos vidiniai protokolai PF_INET Interneto Protokolai (IPv4) PF_INET Interneto Protokolai (IPv6) Sarafinienė Nijolė
34
Du pagrindiniai soketų tipai
SOCK_DGRAM UDP Nepatikimas pristatymas Negarantuota eilės tvarka Neorientuotas į susijungimus Gali siųsti arba priimti SOCK_STREAM TCP Patikimas pristatymas Garantuota pristatymo tvarka Orientuotas į susijungimą dvipusis App socket 3 2 1 Dest. App socket 3 2 1 D1 D3 D2 Sarafinienė Nijolė
35
#include <stdio.h>
#include <stdlib.h> #include <unistd.h> #include <errno.h> #include <string.h> #include <sys/types.h> #include <sys/socket.h> main(int argc,char **argv) { int z; /* Status return code */ int s[2]; /* Pair of sockets */ z = socketpair(AF_UNIX,SOCK_STREAM,0,s); if ( z == -1 ) { fprintf(stderr,"%s: socketpair(AF_LOCAL,SOCK_STREAM,0)\n", strerror(errno)); return 1; /* Failed */ } /* Report the socket file descriptors returned */ printf("s[0] = %d;\n",s[0]); printf("s[1] = %d;\n",s[1]); return 0; soketų sukūrimas yra beveik toks pat paprastas kaip pipe jungties sukūrimas Atsakymai: ./soc_pora.exe s[0] = 5; s[1] = 4; Sarafinienė Nijolė
36
Soketas Kai soketas yra sukurtas, tai dar neturi savyje detalios informacijos apie tai, kaip jis bus naudojamas. Socket’as neturi savyje informacijos apie protokolo portų numerius ar lokalių mašinų ar nutolusių mašinų IP adresus. Ryšio galinis-taškas = <IP adresas> + <protokolo-porto-numeris> Sarafinienė Nijolė
37
Bendra adresinė struktūra
Apibendrintas adreso formatas susideda iš poros: (adreso šeima, šios šeimos galinio taško adresas) Soketo adresinė struktūra yra sockaddr , kuri susideda iš tokių laukų: struct sockaddr { sa_family_t sa_family; /* adreso šeima AF_xxx */ char sa_data[14]; /* iki 14 baitų nusakančių adresą */ }; Bendra soketo adresinė struktūra yra aprašyta <sys/socket.h> faile. sa_data uždavimo forma yra surišta su atitinkama protokolų šeima. Sarafinienė Nijolė
38
AF_INET adresų struktūra
Programos, kurios išimtinai naudoja TCP/IP protokolus gali išskirtinai naudoti struktūrą, taikomą protokolui IPv4 sockaddr_in; Nenaudoja sockaddr struktūros, nes joje sa_data turi nurodyt galinį adresą ir porto nr. soketo. Nesinori sa_data formuoti rankiniu būdu. Naudojama struktūra struct sockaddr_in ("in" žymi “Internet".) struct sockaddr_in { short int sin_family; // Address family unsigned short int sin_port; // Port number struct in_addr sin_addr; // Internet address unsigned char sin_zero[8]; // Same size as struct sockaddr }; Šioje struktūroje naudojama adreso struktūra: struct in_addr { in_addr_t s_addr; /* 32-bit IPv4 address */ /* network byte ordered */ }; Sarafinienė Nijolė
39
Pastabos Ši struktūra palengvina kreipimąsi į soketo adreso elementus.
sin_zero (kuris naudojamas siekiant suvienodinti jos ilgį su bendra struktūra struct sockaddr) turi būti nustatoma į nulius naudojant f-ją memset(). nuoroda į struct sockaddr_in gali būti naudojama vietoje nuorodos į struct sockaddr ir atvirkščiai. sin_family atitinka sa_family struktūroje sockaddr ir turi būti nustatomas į "AF_INET". sin_port ir sin_addr turi būti Network Byte Order!- labiau reikšminiai baitai - pirmi Sarafinienė Nijolė
40
struct sockaddr Internetui-orientuota: Bendra: struct sockaddr_in {
short sin_family; u_short sin_port; struct in_addr sin_addr; char sin_zero[8]; }; sin_family = AF_INET sin_port: portas # ( ) sin_addr: IP-adresas sin_zero: nenaudojama Bendra: struct sockaddr { u_short sa_family; char sa_data[14]; }; sa_family Nusako, kuri adresų šeima yra naudojama. sa_data Apsprendžia, galinį komunikavimo tašką. Sarafinienė Nijolė
41
Adresinės struktūros Keturios su soketais surištos funkcijos perduoda soketo adresinę struktūrą iš proceso branduoliui (kernel): bind, connect, sendto, ir sendmsg Jos perduoda soketo adresinę struktūrą per šių funkcijų argumentus, jų saraše nurodant nuorodą į struktūrą bei struktūros ilgį. Penkios su soketais surištos funkcijos perduoda soketo adresinę struktūrą iš branduolio (kernel) – procesui: accept, recvfrom, recvmsg, getpeername, ir getsockname, visose jose yra nurodoma perduodamos struktūros ilgis. Sarafinienė Nijolė
42
Adresinių struktūrų palyginimas
visos soketų adresinės struktūros turi 1baito ilgio struktūros ilgio lauką, adresinė šeima užima 1 baitą. Dvi iš šių soketų adresinių struktūrų yra fiksuoto ilgio, o Unix domeno struktūra ir datalink struktūra yra kintamo ilgio. Sarafinienė Nijolė
43
Soketo surišimas su lokaliu protokolo adresu
Funkcija bind soketui priskiria lokalų protokolo adresą. Interneto protokolų atveju, protokolo adresą nusako kombinacija 32 bitų IPv4 adreso (arba 128 bitų IPv6 adreso), kartu su 16 bitų TCP arba UDP porto numeriu. Surišimas reikalingas tais atvejais, jei, pavyzdžiui, yra ruošiamasi naudoti listen() klausymui ateinančių sujungimų. int bind(int sockfd, const struct sockaddr *name, socklen_t namelen); bind() suriša soketą su galiniu komunikavimo tašku. Kai soketas yra sukuriamas, jis egzistuoja vardų erdvėje, kurią nusako adresų šeima. bind() f-ja suriša soketą, nurodomą deskriptoriumi su adresine struktūra, kuri talpina informaciją apie jūsų adresą, tai yra, portą ir IP adresą. Jei surišimas pavyksta yra grąžinamas 0, -1 indikuoja klaidą. Startuojant serveriams, jie pririša atitinkamus soketus prie gerai žinomų portų. TCP klientams soketo surišimas su adresu nėra būtinas. Operacinė sistema pati vykdo šį surišimą vykdydama connect kreipinį. Sarafinienė Nijolė
44
Pastabos Savojo IP adreso ir porto uždavimas gali būti automatizuotas:
my_addr.sin_port = 0; // choose an unused port at random my_addr.sin_addr.s_addr = INADDR_ANY; // use my IP address Nustatydami my_addr.sin_port lygų nuliui, pranešate bind() parinkti laisvą portą. Nustatant my_addr.sin_addr.s_addr į INADDR_ANY, liepiate automatiškai įrašyti mašinos IP adresą (kurioje šis procesas sukasi). INADDR_ANY nereikia užduoti, kad būtų “Network Byte Order”! : INADDR_ANY realiai yra nuliai Sarafinienė Nijolė
45
/* Establish address */ memset(&adr_inet,0,sizeof adr_inet);
adr_inet.sin_family = AF_INET; adr_inet.sin_port = htons(9000); adr_inet.sin_addr.s_addr = inet_addr(" "); // if ( adr_inet.sin_addr.s_addr == INADDR_NONE ) // bail("bad address."); len_inet = sizeof adr_inet; /* Bind it to the socket */ z = bind(sck_inet, (struct sockaddr *)&adr_inet, len_inet); if ( z == -1 ) bail("bind()"); /* Display our socket address */ system("netstat -pa "); return 0; } Soketo sukūrimas ir surišimas su portu #include <stdio.h> #include <unistd.h> #include <stdlib.h> #include <errno.h> #include <string.h> #include <sys/types.h> #include <sys/socket.h> #include <netinet/in.h> #include <arpa/inet.h> /* This function reports the error */ static void bail(const char *on_what) { fputs(on_what,stderr); fputc('\n',stderr); exit(1); } Sarafinienė Nijolė
46
Soketo sukūrimas ir surišimas su portu
int main(int argc,char **argv) { int z; struct sockaddr_in adr_inet;/* AF_INET */ int len_inet; /* length */ int sck_inet; /* Socket */ /* Create a Socket */ sck_inet = socket(AF_INET,SOCK_STREAM,0); if ( sck_inet == -1 ) bail("socket()"); /* Establish address */ memset(&adr_inet,0,sizeof adr_inet); adr_inet.sin_family = AF_INET; adr_inet.sin_port = htons(9000); adr_inet.sin_addr.s_addr = inet_addr(" "); Sarafinienė Nijolė
47
Soketo sukūrimas ir surišimas su portu
len_inet = sizeof adr_inet; /* Bind it to the socket */ z = bind(sck_inet,(struct sockaddr *)&adr_inet, len_inet); if ( z == -1 ) bail("bind()"); /* Display our socket address */ system("netstat -pa "); return 0; } Sarafinienė Nijolė
48
Adresai ir portai baitų-rikiavimas
Problema: Skirtingos mašinos / OS naudoja skirtingą žodžių rikiavimą little-endian: žemiausio svorio baitai - pirmi big-endian: aukščiausio svorio baitai pirmi Šios mašinos gali komunikuoti viena su kita tinkle. Big-Endian machine Little-Endian machine 128 119 40 12 128 119 40 12 Sarafinienė Nijolė
49
Konvertavimas iš tinklo į hosto baitų tvarką.
Galimi du duomenų tipai, kuriuos gali prireikti konvertuoti : short (du baitai) ir long (keturi baitai). Konvertavimo f-jos taikomos beženkliams dydžiams taip pat Pavyzdžiui: norima konvertuoti short tipo dydį iš “Host Byte Order” į “Network Byte Order”. Naudojama f-ja užrašoma taip "h" - "host", toliau "to", tada "n" - "network", ir "s" - "short": h-to-n-s, or htons() ("Host to Network Short"). adr_inet.sin_port = htons(9000); Sarafinienė Nijolė
50
Galimi konvertavimai htons() -- "Host to Network Short"
htonl() -- "Host to Network Long" ntohs() -- "Network to Host Short" ntohl() -- "Network to Host Long“ Kadangi sin_addr ir sin_port yra įtraukiami į paketų galvutes, jie turi būti pateikiami “Network Byte Order” tvarka. Sarafinienė Nijolė
51
inet_addr() f-ja inet_addr() konvertuoja IP adresą iš formos, išreikštos dešimtainiais skaičiais ir taškais (pavyzdžiui “ ”) į 32 bitų tinklinės orientacijos tvarkos (network byte order) bitų eilutę. Galimas toks adreso uždavimas: ina.sin_addr.s_addr = inet_addr(" "); inet_addr() grąžina adresą “Network Byte Order”, taigi kviesti htonl() nebereikia. Ši f-ja turi problemų su adresu , nes konvertavus į 32 bitus gaunamas pranešimas apie klaidą. inet_addr() grąžina -1 esant klaidai. Sarafinienė Nijolė
52
inet_aton() ascii to network
Kaip ir inet_addr, ši f-ja konvertuoja simbolinę eilutę į 32 bitų tinklinio rikiavimo adresą. struct sockaddr_in my_addr; my_addr.sin_family = AF_INET; // host byte order my_addr.sin_port = htons(MYPORT); // short, network byte order inet_aton(" ", &(my_addr.sin_addr)); memset(&(my_addr.sin_zero), '\0', 8); // zero the rest of the struct inet_aton(), ne taip, kaip kitos visos f-jos, susijusios su soketais grąžina ne nulį sėkmės atveju ir 0 esant klaidai. Tačiau ne visos platformos palaiko inet_aton() , todėl nors ją patartina būtų vartoti, yra naudojama ir inet_addr() Sarafinienė Nijolė
53
spausdinimas Kaip atspausdinti IP adresus?
Tarkim, jie yra struktūroje struct in_addr ina ir norime juos atspausdinti įprastoje formoje – skaičiai – taškai. Naudojama f-ja inet_ntoa() ("ntoa" reiškia "network to ascii") : printf("%s", inet_ntoa(ina.sin_addr));Pavyzdžiui: char *a1, *a2; . . a1 = inet_ntoa(ina1.sin_addr); // this is a2 = inet_ntoa(ina2.sin_addr); // this is printf("address 1: %s\n",a1); printf("address 2: %s\n",a2); Sarafinienė Nijolė
54
Tinklo adresų baitų rikiavimas
Visi dydžiai saugomi struktūroje sockaddr_in turi turėti tinklo baitų rikiavimą(network byte order- aukščiausio svorio baitai - pirmi). sin_port TCP/IP porto numeris. sin_addr IP adresas. Common Mistake: Ignoring Network Byte Order Sarafinienė Nijolė
55
Susijungimas – connect()
Įsivaizduokite kelioms minutėms, kad jūs esate “telnet” aplikacija. Jūsų vartotojas liepia jums gauti soketo failų deskriptorių. Jūs kviečiate socket(). Toliau jums liepia susijungti su IP adreso " " --- "23” portu ( standartiniu telnet portu.) Kokie seks veiksmai? Kviečiamas connect()—tikslu susijungti su nutolusiu hostu. Sarafinienė Nijolė
56
Connection est.: connect()
Aktyvi pusė: int status = connect(sock, &name, namelen); status: 0 if successful connect, -1 otherwise sock: integer, socket to be used in connection name: struct sockaddr: address of passive participant namelen: integer, sizeof(name) Sarafinienė Nijolė
57
Susijungimo sudarymas
TCP soketo atveju, connect() inicijuoja trijų rankų paspaudimą ir ši funkcija grąžina reikšmę tik po to kai šis susijungimas įvyksta, arba įvyksta klaida. Jei TCP klientas negauna atsakymo, tai jo paketas su įjungta SYN reikšme kartojamas po 6 sekundžių, ir jei per 75 sek negaunamas atsakymas, pranešama apie klaidą. Jei į kliento SYN grįžta RST, pranešama apie klaidą (ECONNREFUSED)- tame porte nėra klausančio serverio. Jei iš maršrutizatoriaus grįžta ICMP "destination unreachable" , tai reiškia, kad nutolusi sistema yra nepasiekiama, ir aplikacinei programai grąžinamas klaidos pranešimas (EHOSTUNREACH or ENETUNREACH ) Sarafinienė Nijolė
58
Susijungimas #include <string.h> #include <sys/types.h>
#include <sys/socket.h> #include <netinet/in.h> #define DEST_IP " " #define DEST_PORT 23 main() { int sockfd; struct sockaddr_in dest_addr; // will hold the destination addr sockfd = socket(AF_INET, SOCK_STREAM, 0); /* do some error checking! */ dest_addr.sin_family = AF_INET; // host byte order dest_addr.sin_port = htons(DEST_PORT); /* short, network byte order */ dest_addr.sin_addr.s_addr = inet_addr(DEST_IP); memset(&(dest_addr.sin_zero), '\0', 8); // zero the rest of the //struct don't forget to error check the connect()! connect(sockfd, (struct sockaddr *)&dest_addr, sizeof(struct sockaddr)); . . Sarafinienė Nijolė
59
Pastabos Patikrinti reikia ką grąžina connect()--jei -1 įvyko klaida.
Nebuvo kviesta f-ja bind(). Praktiškai nereikia rūpintis apie lokalų porto numerį. Reikia rūpintis tik apie tą porto numerį nutolusios mašinos, su kuria norima susijungti. Operacinės sistemos branduolys parinks lokalų portą ir tas hostas su kuriuo jungiamasi automatiškai gaus informaciją apie portą. Sarafinienė Nijolė
60
Susijungimo sudarymas (SOCK_STREAM)
Susijungimas gali būti organizuojamas tarp dviejų rūšių dalyvių: Pasyvių: laukiančių kol aktyvus dalyvis pareikalaus susijungimo Aktyvių: inicijuojančių susijungimo užklausas į pasyviojo dalyvio pusę. Kai susijungimas yra sukuriamas tiek “pasyvus” dalyvis, tiek “aktyvus” dalyvis elgiasi vienodai: Abu gali siųsti &gauti duomenis Bet kuris gali užbaigti susijungimą Sarafinienė Nijolė
61
Susijungimo sudarymas
Aktyvus dalyvis step 2: request & establish connection step 4: data transfer Pasyvus dalyvis step 1: listen (for incoming requests) step 3: accept (a request) step 4: data transfer Priimtas susijungimas realizuojamas naujame sokete Senas soketas toliau naudojamas klausymui Passive Participant a-sock-1 l-sock a-sock-2 Active 1 Active 2 socket socket Sarafinienė Nijolė
62
Pasyvus dalyvis Jis neorganizuoja susijungimo su nutolusiu hostu.
Jis laukia ateinančių užklausų susijungimui ir jas tam tikru būdu apdoroja. Jo vykdomi veiksmai susideda iš susijungimo užklausų klausymo- listen(), o po to jų priėmimo- accept() . int listen(int sockfd, int backlog); sockfd yra paprastas soketo failo deskriptorius iš socket() kreipinio. backlog leistinų susijungimų kiekis įėjimo eilėje.Ateinantys susijungimai lauks šioje eilėje, kol bus priimti accept(), riba 5-20. Sarafinienė Nijolė
63
Pasyvus dalyvis Jei norima klausytis ateinančių užklausų, tai reikia panaudoti bind() prieš kviečiant listen() arba operacinės sistemos branduolys bus priverstas klausytis atsitiktiniame porte. Taigi kreipinių seka turi būti tokia: socket(); bind(); listen(); /* accept() po to */ Sarafinienė Nijolė
64
Pasyvus dalyvis accept()
Kažkas iš kažkur bandys susijungti- vykdys: connect() į jūsų mašinos portą, kuriame klausomasi listen(). Susijungimas bus patalpintas į eilę ir lauks accept(). Iškvietus accept() yra išimamas “kabantis” susijungimo prašymas. Accept() grąžins naują soketo failo deskriptorių šio susijungimo realizavimui Atsiras du soketų failų deskriptoriai: Naujas bus pasiruošęs f-joms send() ir recv() Senas ir toliau vykdys klausymą. Sarafinienė Nijolė
65
Connection est.: listen() & accept()
Pasyvus dalyvis int status = listen(sock, queuelen); status: 0 if listening, -1 if error sock: integer, socket descriptor queuelen: integer, # of active participants that can “wait” for a connection int s = accept(sock, &name, &namelen); s: integer, the new socket (used for data-transfer) sock: integer, the orig. socket (being listened on) name: struct sockaddr, address of the active participant namelen: sizeof(name): value/result parameter Sarafinienė Nijolė
66
#define MYPORT 3490 // the port users will be connecting to
#include <string.h> #include <sys/types.h> #include <sys/socket.h> #include <netinet/in.h> #define MYPORT 3490 // the port users will be connecting to #define BACKLOG 10 // how many pending connections queue will hold main() { int sockfd, new_fd; // listen on sock_fd, // new connection on new_fd struct sockaddr_in my_addr; // my address information struct sockaddr_in their_addr; // connector's address information int sin_size; sockfd = socket(AF_INET, SOCK_STREAM, 0); // do some error checking! my_addr.sin_family = AF_INET; // host byte order my_addr.sin_port = htons(MYPORT); // short, network byte order my_addr.sin_addr.s_addr = INADDR_ANY; // auto-fill with my IP memset(&(my_addr.sin_zero), '\0', 8); // zero the rest of the struct // don't forget your error checking for these calls: bind(sockfd, (struct sockaddr *)&my_addr, sizeof(struct sockaddr)); listen(sockfd, BACKLOG); sin_size = sizeof(struct sockaddr_in); new_fd = accept(sockfd, (struct sockaddr *)&their_addr, &sin_size); . . Sarafinienė Nijolė
67
Duomenų siuntimas / priėmimas
Esant soketams (SOCK_STREAM): int count = send(sock, &buf, len, flags); count: # bytes transmitted (-1 if error) buf: char[], buffer to be transmitted len: integer, length of buffer (in bytes) to transmit flags: integer, special options, usually just 0 int count = recv(sock, &buf, len, flags); count: # bytes received (-1 if error) buf: void[], stores received bytes len: # max size of buf Sarafinienė Nijolė
68
Duomenų siuntimas / priėmimas
Esant soketams (SOCK_DGRAM): int count = sendto(sock, &buf, len, flags, &addr, addrlen); count, sock, buf, len, flags: same as send addr: struct sockaddr, address of the destination addrlen: sizeof(addr) int count = recvfrom(sock, &buf, len, flags, &name, &namelen); count, sock, buf, len, flags: same as recv name: struct sockaddr, address of the source namelen: sizeof(name): value/result parameter Sarafinienė Nijolė
69
Susijungimo nutraukimas
Baigus perdavimus, uždaromas susijungimas susijęs su soketu. Galima naudoti įprastą UNIX f-ją status = close(s); status: 0 jei pavyko, -1 jei klaida s: soketo deskriptorius (soketo, kuris uždaromas). Toliau negalimas nei skaitymas nei rašymas, susijęs su soketu (duos klaidą) Uždarant soketą Uždaromas susijungimas ( SOCK_STREAM soketams) Atlaisvinamas su soketu susijęs portas Sarafinienė Nijolė
70
Susijungimo nutraukimas
shutdown() funkcija. Ji leidžia nutraukti komunikacijas tam tikra kryptimi arba abiem kryptimis. int shutdown(int sockfd, int how); sockfd yra soketo failo deskriptorius, kurį norite uždaryti, ir how yra viena iš reikšmių: 0 – Tolimesni priėmimai yra neleidžiami 1 – Tolimesni siuntimai yra neleidžiami 2 -- Tolimesni siuntimai ir priėmimai yra neleidžiami (kaip close()) shutdown() grąžins 0 sėkmės atv, ir -1 esant klaidai Sarafinienė Nijolė
71
Log off Sarafinienė Nijolė
Similar presentations
© 2025 SlidePlayer.com. Inc.
All rights reserved.