Flock frage

Hallo

ich benutze in vielen Bereichen folgenden Code. Hier ein Beispiel von meinem Gästebuch. Das habe ich vor langer Zeit mal im Internet gefunden. Ich frage mich gerade, ob das erste „flock“ (unter dem fopen) überhaupt nötig ist?

Ich möchte jedenfalls folgendes erreichen. Wenn zwei Besucher zur gleichen Zeit einen Gästebuch Eintrag schreiben, dann soll dieser Code dafür sorgen, dass alles funktioniert.

$data=fopen(„gaestebuch.dat“,„a“);
flock($data,LOCK_EX);
$canWrite = false;
while (!$canWrite)
{
$canWrite = flock($data, LOCK_EX);
}
fputs($data,„inhalt…\r\n“);
fclose($data);

An einer anderen Stelle wird das Gästebuch mit:

$gb = file(„gaestebuch.dat“);

gelesen. Geht dies immer? Oder gibt es hier Probleme, wenn gerade ein User schreibt (also der obige code mit dem „flock“ ausgeführt wird)?

Mit den Infos komme ich nicht so ganz klar bzw. die Praxis kann man schlecht testen. Jedenfalls hört sich „LOCK_SH“ (da steht „zum Lesen geeignet“) besser an und da ich lese, es gibt noch „LOCK_UN“ (entsperren), frage ich mich ob ich dies benutzen muss. Könnte mir aber vorstellen, dass mit „fclose“ dies sowieso gemacht wird.

Ich hoffe mal, mit dem ganzen kennt sich jemand aus.

Gruß
Michael

Also hier steht, dass fclose den Lock automatisch wieder freigibt:
http://php.net/manual/en/function.flock.php

Der Aufruf mit LOCK_EX gibt dem schreibenden Skript einen exklusiven Schreib-Zugriff,
so dass jedes andere schreibende Skript warten muss, bis die Schreiboperationen abgeschlossen sind.
Also ich bin der Meinung, dass es schon so richtig ist.
Allerdings könnte es sehr wohl passieren, dass ein Skript in die Datei schreibt, während ein anderes grade von ihr ließt.
Allerdings führt das nicht zu schwerwiegenden Fehlern,
da die Datei selbst nicht gefährdet ist aber
die gelesenen Daten könnten dann manchmal inkonsistent sein.
Um das zu verhindern, müsste man auch beim Lesen flock mit LOCK_SH verwenden.

Die Schleife
while (!$canWrite)
{
$canWrite = flock($data, LOCK_EX);
}
ist eigentlich überflüssig, da der flock-Aufruf das Skript solange schlafen legt, bis der Lock wieder frei wird.
Eine derartige Schleife ist nur notwendig, wenn man die LOCK_NB Bitmaske verwendet.
Dann sollte man aber unbedingt das Skript in jeder Schleifeniteration
schlafen legen (usleep), da das Skript sonst aktiv wartet und dabei sehr viel Prozessorlaufzeit vergäudet.
Ausserdem läuft die Schleife ewig, wenn man kein Lock bekommt.
was man mit einem Timer verhindern kann.

Siehe dazu auch die „User Contributed Notes“ auf der oben angegebenen Seite.

Gruß
VoidZer0

Danke. Habe nun auch meine fopen sachen neu angepasst und zwischenzeitlich hier und da über flock gelesen.

Gruß
Michael