Обновление до версии 0.3.0

- обновлен elbear_fw_bootloader - добавлена проверка контрольной суммы каждой строки hex файла.
- в модуль работы с АЦП добавлена функция analogReadResolution(). Функция analogRead() теперь возвращает усредненное по 10 измерениям значение.
- общая функция обработки прерываний перенесена в память RAM. Обработчики прерываний модулей External Interrupts и Advanced I/O (функция tone()) так же перенесены в память RAM для увеличения скорости выполнения кода.
- в пакет добавлены библиотеки EEPROM, Servo, SoftSerial, NeoPixel, MFRC522 адаптированные для работы с платой Elbear Ace-Uno.
- добавлено описание особенностей работы с пакетом
This commit was merged in pull request #6.
This commit is contained in:
klassents committed 2024-10-17 08:27:39 +03:00
1 parent 7a7c552743
commit 766b7b32ea
114 files changed
+11064 -666

No files matched your search

+45 -89
View File
@@ -2,10 +2,11 @@
#include "mik32_hal_spi.h"
SPI_HandleTypeDef hspi;
bool newConfig = false;
bool isInited = false;
uint32_t currentSpeed = 0;
int8_t currentDataOrder = -1;
int8_t currentDataOrder = MSBFIRST;
int8_t currentDataMode = -1;
static uint8_t reverse_bits(uint8_t byte);
@@ -31,16 +32,10 @@ void SPISettings::spiUpdateSettings(uint32_t speedMaximum, uint8_t dataOrder, ui
}
// if break didn't call in cycle, it will be the greatest divRegVal (and divider)
// update config
hspi.Instance = SPI_1;
hspi.Init.SPI_Mode = HAL_SPI_MODE_MASTER; // only master mode
// update params in struct
hspi.Init.CLKPhase = dataMode & 0b00000001;
hspi.Init.CLKPolarity = (dataMode & 0b00000010)>>1;
hspi.Init.ThresholdTX = 4;
hspi.Init.BaudRateDiv = divRegVal;
hspi.Init.Decoder = SPI_DECODER_NONE;
hspi.Init.ManualCS = SPI_MANUALCS_ON;
hspi.Init.ChipSelect = SPI_CS_NONE;
currentSpeed = speedMaximum;
currentDataOrder = dataOrder;
@@ -50,9 +45,6 @@ void SPISettings::spiUpdateSettings(uint32_t speedMaximum, uint8_t dataOrder, ui
}
// ------------------------------------------------------------------ //
// pins shift in gpio register
#define PIN_1_3_GPIO_S 3
#define PIN_1_4_GPIO_S 4
SPIClass SPI;
bool SPIClass::spiInUse = false;
@@ -61,42 +53,19 @@ uint8_t SPIClass::interruptMask = 0;
void SPIClass::begin()
{
// there is a seller on pin 1.6 which replace D10 from spi NSS pin 1.3 to pin 1.4,
// because spi needs pin 1.3 for correct work
// replace config from 1.3 to 1.4
uint8_t config = ((PAD_CONFIG->PORT_1_CFG) & (0b11<<(2*PIN_1_3_GPIO_S))) >> (2*PIN_1_3_GPIO_S);
if (config == 0) // common gpio
{
// pin direction
uint8_t direction = ((GPIO_1->DIRECTION_IN) & (1<<PIN_1_3_GPIO_S)) >> PIN_1_3_GPIO_S;
if (direction == 1) // input
GPIO_1->DIRECTION_IN |= (1<<PIN_1_4_GPIO_S);
else // output
GPIO_1->DIRECTION_OUT |= (1<<PIN_1_4_GPIO_S);
spi_onBegin();
// pull up/down
uint8_t pupd_1_3 = ((PAD_CONFIG ->PORT_1_PUPD) & (0b11<<(2*PIN_1_3_GPIO_S))) >> (2*PIN_1_3_GPIO_S);
PAD_CONFIG ->PORT_1_PUPD &= (~(0b11<<(2*PIN_1_4_GPIO_S))); // clear
PAD_CONFIG ->PORT_1_PUPD |= ((pupd_1_3&0b11)<<(2*PIN_1_4_GPIO_S)); // set new
//current state
uint8_t state1_3 = ((GPIO_1->OUTPUT_) & (1<<PIN_1_3_GPIO_S)) >> PIN_1_3_GPIO_S;
GPIO_1->OUTPUT_ &= (~(0b1<<PIN_1_4_GPIO_S)); // clear
GPIO_1->OUTPUT_ |= ((state1_3&0b1)<<PIN_1_4_GPIO_S); // set new
}
else if(config == 2) // timer for pwm
{
// if D10 (spi NSS pin) was used as pwm, we need to stop timer,
// because 1.4 don't support timer
analogWriteStop(10);
ErrorMsgHandler("analogWrite(): D10 cannot be used as PWM pin while SPI is running");
}
// switch seller to pin 1.4
HAL_GPIO_PinConfig(GPIO_1, GPIO_PIN_6, HAL_GPIO_MODE_GPIO_OUTPUT, HAL_GPIO_PULL_NONE, HAL_GPIO_DS_2MA);
HAL_GPIO_WritePin(GPIO_1, GPIO_PIN_6, GPIO_PIN_HIGH);
blockSpiPin();
// set constant parameters in spi struct
hspi.Instance = SPI_1;
hspi.Init.SPI_Mode = HAL_SPI_MODE_MASTER; // only master mode used
hspi.Init.ThresholdTX = 4;
hspi.Init.Decoder = SPI_DECODER_NONE;
hspi.Init.ManualCS = SPI_MANUALCS_ON;
hspi.Init.ChipSelect = SPI_CS_NONE;
// adjustable parameters default values as in SPISettings()
hspi.Init.BaudRateDiv = SPI_CLOCK_DIV8;
hspi.Init.CLKPhase = SPI_MODE0 & 0b00000001;
hspi.Init.CLKPolarity = (SPI_MODE0 & 0b00000010)>>1;
spiInUse = true;
}
@@ -113,31 +82,9 @@ void SPIClass::end()
{
HAL_GPIO_PinConfig(GPIO_1, (HAL_PinsTypeDef)(GPIO_PIN_0 | GPIO_PIN_1 | GPIO_PIN_2),
HAL_GPIO_MODE_GPIO_INPUT, HAL_GPIO_PULL_NONE, HAL_GPIO_DS_2MA);
}
}
// return D10 with common gpio config to pin 1.3
PAD_CONFIG->PORT_1_CFG &= (~(0b11<<(2*PIN_1_3_GPIO_S))); // set config to 0 - common gpio mode
// pin direction
uint8_t direction = ((GPIO_1->DIRECTION_IN) & (1<<PIN_1_4_GPIO_S)) >> PIN_1_4_GPIO_S;
if (direction == 1) // input
GPIO_1->DIRECTION_IN |= (1<<PIN_1_3_GPIO_S);
else // output
GPIO_1->DIRECTION_OUT |= (1<<PIN_1_3_GPIO_S);
// pull up/down
uint8_t pupd_1_4 = ((PAD_CONFIG ->PORT_1_PUPD) & (0b11<<(2*PIN_1_4_GPIO_S))) >> (2*PIN_1_4_GPIO_S);
PAD_CONFIG ->PORT_1_PUPD &= (~(0b11<<(2*PIN_1_3_GPIO_S))); // clear
PAD_CONFIG ->PORT_1_PUPD |= ((pupd_1_4&0b11)<<(2*PIN_1_3_GPIO_S)); // set new
// current state
uint8_t state1_4 = ((GPIO_1->OUTPUT_) & (1<<PIN_1_4_GPIO_S)) >> PIN_1_4_GPIO_S;
GPIO_1->OUTPUT_ &= (~(0b1<<PIN_1_3_GPIO_S)); // clear
GPIO_1->OUTPUT_ |= ((state1_4&0b1)<<PIN_1_3_GPIO_S); // set new
// switch seller back to pin 1.3
HAL_GPIO_WritePin(GPIO_1, GPIO_PIN_6, GPIO_PIN_LOW);
unblockSpiPin();
spi_onEnd();
spiInUse = false;
isInited = false;
@@ -299,35 +246,44 @@ void SPIClass::endTransaction(void)
// ------------------------------------ //
void SPIClass::setBitOrder(uint8_t bitOrder)
{
currentDataOrder = bitOrder;
if (spiInUse)
currentDataOrder = bitOrder;
else
ErrorMsgHandler("SPI.setBitOrder():SPI.begin() need to be called first");
}
void SPIClass::setDataMode(uint8_t dataMode)
{
uint32_t config = hspi.Instance->CONFIG;
HAL_SPI_Disable(&hspi);
hspi.Init.CLKPhase = dataMode & 0b00000001;
hspi.Init.CLKPolarity = (dataMode & 0b00000010)>>1;
config &= ~((1 << SPI_CONFIG_CLK_PH_S) | (1 << SPI_CONFIG_CLK_POL_S)); // clear
config |= ((hspi.Init.CLKPhase << SPI_CONFIG_CLK_PH_S) |
(hspi.Init.CLKPolarity << SPI_CONFIG_CLK_POL_S)); // set new
hspi.Instance->CONFIG = config;
HAL_SPI_Enable(&hspi);
if (spiInUse)
{
hspi.Init.CLKPhase = (dataMode&0b00000001);
hspi.Init.CLKPolarity = (dataMode&0b00000010)>>1;
HAL_SPI_Set_Clock_Mode(&hspi);
currentDataMode = dataMode;
}
else
ErrorMsgHandler("SPI.setDataMode():SPI.begin() need to be called first");
}
void SPIClass::setClockDivider(uint8_t clockDiv)
{
// if divider is in valid range
if ((clockDiv >= SPI_CLOCK_DIV4) && (clockDiv <= SPI_CLOCK_DIV256))
if (spiInUse)
{
uint32_t config = hspi.Instance->CONFIG;
HAL_SPI_Disable(&hspi);
hspi.Init.BaudRateDiv = clockDiv;
config &= ~(0b111 << SPI_CONFIG_BAUD_RATE_DIV_S); // clear
config |= (hspi.Init.BaudRateDiv << SPI_CONFIG_BAUD_RATE_DIV_S); // set new
hspi.Instance->CONFIG = config;
HAL_SPI_Enable(&hspi);
// if divider is valid
if ((clockDiv == SPI_CLOCK_DIV4) || (clockDiv == SPI_CLOCK_DIV8) ||
(clockDiv == SPI_CLOCK_DIV16) || (clockDiv == SPI_CLOCK_DIV32) ||
(clockDiv == SPI_CLOCK_DIV64) || (clockDiv == SPI_CLOCK_DIV128) ||
(clockDiv == SPI_CLOCK_DIV256))
{
hspi.Init.BaudRateDiv = clockDiv;
currentSpeed = F_CPU >> (clockDiv+1);
HAL_SPI_Set_Clock_Divider(&hspi);
}
else
ErrorMsgHandler("SPI.setClockDivider(): Invalid clock devider");
}
else
ErrorMsgHandler("SPI.setClockDivider():SPI.begin() need to be called first");
}
static uint8_t reverse_bits(uint8_t byte)