Go Down

Topic: Sine wave reading in... Interrupt pins not working? (Read 1 time) previous topic - next topic

CloDawg

I have a MEGA 2560 : External Interrupts: 2 (interrupt 0), 3 (interrupt 1), 18 (interrupt 5), 19 (interrupt 4), 20 (interrupt 3), and 21 (interrupt 2). These pins can be configured to trigger an interrupt on a low value, a rising or falling edge, or a change in value. See the attachInterrupt() function for details.

I amtrying to generate a interupt on the rising edge of a sine wave. I im running the code below, but im having problems with the innterupts. only intterupt 2 seemed to be working (Timer interrupt DOES work fine). I know this because if i change the inerupt number between my 2 interupts only the one connected to pin21 (interrupt 2) works. The other is always a factor of 10-100 times faster than it should be.

I have an LCD connected.

Quote
#include <TimerThree.h>



// These constants won't change.  They're used to give names
// to the pins used:
const int WindInPin = A0;  // Analog input pin for the Wind direction - Potentiometer
const int TurbineInPin = A1;  // Analog input pin for the Turbine orientation - Potentiometer

float maxallow = 0.0;
int degout = 0;
float K = 0.0;
float direc = 0.0;
float error = 0.0;

volatile int count3 = 0;

volatile float WindMS[10] = {0,0,0,0,0,0,0,0,0,0};
volatile float TurRPM[10] = {0,0,0,0,0,0,0,0,0,0};
volatile float sumTurRPM = 0.0;
volatile float sumWindMS = 0.0;

volatile float turrpm = 0.0;
volatile float windms = 0.0;

volatile int Count1 = 0;
volatile int Count2 = 0;

const float CRMP = 367.4;
const float k1 = 22.33;
const float k = 0.708;
const float k2 = 0.763;

const float pi = 3.14;

const int analogOutPin = 9; // Analog output driver is attached to this pin

int WindValue = 0;        // value read from the Wind direction - Potentiometer
int TurbineValue = 0;     // value read from the Turbine orientation - Potentiometer

int outputValue = 0;        // value output to the PWM (driver - analog out)

void setup() {
 // initialize serial communications at 9600 bps:
 Serial.begin(9600);
 
 attachInterrupt(1, WindSpeed, RISING);
 attachInterrupt(2, TurbineRPM, RISING);
//  Timer3.attachInterrupt(Second);
 backlightOn();
}

void loop() {
 // read the analog in value:
//  Timer3.initialize(1000000);
 WindValue = analogRead(WindInPin);      
 TurbineValue = analogRead(TurbineInPin);    

 error = WindValue - TurbineValue;
 
 if (error < 0.0){
   error = error*-1;
   direc = 0.0;}
 else
   direc = 1.0;
   
 
   if(turrpm>0.0)
 maxallow = CRMP/turrpm; //Maxallowin RPM
 else
 maxallow = 0.0 ;
 
 //convert to motor max RPM /50 for gear ratio and max
 if((error >= 10.625) || (maxallow >= 6.67)) // bigger than 15deg or maxallow speed
   maxallow = 335.0;
 else
 {  
   maxallow = maxallow*50;
   degout= error/k;
   if(degout < 2)
   maxallow = 8.33;
   else{
     degout = degout-1;
   maxallow = degout*k1;
   
   }
 }
 
 //convert to 0-5V output range
 maxallow = maxallow*k2;
 // map it to the range of the analog out:
 outputValue = map(maxallow, 0, 1023, 0, 255);  
 // change the analog out value:
 
 analogWrite(analogOutPin, outputValue);
 

 // print the results to the serial monitor:
 goTo(0);
Serial.print("Turb RPM: " );                      
Serial.print(turrpm);  
 goTo(16);
Serial.print("Wind Sped: ");      
Serial.println(Count1);  

 // wait 10 milliseconds before the next loop
 // for the analog-to-digital converter to settle
 // after the last reading:
 delay(10);                    
}

void Second()
{
 
 for (int i = 0; i < 9; i++)
 {
   sumTurRPM = TurRPM[i+1] +sumTurRPM;
   sumWindMS = WindMS[i+1] +sumWindMS;
   
   TurRPM = TurRPM[i+1];
   WindMS = WindMS[i+1];
 }
   
 TurRPM[9] = (Count1*15); //Gives Turbine in RPM
 Count1 = 0;
 
 turrpm = (sumTurRPM + TurRPM[9])/10;
 sumTurRPM = 0;
 
 //Gives wind in ms
 WindMS[9] = (2*pi*6*(Count2*60))/(60*100); //wind M/S
 Count2 = 0;
 
 windms = (sumWindMS + WindMS[9])/10;
 sumWindMS = 0;
}
 
void WindSpeed()
{
 Count2 = Count2 +1;
}
void TurbineRPM()
{
 Count1 = Count1 +1;
}

void goTo(int position) { //position = line 1: 0-15, line 2: 16-31, 31+ defaults back to 0
if (position<16){ Serial.print(0xFE, BYTE);   //command flag
             Serial.print((position+128), BYTE);    //position
}else if (position<32){Serial.print(0xFE, BYTE);   //command flag
             Serial.print((position+48+128), BYTE);    //position
} else { goTo(0); }
  delay(10);
}

void backlightOn(){  //turns on the backlight
   Serial.print(0x7C, BYTE);   //command flag for backlight stuff
   Serial.print(157, BYTE);    //light level.
  delay(10);
}


What is goin on? I need to use these other interrupt ports.

Grumpy_Mike

Quote
What is goin on?

You are hitting the wrong button when posting the code you should use the # icon not the quote one next to it.

What is your hardware arrangement? You just can't feed a sin wave into an arduino.

PeterH

I'm not familiar with this, but isn't pin 21 a signal line for the TWI? Maybe that is interfering with what you're trying to do.

You don't seem to be initialising the pin mode or pull-up status for any of your inputs/outputs. I think explicitly initialising all the pins you use would make things more obvious.

How clean is your input signal? Depending how it's connected up, you could easily be triggering off noise on the line, rather than a clean sin wave. Have you tried scoping it? (Many years ago I tried to use current ripple to detect speed on a DC motor - utterly hopeless because there was far too much noise!)
I only provide help via the forum - please do not contact me for private consultancy.

CloDawg

Ok with a bit of mucking about i managed to figure out how to get it too work. The other interrupts start to work if i change the input to a square wave, interrupt 2 seems to be the only one to work with the sine wave. Thats ok. i actually only need to read in 1 sine wave, and one square.

Quote
What is your hardware arrangement? You just can't feed a sin wave into an arduino


Im using a function generator to create the signal so its a pretty acurate sine wave. This also means the input current is low, so i dont need to

Quote
I'm not familiar with this, but isn't pin 21 a signal line for the TWI? Maybe that is interfering with what you're trying to do.


TWI? well its the only one working?

Quote
You don't seem to be initialising the pin mode or pull-up status for any of your inputs/outputs. I think explicitly initialising all the pins you use would make things more obvious.


Do i need to initialise the interrupt pins? in the example it didnt say i have to, and does pull-up status reffer to pull up resistors?

Thanks

Grumpy_Mike

Quote
This also means the input current is low, so i dont need to

need to what?

A sin wave will put a negative 5V on the input, what are you doing about that. Don't say nothing. Also the rise and fall time of a sin wave means that the logic triggering is not going to be very good. You need some way of squaring it up. Best is with a buffer with a bit of hysteresis, something like a 74LS14.

GoForSmoke

I find it harder to express logic in English than in Code.
Sometimes an example says more than many times as many words.

Go Up