Ср янв 26, 2022 01:01:28
Ср янв 26, 2022 01:27:58
Ср янв 26, 2022 08:14:05
так я и потерял... профессионально (т.е. по должности) я программировал (недолго) еще в те времена, когда написание программ на ассемблере для MS DOS было вполне естественным... а потом увы.ПростоНуб писал(а):в IT, если даже всего год не учиться ничему новому, квалификацию теряешь заметно
Ср янв 26, 2022 09:02:23
.data :
{
. = ALIGN(4);
_sdata = .;
*(.data)
*(.data*)
. = ALIGN(4);
_edata = .;
} > SRAM
#ifndef __DEBUG_SRAM__
extern uint32_t _sidata[], _sdata[], _edata[];
for (volatile uint32_t *pSrc = _sidata, *pDst = _sdata; pDst != _edata; *pDst ++= *pSrc++) ;
#endif
Ср янв 26, 2022 20:40:28
Ср янв 26, 2022 20:51:57
Ср янв 26, 2022 22:21:38
Пробовал. Это долго. Понадобилось около 2-ух месяцев нахождения на солнце.ПростоНуб писал(а):тогда уж солнышком.
linkov1959 писал(а):сваркой
Чт янв 27, 2022 05:26:05
Чт янв 27, 2022 09:15:26
/*----------
Reset Handler called on controller reset
*----------*/
void Reset_Handler(void)
{
SystemInit(); /* CMSIS System Initialization */
__PROGRAM_START(); /* Enter PreMain (C library entry point) */
}
а я то думал, но по чему из ram толком ни чего не работает.VladislavS писал(а):что при выполнении кода из RAM
Чт янв 27, 2022 10:34:18
Чт янв 27, 2022 12:50:23
Dimon456 писал(а):И где само копирование? Самому ручками прописывать?
Пт апр 22, 2022 19:36:27
Пт апр 22, 2022 19:49:24
Пт апр 22, 2022 20:23:40
делать функцию расчёта частоты работы МК.
Пт апр 22, 2022 20:52:36
делать функцию расчёта частоты работы МК.
Всё в виде научного эксперимента В рамках изучения STM32 =)VladislavS писал(а):Все делители в конце концов ложатся в регистры RCC. Оттуда их можно читать. Только пустое это. Зачем вычислять то что вы сами же и задаёта?
Пт апр 22, 2022 21:12:27
Пт апр 22, 2022 21:18:28
Вс май 01, 2022 21:45:21
#pragma once
#define DEBUG_USART1 1
#define SOME_FUNC 1
#define LED_FLASH 1
extern volatile uint32_t uwTick;
#define ChDataBits (8u)
#define ChDataSize (1u << ChDataBits)
typedef struct {
uint16_t ch0;
uint16_t ch1;
} ChData_TypeDef;
extern volatile ChData_TypeDef ChData[ChDataSize];
extern volatile uint16_t adcRawCh0, adcRawCh1;
void initRCC(void);
void initGPIO(void);
void initADC1(void);
void calADC1(void);
void stopADC1(void);
void startADC1(void* pData, uint16_t num, uint32_t ch, uint8_t stime);
#ifdef SOME_FUNC
void delayMs(uint32_t delay);
uint16_t scmADC1(uint32_t ch);
#endif
#ifdef DEBUG_USART1
extern char aText[64];
void initUSART1(void);
void postsz(char* pSz);
void sendsz(char* pSz);
void sendc(char c);
#endif
#include <stdint.h>
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
#include <inttypes.h>
#include "stm32f0xx.h"
#include "main.h"
volatile ChData_TypeDef ChData[ChDataSize];
volatile uint16_t adcRawCh0 = 0, adcRawCh1 = 0;
// DMA1 Channel 2 and Channel 3 interrupt handler
void DMA1_Channel2_3_IRQHandler(void)
{
// A Transfer Complete or Transfer Error flag
if(READ_BIT(DMA1->ISR, DMA_ISR_TCIF2 | DMA_ISR_TEIF2) != RESET) {
// Disable DMA1 Channel2
CLEAR_BIT(DMA1_Channel2->CCR, DMA_CCR_EN);
// Channel2 clear interrupt flags
SET_BIT(DMA1->IFCR, DMA_IFCR_CGIF2 | DMA_IFCR_CTCIF2 | DMA_IFCR_CHTIF2 | DMA_IFCR_CTEIF2);
// average calc
uint32_t sch0 = 0, sch1 = 0;
ChData_TypeDef* pch = (ChData_TypeDef*)ChData;
for(uint16_t i = 0; i < (sizeof(ChData)/(sizeof(ChData[0]))); i++, pch++) {
sch0 += pch->ch0;
sch1 += pch->ch1;
}
sch0 += (sizeof(ChData)/(sizeof(ChData[0]))) >> 1;
sch1 += (sizeof(ChData)/(sizeof(ChData[0]))) >> 1;
adcRawCh0 = sch0 >> ChDataBits;
adcRawCh1 = sch1 >> ChDataBits;
}
}
int main(void)
{
initRCC();
initGPIO();
#ifdef DEBUG_USART1
initUSART1();
#endif
initADC1();
memset((void*)ChData, 0, sizeof(ChData));
#ifdef LED_FLASH
SET_BIT(GPIOB->BSRR, GPIO_BSRR_BS_1);
#endif
#ifdef DEBUG_USART1
postsz("\r\nStart!\r\n\r\n");
#endif
uint32_t uwAdcMs = uwTick;
uint32_t uwCalcMs = uwTick;
#ifdef LED_FLASH
uint32_t uwLedMs = uwTick;
#endif
while(1) {
if(uwTick - uwAdcMs >= 100u) { // every 100 msec
uwAdcMs = uwTick;
startADC1((void*)ChData,
(sizeof(ChData)/(sizeof(ChData[0])) << 1),
ADC_CHSELR_CHSEL1 | ADC_CHSELR_CHSEL0,
ADC_SMPR_SMP_2 | ADC_SMPR_SMP_1); // tCONV = 6 usec
}
if(uwTick - uwCalcMs >= 500u) { // every 500 msec
uwCalcMs = uwTick;
sprintf(aText, "%u\t%u\r\n", adcRawCh0, adcRawCh1);
postsz(aText);
}
#ifdef LED_FLASH
if(uwTick - uwLedMs >= 500u) { // every 500 msec
uwLedMs = uwTick;
SET_BIT(GPIOB->BSRR, READ_BIT(GPIOB->IDR, GPIO_IDR_1) ? GPIO_BSRR_BR_1 : GPIO_BSRR_BS_1);
}
#endif
}
}
// GPIO initialization
void initGPIO(void)
{
// I/O port A, B, F clock enable
SET_BIT(RCC->AHBENR, RCC_AHBENR_GPIOAEN | RCC_AHBENR_GPIOBEN | RCC_AHBENR_GPIOFEN);
// ADC1: PORTA0 (NTC0), PORTA1 (NTC1) Analog mode
SET_BIT(GPIOA->MODER, GPIO_MODER_MODER0 | GPIO_MODER_MODER1);
#ifdef LED_FLASH
// PORTB1: General purpose output mode (LED)
MODIFY_REG(GPIOB->MODER, GPIO_MODER_MODER1, GPIO_MODER_MODER1_0);
// PORTB1: push-pull
CLEAR_BIT(GPIOB->OTYPER, GPIO_OTYPER_OT_1);
// PORTB1: 2 MHz
CLEAR_BIT(GPIOB->OSPEEDR, GPIO_OSPEEDR_OSPEEDR1);
// PORTB1: No pull-up or pull-down
CLEAR_BIT(GPIOB->PUPDR, GPIO_PUPDR_PUPDR1);
#endif
#ifdef DEBUG_USART1
// USART1: PORTA9 (Tx), PORTA10 (Rx): Alternate function mode
MODIFY_REG(GPIOA->MODER, GPIO_MODER_MODER9 | GPIO_MODER_MODER10, GPIO_MODER_MODER9_1 | GPIO_MODER_MODER10_1);
// PORTA9 (Tx), PORTA10 (Rx): Output push-pull
CLEAR_BIT(GPIOA->OTYPER, GPIO_OTYPER_OT_9 | GPIO_OTYPER_OT_10);
// PORTA9 (Tx), PORTA10 (Rx): 50 MHz
SET_BIT(GPIOA->OSPEEDR, GPIO_OSPEEDR_OSPEEDR9_0 | GPIO_OSPEEDR_OSPEEDR9_1 | GPIO_OSPEEDR_OSPEEDR10_0 | GPIO_OSPEEDR_OSPEEDR10_1);
// PORTA9 (Tx): No pull-up or pull-down, PORTA10 (Rx): Pull-up
MODIFY_REG(GPIOA->PUPDR, GPIO_PUPDR_PUPDR9 | GPIO_PUPDR_PUPDR10, GPIO_PUPDR_PUPDR10_0);
// PORTA9 (Tx), PORTA10 (Rx): Alternate function AF1
MODIFY_REG(GPIOA->AFR[1], GPIO_AFRH_AFSEL9 | GPIO_AFRH_AFSEL10, (1UL << GPIO_AFRH_AFSEL9_Pos) | (1UL << GPIO_AFRH_AFSEL10_Pos));
#endif
}
// ADC stop
void stopADC1(void)
{
// ADC group regular conversion stop
if(READ_BIT(ADC1->CR, ADC_CR_ADSTART) != RESET) {
SET_BIT(ADC1->CR, ADC_CR_ADSTP);
// wait for ADC group regular conversion stop
while(READ_BIT(ADC1->CR, ADC_CR_ADSTP) != RESET);
}
}
// ADC start
void startADC1(void* pData, uint16_t num, uint32_t ch, uint8_t stime)
{
// ADC stop
stopADC1();
// Sampling time selection, Fadc = 14 MHz
// SMP Sampling tCONV,
// time,ADCcycles usec
// 000 1,5 1,00
// 001 7,5 1,43
// 010 13,5 1,86
// 011 28,5 2,93
// 100 41,5 3,86
// 101 55,5 4,86
// 110 71,5 6,00
// 111 239,5 18,00
MODIFY_REG(ADC1->SMPR, ADC_SMPR_SMP, stime);
// ADC channel selection
MODIFY_REG(ADC1->CHSELR, ADC_CHSELR_CHSEL, ch);
// Analog watchdog disabled, ADC group regular sequencer discontinuous mode disabled,
// ADC low power auto power off disabled, Wait conversion mode off,
// DR register is preserved with the old data when an overrun is detected,
// Hardware trigger detection disabled, Right alignment, Data resolution 12 bits,
// Scan sequence direction Upward, DMA one shot mode selected,
// Continuous conversion mode enabled, DMA enabled
MODIFY_REG(ADC1->CFGR1, ADC_CFGR1_AWD1EN | ADC_CFGR1_DISCEN | ADC_CFGR1_AUTOFF | ADC_CFGR1_WAIT |
ADC_CFGR1_OVRMOD | ADC_CFGR1_EXTEN | ADC_CFGR1_ALIGN | ADC_CFGR1_RES | ADC_CFGR1_SCANDIR | ADC_CFGR1_DMACFG,
ADC_CFGR1_CONT | ADC_CFGR1_DMAEN);
// DMA
// wait DMA1 Channel2 Transfer Complete flag
if(READ_BIT(DMA1_Channel2->CCR, DMA_CCR_EN) != RESET)
// wait for Transfer Complete or Transfer Error flag
while(READ_BIT(DMA1->ISR, DMA_ISR_TCIF2 | DMA_ISR_TEIF2) == RESET);
// Disable DMA1 Channel2
CLEAR_BIT(DMA1_Channel2->CCR, DMA_CCR_EN);
// ADC DMA remap to DMA1 Chanel2
SET_BIT(SYSCFG->CFGR1, SYSCFG_CFGR1_ADC_DMA_RMP);
// Configure the peripheral address register
WRITE_REG(DMA1_Channel2->CPAR, (uint32_t)&(ADC1->DR));
// Configure the memory address
WRITE_REG(DMA1_Channel2->CMAR, (uint32_t)pData);
// Configure the number of DMA tranfer to be performs on channel
MODIFY_REG(DMA1_Channel2->CNDTR, 0xffffu, num);
// Channel priority level 01 Medium, Peripheral & Memory size 01 16-bits,
// Memory increment mode 1 enabled, Data transfer direction 0 Read from peripheral
// Circular mode disabled, Transfer complete interrupt enabled
MODIFY_REG(DMA1_Channel2->CCR, DMA_CCR_MEM2MEM | DMA_CCR_PL | DMA_CCR_MSIZE | DMA_CCR_PSIZE |
DMA_CCR_PINC | DMA_CCR_CIRC | DMA_CCR_DIR | DMA_CCR_TEIE | DMA_CCR_HTIE | DMA_CCR_EN,
DMA_CCR_PL_0 | DMA_CCR_MSIZE_0 | DMA_CCR_PSIZE_0 | DMA_CCR_MINC | DMA_CCR_TCIE);
// ADC group regular conversion start
SET_BIT(ADC1->CR, ADC_CR_ADSTART);
// Enable DMA1 Channel2
SET_BIT(DMA1_Channel2->CCR, DMA_CCR_EN);
// DMA1 Channel2 (ADC) and Channel3 interrupt enable
NVIC_EnableIRQ(DMA1_Channel2_3_IRQn);
NVIC_SetPriority(DMA1_Channel2_3_IRQn, 2);
}
// ADC calibration
void calADC1(void)
{
// ADC disable
if(READ_BIT(ADC1->CR, ADC_CR_ADEN) != RESET) {
// ADC stop
stopADC1();
// ADC disable
SET_BIT(ADC1->CR, ADC_CR_ADDIS);
// wait for ADC1 disable
while(READ_BIT(ADC1->CR, ADC_CR_ADEN) != RESET);
}
// ADC DMA transfer disable
CLEAR_BIT(ADC1->CFGR1, ADC_CFGR1_DMAEN | ADC_CFGR1_DMACFG);
// ADC calibration
SET_BIT(ADC1->CR, ADC_CR_ADCAL);
// Wait until ADCAL=0
while(READ_BIT(ADC1->CR, ADC_CR_ADCAL) != RESET);
// ADC Enable
// Clear the ADRDY bit
if(READ_BIT(ADC1->ISR, ADC_ISR_ADRDY) != RESET)
SET_BIT(ADC1->ISR, ADC_ISR_ADRDY);
// ADC enable
SET_BIT(ADC1->CR, ADC_CR_ADEN);
// wait for ADC ready flag
while(READ_BIT(ADC1->ISR, ADC_ISR_ADRDY) == RESET);
}
// ADC initialization
void initADC1(void)
{
// HSI14 clock request from ADC disable
SET_BIT(RCC->CR2, RCC_CR2_HSI14DIS);
// Internal High Speed 14MHz clock enable
SET_BIT(RCC->CR2, RCC_CR2_HSI14ON);
// wait for Internal High Speed 14MHz clock ready
while(READ_BIT(RCC->CR2, RCC_CR2_HSI14RDY) == RESET);
// Internal High Speed 14MHz clock enable
CLEAR_BIT(RCC->CR2, RCC_CR2_HSI14DIS);
// ADCCLK (Asynchronous clock mode), generated at product level (refer to RCC section)
CLEAR_BIT(ADC1->CFGR2, RCC_CFGR2_PREDIV);
// ADC1 clock enable
SET_BIT(RCC->APB2ENR, RCC_APB2ENR_ADCEN);
// ADC calibration
calADC1();
}
volatile uint32_t uwTick = 0;
// SysTick interrupt handler
void SysTick_Handler(void)
{
uwTick++;
}
// RCC initialization
void initRCC(void)
{
// SYSCFG and comparator clock enable
SET_BIT(RCC->APB2ENR, RCC_APB2ENR_SYSCFGCOMPEN);
// Flash Latency: One wait state, if 24 MHz < SYSCLK ≤ 48 MHz
SET_BIT(FLASH->ACR, FLASH_ACR_LATENCY);
// Enable the Internal High Speed oscillator (HSI)
SET_BIT(RCC->CR, RCC_CR_HSION);
while(READ_BIT(RCC->CR, RCC_CR_HSIRDY) == RESET);
// Disable the main PLL
CLEAR_BIT(RCC->CR, RCC_CR_PLLON);
while(READ_BIT(RCC->CR, RCC_CR_PLLRDY) != RESET);
// PLL HSI /2 x12
MODIFY_REG(RCC->CFGR, RCC_CFGR_PLLSRC | RCC_CFGR_PLLMUL, RCC_CFGR_PLLSRC_HSI_DIV2|RCC_CFGR_PLLMUL12);
MODIFY_REG(RCC->CFGR2, RCC_CFGR2_PREDIV, RCC_CFGR2_PREDIV_DIV1);
// Enable the PLL
SET_BIT(RCC->CR, RCC_CR_PLLON);
while(READ_BIT(RCC->CR, RCC_CR_PLLRDY) == RESET);
// HCLK and PCLK: no prescaler, System clock: PLL 48 MHz
MODIFY_REG(RCC->CFGR, RCC_CFGR_HPRE | RCC_CFGR_PPRE | RCC_CFGR_SW, RCC_CFGR_HPRE_DIV1 | RCC_CFGR_PPRE_DIV1 | RCC_CFGR_SW_PLL);
// PLL used as system clock
while(READ_BIT(RCC->CFGR, RCC_CFGR_SWS) != RCC_CFGR_SWS_PLL);
// set system variable SystemCoreClock to current clock value
SystemCoreClockUpdate();
// set SysTick timer to 1 ms delay
SysTick_Config(SystemCoreClock / 1000);
// DMA1 clock enable
SET_BIT(RCC->AHBENR, RCC_AHBENR_DMAEN);
}
#ifdef SOME_FUNC
// set delay in miliseconds using sysTick timer
void delayMs(uint32_t delay)
{
uint32_t uwT0 = uwTick;
while(uwTick - uwT0 < delay);
}
uint16_t scmADC1(uint32_t ch)
{
// ADC stop
stopADC1();
// Sampling time selection
MODIFY_REG(ADC1->SMPR, ADC_SMPR_SMP, ADC_SMPR_SMP_2);
// Analog watchdog disabled, ADC group regular sequencer discontinuous mode disabled,
// ADC low power auto power off disabled, Wait conversion mode off,
// Continuous conversion mode disabled, DR register is preserved with the old data when an overrun is detected,
// Hardware trigger detection disabled, Right alignment, Data resolution 12 bits,
// Scan sequence direction Upward, DMA one shot mode selected, DMA disabled
CLEAR_BIT(ADC1->CFGR1, ADC_CFGR1_AWD1EN | ADC_CFGR1_DISCEN | ADC_CFGR1_AUTOFF | ADC_CFGR1_WAIT |
ADC_CFGR1_CONT | ADC_CFGR1_OVRMOD | ADC_CFGR1_EXTEN | ADC_CFGR1_ALIGN | ADC_CFGR1_RES |
ADC_CFGR1_SCANDIR | ADC_CFGR1_DMACFG | ADC_CFGR1_DMAEN);
// ADC channel selection
MODIFY_REG(ADC1->CHSELR, ADC_CHSELR_CHSEL, ch);
// ADC group regular conversion start
SET_BIT(ADC1->CR, ADC_CR_ADSTART);
// ADC group regular end of unitary conversion flag
while(READ_BIT(ADC1->ISR, ADC_ISR_EOC) == RESET);
// ADC data register
return (uint16_t)(READ_REG(ADC1->DR) & 0xffffu);
}
#endif
#ifdef DEBUG_USART1
char aText[64];
// USART initialization
void initUSART1(void)
{
// System clock (SYSCLK) selected as USART1 clock
MODIFY_REG(RCC->CFGR3, RCC_CFGR3_USART1SW, RCC_CFGR3_USART1SW_SYSCLK);
// USART1 clock enable
SET_BIT(RCC->APB2ENR, RCC_APB2ENR_USART1EN);
// USART1: Baud rate 115200 for standard USART (oversampling by 16, OVER8 = 0)
MODIFY_REG(USART1->BRR, 0xffffu, 417u);
// USART1: DMA Enable Transmitter
SET_BIT(USART1->CR3, USART_CR3_DMAT);
// USART1: 1 stop bit, CK pin disabled,
// USART1->CR2 = 0;
// USART1: 1 Start bit, 8 data bits, Parity control disabled, Oversampling by 16,
// Transmitter Enable, Receiver Enable, USART1 Enable | USART_CR1_RE
SET_BIT(USART1->CR1, USART_CR1_TE | USART_CR1_UE);
}
void postsz(char* pSz)
{
// wait DMA1 Channel4 Transfer Complete flag
if(READ_BIT(DMA1_Channel4->CCR, DMA_CCR_EN))
// wait for Transfer Complete or Transfer Error flag
while(READ_BIT(DMA1->ISR, DMA_ISR_TCIF4 | DMA_ISR_TEIF4) == RESET);
// Disable DMA1 Channel4
CLEAR_BIT(DMA1_Channel4->CCR, DMA_CCR_EN);
// Remap (USART1_TX DMA request mapped on DMA channel 4)
SET_BIT(SYSCFG->CFGR1, SYSCFG_CFGR1_USART1TX_DMA_RMP);
// Configure the peripheral address register
WRITE_REG(DMA1_Channel4->CPAR, (uint32_t)&(USART1->TDR));
// Configure the memory address
WRITE_REG(DMA1_Channel4->CMAR, (uint32_t)pSz);
// Configure the number of DMA tranfer to be performs on channel
WRITE_REG(DMA1_Channel4->CNDTR, strlen(pSz));
// Channel priority level 00 Low, Peripheral & Memory size 00 8-bits,
// Memory increment mode 1 enabled, Data transfer direction 1: Read from memory
MODIFY_REG(DMA1_Channel4->CCR, DMA_CCR_MEM2MEM | DMA_CCR_PL | DMA_CCR_MSIZE | DMA_CCR_PSIZE |
DMA_CCR_PINC | DMA_CCR_CIRC | DMA_CCR_TEIE | DMA_CCR_HTIE | DMA_CCR_TCIE | DMA_CCR_EN,
DMA_CCR_MINC | DMA_CCR_DIR);
// Enable DMA1 Channel4
SET_BIT(DMA1_Channel4->CCR, DMA_CCR_EN);
}
void sendsz(char* pSz)
{
if(pSz)
while(*pSz)
sendc(*pSz++);
}
void sendc(char c)
{
// wait
if(READ_BIT(DMA1_Channel4->CCR, DMA_CCR_EN))
// wait DMA1 Channel4 Transfer Complete flag
while(READ_BIT(DMA1->ISR, DMA_ISR_TCIF4 | DMA_ISR_TEIF4) == RESET);
else
// Wait Transmit Data Register Empty
while(READ_BIT(USART1->ISR, USART_ISR_TXE) == RESET);
USART1->TDR = c;
}
#endif
Пн май 02, 2022 10:37:12
uint32_t tmp = __get_PRIMASK();
__disable_irq();
// код
__set_PRIMASK(tmp);
Пн май 02, 2022 10:55:14