2016-07-01 13 views
1

Ich benutze einen Klon von Arduino UNO, Dccduino und ich habe ein Problem mit dem Speicher.Skizze verwendet 25.114 Bytes (77%) Programmspeicherplatz. Das Maximum ist 32.256 Bytes. Globale Variablen verwenden 1,968 Byte (96%) des dynamischen Speichers, wobei für lokale Variablen 80 Byte verbleiben. Das Maximum beträgt 2.048 Bytes. Geringer Speicher verfügbar, Stabilitätsprobleme können auftreten. Gibt es eine Möglichkeit, den Speicher über 20%, wenn nicht ich glaube, ich habe zu kaufen Arduino MegaSo verringern Sie die Speichernutzung auf Arduino Uno

Hier ist der Code zu reduzieren:

#include <OneWire.h> 
#include <DallasTemperature.h> 
#include <SPI.h> 
#include <SD.h> 
#include <Wire.h> 
#include "RTClib.h" 
#include <GPRS_Shield_Arduino.h> 
#include <SoftwareSerial.h> 

// Data wire is plugged into port 3 and 2 on the Arduino 
#define ONE_WIRE_BUS_1 3 // Many sensors on pin 3 
#define ONE_WIRE_BUS_2 2 // Many sensors on pin 2 
#define TEMPERATURE_PRECISION 9 // Lower resolution 
#define PIN_TX 7 
#define PIN_RX 8 
#define BAUDRATE 9600 
#define PHONE_NUMBER "xxxxxxxxxxxxx" 

GPRS gprsTest(PIN_TX, PIN_RX, BAUDRATE); //RX,TX,PWR,BaudRate 

// Setup a oneWire instance to communicate with any OneWire devices (not just Maxim/Dallas temperature ICs) 
OneWire oneWire1(ONE_WIRE_BUS_1); 
OneWire oneWire2(ONE_WIRE_BUS_2); 

// Pass our oneWire reference to Dallas Temperature. 
DallasTemperature sensors1(&oneWire1); 
DallasTemperature sensors2(&oneWire2); 
int numberOfDevices1; // Number of temperature devices found on pin 3 
int numberOfDevices2; // Number of temperature devices found on pin 2 
DeviceAddress tempDeviceAddress1; // We'll use this variable to store a found device address for bus 3 
DeviceAddress tempDeviceAddress2; // We'll use this variable to store a found device address for bus 2 

File myFile; 

RTC_DS3231 rtc; // Create a RealTimeClock object 


void setup(void) 
{ 

    // start serial port 
#ifndef ESP8266 
    while (!Serial); // for Leonardo/Micro/Zero 
#endif 
    Serial.begin(9600); 
    delay(3000); 
    Serial.println(F("Dallas Temperature IC Control Library Demo")); 


    Serial.print(F("Initializing SD card...")); 

    if (!SD.begin(4)) { 
    Serial.println(F("\ninitialization failed!")); 
    return; 
    } 
    Serial.println(F("initialization done.")); 

    if (! rtc.begin()) { 
    Serial.println("Couldn't find RTC"); 
    while (1); 
    } 


    if (rtc.lostPower()) { 
    Serial.println("RTC lost power, lets set the time!"); 
    // following line sets the RTC to the date & time this sketch was compiled 
    //rtc.adjust(DateTime(F(__DATE__), F(__TIME__))); 
    // This line sets the RTC with an explicit date & time, for example to set 
    // January 21, 2014 at 3am you would call: 
    // rtc.adjust(DateTime(2014, 1, 21, 3, 0, 0)); 
    } 

    /* while(!gprsTest.init()) { //gprs init 
     delay(1000); 
     Serial.print(F("init error\r\n")); 
     Serial.println(F("gprs init success"));*/ It takes 20% of dynamic memory so i cant use it 
    } 
    Serial.println(F("start to call ..."));// Call when device will start 
    gprsTest.callUp(PHONE_NUMBER); 
    Serial.println("start to send message ..."); 
    gprsTest.sendSMS(PHONE_NUMBER, "Hi device is ON"); //define phone number and text 


    // Start up the library 
    sensors1.begin(); 
    sensors2.begin(); 

    // Grab a count of devices on the wire 
    numberOfDevices1 = sensors1.getDeviceCount(); 
    numberOfDevices2 = sensors2.getDeviceCount(); 

    // locate devices on the bus 
    Serial.print(F("Locating devices...")); 

    Serial.print(F("Found ")); 
    Serial.print(numberOfDevices1, DEC); 
    Serial.print(F("+")); 
    Serial.print(numberOfDevices2, DEC); 
    Serial.println(F(" devices.")); 

    // report parasite power requirements 
    Serial.print("Parasite power is: "); 
    if (sensors1.isParasitePowerMode()) Serial.println(F("Sensors 1 ON")); 
    else Serial.println(F("\nSensors 1 OFF")); 
    if (sensors2.isParasitePowerMode()) Serial.println(F("Sensors 2 ON")); 
    else Serial.println(F("Sensors 2 OFF")); 


    // Loop through each device, print out address for pin 3 
    for (int i = 0; i < numberOfDevices1; i++) 
    { 
    // Search the wire for address 
    if (sensors1.getAddress(tempDeviceAddress1, i)) 
    { 
     Serial.print(F("Found device ")); 
     Serial.print(i, DEC); 
     Serial.print(F(" with address: ")); 
     printAddress(tempDeviceAddress1); 
     Serial.println(); 
     Serial.println(F("\n")); 
     // set the resolution to TEMPERATURE_PRECISION bit (Each Dallas/Maxim device is capable of several different resolutions) 
     sensors1.setResolution(tempDeviceAddress1, TEMPERATURE_PRECISION); 


    } else { 
     Serial.print(F("Found ghost device for pin 3 at ")); 
     Serial.print(i, DEC); 
     Serial.print(F(" but could not detect address. Check power and cabling")); 
    } 
    } 


    // Loop through each device, print out address for pin 2 
    for (int i = 0; i < numberOfDevices2; i++) 
    { 
    // Search the wire for address 
    if (sensors2.getAddress(tempDeviceAddress2, i)) 
    { 
     Serial.print(F("Found device ")); 
     Serial.print(i + numberOfDevices1, DEC); 
     Serial.print(F(" with address: ")); 
     printAddress(tempDeviceAddress2); 
     Serial.println(); 
     Serial.println(F("\n")); 
     // set the resolution to TEMPERATURE_PRECISION bit (Each Dallas/Maxim device is capable of several different resolutions) 
     sensors2.setResolution(tempDeviceAddress2, TEMPERATURE_PRECISION); 

    } else { 
     Serial.print(F("Found ghost device for pin 2 at ")); 
     Serial.print(i, DEC); 
     Serial.print(F(" but could not detect address. Check power and cabling")); 
    } 
    } 

} 



void loop(void) 
{ 
    // call sensors1.requestTemperatures() to issue a global temperature 
    // request to all devices on the bus 
    Serial.print(F("Requesting temperatures to pin 3...")); 
    sensors1.requestTemperatures(); // Send the command to get temperatures for pin 3 
    Serial.println(F("DONE")); 

    myFile = SD.open("test1.txt", FILE_WRITE); //open file 

    // Loop through each device , print out temperature data for pin 3 
    for (int i = 0; i < numberOfDevices1; i++) 
    { 
    // Search the wire for address 
    if (sensors1.getAddress(tempDeviceAddress1, i)) 
    { 
     // Output the device ID 
     Serial.print(F("Temperature for device: ")); 
     Serial.println(i, DEC); 

     // It responds almost immediately. Let's print out the data 

     printTemperature1(tempDeviceAddress1);// Use a simple function to print out the data 

     Serial.print(F("\n")); 
    } 
    delay(4000); 
    //else ghost device! Check your power requirements and cabling 
    }// End forloop for pin 3 
    if (numberOfDevices2 != 0) { 
    Serial.print(F("Requesting temperatures to pin 2...")); 
    sensors2.requestTemperatures(); // Send the command to get temperatures for pin 2 
    Serial.println(F("DONE")); 
    } 


    // Loop through each device for pin 2, print out temperature data 
    for (int i = 0; i < numberOfDevices2; i++) 
    { 
    // Search the wire for address 
    if (sensors2.getAddress(tempDeviceAddress2, i)) 
    { 
     // Output the device ID 
     Serial.print(F("Temperature for device: ")); 
     Serial.println(i + numberOfDevices1, DEC); 
     // It responds almost immediately. Let's print out the data 
     printTemperature2(tempDeviceAddress2);// Use a simple function to print out the data 
     Serial.print(F("\n")); 
    } 
    else Serial.print(F("ghost device! Check your power requirements and cabling")); 
    delay(4000); 
    } //End forloop for pin 3 

    myFile.close(); // Should I close it? 

}// End loop() 






void printAddress(DeviceAddress deviceAddress) // function to print a device address 
{ 
    for (uint8_t i = 0; i < 8; i++) 
    { 
    if (deviceAddress[i] < 16) Serial.print(F("0")); 
    Serial.print(deviceAddress[i], HEX); 
    } 
} 






void printTemperature1(DeviceAddress deviceAddress1) // function to print the temperature for a device (pin 3) 
{ 
    float tempC = sensors1.getTempC(deviceAddress1); 
    Serial.print("Temp C: "); 
    Serial.print(tempC); 
    if (myFile) 
    { 
    Serial.println(F("\nWriting to test.txt...")); 
    myFile.print(F("C: ")); 
    myFile.print(tempC); 
    print_time(); // Call print_time() function to print time on file 
    myFile.print(F("\n")); 
    Serial.print(F("Done!")); 
    } 
    else Serial.print(F("Error opening file 1")); 
    Serial.println("\n"); 
} 



void printTemperature2(DeviceAddress deviceAddress2) // function to print the temperature for a device (pin 2) 
{ 
    float tempC = sensors2.getTempC(deviceAddress2); 
    Serial.print(F("Temp C: ")); 
    Serial.print(tempC); 
    if (myFile) 
    { 
    Serial.print(F("\nWriting to test.txt...")); 
    myFile.print(F("C: ")); 
    myFile.print(tempC); 
    print_time(); // Call print_time() function to print time on file 
    myFile.print(F("\n")); 
    Serial.print(F("Done!")); 
    } else Serial.print(F("Error opening file 2")); 

    Serial.println("\n"); 
} 

void print_time() { // print time function 

    DateTime now = rtc.now(); 
    Serial.print(now.year(), DEC); 
    Serial.print('/'); 
    Serial.print(now.month(), DEC); 
    Serial.print('/'); 
    Serial.print(now.day(), DEC); 
    Serial.print(now.hour(), DEC); 
    Serial.print(':'); 
    Serial.print(now.minute(), DEC); 
    Serial.print(':'); 
    Serial.print(now.second(), DEC); 
    Serial.println(); 
    myFile.print(now.year(), DEC); 
    myFile.print('/'); 
    myFile.print(now.month(), DEC); 
    myFile.print('/'); 
    myFile.print(now.day(), DEC); 
    myFile.print(now.hour(), DEC); 
    myFile.print(':'); 
    myFile.print(now.minute(), DEC); 
    myFile.print(':'); 
    myFile.print(now.second(), DEC); 
    myFile.println(); 
} 

Antwort

1

Ich habe ich diesen Code, bevor sie auf einer anderen Seite gesehen denken . Aus Ihrem Code gehe ich davon aus, dass Sie einen Temperaturlogger erstellen und die Daten auf der SD-Karte protokollieren möchten. Der meiste Code ist redundant, wenn Sie die Bibliothek DS1307RTC.h und die Bibliothek Time.h verwenden. DS1307RTC ist eine generische RTC-Bibliothek. Mit ihr brauchen Sie nicht OneWire, Wire oder SPI und Wire. Software Serial ist auch nicht notwendig. Allerdings , empfehle ich Sie auf Github meinen Arduino Datalogger Bibliothek check out: https://github.com/FreelanceJavaDev/DataLogger

Ich habe den Speicher so ziemlich ausgereizt ich auf meinem Uno gespeichert bis zu 22.680 Bytes (70%) des Programm Speicherplatz und 1.237 Bytes (60%) von SRAM (Dynamischer Speicher). Es konfiguriert automatisch die RTC- und SD-Karte. Es macht eine CSV-Datei für den Export zu Excel für jeden Monat, der nach Datum sortiert ausgeführt wird.

0

Ich habe zu meiner Zeit mehrere Arduino-Datenlogger gebaut, und alle, die SD-Karten verwenden, sind aus Mangel an Speicher fehlgeschlagen. Die SD selbst verwendet die Hälfte des auf einem ATMega 328 verfügbaren Speichers. Fügen Sie dazu einige Bibliotheken für andere Hardware hinzu und Sie haben überhaupt keinen Speicher mehr für Ihre Skizze.

Ich bin zu 24LC512s übergegangen. Eins ist normalerweise genug, aber Sie können bis zu 4 mit verschiedenen Adressen verwenden, wenn Sie möchten. Dies ist eine relativ kleine Menge an Speicher, aber ich habe festgestellt, dass es immer genug ist. Es ist zu einfach, Megabyte an Daten zu erzeugen, die zu groß sind, um analysiert zu werden. Ein 24LC512 enthält mehr als genug Daten für eine Tabelle. Die einzige negative Seite ist, dass Sie ein Arduino verwenden müssen, um die Daten über USB zu lesen.

Ich verwende die ersten zwei Bytes, um die Anzahl der Datensätze zu speichern, und das nächste Byte, um die Anzahl der Bytes pro Datensatz zu speichern. (Obwohl im Nachhinein letzteres nicht wirklich notwendig ist.) Sie könnten denken, dass die ersten zwei Bytes "abnutzen" würden, weil sie jedes Mal neu geschrieben werden, wenn ein neuer Eintrag gemacht wird, aber das ist mir noch nicht passiert. Ich habe das gleiche Arduino seit 7 Jahren ununterbrochen laufen lassen (ununterbrochen abgesehen von einigen Aktualisierungen der Skizze), und mehr als 1000 Aufzeichnungen pro Monat erzeugend, also müssen die ersten zwei Bytes diese Anzahl von Malen aktualisiert worden sein. Ich hatte nie ein Problem mit den ersten zwei Bytes, und selbst wenn ich es tat, wäre es billig genug, um den 24LC512 zu ersetzen.

Sie können sogar mit "hot plugging" durchkommen: Ich lasse den Logger laufen und wechsle den Speicherchip um einen neuen, damit ich die Daten lesen kann, ohne den Logger zu unterbrechen. (Lesen Sie die Anzahl der Datensätze, inkrementieren Sie sie und schreiben Sie die neue Nummer und die Daten.)