219 lines
7.5 KiB
C
Executable File
219 lines
7.5 KiB
C
Executable File
#include "GPIO.h"
|
|
#include "driver/gpio.h"
|
|
#include "parsed_pins.h"
|
|
#include "esp_log.h"
|
|
#include "sdkconfig.h"
|
|
#include "freertos/FreeRTOS.h"
|
|
#include "freertos/task.h"
|
|
#include "esp_timer.h"
|
|
|
|
//external Encoder
|
|
static void IRAM_ATTR index_isr_handler(void *arg);
|
|
static void IRAM_ATTR enc_ab_isr_handler(void *arg);
|
|
|
|
static volatile int64_t delta_index_time = 0;
|
|
static volatile int64_t last_index_time = 0;
|
|
static volatile int64_t delta_AB_time = 0;
|
|
static volatile int64_t last_AB_time = 0;
|
|
|
|
|
|
//internal Encoder
|
|
static void IRAM_ATTR enc_in_isr_handler(void *arg);
|
|
static void IRAM_ATTR enc_in_but_isr_handler(void *arg);
|
|
|
|
static volatile int16_t enc_in_counter = 0;
|
|
static volatile int64_t last_interrupt_time = 0;
|
|
static volatile uint16_t last_interrupt_time_but = 0;
|
|
static volatile bool enc_in_button_state = false;
|
|
static volatile uint8_t last_state = 0;
|
|
|
|
/*############################################*/
|
|
/*############### GPIO-Setup #################*/
|
|
/*############################################*/
|
|
|
|
void configure_GPIO_dir()
|
|
{
|
|
/* reset every used GPIO-pin */
|
|
|
|
gpio_reset_pin(CONFIG_HALL_A_GPIO);
|
|
gpio_reset_pin(CONFIG_HALL_B_GPIO);
|
|
gpio_reset_pin(CONFIG_HALL_C_GPIO);
|
|
|
|
gpio_reset_pin(CONFIG_IN_ENC_A_GPIO);
|
|
gpio_reset_pin(CONFIG_IN_ENC_B_GPIO);
|
|
gpio_reset_pin(CONFIG_IN_ENC_BUT_GPIO);
|
|
|
|
|
|
gpio_reset_pin(CONFIG_EXT_ENC_LEFT_GPIO);
|
|
gpio_reset_pin(CONFIG_EXT_ENC_RIGHT_GPIO);
|
|
|
|
gpio_reset_pin(CONFIG_RFE_GPIO);
|
|
gpio_config_t io_conf_RFE = {};
|
|
io_conf_RFE.intr_type = GPIO_INTR_DISABLE; // Keine Interrupts
|
|
io_conf_RFE.mode = GPIO_MODE_INPUT; // Als Eingang setzen
|
|
io_conf_RFE.pin_bit_mask = (1ULL << CONFIG_RFE_GPIO); // Pin festlegen
|
|
io_conf_RFE.pull_down_en = GPIO_PULLDOWN_DISABLE;
|
|
io_conf_RFE.pull_up_en = GPIO_PULLUP_DISABLE; // Pull-up-Widerstand deaktivieren
|
|
gpio_config(&io_conf_RFE);
|
|
|
|
/* Set the GPIO as a push/pull output*/
|
|
|
|
gpio_set_direction(CONFIG_HALL_A_GPIO, GPIO_MODE_INPUT);
|
|
gpio_set_direction(CONFIG_HALL_B_GPIO, GPIO_MODE_INPUT);
|
|
gpio_set_direction(CONFIG_HALL_C_GPIO, GPIO_MODE_INPUT);
|
|
|
|
gpio_set_direction(CONFIG_IN_ENC_A_GPIO, GPIO_MODE_INPUT);
|
|
gpio_set_direction(CONFIG_IN_ENC_B_GPIO, GPIO_MODE_INPUT);
|
|
gpio_set_pull_mode(CONFIG_IN_ENC_B_GPIO, GPIO_PULLUP_ENABLE);
|
|
gpio_set_direction(CONFIG_IN_ENC_BUT_GPIO, GPIO_MODE_INPUT);
|
|
//gpio_set_direction(CONFIG_BUTTON_GPIO, GPIO_MODE_INPUT);
|
|
|
|
|
|
gpio_set_direction(CONFIG_EXT_ENC_LEFT_GPIO, GPIO_MODE_INPUT);
|
|
gpio_set_direction(CONFIG_EXT_ENC_RIGHT_GPIO, GPIO_MODE_INPUT);
|
|
|
|
|
|
ESP_LOGI("GPIO", "configured for DIY power PCB");
|
|
|
|
gpio_config_t io_conf = {};
|
|
io_conf.pin_bit_mask = (1ULL << CONFIG_EXT_ENC_INDX_GPIO)| (1ULL << CONFIG_HALL_A_GPIO)| (1ULL << CONFIG_IN_ENC_A_GPIO)| (1ULL << CONFIG_IN_ENC_B_GPIO);
|
|
io_conf.mode = GPIO_MODE_INPUT;
|
|
io_conf.pull_up_en = GPIO_PULLUP_ENABLE;
|
|
io_conf.intr_type = GPIO_INTR_ANYEDGE; // Interrupt auf beiden Flanken
|
|
gpio_config(&io_conf);
|
|
|
|
|
|
|
|
gpio_config_t io_conf_negedge = {};
|
|
io_conf_negedge.pin_bit_mask = (1ULL << CONFIG_IN_ENC_BUT_GPIO);
|
|
io_conf_negedge.mode = GPIO_MODE_INPUT;
|
|
io_conf_negedge.pull_up_en = GPIO_PULLUP_ENABLE;
|
|
io_conf_negedge.intr_type = GPIO_INTR_POSEDGE; // Interrupt nur auf positive Flanken
|
|
gpio_config(&io_conf_negedge);
|
|
|
|
gpio_install_isr_service(0);
|
|
ESP_ERROR_CHECK(gpio_isr_handler_add(CONFIG_EXT_ENC_INDX_GPIO, index_isr_handler, NULL));
|
|
ESP_ERROR_CHECK(gpio_isr_handler_add(CONFIG_HALL_A_GPIO, enc_ab_isr_handler, NULL));
|
|
ESP_ERROR_CHECK(gpio_isr_handler_add(CONFIG_IN_ENC_A_GPIO, enc_in_isr_handler, NULL));
|
|
ESP_ERROR_CHECK(gpio_isr_handler_add(CONFIG_IN_ENC_B_GPIO, enc_in_isr_handler, NULL));
|
|
ESP_ERROR_CHECK(gpio_isr_handler_add(CONFIG_IN_ENC_BUT_GPIO, enc_in_but_isr_handler, NULL));
|
|
}
|
|
|
|
/*############################################*/
|
|
/*############### Ext Encoder ################*/
|
|
/*############################################*/
|
|
static void IRAM_ATTR index_isr_handler(void *arg){
|
|
uint64_t current_time = esp_timer_get_time();
|
|
|
|
if (last_index_time != 0){
|
|
delta_index_time = current_time - last_index_time;
|
|
}
|
|
last_index_time = current_time;
|
|
}
|
|
static void IRAM_ATTR enc_ab_isr_handler(void *arg){
|
|
uint64_t current_time = esp_timer_get_time();
|
|
|
|
if (last_AB_time != 0){
|
|
delta_AB_time = current_time - last_AB_time;
|
|
}
|
|
last_AB_time = current_time;
|
|
}
|
|
|
|
float get_speed_index(){
|
|
uint64_t local_delta_time = delta_index_time;
|
|
float speed_rpm = 0;
|
|
if (local_delta_time>0){
|
|
speed_rpm = (60.0*1000000.0/local_delta_time);
|
|
ESP_LOGI("Encoder", "Geschwindigkeit_Indx: %.2f RPM", speed_rpm);
|
|
}
|
|
return speed_rpm;
|
|
}
|
|
float get_speed_AB(){
|
|
uint64_t local_delta_time = delta_AB_time;
|
|
float speed_rpm = 0;
|
|
if (local_delta_time>0){
|
|
speed_rpm = (60.0*1000000.0/local_delta_time)/1000;
|
|
ESP_LOGI("Encoder", "Geschwindigkeit_AB: %.2f RPM", speed_rpm);
|
|
}
|
|
return speed_rpm;
|
|
}
|
|
int get_direction(){//-1=Error,0=right,1=left
|
|
bool right = gpio_get_level(CONFIG_EXT_ENC_RIGHT_GPIO);
|
|
bool left = gpio_get_level(CONFIG_EXT_ENC_LEFT_GPIO);
|
|
int direction;
|
|
if (left && right){
|
|
direction= -1;
|
|
ESP_LOGI("Encoder","Direction: Error");
|
|
}else if(right){
|
|
direction = 0;
|
|
ESP_LOGI("Encoder","Direction: Right");
|
|
}else{
|
|
direction = 1;
|
|
ESP_LOGI("Encoder","Direction: Left");
|
|
}
|
|
return direction;
|
|
|
|
}
|
|
|
|
|
|
/*############################################*/
|
|
/*############ Internal Encoder ##############*/
|
|
/*############################################*/
|
|
|
|
|
|
static void IRAM_ATTR enc_in_isr_handler(void *arg) {
|
|
static uint64_t last_interrupt_time = 0;
|
|
|
|
// Aktueller Zustand der Pins lesen
|
|
uint8_t current_state = (gpio_get_level(CONFIG_IN_ENC_A_GPIO) << 1) | gpio_get_level(CONFIG_IN_ENC_B_GPIO);
|
|
uint64_t interrupt_time = esp_timer_get_time();
|
|
|
|
// Zustandswechsel-Logik (FSM) ohne starre Entprellzeit
|
|
if (current_state != last_state) {
|
|
// Nur wenn der Wechsel signifikant verzögert ist (gute Flanke)
|
|
if ((interrupt_time - last_interrupt_time) > CONFIG_IN_ENCODER_DEBOUNCE_TIME) {
|
|
if ((last_state == 0b01 && current_state == 0b11) ||
|
|
(last_state == 0b10 && current_state == 0b00)) {
|
|
enc_in_counter--; // Vorwärtsdrehen
|
|
} else if ((last_state == 0b10 && current_state == 0b11) ||
|
|
(last_state == 0b01 && current_state == 0b00)) {
|
|
enc_in_counter++; // Rückwärtsdrehen
|
|
}
|
|
last_state = current_state; // Zustand aktualisieren
|
|
last_interrupt_time = interrupt_time;
|
|
}
|
|
}
|
|
}
|
|
|
|
static void IRAM_ATTR enc_in_but_isr_handler(void *arg) {
|
|
uint64_t interrupt_time = esp_timer_get_time();
|
|
|
|
// Entprellung: Verhindert die Erfassung von Störungen aufgrund von Prellung
|
|
if (interrupt_time - last_interrupt_time_but > (CONFIG_IN_ENCODER_DEBOUNCE_TIME*1000)) { // Entprellungszeit
|
|
last_interrupt_time_but = interrupt_time; // Entprellzeit zurücksetzen
|
|
// Bestimmen der Richtung anhand des Zustands von Pin A und B
|
|
if (gpio_get_level(CONFIG_IN_ENC_A_GPIO)) {
|
|
enc_in_button_state = true;
|
|
}
|
|
|
|
}
|
|
}
|
|
|
|
int16_t get_enc_in_counter(){
|
|
ESP_LOGI("Encoder_Int","Counter:%i",enc_in_counter);
|
|
return enc_in_counter;
|
|
}
|
|
|
|
void set_enc_in_counter(int16_t inital_value){
|
|
enc_in_counter = inital_value;
|
|
}
|
|
|
|
bool get_enc_in_but(){
|
|
if (enc_in_button_state){
|
|
enc_in_button_state = false;
|
|
return true;
|
|
}
|
|
else{
|
|
return false;
|
|
}
|
|
} |