Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/xpath/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C AVR:main()/ISR干扰_C_Interrupt_Avr_I2c - Fatal编程技术网

C AVR:main()/ISR干扰

C AVR:main()/ISR干扰,c,interrupt,avr,i2c,C,Interrupt,Avr,I2c,我在C语言的ATmega168(从)上使用I2C(使用avr gcc编译),但这可能是关于中断的一般问题 在我的C程序中,我有一个类型为uint8\u t i2c\u buffer[32]的全局变量,用于存储一些传感器和配置数据。每当总线主设备读取或写入从设备时,I2C-ISR也会访问该阵列。 在硬件中驱动通信时,通过中断触发到ram(我的I2C缓冲变量)的传输 我知道,由于ISR和我的主例程之间的竞争条件,不小心从ISR和主例程访问变量可能会导致数据损坏,但我不确定如何正确处理。 我被告知在m

我在C语言的ATmega168(从)上使用I2C(使用avr gcc编译),但这可能是关于中断的一般问题

在我的C程序中,我有一个类型为
uint8\u t i2c\u buffer[32]
的全局变量,用于存储一些传感器和配置数据。每当总线主设备读取或写入从设备时,I2C-ISR也会访问该阵列。 在硬件中驱动通信时,通过中断触发到ram(我的I2C缓冲变量)的传输

我知道,由于ISR和我的主例程之间的竞争条件,不小心从ISR和主例程访问变量可能会导致数据损坏,但我不确定如何正确处理。 我被告知在main访问相关变量时禁用中断。 这将保护变量不被破坏,但另一方面这不会导致数据丢失吗? 如果主机在中断被禁用的情况下尝试发送数据怎么办

我猜,由于I2C接口仍处于启用状态,传入字节至少会写入TWDR。对吗? 如果是:是否有办法在主例程访问完变量后立即触发ISR


并且:如果一个实例(ISR或main)只读取而不写入缓冲区的特定部分,此问题是否会持续存在?

通常,您需要在主进程(主程序)中创建一个关键部分。当主程序访问共享变量时,需要禁用中断

您有现成的标准解决方案:

 #include <util/atomic.h>

 /* ....*/ 

 ATOMIC_BLOCK(ATOMIC_FORCEON)
 {
     /* potentially non atomic opeartions */
 }
#包括
/* ....*/ 
原子力块(原子力)
{
/*潜在非原子操作*/
}

非常感谢!如果主设备在中断被禁用的情况下进行传输,I2C-ISR是否会在原子_块完成后触发?如果设置了TW中断标志(TWINT),并且启用了TW中断,则立即执行ISR。设置TWINT和启用全局中断时是否相同?这就是想法。只有原子块是受保护的没错!最后一个问题:当使用
ATOMIC_块
时,这实际上会在运行时禁用中断(就像
cli();
那样),还是会在编译时以任何不同的方式使块“原子化”。如果我在for循环中访问变量,我会在每次迭代中“
ATOMIC_BLOCK
”还是包装整个循环?尽量将禁用ISR的时间缩短为possible@SimSon: “如果全局中断状态在进入ATOMIC_块之前不确定,则应使用参数ATOMIC_RESTORESTATE而不是ATOMIC_FORCEON执行。原子_块通过操纵SREG寄存器的全局中断状态(I)位进行操作。”