Frage zu Thread aufruf?



  • @hallobalusa: ne p ist keine lokale kopie..

    @badestrand: hallabusa sagt das eine kope des pointer aufm stack gespeicehrt wird, d.h. wenn der theadentry funktion noch nicht gestartet werden kann, ist ja diekopie trozdem noch da oder irre ich mich... Aber trozdem eine gute idee deine möglichkeit;)



  • while ( ! d->init )
           ;
    

    Na, sowas macht man aber besser mit einer Condition als mit einem Busy-Loop, oder? 😉

    @Boris:
    Ich glaube (glaube, weil ich nicht ganz sicher bin dass wir dasselbe verstehen was Du meinst) das eine hat mit dem anderen wenig zu tun. In dem Moment, wo Du create_thread aufrufst, wird das Argument auf den Stack dieser Funktion kopiert, welche den Thread startet und in dem Thread die Funktion (wieder mit dem Argument auf dem Stack) durchläuft. Das ist bis hierhin noch "normales C(++)" - bei der Betrachtung von Lebenszeiten wird jetzt wichtig, worauf ein dort übergebener Zeiger zeigt, nicht der Zeiger selbst.

    Badestrand wollte Dir glaube ich nur eine Möglichkeit aufzeigen, wie man von der Thread-Funktion aus an den Thread-Ersteller eine Nachricht schicken kann (wobei man das imho lieber über Conditions lösen sollte).



  • Oh ja, ich glaub ich hab die Frage falsch verstanden.. Ich dachte, Funktion A solle weitermachen, wenn B die Daten befüllt hat. Naja, egal.

    Was ich eigentlich wollte:
    Mylord, was meint Er mit Conditions?



  • Badestrand schrieb:

    Was ich eigentlich wollte:
    Mylord, was meint Er mit Conditions?

    Conditions ist ein Threadkontrollmechanismus, der bedingtes Warten ermöglicht. Kurz und bündig (es steckt mehr dahinter, aber das würde zu weit führen) kannst Du damit in Verbindung mit einem Mutex einen oder mehrere Threads in einen Wartezustand schicken, bis ein anderer Threads ihn/sie wieder aufweckt. In Deinem Beispiel sähe das etwa wie folgt aus (Achtung Pseudocode):

    void foo(){
       Condition cond;
    
       cond.lock();
       int code = thread_create(Thread::EntryPoint, (void*) &cond, & ThreadId_);
       cond.unlockAndWait();
       //(A)
    };
    
    void * EntryPoint(void * pthis) {
        Condition* cond = (Condition*) pthis;
    
        cond->lock();
        // mache was, worauf (A) warten muss
        cond->wake_up();
        cond->unlock();
        //(B)
        cond = 0; // FESTLEGUNG: nachdem der Erzeuger aufgeweckt wurde, verschwindet cond aus dem Leben (lokale Variable in (A)) und darf hier nicht mehr benutzt werden!
    }
    


  • ja gut..

    (1) in funktion foo() zeigt p auf ein Objekt im speicher

    (2) bei createthread wird eine kopie des zeigers im stack erstellt.

    (3) foo wird beendet, aber die kopie im stack von createtrhead ist noch da!

    d.h. die entrytrhread funktion hat aufjedenfall einen zeiger auf das objket, obwohl foo schon beendet wurde..

    oder seh ich das falsch?



  • Das siehst Du vollkommen richtig. Allerdings vermute ich Deine Schlussfolgerung ist falsch (was sich aber nicht verifizieren lässt, da Du diese nicht mitteilst 😉 ).



  • meine schlussfolgerung, ich brauch keien conditions, weil der trhead auf jedefall nen gültigen zeiger auf das objekt hat



  • Ok, dann war meine Vermutung inkorrekt.



  • BorisDieKlinge schrieb:

    ja gut..

    (1) in funktion foo() zeigt p auf ein Objekt im speicher

    (2) bei createthread wird eine kopie des zeigers im stack erstellt.

    (3) foo wird beendet, aber die kopie im stack von createtrhead ist noch da!

    d.h. die entrytrhread funktion hat aufjedenfall einen zeiger auf das objket, obwohl foo schon beendet wurde..

    oder seh ich das falsch?

    (3) Stimmt nicht ganz. Die Kopie liegt nicht mehr auf dem Stack, sondern irgendwo wo sie von thread_create gespeichert wurde. Der Stack wird ja nach dem Beenden der Funktion wieder abgeräumt. Du brauchst aber keine Conditions, weil du ja keinen Pointer oder Referenz auf p übergibst, sondern der Wert kopiert wird. Du könntest sogar garnichts machen, weil die Lebenszeit von p garnichts mit der von der Kopie, die beim Funktionsaufruf erzeugt, wird zu tun hat.



  • hallobalusa schrieb:

    (3) Stimmt nicht ganz. Die Kopie liegt nicht mehr auf dem Stack, sondern irgendwo wo sie von thread_create gespeichert wurde.

    Stimmt auch nicht ganz, die Parameter der Funktion EntryPoint liegen natürlich auch wieder auf dem Callstack, nur dass dieser der Stack des neuen Threads ist (den meinte ich zuvor auch) und nicht der Stack des Erzeugers.

    EDIT: Ok, rein technisch stimmt der Satz, da der Stack des neuen Thread auch "irgendwo" liegt 😉



  • ok Jungs... also muss ich jetzt ne condition einbauen oder net??



  • LordJaxom schrieb:

    hallobalusa schrieb:

    (3) Stimmt nicht ganz. Die Kopie liegt nicht mehr auf dem Stack, sondern irgendwo wo sie von thread_create gespeichert wurde.

    Stimmt auch nicht ganz, die Parameter der Funktion EntryPoint liegen natürlich auch wieder auf dem Callstack, nur dass dieser der Stack des neuen Threads ist (den meinte ich zuvor auch) und nicht der Stack des Erzeugers.

    EDIT: Ok, rein technisch stimmt der Satz, da der Stack des neuen Thread auch "irgendwo" liegt 😉

    Genau deshalb hab ich irgendwo geschrieben. Es muss aber auch nicht der Callstack von EntryPoint sein. thread_create kann ja schon wieder beendet sein, vor der andere Thread gestartet wurde. Der Wert könnte irgendwo im Stack oder Heap des Schedulers oder sonst wo sein. Keine Ahnung was das OS da genau macht.

    BorisDieKlinge schrieb:

    ok Jungs... also muss ich jetzt ne condition einbauen oder net??

    nein, nicht für p.



  • d.h. ich habe auf jedefnall ne gültigen zeiger im thread unabhängig wann der thread zum ersteln mal gestartet wird


Anmelden zum Antworten