Hlavní navigace

Názory k článku Síťování v Javě: New I/O

  • Článek je starý, nové názory již nelze přidávat.
  • 11. 5. 2006 15:05

    shinigami (neregistrovaný)
    Ne, dalsi verze (presneji rozsireni stavajici) se ma jmenovat NIO2, dockame se ji snad v JSE 7.
  • 11. 5. 2006 11:28

    bez přezdívky
    > Ani již známé knihovny java.net a java.io nezůstanou stranou. NIO je nad nimi vystavěno, tudíž i je si budeme muset naimportovat.

    To je podivné tvrzení se kterým nesouhlasím.

    > Zajímavostí je třída MappedByteBuffer vhodná pro práci s velkými soubory. Ta však do seriálu o síťování nepatří, takže se jí nebudeme zabývat.

    MappedByteBuffer je mechanismus jak zpřístupnit mapované I/O (v Linuxu mmap()) o kterém si někdo bůh ví proč myslí že je rychlejší než to normální.
    Je to dobré ke všemu možnému _kromě_ práce s velkými soubory (zkus si namapovat do paměti 5GB soubor na 32bitové mašině ;-) )

    > Bajtové buffery je možné alokovat jako přímé nebo nepřímé. Přímé nabízejí vyšší výkon, protože data se ukládají do nativních datových struktur.

    "nativní datové struktury"? Celý rozdíl je v tom, že bajtové pole které je v pozadí bufferu se u nativního bufferu nealokuje z hromady JVM pod správou garbage collectoru ale mimo ni, jaksi navíc, normálními prostředky operačního systému. To zrychluje přístup protože se nemusí řešit jak pole zamknout aby s ním GC nehejbal v paměti - nativní buffer lze používat přímo v systémových funkcích (např. I/O) bez nutnosti data nejdřív zamykat nebo někam kopírovat.
  • 11. 5. 2006 14:55

    bez přezdívky
    Heh a jeste tu o karkulce...:-r

    A ted k veci - pametove mapovany soubor je naprosto std. vec, ktera se pouziva na mnoha platformach... namatkou bych jmenoval vlastnosti jako asynchrocnost, overlaping, HW podpora atd... - kdo rika, ze musime mapovat naraz cely velky soubor do pametoveho prostoru aplikace? Copak data po sbernicich take litaji naraz nebo po shlucich? Proc asi?

  • 11. 5. 2006 16:46

    bez přezdívky
    Asynchronnost? Pokud se stránka načte v okamžiku kdy program čte z paměti kam je namapovaná předpokládám že se daný thread blokuje dokud se stránka nenačte - tak jaká asynchronnost?

    HW podpora je nutná aby to vůbec šlo (MMU v procesoru která si umí osnačit v tabulce stránek že do dané stránky bylo zapisováno).

    Mapovat celý velký soubor do paměti nemusíš, můžeš namapovat jen okýnko, ale pak přijdeš o všechy výhody protože tím okýnkem budeš stějně muset posouvat a budeš s tím mít stejně práce jako bys používal normální I/O.
  • 12. 5. 2006 9:01

    bez přezdívky
    Kdo rika, ze se musi data z disku stehovat do RAM az v okamziku vypadku stranky? Kdo rika, ze podpora ze strany CPU je nezbytne nutnym predpokladem aby pametove mapovane soubory fungovaly (ja mel spise nez nezbytnou HW podporu na mysli moznost pres arbitra sbernice to vyridit bez ucasti CPU - pouze mezi diskem, I/O subsystemem, systemovou sbernici a radicem pameti)? Kdo rika, ze prace s vyrezenem degraduje tuto metodu prace se souborem na klasicke I/O?

    Dle meho skromneho nazoru ani jedno z vyse uvedenych tvrzeni neni pravdive, pametove mapovane soubory jsou mimo jine vsechny DLLka v MS Windows, je timto zpusobem zprocesovan odkladaci prostor (swap) - proc asi, kdyz by to bylo "tak neefektivni" atd... Nemam cas ani to neni mym cilem Vas presvedcovat o Vasem omylu, zdroju kde se muzete dozvedet jak to opravdu ve skutecnosti v OS, ktera jsou dnes IN, je habakuk...

  • 12. 5. 2006 12:29

    bez přezdívky
    > Kdo rika, ze se musi data z disku stehovat do RAM az v okamziku vypadku stranky?

    Já to říkám. A triviální test ti to potvrdí. Zkus si vyrobit 512MB soubor, namapovat ho do paměti a sáhnout na poslední bajt souboru v paměti. Zjistíš že to jde velice rychle.
    Pak si zkus ten soubor zkopírovat do /dev/null. Zjistíš že to jde velice pomalu.
    A ne, není to tím že by memory mapped soubory byly TAK rychlé. Prostě se čte jen ta jedna stránka.
    Jestli to nedokážeš, pošlu ti zdroják.

    > Kdo rika, ze podpora ze strany CPU je nezbytne nutnym predpokladem aby pametove mapovane soubory fungovaly?

    Já to říkám. Právě z toho důvodu že MMU v procesoru je mechanismus jakým se vůbec detekuje že program sahá na nějaké místo v paměti. Je to totéž co virtuální paměť - když daná stránka není ještě načtená, dojde při přístupu k page faultu (výjimce, přerušení) (který má mimochodem taky pěkný overhead), v rámci obsluhy systém na dané místo namapuje stránku fyzické paměti, načte do ní stránku ze souboru a pak se obsluha page faultu ukončí a program pokračuje znovu od instrukce která page fault vyvolala.

    V případě zápisu je (na x86) v tabulce stránek v deskriptoru stránky bit který se nastaví při zápisu do stránky. Když se mají data uložit na disk, stačí tedy projít všechy deskriptory stránek pro danou oblast mapování a uložit jen ty stránky do kterých někdo zapisoval.

    > Kdo rika, ze prace s vyrezenem degraduje tuto metodu prace se souborem na klasicke I/O?

    Jen si představ že budeš před každým přístupem do paměti výřezu muset zkontrolovat jestli ten výřez je zrovna na správném místě, a když ne, tak ho posunout... to je snad ještě větší pakárna než normální I/O kde bys rovnou pracoval s offsety v rámci souboru!

    > Dle meho skromneho nazoru ani jedno z vyse uvedenych tvrzeni neni pravdive, pametove mapovane soubory jsou mimo jine vsechny DLLka v MS Windows, je timto zpusobem zprocesovan odkladaci prostor (swap) - proc asi, kdyz by to bylo "tak neefektivni" atd...

    A ty máš pocit že Windowsy jsou rychlé? Myslíš že když se program spouští 10 vteřin že je to OK? Že virtuální paměť je dobrá pro výkon? ;)

    On celý problém je totiž v tom, že mapované I/O svádí k tomu přistupovat k datům v souboru ve víceméně náhodném pořadí. Je to přece paměť ne? Pokud by se obsah souboru při namapování zázračně okamžitě objevil v paměti tak je to jedno, jenomže on se načítá po jednotlivých stránkách z disku. A ty stránky jsou na přeskáčku, víceméně náhodně.

    Problém s náhodnými přístupy na disk je v tom že jsou o moc pomalejší než sekvenční přístup, kvůli přesouvání diskové hlavičky sem tam během kterého se musí čekat. V nejhorším případě načtení každé stránky znamená overhead několik milisekund! Navíc protože mechanismus mapování netuší co bude dál nedá se ani pořádně využít read ahead a spíš to zhoršuje...


    Existují způsoby jak vliv stránkování na start programu snížit pomocí chytrého přeorganizování kódu ve spustitelném souboru tak aby všechny stránky které budou potřeba pro spuštění programu byly pohromadě a ve správném pořadí aby zafungoval read ahead, ale nevím jestli je něco takového v open source nástrojích pod Linux...

    Na druhou stranu, mapování do paměti je šikovným mechanismem pro komunikaci mezi procesy a vtom vidím asi tak jediné rozumné využití ;)
  • 12. 5. 2006 12:52

    bez přezdívky
    Takze postupne...

    Bod 1 - jenze to, co popisujes je specialni pripad kdy veskere operace serializujes... - predstav si takove vypalovani - opravdu tento proces potrebuje plnou rychlost disku, sbernice, pametoveho pristupu? Nebo staci operaci "vytvorit", zahajit a nechat na jinych (nejlepe bez prispeni CPU aby se mohlo venovat efektivnejsi cinnosti) aby ji provedly, dokoncily a posleze signalizovaly? Smir se s tim, ze neexistuje zadny the best pristup, ktery by pokryl vsechny varianty pouziti... a ja rikam (a asi nejsem sam, kdyz je to implementovano dnes VSUDE) ze pametove mapovane soubory smysl maji a v mnoha situacich je to rychlejsi. Rychlosti v tomto pripade opravdu nerozumim jen rychlost provadeni kodu (pocitano na takty - dneska v podstate zhola nemozne diky spekulativnimu, prediktivnimu vyhodnocovani atd.) - rekneme na urovni CPI a IPT, ale treba rychlost efektivniho prevodu algorytmizovane ulohy na Op kod... (meni nez programatorskou praci pocitam taktez).

    Bod 2 - nutna podpora v HW neni nezbytne nutna, ale vyrazne vse urychluje a zjednodusuje... - chces rici, ze odkladaci soubor, overlaye, DLLka pred erou I80386 neexistovaly? To co popisujes je vlastne implementace virtualniho modu v I80386 a novejsi... jenze tim era nezacala... Asi jsi prilis mlad, protoze mozna nepamatujes programovani OVL nad Turbo C ci Turbo Pascalem, asi nepamatujes virtualizaci nikoli strankovanim, ale segmentovanim apod. mechanismy. Ano souhlasim, jejich vykon je nizsi nez to, co dnes bezne pouzivame, ale to na principu nic nemeni.

    Bod 3 - castecne povazuji zodpovezen v bodu 1 - stejne jako je mozne casto znacny cas usetrit vhodnou paralelizaci ulohy na vypocty v pevne carce a pohyblive carce (a provadet je pararelne via ALU a FPU) a pote si zkombinovat vysledky dle potreby, lze to i v mnoha jinych oblastech - samozrejme ne vsude.

    Bod 4 - Ja mam pocit, ze MS Windows jsou rychle na urovni toho, kolik operaci provadi - stejne jako jakakoli aplikace v Linux GUI - chces rici, ze systemova inicializace aplikace postavene na qt je zasadnim zpusobem rychlejsi nez to same na MFC? Pokud ano, chci videt jasne testy a vysledky - presto jsem k tomuto vysledku znacne skepticky...

    Na dalsi odstavec mohu jen podotknout zhruba toliko, ze Ti zrejme unikl smysl, proc je toto API (ktere ma kazdy system s odkladacim souborem a tedy virtual memory) exportovano i do uzivatelskeho prostoru pro "aplikacni" vyuziti... kdyby to nebylo ku prospechu, neni nic slozitejsiho nez ho neexportovat... Jako zcela stezejni vlastnost, ktera je na tomto pristupu cenena, je moznost pracovat se souborem a daty v nem ulozenych jako by to byly klasicke struktury v tom kterem konkretnim prog. jazyce. Uz jen tato vec zcela zastinuje cokoli co pises, vcetne nejake miniaturni rezie... - zvykni si na to, ze prace masiny je uz dost dlouho vyrazne levnejsi nez prace cloveka... a bude to cim dal horsi...

    A ten posledni odstavec snad nemuzes myslet vazne... ano PMS je jeden ze zpusobu IPC, chces rici, ze je sikovny a jeden z nejlepsich? Zvlastni - neznam ani jeden OSS vyznamny projekt, ktery by se touto cestou vydal a tuto vlastnost ocenil natolik, ze IPC realizuje timto zpusobem... a to mame aplikace, ktere prosim pekne spolu komunikuji podstatne vice nez s klientem...

    Skutecne - ber to jako dobrou radu - nastuduj si principy a vyznam a zpusob optimalniho pouziti PMS a muzeme v debate pokracovat.
  • 12. 5. 2006 14:32

    bez přezdívky
    Odpovídáš vůbec na můj příspěvek? Mě se zdá že já o voze a ty o koze...
    Moje rychlé = rychlé za běhu, tvoje rychlé = rychle naprogramované???

    Co pořád máš s tou serializací / plným vytížením sběrnice?
    Nemícháš do toho náhodou to druhé memory mapped I/O (přístup k hardware namapováním I/O registrů/paměti hardwarového zařízení do adresového prostoru procesoru)?

    Proti asynchronnímu I/O nic nemám ;) Bavíme se o souborech mapovaných do paměti v userspace jakožto rychlejší variantě operací se souborem ne? Chci vidět jak bys používal soubor mapovaný do paměti asynchronně (sáhneš do paměti, jéje, ono to tam ještě není, co budeme dělat?)

    Ano, sdílení kódu / víc kódu než je paměti lze realizovat jinak než mapováním souboru do paměti, a co jako má bejt?

    Pokud jde o "I/O líného programátora" - přistupování k datovým strukturám přímo v souboru, veškerá elegance tohoto přístupu mizí v okamžiku kdy musíš ošetřovat chyby - např. poškozená data v souboru. Když to neuděláš, riskuješ náhodné přístupy někam do adresového prostoru procesu a nejspíš i nějaké ty bezpečnostní slabiny. Navíc některé architektury procesorů nemají rády unaligned přístupy do paměti (např. 32bitové hodnoty na adresách nedělitelných 4). Struktury můžeš používat i s normálním I/O, jen si je musíš někam načíst. Tak velký rozdíl to není, a když načteš do paměti celý soubor najednou bude to určitě i rychlejší díky sekvenčnímu přístupu.

    Pokud jde o IPC, soubory mapované do paměti jsou na Windows jsou asi nejefektivnějším způsobem jak mezi dvěma procesy sdílet velké objemy dat. Linux/unix má na to sdílené paměťové segmenty takže tam to není tak užitečné. Netvrdím že je to jediný a nejlepší způsob IPC - kde to čteš?
  • 12. 5. 2006 14:43

    bez přezdívky
    A proc by vse za behu melo byt serializovane? Copak nedokazes pochopit, ze existuje nepreberne mnozstvi uloh (resp. je jich vetsina, zapomen na "chci TED zkopirovat soubor" - ponekud specializovana uloha), kdy v danou chvili je mozno zacit I/O operaci, pracovat dale (nebo pracovat s castmi, ktere se "uz vyridily") a za nejakou dobu mit vysledek. V prubehu te doby lze delat daleko rozumnejsi operace nez tupe cekat na dokonceni I/O (a v tuto chvili je uplne jedno jakym zpusobem implementovane a odkud kam data plynou).

    Ke tretimu odstavci... - proboha - pokud si namapujes soubor do pameti - myslis si, ze ho OS bude natahovat hned? Ale kde ze (tady opet vstupuje strategie, ale to je porad mimo moznost ovlivneni aplikacniho programatora - je to vec spravce virtualni pameti), pekne pocka na prvni vypadek stranky a pak natahne tu, ktera je nejnutnejsi a dle strategie mozna i nejake dalsi (okolo apod.).

    K 5. odstavci - nejde o lineho programatora... - spousta zajimavych veci okolo tohoto je schovano v knihovnach... ano vymenime dodavatele knihovny a budeme porad do kola prepisovat neefektivne aplikace (oni jaksi interface knihoven mezi ruznymi dodavateli nebyvaji shodne, o semantice ani nemluve) protoze jinde ziskame 00 nic vykonu navic...

    Naprosto nechapu korelaci rozbitych dat v souboru s pristupem do zakazanych oblasti pameti... jo ty ses omezil vlastne na jazyk C a pointerovou aritmetiku...:-r Vis ony existuji i jine pristupy k teto problematice nevedouci k tak zasadnimu selhani software... Navic rozbity soubor neni problem aplikace, ale toho, kdo se snazi nad nim provest operace... - a zdetekovat tento neliby stav urcite vis jak... co treba jakakoli signatura?
  • 12. 5. 2006 14:53

    bez přezdívky
    1) Co furt maš s ňákým serializováním všeho? O žádném serializování jsem nikdy nepsal. Psal jsem že přístup do souboru mapovaného v paměti tím že hrabeš do té paměti je v rámci jednoho threadu z principu synchronní.

    2) Čili přesně to co píšu od začátku ;)

    3) nevim co tím myslíš, výměnu dodavatele I/O knihoven????

    4) No, na ověření signatury potřebuješ ten soubor stejně celý načíst ne ;) Leda bys podepisoval jednotlivé struktury...
  • 11. 5. 2006 15:27

    shinigami (neregistrovaný)
    K te rychlosti bych jeste dodal, ze to pomaha zejmena pokud k datum v bufferu pristupuje pouze system, pristup z Javovskeho kodu je pomalejsi nez u bufferu alokovanych na halde.
  • 31. 8. 2007 10:32

    beginner (neregistrovaný)
    Zkoušel jsem celý vzorový zdroják beze změny zkopírovat a spustit. Bohužel na řádku
    SocketAddress addr = new InetSocketAddress(url.getHost(), url.getPort());
    dochází k chybě, že url.getPort() vrátí -1. Zkoušel jsem všechny možné adresy, co mě napadly, a nepomohlo to. Když pevně zadám třeba port 80, tak ze socketu zase přečtu požadavek, který jsem zapsal.
  • 23. 9. 2007 0:17

    useful.idiot (neregistrovaný)
    musis tu adresu zadat takhle:

    protokol://server:port/soubor

    takze napr.:

    http://www.root.cz:80/index.htm