Forums Rue-Montgallet.com
Rue-Montgallet.comRue-Hardware.comRue-Occasion.comRue-DVD.comRue-Jeuxvideo.comRue-AudioVideo.comRue-Telephone.comForums
S'inscrire | S'identifier |
| Recherche avancée | Aide
 
 

billylebegue Achat - Vente Informatique : pj40 Achat - Vente Divers : fougord, nemo9, russe_91, 1 utilisateur anonyme et 61 utilisateurs inconnus

 Mot :   Pseudo :  
 
Bas de page
Auteur
 Sujet :

Probleme Port SERIE avec XON/XOFF

 
n°10911
koros
Profil : Jeune recrue
Posté le 22-12-2004 à 11:04:08  profilanswer
 

Bonjour,  
 
Je veux pouvoir envoyer une chaine de caratcere (4) du port Com1 et la recevoir sur le port Com2 de mon pc (sous Linux red hat 9.0).  
Mon probleme est que ca envoi la chaine de caractere mais je ne recois que le dernier caractere envoyé.  
Cela est du au fait que si le port COM2 ne lit pas assez vite, la donnée sera ecrasé par la donnée suivante envoyé du COM1!  
Donc j'ai voulu utiliser XON/OFF qui permet de regler se probleme en retardant l'émission de caractere pour ne pas ecraser le precedent sans qu'il soit lu.  
Mais voilà il ne prends pas en compte le XON/XOFF que j'ai mis a l'interieur du programme suivant!  
 
Si vous pouvez m'aider car là je suis vraiment embeter!  
 
merci @+++  
PS: je suis obligé de le faire avec ioperm...  
 
Programme:  
...  
...  

Code :
  1. void Init_Com1(void)
  2. {
  3. outb(0x80,LCR); /* DLAB=1*/
  4. outb(0x0c,DLLB); /* 9600 bauds */
  5. outb(0x00,DLHB);
  6. outb(0x1b,LCR);  /* DLAB=0  8bits de donnee, 1 bit de stop, parite paire*/
  7. }
  8. void Emet_car(char car)
  9. {
  10. /*sleep(1);*/
  11. while((inb(LSR)&0x40)!=0x40)
  12. {printf("Buffer transmission plein \n ";};
  13. if(inb(RXD)==0x13)                                         // XON/XOFF  
  14.    {           while((inb(RXD))!=0x11);
  15.    }
  16. outb(car,TXD);
  17. }
  18. void Emet_chaine(char chaine[4])
  19. {
  20. char car_tempo;
  21. int i=0;
  22. while(i<4)
  23.    {       car_tempo=chaine[i];
  24.       Emet_car(car_tempo);
  25.       i++;
  26.    }
  27. }
  28. int main()
  29. {
  30. unsigned char val;
  31. char buffer[4]="bonj";
  32. char ecrit;
  33. /*Ouverture COM1*/
  34. val=ioperm(COM1,8,1);  // ouverture com1  
  35. if (val)
  36. {
  37.    printf("\nErreur Ioperm = %d",val);
  38.    exit(1);
  39. }
  40. else {printf("\nPort Com1 ouvert=%d\n",val);}
  41.  
  42. Init_Com1();   // Initialisation Com1  
  43.  
  44. printf("Ecriture ?\n" );
  45. scanf("%c",&ecrit);
  46. if (ecrit=='o')
  47. {
  48. Emet_chaine(buffer);
  49. }
  50. /* Fermeture Com1 */
  51. val=ioperm(COM1,8,0);
  52. if (val)
  53. {
  54.    printf("\nErreur Ioperm = %d",val);
  55.    exit(1);
  56. }
  57. else {printf("\nPort Com1 ferme=%d\n",val);}
  58.      
  59. }

 
 
 
Par contre si je mets le "SLEEP(1);" dans la fonction Emet_car() ca marche tres bien! mais je voudrai ne pas le mettre!  
Si ca peux vous aider voici le programme qui lit la chaine de caractere sur le port COM2:  
 
programme:  
 
 

Code :
  1. void Init_Com2(void)
  2. {
  3. outb(0x80,LCR); /* DLAB=1*/
  4. outb(0x0c,DLLB); /* 9600 bauds */
  5. outb(0x00,DLHB);
  6. outb(0x1b,LCR);  /* DLAB=0  8bits de donnee, 1 bit de stop, parite paire*/
  7. }
  8. char Recep_car(void)
  9. {
  10. while((inb(LSR)&0x01)!=0x01) //Attente de donnée  
  11. return (inb(RXD));
  12. }
  13. cahr *Recep_chaine(void)
  14. {
  15. char *ptr;
  16. ptr=(char *)malloc(sizeof(char));
  17. char i=0,j=0,recep_car;
  18. while(i<4)
  19.    {  recep_car=Recep_car();
  20.        *(ptr+j)=recep_car;
  21.        i++;j++;   }
  22. *(ptr+j)='\0';
  23. return (ptr);
  24. }
  25. int main()
  26. {
  27. unsigned char val;
  28. char *buffer;
  29. /*Ouverture COM2*/
  30. val=ioperm(COM2,8,1);  // ouverture com1  
  31. if (val)
  32. {
  33.    printf("\nErreur Ioperm = %d",val);
  34.    exit(1);
  35. }
  36. else {printf("\nPort Com1 ouvert=%d\n",val);}
  37.  
  38. Init_Com2();   // Initialisation Com2  
  39.  
  40. buffer=Recep_chaine();
  41. /* Fermeture Com2 */
  42. val=ioperm(COM2,8,0);
  43. if (val)
  44. {
  45.    printf("\nErreur Ioperm = %d",val);
  46.    exit(1);
  47. }
  48. else {printf("\nPort Com1 ferme=%d\n",val);}
  49.      
  50. }

n°10914
podone
POD first ONE of best game
Profil : Habitué
Posté le 22-12-2004 à 21:53:18  profilanswer
 

Je ne connais pas Linux !
Par contre, sous Windows, c'est un driver qui s'occupe de cela. Le principe est d'avoir deux buffers tournants qui sont chargés (déchargés) sous interruption.
Dans ce cas, on peut se passer des signaux du port série et ne fonctionner qu'avec Tx Rx en définissant un protocole de communication standard en demandant au serveur de fournir ses capacités de transmission (vitesses autorisées et taille maximale d'un paquet).

n°11004
Florian Ma​nach
NON aux brevets logiciels
Profil : Jeune recrue
Posté le 01-01-2005 à 12:18:43  profilanswer
 

Je suis sous linux et je cherche déséspérément un cours sur la programmation des ports série en C sous nunux.
 
koros, je sais pas répondre à ta question mais je peux néanmoins t'en poser une....
 
T'as pas des liens là dessus ?
 


---------------
Florian Manach
n°11014
Pepe Le Mo​ko
Profil : Jeune recrue
Posté le 02-01-2005 à 06:06:56  profilanswer
 

Bonjour,
 
je ne connais plus tres bien linux ( mes cours d'UNIX sont loin ) ,
 
par contre j'ai vu un truc tout bete le programme de reception n'envoie aucun XOFF, donc le programme d'emission ne recoit jamais de XOFF et envoie les caractères à toute vitesse vers le recepteur. Bien sur si tu ajoutes un sleep ca marche .
 
Il faudrait emettre un XOFF des la reception d'un caractere sur le recepteur le temps que tu fasses tous le traitement puis un XON des que tout est terminé .

Code :
  1. char Recep_car(void
  2. while((inb(LSR)&0x01)!=0x01) //Attente de donnée   
  3. return (inb(RXD)); 
  4. char *Recep_chaine(void
  5. char *ptr; 
  6. ptr=(char *)malloc(sizeof(char)); 
  7. char i=0,j=0,recep_car; 
  8. while(i<4) 
  9.    {  recep_car=Recep_car(); 
  10.        *(ptr+j)=recep_car; 
  11.        i++;j++;   } 
  12. *(ptr+j)='\0'; 
  13. return (ptr); 
  14. }


 
devient quelque chose dans le genre  

Code :
  1. char Recep_car(void
  2.     while((inb(LSR)&0x01)!=0x01) //Attente de donnée   
  3.     Emet_car(XOFF);
  4.     return (inb(RXD)); 
  5. char *Recep_chaine(void
  6.     char *ptr; 
  7.     ptr=(char *)malloc(sizeof(char)*5);  // erreur dans le malloc tu recois 4 caracteres  + le caractere de terminaison (\0)
  8.     char i=0,j=0,recep_car; 
  9.     while(i<4) 
  10.     { 
  11.         Emet_car(XON);
  12.         recep_car=Recep_car(); 
  13.        *(ptr+j)=recep_car; 
  14.        i++;j++; 
  15.     } 
  16.     *(ptr+j)='\0'; 
  17.     return (ptr); 
  18. }


 
 
par contre un petit conseil ton code est déjà un peu trop compliqué, simplifie l'écriture  
 

Code :
  1. char Recep_car(void
  2.      while((inb(LSR)&0x01)!=0x01) //Attente de donnée   
  3. Emet_car(XOFF);
  4.      return (inb(RXD)); 
  5. char *Recep_chaine(void
  6.     char *ptr; 
  7.     char i=0;
  8.     ptr=(char *)malloc(sizeof(char)*5); 
  9.    
  10.    
  11.     while(i<4) 
  12.     { 
  13.        Emet_car(XON);
  14.        ptr[i]=Recep_car();  // la notation []est plus claire   
  15.        i++;
  16.     } 
  17.     ptr[4]='\0'; 
  18.     return (ptr);  // attention de ne pas oublier de liberer le mémoire  
  19. }


 
Voilà je pense que tu as déjà une bonne piste.
 
Dernier point si mes souvenirs sont bons le protocole XON/XOFF attend un XON avant d'emettre , je suis pas sur que ton programme d'emission le fasse  
 
 
 


Aller à :
Ajouter une réponse