Obsługa kontrolera DMA w mikrokontrolerze AT91SAM7S

Kontroler DMA umożliwia w sposób efektywny przesyłać dane pomiędzy urządzeniami peryferyjnymi, a pamięcią mikrokontrolera(PDC - peripherial DMA). Bloki danych przesyłane są bez udziału rdzenia, co nie powoduje blokowania wykonywania programu na czas transferu.
Aby zaprogramować kanał DNA należy podać ilość danych które mają ulec przesłaniu, oraz adres pod którym się znajdują. Rejestr który zawiera ilość danych do transferu po przesłaniu każdego bajtu zostaje dekrementowany, a przesyłanie zostaje zakończone gdy rejestr ten osiągnie wartość 0 (jednocześnie jest ustawiana odpowiednia flaga sygnalizująca zakończenia operacji).

Przedstawiony poniżej program ma za zadanie periodycznie wysyłać przez port DBGU jakiś ciąg znaków. Znaki te można odczytać na komputerze za pomocą programu HyperTerminal


#include "library.h"
void main(void)
{
	char tekst[]=“Test DMA in uC SAM7S \n\r”;
	int i,j;

	DBGU->BAUD_RATE_GEN_R = 156;			//1
	DBGU->MODE_R = DBGU_MODE_NORMAL | DBGU_PARITY_NONE;
	DBGU->CONTROL_R = DBGU_TX_ENABLE | DBGU_RX_ENABLE ;

	PIO->PERIPH_A_SELECT_R=PIO_PA9 | PIO_PA10;	//2
	PIO->PIO_DISABLE_R=PIO_PA9 | PIO_PA10;

	while(1)
	{
		PDC_DBGU->CONTROL_R=PDC_TX_DISABLE;	//3
		PDC_DBGU->TX_PTR_R=(void*)tekst;	//4
		PDC_DBGU->TX_CNT_R=strlen(tekst);	//5
		PDC_DBGU->CONTROL_R=PDC_TX_ENABLE;	//6
		for(i=0; i<4000; i++)			//7
			for(j=0; j<500; j++) {};
                      					//8
		while(!DBGU->INT_STATUS_R & DBGU_TX_BUFS_EMPTY);
	}
}


1. Ustalenie parametrów pracy portu asynchronicznej transmisji szeregowej DBGU aby pracował z częstotliwością 19200 bodów i bez bitu parzystości.
2. Koncówki A9 i A10 ustawione do pracy z urządzeniem peryferyjnym A, oraz odłączenie od nich portu PIO.
3. Wyłączenie kanału DMA dla portu DBGU
4. Podanie adresu pierwszego elementu bufora
5. Podanie ilości elementów do wysłania.
6. Włączenie kanału DMA
7. Pętla zatrzymująca program na moment
8. Opcjonalna pętla wykonywana do momentu zasygnalizowania ukończenia wysyłania danych (była by niezbędna gdyby nie było pętli opóźniającej).

Drugi program umożliwia odbieranie przez mikrokontroler danych z HyperTerminala (6 znaków), a następnie te znaki zostają odesłane i wyświetlone na komputerze.

#include "library.h"
void main(void)
{
	char text[6];
	int i,j;

	DBGU->BAUD_RATE_GEN_R = 156;			//1
	DBGU->MODE_R = DBGU_MODE_NORMAL | DBGU_PARITY_NONE;
	DBGU->CONTROL_R = DBGU_TX_ENABLE | DBGU_RX_ENABLE ;

	PIO->PERIPH_A_SELECT_R = PIO_PA9 | PIO_PA10;	//2
	PIO->PIO_DISABLE_R = PIO_PA9 | PIO_PA10;

	while(1)
	{

		PDC_DBGU->CONTROL_R = PDC_RX_DISABLE;	//3
		PDC_DBGU->RX_PTR_R = (void*)text;	//4
		PDC_DBGU->RX_CNT_R = 6;			//5
		PDC_DBGU->CONTROL_R = PDC_RX_ENABLE;	//6
							//7
		while(DBGU->INT_STATUS_R & DBGU_RX_BUFS_FULL);

		PDC_DBGU->CONTROL_R = PDC_TX_DISABLE;	//8
		PDC_DBGU->TX_PTR_R = (void*)text;	//9
		PDC_DBGU->TX_CNT_R = 6;			//10
		PDC_DBGU->CONTROL_R = PDC_TX_ENABLE;	//11
							//12
		while(!DBGU->INT_STATUS_R & DBGU_TX_BUFS_EMPTY);
	}
}

1. Ustalenie parametrów pracy portu DBGU.
2. Końcówki A9 i A10 przyłączone dla urządzenia peryferyjnego A
3. Zatrzymanie kanału odbiorczego PDC
4. Podanie adresu pierwszego elementu bufora
5. Podanie ilości elementów które mają zostać przesłane przez kontroler PDC
6. Włączenie kanału odbiorczego
7. Pętla zatrzymująca wykonywanie programu aż do momentu odebrania 6 znaków przez port DBGU.
8. Zatrzymanie kanału nadawczego PDC
9. Podanie adresu pierwszego elementu bufora
10. Podanie ilości elementów które mają zostać wysłąne przez port DBGU do komputera
11. Włączenie kanału nadawczego
12. Pętla zatrzymująca wykonywanie programu aż do momentu wysłania 6 znaków.

Kody źródłowe zostrały napisane w środowisku programistycznym uVision3 firmy Keil w oparciu o książkę dr inż. J. Augustyna pt. “Projektowanie systemów wbudowanych na przykładzie rodziny SAM7S z rdzeniem ARM7TDMI”. Niezbędne biblioteki można pobrać ze strony www.sparrow-rt.com .

 
>