Bienvenue aux nouveaux arrivants sur FantasPic !
- Pensez à lire les règles durant votre visite, il n'y en a pas beaucoup, mais encore faut-il les respecter .
- N’hésitez pas à faire des remarques et/ou suggestions sur le Forum, dans le but de l'améliorer et de rendre vos prochaines visites plus agréables.
- Vous pouvez regarder votre "panneau de l'utilisateur" afin de configurer vos préférences.
- Un passage par "l'utilisation du forum" est recommandé pour connaître les fonctionnalités du forum.
--- L’équipe FantasPic ---
- Pensez à lire les règles durant votre visite, il n'y en a pas beaucoup, mais encore faut-il les respecter .
- N’hésitez pas à faire des remarques et/ou suggestions sur le Forum, dans le but de l'améliorer et de rendre vos prochaines visites plus agréables.
- Vous pouvez regarder votre "panneau de l'utilisateur" afin de configurer vos préférences.
- Un passage par "l'utilisation du forum" est recommandé pour connaître les fonctionnalités du forum.
--- L’équipe FantasPic ---
Modérateur : Jérémy
un piege que si l'on s'en sert
- paulfjujo
Expert- Messages : 2597
- Âge : 73
- Enregistré en : juillet 2015
- Localisation : 01800
- Contact :
bonjour à tous,
Dans la série LES PIEGES à IONS ...
Une fois n'est pas coutume, j'ai voulu utiliser une variable unsigned char , un byte quoi .
dans une boucle for
imprime les valeurs de 0 à 254 .. NORMAL
et avec cec i
Ratio pouvant prendre les valeurs de 0 à 255 .. reste donc inferieur à 256
on pourrait s'attendre à imprimer les valeurs de 0 à 255 !
Mais Non, c'est pas fini !
Tester le ..
part en boucle sans fin et donc plante le programme !
j'ai posé la question sur MikroC Forum
ils proposent cette solution compréhensive (avec le turn over 8 bits 255+1 =0) MAIS assez dérangeante
la notion du passage au maximum 255 étant abstraite.
Habituellement je travaille toujours avec unsigned int dans les boucles for ou while ..
donc I faudra s'attendre à ce qu'un jour ,une boucle comme celle ci
parte en sucette aussi !
on en conclura qu'il ne faut pas s'approcher trop près des frontières ,
même si on est dans la Convention de Schengen !
Dans la série LES PIEGES à IONS ...
Une fois n'est pas coutume, j'ai voulu utiliser une variable unsigned char , un byte quoi .
dans une boucle for
Code : Tout sélectionner
char CRam1[20];
void CRLF(void); //just a CR LF printout
unsigned char Ratio;
....
for (Ratio=0;Ratio<255;Ratio++)
{
ByteToStr(Ratio,CRam1);
UART1_Write_Text(CRam1);
CRLF1();
}
CRLF1();
while(1);
imprime les valeurs de 0 à 254 .. NORMAL
et avec cec i
Code : Tout sélectionner
for (Ratio=0;Ratio<256;Ratio++)
{
ByteToStr(Ratio,CRam1);
UART1_Write_Text(CRam1);
CRLF1();
}
CRLF1();
while(1);
Ratio pouvant prendre les valeurs de 0 à 255 .. reste donc inferieur à 256
on pourrait s'attendre à imprimer les valeurs de 0 à 255 !
Mais Non, c'est pas fini !
Tester le ..
part en boucle sans fin et donc plante le programme !
j'ai posé la question sur MikroC Forum
ils proposent cette solution compréhensive (avec le turn over 8 bits 255+1 =0) MAIS assez dérangeante
la notion du passage au maximum 255 étant abstraite.
Code : Tout sélectionner
Ratio = 0;
do {
...
Ratio++;
} while (Ratio>0);
Habituellement je travaille toujours avec unsigned int dans les boucles for ou while ..
donc I faudra s'attendre à ce qu'un jour ,une boucle comme celle ci
Code : Tout sélectionner
unsigned int IRatio;
for (IRatio=0;Iratio<65536;IRatio++)
{
.. blablabla
}
parte en sucette aussi !
on en conclura qu'il ne faut pas s'approcher trop près des frontières ,
même si on est dans la Convention de Schengen !
un piege que si l'on s'en sert
Salut Paul,
gcc détecte l'anomalie et envoie un warning de compilation sur la ligne for
warning: comparison is always true due to limited range of data type [-Wtype-limits]
gcc détecte l'anomalie et envoie un warning de compilation sur la ligne for
warning: comparison is always true due to limited range of data type [-Wtype-limits]
Code : Tout sélectionner
for (unsigned char i=0; ; i++) {
blabla;
if (i == 255) break;
}
un piege que si l'on s'en sert
-
Jérémy
Administrateur du site- Messages : 2725
- Âge : 45
- Enregistré en : juillet 2015
- Localisation : Dans le sud
- Contact :
Bonsoir à tous,
Effectivement ce n'est pas très sérieux ça ; Je n'ai jamais rencontré ce problème, mais je me serais fait avoir et un bon moment avant de trouver .
Car pour moi, ca fait partis des acquis !
Une valeur arrive à 255 et repasse à zéro si on l'incrémente.
Merci Paul pour cette information qu'il va falloir que je retienne
Effectivement ce n'est pas très sérieux ça ; Je n'ai jamais rencontré ce problème, mais je me serais fait avoir et un bon moment avant de trouver .
Car pour moi, ca fait partis des acquis !
Une valeur arrive à 255 et repasse à zéro si on l'incrémente.
Merci Paul pour cette information qu'il va falloir que je retienne
un piege que si l'on s'en sert
Bonjour,
En effet merci pour l'info.
@++
En effet merci pour l'info.
@++
un piege que si l'on s'en sert
- paulfjujo
Expert- Messages : 2597
- Âge : 73
- Enregistré en : juillet 2015
- Localisation : 01800
- Contact :
bonsoir Satinas,
A part que MikroC NE VOIT RIEN D'ANORMAL ... pas de warning
voici le code complet de test , ci dessous
satinas a écrit :gcc détecte l'anomalie et envoie un warning de compilation sur la ligne for
warning: comparison is always true due to limited range of data type [-Wtype-limits]Code : Tout sélectionner
for (unsigned char i=0; ; i++) {
blabla;
if (i == 255) break;
}
A part que MikroC NE VOIT RIEN D'ANORMAL ... pas de warning
0 1 mikroCPIC1618.exe -MSF -DBG -pP18F26K22 -RA -C -O00000114 -fo16 -N"C:\_MikroC\_MesProjets_MikroC\18F26K22_test_for_with_byte.mcppi" -SP"C:\_MikroC\mikroC PRO for PIC\Defs\" -SP"C:\_MikroC\mikroC PRO for PIC\uses\P18\" -SP"C:\_MikroC\_MesProjets_MikroC\" -SP"C:\_MikroC\_MesProjets_MikroC\common\" -SP"C:\_MikroC\_PICKIT2\" -SP"D:\_Editeur\" "_18F26K22_test_for_byte.c" "__Lib_Math.mcl" "__Lib_MathDouble.mcl" "__Lib_System.mcl" "__Lib_Delays.mcl" "__Lib_CType.mcl" "__Lib_CString.mcl" "__Lib_CStdlib.mcl" "__Lib_CMath.mcl" "__Lib_Conversions.mcl" "__Lib_OneWire.mcl" "__Lib_ADC_K22_B.mcl" "__Lib_EEPROM_1024.mcl" "__Lib_I2C_c34b12.mcl" "__Lib_PWM_c21.mcl" "__Lib_UART_c67b67.mcl"
0 1139 Available RAM: 3875 [bytes], Available ROM: 65536 [bytes]
0 122 Compilation Started P18F26K22.c
2621 123 Compiled Successfully P18F26K22.c
0 122 Compilation Started __Lib_Delays.c
172 123 Compiled Successfully __Lib_Delays.c
0 122 Compilation Started _18F26K22_test_for_byte.c
141 1509 Generated baud rate is 19231 bps (error = 0.16 percent) _18F26K22_test_for_byte.c
171 123 Compiled Successfully _18F26K22_test_for_byte.c
0 127 All files Compiled in 62 ms
0 1144 Used RAM (bytes): 99 (3%) Free RAM (bytes): 3776 (97%) Used RAM (bytes): 99 (3%) Free RAM (bytes): 3776 (97%)
0 1144 Used ROM (bytes): 948 (1%) Free ROM (bytes): 64588 (99%) Used ROM (bytes): 948 (1%) Free ROM (bytes): 64588 (99%)
0 125 Project Linked Successfully 18F26K22_test_for_with_byte.mcppi
0 128 Linked in 47 ms
0 129 Project '18F26K22_test_for_with_byte.mcppi' completed: 297 ms
0 103 Finished successfully: 29 sept. 2017, 20:34:43 18F26K22_test_for_with_byte.mcppi
voici le code complet de test , ci dessous
Code : Tout sélectionner
#define Config "18F26K22_Fosc_interne_16MHz.cfgsch"
#define PROCESSOR "18F26K22"
#define OSCILLATEUR_INTERNE
#define POWER_SUPPLY " 5V"
#define FOSC "16.0" // MHz
#define BAUD 19200 // UART1 COM3 prolific ou COM13 Prolific
#define CLS 12
#define CR 0x0D
#define LF 10
#define TAB 9
#define BACK 8
#define Beep 7
#define Separator 0x20 // space
#ifndef Byte
#define Byte unsigned char
#endif
#ifndef Word
#define Word unsigned int
#endif
/*
CONFIG1H : $300001 : 0x0028
CONFIG2L : $300002 : 0x0019
CONFIG2H : $300003 : 0x003C
CONFIG3H : $300005 : 0x00BE
CONFIG4L : $300006 : 0x0081
CONFIG5L : $300008 : 0x000F
CONFIG5H : $300009 : 0x00C0
CONFIG6L : $30000A : 0x000F
CONFIG6H : $30000B : 0x00E0
CONFIG7L : $30000C : 0x000F
CONFIG7H : $30000D : 0x0040
*/
const int MAX_LEN2= 64;
unsigned int i,j,k,l,m,n;
unsigned char CRam1[MAX_LEN2];
unsigned char Ratio;
void Init_Hardware(void) ;
void CRLF1(void) ;
void Raz_Buffer(void) ;
void UART1_Write_CText(const char *txt);
void CRLF1()
{
UART1_Write(CR); UART1_Write(LF);
}
void UART1_Write_CText(const char *t1)
{ char cx;
do
{ cx=*(t1++);
if (cx==0) break;
UART1_Write(cx);
Delay_us(50);
}while(cx>0);
}
void Init_Hardware()
{
PORTA = 0x00;
ANSELA=0;
ANSELA.ANSA0=1; // analog input on Port RA0 voir page 154
ANSELA.ANSA1=1; // analog input on Port RA1
ANSELA.ANSA2=1; // analog input on Port RA2
TRISA = 0b11101111 ; // PORTA is RA0,1,2,3= analog input ... RA4 =Digital output RA5= Input RTC force
ANSELB=0;
PORTB = 0xFF;
TRISB = 0xFF;
CM1CON0=0;
CM2CON0=0;
PORTC=0;
ANSELC=0;
TRISC=0xFF;
TRISC.TRISC0 = 1; // DTH22 OWS
TRISC.TRISC1 = 0; // output to BT HC06 reset
// ou Synchro_SQ50
TRISC.TRISC2= 1; // PWM output
TRISC.TRISC3 = 0; // SCL I2C
TRISC.TRISC4 = 1; // SDA I2C
TRISC.TRISC7 = 1; // RX - UART1
TRISC.TRISC6 = 0; // TX - UART1
SLRCON=0; // standard rate for PORTA,B,C,D,E
}
void main()
{
OSCCON.IRCF2=1; //HFINTOSC - (16 MHz)
OSCCON.IRCF1=1;
OSCCON.IRCF0=1;
OSCCON.SCS1=1; // choix config bit preponderant sur choix par OSSCON
OSCCON.SCS0=0;
OSCTUNE=0;
OSCTUNE.PLLEN=0; // 1= avec PLL => 64Mhz ou 40Mhz 0 =sans PLL => 16Mhz
Init_Hardware() ;
UART1_Init(19200);
for (i=0;i<MAX_LEN2;i++) CRam1[i]=0;
Delay_ms(500);
UART1_Write(CLS); // Erase screen terminal :it is an option on Vbray Terminal!
Delay_ms(500);
CRLF1();
UART1_Write_CText("\r\nCas NORMAL \r\n");
for (Ratio=0;Ratio<255;Ratio++)
{
ByteToStr(Ratio,CRam1);
UART1_Write_Text(CRam1); CRLF1();
}
CRLF1();
Delay_ms(2000);
UART1_Write_CText("\r\nAvec mauvais choix (volontaire) de type de variable à transcrire\r\n");
for (Ratio=0;Ratio<255;Ratio++)
{
// Short c'est pur un signed char !
ShortToStr(Ratio,CRam1);
UART1_Write_Text(CRam1); CRLF1();
}
CRLF1();
Delay_ms(2000);
UART1_Write_CText("\r\nLe cas K \r\n");
for (Ratio=0;Ratio<256;Ratio++)
{
ByteToStr(Ratio,CRam1);
UART1_Write_Text(CRam1); CRLF1();
}
CRLF1();
while(1);
}
Qui est en ligne
Utilisateurs parcourant ce forum : Aucun utilisateur enregistré et 35 invités