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 :

données binaires ?


Sujet :

C++

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre confirmé
    Profil pro
    Inscrit en
    Novembre 2003
    Messages
    113
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2003
    Messages : 113
    Par défaut données binaires ?
    Bonjour à tous.

    Je travaille avec des sockets et j'ai besoin d'echangers des ordres entre un client et un serveur. Je n'ai jamais travaillé en binaire et je ne suis pas sur de ma methode.


    En gros je pense decomposer un message type de la sorte :

    les 16 premiers bit pour indiquer la longueur totale du message en bit (toujours 16 bit)
    les 4 bits suivant pour definir le type d'ordre à executer
    (les parametres suivants dependent du type d'ordre mais par ex)
    2 bit pour une direction
    3 bit pour une vitesse (soit 8 vitesse possible)
    etc...


    Donc dans ce cas on à forcement un message de 25 bits envoyé sur le socket. Je ne sais pas si je fais pas une erreur de methode à ce niveau deja.


    Ensuite la reception. Avant je travaillais avec des char et je lisais les données comme ça :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    char buffer[200];
    nb=recv(socket,&buffer,sizeof(buffer),0);
    Je pense que maintenant je suis censé utiliser un tableau de boolean mais j'ai lu q'un boolean utilisait autant de mémoire q'un char soit 1 octet ...

    Donc soit je reste sur un tableau de char sachant la j'ai par exemple 25 bit qui ne tombe pas sur un multiple d'octet. Soit je passe sur un tableau de bool.

    Mais dans les deux cas, quelle est la methode la plus simple pour decomposer le message connaissant sa structure à l'avance ? Je vois bien l'utilité des >> et des masque mais je vois mal comment l'utiliser si la valeur est a cheval sur 2 octets !!

    Ou alors je me plante completement.

    Pouvez-vous me donner une petite explication ?

    Merci à tous

  2. #2
    Expert confirmé
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Décembre 2003
    Messages
    3 549
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Décembre 2003
    Messages : 3 549
    Par défaut
    Si t'es pas à l'aise avec les opérateurs sur les bits laisse tomber ce système.

  3. #3
    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, il faut garder en tete que le nombre "idéal" de bits devrait toujours rester un multiple de 8 (du moins, sur les architectures de type "PC"), pour la simple et bonne raison que... c'est la taille généralement utilisée pour un type char...

    Ensuite, un bit donne deux possiblités, et tu pourrais donc envisager le fait que le sens ne soit représenté que par un bit, par exemple
    si 0 dans le sens serveur->client
    si 1 dans le sens client->serveur
    (ou l'inverse, selon ton inspiration du moment)

    Enfin, il serait intéressant de prévoir:
    • Quelques bits de "parité"(pour s'assurer qu'une "petite souris" n'a pas modifié un bit entre l'émetteur et le récepteur)
    • Quelques bits de controle de l'ordre des instructions

    Pour le premier, cela pourrait etre, par exemple, 7 bits renvoyant le modulo de tous les autres par 97 (Q: Oui, mais, pourquoi 97 R: parce que c'est le dernier nombre premier avant 100)

    Pour le deuxième, ce serait une valeur codée sur un nombre de bits à convenir, en "binaire réfléchi" (C'est à dire ce binaire qui permet de n'avoir qu'un seul bit qui change chaque fois que la valeur est augmentée de 1), à placer, bien évidemment, avant les bits de parité

    L'utilisation des bitsets (disponibles dans l'espace de nommage std) pourrait sembler etre une solution adaptée à ton problème...

    Ceci dit, je rejoint l'avis de loufoque: si tu n'es pas habitué au travail en binaire, et à moins que tu ne sois tenu par certains impératifs, tu aurais peut etre plus facile à travailler sans utiliser le binaire
    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

  4. #4
    Expert confirmé
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Décembre 2003
    Messages
    3 549
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Décembre 2003
    Messages : 3 549
    Par défaut
    Tu séléctionnes les bits que tu veux avec << ou >> (suivant où ils se trouvent dans l'octet) ainsi que & éventuellement pour mettre une partie qui t'interesse pas à 0 et tu combines le tout avec |.

  5. #5
    Membre confirmé
    Profil pro
    Inscrit en
    Novembre 2003
    Messages
    113
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2003
    Messages : 113
    Par défaut
    Citation Envoyé par loufoque
    Tu séléctionnes les bits que tu veux avec << ou >> (suivant où ils se trouvent dans l'octet) ainsi que & éventuellement pour mettre une partie qui t'interesse pas à 0 et tu combines le tout avec |.
    Oui c'est bien ce que je pensais, ce qui rend les chose plus complexes c'est que finalement un parametre de 5 bits peut etre à cheval sur 2 octets !! je vais donc boucler quelque part au cas ou je demmande des params de 32 bits par exemple. Donc effectivement je vais faire quelques | pour assembler le tout !

  6. #6
    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
    Citation Envoyé par seal3
    Oui c'est bien ce que je pensais, ce qui rend les chose plus complexes c'est que finalement un parametre de 5 bits peut etre à cheval sur 2 octets !! je vais donc boucler quelque part au cas ou je demmande des params de 32 bits par exemple. Donc effectivement je vais faire quelques | pour assembler le tout !
    Pourquoi ne pas prendre un type "classique" qui permette de disposer d'au minimum 25 bits

    Envoie simplement un int ou un unsigned int... tu *devrais* (à moins que tu n'utilise un tres vieux compilo) pouvoir disposer de 32 bits d'un seul coup, et dans une seule variable...

    Tu utilises les bits de 0 à 24 et tu laisses les bits de poids le plus fort tranquils... Et le tour est joué...

    Tu pourra meme faire une vérification supplémentaire sur la valeur renvoyée qui devra etre, en tout état de cause, inférieure ou égale à 0x1FFFFFF (33 554 431 en décimal)... (sinon, c'est qu'une souris est passée par là )

    Et, honnetement, ce n'est pas *vraiment* le fait d'envoyer 32 bits (+/-, dépendemment de l'implémentation des int) qui te fera perdre énormément de bande passante (un peu plus que 4 char, soit, mais, pas suffisemment pour que cela influe réellement)...

    C'est sans compter sur le fait que, idéalement, le flux envoyé sur le réseau doit etre assez long pour atteindre tous les postes avant que l'émission ne cesse (dépendemment de l'implémentation du réseau)... et que, selon l'implémentation du réseau, il serait sans doute meme utile d'envisager un flux de taille suppérieure...
    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

  7. #7
    Membre confirmé
    Profil pro
    Inscrit en
    Novembre 2003
    Messages
    113
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Novembre 2003
    Messages : 113
    Par défaut
    Salut,

    merci de vos réponses. Dans le protocole que j'ai exposé dans le premier post, j'ai effectivement prevus des bits de controles. Il s'agit plus de controler que les messages arrivent dans l'ordre et surtout q'un petit malin n'a pas cherché à simuler l'envois de messages entre le client et le serveur. Mais bon, de toute facon je suis en TCP donc c'est deja pas mal fiable.

    J'aimerais travailler en binaire pour 2 raisons :

    1) La bande passante. Avant quand j'envoyais des chaines strings au serveur, j'utilisais des carateres de séparations (soit un octet à chaque séparation). Au final pour un simple parametre pouvant etre 0 ou 1, c'etait toujours un octet complet d'envoyé. Pour ce projet, le nombre de client etant vraiment enorme, j'ai besoin de faire un max d'economie de ce côté la.

    2) Dans un projet similaire, on à eu des problemes avec des clients qui "snifent" les paquets et qui parviennent aisement à comprendre/modifier le message en question. Le cryptage n'etant pas possible pour des raisons de conso CPU côté client, le fait de passer en binaire rend deja la tache plus dure. On vise pas la protection absolue de toute facon.

    Donc ok, pour le protocole, je vais effectivement voir ça.

    D'abord, il faut garder en tete que le nombre "idéal" de bits devrait toujours rester un multiple de 8 (du moins, sur les architectures de type "PC"), pour la simple et bonne raison que... c'est la taille généralement utilisée pour un type char...
    Cela veut-il dire que je dois toujours completer avec des bits 0 mon dernier octet par exemple ? Je precise que le serveur est unique et qu'il tournera sur une plateforme linux. Dans ce cas, les bits indiquant la longueur totale du message indiquera le nombre d'octets et non de bits. J'économise qq bits aussi la dessus dans ce cas

    Je vais donc insister sur le binaire, je pense connaitre juste ce qu'il faut sur la gestion bas niveau pour pouvoir travailler dessus. Sinon j'apprendrai

    Le client me permet de coder dans un langage qui sera ensuite interprété. L'avantage c'est que ce langage integre directement des fonctions genre readInt() ou getBytes(nb_bits) le tout sur des tableaux de bytes (et non pas de bits) en gros comme si c'etait un tableau de char quoi.

    J'ai deja pas mal bossé avec les masques et les >> sur des bits. Je me demmandais juste si y avait une méthode connus assez simple à mettre en oeuvre pour decomposer mon message. Pour ma curiosité perso j'aimerais ne pas avoir à utiliser la STL.

    Donc au final, je me retrouve avec un tableau de char et je dois lire à coup de X bits à chaque fois pour en sortir un int finalement. Bon au pire je pense pouvoir ecrire un classe qui gere ce genre de chose mais des conseils seraient les bienvenues

    La question que je me pose c'est, est-ce que l'economie de bande passante en codant à coup de bit justifie une surconso de CPU pour decomposer mes messages. Evidement le tout serait plus simple si je travaillais à coup d'octet. En même temps les messages ne sont pas long, 50 octets en moyenne. Mais ils sont nombreux !!

  8. #8
    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
    Citation Envoyé par seal3
    (snip)
    Cela veut-il dire que je dois toujours completer avec des bits 0 mon dernier octet ? On y gagne qq part ? Je precise que le serveur est unique et qu'il tournera sur une plateforme linux. Dans ce cas, les bits indiquant la longueur totale du message indiquera le nombre d'octets et non de bits. J'économise qq bits aussi la dessus dans ce cas
    (snip)
    Disons que L'utilisation de multiples de 8 bits sera surtout plus de nature à te permettre d'utiliser l'architecture interne de ton processeur...

    Il faut bien comprendre que, finalement, quasi toute l'architecture d'un processeur va travailler avec des multiples de 8 bits (du moins, sur les descendants de la famille X86)...

    Il faut bien comprendre, aussi, qu'il faudrait vraiment un nombre incroyable de clients connectés au meme moment sur le serveur (et, surtout, qui essayent en meme temps de communiquer avec) pour que 7 malheureux bits envoyés en plus (au maximum) fassent saturer la bande passante... Surtout quand on voit les vitesses de connexion actuellement atteinte (si on en était encore à l'époque pionière des transmissions à 26 Kb/s, j'aurais peut etre réagit autrement... mais elle est tres loin, déjà )

    Il faut bien comprendre, enfin, que ce que tu "gagne" en bande passante en "évitant" d'envoyer 7 malheureux bits, tu va de toutes manière le "perdre" au niveau du processeur, parce que ca n'entre pas correctement dans ses "échelles de valeurs"...

    Par contre, plutot que de completer le dernier octet avec des 0, pourquoi ne pas plutot envisager l'inverse: ne pas toucher aux bits inutilisés du premier

    Pour l'instant, tu te base sur 25 bits utilisés, ce qui fait 4 octets (pour que le 25eme bit puisse entrer), et tu envisage de travailler sous la forme de
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    Bits utilises               |Bits inutilises
    00000000 00000000 00000000 0|0000000
    Mais, n'aurais tu pas plus facile de travailler sous la forme de
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    inutili|bits utilises
    0000000|0 00000000 00000000 00000000
    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

Discussions similaires

  1. [xml] Encapsulation de données binaires
    Par yanoche dans le forum XML/XSL et SOAP
    Réponses: 4
    Dernier message: 30/11/2005, 14h32
  2. [MySQL] Données binaires
    Par GregPeck dans le forum PHP & Base de données
    Réponses: 3
    Dernier message: 12/11/2005, 23h40
  3. Manipulation de données binaires
    Par Defre87 dans le forum Général Python
    Réponses: 3
    Dernier message: 28/09/2005, 16h16
  4. Problème avec les données binaire
    Par Lachessis dans le forum VB 6 et antérieur
    Réponses: 5
    Dernier message: 10/08/2005, 17h38
  5. Données ASCII et données binaires
    Par chourmo dans le forum Langage
    Réponses: 2
    Dernier message: 20/06/2005, 12h19

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