Que pensez vous de ce code

Que pensez vous de ce code - C++ - Programmation

Marsh Posté le 05-06-2003 à 09:05:47    

Bon alors voila...
j'aimerai inclure en annexe de mon rapport de stage 3 des fonctions essentielles de mon programme.
Mais d'abord j'aimerai avoir l'avis de specialistes pour savoir si ces fonctions sont biens ecrites, si elles sont comprehensibles, si je devrais ajouter des commentaires,...
Ces fonctions sont issues du pgm client.
 
En meme temps, ce poste peut servir aux gens qui veulent faire du client/serveur et qui se demandent comment ca fonctionne.
 
La premiere fonction est la fonction de "switch" qui permet de se connecter au serveur numero deux si le premier est inactif et inversement
La deuxieme fonction est l'envoi d'un message
La troisieme fonction est la fonction de reception d'un message
 

Code :
  1. bool GatewayComm::SwitchGateway()
  2. {
  3. bool static sw=false;
  4. connected = false;
  5. SOCKADDR_IN gw_addr;
  6. //get information from Registry Base
  7. GetPortFromRB();//port number
  8. GetPPCLocationFromRB();
  9. GetPrimaryIPFromRB();//IP address 1
  10. GetBackupIPFromRB(); // IP address 2
  11. GetGWTOFromRB(); //Timeout
  12. if(WSAStartup(0x0101,&wsadata))
  13.  return false;
  14. s = socket( AF_INET, SOCK_STREAM, 0 );
  15. if( s == INVALID_SOCKET )
  16.  return false;
  17. gw_addr.sin_family = AF_INET;
  18. gw_addr.sin_port = htons(tcp_port);
  19. if (sw == false)
  20. {
  21.  gw_addr.sin_addr.s_addr = inet_addr(secondary_ip_addr);
  22.  sw = true;
  23. }
  24. else
  25. {
  26.  gw_addr.sin_addr.s_addr = inet_addr(primary_ip_addr);
  27.  sw = false;
  28. }
  29. ptr_bar->SetPaneText(0,CString("Connecting to gateway..." ));
  30. if(connect( s, ( LPSOCKADDR ) &gw_addr, sizeof( gw_addr ) ) == SOCKET_ERROR )
  31. {
  32.  if (sw == false)
  33.   gw_addr.sin_addr.s_addr = inet_addr(secondary_ip_addr);
  34.  else
  35.   gw_addr.sin_addr.s_addr = inet_addr(primary_ip_addr);
  36.  if(connect( s, ( LPSOCKADDR ) &gw_addr, sizeof( gw_addr ) ) == SOCKET_ERROR )
  37.  {
  38.   ptr_bar->SetPaneText(0,CString("Unable to connect to any Gateway PCs!" ));
  39.   return (false);
  40.  }
  41.  else
  42.  {
  43.   (sw == false) ? ptr_bar->SetPaneText(0,CString("Connected to Gateway PC #2..." )) : ptr_bar->SetPaneText(0,CString("Connected to Gateway PC #1..." ));
  44.   sw = !sw;
  45.   connected = true;
  46.   return (true);
  47.  }
  48. }
  49. else
  50. {
  51.  (sw == false) ? ptr_bar->SetPaneText(0,CString("Connected to Gateway PC #2..." )) : ptr_bar->SetPaneText(0,CString("Connected to Gateway PC #1..." ));
  52.  sw = !sw;
  53.  connected = true;
  54.  return (true);
  55. }
  56. }


Code :
  1. bool GatewayComm::sends(char *msg)
  2. {
  3. CString SentMessage;
  4. resend = true;
  5. nb_pages1 = nb_pages2;
  6. string_msg.Empty();
  7. page_number = 0;
  8. AfxMessageBox((CString)msg);
  9. ptr_bar->SetPaneText(0,CString("Sending message" ));
  10. if (send( s, msg, strlen(msg), 0 )== SOCKET_ERROR )
  11. {
  12.  if (SwitchGateway())
  13.  {
  14.   if (sends(msg))
  15.   {
  16.    return true;
  17.   }
  18.   else
  19.   {
  20.    return false;
  21.   }
  22.  }
  23.  else
  24.  {
  25.   ptr_bar->SetPaneText(0,CString("Message not sent" ));
  26.   return false;
  27.  }
  28. }
  29. else
  30. {
  31.  ptr_bar->SetPaneText(0,CString("Message sent" ));
  32.  return true;
  33. }
  34. }


Code :
  1. bool GatewayComm::receives()
  2. {
  3. int static count_bad=0;
  4. fd_set input_set;
  5. timeval to;
  6. to.tv_sec = timeout;
  7. to.tv_usec = 0;
  8.  //Set up the input,and exception sets for select().
  9. FD_ZERO(&input_set);
  10. FD_SET(s, &input_set);
  11. ptr_bar->SetPaneText(0,CString("Receiving message..." ));
  12. int  r = select(0 , &input_set, NULL, NULL, &to); 
  13. if (r == 0)
  14. {
  15.  if (SwitchGateway())
  16.  {
  17.   char* t = (char*)malloc((MessageToSend.GetLength())*sizeof(char));
  18.   for (int i=0; i<MessageToSend.GetLength();i++)
  19.   {
  20.    t[i] = (char)MessageToSend.GetAt(i);
  21.   }
  22.   if (sends(t))
  23.   {
  24.    ++count_bad; //we only try 3 times;
  25.    if ((count_bad%3)==0)
  26.     return (false);
  27.    if (receives())
  28.     return true;
  29.    else
  30.     return false;
  31.   }
  32.   else
  33.    return false;
  34.   free(t);
  35.  }
  36.  else
  37.   return (false);
  38. }
  39. else
  40. {
  41.  if (r>0)
  42.  {// server sent data's   
  43.   memset((char*)msg2,'\0',4096);
  44.   if (recv(s,msg2, 4096*sizeof(char), 0 )== SOCKET_ERROR )
  45.   {
  46.    free(msg2);
  47.    msg2 = NULL;
  48.    ptr_bar->SetPaneText(0,CString("Message not received" ));
  49.     return false;
  50.   }
  51.   else
  52.   {
  53.    ptr_bar->SetPaneText(0,CString("Message received" ));
  54. //add null char at the end of the message
  55.    char* correction = strstr(msg2,"LAST" );
  56.    if (correction!=NULL)
  57.    {
  58.     if (*(correction-1) == '\r')
  59.     {
  60.      *(correction+4) = '\0';
  61.     }
  62.    }
  63.    MessageReceived = msg2;
  64.    page_number++;
  65.    return true;
  66.   }
  67.  }
  68.  else
  69.   return false;
  70. }
  71. }


 
voila si vous avez lu tout, pourriez vous me donnez vos commentaires?


Message édité par polo021 le 05-06-2003 à 09:09:14
Reply

Marsh Posté le 05-06-2003 à 09:05:47   

Reply

Marsh Posté le 05-06-2003 à 09:22:41    

ca fait joli le bleu :o


---------------
lecteur mp3 yvele's smilies jeux de fille
Reply

Marsh Posté le 05-06-2003 à 09:26:29    

forummp3 a écrit :

ca fait joli le bleu :o


 :pfff:
C'est bien ce que je pensais, personne n'a pris 10 minutes pour lire ce code  :cry:  

Reply

Marsh Posté le 05-06-2003 à 09:27:21    

polo021 a écrit :


 :pfff:
C'est bien ce que je pensais, personne n'a pris 10 minutes pour lire ce code  :cry:  


 
Scuse nous de bosser  :whistle:


---------------
Le Tyran
Reply

Marsh Posté le 05-06-2003 à 09:29:25    

LetoII nous fait croire qu'il bosse :


 
Scuse nous de bosser  :whistle:  


 :non:  ca te permettrai aussi d'apprendre la programmation des sockets  :o  

Reply

Marsh Posté le 05-06-2003 à 09:32:31    

polo021 a écrit :


 :non:  ca te permettrai aussi d'apprendre la programmation des sockets  :o  
 


 
J'ai des cours pour ça merci ;)


---------------
Le Tyran
Reply

Marsh Posté le 05-06-2003 à 11:46:11    

up?

Reply

Marsh Posté le 05-06-2003 à 13:58:56    

Je sais pas en quel nivo tu es, mais koikilensoit ca me parrait bien ecrit. On peut chipoter un peu :

Code :
  1. if (sends(msg))
  2.     {
  3.         return true;
  4.     }
  5.     else
  6.     {
  7.         return false;
  8.     }
  9. se limite à :
  10.     return sends( msg );
  11. et ton MessageToSend aussi, je sais pas trop d'ou il sort, mais normalement pas besoin de faire de malloc (utilise plutot new en C++).
  12. char* t = (char*)malloc((MessageToSend.GetLength())*sizeof(char));
  13. for (int i=0; i<MessageToSend.GetLength();i++)
  14. {
  15.    t[i] = (char)MessageToSend.GetAt(i);
  16. }


Y'a une fonction avec les CString (GetBuffer je crois, ou un truc comme ca) qui te renvoie un const char *, si ce n'est même un char * (je connais pas les MFC).
Si c'est un variable globale ton MessageToSend, faudrait la gercler. Si c'est un attribut de ta classe, un petit this-> devant lève l'ambiguite, ou alors respecte la notation MFC et renomme en m_MessageToSend;
 
Tu peux aussi éviter de caster des chaines en CString, genre ptr_bar->SetPaneText(0,CString("Connecting to gateway..." ));  
ptr_bar->SetPaneText( 0, "Connecting to gateway..." ); doit suffir, ca allège un peu, et un allergique aux MFC t'en voudra pas. Après c'est selon chacun. On pourrait reprocher de mixer du code d'interface (vue) au milieu du code du coeur du programme (document), mais bon, dans ton cas ca passe (je fait référence au SetPaneText). Tu peux oublier ce point. Surtout si t'es nivo bac+2, car les MFC, c'est pas facile, et pour un premier stage, tu t'es appliqué à écrire quelque chose de lisible, et c'est très bien. Ca manque un peu de commentaires, et ton erreur a été de ne pas les écrire tout de suite. Un commentaire ca se fait tout de suite, jamais après.
Moi je suis attaché à cette règle : si on enlève le code, les commentaires doivent permettre de retrouver l'algo.
Voilou voilou pour ce que j'ai regardé. Mais moi je trouve que ca va. Continue comme ca.


---------------
FAQ fclc++ - FAQ C++ - C++ FAQ Lite
Reply

Marsh Posté le 05-06-2003 à 14:08:57    

HelloWorld a écrit :

Je sais pas en quel nivo tu es, mais koikilensoit ca me parrait bien ecrit. On peut chipoter un peu :

Code :
  1. if (sends(msg))
  2.     {
  3.         return true;
  4.     }
  5.     else
  6.     {
  7.         return false;
  8.     }
  9. se limite à :
  10.     return sends( msg );
  11. et ton MessageToSend aussi, je sais pas trop d'ou il sort, mais normalement pas besoin de faire de malloc (utilise plutot new en C++).
  12. char* t = (char*)malloc((MessageToSend.GetLength())*sizeof(char));
  13. for (int i=0; i<MessageToSend.GetLength();i++)
  14. {
  15.    t[i] = (char)MessageToSend.GetAt(i);
  16. }


Y'a une fonction avec les CString (GetBuffer je crois, ou un truc comme ca) qui te renvoie un const char *, si ce n'est même un char * (je connais pas les MFC).
Si c'est un variable globale ton MessageToSend, faudrait la gercler. Si c'est un attribut de ta classe, un petit this-> devant lève l'ambiguite, ou alors respecte la notation MFC et renomme en m_MessageToSend;
 
Tu peux aussi éviter de caster des chaines en CString, genre ptr_bar->SetPaneText(0,CString("Connecting to gateway..." ));  
ptr_bar->SetPaneText( 0, "Connecting to gateway..." ); doit suffir, ca allège un peu, et un allergique aux MFC t'en voudra pas. Après c'est selon chacun. On pourrait reprocher de mixer du code d'interface (vue) au milieu du code du coeur du programme (document), mais bon, dans ton cas ca passe (je fait référence au SetPaneText). Tu peux oublier ce point. Surtout si t'es nivo bac+2, car les MFC, c'est pas facile, et pour un premier stage, tu t'es appliqué à écrire quelque chose de lisible, et c'est très bien. Ca manque un peu de commentaires, et ton erreur a été de ne pas les écrire tout de suite. Un commentaire ca se fait tout de suite, jamais après.
Moi je suis attaché à cette règle : si on enlève le code, les commentaires doivent permettre de retrouver l'algo.
Voilou voilou pour ce que j'ai regardé. Mais moi je trouve que ca va. Continue comme ca.


merci beaucoup, je vais donc aller suivre tes quelques conseils.
MessageToSend est bien une une DM de ma classe. Mais je pensais qu'on utilisait la notatiom "m_" que pour les DM associees a un CEdit.
Et pour la methode getBuffer, j'ai essaye mais ca ne convient pas vraiment pour ce que je veux faire. GetBuffer il me semble renvoie un pointeur sur le CString alors que ce que je veux c'est une nouvelle chaine de caratere avec le contenu du CString.
 
Merci bcp pour tes encouragements ca fait du bien.  :jap:  :hello:

Reply

Marsh Posté le 05-06-2003 à 14:18:11    

je vais peut etre quand meme continuer a utiliser

Code :
  1. if (SwitchGateway())
  2.  {
  3.   if (sends(msg))
  4.   {
  5.    return true;
  6.   }
  7.   else
  8.   {
  9.    return false;
  10.   }
  11.  }


plutot que

Code :
  1. if (SwitchGateway())
  2.  {
  3.   return (sends(msg));
  4.  }


parce que sinon ca devient encore plus casse tete de comprendre comment fonctionne le pgm [:spamafote]

Reply

Marsh Posté le 05-06-2003 à 14:18:11   

Reply

Marsh Posté le 05-06-2003 à 16:42:20    

Citation :

GetBuffer il me semble renvoie un pointeur sur le CString alors que ce que je veux c'est une nouvelle chaine de caratere avec le contenu du CString.


 
Pas besoin dans ton cas.

Code :
  1. sends( MessageToSend.GetBuffer() );


Mais je comprends pas trop ... dans ton code, où tu fais en gros un GetBuffer à la main, où est-ce que tu places le '\0' final ?
 

Code :
  1. // ici tu n'alloues pas de place pour le caractere nul
  2. char* t = (char*)malloc((MessageToSend.GetLength())*sizeof(char));
  3. // ici tu recopies, ok
  4. for (int i=0; i<MessageToSend.GetLength();i++)
  5. {
  6.    t[i] = (char)MessageToSend.GetAt(i);
  7. }
  8. // ici, tu ne mets pas le nul
  9. // et t'appelles sends ...
  10. if (sends(t))
  11. // sends recoit t ...
  12. bool GatewayComm::sends(char *msg)
  13. {
  14.     (...)
  15.     // strlen( msg ), pas de nul final, aille aille aille
  16.     if (send( s, msg, strlen(msg), 0 )== SOCKET_ERROR )


 
Ca semble marcher ... a mon avis, tu as beaucoup beaucoup de chance. En effectuant le malloc, il doit initialiser la memoire à zéro, et comme il alloue un peu plus que ce que tu demandes (puissance de 2, + mode debug), tu t'en sors bien.
Mais ca, AMHA, c'est un bug, qui se manifestera par un plantage un des ces 4. A moins que j'ai raté un épisode.
Avec GetBuffer, plus de problèmes.
 
Cela m'amène à cette remarque :  de même que malloc c'est du C et pas du C++, les char *, c'est fini.
Utilise des string, ou des CString dans ton cas. C'est fait pour, c'est plus fiable.
Perso, ta fonction sends, je transformerais même le char * msg en CString.
On peut toujours passer du char *, ca converti implicitement. Et plus besoin de caster ton code.
Enfin, pour le return sends(msg), je t'encourage à l'écrire ainsi. Ca fait partie des petites astuces qui surprennent la 1° fois, mais ensuite on y est habitué. Et même, ça fait mauvaise impression de laisser comme tu fais. T'en fait pas, tes profs sont habitués. Tu trouveras plein de sites gueulant plus ou moins sur du code où cet exemple est donné. C'est un classique, et contrairement à ce que tu crois, ça améliore la lisibilité.
 
PS : tu compiles en release ?


Message édité par HelloWorld le 05-06-2003 à 16:44:17

---------------
FAQ fclc++ - FAQ C++ - C++ FAQ Lite
Reply

Marsh Posté le 05-06-2003 à 17:32:50    

oui je compile en release. Ca change quoi en gros de compiler en release ou en debug?
 
Pour le getbuffer, j'essayerai MessageToSend.GetBuffer() demain car la j'ai un train a prendre.
 
 
Et pour le probleme du '\0' dans la fonction ou j'appele le sends je fais

Code :
  1. CString SentMessage=UserName+"\t1\t1\t1\r"
  2.      +UserName+"/48\r"
  3.      +"HHMR\r"+(ptr_gw->location)+"\r"
  4.      +"LCN/"+m_Location+"/"+(ptr_gw->location)
  5.      +"\rLAST";
  6. MessageToSend = SentMessage; //MessageToSenmd est un DM de cette classe
  7. char temp[255];
  8. i=0;
  9. while(i<SentMessage.GetLength())
  10. {
  11.  temp[i]=(char)SentMessage.GetAt(i);
  12.  i++;
  13. }
  14. temp[i]='\0';
  15. ptr_gw->MessageToSend = MessageToSend;
  16. ret = ptr_gw->sends(temp);


donc ici ca ne pose pas de probleme pour le send mais c'est vrai que je ferais peut etre bien d'allouer une taille en plus et de mettre un '\0'.  
 
Pour l'utilisation des string et CString a la place de char*, je verrai aussi ca demain mais je ne suis pas sur que  
send(s,unCString,unCString.GetLength(),0);  
enfin, je te dis quoi demain apres avoir essaye tout ca.
 
MERCI  :hello:

Reply

Marsh Posté le 05-06-2003 à 17:42:54    

HelloWorld a écrit :

[quote]Cela m'amène à cette remarque :  de même que malloc c'est du C et pas du C++, les char *, c'est fini.
Utilise des string, ou des CString dans ton cas. C'est fait pour, c'est plus fiable.
Perso, ta fonction sends, je transformerais même le char * msg en CString.
 


 
mouais... pour tout ce qui est sockets en tout cas, c'est du char* et pas autre chose, et pour cause, t'envoie pas forcement des "phrases", mais peut etre des données en hexa. alors oui les string sont modernes de nos jours, mais me vois mal mettre de l'hexa ds une string...
 
et sinon autre chose : y a un malloc avec le free qui correspond, mais plein de return possibles entre les 2, ca la fout mal, meme si les return n'arrivent jamais...
 
beaucoup plus grave par contre, surtout dans un code c++ :
 
aucun CONST !!!

Reply

Marsh Posté le 05-06-2003 à 18:39:00    

polo021 a écrit :

je vais peut etre quand meme continuer a utiliser

Code :
  1. if (SwitchGateway())
  2.  {
  3.   if (sends(msg))
  4.   {
  5.    return true;
  6.   }
  7.   else
  8.   {
  9.    return false;
  10.   }
  11.  }


plutot que

Code :
  1. if (SwitchGateway())
  2.  {
  3.   return (sends(msg));
  4.  }


parce que sinon ca devient encore plus casse tete de comprendre comment fonctionne le pgm [:spamafote]


sinon t'as aussi :

Code :
  1. if (SwitchGateway())
  2.    sends(msg)?true:false;


 
[:dehors2]


---------------
J'ai un string dans l'array (Paris Hilton)
Reply

Marsh Posté le 05-06-2003 à 18:43:53    

Sinon, pour parler sérieusement, étant donné que tu sembles tester les cas d'erreurs dans ton programme (ce qui est bien), tu as oublié de tester le cas ou WSAStartup() renvoie un code d'erreur. Imagine que ton client n'ait pas Winsock 2 d'installé sur la machine, il ne saura jamais pourquoi ton programme ne fonctionne pas.
 
Rappel des erreurs retournées par WSAStartup() en cas d'initialisation échouée :
 

Citation :


WSASYSNOTREADY Indicates that the underlying network subsystem is not ready for network communication.  
WSAVERNOTSUPPORTED The version of Windows Sockets support requested is not provided by this particular Windows Sockets implementation.  
WSAEINPROGRESS A blocking Windows Sockets 1.1 operation is in progress.  
WSAEPROCLIM Limit on the number of tasks supported by the Windows Sockets implementation has been reached.  
WSAEFAULT The lpWSAData is not a valid pointer.  


Message édité par Harkonnen le 05-06-2003 à 18:46:01

---------------
J'ai un string dans l'array (Paris Hilton)
Reply

Marsh Posté le 05-06-2003 à 19:55:32    

Harkonnen a écrit :

Sinon, pour parler sérieusement, étant donné que tu sembles tester les cas d'erreurs dans ton programme (ce qui est bien), tu as oublié de tester le cas ou WSAStartup() renvoie un code d'erreur. Imagine que ton client n'ait pas Winsock 2 d'installé sur la machine, il ne saura jamais pourquoi ton programme ne fonctionne pas.
 
Rappel des erreurs retournées par WSAStartup() en cas d'initialisation échouée :
 

Citation :


WSASYSNOTREADY Indicates that the underlying network subsystem is not ready for network communication.  
WSAVERNOTSUPPORTED The version of Windows Sockets support requested is not provided by this particular Windows Sockets implementation.  
WSAEINPROGRESS A blocking Windows Sockets 1.1 operation is in progress.  
WSAEPROCLIM Limit on the number of tasks supported by the Windows Sockets implementation has been reached.  
WSAEFAULT The lpWSAData is not a valid pointer.  




ben mon programm est fait pour tourner sur un PPC et je pense que ce sera toujours le meme. Donc pas de reel probleme de ce cote la mais je vais faire le test quand meme, ca fait plus serieux  :D  
 
 :jap:

Reply

Marsh Posté le 05-06-2003 à 21:57:26    

Moi mon avis c que niveau nomage de fonctions et variable c crade (enfin pour moi ;))
 
De plus la recup des var in registry euh pareil un poil crade de faire ca comem ca.
Une macro fonctions Initialise par exemple qui recup valeur registry, set ses var interne en fonction et init WSA, tout ca en retournant un booleen par exemple (et idem pour le cleanup) ca serait un bon debut.
 
Enfin je chipote.

Reply

Marsh Posté le 06-06-2003 à 08:59:34    


Sans le cast en CString :  
ptr_bar->SetPaneText(0,"Message received" );
error C2664: 'SetPaneText' : cannot convert parameter 2 from 'char [17]' to 'const unsigned short *'
 
et
 
sends( MessageToSend.GetBuffer(0) ); ne fonctionne pas car il ne passe a ma fonction que le premier caractere donc je vais garder mon getbuffer fait a la main [:spamafote]
 


pour les const, tu veux dire que je ferais mieux de passer le parametre de sends en const?
Et quels sont les return qui n'arrivent jamais d'apres toi? [:gratgrat]

Reply

Marsh Posté le 06-06-2003 à 09:39:39    

SetPaneText prend un LPCTSTR (si c bien un CStatusBar ton ptr_bar et que ils ont pas changer entre aide vc6 et vc.net) donc normalement devrait marcher le "ton text" sans CString, je comprend pas trop pkoi compilo te gueule.
 
Pour ta fonction sends enfin vis a vis de passer comem l'indique Helloworld, euh je vois pas en koi avoir

Code :
  1. bool GatewayComm::sends(CString& msg)


pose pb, par contre c sur qu'il faut pas appeler la fonction par

Code :
  1. sends( MessageToSend.GetBuffer(0) )


comem tu l'indiques, mais un

Code :
  1. sends( MessageToSend )


suffit


Message édité par VisualC++ le 06-06-2003 à 09:40:37
Reply

Marsh Posté le 06-06-2003 à 09:42:48    

VisualC++ a écrit :

SetPaneText prend un LPCTSTR (si c bien un CStatusBar ton ptr_bar et que ils ont pas changer entre aide vc6 et vc.net) donc normalement devrait marcher le "ton text" sans CString, je comprend pas trop pkoi compilo te gueule.
 
Pour ta fonction sends enfin vis a vis de passer comem l'indique Helloworld, euh je vois pas en koi avoir

Code :
  1. bool GatewayComm::sends(CString& msg)


pose pb, par contre c sur qu'il faut pas appeler la fonction par

Code :
  1. sends( MessageToSend.GetBuffer(0) )


comem tu l'indiques, mais un

Code :
  1. sends( MessageToSend )


suffit


oui mais la n'est pas le probleme. Je pourrais en effet passer la CString en param plutot qu'un char*
Je vois pas trop ou tu as vu que ca pouvait poser probleme. Tu as peut etre confondu MA fonction sendS et la fonction send des socket (pour cette fonction un char* est obligatoire)

Reply

Marsh Posté le 06-06-2003 à 09:46:18    

Ben au dessus de mon message tu marques sends donc c ta fonction ou alros erreur

Reply

Marsh Posté le 06-06-2003 à 09:50:31    

VisualC++ a écrit :

Ben au dessus de mon message tu marques sends donc c ta fonction ou alros erreur  


oui d'accord mais la c'est juste un probleme de convertion de CString vers char* en fait.
Que je fasse la conversion avant l'appel a sends ou que je fasse la converstion dans sends ca revient au meme, le probleme de converstion est toujours la.
 
Mais merci pour l'idee, je vais peut etre passer une CString et faire la conversion dans sends, ca me permettre de diminuer la grandeur de mon code
 
EDIT : en fait non, c'est completement nulle cette idee de convertir dans sends puisque c'est l'objet de mon deuxieme topic. Faire une fonction qui converse  
OU avais je la tete  :pfff:  
 
http://forum.hardware.fr/forum2.ph [...] h=&subcat=


Message édité par polo021 le 06-06-2003 à 09:58:28
Reply

Marsh Posté le 06-06-2003 à 10:07:07    

euh enfin pas lu l autre mais un mastring.GetBuffer(0) suivit d'un ReleaseBuffer() non :??:
 
Car si c pour le socket send c comme ca que je fait et no soucis.

Reply

Marsh Posté le 06-06-2003 à 10:11:57    

VisualC++ a écrit :

euh enfin pas lu l autre mais un mastring.GetBuffer(0) suivit d'un ReleaseBuffer() non :??:
 
Car si c pour le socket send c comme ca que je fait et no soucis.


Donc d'apres toi, je fais un sends (CString) puis dans le sends, un send (socket,CString.GetBuffer(0),CString.GetLength(),0);
 
Ben je vais essayer ca

Reply

Marsh Posté le 06-06-2003 à 10:22:08    

polo021 a écrit :


Donc d'apres toi, je fais un sends (CString) puis dans le sends, un send (socket,CString.GetBuffer(0),CString.GetLength(),0);
 
Ben je vais essayer ca


 
 :non:  

Code :
  1. bool GatewayComm::sends(CString source)
  2. {
  3. CString SentMessage;
  4. resend = true;
  5. nb_pages1 = nb_pages2;
  6. string_msg.Empty();
  7. page_number = 0;
  8. AfxMessageBox(source);
  9. ptr_bar->SetPaneText(0,CString("Sending message" ));
  10. if (send( s, (char*)source.GetBuffer(0), strlen(msg), 0 )== SOCKET_ERROR )
  11. {


beau plantage. Arret pur et simple du programme  :cry:  
 
Bon ben je sens que je vais garder mon programme pas tres oiptimise pour la converstion puis ben teanp pis [:spamafote]

Reply

Marsh Posté le 06-06-2003 à 10:38:36    

Oui mais bon tu dits toi mm GetLength() et a priori tu codes strlen(msg) ... honnetement tu es pas coherent ds les infos fournis ici (ni ds ton code il semble).

Reply

Marsh Posté le 06-06-2003 à 11:53:56    

VisualC++ a écrit :

Oui mais bon tu dits toi mm GetLength() et a priori tu codes strlen(msg) ... honnetement tu es pas coherent ds les infos fournis ici (ni ds ton code il semble).


mais c'est bien vrai, rholala
[:neowen]
 
EDIT : bah ca change pas grand chose en fait. Mon pgm envoie apparement mais je ne recois rien du serveur. Ce qui signifie que le serveur n'a pas recu la syntaxe attendue. [:spamafote]
 
MErci quand meme  :jap:


Message édité par polo021 le 06-06-2003 à 11:58:53
Reply

Marsh Posté le 06-06-2003 à 12:22:00    

polo021 a écrit :


beau plantage. Arret pur et simple du programme  :cry:  
 
Bon ben je sens que je vais garder mon programme pas tres oiptimise pour la converstion puis ben teanp pis [:spamafote]
 


 
garde tes char*... les gens ki te disent qu'il ne faut utiliser que des string et oublier définitivement les char* dès que ton prog est en c++, (a mon avis) ils ratent, en tout cas dès que ton prog utilise des fct en pur c, qui veulent donc des char* (comme les fct socket). ca veut un char*, bah utilise des char* si ca te facilite la vie.
 
autre chose : ca manque de const et de & ds le code d'en haut.
par ex, si 'source' ne sera pas modifiée, passe un const. et utilise une reference, sinon la string est copiée a l'appel de la fct.
 
le const de la fin est utile si ta méthode ne modifie aucun membre de ta classe.
 

Code :
  1. bool GatewayComm::sends(const CString &source) const


 
un code avec des const, c'est toujours mieux, et plus lisible (tant kon en abuse pas qd meme)

Reply

Marsh Posté le 06-06-2003 à 12:41:14    

Konar a écrit :


 
garde tes char*... les gens ki te disent qu'il ne faut utiliser que des string et oublier définitivement les char* dès que ton prog est en c++, (a mon avis) ils ratent, en tout cas dès que ton prog utilise des fct en pur c, qui veulent donc des char* (comme les fct socket). ca veut un char*, bah utilise des char* si ca te facilite la vie.
 
autre chose : ca manque de const et de & ds le code d'en haut.
par ex, si 'source' ne sera pas modifiée, passe un const. et utilise une reference, sinon la string est copiée a l'appel de la fct.
 
le const de la fin est utile si ta méthode ne modifie aucun membre de ta classe.
 

Code :
  1. bool GatewayComm::sends(const CString &source) const


 
un code avec des const, c'est toujours mieux, et plus lisible (tant kon en abuse pas qd meme)


et qu'est ce que ca change qu'on passe une reference ou pas? Ca ne me derange pas que mon CString soit copie au passage par parametre.
Et puis ca fait pas un peu contraste de passer une reference a un const??  :??:  
- reference : pour que ca puisse etre modifie ds la foncion,
- const : pour que ca ne soit pas modifie  
[:gratgrat]

Reply

Marsh Posté le 06-06-2003 à 12:45:19    

polo021 a écrit :


et qu'est ce que ca change qu'on passe une reference ou pas? Ca ne me derange pas que mon CString soit copie au passage par parametre.
Et puis ca fait pas un peu contraste de passer une reference a un const??  :??:  
- reference : pour que ca puisse etre modifie ds la foncion,
- const : pour que ca ne soit pas modifie  
[:gratgrat]


 
Un objet tu le passe tjrs par référence ou pointeur jamais par valeur (economie de place sur la pile). Et une référence contante ne peut être modifiée (d'où le const Truc& truc).


---------------
Le Tyran
Reply

Marsh Posté le 06-06-2003 à 12:50:09    

je vais mettre  bool sends(const char*);
mais pas la methode en const car je modifie des DM dedans   :jap:

Reply

Marsh Posté le 06-06-2003 à 14:47:20    

Citation :

SetPaneText prend un LPCTSTR (si c bien un CStatusBar ton ptr_bar et que ils ont pas changer entre aide vc6 et vc.net) donc normalement devrait marcher le "ton text" sans CString, je comprend pas trop pkoi compilo te gueule.


 
C'est parce que c'est de l'UNICODE.
LPCTSTR, où T signifie soit ANSI, soit UNICODE.
C'est un poitn que j'avais pas mentionné vu que ça va chercher un peu plus loin déjà, mais apparement t'es en UNICODE.
Donc entoure toutes des chaînes dans ton code par la macro TEXT() (ou _T() aussi, koike des fois elle passe pas celle-là).
=> ptr_bar->SetPaneText(0, TEXT( "Message received" ) );  
 
Cette macro ne fait rien en ANSI, et rajoute un L devant en UNICODE
(dans ton cas, il fait faire ptr_bar->SetPaneText(0, L"Message received" ); pour que ca marche, la macro TEXT le fait proprement).
Pour être parfait à ce sujet, faudrait mettre tes string dans une ressource ... afin d'être traduisible ... mais on chipote on chipote.
 
Dernier point, le sends, c'est comme ca :
 
send(s,unCString.GetBuffer(),unCString.GetLength(),0);  
 
konar >
vi c'est du char *, parce que les socket c'est du C. Et quand je dit de se passer des char *, c'est pour des chaînes de caractères biensûr. Son exemple n'envoie pas d'"hexa", d'où ma remarque. Mais je pense qu'on se comprend.
La seule raison valable d'utiliser les char * pour des chaînes de caractères en C++ c'est quand on se trimballe des fonctions C (qu'il faudrait préfixer par :: pour faire bien  

Code :
  1. ::send( this->s, unCString.GetBuffer(), unCString.GetLength(), 0 );


Mais les string sont bien concues et offrent une fonction pour cela, c_str pour les std::string et GetBuffer ici.


---------------
FAQ fclc++ - FAQ C++ - C++ FAQ Lite
Reply

Marsh Posté le 06-06-2003 à 15:03:20    

HelloWorld a écrit :

Citation :

SetPaneText prend un LPCTSTR (si c bien un CStatusBar ton ptr_bar et que ils ont pas changer entre aide vc6 et vc.net) donc normalement devrait marcher le "ton text" sans CString, je comprend pas trop pkoi compilo te gueule.


 
C'est parce que c'est de l'UNICODE.
LPCTSTR, où T signifie soit ANSI, soit UNICODE.
C'est un poitn que j'avais pas mentionné vu que ça va chercher un peu plus loin déjà, mais apparement t'es en UNICODE.
Donc entoure toutes des chaînes dans ton code par la macro TEXT() (ou _T() aussi, koike des fois elle passe pas celle-là).
=> ptr_bar->SetPaneText(0, TEXT( "Message received" ) );  
 
Cette macro ne fait rien en ANSI, et rajoute un L devant en UNICODE
(dans ton cas, il fait faire ptr_bar->SetPaneText(0, L"Message received" ); pour que ca marche, la macro TEXT le fait proprement).
Pour être parfait à ce sujet, faudrait mettre tes string dans une ressource ... afin d'être traduisible ... mais on chipote on chipote.
 
Dernier point, le sends, c'est comme ca :
 
send(s,unCString.GetBuffer(),unCString.GetLength(),0);  
 
konar >
vi c'est du char *, parce que les socket c'est du C. Et quand je dit de se passer des char *, c'est pour des chaînes de caractères biensûr. Son exemple n'envoie pas d'"hexa", d'où ma remarque. Mais je pense qu'on se comprend.
La seule raison valable d'utiliser les char * pour des chaînes de caractères en C++ c'est quand on se trimballe des fonctions C (qu'il faudrait préfixer par :: pour faire bien  

Code :
  1. ::send( this->s, unCString.GetBuffer(), unCString.GetLength(), 0 );


Mais les string sont bien concues et offrent une fonction pour cela, c_str pour les std::string et GetBuffer ici.
 


non non non, GetBuffer prends un parametre. Ca passe pas au compilo si je lui mets rien en parametre.
Peut etre parce que je suis en Microsoft Embedded Visual Tools 3.0 [:spamafote]
 
et je suis donc sur Pocket PC  (windows CE) donc il me semble en effet que ce soit de l'UNICODE, je vais mettre TEXT alors
 
 

Citation :


LPTSTR GetBuffer(  
int nMinBufLength );  
 
nMinBufLength  
Specifies the minimum size of the character buffer in characters. This value does not include space for a null terminator.


Message édité par polo021 le 06-06-2003 à 15:04:26
Reply

Marsh Posté le 06-06-2003 à 15:29:08    

Non c pas a cause de ta version de VC, GetBuffer y a un parametre oui qq soit l'environnement de dev.

Reply

Marsh Posté le    

Reply

Sujets relatifs:

Leave a Replay

Make sure you enter the(*)required information where indicate.HTML code is not allowed