AttachInterrupt and receiving messages problem


  • Contest Winner

    I'm working on a Sketch in which I want to monitor a PIR sensor and be able to control a relais from Domoticz. This combination will replace my PIR controlled front door light. But I'm having a hard time coding the sketch.

    I'm using an Arduino Nano for the development. And this is the Sketch

    #include <SPI.h>
    
    #define SENSOR_ACTIVE_LIGHT 15 // the pin for indicating that the sensor is active.
    #define DIGITAL_INPUT_SENSOR 3   // The digital input you attached your motion sensor.  (Only 2 and 3 generates interrupt!)
    #define RELAIS_ACTIVE_PIN 14 // The pin for the led indicator for indicating whether the relais is on.
    #define INTERRUPT DIGITAL_INPUT_SENSOR-2 // Usually the interrupt = pin -2 (on uno/nano anyway)
    #define CHILD_ID_MOTIONSENSOR 1   // Id of the sensor child
    #define CHILD_ID_RELAY 2 // Id of the relais switch
    
    // Declare variables
    unsigned long SLEEP_TIME = 120000; // Sleep time between reports (in milliseconds)
    MySensor gw;
    boolean lasTrippedValue = false;
    
    // Initialize motion message
    MyMessage msgMotionSensor( CHILD_ID_MOTIONSENSOR, V_TRIPPED );
    // Change to V_LIGHT if you use S_LIGHT in presentation below
    MyMessage msgRelaisActuator( CHILD_ID_RELAY, V_LIGHT );
    
    void setup()  
    {
      Serial.begin(115200);  
      gw.begin(incomingMessage);
    
      // Send the sketch version information to the gateway and Controller
      gw.sendSketchInfo("Motion Sensor", "1.0");
    
      pinMode( DIGITAL_INPUT_SENSOR, INPUT );      // sets the motion sensor digital pin as input
      pinMode( SENSOR_ACTIVE_LIGHT, OUTPUT );      // visual indicator for motion detection
      pinMode (RELAIS_ACTIVE_PIN, OUTPUT );
      attachInterrupt(digitalPinToInterrupt( DIGITAL_INPUT_SENSOR ), pirSensorValueChanged, CHANGE); // attach interrupt handler to the PIR motion sensor.
    
      // Register all sensors to gw (they will be created as child devices)
      gw.present(CHILD_ID_MOTIONSENSOR, S_MOTION);
      gw.present(CHILD_ID_RELAY, S_LIGHT);
      digitalWrite( SENSOR_ACTIVE_LIGHT, LOW );
    }
    
    void loop()     
    {     
      // space for Hummidity and Temp reading
      gw.wait(50);
    }
    
    void incomingMessage(const MyMessage &message) {
      Serial.println("message");
      // We only expect one type of message from controller. But we better check anyway.
      if (message.type==V_LIGHT) {
         if ( message.sensor == CHILD_ID_RELAY ) {
            digitalWrite( RELAIS_ACTIVE_PIN, message.getBool()? HIGH :LOW );
         }
       }
    }
    
    void pirSensorValueChanged() {
      boolean tripped = digitalRead(DIGITAL_INPUT_SENSOR) == HIGH;
      digitalWrite( SENSOR_ACTIVE_LIGHT, tripped? HIGH :LOW );
      gw.send(msgMotionSensor.set(tripped?"1":"0"));  // Send tripped value to gw
    }
    

    I'm trying to attach an interrupt handler to the PIR motion sensor, so that I keep my main loop clean. If possible I want to attach a DHT11 sensor, so that I can measure the temperature and humidity of the little work shop in which the Arduino will be mounted. Be keeping my loop clean, I can put the code for temp measurement there, without having to schedule the measurements.

    The problem is that the Sketch causes the Arduino to crash. I have manage to find out where abouts it happens. It happens when my Arduino receives a message from the GateWay. After a couple of runs from the loop. I see the the following text in the serial monitor:
    me

    Which should be "message"- which is in the incomingMessage method - and my arduino stalls. It doesn't do anything. What am I doing wrong?

    Updated: attached a new version of the Sketch. In the last one, the attaching of the interrupt handler was commented out. That was for my own test purpose to see if the interrupt handler caused the problem and it did.


  • Contest Winner

    Update:

    It looks like the interrupt handler is interfering with the MySensors core. Before the sketch stalls, I see that the communication is getting lost. I get failures. Then the sensors tries to connect to the parent again, in the following example it succeeds with that, but just a little bit later the sketch stalls.

    send: 1-1-0-0 s=1,c=1,t=16,pt=0,l=1,sg=0,st=ok:1
    read: 0-0-1 s=2,c=1,t=2,pt=0,l=1,sg=0:1
    message
    send: 1-1-0-0 s=1,c=1,t=16,pt=0,l=1,sg=0,st=ok:0
    read: 0-0-1 s=2,c=1,t=2,pt=0,l=1,sg=0:0
    message
    send: 1-1-0-0 s=1,c=1,t=16,pt=0,l=1,sg=0,st=ok:1
    send: 1-1-0-0 s=1,c=1,t=16,pt=0,l=1,sg=0,st=ok:0
    send: 1-1-0-0 s=1,c=1,t=16,pt=0,l=1,sg=0,st=ok:1
    send: 1-1-0-0 s=1,c=1,t=16,pt=0,l=1,sg=0,st=fail:0
    send: 1-1-0-0 s=1,c=1,t=16,pt=0,l=1,sg=0,st=fail:1
    send: 1-1-0-0 s=1,c=1,t=16,pt=0,l=1,sg=0,st=fail:0
    send: 1-1-0-0 s=1,c=1,t=16,pt=0,l=1,sg=0,st=fail:1
    send: 1-1-0-0 s=1,c=1,t=16,pt=0,l=1,sg=0,st=fail:0
    send: 1-1-0-0 s=1,c=1,t=16,pt=0,l=1,sg=0,st=fail:1
    find parent
    send: 1-1-255-255 s=255,c=3,t=7,pt=0,l=0,sg=0,st=bc:
    read: 0-0-1 s=2,c=1,t=2,pt=0,l=1,sg=0:1
    message
    read: 0-0-1 s=2,c=1,t=2,pt=0,l=1,sg=0:0
    message
    read: 0-0-1 s=2,c=1,t=2,pt=0,l=1,sg=0:1
    message
    read: 0-0-1 s=255,c=3,t=8,pt=1,l=1,sg=0:0
    parent=0, d=1
    read: 0-0-1 s=2,c=1,t=2,pt=0,l=1,sg=0:1
    me
    


  • @TheoL I'm also having this problem using TimerOne.
    My code is simply
    Timer1.initialize(freqStep); // Initialize TimerOne library for the freq we need 75uS
    Timer1.attachInterrupt(dim_check);

    This code is part of a 2xSSR and 2x Triac Dimmer project.
    The SSR's work fine being controlled by Veralite so long as the attachInterrupt is commented out. as soon as the line is included, Vera cannot control the SSR's.

    I wonder if Mysensors might have something to do with the problem. Hope Hek sees this post and can reply


  • Hardware Contributor

    Maybe this could be a comcurrency problem. The code inside the interrupt-routines should be very short (calc some values und flag variables). The main code is then in the loop.

    Try to avoid calling mysensor code (e.g. gw.send) in the interrupt routine and keep it as short as possible.


  • Contest Winner

    @FotoFieber it might be. I have taken a different road with the code and completely skipped using interrupts. But it might be worth trying. Even thought the sending of a message doesn't take a lot of time on the node part. And I wasn't using the ACK mechanism.

    I know I tested the interrupt handler with a single Serial.println() statement which still caused the Sketch to stop. But what might help is using interrupts() and noInterrupts() in the interruptHandler. I just typed the following code directly in this post so it might give compile errors, but I think you'll get the idea.

    void pirSensorValueChanged() {
      noInterrupts();
      boolean tripped = digitalRead(DIGITAL_INPUT_SENSOR) == HIGH;
      digitalWrite( SENSOR_ACTIVE_LIGHT, tripped? HIGH :LOW );
      gw.send(msgMotionSensor.set(tripped?"1":"0"));  // Send tripped value to gw
      interrupts();
    }
    

  • Admin

    As @FotoFieber says, keep interrupt handler to a absolute minimum. Like updating a status flag.

    You cannot call mysensors functions like send in there.



  • Hello again
    I've attached a version which show/demonstrates the problem I have when using Timer1.attachInterrupt(dim_check, freqStep);. I'm using a Veralite and simple pro mini arduino to controll 2x SSR and 2x Triac dimmers. I use a structured array to hole the various valus for the lamps.
    When I upload a version of this attached code with Timer1.attachInterrupt(dim_check, freqStep);commented out - the SSR's work fine.
    When I uncomment the one line in the code the is no response to the Vera's command to switch on a SSR lamp.
    As you can see the interrupt routine is extremely short - nothing but the call.
    I wonder if someone else might have any idea or have run into this problem before.. The interrupt is to occur every 75uS so as to allow 128 steps of dimming.Timer1Testing.ino


 

280
Online

8.5k
Users

9.3k
Topics

98.7k
Posts