title: Working with Wire core library

text:
# Question
Title: Working with Wire core library
I'm studying the Wire library code driver `utility/twi.h` to learn how twi buffering and ISR management work.

What I did actually, is that I copied the header/source files from the Arduino path `F:\Program Files\Arduino\hardware\arduino\avr\libraries\Wire\src\utility` and put them in the Arduino custom libraries and changed the `.c` to `.cpp` and it worked.

I actually ran through different i2c libraries for avr and this code library is one of the best IMHO.

My test code is to initialize the HMC5883L, and read back those configuration setting from the first SFRs of the HMC5883L.

I'm using Serial.prints inside/outside the ISR to debug my coding. It is working pretty much OK. I'm not sure if this could cause some problems.

But, because I don't have a complete understanding of how twi works, I'm trying to understand things now as displaying the content that is going in the ISR.

I think the initialize is working ok, but the read procedure may not as it should be.

Here's my code, for application code in the Arduino IDE, and the code in the library.

Arduino IDE code:

```
#include "twi.h"
////////////////////////////////////////////////////////////////////////////
// HMC5883L
#define HMC5883L                    0x1E
#define CONFIG_REG_A                0x00  //Read/Write
#define CONFIG_REG_B                0x01  //Read/Write
#define MODE_REGISTER               0x02  //Read/Write
#define DATA_OUTPUT_X_MSB_REGISTER  0x03  //Read
#define DATA_OUTPUT_X_LSB_REGISTER  0x04  //Read
#define DATA_OUTPUT_Z_MSB_REGISTER  0x05  //Read
#define DATA_OUTPUT_Z_LSB_REGISTER  0x06  //Read
#define DATA_OUTPUT_Y_MSB_REGISTER  0x07  //Read
#define DATA_OUTPUT_Y_LSB_REGISTER  0x08  //Read
#define STATUS_REGISTER             0x09  //Read
#define IDENTIFICATION_REGISTER_A   0x10  //Read
#define IDENTIFICATION_REGISTER_B   0x11  //Read
#define IDENTIFICATION_REGISTER_C   0x12  //Read
#define DECLINATION_ANGLE 3.46

void hmc5883l_init(void);
void init_read(void);
void hmc5883l_print_serial(void);

void setup() {
  Serial.begin(9600);
  twi_init();
  hmc5883l_init();
  init_read();
}

void loop() {
  hmc5883l_print_serial();
}

void hmc5883l_init(void){
  uint8_t err,HMC5883L_ini[] = {CONFIG_REG_A,0x78,0x20,0x00};//
    err = twi_writeTo(HMC5883L,HMC5883L_ini,4,1,1);
    if(err != 0){Serial.print("error of init is");Serial.println(err);}
    Serial.println();
}

void init_read(void){
    uint8_t err,len,dat[3];
    err = twi_writeTo(HMC5883L,0x00,1,0,1);
    if(err != 0){Serial.print("error of init is");Serial.println(err);}
    Serial.println();

    len = twi_readFrom(HMC5883L,dat,3,1);
    Serial.print("length of read op:              ");
    Serial.println(len);
    Serial.println();

    Serial.print("config settings:                ");
    Serial.print(dat[0],HEX);Serial.print("\t");
    Serial.print(dat[1],HEX);Serial.print("\t");
    Serial.println(dat[2],HEX);
}

void hmc5883l_print_serial(void){
  int16_t x,z,y;
  uint8_t data[6],len,err, dst_reg[] = {0x03};
  float heading,heading_in_degrees,declination_angle_YANBU;

  err = twi_writeTo(HMC5883L,dst_reg,1,0,1);
  if(err != 0){Serial.print("error of init is");Serial.println(err);}
  Serial.println();

  len = twi_readFrom(HMC5883L,data,6,1);
  Serial.print("len is: ");Serial.println(len);
  x = data[0] << 8 | data[1];
  z = data[2] << 8 | data[3];
  y = data[4] << 8 | data[5];

  heading = atan2(y,x);
  declination_angle_YANBU = ((3.0 + (52.0 / 60.0)) / (180 / M_PI));  // in yanbu city it's
  heading += declination_angle_YANBU;

  if (heading < 0){heading += 2 * PI;}
  if (heading > 2 * PI){heading -= 2 * PI;}

  heading_in_degrees = heading * 180 / M_PI;
  Serial.println(heading_in_degrees);

  //Serial.print("x-axis\t");Serial.print("z-axis\t");Serial.println("y-axis");
  Serial.print(x);Serial.print("\t");
  Serial.print(z);Serial.print("\t");
  Serial.println(y);
}

```

And this is the core library:

In this part, I've put Serial.prints inside the ISR cases to display what's going from the start of the tx/rx buffers. Also, I've cut the slave half of the code because it's not necessary in this problem, as I'm only dealing with HMC5883L as a slave and I'm the master.

```
#include <math.h>
#include <stdlib.h>
#include <inttypes.h>
#include <avr/io.h>
#include <avr/interrupt.h>
#include <compat/twi.h>
#include "Arduino.h" // for digitalWrite

#ifndef cbi
#define cbi(sfr, bit) (_SFR_BYTE(sfr) &= ~_BV(bit))
#endif

#ifndef sbi
#define sbi(sfr, bit) (_SFR_BYTE(sfr) |= _BV(bit))
#endif

#include "pins_arduino.h"
#include "twi.h"

static volatile uint8_t twi_state;
static volatile uint8_t twi_slarw;
static volatile uint8_t twi_sendStop;           // should the transaction end with a stop
static volatile uint8_t twi_inRepStart;         // in the middle of a repeated start

static void (*twi_onSlaveTransmit)(void);
static void (*twi_onSlaveReceive)(uint8_t*, int);

static uint8_t twi_masterBuffer[TWI_BUFFER_LENGTH];
static volatile uint8_t twi_masterBufferIndex;
static volatile uint8_t twi_masterBufferLength;

static uint8_t twi_txBuffer[TWI_BUFFER_LENGTH];
static volatile uint8_t twi_txBufferIndex;
static volatile uint8_t twi_txBufferLength;

static uint8_t twi_rxBuffer[TWI_BUFFER_LENGTH];
static volatile uint8_t twi_rxBufferIndex;

static volatile uint8_t twi_error;

void twi_init(void)
{
  // initialize state
  twi_state = TWI_READY;
  twi_sendStop = true;      // default value
  twi_inRepStart = false;

  // activate internal pullups for twi.
  digitalWrite(SDA, 1);
  digitalWrite(SCL, 1);

  // initialize twi prescaler and bit rate
  cbi(TWSR, TWPS0);
  cbi(TWSR, TWPS1);
  TWBR = ((F_CPU / TWI_FREQ) - 16) / 2;

  // enable twi module, acks, and twi interrupt
  TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWEA);
}

void twi_disable(void)
{
  // disable twi module, acks, and twi interrupt
  TWCR &= ~(_BV(TWEN) | _BV(TWIE) | _BV(TWEA));

  // deactivate internal pullups for twi.
  digitalWrite(SDA, 0);
  digitalWrite(SCL, 0);
}

uint8_t twi_readFrom(uint8_t address, uint8_t* data, uint8_t length, uint8_t sendStop)
{
  uint8_t i;

  // ensure data will fit into buffer
  if(TWI_BUFFER_LENGTH < length){
    return 0;
  }

  // wait until twi is ready, become master receiver
  while(TWI_READY != twi_state){
    continue;
  }
  twi_state = TWI_MRX;
  twi_sendStop = sendStop;
  // reset error state (0xFF.. no error occured)
  twi_error = 0xFF;

  // initialize buffer iteration vars
  twi_masterBufferIndex = 0;
  twi_masterBufferLength = length-1;  // This is not intuitive, read on...

  twi_slarw = TW_READ;
  twi_slarw |= address << 1;

  if (true == twi_inRepStart) {
    twi_inRepStart = false;         // remember, we're dealing with an ASYNC ISR
    do {
      TWDR = twi_slarw;
    } while(TWCR & _BV(TWWC));
    TWCR = _BV(TWINT) | _BV(TWEA) | _BV(TWEN) | _BV(TWIE);  // enable INTs, but not START
  }
  else
    // send start condition
    TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWEA) | _BV(TWINT) | _BV(TWSTA);

  // wait for read operation to complete
  while(TWI_MRX == twi_state){
    continue;
  }

  if (twi_masterBufferIndex < length)
    length = twi_masterBufferIndex;

  // copy twi buffer to data
  for(i = 0; i < length; ++i){
    data[i] = twi_masterBuffer[i];
  }

  return length;
}

uint8_t twi_writeTo(uint8_t address, uint8_t* data, uint8_t length, uint8_t wait, uint8_t sendStop)
{
  uint8_t i;

  // ensure data will fit into buffer
  if(TWI_BUFFER_LENGTH < length){
    return 1;
  }

  // wait until twi is ready, become master transmitter
  while(TWI_READY != twi_state){
    continue;
  }
  twi_state = TWI_MTX;
  twi_sendStop = sendStop;
  // reset error state (0xFF.. no error occured)
  twi_error = 0xFF;

  // initialize buffer iteration vars
  twi_masterBufferIndex = 0;
  twi_masterBufferLength = length;

  // copy data to twi buffer
  for(i = 0; i < length; ++i){
    twi_masterBuffer[i] = data[i];
  }

  // build sla+w, slave device address + w bit
  twi_slarw = TW_WRITE;
  twi_slarw |= address << 1;

  // if we're in a repeated start, then we've already sent the START
  // in the ISR. Don't do it again.
  //
  if (true == twi_inRepStart) {
    // if we're in the repeated start state, then we've already sent the start,
    // (@@@ we hope), and the TWI statemachine is just waiting for the address byte.
    // We need to remove ourselves from the repeated start state before we enable interrupts,
    // since the ISR is ASYNC, and we could get confused if we hit the ISR before cleaning
    // up. Also, don't enable the START interrupt. There may be one pending from the
    // repeated start that we sent outselves, and that would really confuse things.
    twi_inRepStart = false;         // remember, we're dealing with an ASYNC ISR
    do {
      TWDR = twi_slarw;
    } while(TWCR & _BV(TWWC));
    TWCR = _BV(TWINT) | _BV(TWEA) | _BV(TWEN) | _BV(TWIE);  // enable INTs, but not START
  }
  else
    // send start condition
    TWCR = _BV(TWINT) | _BV(TWEA) | _BV(TWEN) | _BV(TWIE) | _BV(TWSTA); // enable INTs

  // wait for write operation to complete
  while(wait && (TWI_MTX == twi_state)){
    continue;
  }

  if (twi_error == 0xFF)
    return 0;   // success
  else if (twi_error == TW_MT_SLA_NACK)
    return 2;   // error: address send, nack received
  else if (twi_error == TW_MT_DATA_NACK)
    return 3;   // error: data send, nack received
  else
    return 4;   // other twi error
}

void twi_reply(uint8_t ack)
{
  if(ack){
    TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWINT) | _BV(TWEA);
  }else{
      TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWINT);
  }
}

void twi_stop(void)
{
  // send stop condition
  TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWEA) | _BV(TWINT) | _BV(TWSTO);

  while(TWCR & _BV(TWSTO)){
    continue;
  }

  // update twi state
  twi_state = TWI_READY;
}

/*
 * Function twi_releaseBus
 * Desc     releases bus control
 * Input    none
 * Output   none
 */
void twi_releaseBus(void)
{
  // release bus
  TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWEA) | _BV(TWINT);

  // update twi state
  twi_state = TWI_READY;
}

ISR(TWI_vect)
{
  switch(TW_STATUS){
    // All Master
    case TW_START:     // sent start condition
    case TW_REP_START: // sent repeated start condition
      // copy device address and r/w bit to output register and ack
      TWDR = twi_slarw;
      Serial.print("mt add sent is:                 0x");
      Serial.println(twi_slarw, HEX);
      twi_reply(1);
      break;

    // Master Transmitter
    case TW_MT_SLA_ACK:  // slave receiver acked address
    case TW_MT_DATA_ACK: // slave receiver acked data
      // if there is data to send, send it, otherwise stop
      if(twi_masterBufferIndex < twi_masterBufferLength){
        // copy data to output register and ack
        Serial.print("mt byte transmitted no:         ");
        Serial.println(twi_masterBufferIndex);
        Serial.print("content of tx byte:             0x");
        Serial.println(twi_masterBuffer[twi_masterBufferIndex], HEX);
        TWDR = twi_masterBuffer[twi_masterBufferIndex++];
        twi_reply(1);
      }else{
    if (twi_sendStop){
        Serial.println("mt stop");
        twi_stop();
    }

    else {
      Serial.println("mt repst");
      twi_inRepStart = true;    // we're gonna send the START
      TWCR = _BV(TWINT) | _BV(TWSTA)| _BV(TWEN) ;
      twi_state = TWI_READY;
    }
      }
      break;
    case TW_MT_SLA_NACK:  // address sent, nack received
    Serial.println("mt add sent nack");
      twi_error = TW_MT_SLA_NACK;
      twi_stop();
      break;
    case TW_MT_DATA_NACK: // data sent, nack received
      twi_error = TW_MT_DATA_NACK;
      twi_stop();
      break;
    case TW_MT_ARB_LOST: // lost bus arbitration
      twi_error = TW_MT_ARB_LOST;
      twi_releaseBus();
      break;

    // Master Receiver
    case TW_MR_DATA_ACK: // data received, ack sent
      // put byte into buffer
        Serial.print("mr byte received no:            ");
        Serial.println(twi_masterBufferIndex);
        Serial.print("content of rx byte:             0x");
        Serial.println(twi_masterBuffer[twi_masterBufferIndex], HEX);
      twi_masterBuffer[twi_masterBufferIndex++] = TWDR;
    case TW_MR_SLA_ACK:  // address sent, ack received
      // ack if more bytes are expected, otherwise nack
      if(twi_masterBufferIndex < twi_masterBufferLength){
        twi_reply(1);
      }else{
        twi_reply(0);
      }
      break;
    case TW_MR_DATA_NACK: // data received, nack sent
      // put final byte into buffer
        Serial.print("mr last received byte:          ");
        Serial.println(twi_masterBufferIndex);
        Serial.print("content of last rx byte:        0x");
        Serial.println(twi_masterBuffer[twi_masterBufferIndex], HEX);
      twi_masterBuffer[twi_masterBufferIndex++] = TWDR;
    if (twi_sendStop)
          twi_stop();
    else {
      twi_inRepStart = true;
      TWCR = _BV(TWINT) | _BV(TWSTA)| _BV(TWEN) ;
      twi_state = TWI_READY;
    }
    break;
    case TW_MR_SLA_NACK:
      twi_stop();
      break;
}

```

**The problem now is:**

I get these readings on the Arduino serial monitor. Note: I've wrote my notes on each section.

```
// initialization
// I think this process is done just fine, the exact bytes are sent
// but each time I open the serial monitor I get like garbage at the first
// of the window, like this flipped question mark I get it most the time
// Is there something like flush function to clear things?
⸮mt add sent is:                 0x3C
mt byte transmitted no:         0
content of tx byte:             0x0
mt byte transmitted no:         1
content of tx byte:             0x78
mt byte transmitted no:         2
content of tx byte:             0x20
mt byte transmitted no:         3
content of tx byte:             0x0
mt stop

// writing target register which is 0x00, but I get 0xA3 ??!
m
mt byte transmitted no:         0
content of tx byte:             0xA3
mt stop

// Here requesting the 6 bytes data, I send read of HMC5883L which is 0x3D
// but 1st byte should be 0x78 then 2nd should be 0x20, 3rd 0x00
// but the result is different ! it's like they are shifted somehow

// At the end I'm trying to read back the passed array to the function, but
// I get 0s!!
mt add sent is:                 0x3D
mr byte received no:            0
content of rx byte:             0xA3
mr byte received no:            1
content of rx byte:             0x78
mr last received byte:          2
content of last rx byte:        0x20
length of read op:              3

config settings:                0   0   0

```

# Answer
The second parameter to `twi_writeTo` should be a pointer to a buffer. You have now

```
twi_writeTo(HMC5883L,0x00,1,0,1);

```

which sends a byte read at address 0x00. change it to

```
uint8_t b = 0x00;
twi_writeTo(HMC5883L,&b,1,0,1);

```

(C arrays are a pointer to first item)
> 1 votes

---
Tags: programming, i2c, c, wire-library
---


# Question
Title: Passing variables for a PID in an interrupt
I'm needing to pass variables from my timerIsr() function to my loop() function. I have little experience with the Arduino language, I'm mostly familiar with Python so this has been quite difficult for me.

Essentially I'm creating a PID controller to maintain RPM of a fan motor if friction is applied to it. I'm implementing the PID control in the loop() function but I need the rotation variable information from my timerIsr() function. I've tried to return the variable info but it doesn't match up to the actual fan speed. I think it has something to do with difference delay/timer times operating at different instances but I'm unsure.

Here's what I have so far

```
#include "TimerOne.h"
#include <PID_v1.h>

int counter=0;

const int IN1 = 11;
const int IN2 = 10;
volatile float pot=0;
const int POT = 0;
const int ENA = 6;

double Setpoint, Input, Output;
double Kp=2, Ki=5, Kd=1;

PID myPID(&Input, &Output, &Setpoint, Kp, Ki, Kd, DIRECT);

void docount()  // counts from the speed sensor
{
  counter++;  // increase +1 the counter value
}

void timerIsr()
{
  Timer1.detachInterrupt();  //stop the timer
  Serial.print("Motor Speed: ");
  int rotation = (counter / 30);  // divide by number of holes in Disc
  Serial.print(rotation,DEC);
  Serial.println(" Rotation per second");
  counter=0;  //  reset counter to zero
  Timer1.attachInterrupt( timerIsr );  //enable the timer
  Serial.print("pot = ");
  Serial.print(pot);
  Serial.print("\n");

  //return rotation;
}

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

  pinMode(IN1, OUTPUT);
  pinMode(IN2, OUTPUT);

  Timer1.initialize(1000000); // set timer for 1sec
  attachInterrupt(0, docount, FALLING);  // increase counter when speed sensor pin goes High
  Timer1.attachInterrupt( timerIsr ); // enable the timer

  myPID.SetMode(AUTOMATIC);
}

void loop()
{
  //Input = timerIsr();
  pot=analogRead(POT)/4.01569;
  //Setpoint = sp;

  //Serial.print(Input);

  analogWrite(ENA, pot);
  digitalWrite(10, HIGH);  // set rotation of motor to Clockwise
  digitalWrite(11, LOW);

  delay (250);
}

```

As you can see I've commented some stuff out that's related to the PID library. Right now I'm just trying to pass the rotation variable to the loop() function.

Is it possible to update global variables at different times so any function can access them?

# Answer
> 2 votes
Short answer: Yes, it is possible to update global variables from interrupt routines, but it comes also with problems.

Long answer:

First you have to understand, how interrupts work. You are using a timer interrupt and an external (pin) interrupt. The compiled program lies in the flash of the chip. At the start there are some special addresses for the different interrupts. If the hardware then registers a condition for an interrupt, it will stop the execution of the main code (the code, that was executed, when the interrupt condition occured), saving the current state and jumping to the corresponding address, where it get's send to the ISR (interrupt service routine), that you defined (in your case the function `docount()`). After the execution of this program the microcontroller will return to the execution of the main code (by restoring the previously saved state and jumping there). An ISR can only have a return type of `void` (no return value), because when it returns, there is no special code to receive and use this value. The interrupt may occur at different times every time.

Instead it is common to write global variables in the ISR. For this you have to consider some points:

1. Global variables, that may be changed during an ISR, has to be declared (additionally to the type) as `volatile`. This means, that the compiler cannot optimize this variable (for example to a local variable) and has to consider, that it may change anytime, so that he cannot use a cached value.
2. The usage of the variable in the main code has to be atomic or secured against changing of the variable. If you use a variable in a calculation, it may take many cycles for it (especially if you have a big datatype or some expensive calculations as with `float`). If the interrupt occures in this time, the value might be changed in the middle of calculation, making the result a bunch of garbage. If the calculation only takes 1 statement cycle, is cannot be interrupted and is called atomic. Since this is rarely possible, you can enclose the corresponding code into securing code. For the Arduino platform, you can use the `noInterrupts()` and `interrupts()` functions, to turn off all interrupts, do the calculation and turning the interrupts on again. Be sure do turn the interrupts off only for a short time, so that you don't miss interrupts. Often this is only used to copy the variables value into a local variable (local working copy), which then can safely used for calculations, while the global variable may still change.

Besides that, you also have to think about, what code you write into an ISR. An ISR cannot be interrupted by another interrupt. So functions, that depend on interrupts to work, will not behave like intended. The `delay()` function for example will simply block all code execution, since the return of the `millis()` function will not change (it depends on the timer0 interrupt). In your Timer1 ISR, you use `Serial.print()`. This function can be used, but only until the `Serial` libraries buffer is filled. The actual communication will take place, after the ISR returns, because it also depends on interrupts. When you try to send more, than fits in the buffer (64 bytes), you will loose data. Currently you should be below that, but you should have this in mind, when coding.

---

I don't think, that you really need a timer interrupt for calculating and outputting the data every second. Here I would use a non-blocking coding style in the `loop()` function, like you can see in the `BlinkWithoutDelay` example, that comes with the Arduino IDE. This is better than using `delay()`, which is just busy waiting. You save a timestamp with the `millis()` function and check the time difference. That saves Timer1 for other purposes and also refactors your main code for being extendable and non-blocking, if you want to add more functions.

---

As I read from this example from the PID library, you need to call `myPID.Compute()` once in a while to do the PID calculations with the new values. Since these only change every second, you should call this function directly after the calculation of `Input`.

---

All in all you need something like this (I didn't include all the code, just the important part, so that you should be able to understand the principle):

```
unsigned long timestamp;
#define INTERVAL 1000

void loop(){
    if(millis() - timestamp >= INTERVAL){
        timestamp += INTERVAL;
        noInterrupts();
        int counter_copy = counter;
        interrupts();
        // Do the calculations with counter_copy and same the result to `Input`
        // You can put the code from your timerisr here (without the Timer1 code)
        myPID.Compute();
    }
}

```

Your `pot` code then should also be enclosed in such an if statement, to prevent, that the PWM get's restarted again and again very fast. If a reaction time of 1s is ok for you, you can put this code in the if statement above. If you want faster reaction times, you can add a second if statement like this to the `loop()` function (including it's own global timestamp variable and interval value).

The `digitalWrite()` calls for the direction can be put into the setup, since they don't ever change in your code.

---
Tags: interrupt, loop, pid
---


# Question
Title: Is new.cpp programmed improperly? Arduino 1.8.9
I'm having trouble with my code and I'm not sure if it's a memory allocation issue. So I look at the new, delete to see if it throws errors, and finding the source code I find outrageously simple codes. So simple, I think it can't be right.

```
#include <stdlib.h>

void *operator new(size_t size) {
  return malloc(size);
}

void *operator new[](size_t size) {
  return malloc(size);
}

void operator delete(void * ptr) {
  free(ptr);
}

void operator delete[](void * ptr) {
  free(ptr);
}

```

Does this mean if I call `customClass *ptr = new customClass[10];` it allocates only 10 bytes instead of `sizeof(customClass)*10`?

# Answer
> 1 votes
http://www.cplusplus.com/reference/new/operator%20new\[\]/:

> in C++, new\[\] is an operator with a very specific behavior: An expression with the new operator on an array type, first calls function operator new (i.e., this function) with the size of its array type specifier as first argument (plus any array overhead storage to keep track of the size, if any), and if this is successful, it then automatically initializes or constructs every object in the array (if needed). Finally, the expression evaluates as a pointer to the appropriate type pointing to the first element of the array.

---
Tags: programming, c++, array, memory-usage
---


# Question
Title: is PIN To PIN matching mcu against Atmega328P-AU available?
I want to upgrade my product which is based on Atmega328p-AU, having the problem of programming memory. I don't want to change the PCB of the product. Is PIN To PIN matching MCU against Atmega328P-AU available?

# Answer
The only other AVR chip with more program memory in the 32/TQFP form factor is the ATMEGA4808 at 48 kB.

Unfortunately, the pinout is not the same compared to the ATMEGA328P-AU:

ATMEGAx8P family datasheet

ATMEGAx08 family datasheet
> 2 votes

---
Tags: arduino-uno, memory
---


title: Arduino uno holder

text:
# Question
Title: Arduino uno holder
Arduino sells a holder for the UNO board, but without much documentation or detailed specifications, see this link. Can anyone give the diameter of four small holes, two located on the top edge and one each on the left/right edges? What size of screw will fit? They are smaller than M3 / 4-40 apparently.

Also, does anyone know what material is the holder made from?

# Answer
> 1 votes
\** Self answer:

I obtained several of these holders from Arduino starter kits. They are made from a clear, colorless plastic that seems to have been injection molded. However, it is hard to tell exactly which plastic, since these does not have any recycle logo! The image posted in the original question is perhaps a newer version.

The four smaller holes can accept M2.5 screws, I checked.

# Answer
> 1 votes
Arduino UNO holes are just over 3mm in diameter. Both 4-40 and M3 bolts will work well, giving you a bit of wiggle room. You will have to file down the width of the bolt head to fit against the 6 pin header near D13.

As far as the holder material, I don't know. I 3D print my own.

---
Tags: arduino-uno
---


# Question
Title: How many Amps can a Nano Arduino hold for LED project
I'm really new at this, and here is my doubt. What if I need to light 120x WS2812B (5v)LEDs (link: LEDs) using an Arduino Nano? if it takes 60 mAh each pixel, the total amount needed should be around 7,200 mA.

Could I use the same 5V/ 8A power supply (PowerSupply) for the Nano board and lights? Is that possible?

Thanks in advance, and sorry my ignorance on this area.

# Answer
> 0 votes
Yes, 120 LEDs * 60 mA = 7200 mA = 7.2A

An Arduino Nano will use 19 mA (Arduino Nano Tech Spec). Of course, if you add a power LED, or other components it will add, but it will likely be less than a few 100 mA. So that totals to max 7.4A.

It's always good to have some headroom which is 0.6A in your case (that's enough).

Actually what's happening is as follows: \- Your 8 mA gives the current the components request \- Your Nano requests 19 mA \- Your LEDs require 7.200 mA.

As long as the voltage is the same (5V for both the LEDs, Nano, and adapter), and the components do not request more than 8 A summed up (with some headroom), the adapter will deliver the current needed. If all components request more than 8 A, than high likely the adapter will break (and possibly the attached components too).

# Answer
> 0 votes
It can supply both, *as long as they are supplied separately*; the LEDs must not be supplied through the Nano board, but connected directly from the power supply.

---
Tags: arduino-nano, led, current
---


# Question
Title: Arduino - "expected primary-expression before '.' token" Error
```
#include "Ultrasonic.h"
#include <Wire.h>
#include <LiquidCrystal_I2C.h>

// Set the LCD address to 0x27 for a 16 chars and 2 line display
LiquidCrystal_I2C lcd(0x27, 16, 2);

void setup() {
  // put your setup code here, to run once:
  lcd.begin();
  Serial.begin(9600);
}
Ultrasonic ultrasonic(11, 12); //Ultrasonic ultrasonic(Trig,Echo);
void loop()
{
  int a = (Ultrasonic.Ranging(CM));
  if (a >= 15 && a < 20)
  { Serial.println("guvenli");
    lcd.print("guvenli");
    delay(500);
    lcd.clear();
    tone(3, 2000, 100);
    delay(500);
    noTone(3);
  }
  if (a >= 10 && a < 15) {
    Serial.println("guvenli dikkat");
    lcd.print("guvenli dikkat");
    delay(500);
    lcd.clear();
    tone(3, 2000, 50);
    delay(250);
    noTone(3);
  }
  if (a < 5)
  {
    Serial.println("vurdun");
    lcd.print("vurdun");
    delay(500);
    lcd.clear();**uıhhf
    tone(3, 2000, 50);
    delay(50);
    noTone(3);
  }
}

```

In this code i'm getting an error like this:

```
   C:\Users\*\AppData\Local\Temp\arduino_modified_sketch_113625\sketch_apr29a.ino: In function 'void loop()':

sketch_apr29a:19:22: error: expected primary-expression before '.' token

   int a = (Ultrasonic.Ranging(CM));

                      ^

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

```

# Answer
> 2 votes
`Ultrasonic` is a class name. Why are you trying to use it before a `.` in an expression?

Judging by the declaration, you need `ultrasonic`. That is your object name. `ultrasonic`, not `Ultrasonic`.

---
Tags: error
---


# Question
Title: Implement Visible Light communication using Arduino
I want to implement a simple VLC based communication system using two Arduinos and send messages/data/files between two PCs. For that I have a simple transmitter circuit with an LED on Tx side and a photo-transistor on the receiver side. The codes im using for transmission and reception are attached below, also the circuit image is attached below, but im unable to bring about any communication between the two PCs, the transmitter side works fine as the LED flickers indicating data is being transferred, but its not being received by the photo transistor. I don't know what im doing wrong. Any help would be appreciated, I am doing this as a part of my academics. Transmitter Code :

```
void setup()
{
  pinMode(9, OUTPUT);
  pinMode(10, OUTPUT);

  // Clear Timer on Compare Match (CTC) Mode
  bitWrite(TCCR1A, WGM10, 0);
  bitWrite(TCCR1A, WGM11, 0);
  bitWrite(TCCR1B, WGM12, 1);
  bitWrite(TCCR1B, WGM13, 0);

  // Toggle OC1A and OC1B on Compare Match.
  bitWrite(TCCR1A, COM1A0, 1);
  bitWrite(TCCR1A, COM1A1, 0);
  bitWrite(TCCR1A, COM1B0, 1);
  bitWrite(TCCR1A, COM1B1, 0);

  // No prescaling
  bitWrite(TCCR1B, CS10, 1);
  bitWrite(TCCR1B, CS11, 0);
  bitWrite(TCCR1B, CS12, 0);

  OCR1A = 210;
  OCR1B = 210;

  Serial.begin(2400);
}

void loop()
{
  Serial.println("testing testing testing");
  delay(500);
}

```

Receiver Code:

```
void setup()
{
  Serial.begin(2400);
  pinMode(13, OUTPUT);
}

void loop()
{
  // if incoming serial
  if (Serial.available()) {
    readSerial();
    digitalWrite(13, HIGH);
  }
  else {
    digitalWrite(13, LOW);
  }
  delay(500);
}
void readSerial() {
  char val = Serial.read();
  Serial.print(val);
}

```

the transmitter works fine, but the receiver is not receiving anything, I don't know what i'm doing wrong.

# Answer
> 1 votes
The amplitude of the signal at the photodetector is small. Better use ADC for reading.

# Answer
> 1 votes
I think you have problem with your hardware side. I would like to suggest a few things; maybe it will work.

**Transmitter**

Instead of a normal LED use an IR LED because it has advantages over normal led for transmission of data like it is more secure, support max transmission speed, less power consumption, and much more. For transmitter of signal use the following circuit. Ihave used TSOP1738 for receiver, so we need to generate the modulated IR of 38 kHz. You can use any TSOP, but you need to generate IR of respective frequency as TSOP. So using 555 timer in Astable mode to oscillate the IR at 38KHz frequency. As we know oscillation frequency of 555 timer is decided by resistor R1, R2 and capacitor C1. We have used a 1k R1, 20K R2 and 1nF capacitor to generate a frequency of approx. 38 KHz. It can be calculated using this formula: 1.44/((R1+2\*R2)\*C1)

and instead of a push button you can use a transistor or mosfet as switch, which will be controlled with a controller.

**Receiver**

I don't know which phototransistor you are using but I'll suggest to use a **TSOP17XX**. TSOP17XX receives the modulated Infrared waves and changes its output. TSOP is available in many frequency ranges like TSOP1730, TSOP1738, TSOP1740 etc. The last two digits represent the frequency (in Khz) of modulated IR rays, on which TSOP responds. Like for example TSOP1738 reacts when it receives the IR radiation modulated at 38Khz. Means it detects the IR which is switching On and Off at the rate of 38Khz. TSOP’s output is active low, means its output is remains HIGH when there is no IR, and becomes low when it detects IR radiation. TSOP operates on particular frequency so that other IRs in the environment can’t interfere, except the modulated IR of particular frequency.

To receive the data here is some simple circuitry:

Instead of LED connect that pin to your receiver controller; you will get the signal properly. Hope this works for you.

Please try to perform our experiment in a noiseless (IR free) environment to get the correct output.

Reference: https://circuitdigest.com/electronic-circuits/ir-transmitter-and-receiver-circuit

# Answer
> 0 votes
Your receiver(ldr) might not be accurate enough, rather try using an led as a receiver as well. You will just need to boost the signal then with something like a 1Mohm resistor in parallel with the receiving led.

You can use something like this as well, haven't tried it but it looks like it will work: http://www.instructables.com/id/Arduino-Communication/ maybe just a 1Mohm resistor instead of the 1Kohm one

---
Tags: arduino-uno, programming, led, communication, sketch
---


title: Arduino keeps looping

text:
# Question
Title: Arduino keeps looping
I made a program where I give a number(4 bit) as input and four led on the breadboard lights up according to its binary. The problem is the program works all well only for (2-15) but if I give 0 or 1 as input it keeps looping and the serial monitor keeps printing that number. If I remove the "**prbline**" from the code the program works but the serial monitor only prints the input number if it is 0 or 1. Why is it like this?

```
#include<stdlib.h>
#include<string.h>
int red1=2;
int red2=3;
int red3=4;
int red4=5;
int num=1; // this is the input number
char number[4];
int len;
char str3[]="000",str2[]="00",str1[]="0",str[]="0000";

void setup() {
  // put your setup code here, to run once:
  pinMode(red1,OUTPUT);
  pinMode(red2,OUTPUT);
  pinMode(red3,OUTPUT);
  pinMode(red4,OUTPUT);
  itoa (num,number,2);
  len=strlen(number);
  Serial.begin(9600);
  Serial.println(num);
  Serial.println(number);
  Serial.println(len);
  Serial.println(str);

  if(len==1){
    strcat(str3,number);
    strcpy(str,str3);
    }
  else if(len==2){
    strcat(str2,number);
    strcpy(str,str2);
    }
  else if(len==3){
    strcat(str1,number);
    strcpy(str,str1);
    }
  else {
    strcpy(str,number);
    }
  Serial.println(str); //prbline

}

void loop() {
  // put your main code here, to run repeatedly:
  if(str[0]=='1'){
    digitalWrite(red1,HIGH);
    }
  if(str[1]=='1'){
    digitalWrite(red2,HIGH);
    }
  if(str[2]=='1'){
    digitalWrite(red3,HIGH);
    }
  if(str[3]=='1'){
    digitalWrite(red4,HIGH);
    }

}

```

# Answer
> 1 votes
So many mistakes in such a short code:

* number is too short for more than 3 bit numbers (8 and higher)
* strcat is modifying first string, so all strings str1, str2, str3 are too short too
* if you want to use them more than once, it'l be adding string to them over and over.....

Basically, if you can see output from the setup over and over, it means crash and start from the reset vector.

But, the main question is why don't you use bit manipulation on num directly:

```
  digitalWrite(red1, (num & 0b1000) != 0 );
  digitalWrite(red2, (num & 0b0100) != 0 );
  digitalWrite(red3, (num & 0b0010) != 0 );
  digitalWrite(red4, (num & 0b0001) != 0 );

```

Or with using bit positions:

```
  digitalWrite(red1, (num & (1 << 3)) != 0 );
  digitalWrite(red2, (num & (1 << 2)) != 0 );
  digitalWrite(red3, (num & (1 << 1)) != 0 );
  digitalWrite(red4, (num & (1 << 0)) != 0 );

```

Bit positions little bit more readable by using macro `_BV` (which is translated to 1 \<\< ..)

```
  digitalWrite(red1, (num & _BV(3)) != 0 );
  digitalWrite(red2, (num & _BV(2)) != 0 );
  digitalWrite(red3, (num & _BV(1)) != 0 );
  digitalWrite(red4, (num & _BV(0)) != 0 );

```

or more interesting macro wrapper `bit_is_set` to be more readable:

```
  digitalWrite(red1, bit_is_set(num,3));
  digitalWrite(red2, bit_is_set(num,2));
  digitalWrite(red3, bit_is_set(num,1));
  digitalWrite(red4, bit_is_set(num,0));

```

And, as a bonus, it can be even done in a loop:

```
byte reds[] = { 5, 4, 3, 2 }; // to preserve the same order as in the question
byte num    = 1;

void loop() {
  byte tmp = num;
  for (byte pin : reds) {
    digitalWrite(pin, tmp & 1);
    tmp >>= 1; // bit shift by one to the right (= division by 2)
  }
}

```

# Answer
> 1 votes
To add to KIIV's concise response, the line

```
Serial.println(str); //prbline

```

can be easiest created without itoa and leading zero helper strings by

```
int num = 9; // Test input 0 .. 9 ( or even 15 = 0x0F )
void setup() {
 char str[] = "0000";
 byte tmp = num & 0x0F; // limit to valid values
 for (byte i=3; tmp != 0; i--, tmp >>= 1)
   if (tmp & 0x01) str[i] = '1';
Serial.begin(9600);
Serial.print(num);
Serial.print(" = ");
Serial.println(str);
}

```

# Answer
> 0 votes
You are overwriting memory.

```
 if(len==1){
    strcat(str3,number);
    strcpy(str,str3);
    }

```

There is room for 3 characters in str3, however you are using strcat to add more characters.

I don't understand your technique, however this might help make it work:

```
char str3[6]="000",str2[6]="00",str1[6]="0",str[6]="0000";

```

---
Tags: serial, arduino-mega, programming, arduino-ide
---


# Question
Title: Firmware gets stuck at obj.printto(client) in esp32
I am using an ESP32 to capture some data and then sending it over using ArduinoJson. However, sometimes, the firmware gets stuck at the line where it is transmitting data at obj.printTo(client). I have the logs for the same. Do you have any idea as to what might be making it freeze? And any way to avoid it in the future.

Logs:

12:28:00.584 -\> \[V\]\[ssl\_client.cpp:276\] send\_ssl\_data(): Writing HTTP request...

12:28:00.584 -\> \[V\]\[ssl\_client.cpp:276\] send\_ssl\_data(): Writing HTTP request...
12:47:11.229 -\> \[E\]\[ssl\_client.cpp:33\] handle\_error(): UNKNOWN ERROR CODE (004E) 12:47:11.229 -\> \[E\]\[ssl\_client.cpp:35\] handle\_error(): MbedTLS message code:-78

12:47:11.229 -\> \[V\]\[ssl\_client.cpp:245\] stop\_ssl\_socket(): Cleaning SSL connection.
12:47:11.229 -\> request sent
12:47:12.217 -\> esp32/Arduino CI has failed
12:47:12.217 -\> reply was: 12:47:12.217-\> ==========
12:47:12.217 -\>
12:47:12.217 -\> ==========
12:47:12.217 -\> closing connection

The send code:

```
jsonBuffer.clear();
JsonObject &rootObject = jsonBuffer.createObject();
JsonObject &dataObject = rootObject.createNestedObject("data");
JsonArray &X1dataObject = dataObject.createNestedArray("X1");
JsonArray &Y1dataObject = dataObject.createNestedArray("Y1");
JsonArray &Z1dataObject = dataObject.createNestedArray("Z1");
JsonArray &T1dataObject = dataObject.createNestedArray("T1");

vTaskDelay(10);

if (send_flag) {
  digitalWrite(2,0);
  send_flag = false;
  int connection_iterator = 0;
  int connection_iterator2 = 0;
  for (int iterator = 0; iterator < SAMPLE_SIZE; iterator++) {
    X1dataObject.add(X1dataArray[iterator]);
    Y1dataObject.add(Y1dataArray[iterator]);
    Z1dataObject.add(Z1dataArray[iterator]);
  }
  T1dataObject.add((float)(analogRead(NTC)*0.0244));

  rootObject["coreid"] = String(low, HEX) + String(high, HEX);
  //rootObject["coreid_high"] = String(high, HEX);
  rootObject["sample_time"] = int(time_taken);
  rootObject["firmware_version"] = FIRMWARE_UPDATE_VERSION;
  rootObject.prettyPrintTo(Serial);
  Serial.print("connecting to ");
  Serial.println(host);
  while ((!client.connect(host, httpsPort)) && !setup_mode) {
    connection_iterator++;
    Serial.println("connection failed! Retrying..");
    delay(5000);
    if (connection_iterator >= 10)
      ESP.restart();
  }
  if (client.verify(fingerprint, host)) {
    Serial.println("certificate matches");
  } else {
    Serial.println("certificate doesn't match");
  }
  digitalWrite(LED_BUILTIN, HIGH);
  Serial.print("requesting URL: ");
  Serial.println(url);
  client.println(String("POST ") + url + " HTTP/1.0");
  client.println(String("Host: ") + host);
  client.println("Cache-Control: no-cache");
  client.println("Content-Type: application/json");
  client.print("Content-Length: ");
  client.println(rootObject.measureLength());
  client.println();
  rootObject.printTo(client);
  Serial.println("NUMBER OF INTERRUPTS:");
  Serial.println(interruptCounter);
  Serial.println("request sent");
  while ((client.connected()) && !setup_mode) {
    connection_iterator2++;

    String line = client.readStringUntil('\n');
    if (line == "\r") {
      Serial.println("headers received");
      break;
    }
    Serial.println("Waiting for response");
    delay(500);
    if (connection_iterator2 >= 40)
      break;
  }
  String line = client.readStringUntil('\n');
  if (line.startsWith("{")) {
    Serial.println("esp32/Arduino CI successfull!");
  } else {
    Serial.println("esp32/Arduino CI has failed");
  }
  Serial.println("reply was:");
  Serial.println("==========");
  Serial.println(line);
  Serial.println("==========");
  Serial.println("closing connection");
  digitalWrite(LED_BUILTIN, LOW);
  // readRegister(INT_SOURCE, 1, &dummy_read);
}

```

# Answer
> 2 votes
I see that you are using SSL. SSL uses a lot of RAM and it is possible that the stack and the heap are colliding which will corrupt the running sketch. I recommend you add the amount of free heap to your log statements so that you can see how it changes, which will help you see if this is what is happening.

To obtain the free heap you can use esp\_get\_free\_heap\_size() - there's more documentation about this function in the espressif online documentation.

# Answer
> 0 votes
So I have found out that apparently there is some issue working with WiFiClientSecure to send large data packets. The secure line sends data in small packets which take up a lot of time and also if the server gets unavailable at any moment, the program will get stuck there. This problem, however, was not this prominent when I used the same mechanism in esp8266. Nevertheless, the solution would be to use a buffer to send the data.

Also, this version of code was written with ArduinoJson V5. But, even after migrating to ArduinoJson V6 the problem persists. It seems that whatever new JsonDocument feature has been implemented in the new version is still far from providing the efficiency of a buffer and it recoils back.

However still, if anyone else finds a better solution, please do update.

---
Tags: esp32, json
---


# Question
Title: error: invalid use of non-static member function attachInterrupt(0,count,RISING);
```
XRPM_COUNTERS.h:15:5: error: expected unqualified-id before string constant

     ISR(PCINT0_vect) {

     ^

In file included from C:\Documents and Settings\SAM\Desktop\automation_1_A_NEW_AAA\automation_1_A_NEW_AAA.ino:10:0:

XRPM_COUNTERS.h:72:1: error: expected ';' after class definition

 }

 ^

sketch\XRPM_COUNTERS.h: In function 'void XRPMLoop()':

XRPM_COUNTERS.h:77:19: error: 't' was not declared in this scope

   if ((millis() - t) > 300) rpm = 0;

                   ^

XRPM_COUNTERS.h:77:29: error: 'rpm' was not declared in this scope

   if ((millis() - t) > 300) rpm = 0;

                             ^

XRPM_COUNTERS.h:79:17: error: 'ot' was not declared in this scope

   else if (t != ot) {

                 ^

XRPM_COUNTERS.h:81:5: error: 'rpm' was not declared in this scope

     rpm = 60000.0 / (float)(t - ot);

     ^

XRPM_COUNTERS.h:87:13: error: 'rpm' was not declared in this scope

   lcd.print(rpm);

             ^

XRPM_COUNTERS.h:93:14: error: 'printVu' was not declared in this scope

   printVu(rpm);

              ^

sketch\XRPM_COUNTERS.h: At global scope:

XRPM_COUNTERS.h:97:1: error: expected declaration before '}' token

 };

 ^

exit status 1
expected unqualified-id before string constant

```

My source code

```
class XRPM_COUNTERS {

  private:
#include <Wire.h>  // Comes with Arduino IDE
#define interrupt_pin2 A8 //Define Analog Pin (analog pins are 16-21)

    volatile unsigned long t = 0;

    volatile unsigned long ot = 0;

    ISR(PCINT0_vect) {

      if (PINB & 1) {

        ot = t;

        t = millis();

      }

    }

    //actualizar o visor (aqui calibrado para um maximo de 3000 rpm, basta mudar o valor)

#define max_rpm 3000

    void printVu(int r) {

      int i = map(r, 0, max_rpm, 0, 20);

      for (int n = 0; n < 20; n++) {

        lcd.print((char)(n < i ? 255 : ' '));

      }

    }

  public:

    void XRPMSetup() {
      lcd.begin(16, 2);  // initialize the lcd for 20 chars 4 lines, turn on backlight

      lcd.print("RPM with PCINT");

      MCUCR = (1 << ISC01) | (1 << ISC00);

      PCICR |= (1 << PCIE0);

      PCMSK0 |= (1 << PCINT0);

      pinMode(interrupt_pin2, INPUT); //Make pin an input

      digitalWrite(interrupt_pin2, HIGH); //Enable pullup resistor on Analog Pin

      interrupts();

    }

    unsigned int rpm = 0;

}
void XRPMLoop() {

  //lcd.setCursor(0,3);lcd.print(millis()-t);lcd.print("     ");

  if ((millis() - t) > 300) rpm = 0;

  else if (t != ot) {

    rpm = 60000.0 / (float)(t - ot);

  }

  lcd.setCursor(0, 1);

  lcd.print(rpm);

  lcd.print(" rpms    ");

  lcd.setCursor(0, 2);

  printVu(rpm);

}

};
XRPM_COUNTERS XRPM;

```

# Answer
> 1 votes
You placed an `#include` directive inside a class definition. Don't place `#include` directives inside class definitions. (Unless you are including a file specifically designed for that purpose.)

`#include` directives for regular header files should normally reside somewhere at the top of your file, separately from any other declarations.

---
Tags: arduino-mega
---


# Question
Title: How to use a variable format in `sprintf`
How should I make a variable format sequence for sprintf?.

```
int i=2,d=9;
String sf;
sprintf(sf,"%%0%d",i);
fprintf(sf,d);

```

While expecting the output.

```
09

```

The compilation fails, with several errors, according the failing change I apply.

```
Invalid cast from type 'String' to type 'char*'

```

# Answer
1. `sprintf` cannot be used to write data into `String` objects. More precisely, it is possible to come up with a "hackish" way to write the result directly into a `String` object, but the latter is definitely not designed for such use.

The target buffer should be an array of `char`, not a `String`. Which is what the compiler is telling you.

```
char buffer[64];
sprintf(buffer, "%%0%d", i);

```

or better

```
char buffer[64];
snprintf(buffer, sizeof buffer, "%%0%d", i);

```
2. The format string you used in your `sprintf` will generate `%02` result (since `i` contains `2` at that moment). Why you are expecting `09` is not clear. Why are you expecting the `%` character to disappear is not clear either, considering that the format string seems to be deliberately designed to include it.
3. A `String` object cannot be used as the first parameter of `fprintf`. It is not clear what that `fprintf` is doing in your code.

---

Apparently you are trying to use `sprintf` to generate another format string at run time (using `i` as field width), which is later used to output the `d` variable. In that case that would be something like

```
char format[16];
snprintf(format, sizeof format, "%%0%dd", i);
fprintf(file, format, d);

```

That `fprintf` will indeed output `09`.
> 3 votes

---
Tags: printf
---


# Question
Title: Is there a simple (permissive license) Leonardo driver for a USB-to-USART bridge to substitute an FTDI chip?
I'm making an ESP32 development board and I'm thinking about putting an Arduino Leonardo chip between the USB port and the ESP32's USART pins to act as a USB/USART converter instead of the FTDI chip so that I can program the ESP32 through a USB serial port like any other Arduino board.

Is there a library/sketch licensed under a permissive license (MIT, BSD, Apache, etc.) which can make the Leonardo chip act as a HID Serial Port device which has a device name I want for easy identification in Device Manager and which requires no special driver installation in Windows and Linux once plugged into the computer?

Thank you for your time.

# Answer
Why not write your own?

First off, you'll want to create your own custom board definition. To do that, find the `boards.txt` file in the AVR core of your installation. Then find the block of entries that starts `leonardo.` and copy the whole block. Change the `leonardo` to a name of your choosing.

Then change the `.name` entry to give your board a new name in the IDE.

Finally look for the (renamed) entries:

```
leonardo.build.vid=0x2341
leonardo.build.pid=0x8036
leonardo.build.usb_product="Arduino Leonardo"

```

Of course the `leonardo` will be whatever you changed them to. You can now give your board a new VID and PID to uniquely identify them - and also change the `usb_product` to name your board.

You can also add a `myboard.build.usb_manufacturer="..."` entry to change the manufacturer from the default of Arduino.

Now you have a board definition that identifies your board as what you want it to be. So now just write a sketch that passes through the serial between USB and UART, and also handles the DTR and RTS signals to be able to enter flash mode on the ESP32 (hint: use `Serial.dtr()` and `Serial.rts()` to check the status of those signals).
> 1 votes

---
Tags: serial, usb, programmer
---


# Question
Title: NodeMCU run sensor code while listening for wifi input?
Is it possible to have code running while also listening for local inputs via ip address? I thought it would go in the 'while' portion but I presume that only responses when the ip is loaded.

```
void loop() {

  WiFiClient client = server.available();
  if (!client) {
    return;
  }
  while (!client.available()) {
    delay(1);
  }
  String query = client.readStringUntil('\r');
  client.flush();

  if (query.indexOf("/open") != -1)  {
    open_fast();
  } else if (query.indexOf("/close") != -1)  {
    close_fast();
  }

  sensor = analogRead(A0);
  sensor = map(sensor, 0, 1023, 0, full);

  Serial.print(sensor);
  Serial.print("  ");
  Serial.println(pos);

  if (sensor > pos) {
    open_slow();
    delay(1000);
  } else if (sensor < pos) {
    close_slow();
    delay(1000);
  }
  delay(100);

}

```

# Answer
> 0 votes
The problem is that at

```
while (!client.available()) {
  delay(1);
}
// your wifi code

```

you wait for a wifi event and in that time you obviously can't read the sensor. Just poll for incoming requests by doing it like

```
if (client.available()) {
  // your wifi code
}

```

This way your loop skips the wifi-routine if there is nothing to do and proceeds with reading the sensor.

As mikrocontrollers usually don't run a OS, you don't have multitasking which you have to implement yourself. Generally you have to avoid using delay loops when you want several tasks being executed "parallely".

---
Tags: wifi, nodemcu
---


# Question
Title: Counting the number of pulses in a second
For my speedometer application, I want to count the number of pulses occurring every second and convert it to speed. So for that, I need to count the number of pulses occurring at a given input pin for one second. This count is used to convert to speed. The count should go to zero and start over after every second. But I don't get how to set a limit of one second and start over every second. So far I have come up to this:

```
int count = 0;
float lasttime = 0;
float currenttime = 0;
const int speedpin = 52;

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

void loop()
{
    currenttime = millis();
    if (currenttime - lasttime <= 1000)
    {
        if (digitalRead(speedpin == HIGH))
        {
            count = count + 1;
        }
        else
        {
            count = count;
        }
    }
    else
    {
        count = 0;
    }
    Serial.println(count);
}

```

# Answer
As already explained in Michel Keijzers' answer, instead of counting how many times you find the input `HIGH`, you should count the `LOW``HIGH` transitions. This requires saving the previous input state and counting a transition only when the input is `HIGH` while it was `LOW` last time you saw it:

```
static int last_pin_state = LOW;
int pin_state = digitalRead(SPEED_PIN);
if (pin_state == HIGH && last_pin_state == LOW) {  // rising edge
    count++;
}
last_pin_state = pin_state;

```

For displaying the count every second, use the technique explained in the Blink without delay Arduino tutorial:

```
static uint32_t last_time = 0;
if (millis() - last_time >= PERIOD) {
    Serial.println(count);
    count = 0;
    last_time += PERIOD;
}

```

Note that you have to reset the count every time you print it.

VE7JRO suggests using interrupts. Interrupts save you the pain of writing the edge detection. On the other hand, they also make things slightly more complicated, because you now have to worry about atomicity, race conditions, volatile variables and such. There is no need to use interrupts unless the pulses are so fast (or your `loop()` is so slow) that you may miss a pulse. If your `loop()` gets bigger and slower, and you risk missing pulses, then interrupts can really help. But the proper way to use them is to count the pulses in the ISR. If you use the ISR only to rise a flag, you loose the speed advantage of the interrupts, which is the whole point of this approach.

The interrupt service routine would then be like this:

```
volatile unsigned int count;

void count_pulse()
{
    count++;
}

```

Then, the loop only has to print and reset the count:

```
void loop()
{
    // Periodically print and reset the count.
    static uint32_t last_time = 0;
    if (millis() - last_time >= PERIOD) {
        noInterrupts();
        unsigned int count_copy = count;
        count = 0;
        interrupts();
        Serial.println(count_copy);
        last_time += PERIOD;
    }
}

```

Note that the variable `count` is shared between the ISR and the main loop. That's why it has to be declared `volatile`. Also, its access within `loop()` has to be protected within a critical section delimited by a `noInterrupts()`/`interrupts()` pair, otherwise you would have a race condition. Also note that, in order to keep the critical section as short as possible, the value of `count` is only copied within the critical section, and the actual printing is deferred to after the critical section is finished.
> 3 votes

# Answer
First align your code:

```
int count = 0;
float lasttime = 0;
float currenttime = 0;
const int speedpin = 52;

void setup()
{
  Serial.begin(115200);
  // put your setup code here, to run once:
  pinMode(speedpin, INPUT);
}

void loop() {
  // put your main code here, to run repeatedly:
  currenttime = millis();
  if(currenttime - lasttime <= 1000)
  {
    if (digitalRead(speedpin == HIGH))
    {
      count = count + 1;
    }
    else
    {
      count=count;
    }
  }
  else
  {
    count=0;
  }
  Serial.println(count);
}

```

Than the statement `count = count` assigns a variable to itself which is not needed, and for increment you can use `count++`, so you get:

```
int count = 0;
float lasttime = 0;
float currenttime = 0;
const int speedpin = 52;

void setup()
{
  Serial.begin(115200);
  // put your setup code here, to run once:
  pinMode(speedpin, INPUT);
}

void loop() {
  // put your main code here, to run repeatedly:
  currenttime = millis();
  if(currenttime - lasttime <= 1000)
  {
    if (digitalRead(speedpin == HIGH))
    {
      count++;
    }
  }
  else
  {
    count = 0;
  }
  Serial.println(count);
}

```

In the loop, you do not count pulses, but only the measurements where a pin is HIGH and when the pin is LOW anywhere within the second, it is set to 0.

What you instead want to do is (assuming you want to count the LOW -\> HIGH transients: Make a global variable called e.g. previousState. Now, if the previousState == LOW and the current state of the GPIO is HIGH, only than increase count with one. Also, within the loop, each time update the previousState with the current state.

I leave the implementation to yourself.
> 0 votes

# Answer
If 'count' comes from a counter or device register, or is kept by an interrupt service routine, you don't ever want to zero the count. If a pulse arrives between the time you read the variable and the time you clear it, you will have failed to count that pulse.

Instead, make sure 'count' is of a suitable length to contain the largest number of pulses you could ever receive in one interval. Then, at each interval, save count to a temporary, say, 'tempCount'. Subtract the current 'tempCount' from the previous count, 'prevCount', in which you stored 'count' the previous time through. The difference will be the number of pulses counted in this interval. Use it or save it or whatever you need to do with it. Then store 'tempCount' into 'prevCount', and you're done.

No missed pulses, no overflow errors.
> 0 votes

---
Tags: arduino-ide
---


title: Built-In Digital Map for Robot Driving

text:
# Question
Title: Built-In Digital Map for Robot Driving
So, I'm creating this project for school. It's a simple robot with Arduino MEGA 2560 and basically, I create a digital map, feed it into the Arduino program and then the robot can drive. However, I've run into some problems while trying to implement my idea. Parsing errors mostly. And I want to know if there is another and different approach.

So, basically at the moment, this is how my digital map works:

Using C# and Visual Studio IDE I've created a program with which I can create the map. Basically, I create connections(lines/roads) and the connection has a starting and end point, a median point and a label(what it is). So, each connection info token is something like this:

`"Connection[x1: 0, y1: 0|x2: 13, y2: 0|xm: 6.5, ym: 0|label: Nothing]"` `"Connection[x1: 13, y1: 0|x2: 13, y2: 28|xm: 13, ym: 14|label: library]"`

Now, I have figured out a way to import this information into Arduino, and I've stored the information into a class object I created. Now, the difficulty I'm experiencing is how am I going to drive the robot from one point to another, store the robot's position and go to any point in the map when asked to.

**Edit:**

As for the implementation and storage of the map, it's like this:

So, I have a class Vertex. It basically the equivalent of a point and store (x, y) values.

```
class Vertex {
  public:
    int x;
    int y;

    Vertex(int _x, int _y) {
       x = _x;
       y = _y;
    }
};

```

Then there's the connection class. It stores the starting vertex, the end vertex, the median vertex and the label(string). It's like this:

```
class Connection {
  Vertex v1();
  Vertex v2();
  Vertex median();
  String label;

  public:
    Connection(Vertex _v1, Vertex _v2, Vertex _median, String _label) {
        v1() =  Vertex(_v1.x, _v1.y);
        v2() =  Vertex(_v2.x, _v2.y);
        median() = Vertex(_median.x, _median.y);
        String label = _label;
  }
};

```

And, finally, there's the map class where the user passes in the info tokens produced by my map creating application made in Visual Studio and it works like this:

```
#include "Connection.h"

class Map {
  public:
    Map(string infoTokens[]) {
      //I import the info tokens here.
    }

    void drawMap(MCUFRIEND_kbv tft, String ) {
      //This is a totally different function, it is just for drawing the map
        on top of the TFT screen that I have on my robot.
    }

    void driveTo(Vertex rP, String destinationLabel) {
      //This is where I drive my robot when the user requests to go to a
        destination and provides the label.
    }
};

```

As for the importing of the info tokens(the map information) I just do some `String Manipulation` on, for example, this `"Connection[x1: 0, y1: 0|x2: 13, y2: 0|xm: 6.5, ym: 0|label: Nothing]"` and get back all the info in the required data types. As for the importing it doesn't really change anything because I have tested my function(not present here) a lot of times and it works brilliantly. My question is how to use that information to hopefully drive the robot.

# Answer
> 1 votes
You were able to create a custom data structure from your string, but it seems, that the connections, that are stored in the `Map` class, are not connected. So the map does not really represent the structure of the "street" net. I would propose a different approach:

Instead of defining connections you can define the nodes of your net (where 2 or more streets meet). For each node you save the position (x, y) (or an instance of your vertex class), a label (like "library") and an array of pointers to other node objects. In code this may look like this (I left the methods out):

```
class Node {
    Vertex pos;
    char label[25];
    Node *connections[6];
}

```

---

Excursion: If you don't know, what pointers are in C/C++, here a short introduction. You should definitely read more about it on the web.

A pointer variable contains the address of another variable in the RAM. You can change this address and let the pointer point to another variable. A variable is marked as pointer with a `*` at the declaration. You can get the address of a variable (to set the pointer to this variable) through the `&` operator: `pointer = &variable` . If you dereference a pointer (by writing a `*` before the pointer name), you can work with the value, that the pointer points to. Each pointer variable has a type. It is the type of the object, that it points to. The pointer declaration `int *var` let's `var` point to `int` variables. If the type is a `class` or `struct` and you want to access members of the target (where it points to), you can use the shortened version `pointer->member`.

---

You define each node and add pointers to other nodes to represent connections. To traverse through the map, you need a start node. You save the address of the current node in a pointer. Then you can use it to access the connections of the current node. To actually go to the next node, you would set your pointer to the value saved in one of the `connections` elements, because that are pointers to the connected nodes.

The robot can then be moved along the straight lines between 2 nodes. When you want to also have non-straight, you can also do that by defining a middle point. You just to define the geometrical form, that the line should take.

The `Map` class can contain an array of `Nodes`. You can loop through all nodes in the array, if you need to, or you can traverse through the net by using the pointers.

---

The actual algorithm to find the path with the smallest travel distance is a big out of scope here. Doing that efficiently can be a complex task. You can research these algorithms on the web. The easiest way is to test all different paths in your program (without actually moving the robot), save the needed distance for each path and then choose the path based on that. You would need to write a termination condition, so that no connected will be taken twice on the same path (which would mean some kind of loop). Also keep in mind, that this will need more and more computation time, as your net grows. If it stays small and you don't need very fast computation, it might stay sufficient. If your implementation is recursive, you also have to consider, that each recursion takes up memory on the stack. You don't want to get out of memory.

Speaking of memory: In your implementation you use `String` for the label and you might want to use dynamic memory allocation for your map. That is not a good idea, because it can make swiss cheese out of your heap memory (heap fragmentation). It is better to define a fixed array, that can hold the maximal number of elements (as I have done with the connection of a node). The not needed elements can be set to something meaningless (for the connections you can use the null pointer and for unused nodes simply only null pointer connections).

---
Tags: arduino-mega, robotics, algorithm, error
---


# Question
Title: NodeMCU (ESP8266) board controlled over shared hosting database
I have a NodeMCU (ESP8266) board that I want to control over the internet. I am trying to find a solution where I don't have to set up any configurations on my router like port forwarding. I came up with the following solution:

I have a website where the user changes the device status (with status I mean for example GPIO5 pin value HIGH or LOW) which is then saved to a database on a shared hosting server. The NodeMCU sends periodically (for example every 5 seconds) a HTTP GET request to the database. According to the value that is received from the database the NodeMCU board changes the pin value to HIGH or LOW. If NodeMCU changes it's status (for example a pin value from HIGH to LOW) the new device status is sent to the database with a HTTP POST request. The device also sends a HTTP POST request periodically (for example every 60 seconds) so the user can monitor the device status on the website.

There are a few problems with this configuration:

1. There is no real-time connection between NodeMCU and the user (there is always a delay in the device response)
2. The device sends thousand of queries every day that are a load to the shared hosting server. For example if the GET request is sent every 5 seconds, that gives 17280 queries per day for one device.

So my question is how practical is this configuration on shared hosting or any kind of hosting, what are the alternatives or improvements to this configuration and how to establish a connection with the NodeMCU so that the device sends a GET request to the database only when the device status is changed in the database by the user.

# Answer
> 2 votes
Use MQTT.

You need:

1. The PubSubClient.h library
2. An MQTT server

For MQTT there are some free ones around on the internet (ask Google). Or if you have a Linux server available for use (e.g., a cheap VPS server from one of many many providers online) then you can run your own with `mosquitto`.

MQTT works kind of how you describe, but it's not making constant GET requests - it opens a single connection to the MQTT server and realtime requests are sent down it to the client, and back from the client to the server.

Near realtime communication.

---
Tags: esp8266, nodemcu
---


title: DateTime to string

text:
# Question
Title: DateTime to string
For some reason I can't use the `Time.h` lib.

Can you guys tell me how to create a string from the datetime into a format like this:

```
yyyy.MM.dd:hh.mm.ss
2014.10.29:07.12.33

```

Seems odd that I can't find any examples of this.

# Answer
> 4 votes
Is that what you want, mate?

```
char buf1[20];
DateTime now = rtc.now();
//Updated now.day to now.date
sprintf(buf1, "%02d:%02d:%02d %02d/%02d/%02d",  now.hour(), now.minute(), now.second(), now.date(), now.month(), now.year());

Serial.print(F("Date/Time: "));
Serial.println(buf1);

```

# Answer
> 3 votes
If by `DateTime` you are referring to RTClib's `DateTime` (this is something you have to clarify in your question), then you can call `unixtime()` method on your `DateTime` object. The returned value is regular Unix "epoch" time, which can be used as `time_t` value with functions from `<time.h>` (and it's `<time.h>`, not `<Time.h>`).

For example, you can use `ctime` to convert Unix `time_t` value to a C-string, although the format of that string is different from the one you requested

```
DateTime dt;
...
time_t t = dt.unixtime();

const char *str = ctime(&t);
Serial.println(str);

```

On Arduino you also have `ctime_r` available to you as a reentrant version of `ctime`.

Or, if you need more flexibility with the format, you can use `gmtime` or `localtime` and then `strftime`, but this might be excessive, since `struct tm` generated by `gmtime` is in essence very similar to `DateTime`. You can simply use `snprintf` in a manner suggested in @şevket Karayılan's answer.

Nevertheless, note that `strftime` provides you with quite extensive formatting capabilities, which would take some effort to reimplement manually

```
DateTime dt;
...
time_t t = dt.unixtime();
struct tm *lt = localtime(&t);

char str[32];
strftime(str, sizeof str, "%Y.%m.%d:%H.%M.%S", lt);
Serial.println(str);

strftime(str, sizeof str, "%x %X", lt);
Serial.println(str);

strftime(str, sizeof str, "%F %T", lt);
Serial.println(str);

```

# Answer
> 2 votes
There's no built in function to do that, I'm afraid.

I suggest you create a method that will format the string like so. Something along the lines of:

```
void formatTime()
{
   string str = year() + "." + month() + "." + day() + ":" + hour() + "FILL IN THE REST";
}

```

---
Tags: string
---


# Question
Title: Include in different file make different compiling error
I'm have problem compiling a code.

ardutest.ino:

```
#include "mylib.h"
#include <SD.h>

void setup() {

}

void loop() {
  fn();
}

```

mylib.h:

```
#ifndef mylib_h
#define mylib_h

#include "Arduino.h"

void fn(File &_file);

#endif

```

mylib.c:

```
#include "mylib.h"

void fn(File &_file)
{
  _file = SD.open("LOG.TXT", FILE_WRITE);
  _file.println(42);
  _file.close();
}

```

When checking code in Arduino IDE I have this error:

```
In file included from sketch/mylib.c:1:0:
mylib.h:7: error: expected ')' before '&' token
 void fn(File &_file);
          ^
mylib.c:3: error: expected ')' before '&' token
 void fn(File &_file)
          ^
Multiple libraries were found for "SD.h"
 Used: /home/mario/Arduino/libraries/SD
 Not used: /home/mario/Programs/arduino/libraries/SD
exit status 1
expected ')' before '&' token

```

But if I put SD.h in mylib.h (other files are the same):

```
#ifndef mylib_h
#define mylib_h

#include "Arduino.h"
#include <SD.h>

void fn(File &_file);

#endif

```

I have this error:

```
In file included from /home/user/Arduino/libraries/SD/src/utility/Sd2Card.h:26:0,
                 from /home/user/Arduino/libraries/SD/src/utility/SdFat.h:29,
                 from /home/user/Arduino/libraries/SD/src/SD.h:20,
                 from sketch/mylib.h:5,
                 from sketch/mylib.c:1:
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h:423:14: error: unknown type name 'pin_map_t'
 static const pin_map_t digitalPinMap[] = {

              ^
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h:447:69: error: 'pin_map_t' undeclared here (not in a function)
 static const uint8_t digitalPinCount = sizeof(digitalPinMap)/sizeof(pin_map_t);

                                                                     ^
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h: In function 'getPinMode':
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h:455:32: error: request for member 'ddr' in something not a structure or union
     return (*digitalPinMap[pin].ddr >> digitalPinMap[pin].bit) & 1;

                                ^
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h:455:58: error: request for member 'bit' in something not a structure or union
     return (*digitalPinMap[pin].ddr >> digitalPinMap[pin].bit) & 1;

                                                          ^
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h: In function 'setPinMode':
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h:464:26: error: request for member 'ddr' in something not a structure or union
       *digitalPinMap[pin].ddr |= 1 << digitalPinMap[pin].bit;

                          ^
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h:464:57: error: request for member 'bit' in something not a structure or union
       *digitalPinMap[pin].ddr |= 1 << digitalPinMap[pin].bit;

                                                         ^
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h:466:26: error: request for member 'ddr' in something not a structure or union
       *digitalPinMap[pin].ddr &= ~(1 << digitalPinMap[pin].bit);

                          ^
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h:466:59: error: request for member 'bit' in something not a structure or union
       *digitalPinMap[pin].ddr &= ~(1 << digitalPinMap[pin].bit);

                                                           ^
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h: In function 'fastDigitalRead':
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h:475:32: error: request for member 'pin' in something not a structure or union
     return (*digitalPinMap[pin].pin >> digitalPinMap[pin].bit) & 1;

                                ^
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h:475:58: error: request for member 'bit' in something not a structure or union
     return (*digitalPinMap[pin].pin >> digitalPinMap[pin].bit) & 1;

                                                          ^
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h: In function 'fastDigitalWrite':
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h:484:26: error: request for member 'port' in something not a structure or union
       *digitalPinMap[pin].port |= 1 << digitalPinMap[pin].bit;

                          ^
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h:484:58: error: request for member 'bit' in something not a structure or union
       *digitalPinMap[pin].port |= 1 << digitalPinMap[pin].bit;

                                                          ^
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h:486:26: error: request for member 'port' in something not a structure or union
       *digitalPinMap[pin].port &= ~(1 << digitalPinMap[pin].bit);

                          ^
/home/user/Arduino/libraries/SD/src/utility/Sd2PinMap.h:486:60: error: request for member 'bit' in something not a structure or union
       *digitalPinMap[pin].port &= ~(1 << digitalPinMap[pin].bit);

                                                            ^
In file included from /home/user/Arduino/libraries/SD/src/utility/SdFat.h:29:0,
                 from /home/user/Arduino/libraries/SD/src/SD.h:20,
                 from sketch/mylib.h:5,
Multiple libraries were found for "SD.h"
 Used: /home/user/Arduino/libraries/SD
 Not used: /home/user/Programs/arduino/libraries/SD
                 from sketch/mylib.c:1:
/home/user/Arduino/libraries/SD/src/utility/Sd2Card.h: At top level:
/home/user/Arduino/libraries/SD/src/utility/Sd2Card.h:70:1: error: initializer element is not constant
 uint8_t const  SD_CHIP_SELECT_PIN = SS;

 ^
/home/user/Arduino/libraries/SD/src/utility/Sd2Card.h:79:1: error: initializer element is not constant
 uint8_t const  SPI_MOSI_PIN = MOSI;

 ^
/home/user/Arduino/libraries/SD/src/utility/Sd2Card.h:81:1: error: initializer element is not constant
 uint8_t const  SPI_MISO_PIN = MISO;

 ^
/home/user/Arduino/libraries/SD/src/utility/Sd2Card.h:83:1: error: initializer element is not constant
 uint8_t const  SPI_SCK_PIN = SCK;

 ^
/home/user/Arduino/libraries/SD/src/utility/Sd2Card.h:176:1: error: unknown type name 'class'
 class Sd2Card {

 ^
/home/user/Arduino/libraries/SD/src/utility/Sd2Card.h:176:15: error: expected '=', ',', ';', 'asm' or '__attribute__' before '{' token
 class Sd2Card {

               ^
In file included from /home/user/Arduino/libraries/SD/src/utility/SdFat.h:30:0,
                 from /home/user/Arduino/libraries/SD/src/SD.h:20,
                 from sketch/mylib.h:5,
                 from sketch/mylib.c:1:
/home/user/Arduino/libraries/SD/src/utility/FatStructs.h:405:1: error: initializer element is not constant
 uint8_t const DIR_ATT_FILE_TYPE_MASK = (DIR_ATT_VOLUME_ID | DIR_ATT_DIRECTORY);

 ^
In file included from /home/user/.arduino15/packages/arduino/hardware/avr/1.6.21/cores/arduino/Print.h:27:0,
                 from /home/user/Arduino/libraries/SD/src/utility/SdFat.h:31,
                 from /home/user/Arduino/libraries/SD/src/SD.h:20,
                 from sketch/mylib.h:5,
                 from sketch/mylib.c:1:
/home/user/.arduino15/packages/arduino/hardware/avr/1.6.21/cores/arduino/Printable.h:25:1: error: unknown type name 'class'
 class Print;
 ^
/home/user/.arduino15/packages/arduino/hardware/avr/1.6.21/cores/arduino/Printable.h:33:1: error: unknown type name 'class'
 class Printable
 ^
/home/user/.arduino15/packages/arduino/hardware/avr/1.6.21/cores/arduino/Printable.h:34:1: error: expected '=', ',', ';', 'asm' or '__attribute__' before '{' token
 {
 ^
In file included from /home/user/Arduino/libraries/SD/src/utility/SdFat.h:31:0,
                 from /home/user/Arduino/libraries/SD/src/SD.h:20,
                 from sketch/mylib.h:5,
                 from sketch/mylib.c:1:
/home/user/.arduino15/packages/arduino/hardware/avr/1.6.21/cores/arduino/Print.h:37:1: error: unknown type name 'class'
 class Print
 ^
/home/user/.arduino15/packages/arduino/hardware/avr/1.6.21/cores/arduino/Print.h:38:1: error: expected '=', ',', ';', 'asm' or '__attribute__' before '{' token
 {
 ^
In file included from /home/user/Arduino/libraries/SD/src/SD.h:20:0,
                 from sketch/mylib.h:5,
                 from sketch/mylib.c:1:
/home/user/Arduino/libraries/SD/src/utility/SdFat.h:39:1: error: unknown type name 'class'
 class SdVolume;

 ^
/home/user/Arduino/libraries/SD/src/utility/SdFat.h:55:1: error: initializer element is not constant
 uint8_t const O_RDONLY = O_READ;

 ^
/home/user/Arduino/libraries/SD/src/utility/SdFat.h:59:1: error: initializer element is not constant
 uint8_t const O_WRONLY = O_WRITE;

 ^
/home/user/Arduino/libraries/SD/src/utility/SdFat.h:61:1: error: initializer element is not constant
 uint8_t const O_RDWR = (O_READ | O_WRITE);

 ^
/home/user/Arduino/libraries/SD/src/utility/SdFat.h:63:1: error: initializer element is not constant
 uint8_t const O_ACCMODE = (O_READ | O_WRITE);

 ^
/home/user/Arduino/libraries/SD/src/utility/SdFat.h:94:1: error: initializer element is not constant
 uint8_t const FAT_FILE_TYPE_MIN_DIR = FAT_FILE_TYPE_ROOT16;

 ^
/home/user/Arduino/libraries/SD/src/utility/SdFat.h:137:1: error: unknown type name 'class'
 class SdFile : public Print {

 ^
/home/user/Arduino/libraries/SD/src/utility/SdFat.h:137:14: error: expected '=', ',', ';', 'asm' or '__attribute__' before ':' token
 class SdFile : public Print {

              ^
/home/user/Arduino/libraries/SD/src/utility/SdFat.h:431:1: error: unknown type name 'class'
 class SdVolume {

 ^
/home/user/Arduino/libraries/SD/src/utility/SdFat.h:431:16: error: expected '=', ',', ';', 'asm' or '__attribute__' before '{' token
 class SdVolume {

                ^
In file included from /home/user/Arduino/libraries/SD/src/SD.h:21:0,
                 from sketch/mylib.h:5,
                 from sketch/mylib.c:1:
/home/user/Arduino/libraries/SD/src/utility/SdFatUtil.h: In function 'FreeRam':
/home/user/Arduino/libraries/SD/src/utility/SdFatUtil.h:43:7: error: 'reinterpret_cast' undeclared (first use in this function)
   if (reinterpret_cast<int>(__brkval) == 0) {

       ^
/home/user/Arduino/libraries/SD/src/utility/SdFatUtil.h:43:7: note: each undeclared identifier is reported only once for each function it appears in
/home/user/Arduino/libraries/SD/src/utility/SdFatUtil.h:43:24: error: expected expression before 'int'
   if (reinterpret_cast<int>(__brkval) == 0) {

                        ^
/home/user/Arduino/libraries/SD/src/utility/SdFatUtil.h:45:36: error: expected expression before 'int'
     free_memory = reinterpret_cast<int>(&free_memory)

                                    ^
/home/user/Arduino/libraries/SD/src/utility/SdFatUtil.h:49:36: error: expected expression before 'int'
     free_memory = reinterpret_cast<int>(&free_memory)

                                    ^
/home/user/Arduino/libraries/SD/src/utility/SdFatUtil.h: In function 'SerialPrint_P':
/home/user/Arduino/libraries/SD/src/utility/SdFatUtil.h:62:52: error: 'Serial' undeclared (first use in this function)
   for (uint8_t c; (c = pgm_read_byte(str)); str++) Serial.write(c);

                                                    ^
/home/user/Arduino/libraries/SD/src/utility/SdFatUtil.h: In function 'SerialPrintln_P':
/home/user/Arduino/libraries/SD/src/utility/SdFatUtil.h:72:3: error: 'Serial' undeclared (first use in this function)
   Serial.println();

   ^
In file included from sketch/mylib.h:5:0,
                 from sketch/mylib.c:1:
/home/user/Arduino/libraries/SD/src/SD.h: At top level:
/home/user/Arduino/libraries/SD/src/SD.h:26:1: error: unknown type name 'namespace'
 namespace SDLib {
 ^
/home/user/Arduino/libraries/SD/src/SD.h:26:17: error: expected '=', ',', ';', 'asm' or '__attribute__' before '{' token
 namespace SDLib {
                 ^
/home/user/Arduino/libraries/SD/src/SD.h:119:1: error: unknown type name 'using'
 using namespace SDLib;
 ^
/home/user/Arduino/libraries/SD/src/SD.h:119:17: error: expected '=', ',', ';', 'asm' or '__attribute__' before 'SDLib'
 using namespace SDLib;
                 ^
/home/user/Arduino/libraries/SD/src/SD.h:123:14: error: expected '=', ',', ';', 'asm' or '__attribute__' before ':' token
 typedef SDLib::File    SDFile;
              ^
/home/user/Arduino/libraries/SD/src/SD.h:124:14: error: expected '=', ',', ';', 'asm' or '__attribute__' before ':' token
 typedef SDLib::SDClass SDFileSystemClass;
              ^
In file included from sketch/mylib.c:1:0:
mylib.h:7: error: expected ')' before '&' token
 void fn(File &_file);
              ^
mylib.c:3: error: expected ')' before '&' token
 void fn(File &_file)
              ^
exit status 1
expected ')' before '&' token

```

If I use SD.h function in mylib, I need this in mylib.h file. Why is it happens?

The first error is about passing object as function argument. I'm following sample I found in others forum, then I don't know why it isn't working.

\[SOLVED\] I rename mylib.c to mylib.cpp and solved the problem.

# Answer
> 1 votes
SD.h defines `class File`. Without that definition, 'File' is taken to be the name of an untyped argument (which will be assumed to be an int). Given that assumption, '&\_file' is unexpected.

# Answer
> 1 votes
Firstly, there are different strategies for organizing header file structure. I don't know which one you follow. Within the popular approach that strives to keep all header files in self-sufficient state, `mylib.h` should include `<SD.h>` since `mylib.h` uses `File` type.

Secondly, when you actually included `<SD.h>` into `mylib.h`, you ran into a different problem. SD library is written as a C++ library. Its header files will not compile as C code. Meanwhile, you are trying to compile `<SD.h>` in C mode by indirectly including it into a `mylib.c` file, which is what causes the errors.

---

This library's header files contain many bizarre coding patterns that might create an impression *as if* someone was trying to make these headers compatible with C code (`static const`? `static inline`? Etc.), but this is an illusion. The code is exclusively C++, not C.

---
Tags: arduino-ide, compilation-errors
---


# Question
Title: Output pin low used to complete 12V LED circuit?
I have a project that (in part) will drive 3 LEDs where the LED anodes are at 12V. The thought is to drive each LED by connecting each cathode to a 650 ohm resistor, and connect that to an Arduino DIO pin which, when needed, is set to output LOW. Arduino VIN = same 12V with common ground. Am I going to have an Arduino problem of any sort?

# Answer
No, what you propose will not work. And it risks damaging your Arduino.

Normally you would include a single transistor which the Arduino uses to control the power through the LEDs. This removes the 12V from the Arduino and turns the output into an actual switch.

The problem is that the Arduino's GPIO isn't just a single transistor. It is (amomgst other things):

* Two complimentary transistors (that's the C in CMOS) for HIGH and LOW switches
* ESD Diodes
* Input buffer

By just adding the one transistor like this:

simulate this circuit – Schematic created using CircuitLab

the 12V is kept well away from the Arduino. Setting the output HIGH will turn on the transistor, allowing the current to flow to ground. Setting it LOW with turn it off, blocking the flow of current and switching the LEDs off.

Further: the Arduino's GPIO has a maximum sustained current of 25mA. Ideally you don't want to even come anywhere near this. By adding the transistor it acts as a buffer and allows you to deal with much higher currents - and hence more, and brighter, LEDs.

Incidentally, R1 in that schematic is there solely to keep the transistor *off* when the Arduino is not actively driving the output - e.g., when it's either unpowered or is running the bootloader - or you happen to have the GPIO in INPUT mode (as it defaults to).
> 1 votes

---
Tags: led
---


# Question
Title: ESP8266 print DNS address (obtained via DHCP)
I've set up an ESP8266 (Wemos D1 Mini) to get IP-information via DHCP. Everything works fine and I can print the information :

Serial.print(WiFi.macAddress()); Serial.print(WiFI.localIP()); Serial.print(WiFi.subnetMask()); Serial.print(WiFi.gateway.IP());

But how do I print the DNS-address ??

I cant find a function for this ???

/Kind regards : Gurra

# Answer
```
Serial.println(WiFi.dnsIP());

```

If you have more than one DNS server you can specify the index:

```
Serial.println(WiFi.dnsIP(1));

```
> 5 votes

---
Tags: esp8266, wifi
---


# Question
Title: SR505 PIR sensor Time Delay Using Ticker Library NodeMCU
I am trying to make the value of PIR sensor value HIGH for certain time using code. SR505 have a default time delay of 8 seconds. But I want to increase it to 20 seconds.

I am thinking of increasing it using `TICKER` library. I have tried and tested a basic code and seems to be working fine. But I want to implement it with Ticker which will keep the value HIGH for 20 seconds as soon as the timer goes above 20 seconds and PIR is not detecting the motion then it will go set again the timer to 0.

Here is how my code looks like:

```
#include <Ticker.h>

#define SIGNAL_PIN D2

Ticker flipper;

void setup()
{
  Serial.begin(9600);
  pinMode(SIGNAL_PIN, INPUT);
  digitalWrite (SIGNAL_PIN, LOW);

}

void flip(){
  Serial.println("From callback");
  digitalWrite (SIGNAL_PIN, HIGH);
}

void loop() {
  if(digitalRead(SIGNAL_PIN)==HIGH) {
    Serial.println("Movement detected.");
    flipper.attach(1, flip);
  } else {
    Serial.println("Did not detect movement.");
    flipper.detach();
  }
  delay(1000);
}

```

Thank you!

# Answer
You really don't need the Ticker library. Just maintain a timestamp of the last time the PIR was seen to be HIGH:

```
void loop() {
    static uint32_t lastSeenHigh = millis();
    static bool pirState = false;

    // If it's active then record that fact along with the time
    if (digitalRead(SIGNAL_PIN) == HIGH) {
        lastSeenHigh = millis();
        pirState = true;
    } else {
        // otherwise, if it's been 12 seconds since last seen
        // active, record that it's inactive.
        // 20 seconds, minus the 8 second active time, times 1000 is
        // 12000 milliseconds to extend the time by
        if ((millis() - lastSeenHigh) > 12000) {
            pirState = false;
        }
    }

    if (pirState == true) {
        // Do whatever you want in here when the PIR is active
    }
}

```

With that (untested) code:

* Any time the PIR is active the current time is recorded and the state is set true
* When the PIR is LOW and at least 12 seconds have passed since the last activation, set the state to false.
> 0 votes

---
Tags: esp8266, nodemcu
---


# Question
Title: Help with Arduino Micro Keypress Algorithm
Greeting, first time Arduino user here.

So I am using the Arduino Micro as an HID keyboard device. It accepts arbitrary input from a Node-JavaScript program I am running (so I have full freedom in in the data transferred to the micro).

The goal is for the data transmitted to the micro to include information about a keypress: whether it was pressed or released and which key it is. The serial connections are all fine and dandy - I just have questions regarding the key pressing logic.

As far as the JavaScript program goes, a key down is detected based on the keyCode, not the character code so when tapping “a”, character code 97, the Arduino micro is receiving “A”, character code 65 since the JavaScript detected keyCode is 65. So that all sounds like problems with JavaScript (which it is), but remember that I have freedom in portraying the information sent to the micro.

That being said, instead of detecting by keyCodes and character codes in JavaScript, I could just transmit the letter e.g. “a” with some identifier for press/release such as “+a” for release and “-a” for press. My problem here is how would I handle modifier keys using the Keyboard library.

Should I handle character keys and modifiers keys separately i.e. `Keyboard.write` for characters and `Keyboard.press/release` for modifiers or are there cases where it would make sense to press and hold “a” (which would also be different than pressing and holding “A”)?

Below is my original code using keyCodes and “u/d” identifiers to denote up or down (which I am thinking now that “u/d” could be easily confused as a letter if I decide to transmit characters as characters:

```
/*
  Receives from the hardware serial, sends to software serial.
  Receives from software serial, sends to hardware serial.

  The circuit:
   RX is digital pin 10 (connect to TX of other device)
   TX is digital pin 11 (connect to RX of other device)

  Not all pins on the Leonardo and Micro support change interrupts,
  so only the following can be used for RX:
  8, 9, 10, 11, 14 (MISO), 15 (SCK), 16 (MOSI).
*/

#include <SoftwareSerial.h>
#include <Keyboard.h>

SoftwareSerial rpiSerial(10, 11); // RX, TX

void setup() {
  // Open serial communications and wait for port to open:
  Serial.begin(115200);
  // Set the data rate for the SoftwareSerial port
  rpiSerial.begin(115200);
  // initialize control over the keyboard:
  Keyboard.begin();
  while (!Serial) {
    ; // wait for serial port to connect. Needed for native USB port only
  }

  Serial.println("Keyboard Serial Connection Established");
}

String keyCode = "";
char state;

void loop() {
  while (rpiSerial.available() > 0) {
    // "Type" via keyCodes (recommended for modifiers)
    // https://www.arduino.cc/en/Reference/KeyboardWrite not behaving as expected

    int data = rpiSerial.read();
    if (isDigit(data)) {
      keyCode += (char)data;
    }

    if (isAlpha(data)) {
      state = (char)data;
    }

    if (data == '\n') {
      Serial.print(state);
      Serial.println(keyCode.toInt());

      if (state == 'd') {
        Keyboard.press(keyCode.toInt());
      }

      if (state == 'u') {
        Keyboard.release(keyCode.toInt());
      }

      keyCode = "";
      char state;
    }
  }
}

```

I have also noticed that the data from the serial connection parsed by the micro is sometimes incorrect i.e. a keyCode will be misidentified. For instance, by repeatedly pressing “a” through my JavaScript program, the JavaScript program will consistently identify keyCode 65 yet Arduino will identify the received data as keyCode 65 most of the time and then randomly keyCode 64. This happens with other keys as well and the keyCode doesn’t always happen to be just one less nor does it always occur after “n” presses.

# Answer
> 1 votes
Modifier keys are treated no different to normal keys.

The Arduino Keyboard library contains code to map different keys from the internal list of macros to specific keypresses:

* If the key value is \>= 138 it's a non-printing special key (subtract 138)
* If the key value is \>= 128 it is a modifier key (1 \<\< (k - 128))
* Otherwise look the code up in a mapping table.

That means you can use:

```
Keyboard.press(KEY_LEFT_SHIFT);

```

or

```
Keyboard.release(KEY_RIGHT_GUI);

```

The full list of modifier keys is:

```
#define KEY_LEFT_CTRL   0x80
#define KEY_LEFT_SHIFT    0x81
#define KEY_LEFT_ALT    0x82
#define KEY_LEFT_GUI    0x83
#define KEY_RIGHT_CTRL    0x84
#define KEY_RIGHT_SHIFT   0x85
#define KEY_RIGHT_ALT   0x86
#define KEY_RIGHT_GUI   0x87

```

So to do a capital A you can use:

```
Keyboard.press(KEY_LEFT_SHIFT);
Keyboard.press('a');
Keyboard.release('a');
Keyboard.release(KEY_LEFT_SHIFT);

```

There is also a shortcut, and that is:

```
Keyboard.press('A');
Keyboard.release('A');

```

The character 'A' is the same in the lookup table as character 'a' except the high bit of the result is set, which triggers a "Press or release the shift key" addition in the mapping code.

A USB keyboard report consists of 8 bytes:

* Up to 8 modifier keys (bitmap)
* One reserved byte
* 6 bytes to indicate pressed keys

This means that you can have up to 6 keys pressed at once, plus modifier keys. Never any more than that. So you don't need to handle any more than that in your code.

The current list of pressed keys is maintained by the keyboard and is sent in every report. There's no concept as such of "pressed" or "released" - only the list of what is currently pressed. If a key is released it's just removed from that list of pressed keys.

So what you need is some way of transferring that data in such a way that the Arduino can interpret it properly.

Since the data is not high throughput you can afford to be quite wasteful in your protocol. I would suggest using a fairly verbose ASCII based protocol.

* All the protocol data is using ASCII characters between 32 and 127 inclusive
* This frees up control characters (\<32) for controlling the protocol.

The simplest thing is to use a single control character (such as `\n`) to act as a line ending to break your data up into packets. Each packet can then contain a list of instructions.

For example, you might choose to have a protocol that looks like:

```
P,129\n
P,97\n
R,97\n
R,129\n

```

By treating each line as a complete entity you know that you want to **P**ress key 129 (`#define KEY_LEFT_SHIFT 0x81`), press key 97 ('a'), release 97, then release 129.

There's no confusion, since commands are all a single upper-case character, and keys are all a decimal number.

For your application, though, a "raw" access interface would be of more use, since you don't really want the Arduino interpreting things for you. However, the API doesn't provide that kind of thing. So you just have to make the best of what you have and work around it.

---
Tags: serial, arduino-micro, keyboard
---


# Question
Title: Arduino stopped working: avrdude: ser_open(): can't set com-state
I'm playing with my first Arduino device (Arduino Leonardo). It worked fine but at some point it failed. **I'm getting this error**:

> avrdude: ser\_open(): can't set com-state for "\\.\COM6"
>
> An error occurred while uploading the sketch

The error came out of nowhere because I didn't change the port or cable or anything. Everything seems to be in order: the port, the driver, the IDE, the cable. And everything worked just an hour ago.

1) I've tried to change the port 2) I've reinstalled IDE 3) I've tried different cable

What else can I do?

And another thing: after manual reset of Arduino (with button) device disappears.

# Answer
The thing to remember with the Leonardo and other ATMega32U4 based boards is that there is no actual serial connection.

What there is, is a USB connection which is controlled by the sketch (and independently by the bootloader) to provide a "CDC/ACM" connection over USB. This emulates a serial connection, but it's not a *real* serial connection.

This actually has a huge number of benefits, because you can be other things besides a serial port, such as a keyboard or a mouse. However, it comes at a cost: the serial port is at the mercy of the sketch that's running at the time.

If your sketch crashes for any reason then the serial port can no longer be used. That's bad. It can cripple your Arduino. Since it's the sketch that is providing the driving force for the CDC/ACM serial emulation, if that sketch dies, so does the control of the USB and thus the CDC/ACM.

So while the port may be created initially by the sketch, if it then subsequently crashes the port is still there, but unresponsive. Or the port can vanish completely.

So how do you fix it? Well, there's a couple of strategies:

1. Some people have had success by pressing the RESET button twice in quick succession. This depends on the version of the bootloader in use though, and it's not something I have ever tried.
2. Pressing RESET at just the right moment to get the bootloader to run *just before* `avrdude` runs and catch it at the right time to accept a new sketch, or
3. Using a hardware programmer (e.g., USBASP) or another Arduino to wipe the chip and reinstall the bootloader

My preferred method is 3, since it is certain to always work - however it requires either a hardware programmer or another Arduino. However you can pick up a USBASP on eBay / AliExpress / Amazon etc for next to nothing, and when you're working with AVR chips they're always good to have to get you out of tight spots like this.
> 2 votes

---
Tags: arduino-leonardo, atmega32u4
---