1. #1

    Inscrit en
    janvier 2012
    Messages
    6
    Détails du profil
    Informations forums :
    Inscription : janvier 2012
    Messages : 6
    Points : -1
    Points
    -1

    Par défaut [Socket] Réception incohérente

    Bonjour,

    Je viens aujourd'hui suite à un petit soucis que je rencontre dans mon application réseau et qui me parait étrange. Le problème se situe lors d'un envoi/réception précis. Donc tout d'abord voici un petit bout de code pour illustrer:

    Méthode add:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    template<typename T>
    void add(const T & msg )
    {
          std::ostringstream oss;
          oss << msg;
          m_Data += oss.str() + '|';
    }
    Méthode SendData:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    void Server::sendData(int index, NetworkMessage& msg)
    {
        ostringstream oss;
        string str = "";
     
        oss << msg.getType();
        str = oss.str() + '|' + msg.getMessage();
     
        unsigned int n = send(m_Client[index]->getSocket(), str.c_str(), str.size(), 0);
        if(n < 0)
            removeClient(index);
    }
    Code incriminé:
    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
    NetworkMessage msg1(DATA_NEW_CARD, "blablabla");
    sendData(index, msg1);// (envoi 1)
     
    vector<int> infosIndex = m_Zone[num]->getInfos();
    for (unsigned int i = 0; i < infosIndex.size(); i++)
    {
          NetworkMessage msg(DATA_NEW_CARD);
          msg.add(m_Cards[infosIndex[i]]->getIndex());
          msg.add(m_Cards[infosIndex[i]]->getName());
          msg.add(m_Cards[infosIndex[i]]->getNum());
          msg.add(m_Cards[infosIndex[i]]->getType());
          msg.add(m_Cards[infosIndex[i]]->getSize());
          sendData(index, msg); // (envoi 2)
    }
     
    NetworkMessage msg2(DATA_NEW_CARD, "blablabla");
    sendData(index, msg2);// (envoi 3)
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    Format trame attendue côté client: msg_type|index|name|num|type|size|
    Lors des envois 1 et 3 la trame attendue est correcte mais le problème se pose lors de l'envoi 2.

    Ma vision de l'envoi 2:

    - Instanciation d'un objet msg avec en paramètre le type du message
    - Ajout de divers infos au contenu de msg
    - Envoi
    - Puis on recommence autant de fois que nécessaire...

    Il devrai donc y avoir X envois (i < infosIndex.size()) mais voici ce que j'obtiens côté client:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    Trame reçue: msg_type|index|name|num|type|size|msg_type|index|name|num|type|size|msg_type|index|name|num|type|size|...
    (les X envois qui devrait êtres reçues séparément sont condenser en un message)

    J'espère que tout cela sera suffisant pour tenter de me répondre ^^"
    En tout cas, j'arrive pas a comprendre pourquoi le code fait cela =/

    Cordialement,

  2. #2
    Membre du Club
    Homme Profil pro
    Étudiant
    Inscrit en
    mai 2011
    Messages
    29
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : mai 2011
    Messages : 29
    Points : 60
    Points
    60

    Par défaut

    Salut, c'est sûrement parce que les données sont placées dans un tampon pour éviter de consommer trop de ressources. Du coup elle ne sont envoyées qu'au dernier moment (ou quand le tampon est plein).
    Pour éviter ça il faut activer le flag PUSH dans le paquet, ça fait une émission immédiate du paquet à l'appel de send.

    J'imagine que le protocole doit être TCP, donc normalement il faut s'y prendre comme ça :
    (en rajoutant l'option NO_DELAY à la socket)

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
     
    /* ... création de de la socket */
     
    int autorisation = 1;
     
    if (setsockopt(socket, IPPROTO_TCP, TCP_NODELAY, &autorisation, sizeof(int)) < 0)
       perror("erreur");
     
    /* ...*/
    Où socket est la socket sur laquelle tu envoies. Donc comme c'est un tableau va sûrement falloir l'appeler à la création des sockets de chaque client.

    C++dialement,

    Pop360

Discussions similaires

  1. Séparation socket réception/émission
    Par eric.caao dans le forum Développement
    Réponses: 4
    Dernier message: 14/05/2013, 22h16
  2. Codage des entiers dans socket (réception par java)
    Par theanthony33 dans le forum C#
    Réponses: 3
    Dernier message: 26/06/2010, 21h16
  3. Socket - Réception de plusieurs données à la suite
    Par dvp_zero dans le forum Réseau
    Réponses: 8
    Dernier message: 06/12/2009, 17h43
  4. Réponses: 2
    Dernier message: 06/06/2006, 12h10
  5. Réponses: 6
    Dernier message: 13/04/2006, 15h54

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