Потенциальный источник ошибок. Лучше правую часть приводить к левой:*(T*)&SPI1->DR = data;
"*(volatile uint16_t*)&SPI1->DR = cd;" => "SPI1->DR = (decltype(SPI1->DR))cd;" или просто "SPI1->DR = (uint16_t)cd;"; эстеты могут использовать static_cast.
Потенциальный источник ошибок. Лучше правую часть приводить к левой:*(T*)&SPI1->DR = data;
Код: Выделить всё
*(uint8_t *)&SPI1->DR = 0xA0;
*(uint8_t *)&SPI1->DR = 0xA1;
*(uint8_t *)&SPI1->DR = 0xA2;
*const_cast<uint8_t *>((uint8_t *)&SPI1->DR) = 0xA3;
*const_cast<uint8_t *>((uint8_t *)&SPI1->DR) = 0xA4;
*const_cast<uint8_t *>((uint8_t *)&SPI1->DR) = 0xA5;
*(volatile uint8_t *)&SPI1->DR = 0xA6;
*(volatile uint8_t *)&SPI1->DR = 0xA7;
*(volatile uint8_t *)&SPI1->DR = 0xA8;
Код: Выделить всё
/**
* @brief Transmits a Data through the SPIx/I2Sx peripheral.
* @param SPIx: where x can be
* - 1, 2 or 3 in SPI mode
* - 2 or 3 in I2S mode
* @param Data : Data to be transmitted.
* @retval None
*/
void SPI_I2S_SendData(SPI_TypeDef* SPIx, uint16_t Data)
{
/* Check the parameters */
assert_param(IS_SPI_ALL_PERIPH(SPIx));
/* Write in the DR register the data to be sent */
SPIx->DR = Data;
}
Сначала "убить" volatile приведением типа, а потом геройски найти решение. *КРУТОЧЁ*IAR делает 9 операций записи, GCC три. Комментарии излишни.
обрежется до необходимых 16 и 8 бит.
Хм-м-м... Тупая документация, на помойку её.25.5
SPI and I2S registers
Refer to Section 2.1 on page 46 for a list of abbreviations used in register descriptions.
The peripheral registers can be accessed by half-words (16-bit) or words (32-bit).
Код: Выделить всё
LDR.N R0,??DataTable1 ;; 0x4001300c
//*(volatile uint16_t *)&SPI1->DR = 0xAABB;
MOVW R1,#+43707
STRH R1,[R0, #+0]
//*(volatile uint8_t *)&SPI1->DR = 0xAA;
MOVS R2,#+170
STRB R2,[R0, #+0]
При использовании очереди. Да, не знал такой особенности. Наверное подсознательно берёгся от этого подблока с такой глупой логикой.РАЗНОЕ поведение блока SPI
Код: Выделить всё
if (hspi->TxXferCount > 1U)
{
/* write on the data register in packing mode */
hspi->Instance->DR = *((uint16_t *)pData);
pData += sizeof(uint16_t);
hspi->TxXferCount -= 2U;
}
else
{
*((__IO uint8_t *)&hspi->Instance->DR) = (*pData++);
hspi->TxXferCount--;
}
....
/* Set the Rx Fifo threshold */
if (hspi->Init.DataSize > SPI_DATASIZE_8BIT)
{
/* Set RX Fifo threshold according the reception data length: 16bit */
CLEAR_BIT(hspi->Instance->CR2, SPI_RXFIFO_THRESHOLD);
}
else
{
/* Set RX Fifo threshold according the reception data length: 8bit */
SET_BIT(hspi->Instance->CR2, SPI_RXFIFO_THRESHOLD);
}
Код: Выделить всё
template<uint32_t dmask>
static _inline_ void writeReg32(volatile uint32_t* reg, uint32_t value)
{
if constexpr (dmask == 0xFFFFFFFF)
*reg = value;
else if constexpr (dmask == 0x0000FFFF)
*(volatile uint16_t*)reg = value;
else if constexpr (dmask == 0xFFFF0000)
*((volatile uint16_t*)reg + 1) = value >> 16;
else if constexpr (dmask == 0x000000FF)
*(volatile uint8_t*)reg = value;
else if constexpr (dmask == 0x0000FF00)
*((volatile uint8_t*)reg + 1) = value >> 8;
else if constexpr (dmask == 0x00FF0000)
*((volatile uint8_t*)reg + 2) = value >> 16;
else if constexpr (dmask == 0xFF000000)
*((volatile uint8_t*)reg + 3) = value >> 24;
else
*reg = (*reg & ~dmask) | value;
}
Код: Выделить всё
*reg = (*reg & ~dmask) | (value & dmask);
слева!Код: Выделить всё
*reg = (*reg & ~((uint32_t)0x0000FFFF)) | (value & 0x0000FFFF)
слева!Код: Выделить всё
ConfigList<
PinMode::PushPull_MediumSpeed<0>,
PA3, PA5, PA7, PA12,
GpioB<0x3F>, PB13, PB14, PB15,
GpioC<0xF>, PC5, PC6, PC8, PC9, PC15,
PinMode::Floating,
PA0, PA1, PA2, PA4, PA6, PA10, PA11,
PB6, PB12, PC4, PC7,
PinMode::PullDown, PA13, PA14,
PinMode::AF_PushPull_MediumSpeed,
PA8, PA9, PA15,
PinMode::AF_OpenDrain_MediumSpeed,
PB8, PB9, PB10, PB11,
PinMode::AF_PushPull_HighSpeed, PB7,
PinMode::Floating, CfgCmd::AllUnusedPins
>::mode();Код: Выделить всё
LDR.N R2,??__low_level_init_0+0x2C ;; 0x40010004
LDR.N R3,??__low_level_init_0+0x30 ;; 0x14141444
LDR.N R4,??__low_level_init_0+0x34 ;; 0x98814499
LDR.N R5,??__low_level_init_0+0x38 ;; 0x836f0000
STR R3,[R2, #+2044]
STR R4,[R2, #+2048]
LDR.N R3,??__low_level_init_0+0x3C ;; 0x70a80000
LDR.N R4,??__low_level_init_0+0x40 ;; 0xb4111111
STR R3,[R2, #+2060]
STR R4,[R2, #+3068]
LDR.N R3,??__low_level_init_0+0x44 ;; 0x1114dddd
LDR.N R4,??__low_level_init_0+0x48 ;; 0xe03f0000
STR R3,[R2, #+3072]
STR R4,[R2, #+3084]
LDR.N R3,??__low_level_init_0+0x4C ;; 0x41141111
LDR.N R4,??__low_level_init_0+0x50 ;; 0x14444411
STR R3,[R2, #+4092]
LDR.N R3,??__low_level_init_0+0x54 ;; 0x40011004
STR R4,[R3, #+0]
STR R5,[R3, #+12]
В одной микросхеме?Shumadan писал(а):Нужно реализовать многоразрядный параллельный регистр в одном корпусе.