реклама на сайте
подробности

 
 
> stm32 АЦП в инжекторном режиме
anubis
сообщение Oct 25 2013, 13:25
Сообщение #1


Участник
*

Группа: Участник
Сообщений: 25
Регистрация: 14-01-06
Пользователь №: 13 178



На stm32f107 нужно заюзать второй ADC, первый сейчас используется в регулярном режиме:
В основном коде включаю порт А:
Код
  RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);


Код
void AdcInit(void)
{
  RCC->APB2ENR |= RCC_APB2ENR_IOPAEN;    // Разрешить тактирование порта PORT A
  //Конфигурирование PORT PA.3 - аналоговый вход
  GPIOA->CRL   &= ~GPIO_CRL_MODE3;       //Очистить биты MODE
  GPIOA->CRL   &= ~GPIO_CRL_CNF3;        //Очистить биты CNF

  RCC->APB2ENR |=  RCC_APB2ENR_ADC1EN;   //подаем тактирование АЦП
  RCC->CFGR    &= ~RCC_CFGR_ADCPRE;      //входной делитель
  ADC1->CR1     =  0;                    //
  ADC1->SQR1    =  0;                    //
  ADC1->CR2    |=  ADC_CR2_CAL;          //запуск калибровки
  while (!(ADC1->CR2 & ADC_CR2_CAL)){};  //ждем окончания калибровки
  ADC1->CR2     =  ADC_CR2_EXTSEL;       //выбрать источником запуска разряд  SWSTART
  ADC1->CR2    |=  ADC_CR2_EXTTRIG;      //разр. внешний запуск регулярного канала
  ADC1->CR2    |=  ADC_CR2_CONT;         //режим непрерывного преобразования

  /* Задаем длительность выборки */
    ADC1->SMPR2 |= (ADC_SMPR2_SMP4_2 | ADC_SMPR2_SMP4_1 | ADC_SMPR2_SMP4_0);

  ADC1->SQR3    =  3;                    //загрузить номер канала
  ADC1->CR2    |=  ADC_CR2_ADON;         //включить АЦП
  ADC1->CR2    |=  ADC_CR2_SWSTART;      //запустить процес преобразования
}

А вот подключить второй АЦП и заставить его работать в инжекторном режиме не получается.
Нужно считывать периодически 4 канала (на каждый подключено Vcc через кнопки), таким образом с АЦП по каждому каналу нужно проверять есть ли Vcc или нет.
Вот код для инициализации АЦП2:

Код
void AdcInjInit(void)
{
    RCC->APB2ENR |=  RCC_APB2ENR_ADC2EN;   //подаем тактирование АЦП
      RCC->CFGR    &= ~RCC_CFGR_ADCPRE;      //входной делитель
      ADC2->CR1     =  0;                    //предочистка регистра
      ADC2->CR2    |=  ADC_CR2_CAL;          //запуск калибровки
      while (!(ADC2->CR2 & ADC_CR2_CAL)){};  //ждем окончания калибровки
      ADC2->CR2     =  ADC_CR2_JEXTSEL;      //выбрать источником запуска разряд  JSWSTART
      ADC2->CR2    |=  ADC_CR2_JEXTTRIG;     //разр. внешний запуск инжектированной группы
      ADC2->CR2    |=  ADC_CR2_CONT;         //режим непрерывного преобразования
      ADC2->CR1    |=  ADC_CR1_SCAN;         //режим сканирования (т.е. несколько каналов)
      ADC2->CR1    |=  ADC_CR1_JAUTO;  //автомат. запуск инжектированной группы
      ADC2->JSQR    =  (uint32_t)(4-1)<<20;  //задаем количество каналов в инжектированной группе
      ADC2->JSQR   |=  (uint32_t)10<<(5*0);   //номер канала для первого преобразования (10)
      ADC2->JSQR   |=  (uint32_t)11<<(5*1);   //номер канала для второго преобразования (11)
      ADC2->JSQR   |=  (uint32_t)12<<(5*2);   //номер канала для третьего преобразования
      ADC2->JSQR   |=  (uint32_t)13<<(5*3);   //номер канала для четвертого преобразования
      ADC2->CR2    |=  ADC_CR2_ADON;         //включить АЦП
      ADC2->CR2    |=  ADC_CR2_JSWSTART;     //запустить процес преобразования
}


и забираю таким способом:

Код
     short  adc_btn1 = ADC2->JDR1;
     short  adc_btn2 = ADC2->JDR2;
     short  adc_btn3 = ADC2->JDR3;
     short  adc_btn4 = ADC2->JDR4;

Но на выходе почему то всегда значения 25-28 в не зависимости от нажатия кнопок.
Go to the top of the page
 
+Quote Post
 
Start new topic
Ответов
smk
сообщение Oct 27 2013, 12:18
Сообщение #2


Гуру
******

Группа: Свой
Сообщений: 2 246
Регистрация: 17-03-05
Из: Украина, Киев
Пользователь №: 3 446



Код
unsigned short  adc_btn1 = ADC2->JDR1;


так правильнее, думаю.

Вот моя инициализация ADC1. Три канала непрерывно оцифровываются и выкладываются в буфер. Думаю из 3 сделать 4 не трудно. ADC1 поменять на ADC2 тоже. Номера каналов тоже выберете какие нужно.

Код
void ADC1_Init(void)
{
    RCC->APB2ENR |=(1UL<<2);                                    //тактирование GPIOA включить
    GPIOA->CRL &= ~0x00000FF0UL;                 // PA1 & PA2 analog input        
    
    RCC->CFGR    |= 0x8000UL;                                 //установить ADCPRE[1;0] дел. на 6 Fadc = 72/6=12 MHz
    RCC->APB2ENR |= (1UL<<9);                                    //тактирование ADC1 включить
    ADC1->JSQR    = 0x288820UL;                                //3 канала 1,2,17
    ADC1->SMPR1   = 0xE00000UL;                                //Канал 17 х 239,5 тактов
    ADC1->SMPR2   = 0x1F8UL;                                    //Канал 1 и 2 х 239,5 тактов

  ADC1->CR1    |= (1UL<< 8);                       //Scan mode on                    
    ADC1->CR2       |= (1UL<<23);                                //Включить термометр и ИОН
    ADC1->CR2       |= (7UL<<12);                                //выбрать внешним событием программный старт преобразования инж. каналов
    ADC1->CR2       |= (1UL<<15);                                //разрешить начало преобразования по внешнему событию    

  ADC1->CR2    |= (1UL <<  0);                   /* ADC enable                       */
  ADC1->CR2    |= (1UL <<  3);              /* Initialize calibration registers */
  while (ADC1->CR2 & (1UL << 3));           /* Wait for init to finish          */
  ADC1->CR2    |= (1UL <<  2);              /* Start calibration                */
  while (ADC1->CR2 & (1UL << 2));              /* Wait for calibration to finish   */    

  ADC1->CR1    |= (1UL << 10);                   // JAUTO: Automatic Injected Group conversion
    ADC1->CR2    |= (1UL <<  1);                            // CONT: Continuous conversion

    ADC1->CR2    |= (1UL <<  8);                   //DMA mode enabled
    RCC->AHBENR     |= (1UL <<  0);                   //DMA1 clock enabled
    
    DMA1_Channel1->CCR |= (1UL << 11);                                //Memory size 32-bits
    DMA1_Channel1->CCR |= (1UL <<  9);                                //Peripheral size 32-bits
    DMA1_Channel1->CCR |= (1UL <<  5);                                //Circular mode enabled
    DMA1_Channel1->CCR |= (1UL <<  6);                                //Peripheral increment mode enabled
    DMA1_Channel1->CCR |= (1UL <<  7);                                //Memory increment mode enabled    
    DMA1_Channel1->CNDTR = 3;                                                    //Number of data to transfer
    DMA1_Channel1->CPAR = (uint32_t) &ADC1->JDR1;            //Peripheral address
    DMA1_Channel1->CMAR = (uint32_t) &data_buf[0];         //Memory address

    DMA1_Channel1->CCR |= (1UL <<  0);                //Channel1 enabled

    ADC1->CR2    |= (1UL << 21);                   // Start A/D conversion инжектированных каналов    
}


--------------------
Живи днем так, чтобы ночью ты спал спокойно.
Go to the top of the page
 
+Quote Post



Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 23rd August 2025 - 04:01
Рейтинг@Mail.ru


Страница сгенерированна за 0.01377 секунд с 7
ELECTRONIX ©2004-2016