Probleme mit erstellen von Threads
-
Weil ich im Moment gerade mit Sockets arbeite möchte ich nun
Threads benutzen um den accept freeze zu umgehen.
Dazu habe ich erst einmal nen Tutorial angeschaut und
mir ein BSP Projekt zusammengestellt.Allerdings bekommen ich immer folgende Fehlermeldung:
[C++ Error] qc.h(27): E2034 Cannot convert 'unsigned long (*)(void *)' to 'unsigned long (__stdcall *)(void *)' [C++ Error] qc.h(27): E2342 Type mismatch in parameter 'lpStartAddress' (wanted 'unsigned long (__stdcall *)(void *)', got 'unsigned long (*)(void *)')
Gleich mal bei Google eingegeben und auch was gefunden.
Leider verstehe ich den Lösungsansatz nicht ganz.Soweit ich das verstanden habe muss ich meine Funktionen aufbestimmte weise
declarieren und definieren:Meine Funktionen:
DWORD NewThread(void *param) { return 1; } bool CreateIt() { CreateThread(NULL,0,NewThread,0,0,NULL); return true; }
Ich sollte die NewTread() Funktion irgendwie als static deklarieren.
Nun wieß ich aber nicht genau wie(die Funktionen sollen bei in einer Klasse sein).
1.Wie muss ich die Funktionen deklarieren und definieren damit der Code
funktioniert?
2.Was macht eine static Variable nochmal genau?(bleib nach dem "Ableben einer Funktion" erhalten????)Thx schonmal
MFG
Ace
-
Dene Threadfunktion muss vom Typ stdcall sein!
DWORD __stdcall NewThread(void *param)
-
Wenn Du die CRT verwendest solltest Du besser _beginthread(ex) verwenden; dann wird beim beenden des Threads der Speicher (welcher von der CRT intern allokiert wird) auch wieder automatisch aufgeräumt...
PS: Anstelle von __stdcall würde ich WINAPI verwenden (wie in der Doku erwähnt...) so gibt es ab x64 z.B. gar kein __stdcall mehr
-
so gibt es ab x64 z.B. gar kein __stdcall mehr
Ich hoffe es wird dann einfach nur ignoriert vom 64-Bit Compiler.
MfG,
Ranner
-
Problem ist immer noch da:
Ich denke ich benutze irgendwo falsche typen oder so aber
ich weiß nicht was der fehler genau ist:
Hier mal meine Klasse:class All { public: DWORD WINAPI NewThread(void *param) { return 1; } bool Create() { CreateThread(NULL,0,NewThread,0,0,NULL); return true; } };
Hat es vllt was damit zu tun, dass Create() keine Zugriffrechte besitz??
MFG
Ace
-
makro-auflöser schrieb:
so gibt es ab x64 z.B. gar kein __stdcall mehr
Ich hoffe es wird dann einfach nur ignoriert vom 64-Bit Compiler.
MfG,
RannerIch poste nie solche Idiotie, unterlasse es mit dem Namen eines Großen zu unterschreiben, Kleiner.
MfG,
Ranner
-
So wie es aussieht, solltest du die Thread-Funktion ausserhalb der Klasse deklarieren.
-
Du brauchst die Thread-Methode nicht ausserhalb der Klasse zu definieren; sondern einfach nur innerhalb der Klasse ein "static" davorzuschreiben!
-
makro-auflöser schrieb:
so gibt es ab x64 z.B. gar kein __stdcall mehr
Ich hoffe es wird dann einfach nur ignoriert vom 64-Bit Compiler.
MfG,
RannerLaut einem Artikel den ich im MSDN Magazin gelesen habe soll das so sein
Ehrlich gesagt finde ich es gut, dass das dann ignoriert wird und das es nur noch eine Art der Aufrufkonvention gibt.
Es gibt damit einige Bugs weniger die durch vergessenes Angeben der Aufrufkonvention aufgetreten sind.
Ich hab da auch gelesen das die Aufrufkonvention auf dem x86_64 dann der __fastcall Aufrufkonvention ähneln soll.
BR
-
AceKiller73 schrieb:
Problem ist immer noch da:
Ich denke ich benutze irgendwo falsche typen oder so aber
ich weiß nicht was der fehler genau istDu übergibst eine Funktion vom Typ
DWORD WINAPI (All::*)(void*)
CreateThread erwartet aber eine Funktion mit folgender Signatur
DWORD WINAPI ThreadProc(void*)
Denk nochmal darüber nach, dann wird dir schnell klar, warum es nicht funktioniert.
-
Probier es mal so:
class All { public: static DWORD WINAPI NewThread(void *param) { return 1; } bool Create() { CreateThread(0,0,reinterpret_cast<LPTHREAD_START_ROUTINE>(&All::NewThread),0,0,0); return true; } };
BR
-
Ranner schrieb:
makro-auflöser schrieb:
so gibt es ab x64 z.B. gar kein __stdcall mehr
Ich hoffe es wird dann einfach nur ignoriert vom 64-Bit Compiler.
MfG,
RannerIch poste nie solche Idiotie, unterlasse es mit dem Namen eines Großen zu unterschreiben, Kleiner.
MfG,
RannerTja die Idiotie ist aber keine. :p
-
Einen Cast nach LPTHREAD_START_ROUTINE braucht man nie!!
-
Und den Zeiger auf die Thread-ID würde ich auf jeden Fall übergeben damit es nicht unter Windows 98 abstürzt.
-
....... schrieb:
Einen Cast nach LPTHREAD_START_ROUTINE braucht man nie!!
Wenn man keinen Bock auf langweilige Warnungen hat schon
BR
-
Wenn ohne den Cast Warnungen kommen hast du was falsch gemacht.
-
Hmm ok. Ich gebs zu, ich habe mich getäuscht *fg*
Ich habs grad mal getestet.
*g*
BR
-
Also bei mir kommen da keine Warnungen:
#include <windows.h> class Foo { static DWORD WINAPI Bar(LPVOID pData) { return 0; } void StartThread() { DWORD dwThreadId; CreateThread(NULL, 0, Bar, NULL, 0, &dwThreadId); } };
Aber wie gesagt> Besser w're>
#include <process.h> class Foo { static void Bar(void* pData) { } void StartThread() { _beginthread(Bar2, 0, NULL); } };
-
Jochen Kalmbach schrieb:
Also bei mir kommen da keine Warnungen:
#include <windows.h> class Foo { static DWORD WINAPI Bar(LPVOID pData) { return 0; } void StartThread() { DWORD dwThreadId; CreateThread(NULL, 0, Bar, NULL, 0, &dwThreadId); } };
Ich hab ja gesagt das ich mich getäuscht habe
BR
-
evilissimo schrieb:
Ich hab ja gesagt das ich mich getäuscht habe
Sorry! Ich hab Dich dann falsch verstanden...