EMI (Electromagnetic Interference) on Arduino UNO and Interrupts

Hello
I have a rather unexplained weirdness happening with a simple implementation for counting impulses with Arduino UNO. The impulses come from relays on the security access control panel. I’m using Arduino to count people entering/exiting the room.
I hope to get educated and to resolve that “mystery”.

My project consists of Arduino UNO. with an Ethernet shield (to sent the counter values to .net software on my PC) and LCD display (to show the value of the counter locally).

The impulses from the access control panel are not frequent and last for around 0.5 sec.

Here’s the application break through. First relay NC contacts are connected between GND and PIN2, second relay’s NC contacts between GND and PIN3. I use 22/2 wires for these connections and the relays are located around 3 feet away. The pins are set to INPUT_PULLUP. I’m attaching interrupt routines on them. I use interrupts because in case of a problem with the Ethernet the routine that sends the counter value holds the execution of the program making it possible for Arduino to not register the impulses from the relays during that time - it is very critical to count precisely. When the contact on one of the relays open the PIN on Arduino is pulled up with internal resistor. When the relay contacts close the PIN gets connected to GND.

The problem is that I’m getting random counts just by me moving something on the table. It’s something like screwdriver, plate etc. nothing that’s powered. I say it’s random because I can’t reproduce it to detect how and when exactly it’s happening. Also I’ve noticed I’m getting these counts whenever I’m turning the switch On and Off on the soldiering station that’s around two feet away from Arduino. This is happening not with every switching but quite often.

Does anyone know how to prevent such behavior?
Here’s a code for the interrupts routines. It’s written that way so I could overcome the bouncing effect from the relays by measuring the time of a pulse.

void setup()
{
attachInterrupt(digitalPinToInterrupt(entrancePIN), CountUpFalling, FALLING);
attachInterrupt(digitalPinToInterrupt(exitPIN), CountDownFalling, FALLING);
}

void CountUpFalling()
{
attachInterrupt(digitalPinToInterrupt(entrancePIN), CountUpRising, RISING);
entryPulseStartTime = millis();
}

void CountUpRising()
{
attachInterrupt(digitalPinToInterrupt(entrancePIN), CountUpFalling, FALLING);
entryPulseEndTime = millis();
if (entryPulseEndTime - entryPulseStartTime >= requiredPulseLength)
{
counter ++;
}
}

void CountDownFalling()
{
attachInterrupt(digitalPinToInterrupt(exitPIN), CountDownRising, RISING);
exitPulseStartTime = millis();
}

void CountDownRising()
{
attachInterrupt(digitalPinToInterrupt(exitPIN), CountDownFalling, FALLING);
exitPulseEndTime = millis();
if (exitPulseEndTime - exitPulseStartTime >= requiredPulseLength)
{
counter --;
}
}

There’s more code in my sketch but didn’t want to blur out the critical lines by pasting it here.
Your help will be greatly appreciated.
Thank you.

Its not EMI, using INPUT_PULLUP is way too weak for this application. Use an external 10K pullup resistor for each interrupt pin. If you want to debounce in hardware, connect a 1µF capacitor in parallel with each resistor. Voilà!

Thank you for your reply. Could you please elaborate on why is the input pull up a bad solution? I thought my application is very comparable to so many examples that use push button just in my case it's a relay.
Thank you.

Its the distance of the wiring - 2 sets of contacts x 3 feet will basically act as an antennae, ready to pick up anything, including the energizing of relay coils, stray signals, etc. The internal pullups (30K-50K) are adequate for only short distances, preferably on the same pcb.

Edit: Also, some relays have their contacts specified with minimum current (i.e. 1mA DC), so if that's the case, don't use greater than 5K for pullup. Try anything from 1K - 4.7K and I'm sure the problem will be resolved.

I would use the NO contacts to switch the normally high signal to GND. The reason for this is that the NC contacts would be slightly oxidized and you would be relying on the weak spring force to keep the connection of a low level signal. Any vibration on the relay getting through to the contacts would trigger the interrupt. This is next to impossible to occur if using the NO contacts due to the air gap. Ever wonder why the NO contacts usually have a higher rating? The electromagnetic force that closes these contacts is stronger than the force of the spring action that holds the NC contacts closed.

Thank you for that explanation - already feel better that it's a less of a "mystery". I'll give it a try.

This solution worked for you? I have a similar set up, with 10K pullup resistors, and having similar problems.
Best regards