gpt4 book ai didi

c++ - 在 C++11 中将方法附加到中断例程

转载 作者:行者123 更新时间:2023-11-28 02:08:10 26 4
gpt4 key购买 nike

我正在为我的嵌入式机器人项目编写一个小框架。我们在 Xilinx Zynq FPGA 上运行(FPGA 和 ARM Cortex A9 嵌入在一个芯片上)

思路比较简单。在我的 main() 中,我想初始化中断,然后也从 main 调用例程(run() 方法)。 run() 方法必须以某种方式附加到中断,而它们位于代码中的不同位置。

中断在静态Timer 类中初始化。在 initInterrupt() 中附加了 interruptRoutine(),它也在 Timer 类中。最终,这迫使我们所有的代码都必须在 interruptRoutine() 运行。

我们希望在 main.cc 文件中(在 Timer 类之上)有一个 run() 方法来存储所有的逻辑和所有其他函数调用。

我们怎样才能做到这一点?

main.cc:

int main() {
Timer::initInterrupt();
Timer::run([] {
// All logic goes here?
// Very hopeful thinking that this is possible...
});
}

定时器类:

class Timer {
public:
static void initInterrupt(void);
static void interruptRoutine(void*);
static void run();

};

/**
* Initialize main interrupt routine
*/
void initInterrupt(void) {
// Declare pointers
XScuTimer_Config* ConfigPtr;
XScuGic_Config* IntcConfig;

// Initialize timers by looking up config and initializing with that config
ConfigPtr = XScuTimer_LookupConfig(TIMER_DEVICE_ID);
XScuTimer_CfgInitialize(&TimerInstance, ConfigPtr, ConfigPtr->BaseAddr);
IntcConfig = XScuGic_LookupConfig(INTC_DEVICE_ID);
XScuGic_CfgInitialize(&IntcInstance, IntcConfig,
IntcConfig->CpuBaseAddress);

// Initialize exception handling
Xil_ExceptionInit();
Xil_ExceptionRegisterHandler(XIL_EXCEPTION_ID_IRQ_INT,
(Xil_ExceptionHandler) XScuGic_InterruptHandler, &IntcInstance);

// Connect interrupt routine to exception handler
XScuGic_Connect(&IntcInstance, TIMER_IRPT_INTR,
(Xil_ExceptionHandler) interruptRoutine, (void *) (&TimerInstance));

// Enable interrupts
XScuGic_Enable(&IntcInstance, TIMER_IRPT_INTR);
XScuTimer_EnableInterrupt(&TimerInstance);

// Enable exception handler
Xil_ExceptionEnable();

// Set auto reload so timer reloads when interrupt is cleared
XScuTimer_EnableAutoReload(&TimerInstance);

// Set timer value
XScuTimer_LoadTimer(&TimerInstance, TIMER_LOAD_VALUE);

// Start interrupt
XScuTimer_Start (&TimerInstance);
}
/**
* main interrupt routine
*/
inline void Timer::interruptRoutine(void *CallBackRef) {
// Define pointer to timer
XScuTimer *TimerInstancePtr = (XScuTimer *) CallBackRef;

// If timer is expired, clear interrupt status
if (XScuTimer_IsExpired(TimerInstancePtr)) {
XScuTimer_ClearInterruptStatus(TimerInstancePtr);

// Currently all the application logic is handled in here
}
}

inline void Timer::run(Callback){
// We want all our application logic to be handled in here but it has to be called from the main()
}

最佳答案

在计时器类中,添加一个 bool 标志“timer elapsed”。这个标志是从定时器回调中设置的。

然后主程序通过定时器类中的 getter 函数检查这个标志。

如果设置了标志,main通过定时器类中的setter函数清除标志,然后执行需要执行的代码。

请记住,对标志的访问必须是原子的!假设它不会被中断,这不是来自 ISR 内部的问题,但它可能是上述 setter/getter 函数内部的问题。

请注意,以上可能是最常见的中断设计方式。您将希望避免从 ISR 内部执行实际代码,除非您的实时要求非常严格。

关于c++ - 在 C++11 中将方法附加到中断例程,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36718453/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com