Diskuze: C++ Ofset tabulky dat v ASM x64 funkci
V předchozím kvízu, Online test znalostí C++, jsme si ověřili nabyté zkušenosti z kurzu.

Člen

Zobrazeno 8 zpráv z 8.
//= Settings::TRACKING_CODE_B ?> //= Settings::TRACKING_CODE ?>
V předchozím kvízu, Online test znalostí C++, jsme si ověřili nabyté zkušenosti z kurzu.
Můžeš zkusit rozepsat třeba do instrukcí:
lea rcx, [tabulka]
add r10d, [rcx + 4*rax]
Je třeba si ohlídat použití těch správných registrů, abys nepřepsal hodnotu některého. Nebo se podívej, jaké všechny varianty instrukce ADD dovoluje (jestli ta tebou použitá dává rozumný smysl pro tvůj účel).
Co se týče té alokace, nech si v případě chyby vypsat chybové kód (GetLastError). Předpokládám, že máš dostatek virtuální paměti (volné), abys mohl směle alokovat 7 GB.
Díky, vyřešil jsem to pomocí:
lea rdi, tabulka
add r10d, [rdi+rax]
S pamětí nemám problém, na notebooku mám 24 GB. Zajímám se o záhadu letu MH370 a v tabulce hledám NOAA bóje. V těch 7 GB je cca 50 mil. řádků dat. Převod GPS souřadnic ve tvaru např. 35,167 na integer číslo 35167 (aby se mi pak snadněji hledalo) trvá cca 0,8 sekundy. Načtení dat pomocí funkce ReadFile na 3x (počet byte pro čtení je bohužel jen DWORD) trvá z SSD NVMe M.2 disku (seq. čtení a zápis 1800MB/s) pár sekund.
Aha, takže Assemblerem se snažíš dosáhnout vyššího výkonu?
Tady bych spíš šel cestou paralelizace (ten převod půjde krásně dělat vícevláknově, neb jsou to na sobě nezávislé úlohy) a asynchronními operacemi (místo ReadFile použít ReadFileEx a začít data zpracovávat ještě během načítání jejich další části).
Případně pokud bys chtěl "načíst" těch 7 GB dat najednou (je to ale spíše taková iluze), tak CreateFileMapping, MapViewOfFile.
Jasně, jde mi o maximální rychlost. Se souborem, jako externím zdrojem dat, pracuji běžně v Excelu pomocí Power Query. Načtení a vyhledání ale trvá několik minut.
Funkce, zmíněné výše, mi ale asi moc nepomohou, neumí najednout načíst více dat než DWORD (32 bit) dat, takže bych je musel také volat opakovaně (3x pro 6 201 216 875 bytů, Funkce ReadFile umí najednou načíst max. 2 501 566 399 bytů).
Funkce, zmíněné výše, mi ale asi moc nepomohou, neumí najednout načíst více dat než DWORD (32 bit) dat, takže bych je musel také volat opakovaně (3x pro 6 201 216 875 bytů, Funkce ReadFile umí najednou načíst max. 2 501 566 399 bytů).
Jestli se dívám dobře do dokumentaci CreateFileMapping a MapViewOfFile dokáží pracovat dobře i se soubory většími než 4 GB (DWORD). V podstatě ti namapují celý soubor do paměti, takže pak s ním můžeš pracovat stejně, jako bys jej předtím do té paměti načetl manuálně přes ReadFile. Trik je v tom, že vlastní načítání do paměti provádí jádro systému, když o ta data požádáš (přistoupíš na příslušnou paměťovou oblast).
Co se týče ReadFileEx, máš pravdu v tom, že jej pořád budeš muset volat několikrát (limit na ty 2 GB). Myslel jsem to ale tak, že bys postupoval následovně:
Cíl je zaměstnat procesor i v době, kdy načítáš data z disku (a procesor tak nemá co na práci). Samozřejmě je otázka, zda-li to vzhledem k tvé úloze můžeš udělat.
Naprogramovat to správně ale není úplně jednoduché. Mám na těchto
asynchronních čteních a zápisech založenou jednu moji utilitu (zatím není
na GitHubu) pro práci s disky a ještě tam s tím mám nějaké problémy .
Díky za tipy, podívám se na to. V C++ jsem začal programovat asi před
týdnem. Před x lety mě moc bavilo programovat MOS 6502 v Commodore 64, v
assembleru jsem dělal grafické funkce .
Je otázkou, zda by paralerní programování věc nějak zásadně
urychlilo. Pro hlavní smyčku (50 mil. řádků o délce 125 bytů) používám
RCX a instrukci loop. Jako pomocné proměnné používám pouze registry
i7-7500u. Z MOS 6502 a kalkulačky HP-41CV (obrácená polská logika) jsem
zvyklý psát kód úsporně .
Našel jsem zajímavý článek Mapped Files give very fast access to huge amounts of data
Zobrazeno 8 zpráv z 8.