用ESP32通过SPI读取设备数据,采用GPIO中断方式触发读取,设备数据准备好后通过GPIO5上升沿触发。GPIO的配置完全按照例程设置,SPI的配置是在eeprom例程的基础上改的。
现象是运行程序可以进入中断读取设备数据,但读取一段时间后,中断不再触发。
中断不触发的原因是设备数据准备好发出上升沿后,如果没有通过SPI读取数据,则设备输出将保持高电平,不会在输出上升沿,直到读取数据后恢复正常。我这样判断的原因是在main_app()函数的循环中加入延时和读取数据的操作后,可以连续产生中断,不会停止。
我的问题是:如何保证每次上升沿中断都被触发并调用中断服务函数?设备正常输出上升沿触发中断的频次是3200次/秒。
IO配置程序如下:
#define GPIO_INPUT_IO_1 5
#define GPIO_INPUT_PIN_SEL (1ULL<<GPIO_INPUT_IO_1)
#define ESP_INTR_FLAG_DEFAULT 0
static xQueueHandle gpio_evt_queue = NULL;
eeprom_handle_t eeprom_handle;
short Accel_RAW[3] = {0,0,0};
void get_acc(void){
Accel_Device_Read_Accel_Raw(eeprom_handle, Accel_RAW);//读取设备数据
printf("x = %d, y = %d, z= %d.\r\n", Accel_RAW[0],Accel_RAW[1],Accel_RAW[2]);//输出
}
static void IRAM_ATTR gpio_isr_handler(void* arg)
{
uint32_t gpio_num = (uint32_t) arg;
xQueueSendFromISR(gpio_evt_queue, &gpio_num, NULL);
}
static void gpio_task_example(void* arg)
{
uint32_t io_num;
for(;;) {
if(xQueueReceive(gpio_evt_queue, &io_num, portMAX_DELAY)) {
printf("GPIO[%d] intr, val: %d\n", io_num, gpio_get_level(io_num));
get_acc();
}
vTaskDelay(10 / portTICK_RATE_MS);
}
}
void app_main(void)
{
ESP_ERROR_CHECK(init_services());
// Set UART log level
esp_log_level_set(TAG, ESP_LOG_INFO);
ESP_LOGI(TAG, "Initializing device...");
//zero-initialize the config structure.
gpio_config_t io_conf = {};
//interrupt of rising edge
io_conf.intr_type = GPIO_INTR_POSEDGE;
//bit mask of the pins, use GPIO4/5 here
io_conf.pin_bit_mask = GPIO_INPUT_PIN_SEL;
//set as input mode
io_conf.mode = GPIO_MODE_INPUT;
//enable pull-up mode
io_conf.pull_down_en = 1;
gpio_config(&io_conf);
//create a queue to handle gpio event from isr
gpio_evt_queue = xQueueCreate(10, sizeof(uint32_t));
//start gpio task
xTaskCreate(gpio_task_example, "gpio_task_example", 2048, NULL, 10, NULL);
//install gpio isr service
gpio_install_isr_service(ESP_INTR_FLAG_DEFAULT);
//hook isr handler for specific gpio pin
gpio_isr_handler_add(GPIO_INPUT_IO_1, gpio_isr_handler, (void*) GPIO_INPUT_IO_1);
Accel_Device_Read_Accel_Raw(eeprom_handle, Accel_RAW);// 读取设备数据
ESP_LOGI(TAG, "Initialization finished.");
while (1) {
ESP_LOGI(TAG, "In main\r\n");
vTaskDelay(1000 / portTICK_RATE_MS);
// Accel_Device_Read_Accel_Raw(eeprom_handle, Accel_RAW);//加入这句后中断可以连续触发,不会停止
}
GPIO中断漏触发
Jump to
- English Forum
- Explore
- News
- General Discussion
- FAQ
- Documentation
- Documentation
- Sample Code
- Discussion Forum
- Hardware
- ESP-IDF
- ESP-BOX
- ESP-ADF
- ESP-MDF
- ESP-WHO
- ESP-SkaiNet
- ESP32 Arduino
- IDEs for ESP-IDF
- ESP-AT
- ESP IoT Solution
- ESP RainMaker
- Rust
- ESP8266
- Report Bugs
- Showcase
- Chinese Forum 中文社区
- 活动区
- 乐鑫活动专区
- 讨论区
- 全国大学生物联网设计竞赛乐鑫答疑专区
- ESP-IDF 中文讨论版
- 《ESP32-C3 物联网工程开发实战》书籍讨论版
- 中文文档讨论版
- ESP-AT 中文讨论版
- ESP-BOX 中文讨论版
- ESP IoT Solution 中文讨论版
- ESP-ADF 中文讨论版
- ESP Mesh 中文讨论版
- ESP Cloud 中文讨论版
- ESP-WHO 中文讨论版
- ESP-SkaiNet 中文讨论版
- ESP 生产支持讨论版
- 硬件问题讨论
- 项目展示
Who is online
Users browsing this forum: No registered users and 84 guests
- All times are UTC
- Top
- Delete cookies
About Us
Espressif Systems is a fabless semiconductor company providing cutting-edge low power WiFi SoCs and wireless solutions for wireless communications and Internet of Things applications. ESP8266EX and ESP32 are some of our products.