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

Осуществить попеременный вывод двух сигналов sin.cos

необходимо сделать попеременный вывод двух типов сигналов: исходного и сдвинутого на четверть периода (sin, cos), обеспечить вывод целого числа периодов.

 

Вот программа не выводит косинус,что необходимо исправить, подскажите пожалуйста

//---------------------------------------------------------------------------
// 
//  ??????? ??????
//  ????????????? ???????? ? ?????? ?????????
//  Copyright (C) 2020 ?????
//
//  ? ??????? ???????????????: 
//   - ????????? ??????????? ?????????????? ??????? ?????????? ????? ??????????;
//   - ????????? ????? ??????? ??????????? ???;
//   - ????? ??????? ????? ??? ???????????.
//
//---------------------------------------------------------------------------

#include "stm32f10x.h"                  //??????????? ??? ??????????? ????????? STM32F10x
#include "periphF1.h"                   //??????? ?????? ? ?????????? (???, ???????) ? ?????? ?????????
#include "boardF1.h"                    //????????? ? ??????? ?????? ? ????????, ??????????
#include <math.h>

//---------------------------------------------------------------------------
// ?????????? ??????
int16_t DataADC1, DataADC2;             //??????? ??????? ??????? ? ???
int16_t DataChannel1, DataChannel2;     //?????? ??? ?????? ? ?????????????? ????
TIM_TimeBaseInitTypeDef TimeBase;       //????????? ???????????? ???????? ???????
int16_t p=0,c=1;
int x =0;
bool flag = true;

extern float Codec_Out1, Codec_Out2;    //?????????? ???????? ??????? ? ??????

//---------------------------------------------------------------------------
// ??????? ??????? 
int main (void)
{
  //??????? ??? ?????????? ??????? ????????? ???????? ?????????
  volatile uint32_t i = 0;

  //????????????? ???????? ???????????
  STM_LEDInit(LED1); STM_LEDInit(LED2);  STM_LEDInit(LED3); STM_LEDInit(LED4);

  //????????????? ??????
  STM_PBInit(BUTTON_TAMPER, BUTTON_MODE_GPIO);
  STM_PBInit(BUTTON_WAKEUP, BUTTON_MODE_GPIO);

  //????????????? ??? - ????? ?? ????????????, ??? ??? ?????? ??????????? 
  // ??????????? ????????? ????? ??????????

  //????????????? ?????????? ??????? ????????????? ???; ??? ???? ????
  // ???????????? ?????? 3 ? ??????????? ???????? ???????????? 72 ???
  RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);
  TimeBase.TIM_Period = 720000u/8000-1;
  TimeBase.TIM_Prescaler = 100-1;
  TimeBase.TIM_ClockDivision = 0;
  TimeBase.TIM_CounterMode = TIM_CounterMode_Up;
  TIM_TimeBaseInit(TIM3, &TimeBase);
  TIM_SelectOutputTrigger(TIM3, TIM_TRGOSource_Update);
  TIM_ITConfig(TIM3, TIM_IT_Update, ENABLE);
  NVIC_EnableIRQ(TIM3_IRQn);
  TIM_Cmd(TIM3, ENABLE);

  //????????????? ?????????????? ??? ? ???????? ?? ??????? ???????????? ??????? 3
  ADC_Initialize();
  ADC_StartCnv();

  //????????????? ?????? ??? ?????????? ?????? ???????
  SoundCodecConfig(32000);

  //???????? ????
  while (1)
  {
    c=p;
    p=ADC_GetConversionValue();
    if(c<0 && p>0)
    {
      x++;
      if(x>2){
      flag = !flag;
      x=0;  
      }
    }

    
    if (i++ == 0x800) STM_LEDOff(LED1);         //???????? ?????????? ???????????
    if (i == 0xB0000) STM_LEDOn(LED1), i = 0;
    if (STM_PBGetState(BUTTON_WAKEUP)) NVIC_SystemReset();    //???????? ?? ??????????
  }
}

//---------------------------------------------------------------------------
// ?????????? ?????????? ?? ??? (??????? ???????????? ???)
void ADC_IRQHandler(void)
{
  STM_LEDOn(LED4);                                      //?????????? ????? (????? "1") 
  TIM_ClearITPendingBit(TIM3, TIM_IT_Update);           //????? ????? ??????? ??????????
  DataADC1 = DataADC2 = ADC_GetConversionValue();       //????????? ???
  DataChannel1 = DataADC1 ^ 0x8000;                     //?????????????? ? ??????????????
  DataChannel2 = DataADC2 ^ 0x8000;
 
  if(flag == true){
    if(p-c>0)
    {
    DataChannel2 = sqrtf(10000000000000000-powf(DataChannel2,2));       //?????????????? ? ?????????????? 
    }
    else
    {
    DataChannel2 = -sqrtf(10000000000000000-powf(DataChannel2,2));       //?????????????? ? ??????????????
    }
                                                     //?????????????? ? ??????????????
  DataChannel1 = ~DataChannel1;
  }
  if (flag == false)
  {
    if(p-c>0)
    {
    DataChannel1 = sqrtf(10000000000000000-powf(DataChannel1,2));       //?????????????? ? ?????????????? 
    }
    else
    {
    DataChannel1 = -sqrtf(10000000000000000-powf(DataChannel1,2));       //?????????????? ? ??????????????
    }
    DataChannel2 = ~DataChannel2;
  }     
     STM_LEDOff(LED4);                                     //?????????? ????? (????? "0")  
}


//---------------------------------------------------------------------------
// ?????????? ?????????? ?? ??????
void Sample_Handler(void)
{
  //????????? ???????? - ? DataChannel1, DataChannel2
}
у меня выводит только синус,после не могу косинус вывести

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


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

ф-ия ADC_GetConversionValue() вызывается и в main(), и в void ADC_IRQHandler(). На месте процессора, по жалобе ADC, я бы вообще проигнорировал код.

В обработчике прерывания довольно тяжеловесные мат. ф-ии, возможно время их работы перекрывает вызовы прерывания.

Поскольку комментарии засекречены уже второй раз, непонятно, какой в этом сокральный смысл.

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

Затертость комментариев и краткость ТС впечатляют :crazy:

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


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

23 минуты назад, k155la3 сказал:

Затертость комментариев и краткость ТС впечатляют :crazy:

Так наверняка он за каждую букву деньги платит, а знак "?" у него идет со скидкой. Или просто эта клавиша заедает и печатает сама по себе...

А уж вывести код в "codebox" и вообще невероятно сложно...

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


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

Ясно что ТС - типичный представитель целевой аудитории для недавно созданной ветки форума (необходимость которой так долго обсуждалась).

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


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

Я перенёс тему в раздел задач, когда прочитал начальное сообщение. Потом пришлось перенести сюда, поскольку это не задача.

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


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

10 часов назад, k155la3 сказал:

 комментарии засекречены 

Имхо, обычная небрежность, связанная с кодировкой.

Например, в Квартусе когда копируешь кусок кода с русскими комментариями и вставляешь его, то если раскладка клавиатуры английская, вставляются кракозябры.

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

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


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

15 часов назад, k155la3 сказал:

ф-ия ADC_GetConversionValue() вызывается и в main(), и в void ADC_IRQHandler(). На месте процессора, по жалобе ADC, я бы вообще проигнорировал код.

В обработчике прерывания довольно тяжеловесные мат. ф-ии, возможно время их работы перекрывает вызовы прерывания.

Поскольку комментарии засекречены уже второй раз, непонятно, какой в этом сокральный смысл.

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

Затертость комментариев и краткость ТС впечатляют :crazy:

//---------------------------------------------------------------------------

//
//  В проекте демонстрируются: 
//   - генерация отладочного гармонического сигнала средствами среды разработки;
//   - оцифровка этого сигнала посредством АЦП;
//   - вывод сигнала через ЦАП аудиокодека.
//
//---------------------------------------------------------------------------

#include "stm32f10x.h"                  //Определения для процессоров семейства STM32F10x
#include "periphF1.h"                   //Функции работы с периферией (ЦАП, кодеком) в режиме симуляции
#include "boardF1.h"                    //Константы и функции работы с кнопками, индикацией
#include <math.h>

//---------------------------------------------------------------------------
// ОБЪЯВЛЕНИЯ ДАННЫХ
int16_t DataADC1, DataADC2;             //Текущие отсчеты сигнала с АЦП
int16_t DataChannel1, DataChannel2;     //Данные для кодека в дополнительном коде
TIM_TimeBaseInitTypeDef TimeBase;       //Структура конфигурации базового таймера
//int16_t max=0, max1=0, max2=0;
int16_t p=0,c=0;
int x =0;
bool flag = true;

extern float Codec_Out1, Codec_Out2;    //Аналоговые выходные сигналы с кодека

//---------------------------------------------------------------------------
// ГЛАВНАЯ ФУНКЦИЯ 
int main (void)
{
  //Счетчик для реализации периода изменения тестовой индикации
  volatile uint32_t i = 0;

  //Инициализация тестовых индикаторов
  STM_LEDInit(LED1); STM_LEDInit(LED2);  STM_LEDInit(LED3); STM_LEDInit(LED4);

  //Инициализация кнопок
  STM_PBInit(BUTTON_TAMPER, BUTTON_MODE_GPIO);
  STM_PBInit(BUTTON_WAKEUP, BUTTON_MODE_GPIO);

  //Инициализация ЦАП - здесь не используется, так как сигнал формируется 
  // отладочными функциями среды разработки

  //Инициализация генератора частоты дискретизации АЦП; для этой цели
  // задействован таймер 3 с собственной частотой тактирования 72 МГц
  RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);
  TimeBase.TIM_Period = 720000u/8000-1;
  TimeBase.TIM_Prescaler = 100-1;
  TimeBase.TIM_ClockDivision = 0;
  TimeBase.TIM_CounterMode = TIM_CounterMode_Up;
  TIM_TimeBaseInit(TIM3, &TimeBase);
  TIM_SelectOutputTrigger(TIM3, TIM_TRGOSource_Update);
  TIM_ITConfig(TIM3, TIM_IT_Update, ENABLE);
  NVIC_EnableIRQ(TIM3_IRQn);
  TIM_Cmd(TIM3, ENABLE);

  //Инициализация одноканального АЦП с запуском от события перезагрузки таймера 3
  ADC_Initialize();
  ADC_StartCnv();

  //Инициализация кодека как устройства вывода сигнала
  SoundCodecConfig(32000);

  //Основной цикл
  while (1)
  {
    c=p;
    p=ADC_GetConversionValue();
    if(c<0 && p>0)
    {
      x++;
      if(x>2){
      flag = !flag;
      x=0;  
      }
    }

    
    if (i++ == 0x800) STM_LEDOff(LED1);         //Тестовое управление индикатором
    if (i == 0xB0000) STM_LEDOn(LED1), i = 0;
    if (STM_PBGetState(BUTTON_WAKEUP)) NVIC_SystemReset();    //Проверка на завершение
  }
}

//---------------------------------------------------------------------------
// ОБРАБОТЧИК ПРЕРЫВАНИЯ ОТ АЦП (ТАЙМЕРА ТАКТИРОВАНИЯ АЦП)
void ADC_IRQHandler(void)
{
  STM_LEDOn(LED4);                                      //Отладочная метка (вывод "1") 
  TIM_ClearITPendingBit(TIM3, TIM_IT_Update);           //Сброс флага запроса прерывания
  DataADC1 = DataADC2 = ADC_GetConversionValue();       //Смещенный код
  DataChannel1 = DataADC1 ^ 0x8000;                     //Преобразование в дополнительный
  DataChannel2 = DataADC2 ^ 0x8000;
  //Здесь должна быть обработка
   //if(DataChannel1&0x8000)
    //DataChannel1=0;                                     //однополупериодовое выпрямление
    //DataChannel1=DataChannel1^0xFFFF;                   //двухполупериодовое выпрямление
  
  /*max1=DataChannel1;                                    //Ограничение амплитуды
  if(DataChannel1<0)
  {
    max2=0;
  }
  if (max1>max2)
  {
    max2=max1;
  }
    else
    {
      if ((max1<max2)&&(max1>=0))
        {
          max=max2;
        }
    }
  if (max==0)
  {
    DataChannel2=(7*DataChannel1)/10;
  }
  else
  {
    if (DataChannel2>=(7*max)/10)
       {
         DataChannel2=(7*max)/10;
       }
    if (DataChannel2<=(7*(-max)/10))
       {
         DataChannel2=(7*(-max)/10); 
       }                                */
  if(flag == true){
    if(p-c>0)
    {
    DataChannel2 = sqrtf(1-powf(DataChannel2,2));       //Преобразование в дополнительный 
    }
    else
    {
    DataChannel2 = -sqrtf(1-powf(DataChannel2,2));       //Преобразование в дополнительный
    }
                                                     //Преобразование в дополнительный
  DataChannel1 = ~DataChannel1;
  }
  if (flag == false)
  {
    if(p-c>0)
    {
    DataChannel1 = sqrtf(1-powf(DataChannel1,2));       //Преобразование в дополнительный 
    }
    else
    {
    DataChannel1 = -sqrtf(1-powf(DataChannel1,2));       //Преобразование в дополнительный
    }
    DataChannel2 = ~DataChannel2;
  }     
     STM_LEDOff(LED4);                                     //Отладочная метка (вывод "0")  
}


//---------------------------------------------------------------------------
// ОБРАБОТЧИК ПРЕРЫВАНИЯ ОТ КОДЕКА
void Sample_Handler(void)
{
  //Выводимые значения - в DataChannel1, DataChannel2
}

Подскажите что нужно исправить,чтобы поочередно синус и косинус выводился?

 

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


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

Осуществлять попеременный вывод двух типов сигналов: исходного и сдвинутого на четверть периода (sin, cos), обеспечить вывод целого числа периодов.

убрал лишнее из предыдущей программы

 

//---------------------------------------------------------------------------
// 
// 
//
// В проекте демонстрируются: 
//   - генерация отладочного гармонического сигнала средствами среды разработки;
//   - оцифровка этого сигнала посредством АЦП;
//   - вывод сигнала через ЦАП аудиокодека.
//
//---------------------------------------------------------------------------

#include "stm32f10x.h"                  //Определения для процессоров семейства STM32F10x
#include "periphF1.h"                   //Функции работы с периферией (ЦАП, кодеком) в режиме симуляции
#include "boardF1.h"                    //Константы и функции работы с кнопками, индикацией
#include <math.h>

//---------------------------------------------------------------------------
// ОБЪЯВЛЕНИЯ ДАННЫХ
int16_t DataADC1, DataADC2;             //Текущие отсчеты сигнала с АЦП
int16_t DataChannel1, DataChannel2;     //Данные для кодека в дополнительном коде
TIM_TimeBaseInitTypeDef TimeBase;       //Структура конфигурации базового таймера
int16_t p=0,c=0;
int x =0;
bool flag = true;

extern float Codec_Out1, Codec_Out2;    //Аналоговые выходные сигналы с кодека

//---------------------------------------------------------------------------
// ГЛАВНАЯ ФУНКЦИЯ 
int main (void)
{
  //Счетчик для реализации периода изменения тестовой индикации
  volatile uint32_t i = 0;

  //Инициализация тестовых индикаторов
  STM_LEDInit(LED1); STM_LEDInit(LED2);  STM_LEDInit(LED3); STM_LEDInit(LED4);

  //Инициализация кнопок
  STM_PBInit(BUTTON_TAMPER, BUTTON_MODE_GPIO);
  STM_PBInit(BUTTON_WAKEUP, BUTTON_MODE_GPIO);

  //Инициализация ЦАП - здесь не используется, так как сигнал формируется 
  // отладочными функциями среды разработки

  //Инициализация генератора частоты дискретизации АЦП; для этой цели
  // задействован таймер 3 с собственной частотой тактирования 72 МГц
  RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);
  TimeBase.TIM_Period = 720000u/8000-1;
  TimeBase.TIM_Prescaler = 100-1;
  TimeBase.TIM_ClockDivision = 0;
  TimeBase.TIM_CounterMode = TIM_CounterMode_Up;
  TIM_TimeBaseInit(TIM3, &TimeBase);
  TIM_SelectOutputTrigger(TIM3, TIM_TRGOSource_Update);
  TIM_ITConfig(TIM3, TIM_IT_Update, ENABLE);
  NVIC_EnableIRQ(TIM3_IRQn);
  TIM_Cmd(TIM3, ENABLE);

  //Инициализация одноканального АЦП с запуском от события перезагрузки таймера 3
  ADC_Initialize();
  ADC_StartCnv();

  //Инициализация кодека как устройства вывода сигнала
  SoundCodecConfig(32000);

  //Основной цикл
  while (1)
  {
    c=p;
    p=ADC_GetConversionValue();
    if(c<0 && p>0)
    {
      x++;
      if(x>2){
      flag = !flag;
      x=0;  
      }
    }

    
    if (i++ == 0x800) STM_LEDOff(LED1);         //Тестовое управление индикатором
    if (i == 0xB0000) STM_LEDOn(LED1), i = 0;
    if (STM_PBGetState(BUTTON_WAKEUP)) NVIC_SystemReset();    //Проверка на завершение
  }
}

//---------------------------------------------------------------------------
// ОБРАБОТЧИК ПРЕРЫВАНИЯ ОТ АЦП (ТАЙМЕРА ТАКТИРОВАНИЯ АЦП)
void ADC_IRQHandler(void)
{
  STM_LEDOn(LED4);                                      //Отладочная метка (вывод "1") 
  TIM_ClearITPendingBit(TIM3, TIM_IT_Update);           //Сброс флага запроса прерывания
  DataADC1 = DataADC2 = ADC_GetConversionValue();       //Смещенный код
  DataChannel1 = DataADC1 ^ 0x8000;                     //Преобразование в дополнительный
  DataChannel2 = DataADC2 ^ 0x8000;
 
 
  if(flag == true){
    if(p-c>0)
    {
    DataChannel2 = sqrtf(1-powf(DataChannel2,2));       //Преобразование в дополнительный 
    }
    else
    {
    DataChannel2 = -sqrtf(1-powf(DataChannel2,2));       //Преобразование в дополнительный
    }
                                                     //Преобразование в дополнительный
  DataChannel1 = ~DataChannel1;
  }
  if (flag == false)
  {
    if(p-c>0)
    {
    DataChannel1 = sqrtf(1-powf(DataChannel1,2));       //Преобразование в дополнительный 
    }
    else
    {
    DataChannel1 = -sqrtf(1-powf(DataChannel1,2));       //Преобразование в дополнительный
    }
    DataChannel2 = ~DataChannel2;
  }     
     STM_LEDOff(LED4);                                     //Отладочная метка (вывод "0")  
}


//---------------------------------------------------------------------------
// ОБРАБОТЧИК ПРЕРЫВАНИЯ ОТ КОДЕКА
void Sample_Handler(void)
{
  //Выводимые значения - в DataChannel1, DataChannel2
}

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


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

А что за аудиокодек, может в нем все ЭТО уже реализовано ? (В частности, задержка сигналов между каналами)

Зачем эти хитрые преобразования в доп. код, знаковые целые в С и так в дополнительном коде.

Единственное, если исходная разрядность нестандартная и ее надо "приводить" к 8/16/32.  

У Вас упрощенный проект работает, когда входной сигнал просто транслируется на выход, те на кодек ?

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


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

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

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

Гость
К сожалению, ваш контент содержит запрещённые слова. Пожалуйста, отредактируйте контент, чтобы удалить выделенные ниже слова.
Ответить в этой теме...

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

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

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

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

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

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