Operácie

Automatické nastavenie prenosovej rýchlosti: Rozdiel medzi revíziami

Zo stránky SensorWiki

StudentMIPS (diskusia | príspevky)
StudentMIPS (diskusia | príspevky)
 
(31 medziľahlých úprav od rovnakého používateľa nie je zobrazených.)
Riadok 1: Riadok 1:
Záverečný projekt predmetu MIPS / LS2025 - '''Matúš Kráľ'''
Záverečný projekt predmetu MIPS / LS2025 - '''Matúš Kráľ'''


== Zadanie ==
== Zadanie ==
Riadok 7: Riadok 6:




 
[[Obrázok:Arduino_UNO_PU.jpg|450px|thumb|center|Vývojová doska Arduino UNO.]]
 
[[Obrázok:Arduino_UNO_PU.jpg|500px|thumb|center|Vývojová doska ACROB.]]


'''Literatúra:'''  
'''Literatúra:'''  
* [http://ap.urpi.fei.stuba.sk/sensorwiki/index.php/Acrob_technical_description Dokumentácia k doske Acrob]
* [https://docs.arduino.cc/hardware/uno-rev3/ Dokumentácia k doske Arduino UNO]
* [http://www.humanbenchmark.com/tests/reactiontime/index.php Vyskúšajte si zmerať reakciu on-line]




Riadok 20: Riadok 16:
== Analýza  a opis riešenia ==
== Analýza  a opis riešenia ==


Opíšte sem čo a ako ste spravili, ak treba, doplňte obrázkami...
<strong>Použité komponenty:</strong>
Podrobne opíšte použité komponenty (okrem základnej dosky s ATmega328P procesorom), pridajte linky na datasheety alebo opis obvodu.  
* Vývojová doska Arduino UNO (ATmega328P-PU, 16 MHz).
* UART prevodník integrovaný cez USB.


[[Súbor:GeminiAI-image3.jpg|400px|thumb|center|Celkový pohľad na zariadenie.]]
<strong>Link pre Datasheet ATmega328P:</strong> [https://www.mouser.sk/datasheet/2/268/Atmel_7810_Automotive_Microcontrollers_ATmega328P_-3499768.pdf Datasheet ATmega328P]


Nezabudnite doplniť schému zapojenia! V texte by ste mali opísať základné veci zo zapojenia, samotná schéma nie je dostačujúci opis.
<strong>Zapojenie:</strong>
* UART prevodník bude zapojený do Arduina UNO a pomocou zapojeného prevodníka budeme môcť komunikovať s Arduinom.


[[Súbor:GeminiAI-image2.jpg|400px|thumb|center|Schéma zapojenia.]]
 
[[Súbor:Arduino_UNO_schematic.jpg|500px|thumb|center|Schéma zapojenia.]]




=== Algoritmus a program ===
=== Algoritmus a program ===


Algoritmus programu využíva toto a toto, základné funkcie sú takéto a voláma ich tuto...
<strong>Popis funkčnosti programu:</strong>
Výpis kódu je nižšie...


<strong>1.</strong> Program inicializuje premennú "velkost" a do nej následne zapíše počet prvkov v poli "baud_rychlost".
<strong>2.</strong> inicializuje premenné "baud_index", "najdeny", "znak".
<strong>3.</strong> Následne program vojde do slučky a v slučke "for" bude robiť toľko cyklov, koľko je prvkov v poli "baud_rychlost". V našom prípade bude robiť 12 cyklov.
<strong>4.</strong> V slučke vyberie Baud rýchlosť podľa premennej "i" a inicializuje UART, a potom počká 200ms na ustálenie komunikácie.
<strong>5.</strong> Vypíše jeho očakávaný znak a následne čaka 2 sekundy na vstup znaku.
<strong>6.</strong> Keď príjme znak, tak potom overí, že či znak sa rovná 'a'. Ak do 2 sekúnd nedostane očakávaný znak, tak potom ide naspäť na začiatok slučky a nastaví novú Baud rýchlosť.
<strong>7.</strong> Ak príjme očakávaný znak, tak potom vypíše nájdenú Baud rýchlosť komunikácie, a následne program bude vypisovať prijímané znaky.


<tabs>
<tabs>
<tab name="AVR C-code"><syntaxhighlight  lang="c++" style="background: LightYellow;">
<tab name="AVR C-code"><syntaxhighlight  lang="c++" style="background: LightYellow;">
#define F_CPU 16000000UL
#include <stdio.h>
#include <avr/io.h>
#include <avr/io.h>
#include <util/delay.h>
#include "uart.h"
FILE uart_output = FDEV_SETUP_STREAM(uart_putc, NULL, _FDEV_SETUP_WRITE);
FILE uart_input  = FDEV_SETUP_STREAM(NULL, uart_getc, _FDEV_SETUP_READ);
const unsigned long baud_rychlost[] = {
600,
1200,
2400,
4800,
9600,
14400,
19200,
28800,
38400,
56000,
57600,
115200
};


int main(void)
int main(void)
{
{
  unsigned int measuredValue;
int velkost = sizeof(baud_rychlost)/sizeof(baud_rychlost[0]);
int baud_index = 0;
int najdeny = 0;
char znak;
    while (1)
    {
if(najdeny == 0){
for(int i=0; i<velkost; i++){
baud_index = i;
uart_init(baud_rychlost[i]);
stdout = &uart_output;
stdin = &uart_input;
_delay_ms(200);
opakovat:
znak = uart_getc_timeout(1500); // Caka na vstup znaku 1.5 sekundy
if(znak=='\r'){
goto opakovat;
}
if(znak=='\n'){ // Ocakavany znak je "Enter"
najdeny = 1;
printf("Komunikacia naviazana \n");
printf("Prenosova rychlost: Baud = %lu \n",baud_rychlost[baud_index]);
break;
}
}
}
else{
znak = uart_getc();
uart_putc(znak);
}
    }
}
</syntaxhighlight ></tab>
<tab name="uart.h"><syntaxhighlight  lang="c++" style="background: LightYellow;">
void uart_init( unsigned long baudrate );
   
void uart_putc( char c );
void uart_puts( const char *s );


  while (1)
char uart_getc( void );
  {
int uart_getc_timeout(unsigned long timeout);
    /*  relax  */   
</syntaxhighlight ></tab>
  }
<tab name="uart.c"><syntaxhighlight lang="c++" style="background: LightYellow;">
#define F_CPU 16000000UL


  return(0);
#include <avr/io.h>
#include <util/delay.h>
 
void uart_init(unsigned long baudrate)  
{
uint16_t prescaler;
 
if (baudrate > 9600) {
UCSR0A |= (1 << U2X0);
_delay_ms(50);
prescaler = (F_CPU / (8UL * baudrate)) - 1;
} else {
UCSR0A &= ~(1 << U2X0);
_delay_ms(50);
prescaler = (F_CPU / (16UL * baudrate)) - 1;
}
UBRR0H = (uint8_t)(prescaler >> 8);
UBRR0L = (uint8_t)prescaler;
UCSR0B = (1 << TXEN0) | (1 << RXEN0); // povoliť TX a RX
UCSR0C = (1 << UCSZ01) | (1 << UCSZ00); // 8 bitov, 1 stop, no parity
}
 
 
void uart_putc(char c)
{
  if (c == '\n')
{
  uart_putc('\r');
}
  loop_until_bit_is_set(UCSR0A, UDRE0); /* Wait until data register empty. */
  UDR0 = c;
}
}


</syntaxhighlight ></tab>
<tab name="filename.h"><syntaxhighlight  lang="c++" style="background: LightYellow;">
#include <avr/io.h>


void adc_init(void);                                   // A/D converter initialization
void uart_puts(const char *s)
{
while(*s!='\0')
{
uart_putc(*s++);
}
}
 
char uart_getc(void) {
loop_until_bit_is_set(UCSR0A, RXC0); /* Wait until data exists. */
return UDR0;
}


unsigned int adc_read(char a_pin);
int uart_getc_timeout(unsigned long timeout) {
unsigned long cas = 0;
while(cas < timeout){
if (UCSR0A & (1 << RXC0))  // ak prišiel znak
{
return UDR0;
}
_delay_ms(1);
cas++;
}
return -1; // timeout
}
</syntaxhighlight ></tab>
</syntaxhighlight ></tab>
</tabs>
</tabs>


Pridajte sem aj zbalený kompletný projekt, napríklad takto (použite jednoznačné pomenovanie, nemôžeme mať na serveri 10x ''zdrojaky.zip'':
'''Zdrojový kód:''' [[Médiá:ProjektMatusKral.zip|ProjektMatusKral.zip]]
 
Zdrojový kód: [[Médiá:projektMenoPriezvisko.zip|zdrojaky.zip]]


=== Overenie ===
=== Overenie ===


Ako ste overili funkciu, napríklad... Na používanie našej aplikácie stačia dve tlačítka a postup používania je opísaný v sekcii popis riešenia.  
'''Program budeme overovať použitím Serial Terminalu:'''
Na konci uvádzame fotku hotového zariadenia.  
* Arduino pripojíme do počítača pomocou UART prevodníka.
* V Serail Terminale nastavíme Data bits: 8, Parity: none, Stop bits: 1.
* Nastavíme si Baud rate v rozsahu od 600 do 115200.
* Serial Terminal prepojíme s Arduinom.
* Cez Serial Terminal budeme opakovane posielať očakávaný znak "Enter" do Arduina.
* Budeme neustále posielať znak "Enter" do momentu, keď nám Arduino neodpovie, že našiel hodnotu prenosovej rýchlosti.
* Následne môžme posielať ľubovoľné znaky do Arduina a bude nám odpovedať rovnakými znakmi.


[[Súbor:GeminiAI-image1.jpg|400px|thumb|center|Aplikácia.]]
[[Súbor:arduino_uno_r3.jpeg|400px|thumb|center|Arduino UNO]]


'''Video:'''
'''Video:'''
Riadok 79: Riadok 214:




Kľúčové slová 'Category', ktoré sú na konci stránky nemeňte.
 


[[Category:AVR]] [[Category:MIPS]]
[[Category:AVR]] [[Category:MIPS]]

Aktuálna revízia z 11:10, 8. máj 2025

Záverečný projekt predmetu MIPS / LS2025 - Matúš Kráľ

Zadanie

Pri sériovej komunikácii musíme nastaviť niekoľko parametrov.: Prenosovú rýchlosť, počet dátových bitov, paritu a počet stop bitov. Vytvorte program, na automatické testovanie nastavenej prenosovej rýchlosti „druhej strany“ komunikačného kanála.


Vývojová doska Arduino UNO.

Literatúra:


Analýza a opis riešenia

Použité komponenty:

  • Vývojová doska Arduino UNO (ATmega328P-PU, 16 MHz).
  • UART prevodník integrovaný cez USB.

Link pre Datasheet ATmega328P: Datasheet ATmega328P

Zapojenie:

  • UART prevodník bude zapojený do Arduina UNO a pomocou zapojeného prevodníka budeme môcť komunikovať s Arduinom.


Schéma zapojenia.


Algoritmus a program

Popis funkčnosti programu:

1. Program inicializuje premennú "velkost" a do nej následne zapíše počet prvkov v poli "baud_rychlost".

2. inicializuje premenné "baud_index", "najdeny", "znak".

3. Následne program vojde do slučky a v slučke "for" bude robiť toľko cyklov, koľko je prvkov v poli "baud_rychlost". V našom prípade bude robiť 12 cyklov.

4. V slučke vyberie Baud rýchlosť podľa premennej "i" a inicializuje UART, a potom počká 200ms na ustálenie komunikácie.

5. Vypíše jeho očakávaný znak a následne čaka 2 sekundy na vstup znaku.

6. Keď príjme znak, tak potom overí, že či znak sa rovná 'a'. Ak do 2 sekúnd nedostane očakávaný znak, tak potom ide naspäť na začiatok slučky a nastaví novú Baud rýchlosť.

7. Ak príjme očakávaný znak, tak potom vypíše nájdenú Baud rýchlosť komunikácie, a následne program bude vypisovať prijímané znaky.

#define F_CPU 16000000UL

#include <stdio.h>
#include <avr/io.h>
#include <util/delay.h>
#include "uart.h"

FILE uart_output = FDEV_SETUP_STREAM(uart_putc, NULL, _FDEV_SETUP_WRITE);
FILE uart_input  = FDEV_SETUP_STREAM(NULL, uart_getc, _FDEV_SETUP_READ);

const unsigned long baud_rychlost[] = {
	600,
	1200,
	2400,
	4800,
	9600,
	14400,
	19200,
	28800,
	38400,
	56000,
	57600,
	115200
	};

int main(void)
{
	int velkost = sizeof(baud_rychlost)/sizeof(baud_rychlost[0]);
	int baud_index = 0;
	int najdeny = 0;
	
	char znak;
	
    while (1) 
    {	
		if(najdeny == 0){
			for(int i=0; i<velkost; i++){
				baud_index = i;
				uart_init(baud_rychlost[i]);
				
				stdout = &uart_output;
				stdin = &uart_input;
				
				_delay_ms(200);
				
				opakovat:
				znak = uart_getc_timeout(1500); // Caka na vstup znaku 1.5 sekundy
				
				if(znak=='\r'){
					goto opakovat;
				}
				
				if(znak=='\n'){	// Ocakavany znak je "Enter"
					najdeny = 1;
					printf("Komunikacia naviazana \n");
					printf("Prenosova rychlost: Baud = %lu \n",baud_rychlost[baud_index]);
					break;
				}
			}
		}
		else{
			znak = uart_getc();
			uart_putc(znak);
		}
    }
}
void uart_init( unsigned long baudrate );
     
void uart_putc( char c );
void uart_puts( const char *s );

char uart_getc( void );
int uart_getc_timeout(unsigned long timeout);
#define F_CPU 16000000UL

#include <avr/io.h>
#include <util/delay.h>

void uart_init(unsigned long baudrate) 
{
	uint16_t prescaler;

	if (baudrate > 9600) {
		UCSR0A |= (1 << U2X0);
		_delay_ms(50);
		prescaler = (F_CPU / (8UL * baudrate)) - 1;
		} else {
		UCSR0A &= ~(1 << U2X0);
		_delay_ms(50);
		prescaler = (F_CPU / (16UL * baudrate)) - 1;
	}
	
	UBRR0H = (uint8_t)(prescaler >> 8);
	UBRR0L = (uint8_t)prescaler;
	UCSR0B = (1 << TXEN0) | (1 << RXEN0); // povoliť TX a RX
	UCSR0C = (1 << UCSZ01) | (1 << UCSZ00); // 8 bitov, 1 stop, no parity
}


void uart_putc(char c) 
{
   if (c == '\n') 
	{
	   uart_putc('\r');
	}
   loop_until_bit_is_set(UCSR0A, UDRE0); /* Wait until data register empty. */
   UDR0 = c;
}


void uart_puts(const char *s)
{
	while(*s!='\0')
	{
		uart_putc(*s++);
	}
}

char uart_getc(void) {
	loop_until_bit_is_set(UCSR0A, RXC0); /* Wait until data exists. */
	return UDR0;
}

int uart_getc_timeout(unsigned long timeout) {
	unsigned long cas = 0;
	
	while(cas < timeout){
		if (UCSR0A & (1 << RXC0))  // ak prišiel znak
		{
			return UDR0;
		}
		_delay_ms(1);
		cas++;
	}
	
	return -1; // timeout
}

Zdrojový kód: ProjektMatusKral.zip

Overenie

Program budeme overovať použitím Serial Terminalu:

  • Arduino pripojíme do počítača pomocou UART prevodníka.
  • V Serail Terminale nastavíme Data bits: 8, Parity: none, Stop bits: 1.
  • Nastavíme si Baud rate v rozsahu od 600 do 115200.
  • Serial Terminal prepojíme s Arduinom.
  • Cez Serial Terminal budeme opakovane posielať očakávaný znak "Enter" do Arduina.
  • Budeme neustále posielať znak "Enter" do momentu, keď nám Arduino neodpovie, že našiel hodnotu prenosovej rýchlosti.
  • Následne môžme posielať ľubovoľné znaky do Arduina a bude nám odpovedať rovnakými znakmi.
Arduino UNO

Video: