Tutorial STM32 CubeMX – SDIO

Ziel des Artikels

Ziel des Artikels ist es, anhand eines Beispiels zu zeigen, wie sich mit einem STM32F4 und unter Verwendung der HAL-Library Dateien auf einer SD-Karte erstellen, beschreiben und auslesen lassen.

Eingesetzte Hardware

  • Board: STM32F469I-Discovery (microSD slot onboard)
  • MicroSD-Karte (Kingston microSDHC 16GB), eine Partition – formatiert mit FAT16

Eingesetzte Software

  • System Workbench for STM32 (SW4STM32)
  • STM32CubeMX Eclipse plugin

Verwendete Abkürzungen

  • MCU: Microcontroller Unit
  • SDIO: Secure Digital Input Output
  • FAT: File Allocation Table
  • FS: File System
  • IDE: Integrated Development Environment

Einrichten der Entwicklungsumgebung

Installation

Erstellung des Projekts

Um die Code-Generierung von CubeMX nutzen zu können, gilt es zunächst, ein CubeMX-Projekt zu erstellen. Dies kann in der STM32CubeMX-Ansicht der Workbench erledigt werden.

cmx_sdio_01

Bei der Projekterstellung wird nach der Hardware gefragt, auf welcher der später generierte Code ausgeführt werden soll (In unserem Fall das STM32F469I-Discovery Board).

cmx_sdio_02

Hat man die entsprechende Hardware selektiert, bestätigt man dies durch den Ok-Button. Nun sollte eine Übersicht erscheinen, in der sich die Hardware konfigurieren lässt.

cmx_sdio_03

In diesem Artikel möchten wir uns auf die Konfiguration der Peripherieeinheit SDIO und der Middleware-Komponente FATFS beschränken. Die SDIO-Peripherie ermöglicht den Zugriff auf unsere SD-Karte während FATFS Dateisystem-Funktionen zur Verfügung stellt, über die sich Dateien erstellen, beschreiben und auslesen lassen.

cmx_sdio_03_Auswahl

Die von CubeMX erstellte Clock-Configuration sowie Configuration kann in unserem Fall übernommen werden. Über den Menüeintrag Project -> Generate Code lässt sich nun der entsprechende Quellcode generieren. Dazu muss ein Zielordner definiert und in unserem Fall SW4STM32 als Toolchain/IDE selektiert werden. Die übrigen Parameter können auf den Standardwerten gelassen werden.

cmx_sdio_04

Nach abgeschlossener Code-Generierung kann unter der Standard-Ansicht(C/C++) das generierte Projekt mitsamt des Quellcodes zur weiteren Modifizierung importiert werden. Unter dem Menueintrag File ->Import wählt man dazu General -> Existing Projects into workspace.

cmx_sdio_05

Unter Select root directory wählt man den Ordner aus, den man bei der Code-Generierung als Zielordner angegeben hat. Sobald das Projekt erkannt wurde, kann man den Import mit Finish abschliessen.

Die anzupassende main-Funktion findet sich in der Datei Src/main.c. Folgendes Snippet zeigt die vorgenommenen Modifizierungen.

[...]

/* USER CODE BEGIN PV */
/* Private variables ---------------------------------------------------------*/

FATFS sdFatFs;	// File system object for SD disk logical drive
char sdPath[4];	// SD disk logical drive path
FIL myFile;	// File object

/* USER CODE END PV */

[...]

int main(void) {

	/* USER CODE BEGIN 1 */

	FRESULT res = FR_OK;			// FatFs function common result code
	uint8_t wtext[] = "Hello world";	// File write buffer
	uint8_t rtext[100];			// File read buffer
	uint32_t byteswritten, bytesread;	// File write/read counts

	/* USER CODE END 1 */

	[...] // Initialisierungen

	/* USER CODE BEGIN 2 */

	res = f_mount(&sdFatFs, (TCHAR const*) sdPath, 0);
	if (res != FR_OK) {
		// Fehler beim Mounten
		return -1;
	}

	res = f_open(&myFile, "TEST.TXT", FA_CREATE_ALWAYS | FA_WRITE);
	if (res != FR_OK) {
		// Fehler beim Erstellen oder Öffnen der Datei
		return -1;
	}

	res = f_write(&myFile, wtext, sizeof(wtext),(void *) &byteswritten);
	if (res != FR_OK) {
		// Fehler beim Beschreiben der Datei
		return -1;
	}

	f_close(&myFile);	// Schliessen der Datei

	res = f_open(&myFile, "TEST.TXT", FA_READ);
	if (res != FR_OK) {
		// Fehler beim Öffnen der Datei
		return -1;
	}

	res = f_read(&myFile, rtext, sizeof(rtext),(UINT*) &bytesread);
	if ((bytesread == 0) || (res != FR_OK)) {
		// Fehler beim Lesen aus der Datei
		return -1;
	}

	f_close(&myFile);		// Schliessen der Datei
	FATFS_UnLinkDriver(sdPath);	// Trennen des SDIO-Treibers von der Middleware-Komponente

	/* USER CODE END 2 */

	[...]
}

[...]

 

Der Quellcode soll lediglich ein Grundgerüst aufzeigen, auf weitergehende Validierungen wird hier bewusst verzichtet.

Im Codeblock nach /* USER CODE BEGIN PV */ werden zunächst Variablen erzeugt (sdFatFs, sdPath), die zum Mounten des Dateisystems benötigt werden. Zudem wird hier das Objekt erzeugt, das die zu bearbeitende Datei repräsentieren wird.

Im Codeblock /* USER CODE BEGIN 1 */ wird zunächst eine Variable erzeugt, in der wir den ErrorCode zukünftiger FATFS-Operationen speichern werden. Ausserdem werden hier Lese-, Schreib-Puffer sowie Variablen (byteswritten, bytesread) erzeugt, in der die Anzahl der geschriebenen bzw. gelesenen Bytes gespeichert werden.

Im Codeblock /* USER CODE BEGIN 2 */ finden die eigentlichen Operationen statt. Dabei wird nach dem Mounten des Dateisystems mit f_mount(…) zunächst eine Datei mit f_open(…) erzeugt und geöffnet und mit f_write(…) beschrieben. Mit f_close(…) wird die Datei geschlossen. Anschließend wird die Datei mit f_open(…) zum Lesen geöffnet. Mit f_read(…) werden die in ihr gespeicherten Daten gelesen.Nachdem die Datei ausgelesen wurde, wird diese mit f_close(…) geschlossen. Zuletzt wird der SDIO-Treiber von der FATFS-Middleware-Komponente getrennt.

de_DEDeutsch
en_GBEnglish (UK) de_DEDeutsch