IdentifiantMot de passe
Loading...
Mot de passe oubli� ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les r�ponses en temps r�el, voter pour les messages, poser vos propres questions et recevoir la newsletter

C++ Discussion :

Code non thread-safe


Sujet :

C++

Vue hybride

Message pr�c�dent Message pr�c�dent   Message suivant Message suivant
  1. #1
    Membre �prouv�
    Profil pro
    Inscrit en
    F�vrier 2007
    Messages
    217
    D�tails du profil
    Informations personnelles :
    �ge : 32
    Localisation : France

    Informations forums :
    Inscription : F�vrier 2007
    Messages : 217
    Par d�faut Code non thread-safe
    Bonjour,

    AVERTISSEMENT: il y a beaucoup de code. Si vous n'avez pas le temps de trop regarder, ce serait sympa de me dire � quoi peut-�tre du un seg fault dans une app multithread�e , je me d�broullerai avec �a.

    POUR CEUX QUI ONT DU TEMPS:
    Je suis entrain de faire une application capable de crypter/d�crypter des messages par courbe elliptique. On m'a conseill� aussi de faire un crackeur par force brute pour montrer que cette m�thode de cryptage est par son concept s�re.
    J'ai fait une classe User<T> repr�sentant une personne souhaitant pouvoir envoyer des messages crypt�s � un autre User qui le d�cryptera. J'ai fait une classe Cracker<T> (nom tr�s recherch� ) d�riv�e de User<T> qui elle intercepte les messages des users et tente de les d�crypter (le pauvre ne sait pas que c'est dur et long)...
    Le crackeur cherche � trouver une cl� secr�te d'un des deux user qu'il surveille. Pour ce faire je le dote de 4 threads supl�mentaires (je pourrais ajouter des centaines de threads si j'avais une machine avec assez de cores et de processeurs)pour l'aider � trouver plus vite.
    Sauf que mon code plante lamentablement sur un seg fault d�s que j'ajoute un crackeur.
    J'ai essay� d'ajouter des blocages/d�blocages de mutex un peu partout dans le code qui acc�de � des membres et je fait des copies de ceux-ci. Mais �a plante toujours.
    J'ai jamais r�ellement touch� aux threads avant ce projet donc je sais pas quoi faire. Le debugueur de VS ne m'est pas super utile en plus (il me rep�re juste le seg fault mais ne me dit pas quel appel l'a provoqu� dans quel thread).

    J'ai fait mes propres classes de thread et de mutex (c'est un imp�ratif) donc le probl�me vient peut-�tre de l�...

    Mon code:
    ZThread.hpp
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
     
    #ifndef ZTHREAD_HPP_INCLUDED
    #define ZTHREAD_HPP_INCLUDED
     
    #include <windows.h>
     
    unsigned __stdcall launcherfunc(void* data);
     
    class ZThread
    {
            friend unsigned __stdcall launcherfunc(void* data);
     
        public:
     
            ZThread();
            ZThread(void* (*ptrFunc)(void*),void* data=NULL);
     
            virtual ~ZThread();
     
            void Start();
            void Wait();
            void Terminate();
     
            bool IsRunning(){return m_isRunning;}
            void* GetReturnedValue(){return m_returnedValue;}
     
        protected:
     
            virtual void* Run();
     
            HANDLE m_handle;
            unsigned m_id;
     
            void* m_data;
            void* (*m_ptrFunc)(void*);
     
            bool m_isRunning;
     
            void* m_returnedValue;
    };
     
    #endif // ZTHREAD_HPP_INCLUDED
    ZThread.cpp
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
     
    #include "ZThread.hpp"
    #include <process.h>
    #include <iostream>
     
    unsigned __stdcall launcherfunc(void* data)
    {
        ZThread* tmpInstance=static_cast<ZThread*>(data);
        tmpInstance->m_isRunning=true;
        tmpInstance->m_returnedValue=tmpInstance->Run();
        tmpInstance->m_isRunning=false;
        _endthreadex(0);
        return 0;
    }
     
    ZThread::ZThread(): m_handle(NULL),
     m_ptrFunc(NULL),
     m_data(NULL),
     m_isRunning(false),
     m_returnedValue(NULL)
    {
    }
     
    ZThread::ZThread(void* (*ptrFunc)(void*), void* data):
     m_handle(NULL),
     m_ptrFunc(ptrFunc),
     m_data(data),
     m_isRunning(false),
     m_returnedValue()
    {
    }
     
    ZThread::~ZThread()
    {
        if(m_isRunning)
            Wait();
    }
     
    void*  ZThread::Run()
    {
        if(m_ptrFunc!=NULL)
            return m_ptrFunc(m_data);
        return (void*) 0;
    }
     
    void ZThread::Start()
    {
        m_handle=(HANDLE)_beginthreadex(NULL,0,&launcherfunc,this, 0,&m_id);
        if(m_handle==NULL)
            throw("Unable to create a new thread");
    }
     
    void ZThread::Wait()
    {
        if(m_isRunning)
        {
            WaitForSingleObject(m_handle,INFINITE);
            CloseHandle(m_handle);
            m_handle=NULL;
        }
    }
    ZMutex.hpp
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
     
    #ifndef ZMUTEX_HPP_INCLUDED
    #define ZMUTEX_HPP_INCLUDED
     
    #include <windows.h>
     
    class ZMutex
    {
        public:
     
            ZMutex();
            ~ZMutex();
     
            void Lock();
            void UnLock();
            bool IsLocked(){return m_isLocked;}
     
        protected:
     
            CRITICAL_SECTION m_mutex;
            bool m_isLocked;
    };
     
    #endif // ZMUTEX_HPP_INCLUDED
    ZMutex.cpp
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
     
    #include "ZMutex.hpp"
     
    ZMutex::ZMutex():
     m_isLocked(false)
    {
        InitializeCriticalSection(&m_mutex);
    }
     
    ZMutex::~ZMutex()
    {
        DeleteCriticalSection(&m_mutex);
    }
     
     
    void ZMutex::Lock()
    {
        if(!m_isLocked)
        {
            m_isLocked=true;
            EnterCriticalSection(&m_mutex);
        }
    }
     
    void ZMutex::UnLock()
    {
        if(m_isLocked)
        {
            LeaveCriticalSection(&m_mutex);
            m_isLocked=false;
        }
    }
    User.hpp
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
    110
    111
    112
    113
    114
    115
    116
    117
    118
    119
    120
    121
    122
    123
    124
    125
    126
    127
    128
    129
    130
    131
    132
    133
    134
    135
    136
    137
    138
    139
    140
    141
    142
    143
    144
    145
    146
    147
    148
    149
    150
    151
     
    #ifndef USER_HPP_INCLUDED
    #define USER_HPP_INCLUDED
     
    #include <cstdlib>
    #include <iostream>
    #include <string>
    #include <vector>
    #include <map>
    #include "ZMutex.hpp"
     
    #include "EllipticCurveUT.hpp"
     
    template<typename T>
    class Connection
    {
        public:
     
            Connection(){}
            Connection(std::multimap<char, std::pair<T,T> > correspondanceTable, EllipticCurve<T> curve,std::pair<T,T> refPoint):
             m_correspondanceTable(correspondanceTable),
             m_curve(curve),
             m_refPoint(refPoint)
             {}
     
        std::multimap<char, std::pair<T,T> > m_correspondanceTable;
        EllipticCurve<T> m_curve;
        std::pair<T,T> m_refPoint;
        std::pair<T,T> m_firstPoint;
        std::pair<T,T> m_secondPoint;
    };
     
    template<typename T>
    class User
    {
     
    public:
     
        User()
        {
            m_key = 1;//c'est pour voir si le crackage marche
        }
     
        static void EstablishConnection(User* firstUser, User* secondUser, std::multimap<char, std::pair<T,T> > correspondanceTable, EllipticCurve<T> curve, std::pair<T,T> refPoint)
        {
            firstUser->EstablishConnection(secondUser, correspondanceTable, curve, refPoint);
            secondUser->EstablishConnection(firstUser, correspondanceTable, curve, refPoint);
            firstUser->EstablishConnection(secondUser, correspondanceTable, curve, refPoint, true);
            secondUser->EstablishConnection(firstUser, correspondanceTable, curve, refPoint, true);
        }
     
        void EstablishConnection(User* beConnectedTo, std::multimap<char, std::pair<T,T> > correspondanceTable, EllipticCurve<T> curve, std::pair<T,T> refPoint, bool secondPart = false)
        {
            m_mutex.Lock();
            if(!secondPart){
                m_connections[beConnectedTo] = Connection<T>(correspondanceTable, curve, refPoint);
                m_connections[beConnectedTo].m_firstPoint = curve.QuickExponentiation(m_key, refPoint);
            }if(secondPart){
                m_connections[beConnectedTo].m_secondPoint = m_connections[beConnectedTo].m_curve.QuickExponentiation(m_key, beConnectedTo->GetComputedPoint(this));
            }
            m_mutex.UnLock();
        }
     
        Connection<T> GetConnection(User* user){m_mutex.Lock(); return m_connections[user]; m_mutex.UnLock();}
     
        std::pair<T,T> GetComputedPoint(User* connectedTo){m_mutex.Lock(); return m_connections[connectedTo].m_firstPoint; m_mutex.UnLock();}
     
        std::vector<std::pair<T,T> > CryptMessage(User* receiver, std::string message)
        {
            m_mutex.Lock();
            std::vector<std::pair<T,T> > cryptedMessage;
            cryptedMessage.push_back(m_connections[receiver].m_firstPoint);
     
            std::multimap<char, std::pair<T,T> > correspondanceTable = m_connections[receiver].m_correspondanceTable;
            m_mutex.UnLock();
     
            typename std::multimap<char, std::pair<T,T> >::iterator iter;
            for(unsigned int i =0; i < message.length(); i++)
            {
                iter = correspondanceTable.find(message[i]);
     
                if( iter != correspondanceTable.end())
                {
                    m_mutex.Lock();
                    cryptedMessage.push_back(m_connections[receiver].m_curve.AddPoints(m_connections[receiver].m_secondPoint, iter->second));
                    m_mutex.UnLock();
                }
                //!TODO: gérer le cas où le caractère est absent de la table
            }
     
            return cryptedMessage;
        }
     
        std::string DecryptMessage(User* sender, std::vector<std::pair<T,T> > message)
        {
            std::string decryptedMessage;
            m_mutex.Lock();
            std::multimap<char, std::pair<T,T> > correspondanceTable = m_connections[sender].m_correspondanceTable;
            m_mutex.UnLock();
     
            typename std::multimap<char, std::pair<T,T> >::iterator iter;
            std::pair<T,T> decryptedPoint;
            for(unsigned int i = 0; i < message.size(); i++)
            {
                m_mutex.Lock();
                decryptedPoint = m_connections[sender].m_curve.SoustractPoints(message[i], m_connections[sender].m_secondPoint);
                m_mutex.UnLock();
                for(iter = correspondanceTable.begin(); iter != correspondanceTable.end(); iter++)
                {
                    if(iter->second == decryptedPoint)
                    {
                        char car[2];
                        car[0] = iter->first;
                        car[1] = '\0';
                        decryptedMessage = decryptedMessage + car;
                        break;
                    }
                }
            }
     
            return decryptedMessage;
        }
     
        void sendMessage(User* receiver, std::string message)
        {
            sendCryptedMessage(receiver, CryptMessage(receiver, message));
        }
     
        void sendCryptedMessage(User* receiver, std::vector<std::pair<T,T> > cryptedMessage)
        {
            receiver->receiveCryptedMessage(this, cryptedMessage);
        }
     
        void receiveCryptedMessage(User* sender,  std::vector<std::pair<T,T> > cryptedMessage)
        {
            std::cout<<"Received message :"<<DecryptMessage(sender, cryptedMessage)<<std::endl;
        }
     
        std::map<User*, Connection<T> > m_connections;
     
        static ZMutex m_mutex;
     
    protected:
     
        long long m_key;
    };
     
    template<typename T>
    ZMutex User<T>::m_mutex;
     
    #endif // USER_HPP_INCLUDED
    Cracker.hpp
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
    110
    111
    112
    113
    114
    115
    116
    117
    118
    119
    120
    121
    122
    123
    124
    125
    126
    127
     
    #ifndef CRACKER_HPP_INCLUDED
    #define CRACKER_HPP_INCLUDED
     
    #include <iostream>
    #include "User.hpp"
    #include "ZMutex.hpp"
    #include "ZThread.hpp"
     
    template<typename T>
    class Cracker;
     
    template<typename T>
    class InfoPackage
    {
        public:
     
            InfoPackage(){}
            InfoPackage(Cracker<T>* cracker, User<T>* user, User<T>* connectedUser, int offset, int iterateBy):
             m_cracker(cracker),
             m_user(user),
             m_connectedUser(connectedUser),
             m_offset(offset),
             m_iterateBy(iterateBy)
            {}
     
            InfoPackage(const InfoPackage<T>& rhs)
            {
                m_cracker = rhs.m_cracker;
                m_user = rhs.m_user;
                m_connectedUser = rhs.m_connectedUser;
                m_offset = m_offset;
                m_iterateBy = rhs.m_iterateBy;
            }
     
            Cracker<T>* m_cracker;
            User<T>* m_user;
            User<T>* m_connectedUser;
            int m_offset;
            int m_iterateBy;
    };
     
    template<typename T>
    void* CrackKey(void* infos)
    {
        InfoPackage<T> informations = *(static_cast<InfoPackage<T>*>(infos));
        Cracker<T>* cracker = informations.m_cracker;
        cracker->m_mutex.Lock();
        std::pair<T,T> point = cracker->m_connections[informations.m_user].m_refPoint;
        std::pair<T,T> researchedPoint = informations.m_user->GetComputedPoint(informations.m_connectedUser);
        EllipticCurve<T> curve = cracker->m_connections[informations.m_user].m_curve;
        cracker->m_mutex.UnLock();
     
        for(long long i = informations.m_offset + 1;; i+= informations.m_iterateBy)
        {
            cracker->m_mutex.Lock();
            if(cracker->keyA != 0)
                break;
     
            if(curve.QuickExponentiation(i, point) == researchedPoint)
            {
                cracker->keyA = i;
                std::cout<<"KeyA found: "<<i<<std::endl;
                break;
            }
            cracker->m_mutex.UnLock();
        }
        cracker->m_mutex.UnLock();
        return (void*)1;
    }
     
    template<typename T>
    class Cracker: public User<T>
    {
        public:
     
            Cracker():
             keyA(0),
             keyB(0)
            {
            }
     
            void EstablishConnection(User<T>* firstUser, User<T>* secondUser)
            {
                this->m_connections[firstUser] = firstUser->GetConnection(secondUser);
                CrackKeys(firstUser, secondUser);
            }
     
            void CrackKeys(User<T>* firstUser, User<T>* secondUser)
            {
                InfoPackage<T> infos(this, firstUser, secondUser, 0, 4);
                firstThread = new ZThread(&CrackKey<T>, (void*)&infos);
                firstThread->Start();
                infos.m_offset = 1;
                secondThread = new ZThread(&CrackKey<T>, (void*)&infos);
                secondThread->Start();
                infos.m_offset = 2;
                thirdThread = new ZThread(&CrackKey<T>, (void*)&infos);
                thirdThread->Start();
                infos.m_offset = 3;
                fourthThread = new ZThread(&CrackKey<T>, (void*)&infos);
                fourthThread->Start();
            }
     
     
            std::string DecryptMessage(User<T>* sender, std::vector<std::pair<T,T> > message)
            {
            }
     
            void Wait()
            {
                firstThread->Wait();
                secondThread->Wait();
                thirdThread->Wait();
                fourthThread->Wait();
            }
     
        long long keyA;
        long long keyB;
     
        protected:
     
        ZThread* firstThread;
        ZThread* secondThread;
        ZThread* thirdThread;
        ZThread* fourthThread;
    };
    voil�.
    Merci pour votre aide.

  2. #2
    screetch
    Invit�(e)
    Par d�faut
    il manque le main dfficile dans tant de code de s'y retrouver

  3. #3
    Membre �prouv�
    Profil pro
    Inscrit en
    F�vrier 2007
    Messages
    217
    D�tails du profil
    Informations personnelles :
    �ge : 32
    Localisation : France

    Informations forums :
    Inscription : F�vrier 2007
    Messages : 217
    Par d�faut
    Je peux r�sumer le main � �a (il est assez long):
    Code : S�lectionner tout - Visualiser dans une fen�tre � part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     
    int main(int argc, char** argv)
    {
        User<long long> bob, alice;
        User<long long>::EstablishConnection(&bob, &alice, correspondancesTable, curve, GetAzardousPoint(points));//table de correspondance caractère/point, courbe utilisée, point de référence
        Cracker<long long> oscar;
        oscar.EstablishConnection(&bob, &alice);
     
        bob.sendMessage(&alice, "BONJOUR");
     
        oscar.Wait();
    }

  4. #4
    Membre �prouv�
    Profil pro
    Inscrit en
    F�vrier 2007
    Messages
    217
    D�tails du profil
    Informations personnelles :
    �ge : 32
    Localisation : France

    Informations forums :
    Inscription : F�vrier 2007
    Messages : 217
    Par d�faut
    Bon en fait, �a ne marchait pas parceque le pointeur sur mon InfoPackage ne pointait plus vers une adresse m�moire valide apr�s la fin de la fonction CrackKeys();

  5. #5
    Expert �minent
    Avatar de koala01
    Homme Profil pro
    aucun
    Inscrit en
    Octobre 2004
    Messages
    11 644
    D�tails du profil
    Informations personnelles :
    Sexe : Homme
    �ge : 53
    Localisation : Belgique

    Informations professionnelles :
    Activit� : aucun

    Informations forums :
    Inscription : Octobre 2004
    Messages : 11 644
    Par d�faut
    Salut,

    D'abord, je rappellerais que l'erreur de segmentation a quasi toujours la m�me origine: on essaye d'acc�der � une adresse m�moire qui n'est plus consid�r�e comme valide.

    Ensuite, il faut se rappeler que le principe m�me du thread est de permettre du travail "concurrent", mais donc que les diff�rents threads sont susceptibles de terminer � des moments diff�rents...

    Ainsi, il se peut tr�s bien le que thread "second" finisse son travail avant les threads first, third et fourth, et que tu devrait veiller � pouvoir g�rer cela de mani�re s�curisante pour toi.

    Enfin, j'ai crois� quelques new qui n'ont pas leur delete �quivalent...

    Avant de te lancer dans les threads, tu devrait d�j� sans doute essayer d'�viter les fuites m�moire de ce type, et, comme de nombreux membres sont des pointeurs, je te conseillerais de les initialiser � NULL au d�part, et de les refaire pointer sur NULL d�s que l'adresse sur laquelle ils pointent devient invalide.

    De cette mani�re, il te sera plus facile de tester si chacun de tes pointeurs est valide, et de ne lancer un traitement que si c'est effectivement le cas.

    toutes ces remarques devraient d�j� te permettre d'�viter pas mal d'erreurs de segmentation, m�me si je ne suis pas (loin s'en faut) un sp�cialiste des threads
    A m�diter: La solution la plus simple est toujours la moins compliqu�e
    Ce qui se con�oit bien s'�nonce clairement, et les mots pour le dire vous viennent ais�ment. Nicolas Boileau
    Compiler Gcc sous windows avec MinGW
    Coder efficacement en C++ : dans les bacs le 17 f�vrier 2014
    mon tout nouveau blog

  6. #6
    Membre �prouv�
    Profil pro
    Inscrit en
    F�vrier 2007
    Messages
    217
    D�tails du profil
    Informations personnelles :
    �ge : 32
    Localisation : France

    Informations forums :
    Inscription : F�vrier 2007
    Messages : 217
    Par d�faut
    Je savais � quoi est d� une erreur de segmentation mais je ne voyais pas d'o� elle provenait: elle �tait sous mes yeux et je cherchait ailleurs
    J'ai enlev� une partie du code dont le destructeur, qui fait pas mal de choses dont les d�-allocations.
    Merci pour les conseil toujours bons � respecter

  7. #7
    Expert �minent
    Avatar de M�dinoc
    Homme Profil pro
    D�veloppeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 397
    D�tails du profil
    Informations personnelles :
    Sexe : Homme
    �ge : 41
    Localisation : France

    Informations professionnelles :
    Activit� : D�veloppeur informatique
    Secteur : High Tech - �diteur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 397
    Par d�faut
    Ta classe de mutex n'est pas bonne. Elle ne devrait pas m�moriser le fait d'�tre verrouill�e ou non, ce n'est pas son r�le (si tu veux une fonction qui retourne imm�diatement si elle ne peut pas verrouiller, tu dois impl�ment� un vrai TryLock() qui retourne une valeur pour indiquer le succ�s ou l'�chec du verrouillage. Et dans celui-ci, appeler directement TryEnterCriticalSection() sans t'embarrasser d'une variable suppl�mentaire).

    Par contre, tu peux m�moriser l'id du thread qui poss�de le lock si tu veux emp�cher les verrouillages r�cursifs...

    Et tu peux aussi te faire une classe VerrouMutex qui serait utilis�e en RAII sur la classe de Mutex...
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parl� avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

+ R�pondre � la discussion
Cette discussion est r�solue.

Discussions similaires

  1. [MultiThreading] DecimalFormat.parse non thread-safe
    Par Jidefix dans le forum Concurrence et multi-thread
    R�ponses: 9
    Dernier message: 06/05/2009, 16h17
  2. [RCP] Treeviewer non thread-safe ?
    Par Guildux dans le forum Eclipse Platform
    R�ponses: 4
    Dernier message: 09/01/2007, 13h00
  3. [Composant] Comment déclarer un code thread safe ?
    Par AiSpirit dans le forum Framework .NET
    R�ponses: 5
    Dernier message: 26/08/2006, 11h37
  4. Code "Thread Safe" ?
    Par Neitsa dans le forum C++
    R�ponses: 3
    Dernier message: 23/12/2005, 14h33
  5. [MFC] CMAP non thread safe ?
    Par fmarot dans le forum MFC
    R�ponses: 5
    Dernier message: 04/10/2005, 13h21

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo