View Full Version : [C] Programma multi-thread
Marinelli
23-05-2005, 13:23
Buongiorno a tutti.
Mi interesserebbe creare un programma che utilizza due thread per eseguire dei calcoli, in modo da sfruttare l'HT del P4. Premetto che lavoro sotto Windows e in genere compilo con il Dev-C++, ma posso anche utilizzare il MS Visual Studio 6. Quali funzioni mi permettono di fare ciò? Qualcuno potrebbe spiegarmi?
In alternativa mi interesserebbe sapere come poter allocare della memoria condivisa, utilizzabile (lettura/scrittura) da due processi diversi.
Vi ringrazio molto. :)
Alberto.
Cecco BS
23-05-2005, 18:19
up! Interessa pure me! ;)
beppegrillo
23-05-2005, 19:04
Per i thread sotto winzozz, mi pare esiste una libreria chiamata fiber.
Però non posso esserti molto d'aiuto, non l'ho mai utilizzata. :)
Buongiorno a tutti.
Mi interesserebbe creare un programma che utilizza due thread per eseguire dei calcoli, in modo da sfruttare l'HT del P4. Premetto che lavoro sotto Windows e in genere compilo con il Dev-C++, ma posso anche utilizzare il MS Visual Studio 6. Quali funzioni mi permettono di fare ciò? Qualcuno potrebbe spiegarmi?
In alternativa mi interesserebbe sapere come poter allocare della memoria condivisa, utilizzabile (lettura/scrittura) da due processi diversi.
Vi ringrazio molto. :)
Alberto.
carissimo omonimo, :D
usi il PSDK? hai a disposizione gli headers delle Win32? allora è facilissimo! per creare un nuovo thread chiama la CreateThread, e non ti spaventare per tutti quei parametri: per alcuni va bene anche se passi 0 o NULL, e vengono settati i parametri di default (ad esempio, non preoccuparti della dimensione dello stack, degli attributi di sicurezza, ecc.). una volta creato, il nuovo thread inizierà la sua esecuzione da un entry point da te definito, ovverosia una funzione nella forma: DWORD WINAPI ThreadProc(LPVOID lpParameter) dove naturalmente "ThreadProc" è il nome che tu sceglierai per la funzione, e "lpParameter" è un parametro che puoi usare a tuo piacimento per passare dati al thread; essendo un puntatore, solitamente è una variabile da 4 byte che il programmatore fa puntare ad una struttura dati contenente (se necessarie, altrimenti il parametro può anche rimanere inutilizzato) alcune informazioni usate dal nuovo thread. per il prototipo della CreateThread e per ulteriori dettagli ti rimando alla libreria MSDN (qui (http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dllproc/base/createthread.asp); è meglio se la vedi con IE perché con FF il frame laterale si vede male; purtroppo è così ^^).
ciao ;)
Per i thread sotto winzozz, mi pare esiste una libreria chiamata fiber.
ehm... non c'entrano niente ^^
beppegrillo
23-05-2005, 19:57
ehm... non c'entrano niente ^^
Si in effetti mi sà che mi sono confuso :D
Marinelli
23-05-2005, 20:29
carissimo omonimo, :D
usi il PSDK? hai a disposizione gli headers delle Win32? allora è facilissimo! per creare un nuovo thread chiama la CreateThread, e non ti spaventare per tutti quei parametri: per alcuni va bene anche se passi 0 o NULL, e vengono settati i parametri di default (ad esempio, non preoccuparti della dimensione dello stack, degli attributi di sicurezza, ecc.). una volta creato, il nuovo thread inizierà la sua esecuzione da un entry point da te definito, ovverosia una funzione nella forma: DWORD WINAPI ThreadProc(LPVOID lpParameter) dove naturalmente "ThreadProc" è il nome che tu sceglierai per la funzione, e "lpParameter" è un parametro che puoi usare a tuo piacimento per passare dati al thread; essendo un puntatore, solitamente è una variabile da 4 byte che il programmatore fa puntare ad una struttura dati contenente (se necessarie, altrimenti il parametro può anche rimanere inutilizzato) alcune informazioni usate dal nuovo thread. per il prototipo della CreateThread e per ulteriori dettagli ti rimando alla libreria MSDN (qui (http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dllproc/base/createthread.asp); è meglio se la vedi con IE perché con FF il frame laterale si vede male; purtroppo è così ^^).
ciao ;)
Ciao! Grazie mille per la risposta... :)
Dunque, non utilizzo il PSDK e non so se ho a disposizione gli headers delle Win32, ma suppongo di sì visto che ho il MS Visual Studio 6. Proverò a guardare al sito MSDN. Ma con CreateThread e compagnia posso compilare solo con il Visual Studio? Altri compilatori non funzionano?
Quindi dei parametri quello importante è lpStartAddress vero? Mi sfugge però il concetto di puntatore a funzione...
Ciao e grazie mille, omonimo ;)
lombardp
23-05-2005, 21:37
Si in effetti mi sà che mi sono confuso :D
Qualcosina potrebbero entrarci... se non ricordo male le fiber sono state introdotte con WindowsNT è sono praticamente come i thread, ma con grana minore. Per capirsi, a grana via via minore ci sono i processi, i thread e le fiber.
...spero di non ricordare male.
Ciao! Grazie mille per la risposta... :)
Dunque, non utilizzo il PSDK e non so se ho a disposizione gli headers delle Win32, ma suppongo di sì visto che ho il MS Visual Studio 6. Proverò a guardare al sito MSDN. Ma con CreateThread e compagnia posso compilare solo con il Visual Studio? Altri compilatori non funzionano?
Quindi dei parametri quello importante è lpStartAddress vero? Mi sfugge però il concetto di puntatore a funzione...
Ciao e grazie mille, omonimo ;)
anche il Dev-cpp ha inclusi gli header e le librerie (il SDK appunto) per usare le winapi et similia, quindi anche CreateThread :)
Ciao! Grazie mille per la risposta... :)
Dunque, non utilizzo il PSDK e non so se ho a disposizione gli headers delle Win32, ma suppongo di sì visto che ho il MS Visual Studio 6.
Ce l'hai ce l'hai...in dev-c++ è inclusa tutto il Win32 SDK...
Qualcosina potrebbero entrarci... se non ricordo male le fiber sono state introdotte con WindowsNT è sono praticamente come i thread, ma con grana minore. Per capirsi, a grana via via minore ci sono i processi, i thread e le fiber.
...spero di non ricordare male.
si, in un certo senso è così: i fibers sono dei thread schedulati non dal sistema operativo, ma dal programma stesso; alla fine MSDN stessa dice che si usano abbastanza raramente: quasi sempre un programma che anziché i fibers usa i thread è ugualmente efficiente.
Ciao! Grazie mille per la risposta... :)
Dunque, non utilizzo il PSDK e non so se ho a disposizione gli headers delle Win32, ma suppongo di sì visto che ho il MS Visual Studio 6. Proverò a guardare al sito MSDN. Ma con CreateThread e compagnia posso compilare solo con il Visual Studio? Altri compilatori non funzionano?
Quindi dei parametri quello importante è lpStartAddress vero? Mi sfugge però il concetto di puntatore a funzione...
Ciao e grazie mille, omonimo ;)
se hai il Visual Studio è praticamente sicuro che hai il PSDK; mi sa che ce l'hai ma non sapevi che si chiamasse così :p
il PSDK (Platform SDK) è costituito dagli headers e i lib delle Win32 e spesso anche da una versione offline della libreria MSDN (con tanto di esempi non compilati). se in Visual Studio puoi includere windows.h senza errori, allora ce l'hai ;)
un puntatore a funzione non è niente di speciale, è esattamente quello che il nome lascia ad intendere: un puntatore che punta alla prima istruzione della funzione (o talvolta, ad un JMP che rimanda immediatamente alla prima istruzione). CreateThread vuole il puntatore all'entry point per sapere dov'è che deve iniziare l'esecuzione del thread.
per ottenere un puntatore a una funzione devi scrivere semplicemente il nome della funzione senza parametri, cioè se scrivi così ThreadProc(NULL) è una chiamata a una funzione, se scrivi così ThreadProc è un puntatore a funzione; talvolta si scrive anche così &ThreadProc che è la stessa cosa.
ciao
Marinelli
24-05-2005, 21:29
Vi ringrazio per le numerose e utili risposte, appena ho un attimo di tempo faccio due prove e poi vi faccio sapere ;)
In realtà cmq non compilerò con il Dev-C++ ma con il compilatore Intel (anch'esso non dovrebbe avere problemi, spero ;))
Ciao :)
In realtà cmq non compilerò con il Dev-C++ ma con il compilatore Intel grande, abbiamo già due cose in comune :D
(anch'esso non dovrebbe avere problemi, spero ;)) anzi!!! ;)
Marinelli
24-05-2005, 23:59
Direi di essere riuscito con successo a creare il thread. Ora però ho un problema: a me interessa che il ciclo che c'è nel main termina, il thread termini oppure quando il ciclo che c'è nel thread termina il main termini. Allora ho pensato: creo una bella variabile globale, quando uno dei due cicli termina questa viene messa a 1 e fa terminare l'altro. Ok, il trucco funziona se compilo il codice con il Dev-C++, invece non funziona (ovvero la variabile globale non viene modificata al di fuori del thread o del main) se uso il compilatore Intel.
Qualche idea?
Grazie mille! :)
Strano...dovrebbe funzionare tranquillamente...
Prima di tutto se metti la var a 1 dal main per far terminare il thread devi mettere una WaitForSingleObject....
WaitForSingleObject(hThread, INFINITE);
In questo modo, se il main termina prima il ciclo...attende che sia terminato il thread prima di terminare (altrimenti il thread viene terminato nel punto in cuis i trova)... hThread è l'HANDLE ritornaro da CreateThread...
Ora...problema della variabile che non cambia non mi è mai successo...non so cosa dirti...
Direi di essere riuscito con successo a creare il thread. Ora però ho un problema: a me interessa che il ciclo che c'è nel main termina, il thread termini oppure quando il ciclo che c'è nel thread termina il main termini. Allora ho pensato: creo una bella variabile globale, quando uno dei due cicli termina questa viene messa a 1 e fa terminare l'altro. Ok, il trucco funziona se compilo il codice con il Dev-C++, invece non funziona (ovvero la variabile globale non viene modificata al di fuori del thread o del main) se uso il compilatore Intel.
Qualche idea?
Grazie mille! :)
hmmm, fa vedere il codice. comunque da me questa cosa col compilatore Intel funziona perfettamente: #include <stdlib.h>
#include <stdio.h>
#include <time.h>
#include <windows.h>
BOOL fQuit = FALSE;
BOOL DoSomething() {
srand(time(NULL));
if (rand() >= RAND_MAX / 2) {
return FALSE;
}
return TRUE;
}
DWORD WINAPI OtherThread(LPVOID lpParameter) {
while (!fQuit) {
if (!DoSomething()) {
fQuit = TRUE;
}
}
return 0;
}
int main() {
DWORD dwDummy;
HANDLE hOtherThread = CreateThread(NULL, 0, OtherThread, NULL, 0, &dwDummy);
while (!fQuit) {
if (!DoSomething()) {
fQuit = TRUE;
}
}
WaitForSingleObject(hOtherThread, INFINITE);
system("pause");
return 0;
}
Marinelli
25-05-2005, 00:25
Questo è il codice sfoltito da tutto ciò che non riguardava il problema:
#include <stdio.h>
#include <math.h>
#include <windows.h>
#include <stdlib.h>
#ifdef _WIN32
#include <sys/timeb.h>
#include <sys/types.h>
#include <winsock.h>
void gettimeofday(struct timeval* t,void* timezone)
{ struct _timeb timebuffer;
_ftime( &timebuffer );
t->tv_sec=timebuffer.time;
t->tv_usec=1000*timebuffer.millitm;
}
#endif
int stop=0;
DWORD WINAPI ThreadProc( LPVOID lpParam )
{
//dichiarazioni locali
while (!ferma2)
{
//ciclo
if (stop==1) return(0);
}
stop=1;
//istruzioni di fine programma
return (0);
}
int main ()
{
//dichiarazioni locali
CreateThread(NULL, 0, ThreadProc, NULL, 0, NULL);
while (!ferma)
{
//ciclo
if (stop==1) return(0);
}
stop=1;
//istruzioni di fine programma
return (0);
}
Ciao e grazie :)
Questo è il codice sfoltito da tutto ciò che non riguardava il problema:
[...]
Ciao e grazie :)
be', intanto la WaitForSingleObject alla fine ce la devi mettere perché se esci dal thread primario termina tutto il processo e quindi anche l'altro thread :)
poi non so :mbe: a me sembra che dovrebbe andare :mbe:
potrebbe trattarsi (ma ne dubito) di qualche ottimizzazione del compilatore; prova a visualizzare l'assembly quando fai il debug (Alt+8) e controlla che entrambi i thread usino la variabile in RAM e non un registro; per fare il debug di due thread però devi impostare le informazioni di debug per il multithreading, altrimenti il Visual Studio in certi casi ti si pianta (mi è successo: diventava lentissimo).
Marinelli
25-05-2005, 00:37
be', intanto la WaitForSingleObject alla fine ce la devi mettere perché se esci dal thread primario termina tutto il processo e quindi anche l'altro thread :)
poi non so :mbe: a me sembra che dovrebbe andare :mbe:
Quando termina uno deve terminare anche l'altro... aspettarlo non ha alcuna importanza.
Ho provato anche con delle printf a stampare il valore di stop: quando nel main diventa 1 nel nuovo thread rimane 0... ma non ha senso :(
Ciao, ora vado a nanna che altrimenti domani mattina sono cadavere.
Marinelli
25-05-2005, 00:42
Oh, bella questa... ho provato a compilare con il compilatore intel e nessuna ottimizzazione (-Od come parametro passato al compilatore) e il problema non si presenta. :confused:
Non ci capisco più una cippa :(
Ciao
Oh, bella questa... ho provato a compilare con il compilatore intel e nessuna ottimizzazione (-Od come parametro passato al compilatore) e il problema non si presenta. :confused:
Non ci capisco più una cippa :(
Ciao
allora si trattava proprio di un'ottimizzazione... bah, strano... non dovrebbe farli sti scherzetti (a me non li fa) :mbe:
Marinelli
25-05-2005, 00:47
Infatti... non riesco a capire come mai senza ottimizzazioni funzioni tutto e con le ottimizzazioni funzioni tutto tranne che la variabile globale :confused:
Vediamo se qualcuno riesce ad illuminarci.
Buonanotte e grazie ancora
Infatti... non riesco a capire come mai senza ottimizzazioni funzioni tutto e con le ottimizzazioni funzioni tutto tranne che la variabile globale :confused:
Vediamo se qualcuno riesce ad illuminarci.
Buonanotte e grazie ancora
ovvio, usa un registro anzichè la copia in memoria della variabile (lo puoi verificare col debug; l'avevo scritto un paio di post fa ma forse non l'hai letto perché ho editato successivamente :p)
'notte :)
No...ma che registro...basta una mutex...
No...ma che registro...basta una mutex...
un mutex per proteggere una risorsa da un'operazione atomica? :)
No...usarla...al posto dell'operazione atomica ;)
Ma per registro tu cosa intendevi ?
No...usarla...al posto dell'operazione atomica ;) non capisco in che senso :mbe:
Ma per registro tu cosa intendevi ? come cosa intendevo? sugli x86 eax, ebx, ecx, edx, esi, edi...
non capisco in che senso :mbe:
come cosa intendevo? sugli x86 eax, ebx, ecx, edx, esi, edi...
Ma figuarti cosa avevo capito !!!! Avevo capito che gli dicevi di mettere un valore nel registro di Windows...
Comunque quell'ottimizzazione è assurda...anche usando un registro dovrebbe prevedere la memoria è condivisa...
Comunque ora ripensandoci si può fare con la sola WaitForSingleObject... Nel main si fa una WaitForSingleObject sul thread con attesa zero...se il thread è terminato (WAIT_OBJECT_0) allroa si fa terminare anche il main... Se termina il main si richiama TerminateThread oppure si usa qualche altro meccanismo per far terminare il thread più "delicatamente"...
Marinelli
25-05-2005, 12:36
Ciao, dunque sono andato a sbirciare la mutex sulla MSDN, ma ci ho capito poco... ok, posso provare con la WaitForSingleObject e la TerminateThread... vediamo se riesco a fare qualcosa :)
Vi tengo aggiornati ;)
Marinelli
25-05-2005, 13:06
Dunque, se ho capito bene... nel ciclo della main devo inserire un:
if (WAIT_OBJECT_0==WaitForSingleObject(hThread, 0)) return (0);
e in fondo alla main devo inserire un:
TerminateThread(hThread, dwExitCode);
In entrambi hThread è l'handle al thread creato in precedenza... invece non capisco a cosa serva dwExitCode.
Il problema è che inserendo la WaitForSingleObject nel ciclo di calcolo vengono ridotte moltissimo le prestazioni.
Qualche idea? ;)
Dunque, se ho capito bene... nel ciclo della main devo inserire un:
if (WAIT_OBJECT_0==WaitForSingleObject(hThread, 0)) return (0);
e in fondo alla main devo inserire un:
TerminateThread(hThread, dwExitCode);
In entrambi hThread è l'handle al thread creato in precedenza... invece non capisco a cosa serva dwExitCode.
Il problema è che inserendo la WaitForSingleObject nel ciclo di calcolo vengono ridotte moltissimo le prestazioni.
Qualche idea? ;)
none, non ci siamo :p
guarda il mio esempio: al limite usa quello per iniziare e inserisci il codice nella funzione DoSomething. la WaitForSingleObject va inserita alla fine della main e serve semplicemente per aspettare che l'altro thread sia compleamente terminato (dal momento che i thread terminano più o meno insieme, alla fine la WaitForSingleObject non sarebbe neanche necessaria tutto sommato).
la TerminateThread invece non la devi usare: serve a terminare un thread "brutalmente" senza tante storie mentre sta lavorando; nel tuo caso non credo che serva; comunque dwExitCode era semplicemente il codice d'uscita che doveva essere assegnato al thread dopo che questo era terminato; corrisponde esattamente al codice che viene ritornato dalla ThreadProc in casi di terminazione "normale", e può essere ritrovato da altri thread con GetExitCodeThread.
inoltre il mutex secondo me non serve perché scrivere in una variabile a 32 bit sui processori d'oggi è un'operazione atomica, cioè è impossibile che mentre un thread scrive l'altro vada a leggere i dati scritti "a metà" perché un'operazione atomica non può essere interrotta da nessuna interrupt e quindi non può essere interrotta dal multithreading del sistema operativo.
Cavolo...ti prende così tanta CPU ?
In che percentuale rallenta ? Hai rimesso le ottimizzazioni dopo ?
inoltre il mutex secondo me non serve perché scrivere in una variabile a 32 bit sui processori d'oggi è un'operazione atomica, cioè è impossibile che mentre un thread scrive l'altro vada a leggere i dati scritti "a metà" perché un'operazione atomica non può essere interrotta da nessuna interrupt e quindi non può essere interrotta dal multithreading del sistema operativo.
Sono d'accordo...ma non è questo il punto... Credo che lui volesse trovare un rimedio alla questione della variabile che non viene aggiornata nell'altro thread...cosa che tra l'altro mi sembra assurda...
Sono d'accordo...ma non è questo il punto... Credo che lui volesse trovare un rimedio alla questione della variabile che non viene aggiornata nell'altro thread...cosa che tra l'altro mi sembra assurda...
ma aveva detto che aveva risolto anche col compilatore intel disabilitando le ottimizzazioni, dal che era evidente che il compilatore chissà perché andava ad usare un registro anziché la copia originale in memoria della variabile.
Alberto, ma hai verificato questa ipotesi col debug?
Ma se cerca il massimo delle prestazioni mi sa che vuole abilitare nuovamente le opzioni di compilazione...
Mi verrebbe in mente una soluzione stupida in assembly, ma non mi sembra il caso...
Marinelli
25-05-2005, 15:26
none, non ci siamo :p
guarda il mio esempio: al limite usa quello per iniziare e inserisci il codice nella funzione DoSomething. la WaitForSingleObject va inserita alla fine della main e serve semplicemente per aspettare che l'altro thread sia compleamente terminato (dal momento che i thread terminano più o meno insieme, alla fine la WaitForSingleObject non sarebbe neanche necessaria tutto sommato).
la TerminateThread invece non la devi usare: serve a terminare un thread "brutalmente" senza tante storie mentre sta lavorando; nel tuo caso non credo che serva; comunque dwExitCode era semplicemente il codice d'uscita che doveva essere assegnato al thread dopo che questo era terminato; corrisponde esattamente al codice che viene ritornato dalla ThreadProc in casi di terminazione "normale", e può essere ritrovato da altri thread con GetExitCodeThread.
inoltre il mutex secondo me non serve perché scrivere in una variabile a 32 bit sui processori d'oggi è un'operazione atomica, cioè è impossibile che mentre un thread scrive l'altro vada a leggere i dati scritti "a metà" perché un'operazione atomica non può essere interrotta da nessuna interrupt e quindi non può essere interrotta dal multithreading del sistema operativo.
Credo tu non abbia colto il mio problema... dei due cicli solo uno ottiene un risultato; l'altro potrebbe andare in loop infinito e, le volte che termina, impiega molto più tempo del primo. Quindi a me interessa poter bloccare uno dei due cicli quando l'altro è terminato.
Cavolo...ti prende così tanta CPU ?
In che percentuale rallenta ? Hai rimesso le ottimizzazioni dopo ?
Sì, ciuccia un sacco di tempo... con la versione senza la WaitForSingleObject impiega circa 13 secondi, se invece utilizzo la funzione il problema si risolve ma impiega la bellezza di 73 secondi circa... un'enormità!!!
Sono d'accordo...ma non è questo il punto... Credo che lui volesse trovare un rimedio alla questione della variabile che non viene aggiornata nell'altro thread...cosa che tra l'altro mi sembra assurda...
E' proprio questo che mi interessa ;) e purtroppo sembra assurdo anche a me, ma accade.
ma aveva detto che aveva risolto anche col compilatore intel disabilitando le ottimizzazioni, dal che era evidente che il compilatore chissà perché andava ad usare un registro anziché la copia originale in memoria della variabile.
Alberto, ma hai verificato questa ipotesi col debug?
Dunque, preferirei poter utilizzare le ottimizzazioni ;)
No, non ho ancora verificato, anzi non credo di aver mai effettuato l'operazione in vita mia :p
Ma se cerca il massimo delle prestazioni mi sa che vuole abilitare nuovamente le opzioni di compilazione...
Mi verrebbe in mente una soluzione stupida in assembly, ma non mi sembra il caso...
Ma la tua prima idea sulle mutex (dovresti però spiegarmi come usarle :p) potrebbe risolvere il problema?
Ciao e grazie a tutti ;)
Credo tu non abbia colto il mio problema... dei due cicli solo uno ottiene un risultato; l'altro potrebbe andare in loop infinito e, le volte che termina, impiega molto più tempo del primo. Quindi a me interessa poter bloccare uno dei due cicli quando l'altro è terminato. allora se usi TerminateThread devi anche aprire un handle al thread primario; a dir la verità però io avrei preferito la soluzione che avevi scelto inizialmente (variabile stop); casomai cerca di capire qual'è l'ottimizzazione che devi togliere (tanto le opzioni del compilatore Intel sono uguali a quelle Microsoft documentate in MSDN, quindi basta che cerchi lì).
Marinelli
25-05-2005, 15:48
allora se usi TerminateThread devi anche aprire un handle al thread primario; a dir la verità però io avrei preferito la soluzione che avevi scelto inizialmente (variabile stop); casomai cerca di capire qual'è l'ottimizzazione che devi togliere (tanto le opzioni del compilatore Intel sono uguali a quelle Microsoft documentate in MSDN, quindi basta che cerchi lì).
Certo, infatti ora la CreateThread è così:
hThread=CreateThread(NULL, 0, ThreadProc, NULL, 0, NULL);
Certo, piaceva anche a me quella soluzione, era semplice e funzionerebbe benissimo.
Ora faccio qualche prova con il compilatore, ma ho il brutto presentimento che non caverò ragni dal buco.
Ciao :)
Mi è venuta un'idea...fai così:
int *stop = &a; /*a è un intero*/
Passa alla CreateThread stop come parametro (LPVOID lpParameter)...basta fare un cast: (LPVOID)stop
Nel thread recpera il parametro che è quelo che viene passato alla ThreadProc
DWORD ThreadProc(LPVOID lpParameter)
{
int *stop = (int *)lpParameter;
while(*stop == 0)
{
.....
.....
if(finito) {
*stop == 1;
ExitThread(0);
}
}
}
int main....
{
int a = 0;
int *stop = &a;
hThread = CreateThread.....
while(*stop == 0)
{
.....
.....
if(finito) {
*stop == 1;
ExitThread(0);
}
}
WaitForSingleObject(hThread, INFINITE);
}
E se non funziona così si usa la new per allocare l'intero puntato da stop...
Comunque è un workaround del cacchio questo...
Marinelli
25-05-2005, 16:20
Incredibile... effettivamente passando ad un'ottimizzazione inferiore (da -O3 a -O2) e adattando parte del codice (altrimenti non funziona lo stesso) il problema si risolve. Ma il tutto continua a rimanere un mistero!!! :eek:
Ora provo la tua soluzione :)
Attento che c'è qualche errorino...deve essere così:
DWORD ThreadProc(LPVOID lpParameter)
{
int *stop = (int *)lpParameter;
while(*stop == 0)
{
.....
.....
if(finito)
*stop = 1;
}
return 0;
}
int main....
{
int a = 0;
int *stop = &a;
hThread = CreateThread.....
while(*stop == 0)
{
.....
.....
if(finito) *stop = 1;
}
WaitForSingleObject(hThread, INFINITE);
}
Marinelli
25-05-2005, 16:45
Riccardo... con il passaggio del parametro al thread non riesco a farlo funzionare. Fortuna che ho trovato il modo per riuscirci con la variabile globale e non crederai quando ti dico che, nella condizione di uscita dal ciclo:
if (stop==vero) break;
così funziona...
if (stop==vero) return (0);
così no.
Ora lascio, è meglio che mi vada a fare qualcos'altro... tipo studiare :cry:
Ciao e ancora grazie mille :D
Interessante :doh: Certo che è un comportamento strano forte...
Riccardo...
LOL, cionci si chiama Riccardo :D
piano piano sto scoprendo i nomi di tutto lo staff :D
Marinelli
25-05-2005, 22:43
Interessante :doh: Certo che è un comportamento strano forte...
E' bello riuscire a sorprendere qualcuno molto più esperto di se stessi :D:D:D
Ciao ;)
vBulletin® v3.6.4, Copyright ©2000-2025, Jelsoft Enterprises Ltd.