- 3D-Druck Einstieg und Tipps         
Ergebnis 1 bis 10 von 15

Thema: Atmega8 ADC \ eeprom

Hybrid-Darstellung

Vorheriger Beitrag Vorheriger Beitrag   Nächster Beitrag Nächster Beitrag
  1. #1
    Neuer Benutzer Öfters hier
    Registriert seit
    12.08.2014
    Beiträge
    11

    Frage Atmega8 ADC \ eeprom

    Hi,

    nach stunden des Probierens und suchen hier meine Fragen....
    Ich möchte am Analog eingang einen Strom messen, und diesen Wert ins eeporm speichern damit ich ihn nach dem einschalten wieder habe, das Ganze wird an einer 12V 3Ah Batterie angeschloßen.

    Zum Testen hab ich Versucht and den PC0 einen Widerstand hängen und den auf die 5V vom µC gehängt, aber nach einen Spannungswert hat es mir nicht ausgesehen.. (hab es um den Wert zu sehen in den eeprom gepseichert)

    1) wie könnte ich den adc wert sonst ausgeben ohne lcd display bzw. eeprom ?

    2) Soweit ich das richtig nachgelesen habe bekomme ich vom analog eingang aber nur einen Spannungs wert und damit ich ich auf meinen Strom komme müsste das dann so aussehen
    u = ADC*5.0;
    i = u/r;

    3) Daher das eeprom auf ca. 100.000 cyclen brenzt ist, wird es nicht sinnvoll sein den Wert immer zu beschreiben.
    Meine Idee wäre so eine art dauerplus damit der µC immer unter spannung (Ruhemodus oder so) ist und der Wert im RAM somit erhalten bleibt aber geht das ohne das die Baterie gleich leer ist ?

    Code:
    #include <avr/io.h>
    #include <util/delay.h>
    #include <avr/eeprom.h>
    
    uint16_t eeLastValueAddr EEMEM = 1;
    uint16_t lastValue = 0;
    
    int main()
    {
        // Set PORTD as Output
    	DDRD = (1<<PD7)| (1<<PD6)|(1<<PD5) | (1<<PD4) | (1<<PD3) | (1<<PD2)| (1<<PD1)| (1<<PD0);
    
    	// Set PortB (PB0,PB1) as Input
        PORTB |= (1<<PB0);
    	PORTB |= (1<<PB1);
    
        // Set Reference to AVCC and input to ADC0
        ADMUX = (1<<REFS0);
    
        // Enable ADC, set prescaler to 16
        // Fadc=Fcpu/prescaler=1000000/16=62.5kHz
        // Fadc should be between 50kHz and 200kHz
        ADCSRA = (1<<ADFR)|(1<<ADEN)|(1<<ADPS2);
    
        // Start the first conversion
        ADCSRA |= (1<<ADSC);
    
        while (1)
    	{
            if (!(PINB & (1<<PB0)) && !(PINB & (1<<PB0)))
            {
                //Ruecksetzung des Wertes
    			lastValue = 0;
                eeprom_write_word (&eeLastValueAddr, lastValue);
            }
            if ((PINB & (1<<PB0)))
            {
    		    //Analog Wert lesen und in eeprom schreiben
    			lastValue = ADC;
                eeprom_write_word(&eeLastValueAddr, lastValue);
    			Set_LED();
            }
    
            //Wartezeit fuer Taster abfrage
            _delay_ms(100);
        }
    }
    
    void Set_LED()
    {
    	switch (lastValue)
    	{
    		case > 700:
    			PORTD = 0b00000000;
    			break;
    
    		case > 600:
    			PORTD = 0b10000000;
    			break;
    
    		case > 500:
    			PORTD = 0b11000000;
    			break;
    
    		case > 400:
    			PORTD = 0b11100000;
    			break;
    
    		case > 300:
    			PORTD = 0b11110000;
    			break;
    
    		case > 200:
    			PORTD = 0b11111000;
    			break;
    
    		case > 100:
    			PORTD = 0b11111100;
    			break;
    
    		case >50:
    			PORTD = 0b11111110;
    			break;
    			
    		case 0:
    			PORTD = 0b11111111;
    			break;
    	}
    }

  2. #2
    Erfahrener Benutzer Lebende Robotik Legende Avatar von PICture
    Registriert seit
    10.10.2005
    Ort
    Freyung bei Passau in Bayern
    Alter
    73
    Beiträge
    11.077
    Hallo!

    Zitat Zitat von live5 Beitrag anzeigen
    Meine Idee wäre so eine art dauerplus damit der µC immer unter spannung (Ruhemodus oder so) ist und der Wert im RAM somit erhalten bleibt aber geht das ohne das die Baterie gleich leer ist ?
    Eine Baterrie wird nach eine Zeit t = C / I leer, wobei C seine Kapazität (hier 3 Ah) und I laufender Stromverbrauch ist. Beispielweise, wenn deine Schaltung 1 mA aus der 3 Ah Batterie ständig "saugt", dann wird die Batterie theoretisch nach 3000 Stunden, also ca. 4 Monaten leer.
    MfG (Mit feinem Grübeln) Wir unterstützen dich bei deinen Projekten, aber wir entwickeln sie nicht für dich. (radbruch) "Irgendwas" geht "irgendwie" immer...(Rabenauge) Machs - und berichte.(oberallgeier) Man weißt wie, aber nie warum. Gut zu wissen, was man nicht weiß. Zuerst messen, danach fragen. Was heute geht, wurde gestern gebastelt. http://www.youtube.com/watch?v=qOAnVO3y2u8 Danke!

  3. #3
    Erfahrener Benutzer Robotik Visionär
    Registriert seit
    26.11.2005
    Ort
    bei Uelzen (Niedersachsen)
    Beiträge
    7.942
    Die µC-Schaltung kann man schon sehr sparsam machen. Mit Sleepmodes und sparsamen Regler sind Werte Deutlich unter 1mA, so um 10 µA drin. Es reicht auch nur für die Zeit zu Puffern (per Elko), die der µC zum schreiben der Daten in EEPROM braucht. Das sind eher nur ein paar Millisekunden.
    Die ausgabe zu Testzwecken geht etwa per UART an den PC (RS232).

  4. #4
    Neuer Benutzer Öfters hier
    Registriert seit
    12.08.2014
    Beiträge
    11
    ok,danke...

    eine frage hätte ich noch zum set_sleep_mode...

    Also dann würde ich z.B PC1 die AVCC (5V) messen und wenn diese unter 4.5V abfällt könnte ich ihn in den set_sleep_mode(SLEEP_MODE_PWR_DOWN) setzen.
    Wenn am INT0 wieder 5V anliegen sollte der Interrup reagieren und ihn wieder starten.

    Ist das so richtig oder habe ich einen denkfehler ?
    Geändert von live5 (12.08.2014 um 12:40 Uhr)

  5. #5
    Erfahrener Benutzer Roboter Genie
    Registriert seit
    01.03.2008
    Ort
    Niederlanden
    Beiträge
    1.170
    Du möchtest AVcc an PC1 messen. Aber gegen welcher Referenzspannung wird das passieren? Was wird den ADC-Wert 1023 definieren?


    Zurück zu deinem ersten Beitrag. Dort sagst du, du hast ein Widerstand zwischen PC0 und 5 Volt geschaltet. Und davon möchtest du ein Spannung messen, und daraus ein Strom berechnen. Was bedeutet diese Strom für dich? Was ist den Zweck? Leider geht das messen einer Spannung nicht auf diese weise. Ein Pin das als Eingang geschaltet wird ist hochohmig. Da fliest kaum Strom rein. Den Widerstand wird den Spannung an den Pin nur zu 5 Volt hoch ziehen. Und immer ein Wert in die nahe von 1023 bekommen.Wenn du ein Spannung messen möchtest, nimmst du ein Spannungsteiler aus 2 Widerstanden zwischen GND und 5 Volt. Dann den Mittelpunkt der beiden Widerstanden messen. Den Ratio der Widerstanden ist abhängig von dein Anwendung.


    Den AVR Mikrocontroller haben oft ein internen Spannungsreferenz, den man auch als Mess-eingang wählen kann. Als Referenz für den ADC wert 1023 kannst du aber auch aVcc wählen, was oft quasi gleich an Vcc angeschaltet ist. Und damit ist es möglich den Bordspannung zu messen, aber in ein invertierte Weg.
    Geändert von Valen (12.08.2014 um 22:29 Uhr)

  6. #6
    Neuer Benutzer Öfters hier
    Registriert seit
    12.08.2014
    Beiträge
    11
    Ziel wäre es einen Drucksensor anzuschließen und dessen wert einzulesen (ergibt 4-20mA aus)
    Ich habe mich jetzt nur mal auf das einlesen des ADC konzentriert, bei mir wären 5V = 1023

    Mein aktuelles Problem ist das der ADC wert > 205 und < 409 ist und das Immer sogar wenn nichts angeschlossen ist ?
    Ich konnte den Fehler noch nicht finden, daher ich noch kein Poti habe verwende ich verschiedene widerstände.

    Code:
    #include <avr/io.h>
    #include <util/delay.h>
    #include <avr/eeprom.h>
    
    uint16_t lastValue = 0;
    uint16_t ADC_Read(uint8_t channel);
    
    int main()
    {
      // Set PORTD as Output
      DDRD = (1<<PD7)| (1<<PD6)|(1<<PD5) | (1<<PD4) | (1<<PD3) | (1<<PD2)| (1<<PD1)| (1<<PD0);
      PORTD |= ((1 << PD7) | (1 << PD6) |(1<<PD5) | (1<<PD4) | (1<<PD3) | (1<<PD2)| (1<<PD1)| (1<<PD0));
    
      ADC_init();
    
      while (1)
      {
        //0V = 0
        //1V = 205
        //2V = 409
        //3V = 614
        //4V = 816
        //5V = 1023
        //Vgemessen=lastValue*5/1024;
    
        lastValue = ADC_Read(0);
        if (lastValue = 0) {
           PORTD = 0b11111111;
        }
        else if (lastValue > 205) {
           PORTD = 0b11111110;
        }
        else if (lastValue < 409) {
          PORTD = 0b11111100;
        }
        else if (lastValue > 614) {
           PORTD = 0b11111000;
        }
        else if (lastValue > 816) {
          PORTD = 0b11110000;
        }
        else if (lastValue > 1023) {
          PORTD = 0b11100000;
        }
        }
    }
    
    /* ADC initialisieren */
    void ADC_init(void) {
        // die Versorgungsspannung AVcc als Refernz wählen:
        ADMUX = (1<<REFS0);
        // oder interne Referenzspannung als Referenz für den ADC wählen:
        //ADMUX = (1<<REFS1) | (1<<REFS0);
        // Bit ADFR ("free running") in ADCSRA steht beim Einschalten
        // schon auf 0, also single conversion
        ADCSRA = (1<<ADPS1) | (1<<ADPS0);     // Frequenzvorteiler
        ADCSRA |= (1<<ADEN);                  // ADC aktivieren
    
        /* nach Aktivieren des ADC wird ein "Dummy-Readout" empfohlen, man liest
         also einen Wert und verwirft diesen, um den ADC "warmlaufen zu lassen" */
    
    
        ADCSRA |= (1<<ADSC);                  // eine ADC-Wandlung
        while (ADCSRA & (1<<ADSC) ) {         // auf Abschluss der Konvertierung warten
        }
    
        /* ADCW muss einmal gelesen werden, sonst wird Ergebnis der nächsten
         Wandlung nicht übernommen. */
        (void) ADCW;
    }
    
    /* ADC Einzelmessung */
    uint16_t ADC_Read(uint8_t channel)
    {
        // Kanal waehlen, ohne andere Bits zu beeinflußen
        ADMUX = (ADMUX & ~(0x1F)) | (channel & 0x1F);
        ADCSRA |= (1<<ADSC);            // eine Wandlung "single conversion"
        while (ADCSRA & (1<<ADSC) ) {   // auf Abschluss der Konvertierung warten
        }
        return ADCW;                    // ADC auslesen und zurückgeben
    }
    Klicke auf die Grafik für eine größere Ansicht

Name:	Drawing1.jpg
Hits:	10
Größe:	51,9 KB
ID:	28892

Ähnliche Themen

  1. ATMega32, Werte vom ADC ins EEPROM
    Von Spessi im Forum C - Programmierung (GCC u.a.)
    Antworten: 9
    Letzter Beitrag: 13.11.2008, 00:12
  2. ATMega8 + EEPROM
    Von Bumbum im Forum C - Programmierung (GCC u.a.)
    Antworten: 6
    Letzter Beitrag: 14.06.2008, 23:00
  3. I2C-EEprom an ATMega8
    Von .Johannes. im Forum AVR Hardwarethemen
    Antworten: 1
    Letzter Beitrag: 08.06.2006, 14:42
  4. ATmega8 aus dem EEPROM lesen und ins EEPROM Schreiben
    Von melowtrax im Forum AVR Hardwarethemen
    Antworten: 6
    Letzter Beitrag: 20.02.2006, 23:32
  5. Messwerte aus ADC in internem EEPROM vom ATMega8 abspeichern
    Von RalfP im Forum Basic-Programmierung (Bascom-Compiler)
    Antworten: 5
    Letzter Beitrag: 28.10.2005, 17:43

Stichworte

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •  

LiFePO4 Speicher Test