2017-10-23 9 views
2

Ich versuche mit BQ24259 über I2C mit PIC16LF1554 zu kommunizieren. Das 7. Register des Gerätes hat ein Bit, mit dem die Batterie ausgeschaltet werden kann. Ich habe Mplabs MCC verwendet, um die I2C-Einstellungen zu konfigurieren. Mit dem Beispielcode in Headerdateien habe ich eine ähnliche Funktion geschrieben.mit MPLAB's MCC, um I2C und ADC zu konfigurieren

hier ist der entsprechende Ausschnitt aus dem Code

#define RETRY_MAX  100 
    #define ON    0x4B //register 7 toggle 5th bit to turn ON/OFF 
    #define OFF    0x6B 
    I2C_MESSAGE_STATUS status; 

    uint16_t  timeOut; 
    uint8_t   writeBuffer[1];    // writeBuffer[0] = 07, writeBuffer[1] = data 01001011b(on) 01101011b(off) 
    uint8_t   stat; 
    uint16_t  address = (0x6B/2) ;   //Bit shifting to the write, and having '0' for write opertaoin, at MSB 

uint8_t bat_fet(uint8_t val){ 
    writeBuffer[0] = 7;      //slave's seventh register 
    writeBuffer[1] = val; 
    timeOut=0; 
    while(status != I2C_MESSAGE_FAIL){ 
     I2C_MasterWrite(writeBuffer,  // address of data to be sent 
         2,     // number of data bytes 
         address,   // address of the peripheral 
         &status);   // address of status register 

     while(status == I2C_MESSAGE_PENDING); 

     if(status == I2C_MESSAGE_COMPLETE){ 
      return 1; 
      break; 
     } 
     if(timeOut == RETRY_MAX){ 
      return 0; 

      break; 
     } 
     else 
      timeOut++; 
    } 
    if(status == I2C_MESSAGE_FAIL) 
     return 0; 

} 

aber seine nicht funktioniert, passiert nichts, manchmal die Steuerung nur friert, meistens ist es weiter zu arbeiten. Ich habe eine LED an einen unbenutzten IO-Pin angeschlossen und ihn so programmiert, dass er eingeschaltet wird, wenn die Funktion 1 zurückgibt und sich einschaltet. Aber die Batterie bleibt auch eingeschaltet.

Und ich versuche, ADC zu verwenden 1 des pic die Batteriespannung zu überprüfen,

hier ist der Code,

uint16_t check_bat_voltage(){ 

    uint16_t bat_v; 

    ADC1_StartConversion(01011); //i am using Channel AN11, but no matter what variation of channel and AN11 i passed, it just wouldn't recognize. so i just pass the 5 bit values of the ADCON1 register. 

    while(ADC1_IsConversionDone()); 

    bat_v = ADC1_GetConversionResult(); 

//digital value = [analog voltage/(vref+ - vref-)] * 1024 
//analog value minimum = 2.5/2, voltage divider network 
//vref+ 5 
//vref- 0 
// 1.25/5 * 1024 = 256 
    return bat_v; 
} 

aber wieder nichts passiert. Kann jemand bitte es überprüfen? Ich stecke einfach fest. Vielen Dank.

Ich kann auch Screenshots von MCC anhängen, vielleicht habe ich die Peripheriegeräte nicht richtig konfiguriert.

P.S. Ich initialisiere beide Module in main().

+0

adc funktioniert, ich habe die Werte falsch berechnet. Mein Fehler. – aamir

Antwort

0

Ich glaube, dass Ihr Problem ist, dass Sie vergessen, status etwas zu initialisieren andere als I2C_MESSAGE_FAIL vor Ihrer Schleife (Ich gehe davon aus, dass Ihre globalen stat ein Tippfehler ist - es sollte status sein).

Wenn keine Variablen mit __attribute__((persistent)) (XC16-Compiler - nicht sicher über XC8) als persistent deklariert werden, initialisiert der Startup-Code alle globalen Variablen auf Null. Da ich denke, die Konstante I2C_MESSAGE_FAIL ist nicht Null, bedeutet dies, dass Ihre Schleife nie ausgeführt wird.

Der Compiler gab wahrscheinlich eine Warnung über die Verwendung einer Variablen, bevor sie initialisiert wurde.

Verwenden Sie stattdessen eine do {} while Schleife.

+0

Ich bin nicht kreativ, wenn es darum geht, Variablen zu benennen; Status und Status sind verschiedene Variablen. Ich habe den Status auf I2C_MESSAGE_PENDING initialisiert, aber wieder passiert nichts. – aamir

+0

Ah, ich sehe die Erklärung für 'Status' jetzt. Nun, da die Initialisierung erledigt ist, ist vielleicht das Problem die Konfiguration des I2C-Ports. Ich kenne diese spezielle MPU nicht. Hat es mehr als ein I2C-Peripheriegerät? Verwendet es PPC (programmierbare Port-Konfiguration)? IMHO, ist es nützlich, keine vorgefertigten Routinen zu verwenden, da der Aufwand beim Schreiben der Raw-Port-Lese-/Schreibvorgänge zu einem besseren Verständnis der Hardware führt. – EBlake

0

vielleicht ist es ein Tippfehler in Ihren Erklärungen? versuchen zu ändern:

uint8_t writeBuffer[1]; 

zu

uint8_t writeBuffer[2]; 

empfehlen würde die scl und sda Linien Scoping und Kontrolle, was tatsächlich gesendet wird, wenn die LED leuchtet auf.