[so] [Tema5] [LINUX] Transmitere fisiere static / dynamic
Georgiana Diana
geodiana93 at gmail.com
Tue May 26 20:35:10 EEST 2015
2015-05-26 20:31 GMT+03:00 Adrian Stanciu <adrian.stanciu.pub at gmail.com>:
> 2015-05-26 20:26 GMT+03:00 Adrian Stanciu <adrian.stanciu.pub at gmail.com>:
> > 2015-05-26 19:17 GMT+03:00 Georgiana Diana <geodiana93 at gmail.com>:
> >> Buna,
> >> Eu tot am niste nelamuriri legate de citirea asincrona / trimiterea cu
> send
> >> (inline):
> >>
> >
> > Bună, Georgiana!
> >
> >> 2015-05-25 20:53 GMT+03:00 Adrian Stanciu via so <so at cursuri.cs.pub.ro
> >:
> >>>
> >>> 2015-05-25 20:49 GMT+03:00 Madalina Hristache via so
> >>> <so at cursuri.cs.pub.ro>:
> >>> > Salut,
> >>>
> >>> Bună, Mădălina!
> >>>
> >>> >
> >>> > Am câteva nelămuriri și am nevoie de clarificarea lor ca să pot
> continua
> >>> > tema.
> >>> >
> >>> > 1. Când transmitem un fișier din directorul static, trimitem
> header-ul
> >>> > HTTP
> >>> > cu send (non-blocant, asincron), apoi fișierul cu sendfile. Fără
> nicio
> >>> > legătură cu libaio.h, da?
> >>>
> >>> Da, așa este.
> >>>
> >>> >
> >>> > 2. Când transmitem un fișier din directorul dynamic, îl citim de pe
> disc
> >>> > cu
> >>> > apeluri legate de libaio.h, apoi îl punem pe socket. Și cum îl
> trimitem?
> >>> > Cu
> >>> > send? Sendfile? La partea asta sunt în ceață.
> >>> >
> >>>
> >>> Cu send().
> >>
> >>
> >> In exemplul din laborator [1], precum si in exemplul sugerat in tema [2]
> >> (xmailserver), am observat ca se face read pe un file descriptor,
> pentru a
> >> notifica serverul atunci cand operatia asincrona de citire s-a terminat.
> >>
> >> 1) Este acest read blocant, sau nu ?
> >
> > Acel read() pe eventfd este blocant, dar nu se va bloca dacă îl apelâm
> > atunci când primim o notificare de la kernel, prin intermediul epoll.
> >
> >> 2) Care ar trebui sa fie workflow-ul server-ului in cazul trimiterii
> unui
> >> fisier dinamic ? Ma gandeam ca unul posibil este acesta, dar inca nu
> imi dau
> >> seama daca este corect:
> >>
> >> initializare io_context (in main, inainte de logica serverului);
> >
> > Este mai ușor dacă folosești un context IO per conexiune.
>
Atunci cred ca ar trebui modificat enuntul, care spune: "Recomandăm
folosirea unei variabile globale de tipul io_context_t și a unui descriptor
eventfd pentru fiecare conexiune." In rest, mersi mult pentru raspuns !
> >
> >> in server, primirea unui request de citire fisier dinamic;
> >> trimiterea catre client a unui raspuns: 200/404, in functie de caz, prin
> >> send-uri repetate (metoda comuna, atat pentru fisier static, cat si
> pentru
> >> dinamic);
> >> dupa trimiterea header-ului, in cazul unui fisier dinamic, serverul
> seteaza
> >> un eventfd si submite un request de read pentru contextul aio -- actiune
> >> neblocanta;
> >> serverul face read pe eventfd-ul anterior -- actiune blocanta ?;
> >
> > Practic neblocantă dacă citirea se face la semnalizarea pe eventfd din
> > partea epoll.
> >
> >> in urma notificarii de terminare a citirii din fisier a unui buffer in
> >> general mai mic decat dimensiunea fisierului, serverul face apeluri send
> >> repetate, pentru a trimite buffer-ul proaspat citit; -- in timpul
> acesta, se
> >> presupune ca serverul initiaza o noua cerere de citire asincrona, sau
> >> asteapta trimiterea buffer-ului curent ? ;
> >
> > E mai ușor dacă nu faci aceste operații simultan; e mai eficient dar
> > ar trebui să tratezi în același timp mai multe tipuri de evenimente
> > (read din fișier, send pe socket), care ar fi starea conexiunii? iar
> > complexitatea implementării ar fi mai mare.
> >
> >> serverul continua sa citeasca bucati de fisier si sa le trimita catre
> >> client.
> >>
> >> 3) Este corect ca in functia de trimitere fisier, pentru cazul unui
> fisier
> >> dinamic, si care se tot apeleaza in bucla principala a server-ului
> (pentru
> >> ca epoll este setat pe out, cat timp trimit un fisier), sa verific si sa
> >> schimb starea conexiunilor (de ex, cat timp trimit fisierul, starea sa
> fie
> >> SENDING_DATA, apoi, cand citirea asincrona se termina, pur si simplu sa
> >> schimb starea in DATA_SENT si sa inchid conexiunea) ?
> >
> > Poți să:
> > * activezi EPOLLIN pe eventfd pentru a aștepta finalizarea citirii
> > asincrone a unei bucăți din fișier
> > * planifici citirea asincronă a unei bucăți din fișier
> > * activezi EPOLLOUT pe socket
>
> Nu am spus complet aici ... activarea EPOLLOUT pe socket se face când
> citirea asincronă a fost încheiată. Atunci avem date de trimis.
>
> > * când ești notificată de epoll că poți să trimiți pe socket, trimiți
> > bucata de fișier
> > * dacă nu s-a trimis întreaga bucată mai aștepți un nou eveniment de
> > EPOLLOUT pe socket din partea epoll și apoi trimiți ce ți-a mai rămas
> > și tot așa
> > * când ai terminat de trimis acea bucată, dezactivezi EPOLLOUT pe
> > socket (căci deocamdată nu mai ai ce trimite)
> > * o iei de la capât pentru a citi următoarea bucată din fișier
> > * când ai trimis întreg fișierul se poate închide conexiunea
> >
>
>
> Adrian
>
--
*Georgiana Diana Ciocirdel*
Polytechnic University of Bucharest,
Computer Science
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://cursuri.cs.pub.ro/pipermail/so/attachments/20150526/bf29e6b6/attachment.html>
More information about the so
mailing list