body:
I am creating a miniature computer using an Arduino, and I am creating a full-scale interpreter for it. Everything works, and the code begins to run after calling the runCode method, but once the run is finished it doesn't return to the calling function. I have Serial outputs to tell me where the code reaches.

My code contains an **"Function" object** with a name and a function pointer, an **object to run the code** (with a working Lexer object that splits the inputted code by spaces), and an **in-computer editor** (which completely works except the one function) to input programs to be run.

The function that calls the runCode method for my code-running object (called Joker) **is in the editor**. The problem is, once the runCode finishes, it does not return. **The system halts.** I will post the Function class, runCode Method, and calling method.

P.S. There are Serial prints to determine where the code reaches. It outputs "Function End!", but not "Failed!"/"Succeeded".

P.P.S. It uses a parallax 4x20 Back-lit Single-pin Serial LCD which completely 100% works.

P.P.P.S It uses the QueueList<T> library which is basically a dynamic list that works like a stack.

One more note: The code heavliy uses dynamic lists, function pointers, and lambda expressions, so.... be prepared....

---

Code for Function class (no it does not have any actual functions):

    class Function {
    public:
      String f_name;
      bool (*f_run) (QueueList<float> &stack, SoftwareSerial &lcd);
    };

Code for runCode method:

    bool Joker::runCode(QueueList<String> lineTable, SoftwareSerial &lcd) {
      // Set up lexer
      Lexer lexer;
      // Get all lexer words
      lexer.getWords(lineTable);

      String cur_word = "";
      float num_val = 0.0f;
      bool quit = false;

      while(!quit) {
        cur_word = lexer.nextWord();
        if(cur_word == "")
          quit = true;
        else {
          // Get word in uppercase
          cur_word.toUpperCase();

          Serial.println(cur_word);

          // Parse the first number from it
          num_val = cur_word.toFloat();

          // Check if we have a function
          if(queueListContains(cur_word, dictionary)) {
            Function theFunc = getDictionaryFunction(cur_word, dictionary);
            if(!theFunc.f_run(stack, lcd)) {
              error(F("Unable to process word!!"), lcd);
              return false;
            }
          } else if(num_val != 0) {         // check if the parse was good
            stack.push(num_val);            // if it was: push num to the stack
          } else if(num_val == 0) {         // if zero it could be parsing a zero or it could have failed
            if(cur_word.indexOf("0") != -1) // if it didn't fail:
              stack.push(num_val);          // push to the stack
            else {                          // otherwise:
              error(F("Unknown word!!"), lcd);   // Unknown word error
              return false;
            }
          } else {
            error(F("Unknown word!!"), lcd);
            return false;
          }
        }
      }

      // Test printing the stack
      /*while(!stack.isEmpty()) {
        lcd.print(stack.pop());
        lcd.print(' ');
      }*/

      Serial.print(F("Function end!"));
      return true;
    }

And the caller method:

    void line_editor::RunProgram(SoftwareSerial &lcd) {
      Serial.println("Running program!!");
      // Move to top line
      currentLine = 0;
      while(!lineTableB.isEmpty()) {
        lineTableA.push(lineTableB.pop());
        // Serial.print(lineTableB.peek());
      }

      // Clear the string
      lcd.write(12);
      delay(5);
      lcd.write(128);

      // Joker language object
      Joker joker;

      QueueList<Function> PrintingWords;

      // Create the printing functions
      Function printWord;
      printWord.f_name = "BC"; // print "Beginning Card"
      printWord.f_run = [] (QueueList<float> &stack, SoftwareSerial &lcd) {
        if(stack.isEmpty()) {
          return false;
        }

        float num = stack.pop();
        lcd.print(num);
        lcd.write(13);

        return true;
      };
      PrintingWords.push(printWord);

      // Print the whole stack
      Function printStack;
      printStack.f_name = "AC"; // print "All Cards"
      printStack.f_run = [] (QueueList<float> &stack, SoftwareSerial &lcd) {
        while(!stack.isEmpty()) {
          lcd.print(stack.pop());
          lcd.print(' ');
        }

        lcd.write(13);

        return true;
      };
      PrintingWords.push(printStack);

      // Add all the functions
      joker.addWords(PrintingWords);

      // Run Program here...
      if(joker.runCode(lineTableA, lcd))
        Serial.println("Success!!");
      else
        Serial.println("Failed!!");

      // lineTableA.push(lineTableB.pop());

      Serial.println("Here!!");

      return;
    }

Sorry if I confused anyone. If there are any questions, then leave a comment, and I'll try to clear up the confusion. Any help would be appreciated.

**EDIT::ADDING FULL CODE:**
Here is a [LINK][1] to the rest of the code on github.

  [1]: https://github.com/blueOkiris/TASIC-PC/tree/master

Also, here is the rest of the Joker.cpp:

    void Joker::addWords(QueueList<Function> new_dict) {
      while(!new_dict.isEmpty()) {
        dictionary.push(new_dict.pop());
      }
    }

    bool Joker::queueListContains(String theWord, QueueList<Function> &list) {
      Serial.println("Finding word:");

      QueueList<Function> temp;

      while(!list.isEmpty()) {
        Function r = list.pop();
        temp.push(r);

        Serial.print(">> ");
        Serial.println(theWord);
        Serial.print(">> equals? ");
        Serial.println(r.f_name);
        delay(5);

        if(r.f_name.equals(theWord)) {
          while(!temp.isEmpty())
            list.push(temp.pop());
          return true;
        }
      }

      while(!temp.isEmpty())
        list.push(temp.pop());

      return false;
    }

    Function Joker::getDictionaryFunction(String theWord, QueueList<Function> &list) {
      QueueList<Function> temp;

      while(!list.isEmpty()) {
        Function theFunction = list.pop();
        temp.push(theFunction);

        if(theFunction.f_name.equals(theWord)) {
          while(!temp.isEmpty()) {
            list.push(temp.pop());
          }
          return theFunction;
        }
      }
    }

    void Joker::error(String message, SoftwareSerial &lcd) {
      lcd.write(12);
      delay(5);
      lcd.write(128);

      lcd.print(message);

      delay(2000);
    }

And the header:

    #pragma once

    class Joker {
    private:
      bool queueListContains(String theWord, QueueList<Function> &list);
      Function getDictionaryFunction(String theWord, QueueList<Function> &list);

    public:
      QueueList<float> stack;
      QueueList<Function> dictionary;

      void error(String message, SoftwareSerial &lcd);
      void addWords(QueueList<Function> new_dict);
      bool runCode(QueueList<String> lineTable, SoftwareSerial &lcd);
    };

title: Why doesn't my object's method return back to my caller method?

Answers: 1

body:
The short answer here is - It does not return because you have corrupted the stack.
The return address is pushed onto the stack as part of the function call.  If you overwrite (corrupt) that address the program cannot jump back to where it was (return).

So where is the cause of the problem?

Does `getDictionaryFunction(cur_word, dictionary)` ever return NULL or an invalid pointer?  The code tries to execute it anyway.  EDIT: What happens below when *theWord* is not matched or *list* is empty?  Actually I'm surprised this compiles, since there's a few paths where no value is returned.  (I'm no expert on the GCC AVR compiler, but what happens if we don't assign a return value at all?)

    Function Joker::getDictionaryFunction(String theWord, QueueList < Function > &list)
    {
        QueueList < Function > temp;

        while (!list.isEmpty())
        {
            Function theFunction = list.pop();
            temp.push(theFunction);

            if (theFunction.f_name.equals(theWord))
            {
                while (!temp.isEmpty())
                {
                    list.push(temp.pop());
                }
                return theFunction;
            }
        }
        // BAD-JUJU HAPPENS IF WE GET HERE
        assert(false);
    }

Coding style tip: except in trivial cases, it's good to only return from the bottom of your function.  Then the above never happens, and supposedly it's easier for the compiler to optimise.  NOTE: I'm unsure if `assert()` will even do anything on Arduino.  It's left as a marker to mean *Handle Error Here*.

    Function Joker::getDictionaryFunction(String theWord, QueueList < Function > &list)
    {
        Function dict_func = NULL;
        QueueList < Function > temp;

        while (!list.isEmpty())
        {
            Function theFunction = list.pop();
            temp.push(theFunction);

            if (theFunction.f_name.equals(theWord))
            {
                while (!temp.isEmpty())
                    list.push(temp.pop());
                dict_func = theFunction;
                break;
            }
        }
        assert(dict_func != NULL);  // This should never happen
        return dict_func;
    }

Coding style tip: WoRd CasE ~ lower_case, mixedCase, CapitalCase, UPPER_CASE.  I use lower case for all_variable_names, mixed case for functionNames(), capital case for ClassNames and StructureNames, and upper case for MACROS and CONSTANT_DEFINITIONS.  Pick a system, and stick to it absolutely.

Have you run out of memory - the stack could have hit the heap.
What sort of Arduino are you using?

On an Uno, with only 2k of RAM, you might need to make some scope-cuts.
Even on an Arduino Mega, you still only have 8k.

Maybe you can make use of a `freeMemory()` function.  This will give you an indication of the free space between the stack and the heap.  The AdaFruit version is below, but there are others too.

    int freeRam ()
    {
      extern int __heap_start, *__brkval;
      int v;
      return (int) &v - (__brkval == 0 ? (int) &__heap_start : (int) __brkval);
    }

It may be worthwhile reading their [page on Arduino memory usage][1].

So after having a browse through your code, I can't see any obvious problems.  Fix the `getDictionaryFunction()` so you know if it's failing.  Check to see if you're running out of RAM - you are making heavy use of it copying strings around, especially with that template class.

Maybe consider re-compiling the code on a workstation in GCC - it wouldn't take much, just change your serial outputs to printf(), and hard-code your input data (or read from a file).  That will enable easier debugging.

  [1]: https://learn.adafruit.com/memories-of-an-arduino/measuring-free-memory


body: I've gotten contradicting information on the subject.  Some say that digital input pins send out positive voltage, and if it goes to ground (for example) it reads LOW but if the pin is connected to power, it will read HIGH.  On the other hand, some say that the input pin is receiving voltage from either power (+5V) or ground (0V).  which one is it?

title: do digital input pins act as a positive or negative

Answers: 2

body: It's both, depending on whether or not the internal pullup has been enabled (`INPUT` versus `INPUT_PULLUP`). The pullup ties the input to the positive supply through a moderately large resistance, meaning that it is possible to source a small amount of current from the input pin.

body:
Digital pins sink or source current. They don't provide negative voltages. If the pin is set to `INPUT` then it is high impedance and will not "send out positive voltage".

However if you activate the internal pull-ups, as Ignacio said, then effectively the pin is connected to +5V via (approximately) a 50k resistor.


body:
I have moved the MCU of the Arduino to a breadboard using these steps https://www.arduino.cc/en/Main/Standalone then interfaced it with an LM35 temperature sensor to the ADC0. But I can't get proper values from the LM35. I think it's because of the Aref or AVcc. Both are just connected to +5?
Here is my code:

<!-- language: c -->

    float tempC;
    float reading;

    void setup()
    {
        Serial.begin(9600);
    }

    void loop()
    {
        reading = analogRead(0);
        tempC = (reading * 0.4882815) + 5;
        Serial.print(tempC);
        delay(1000);
    }

I get hex values and sometime high values. What to do with Aref and AVcc?

**EDIT:** I get values like these
€
Œ

title: Arduino to breadboard with LM35 temp sensor

Answers: 2

body:
Check the `baud rate` of your serial monitor matches what you have set in your setup() function.  In the above code that is 9600.  If the baud rate is incorrect you typically get rubbish output in the serial monitor.

[![Serial Monitor set at 9600 baud][1]][1]

You may also want to change the Serial.print(tempC) to

    Serial.println(tempC,2);

To get some decimal places.

As for the circuit ~

[![Ricardo Sequeria's example Arduio & LM35][2]][2]

 - You don't need ARef connected.
 - The LM35 VCC should be connected to Arduino 5V
 - The LM35 GND to Arduino Gnd (any of them)
 - Finally LM35 signal (Vout) to Arduino A0.

  [1]: https://i.stack.imgur.com/7oANR.png
  [2]: https://i.stack.imgur.com/vs7wj.png

body:
> clearly it's not flashing every second.

Is it flashing about every .73 seconds? That would be the period you'd expect if you have a 22.000MHz crystal: period = (16/22 * 1.00 sec). (If so, that is a rather high over-clock rate for the chip but suggests just how hardy they really are.)

> I haven't bought any 16 MHz crystal. What will I do?

Buy a 16MHz crystal. That's the right fix. But you might (if I guessed correctly that you have a 22MHz crystal) - *might* - get away with trying a baud rate of (16/22) times your present baud rate, de-rating it to compensate for the clock rate. Be as precise as you can. You'll need to reprogram the chip with your Arduino board because the chip's bootloader expects a 16MHz clock.

Or, if it's not 22MHz, you could time a number of blinks (50 or 100), calculate the clock rate error, and re-calculate a baud rate the way I did above. Use a lower baud rate to start with; it is likely to be less affected by small timing errors.


body: Does anyone know how to do the run time calibration for MPU9250 ?

title: How to do run time calibration for MPU9250?

Answers: 1

body:
I used [this script][1] to calibrate the MPU6050, which is the same as the MPU9250 minus the digital compass. [This guide][2] explains how to calibrate the MPU9250's magnetometer.

  [1]: http://wired.chillibasket.com/2015/01/calibrating-mpu6050/
  [2]: https://github.com/kriswiner/MPU-6050/wiki/Simple-and-Effective-Magnetometer-Calibration


body:
I tried to build a simple l-meter with my arduino due. I programmed a simple frequency meter with one timer and one counter. The timer takes an interrupt each 10s, 100ms, 10ms and 1ms. But ones the interrupt is taken it is stopped and even a short `Serial.println("Hello World");` does not appear in the serial monitor of the arduino IDE. I don't know what I forgot.
Here is my code:

    #define voltage 26

    volatile uint32_t current_range = 10000;               //starts with highest range and decrements. longer measurements produce more precise results. measurements for small l values require 11.111ms
    volatile const double c_1 = 2533029590000000.0;        //constant value for l value calculation
    volatile double correction_value = 0;
    volatile boolean calib = true;
    volatile uint32_t counter_value = 0;

    void initCounter(){
        pmc_enable_periph_clk(ID_TC0);              //enable peripheral clock for TC0

        REG_TC0_CMR0 = TC_CMR_TCCLKS_XC0;           //External clock 0 connected to PB26 (Digital Pin 22)
        REG_TC0_CCR0 = TC_CCR_CLKEN;                //Enable clock
    }

    void initTimer(){
        pmc_enable_periph_clk(ID_TC1);              //enable peripheral clock for TC1

        REG_TC0_CMR1 = TC_CMR_TCCLKS_TIMER_CLOCK1;  //42MHz clock
        REG_TC0_IER1 = TC_IER_CPCS;                 //Enable compare RC interrupt
        REG_TC0_IDR1 = ~TC_IDR_CPCS;                //Enable compare RC interrupt (disbale interrupt = 0)
        REG_TC0_CCR1 = TC_CCR_CLKEN;                //Enable clock

        NVIC_EnableIRQ(TC1_IRQn);                   //Enable interrupt in nested vectored interrupt controller NVIC (IRQN number = TC number * channels + channel number)
    }

    double calc_l(uint32_t CV){
        double freq = (double)CV / ((double)current_range / 1000.0);
        freq = freq * freq;

        return c_1 / freq;
    }

    void calibrate(){
        Serial.println("---Calibrating... shorten inputs then press enter---");
        while(!(Serial.available() == '\n'));
        Serial.print("Start calibration\n");
        initCounter();                              //initialize counter
        initTimer();                                //initialize timer

        REG_TC0_RC1  = 0x1908B100;                  //RC = 420.000.000 to run 10.000ms

        REG_TC0_BCR = TC_BCR_SYNC;                  //reset and start timer and counter simultaneously
    }

    void measure(){
        calib = false;

        //Serial.println("---Measure... connect inductivity then press any key---");
        //while(!(Serial.available() > 0));
        initCounter();                              //initialize counter
        initTimer();                                //initialize timer
        REG_TC0_RC1  = 0x1908B100;                  //RC = 420.000.000 to run 10.000ms

        REG_TC0_BCR = TC_BCR_SYNC;                  //reset and start timer and counter simultaneously
    }

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

        pmc_set_writeprotect(false);                //disable writeprotect for pmc
        pinMode(13, OUTPUT);
        pinMode(voltage, OUTPUT);                   //set digital pin 26 as output
        digitalWrite(voltage, HIGH);                //set digital pin 26 HIGH
        delay(1000);                                //wait 1 second to get circuit working

        calibrate();
    }

    void loop() {
        analogWrite(13, 25);
        delay(100);
        Serial.print(REG_TC0_SR1);
        Serial.print(";");
        Serial.print(REG_TC0_CMR1);
        Serial.print(";");
        Serial.print(REG_TC0_IER1);
        Serial.print(";");
        Serial.print(REG_TC0_IDR1);
        Serial.print(";");
        Serial.print(REG_TC0_CCR1);
        Serial.print("\n");
    }

    void TC1_Handler(){

        uint32_t SR = REG_TC0_SR0;                    //save status register
        uint32_t CV = REG_TC0_CV0;                    //save counter value

        if((SR & TC_SR_CLKSTA) == TC_SR_CLKSTA){      //check whether counter clock is enabled
            if((SR & TC_SR_COVFS) == TC_SR_COVFS){      //check whether counter overflow accured
                switch(current_range){                    //check current range. decrement until smallest range is reached. then print error
                    case 10000: REG_TC0_RC1  = 0x280DE80;                   //RC = 42.000.000 to run 1.000ms
                                current_range = 1000;
                                REG_TC0_BCR  = TC_BCR_SYNC;
                                break;
                    case 1000:  REG_TC0_RC1  = 0x401640;                    //RC = 4.200.000 to run 100ms
                                current_range = 100;
                                REG_TC0_BCR  = TC_BCR_SYNC;
                                break;
                    case 100:   REG_TC0_RC1  = 0x668A0;                     //RC = 420.000 to run 10ms
                                current_range = 10;
                                REG_TC0_BCR  = TC_BCR_SYNC;
                                break;
                    case 10:    REG_TC0_RC1  = 0xA410;                      //RC = 42.000 to run 1ms
                                current_range = 1;
                                REG_TC0_BCR  = TC_BCR_SYNC;
                                break;
                    case 1:     //Serial.println("Error: l value out of range!");
                                REG_TC0_CCR0 = ~TC_CCR_CLKEN;
                                REG_TC0_CCR1 = ~TC_CCR_CLKEN;
                                break;
                }
            } else {
                if(calib){
                    if(CV < 10){
                        //Serial.println("Error: wrong calibration value!");
                        REG_TC0_CCR0 = ~TC_CCR_CLKEN;
                        REG_TC0_CCR1 = ~TC_CCR_CLKEN;
                    } else {
                        //correction_value = calc_l(CV);
                        measure();
                    }
                } else {
                    if(CV < 10){                           //check if counter value is below 10. then l value is to high to get accurate results
                        //Serial.println("Error: l value out of range!");
                        REG_TC0_CCR0 = ~TC_CCR_CLKEN;
                        REG_TC0_CCR1 = ~TC_CCR_CLKEN;
                    } else {                               //l value in nH;
                        counter_value = CV;
                        //Serial.print(calc_l(CV) - correction_value);
                        //Serial.print(" nH; ");
                        //Serial.print(CV);
                        //Serial.print(" ticks in ");
                        //Serial.print(current_range);
                        //Serial.println("ms.");
                        REG_TC0_CCR0 = ~TC_CCR_CLKEN;
                        REG_TC0_CCR1 = ~TC_CCR_CLKEN;
                    }
                }
            }
        } else {
            REG_TC0_CCR0 = TC_CCR_CLKEN;
            REG_TC0_BCR  = TC_BCR_SYNC;
        }
    }

It would be very nice if someone could help me with this.

title: Arduino Due interrupt is taken but not executed completely

Answers: 1

body:
Maybe I'm dense, but I don't understand why most of the config code is in the ISR.  If the system is getting bound up there, I'd move much of it out and try to simplify it as much as possible, maybe saving only the counter value and the fact that the timer triggered on interrupt, and saving the overflow value if it overflowed.  Then, outside the ISR, on the reporting timescale, I'd check that there was valid data and report or reconfigure as needed.

    int validReading = 0;
    uint32_t measuredCount;
    int overflowed =0;

    void TC1_Handler(){
        measuredCount = REG_TC0_CV0;
        if((SR & TC_SR_COVFS) == TC_SR_COVFS){  //counter overflow occurred
           validMeasurement=0;
           overflow=1;
        else {
           validMeasurement = 1;
           // either reset counter and clock or stop handling interrupts
        }
     }

     loop(){
       ...
       if (validReading) { // report
          ...
       } else {
       if (overflowed ) { // shorten sampling time, calibrate, and initialize
          ...
       }
       if ( measuredCount < 10 ) { // lengthen sampling time?
          ...
       }
       // calibrate and reinitialize
     }


body:
I am using the pin 4 as an OUTPUT and pin 8 as an INPUT to turn on/off the light, but for some reason it is not working. Light is on all the time, but when I try to input something it gets brighter and doesn't turn off when I don't give anything to pin 8.

LED is connected to pin 4 with a 220 R, and the other side to GND. When pin 8 is connected to 5V pin then the light should come on, and off when I disconnect them.

Here is the code:

    void setup()
    {
      Serial.begin(9600);
      pinMode(4, OUTPUT);
      pinMode(8, INPUT);
    }

    void loop()
    {
       bool on = digitalRead(8);
       if(on)
       {
         digitalWrite(4, HIGH);
       }
       else
       {
         digitalWrite(4, LOW);
       }
    }

What am I doing wrong?

title: Turn on a light when there is an input

Answers: 1

body:
Use input with pullup on pin 8 and a button to ground (GND). See below:

    const int ledPin = 4;
    const int buttonPin = 8;

    void setup()
    {
      pinMode(ledPin, OUTPUT);
      pinMode(buttonPin, INPUT_PULLUP);
    }

    void loop()
    {
       digitalWrite(ledPin, digitalRead(buttonPin));
    }

Using the pin as input and disconnecting is not the same as GND. The pin is floating. By using the internal pullup resistor the pin is HIGH when the button is not connected to GND.


body:
I have designed a circuit for an SGX EC410 oxygen sensor by using these application note -PAGE 4, FIGURE 4 - (http://www.sgxsensortech.com/content/uploads/2014/08/A1A-EC_SENSORS_AN2-Design-of-Electronics-for-EC-Sensors-V3.pdf). When I try to measure the biased voltage between working (SENS) and reference (REF) electrode, the value of -600 mV is held for about one second and goes down to few milli volts rapidly. The same happens when I connect the sensor without voltmeter. Am I doing something totally wrong, or the circuit is not quite right?
[![enter image description here][1]][1]

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

title: Problem with biased circuit for oxygen sensor (SGX EC410)

Answers: 0


body:
Recently I ordered some ATtiny85's from [Jameco][1], and I've been trying to upload code to them through an Arduino Uno, following the instructions from [this video on YouTube][2]. I've been getting a lot of unexpected errors and I am now wondering if the chips I bought are the problem. Here are the specs from the Jameco website:

> Flash (Kbytes): 8 Kbytes
>
> Pin Count: 8
>
> Max. Operating Frequency: 20 MHz
>
> Power Supply: 2.7 - 5.5V
>
> Operational Range: Industrial (A) (-40°C to 85°C)
>
> CPU: 8-bit AVR
>
> Number of Touch Channels: 3
>
> Hardware QTouch Acquisition: No
>
> Max I/O Pins: 6
>
> Ext Interrupts: 6
>
> USB Speed: No
>
> USB Interface: No

Does the "USB Speed: No; USB Interface: No" mean these aren't programmable by my set up? Or is there is anything else I should know about these chips? Do I need to get new ones that are different?

  [1]: http://www.jameco.com/webapp/wcs/stores/servlet/Product_10001_10001_2151312_-1
  [2]: https://www.youtube.com/watch?v=9LjfkjwMqXI

title: Programming an ATtiny85

Answers: 2

body:
Before you panic (try not to panic) and buy new chips, test the existing ones. See my [page about detecting chip signatures](http://www.gammon.com.au/forum/?id=11633) which has links to [code on Github](https://github.com/nickgammon/arduino_sketches) for a sketch you can run on your Uno, to test the ATtiny85.

[![Chip detector wiring][1]][1]

---

You can also upload code from a .hex file (which the IDE produces) by using a different sketch (same code link) from [this page about a hex uploader](http://www.gammon.com.au/uploader) and wiring like this (you also need an SD card adapter):

[![Chip programmer][2]][2]

---

The first sketch and wiring should at least confirm your chips are OK. The second one is an alternative way of programming them.

  [1]: https://i.stack.imgur.com/OMHlr.jpg
  [2]: https://i.stack.imgur.com/7JMKQ.jpg

body:
I would suggest you to take a look at this video which explains step by step how to program the ATtiny85. <https://www.youtube.com/watch?v=i9WOwDrpRKs>

From my early days trying to program the ATtiny, i have watched this video.


body:
I bought some material on the net to start working with Arduino. I didn't want to buy an Arduino, since it costs a bit too much IMHO, so I bought an ATMega328P-PU, and made an Arduino on a breadboard. However, when I use my USBasp to program it it says that he can't set sck period (settings are: Arduino Uno as Board, USBasp as Programmer). It says that it has loaded the bootloader/program anyway, so I tried to go on and ignore it. The blink program can be loaded via programmer, but it doesn't blink (I'm using a small lamp, connecting it directly to 5V and ground works). Here I describe the circuit:

* First Atmega Pin, Arduino Reset -> 10 kOhm Resistor (Brown, Black, Black, Red, Brown) -> Ground (not GND pin);

* 1st pin, Arduino Reset -> also to USBasp RST;

* 7th pin, Arduino VCC -> directly to 5V (and USBasp VCC);

* 8th, GND -> directly to Ground (and USBasp GND);

* 9th, XTAL -> to one pin of the 16MHz Crystal Oscillator, and to 22 pF capacitor, which connects to ground (not the pin);

* 10th, XTAL -> exactly as above, but it's connected to the other pin of the same crystal;

* 17th, digital 11 -> USBasp MOSI;

* 18th, dig 12 -> USBasp MISO;

* 19th, dig 13 -> USBasp SCK, and to the lamp whose other pin goes to ground (neither pin nor direct works), but the lamp needs to be disconnected while loading programs to prevent errors (target not responding);

* 20th, AVCC, and 21st, AREF -> directly to 5V;

* 22nd -> directly to ground (not pin).

title: ATMega328P-PU not working

Answers: 2

body:
> The blink program can be loaded via programmer, but it doesn't blink (I'm using a small lamp, connecting it directly to 5V and ground works).
>
> 19th, dig 13 -> USBasp SCK, and to the lamp whose other pin goes to ground (neither pin nor direct works), but the lamp needs to be disconnected while loading programs to prevent errors (target not responding);

The lamp needs to be low power (< 20 mA) to work this way. If it uses more power you will burn the MCU pin.

Use a LED and a resistor instead. Or at least use a voltmeter.

> 21st, AREF -> directly to 5V;

This is not a good idea. Should be capacitor to ground. See for instance [Uno schematics][1].

Cheers!

  [1]: https://www.arduino.cc/en/uploads/Main/Arduino_Uno_Rev3-schematic.pdf

body:
> First Atmega Pin, Arduino Reset -> 10 kOhm Resistor (Brown, Black, Black, Red, Brown) -> Ground (not GND pin);

So it's permanently in RESET mode then? How can it ever do anything if you're holding it in RESET all the time?

RESET should be pulled UP by the resistor, not DOWN.


body:
Here's the whole error:

     Arduino: 1.6.7 (Windows 7), Board: "Arduino/Genuino Uno"

     *\readMifare\readMifare.ino: In function 'void loop()':

     readMifare:113: error: expected primary-expression before ']' token

        if (uid[] == { 0x04, 0xEC, 0x89, 0x32, 0x55, 0x42, 0x80 }) {

                ^

     readMifare:113: error: expected primary-expression before '{' token

        if (uid[] == { 0x04, 0xEC, 0x89, 0x32, 0x55, 0x42, 0x80 }) {

                     ^

     readMifare:113: error: expected ')' before '{' token

     readMifare:121: error: expected '}' at end of input

        }

        ^

     exit status 1
     expected primary-expression before ']' token

       This report would have more information with
       "Show verbose output during compilation"
       enabled in File > Preferences.

Here's the code

     #include <Wire.h>
     #include <SPI.h>
     #include <Adafruit_PN532.h>

     // If using the breakout with SPI, define the pins for SPI communication.
     #define PN532_SCK  (2)
     #define PN532_MOSI (3)
     #define PN532_SS   (4)
     #define PN532_MISO (5)
     // If using the breakout or shield with I2C, define just the pins connected
     // to the IRQ and reset lines.  Use the values below (2, 3) for the shield!
     #define PN532_IRQ   (2)
     #define PN532_RESET (3)  // Not connected by default on the NFC Shield

     // Uncomment just _one_ line below depending on how your breakout or shield
     // is connected to the Arduino:

     // Use this line for a breakout with a software SPI connection (recommended):
     Adafruit_PN532 nfc(PN532_SCK, PN532_MISO, PN532_MOSI, PN532_SS);

     // Use this line for a breakout with a hardware SPI connection.  Note that
     // the PN532 SCK, MOSI, and MISO pins need to be connected to the Arduino's
     // hardware SPI SCK, MOSI, and MISO pins.  On an Arduino Uno these are
     // SCK = 13, MOSI = 11, MISO = 12.  The SS line can be any digital IO pin.
     //Adafruit_PN532 nfc(PN532_SS);

     // Or use this line for a breakout or shield with an I2C connection:
     //Adafruit_PN532 nfc(PN532_IRQ, PN532_RESET);

     #if defined(ARDUINO_ARCH_SAMD)
     // for Zero, output on USB Serial console, remove line below if using      programming port to program the Zero!
     // also change #define in Adafruit_PN532.cpp library file
     #define Serial SerialUSB
     #endif
     #include <Servo.h>

     Servo servo1;

     void setup(void) {
       #ifndef ESP8266
       while (!Serial); // for Leonardo/Micro/Zero
       #endif
       Serial.begin(115200);
       Serial.println("Hello!");

       nfc.begin();

       uint32_t versiondata = nfc.getFirmwareVersion();
       if (! versiondata) {
         Serial.print("Didn't find PN53x board");
         while (1); // halt
       }
       // Got ok data, print it out!
       Serial.print("Found chip PN5"); Serial.println((versiondata>>24) & 0xFF, HEX);
       Serial.print("Firmware ver. "); Serial.print((versiondata>>16) & 0xFF, DEC);
       Serial.print('.'); Serial.println((versiondata>>8) & 0xFF, DEC);

       // configure board to read RFID tags
       nfc.SAMConfig();

       Serial.println("Waiting for an ISO14443A Card ...");
       servo1.attach(9);
     }

     void loop(void) {
       uint8_t success;
       uint8_t uid[] = { 0, 0, 0, 0, 0, 0, 0 };  // Buffer to store the returned UID
       uint8_t uidLength;                        // Length of the UID (4 or 7 bytes depending on ISO14443A card type)

       // Wait for an ISO14443A type cards (Mifare, etc.).  When one is found
       // 'uid' will be populated with the UID, and uidLength will indicate
       // if the uid is 4 bytes (Mifare Classic) or 7 bytes (Mifare Ultralight)
       success = nfc.readPassiveTargetID(PN532_MIFARE_ISO14443A, uid, &uidLength);

       if (uid[] = { 0x04, 0xEC, 0x89, 0x32, 0x55, 0x42, 0x80 }) {

          int position;
          for(position = 0; position < 180; position += 2){
           servo1.write(position);
           delay(20);
          }

       }

Please note that I'm using an example from the *Adafruit official PN532 library examples* and trying to edit it.

title: Exit status 1 expected primary-expression before ']' Arduino

Answers: 2

body:
You probably need something like:

    uint8_t uidTarget[] = { 0x04, 0xEC, 0x89, 0x32, 0x55, 0x42, 0x80 };

    ...
    if (success && !strncmp((const char*) uidTarget,(const char*)uidSource,8)) {

Your '=' tries to do an assignment, and an '==' would check if the pointers to the arrays are identical, rather than the contents of the arrays.  strncmp() tests equality of strings of characters, and the (const char*) casts the uint8_t values as characters.

Nick Gammon's answer is better.

body:
I wouldn't use `strncmp` because the UID might have zeroes in it. This looks safer:

<!-- language-all: lang-C++ -->

       uint8_t uid[] = { 0, 0, 0, 0, 0, 0, 0 };  // Buffer to store the returned UID
       uint8_t uidLength;                        // Length of the UID (4 or 7 bytes depending on ISO14443A card type)

       const uint8_t wantedUid [] = { 0x04, 0xEC, 0x89, 0x32, 0x55, 0x42, 0x80 };

       // Wait for an ISO14443A type cards (Mifare, etc.).  When one is found
       // 'uid' will be populated with the UID, and uidLength will indicate
       // if the uid is 4 bytes (Mifare Classic) or 7 bytes (Mifare Ultralight)
       success = nfc.readPassiveTargetID(PN532_MIFARE_ISO14443A, uid, &uidLength);

       if (success &&
          uidLength == sizeof (wantedUid) &&
          memcmp (uid, wantedUid, sizeof wantedUid) == 0) {
          ...

I threw in a test for the uidLength being the expected size, otherwise you might find a 4-byte card happens to match the first four bytes of the wanted UID.

`memcmp` compares a block of memory for the number of bytes you specify. It returns zero on a match.


body:
So I have a programme that loads a text file from an sd card into a string array. Each line in the text file is stored in a different string in a string array. Well its supposed to be.

    file = SD.open("/classes/basic.txt", FILE_READ);
    Serial.print("Reading, Checking and Compiling \n\n\n");

    for(int i = 0; i < sizeof(result)-1;i++){
     while(file.available()) {
      character23 = file.read();
      content.concat(character23);

    }
    if (content != "") {
      result[i] = content;
        Serial.println(content);

    }

  }

I want each line in the txt file to be stored in a different string in the array, in chronological order and each string has to be accessible individually. The problem with this code is that it stores the whole text file in one string. How can I fix this?

EDIT: here is what I have now

      file = SD.open("/classes/basic.txt", FILE_READ);
      Serial.print("Reading, Checking and Compiling \n\n\n");

     for(int i = 0; i < sizeof(result)-1;i++){
       while(file.available()) {
      character23 = file.read();
      if (character23 == '^') break;
      content.concat(character23);

    }
    if (content != "") {
      result[i] = content;
      Serial.println(content);

      delay(1000);
    }

  }
 Serial.println(result[3]);

title: Arduino array length

Answers: 1

body:
To do that, you need to read the file until you reach a line break.

Replace this code:

    while(file.available()) {
      character23 = file.read();
      content.concat(character23);
    }

by this:

    while(file.available()) {
       character23 = file.read();
       if (character23 == '\n') break;
       content.concat(character23);
    }


body:
I'm working on a project where I need a high torque stepper motor. The stepper motor being used is rated at 12 - 24 volts and when I used a 12 volt battery supply composed of 8 AA batteries it appeared to work fine.

Because I wanted higher torque I set the pot on the Easy Driver to 0.5 amps which is within what was recommended for the motor, and used a Lithium Ion battery originally being used for a power drill rated at 18V and 1.5Ah.

When I connected the battery to the easy driver the motor got very hot and would shake when I tried to turn it but not turn. Now the motor will not work with the 8 AA batteries either. Heres a link to the motor [US Ship OSM 5:1 Planetary Gearbox Nema 8 Stepper Motor Samll Size High Torque][1].

[![Project][2]][2]

What did I do wrong and how can I fix it?

P.S. I am using a photon as the micro controller and the motor is being controlled using the Blynk app I eliminated the chance of it having to do with the photon or Blynk App.

I found out that the battery I'm using is the Makita BL1815 and it is really composed of 2 batteries which are both rated at 15C. I am not sure if C-rating adds or stays the same when you are using two batteries. When I measure the Voltage on the test points I get 4.27V and when using a formula to find current for the Easy Driver I get 0.480A.

  [1]: http://www.ebay.com/itm/US-Ship-OSM-5-1-Planetary-Gearbox-Nema-8-Stepper-Motor-Samll-Size-High-Torque-/231616295885?hash=item35ed6833
  [2]: https://i.stack.imgur.com/snDwc.jpg

title: Powering a stepper motor

Answers: 1

body:
How did you set the amps on the http://www.schmalzhaus.com/EasyDriver/ to 0.5A?   What was the voltage at the test point?  The EasyDriver v4.5 schematic says the formula for coil current is A = V/6.  So rearranging, V=A*6, and to get 0.5A, the voltage should be 0.5*6=3V at the motor driver's test point.

The linked motor spec is 0.6A max per coil, and if things went wrong, you could have overloaded a motor.  The 18V battery could have easily provided 1.8 amps to the 10ohm coil in the motor for a bit, before 3x the rated current of the coils would burn it out, or the easydriver went into thermal shutdown or something.

The easydriver looks like it would be capable of controlling the current adequately, but if misconfigured, could easily overcurrent the motor.


body:
I'm having problem  on how can I use IMU and NRF24 together.

 This is the code that i'm trying to use,

     /*
     Copyright (C) 2012 James Coliz, Jr. <maniacbug@ymail.com>
     This program is free software; you can redistribute it and/or
     modify it under the terms of the GNU General Public License
     version 2 as published by the Free Software Foundation.

     Update 2014 - TMRh20
    */
    /**
    * Simplest possible example of using RF24Network
    *
    * TRANSMITTER NODE
    * Every 2 seconds, send a payload to the receiver node.
    */
    #include <RF24Network.h>
    #include <RF24.h>
    #include <SPI.h>
    #include <Wire.h>
    #include "I2Cdev.h"
    #include "RTIMUSettings.h"
    #include "RTIMU.h"
    #include "RTFusionRTQF.h"
    #include "CalLib.h"

    RTIMU *imu;                                           // the IMU object
    RTFusionRTQF fusion;                                  // the fusion object
    RTIMUSettings settings;                               // the settings object

    //  DISPLAY_INTERVAL sets the rate at which results are displayed

    #define DISPLAY_INTERVAL  300                         // interval between
    pose displays

    //  SERIAL_PORT_SPEED defines the speed to use for the debug serial port

    #define  SERIAL_PORT_SPEED  11520
    unsigned long lastDisplay1;
    unsigned long lastRate1;
    int sampleCount1;

     RF24 radio(7,8);                    // nRF24L01(+) radio attached using
     Getting Started board
     RF24Network network(radio);          // Network uses that radio
     const uint16_t this_node = 01;        // Address of our node in Octal
     format
     const uint16_t other_node = 00;       // Address of the other node in Octal
     format
     const unsigned long interval = 2000; //ms  // How often to send 'hello
     world to the other unit
     unsigned long last_sent;             // When did we last send?
     unsigned long packets_sent;          // How many have we sent already
     struct payload_t {                  // Structure of our payload
     unsigned long ms;
     unsigned long counter;
     };
     void setup(void)
     {
     int errcode;

     Serial.begin(SERIAL_PORT_SPEED);
     Wire.begin();
     imu = RTIMU::createIMU(&settings);                        // create the imu
     object

     Serial.print("ArduinoIMU starting using device "); Serial.println(imu-
     >IMUName());
     if ((errcode = imu->IMUInit()) < 0) {
     Serial.print("Failed to init IMU: "); Serial.println(errcode);
     }

     if (imu->getCalibrationValid())
        Serial.println("Using compass calibration");
     else
        Serial.println("No valid compass calibration data");

     lastDisplay = lastRate = millis();
     sampleCount = 0;

    // Slerp power controls the fusion and can be between 0 and 1
    // 0 means that only gyros are used, 1 means that only accels/compass are used
    // In-between gives the fusion mix.

    fusion.setSlerpPower(0.02);

    // use of sensors in the fusion algorithm can be controlled here
    // change any of these to false to disable that sensor

    fusion.setGyroEnable(true);
    fusion.setAccelEnable(true);
    fusion.setCompassEnable(true);

    Serial.println("RF24Network/examples/helloworld_tx/");

    SPI.begin();
    radio.begin();
    network.begin(/*channel*/ 90, /*node address*/ this_node);
    }
    void loop() {

    unsigned long now1 = millis();
    unsigned long delta1;
    int loopCount1 = 1;

    while (imu->IMURead()) {                                // get the latest
    data if ready yet
    // this flushes remaining data in case we are falling behind
    if (++loopCount1 >= 10)
            continue;
        fusion.newIMUData(imu->getGyro(), imu->getAccel(), imu->getCompass(),
    imu->getTimestamp());
        sampleCount++;
        if ((delta1 = now1 - lastRate1) >= 1000) {
            Serial.print("Sample rate: "); Serial.print(sampleCount);
            if (imu->IMUGyroBiasValid())
                Serial.println(", gyro bias valid");
            else
                Serial.println(", calculating gyro bias");

            sampleCount = 0;
            lastRate1 = now1;
        }
        if ((now1 - lastDisplay1) >= DISPLAY_INTERVAL) {
            lastDisplay1 = now1;
         RTMath::display("Gyro:", (RTVector3&)imu->getGyro());                // gyro data
          RTMath::display("Accel:", (RTVector3&)imu->getAccel());              // accel data
          RTMath::display("Mag:", (RTVector3&)imu->getCompass());              // compass data
            RTMath::displayRollPitchYaw("Pose:", (RTVector3&)fusion.getFusionPose()); // fused output
           Serial.println();
        }
    }

       network.update();                          // Check the network regularly

      unsigned long now = millis();              // If it's time to send a
      message, send it!
      if ( now - last_sent >= interval  )
      {
      last_sent = now;
      Serial.print("Sending...");
      payload_t payload = { millis(), packets_sent++ };
       RF24NetworkHeader header(/*to node*/ other_node);
       bool ok = network.write(header,&payload,sizeof(payload));
      if (ok)
      Serial.println("ok.");
      else
      Serial.println("failed.");
      }
      }

My question is what  should I put in this part

       [code]struct payload_t {                  // Structure of our payload
        unsigned long ms;
        unsigned long counter;
        };
so that the output for

     RTMath::display("Gyro:", (RTVector3&)imu->getGyro());                //
     gyro data
          RTMath::display("Accel:", (RTVector3&)imu->getAccel());
     // accel data
          RTMath::display("Mag:", (RTVector3&)imu->getCompass());
     // compass data
          RTMath::displayRollPitchYaw("Pose:",
     (RTVector3&)fusion.getFusionPose()); // fused output[/code]

 will Transmit to the RX ..

What will I put in this part :

       Serial.print("Sending...");
       payload_t payload = { millis(), packets_sent++ };
       RF24NetworkHeader header(/*to node*/ other_node);
       bool ok = network.write(header,&payload,sizeof(payload));
       if (ok)
       Serial.println("ok.");
       else
       Serial.println("failed.");

Please help me guys. Thanks :)

title: Don't know how to work IMU and NRF24 together

Answers: 1

body:
> My question is what should I put in this part

You need to take the data from IMU sensor and put it into the payload. Remember that NRF24L01 allows max 32 byte payload and the library uses some of that.

The RTVector3 is a C++ class with 3 floating point numbers. With AVR float/double that is 12 bytes. This means that you will have to send several messages.

    enum {
       GYRO_TYPE = 0,
       ACCEL_TYPE = 1,
       COMPASS_TYPE =2
    };

    struct payload_t {
      int8_t type;
      float data[3];
    };

This assumes that the sender and receiver have the same data representation. The type field is for the value type (GYRO, ACCEL, COMPASS).

Cheers!


body:
I have an Arduino MEGA hooked up with a NRF24L01, and working nicely, talking with another Arduino Uno. It works as described, power supply to 3.3V, and SPI lines (MISO,MOSI,CLK) connected directly to the Arduino;

However, when I hook up a level converter in the end (5V to 3V, bidirectional) (making the NRF module in the middle, like in a T connection), the module stops working, and I don't know why. How does the level converter module is interfering in the connection? Is there any way I can prevent this and use it?

I intend in adding in the future, modules that talk in 3.3V SPI;

This is the level converter I'm using:

[![JY-MCU 5V-3V four channel convert module][1]][1]
<sub>(source: [at-the.space](http://ralphfox.at-the.space/imglink/hGTdg.jpg))</sub>

I suspect it is because of the pullups (5 think that these 10kΩ resistors are pull-ups, but I'm a noob in that part), but I really don't know if that is the problem, as the seller advertises it as being compatible with SPI, I2C, and UART. I have successfully used these for a UART.

I have checked https://arduino.stackexchange.com/questions/9616/slaving-multiple-arduinos-via-spi and tried using an external 5V supply, and a 3.3V supply, but no dice.. However, the 3V side has no connections to it; But, being bi-directional, I don't think there is a problem with this...

I found that 74HCT245D works very well for this, but I'd like to know why with the level converter from JY-MCU this won't work.

Providing the library and connections just in case (the module works without the level converter):

 - Library & sketch comes from [Optimized High Speed NRF24L01+ Driver Class Documenation][2].

 - Connection:

   - NRF2401 Pinout:
     [![NRF24l01][3]][3]

   - My connection:
     [![Arduino with NRF24l01 and Level Converter ][4]][4]

  [1]: https://i.stack.imgur.com/jHsyc.jpg
  [2]: http://tmrh20.github.io/RF24/index.html
  [3]: http://ralphfox.at-the.space/imglink/nrf24l01.jpg
  [4]: http://ralphfox.at-the.space/imglink/nrf_bb.png

title: SPI with a level converter in the other end of connection

Answers: 2

body:
More than probably your level shifter is not fast enough.
A level shifter uses a mosfet to copy signals from one voltage level to the other, but each mosfet has a latency or, if you prefer, a rise time.
Your board probably doesn't use a fast switching mosfet and so the SPI protocol (which is a quite fast one) is not *copied* correctly.

On top of that you **actually don't need a level switcher** for the nRF24 modules: the power pin must be limited to 3.3V, but the signal pins are 5V tolerant.
This means you only need a 3.3V voltage source and all the remaining connections can go directly (and safely) into your Arduino board.

**UPDATE**: the speed concept still applies, it doesn't matter which side of the connection you are using. A mosfet has a little capacitance which *slows* down the signal transmission: higher the capacitance, slower the maximum data rate.
The cheap chinese level shifter is not designed for high speed communication, while the Texas Instrument device is clearly designed for high speed.
If you look at the SN74HCT245 datasheet you'll notice the switching speed is reported for 50pF capacitance and ranges from 8ns to 16ns: that's the time needed to build enough charge in the switching circuit.
[![enter image description here][1]][1]

  [1]: https://i.stack.imgur.com/3Um6i.gif

body:
AVR's like all digital have their limits. In this case you're dealing with source resistances that need to charge multiple gate capacitances through series resistances (wires and metal contact connections. Specifically an Absolute MAX 40mA/pin, some milliohms in your copper wire and PCB traces, and pico to nano Farad capacitances, plus depending on how High Speed the SPI is (the spec does not list an upper limit), you will be also contending with frequency limiting parasitics. At MHz frequencies, your wire and PCB traces will have higher resistances due to "skin" effect, where the electrons migrate to the surface of the wire when transferring. Depending on frequency of the wire, adding just a single gate could degredate rise/fall times enough to corrupt data, as the SPI library (whichever you choose) and the SPI peripheral within the AVR probably won't be as sophisticated as a PC based one. The AVR & the SPI library lacks sophistication in that neither has provisions to detect and compensate for extra gate capacitance on the bus line, nor could they compensate for china jumper wires which are quite small (9x40ga) wiring.
There are many factors which could corrupt your SPI project that are coming into play to limit performance.
You should probably do some internet research on high speed bus anatomy if you intend on pushing the SPI bus on the arduino to it's limits.

I think the gate capacitances are combining with source resistance and skin effect and your 40mA/pin is not in fact 40mA per pin but more like 10-20mA is hitting all gate capacitances when skin effect is considered (it effectively raises the resistance of the wire sufficiently to then be a factor).
If connecting the JY-MCU converter AND running SPI at minimum speed corrects communication, then the extra gate capacitances are the factor you should change to higher performance versions. There's the 74AS series with gate times down to 1.7nS and fMAX up to 40MHz!

Hope this helps.


body:
When I learn the tutorial in

 - [Analog Read Serial][1]
 - [Digital Read Serial][2]

both of the code examples have a line of code of `delay(1)` and I cannot understand the comments clearly:

     delay(1);        // delay in between reads for stability

 The **stability** for/of what?

  [1]: https://www.arduino.cc/en/Tutorial/AnalogReadSerial
  [2]: https://www.arduino.cc/en/Tutorial/DigitalReadSerial

title: Why need a delay between readings?

Answers: 2

body:
Those delays are nonsense. They don't add to the stability of anything. The best you could say is that they stop you spamming your serial port. (However 1 ms is not very long).

Sometimes people throw in a delay because "it seems to work better" without examining the underlying cause. I would speculate that in this case the author may have been using delays to improve receiving serial data, and got the idea into their head that the occasional delay now and then "improves stability".

body:
**Analog Stability**

From the [Datasheet of ATMEGA328][1] Page 240:

`When the bandgap reference voltage is used as input to the ADC, it will take a certain time for the voltage to stabilize. If not stabilized, the first value read after the first conversion may be wrong.`

So if you are doing multiple reads, you need to wait a few cycles.

Delays are not required when using auto-triggering:

`When Auto Triggering is used, the prescaler is reset when the trigger event occurs. This assures a fixed delay from the trigger event to the start of conversion. In this mode, the sample-and-hold takes place two ADC clock cycles after the rising edge on the trigger source signal. Three additional CPU clock cycles are used for synchronization logic.`

Also if reading different channels of the same ADC module, you need to provide a delay between the reads so that the analog MUX is positioned and the S&H capacitor is charged.

This information is from hardware perspective and I'm not sure if Arduino internal ADC routines compensate for those delays.

**Digital Stability**

From the digital read tutorial schmatic:

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

In the schematic, the push button is not electrically de-bounced. A delay in reading states would help de-bounce it in software.

As Nick Gammon suggested, they also improve serial flooding.

  [1]: http://www.atmel.com/images/atmel-8271-8-bit-avr-microcontroller-atmega48a-48pa-88a-88pa-168a-168pa-328-328p_datasheet_complete.pdf
  [2]: https://i.stack.imgur.com/GiHD6.png


body:
Hello  have an array of strings that loads strings from a txt file on an sd card.
The txt file on the SD card can change from time to time(not while the Arduino is running).I want to be able to get the amount of elements in the array after the txt file has been loaded into the array. The txt file has lines of txt in it. Each line in the file is put into a string in the array. I want to be able to get the amount of elements in the array how can I do this?

title: Arduino how to get amount of elements in an array?

Answers: 2

body:
You can't. That concept does not exist in C.

An array has a fixed size - as such you know how many elements are in it, since that is the number of elements you created it with.

    String myStrings[4];

That is an array of 4 String objects. It has 4 elements. It will always have 4 elements.

body: numElements = (sizeof(array) / sizeof(array[0]));


body:
I have a Genuino 101 which has a built in Bluetooth LE module. I have been trying to connect this to my phone using phonegap. I have been using [cordova-plugin-bluetootle][1] and with it I have been able to receive data from the arduino and display that data on the phone.
I tired adapting it so that I could send data from the phone to the arduino. I noticed in the CurieBle examples there was a project called "Callback LED" but when I connected to the Arduino from the Phone gap app I noticed in the debug message about characteristics it said `"properties":{"notify": true, "read": true}` but nothing about write. I tried writing "Hello world" (converted into bytes then encoded string) I got an error similar to (I couldn't copy it exactly as it was an alert on the phone): `"error": "write", "message": "Error Domain=CBATTErrorDomain Code = 3 \"Writing is not permitted.\" ..."...`There is more detail to the error message that is not at all relevant and is slightly repetitive.
Here is the arduino code (which is almost straight from the example):

    #include <CurieBle.h>

    const int ledPin = 13; // set ledPin to use on-board LED
    BLEPeripheral blePeripheral; // create peripheral instance

    BLEService ledService("19B10000-E8F2-537E-4F6C-D104768A1214"); // create service

    // create switch characteristic and allow remote device to read and write
    BLECharCharacteristic switchChar("19B10001-E8F2-537E-4F6C-D104768A1214", BLERead | BLEWrite);

    void setup() {
      Serial.begin(9600);
      pinMode(ledPin, OUTPUT); // use the LED on pin 13 as an output
      digitalWrite(ledPin, HIGH);
      while(!Serial);
      digitalWrite(ledPin, LOW);
      // set the local name peripheral advertises
      blePeripheral.setLocalName("LEDCB");
      // set the UUID for the service this peripheral advertises
      blePeripheral.setAdvertisedServiceUuid(ledService.uuid());

      // add service and characteristic
      blePeripheral.addAttribute(ledService);
      blePeripheral.addAttribute(switchChar);

      // assign event handlers for connected, disconnected to peripheral
      blePeripheral.setEventHandler(BLEConnected, blePeripheralConnectHandler);
      blePeripheral.setEventHandler(BLEDisconnected, blePeripheralDisconnectHandler);

      // assign event handlers for characteristic
      switchChar.setEventHandler(BLEWritten, switchCharacteristicWritten);
    // set an initial value for the characteristic
      switchChar.setValue(0);

      // advertise the service
      blePeripheral.begin();
      Serial.println(("Bluetooth device active, waiting for connections..."));
    }

    void loop() {
      // poll peripheral
      blePeripheral.poll();
    }

    void blePeripheralConnectHandler(BLECentral& central) {
      // central connected event handler
      Serial.print("Connected event, central: ");
      Serial.println(central.address());
    }

    void blePeripheralDisconnectHandler(BLECentral& central) {
      // central disconnected event handler
      Serial.print("Disconnected event, central: ");
      Serial.println(central.address());
    }

    void switchCharacteristicWritten(BLECentral& central, BLECharacteristic& characteristic) {
      // central wrote new value to characteristic, update LED
      Serial.print("Characteristic event, written: ");

      if (switchChar.value()) {
        Serial.println("LED on");
        digitalWrite(ledPin, HIGH);
      } else {
        Serial.println("LED off");
        digitalWrite(ledPin, LOW);
      }
    }
Here is the write function (phonegap) which is where the error is being produced from :

    var string = "Hello World";
    var bytes = bluetoothle.stringToBytes(string);
    var encodedString = _arrayBufferToBase64(bytes);
    alert("Service : " + connection.service + "  char : " + connection.char + " Address: " + address);
    var params = {"value":encodedString,"service":connection.service,"characteristic":connection.char,"address":address};
    alert("params : " + JSON.stringify(params));
    bluetoothle.write(function(res) {
    alert("Success writing : " + JSON.stringify(res));
    }, function(err) {
    alert("Error writing: " + JSON.stringify(err));
    }, params);

I think the error lies in the fact that the Arduino appears not to be advertising the "write" characteristic.
BTW the phone tells me that the service was `180d` and the characteristic was `2a37`.

  [1]: https://github.com/randdusing/cordova-plugin-bluetoothle

title: Writing not permitted on genuino 101 Built in Bluetooth LE (phonegap)

Answers: 1

body:
I finally figured it out thanks to finding [this GitHub issue][1]. It turns out to be an error with CurieBLE which manifests in a way that means that on IOS it reads the original characteristics and services so when I tried to write it was still thought that the characteristic was `read-only`. I had to restart my phone and it is working now.
There was another thing which is that I needed to send a shorter message, I think it was 20 bytes max per message although I'm not sure, but I sent "h" and the Arduino received it.

  [1]: https://github.com/01org/corelibs-arduino101/issues/96


body:
I'm with some friends from my school and we have started to do a project where we send an SMS text message to our Arduino UNO (with GSM module), which then print the text message on a thermal printer(tx, rx). we've got huge problems, and now we can not figure it out anymore.

We started making a machine that will print out a message that is sent from any mobile.So I send an SMS message with my mobile to Arduino connected to a GSM shield (SIM800L). Then sends the Arduino the message to the thermal printer via TX RX, and then the message should be printed out.

We have spent two examples, GSM shield from Arduino itself, and thermal printer example from SparkFun.

These two files work fine separately, but when we try to merge them together, there is a compilation error.

The printer model from Sparkfun.

---------------------------------------------------
code:

    #include <GSM.h>
    #include <SoftwareSerial.h>

    #define PINNUMBER ""

    //Printer
    SoftwareSerial Thermal(6, 7);
    //GSM modul
    //SoftwareSerial GSM(4, 5);

    int heatTime = 10;
    int heatInterval = 2;
    char printDensity = 15;
    char printBreakTime = 15;

    // initialize the library instances

    GSM_SMS sms;

    // Array to hold the number a SMS is retreived from
    char senderNumber[20];

    void setup() {
    // Open serial communications and wait for port to open:
    Serial.begin(9600);
      while (!Serial) {
    ; // wait for serial port to connect. Needed for native USB port only
      }
    Serial.println("SMS Messages Receiver");

    // connection state
    boolean notConnected = true;

     Thermal.println("GSM initialized");
     Thermal.println("Waiting for messages");
     }
     /*{
     Thermal.begin(19200); // to write to our new printer
     initPrinter();
     }
     */
    void initPrinter()
    {
     //Modify the print speed and heat
     Thermal.write(27);
     Thermal.write(55);
     Thermal.write(7); //Default 64 dots = 8*('7'+1)
     Thermal.write(heatTime); //Default 80 or 800us
     Thermal.write(heatInterval); //Default 2 or 20us
     //Modify the print density and timeout
     Thermal.write(18);
     Thermal.write(35);
     int printSetting = (printDensity<<4) | printBreakTime;
     Thermal.write(printSetting); //Combination of printDensity and     printBreakTime

     }
     void loop() {
     char c;

     // If there are any SMSs available()
      if (sms.available()) {
      Thermal.println("Message received from:");

    // Get remote number
    sms.remoteNumber(senderNumber, 20);
    Thermal.println(senderNumber);

    // An example of message disposal
    // Any messages starting with # should be discarded
    if (sms.peek() == '#') {
      Thermal.println("Discarded SMS");
      sms.flush();
    }

    // Read message bytes and print them
    while (c = sms.read()) {
      Thermal.print(c);
    }

    }

    delay(1000);

    }

title: Help with school project (Arduino GSM and Thermal printer)

Answers: 0


body:
Hello I have a method where when you press a button a string is compared with a substring to see if the string contains the substring. The problem is when I load in the string I call the check button press and substring comparing method. Which only ever happens once. I want to know how I can keep calling the method. It sounds simple but it isn't.

    void loadPrograme(){
       file = SD.open("/classes/basic.txt", FILE_READ);
       Serial.print("Reading, Checking and Compiling \n\n\n");

       for (int i = 0; i < arraysize; i++) {
          while (file.available()) {
             character23 = file.read();
             if (character23 == '\n') break;
             if (character23 != '^') {
                content += character23;
             }
          }
          content.trim();
          if (content != "") {
             result[i] = content;
             content = "";
             delay(1000);
          }
       }
       for (int i = 0; i <arraysize; i++) {
          if(result[i].substring(0,5) == "print"){
             printlnMethod(result[i]);

          }else
             if(result[i].substring(0,5) == "delay"){
                delayMethod(result[i]);
             }else
                if(result[i].substring(0,11) == "buttonPress"){
                   buttonMethod(result[i]);

                }

       }

       file.close();
    }

    void buttonMethod(String s){
       s = s.substring(s.indexOf('{') + 1);
       s = s.substring(0, s.lastIndexOf('}'));
       String btn =" ";
       String daction = " ";
       String indaction = " ";
       btn= s.substring(s.indexOf('"')+1 );
       btn= btn.substring(0, btn.lastIndexOf('"'));
       daction = s.substring(s.indexOf(',')+1);
       daction = daction.substring(0, daction.lastIndexOf('('));
       indaction = s.substring(s.indexOf('~')+1);
       indaction = indaction.substring(0, indaction.lastIndexOf('~'));
       int buttonpressed;
       if(btn == "BUTTON_PIN_ENTER"){
          buttonpressed = 2;
       }else if(btn == "BUTTON_PIN_LEFT"){
          buttonpressed = 3;
       }else if(btn == "BUTTON_PIN_RIGHT"){
          buttonpressed = 4;
       }else if(btn == "BUTTON_PIN_DOWN"){
          buttonpressed = 5;
       }else if(btn == "BUTTON_PIN_UP"){
          buttonpressed = 6;
       }else if(btn == "BUTTON_PIN_ACTION"){
          buttonpressed = 7;
       }

       int btncheck = digitalRead(buttonpressed);
       if(btncheck == LOW){
          if(daction.substring(0,5) == "print"){
             printlnMethod(indaction);

          }else if(daction.substring(0,5) == "delay"){
             delayMethod(indaction);
          }
       }
    }

    }

So basically it loads in the txt file into the string array and loops through it and reads each line. each line is executed. for example if it get the substring of buttonpressed it goes to the buttonmethod(). The problem is in the button method. I want to have the button method keep looping until the button is pressed but it only runs through that method once. How can I keep running threw this method until the button is pressed?

title: Arduino how to loop a method

Answers: 1

body:
Testing for string equality with '==' is a mistake: https://stackoverflow.com/questions/8004237/how-do-i-properly-compare-strings-in-c  The '==' operator on strings will compare the pointers to the strings rather than their content and likely always fail the if() tests.

To loop and block on the last bit, if that is what you mean, you might try:

       int btncheck;
       ...
       while(btncheck = digitalRead(buttonpressed)){ // wait for button
          if(strcmp(daction.substring(0,5),"delay")){
             delayMethod(indaction);
          }
       }  // blocked until btncheck == LOW
       if(strcmp(daction.substring(0,5), "print")){
             printlnMethod(indaction);
       }

This has the blocking on non-pressed button feature, but also has the same logic as the original.  If the string equality tests do not match, it appears you want to do nothing and quickly pass on.

To loop buttonMethod(), put it in a loop:

    while(1)buttonMethod(string);

If you want to condition on getting the button press that corresponds with the string, I'd make buttonMethod return a value and loop conditionally on that:

    int buttonMethod(...
        int retVal = 0;
        ...

      if(btncheck == LOW){
         retVal = 1;
         ...
      }
      return(retVal);
    }

    ...
    while(!buttonMethod(result[i]));  // wait for the button


body: If so, please tell me and also tell me if any interfacing of other microcontroller needed?

title: Can we detect a magnet using Arduino? If so how?

Answers: 2

body:
I can't comment yet but you probably are looking for a hall effect sensor.

Something like this is a simple version of the sensor. https://www.sparkfun.com/products/9312

You can then do a digitalRead on the DO pin to detect if a magnet is near the sensor.

You would connect the Vdd to 5v arduino supply and GND to the GND of the board.

body: If you don't care about measuring the strength of the magnetic field, you can use a magnetic switch (sometimes called a reed switch). A magnetic switch closes when a magnet is put up to it and opens when there is not. The only problem with this is that the magnet has to be within about one inch from the switch. The magnetic switch works just like a normal switch and usually has two contacts. [Here](http://www.mouser.com/ProductDetail/Standex-Electronics/ORD324-1520/?qs=JzJq8kwFq1kL6csKqXqJlw==&gclid=CjwKEAiA0ZC2BRDpo_Pym8m-4n4SJAB5Bn4xq9r0brZEKWex5eS-FfwskFgNwpZVISwIe8pVCaHRaBoCKxnw_wcB) is an example.


body:
I have a question. How to run stepper motor (Nema 17) that has 5 wires with arduino and stepper driver.
Here is the driver, stepper and Arduino when stepper has 4 wires.
http://jdreyer.com/projects/Arduino/ArduinoEasyDriverStepperMotorv1_Resize.png

I need help identifying the wires on my hibrid stepper motor. I will provide picture of dissasembled motor.

Questions are:

 1. Wires identification?
 2. How to connect it to ArduinoEasyDriver?
 3. Code example desired.

[![Dissasembled stepper][1]][1]

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

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

  [2]: https://i.stack.imgur.com/T5Bk9.jpg

**UPDATE**

> I am now thinking of making it bipolar (4 wires), because now in 5
> wires configuration motor is unipolar. I did some research and this
> motor is HIBRID. It can be driven as unipolar or bipolar. I will try
> to troubleshoot the wiring and find the common wire. Ill keep you
> informed.

title: How to run 5 wires hibrid stepper motor with arduino uno?

Answers: 4

body:
**Finding the ground pin**

We should start off by finding the Ground/GND pin.

Do you have an Ohm-meter? I believe one of the pins should be GND/ground, and should have low resistance when referenced to the other pins.

**Wiring the stepper**

Steppers have a coil and thus are an inductive load, you should really check your wiring with sources, to be sure they're valid.
(At this point I can't give you a 100% accurate wiring diagram, but it should be easy to find, as wiring steppers is quite common.)
You could use a pre-assembled stepper-driver. Having such a thing is usefull when you want to design the circuitry yourself.

**Driving the steppers**

You should generate a signal like this: https://en.wikipedia.org/wiki/Stepper_motor#Phase_current_waveforms

(The source/link describes the different forms of stepping. Like "Wave drive (one phase on)" in which each coil is activated/deactivated in a rotary fashion, making the core turn around.)

**Extra**

Adafruit always has extremely well documented tutorials for beginners:
https://learn.adafruit.com/all-about-stepper-motors/types-of-steppers

The wiki of RepRap should be a good source, since steppers are the hearth of 3D printers (RepRap is a 3D printer brand):
http://reprap.org/wiki/Stepper_wiring

body:
On stepper motors there are a few types of wiring, but essentially there are two coils inside the stepper motor. To figure out where the wiring is you need a way to test if the coils are being connected. On your setup I would suggest to connect two of the wires together at a time and spin the shaft. If the shaft offers resistance then you have found the two wires for one coil.

For your stepper motor it looks like it may have three coils, but out of the 6 wires you may also only come up with 4 wires; which would equal 2 coils.

As far as connecting it to an easy driver, the easy driver only takes two coils. you would need to find a driver that can take three coils, or just connect two coils out of the three and hope for the best.

body:
1) it is probably something like A1, A2, Common, B1, B2.  You could confirm this with an ohmmeter. Common to any of the others would be a certain resistance X, while between any of the others (A1-A2, B1-B2, A1-B1, A1-B2, B1 A2) would be 2X.

2) You can't.  It is a unipolar stepper.

The EasyDriver faq number 5.1 at http://www.schmalzhaus.com/EasyDriver/ says:  "... The only kind you can't use is 5-wire stepper motors. (They need uni-polar drivers.)"

The difficulty with the 5-wire steppers is that they short the middle of the two coils together, which makes it hard to drive the coils independently.

Since you have the motor open, you might be able to do some surgery and disconnect the centers of the coils from each other, but you'll probably be better off getting a 4, 6 or 8 wire stepper instead.

body: Instead of doing surgery on your unipolar stepper, you can use it like a unipolar stepper. Some transistors to hook the motor to power (just get a darlington array chip), and four output pins on the arduino. Works fine.


body:
Hello I have a programme that loads a piece of text from a file. In this case it loads "drawrect(4,10,20,20);" from the txt file and stores it in a string. I then use substrings to change the string into just "4,10,20,20" which is good but I need to simplify it down even more to four strings each with one of those 4 numbers in it.

Currently I use:

    void drawRectMethod(String s){
      String var1,var2,var3,var4;
      s = s.substring(s.indexOf('(') + 1);
      s = s.substring(0, s.lastIndexOf(')'));
      Serial.println(s);
    }
to simplify the string down to "4,10,20,20" but this wont work to store each number in a separate string. How can I can I store each variable in a separate string. The numbers will be stored in var1 - var4.

title: Arduino loading from file

Answers: 1

body:
Need some more help? As I previously wrote that snippet I might as well continue until you understand how to use indexOf() and substring().

      String s = "draw(10,20,30,40)";

      // Parse the argument list
      s = s.substring(s.indexOf('(') + 1);
      s = s.substring(0, s.lastIndexOf(')'));

      // Parse comma separated arguments
      String arg[4];
      for (int i = 0; i < 3; i++) {
        int ix = s.indexOf(',');
        arg[i] = s.substring(0, ix);
        s = s.substring(ix + 1);
        Serial.println(arg[i]);
      }
      arg[3] = s;
      Serial.println(arg[3]);

There is absolutely no error handling in this. You will have to add that. You can also improve the parse of the right parenthesis. That could be added last instead.

Later in the game we will come to why using String is a bad idea and why a character buffer and the standard library functions such as [strtok()][1] is a much better solution strategy both performance and memory footprint and especially heap.

      char* s = (char*) "draw(10,20,30,40)";
      s = strtok(s, "(),");
      Serial.println(s);
      while ((s = strtok(NULL, "(),")) != NULL)
        Serial.println(s);

Maybe the simplest solution is to use [sscanf()][2]. That will also do the conversion from text to binary.

      const char* s = "draw(10,20,30,40)";
      int x, y, w, h;
      int n = sscanf(s, "draw(%d,%d,%d,%d)", &x, &y, &w, &h);
      Serial.print(F("n="));
      Serial.println(n);
      Serial.print(F("x="));
      Serial.println(x);
      Serial.print(F("y="));
      Serial.println(y);
      Serial.print(F("w="));
      Serial.println(w);
      Serial.print(F("h="));
      Serial.println(h);

Cheers!

  [1]: http://www.nongnu.org/avr-libc/user-manual/group__avr__string.html#ga6ace85338eafe22a0ff52c00eb9779b8
  [2]: http://www.nongnu.org/avr-libc/user-manual/group__avr__stdio.html


body:
During the last two months I have been working on a project that consists of using a Seeeduino Stalker V2.3, two AM2305 sensors, a TSL2561 sensor, an HC-05 XBee module, a 1,800 mAh 3.7V LiPo, a 7 cm x 7 cm 5V solar cell, and a waterproof suction box, to assemble a portable and waterproof environmental data logger that can be used to take samples on a continuous basis (1 sample every 30 minutes, 48 samples per day).

After struggling to make my logger work, I finally did it last week. It all runs fine, except that the intervals between readings are incorrect. When I program my board to store samples every 30 minutes (1,800,000), it takes them every 30 minutes and some extra seconds. When I try the same but with a rate of 1 sample every 10 seconds, my device logs data every 13 seconds more or less...

Here is the code I have been using:

    #include "SPI.h"
    #include "Wire.h"
    #include "SD.h"
    #include "DS3231.h"**

    DS3231 clock;
    RTCDateTime dt;

    #include "DHT.h"

    #define DHTPIN 8
    #define DHTTYPE DHT21
    DHT dht1(DHTPIN, DHTTYPE);
    #define DHTPIN2 7
    DHT dht2(DHTPIN2, DHTTYPE);
    #include "TSL2561.h"
    TSL2561 tsl(TSL2561_ADDR_FLOAT);

    const int chipSelect = 10;
    int XBEE = 5;
    int FLASH = 4;

    void setup() {
      pinMode(5, OUTPUT);
      digitalWrite(XBEE, HIGH);
      Serial.begin(9600);
      Wire.begin();
      clock.begin();
      analogReference(INTERNAL);
      pinMode(10, OUTPUT);
      pinMode(4, INPUT);
      SD.begin(10);
      dht1.begin();
      dht2.begin();
      Serial.println("EcoLOGGER DE PRUEBA PARA GENERACION DE DATOS ...");
      Serial.println(" ");
      delay(3000);
      Serial.println("RECUERDA QUE ESTE PROYECTO NO HUBIERA SIDO POSIBLE SIN LA AYUDA DE LA COMUNIDAD ARDUINO...");
      Serial.println(" ");
      delay(3000);
    }

    int counter = 0;

    void loop() {
      float h = dht1.readHumidity();
      float t = dht1.readTemperature();
      float f = dht1.readTemperature(true);
      float h2 = dht2.readHumidity();
      float t2 = dht2.readTemperature();
      float f2 = dht2.readTemperature(true);
      dt = clock.getDateTime();
      if (tsl.begin()) {
      } else {
        while (1);
      }
      tsl.setGain(TSL2561_GAIN_0X);
      tsl.setTiming(TSL2561_INTEGRATIONTIME_402MS);
      uint16_t x = tsl.getLuminosity(TSL2561_FULLSPECTRUM);
      uint32_t lum = tsl.getFullLuminosity();
      uint16_t ir, full;
      ir = lum >> 16;
      full = lum & 0xFFFF;
      float vis = full-ir;
      Serial.print("Muestreo: ");
      Serial.println(counter);
      Serial.print("Fecha: ");
      Serial.print(dt.day);
      Serial.print('/');
      Serial.print(dt.month);
      Serial.print('/');
      Serial.println(dt.year);
      Serial.print("Hora: ");
      Serial.print(dt.hour);
      Serial.print(':');
      Serial.print(dt.minute);
      Serial.print(':');
      Serial.println(dt.second);
      Serial.print("Temperatura sistema: ");
      Serial.print(clock.readTemperature());
      Serial.println("*C ");
      Serial.print("Voltaje bateria: ");
      Serial.print(analogRead(A7) * (1.1 / 1024)* (10+2)/2);
      Serial.println(" V ");
      Serial.print("Carga bateria: ");
      Serial.print(-149.4 + 59.52 * (analogRead(A7) * (1.1 / 1024)* (10+2)/2));
      Serial.println("% ");
      Serial.print("Luz FULL: ");
      Serial.println(full);
      Serial.print("Temperatura ambiente: ");
      Serial.print(t);
      Serial.println(" *C ");
      Serial.print("Humedad relativa: ");
      Serial.print(h);
      Serial.println("%");
      Serial.print("Temperatura suelo: ");
      Serial.print(t2);
      Serial.println(" *C ");
      Serial.print("Humedad suelo: ");
      Serial.print(h2);
      Serial.println("%");
      Serial.println(" ");
      digitalWrite (FLASH, HIGH);
      File dataFile = SD.open("datalog.txt", FILE_WRITE);
      if (dataFile) {
        dataFile.print(" Muestreo: ");
        dataFile.print(counter);
        dataFile.print(",");
        dataFile.print(" Fecha: ");
        dataFile.print(dt.day);
        dataFile.print('/');
        dataFile.print(dt.month);
        dataFile.print('/');
        dataFile.print(dt.year);
        dataFile.print(",");
        dataFile.print(" Hora: ");
        dataFile.print(dt.hour);
        dataFile.print(':');
        dataFile.print(dt.minute);
        dataFile.print(':');
        dataFile.print(dt.second);
        dataFile.print(",");
        dataFile.print(" Temperatura sistema: ");
        dataFile.print(clock.readTemperature());
        dataFile.print("*C ");
        dataFile.print(",");
        dataFile.print(" Voltaje bateria: ");
        dataFile.print(analogRead(A7) * (1.1 / 1024)* (10+2)/2);
        dataFile.print(" V ");
        dataFile.print(",");
        dataFile.print(" Porcentaje carga: ");
        dataFile.print(-149.4 + 59.52 * (analogRead(A7) * (1.1 / 1024)* (10+2)/2));
        dataFile.print("% ");
        dataFile.print(",");
        dataFile.print(" Luz FULL: ");
        dataFile.print(full);
        dataFile.print(",");
        dataFile.print(" Temperatura ambiente: ");
        dataFile.print(t);
        dataFile.print(" *C ");
        dataFile.print(",");
        dataFile.print(" Humedad relativa: ");
        dataFile.print(h);
        dataFile.print("%");
        dataFile.print(",");
        dataFile.print(" Temperatura suelo: ");
        dataFile.print(t2);
        dataFile.print(" *C ");
        dataFile.print(",");
        dataFile.print(" Humedad suelo: ");
        dataFile.print(h2);
        dataFile.print("%");
        dataFile.println("");
        dataFile.close();
        digitalWrite (FLASH, LOW);
      } else {
        Serial.println("");
        Serial.println("IMPOSIBLE GUARDAR DATOS");
        Serial.println("");
      }
      counter++;
      if (counter > 5) {
        delay (1000);
        digitalWrite (XBEE, LOW);
        delay (1799000);
      } else
        digitalWrite (XBEE, HIGH);
      delay (10000);
    }

I have been trying to find possible solutions, but I am just lost. Do any of you have an idea of what could be going on?

Thank you in advance :)

title: Problem with inaccurate delays between sensor readings

Answers: 2

body:
The problem is that you are using `delay()`.

`delay()` will wait, from the moment `delay()` is called, for the given number of milliseconds.

That is, in more structured terms:

1. Do something
2. Do something else
3. Do something more
4. Wait 30 minutes

That will only take precisely 30 minutes if steps 1 to 3 take absolutely no time at all.  And that will never be the case. Things take time. Reading from sensors, writing to SD cards, etc, all take time.

So waiting for 30 minutes between doing things means that every 30 minutes will be slightly later than the one before.

And as you saw the difference is more pronounced when you have 10 seconds instead - it ends up as 13 seconds.  So your other actions - reading from sensors, writing to SD card, etc, must be taking about 3 seconds each time.

So instead of "Stop everything for half an hour", you need to think slightly differently:

1. Look at the time.
2. Decide if 30 minutes have passed since the last time you ran the code
3. Remember the time so you can know when 30 minutes have elapsed next time
4. Do your sensor/SD actions.

Since you're now keying things happening on the difference between now and when you last *started* to do things you get a 30 minute *total* delay, rather than a 30 minute delay *plus other bits*.

For an example of how this is done programatically you can look at the *BlinkWithoutDelay* example in the Arduino IDE.

body:
The second problem is that delay() on the arduino uses the on-board clock cycle. This is powered by a resonator, which can be off by as much as 10%. If you need accurate timings and timestamps, you will want to use a Real-Time Clock (RTC) module.

Instead of using delay, the loop() asks the RTC what time it is, and uses that to determine if it's time to take another reading.

Another very common thing for this type of monitoring is for the arduino to go into sleep mode and be woken by a tick from the RTC every second (or longer), in order to extend the battery life.


body:
I recently got the RedBearLabs BLE shield to use it to control two high spped continuous rotation servos. I have the BLE example sketch loaded and the ios controller app works. The problem is that the servos are too fast to control and I want to slow them down. I cannot use the app to slow them down. I was wondering how I could modify the example sketch or servo library to change the ax speed or something. Thanks in advance.

BLE Shield Homepage: http://redbearlab.com/bleshield/

BLE Libraries and Example Sketch: https://github.com/RedBearLab/nRF8001

title: Change Servo Speed With RedBearLabs BLE Shield

Answers: 1

body:
The bi-directional Parallax [High Speed Continuous Rotation Servo](https://www.parallax.com/product/900-00025) responds to “simple pulse-width modulation”, according to its web page.  That is, pulse widths in the range from about 500 μs to 2500 μs will set the speed and direction, with some value near 1500 μs corresponding to zero RPM.

The code in the [BLEControllerSketch](https://codebender.cc/sketch:245943#BLEControllerSketch.ino) uses the following bits of code, among others, to initialize servo-control data structures and to control them:

<!-- language: lang-c -->

    #include <Servo.h>
    ...
    byte pin_servo[TOTAL_PINS];
    Servo servos[MAX_SERVOS];
    ...
          case 'O': // set Servo
            {
              byte pin = ble_read();
              byte value = ble_read();

              if (IS_PIN_SERVO(pin))
                servos[PIN_TO_SERVO(pin)].write(value);
              pin_servo[pin] = value;
              reportPinServoData(pin);
            }
            break;

Thus, you will need to send an `O` message from your iOS app, together with servo pin number and control value, to set a servo's speed.

As noted on the [ServoWrite](https://www.arduino.cc/en/Reference/ServoWrite) page at arduino.cc, the parameter to Servo's `.write()` method is a number:

> On a standard servo, this will set the angle of the shaft (in degrees), moving the shaft to that orientation. On a continuous rotation servo, this will set the speed of the servo (with 0 being full-speed in one direction, 180 being full speed in the other, and a value near 90 being no movement).

You can find out a little more by looking at Servo's `.write()` method in Servo.cpp:

<!-- language: lang-c -->

    void Servo::write(int value)
    {
      if(value < MIN_PULSE_WIDTH)
      {  // treat values less than 544 as angles in degrees (valid values in microseconds are handled as microseconds)
        if(value < 0) value = 0;
        if(value > 180) value = 180;
        value = map(value, 0, 180, SERVO_MIN(),  SERVO_MAX());
      }
      this->writeMicroseconds(value);
    }

`SERVO_MIN()` and `SERVO_MAX()` are macros that access `min` and `max` fields in a `Servo` object and convert them to microsecond values.  Because the code in BLEControllerSketch.ino lets those fields default, the range evidently will be from 544 to 2400 μs (see the values given in Servo.h).

Note that you can get better resolution – hence, better speed control – by sending values in that range of microseconds to your servos, instead of trying to control it using values in degrees.  The `.write()` method will interpret such numbers as microseconds instead of as degrees.  Servo.cpp appears to use half-microsecond timer ticks; and each degree corresponds to about 10 μs of pulse width; so resolution using microsecond values should be about 10 times better than using degrees.

In short, it appears that you should do some experimenting with `O` messages that send values around 1500, to find the values that correspond to slowest forward and backward speeds.


body:
I am doing a motorcycle security system. In this system, I will receive a message from GSM in the form `{password:operation (like start,stop,alarm):time}`.
Example:(9990:start:30)

now i need to split  each term seperately (a=9990,b=start,c=30).help me to solve

title: How to split a string received via a GSM module (message)

Answers: 1

body:
Simplest solution is to use [sscanf()][1].

      int password;
      char operation;
      int time;
      char* buf = "{14:C:123}";
      int n = sscanf(buf, "{%d:%c:%d}", &password, &operation, &time);
      Serial.print(F("n="));
      Serial.println(n);
      Serial.print(F("password="));
      Serial.println(password);
      Serial.print(F("operation="));
      Serial.println(operation);
      Serial.print(F("time="));
      Serial.println(time);

  [1]: http://www.cplusplus.com/reference/cstdio/scanf/


body:
I have this double clap sensor code written, it seems it would work but it seems to trigger the double clap even on a single clap, any ideas?

<!-- language: c -->

    int soundSensor = A1;
    int relay = A2;
    int relay2 = A3;
    int relay3 = A4;
    int relay4 = A5;
    int claps = 0;
    long detectionSpanInitial = 0;
    long detectionSpan = 0;
    boolean clapState = false;
    int doubleClap = 0;

    //Light sensor
    int photocellPin = A0;     // the cell and 10K pulldown are connected to a0
    int LEDbrightness;

    //int delayValue = 100;
    int photoSensor = 0;

    // sound sample
    const int sampleWindow = 50; // Sample window width in mS (50 mS = 20Hz)
    unsigned int sample;

    //other
    boolean isRelaysOn = false;
    void setup() {
      pinMode(soundSensor, INPUT);
      pinMode(relay, OUTPUT);
      pinMode(relay2, OUTPUT);
      pinMode(relay3, OUTPUT);
      pinMode(relay4, OUTPUT);
      turnRelayOff();
      Serial.begin(9600);
    }

    boolean state = false;
    boolean lastState = true;
    boolean lightTurnedItOff = false;
    void loop() {

      /////////////
      // photo sensor
      ////////////////////

      photoSensor = analogRead(photocellPin) > 623;

      /////////////
      // clap sensor
      /////////////////////
      double sensorState = getSoundLevel();
      Serial.println(sensorState);
      double threshold = .2;

      if (sensorState > threshold)
      {
        if (claps == 0)
        {
          detectionSpanInitial = detectionSpan = millis();
          claps++;
        }
        else if (claps > 0 && millis()-detectionSpan >= 50)
        {
          detectionSpan = millis();
          claps++;
          Serial.println(" CLAP ADDED!!!!");
        }
      }

      if (millis()-detectionSpanInitial >= 400){

        if (claps == 2)
        {
          claps++;
          doubleClap = 1 - doubleClap;
          state = !state;
          Serial.println("TWO claps!");

          if(lastState == state ){
            relayControl(doubleClap);
            lastState = !lastState;
          }
        }
        claps = 0;
      }

      if(isRelaysOn == true && photoSensor == 1){
        turnRelayOff();
        lightTurnedItOff = true;
      }
      if(isRelaysOn == true && photoSensor == 0 && lightTurnedItOff == true){
        turnRelayOn();
        lightTurnedItOff = false;
      }

    }

    void relayControl(int doubleClap){
      /////////////
      // relay control
      /////////////////////

      if(doubleClap == 1){
        turnRelayOn();
        Serial.println("on");
        isRelaysOn = true;

      }
      else{
        turnRelayOff();
        Serial.println("off");
        isRelaysOn = false;
      };

    }

    void turnRelayOn(){
      int delayAmount = 100;
      digitalWrite(relay, LOW);
      delay(delayAmount);
      digitalWrite(relay2, LOW);
      delay(delayAmount);
      digitalWrite(relay3, LOW);
      delay(delayAmount);
      digitalWrite(relay4, LOW);
      delay(100);
      digitalWrite(relay4, HIGH);
      delay(100);
      digitalWrite(relay4, LOW);
    }

    void turnRelayOff(){
      digitalWrite(relay, HIGH);
      digitalWrite(relay2, HIGH);
      digitalWrite(relay3, HIGH);
      digitalWrite(relay4, HIGH);
    }

    double getSoundLevel(){

      unsigned long startMillis= millis();  // Start of sample window
      unsigned int peakToPeak = 0;   // peak-to-peak level

      unsigned int signalMax = 0;
      unsigned int signalMin = 1024;

      // collect data for 50 mS
      while (millis() - startMillis < sampleWindow)
      {
        sample = analogRead(soundSensor);
        if (sample < 1024)  // toss out spurious readings
        {
          if (sample > signalMax)
          {
            signalMax = sample;  // save just the max levels
          }
          else if (sample < signalMin){
            signalMin = sample;  // save just the min levels
          }
        }
      }
      peakToPeak = signalMax - signalMin;  // max - min = peak-peak amplitude
      double volts = (peakToPeak * 3.3) / 1024;  // convert to volts

      return volts;
    }

Serial monitor:

> 0.02
> 0.02
> 0.02
> 0.02
> 0.01
> 0.01
> 2.20
> 0.30  CLAP ADDED!!!!
> 0.13
> 0.09
> 0.04
> 0.02
> 0.02
> 0.01
> 0.02 TWO claps! on
> 1.11
> 0.06
> 0.05
> 0.07
> 0.15
> 0.10
> 0.03
> 0.10
> 0.06
> 0.03
> 0.04
> 0.06

title: Double clap sensor not working as intended

Answers: 3

body:
I have noticed that you have used analogue inputs as your digital outputs by connecting relays to them.

I think this is wrong. You should connect your digital signals to the digital pins.

body: If your first clap rings for more than 50ms, the program counts it as a second clap.  After detecting a clap, you need to wait for the sound to die down before you start listening for a second clap.

body:
What you probably want to track is something more like:

 - high sound period of highMin to highMax ms
 - low sound period of lowMin to lowMax ms
 - high sound period of highMin to highMax ms
 - low sound period of at least lowDone ms (no max needed)

Anything not meeting those time bounds is not two claps, reset state and timers.  If you get to the end of the fourth step, accept as two claps.

I have not tested timing of claps to estimate the periods needed; you need to tweak that with the hardware you are actually using; for example, different microphones may ring for different times after a sharp clap impulse.

States could be:

 - waiting for start of first clap (sample until > threshold)
 - waiting for end of first clap (sample until < threshold or timeout)
 - waiting for start of second clap (sample until > threshold or timeout)
 - waiting for end of second clap (sample until < threshold or timeout)
 - got second clap


body:
For a project I'm using 2 Arduino Uno's, where Arduino#1 (master) sends raw data to Arduino#2 (slave). The slave should receive and encrypt the data and afterwards send the encrypted data back to the master. I'm building my project from the [sketch found at arduino.cc][1].

How can I make the slave send back data, if he's the only one listening on incoming data, should both arduinos be listening to each other, and how to achieve this?

  [1]: https://www.arduino.cc/en/Tutorial/MasterWriter

title: Send AND Receive through i2c / set Arduino as master AND slave

Answers: 1

body:
The I2C protocol is both read and write. Master/Slave depends on who initiates the communication. Typically the master will issue a read command to the slave to retrieve the results.

Cheers!


body:
Well im new to coding, but i do have the basic knowledge.
I'm using an UNO to measure a duty cycle.
The source of pulse is a Tektronic signal generator (Duty cycle set to 50.000 with frequency of 2khz).
my code is as follows,

    byte PWM_PIN = 3;
    float pwm_value_H;
    float pwm_value_L;
    float D;

    void setup() {
     pinMode(PWM_PIN, INPUT);
     Serial.begin(115200);
    }

    void loop() {
     pwm_value_H = pulseIn(PWM_PIN, HIGH);
     Serial.println(pwm_value_H);
     pwm_value_L = pulseIn(PWM_PIN, LOW);
     Serial.println(pwm_value_L);
     D = ((pwm_value_H) / (pwm_value_H + pwm_value_L)) * 100.0;
     Serial.print("D=");
     Serial.println(D);
     Serial.print("D=%");
    }

but the problem is that my output value of "D" keeps on varying between 49.71, 49.90, 50.00 and 50.7
Is this because of PULSEIN() function ineffiency?
or can anyone suggest a better way to measure the duty cycle with +/- 0.01 accuracy.

Regards,
Cj

title: how to solve Varing duty cycle value while using Pulsein()

Answers: 2

body:
I would start by removing Serial interrupts from the pulseIn period.

    void loop() {
        pwm_value_H = pulseIn(PWM_PIN, HIGH);
        pwm_value_L = pulseIn(PWM_PIN, LOW);
        Serial.println(pwm_value_H);
        Serial.println(pwm_value_L);
        D = ((pwm_value_H) / (pwm_value_H + pwm_value_L)) * 100.0;
        Serial.print("D=");
        Serial.println(D);
        Serial.print("D=%");
        Serial.flush();
    }

For higher accuracy I would then look to the Timer based Input Capture.

Cheers!

body:
There's two basic things wrong with what you are doing there:

1. `pulseIn()` isn't good for very accurate measurements
2. The signal is still happening while you're doing other things, such as printing the high/low times.

You're not actually measuring the duty cycle of one single cycle, but the HIGH time of one cycle followed by the low cycle of a later one. If you want to do it properly you will have to ditch `pulseIn()` and instead get your head around interrupts and timestamps.

The basic method is to present the signal to one of the INT pins, and attach an interrupt to that pin with the trigger set to CHANGE.  The interrupt routine you specify will then be triggered every time the signal changes from HIGH to LOW or from LOW to HIGH.

Then the interrupt routine does very little.  It basically records the time the interrupt happened (that must be the very first thing you do), then looks to see if it's a HIGH or a LOW signal on the pin.  You then use the previous timestamp from the last time the interrupt was triggered to work out how long the previous phase lasted and set either a HIGH or a LOW variable depending on the current level of the state (if it's low set a high variable since that was the previous phase level, and if it's high set a low variable) with the time that phase lasted.

Then in your main loop you interrogate those variables periodically to display the duty cycle.

If that still isn't accurate enough then you should look at the hardware *Input Capture* module built into the MCU. That uses a hardware timer in much the same way as the interrupt but is able to capture a much more accurate time stamp for you since the time stamp is grabbed the moment the signal changes, rather than after a short delay once the interrupt routine has been called.  Details can be found in the datasheet for the MCU on your Arduino.