Handhabung sehr großer Datenmengen



  • Skysnake schrieb:

    Hier der Code-Ausschnitt der relevant ist:

    #include <iostream>
    
    #include <vector>
    #include <utility>
    
    #define alloca _alloca
    #define __NO_STD_VECTOR //Use cl::vektor instead of STL version
    
    #include <functional>
    //#include <cstdlib> für rand() eventuell nötig
    
    #include <CL\cl.hpp>
    #include <stdio.h>
    
    using namespace std;
    
    .
    .
    .
    const unsigned int xblockSize=64;
    const unsigned int xblocks	=5;
    
    const unsigned int yblockSize=64;
    const unsigned int yblocks	=5;
    
    const unsigned int xdimension=xblockSize*xblocks;
    const unsigned int ydimension=yblockSize*yblocks;
    
    const unsigned int dimension=ydimension*xdimension;
    
    const unsigned int anzahlBilder=1000;
    
    .
    .
    // nein lieber nicht so machen
                    int * A=new int [ydimension*xdimension*anzahlBilder];
    		int * B=new int [ydimension*xdimension*anzahlBilder];
    		int * C=new int [ydimension*xdimension*anzahlBilder];
    		int * D=new int [ydimension*xdimension*anzahlBilder];
    
    //
    
    std::vector<int> A(ydimension*xdimension*anzahlBilder);
    std::vector<int> B(ydimension*xdimension*anzahlBilder);
    std::vector<int> C(ydimension*xdimension*anzahlBilder);
    std::vector<int> D(ydimension*xdimension*anzahlBilder);
    .
    .
    .
    

    Fürs erste langen 500MB an Daten aus, also das was oben initialisiert werden soll. Wenn ihr ne Lösung für Arrays mit Daten >1GB habt, bin ich auch sehr aufgeschlossen. Wichtig ist halt nur, das wirklich alles im RAM hab und die Datenpackete nicht kleiner als 100k Einträge haben sollen.

    Du solltest statt der einfachen C Felder lieber std::vector nehmen, da so auch sauber der Speicher verwaltet wird. Es gibt keine Nachteile und man kann einen std::vector immer als Ersatz für ein C Feld verwenden.

    Zur Problematik der Feldgröße: als 64Bit Applikationen übersetzen und passenden Rechner nutzen.



  • Du mußt mal schreiben, ob du ein 32 Bit oder 64 Bit system nutzt. Auf 64 Bit Systemen wäre es, wie ~John gerade bemerkte, kein Problem mit passendem Rechner, da dir insgesamt auf aktueller Hardware/aktuellem OS 8192 GB virtueller Speicher zur Verfügung stehen. Auf 32 Bit Systemen kannst du im PE-Header ein Flag setzen, so dass dir zumindest 3 GB virtueller Speicher gewährt wird. Das OS nimmt dann nur noch 1GB für sich in Anspruch.



  • is 64 bit, mit 4GB realem Ram. Ich schreibs hier nochmal rein, der edit geht sicher utner.

    ich schau mir das mit dem <vector> nochmal an.

    EDIT: habs mir nochmal unter http://www.cplusplus.com/reference/stl/vector/ angeschaut. Jetzt ist mir auch wieder klar, warum ichs nicht vorher eingesetzt hab. Ich steig da nicht so 100% durch 😃



  • Ernst gemeinter Ratschlag: Geh morgen mal in die Uni-Bibiothek und leih' dir ein richtig gutes Buch über C++ aus.
    Das kann bspw. "Die C++ Programmiersprache" (original "The C++ Programming Language" 🤡 ) von Bjarne Stroustrup sein. Dieses Buch kann ich wirklich empfehlen.
    Alternativ soll auch der C++ Primer sehr gut sein (nicht gelesen).
    In die STL solltest du dich wirklich einarbeiten, sie hilft dir bei sehr vielen Dingen ungemein!



  • Nur so interessehalber ... wie groß ist denn dein GPU Speicher?



  • machts aber nicht unbedingt einfacher wie ich bisher die Erfahrung gemacht hab.

    mit <vector> kann ich jetzt z.B. toll den Speicher initialisieren und füllen, aber meine Übergabe an die OpenCL Funktion geht nicht mehr, und wird wie ich befürchte auch nicht so einfach werden, da ich nicht den entsprechenden Pointer so einfach übergeben kann

    Ist folgender Funktionsaufruf:

    cl_mem clCreateBuffer  (      cl_context context,
          cl_mem_flags flags,
          size_t size,
          void *host_ptr,
          cl_int *errcode_ret)
    

    Ich schau mal ob ich den entsprechenden Pointer find.

    Was das Buch angeht, so hab ich hier son Welzer liegen, hilft mir aber für die Sachen die ich such im Allgemeinen auch nicht weiter. Mit Speziallösungen etc. kann ich nicht soo viel anfangen, denn ich nutz C++ nur als Zwischenmedium für OpenCL. Daher würd ich gern die Gleichen Funktionen sowohl im C++ Teil als auch im OpenCL kernel verwenden. Falls es aber wirklich nicht anders geht, muss ich halt alles in RAM laden und dann kleinere Anteile halt an meinen OpenCL Kernel übergeben, was ja auch ohne Probleme für (5*64)*(5*65)*5 Bilder geklappt hat.

    EDIT: 1Gb ist der Ram groß von dem atm nur 512 ohne Tricks genutzt werden können. Mit tricks 800MB rum. Was mir grad aufzeigt, das ich atm zu groß bin -.- Hatte noch die 16 bit die ich erstmal nur brauch noch im Kopf 😕

    Damit wirds etwas zu groß. Willte eigentlich den Stack von 2k Bildern auf A und B aufteilen, so das es zu keinen Speicherüberschneidungen kommt, aber muss ich dann wohl jetzt nochmal schauen, ob ichs nicht vielleicht in Blöcke a 250 Bilder aufteile oder so.



  • Jetzt habe ich aber selber mal eine Frage. Warum crasht das Porgramm unter win64?
    Der Memory-Manager von Windows kann doch die angeforderten ~1.6 GB bei dem System direkt in den physischen Speicher mappen (4 GB sind ja vorhanden), ohne überhaupt dran denken zu müssen, irgend etwas zurück auf Disk zu pagen ?



  • Ok, hab mal noch nen bischen rumprobiert.

    (5*64)*(5*64)*250 geht, das von der größe dann auch absolut ok, dann kann ich genug Bilder laden um damit lang genug arbeiten zu können vorm nächsten Speicherzugriff und hab eventuell auch noch genug Zeit um zwischen drin mit den Daten auch was auf der CPU arbeiten zu lassen, bevor die anderen Teile fertig sind.

    Und insgesamt kann ich alle Daten wenn ich will dann ja mit dem <vector> speichern.

    Sauber Leute, mein Problem scheint erstmal gelöst zu sein 😃 👍

    Zumindest so lange, Bilder von zwei Kameras gleichzeitig ankommen und das dann wohl auch noch in höherer Auflösung 🙄

    EDIT: Ich schau dann aber wohl wenns zeitlich langt, das ich gleich auf ne 64 bit Anwendung umsattel, damits für die Zukunft nicht doch noch zu Engpässen kommt.



  • Hi,

    Ich weiss jetzt nicht, ob das Problem noch fuer dich von Relevanz ist, aber eigentlich garantiert vector, dass die Daten im Speicher linear abgelegt werden:
    [quote="C++ Referenz von dieser Seite hier"]Just as regular arrays, vector containers have their elements stored in contiguous storage locations, which means that their elements can be accessed not only using iterators but also using offsets on regular pointers to elements.[/cpp]
    Also sollte &A.front() als Zeiger doch eigentlich funktionieren fuer deine Grafikbibliotheksfunktion und damit kannst Du alles in vectoren speichern, sowohl temporaer als auch auf laengere Sicht. Aber ohne Gewaehr, ob ich irgendwas uebersehe.



  • Skysnake schrieb:

    machts aber nicht unbedingt einfacher wie ich bisher die Erfahrung gemacht hab.

    mit <vector> kann ich jetzt z.B. toll den Speicher initialisieren und füllen, aber meine Übergabe an die OpenCL Funktion geht nicht mehr, und wird wie ich befürchte auch nicht so einfach werden, da ich nicht den entsprechenden Pointer so einfach übergeben kann

    Ein std::vector erlaubt es, daß man die Adresse des ersten Elements übergibt.

    std::vector<int> A(5000);
    
    int* p = &A[0]
    

  • Mod

    @Eisflamme:
    Ja, da hast du vollkommen recht. Diese Klausel im Standard sorgt dafür, dass vector und dynamisches Array vollkommen äquivalent ist und die Adresse des ersten Vectorelementes so benutzt werden kann wie die Adresse eines dynamischen Arrays. Außer bei dem berüchtigten vector<bool> bei dem sich das Standardkomitee bis heute ärgert diesen überhaupt eingeführt zu haben.

    (Rein theoretisch erlaubt es der Standard auch, dass die Vectorelemente rückwärts im Speicher angeordnet sind. Dies macht aber keine einzige Implementierung so und wird sicherlich auch niemals eine machen. Darauf sollte man keine Rücksicht nehmen. Im neuen Standard wird (soweit ich weiß) auch dies ausgeschlossen)



  • ~john schrieb:

    Ein std::vector erlaubt es, daß man die Adresse des ersten Elements übergibt.

    std::vector<int> A(5000);
    
    int* p = &A[0]
    

    Hey vielen Dank, das sieht ziemlich genau nach der Lösung für mein Problem mit der Übergabe an die OpenCL-Funktion aus 👍


Anmelden zum Antworten