Added one channel mode
Dependents: CW_Decoder_using_FFT_on_F446
Fork of F446_AD_DA by
Revision 4:03e91e464ce5, committed 2017-02-05
- Comitter:
- kenjiArai
- Date:
- Sun Feb 05 07:59:14 2017 +0000
- Parent:
- 3:d1da91aec62f
- Commit message:
- added one channel mode (only A0/PA_0 input)
Changed in this revision
diff -r d1da91aec62f -r 03e91e464ce5 F446_ADC.cpp --- a/F446_ADC.cpp Mon Jan 30 08:12:44 2017 +0000 +++ b/F446_ADC.cpp Sun Feb 05 07:59:14 2017 +0000 @@ -9,6 +9,14 @@ // // 2016/11/12, Copyright (c) 2016 MIKAMI, Naoki //---------------------------------------------------------- +/* + * Modified by Kenji Arai + * http://www.page.sannet.ne.jp/kenjia/index.html + * http://mbed.org/users/kenjiArai/ + * + * Started: Feburary 1st, 2017 + * Revised: Feburary 1st, 2017 + */ #include "F446_ADC.hpp" @@ -89,4 +97,73 @@ myTim->PSC = psc; // Prescaler myTim->CR1 = TIM_CR1_CEN; // Enable TIM8 } + +//------------------------------------------------------------------------------ + + AdcSingle::AdcSingle(int frequency) + { + // ADC input is assigned PA0 + __HAL_RCC_GPIOA_CLK_ENABLE(); + GPIO_InitTypeDef gpioInit; + gpioInit.Pin = GPIO_PIN_0; + gpioInit.Mode = GPIO_MODE_ANALOG; + gpioInit.Pull = GPIO_NOPULL; + gpioInit.Speed = GPIO_SPEED_FREQ_VERY_HIGH; + HAL_GPIO_Init(GPIOA, &gpioInit); + + // ADC2 (port:PA0) + __HAL_RCC_ADC2_CLK_ENABLE(); + ADC2->CR1 = 0x0; + ADC2->CR2 = ADC_EXTERNALTRIGCONVEDGE_RISING // Ext. trigger + rising eggde + | ADC_EXTERNALTRIGCONV_T8_TRGO // Ext. trigger Timer8 TRGO event + | ADC_CR2_ADON; // ADC を有効にする + ADC2->SQR3 = 0x0; // CH0 を使う + + // ADC 共通の設定 + ADC->CCR = 0x0; // 念のため + + // AD 変換器の外部トリガに使うタイマ (TIM8) の設定 + SetTim8(frequency); + } + + void AdcSingle::Read(float &ad) + { + WaitDone(); + ad = ToFloat(ADC2->DR); + } + + void AdcSingle::Read(uint16_t &ad) + { + WaitDone(); + ad = ADC2->DR; + } + + void AdcSingle::SetTim8(int frequency) + { + __HAL_RCC_TIM8_CLK_ENABLE(); // Supply clock. See "stm32f4xx_hal_rcc.h" + SystemCoreClockUpdate(); // Update core clock. See "system_stm32f4xx.h" + TIM_TypeDef* const myTim = TIM8; + + myTim->CR2 = TIM_CR2_MMS_1; // Update event: as trigger out + + uint32_t psc = 0; + uint16_t mul = 1; + uint32_t arr; + while (true) + { + arr = SystemCoreClock/(mul*frequency); + if (arr <= 65536) break; + psc++; + mul++; + if (psc > 65535) + { + fprintf(stderr, "Sampling frequency: too low.\r\n"); + while (true) {} + } + } + myTim->ARR = arr - 1; // Auto-reload + myTim->PSC = psc; // Prescaler + myTim->CR1 = TIM_CR1_CEN; // Enable TIM8 + } } +
diff -r d1da91aec62f -r 03e91e464ce5 F446_ADC.hpp --- a/F446_ADC.hpp Mon Jan 30 08:12:44 2017 +0000 +++ b/F446_ADC.hpp Sun Feb 05 07:59:14 2017 +0000 @@ -11,6 +11,14 @@ // // 2017/01/30, Copyright (c) 2017 MIKAMI, Naoki //---------------------------------------------------------- +/* + * Modified by Kenji Arai + * http://www.page.sannet.ne.jp/kenjia/index.html + * http://mbed.org/users/kenjiArai/ + * + * Started: Feburary 1st, 2017 + * Revised: Feburary 1st, 2017 + */ #include "mbed.h" @@ -20,11 +28,11 @@ #include "F446_DAC.hpp" +namespace Mikami +{ #ifndef F446_ADC_DUAL_HPP #define F446_ADC_DUAL_HPP -namespace Mikami -{ class AdcDual { public: @@ -60,5 +68,44 @@ // for inhibition of substitute operator AdcDual& operator=(const AdcDual&); }; + +#endif // F446_ADC_DUAL_HPP + +#ifndef F446_ADC_SINGLE_HPP +#define F446_ADC_SINGLE_HPP + + class AdcSingle + { + public: + // Constructor + // frequency: sampling frequency + explicit AdcSingle(int frequency); + + virtual void Read(float &ad); + + virtual void Read(uint16_t &ad); + + protected: + float ToFloat(uint16_t x) + { return AMP_*(x - 2048); } + + private: + static const float AMP_ = 1.0f/2048.0f; + static const uint32_t EOC2_ = ADC_CSR_EOC2; + + // waiting ADC conversion + void WaitDone() + { while((ADC->CSR & EOC2_) != EOC2_); } + + // Set timer(TIM() for trigger for ADC + void SetTim8(int frequency); + + // for inhibition of copy constructor + AdcSingle(const AdcSingle&); + // for inhibition of substitute operator + AdcSingle& operator=(const AdcSingle&); + }; + +#endif // F446_ADC_SINGLE_HPP } -#endif // F446_ADC_DUAL_HPP +
diff -r d1da91aec62f -r 03e91e464ce5 F446_ADC_Interrupt.hpp --- a/F446_ADC_Interrupt.hpp Mon Jan 30 08:12:44 2017 +0000 +++ b/F446_ADC_Interrupt.hpp Sun Feb 05 07:59:14 2017 +0000 @@ -9,13 +9,14 @@ // 2016/11/12, Copyright (c) 2016 MIKAMI, Naoki //---------------------------------------------------------- -#ifndef F446_ADC_DUAL_INTERRUPT_HPP -#define F446_ADC_DUAL_INTERRUPT_HPP - #include "F446_ADC.hpp" namespace Mikami { + +#ifndef F446_ADC_DUAL_INTERRUPT_HPP +#define F446_ADC_DUAL_INTERRUPT_HPP + class AdcDual_Intr : public AdcDual { public: @@ -52,5 +53,47 @@ // for inhibition of substitute operator AdcDual_Intr& operator=(const AdcDual_Intr&); }; + +#endif // F446_ADC_DUAL_INTERRUPT_HPP + +//------------------------------------------------------------------------------ + +#ifndef F446_ADC_SINGLE_INTERRUPT_HPP +#define F446_ADC_SINGLE_INTERRUPT_HPP + + class AdcSingle_Intr : public AdcSingle + { + public: + AdcSingle_Intr(int frequency) : AdcSingle(frequency) + { ADC2->CR1 |= ADC_CR1_EOCIE; } + + virtual void Read(float &ad) + { + ad = ToFloat(ADC2->DR); + } + + virtual void Read(uint16_t &ad) + { + ad = ADC2->DR; + } + + // Set interrupt vector and enable IRQ of ADC + void SetIntrVec(void (*Func)()) + { + NVIC_SetVector(ADC_IRQn, (uint32_t)Func); // See "cmsis_nvic.h" + NVIC_EnableIRQ(ADC_IRQn); // See "core_cm4.h" + } + + void DisableAdcIntr() + { NVIC_DisableIRQ(ADC_IRQn); } + + private: + // for inhibition of copy constructor + AdcSingle_Intr(const AdcSingle_Intr&); + // for inhibition of substitute operator + AdcSingle_Intr& operator=(const AdcSingle_Intr&); + }; +#endif // F446_ADC_SINGLE_INTERRUPT_HPP + } -#endif // F446_ADC_DUAL_INTERRUPT_HPP +