Go Down

Topic: Loop error with Interrupts (Read 148 times) previous topic - next topic

bauermatthews

Hello everyone,

I keep getting the following error:
Quote
core.a(main.cpp.o): In function `main':
/Applications/Arduino.app/Contents/Java/hardware/arduino/avr/cores/arduino/main.cpp:43: undefined reference to `loop'
collect2: error: ld returned 1 exit status
Error compiling.
And I am not sure why. It's my first time using interrupts so I may have made a mess of it.

Code: [Select]
int timer = 500;
int hold = 1000;
int ledpin = 10;
volatile byte f1 = LOW;
volatile byte f2 = LOW;
volatile byte f3 = LOW;
volatile byte f4 = LOW;
volatile int button = 0;
int current;
int stopfloor;


void setup() {
  for (int ledpin = 10; ledpin<14; ledpin++){
    pinMode(ledpin, OUTPUT);
  }
  for (int buttonpin = 2; buttonpin<6; buttonpin++){
    pinMode(buttonpin, INPUT);
  }
 
}

void floorsetup(){
  if(digitalRead(2)==1){
    f1=HIGH;
  }
  if(digitalRead(3)==1){
    f2=HIGH;
  }
  if(digitalRead(4)==1){
    f3=HIGH;
  }
  if(digitalRead(5)==1){
    f4=HIGH;
  }
}

void switchfloor(int number){
  if(number == 1){
    digitalWrite(10,HIGH);
    digitalWrite(11,LOW);
    digitalWrite(12,LOW);
    digitalWrite(13,LOW);
  }
    if(number == 2){
    digitalWrite(10,LOW);
    digitalWrite(11,HIGH);
    digitalWrite(12,LOW);
    digitalWrite(13,LOW);
  }
    if(number == 3){
    digitalWrite(10,LOW);
    digitalWrite(11,LOW);
    digitalWrite(12,HIGH);
    digitalWrite(13,LOW);
  }
    if(number == 4){
    digitalWrite(10,LOW);
    digitalWrite(11,LOW);
    digitalWrite(12,LOW);
    digitalWrite(13,HIGH);
  }
}

void tofloor(int stopfloor, int current){
  if(stopfloor == current){
    switchfloor(stopfloor);
  }
  if(stopfloor>current){
    while(current <= stopfloor){
      switchfloor(current);
      delay(500);
      current = current+1;
    }
  }
  if(stopfloor<current){
    while(current >= stopfloor){
      switchfloor(current);
      delay(timer);
      current = current-1;
    }
  }
  delay(hold);
}


void floorcheck(){
  if(f1==HIGH){
    tofloor(1, current);
    current = 1;
    f1=LOW;
  }
  if(f2==HIGH){
    tofloor(2, current);
    current = 2;
    f2=LOW;
  }
  if(f3==HIGH){
    tofloor(3, current);
    current = 3;
    f3=LOW;
  }
  if(f4==HIGH){
    tofloor(4, current);
    current = 4;
    f4=LOW;
  }
 
}


void returnfloor() {
  switchfloor(1);
  attachInterrupt(2, floorcheck, HIGH);
  attachInterrupt(3, floorcheck, HIGH);
  attachInterrupt(4, floorcheck, HIGH);
  attachInterrupt(5, floorcheck, HIGH);

}

el_supremo

It's telling you that there's no loop() function in your sketch. There must be one and in your case it presumably should be calling one or more of those functions you've declared but which aren't being called by anything.

Pete
Don't send me technical questions via Private Message.

el_supremo

There won't be any interrupts because the function which attaches them, returnfloor(), isn't called by anything either. Attaching interrupts is usually done once and usually from setup().

Pete
Don't send me technical questions via Private Message.

bauermatthews

Thank you, that was a silly mistake. How do I incorporate an interrupt to start the "floorcheck" function if a button is pressed? I'd want it to interrupt the main loop which has been changed from returnfloor to "loop"

el_supremo

As I said, attachInterrupt should only be done once. Changing returnfloor so that it is your loop function means that those four attachInterrupt statements are going to be executed thousands of times a second.
Call the returnfloor function from setup so that the four interrupts are attached - once.

Then add a loop function
Code: [Select]

void loop(void)
{
}


Now, which Arduino are you using?

Pete
Don't send me technical questions via Private Message.

bauermatthews

Right, I'll change that. I'm using an Uno R3

el_supremo

#6
Mar 21, 2017, 04:28 am Last Edit: Mar 21, 2017, 04:28 am by el_supremo
In that case, you're going to have a problem with:
Code: [Select]
  attachInterrupt(2, floorcheck, HIGH);
  attachInterrupt(3, floorcheck, HIGH);
  attachInterrupt(4, floorcheck, HIGH);
  attachInterrupt(5, floorcheck, HIGH);

because there are only two interrupts on UNO. Pins 2 (interrupt 0) and 3 (interrupt 1) can interrupt.
See https://www.arduino.cc/en/Reference/AttachInterrupt

Pete
Don't send me technical questions via Private Message.

bauermatthews

That'll be a problem. Is there any way around this?

GoForSmoke

You don't need interrupts for what you're doing. I see the delays, you don't.

What kind of buttons are you using? Contact switches bounce, they might bounce your interrupt too.

Here is VERY GOOD information about contact switches/buttons:
http://www.gammon.com.au/switches

If your buttons are not contact switches and getting activated 1000+ times a second, then think of interrupts.

Here is VERY GOOD information about interrupts:
http://www.gammon.com.au/interrupts

And just so you know, I am not Nick Gammon but I do appreciate his site tremendously.
Nick Gammon on multitasking Arduinos:
1) http://gammon.com.au/blink
2) http://gammon.com.au/serial
3) http://gammon.com.au/interrupts

sterretje

Don't use interrupts is one solution; I doubt you really need them.

Or use pinchange interrupt. In the interrupt, you can read the Arduino pins.
If you understand an example, use it.
If you don't understand an example, don't use it.

Electronics engineer by trade, software engineer by profession. Trying to get back into electronics after 15 years absence.

bauermatthews

Okay I tried that and now have this:

Code: [Select]
int timer = 500;
int hold = 1000;
int ledpin = 10;
volatile byte f1 = LOW;
volatile byte f2 = LOW;
volatile byte f3 = LOW;
volatile byte f4 = LOW;
volatile int button = 0;
int current=1;
int stopfloor;


void setup() {
  for (int ledpin = 10; ledpin<14; ledpin++){
    pinMode(ledpin, OUTPUT);
  }
  InitialiseIO();
  InitialiseInterrupt();
}

void InitialiseIO(){   
  pinMode(A1, INPUT);   
  digitalWrite(A1, HIGH);   
  pinMode(A2, INPUT);   
  digitalWrite(A2, HIGH);   
   pinMode(A3, INPUT);   
  digitalWrite(A3, HIGH); 
  pinMode(A4, INPUT);   
  digitalWrite(A4, HIGH); 
}

void InitialiseInterrupt(){
  cli();     
  PCICR =0x02;       
  PCMSK1 = 0b00011110;
  sei();   
}

ISR(PCINT1_vect){
  if(digitalRead(A4)==1){
    f1=HIGH;
  }
  if(digitalRead(A3)==1){
    f2=HIGH;
  }
  if(digitalRead(A2)==1){
    f3=HIGH;
  }
  if(digitalRead(A1)==1){
    f4=HIGH;
  }
}

void switchfloor(int number){
  if(number == 1){
    digitalWrite(10,HIGH);
    digitalWrite(11,LOW);
    digitalWrite(12,LOW);
    digitalWrite(13,LOW);
  }
    if(number == 2){
    digitalWrite(10,LOW);
    digitalWrite(11,HIGH);
    digitalWrite(12,LOW);
    digitalWrite(13,LOW);
  }
    if(number == 3){
    digitalWrite(10,LOW);
    digitalWrite(11,LOW);
    digitalWrite(12,HIGH);
    digitalWrite(13,LOW);
  }
    if(number == 4){
    digitalWrite(10,LOW);
    digitalWrite(11,LOW);
    digitalWrite(12,LOW);
    digitalWrite(13,HIGH);
  }
}

void tofloor(int stopfloor, int current){
  if(stopfloor == current){
    switchfloor(current);
    delay(hold);
    return;
  }
  if(stopfloor>current){
    while(current <= stopfloor){
      switchfloor(current);
      delay(timer);
      current = current+1;
    }
   
  }
  else if(stopfloor<current){
    while(current >= stopfloor){
      switchfloor(current);
      delay(timer);
      current = current-1;
    }
   
  }
  //tofloor(stopfloor, current);??
  delay(hold);
}

void loop(){
  current = 1;
  if(f1==HIGH){
    tofloor(1, current);
    current = 1;
    f1=LOW;
  }
  if(f2==HIGH){
    tofloor(2, current);
    current = 2;
    f2=LOW;
  }
  if(f3==HIGH){
    tofloor(3, current);
    current = 3;
    f3=LOW;
  }
  if(f4==HIGH){
    tofloor(4, current);
    current = 4;
    f4=LOW;
  }
  returnfloor();
}


void returnfloor() {
  if(current==1){
    digitalWrite(10,HIGH);
    delay(hold);
    return;
  }
  if(current>1){
    while(current>=1){
      current = current-1;
      switchfloor(current);
      delay(timer);
     
    }
  }current = current +1;
}


It seems like it always lights up all LED's in sequence (1-4) no matter which button i press

sterretje

So you push a button (e.g. A4) and interrupt fires.
You check the states
A4 is LOW so f1 is not affected
A3, A2 and A1 are HIGH so f2, f3 and f4 will be set to HIGH.

You have to redesign your logic a little ;)
If you understand an example, use it.
If you don't understand an example, don't use it.

Electronics engineer by trade, software engineer by profession. Trying to get back into electronics after 15 years absence.

Go Up
 


Please enter a valid email to subscribe

Confirm your email address

We need to confirm your email address.
To complete the subscription, please click the link in the email we just sent you.

Thank you for subscribing!

Arduino
via Egeo 16
Torino, 10131
Italy