Перейти к содержанию
    

STM32F100 синхронизировать чтение АЦП с генерацией меандра ШИМ .

26 minutes ago, ViKo said:

На картинке не так.

На картинке я сделал 6 , как пример . Но не с точным соответствием как в проекте.

У меня в проекте 8.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

6 - это так делит Таймер 3. А таймер 2 должен делить на 8. Видимо, такая задумка.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Spoiler

 

Выкладываю инициализацию таймеров и АЦП:


static void MX_ADC1_Init(void)
{

  /* USER CODE BEGIN ADC1_Init 0 */

  /* USER CODE END ADC1_Init 0 */

  ADC_InjectionConfTypeDef sConfigInjected = {0};
  ADC_ChannelConfTypeDef sConfig = {0};

  /* USER CODE BEGIN ADC1_Init 1 */

  /* USER CODE END ADC1_Init 1 */
  /** Common config 
  */
  hadc1.Instance = ADC1;
  hadc1.Init.ScanConvMode = ADC_SCAN_ENABLE;
  hadc1.Init.ContinuousConvMode = ENABLE;
  hadc1.Init.DiscontinuousConvMode = DISABLE;
  hadc1.Init.ExternalTrigConv = ADC_EXTERNALTRIGCONV_T3_TRGO;
  hadc1.Init.DataAlign = ADC_DATAALIGN_RIGHT;
  hadc1.Init.NbrOfConversion = 1;
  if (HAL_ADC_Init(&hadc1) != HAL_OK)
  {
    Error_Handler();
  }
  /** Configure Injected Channel 
  */
  sConfigInjected.InjectedChannel = ADC_CHANNEL_1;
  sConfigInjected.InjectedRank = ADC_INJECTED_RANK_1;
  sConfigInjected.InjectedNbrOfConversion = 2;
  sConfigInjected.InjectedSamplingTime = ADC_SAMPLETIME_239CYCLES_5;
  sConfigInjected.ExternalTrigInjecConv = ADC_INJECTED_SOFTWARE_START;
  sConfigInjected.AutoInjectedConv = DISABLE;
  sConfigInjected.InjectedDiscontinuousConvMode = DISABLE;
  sConfigInjected.InjectedOffset = 0;
  if (HAL_ADCEx_InjectedConfigChannel(&hadc1, &sConfigInjected) != HAL_OK)
  {
    Error_Handler();
  }
  /** Configure Injected Channel 
  */
  sConfigInjected.InjectedChannel = ADC_CHANNEL_9;
  sConfigInjected.InjectedRank = ADC_INJECTED_RANK_2;
  if (HAL_ADCEx_InjectedConfigChannel(&hadc1, &sConfigInjected) != HAL_OK)
  {
    Error_Handler();
  }
  /** Configure Regular Channel 
  */
  sConfig.Channel = ADC_CHANNEL_7;
  sConfig.Rank = ADC_REGULAR_RANK_1;
  sConfig.SamplingTime = ADC_SAMPLETIME_7CYCLES_5;
  if (HAL_ADC_ConfigChannel(&hadc1, &sConfig) != HAL_OK)
  {
    Error_Handler();
  }
  /* USER CODE BEGIN ADC1_Init 2 */

  /* USER CODE END ADC1_Init 2 */

}

static void MX_TIM2_Init(void)
{

  /* USER CODE BEGIN TIM2_Init 0 */

  /* USER CODE END TIM2_Init 0 */

  TIM_SlaveConfigTypeDef sSlaveConfig = {0};
  TIM_MasterConfigTypeDef sMasterConfig = {0};
  TIM_OC_InitTypeDef sConfigOC = {0};

  /* USER CODE BEGIN TIM2_Init 1 */

  /* USER CODE END TIM2_Init 1 */
  htim2.Instance = TIM2;
  htim2.Init.Prescaler = 1;
  htim2.Init.CounterMode = TIM_COUNTERMODE_UP;
  htim2.Init.Period = 5000;
  htim2.Init.ClockDivision = TIM_CLOCKDIVISION_DIV1;
  htim2.Init.AutoReloadPreload = TIM_AUTORELOAD_PRELOAD_ENABLE;
  if (HAL_TIM_Base_Init(&htim2) != HAL_OK)
  {
    Error_Handler();
  }
  if (HAL_TIM_PWM_Init(&htim2) != HAL_OK)
  {
    Error_Handler();
  }
  sSlaveConfig.SlaveMode = TIM_SLAVEMODE_TRIGGER;
  sSlaveConfig.InputTrigger = TIM_TS_ITR2;
  if (HAL_TIM_SlaveConfigSynchronization(&htim2, &sSlaveConfig) != HAL_OK)
  {
    Error_Handler();
  }
  sMasterConfig.MasterOutputTrigger = TIM_TRGO_UPDATE;
  sMasterConfig.MasterSlaveMode = TIM_MASTERSLAVEMODE_ENABLE;
  if (HAL_TIMEx_MasterConfigSynchronization(&htim2, &sMasterConfig) != HAL_OK)
  {
    Error_Handler();
  }
  sConfigOC.OCMode = TIM_OCMODE_PWM1;
  sConfigOC.Pulse = 0;
  sConfigOC.OCPolarity = TIM_OCPOLARITY_HIGH;
  sConfigOC.OCFastMode = TIM_OCFAST_DISABLE;
  if (HAL_TIM_PWM_ConfigChannel(&htim2, &sConfigOC, TIM_CHANNEL_3) != HAL_OK)
  {
    Error_Handler();
  }
  /* USER CODE BEGIN TIM2_Init 2 */

  /* USER CODE END TIM2_Init 2 */
  HAL_TIM_MspPostInit(&htim2);

}

/**
  * @brief TIM3 Initialization Function
  * @param None
  * @retval None
  */
static void MX_TIM3_Init(void)
{

  /* USER CODE BEGIN TIM3_Init 0 */

  /* USER CODE END TIM3_Init 0 */

  TIM_ClockConfigTypeDef sClockSourceConfig = {0};
  TIM_MasterConfigTypeDef sMasterConfig = {0};

  /* USER CODE BEGIN TIM3_Init 1 */

  /* USER CODE END TIM3_Init 1 */
  htim3.Instance = TIM3;
  htim3.Init.Prescaler = 4;
  htim3.Init.CounterMode = TIM_COUNTERMODE_UP;
  htim3.Init.Period = 25;
  htim3.Init.ClockDivision = TIM_CLOCKDIVISION_DIV1;
  htim3.Init.AutoReloadPreload = TIM_AUTORELOAD_PRELOAD_ENABLE;
  if (HAL_TIM_Base_Init(&htim3) != HAL_OK)
  {
    Error_Handler();
  }
  sClockSourceConfig.ClockSource = TIM_CLOCKSOURCE_INTERNAL;
  if (HAL_TIM_ConfigClockSource(&htim3, &sClockSourceConfig) != HAL_OK)
  {
    Error_Handler();
  }
  sMasterConfig.MasterOutputTrigger = TIM_TRGO_UPDATE;
  sMasterConfig.MasterSlaveMode = TIM_MASTERSLAVEMODE_DISABLE;
  if (HAL_TIMEx_MasterConfigSynchronization(&htim3, &sMasterConfig) != HAL_OK)
  {
    Error_Handler();
  }
  /* USER CODE BEGIN TIM3_Init 2 */

  /* USER CODE END TIM3_Init 2 */

}



//Вот так частота ШИМ задается:
//Смею заметить что скважность ШИМ 50%

#define FREQ_MIN 8000 // 24000000/8000/2 = 1500Hz
#define FREQ_MAX 400  // 24000000/400/2 = 30000Hz

#define TX_FREQ_F TIM2->CCR3
#define TX_FREQ_R TIM2->ARR
#define TX_FREQ TIM2->PSC
#define TX_FASE TIM2->CNT

void tx_freq(uint16_t pwm_tx)
{
    TX_FREQ_F=pwm_tx/2;
    TX_FREQ_R=pwm_tx;

    TX_FREQ = 1;
}

//АЦП опрашивается уже в обработчике прерывания 
  void HAL_ADC_ConvCpltCallback(ADC_HandleTypeDef* hadc1)
  {

  buf_adc_rx[data_cnt] += HAL_ADC_GetValue(hadc1);
  buf_tim_rx[data_cnt] = TX_FASE;
  if(data_cnt<(BUFF_SIZE-1)){data_cnt++; error=0; }
  else error=1;
  HAL_ADC_Start_IT(hadc1);//запустим аналогово-цифровое преобразование

  }
 // в прерывании таймера уже выполняется сброс указателя и усреднение результатов 
  uint8_t data_rst=0;
void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim2)
{
	buf_adc_rx[24] = data_cnt;
	buf_adc_rx[23] = error;



	if(++data_rst>1)
	{
		data_rst=0;
		data_cnt=0;

		  if(++filtr>FILTR)
			  {
			   for(data_cnt=0; data_cnt<(BUFF_SIZE/3); data_cnt++)
				   {
				    buf_adc_rx_[data_cnt] = (uint16_t)(buf_adc_rx[data_cnt]/filtr);
				    buf_adc_rx[data_cnt]=0;
				   }
			   filtr=0;
			  }
	}


}
// а по юарт в основном цикле программы я смотрю результат в виде отладки
if(++timer1>5){
sprintf(buff_lcd1 ,"U_RX:%04d  %04d %04d %04d %04d %04d %04d; %04d; %04d; TIM3: %04d; %04d; %04d; %04d %04d %04d %04d; %04d; %04d; %04d; %04d; %04d\r\n" ,buf_adc_rx_[0], \
				  buf_adc_rx_[1],buf_adc_rx_[2],buf_adc_rx_[3],buf_adc_rx_[4],buf_adc_rx_[5],buf_adc_rx_[6],buf_adc_rx_[7],buf_adc_rx_[8],buf_tim_rx[0],buf_tim_rx[1],buf_tim_rx[2] ,\
buf_tim_rx[3],buf_tim_rx[4],buf_tim_rx[5],buf_tim_rx[6],buf_tim_rx[7],buf_tim_rx[8],buf_adc_rx_[18],buf_adc_rx_[23],buf_adc_rx_[24]);
S_uart1_N(buff_lcd1); timer1=0; injected_soft();
}  
 
// Вот сама функция юарт:
void S_uart1_N(char *str)
{
int x=0;
str+=0;
while(str[x])
{
x++;
}
HAL_UART_Transmit_IT(&huart1,(uint8_t*)str,x);
}

 

 

 

 

Изменено пользователем Artos5

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

А на какой скорости UART работает? Успевает всё выдать и дать поработать чему-то еще? И эта sprintf...

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

16 hours ago, ViKo said:

А на какой скорости UART работает?

115200. Но я данные передаю по юарт периодически , и они сильно пляшут . Хотя должны быть +- стабильны и тики таймера одинаковые должны выводиться .

Изменено пользователем Artos5

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Присоединяйтесь к обсуждению

Вы можете написать сейчас и зарегистрироваться позже. Если у вас есть аккаунт, авторизуйтесь, чтобы опубликовать от имени своего аккаунта.

Гость
Ответить в этой теме...

×   Вставлено с форматированием.   Вставить как обычный текст

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

×
×
  • Создать...