[so] Greseli la tema 4

cosminratiu at gmail.com cosminratiu at gmail.com
Wed Feb 14 21:53:48 EET 2007


Ca o continuare la mailul lui Max, as vrea sa adaug cateva cuvinte despre
greselile frecvente la tema 4, mai precis despre partea de retea.

De departe cea mai des intalnita greseala este presupunerea ca recv/read pe
socketi citeste exact ce s-a trimis in partea cealalta. Daca pe localhost
chestia asta e adevarata 99% din cazuri, in retea pachetele se pot
fragmenta. Solutia este cod care pastreaza ce s-a citit intr-un buffer pana
este receptionat un mesaj complet.

De asemenea, vad ca multi au folosit socketi blocanti in server. Asta nu e o
problema in sine, mai ales cand se foloseste epoll pentru notificari.
Problema apare cand pentru o notificare primita se apeleaza de mai multe ori
consecutiv recv/read pentru conexiunea in cauza. Primul recv e garantat ca
nu blocheaza(doar a fost primita notificarea), dar urmatoarele pot bloca
pentru ca s-ar putea sa nu mai fie nimic de citit o anumita perioada. In
server nu trebuie sa se blocheze _decat_ in epoll_wait.

In cateva teme am gasit o forma deghizata de busy waiting. Cand adaugati un
socket nou creat in setul epoll NU dati flag-ul EPOLLOUT. Daca EPOLLOUT e
pus, o sa se genereze incontinuu notificari ca "e loc de scris in socket" si
daca nu aveti nimic de scris, e echivalentul unui busy waiting. EPOLLOUT
este facut ca sa rezolve problema descrisa in continuare.

Urmatoarea problema: write pe socketi blocanti s-ar putea sa blocheze pana
se face loc in bufferele socket-ului pentru a putea pune datele pe care le
vreti trimise. write pe socketi neblocanti s-ar putea sa nu trimita tot ce
ii dati daca nu poate face asta fara sa blocheze. Am vazut in prea putine
teme tratata situatia asta. Multi fac send si nu verifica daca s-a trimis
tot sau nu. Saracul client o sa primeasca in partea cealalta un pachet
trunchiat. Solutia: activati EPOLLOUT si pastrati ce mai e de trimis. Cand
se termina de trimis scoateti EPOLLOUT. Simplu si logic.

Next: designul protocolului. Cand creati un protocol trebuie sa aveti in
vedere ce am zis mai sus(grija la fragmentare in principiu) si in plus inca
cateva aspecte care fac diferenta intre programatorii buni si cei care
introduc gauri de securitate. Regula de aur este SA NU AI INCREDERE IN CE
VINE DE PE RETEA. Asta inseamna verificarea chestiilor primite, MARE GRIJA
la stringuri. Extrem de multe gauri de securitate sunt cauzate de protocoale
care primesc stringuri terminate cu 0, numai ca stringul primit...nu contine
0 la sfarsit. De aici rezulta diverse probleme.

Sper ca mail-ul acesta va avea un efect oricat de mic...


On 2/8/07, Maximilian Machedon <maximilian.machedon at gmail.com> wrote:
>
>          Scriu acest mail pentru că m-am apucat să corectez temele 1 (şi
> sper să le şi termin la timp :-D, ţinând cont că sunt şi eu în sesiune) şi
> am găsit unele greşeli extrem de frecvente...
> [...bucata taiata...]
> ...PS: Ştiu că este "doar o temă", dar vă asigur că există o diferenţă
> între a scrie cod bun şi a scrie cod care să meargă. Adică dacă aţi scris
> codul doar că să meargă asta nu v-a ajutat cu nimic pentru a învăţa să
> scrieţi cod bun.
>
>
> _______________________________________________
> so mailing list
> so at cursuri.cs.pub.ro
> http://cursuri.cs.pub.ro/cgi-bin/mailman/listinfo/so
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://cursuri.cs.pub.ro/pipermail/so/attachments/20070214/dbfd7e7b/attachment.htm


More information about the so mailing list