Crosstalk between switches on AVR 88P

Thread Starter

KaloyanP

Joined May 27, 2012
5
Hello, I have been working on an embedded programming problem and ran into a very weird problem that I kind of solved. However, I don't really understand why my solution works.

This is the code I use to initialize the switches:

Rich (BB code):
inline void switch_init(void)
{
	PCMSK2|=(1<<SW1|1<<SW2|1<<SW3); //allow interrupts for switches
	DDRD&=~(1<<SW1|1<<SW2|1<<SW3); //set pins to input
	PORTD|=(1<<SW1|1<<SW2|1<<SW3);
}
This is how I read them:

Rich (BB code):
		if(PCIFR&1<<PCIF2)//pin change interrupt on Port D
		{
			if(reg.bounce!=1){
				unsigned char port;//can be merged with the bottom one
				port=PIND&((1<<SW3)|(1<<SW2)|(1<<SW1));
				if(reg.sw1&reg.sw2&reg.sw3){reg.pause^=1;}//toggle the pause
				reg.sw1=(port&(1<<SW1))>>SW1;
				reg.sw2=(port&(1<<SW2))>>SW2;
				reg.sw3=(port&(1<<SW3))>>SW3;
				reg.bounce=1;
				i1=0;
			}
				
			PCIFR|=1<<PCIF2;//reset the interrupt flag
		}
And this is the culprit line that, when commented, solved my problems:

Rich (BB code):
DDRD|=(1<<PD3);//turn on the motor pin
I have three switches, wired to pins PD[0:2].

Debouncing:
They are all hardware and software debounced, I have confirmed the operation of the hardware debouncer on an oscilloscope, it works perfectly. The software is a simple 20-40ms timer that disregards readings from the buttons. Also, I wait about a second before depressing the button after I have pressed it and vice versa. Thus, I can be 95% sure that no bouncing occurs.

The problem is the following: If I have all three switches active, the last one (SW3, for example) does not behave properly. It refuses to behave when its especially noisy neigbor, PD3 is set to output (DDRD|=1<<PD3; ). There is a 10kHz PWM signal on this pin. The same happens to SW2, connected to PD1. SW1 (PD0) always behaves.

I noticed that whenever I try and measure the voltage on PD2 with a rather cheap multimeter (i.e. "low" resistance, probably in the order of 1M), the system would behave correctly about 9 out of 10 times. Thus, I decided to put a rather weak 100k pullup on the PD2 pin. I also put caps between all the switch pins and ground. I still get the occasional error, but its now usable.

This leads me to believe that the problem is somewhere in the silicon. Is it somehow possible that the rapid switching of the PD3 (OC02B) pin can be the culprit? What else should I test for to make sure that its not my circuitry thats the problem?

P.S. Please, don't be too harsh on the grammar of this post, its 4AM here and I have been staring at LEDs and code for far too long today.
 
Top