Кто любит RISC в жизни, заходим, не стесняемся.
Ответить

stm32f4 cmsis ADC прерывание

Вс дек 29, 2019 14:59:22

void inits_adc(void)
{
RCC->AHB1ENR|=RCC_AHB1ENR_GPIOAEN;
RCC->APB2ENR |= RCC_APB2ENR_ADC1EN;
GPIOA->MODER |= GPIO_MODER_MODER0_1;
GPIOA->MODER |= GPIO_MODER_MODER0_0;
GPIOA->PUPDR &=~GPIO_PUPDR_PUPDR0_1;
GPIOA->PUPDR &=~ GPIO_PUPDR_PUPDR0_0;


ADC->CCR&= ~ ADC_CCR_ADCPRE;
// ADC1->CR1|= ADC_CR1_EOCIE;

// ADC1->CR2 |=ADC_CR2_CONT;
ADC1->CR2 |=ADC_CR2_EXTEN;

ADC1->CR2|=ADC_CR2_EXTSEL;
ADC1->SMPR2 &= ~(ADC_SMPR2_SMP1_2 | ADC_SMPR2_SMP1_1 | ADC_SMPR2_SMP1_0);

/* номер канал */
ADC1->SQR3 &=~ ADC_SQR3_SQ1_0; //1 IN0
ADC1->SQR3 &= ~ ADC_SQR3_SQ3_1; //0
ADC1->SQR3 &= ~ADC_SQR3_SQ1_2; //0
ADC1->SQR3 &=~ ADC_SQR3_SQ1_3; //0
ADC1->SQR3 &= ~ADC_SQR3_SQ1_4;//0
// ADC1->CR2 |=ADC_CR2_CONT;
ADC1->CR1|= ADC_CR1_EOCIE;
//ADC1->SR=0;


//NVIC_EnableIRQ (ADC_IRQn);
ADC1->CR2 |= ADC_CR2_ADON;
NVIC_EnableIRQ (ADC_IRQn);

}


void inits_adc2(void)
{

}
void inits_GPIOC(void)
{
RCC->AHB1ENR|=RCC_AHB1ENR_GPIOCEN;


GPIOC->MODER &=~ GPIO_MODER_MODER13_1;
GPIOC->MODER |= GPIO_MODER_MODER13_0;
GPIOC ->OTYPER &=~GPIO_OTYPER_OT13;
//бит0 определяет скорость работы GPIO
GPIOC->OSPEEDR &=~ GPIO_OSPEEDER_OSPEEDR13_1; //бит1
GPIOC->OSPEEDR &=~ GPIO_OSPEEDER_OSPEEDR13_0;
GPIOC->PUPDR |=GPIO_PUPDR_PUPDR13_1;
GPIOC->PUPDR &=~ GPIO_PUPDR_PUPDR13_0;
/* настройка на вход */

// RCC->AHB1ENR|=RCC_AHB1ENR_GPIOCEN;

GPIOC->MODER &=~ GPIO_MODER_MODER0_1;
GPIOC->MODER &=~ GPIO_MODER_MODER0_0;
GPIOC ->OTYPER &=~GPIO_OTYPER_OT0;
//бит0 определяет скорость работы GPIO
GPIOC->OSPEEDR &=~ GPIO_OSPEEDER_OSPEEDR0_1; //бит1
GPIOC->OSPEEDR &=~ GPIO_OSPEEDER_OSPEEDR0_0;
GPIOC->PUPDR &=~ GPIO_PUPDR_PUPDR0_1;
GPIOC->PUPDR |= GPIO_PUPDR_PUPDR0_0;

GPIOC->MODER &=~ GPIO_MODER_MODER1_1;
GPIOC->MODER |= GPIO_MODER_MODER1_0;
GPIOC ->OTYPER &=~GPIO_OTYPER_OT1;
//бит0 определяет скорость работы GPIO
GPIOC->OSPEEDR &=~ GPIO_OSPEEDER_OSPEEDR1_1; //бит1
GPIOC->OSPEEDR &=~ GPIO_OSPEEDER_OSPEEDR1_0;
GPIOC->PUPDR |=GPIO_PUPDR_PUPDR1_1;
GPIOC->PUPDR &=~ GPIO_PUPDR_PUPDR1_0;
}

int main(void)
{
inits_GPIOC();
//inits_adc();


//ADC1->CR2 |= ADC_CR2_SWSTART;
//inits_timer1();
// inits_timer3();
// inits_timer5();
//inits_timer3();
inits_adc();

ADC1->CR2|= ADC_CR2_SWSTART;

while(1)
{


//ADC1->CR2 |= ADC_CR2_SWSTART; //Запуск преобразований
// while (!(ADC1->SR & ADC_SR_EOC)); //ждем пока первое преобразование завершится
//ADC1->SR &=~ADC_SR_EOC ;
// ADC1->SR = 0;
//adc_data = ADC1->DR;

// if(adc_data > 2024)
// {
// GPIOC->ODR|=1<<13;
// GPIOC->BSRR |= GPIO_BSRR_BS13;
// }
// else
// {
// // GPIOC->ODR&=~1<<13;
// GPIOC->BSRR |= GPIO_BSRR_BR13;
// }
}
}
void adc_IRQhanler(void)
{
if(ADC1->SR & ADC_SR_EOC)
{
ADC1->SR &=~ ADC_SR_EOC;
// ADC1->SR = 0;
adc_data = ADC1->DR;
if(adc_data>2045)
{
GPIOC-> BSRR |=GPIO_BSRR_BS13;
}
else
{
GPIOC-> BSRR |=GPIO_BSRR_BR13;
}
}
}
работает в основном цикле не работает в прерывании в чём дело не понимаю

Re: stm32f4 cmsis ADC прерывание

Пн дек 30, 2019 14:48:50

ivan dimir писал(а):работает в основном цикле не работает в прерывании в чём дело не понимаю
казнить нельзя помиловать __enable_irq ();

Re: stm32f4 cmsis ADC прерывание

Пн дек 30, 2019 17:48:22

и так тоже не работает ни ацп ни таймер

Re: stm32f4 cmsis ADC прерывание

Пн дек 30, 2019 18:20:51

казнить нельзя помиловать __enable_irq ();
У Cortex-M они включены по умолчанию при включении.

и так тоже не работает ни ацп ни таймер
Информацию из вас клещами тянуть? Какая среда разработки, какой стартап, какой режим компилятора? Я то может там банальный extern "C"...

Re: stm32f4 cmsis ADC прерывание

Пн дек 30, 2019 19:09:19

ivan dimir, сброс флага неверный.
Код:
ADC1->SR &=~ ADC_SR_EOC;
исправте на
Код:
ADC1->SR  =~ ADC_SR_EOC;
Это конечно не решит Вашу проблему, но убережет от новых.

Re: stm32f4 cmsis ADC прерывание

Пн дек 30, 2019 19:15:30

extern "C"... отключён среда компиляции atolic truestudio проект создаю с нуля.включаю прерывание по ацп и отключается таймер.Вместе таймера работают как часики.Когда включаешь ацп не в прерывании всё хорошо работает.Проект создавал в С не в С++.startap_stm32f407xx.s. режим компилятора?оптимизация?

Добавлено after 1 minute 59 seconds:
ADC1->SR &=~ ADC_SR_EOC; а почему в Hal это работает?

Re: stm32f4 cmsis ADC прерывание

Пн дек 30, 2019 19:34:07

ivan dimir писал(а):а почему в Hal это работает?
Во вторых, &= это чтение, побитовое И, запись, т.е. лишние команды без необходимости (запись 1 в регистр статуса никак не влияет на содержимое).
А во первых, если между чтением и записью установится другой флаг в данном регистре, вы его сбросите, так и не узнав, что он был установлен. Заколебешься потом искать, почему, в редких случаях не вызывается прерывание.

Если в ХАЛе так, значит там косяк.

Добавлено after 1 minute 20 seconds:
Отладчик работает? Тормознитесь где-нибудь и поглядите, что в регистрах SR. От этого уже можно сделать какой-либо вывод.

Re: stm32f4 cmsis ADC прерывание

Пн дек 30, 2019 20:05:59

/*
* main.c
*
* Created on: 29 жовт. 2019 р.
* Author: Ivan
*/

#include"main.h"
//#include "stm32f103xb.h"
//#include "stm32f1xx.h"
volatile unsigned int flag=0;
volatile unsigned int adc_data=0;
void ADC1_2_IRQHandler()
{
while (!(ADC1->SR & ADC_SR_EOC)); //ждем пока первое преобразование завершится
ADC1->SR &=~ ADC_SR_EOC;
adc_data = ADC1->DR;

if(adc_data > 2024)
{

GPIOC->BSRR |= GPIO_BSRR_BS13;
}
else
{

GPIOC->BSRR |= GPIO_BSRR_BR13;
}
}


void init_ADC1(void)
{

RCC->APB2ENR|=RCC_APB2ENR_IOPCEN;
GPIOC->CRH&=~GPIO_CRH_CNF13;
GPIOC->CRH|= GPIO_CRH_MODE13_1;
RCC->CFGR &=~ RCC_CFGR_ADCPRE;

RCC->APB2ENR|=RCC_APB2ENR_IOPAEN;

GPIOA->CRL&=~GPIO_CRL_CNF1;
GPIOA->CRL&=~ GPIO_CRL_MODE1;

RCC->APB2ENR |= RCC_APB2ENR_ADC1EN;
RCC->CFGR |= RCC_CFGR_ADCPRE_DIV2;

//подаем тактирование АЦП
ADC1->CR2 |= ADC_CR2_RSTCAL;
while (!(ADC1->CR2 & ADC_CR2_RSTCAL))
{
}
ADC1->CR2 |= ADC_CR2_CAL;
while (!(ADC1->CR2 & ADC_CR2_RSTCAL))
{
}

ADC1->CR2 |=ADC_CR2_CONT;//включить АЦП
ADC1->CR2 |= ADC_CR2_EXTSEL;

ADC1->CR2 |= ADC_CR2_EXTTRIG;


ADC1->SQR3 |= ADC_SQR3_SQ1_0; //1 IN1
ADC1->SQR3 &= ~ ADC_SQR3_SQ1_1; //0
ADC1->SQR3 &= ~ADC_SQR3_SQ1_2; //0
ADC1->SQR3 &=~ ADC_SQR3_SQ1_3; //0
ADC1->SQR3 &= ~ADC_SQR3_SQ1_4;

ADC1->SMPR2 &=~ ADC_SMPR2_SMP1_0; //1
ADC1->SMPR2&=~ADC_SMPR2_SMP1_1; //1
ADC1->SMPR2 &=~ ADC_SMPR2_SMP1_2; //1
}

int main(void)
{

//inits_GPIO();

init_ADC1();
ADC1->CR1|= ADC_CR1_EOCIE;
ADC1->CR2 |= ADC_CR2_ADON;
NVIC_EnableIRQ ( ADC1_2_IRQn);
ADC1->CR2 |= ADC_CR2_SWSTART;
while(1)
{


}
}
вот работающий код в stm32f103

Добавлено after 1 minute 2 seconds:
Я думаю никаких косяков нет.Ваш вариант не работает

Re: stm32f4 cmsis ADC прерывание

Пн дек 30, 2019 20:10:31

ivan dimir писал(а):Я думаю никаких косяков нет.Ваш вариант не работает
Я объяснил почему. Что значит не работает? Сброса флага нет или что?

З.Ы. Для кода есть специальные тэги и спрячьте его под спойлер. Нечитаемо же.

Re: stm32f4 cmsis ADC прерывание

Пн дек 30, 2019 20:28:10

/*
* main.c
*
* Created on: 2 лист. 2019 р.
* Author: Ivan
*/


#include "main.h"

volatile unsigned char flag=0;
volatile unsigned char program=0;
//uint32_t adc_data = 0;
volatile unsigned int adc_data=0;
volatile unsigned int pauza1=0;
volatile unsigned int pauza2=0;
void pauza (int T)//ввод самой паузы(программы) она написана отдельно и введеннием #include "paua.h"можно писать в основном цыкле pauza()с вводом целой переменной T
{
int i=0;//введение целойперемменой i
char t=0;// введение вещественной переменной t считает такты микроконтролера
for(i=0;i<T;t++) //програмама в цыкле
{
if(t==255)i=i+1;// условия одного цыкла счёта пределитель i определяется регистром TCCR2 определяется 0.1.2 битами это делителем частоты работы таймера
}
}

void TIM3_IRQHandler(void)
{
// TIM1->DIER&=~TIM_DIER_UIE;
TIM3->SR &= ~ TIM_SR_UIF;
pauza1++;
if(pauza1>10)
{
GPIOC->ODR|=GPIO_ODR_OD1;
// GPIOC-> BSRR |=GPIO_BSRR_BS1;
}
if(pauza1>20)
{
GPIOC->ODR&=~GPIO_ODR_OD1;
// GPIOC-> BSRR |=GPIO_BSRR_BR1;
pauza1=0;
}

// GPIOC->ODR ^= GPIO_ODR_OD1;
}
void TIM5_IRQHandler(void)
{
//TIM2->DIER&=~TIM_DIER_UIE;
if(TIM5->SR& TIM_SR_UIF)
{
TIM5->SR &= ~ TIM_SR_UIF;
pauza2++;
//if(!(GPIOC->IDR& GPIO_IDR_ID0))
//{
// pauza(20);
if(pauza2>10)
{
// GPIOC-> BSRR |=GPIO_BSRR_BS13;
}
if(pauza2>20)
{
// GPIOC-> BSRR |=GPIO_BSRR_BR13;
pauza2=0;
}
//TIM3->SR &= ~ TIM_SR_UIF;
}
}

//void adc_IRQhanler(void)
//{
// uint16_t adc_data = 0;
//adc_data = ADC1->DR;
// if(ADC1->SR & ADC_SR_EOC)
// {
// ADC1->SR&=~ ADC_SR_EOC;
// ADC1->SR = 0;
// adc_data = ADC1->DR;
// if(adc_data > 2024)
// {
// GPIOC->ODR|=(1<<13);
// GPIOC->BSRR |= GPIO_BSRR_BS13;
// }
// else
// {
// GPIOC->ODR&=~(1<<13);
// GPIOC->BSRR |= GPIO_BSRR_BR13;
// }



//ADC1->SR &=~ ADC_SR_EOC;
// }
//}
void PROGRAM(void)
{
//GPIOC-> BSRR |=GPIO_BSRR_BS1;
// pauza(2000);
// GPIOC-> BSRR |=GPIO_BSRR_BR1;
// pauza(2000);
}
void inits_timer1(void)
{
RCC->APB2ENR |=RCC_APB2ENR_TIM1EN;

TIM1->PSC = 2000-1;//24000 - 1; // Настраиваем делитель что таймер тикал 1000 раз в секунду
TIM1->ARR = 10 ;

TIM1->DIER |= TIM_DIER_UIE;//устанавливаем флаг 1по таймеру
TIM1->EGR = TIM_EGR_UG;
TIM1->CR1|= TIM_CR1_CEN;//разрешаем работу таймера
NVIC_EnableIRQ (TIM1_UP_TIM10_IRQn );
}
void inits_timer5(void)
{
RCC->APB1ENR |=RCC_APB1ENR_TIM5EN;

TIM5->PSC = 3500 - 1; // Настраиваем делитель что таймер тикал 1000 раз в секунду

TIM5->ARR = 100 ;


TIM5->DIER = TIM_DIER_UIE;//устанавливаем флаг 1по таймеру
TIM5->EGR = TIM_EGR_UG;
TIM3->SR =0;
TIM5->CR1|= TIM_CR1_CEN;//разрешаем работу таймера
// NVIC_SetPriority(TIM5_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(),0, 0));
NVIC_EnableIRQ ( TIM5_IRQn );

}
void inits_timer3(void)
{




RCC->APB1ENR |=RCC_APB1ENR_TIM3EN;

TIM3->PSC=3500-1; // Настраиваем делитель что таймер тикал 1000 раз в секунду

TIM3->ARR=100;

TIM3->DIER = TIM_DIER_UIE;
TIM3->EGR=TIM_EGR_UG;
TIM3->SR =0;



TIM3->CR1|= TIM_CR1_CEN;
// NVIC_SetPriority(TIM3_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(),0, 0));
NVIC_EnableIRQ(TIM3_IRQn);
}

void inits_adc(void)
{


RCC->AHB1ENR|=RCC_AHB1ENR_GPIOAEN;

GPIOA->MODER |= GPIO_MODER_MODER0_1;
GPIOA->MODER |= GPIO_MODER_MODER0_0;
GPIOA->PUPDR &=~GPIO_PUPDR_PUPDR0_1;
GPIOA->PUPDR &=~ GPIO_PUPDR_PUPDR0_0;

RCC->APB2ENR |= RCC_APB2ENR_ADC1EN;
ADC->CCR|= ADC_CCR_ADCPRE;

ADC1->CR2 |=ADC_CR2_CONT;

ADC1->CR2|=ADC_CR2_EXTSEL;
ADC1->CR2 |=ADC_CR2_EXTEN;
ADC1->SMPR2 &= ~(ADC_SMPR2_SMP1_2 | ADC_SMPR2_SMP1_1 | ADC_SMPR2_SMP1_0);

/* номер канал */
ADC1->SQR3 &=~ ADC_SQR3_SQ1_0; //1 IN0
ADC1->SQR3 &= ~ ADC_SQR3_SQ3_1; //0
ADC1->SQR3 &= ~ADC_SQR3_SQ1_2; //0
ADC1->SQR3 &=~ ADC_SQR3_SQ1_3; //0
ADC1->SQR3 &= ~ADC_SQR3_SQ1_4;//0
// ADC1->CR2 |=ADC_CR2_CONT;
// ADC1->CR1 = ADC_CR1_EOCIE;
//ADC1->SR=0;
// ADC1->SMPR2 &= ~(ADC_SMPR2_SMP1_2 | ADC_SMPR2_SMP1_1 | ADC_SMPR2_SMP1_0);
// NVIC_SetPriority(ADC_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(),0, 0));
//NVIC_EnableIRQ (ADC_IRQn);


//NVIC_EnableIRQ (ADC_IRQn);
ADC1->CR2 |= ADC_CR2_ADON;
// NVIC_SetPriority(ADC_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(),0, 0));
// NVIC_EnableIRQ (ADC_IRQn);
}


void inits_adc2(void)
{

}
void inits_GPIOC(void)
{
RCC->AHB1ENR|=RCC_AHB1ENR_GPIOCEN;


GPIOC->MODER &=~ GPIO_MODER_MODER13_1;
GPIOC->MODER |= GPIO_MODER_MODER13_0;
GPIOC ->OTYPER &=~GPIO_OTYPER_OT13;
//бит0 определяет скорость работы GPIO
GPIOC->OSPEEDR &=~ GPIO_OSPEEDER_OSPEEDR13_1; //бит1
GPIOC->OSPEEDR &=~ GPIO_OSPEEDER_OSPEEDR13_0;
GPIOC->PUPDR |=GPIO_PUPDR_PUPDR13_1;
GPIOC->PUPDR &=~ GPIO_PUPDR_PUPDR13_0;
/* настройка на вход */

// RCC->AHB1ENR|=RCC_AHB1ENR_GPIOCEN;

GPIOC->MODER &=~ GPIO_MODER_MODER0_1;
GPIOC->MODER &=~ GPIO_MODER_MODER0_0;
GPIOC ->OTYPER &=~GPIO_OTYPER_OT0;
//бит0 определяет скорость работы GPIO
GPIOC->OSPEEDR &=~ GPIO_OSPEEDER_OSPEEDR0_1; //бит1
GPIOC->OSPEEDR &=~ GPIO_OSPEEDER_OSPEEDR0_0;
GPIOC->PUPDR &=~ GPIO_PUPDR_PUPDR0_1;
GPIOC->PUPDR |= GPIO_PUPDR_PUPDR0_0;

GPIOC->MODER &=~ GPIO_MODER_MODER1_1;
GPIOC->MODER |= GPIO_MODER_MODER1_0;
GPIOC ->OTYPER &=~GPIO_OTYPER_OT1;
//бит0 определяет скорость работы GPIO
GPIOC->OSPEEDR &=~ GPIO_OSPEEDER_OSPEEDR1_1; //бит1
GPIOC->OSPEEDR &=~ GPIO_OSPEEDER_OSPEEDR1_0;
GPIOC->PUPDR |=GPIO_PUPDR_PUPDR1_1;
GPIOC->PUPDR &=~ GPIO_PUPDR_PUPDR1_0;
}

int main(void)
{
// int adc_data=0;
inits_GPIOC();
//inits_adc();


//ADC1->CR2 |= ADC_CR2_SWSTART;
//inits_timer1();
inits_timer3();
inits_timer5();
//inits_timer3();
inits_adc();
//ADC1->CR1 |= ADC_CR1_EOCIE;
// ADC1->CR2 |= ADC_CR2_ADON;
// NVIC_EnableIRQ (ADC_IRQn);
//ADC1->CR2|= ADC_CR2_SWSTART;

// __enable_irq ();

while(1)
{
ADC1->CR2 |= ADC_CR2_SWSTART;

//ADC1->CR2 |= ADC_CR2_SWSTART; //Запуск преобразований
while (!(ADC1->SR & ADC_SR_EOC)); //ждем пока первое преобразование завершится
ADC1->SR &=~ADC_SR_EOC ;
// ADC1->SR = 0;
adc_data = ADC1->DR;

if(adc_data > 2024)
{
// GPIOC->ODR|=1<<13;
GPIOC->BSRR |= GPIO_BSRR_BS13;
}
else
{
// GPIOC->ODR&=~1<<13;
GPIOC->BSRR |= GPIO_BSRR_BR13;
}
}
}
вот рабочий код правда ацп работает не в прерывании.

Добавлено after 6 minutes 2 seconds:
что такое теги я нерусский и не понимаю учител.Я вам показал три кода один неработает вы специалисты что можете сказать.Ваши аргумент не убедителен.Ну вообщем спасибо.Наверное в HAL прийдётся ещё посидеть.

Re: stm32f4 cmsis ADC прерывание

Чт янв 02, 2020 19:26:09

Ау коты где вы?.С Новым Годом!

Re: stm32f4 cmsis ADC прерывание

Пт янв 10, 2020 04:52:35

Код в сообщениях под спойлер прятать нужно.

Re: stm32f4 cmsis ADC прерывание

Вс янв 12, 2020 22:02:40

...я нерусский ...

:))) улыбнуло
кто же ты Ванюша?
(? риторический, отвечать не надо)

"... void adc_IRQhanler(void)..." - здесь все правильно?

Re: stm32f4 cmsis ADC прерывание

Вс мар 29, 2020 22:02:45

гагаузский

Re: stm32f4 cmsis ADC прерывание

Пн мар 30, 2020 12:25:39

Вот пример с живого проекта

Re: stm32f4 cmsis ADC прерывание

Пн мар 30, 2020 17:22:49

Спасибо конечно .Но когда вы коты спали.Я ловил мышей.Я решил вопрос частично.

Re: stm32f4 cmsis ADC прерывание

Ср апр 08, 2020 02:03:31

Вот пример с живого проекта

Re: stm32f4 cmsis ADC прерывание

Чт апр 09, 2020 10:25:29

Используются и запускаются только инжекторные каналы.

Re: stm32f4 cmsis ADC прерывание

Вт апр 14, 2020 13:18:35

Вобщето да извините.
Ответить