amis(es) pro du pic bonjourje travail sur un projet permettant de réaliser la supérvison d'une batterie à 5 cellules grace à un composant BQ2060A de texas instrument(si quelqun l'a déjà utilisé, je seré ravi d'avoir plus d'info)
mon problème est la programmation du pic 18f8722 qui va aller lire des info enregistrées dabs l'EEPROM du BQ2060A grace au bus de communication SMBus.Pour se faire je dois programmer mon pic pour une communication type I2C.
je sui complétement novice dans le domaine mais j'ai réussi a me débrouiller la ou ca coince c ke je ne c pa si jé pri la donne configuration pour l registre SSP1CON1: le pic est toujours maitre du SMBus donc j'hésite entre SSPM3:SSP0=1011 ou 1000 .qu'elle est la différence entre les deux config??(je travail avec un oscillateur externe de 8Mhz sur les broches OSC1 et OSC2)
j'ai reussi à récupéré un octet de données de l'EEPROM mais j'arrive pas a avoir le 2ème octet(alarm_test a al bonne valeur mais pas alarm_test2)
voilà mon code et des piéces jointes qui vous aideron a voir plus clair dans l'application(voir les pages 4(SMBus AC specification)9,10,18,19,20/57)
ps1: je travail en SMBus without PEC
ps2:c'est quoi la différence entre PORTC et DDRC??
merci d'avanceeeeeeeeeeee
Code:#include <p18f8722.h> #include <stdio.h> //Configuration1 #pragma config DEBUG = OFF // watchdog timer disabled #pragma config XINST = OFF #pragma config OSC = HS // oscillateur haute fréquence #pragma config FCMEN = OFF // fail-safe clock monitor disabled #pragma config IESO = OFF // two-speed start-up disabled //declaration des variables #define adresse 0b00010110 //adresse BQ en mode écriture #define ERROR_OVER_CHARGED 0x0100 // flag d'indication erreur #define ERROR_TERMINATE_CHARGE 0x0200 // flag d'indication erreur #define ERROR_OVER_TEMPERATURE 0x0400 // flag d'indication erreur #define ERROR_TERMINATE_DISCHARGE 0x0800 // flag d'indication erreur #define ERROR_REMAINING_CAPACITY 0x1000 // flag d'indication erreur #define ERROR_REMAINING_TIME 0x2000 // flag d'indication erreur char alarm_test; char alarm_test2; int i; char valid;// octet de test void COM_ERROR(void); void PostRequest(char requestcode); char requestcode; void ack(void); char lit_i2c(char comande_code); void init_i2c(void); //retourne le contenu du registre cmd dans TC74 char lit_i2c(char comande_code) { //char alarm_test; SSP1CON2bits.SEN=1; // START while (SSPCON2bits.SEN); SSP1BUF=adresse; // adresse ecriture ack(); SSP1BUF=comande_code; // code commande SMBus de la fonction à lire ack(); SSP1CON2bits.RSEN=1; // RESTART while (SSPCON2bits.RSEN); SSP1BUF=adresse|0b00000001; // adresse lecture ack(); SSP1CON2bits.RCEN=1; // passe en mode lecture d'un octet while (SSP1CON2bits.RCEN); // attend reception terminée alarm_test=SSPBUF; // mémorise msb SSP1CON2bits.ACKDT=0; // NON-ACK /*reception du deuxième octet*/ SSP1CON2bits.RCEN=1; // passe en mode lecture d'un octet while (SSP1CON2bits.RCEN); // attend reception terminée alarm_test2=SSPBUF; // mémorise msb SSP1CON2bits.ACKDT=1; // NON-ACK SSP1CON2bits.ACKEN=1; while(SSP1CON2bits.ACKEN);//attente fin acknowladge sequence enable SSP1CON2bits.PEN=1; // STOP while(SSP1CON2bits.PEN); return (alarm_test,alarm_test2); }//fin lit_i2c void init_i2c(void) { PORTCbits.RC3 = 1; // SCL (PORTC,3) en entrée PORTCbits.RC4 = 1; // SDA (PORTC,4) en entrée SSP1CON1=0b00101000; // WCOL SSPOV SSPEN CKP SSPM3:SSPM0 // efface WCOL et SSPOV, active I2C, I2C mode maitre horloge=FOSC/(4*(SSPADD+1)) SSP1CON2=0b01000000; SSP1STATbits.SMP=1; // slew rate inhibé (f<400Khz) SSP1ADD=19; // horloge =8Mhz /SMBus clock=100Khz au maximum }//fin init i2c void main(void) { init_i2c(); while (1) { // for(i=0;i<24000;i++);//tempo alarm_test=lit_i2c(0x16); if (alarm_test & 0x80) PostRequest(ERROR_OVER_CHARGED); if (alarm_test & 0x40) PostRequest(ERROR_TERMINATE_CHARGE); if (alarm_test & 0x10) // bit 5 et 2 reserves donc n'indique pas d'alarmes => pas de test PostRequest(ERROR_OVER_TEMPERATURE); if(alarm_test & 0x080) PostRequest(ERROR_TERMINATE_DISCHARGE); if(alarm_test & 0x02) PostRequest(ERROR_REMAINING_CAPACITY); if(alarm_test & 0x01) PostRequest(ERROR_REMAINING_TIME); else COM_ERROR(); } }//fin main void ack(void) // attend acknowledge (I2C) de l'esclave { while(SSP1STATbits.R_W); // attend fin de transmission while (SSP1CON2bits.ACKSTAT); // attend fin ACK esclave } void PostRequest(char requestcode) { valid=1; } void COM_ERROR(){ valid=10; }
-----