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

Réseau C Discussion :

checksum icmp et ip !


Sujet :

Réseau C

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre confirmé
    Étudiant
    Inscrit en
    Juin 2010
    Messages
    82
    Détails du profil
    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Juin 2010
    Messages : 82
    Par défaut checksum icmp et ip !
    salut a tous j'ai un soucis avec le calcul du checksum .

    j'utilise une fonction checksum() pour le calcule de cette somme , pour lentete IP la somme est bien correcte mais cette meme fonction , la somme ICMP est pas correcte je comprend pas pourquoi .

    puis je avoir un peu d'aide ? ( jutilise winpcap sous vc++ 06 )

    ou savoir si avec cette libcat (winpcap) y'a une fonction pour calculer ce checksum .

  2. #2
    Modérateur
    Avatar de Obsidian
    Homme Profil pro
    Chercheur d'emploi
    Inscrit en
    Septembre 2007
    Messages
    7 487
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Chercheur d'emploi
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2007
    Messages : 7 487
    Par défaut
    Avec si peu d'infos, c'est difficile.

    Toutefois, on peut quand même signaler que si ces deux checksums se calculent de la même façon, les longueurs des entêtes sur lesquels elles portent ne sont pas les mêmes. Est-ce que passe bien la longueur des données à balayer à ta fonction checksum() ?

  3. #3
    Membre confirmé
    Étudiant
    Inscrit en
    Juin 2010
    Messages
    82
    Détails du profil
    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Juin 2010
    Messages : 82
    Par défaut
    merci pour ta reponse .

    voila la fonction que j'utilise

    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
     
    USHORT checksum(void * lpData, size_t size)
    {
        USHORT * t = lpData;
        DWORD somme = 0;
        size_t i, n = size / sizeof(USHORT);
     
        for(i = 0; i < n; i++)
            somme += t[i];
     
        if (size % 2)
        {
            UCHAR * u = lpData;
            somme += u[size - 1];
        }
     
        while (HIWORD(somme))
            somme = HIWORD(somme) + LOWORD(somme);
     
        return LOWORD(~somme); 
    }

    appeler de cette facon

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    ip.somme      = checksum( &ip, sizeof(ip) );
    et en utilisant pour ICMP

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    icmp.Sommecontrole      =checksum( (&icmp, sizeof(icmp));
    j'obtiens bien une somme mais wireshark (en sniffant mon packet) me donne valeur incorrect ce qui empeche lenvoi reel de mon packet a destination .

    donc je me demandais peut etre qu'il fallait inclure d'autre element aux 2eme argument de la fonction checksum .

    enfin je suis perdu, sur ce site http://www.frameip.com/entete-icmp/ , l'exemple donné je vois pas comment l'appeler dans mon code (enfin les arguments a lui donné ) .

  4. #4
    Modérateur
    Avatar de sevyc64
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Janvier 2007
    Messages
    10 251
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 52
    Localisation : France, Pyrénées Atlantiques (Aquitaine)

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : Janvier 2007
    Messages : 10 251
    Par défaut
    Ton code me semble correct.

    Le code de l'exemple traduit dans ton code donne ceci :
    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
    unsigned short checksum(unsigned short *lpData, int size)
        {
        unsigned long somme=0;
        // ********************************************************
        // Complément à 1 de la somme des complément à 1 sur 16 bits
        // ********************************************************
        while(size>1)
            {
            somme = somme + *lpData++;
            size = size - sizeof(unsigned short);
            }
     
        if(size)
            somme = somme + *(unsigned char*)lpData;
     
        somme = (somme >> 16)+(somme & 0xffff);
        somme = somme + (somme >> 16);
     
        return (unsigned short)(~somme);
        }
    NOTA : La RFC indique "Complément à 1 de la somme des complément à 1 sur 16 bits" mais il semble que c'est plutôt "Complément à 1 sur 16 bits de la somme mots de 16 bits"


    On va voir sur un exemple :
    Soit la trame ICMP suivante (uniquement la partie ICMP, pas la partie IP) :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    08 00 ?? ??  00 01 00 01 61 62 63 64 65 66 67 68
    69 6a 6b 6c 6d 6e 6f 70 71 72 73 74 75 76 77 61
    62 63 64 65 66 67 68 69
    on va donc faire la somme de 0800+0000+0001+0001+6162+....
    Ce qui va nous donner : 6B29F
    On travaille sur 16 bits mais on conserve la retenue, donc on fait B29F+6 = B2A5 (si cette comme génère à nouveau une retenue faut recommencer jusqu'à tenir sur uniquement 16 bits)

    Ensuite on fait le complément à 1 de B2A5 ==> 4D5A, qui était bien le checksum attendu.

  5. #5
    Modérateur
    Avatar de Obsidian
    Homme Profil pro
    Chercheur d'emploi
    Inscrit en
    Septembre 2007
    Messages
    7 487
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Chercheur d'emploi
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2007
    Messages : 7 487
    Par défaut
    Citation Envoyé par sevyc64 Voir le message
    NOTA : La RFC indique "Complément à 1 de la somme des complément à 1 sur 16 bits" mais il semble que c'est plutôt "Complément à 1 sur 16 bits de la somme mots de 16 bits"

    On travaille sur 16 bits mais on conserve la retenue, donc on fait B29F+6 = B2A5 (si cette comme génère à nouveau une retenue faut recommencer jusqu'à tenir sur uniquement 16 bits)
    C'est plus subtil encore : c'est le complément à 1 de la somme des « nombres de 16 bits en représentation complément à 1 ».

    Je ne m'étais jamais réellement penché sur le cas et ça m'a donné l'occasion de me replonger dans la lecture desdites RFC, notamment la RFC 1071 ainsi que ceci.

    En gros, on considère que l'on change de signe en inversant tous les bits mais sans ajouter le +1 qui suit. Ce qui fait que « -1 » est représenté par « FFFE » plutôt que par « FFFF ». Ça, d'accord. La difficulté consiste à faire les calculs en tenant compte de ces signes et à rendre un résultat correct selon les mêmes règles. Et il est précisé notamment dans la RFC que sur les machines à complément à 2 (les additions binaires ordinaires que l'on connaît), cela se fait en additionnant tous les mots puis en ajoutant la retenue, soit la partie qui déborde, au résultat.

    Citation Envoyé par Shark9 Voir le message
    merci pour ta reponse .

    j'obtiens bien une somme mais wireshark (en sniffant mon packet) me donne valeur incorrect ce qui empeche lenvoi reel de mon packet a destination .

    donc je me demandais peut etre qu'il fallait inclure d'autre element aux 2eme argument de la fonction checksum .
    Deux remarques :

    • Quand tu calcules un checksum Internet, tu passes en revue l'entête entière qui contient justement le checksum que tu cherches à calculer. Il est précisé dans la RFC que ce champ « checksum » doit être mis à zéro avant les calculs. Est-ce que tu as bien pris soin de le faire, dans un cas comme dans l'autre ?
    • Un datagramme ICMP est encapsulé dans un paquet IP (même si ces deux protocoles sont censés être au même niveau du point de vue OSI). Or, le checksum ICMP ne s'appuie que sur l'entête ICMP et pas sur l'entête IP qui le précède. Est-ce que, là encore, cette condition est vérifiée chez toi ?

  6. #6
    Modérateur
    Avatar de sevyc64
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Janvier 2007
    Messages
    10 251
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 52
    Localisation : France, Pyrénées Atlantiques (Aquitaine)

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : Janvier 2007
    Messages : 10 251
    Par défaut
    Citation Envoyé par Obsidian Voir le message
    C'est plus subtil encore : c'est le complément à 1 de la somme des « nombres de 16 bits en représentation complément à 1 ».
    Oui c'est ce que dit la RFC mais lorsque tu regarde les bouts de code parfois fournis ou que tu calcule toi même le checksum à partir d'une trame correcte interceptée (dont tu connais donc le checksum à obtenir) tu te rend compte qu'il ne faut pas faire la somme des « nombres de 16 bits en représentation complément à 1 » mais bien la somme « nombres de 16 bits » directs.

    Citation Envoyé par Obsidian Voir le message
    En gros, on considère que l'on change de signe en inversant tous les bits mais sans ajouter le +1 qui suit. Ce qui fait que « -1 » est représenté par « FFFE » plutôt que par « FFFF ».
    Oui, c'est la définition même du complément à 1. On inverse les bits, 0 devient 1 et 1 devient 0.

  7. #7
    Membre confirmé
    Étudiant
    Inscrit en
    Juin 2010
    Messages
    82
    Détails du profil
    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Juin 2010
    Messages : 82
    Par défaut
    e checksum ICMP ne s'appuie que sur l'entête ICMP et pas sur l'entête IP qui le précède. Est-ce que, là encore, cette condition est vérifiée chez toi ?

    - oui la fonction est parametrer pour calculer que le checksum de lentete icmp comme dans le code plus haut .



    doit être mis à zéro avant les calculs. Est-ce que tu as bien pris soin de le faire, dans un cas comme dans l'autre ?


    - oui je prend le soin de bien le mettre a 0 avant le calcul et pourtant le checksum eu en resultat est incorrecte , donc est pour cela que j'aurai aimé savoir comment faut faire le calcule pour obtenir le checksum que wireshark conseil .


    merci de vos reponses

  8. #8
    Expert confirmé

    Inscrit en
    Novembre 2005
    Messages
    5 145
    Détails du profil
    Informations forums :
    Inscription : Novembre 2005
    Messages : 5 145
    Par défaut
    Citation Envoyé par sevyc64 Voir le message
    Oui c'est ce que dit la RFC mais lorsque tu regarde les bouts de code parfois fournis ou que tu calcule toi même le checksum à partir d'une trame correcte interceptée (dont tu connais donc le checksum à obtenir) tu te rend compte qu'il ne faut pas faire la somme des « nombres de 16 bits en représentation complément à 1 » mais bien la somme « nombres de 16 bits » directs.
    Non. On fait bien la "somme complément aux uns" des nombres de 16 bits. Autrement dit, la somme en considérant que les nombres de 16 bits sont des entiers signés en représentation en complément aux uns et en représentant le résultat en complément aux uns. Quand on ne dispose qu'une somme non signée (ou en complément à deux, le fait que ce soit la même est une des raisons qui ont fait du complément à deux la représentation dominante, un ordinateur fonctionnant en complément aux 1 a deux instructions d'addition -- s'il fournit une somme non signée, tous ne l'ont pas fait -- tout comme un ordinateur fonctionnant en complément à 2 a deux instructions de multiplication) une telle somme se fait en ajoutant le report sortant.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Réponses: 15
    Dernier message: 04/01/2007, 11h15
  2. checksum d'une entête ICMP
    Par poporiding dans le forum C++
    Réponses: 6
    Dernier message: 20/01/2006, 14h19
  3. CMOS checksum error
    Par Hakim dans le forum Ordinateurs
    Réponses: 3
    Dernier message: 28/10/2003, 09h33
  4. Envoyer un message icmp (Echo Request)
    Par ovdz dans le forum Développement
    Réponses: 5
    Dernier message: 19/06/2003, 14h14
  5. Différence entre TCP, UDP, ICMP
    Par GliGli dans le forum Développement
    Réponses: 1
    Dernier message: 13/09/2002, 08h25

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