Ich arbeite derzeit an einem Projekt, in dem ich versuche, ein MCP4151-Digitalpotentiometer mit dem STM32F4-Discovery Board unter Verwendung der Mars Eclipse IDE zu verbinden. Ich habe den STM32F4xx HAL heruntergeladen und eingebunden, habe aber Schwierigkeiten, alle Pins und Einstellungen richtig zu bekommen.
Aus dem STM32F407-Datenblatt (Seite 49) konnte ich ableiten, dass ich PA5 und PA7 als Pins für SPI_SCK und SPI_MOSI verwenden möchte. Also habe ich den Code aus diesem Projekt geändert , um diese Pins zu aktivieren:
void SPI_Init(){
hspi1.Instance = SPI1;
hspi1.Init.Mode = SPI_MODE_MASTER;
hspi1.Init.Direction = SPI_DIRECTION_2LINES;
hspi1.Init.DataSize = SPI_DATASIZE_8BIT;
hspi1.Init.CLKPolarity = SPI_POLARITY_LOW;
hspi1.Init.CLKPhase = SPI_PHASE_1EDGE;
hspi1.Init.FirstBit = SPI_FIRSTBIT_MSB;
hspi1.Init.CRCCalculation = SPI_CRCCALCULATION_DISABLE;
hspi1.Init.NSS = SPI_NSS_SOFT;
hspi1.Init.BaudRatePrescaler = SPI_BAUDRATEPRESCALER_2;
HAL_SPI_Init(&hspi1);
/* Peripheral clock enable */
__SPI1_CLK_ENABLE();
GPIO_InitTypeDef GPIO_InitStruct;
/**SPI1 GPIO Configuration
PA5 ------> SPI1_SCK
PA7 ------> SPI1_MOSI
*/
GPIO_InitStruct.Pin = GPIO_PIN_5 | GPIO_PIN_7;
GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
GPIO_InitStruct.Pull = GPIO_NOPULL;
HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);
GPIO_InitStruct.Pin = GPIO_PIN_0; //Chip Select
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
GPIO_InitStruct.Pull = GPIO_PULLDOWN;
HAL_GPIO_Init(GPIOC, &GPIO_InitStruct);
__HAL_SPI_ENABLE(&hspi1);
}
Damit versuche ich die Werte am Potentiometer zu initialisieren mit:
void SPI_SendData(uint8_t* adress, uint8_t* data, uint16_t size, uint32_t timeout){
HAL_GPIO_WritePin(GPIOC, GPIO_PIN_0, GPIO_PIN_SET);
HAL_SPI_Transmit(&hspi1, adress, size, timeout);
while(HAL_SPI_GetState(&hspi1) == HAL_SPI_STATE_BUSY);
HAL_SPI_Transmit(&hspi1, data, size, timeout);
while(HAL_SPI_GetState(&hspi1) == HAL_SPI_STATE_BUSY);
HAL_GPIO_WritePin(GPIOC, GPIO_PIN_0, GPIO_PIN_RESET);
}
Und dann schreiben:
void POT_Init(){
uint8_t data = 0x00;
SPI_SendData(&STATUS_REGISTER_ADDRESS, &data, 8, 100); //Set SREG bit 1 to 0. Device is NOT in shutdown.
data = 0x0F;
SPI_SendData(&TCON_BIT_REGISTER_ADDRESS, &data, 8, 100); //Connect Wiper 0
data = 0x08;
SPI_SendData(&WIPER_0_REGISTER_ADDRESS, &data, 8, 100);
}
Das Problem ist, dass ich SCK und SDI/PA5 und PA7 sondiere und keine Bewegung über die Leitung sehe. Die beiden Geräte werden wie folgt verbunden:
Warum sehe ich also nichts? Ich gehe davon aus, dass etwas in meiner Init-Funktion fehlt, aber ich kann es nicht genau sagen und würde mich über einen zweiten Blick freuen.
Ich bin mir nicht sicher, ob das hilft, wenn man bedenkt, wie alt dieser Beitrag ist. Mir ist jedoch aufgefallen, dass Sie PA5 und PA7 als alternative Funktion festlegen, aber nicht wirklich angeben, welche alternative Funktion durch eine GPIO_InitStruct.Alternate-Zuweisung erfolgt.
Zunächst müssen Sie die Uhr für das SPI-Peripheriegerät aktivieren, bevor Sie versuchen, sie zu initialisieren. Zweitens, haben Sie auch die Uhr für die GPIO-Peripherie aktiviert?
(Ich habe nur STM32F103 verwendet, was zugegebenermaßen etwas anders sein könnte, aber ich bezweifle es)
Ich habe diesen Beitrag gefunden, als ich nach einem ähnlichen Beitrag gesucht habe, und festgestellt, dass es keine akzeptierte Antwort gibt, also habe ich beschlossen, eine Antwort zu schreiben (damit jeder mit einem ähnlichen Problem hoffentlich eine Lösung finden kann).
Bevor Sie SPI verwenden, sollten Sie einige Dinge beachten:
Allerdings gibt es ein paar Dinge, die ich erwähnen möchte.
Als erstes sehe ich, dass void SPI_SendData(uint8_t* adress, uint8_t* data, uint16_t size, uint32_t timeout)
du in deiner Funktion den Chip Select Pin setzt, die Adresse schickst, die Daten schickst und dann resettest. Normalerweise ist der Chip-Select-Pin aktiv niedrig. Damit der SPI funktioniert, müssen Sie den Pin zurücksetzen und danach erneut einstellen.
Außerdem müssen Sie die Frequenz der SPI-Uhr überprüfen. Wenn Ihr Gerät (stm32f4) mit 168 MHz getaktet ist und Sie dies ausgewählt haben, SPI_BAUDRATEPRESCALER_2
bedeutet dies, dass Ihr SPI mit 42 MHz getaktet ist, was ziemlich hoch ist, und ich bin mir ziemlich sicher, dass der MCP4151 nicht mit einer so hohen Frequenz arbeiten kann. Um die maximale Frequenz zu finden, die Ihr Gerät verarbeiten kann, müssen Sie im Datenblatt nachsehen.
Zu guter Letzt müssen Sie in Ihrem Datenblatt prüfen, in welchem SPI-Modus der MCP4151 arbeitet. Es gibt 4 verschiedene SPI-Modi, daher kann der ausgewählte Modus falsch sein.
PS Viele Geräte haben strenge Timing-Anforderungen zwischen Lese- und Schreibbefehlen oder zwischen aufeinanderfolgenden Schreib- oder Lesebefehlen.
Ich hatte ein Problem mit SPI auf STM32H7. Das Problem war, dass die Taktimpulse fehlten. Das letzte Byte hatte 4-7 Taktimpulse statt 8. Die Anzahl der Impulse war bei jedem Übertragungszyklus unterschiedlich. Nach einer Untersuchung stellte ich fest, dass dieses Problem nur besteht, wenn SPI-Pins mit GPIO_SPEED_FREQ_LOW konfiguriert sind. Auch bei einer SPI-Frequenz von bis zu 7 kHz. Sobald ich die GPIO-Frequenzeinstellungen auf eine andere (mittel, hoch, sehr hoch) ändere, verschwindet das Problem. Ich habe noch keine Erklärung für das Problem gefunden.
Bence Kaulics
__GPIOA_CLK_ENABLE();
und__GPIOC_CLK_ENABLE();
Anrufe fehlen.Jan Bartels
Bence Kaulics
Jan Bartels
William Brodie-Tyrrell