Zamykani pres flock()

Jan Kasprzak kas na fi.muni.cz
Pátek Červen 5 00:07:56 CEST 2009


	Dobry den,

asi nerozumim UNIXu a/nebo Perlu:

mam paralelni vypocet - rodicovsky proces otevre rekneme 512 souboru
(jako ">:bytes"), pak pres fork() spusti tolik potomku kolik je procesoru,
potomci neco pocitaji a generuje dvacetibajtove struktury, ktere tridi
do 512 skupin (retezi do 512 skalaru) a jednou za cas tyhle skalary
zapisou pres ->print($skalar_velikosti_delitelne_dvaceti) do tech 512 souboru.

No a problem je, ze nekdy nektery ten soubor obsahuje na urcitem miste
treba jen 16 bajtu te struktury misto 20, a pak nasleduji dalsi struktury
timto posunute o 4 bajty. Cili nekde se neco prepisuje.

Myslel bych, ze zdedene filedeskriptory pres fork maji sdilene ukazovatko
pozice v souboru, takze se nestane, ze by si skutecne prepisovali data,
ale spis ze jeden proces zapise kratsi blok, a nez se dostane k dalsimu
write(2), vecpe se pred neho nekdo jiny. Teto interpretaci taky napomaha
to, ze zmena ">:bytes" za ">>:bytes" nepomohla.

I rekl jsem si ze je treba zamykat, a pred kazde
$fh->print($skalar_velikosti_delitelne_dvaceti)
jsem napsal

	flock $fh, LOCK_EX;

a za ne jsem napsal

	flush $fh;
	flock $fh, LOCK_UN;

(flush je zbytecny, v dokumentaci pisou ze flock dela implicitni flush).
Dost me prekvapilo, ze ani toto nepomohlo, porad jsou data ve vyslednych
souborech prokladana.

Vynecham dalsi slepe cesty a napisu happy end: nakonec pomohlo
nahradit $fh->print() za syswrite($fh, ...). Ale fakt nechapu proc
to pomohlo, kdyz flock by prece mel zajistit, ze do souboru nebude
po tu dobu zapisovat nikdo jiny (pokud ten jiny si taky zkusi zavolat
flock, coz jsem delal).

Overoval jsem si, ze fakt zapisuju blok velikosti delitelne dvaceti.
Dokonce jsem za flock() dopsal seek na konec a pres tell jsem zjistoval
jestli soubor ma velikost delitelno dvaceti: stavalo se ze nemel. Coz
znamena, ze i uvnitr flock() byly videt "castecne zapisy", nebo ze
flush() nedela co ma. Nevim.

	?

[ kod s prikladem se mi nechce psat vzhledem k tomu, ze problem
  samotny jsem tim syswrite vyresil. Jen me zajima proc flock() + print
  neni dostatecny. ]

-Yenya

-- 
| Jan "Yenya" Kasprzak  <kas at {fi.muni.cz - work | yenya.net - private}> |
| GPG: ID 1024/D3498839      Fingerprint 0D99A7FB206605D7 8B35FCDE05B18A5E |
| http://www.fi.muni.cz/~kas/    Journal: http://www.fi.muni.cz/~kas/blog/ |
>> If we wanted to trade simplicity and kewl design for usability I think <<
>> we all know the URL of the Apple Store.               --jmorris42 @LWN <<


Další informace o konferenci Perl