message:
Issue with length of string value

I have been getting some weird issues with a sketch I put together(apart from memory low warnings, it was working fine)

When im about to post data to my php server - it seems not all the information is available

eg the output will be

    42399.92
    &HAAlt=-18.24

Is there a limit to string length?

Im crudely constructing a string to send to a post request

    #include <SPI.h>
    #include <Ethernet.h>
    #include "DHT.h"
    #include <math.h>
    #include <Wire.h>
    #include "MutichannelGasSensor.h"
    #include "HP20x_dev.h"
    #include "KalmanFilter.h"

    unsigned char ret = 0;

    /* Instance */
    KalmanFilter t_filter;    //temperature filter
    KalmanFilter p_filter;    //pressure filter
    KalmanFilter a_filter;    //altitude filter

    // Enter a MAC address for your controller below.
    // Newer Ethernet shields have a MAC address printed on a sticker on the shield
    byte mac[] = { 0xDE, 0xAD, 0xBE, 0xEF, 0xFE, 0xED };
    // if you don't want to use DNS (and reduce your sketch size)
    // use the numeric IP instead of the name for the server:
    IPAddress server(192, 168, 0, 30); // numeric IP for Google (no DNS)
    //char server[] = "www.google.com";    // name address for Google (using DNS)

    // Set the static IP address to use if the DHCP fails to assign
    IPAddress ip(192, 168, 0, 40);

    // Initialize the Ethernet client library
    // with the IP address and port of the server
    // that you want to connect to (port 80 is default for HTTP):
    EthernetClient client;

    #define Vc 4.95
    //the number of R0 you detected just now
    #define R0 35.54
    #define DHTPIN A1     // what pin we're connected to

    // Uncomment whatever type you're using!
    //#define DHTTYPE DHT11   // DHT 11
    #define DHTTYPE DHT22   // DHT 22  (AM2302)
    //#define DHTTYPE DHT21   // DHT 21 (AM2301)

    DHT dht(DHTPIN, DHTTYPE);

    int pin = 8;
    unsigned long duration;
    unsigned long starttime;
    unsigned long sampletime_ms = 2000;//sampe 30s ;
    unsigned long lowpulseoccupancy = 0;
    float ratio = 0;
    float concentration = 0;
    String data;
    String data2;

    void setup() {
      Serial.begin(9600);
      while (!Serial) {
        ; // wait for serial port to connect. Needed for native USB port only
      }

      delay(150);
      HP20x.begin();
      delay(100);

      /* Determine HP20x_dev is available or not */
      ret = HP20x.isAvailable();
      if (OK_HP20X_DEV == ret)
      {
        Serial.println("HP20x_dev is available.\n");
      }
      else
      {
        Serial.println("HP20x_dev isn't available.\n");
      }

      pinMode(8, INPUT);
      starttime = millis();//get the current time;
      Serial.println("power on!");

      pinMode(4, OUTPUT);
      digitalWrite(4, HIGH);

      //if (Ethernet.begin(mac) == 0) {
      //  Serial.println("Failed to configure Ethernet using DHCP");
      // try to congifure using IP address instead of DHCP:
      Ethernet.begin(mac, ip);

      // give the Ethernet shield a second to initialize:
      delay(10000);
      Serial.println("connecting...");
      //}
      // give the Ethernet shield a second to initialize:
      //delay(1000);
      //Serial.println("connecting...");

      // Serial.println(Ethernet.localIP());

      gas.begin(0x04);//the default I2C address of the slave is 0x04
      gas.powerOn();
      //Serial.print("Firmware Version = ");
      //Serial.println(gas.getVersion());
      //Serial.println("Particles\tRS\tHCHO (PPM)\tNH3 (PPM)\tCO (PPM)\tNO2 (PPM)\tC3H8 (PPM)\tC4H10 (PPM)\tCH4 (PPM)\tH2 (PPM)\tC2H5OH (PPM)");
      dht.begin();
      delay(10000);

      data = "";
      data2 = "";
    }

    void loop() {

      if (client.available()) {
        char c = client.read();
        Serial.print(c);
      }

      float HATemp2;
      float HAPres2;
      float HAAlt2;

      if (OK_HP20X_DEV == ret)
      {
        long HATemp = HP20x.ReadTemperature();
        float p = HATemp / 100.0;
        HATemp2 = t_filter.Filter(p);

        long HAPres = HP20x.ReadPressure();
        p = HAPres / 100.0;
        HAPres2 = p_filter.Filter(p);

        long HAAlt = HP20x.ReadAltitude();
        p = HAAlt / 100.0;
        HAAlt2 = a_filter.Filter(p);

      }

      duration = pulseIn(pin, LOW);
      lowpulseoccupancy = lowpulseoccupancy + duration;

      float d;

      if ((millis() - starttime) >= sampletime_ms) //if the sampel time = = 30s
      {
        ratio = lowpulseoccupancy / (sampletime_ms * 10.0); // Integer percentage 0=>100

        d = 1.1 * pow(ratio, 3) - 3.8 * pow(ratio, 2) + 520 * ratio + 0.62; // using spec sheet curve
        //Serial.print("concentration = ");

        lowpulseoccupancy = 0;
        starttime = millis();
      }
      //Serial.print("\t");
      //HCHO

      int sensorValue = analogRead(A0);
      double Rs = (1023.0 / sensorValue) - 1;

      double ppm = pow(10.0, ((log10(Rs / R0) - 0.0827) / (-0.4807)));
      //Serial.print("HCHO ppm = ");

      //MultiChannel Gas
      float NH3 = gas.measure_NH3();
      float CO = gas.measure_CO();
      float NO2 = gas.measure_NO2();
      float C3H8 = gas.measure_C3H8();
      float C4H10 = gas.measure_C4H10();
      float CH4 = gas.measure_CH4();
      float H2 = gas.measure_H2();
      float C2H5OH = gas.measure_C2H5OH();

      // Reading temperature or humidity takes about 250 milliseconds!
      // Sensor readings may also be up to 2 seconds 'old' (its a very slow sensor)
      float h = dht.readHumidity();
      float t = dht.readTemperature();

      data = String("dust=") + d + "&rs=" + Rs + "&hcho=" + ppm + "&nh3=" + NH3 + "&co=" + CO + "&no2=" + NO2 + "&c3h8=" + C3H8 + "&c4h10=" + C4H10 + "&ch4=" + CH4;
      data2 = String("&h2=") + H2 + "&c2h5oh=" + C2H5OH + "&temp=" + t + "&hum=" + h + "&HATemp=" + HATemp2 + "&HAPres=" + HAPres2 + "&HAAlt=" + HAAlt2;

      Serial.println(data);
      Serial.println(data2);

      if (client.connect(server, 80)) {
        Serial.println("connected");
        client.println("POST /air_add.php HTTP/1.1");
        client.println("Host:  192.168.0.30");
        client.println("User-Agent: Arduino/1.0");
        client.println("Connection: close");
        client.println("Content-Type: application/x-www-form-urlencoded;");
        client.print("Content-Length: ");
        client.println(data.length());
        client.println();
        client.println(data);
      }
      else
      {
        Serial.println("could not connect");
      }

      if (client.connected()) {
        client.stop();
      }

      Serial.println("done.");

      delay(30000);
    }

body:
There isn't a real limit on the length of a String that you are running into.  But when you are running low on RAM (the low memory warnings you mentioned) then there is a limit on how much memory you have to put that String before you cause memory corruption and either crash the program or at best get some weird output.

The String class is particularly wasteful of memory and it has some issues when using the + operator to concatenate Strings that will leave the heap memory full of holes and reduce the amount of memory you have even further.  On memory constrained systems like microcontrollers, the String class crutch is a thing to be avoided.  Learn to use char arrays and real c-style strings and you'll be better off.

One place you could immediately save some memory would be by putting all the constant strings in your code into PROGMEM instead of leaving them out in RAM.  So this:

    client.println("Connection: close");
    client.println("Content-Type: application/x-www-form-urlencoded;");

becomes

    client.println(F("Connection: close"));
    client.println(F("Content-Type: application/x-www-form-urlencoded;"));


sender: user

sender: assistant

body:
There is no limit for String other than the available memory. No String can be longer that ~2KB.

In these statments

    data = String("dust=") + d + "&rs=" + Rs + "&hcho=" + ppm + "&nh3=" + NH3 + "&co=" + CO + "&no2=" + NO2 + "&c3h8=" + C3H8 + "&c4h10=" + C4H10 + "&ch4=" + CH4;
    data2 = String("&h2=") + H2 + "&c2h5oh=" + C2H5OH + "&temp=" + t + "&hum=" + h + "&HATemp=" + HATemp2 + "&HAPres=" + HAPres2 + "&HAAlt=" + HAAlt2;

you are creating and deleting a lot of temporary Strings. How much memory will you need to hold all those temp Strings togheter? You don't know. Hard to say, because it's implementation dependent.

In Arduino you have to learn to use `char` arrays (and pointers) to works with strings. With a low level C method you know exactly how much space you will need. If you don't have enough memory, you still can reorganize your sketch to work around limitations.

Arduino is a low level world.


message:
Connection of serial pin on ATMEGA328P to connector B type(female) D+ and D-

Now I am using ATMEGA328P and want to communicate with computer in serial using B connector female (also want to provide power from computer to ATMEGA328P using B connector).

So here is my question. How can I connect D+ and D- to ATMEGA328P's pin No. 2 (PD0/RX) and pin No. 3 (PD1/TX)? In other words which pin should I connect to D+ and D- ? Also is it possible to connect them directly?

Thank you in advance.

body:
The Arduino Uno (and similar boards) have a chip on them that does serial communication via a dedicated USB chip (the ATmega16U2 chip). You can't just connect pins 2 and 3 to D+ and D- and turn that into USB.

You can conceivably do it using [V-USB](https://www.obdev.at/products/vusb/index.html) which does USB in software in conjunction with a few extra components.

You can also buy external serial to USB adapters which do the conversion externally. If you Google `serial to usb adapter` you will find quite a few for around $3.


message:
ATtiny85 MIDI IN using SoftwareSerial - Is it possible?

I'm trying to read MIDI notes using an ATtiny85 via SoftwareSerial; so far, I've got no success at all.

 - The ATtiny is using the internal clock, 8Mhz, 5V.
 - The MIDI keyboard sends clean note on/off messages (tested with a MIDI monitor).
 - I've tried several test programs, particularly Nick Gammon's, as described [here][1].
 - I've followed Nick's schematics to build the connector, and I can confirm his program works with an Arduino, but not with the ATtiny.
 - I calibrated the Tiny with OSCCAL - still no luck.
 - As far as I can tell, `midiSerial.available()` is always 0, in every program I've tried.
 - SoftwareSerial works fine for the purpose of MIDI out.

That's as far as I've got. I'd appreciate any pointers, especially if anyone else could try Nick's code and see if it works.

**EDIT**

There was an issue with my local version of SoftwareSerial. I had commented out code so that I could use pin change interrupts in my MIDI out program, but those interrupts are essential for MIDI input. Once I uncommented the code, all the programs I tested worked, so it is indeed possible to receive MIDI using an ATtiny.

That said, I've tried four keyboards as inputs and only one has worked so far, a Korg 01/W proX. The same happens when I load the MIDI code directly in the Arduino, so based on the answers below I will try a different optocoupler, and post my results here for the sake of improving on the answer.

Here's the schematics I was talking about:

[![MIDI connections][2]][2]

  [1]: https://arduino.stackexchange.com/questions/14054/interfacing-an-attiny85-with-midi-via-software-serial?answertab=active#tab-top
  [2]: https://i.stack.imgur.com/WIJf4.png

body:
I have done tests with a normal Arduino with software serial and missed quite a bit of messages, so I would advice to use hardware serial's instead.

For MIDI Out probably it works, but for MIDI In I have bad experiences. Especially when it comes to many messages, like aftertouch/pitch bend etc.

Also, I tried some optocouplers which didn't work well (like 6N137). I now use H11L1 optocouplers (they are white compared to most black ICs) and work perfectly.

You already checked the clean note on/note off ... are you sure it doesn't send active messages?

Below the schematic as I use it.. It does not matter if an STM32 or Arduino is used. Actually I haven't checked if H11L1 are 3.3V or 5V but they seem to work on both.

<!-- Begin schematic: In order to preserve an editable schematic, please
     don't edit this section directly.
     Click the "edit" link below the image in the preview instead. -->

![schematic](https://i.stack.imgur.com/D7ayK.png)

<!-- End schematic -->


message:
How to filter data of ultrasonic sensor using arduino

I am working on a project that uses ultrasonic HC-SR04 sensor to measure distance. I've connected the sensor to the Arduino Uno board, I am also using Arduino IDE to program the Arduino. The problem is that I am not getting stable readings, there is the presence of some noise in the readings. How should I filter out this noise.

Circuit connections are as follows:

<!-- language: lang-none -->

    Ultrasonic sensor | Arduino
    VCC                 5V
    GND                 GND
    Trigger             12 (digital)
    Echo                11 (digital)

I am using new ping to measure distance.

body:
First off, Start a time counter. You can get the current time instant by using:

    unsigned long StartTime = millis();

After that, keep counting time by using the following block:

     unsigned long elapsedTime = currentTime - StartTime;

With this you can know how much time (in ms) has passed since StartTime. In this time loop, keep reading data from the Ultrasonic sensor. As the sensor may need some time to get each reading, take a conservative delay (e.g. 100 ms). You can again increment the timer by using a goto statement. Note that you must also maintain a counter for later. In this time loop, keep adding the readings from the sensor to itself. Finally when the stipulated time is over, you can take the average by dividing the final sum of the sensor values with the counter maintained earlier.


body:
Having noise in the sensor data is common and normal, especially on low end sensor.

As you can imagine there is a "data science" to clean up the values, mostly based on statistic.

One of the easiest trick is to remove all values that have a difference > Xt from previous value; as you can imagine the tolerance Xt is calculated by a factor X, let's say a bit more the maximum speed you think the system will operate in time multiplies by the time since the last valid measure.

For example you expect a max distance chance of 10m in one second, so we use as tolerance 15m/s. If we don't read valid value, after 6 seconds our tolerance is 15m/s * 6s = 90m

Of course after much time maybe you just want to accept the first reading that seems valid, so you analyze 10, 100, 1000 value and see if they seems correct.

Then for a quick and dirty smoothing and cleaning if the remaining data, you can run a average on the value, there are different forms, and more value you use more stable are your output, but also less fast to follow changes.

A kallmann filter is the most common but also complex way to clean the data, but I guess in most hobbyist application is just overkill.


message:
Hall effect sensor

I've taken velocity readings of a wheel using a hall effect sensor. Is it possible to take the **acceleration** readings corresponding to those velocities as well? Do I just have to divide the velocity by the time taken?

body: Yes, you can divide speed by time and get acceleration, obviously that will give you the mean acceleration between speed reading.


message:
Advice for lower power clock type project

Arduino newbie here! I'm a programmer but my hardware knowledge is ... slim.

I'd like to build a clock type wake up timer for my daughter, using an Arduino type board. Probably overkill, but it's practice for me, not just the end result! The idea is that is sleeps all night, then around say 4, gradually fade on a red LED. At 6, which is when she's allowed to come in, the red LED switches to a green, or some colourful sequence that tells her it's time. At a later time, maybe 7/8, it goes back to sleep to conserve power.

I have an Arduino Uno, but looks like I'll also need an RTC, and I've read that the sleep power consumption is ~40mA, which on batteries is what? A day or two max?

So I'm thinking I can't do this with a Uno.

So, my question is, are there any very low power Arduino compatible boards with built in RTCs that I can use for this project that will get me up and running as quickly as if I was using the Uno?

body:
I will make my comment an answer:
Try one of Arduino supported RTC's boards. The most popular (and simple) are: DS1302, DS1307, PCF8563, and - very nice, precise DS3231 (my fav). Hook any of them up to your Arduino, add some (readily available) libraries, tweak a little and voila. The RTC will work from coin battery (or high capacity capacitor called supercapacitor, like [this one][1])

 Most (if not all) of mentioned RTC have 'alarm' function: you can set up your system to wake up your Arduino from sleep (sleep state to save battery) and gradually light up the LED.

To limit current of Arduino try removing LED, or - better - try to use Arduino Pro Mini. To modify it for better power saving see [here][2]

EDIT:
There are some other low-power boards:
[Moteino][3]
[Rocket Scream Mini Ultra][4]
[JeeLink][5]

Also, (as mentioned in one of comments) you can try one of ESP8266 and push it to one of many sleep modes. Try [this link][6].

  [1]: http://uk.farnell.com/panasonic-electronic-components/eecs5r5h105/cap-double-1f-5-5v-rad/dp/9697497
  [2]: http://www.home-automation-community.com/arduino-low-power-how-to-run-atmega328p-for-a-year-on-coin-cell-battery/
  [3]: https://lowpowerlab.com/guide/moteino/
  [4]: http://www.rocketscream.com/shop/mini-ultra-8-mhz-arduino-compatible
  [5]: https://www.digitalsmarties.net/products/jeelink
  [6]: https://www.losant.com/blog/making-the-esp8266-low-powered-with-deep-sleep


message:
My Arduino isn't showing up on my computer. What should I do?

You have your spangly new Arduino board, you've installed the software, and you plug it in. Nothing happens. Diagnosing problems may be a little tricky for the beginner, so what hoops should you go through to try and work out where the problem is and why you can't get your board working?

----

Note: this is an FAQ. Do not use it to ask about your specific problem. Comments will be deleted. Either ask a new question detailing all the steps you have taken, or, better, [discuss your problem in chat](https://chat.stackexchange.com/rooms/8489/pin-13).

body:
# Windows
Ok, the first thing you need to do is identify the kind of board you have. I don't mean is it an Uno, a Mega, or one of Intel's brief forays into the Arduino world - I mean what kind of USB interface the board has.

Boards can be loosely grouped into two categories - CDC/ACM and Custom USB Profile.

Current versions of the official Arduino Uno and Mega are both CDC/ACM devices (CDC/ACM, by the way, stands for Communication Device Class / Abstract Control Model). This means that between the main microcontroller (ATMega328P, ATMega2560, etc) there is another microcontroller - usually an ATMega16U2. This takes the serial data from the main microcontroller and sends it to the PC over USB using the USB CDC/ACM protocol.

You can identify these boards by the chip that is nearest the USB connector.

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

That small black chip with the Atmel logo on it is the USB interface chip.

Boards of this style have the USB drivers included in the Arduino IDE. If you have installed the IDE properly the drivers should have been installed for you automatically. Also Windows 10 (finally) contains "class compliant" drivers for CDC/ACM, so no drivers actually need to be installed for these boards anyway (installing the Arduino ones doesn't hurt, though, and helps it to show the right board name in the device manager).

The other category of board, "Custom USB Profile", use different chips. And there's lots of different chips it can be using.

Early Arduinos and some other makes of board (such as chipKIT boards from Digilent) use the Future Technologies RT232R chip. This sometimes looks at first glance like the Atmel chip above, but is very very different. You have to check the number on it to be sure. Other times a different package is used and it's obvious it's different.

Then there are the cheap clone boards you get on eBay and Amazon. These, more often than not, use yet another chip - the CH340G. This is a fraction of the cost than the FT232R or ATMega16U2 chips, which is why cheap boards tend to use them. They're also less reliable and harder to get working in some operating systems (most notably OS X).

For these kind of chips you need to install the right driver for the specific chip you have. For the FT232R chips that's not too hard - Future Tech have the drivers [on their website](http://www.ftdichip.com/Drivers/VCP.htm).

The CH340G driver is harder to find from a reliable source.<sup>(someone with more knowledge please fill this in)</sup>

Ok, so your board is a CDC/ACM based one, or you are sure you have installed the right drivers. The next thing to check is if the board is even being seen by the operating system.

When you plug it in for the first time it should pop up a bubble saying it found new hardware:

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

Or something similar to that. It should also make a noise.

If neither of those happen then it's likely the computer isn't seeing the device at all. This sounds more like a hardware problem than a Windows problem.

The first thing to try is to plug the Arduino into a different port. Even better is, if you have access to one, plug the Arduino into an entirely different computer.  What you are trying to diagnose here is if the problem is related to the Arduino/USB cable or to the computer/USB port.

If it works in a different computer but not your computer then there is something wrong with your USB ports. It may be that you are using a computer that is locked down (such as in a school or an office) where the "group policy" has been configured to not allow any USB devices to be used (chiefly to prevent people bringing in memory sticks with viruses on them). If this is the case you will have to consult with the powers that be in your organisation to get your device authorised.  If not, then you may have more luck plugging your Arduino into a *powered* USB hub instead of directly into your computer (it may be that the computer can't provide enough current for the Arduino to run properly).

If it's failing equally as badly on another computer / port then you should start looking at the USB cable and the Arduino.

It is quite common for small battery powered devices that are charged through USB to be shipped with cheap cables. These are cables that only have the +5V and GND wires in them - no D+ and D- wires. For obvious reasons these can't be used with an Arduino: with no data wires how can the computer see it? However it's generally impossible to tell these cables apart from a full USB cable.

If you happen to be using one of these cables without knowing it you'll get a power light on the Arduino and not much else. So you need to swap the USB cable for another one - preferably one you know works properly.  If it suddenly springs into life then you know you have a bad cable. Throw the old one away - it's almost useless - or stick a label on it saying "power only" so you know what it is.

Another thing to mention in passing: I have known some of the early Arduino boards to have lower quality USB connectors on them (Uno R2). These sometimes have trouble connecting properly with some cables (not all), so maybe a better quality cable may fix the problem, or tweaking the contacts within the USB connector with a needle may help.

Right - the other direction to go in is if it does identify that you plugged a board in, but can't install the drivers. Maybe it's saying the device failed, or it can't find the drivers.

Step one is to go into the device manager and look for an "Unknown Device":

[![enter image description here][3]][3]

That is most likely the Arduino.  You should be able to inspect all the data for it to find the USB Vendor ID (VID) and Product ID (PID).  If those are showing up as corrupted, not available, or `FFFF`, then your Arduino has a serious problem and Windows cannot work out what it is. In this case it may be that the USB interface chip has failed (there have been unsubstantiated rumours that shorting 5V to GND on an Uno R3 can kill the ATMega16U2 chip). There's not much you can do when that has happened.

If you can find reasonable data in the device manager, as in the image below, then it's going to be a case of trying to fix (or find the *correct*) driver, since you may not have the right one installed. Also note that some other board manufacturers use the same VID and PID as the Arduino and having their drivers installed could cause the Arduino to not function properly - you should uninstall their drivers first, or manually set the Arduino to use the proper Arduino driver.

[![enter image description here][4]][4]

  [1]: https://i.stack.imgur.com/j1qpC.jpg
  [2]: https://i.stack.imgur.com/BpxQR.jpg
  [3]: https://i.stack.imgur.com/ZSLV1.png
  [4]: https://i.stack.imgur.com/5kRYC.png


body:
# Linux

Getting Arduino and Arduino-like boards working properly under Linux can be a troublesome task if you are not familiar with how Linux works.

So I am going to introduce you to some of the basic tools you will need to work out why your board isn’t working as you’d like it to work.

The majority of problems a new user is faced with boil down to one simple thing: permissions. A normal user doesn’t, by default, have permission to talk to much in the way of hardware. That include serial ports and USB serial emulation ports (FTDI, etc). Fortunately granting permission to your user to access the serial ports is a simple matter, and one that you should always do by default to make life much simpler for you. This is done through a Linux permission facility called groups. A group is a name given to a collection of users, files, devices etc., that go together. Permissions can be granted on files to the group that it belongs to, and users that are in that group can access those files. On Linux most devices are just files.

The serial ports are all in the default group dialout, but your normal user isn’t. So you need to add your user to that group. Only root has the permission to do that, so use sudo to execute the commands as root. If you don’t have access to root through sudo or some other means then you will have to seek the assistance of an administrator who does have permission.

First add your user (you’re called fred, right?) to the dialout group:

    $ sudo usermod -a -G dialout fred

The “-a” is of vital importance. That says “Add the user to these groups”. Without it you have “Set the user’s groups to be this list”. If you omit the “-a” by accident you will remove your user from any other groups before setting them to be in the dialout group. That means you will never be able to run sudo again. So be sure not to miss that one out, eh?

Now that has only changed the configuration files (/etc/groups in this case) and the change hasn’t actually had any effect yet. The groups are only set when you log in to the computer, so you will either need to log out and back in again or (a more definite solution, especially if you have auto-login turned on) reboot the computer.

Now you should be in the dialout group:

(before)

    $ id
    uid=1000(fred) gid=1000(fred) groups=1000(fred),4(adm),24(cdrom),27(sudo),30(dip),46(plugdev),113(lpadmin),128(sambashare)

(after)

    $ id
    uid=1000(fred) gid=1000(fred) groups=1000(fred),4(adm),20(dialout),24(cdrom),27(sudo),30(dip),46(plugdev),113(lpadmin),128(sambashare)

Now try it, see if that has got you working.

Next step, if that doesn’t fix your problems, is to see if the computer knows about the Arduino. First look to see if there is a device file for the Arduino and if it has the right permissions:

    $ ls -l /dev/ttyACM* /dev/ttyUSB*
    ls: cannot access '/dev/ttyUSB*': No such file or directory
    crw-rw---- 1 root dialout 166, 0 Aug 24 11:05 /dev/ttyACM0

Don’t worry about the “cannot access…” message unless you get two of them. There are two sets of device names that the Arduino could be under depending on which type it is. Genuine UNO and similar boards (the ones with the ATMega16U2 chip as the USB interface) are /dev/ttyACM*. Clones using the CH340G, and FT232 based boards appear as /dev/ttyUSB*. We just asked for both there, so it complained when it couldn’t find any entries for one of the types. Which is fair enough. If you get:

    $ ls -l /dev/ttyACM* /dev/ttyUSB*
    ls: cannot access '/dev/ttyACM*': No such file or directory
    ls: cannot access '/dev/ttyUSB*': No such file or directory

however, then worry. That can’t find anything at all. The computer doesn’t know the Arduino exists.

One thing to check is the permissions on the files that have been listed above. You see the word “dialout” in the list? That’s the group that the device belongs to, and it should match the group you added yourself to earlier. There are times when it may say “tty” instead. This is because some other program has grabbed the device and is using it to allow remote access to the computer through that serial port. For that you need to make sure that there are no agetty processes using that port. How you do that is very much down to your version of Linux. Modern Debian based systems (such as Debian Jessie and Ubuntu) use systemd to manage it. You can examine what is running on your system using

    $ systemctl status

That returns a tree of all the services that your system is running. Look through that list to see if there are any “serial-getty” services running. If there are you should remove them:

    $ sudo systemctl stop serial-getty@ttyACM0
    $ sudo systemctl disable serial-getty@ttyACM0

While you’re there look through the list for another troublesome member: ModemManager. This is a program used to dial out to the internet through old-fashioned modems (you know, the kind that go beep beep beep squark squeek squark ) or USB DSL modems (that no one uses any more, we’re all wireless now. Remember the old green “frog” modem from way back when…?). That has a habit of grabbing a serial port as soon as it appears and trying to configure a modem attached to it. While that’s happening nothing else can access the serial port. It’s especially a problem with boards like the Arduino Leonardno or chipKIT Lenny which create a new serial port when they enter programming mode. So unless you really need the functionality that ModemManager provides you should just remove it:

    $ sudo apt-get remove modemmanager
    Reading package lists... Done
    Building dependency tree
    Reading state information... Done
    The following packages will be REMOVED
    modemmanager
    0 to upgrade, 0 to newly install, 1 to remove and 138 not to upgrade.
    After this operation, 2,826 kB disk space will be freed.
    Do you want to continue? [Y/n] y
    (Reading database ... 180827 files and directories currently installed.)
    Removing modemmanager (1.4.12-1ubuntu1) ...
    Created symlink from /run/systemd/system/ModemManager.service to /dev/null.
    Removed symlink /run/systemd/system/ModemManager.service.
    Processing triggers for man-db (2.7.5-1) ...
    Processing triggers for hicolor-icon-theme (0.15-0ubuntu1) ...
    Processing triggers for dbus (1.10.6-1ubuntu3) ...

Another useful tool is `lsusb`. This lists the USB devices that are connected to your computer. You should find your Arduino listed there. This is especially useful for boards that don’t present a serial port for programming, but we’ll cover those in more depth a little later on.

    $ lsusb
    Bus 001 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub
    Bus 002 Device 002: ID 80ee:0021 VirtualBox USB Tablet
    Bus 002 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub

Nothing much on this computer. Well, actually I am using a virtual machine for this, as you can see by the VirtualBox USB Tablet entry. But let’s connect my Arduino UNO:

    $ lsusb
    Bus 001 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub
    Bus 002 Device 004: ID 2341:0001 Arduino SA Uno (CDC ACM)
    Bus 002 Device 002: ID 80ee:0021 VirtualBox USB Tablet
    Bus 002 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub

So we know that the operating system has identified it. You can find out lots more information about it if you so desire, with:

    $ lsusb -v -d 2341:0001

That gives you all the device descriptors for the device. Tells you all you could ever want to know about the information the board sends to the computer when it is connected.

Another useful tool is dmesg. This is the system message log viewer and can be used to find out exactly what is going on with your computer.  It has a useful “keep running” mode specified by the flag `-w`. I like to run `dmesg` and then press return a few times to create a breakpoint in the listing, then plug in the board I am diagnosing to see just what the messages are that pertain to that board:

    $ dmesg -w
    [ 0.000000] Initializing cgroup subsys cpuset
    [ 0.000000] Initializing cgroup subsys cpu
    [ 0.000000] Initializing cgroup subsys cpuacct
    [ 0.000000] Linux version 4.4.0-24-generic (buildd@lgw01-12) (gcc version 5.3
    ... lots of stuff spools past ...
    [ 19.425870] NFS: Registering the id_resolver key type
    [ 19.425883] Key type id_resolver registered
    [ 19.425885] Key type id_legacy registered
    <press return a few times>

    <connect Arduino>
    [ 131.232511] usb 2-2: new full-speed USB device number 3 using ohci-pci
    [ 131.519307] usb 2-2: New USB device found, idVendor=2341, idProduct=0001
    [ 131.519312] usb 2-2: New USB device strings: Mfr=1, Product=2, SerialNumber=220
    [ 131.519315] usb 2-2: Product: Arduino Uno
    [ 131.519317] usb 2-2: Manufacturer: Arduino (www.arduino.cc)
    [ 131.519319] usb 2-2: SerialNumber: 64934333235351B002E0
    [ 131.605485] cdc_acm 2-2:1.0: ttyACM0: USB ACM device
    [ 131.613792] usbcore: registered new interface driver cdc_acm
    [ 131.613796] cdc_acm: USB Abstract Control Model driver for USB modems and ISDN adapters

Press CTRL+C to terminate the listing.

If nothing appears when you connect the Arduino then there is something fatally wrong. My money is either on a faulty cable (some cheap cables on eBay only have power wires and no data wires) or the Arduino itself is completely dead.

More likely though you get error messages. I can’t replicate them right now (I don’t have a faulty Arduino) but they usually pertain to things like “device not accepting address” and “Error -71”. This is usually caused by bad USB communication. It may, again, be a faulty cable, or it may be that the USB interface chip is not working right. Maybe the crystal has drifted and it’s not running at precisely the right frequency. Maybe it’s a cheap CH340 chip that has failed. Maybe the firmware on the ATMega16U2 has become corrupted.

If all that checks out fine so far and you still can’t upload a sketch there may be something even more fundamentally wrong with your Ardunio board. Maybe it’s time to look to see if there is actually any communication happening. I find the program minicom invaluable, although you could use the ghastly Serial Monitor in the Arduino IDE.

First you need to disable the main chip on your Arduino. You can do this simply by connecting the RESET pin to GND with a piece of wire. Or you can hold the RESET button down, but that means you’re then typing one-handed. That stops the main chip from interfering in any way with the serial communications while you’re testing it. It can also prevent any damage to the chip while testing.

The second step is to connect the TX and RX pins together (pins 0 and 1 usually) with another piece of wire. You are now in what is known as a loopback mode. Any serial data you send to the board should be sent straight back to where it came from. So now fire up `minicom` and try it out (you will need to install it first of course with `sudo apt-get install minicom`).

    $ minicom -D /dev/ttyACM0 -b 115200

Of course replace the `/dev/ttyACM0` with the real device name for your board. The `-b 115200` is the baud rate, though that is pretty much irrelevant since we’re not actively communicating with an external device.

Now you should be able to type some gibberish and get some gibberish back. If you do then communication is working fine, and the problem most likely lies within the target MCU – maybe the bootloader has become corrupted and needs re-flashing, or the chip has died.

CTRL+A, X gets you back out of `minicom` again.

If you didn’t get your gibberish back, or you got back different gibberish than you sent, then there is definitely something up with the serial communications. The main culprit is, again, the USB interface chip.

All this, of course, has been focusing on the traditional Arduino style interface with a USB serial port of some form. Not all boards give you that though. Some, such as the Launchpad boards, use a hardware programmer on the board, and that doesn’t always give a serial port – certainly the programming isn’t done through the serial port. To gain access to those (again by default you don’t have permission to access the low-level devices) you have to get deeper into the operating system.

For these you need to make modifications to the configuration of a system called `udev`. This is a management system for the devices on your computer and is used to control what happens to them when they are plugged in. One of the things you can do is set the permissions on that device so people can actually access it.

The system is configured by a set of rules in “rules files”. These are stored in `/etc/udev/rules.d` and there should already be a few in there for other purposes. You will need to, as root, create a new file to put your rules in.

    $ sudo nano /etc/udev/rules.d/50-boards.rules

The most important thing to know is the VID and PID (Vendor ID and Product ID) of your board. You can get that from `lsusb` as above (it’s the vvvv:pppp bit – v = VID, p = PID). You can then feed that into a simple rule, such as:

    ATTRS{idVendor}=="04d8", ATTRS{idProduct}=="0033", MODE="0660", GROUP="plugdev"

There we are matching a vendor (`04d8` = Microchip) and product (`0033` = PICkit2) and assigning it to the group `plugdev` (make sure you are in that group – default users should be already) and allowing the group members read and write access to it (`MODE="0660"`). Save that file and restart `udev` for the changes to take effect (or reboot your computer if you like):

    $ sudo /etc/init.d/udev restart

Now plug the device in and you should have permission to access it.


body:
**MAC OS X**

Getting an Arduino to work with OS X can be as simple as "plug and play" to almost impossible. It depends on which version of OS X you are using, and more importantly, what "kind" of Arduino you have. "Kind" means, is your Arduino a genuine Arduino, a "counterfeit" claiming to be the real thing or a cheap "knock off" using the CH340 USB interface.

Your first step is to identify exactly what you've got. If you have a CH340 chip on your Arduino like the one on this cheap "knock off" of an Arduino UNO, then you'll need to install a driver so that OS X can communicate with it.

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

Download a CH340 driver for the exact version number of OS X you are using and install it as per the manufacturer's instructions. If you download a driver for the latest version of OS X and install it on an older version of OS X, it may install just fine. When you plug in your Arduino device, OS X reads the .kext file and sees it's for a newer version of the OS so it doesn't load it, and never will (unless you upgrade to that exact version someday).

Here is a picture of a "counterfeit" Arduino UNO. It uses the ATMEL MEGA 16U2 chip as a USB interface which is "suppose to work" with OS X's existing drivers. If you have one of these and it's "not working", don't bother installing the FTDI drivers because that won't solve your problem.

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

Unfortunately, what works on one version of OS X doesn't always work on another version. Solutions are usually specific to OS X versions, but there are some common troubleshooting steps to follow once you know what Arduino USB Interface you have and you've installed the correct driver (if required).

Verify that OS X is recognizing your device.

1. Click on the Apple icon in the top left corner of the menu bar.
2. Click on "About This Mac".
3. Click on the "More Info…" button (OS X 10.6) or "System Report…" button under the "Overview" section (OS X 10.7 and higher).
4. Expand the "Hardware" menu item and click on USB.

You should see something like this:

[![enter image description here][3]][3]

If you plugged in your Arduino and is not listed somewhere on the USB Device Tree, I can guarantee it will not show up in the Arduino IDE Serial Port Menu. It won't show up in the /dev list using terminal either. Please keep in mind that System Profiler does not refresh automatically. If you un-plug your Arduino and plug it back in again, you have to MANUALLY re-fresh System Profiler to see the current data

[![enter image description here][4]][4]

If you still can't get your Arduino working, try swapping the USB cable or using a different computer / OS to see if it works.

  [1]: https://i.stack.imgur.com/lcpnK.jpg
  [2]: https://i.stack.imgur.com/pY0gD.jpg
  [3]: https://i.stack.imgur.com/0g7iC.png
  [4]: https://i.stack.imgur.com/r2jkl.png


message:
Arduino Mega 2560 + BL-TB6560+ Stepper

I am working on an Arduino Mega 2560 and BL-TB6560-V2.0 driver for running a stepper motor. Initially I was able to run the stepper in both direction with code given and a schematic as per this image.

[![schematic wiring][1]][1].

    int dirpin = 7;
    int dirH = 12;
    int steppin = 9;

    void setup() {
      pinMode(dirpin, OUTPUT);
      pinMode(steppin, OUTPUT);
      pinMode(dirH, OUTPUT);
    }

    void loop() {
      digitalWrite(dirpin, LOW); // Set the direction.
      digitalWrite(dirH, LOW);
      delay(1000);
      for (int i = 0; i<32767; i++) {
        // Iterate for 4000 microsteps.(32767)
        digitalWrite(steppin, LOW); // This LOW to HIGH change is what creates the
        digitalWrite(steppin, HIGH); // "Rising Edge" so the easydriver knows to when to step.
        delayMicroseconds(50);
      }
      delay(1000);
      digitalWrite(dirpin, LOW); // Set the direction.
      digitalWrite(dirH, HIGH);
      for (int j = 0; j<32767; j++) {
        // Iterate for 4000 microsteps.
        digitalWrite(steppin, LOW); // This LOW to HIGH change is what creates the
        digitalWrite(steppin, HIGH); // "Rising Edge" so the easydriver knows to when to step.
        delayMicroseconds(50);
      }
    }

But now when I am trying it, the same stepper is not rotating. What could be the reason? I have checked the driver voltage, it's ok, and the code and schematic is the same.

[![schematic Diagram][2]][2]

  [1]: https://i.stack.imgur.com/wQzUs.jpg
  [2]: https://i.stack.imgur.com/k0j5s.jpg

body:
I just removed the ENE(+) pin of the driver, which was connected to the +5V. Now it's working and the stepper is rotating.

I just got a hint from [this video][1].

  [1]: https://www.youtube.com/watch?v=-s5-2p9dRoU


message:
Store 3-dimensional char array in program memory with PROGMEM

I'm running a sketch whith a quite big, constant three dimensional char array (or simply, a table of strings). As this takes lots of RAM I'd like to store it in programm memory in order to keep the RAM free. This is the Sketch I'd like to run (my first idea):

    const char *rules [16][5] PROGMEM ={
     {"1Lorem ipsum dolor sit amet, consetetur sadipscin0g elitr", "sed di7am nonumy 8eirmod tempor invidunt"},
     {"2Lorem ipsum dolor sit amet, consetetur sadipscing2 elitr", "sed diam nonumy 9eirmod tempo5r invidunt"},
     {"3Lorem ipsum dolor sit amet, consetetur sadipscing 4elitr", "sed0 diam nonumy 1eirmod tempor invidunt"},
     {"4Lorem ipsum dolor sit amet, consetetur sadips3cing elitr", "sed diam nonumy 2eirmod tempor in5vidunt"},
     {"5Lorem ipsum dolor sit amet, consetetur 3sadipscing elitr", "sed 7diam nonumy 3eirmod tempor invidunt"},
     {"6Lorem ipsum dolor sit amet, conset9etur sadipscing elitr", "sed diam n8onumy 4eirmod tempor invidunt"},
     {"7Lorem ipsum dolor sit amet, consetetur sadipsc3ing elitr", "sed diam nonumy 5eirmod tempor inv4idunt"},
    };

    void setup() {
      pinMode(LED_BUILTIN, OUTPUT);
      Serial.begin(115200);
      for(int i = 0; i < 16; i++){
        for(int j = 0; j < 5; j++){
         Serial.println(rules[i][j]);
        }
      }
    }

    void loop() {
    }
But this fails with the following error:

    variable 'rules' must be const in order to be put into read-only section by means of '__attribute__((progmem))'

According to [Arduino's FAQ][1] this can be solved by changing the array's declaration to

    const char * const rules [16][5] PROGMEM ={

The sketch compiles now without errors, but the global variables (here only the array) still need lots of RAM:

    Sketch uses 2484 bytes (7%) of program storage space. Maximum is 32256 bytes.
    Global variables use 880 bytes (42%) of dynamic memory, leaving 1168 bytes for local variables. Maximum is 2048 bytes.

I'm not sure what causes this, but is it possible that only the pointers to the strings are stored in program memory, while the strings theirselves are still copied to RAM?

How do I put the whole arary in programm memory?

There has already been [a question like this on StackOverflow][2], but the answer recommends using prog_chars, which are according [to the AVR documentation][3] deprecated.

  [1]: https://github.com/arduino/Arduino/wiki/1.6-Frequently-Asked-Questions#q-i-have-a-similar-error-but-it-seems-to-be-already-const-heres-the-error-variable-lotofmessages-must-be-const-in-order-to-be-put-into-read-only-section-by-means-of-__attribute__progmem-const-char-lotofmessages-progmem--
  [2]: https://stackoverflow.com/questions/15737583/two-dimensional-array-of-character-arrays-progmem-arduino
  [3]: http://www.atmel.com/webdoc/avrlibcreferencemanual/group__avr__pgmspace_1gaa475b6b81fd8b34de45695da1da523b6.html

body:
Here you have:

    const char * const rules [16][5] PROGMEM ={

One `const` refers to the `char*` part. It means *the pointer value doesn't change*.

The other `const` refers to what it is pointed by. It means *the thing this pointer points doesn't change* (but the pointer itself can change).

In your sketch the thing that get put into PROGMEM is the **pointer array**; the texts themselves are still in RAM. Have a look at [PROGMEM page][1] and  study this example:

    const char string_0[] PROGMEM = "String 0";   // "String 0" etc are strings to store - change to suit.
    const char string_1[] PROGMEM = "String 1";
    const char string_2[] PROGMEM = "String 2";
    const char string_3[] PROGMEM = "String 3";
    const char string_4[] PROGMEM = "String 4";
    const char string_5[] PROGMEM = "String 5";

    // Then set up a table to refer to your strings.

    const char* const string_table[] PROGMEM = {string_0, string_1, string_2, string_3, string_4, string_5};

You need to declare each string by itself, and later put them in an array.

As you can see, pointer are inescapable.

**Edit: The F() Macro**

Here is a proof of concept of how to manage an array of string (lowercase "s") and strings constants in PROGMEM:

    const char uno[] PROGMEM = "1Lorem ipsum dolor sit amet, consetetur sadipscin0g elitr";
    const char dos[] PROGMEM = "2Lorem ipsum dolor sit amet, consetetur sadipscin0g elitr";
    const char tre[] PROGMEM = "3Lorem ipsum dolor sit amet, consetetur sadipscin0g elitr";
    const char cua[] PROGMEM = "4Lorem ipsum dolor sit amet, consetetur sadipscin0g elitr";
    const char cin[] PROGMEM = "5Lorem ipsum dolor sit amet, consetetur sadipscin0g elitr";

    const char * const rules [3][2] = {
     {uno, dos},
     {tre, cua},
     {cua, cin}
    };

    void setup() {
      Serial.begin(115200);
      Serial.println(F("PROGMEM string test"));
      Serial.println(F("-------------------"));
      for(int i = 0; i < 3; i++){
        for(int j = 0; j < 2; j++){
          Serial.print(i); Serial.print(" "); Serial.print(j); Serial.print(" ");
         Serial.println((const __FlashStringHelper *) rules[i][j]);
        }
      }
    }

    void loop() {
    }

Use the **F()** macro to put **constant** strings in PROGMEM. Otherwise, the strings will live in RAM. Are running short of RAM? Put the F() macro around those pesky strings and send them out of your RAM.

  [1]: https://www.arduino.cc/en/Reference/PROGMEM


message:
Which of the clock sources are actually internal to the ATmega328P?

I am trying to determine exactly what all of the fuse settings correspond to on the ATmega328P. The options for the `CKSEL` bits are:

 - 1111-1000: Low Power Crystal Oscillator
 - 0111-0110: Full Swing Crystal Oscillator
 - 0101-0100: Low Frequency Crystal Oscillator
 - 0011: Internal 128kHz RC Oscillator
 - 0010: Calibrated Internal RC Oscillator
 - 0000: External Clock

Clearly, the clocks labeled "internal" are part of the "guts" of the microcontroller. No external components are required to use those clock sources. The external clock is clearly an external source.

My question is this: are the low power, full swing, and low frequency sources built in to the microcontroller itself, or do they require an external crystal oscillator to be purchased and connected to the clock pins? This is not 100% clear from reading the data sheet. (Although I am under the impression that they are not internal to the device.)

body:
If it requires a crystal, as the ones in question clearly state, then obviously you need to connect a crystal (and load capacitors).  Or use a ceramic resonator.

Only those labelled as internal are internal. *Everything* else is external.


message:
Cannot get any readings from DHT22 Sensor connected to Arduino M0 Pro

I have directly connected a DHT22 to my Arduino M0 Pro. I have put a 10k Resistor across the Data & V+ of the sensor pinout. The data is connected to pin 5 and I have it connected to 3.3V output of Arduino.

I am just trying to see some readings from the sensor via the SerialUSB console. I have downloaded and unpacked the DHT libraries that I got on the Adafruit website/GitHub. As far as I know I have these libraries in the right directory - C:\Program Files (x86)\Arduino\libraries\DHT\...
I also have installed the Adafruit Unified Sensor library on the IDE.

I am trying to use the Tester program that is provided, this compiles ok but the SerialUSB printout prints:

    Failed to read from DHT sensor!
    Failed to read from DHT sensor!
    Failed to read from DHT sensor!

And so on...

I have tried another DHT22 sensor to no avail.

The only part of the code I have changed is the pin number and changed from Serial to SerialUSB.

Not sure if I have to change anything else? Or am I doing something really silly!

--------------------------------------------------------------------------------------------------------------

Here is the code:

<!-- language: lang-cpp -->

    // Example testing sketch for various DHT humidity/temperature sensors
    // Written by ladyada, public domain

    #include "DHT.h"

    #define DHTPIN 5     // what digital pin we're connected to

    // Uncomment whatever type you're using!
    //#define DHTTYPE DHT11   // DHT 11
    #define DHTTYPE DHT22   // DHT 22  (AM2302), AM2321
    //#define DHTTYPE DHT21   // DHT 21 (AM2301)

    // Connect pin 1 (on the left) of the sensor to +5V
    // NOTE: If using a board with 3.3V logic like an Arduino Due connect pin 1
    // to 3.3V instead of 5V!
    // Connect pin 2 of the sensor to whatever your DHTPIN is
    // Connect pin 4 (on the right) of the sensor to GROUND
    // Connect a 10K resistor from pin 2 (data) to pin 1 (power) of the sensor

    // Initialize DHT sensor.
    // Note that older versions of this library took an optional third parameter to
    // tweak the timings for faster processors.  This parameter is no longer needed
    // as the current DHT reading algorithm adjusts itself to work on faster procs.
    DHT dht(DHTPIN, DHTTYPE);

    void setup() {
      SerialUSB.begin(9600);
      SerialUSB.println("DHTxx test!");

      dht.begin();
    }

    void loop() {
      // Wait a few seconds between measurements.
      delay(2000);

      // Reading temperature or humidity takes about 250 milliseconds!
      // Sensor readings may also be up to 2 seconds 'old' (its a very slow sensor)
      float h = dht.readHumidity();
      // Read temperature as Celsius (the default)
      float t = dht.readTemperature();
      // Read temperature as Fahrenheit (isFahrenheit = true)
      float f = dht.readTemperature(true);

      // Check if any reads failed and exit early (to try again).
      if (isnan(h) || isnan(t) || isnan(f)) {
        SerialUSB.println("Failed to read from DHT sensor!");
        return;
      }

      // Compute heat index in Fahrenheit (the default)
      float hif = dht.computeHeatIndex(f, h);
      // Compute heat index in Celsius (isFahreheit = false)
      float hic = dht.computeHeatIndex(t, h, false);

      SerialUSB.print("Humidity: ");
      SerialUSB.print(h);
      SerialUSB.print(" %\t");
      SerialUSB.print("Temperature: ");
      SerialUSB.print(t);
      SerialUSB.print(" *C ");
      SerialUSB.print(f);
      SerialUSB.print(" *F\t");
      SerialUSB.print("Heat index: ");
      SerialUSB.print(hic);
      SerialUSB.print(" *C ");
      SerialUSB.print(hif);
      SerialUSB.println(" *F");
    }

body: Found what the fault was, it was a solder short between pins on a custom PCB that was sitting on top of the Arduino board. My bad! At least I have it working now!


message:
PROGMEM on Arduino Due (ARM Cortex M3)

I've been working with the `PROGMEM` function on my Arduino Uno and I'm thinking about changing to the bigger Arduino Due which is based on a ARM Cortex M3 processor instead of the AVR processor on the Uno.

The [Arduino Reference][1] now says:

> PROGMEM is part of the pgmspace.h library that is available in the AVR architecture only.

My question now is: Is it possible to store constants in program memory instead of flash on the Due?

If found [this post][2] on the Arduino forums, suggesting that this is done automatically. Does anyone know something about that?

EDIT: Arduino IDE doesn't give stats about RAM usage after compiling, so I can't just try.

  [1]: https://www.arduino.cc/en/Reference/PROGMEM
  [2]: http://forum.arduino.cc/index.php?topic=345026.msg2380744#msg2380744

body: There is no PROGMEM required on ARM. There is no memory bus separation between Flash and RAM, so it doesn't copy constants from flash to RAM which PROGMEM is used to prevent.


message:
Confused between SPI and I2C for SSD1306 OLED

I recently got myself an SSD1306 OLED display: [![SSD1306 OLED display][1]][1]

I haven't been able to successfully wire it to an Arduino (Mega 2560) however. I have been reading up on I2C and SPI and checked some libraries from Adafruit and U8G2.

However, I'm confused, since most of the Internet is talking about [a similar OLED display][2] with GND - VDD - SCL - SDA labelled pins, where mine has SCK instead of SCL.

Now, the number of pins make me believe I need to interface with I2C, but the SCK label points to SPI, right?

[One person seemed to have the same problem as me][3], but the solution he got (pull-up resistors) didn't do the trick for me, I'm afraid.

So, my question remains: how to wire this OLED display to the Mega 2560?

Much appreciated if someone could point me to the right direction.

Thanks!

  [1]: https://i.stack.imgur.com/aWcLh.jpg
  [2]: https://www.tindie.com/products/upgradeindustries/128x64-blue-i2c-oled-display-096-inch/
  [3]: https://community.particle.io/t/oled-4pin-i2c-gnd-vdd-sck-sda-with-photon-solved/29020/5

body:
SCK and SCL are the same thing.

* Serial ClocK
* Serial CLock

They seem to be interchangeable. The fact you have SDA (Serial DAta) as opposed to separate SDI / SDO or MOSI / MISO pins means it's I2C.

Wire it like you would any other I2C device.


body:
I have what appears to be the same display (GM009605 v4) and while both SCL and SCK both stand for Serial Clock many development boards have different SCK and SCL pins that you'd need to interface. On a Wemos d1 mini for example I have this display plugged into SDA => D2 & SCK => D5 where as if it was SCL it would to to D1.

FWIW I use the Wire.h and SSD1306.h libraries (https://github.com/ThingPulse/esp8266-oled-ssd1306) to interface with the display using the Wemos D1 mini.


message:
The most efficient way to test whether a byte is "empty" (B0000000) or not?

I have completed a small project I did to challenge myself to learn more about my arduinos programming. In this project, inside a for loop I have to check whether a MyVar byte fetched from an array of bytes, is "empty" (or `0`, or `B0000000` what applies best). Rough description of the program in note 1.

I did a lot of trial and error, and quickly realized that just asking

    byte MyVar = B0001111
    if {MyVar = 0 ; DoSomethingSpecial() } else {ProceedLoop()}

did not produce anything near the desired state. I deduced that testing bytes probably need to happen bitwise, or something clever (=beyond my understanding) is going on in how the compiler interprets the conversion.

So I created a dummy variable byte

    byte EmptyValue = B0000000

and then did a logical `AND` between the MyVar and the EmptyValue

    if (MyVar&EmptyValue) {DoSomethingSpecial(); } else {ProceedLoop(); }

which *seemed* to do the trick - it was getting late and my ability to find useful Serial.print() to capture the different values was getting low, but the results running the program were at the time indistinguishable to me from the expected way.

My question, firstly - is this a reasonable way to check if a byte is zero? Does it actually do that? I have been reading up on these bitwise calculations and I am truly confused to how it compares a final `TRUE` or `FALSE` from comparing.

Secondly, what would be a more processing-time-optimal way of doing this comparison? Is there a null-test of sorts? Should I have cast it into integer and tested against integer 0?

---

      const int interval=400;
      const byte ByteArrayMakeSound[11]={
        B0001111,                                       //H - length 4
        B0001111,                                       //E - length 4
        B0001111,                                       //L - length 4
        B0001111,                                       //L - length 4
        B0000111,                                       //O - length 3
        B0000000,                                       //
        B0000111,                                       //W - length 3
        B0000111,                                       //O - length 3
        B0000111,                                       //R - length 3
        B0001111,                                       //L - length 4
        B0000111                                        //D - length 3
        };
      const byte ByteArrayLongShort[11] =   {
        B0001111,                                       //H = --- --- --- ---
        B0000001,                                       //E = o o o ---
        B0001011,                                       //L = --- o --- ---
        B0001011,                                       //L = --- o --- ---
        B0000000,                                       //O = o o o
        B0000000,                                       // (pause 7 intervals)
        B0000100,                                       //W = --- o o
        B0000000,                                       //O = o o o
        B0000101,                                       //R = --- o ---
        B0001011,                                       //L = --- o --- ---
        B0000011                                        //D = o --- ---
      };

    void setup()
    {
      pinMode (LED_BUILTIN, OUTPUT);
    }

    void loop()
    {
      for (byte x = 0; x < 10; ++x) {
       byte sound = ByteArrayMakeSound[x];
       byte longshort = ByteArrayLongShort[x];
       byte emptyvalue {B0000000};
        if (sound&emptyvalue) {
          delay(7 * interval);
        }    else    {
          for (byte y = 0; y < 7; ++y)  {
            if (sound & (1<<y)){
              if (longshort & (1<<y))     {
                MakeSound(3);
                delay(interval);
              }   else    {
                MakeSound(1);
                delay(interval);
              }
            }   else      {}
          }
        }
          delay(3 * interval);
      }
    }

    void MakeSound(int del) {
      digitalWrite(LED_BUILTIN, HIGH);
      delay(interval * del);
      digitalWrite(LED_BUILTIN, LOW);
    }

---
**Note 1: Program purpose**

> The program started as a hello world program with me trying to write
> "hello world" in morse code with the builtin led. The two byte arrays
> store the "letter length" of the morse and the "daa" / "dit"
> assignment. I use empty bytes to separate words, which means a delay
> of 3 intervals (= length of "daa") should happen. Then including the
> entire letter-table of morse and a string to byte table conversion (to
> create the byte arrays). It is not very quick... But I am tinkering
> with moving the byte arrays into the flash memory. Just for Hello
> World it is fast enough, but the "daas" and the "dits" are slightly
> uneven so programming time is impacting performance.

body:
The fast way is:

    byte x;
    ...
    if (x) {
    // not zero.
    } else {
    // zero
    }

You are barking at the wrong tree.


message:
Arduino only supports 140 LEDs

I've a problem with an Arduino Uno board. It only supports 140 LEDs using the FastLED library. Any LED which is higher than that number can't be turned on or off using FastLED.

Is this related to the board, the library or any other  circumstances? And help or advice would be appreciated.

body:
Depending on how fast you need to go, the apa102-arduino library by Pololu doesn't seem to have a hard limit on their LED capacity.  They say the refresh rate goes down after 60 LEDs, but don't say anything about the maximum amount of LEDs you can have.

https://github.com/pololu/apa102-arduino

The max I'm doing at a time is only a string of 48, so I haven't checked how many it can update at once.  I am, however, running a total of 180 LEDs with this library, over 5 separate "channels".

To make it even a tiny bit harder, I'm doing it with a Nano.

This library has a "slow" and "fast" way to update the LEDs.  So far, the "slow" way is faster than the BlueTooth connection I'm sending data over to update the LEDs.

They state that the "fast" method is something like 20x faster than the "slow" way, but takes a little more in-depth programming.  Since the "slow" way works for me, so far, I haven't bothered trying the "fast" way.

Other option:

Talking with a friend at my local maker space, he said that it could be due to the speed of your board vs the timing of your LEDs. If your board isn't running fast enough, it can prevent the LEDs from being updated correctly after a certain amount of LEDs.

He was also saying that if you don't have enough available memory, it can affect how many LEDs you can update.

Seeing as you have an Arduino Uno, you shouldn't have a problem with speed or memory. Without knowing what else you are running on your Arduino (code, sensors, GPS, other shields, etc.), it's hard to say what could be holding you back.

My friend's son uses the FastLED library, so I'm going off other-than-first hand knowledge here.


message:
Is there any arduino microphone that can record heart sound?

I'm currently undergoing a project where I record heart sound (mechanical response) and send it over bluetooth to an app.

However I'm finding it really hard to find an arduino microphone or just general microphone that can listen to heart sound.

Any guide would be highly appreciated.

Thanks

body:
First, there is no such thing as an Arduino microphone. There are boards specifically for Arduino which have a microphone, but also these are just generic 'electronic sound sensors'.

In principle any microphone would be a valid choice, but you have to test what are the requirements (distance to heart, environment noice). You also could use piezo sensors for vibration checking possibly.


message:
Help with multi function momentary buttons

I'm using the PunchThrough Bean and trying to build a two button project that has multiple functions. The idea is the user can press button 1 or button 2 for either short or long presses, or they can press both buttons simultaneously for a short or long press. This would give the user up to 6 different functions. Below is my code. I can get button 1 or button 2 press to work, but can't get pressing both to work. Also, I can't figure out how to have a function depending on how long a button sequence was pushed. Any help would be greatly appreciated.

    const int btn0 = 2;
    const int btn1 = 3;

    void setup() {
      Bean.enableWakeOnConnect(true);
      Bean.enablePairingPin(true);
      BeanHid.enable();
      pinMode(btn0, INPUT_PULLUP);
      pinMode(btn1, INPUT_PULLUP);
    }

    void loop() {
      bool connected = Bean.getConnectionState();
      pinMode(btn0, INPUT_PULLUP);
      pinMode(btn1, INPUT_PULLUP);

      if (connected) {
        int btn0State = digitalRead(btn0);
        int btn1State = digitalRead(btn1);

        if ((btn0State == LOW) && (btn1State == HIGH)) {
          Bean.setLed(255, 0, 0);
          Serial.print("up");
          BeanHid.sendKey(KEY_UP_ARROW);
          Bean.sleep(500);
          Bean.setLed(0, 0, 0);
        }

        if ((btn1State == LOW) && (btn0State == HIGH)) {
          Bean.setLed(0, 255, 0);
          Serial.print("down");
          BeanHid.sendKey(KEY_DOWN_ARROW);
          Bean.sleep(500);
          Bean.setLed(0, 0, 0);
        }

        if ((btn1State == LOW) && (btn0State == LOW)) {
          Bean.setLed(0, 0, 255);
          Serial.print("right");
          BeanHid.sendKey(KEY_RIGHT_ARROW);
          Bean.sleep(500);
          Bean.setLed(0, 0, 0);
        }

      }
    }

body:
Don't act immediately when a button gets pressed, instead when a button is pushed all you do is set the timestamp on that button and set a flag.

Then when it is released or the time elapsed is large enough do the appropriate thing.

    void loop(){
        int btn1State = digitalRead(btn1);
        static bool button1 = false;
        static unsigned long time1 = 0;

        if (btn0State == LOW && !button1) {
            button1 = true;
            time1 = millis();
        }

        if (btn0State == LOW && button1) {
            if(millis() - time1  > SHORT){
                //do long action
                time1 = millis(); //reset timer
            }
        }

        if (btn0State == HIGH && button1) {
            button1 = false;
            //do short action
        }

    }


message:
What's the point of a USB to Serial converter in Arduino Uno?

I am trying to understand how an Arduino Uno communicates with a PC and why it does so.

As far as I understand, an Arduino can be programmed to communicate with a PC only via a COM interface. At the same time, an Arduino Uno uses a physical USB interface to connect to a PC and it has a USB-serial converter onboard. So data sent from the board is converted from COM to USB to be transferred to the PC where USB data is converted to COM by a device driver to be read by a COM-port listener.

Why does this COM-related stuff is needed if the Arduino already uses the USB stack for connection? And is the Arduino able to emulate a keyboard and mouse if it has to use interrupts for this, so it has to act like USB device without using COM?

body:
The problem with your understanding is with what "COM" is.

"COMx" is not a physical serial port - it is merely a concept. It is a "serial device" in Windows.

That Serial Device is implemented as a CDC/ACM protocol on USB. It's not "converted" - "COMx" is just the visible interface to the PC's end of the CDC/ACM connection.

The ATMega328P chip (and the ATMega2560) can't talk USB directly. They talk UART. So UART data is sent to another chip that can talk both USB and UART to bridge the two technologies.

So from the PC perspective the chain is:

    CDC/ACM Driver ("COMx") => USB => ATMega16U2 => UART => ATMega328P

Boards with an ATMega32U4 chip on them, like the Leonardo, can talk USB directly - so the sequence is much shorter:

    CDC/ACM Driver ("COMx") => USB -> ATMega32U4

Again there is *no* conversion from "COMx" to "USB" since "COM" is just the name given to the exposed end of the CDC/ACM driver.

It can be said that CDC/ACM *emulates* a serial port over USB. It forms a channel between the CDC/ACM driver ("COMx") and a pair of *bulk* endpoints in the chip at the other end of the connection.


message:
How to send message from one embedded system to another embedded system like in cars, from one car to another?

I want to send message from one embedded system to another embedded system, like from one car to another without using phone number. just turn on the wifi.. connect and send message. There are ways to to send text to phone but not this kind of texting? Iam short of time. I only need to know what will be required to do this ? PLease help

body: You can use ESP8266 modules( like Wemos d1) for wifi connections. The good thing about those are that they are also programmable and you can use arduino IDE to program. You can get two of those and make first one a server/host and second on a client for connection. There is more options of course: Bluetooth, RF link etc. Google "short distance connection arduino"


body:
1. **ESP8266** WiFi Module is a WiFi serial transceiver module, based on ESP8266 SoC. This chip implements a full TCP/IP protocol stack and the very interesting feature is that it has also a great computational power onboard. You can easily program it using Arduino IDE. You can buy this development boards in town market and its very low cost also.

2. **Bluetooth/BLE4.0** Bluetooth is a type of wireless communication used to transmit voice and data at high speeds using radio waves. It is a standard protocol for short-range radio communications between many different types of embedded devices. Devices need to be within approximately 10 meters of each other, and the typical data transfer rate is around 2 megabits per second (Mbps).

These two are the most preferable for shorter distance communication.


message:
Updating firmware on Adafruit Huzzah ESP8266

**tldr**: I'm trying to re-flash a previously working [Adafruit Huzzah ESP8266][1] breakout module to use the latest AT firmware. The re-flash doesn't seem to be working and I'm getting rather confused. This is the first time I've re-flashed one of these modules.

**What I did**:

I installed the latest version of esptool.py using pip, and downloaded the latest Espressif AT firmware from [github][2]. With the Huzzah on a breadboard I grounded GPIO0 and connected the serial port header to my PC using a FTDI cable. VC on the cable is 5v. The red power light lit. I then ran the following commands:

> esptool.py --port COM4 --baud 115200 write_flash -fm dio -fs 32m
> 0x00000 boot_v1.1.bin
>
> esptool.py --port COM4 --baud 115200 write_flash -fm dio -fs 32m
> 0x01000 user1.bin
>
> esptool.py --port COM4 --baud 115200 write_flash -fm dio -fs 32m
> 0x7C000 esp_init_data_default.bin
>
> esptool.py --port COM4 --baud 115200 write_flash -fm dio -fs 32m
> 0x7E000 blank.bin

Each upload seemed to complete ok, but I found that I couldn't upload the next until I pressed the reset button on the module first, otherwise I got the error:

> A fatal error occurred: Failed to connect to Espressif device: Timed
> out waiting for packet header

This doesn't seem right to me.

After uploading all 4 components as above I disconnected GPIO0 and cycled the power on the module. I then tried connecting using putty at 115200 baud but I get no echo back from the module, and it doesn't respond to commands.

Observations:

 - The module previously worked and I could connect to it with putty.
 - If I reset it while connected to putty at 115200, I get a consistent pattern of garbage characters, so my guess is its alive but confused somehow.
 - I've tried connecting at various baud rates: 9600, 14400, 19200, 38400, 57600, as well as 115200. Same result.
 - I've found walkthroughs that show firmware like node.mcu being uploaded as a single binary. Should I be somehow merging the four bin files into one before uploading the the Huzzah?

What am I doing wrong here?

  [1]: https://learn.adafruit.com/adafruit-huzzah-esp8266-breakout/overview
  [2]: https://github.com/espressif/ESP8266_AT/tree/master/bin

body:
I'm confident that I've resolved this now. I'll leave the question here in case it is useful to anyone in the future.

The problem was they way I was downloading the individual bin files from the github repo, using right click -> Save As in Chrome. This downloads a file with the correct name, but it is actually the content of the file's html page, not the binary itself. Downloading the repo as a zip file, extracting the bin files,  and then uploading them to the Huzzah using a single command gave me a properly flashed device.

What happened was I noticed that esptool can upload multiple files in one go so, with the original bin files, I tried the command:

> esptool.py --port COM4 --baud 115200 write_flash -fm dio -fs 32m 0x00000 boot_v1.1.bin 0x01000 user1.bin 0x7C000 esp_init_data_default.bin 0x7E000 blank.bin

and got the following error

> esptool write_flash: error: argument <address> <filename>: Detected overlap at address: 0x1000 for file: user1.bin

Thats when I noticed that boot_v1.1.bin was way to big to fit in the space between 0x00000 and 0x01000. Examining it in notepad++ revealed that it was html.

A learning experience...


message:
Max length of char arrays?

I'm running the following Sketch on my Arduino Uno:

    const boolean verbose = true;

    void debug(const char *s){
        if(verbose){
          char buf[8 + sizeof(s)] = "[DEBUG] ";
          strcat(buf, s);
          Serial.println(buf);
       }
    }

    void setup() {
      Serial.begin(115200);
      char str[] = "Lorem ipsum dolor sit amet, consetetur sad";

      Serial.print("Size of String: ");
      Serial.println(sizeof(str));
      debug(str);
    }

    void loop() {
    }
The `debug()` function should be used to print debugging information to Serial. The Sketch like I posted it works wuite fine and prints the following to Serial:
    Size of String: 43
    [DEBUG] Lorem ipsum dolor sit amet, consetetur sad

But when I add one more character to the string (43 chars excluding null terminator) I get the only follwoing on Serial:

    Size

This problem does not appaer when defining `str` as a global varaible. What does cause this issue and how can it be fixed?

body:
The main issue with your code is:

    sizeof(s)

That doesn't return the string length - it returns the size of the char pointer - which is two bytes (on an 8-bit system, 4 on a 32-bit system).

Instead you need to use `strlen(s)` and add one to it for the NULL character at the end.

    if(verbose){
      char buf[8 + strlen(s) + 1] = "[DEBUG] ";
      strcat(buf, s);
      Serial.println(buf);
    }

However, what you are doing is pointless. Just print twice:

    if(verbose){
      Serial.print(F("[DEBUG] "));
      Serial.println(s);
    }

Note the use of the `F()` macro to ensure that `[DEBUG]` doesn't waste RAM.


body:
`sizeof(s)` does not do what you thing it does. All it does is take the sizeof of the pointer.

So you end up with Undefined Behavior when you concatenate the strings which means than *anything* is allowed to happen.

Instead you can do 2 print statements to concat on the serial stream:

    void debug(const char *s){
        if(verbose){
          Serial.print(F("[DEBUG] "));
          Serial.println(s);
       }
    }


message:
ESP8266 and Python Communication

I'm new to networking and working with ESP8266. I have successfully setup my ESP8266 and can program it from Arduino IDE (tested a blinky code).

I want to send some data from a Python script running on my PC to ESP8266. Similar to a setup where use PySerial in Python, open a COM port and send my serial data to an Arduino. Arduino will parse my data bytes and will perform some action. Now, I am trying to achieve the same with ESP8266 and UART replaced with wireless communication.

First, I would like to connect my PC to ESP which will have its own SSID and password. Once connected, I would like to send my data bytes from Python script to ESP8266 wirelessly. Now, similarly, ESP will parse this received data and perform some function (like control its GPIOs).

How can I achieve this? It seems like a pretty simple task, but I'm really confused with what mode I've to use (AP? Client? Server?). What protocol for communication is the best (TCP? MQTT?). What do functions like Handle client/root do? I understand I've to use socket programming on Python, how to do that specifically in my case? How do I buffer my incoming data on ESP, so that I don't miss the bytes?

Could anyone please explain using an analogy with wireless communication and UART? Any links to tutorials will be helpful too. There are some tutorials online where they do this using a HTTP server and control the GPIOs from the browser, but no, I don't want this. I just simply want to send my data as I would with COM Port/UART/Arduino!

body:
The simplest IP equivalent to UART is TCP/IP sockets.  Create a listening socket on the ESP8266 and connect to it from the PC (or do it the other way around if you like). Data fed in one end comes out the other - just like a serial port.

There's examples with the ESP8266 core that do just that.


body:
You must configure the ESP as an AP, if you want it to have its own IP.
You **then** set up a tcp-server on the ESP (i think there are example functions in the IDE).

Keep in mind, that the communication (server/client you mentioned) has nothing to do with the way PC and ESP are connected with (whether the ESP is providing an Access Point or logged into your WiFi). Those are different protocol layers, which means you will not need to make any changes if you want PC and ESP communicate over your router at all.

Actually the ESP (or at least for the ESP8266-12F I know for sure) is capable of running both ap and wificlient **at the same time**.

It's not a big difference to serial communication, you will need to poll for incomming messages in your loop if you want to run a server. Sending messages to your PC is like printing to the serial interface.


body:
Check my project: "Esp 2 Python"
-----------------------------
https://github.com/KebabLord/esp_to_python

The theori is you can create a localhost and get the sensor data or manage the module through arduino requests or urllib modules with a simple local mDNS server. This project allows you to control and read ESP. ![my  code's diagram](https://github.com/KebabLord/esp_to_python/raw/master/diagram1.png)

[![A screen shot from the code, you use only 3 functions to control it][1]][1]

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


message:
Why can I measure two pins simultaneously?

I would like to do an action if both buttons on my arduino pro micro are depressed simultaneously. I'm getting some strange results:

    // Buttons
    Bounce button0 = Bounce();
    Bounce button1 = Bounce();

    void setup() {
      Serial.begin(115200);
      while (!Serial) {
        ;
      }

      pinMode(2, INPUT_PULLUP);
      button0.attach(2);
      button1.interval(1);

      pinMode(3, INPUT_PULLUP);
      button1.attach(3);
      button1.interval(1);

      Serial.println("Setup Complete");
    }

    void loop() {
      button0.update();
      button1.update();

      if (button0.fell()){
         Serial.println("button0 fell");
      } else if (button0.rose()) {
        Serial.println("button0 rose");
      }

      if (button1.fell()){
         Serial.println("button1 fell");
      } else if (button1.rose()) {
        Serial.println("button1 rose");
      }

      if (button0.fell() & button1.fell()){
        Serial.println("buttons fell");
      } else if (button0.rose() && button1.rose()) {
        Serial.println("buttons rose");
      }
    }

Here is the output to the Serial console:

    Setup Complete
    button0 fell
    button1 fell
    button0 rose
    button1 rose

Why isn't this branch being executed? `button0.fell() & button1.fell()` For the life of me I cannot figure this out. Thank you!

EDIT
====

This doesn't work either, which is crazy:

    void loop() {
      button0.update();
      button1.update();

      if (button0.fell()) {
        if (button1.fell()) {
          Serial.println("buttons fell");
        }
      }

      if (button0.rose()) {
        if (button1.rose()) {
          Serial.println("buttons rose");
        }
      }
    }

EDIT
====
Thank you for the answers! Unless the person was to push both buttons in the exact same iteration of the loop, my code would never work. Here is what I ended up using:

    if ((button0.fell() && !button1.read()) || (button1.fell() && !button0.read())) {

body:
You can test it easily by calling the function twice directly after each other. If the first time a true is returned and the second time a false, the state is internally reset.

But probably because after you call the fell function, the internal state is reset, so after the call not a new fell has been happened.

So store the return value of the fell and rose functions and use those instead.

Update:

I'm not sure if this is the actual implementation but I found for fell/rose and see this:

    bool Bounce::rose()
    {
     return ( state & _BV(DEBOUNCED_STATE) ) && ( state & _BV(STATE_CHANGED));
    }

    bool Bounce::fell()
    {
     return !( state & _BV(DEBOUNCED_STATE) ) && ( state & _BV(STATE_CHANGED));
    }

So as long as the state has not changed it returns false (which is similar/equal as 'resetting the internal state'. Except this reset is done at a different location (but checked in the fell and rose function).

Update:

See remarks from gre_gor below


body:
https://github.com/thomasfredericks/Bounce2/wiki

I'm not familiar with the Bounce(2) library, but looking at the above site, it looks like "fell" is more of an "instant" thing, where it isn't something that maintains state over the Arduino loop.

Seeing as we are human, we can't (normally) push buttons at the same exact time.  This means that we would usually end up pushing the buttons within milliseconds, plural, of each other, but your simple example could loop multiple times between the first button and the 2nd button being triggered.

Don't forget that the Arduino Uno runs at 16mHz.  This is extremely slow compared to today's computers, but it's still running millions of operations a second.  My first computer, the IBM XT, ran at 4.77 mHz and that was _the_ standard computer for years.

https://en.wikipedia.org/wiki/IBM_Personal_Computer_XT

I suggest putting in a loop counter to help you discover if this is the case.  Trying to display it every loop may slow the loop down, so only display the counter on your current displays.  If your "button0 fell {#}" display shows a different number than your "button1 fell {#}", then you know what's going on.  You may also want to display the actual contents of "button{01}.fell()".

IDK if this library does it, but in app programming, sometimes getting the value of an event like this will cause the event to be flushed and reset the value.  This would mean that calling a method the first time would render a different value than calling it a second time, even if the second time was immediately following the first call.  Setting "button{01}.fell()" to a variable might be a better option than trying to call it twice.


body:
> I'm getting some strange results:

your code doesn't really measure the two pins "simultaneously". instead, it measure the two pins sufficiently fast and it appears to be simultaneously.

use input capture for that.


body:
Maybe I missed something but the branch doesn't execute because

    button0.fell() & button1.fell()

should be

    button0.fell() && button1.fell()

the *else if* clause also never executes.


message:
Controlling two AC devices, device turning on incorrectly

I am making use of the code below to control the speed of an AC fan and the intensity of an AC Lamp with an Uno.

The problem I am having is that, when I set the lamp intensity to low or medium, the fan turns on at a very low speed as well, and I cannot turn it off even when setting the fan to off.

Also if I turn the lamp on and then off, the fan (which is still set as off), will spin slowly for a second or two in random intervals.

For troubleshooting purposes, I did separate this program into two programs, controlling each device and its circuit separately, and it works perfectly, but when I combine them, I get the above problem.

Any assistance in troubleshooting or ideas to solve this would be appreciated.
Haven't attempted AC control before.

    int PWM = 3;
    int FAN = 4;
    int dimming;

    void setup()
    {
      Serial.begin(9600);
      Serial.println("Serial connection started, waiting for instructions…n0 =     Offn1 = 25%n2 =50%n3 = 75%n4 = 100%");
      pinMode(PWM, OUTPUT);
      pinMode(FAN, OUTPUT);

      attachInterrupt(0, zero_crosss_int, RISING);
    }

    void zero_crosss_int()
    // function to be fired at the zero crossing to dim the light
    {
      int dimtime = (75 * dimming);  // For 60Hz =>65
      delayMicroseconds(dimtime);    // Off cycle
      digitalWrite(FAN, HIGH);   // triac firing
      delayMicroseconds(10);         // triac On propogation delay
      //(for 60Hz use 8.33)
      digitalWrite(FAN, LOW);    // triac Off
    }

    void loop ()
    {
      if (Serial.available()) {
        char ser = Serial.read(); //read serial as a character

        switch (ser)
    {

      /* Lamp Control  */

      case '0':
        analogWrite(PWM, 0);  //lamp Off
        break;
      case '1':
        analogWrite(PWM, 50);  //lamp low
        break;

      case '2':
        analogWrite(PWM, 130); //lamp medium
        break;

      case '3':
        analogWrite(PWM, 255); //lamp high
        break;

      /* Fan Control  */

      case '4':
        dimming = 128;  //fan off
        break;

      case '5':
        dimming = 90; //fan low
        break;

      case '6':
        dimming = 65; //fan medium
        break;

      case '7':
        dimming = 35; //fan high
        break;

      default:
        Serial.println("Invalid entry");

        }
      }
    }

The circuits it controls is based on these :

Lamp
[![PWM AC Lamp][1]][1]

Fan
[![Dimmer AC Fan][2]][2]

Also, these circuits and code are based on these post, if it may interest you:

Lamp
[PWM AC Lamp][4]

Fan
[Dimmer AC Fan][3]

  [1]: https://i.stack.imgur.com/6Gavz.jpg
  [2]: https://i.stack.imgur.com/95J35.jpg
  [3]: https://arduinodiy.wordpress.com/2012/10/19/dimmer-arduino/
  [4]: https://diyhacking.com/arduino-lamp-dimmer/

body:
The design of the zero_crosss_int() ISR is unreliable. After each interrupt it unconditionally turns on the triac, even in the OFF position. Since the `dimming` value in that case is close to the AC cycle duration, it may miss the current cycle and turn on early in the next cycle. This may happen e.g. due to noise in zero crossing input.

75 us * 128 = 9.6 ms. Assuming 50 Hz AC, cycle duration is 1000 ms / 100 = 10 ms. You only have 4% margin.

You need to avoid turning on the triac close to the end of the AC cycle. Limit the maximum value of `dimming` variable to, say, 75% of the AC cycle. This will impose a lower limit on the output power. However, you want to do this anyway because motors need a minimum power to start rotating. Adjust the ISR so that in the OFF position it does not send a positive pulse at all.

ADDED: so you just need to add an `if` statement to you ISR code:

    void zero_crosss_int()
    // function to be fired at the zero crossing to dim the light
    {
      if (dimming > 96) // choose this value experimentally, adding some margin
        return;
      ... everything else goes here ...
    }

ADDED2: Blocking for extended duration in the ISR is not a good idea in general. If you happen to need to do anything else in addition to 'dimming' a fan, you will almost certainly need to get rid of this. You could start a timer in the ISR and send the output pulse in the timer ISR, making sure that the timer ISR does not get executed after the next zero-crossing ISR...


body:
Imraan, you have most definitely NOT build your circuit safely as to do so is impossible on a 'breadboard' when using 220 VAC.  The contacts on these boards are extremely poor not to mention that the separation between the metal contacts is inadequate.  Please read up on track separation for mains voltages on PCB's to get an idea of what is required.
The commonly used 0.1" pitch strip board is also unsuitable for mains voltages.


message:
How to pass 'Serial' as an input argument in Arduino function?

I have one integer value which I should pass through Serial1, Serial2, Serial3, and Serial4 after performing some algebraic operation on this integer. For this algebraic operation, I made a function and input arguments is an integer and Serial number.
Simple code is given below: *(I deleted every extra part of my code to make easy to understand)*

    String stringG; int d1; int d;

    #include<SoftwareSerial.h>
    //Software Serial #1: Rx = digital pin 10, Tx = digital pin 11
    SoftwareSerial Serial4(10, 11);

    void setup() {
      // put your setup code here, to run once:
      Serial.begin(9600);
      Serial1.begin(9600);
      Serial2.begin(9600);
      Serial4.begin(9600);
    }

    void loop() {
      // put your main code here, to run repeatedly:
      if (Serial.available() > 0)
      {
         String  XX = Serial.readString();
        int d1 = XX.toInt();
        Serial.println(d1);
        int yy;
        yy = compareFunction (d1, Serial4);
        Serial.println("Now the final values are:");
        Serial.println(d1);
        Serial.println(yy);
      }

    }
    int compareFunction (int d, String Serialx)
    {

      int ZZ = Serialx.readString(); // I will receive some values from motor using serial4
      //to avoid long code I deleted unnecessary parts
      // I will use ZZ and d values and output will be yy
      return yy;
    }

As you see in  `compareFunction` I receive value using Serial (it may be 1,2,3 or 4) So I have to pass `Serial as an input argument` in this function. If I can't pass `Serial` then I have to write 4 functions each for Serial1, 2, 3 and 4 which I want to avoid. Is it possible? How can I do it? when I tried with above code it shows error

> exit status 1 could not convert 'Serial4' from 'SoftwareSerial' to
> 'String'

body:
The `Serial` object is the end of a chain of classes, each with a different set of functionality.

    Print -> Stream -> HardwareSerial => [Serial]

Since you are *reading* from it the best class to use is `Stream` since that is the one that is the one that contains the reading functionality.

You should pass it *by reference* or as a *pointer* since you don't want to copy the object.

    int compareFunction (int d, Stream &Serialx)
    {

      int ZZ = Serialx.readString(); // I will receive some values from motor using serial4
      //to avoid long code I deleted unnecessary parts
      // I will use ZZ and d values and output will be yy
      return yy;
    }

By using `Stream` you can use any object type that also uses `Stream` in its class inheritance chain - even things like a WiFi socket connection.

This behaviour is called [polymorphism](http://www.cplusplus.com/doc/tutorial/polymorphism/) and is one of the more powerful features of classes in C++ (and other OO languages).


message:
Arduino force feedback vibration gamepad

I'm projecting a gamepad with Arduino Micro. I'm using the [Arduino Joystick Library][1].

I'm building this gamepad for racing games so I need to catch signal like `hit_the_wall`, `hit_another_car`.

I wonder how the PC game output the signal of the vibration/force feedback and send throw USB to the gamepad.

I already know that the gamepad drivers and the game have to support this function, but I'm completely lost about how I can catch the input to trigger the vibration engine with Arduino.

I was thinking something about (pseudocode):

    input = Serial.read();

    if(input == hit_something_signal){

       digitalWrite(engine, HIGH);

    }

Now my question is which is this magic `hit_something_signal`?

**UPDATE**

I'm reading the [PID document][2] and I notice on page number 24 the register addresses to implement the force feedback.

    ;Start Force Feedback command definitions
    USAGE_PAGE (Physical Interface) 05 0F
    ;Effect Report Definition
     USAGE (Set Effect Report) 09 21
     COLLECTION (Logical) A1 02
     USAGE (Effect Block Index) 09 22
     LOGICAL_MAXIMUM (127) 25 7F
     REPORT_SIZE (7) 75 07
     REPORT_COUNT (1) 95 01
     OUTPUT (Data,Var,Abs)
     .......

In the [Joystick.cpp][3] file I notice the HID implementation:

    // USAGE_PAGE (Generic Desktop)
    tempHidReportDescriptor[hidReportDescriptorSize++] = 0x05;
    tempHidReportDescriptor[hidReportDescriptorSize++] = 0x01;

    // USAGE (Joystick - 0x04; Gamepad - 0x05; Multi-axis Controller - 0x08)
    tempHidReportDescriptor[hidReportDescriptorSize++] = 0x09;
    tempHidReportDescriptor[hidReportDescriptorSize++] = joystickType;

    // COLLECTION (Application)
    tempHidReportDescriptor[hidReportDescriptorSize++] = 0xa1;
    tempHidReportDescriptor[hidReportDescriptorSize++] = 0x01;

    // REPORT_ID (Default: 3)
    tempHidReportDescriptor[hidReportDescriptorSize++] = 0x85;
    tempHidReportDescriptor[hidReportDescriptorSize++] = _hidReportId;
    .......
    ......

Do you think should be possible to implement the force feedback part? I do not need to catch all the forces, but run the vibrator engine every time the game sends and input of every kind of force.

The problem is that I'm not an expert about low-level programming and drivers. Do you have any idea?

  [1]: https://github.com/MHeironimus/ArduinoJoystickLibrary
  [2]: http://www.usb.org/developers/hidpage/pid1_01.pdf
  [3]: https://github.com/MHeironimus/ArduinoJoystickLibrary/blob/master/Joystick/src/Joystick.cpp

body:
That library has no support for vibration.

The HID report descriptor has to include the correct OUTPUT items for the PC to send the vibration instructions to the Arduino - and of course the library has to be able to handle that incoming data - none of which is implemented.

So you can't unless you massively expand that library. And that takes intimate knowledge of USB and HID protocols.


message:
Reconnect to I2C with a different address (ATTiny85)

My project requires to reconnect to an I2C bus as a slave. I can't reset my ATTiny physically because I2C + my project + a pin to trigger the reset isn't possible due to the limited amount of pins available on the ATTiny85. I searched the reference and different forums. If there was an answer to my question, I couldn't find one.

Thanks in advance.

(I want to try to make a plug-and-play kind of experience with a product. I want the chip to join with a defined address (100 or so), get a new address from the master and then reconnect to the I2C bus).

body:
You only need to reinit the I2C slave.

The [TinyWireS][1] lib I found lets you just call `TinyWireS.begin()` with the new slave address. Though it doesn't have a way to stop the I2C connection. But the lib is hackable enough that with the ATTiny's specsheet you can add an end() to it.

However I believe that it may be better if the newly connected ATTiny acts as a master first and requests a free address from a known fixed slave acting as a dhcp server.

  [1]: https://playground.arduino.cc/Code/USIi2c


message:
Arduino Uno to Arduino Uno Word.doc file transfer

I have written a 2 sets of code for the transmitter and receiver section. I am trying to send a word document file from 1 arduino uno to the next arduino uno through serial TX and RX. The file is initially loaded into a micro sd card module at the transmitter section. I would like to transfer that file to the receiver section's sd card module. I am able to receive an empty word document at the receiver section. There is no information in the document. I would like some help with this. I will attach the transmitter and receiver code below.

Transmitter code:

    #include <SD.h>
    #include <SPI.h>

    File fileIn;

    void setup() {
      // put your setup code here, to run once:
      Serial.begin(9600);
       while (!Serial){
        ; //  wait for serial port to connect. Needed for native USB port only
      }
      Serial.print("Initializing SD card...");
      if(!SD.begin(4)){
        Serial.println(F("Initialization failed!"));
        return;
      }
      Serial.println("Initialization done.");
      if(!SD.exists("student.txt")){
        fileIn = SD.open("student.txt", FILE_WRITE);
        fileIn.println(F("abc.txt"));
      }
      fileIn = SD.open("student.txt", FILE_READ);

      while(fileIn.available()){
        Serial.write(fileIn);
      }
      delay(1000);
      fileIn.close();
    }

    void loop() {
      // put your main code here, to run repeatedly:

    }

Receiver code:

    #include <SD.h>
    #include <SPI.h>

    File fileOut;

    void setup() {
      // put your setup code here, to run once:
      Serial.begin(9600);
      while (!Serial){
        ; // wait for serial port to connect. Needed for native USB port only
      }
      Serial.print("Initializing SD card...");
      if(!SD.begin(4)){
        Serial.println(F("Initialization failed!"));
        return;
      }
      Serial.println("Initialization done.");
      if(SD.exists("student2.txt")){
        SD.remove("student2.txt");
      }
      fileOut = SD.open("student2.txt", FILE_WRITE);

      while(fileOut.available()){
        Serial.write(fileOut);
      }
      delay(1000);
      fileOut.close();
      Serial.println("It worked!");
    }

    void loop() {
      // put your main code here, to run repeatedly:

    }

body:
      while(fileOut.available()){
        Serial.write(fileOut);
      }

This doesn't quite do what you think it does.

Instead you should send the file length first and then do:

    for(unsigned long size = 0; i< fileLength; i++){
        Serial.write(fileOut.read());
    }

You should also investigate some kind of rate limiting to avoid overwhelming the reciever and having to drop some bytes.