-1

I would like to share interrupt routine between class. I followed this tutorial.

But I need to call a member function in callback function, I have the issue : enter image description here

This is my code :

Timer.h

static void (*__handleISR)(void);

class Timer
{
    public:
        Timer();
        ~Timer();
        static void init();
        static void handleISR(void (*function)(void));
};

Timer.cpp

Timer::Timer()
{
}

Timer::~Timer()
{}

void Timer::init()
{    
    TCCR2A = 0; //default 
    TIMSK2 = 0b00000001; // TOIE2
}

ISR (TIMER2_OVF_vect) 
{
    // 256-6=250 --> (250 x 16uS = 4mS)
    // Recharge le timer pour que la prochaine interruption se declenche dans 4mS
    TCNT2 = 6;

    __handleISR();
}

Device.h

class Device
{
    public:
        Device();

    private:
        void isr();
};

Device.cpp

Device::Device()
{
    Timer::init();
    Timer::handleISR(isr);
}

void Device::isr()
{
    // Do my stuff
}

If I set function isr() static, it works. But I need to call member from Device in isr().

How I can call non static member function ? Or another solution ?

2
  • 1
    Do none of these results help you? arduino.stackexchange.com/… Commented Aug 17, 2022 at 15:56
  • nop the solution is with static member Commented Aug 18, 2022 at 5:28

1 Answer 1

1

This is not an Arduino specific question but a C++ question, and as such you might get more or better answers on StackOverflow. Anyway, I'll suggest a possible solution.

A member method always receives a pointer to its object as a hidden first argument that we know as this. Only via this argument such a method is able to access member attributes or member methods.

A class method does not have this parameter.

The function type you define is compatible only to functions or class methods.

So you need to provide a pointer (or reference) to the Device object.

I reduced your example and replaced the interrupt macro with something a standard C++ compiler accepts, as this is not part of the issue.

Timer.h

#ifndef TIMER_H
#define TIMER_H

#include "Device.h"

class Timer
{
    public:
        static void setCallback(void (*function)(Device*), Device*);
};

#endif

Timer.cpp

#include "Timer.h"

#define ISR(f) void f()

static void (*_function)(Device*);
static Device* _device;

void Timer::setCallback(void (*function)(Device*), Device* device)
{
    _function = function;
    _device = device;
}

ISR(TIMER2_OVF_vect) 
{
    _function(_device);
}

Device.h

#ifndef DEVICE_H
#define DEVICE_H

class Device
{
    public:
        Device();

    private:
        static void isr(Device* device);
        void isr();
};

#endif

Device.cpp

#include "Device.h"
#include "Timer.h"

Device::Device()
{
    Timer::setCallback(isr, this);
}

void Device::isr(Device* device)
{
    device->isr();
}

void Device::isr()
{
    // Do my stuff
}

If you don't need the Device object, you don't need a member method. Then go with a class method, as you already found out.

0

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.