Twoje PC  
Zarejestruj się na Twoje PC
TwojePC.pl | PC | Komputery, nowe technologie, recenzje, testy
B O A R D
   » Board
 » Zadaj pytanie
 » Archiwum
 » Szukaj
 » Stylizacja

 
M E N U
  0
 » Nowości
0
 » Archiwum
0
 » Recenzje / Testy
0
 » Board
0
 » Rejestracja
0
0
 
Szukaj @ TwojePC
 

w Newsach i na Boardzie
 
OBECNI NA TPC
 
 » Holyboy 10:45
 » JE Jacaw 10:44
 » Soulburne 10:44
 » lavka 10:40
 » Sherif 10:40
 » Zbyl 10:38
 » Nazgul 10:36
 » Sebek 10:29
 » Marian30p 10:29
 » Menah 10:29
 » Liu CAs 10:29
 » PaKu 10:26
 » jenot 10:24
 » KHot 10:22
 » Matti 10:20
 » Kool@ 10:15
 » El Vis 10:13
 » XepeR 10:10
 » Visar 10:08
 » cVas 10:06

 Dzisiaj przeczytano
 41138 postów,
 wczoraj 25974

 Szybkie ładowanie
 jest:
włączone.

 
ccc
TwojePC.pl © 2001 - 2024
A R C H I W A L N A   W I A D O M O Ś Ć
    

[SOFT] PHP, flock i zjawisko deadlock , bwana 14/06/03 08:59
Krotka pilka:

Jak zapewnic sobie sekcje krytyczne w PHP? Chodzi mi o sytuacje, kiedy 2 skrypty php probuja zablokowac na wylacznosc dwa pliki, ale robia to w roznej kolejnosci:

Skrypt1: Blokuje Plik1
Skrypt2: Blokuje Plik2
Skrypt1: Chce zablokowac Plik2, ale nie moze, bo czeka na zakonczenie Skryptu1 (w wlasciwie odblokowanie w nim Pliku1)
Skrypt2: Chce zablokowac Plik1 (ale nie moze, bo... wiadomo)

Takie sytuacje (czyli deadlock) mozna ominac, jesli na poczatku kazdy skrypt bedzie probowal zablokowac sobie od razu oba pliki, i w obu przypadkach bedzie to sie dzialo w tej samej kolejnosci (wtedy skrypt ktory zacznie pierwszy, zrobi wszystko od razu, a ten drugi bedzie czekal troche dluzej, ale za to oba maja szanse zakonczyc sie).
Zeby miec pewnosc, ze takie "zablokowanie z wyprzedzeniem" powiedzie sie, trzeba zapewnic sobie, ze obie instrukcje:

{
flock($plik1...
flock($plik2...
}

wykonaja sie tak jak w sekcji krytycznej, czyli, ze serwer wykona je "ciurkiem" bez wyskakiwania do wykonywania innego skryptu. Jak to uzyskac w PHP?

Podobnie potrzebne jest to chyba w sytuacji takiej:

if (flock($plik, LOCK_EX + LOCK_NB))
{
// ryzyko!
flock($plik, LOCK_EX);
}

W linii opisanej komentarzem "ryzyko!" moze dojsc do tego, ze inny watek na serwerze stanie sie aktywny, i wlasnie w tym momencie zablokuje ten sam plik na ktory wskazuje uchwyt $plik - czyli wartosc wyrazenia w if() zdezaktualizuje sie bez naszej wiedzy. Potrzebne jest wiec znowu cos w rodzaju sekcji krytycznej, ktora obejmie cale wyrazenie if().

Jak to rozwiazac?

"you don't need your smile when I cut
your throat"

  1. hmm , bor@s 14/06/03 10:08
    rozproszone dawno miałem... ale może uda się ręcznie zaimplemenentować sekcje krytyczną. Były jakieś algorytmy (Dijsktry, piekarski). Wiele już nie pamiętam. Jakbym odświeżył sobie wiedzę, to może coś napiszę.

    1. hmm2 , bor@s 14/06/03 10:20
      a może można nawet prościej: pozakładać semafory
      sem_acquire
      sem_get
      sem_release
      sem_remove
      warunkiem oczywiście jest to, że każdy proces odwołujący się do tych plików z nich korzysta.

      1. no wlasnie nie da rady chyba , bwana 14/06/03 17:16
        przynajmniej nie na Windowsie (a to wlasnie wchodzi w gre). Z dokumentacji PHP wynika, ze semafory mozna wprowadzic na SYSTEM V, o Windows ani slowa.
        Sprobuje skorzystac z pamieci dzielonej, ale najpierw musze sie upewnic, czy sa niepodzielne operacje dostepu do pamieci dzielonej (czyli wlasnie otoczone sekcja krytyczna , czy tez - w windowsie - mutexem) - na 99% takie tez powinny byc, bo inaczej byloby to bez sensu.

        "you don't need your smile when I cut
        your throat"

        1. ach ten Windows , bor@s 14/06/03 17:25
          :) niby system zapewnia te mechanizmy, bo widziałem kiedyś odpowiednie polecenia systemowe WinAPI. Dziwne by było gdyby Apache z tego nie korzystał.

          1. ano ach:) Windows ma i pamiec dzielona, i semafory i mutexy , bwana 14/06/03 17:47
            sam serwer www (w moim przypadku to xitami) nie gra tu roli (chociaz na pewno je musi wykorzystywac;-D) tylko silnik php - to on musi zapewnic niepodzielnosc takich operacji jak lock i unlock, flock itp. (tych phpowych, nie systemowych). Tylko ze sam jezyk ich nie "upublicznia" dla kodera php w niektorych systemach.

            "you don't need your smile when I cut
            your throat"

  2. W ogole - po sieci snuje sie makabryczny przyklad blokowania - licznik odwiedzin , bwana 14/06/03 17:53
    Jest w kilku miejscach, np. tutaj http://php.spinacz.pl/...41.html?id=41&npnum=5

    (u dolu strony). Jest napisany tak, ze jesli np. 5 osob jednoczesnie wykona ten skrypt a potem (dzieki blokowaniu) juz kolejno zapisze do pliku zwiekszona wartosc licznika, to niestety, na koniec wartosc licznika bedzie wieksza o 1 a nie o 5 (w najgorszym przypadku).

    Ponizej moj przykladowy licznik, ktory jest wolny od tego bledu (bardzo uproszczony ale tu nie sourceforge;-D):

    if ($plik=fopen("licznik.txt", "r+"))
    {
    flock($plik, LOCK_EX);
    $liczba=fgets($plik);
    if (!$liczba)$liczba=1;
    else $liczba++;
    fseek($plik, 0);
    fputs($plik, $liczba) ;
    flock($plik, LOCK_UN);
    fclose($plik);
    print "Odwiedziny nr: $liczba";
    }

    Moze licznik to pierdola, ale bledny schemat postepowania przy oprogramowywaniu innych zadan moglby zdrowo namieszac.

    "you don't need your smile when I cut
    your throat"

    
All rights reserved ® Copyright and Design 2001-2024, TwojePC.PL