Dobry den,
dakujem za odpoved.
Vcera vecer sa mi to predsa len podarilo nasimulovat. Zjednodusil som
uvedenu slucku na while (running) { sheep ++; }
void run() {
while (running) {
sheep ++;
}
System.out.println("terminating thread " + Thread.currentThread
().getName());
}
void stopThread() {
running = false;
}
(tak to bolo v povodnej prednaske), a skutocne, ak som running premennu
nemal volatile, tak sa uz tento thread po volani stopThread z ineho vlakna
nezastavil. Predpokladam, ze to bolo kvoli uvedenej optimalizacii slucky na:
if (running) { while(true) { sheep++; }}
Po zmene running na volatile, alebo vytvoreni get/set metod (obe
synchronizovane), sa to uz spravalo korektne.
Ten slajd, ktory ste poslali, podla mna nie je spravny: synchronized
nehovori kedy sa ma co flushovat do hlavnej pamate. Moze sa stat, ze mate
metodu synchronized, ale nic sa neflushne, jednoducho preto, ze jvm zisti,
ze objekt na ktorom synchronizujete, je viditelny iba z jedneho threadu.
Dosledkom je, ze tento kod "synchronized (new Object());" neurobi vobec nic,
ziadny flush. Ako sa uvadza v prednaske z JavaOne 2006 (
http://developers.sun.com/learning/javaoneonline/2006/coreplatform/TS-1630.html),
pohlad na synchronized ako na 'flushovanie', je mylny.
S pozdravom,
-Peter Stibrany
On 1/25/07, Petr Ferschmann <[EMAIL PROTECTED]> wrote:
Zdravím,
to co tady popisujete bude nastávat jen v případě, že máte více procesorů
a ty mají oddělené cache.
"Problém" synchronizace Javy nastává tak, že obsah cache se
flushuje/obnovuje do/z hlavní paměti
jen u proměnných volatile a při volání synchronized.
Ale toto vlastně není problém - stejný problém má i C/C++ - zde totiž v
rámci definice jazyka vlastně
vůbec není definováno kdy se cache flushují - je to závislé na OS
(tento význam slova volatile zavádí i Visual Studio C++ 2005).
Jinak z těchto důvodu by neměla v Jave fungovat ani double checking
optimalizace
http://blog.softeu.cz/prednasky/2006/vm-nebo-nativni-kod/architektury-soucasnych-pocitacu-2.html
Ale myslím, že nasimulovat tento problém nebude tak snadné :-)
Jediné na co můžete na jednoprocesorovém stroji narazit je to, že to
překladač vyoptimalizuje tak,
že kód úplně změní.
S pozdravem
Petr Ferschmann
Peter Stibrany píše v St 24. 01. 2007 v 21:20 +0100:
Ahojte,
v poslednom case studujem problematiku Java Memory Model-u, a chcel bysom
nasimulovat problemy, ktore vzniknu z nekorektnej synchronizacie.
Skusal som nasimulovat problem, o ktorom sa zmienuje Brian Goetz vjeho
prezentacii z Javapolisu 2005. Tam spomina, ze hotspot kompilator(-server) je
schopny pretransformovat slucku
while (running) { ... // tu sa running nemeni}
na
if (running) { while (true) { ... // tu sa running nemeni }}
pokial pristup k premennej running nie je volatile a vo vnutri whilecyklu sa
running nemeni.
Vytvoril som si program, ktory spusta thready, ktore v obdobnej
"while(running)" slucke spustaju sleep. Hlavny thread obcas niektoremuthreadu
nastavi running na false (bez akejkolvek synchronizacie,running nie je ani volatile). Ked
pocet threadov klesne pod 50,vytvori dalsie. Dufal som, ze sa casom prejavi uvedeny efekt
tym, zepocet threadov prestane klesat. Zial, nedari sa mi nasimulovat ani lentento
problem.
Nemate nejake priklady programov, ktore vdaka chybnej synchronizaciinebudu
fungovat? Najlepsie spustitelny Javovsky kod, ktory sa spravanecakane. (Na
windows/x86).
Vdaka,-peter
--
Petr Ferschmann
SoftEU s.r.o.
-----------------------------------
Sady Petatricatniku 31
301 00 Plzen
Czech Republic
-----------------------------------
Phone: +420 373 729 300
Fax: +420 373 729 301
Cell: +420 775 638 008
E-mail: [EMAIL PROTECTED]