body:
i made a weather station which is build on a ATmega2560 mini pro, Esp8266 module which communicate with atmega on serial1 which sends values to thingspeak, an TSL2561, 2.4 tft lcd, BMP180, DHT22 and a dust sensor module PMS5003 which is set on serial3 on mega2560.
I made the wiring, program etc. the weather station is working fine for some days when it freezes. The problem is that thingspeak reports that it receive some data every 6 mins like i set it but the data received is blank. Not 0, or any other value, just blank data.
I'm thinking it could be a problem with SRAM since it loses the values it reads. But why the loop is still working since it sends blank data to thingspeak ?

Atmega reads all values from sensors, then communicates with esp8266 by serial and using AT commands it sends the values read to thingspeak. So in my opinion it reads the values, but it won't stores them, then it sending blank data to thingspeak.
If i reset the arduino it works fine for some days when suddenly it decides to stop working.

After compiling the program the arduino ide is reporting this:

Sketch uses 28,890 bytes (11%) of program storage space. Maximum is 253,952 bytes.
Global variables use 1,800 bytes (21%) of dynamic memory, leaving 6,392 bytes for local variables. Maximum is 8,192 bytes.

So, my program it's not filling the SRAM.
I'm a beginner in C++ so i tried to do my best with programming.

Link to thingspeak weather station: https://thingspeak.com/channels/116912

The code:

    #include <SFE_BMP180.h>
    #include <Wire.h>
    #include <DHT.h>
    #include <Adafruit_Sensor.h>
    #include <Adafruit_TSL2561_U.h>
    #include <Adafruit_GFX.h>    // Core graphics library
    #include "SWTFT.h" // Hardware-specific library

    #define DHTPIN 25     // what pin we're connected to
    #define DHTTYPE DHT22   // DHT 22  (AM2302)
    #define ALTITUDE 320.0 // Altitude in Grasse

    // Assign human-readable names to some common 16-bit color values:
    #define  BLACK   0x0000
    #define BLUE    0x001F
    #define RED     0xF800
    #define GREEN   0x07E0
    #define CYAN    0x07FF
    #define MAGENTA 0xF81F
    #define YELLOW  0xFFE0
    #define WHITE   0xFFFF

    SWTFT tft;

    DHT dht(DHTPIN, DHTTYPE); //// Initialize DHT sensor for normal 16mhz Arduino
    SFE_BMP180 pressure;

    Adafruit_TSL2561_Unified tsl = Adafruit_TSL2561_Unified(TSL2561_ADDR_FLOAT, 12345);

    //double bmptemp; //temp bmp rectificata cu 1.9 grade -
    float hum;  //Stores humidity value
    float temp; //Stores temperature value
    float lux; //Stores lux luminosity
    char status; //used by bmp180
    double T,P,p0; //p0 - sea-level compensated pressure in mb, T - temperature, P = absolute pressure in mb

    #define IP "184.106.153.149" // thingspeak.com IP address; see their website for more detail
    String GET = "GET /update?key=NWHWO6SLWNJP3HGQ"; // you channel will have unique code
    int concentration=0;

    //cod dust sensor
    #define LENG 31   //0x42 + 31 bytes equal to 32 bytes
    unsigned char buf[LENG];

    int PM01Value=0;          //define PM1.0 value of the air detector module
    int PM2_5Value=0;         //define PM2.5 value of the air detector module
    int PM10Value=0;         //define PM10 value of the air detector module

    void setup() {

      pinMode(17, OUTPUT); //pin pt esp - on /off
      pinMode(16, OUTPUT); //pin buzzer
      pinMode(31, OUTPUT); //pin on/off dust sensor

      Serial.begin(9600); // this is to start serial monitoring with your Arduino IDE Serial monitor.
      Serial1.begin(9600); // this is to start serial communication with the ESP via Software Serial.
      Serial3.begin(9600); //serial dust sensor

      Serial.println("Begin");
      tft.reset();
      uint16_t identifier = tft.readID();
      tft.begin(identifier);

      dht.begin();

      if (!pressure.begin()) {
        Serial.println("BMP180 init fail"); // Oops, something went wrong, this is usually a connection problem,
        while(1); // Pause forever.
        }

      if(!tsl.begin()) {
        /* There was a problem detecting the ADXL345 ... check your connections */
        Serial.print("Ooops, no TSL2561 detected ... Check your wiring or I2C ADDR!");
        while(1);
      }
      //tsl.setGain(TSL2561_GAIN_1X);      /* No gain ... use in bright light to avoid sensor saturation */
      //tsl.setGain(TSL2561_GAIN_16X);     /* 16x gain ... use in low light to boost sensitivity */
      tsl.enableAutoRange(true);            /* Auto-gain ... switches automatically between 1x and 16x */
      tsl.setIntegrationTime(TSL2561_INTEGRATIONTIME_402MS);  /* 16-bit data but slowest conversions */

    }

    void loop() {
      digitalWrite(31, LOW);
      digitalWrite(17, LOW);
      Serial.println("-----------------------");
      dht22 ();
      bmp120 ();
      tsl2561();
      dust();
      Serial.println("-----------------------");

      tft.fillScreen(BLACK);
      tft.setRotation(1);
      tft.setCursor(0, 0);

      tft.setTextColor(GREEN);
      tft.setTextSize(2);
      tft.println("DHT22");
      tft.setTextColor(WHITE);
      tft.setTextSize(2);
      tft.print("Temperature = ");
      tft.print(temp);
      tft.println(" C");
      tft.print("Humidite = ");
      tft.print(hum);
      tft.println(" %");
      tft.println();

      tft.setTextColor(GREEN);
      tft.setTextSize(2);
      tft.println("BMP180");
      tft.setTextColor(WHITE);
      tft.setTextSize(2);
      tft.print("Temperature = ");
      tft.print(T);
      tft.println(" C");
      tft.print("Pression = ");
      tft.print(p0);
      tft.println(" mb");
      tft.println();

      tft.setTextColor(GREEN);
      tft.setTextSize(2);
      tft.println("TSL2561");
      tft.setTextColor(WHITE);
      tft.setTextSize(2);
      tft.print("Luminosite = ");
      tft.print(lux);
      tft.println(" Lux");
      tft.println();

      tft.setTextColor(GREEN);
      tft.setTextSize(2);
      tft.println("Pollution aux particules");
      tft.setTextColor(WHITE);
      tft.setTextSize(2);
      //tft.println("Concentration - ug/m3");
      tft.print("PM1.0: ");
      tft.print(PM01Value);
      tft.println(" ug/m3");
      tft.print("PM2.5: ");
      tft.print(PM2_5Value);
      tft.println(" ug/m3");
      tft.print("PM10: ");
      tft.print(PM10Value);
      tft.println(" ug/m3");
      //tft.println("Pcs/0.01cf");

      String tempdht22 = String(temp);// turn integer to string
      String humdht22 = String(hum);
      String tempbmp180 = String(T);
      String pressbmp180 = String(p0);
      String lum = String(lux);
      String pol01 = String(PM01Value);
      String pol25 = String(PM2_5Value);
      String pol10 = String(PM10Value);
      esp8266(tempdht22, humdht22, tempbmp180, pressbmp180, lum, pol01, pol25, pol10);
      Serial.println("Waiting..");
      delay(300000);

    }

    void dht22 () {
    //Read data and store it to variables hum and temp
        hum = dht.readHumidity();
        temp= dht.readTemperature();
        //Print temp and humidity values to serial monitor
        Serial.print("Humidity: ");
        Serial.print(hum);
        Serial.println(" % ");
        Serial.print("Temp: ");
        Serial.print(temp);
        Serial.println(" C");
    }

    //cod pt dust sensor
    void dust () {
      digitalWrite(31, HIGH);
      Serial.println("High Pms5003");
      delay(5000);
      for (int i=0; i <= 60; i++){
      if(Serial3.find(0x42)){    //start to read when detect 0x42
        Serial3.readBytes(buf,LENG);

        if(buf[0] == 0x4d){
          if(checkValue(buf,LENG)){
            PM01Value=transmitPM01(buf); //count PM1.0 value of the air detector module
            PM2_5Value=transmitPM2_5(buf);//count PM2.5 value of the air detector module
            PM10Value=transmitPM10(buf); //count PM10 value of the air detector module
          }
        }
      }

      Serial.print("PM1.0: ");
      Serial.print(PM01Value);
      Serial.println("  ug/m3");

      Serial.print("PM2.5: ");
      Serial.print(PM2_5Value);
      Serial.println("  ug/m3");

      Serial.print("PM10: ");
      Serial.print(PM10Value);
      Serial.println("  ug/m3");
      Serial.println();
      delay(1000);
      }
      delay(1000);
      Serial.println("Low Pms5003");
      digitalWrite(31, LOW);
    }

    char checkValue(unsigned char *thebuf, char leng)
    {
      char receiveflag=0;
      int receiveSum=0;

      for(int i=0; i<(leng-2); i++){
      receiveSum=receiveSum+thebuf[i];
      }
      receiveSum=receiveSum + 0x42;

      if(receiveSum == ((thebuf[leng-2]<<8)+thebuf[leng-1]))  //check the serial data
      {
        receiveSum = 0;
        receiveflag = 1;
      }
      return receiveflag;
    }

    int transmitPM01(unsigned char *thebuf)
    {
      int PM01Val;
      PM01Val=((thebuf[3]<<8) + thebuf[4]); //count PM1.0 value of the air detector module
      return PM01Val;
    }

    //transmit PM Value to PC
    int transmitPM2_5(unsigned char *thebuf)
    {
      int PM2_5Val;
      PM2_5Val=((thebuf[5]<<8) + thebuf[6]);//count PM2.5 value of the air detector module
      return PM2_5Val;
      }

    //transmit PM Value to PC
    int transmitPM10(unsigned char *thebuf)
    {
      int PM10Val;
      PM10Val=((thebuf[7]<<8) + thebuf[8]); //count PM10 value of the air detector module
      return PM10Val;
    } //cod dust sensor

    void bmp120 () {
      status = pressure.startTemperature();
      if (status != 0)
      {
        // Wait for the measurement to complete:
        delay(status);

        // Retrieve the completed temperature measurement:
        // Note that the measurement is stored in the variable T.
        // Function returns 1 if successful, 0 if failure.

        status = pressure.getTemperature(T);
        if (status != 0)
        {
          // Print out the measurement:
          Serial.print("Temp2: ");
          Serial.print(T);
          Serial.println(" C ");

          // Start a pressure measurement:
          // The parameter is the oversampling setting, from 0 to 3 (highest res, longest wait).
          // If request is successful, the number of ms to wait is returned.
          // If request is unsuccessful, 0 is returned.

          status = pressure.startPressure(3);
          if (status != 0)
          {
            // Wait for the measurement to complete:
            delay(status);

            // Retrieve the completed pressure measurement:
            // Note that the measurement is stored in the variable P.
            // Note also that the function requires the previous temperature measurement (T).
            // (If temperature is stable, you can do one temperature measurement for a number of pressure measurements.)
            // Function returns 1 if successful, 0 if failure.

            status = pressure.getPressure(P,T);
            if (status != 0)
            {

              // The pressure sensor returns abolute pressure, which varies with altitude.
              // To remove the effects of altitude, use the sealevel function and your current altitude.
              // This number is commonly used in weather reports.
              // Parameters: P = absolute pressure in mb, ALTITUDE = current altitude in m.
              // Result: p0 = sea-level compensated pressure in mb

              p0 = pressure.sealevel(P,ALTITUDE); // we're at 1655 meters (Boulder, CO)
              Serial.print("Pressure: ");
              Serial.print(p0);
              Serial.println(" mb");
            }
            else Serial.println("error retrieving pressure measurement\n");
          }
          else Serial.println("error starting pressure measurement\n");
        }
        else Serial.println("error retrieving temperature measurement\n");
      }
      else Serial.println("error starting temperature measurement\n");
    }

    void tsl2561 () {
      /* Get a new sensor event */
      sensors_event_t event;
      tsl.getEvent(&event);

      /* Display the results (light is measured in lux) */
      if (event.light)
      {
        Serial.print(event.light); Serial.println(" lux"); lux = event.light;
      }
      else
      {
        /* If event.light = 0 lux the sensor is probably saturated
           and no reliable data could be generated! */
        Serial.println("0 lux");
      }
    }

    void esp8266( String temp1, String humm, String temp2, String pression, String luminosite, String pol001, String pol025, String pol010) {
      //update value on thingspeak
      digitalWrite(17, HIGH);
      Serial.println("High ESP8266");
      delay(4000);
      Serial1.println("AT+RST"); // this resets the ESP8266.
      Serial.println("AT+RST"); // this is just echoing the command to your serial monitor so you can follow what is going on
      delay(2000);
      Serial1.println("AT");
      Serial.println("AT");
      delay(5000);
      if(Serial1.find("OK")){
          Serial.println("OK");
          Serial.println("Connected");
      }

      Serial.println("in the update loop");
      //ESP8266.println("AT+RST"); // it seems that mine works better if I reset it everytime before I do CIPSTART
      //Serial.println("AT+RST");
      //delay(5000);
      String cmd = "AT+CIPSTART=\"TCP\",\""; //standard code. see https://github.com/espressif/esp8266_at/wiki //
      cmd += IP; // += is concatenating the previous cmd string with the content of IP
      cmd += "\",80"; // same thing here it just keep adding stuff to the cmd string content
      Serial1.println(cmd);//type in the string in cmd into the ESP8266
      Serial.println(cmd);
      delay(1000);

      if(Serial1.find("Error")){
        Serial.println("AT+CIPSTART Error");
        digitalWrite(16, HIGH);
        delay(250);
        digitalWrite(16, LOW);
        return;
      }
      cmd = GET + "&field1=" + temp1 + "&field2=" + humm + "&field3=" + temp2 + "&field4=" + pression + "&field5=" + luminosite + "&field6=" + pol001 + "&field7=" + pol025 + "&field8=" + pol010 + "\r\n\r\n";
      Serial1.print("AT+CIPSEND=");
      Serial1.println(cmd.length());
      Serial.print("AT+CIPSEND=");
      Serial.println(cmd.length());
      delay(1000);
      if(Serial1.find(">")){ // if ESP8266 return the > prompt back from the CIPSEND command, you are set, if not something is wrong
        Serial1.print(cmd); //type in the GET command string and done
        Serial.print(">");
        Serial.println(cmd);
        Serial.println("OK Sent");
      }
      else
      {
       Serial.println("AT+CIPSEND error");
        digitalWrite(16, HIGH);
        delay(250);
        digitalWrite(16, LOW);
      }
      delay(1000);
      digitalWrite(17, LOW);
      Serial.println("Low ESP8266");
    }

Here i uploaded the data file from thingspeak. You can see that until 2016-06-17 14:58:00 UTC it was working fine then thingspeak started receiving blank data. It received something but only blank data.
The weather station is in another location so i don't have acces all time to reset it.
http://www.filedropper.com/feeds8

[Shown below are some lines from the front, the transition point, and the end of the [feeds (8).csv](http://www.filedropper.com/feeds8) file at Andrei's filedropper link. – jw]

    created_at,entry_id,field1,field2,field3,field4,field5,field6,field7,field8
    2016-06-16 05:50:45 UTC,1,19.10,92.70,20.80,1003.02,1512.00,8,15,15
    2016-06-16 05:55:07 UTC,2,19.00,94.00,20.91,1003.09,1659.00,41,54,61
    2016-06-16 06:01:32 UTC,3,19.10,92.70,20.98,1003.11,2233.00,6,7,12
    2016-06-16 06:07:57 UTC,4,19.00,92.90,21.16,1003.11,2620.00,6,7,11
    2016-06-16 06:14:22 UTC,5,19.10,92.70,21.19,1002.97,2701.00,6,6,12
    2016-06-16 06:20:48 UTC,6,19.10,92.20,21.44,1002.97,2973.00,220,291,327
    2016-06-16 06:27:13 UTC,7,19.30,92.20,21.47,1002.99,3197.00,5,6,7
    ...
    2016-06-17 14:19:30 UTC,305,22.70,50.50,23.43,1013.88,1956.00,1,1,1
    2016-06-17 14:25:55 UTC,306,22.60,51.20,23.27,1013.88,1979.00,1,1,1
    2016-06-17 14:32:20 UTC,307,22.70,50.10,23.18,1014.00,1962.00,1,1,1
    2016-06-17 14:38:45 UTC,308,22.70,49.50,23.17,1014.03,1967.00,1,1,1
    2016-06-17 14:45:10 UTC,309,22.50,50.90,23.55,1014.01,1856.00,2,2,2
    2016-06-17 14:51:35 UTC,310,22.60,51.80,23.62,1013.99,1870.00,1,1,1
    2016-06-17 14:58:00 UTC,311,22.60,50.80,23.21,1013.94,1987.00,1,2,2
    2016-06-17 15:04:26 UTC,312,"",,,,,,,
    2016-06-17 15:10:51 UTC,313,"",,,,,,,
    2016-06-17 15:17:16 UTC,314,"",,,,,,,
    2016-06-17 15:23:41 UTC,315,"",,,,,,,
    2016-06-17 15:30:06 UTC,316,"",,,,,,,
    2016-06-17 15:36:31 UTC,317,"",,,,,,,
    2016-06-17 15:42:56 UTC,318,"",,,,,,,
    ...
    2016-06-17 22:59:18 UTC,386,"",,,,,,,
    2016-06-17 23:05:43 UTC,387,"",,,,,,,
    2016-06-17 23:12:08 UTC,388,"",,,,,,,
    2016-06-17 23:18:33 UTC,389,"",,,,,,,
    2016-06-17 23:24:58 UTC,390,"",,,,,,,
    2016-06-17 23:31:23 UTC,391,"",,,,,,,
    2016-06-17 23:37:48 UTC,392,"",,,,,,,
    2016-06-17 23:44:13 UTC,393,"",,,,,,,

I went and saw the station, it's more like an electrical problem imo because if i reset arduino nothing happens. The data readed by arduino on dht22 is nan and the rest of the sensors is working fine. The only way i could make dht22 reading again is to unplug the power and plug it back. So that's why i think it's more an electrical problem but can't figure why dht22 stops responding and need to switch off all power to bring it back to life. I will try putting an capacitor on wires to dht22 to see if it's better.

title: Atmega2560 + weather station freezing

Answers: 1

body:
You may have a power problem, but with all those libraries, I would also suspect memory issues with `String`.  The percentages reported by the IDE do not show actual `String` memory usage, just the declared variables and double-quoted string constants, like `"BMP180 init fail"`.

I think those humidity sensors have a heating cycle, so maybe they're causing a power sag, or maybe the sketch has run amok and is constantly requesting conversions.

Regardless, instead of building a `String` to be printed all at once, just print the pieces.  That is, instead of this:

    String cmd = "AT+CIPSTART=\"TCP\",\"";
      cmd += IP;
      cmd += "\",80";
      Serial1.println(cmd);

...do this:

    Serial1.println( F("AT+CIPSTART=\"TCP\",\"") );
    Serial1.print( IP );
    Serial1.print( F("\",80") );

This saves copying bytes into buffers, reallocating `String`s, copying them to the output buffer... yuck.

The `F("x bytes")` macro also saves x bytes of RAM each time you use it on a double-quoted string constant!

And this:

    cmd = GET + "&field1=" + temp1 + "&field2=" + humm + "&field3=" + temp2 + "&field4=" + pression + "&field5=" + luminosite + "&field6=" + pol001 + "&field7=" + pol025 + "&field8=" + pol010 + "\r\n\r\n";

OMG.  Use separate `Serial1.print` statements and `F()` macros.  However, because you have to send the command length first to the ESP8266, don't pass them in as `String`s, pass them as ints or floats, and add up the individual string lengths.

There are several ways to do this, depending on the old RAM-vs-speed tradeoff.  Here's a minimal RAM approach:

      //  Pass in values, not Strings
      esp8266( temp, hum, T, p0, lux, PM01Value, PM2_5Value, PM10Value );
    }
        ...

    void esp8266( float temp1, float humm, float temp2, float pression, float luminosite, int pol001, int pol025, int pol010 )
    {
        ...

      //  Start with the fixed-length string constants:
      //     GET + 8 * "&field#" + line termination
      size_t cmdLength = strlen(GET) + 8 * 8 + 4;

      //  Convert each value to a char array to see how big each one is...
      char buf[16]; // to hold temporary "char strings"

      unsigned char decimalPlaces = 2;
      dtostrf( temp1, (decimalPlaces + 2), decimalPlaces, buf);
      cmdLength += strlen(buf);

      dtostrf( humm, (decimalPlaces + 2), decimalPlaces, buf);
      cmdLength += strlen(buf);

      dtostrf( temp2, (decimalPlaces + 2), decimalPlaces, buf);
      cmdLength += strlen(buf);
         ...
      itoa( pol10, buf, 10 );  // value, char *, base
      cmdLength += strlen(buf);

      //  Now we know the total length
      Serial1.print("AT+CIPSEND=");
      Serial1.println( cmdLength ); //  <-- calculated!
      delay(1000);

      if (Serial1.find(">")) {

        // send all the same pieces of the GET command
        Serial1.print( GET );

        Serial1.print( F("&field1=") );
        dtostrf( temp1, (decimalPlaces + 2), decimalPlaces, buf);
        Serial1.print( buf );

        Serial1.print( F("&field2=") );
        dtostrf( humm, (decimalPlaces + 2), decimalPlaces, buf);
        Serial1.print( buf );

        Serial1.print( F("&field3=") );
        dtostrf( temp2, (decimalPlaces + 2), decimalPlaces, buf);
        Serial1.print( buf );
            ...
        itoa( pol010, buf, 10 );  // value, char *, base
        Serial1.print( buf );

        Serial1.print( F("\r\n\r\n") );

**NOTE:** It is important that you use the *same* technique to calculate the length of one piece *and* to print that piece.  Here, the same `dtostrf` call with the same `decimalPlaces` is used for each piece.  Ditto for `itoa`.

The speed penalty is that you convert each parameter twice, but this is probably still quicker than all the alloc/realloc/delete/copy that `String` was doing.

The RAM advantage is that you are using only 16 bytes for `buf` instead of hundreds of bytes on the heap (that's where `String` actually stores its characters).

The program space advantage is about 1600 bytes for *not* using the `String` library.

I hope you now see that the apparent "convenience" of using the `String` class has real costs in speed, RAM and program size.  `String` also affects the long-term stability of your program: you get weird crashes, hangs or string values.


body:
I'm trying to rename pins so that they post as some kind of alpha-numeric combination in a database.  For example, if I define the following....

    #define APLHA 0
    #define BRAVO 2
    #define CHARLIE 5
    #define DELTA 6

...I would like to rename the output of the pins, as recorded in the db, as something other than 0, 2, 5, and 6 (or whatever pin is used). Let's say A, B,C, and D for the purposes of this exercise.

Is this just as simple as creating if() function that is called upon prior to posting to the db (ex. if 0 then A, if 2, then B, etc)?  I feel like there must be a better, dare I say more elegant(?), way of doing this?

Current output:

PIN | VALUE

0  |   1

 2  |   1

 5  |   0

 6  |   0

Desired:

PIN | VALUE

 A  |   1

 B  |   1

 C  |   0

 D  |   0

title: Renaming pins in sketch

Answers: 1

body:
If I understood your question correctly, you're looking for something like this:

    static const byte PIN_NUMBER[4] = { 0, 2, 5, 6 };
    static const char *PIN_NAME[4] = { "A", "B", "C", "D" };

    // and use them like this:

    void Log(byte index)
    {
      byte val = digitalRead(PIN_NUMBER[index]);
      Serial.print(PIN_NAME[index]);
      Serial.print('|');
      Serial.println(val);
    }

    void setup()
    {
      for (byte i = 0; i < 4; ++i) pinMode(PIN_NUMBER[i], INPUT);
    }

    void loop()
    {
      Serial.println("PIN|VALUE");
      for (byte i = 0; i < 4; ++i) Log(i);
      delay(1000);
    }

Also, in the special case of "A", "B", "C", "D" as pin names, you don't really need the `PIN_NAME` array, instead of

    Serial.print(PIN_NAME[index]);

you can use:

    Serial.print('A' + index);


body:
I recently bought an MFRC522 RFID module to use with my Arduino Uno, which came as a kit with a couple of MiFare 1K cards.

The issue I've been having is that, I cannot scan cards consecutively (the same card or two different ones) without resetting the Sketch.  I hold a card in front of the reader and it is scanned, but when I hold another card in front of the reader it just doesn't recognize it as being there in the `mfrc522.PICC_IsNewCardPresent()` function.  It does however work when using the example sketch "DumpInfo".

Here is the code I've written (please excuse any of my bad practices/untidiness).

    /* Include Required Libraries */
    #include <MFRC522.h>
    #include <SPI.h>

    /* Define Values for MFRC522 */
    #define RST_PIN 9
    #define SS_PIN 10

    /* Instantiate the MFRC522 Object */
    MFRC522 mfrc522(SS_PIN, RST_PIN);

    /* Initialize Variables */
    byte resultBuffer[18];
    MFRC522::MIFARE_Key key;
    unsigned int integerValue = 0;
    char incomingByte;

    void setup()
    {
      Serial.begin(9600);
      SPI.begin();
      mfrc522.PCD_Init();
      Serial.println(F("Ready to scan card..."));

      for (byte i = 0; i < 6; i++)
      {
        key.keyByte[i] = 0xFF;
      }
    }

    void loop()
    {
      if (!mfrc522.PICC_IsNewCardPresent())
      {
        if (Serial.available() <= 0)
        {
          return;
        }

        integerValue = 0;
        while(true)
        {
          incomingByte = Serial.read();
          if (incomingByte == '\n') break;
          if (incomingByte == -1) continue;
          integerValue *= 10;
          integerValue = ((incomingByte - 48) + integerValue);
        }

        printHeader();
        Serial.println("NEW BLOCK READ VALUE :");
        Serial.println(integerValue);
      }

      if (!mfrc522.PICC_ReadCardSerial())
      {
        return;
      }

      readAndPrint(integerValue);
    }

    void printHeader()
    {
      Serial.println(" ");
      Serial.println("----------------------------------------");
    }

    int authenticateKeyA(int blockNumber)
    {
      printHeader();
      Serial.println("Authenticating with key A...");

      int largestModulo4Number = blockNumber / 4 * 4;
      int trailerBlock = largestModulo4Number + 3;

      byte status = mfrc522.PCD_Authenticate(MFRC522::PICC_CMD_MF_AUTH_KEY_A, trailerBlock, &key, &(mfrc522.uid));

      if (status != MFRC522::STATUS_OK)
      {
        Serial.println("ERROR : Authentication was unsuccessful.");
        return 0;
      }
      else
      {
        Serial.println("SUCCESS : Authentication was successful.");
        return 1;
      }
    }

    int authenticateKeyB(int blockNumber)
    {
      printHeader();
      Serial.println("Authenticating with key B...");

      int largestModulo4Number = blockNumber / 4 * 4;
      int trailerBlock = largestModulo4Number + 3;

      byte status = mfrc522.PCD_Authenticate(MFRC522::PICC_CMD_MF_AUTH_KEY_B, trailerBlock, &key, &(mfrc522.uid));

      if (status != MFRC522::STATUS_OK)
      {
        Serial.println("ERROR : Authentication was unsuccessful.");
        return 0;
      }
      else
      {
        Serial.println("SUCCESS : Authentication was successful.");
        return 1;
      }
    }

    int readBlock(int blockNumber, byte *resultBuffer)
    {
      printHeader();
      Serial.println("Starting read block function...");

      int authSuccess = authenticateKeyA(blockNumber);
      Serial.println(" ");

      if (!authSuccess)
      {
        Serial.println("ERROR : Terminating function.");
        return 0;
      }

      byte bufferSize = 18;

      byte status = mfrc522.MIFARE_Read(blockNumber, resultBuffer, &bufferSize);

      if (status != MFRC522::STATUS_OK)
      {
        Serial.println("ERROR : Read failed.");
        return 0;
      }
      else
      {
        Serial.print("SUCCESS : Block ");
        Serial.print(blockNumber);
        Serial.print(" was read successfully.");
        return 1;
      }

      mfrc522.PICC_HaltA();
      mfrc522.PCD_StopCrypto1();
    }

    void readAndPrint(int blockNumber)
    {
      readBlock(blockNumber, resultBuffer);

      printHeader();
      Serial.println("RESULT :");
      for (int j=0 ; j<16 ; j++)
      {
       Serial.print(resultBuffer[j], HEX);
       Serial.print(" ");
      }
      Serial.println(" ");

      delay(2000);
      printHeader();
      Serial.println("Ready to scan card...");
    }

Before scanning the card for the first time, the serial output looks like this :

[![First capture of serial monitor.][1]][1]

After scanning the card for the first time, the serial output looks like this :

[![Second capture of serial monitor.][2]][2]

After scanning the card for the second time, the serial output doesn't change from image 2.  I tried running `Serial.println("no card detected");` when the code inside `if (!mfrc522.PICC_IsNewCardPresent())` is ran, just to check if the program was frozen (I'd heard someone else had an issue where the program froze after scanning the first card) - it wasn't frozen, both before and after scanning the first card, it printed out 'no card detected' repeatedly.

I would greatly appreciate any help as I have no clue as to how I should proceed.

Cheers,

  [1]: https://i.stack.imgur.com/eIz0F.png
  [2]: https://i.stack.imgur.com/ZTFLI.png

title: MFRC522 Module Won't Read Multiple PICCs Consecutively

Answers: 1

body:
The correct condition, for what you intend, should be `if (mfrc522.PICC_IsNewCardPresent())`, so that the code in the IF block is run when a card is present, though this isn't the best structure. Like you discovered, your program isn't frozen. One of the 2 return statements (I'm not sure which) is causing it to abort `loop()` before calling `readAndPrint()`. With your current code:

 - the first `return` will always be executed whenever no card is detected. Since you don't seem to be sending anything with the Serial monitor,  `Serial.available()` will return 0 and so `loop()` returns.
 - The second `return` will be executed if the reader fails to obtain the UID of the card with a `SELECT`. The `SELECT` will fail only if you don't first call `PICC_RequestA()` for 'new' cards (just coming within range), or `PICC_WakeupA()` for `HALT`ed cards (cards already within range but sleeping).

I don't know if you're trying different cards or just one. If its just one card, you may have to take it out of range and then bring it within range again for the reader to detect it a second time. But, if you want to read the card's data more than once, without taking it out of range, you have to call `PICC_WakeupA()` instead of `PICC_IsNewCardPresent()` since, as the names indicate, you're waking a sleeping card, not detecting a new card entirely. Also structure your `loop()` like this:

    void loop(){
      if (!mfrc522.PICC_IsNewCardPresent()) {  // replace the condition with PICC_WakeupA()
        return;  // if you dont want the card to leave the reader's range
      }

      if (!mfrc522.PICC_ReadCardSerial()) {
        return;
      }

      // all the code that should be executed if a card has been detected and its UID read

    }

However, there's usually little sense in `HALT`ing a card and then waking it in the very next iteration, so you might want to do all the sector reading and writing at once, HALT the card, and then wait for a new card to enter the field; at least that's what's desired in most applications.


body:
Good day

I'm playing with Arduino and shift register chip 74HC595N and already tried many different ways to solve my problem, but still to luck :(

So that is my current simple scheme:
[![Scheme][1]][1]

Arduino 2,3,4 ports connected to data, clock and latch pins of 74HC595N. I've connected only first two output pins of chip to make minimum power consumption and to simplify this example as much as possible.

That is my sketch:

    const int latchPin = 4; //Pin connected to ST_CP of 74HC595
    const int clockPin = 3; //Pin connected to SH_CP of 74HC595
    const int dataPin = 2;  //Pin connected to DS of 74HC595

    void setup()
    {
      Serial.begin(9600);
      pinMode(latchPin, OUTPUT);
      pinMode(clockPin, OUTPUT);
      pinMode(dataPin, OUTPUT);
      pinMode(13, OUTPUT);
    }

    void loop() {
      Serial.println("ON");
      digitalWrite(13, HIGH);
      send(B10000001);
      Serial.println("OFF");
      digitalWrite(13, LOW);
      send(B01000010);
    }

    void send(byte d) {
      Serial.println(d);
      digitalWrite(latchPin, LOW);
      shiftOut(dataPin, clockPin, MSBFIRST, d);
      delay(1000);
      digitalWrite(latchPin, HIGH);
    }

And the problem is: sometimes leds are blinking but very unstable. Sometimes it's not working at all, sometimes only first led is blinking, but second one is not. Sometimes opposite - second led is blinking, first one is not. Sometimes one of led is blink very fast (just flash instead of 1 second delay).
If I touch wires and elements on breadboard - something changing. Even without touching anything - situation changing. It seems like problem is somewhere in connection or power supply and I've already tried to except it: tried few different breadboard, two different 595 chips, different wires and resistors, tried Arduino Uno, Mega and nano. Even tried atmega328p standalone, tried power it from USB, from 9v battery, old mobile charger (5.4V, 650 mA), tried to power arduino with external source (12V, 1A). In all cases the problem still exists.

I've already read a lot about power supply for Arduino, but I think at least few of the ways I've already tried to supply power is good enough for 595 chip and two LEDs - isn't it?

Please, advice me what else can I try?

  [1]: https://i.stack.imgur.com/SzmlP.png

title: Arduino, 74HC595N, magic

Answers: 1

body:
Even this is quite old, to help others as well:

As you already did, pin 13 (output enable, active low) to ground and pin 10 (master reset, active LOW) to HIGH, to disable reset.


body:
I have recently written a program which is supposed to change the duty-cycle to keep the feedback voltage measured on A0, A1 constant. The problem is that the Arduino will start crashing at pretty constant intervals if it approaches it's target current. Once it crashes I have confirmed that it restarts the program (but crashes again in a moment).

Here's a sample of the serial output during the crash:

    Current A: 65 Current B: 67 PWM A: 174.98 PWM B: 236.00
    Current A: 65 Current B: 67 PWM A: 174.98 PWM B: 235.96
    Current A: 65 Current B: 67 PWM A: 174.98 PWM B: 235.92
    Current A: 64 Current B: 67 PWM A: 175.00 PWM B: 235.88
    Current A: 64 Current B: 66 PWM A: 250.00 PWM B: 285114740000000000000000000.00
    Current A: 0 Current B: 0 PWM A: 1.30     PWM B: 0.00
    Current A: 0 Current B: 0 PWM A: 2.60     PWM B: 1.30
    Current A: 0 Current B: 0 PWM A: 3.90   PWM B: 2.60
    Current A: 0 Current B: 0 PWM A: 5.20     PWM B: 3.90

And here is **all** of my code:

    #include <MemoryFree.h>

    //Program to run on the Vegetarium
    //Written by Leon Teichroeb on 12/6/2016

    //Hardware description:
    //-Oscillator 2A and 2B for the two onboard driver circuits
    //-Pin 13 is attached to the "heartbeat" LED
    //-Channel A (3) and B (11) current measurements on A0 and A1

    //Functionality:
    //-Drive Channels at set current

    float PWMA = 0;
    float PWMB = 0;

    int TARGETA = 65;
    int TARGETB = 65;

    void setup() {
      Serial.begin(115200);

      pinMode(3, OUTPUT);
      pinMode(11, OUTPUT);
      TCCR2A = _BV(COM2A1) | _BV(COM2B1) | _BV(WGM21) | _BV(WGM20);
      TCCR2B = _BV(CS20);
      OCR2A = (int)PWMA;
      OCR2B = (int)PWMB;
      digitalWrite(3, LOW);
      digitalWrite(11, LOW);

      delay(5000);
    }

    void loop() {
      int CURRENTA = analogRead(A0) / 4;

      if(CURRENTA < TARGETA) {
        PWMA += (TARGETA - CURRENTA) * 0.020f;
        if(PWMA > 250) {
          PWMA = 250;
        }
      }
      if(CURRENTA > TARGETA) {
        PWMA += (TARGETA - CURRENTA) * 0.020f;
        if(PWMA < 5) {
          PWMA = 5;
        }
      }

      int CURRENTB = analogRead(A1) / 4;

      Serial.println("Current A: " + (String)CURRENTA + "\t" + "Current B: " + (String)CURRENTB + "\t" + "PWM A: " + (String)PWMA + "\t" + "PWM B: " + (String)PWMB);
      //Serial.println("PWM A: " + (String)PWMA + "\t" + "PWM B: " + (String)PWMB);
      //Serial.print("freeMemory()=");
      //Serial.println(freeMemory());

      if(CURRENTB < TARGETB) {
        PWMB += (TARGETB - CURRENTB) * 0.020f;
        if(PWMB > 250) {
          PWMB = 250;
        }
      }
      if(CURRENTB > TARGETB) {
        PWMB += (TARGETB - CURRENTB) * 0.020f;
        if(PWMB < 5) {
          PWMB = 5;
        }
      }

      if(PWMA < 10) {
        digitalWrite(3, LOW);
      } else {
        analogWrite(3, (int)PWMA);
      }
      if(PWMB < 10) {
        digitalWrite(11, LOW);
      } else {
        analogWrite(11, (int)PWMB);
      }

      delay(40);
    }

My circuit also provides power for the Arduino through a simple 7815 voltage regulator. The analog input does not exceed a few volts, and the PWM outputs are driving two logic level MOSFETs. If more information on the circuit is necessary please let me know!

EDIT: I have found out that it isn't a bug in the two feedback loops, because both work on their own. It crashes as soon as I use both feedback loops together. As far as I'm aware, there are no shared variables or data between them

title: Arduino crashing and rebooting

Answers: 1

body:
I finally figured it out, the Arduino was entering a current protection mode causing it to reset. The pins driving the MOSFETs were pulling too much current once the regulation started because of the BUZ11's input capacitance.

To fix the problem I just had to add 120 ohm resistors in series with the gate. This made the activation and deactation slower resulting in less current flow.


body:
I am getting the following error when attempting to compile my sketch:

> In file included from sketch.ino:24:0: SerialRenderer.h:7: error:
> expected class-name before '{' token

**SerialRenderer.h**

    #ifndef SERIALRENDERER_H_
    #define SERIALRENDERER_H_

    #include <MenuSystem.h>

    class SerialRenderer : public MenuComponentRenderer
    {
    public:
        SerialRenderer();
        virtual ~SerialRenderer();

    public: // methods from MenuComponentRenderer
        virtual void render(Menu const& menu) const;
        virtual void render_menu_item(MenuItem const& menu_item) const;
        virtual void render_back_menu_item(BackMenuItem const& menu_item) const;
        virtual void render_numeric_menu_item(NumericMenuItem const& menu_item) const;
        virtual void render_menu(Menu const& menu) const;
    };

    #endif // SERIALRENDERER_H_

The contents of MenuSystem.h can be found at https://github.com/jonblack/arduino-menusystem/blob/master/MenuSystem.h.

It seems like the include of MenuSystem.h does not happen when SerialRenderer.h is included from my main sketch file. I get the same error if the include in SerialRenderer.h is removed.

Is there something simple I am missing for the compiler to be able to "see" MenuSystem.h?

**EDIT:**

Turns out I was looking at a newer version of the arduino-menusystem library than I had installed (version 2.1.1). That version did not have a class called MenuComponentRenderer.

I pulled the latest version from https://github.com/jonblack/arduino-menusystem/tree/master and it compiles fine.

title: expected class-name before '{' token

Answers: 1

body:
It is most likely caused by the fact that a correct version of MenuSystem library is not properly installed.
Check whether you can add the library to your sketch.

**EDIT**: added that also the version should be correct


body:
I'm having trouble understanding the [datasheets][1] for the ATtiny and I need to know what is the largest prescaler that can be set for an ATtiny Timer Interupt? I'm new to hardware so can someone tell me if this is correct:

    void setupInterupt()
    {
      noInterrupts();
      TCCR2A = 0;
      TCCR2B = 0;
      TCNT2 = 0;
      OCR2A = PERIOD - 1;
      TIMSK2 = _BV(OCIE2A);
      TCCR2B |= _BV(CS13) | _BV(CS12) | _BV(CS12) | _BV(CS10);
      interrupts();
    }

Will this set a prescaler of 16384? Am I understanding the chart on page 89 correctly and is my syntax okay? This is my first Arduino Project.

  [1]: http://www.atmel.com/images/atmel-2586-avr-8-bit-microcontroller-attiny25-attiny45-attiny85_datasheet.pdf

title: What is the maximum prescaler you can set for an ATtiny85 Timer Interrupt?

Answers: 1

body:
I don't know the objectives of your project, or its constraints and requirements.  Thus, portions of the following might not apply.

If I were using an ATtiny85 in an application that needed to “maximize the amount of power saved” and also needed to wake up about every 33 ms, I'd use the factory-calibrated 8 MHz clock (rather than attaching a 20 MHz external crystal), and use system clock prescaling [see §6.3, System Clock Prescaler, on page 31 of [the ATtiny85 specs](http://www.atmel.com/images/atmel-2586-avr-8-bit-microcontroller-attiny25-attiny45-attiny85_datasheet.pdf), and Table 6-15. Clock Prescaler Select, p. 33] to scale that 8 MHz down to 250 KHz.  As implied by Table 21-1, DC Characteristics, page 162 of specs, this will drop CPU current draw down to under 0.1 mA if powered by 2 V, or under 0.35 mA if powered by 3 V.

With the system clock running at 250 KHz, you can use timer 0 prescaled by a factor of 1024 [see §11.3.1, Internal Clock Source with Prescaler, p. 166 of specs] to get an interrupt every 33 ms or so.

If 250 KHz is too slow to get done with whatever computation needs to be done every 33 ms, upon waking I would change the system clock prescale factor per §6.3.1, Switching Time, to 8 MHz or 4 MHz or whatever it needs to be to get the computation done at lowest power cost.  That might or might not be the same as getting the computation done most quickly.

Then, after the periodic computation is done, I'd revert the system clock to 250 KHz, and go to sleep in Idle mode (Ref §7.1.1, Idle Mode) with almost everything except timer 0 shut down via the PRR. (Ref §7.3, Power Reduction Register.)


body:
I have 2 [nRF24L01+ modules][1] that were working fine then...stopped. I'm wondering if I accidentally fried one of the modules.

When I run the RF24 library GettingStarted example, this is the output of the module I believe may be fried:

    RF24/examples/GettingStarted/
    ROLE: Pong back
    *** PRESS 'T' to begin transmitting to the other node
    STATUS        = 0x00 RX_DR=0 TX_DS=0 MAX_RT=0 RX_P_NO=0 TX_FULL=0
    RX_ADDR_P0-1  = 0x0000000000 0x0000000000
    RX_ADDR_P2-5  = 0x00 0x00 0x00 0x00
    TX_ADDR       = 0x0000000000
    RX_PW_P0-6    = 0x00 0x00 0x00 0x00 0x00 0x00
    EN_AA         = 0x00
    EN_RXADDR     = 0x00
    RF_CH         = 0x00
    RF_SETUP      = 0x00
    CONFIG        = 0x00
    DYNPD/FEATURE = 0x00 0x00
    Data Rate     = 1MBPS
    Model         = nRF24L01
    CRC Length    = Disabled
    PA Power      = PA_MIN

I've changed out cables and connections all the way through. I also replaced this module with the other one directly and the other worked fine.

So, my question: Is this output showing definitively that I've killed the module and just need to buy a new one? Or is there some way to "flash" or reset the module?

  [1]: https://www.amazon.com/gp/product/B00E594ZX0/

title: nRF24L01+ module fried?

Answers: 2

body:
Assuming you have triple checked all your wiring before posting this question you should add a small capacitor between Vcc and GND near the nRF24: anything between 10uF and 100uF will do.

Rationale: these devices draw quite a decent amount of current when bootstrapping and transmitting and if they don't receive enough juice they just reset themselves showing those *all zeroes* settings.

They are pretty robust devices, not that easy to *fry*.

body: The nRF24L01 modules are very sensitive to electrostatic damage, I have killed three. By bit-banging the SPI lines it appears that the SCK line dies as I can detect MISO change on activating CSN (since status information should be returned whatever command is sent). I surmise the zeros you see in the status report are the first pre-clock bit repeated when there is no clock signal received. I put a 33k pull-down resistor on SCK.


body:
I am trying to copy my garage door key. I opened it and found out it has dip switches which you can flip so you can send different codes. It uses 12 bits and operates at 315Mhz. I bought a 315Mhz transmitter for arduino and i am trying to send that 12 bit code. I used an RTL-SDR and found out that the key uses AM modulation. Now, the problem is i dont know how to send bits (1,0 or high and low). I connected vcc of the transmitter to arduino 5V and gnd to gnd. Data pin is connected to pin 9. I tried setting pin 9 high or low coresponding to the code with 2ms pause in beetwen but RTL-SDR showed that nothing was transmitted. I tried using rc_switch and virtual_wire libary and using diffferent transmitters in case this one was damaged but no success. So how do i actually send high and low signals with these transmitters?
PS: I know i can buy those garage key copiers but this is more fun and i learn more.

title: Duplicate a garage door key

Answers: 0


body:
I have SIM800l module connected to Arduino and I'm trying to initialize it in my setup function with this code:

    #include <SoftwareSerial.h>

    //SIM800 TX is connected to Arduino D8
    #define SIM800_TX_PIN 6
    //SIM800 RX is connected to Arduino D7
    #define SIM800_RX_PIN 7
    SoftwareSerial serialSIM800(SIM800_TX_PIN,SIM800_RX_PIN);

    void setup()
    {
      Serial.begin(38400);
      while(!Serial);
      serialSIM800.begin(38400);
      Serial.println("wait for .... it");
      delay(10000);

      // comments added just for example, both commands return junk
      //serialSIM800.write("AT\r\n");
      //serialSIM800.write("AT+SAPBR=3,1,\"Contype\",\"GPRS\"\r\n");

      Serial.println("command sent");
      delay(2500);

      Serial.write(serialSIM800.read());
    }

But `Serial.write` returns junk.

When I use this code in loop:

      //Read SIM800 output (if available) and print it in Arduino IDE Serial Monitor
      if(serialSIM800.available()){
        Serial.write(serialSIM800.read());
      }
      //Read Arduino IDE Serial Monitor inputs (if available) and send them to SIM800
      if(Serial.available()){
        serialSIM800.write(Serial.read());
      }

and send `AT+SAPBR=3,1,"Contype","GPRS"` or just `AT` command with serial monitor, everything works fine.

Can someone help with this?

title: How to send AT command to sim800l with SoftwareSerial

Answers: 7

body: You can try to use serialSIM800.println("AT") instead of write. Here some examples https://github.com/stanleyhuangyc/Freematics/issues/17

body: [NeoSWSerial](https://github.com/SlashDevin/NeoSWSerial) would be better for this.  It can read and write at the same time, unlike SoftwareSerial, and it doesn't disable interrupts for the entire character receive time (~1ms!).  AltSoftSerial would be even better, but you can only use it on pins 8 & 9 (on an UNO, different pins on other Arduinos).

body:
My SIM808 returns a bit of junk right from the get-go, so that might be influencing things.

Also, it's conceivable you are retrieving a -1 from your initial serialSIM800.read() call - it's a nonblocking call and returns -1 when no data is available.  That would almost definitely appear as junk.

body:
Somewhere you said that ...but Serial.write return's junk....
Make sure that serial print is Both NL & CR

body:
You are getting junk because of baud rate, set as 9600.

Serial.begin(9600);
  while(!Serial);
  serialSIM800.begin(9600);
  Serial.println("wait for .... it");
  delay(10000);

body:
Sim800 series free Atcommander software.

http://bayanbox.ir/info/3493267131357723232/ATcenter

body:
IIRC, SIM800 modems are very 1990s, they default to 9600 baud. You will get garbage at 38400.

I successfully used a SIM800 at 9600.


body:
Sorry if my code isn't well written or anything because I'm new to Arduino and coding in C, but what is wrong with my code?

    int sidepin = 2;
    int LED = 5;
    int val;
    void setup() {
      pinMode(sidepin, INPUT);
      pinMode(LED, OUTPUT);
    }

    void loop() {
      val = digitalRead(sidepin);
      if(val = 0)
      {
        pinMode(LED, HIGH);
      }
      else(val > 0)
      {
        pinMode(LED, LOW);
      }
    }

title: What's up with my code?

Answers: 1

body:
Your IF statement, you're using: `(val = 0)`, and I believe you meant `(val == 0)`.

Also, you're using `else(val > 0)` and `else` doesn't need any argument. So the fixed code should look like:

    int sidepin = 2;
    int LED = 5;
    int val;
    void setup() {
      pinMode(sidepin, INPUT);
      pinMode(LED, OUTPUT);
    }

    void loop() {
      val = digitalRead(sidepin);
      if(val == LOW)
      {
        pinMode(LED, HIGH);
      }
      else
      {
        pinMode(LED, LOW);
      }
    }


body:
I am trying to use the Arduino as a switch for an external circuit.

I first thought about using a shift register, but this wont allow me to switch the external circuit. Here is a little sketch of what I want to do : [![Desired circuit][1]][1]

So basically I got this external circuit with a 3 position switch. And I want to replace this manual switch with an Arduino so it can be controlled by a PC, without influencing the other circuits Voltage or Amps...

Any suggestions ?

  [1]: https://i.stack.imgur.com/0QNwG.jpg

title: Arduino as switch for external circuit

Answers: 1

body:
Three-position makes it a little more tricky than normal.

The simplest option, though depending on what the circuit is, maybe not the safest option, is to use three relays.

[![enter image description here][1]][1]

Switch only one relay on and it is the same as having the three-position switch in that same state. Switch that relay off and switch another on and you have changed the switch position.

The danger is that this arrangement can have two or even three relays on at once, something that can't happen with a switch.  Also how you do the switching could be critical. Switch one relay off, then add a delay before switching the next one on, so that the previous one has a chance to switch off properly first. That way you avoid having two on at once. Of course, depending on what it is you're switching, that may or may not be an issue.

The safest option, though the hardest to create, would be to physically move the existing switch with, say, a servo motor. Without knowing a little more about the mechanics of your switch I can't really advise more on this option.

  [1]: https://i.stack.imgur.com/CAHmA.png


body:
For my master thesis I've designed a board with an [ATMEGA328P-AU][1] as micro controller.
[![enter image description here][2]][2]
As I want to use some libraries and I like the simplicity, I want to use "Arduino" to program it.

Everything works fine to a point:
I took an Arduino Uno and uploaded the "ArduinoISP" sketch.
I connected the ISP pins and burned the bootloader with board set to "Arduino Duemilanove / Diecimila" - got the message, bootloader burned.
I disconnected the ISP pins, took the ATMEGA out of its socket on the UNO board and connected the serial pins.

Here comes the problem I cant figure out:

Once I have done a above procedure I can upload a sketch and Serial communication is working. But I can only upload it once! The second time (no matter if during the same power-up or at another time) I push the upload sketch button, I get no response for several minutes (I once waited up to 10min to confirm there is nothing coming anymore :)). If I unplug either USB or the TX/RX cables I get the error (or for the USB cable something similar):

> avrdude: stk500v2_ReceiveMessage(): timeout
>
> avrdude: stk500v2_getsync(): timeout communicating with programmer

When I upload the bootloader again I can once again upload a sketch same as before. Then the same problem happens again.

I checked several question on Stackexchange already (specially all points in [this][3] one here) and googled the problem, but until now I am not able to find a solution.

As you can imagine it is quite annoying to always unplug the RX/TX cable and hook up the ISP cable again and burn the bootloader.

**So my question: What could cause this problem and how can I solve it?**

Btw. I am using the Arduino software version I'm using is 1.6.9

  [1]: http://www.atmel.com/devices/ATMEGA328P.aspx
  [2]: https://i.stack.imgur.com/87HhA.png
  [3]: https://arduino.stackexchange.com/questions/13292/have-i-bricked-my-arduino-uno-problems-with-uploading-to-board

title: Standalone Arduino with ATMEGA328P / Serial working, but serial programming not (only once after buning bootloader)

Answers: 2

body:
There is a problem with your circuit and the way you have it wired when programming. You have failed to use the RTS line for Serial programming. You need to have that line connected to the RESET of the ATMega328, this is as the bootloader for programming ove rserial will not start if the IC is not reset. Also you should burn the Arduino UNO bootloader rather than the one you chosen.

Seems you clarified you were using the diode as ESD protection, thank you. It is the recommended arrangement if you have a capacitor attached to the reset line in noisy environments.

The circuit between the RTS signal and the Arduino RESET pin needs to be this:

                C
     RTS >>----||------->> RESET(PIN1)
               0.1µF

From the same "[Have I bricked my Arduino][1]" that you linked, about 3/4 down Nicks post he mentions the use of serial programming of an Arduino

    FTDI    Arduino Uno

    GND       GND  (black wire on FTDI cable, blue jumper wire)
    CTS       not connected
    VCC       5V
    TxD       D0 (RX)
    RxD       D1 (TX)
    RTS       To RESET with a 0.1 µF capacitor in series with it (green wire)

What you can do if you don't have the proper serial programmer with an RTS output, you will have to manually reset the microcontroller to enter the bootloader just as the IDE says "Uploading...".
  [1]: https://arduino.stackexchange.com/a/13293/2944

body: Replying to an old post:  The Reset diode is not really ESD protection, it is there to shunt any high voltage spikes to Vcc to keep the chip from reacting to a high voltage and going into High Voltage programming mode, and then acting hung when there are further control signals to complete the sequence.


body:
After recent flooding of my apartment (pipe burst) I got an idea of automatic water flow watch. I would like to measure or just watch if water flows on main water intake. Arduino will know at what time of day (during nights and when nobody is home) the water flow is a problem and will send me an sms or whatever alarm. Measurement will be better to enable you to go to the bathroom, so the alarm will be raised only after certain amount of water.

The main problem is how to measure the water, are there any water-meter that can communicate with arduino?

title: Water measuring

Answers: 2

body:
I have an electronic water flow meter which uses a turbine wheel inside the pipe. Ostensibly there is a magnet on one or two or all four of the blades, which is read by a hall-effect sensor inside the meter. The specifications require 3 gallons per minute, which may be lower than you wish.
http://catalog.gpi.net/item/chemical-and-water-meters/01-series-electronic-digital-meters/01n31gm-nylon-water-meter?plpver=1001

If the flow rate is acceptable, you could add your own hall-effect sensor outside the pipe and connect an appropriately programmed Arduino to perform the tasks you require.

Alternatively, one could create via 3d modeling software an equivalent design to be printed by an online service or a friend with a printer. For balance purposes, a magnet in each vane would be advised.

Years ago, I had a speedometer for a kayak, about the size of one's thumb. It used the same technology, although the sensor was about two inches away on the upper side of the hull, while the tiny propeller was on the bottom. Apparently small magnets spinning create sufficient disturbances in the force to be read by mass produced sensors, even more than a decade ago.

body:
The utility company probably already placed a meter at your apartment.

Mine has a spinning dial, that's half metal, half plastic. I've had a photo-reflective sensor attached to it that so I could detect the change in amount of light being reflected (metal vs plastic). Every peak meant one liter.

Mine also has a rotating magnet, but I wasn't able to read that using a hal-effect sensor, or the magnetometer on my phone.


body:
To all of this, hope to formulate the question right.

In my project I have 5 sensors connected to Arduino, which I want to interpret via Seria.write() --> Processing.

Arduino:

    firstSens = 100 + (155 * digitalRead(8));
    secondSens = analogRead(A1)/4;
    thirdSens = analogRead(A2)/4;
    fourthSens = humData;
    fifthSens = tempData;
    int sensData[6] = {firstSens, secondSens, thirdSens, fourthSens, fifthSens};

    int i;
    for (i = 0; i < 5; i = i + 1) {
      Serial.write(sensData[i]);
    }

Processing:

    serialInArray[serialCount] = inByte;
        serialCount++;

    if (serialCount > 4 ) {
      firstSens = serialInArray[0];
      secondSens = serialInArray[1];
      thirdSens = serialInArray[2];
      fourthSens = serialInArray[3];
      fifthSens = serialInArray[4];

      // print the values (for debugging purposes only):
      println(firstSens + "\t" + secondSens + "\t" + thirdSens + "\t" + fourthSens + "\t" + fifthSens);

      // Send a capital A to request new sensor readings:
      myPort.write('A');
      // Reset serialCount:
      serialCount = 0;

My problem is that sensors find their place in Processing's array randomly, so for example arduino's *firstSens* could be Processing's *secondSens* or *fifthSens*

Why is this happening and how can I control it?

title: serial.write() five sensors and Processing

Answers: 2

body:
What is happening is you are just spewing out a list of numbers:

    4132
    132
    1928
    3240
    1239
    238
    3048
    391
    ... etc ...

There is nothing anywhere to say what anything is.

You need to add that kind of information. Either as a "start of data" tag before each block, or with each line.  For instance:

    ---START OF DATA---
    4132
    132
    1928
    3240
    1239
    ---START OF DATA---
    238
    3048
    391
    ... etc ...

Or:

    0:4132
    1:132
    2:1928
    3:3240
    4:1239
    0:238
    1:3048
    2:391

It is then up to your processing application to interpret the data and work out what is what.

Personally I like using the second method since it means you don't have to send all the data every time - you can send different values at different speeds of update and maintain a "current value" at the Processing end. For instance if you have one value that updates frequently and others that don't:

    3:4132
    1:132
    3:1928
    3:3240
    3:1239
    2:238
    3:3048
    0:391

You don't even have to use numbers, you could use words:

    pressure:4132
    temperature:132
    pressure:1928
    pressure:3240
    pressure:1239
    humidity:238
    pressure:3048
    rainfall:391

body:
I have done similar code for our car project dash display

you're looking for something like [this][1] on your Arduino side:

      Serial.print("U*"); //A header
      Serial.print("A");  //a token to indicate the message payload
      Serial.print(avgRPM);
      Serial.println("");

      Serial.print("U*"); //A header
      Serial.print("B");  //a token to indicate the message payload
      Serial.print(avgVoltage);
      Serial.println("");

      Serial.print("U*"); //A header
      Serial.print("C");  //a token to indicate the message payload
      Serial.print(avgCurrent);
      Serial.println("");

      Serial.print("U*"); //A header
      Serial.print("D");  //a token to indicate the message payload
      Serial.print(avgThrottle);
      Serial.println("");

      Serial.print("U*"); //A header
      Serial.print("E");  //a token to indicate the message payload
      Serial.print(avgBrake);
      Serial.println("");

and something like [this][2] on processing side:

     if (port.available() > 0) {
        data = port.readStringUntil('\n');
      }
      String payload = "";
      if (data != ""){
        int offset = data.indexOf("U*"); //this is our Header (0x552A)
        if(offset>=0){
          payload = data.substring(offset+3, data.indexOf('\n'));
          switch(data.substring(offset+2, offset+3)){
            case "A":
              RPM = payload;
              break;
            case "B":
              voltage = payload;
              break;
            case "C":
              current = payload;
              break;
            case "D":
              throttle = payload;
              break;
            case "E":
              brake = payload;
              break;
            case "F":
              telemBits = payload;
              break;
            default:
              //packet not recognised
          }
        }
    }

  [1]: https://github.com/EV-Project/DashBridge/blob/master/DashBridge.ino
  [2]: https://github.com/EV-Project/DashDisplay/blob/master/DashDisplay.pde


body:
I am wondering where are the difference in between using something like:
CD4067, which selects which pins to read/write from by "selecting" an address with 4 pins by writing to it. Versus the MCP23017 which uses the i2c interface.

I am trying to learn and build a simple application with lots of digital inputs and outputs, and need something that is fast at switching the pins and reading/writing to it.

title: I/O expander with i2c interface vs Multiplexer

Answers: 1

body:
The MCP23017 gives you 16 extra real IO pins. Each one has facilities such as pull-up resistors, change notification interrupts, etc - the kind of things that you expect from real IO pins. You can read and write to all of the pins.

A multiplexer though just feeds signals through to the existing pins. They're pretty dumb. Only the signal that is currently fed through can have anything done to it. So only one signal can have a value written on it or read from, and pullup resistors and interrupts are non-existent.

However the CD4067 can be used with signals other than digital - as such they are good at being a multiplexer to the analog inputs, something an IO expander can never do. You could, though, use an I2C ADC chip for that.

For high speed IO control you really want to be using the MCP23S17 instead of the MCP23017. It uses SPI instead of I2C and thus is much faster to control.


body:
**Short version**: This is a lighting control project.  Some of the clases are Pin and  Channel. Channel contains a Pin.  Pin is a base class for DigitalOutPin and will be the base class for AnalogOutPin, and I want Channel to be able to use any child of Pin.

Pin has an abstract method setPinValue(), but when I create a DigitalOutPin object and call setPinValue(), Pin.setPinValue() gets called, not DigitalOutPin.setPinValue() and my program doesn't work because Pin.setPinValue() is empty as it's supposed to be overwritten.

**Long version**:
If I leave out the definition of Pin.setPinValue(), I get that most idiotic of error gcc messages, "undefined reference to `vtable for Pin'".  If I make it pure virtual I get several errors in the form of

    In file included from /devel/arduino/lightbright/LightBrightMain/LightBrightMain.ino:9:0:
    /devel/arduino/libraries/LightBrightLib/Channel.h:21:20: error: cannot declare parameter 'pin' to be of abstract type 'Pin'
         void begin(Pin pin, int channelNumber);
                    ^
    In file included from /devel/arduino/libraries/LightBrightLib/DigitalOutPin.h:10:0,
                 from /devel/arduino/lightbright/LightBrightMain/LightBrightMain.ino:8:
    /devel/arduino/libraries/LightBrightLib/Pin.h:16:7: note:   because the following virtual functions are pure within 'Pin':
     class Pin
       ^
    /devel/arduino/libraries/LightBrightLib/Pin.h:33:18: note:  virtual void Pin::setPinValue(int)
         virtual void setPinValue(int value)=0;
                  ^
    In file included from /devel/arduino/lightbright/LightBrightMain/LightBrightMain.ino:9:0:
    /devel/arduino/libraries/LightBrightLib/Channel.h:23:9: error: invalid abstract return type for member function 'Pin Channel::getPin()'
     Pin getPin();
         ^
    In file included from /devel/arduino/libraries/LightBrightLib/DigitalOutPin.h:10:0,
                 from /devel/arduino/lightbright/LightBrightMain/LightBrightMain.ino:8:
    /devel/arduino/libraries/LightBrightLib/Pin.h:16:7: note:   since type 'Pin' has pure virtual functions
     class Pin
       ^
Full code is at [GitHub][1] but here are the relevant parts:
Pin is declared like this right now as pure virtual, but I've tried with and without =0

    class Pin
    {
      public:
       ...
      protected:
       ...
      // This method is child-specific. It's empty in this base class
      virtual void setPinValue(int value)=0;
    };

DigitalOutPin is declared as

    class DigitalOutPin : public Pin
    {
      public:
        void on();
        void off();
      protected:
       void setPinValue(int value);
    };

and defined as

    void DigitalOutPin::setPinValue(int value) {
    ....
 }

**Disclaimer**: I'm primarily a Java developer so C++ OO is very different for me, but as far as I can tell this should work as designed.

Thanks for any advice you can offer.

  [1]: https://github.com/djsegfault/arduino/tree/master/libraries/LightBrightLib

title: Inheritance not working as expected

Answers: 1

body:
I have taken your code from above and compiled it for a PC in Visual Studio.
When I create an object of type DigitalOutPin and call setPinValue() it calls the function I expect.  So this means either you have managed to find a bug in the gcc compiler, or there is something else in your code that is coming into play.  Can you try writing a VERY simple minimal test program that defines the Pin class and DigitalOutPin class (with just the setPinValue functions that print a string) and the setup and loop functions.  Just to see if you have found a gcc bug.

Even if this fixes the inheritance problem, you have other issues with you code because C++ is weird.  In Channel.h your Pin variables will need to be pointers, this will allow them to call the functions in the derived classes, not the base class functions.

I think you may get a performance improvement by using "const int& foo" for you parameters.  The const means the function can't change it, this allows the compiler to treat it differently and the "&" means use a reference to the variable rather than make a new copy of it.

Functions that don't change member variables within the code should also be declared constant.  "int FooBar(const int& value) const;"  It makes it clearer to the reader and the compiler probably does some funky stuff to improve performance.  (You might want to investigate "inline" if you are writing one line functions.)

Finally I'd recommend using constructors and destructors.  In release builds variables are not assigned a value.  If these variables are class members this means you don't know what they are to start with.  Also derived classes should initialise the base class, so:

    // Class constructor for DigitalOutPin
    DigitalOutPin::DigitalOutPin(const int& pinNumber)
      : Pin(pinNumber)  // Initialise the base class
      , m_State(false)  // Initialise all the class members (in order declared in .h file)
    {
      // Lots of lovely code
    }
    // Class destructor for DigitalOutPin (Declared as virtual)
    DigitalOutPin::~DigitalOutPin()
    {}


body:
If I got the picture right(correct me if I'm wrong) the standard bootloader senses the serial comm, and if nothing is read it passes control to the core program, which roughly corresponds to

    int main(void) {
     init();
     setup();
     for (;;) {
      loop();
      if (serialEventRun) serialEventRun();
     }
     return 0;
    }

I wish to understand what happens when  (while the core program is running) I upload a new sketch (using the IDE or `avrdude`). I guess that the bootloader regains control when something is read in the serial comm, and this happens via a board reset (triggered somewhere inside `serialEventRun`).

If so, how does this flow interplay with the usage of the serial port? Assume I want to use `avrdude` to upload the sketch via USB, and also use the serial comm during the program execution.

title: Bootloader sequence

Answers: 2

body:
Most computers begin execution at (or jump indirect through) location zero on startup. There may be variations, but this is the general idea. Whatever is put at location zero when the bootloader is installed causes the bootloader to gain control on a power-up or a reset. After that, it is up to the bootloader what happens next.

What usually happens is that the bootloader watches the serial port for the start of a "handshake" sequence; when (if) it sees what it is looking for, it replies in a manner that lets the loader program, e.g., avrdude, know that this is the bootloader replying and not some random text that was being sent just at that moment. (If the bootloader doesn't see the the handshake sequence begin within a short period, or it sees something other than the handshake, it starts the existing user program).

From there, the loader program and the bootloader cooperate to transfer the user program to the Arduino and load it into Flash memory at specified locations. Also transferred along with the user program is its starting address. When the upload is finished and verified, the bootloader transfers to the user program's starting address.

At this point, the user program owns the machine, including the serial port(s), and will continue to do so until another power-cycle or a reset. There is no need for the user program and the bootloader to negotiate use of the port; the bootloader owns it from reset to end-of-upload, and the user program owns it thereafter.

Update:

> However at that point (while the user program is running) I can start
> an upload (from the IDE or avrdude).

This is possible only because avrdude can send a hardware signal (*not* contained in the data stream) that the Arduino board uses to cause the chip to reset. It is still the reset process that transfers control from the running program to the bootloader. As an example, on a number of my hand-built boards I did not include that auto-reset circuit. On those boards, avrdude cannot begin a new upload autonomously; I have to manually reset them when I start avrdude.

body: It sounds like you're missing the fact that the Arduino IDE resets the Arduino board by toggling one of the comm port flow control signals. This causes a hardware reset on the Arduino board and then things happen as you've explained.


body:
I'm trying to get GPS coordinates using my SIM808 module by connecting it with Arduino. When I use this code,

    #include "SIM900.h"
    #include <SoftwareSerial.h>
    #include "gps.h"

    //To change pins for Software Serial, use the two lines in GSM.cpp.

    //GSM Shield for Arduino
    //www.open-electronics.org
    //this code is based on the example of Arduino Labs.

    //Simple sketch to start a connection as client.

    GPSGSM gps;

    char lon[15];
    char lat[15];
    char alt[15];
    char time[20];
    char vel[15];
    char msg1[5];
    char msg2[5];

    char stat;
    char inSerial[20];
    int i = 0;
    boolean started = false;

    void setup() {
      //Serial connection.
      Serial.begin(9600);
      Serial.println("GSM Shield testing.");
      //Start configuration of shield with baudrate.
      //For http uses it is recommended to use 4800 or slower.
      if (gsm.begin(2400)) {
        Serial.println("\nstatus=READY");
        gsm.forceON(); //To ensure that SIM908 is not only in charge mode
        started = true;
      } else Serial.println("\nstatus=IDLE");
      if (started) {
        //GPS attach
        if (gps.attachGPS())
          Serial.println("status=GPSREADY");
        else Serial.println("status=ERROR");
        delay(20000); //Time for fixing
        stat = gps.getStat();
        if (stat == 1)
          Serial.println("NOT FIXED");
        else if (stat == 0)
          Serial.println("GPS OFF");
        else if (stat == 2)
          Serial.println("2D FIXED");
        else if (stat == 3)
          Serial.println("3D FIXED");
        delay(5000);
        //Get data from GPS
        gps.getPar(lon, lat, alt, time, vel);
        Serial.println(lon);
        Serial.println(lat);
        Serial.println(alt);
        Serial.println(time);
        Serial.println(vel);
      }
    };

    void loop() {
      //Read for new byte on serial hardware, and write them on NewSoftSerial.
      serialhwread();
      //Read for new byte on NewSoftSerial.
      serialswread();
    };

    void serialhwread() {
      i = 0;
      if (Serial.available() > 0) {
        while (Serial.available() > 0) {
          inSerial[i] = (Serial.read());
          delay(10);
          i++;
        }
        inSerial[i] = '\0';
        if (!strcmp(inSerial, "/END")) {
          Serial.println("_");
          inSerial[0] = 0x1a;
          inSerial[1] = '\0';
          gsm.SimpleWriteln(inSerial);
        }
        //Send a saved AT command using serial port.
        if (!strcmp(inSerial, "TEST")) {
          stat = gps.getStat();
          if (stat == 1)
            Serial.println("NOT FIXED");
          else if (stat == 0)
            Serial.println("GPS OFF");
          else if (stat == 2)
            Serial.println("2D FIXED");
          else if (stat == 3)
            Serial.println("3D FIXED");
        }
        //Read last message saved.
        if (!strcmp(inSerial, "MSG")) {
          Serial.println(msg1);
        } else {
          Serial.println(inSerial);
          gsm.SimpleWriteln(inSerial);
        }
        inSerial[0] = '\0';
      }
    }

    void serialswread() {
      gsm.SimpleRead();
    }

After some time, I get this error on the Serial Monitor of Arduino:

    status=ERROR

The connections are as follows:

 - TX of Module = Pin 2 of Arduino
 - RX of Module = Pin 3 of Arduino
 - GND of Module = GND of Arduino
 - 5V of Module = 5V of Arduino

The Arduino is powered by USB connected to my PC.

[![Here is a pic of my connections][1]][1]

[![This is SIM808 module.][2]][2]

[![SIM808 module.][3]][3]

  [1]: https://i.stack.imgur.com/4rDkI.jpg
  [2]: https://i.stack.imgur.com/vrZny.jpg
  [3]: https://i.stack.imgur.com/k0bkp.jpg

title: GPS is not detected on SIM808 module!

Answers: 1

body:
Your problem looks similar to mine. It is possible that your module is a GNSS module and therefore doesn't work with standard AT commands, which are used in "gps.h".

First check that the GPS Module receives enough current, at least 5V -- 2A from an external source like a battery.

Then try sending AT commands in the serial monitor to check if your GPS module works properly:

    #include <SoftwareSerial.h>
    SoftwareSerial SIM808(2,3); //(RX-Pin,TX-Pin)

    void setup() {
      Serial.begin(19200);
      SIM808.begin(19200);
    }

    void loop() {
      if (SIM808.available())
        Serial.write(SIM808.read());
      if (Serial.available())
        SIM808.write(Serial.read());
    }

Upload this to the board an then open the serial monitor and send these commands:

    AT+CGNSPWR=1

This should return OK.

After that input:

     AT+CGNSINF

This should return OK and your GPS Location in this format:

    1,0,<time>,<your latitude>,<your longitude>,..........

If you get the following output:

    1,0,19800106001337.000,,,,0.00,0.0,0,,,,,,0,0,,,,,

It means your GPS is not set. Try to put GPS antenna outside your room, on open space.

For more information about GNSS modules go to  http://www.elecrow.com/wiki/images/0/05/SIM800_Series_GNSS_Application_Note_V1.00.pdf


body:
How to clear the serial buffer of arduino uno?
This is my code to on and off the LED using sms from mobile using gsm module

<!-- language: c -->

    #include <SoftwareSerial.h>
    int Led=7;

    SoftwareSerial mySerial(9, 10);

    void setup()
    {
      pinMode(Led,OUTPUT);
      mySerial.begin(9600);   // Setting the baud rate of GSM Module
      Serial.begin(9600);    // Setting the baud rate of Serial Monitor (Arduino)
      delay(100);
    }

    void loop()
    {
      if (mySerial.available()>0)
      {

      }
       switch(mySerial.read())
      {
        case 'a':
               digitalWrite(Led,HIGH);
               delay(10000);
               digitalWrite(Led,LOW);
               delay(100);
               break;

        case 'b' :
               digitalWrite(Led,LOW);
               break;

      }}

problem is whenever i on the module or the connection is restablished it automatically gets even without an sms.I need it to be fully in my control so i need to clear the serial buffer.

title: Clearing arduino serial buffer

Answers: 2

body:
You can simply clear it by reading it until its empty.

    while(Serial.available()){
        Serial.read();
    }

There also used to be a

    Serial.flush();

to clear the serial. However they changed it to some other functionality. For further details you can look at the arduino reference page on Serial.

body:
If you are receiving unsolicited message (reading junk) then you could extend the bit pattern you are expecting so that there is almost no possibility of you accidentally receiving it.

Rather than 'a' and 'b' as triggers user LED="0" and LED="1".  Doing this makes reading the data much harder, because what you are looking for may start on character 4 of the string you read.  This is what I think you will need to do.

 1. Read each character in turn and store them in a buffer until you have 7.
 2. Is the first character an L.
 3. If it isn't then delete the first character, shuffle the buffer left
    one place and load in the next character before returning to step 1.
 4. If it was, check the next character matches the expected.
 5. If it doesn't match delete all character to the left and this one and return to step one.
 6. If you have a matching token then parse it (get the 1 or 0) and do the action.


body:
I am trying to build a Smart Led project using Arduino Uno, RGB Led, HM-10 BLE module, and Android device.

I am able to connect HM-10 with my android device and read and write characteristic values using Android BlueDroid stack.

But for this project to work I need to check changes in characteristic value in Arduino and process color value and produce output to light up LED.

I thought I could possibly use AT commands (like AT+Name? AT+POWE? AT+CHAR?) parse their result , but I couldn't find any AT command to read characteristic value. **If anyone know such working AT commands for HM-10, please answer?**

Also, I looked into CurieBLE library from Intel for Arduino. I think the library is to work on an Arduino board which has BLE hardware as a built-in feature. If that's not the case, **please help me how can I communicate Arduino and HM-10 using CurieBLE or any other available library?**

title: Read BLE Characteristic Value in Arduino Uno

Answers: 2

body:
I was able to communicate Arduino UNO and HM-10. Whenever one writes a characteristic on BLE using Android application, the exact bytes are transmitted to **Tx/Rx channel** to Arduino and can be read using **SoftwareSerial** Arduino library.

CurieBLE library works on Genuino/Arduino 101 board which has Intel Curie Module.

body:
I found this site that discusses the HM-10 and they linked to the datasheet which lists all the AT commands. The set/query characteristics AT command is listed as #13 on page 24.

[Datasheet link.][1]

["Bluetooth 4.0 with HM-10" tutorial for MIT course "How To Make (almost) Anything"][2]

Hope this helps.

  [1]: http://fab.cba.mit.edu/classes/863.15/doc/tutorials/programming/bluetooth/bluetooth40_en.pdf
  [2]: http://fab.cba.mit.edu/classes/863.15/doc/tutorials/programming/bluetooth.html


body:
[![enter image description here][1]][1]I am a newbie to Arduino and created my first project. The project is using a Sharp short range sensor and a 7 seg LED board (http://embedded-lab.com/blog/new-version-of-max7219-based-4-digit-serial-seven-segment-led-display/) to count objects.

Everything works fine when on USB power to my computer or if I use a 5v 1A wall adapter with a USB cable. The problem is when I use an external power adapter or use a DC power supply to the Vin. The board powers up and I measured the output voltage on the 5v pin and is measuring around 4.8v.

The Sharp sensor is connected to the A0 Analog in and I see the voltage fluctuate when an object passes, but the LED is not displaying a value when on the external power. The display is connected to GRD, 5v where DIN, CLK, and LOAD pins of the display are connected to pins 7, 6, and 5 as the instructions stated.

I tried two different Arduino boards and several different AC to DC power adapters ranging from 9v to 12v plus used a DC power supply to the Vin and same results.

The code is below and pretty simple (although I am sure there is a lot better way of doing it but this is my first project in C so go easy on me and the function for digits is from a website and not written by me).

If a picture of the project would help I can upload one.

Any ideas or thoughts?
Thanks,
Steve

    #include "LedControl.h"
    #include <stdio.h>
    #include <math.h>

    // Arduino Pin 7 to DIN, 6 to Clk, 5 to LOAD, no.of devices is 1
    LedControl lc = LedControl(7, 6, 5, 1);
    int sensorpin = 0;  // analog pin used to connect the sharp sensor
    int val = 0;   // variable to store the values from sensor(initially zero)
    int cnt = 1;

    void setup()
    {
     // Initialize the MAX7219 device
     lc.shutdown(0, false);   // Enable display
     lc.setIntensity(0, 10);  // Set brightness level (0 is min, 15 is max)
     lc.clearDisplay(0);     // Clear display register

    }
    void loop()
    {

     val = analogRead(sensorpin);       // reads the value of the sharp sensor
     if (val >= 650)
     {

  //write values to LED
  if (cnt<=9)
  {
   lc.setDigit(0, 0, cnt, false); // Display 4 to Digit 1-9, " "
  }
  if (cnt >= 10 && cnt <= 99)
  {
   lc.setDigit(0, 0, getDigitFromNum(cnt,0), false); // Display 4 to Digit 1-9, " "
   lc.setDigit(0, 1, getDigitFromNum(cnt, 1), false); // Display 3 to Digit 1-9, " "
  }

  if (cnt >=100)
  {
   lc.setDigit(0, 0, getDigitFromNum(cnt, 0), false); // Display 4 to Digit 1-9, " "
   lc.setDigit(0, 1, getDigitFromNum(cnt, 1), false); // Display 3 to Digit 1-9, " "
   lc.setDigit(0, 2, getDigitFromNum(cnt, 2), false); // Display 2 to Digit 1-9, " "
  }

  delay(400);
  cnt++;

 }
    }

    // Function: getDigitFromNum returns a digit at a given index of a integer.
    // Goes from right to left with the starting index of 0.
    int getDigitFromNum(int num, int digit) {
     num /= pow(10, digit);
     return num % 10;
    }
    // Function: getDigitFromDec returns a digit at a given index of a double.
    // Goes from left to right with the starting index of 0.
    int getDigitFromDec(double dec, int digit) {
     dec *= pow(10, digit);
     return (int)dec % 10;
    }
    // Function: getDigitFromNum returns the decimal values of a double.
    double getDecimals(double dec) {
     return dec - (int)dec;
    }

  [1]: https://i.stack.imgur.com/AlmKv.jpg

title: Arduino Uno - External Power not working properly

Answers: 1

body:
The only difference between powering from USB and powering through the barrel jack is the voltage is reduced to 5V through a Low Dropout (LDO) voltage regulator. These are typically a clone of the popular LM1113-50 and vary in current handling capacity from around 500mA up to 1A.

I notice your board is not a genuine Arduino - therefore the components used may be at the cheaper end. So we'll assume a low-grade LDO that only handles 500mA before going into thermal shutdown with good heatsinking. Since there isn't on these boards we shall therefore assume a maximum of 400mA before it gets too hot. Probably somewhat conservative.

So if your entire circuit is drawing more than about 400mA you can expect the regulator to shut down, or at least to reduce the current and/or voltage available.

The fact you're seeing 4.8V rather than 5V could be an indication that there is *voltage droop* occurring - i.e., the regulator is not able to supply enough current so the voltage drops. This would be accompanied by the regulator getting very hot.

The regulator is the device with 3 pins on the right side and a single tab on the left directly above the barrel jack socket. See how hot that is getting.

As a rule of thumb if you can hold your finger on it without crying for 10 seconds it's not too hot.

----

Another thing you can do is to reduce your circuit to the bare minimum. Unplug absolutely everything and upload the Blink example sketch. Power that from the external DC and see if the LED blinks for you. If it does then the power supply is working OK. You can then add your peripherals one at a time to see when it fails.

If it doesn't blink then there must be something inherently wrong with the supply.

One possibility is that the LDO is *oscillating* due to insufficient or incorrect input and output capacitors. This basically means the "5V" voltage it gives out is actually wildly swinging between say 4.5V and 5V or 4.75V and 5.25V, which really confuses the microcontroller. Cheap LDOs are often more sensitive to the capacitors they are paired with and can suffer from this kind of problem.

To diagnose that kind of thing you would really need access to an oscilloscope to analyse the voltage.

If it is oscillating a 10µF ceramic capacitor connected between the lower two pins of the LDO (as orientated in your picture - that is Vout and GND) may cure it. A 1206 surface mount capacitor fits nicely across those pins and is reasonably easy to hand solder. You could also try a through-hole capacitor (ceramic again) between 5V and GND on the power header, but you really want it as close to the LDO as you can get it, so soldered direct to the LDO's pins is best.


body:
I am trying to make an obstacle avoiding robot with robotic arm. First, I am from software programming field with no experience in electronics, circuits and Arduino. Using online tutorials so far I am able to blink an led, bluetooth communication between PC and Arduino and sonar range measurement.

After doing a lot of research on internet I have made the following diagram to connect  4 servos, 2 motors, hc-05, sr-04 and L293D to Arduino using "fritzing" software. I have the sketches for running servos and motors but I am not sure the circuit is correct due to the lack of knowledge in electronics. My doubts are,

1) Is 6V supply enough for 4 servos and 2 dc to work?

2) Is the connection between L293D and 2 DC motors correct?

The final robot will look like (I hope!) a "mearm" like robot arm attached on top of an obstacle avoiding robot.

[![enter image description here][1]][1]

UPDATED:
[![enter image description here][2]][2]

  [1]: https://i.stack.imgur.com/tvi9Y.png
  [2]: https://i.stack.imgur.com/dk0MB.jpg

title: Connecting 4 servos, 2 motors, hc-05, sr-04 and L293D to Arduino

Answers: 1

body:
> 1) Is 6V supply enough for 4 servos and 2 dc to work?

If the motors are 6V motors then 6V is not only enough, it is what you *need*. What you should be asking is "Can my power source provide enough **current**.

> 2) Is the connection between L293D and 2 DC motors correct?

Not quite. You have only got half your grounds connected up. Also 3,4EN should be connected to Vcc1 not Vcc2.

1A/2A and 3A/4A are the direction/break pins (one high and one low for a direction, both low for break). The EN pins can be (if you wish) used to control the speed with PWM (if you have any spare) - if not then they should be tied to the logic supply voltage, Vcc1, not the power supply voltage, Vcc2, since that can be up to 36V and is way too high for logic inputs like EN.


body: I am newer to arduinos, and could use some help. I have a LCD screen hooked up to an arduino uno. I can get it to display whatever I type in, which is great. But, what i want it to display is a value from an excel spreadsheet. So, it will change depending on what is in that field. Or even better yet, from access. Is this possible? is there code to have the arduino pull information from an existing table? (assuming it is connected via USB, or, eventually, wifi). thanks!

title: Arduino LCD Screen

Answers: 2

body:
Assuming your Excel spreadsheet or Access table is stored on your PC, you can write a PC program to read the file and send the data serially over the USB connection to the connected Arduino, which can display it on the LCD.

If the file is stored on an SD card instead, and you want the Arduino to access the file directly by reading said SD card (through an Ethernet shield perhaps), you need to make the file format a lot simpler than XLS to ease parsing; CSV is quite simple and suitable for a lot of tasks. The built-in `SD` library can be employed to read the data from the card, the Arduino parses the data and displays it on the LCD.

In general, I suggest you do more research.

body:
It is not the easiest thing to do especially if you are newer to arduinos but Roberto Valgolio has made an Arduino Excel interface: http://www.robertovalgolio.com/sistemi-programmi/arduino-excel

I have not worked with it yet but it's worth looking into it.


body: I saw a [YouTube Video](https://www.youtube.com/watch?v=0PgFK85fIHM) of someone who used an aux cord input into pin A0 on their Arduino to control a strip of LEDs. I have a strip of [Adafruit's RGB NeoPixel LEDs](https://www.adafruit.com/products/1461), but I'm not sure how to input my audio into pin A0. If there is a way to do this without a separate shield or board, that'd be great because I'm on a tight budget, but if not possible it'll have to do. Also, would it be possible to send this audio to another Arduino via wifi or bluetooth using a different shield? Thanks.

title: Audio Input into A0?

Answers: 1

body:
Depending on how loud your audio signal is, you may be able to do it with just one capacitor and two resistors:

[![enter image description here][1]][1]

If your signal is quite quiet, though, you may need to amplify it using an op-amp. For instance:

[![enter image description here][2]][2]

That arrangement would double the volume of the audio. It also has the effect of inverting it, so you will need to invert your readings in software.

Also note that both of these methods will give you an AC waveform centred around 2.5V, so silence will be a reading of around 512, and it will go up and down from there. You can sample that audio waveform and do some basic (though quite slow on an Arduino) analysis of it, such as FFT to get the frequency content of the audio - great for visual effects...

  [1]: https://i.stack.imgur.com/n9ONN.png
  [2]: https://i.stack.imgur.com/tgsiz.png


body:
So, I'm not sure what is causing this, but maybe I'm overlooking something simple. I have a simple program designed to read the analog input at 640 Hz, it looks like this:

    int Ch0 = 0;
    int count = 0;
    unsigned long startTime;
    unsigned long currentTime;
    bool startedReading = false;

    void setup() {
      //set up pin(s)
       pinMode(Ch0, INPUT);

      //begin serial at 115200bps
      Serial.begin(115200);
    }

    ...

    //if the current time exceeds the start time by one second, set the start time equal to current time, print the count, set count equal to zero
    if (currentTime - startTime >= 1000) {
      startTime = currentTime;
      Serial.println("time");
      count = 0;
    }

    //read input, delay some microseconds as a means of controlling sampling rate, bring count up by one
    //should read somewhere along the lines of 640-ish Hz
    analogRead(Ch0);
    delayMicroseconds(1230);
    Serial.println(count);
    count++;

And this all works fine and dandy in the Arduino IDE, I pull up the Serial Monitor, and it prints every number 1-640 and then says time, with good consistency. Yet, when I open up a Visual Studio program and call the command:

EDIT: Added entire data received event method

 private: System::Void serialPort1_DataReceived(System::Object^  sender, System::IO::Ports::SerialDataReceivedEventArgs^  e) {
  if (!this->reading) return;
  else
  {
    try
    {
    //get incoming port and read
    SerialPort^ sp = (SerialPort^)sender;
    String^ sInData = sp->ReadLine();
    //parse read data
    double inData = double::Parse(sInData);

    //write data to debugger for testing
    Debug::WriteLine(inData);

    //start populating the "in" array
    AppendIn(inData);
              }
              catch (Exception^ e)
              {
    Debug::WriteLine(e->Message);
              }
        }
    }

Aside from the obvious error that occurs when I try to parse the string "time" to indicate when 1 second has elapsed, everything works fine. Except for the fact that the numbers feed into the debugger *very* slowly. As in, it'll take roughly 4-5 seconds to read through all 640 reads of the count integer and then it throws the time at me. Thus, this leads me to conclude that Arduino is indeed calculating that 1 second has elapsed and then sending that over, but the output is essentially the same, the only difference being that the message takes exactly 1 second to read on the Arduino IDE and over 4 seconds to read in real time in Visual Studio.

Maybe it has something to do with the way I'm reading the data in VS? I have it set up to constantly monitor the stream by calling that read method every as an event when data is received over the serial. No data at all is being lost, it's just very slow...and only in VS. Thanks in advance for any help you can give, but I'm at a bit of a loss.

title: Significant drop in speed between Arduino IDE and Visual Studio?

Answers: 1

body:
>  I have it set up to constantly monitor the stream by calling that read method every as an event when data is received over the serial.

I suspect that is the issue. Waiting for an incoming "serial data available" event and then processing it, is likely to be slow. I would rework how you get serial data. You haven't shown that bit but maybe you can use a larger buffer.


body:
Apparently [these nRF24L01+ modules][1] need 3.3v, but I've only got 5v Trinket Pros that I'm using.

How can I reduce the voltage to the RF transmitter?

Would a voltage regulator work? Specifically looking at this: http://addicore.com/product-p/165.htm

  [1]: https://www.amazon.com/nRF24L01-Wireless-Transceiver-Antistatic-Compatible/dp/B00E594ZX0

title: Reduce 5v Trinket Pro to 3.3v?

Answers: 4

body: There are 3.3V Trinkets. Anything you try to do will cost more than buying one.

body:
As said by JayEye: there are 3,3V Trinkets and that is probably the cheapest option.

If you want to pay the extra money, there are special boards for it by addicore: https://www.amazon.com/gp/product/B00VFNZN8K/ref=s9_dcacsd_bhz_bw_c_x_3

third option is to build yourself a small voltage regulating circuit. The regulator that you linked to will do.

body:
The NRF24L01+ has inputs that are 5V tolerant! So you only need to provide 3.3V on the Vcc pin of the module, which you can do by putting a voltage regulator between it, and the 5V of the Trinket. So there isn't really any need to convert the Trinket to 3.3V.

PS Remember to add some capacitors to the output of the voltage regulator, as the NRF needs a pretty stable 3.3V. Noise in the power lines can cause instability in the operation of the device.

body:
I also had a 5V Pro Trinket on hand and needed to connect one of its 5V output pins to the 3V pairing pin on an Adafruit's EZ-Key HID. I solved it easily for the price of a couple 1/8 watt resistors by including a simple voltage divider in the circuit as a "level shifter" and it works like a charm. In my case it's not serial data but give it a try.

Classic voltage divider equation: V out = V in * R1 / (R1 + R2)

1. In setup(), set the 5V Pro Trinket digital out pin to be normally LOW when it's not doing anything in the sketch, e.g. if it were pin 8: pinMode(8,OUTPUT); digitalWrite(8, LOW);

2. Connect this 5V output pin to one end of a 1.8K resistor (the "R1").

3. Connect the other end of that resistor to both: your 3V module's input pin AND to a 3.3K resistor (the "R2") to ground.

4. If you have a meter, perhaps before connecting to your module input first double check your circuit at the juncture of the resistors. Actual serial data probably won't produce a reliable reading so temporarily alter your sketch to just take the 5V Pro Trinket pin HIGH. I measured 3.1 V output on mine when the output goes HIGH and it works great with the EZ-Key module.