Pages: 1 [2] 3   Go Down
Author Topic: RS485 per programmare ATmega  (Read 1697 times)
0 Members and 1 Guest are viewing this topic.
Global Moderator
Italy
Offline Offline
Brattain Member
*****
Karma: 313
Posts: 21624
Logic is my way
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Usa però la manipolazione diretta delle porte logiche

Leo, ma per chi mi hai preso?
Repetita iuvant  smiley-razz
Logged


Capo d'Orlando
Offline Offline
God Member
*****
Karma: 2
Posts: 723
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Ma quale repetita, mai fatte queste cose  smiley-sad

Stavo vedendo la funzione flash_led, che dovrebbe essere quella che viene ripetuta due volte per segnalare l'inizio di caricamento dello sketch facendo accendere il led13. Pensavo che magari avrei potuto prenderne spunto e semplicemente andare a modificare la porta smiley-mr-green :

Code:
void flash_led(uint8_t count) {
  do {
    TCNT1 = -(F_CPU/(1024*16));
    TIFR1 = _BV(TOV1);
    while(!(TIFR1 & _BV(TOV1)));
#ifdef __AVR_ATmega8__
    LED_PORT ^= _BV(LED);
#else
    LED_PIN |= _BV(LED);
#endif
    watchdogReset();
  } while (--count);
}

Ma sono solo arrivato a capire che se il micro non è un atmega 8 fa un operazione or tra LED_PIN e la funzione _BV(LED)..
Ma tutta queste variabili cosa contengono? Non trovo le assegnazioni!


PS. Forse stava meglio in Software questo topic  smiley-yell
Logged

Capo d'Orlando
Offline Offline
God Member
*****
Karma: 2
Posts: 723
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Comunque leggendo nel reference:
Quote
PORTD is a built-in constant that refers to the output states of digital pins 0,1,2,3,4,5,6,7
PORTD = B00110001; we have made pins 2,3 & 7 HIGH.

Quote
DDRD = DDRD | B11111100; // set direction bits for pins 2 to 7, leave 0 and 1 untouched (xx | 00 == xx)

Non si leggevano in ordine crescente da sinistra verso destra?


Ma carine queste cose comunque smiley
Logged

Global Moderator
Italy
Offline Offline
Brattain Member
*****
Karma: 313
Posts: 21624
Logic is my way
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

http://www.arduino.cc/en/Reference/PortManipulation

Per mettere in input un pin, devi prima vedere dalla piedinatura del microcontrollore a quale porta appartiene e poi imposti il suo bit.
Ad esempio, il pin D10 di Arduino è il piedino PB3, quindi porta "B", bit "3".
Ora, sapendo questo, col link che ti ho dato, vedi che il registro DDx regola la direzione dei pin di una porta.
Quindi se vuoi mettere quel pin come output, devi mettere a 1 il bit 3.
Code:
DDRB |= (1<<3);

Adesso lo stato del pin lo regoli con il registro PORTx corrispondente, quindi PORTB.
1 sul bit 3 mette "HIGH" quel pin, 0 lo mette LOW:
Code:
PORTB |= (1<<3); //mette HIGH
PORTB &= ~(1<<3); //mette LOW

Se vuoi metterlo su output, devi metterlo s
Logged


Capo d'Orlando
Offline Offline
God Member
*****
Karma: 2
Posts: 723
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Eh si, stavo giusto leggendo questi operatori e ora me li studio e provo un po' smiley quindi posso adoperare queste porte nel file optiboot.c no?

Supponiamo che usi il pin 2 pensavo di fare così:
per impostare il pin come output   DDRD |=B0000100 

nella parte di trasmissione            PORTD |=B0000100

nella parte di ricezione                 PORTD &=B1111011
Logged

Global Moderator
Italy
Offline Offline
Brattain Member
*****
Karma: 313
Posts: 21624
Logic is my way
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Eh si, stavo giusto leggendo questi operatori e ora me li studio e provo un po' smiley quindi posso adoperare queste porte nel file optiboot.c no?

Supponiamo che usi il pin 2 pensavo di fare così:
per impostare il pin come output   DDRD |=B0000100  
No.OK

Quote
nella parte di trasmissione            PORTD |=B0000100
No.OK

Quote
nella parte di ricezione                 PORTD &=B1111011
No.OK

Facendo come hai scritto te, cambi lo stato di TUTTI i pin di quella porta.
Devi usare la notazione che ho usato io.

PORTB |= (1<<3)
significa:
PORTB = PORTB | (1<<3)

1<<3 significa:
prendi il valore 1 e shiftalo a SX di 3 posizioni.
La sostanza finale è che accendi solo il bit n° 3 (quello in posizione 4).

Con PORTB &= ~(1<<3)
fai l'opposto, ossia spengi solo il bit n° 3.
Equivale a
PORTB = PORTB & ~(1<<3)
Il segno "~" inverte i bit.
Quindi 1<<3 diventa 00001000
Invertendolo diventa 11110111
Facendo un AND logico, lasci tutti gli altri bit inalterati e metti a 0 solo quello che ti serve.
« Last Edit: March 06, 2013, 05:38:53 pm by leo72 » Logged


Capo d'Orlando
Offline Offline
God Member
*****
Karma: 2
Posts: 723
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Aspe, evidentemente ho capito male qualcosa.. a prescindere dalle tue operazioni:

PIN13=PB5, quindi se volessi fare un esempio di blink perchè non ci riesco così?

DDRB=B000001 ;

PORTB=B000001;
aspetto
PORTB=B000000;
aspetto
Logged

Capo d'Orlando
Offline Offline
God Member
*****
Karma: 2
Posts: 723
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Perchè vanno letti da destra verso sinistra, ecco perchè.. ora posso andare a letto tranquillo  smiley-razz
Code:
void setup(){
 DDRB |=B100000 ;
}
void loop(){
 PORTB |=B100000;
 delay(1000);
 PORTB &=B011111;
 delay(1000);
}


Tornando al discorso di prima:
DDRB |=B100000 ; fa una OR, un'addizione, di conseguenza se sommo 0 alle altre porte non cambia nessun valore..

PORTB &=B011111; invece fa una AND, moltiplicazione, stessa cosa se moltiplico per 1
sarebbe stato lo stesso con una EXOR, sottrazione, facendo così PORTB ^=B100000

Ovviamente è uno sbattimento scrivere tutti i bit e mi studierò il metodo shift e _BV ma non capisco perchè mi hai detto che fosse sbagliato!

Logged

Global Moderator
Italy
Offline Offline
Brattain Member
*****
Karma: 313
Posts: 21624
Logic is my way
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Perché mi sono confuso....
Scusami...  smiley-sweat smiley-sweat
Logged


Ivrea
Offline Offline
God Member
*****
Karma: 5
Posts: 680
"La teoria è quando si sa tutto ma non funziona niente. La pratica è quando funziona tutto ma non si sa il perché. In ogni caso si finisce sempre con il coniugare la teoria con la pratica: non funziona niente e non si sa il perché." Albert Einstein
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Usa però la manipolazione diretta delle porte logiche

Leo, ma per chi mi hai preso? :p vedo se riesco in qualche maniera a farmi aiutare a scuola smiley

Prova a leggere qui:
http://arduino.cc/forum/index.php/topic,72628.msg545828.html#msg545828

P.S. Ma se sei neofita, perché parti dal più difficile?
Logged

Capo d'Orlando
Offline Offline
God Member
*****
Karma: 2
Posts: 723
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Ok, in questa posizione vanno bene?

Code:
DDRD |=B0000100 
int main(void) {

Code:
uint8_t getch(void) {
 PORTD &=B1111011
 [..]
}

Code:
void putch(char ch) {
PORTD |=B0000100
[...]
PORTD &=B1111011
}
Logged

Global Moderator
Italy
Offline Offline
Brattain Member
*****
Karma: 313
Posts: 21624
Logic is my way
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Il primo mettilo dove ti avevo segnalato alcuni post fa.
Sul terzo, non metterei in uscita da putch() un altro PORD &=, non si sa se la prox chiamata è sempre un putch() o un getch()
Logged


Capo d'Orlando
Offline Offline
God Member
*****
Karma: 2
Posts: 723
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Il PORTD &= l'ho messo per riportare a 0 il pin. Cioè, il pin deve stare sempre a 0 cioè in ascolto, nel momento in cui devo "parlare" metto il pin ad 1 e quando finisco lo riporto a 0 (fine della funzione put)

Ah, e per flashare..?  smiley-sweat
« Last Edit: March 10, 2013, 01:58:30 pm by sciorty » Logged

Global Moderator
Italy
Offline Offline
Brattain Member
*****
Karma: 313
Posts: 21624
Logic is my way
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Il PORTD &= l'ho messo per riportare a 0 il pin. Cioè, il pin deve stare sempre a 0 cioè in ascolto, nel momento in cui devo "parlare" metto il pin ad 1 e quando finisco lo riporto a 0 (fine della funzione put)

Ah, e per flashare..?  smiley-sweat
Se hai Linux la cosa è semplice.
Apri un terminale nella cartella dove hai i sorgenti del bootloader, rinomini il file "optiboot_atmega328.hex" in qualcos'altro (per avere il bootloader originale in caso di problemi) e dai un "make atmega328".
Con Windows non so come si fa a compilare. Ti devi informare.

Dopo che hai creato il firmware, hai bisogno di un altro Arduino per scrivere il bootloader su un chip standalone oppure di un programmatore. E da IDE con l'opzione "Scrivi bootloader" flashi il nuovo bootloader.

Prima verifica con avr-size se il bootloader è grande 512 byte altrimenti esce dallo spazio che l'Arduino riserva per l'Optiboot.
Logged


Capo d'Orlando
Offline Offline
God Member
*****
Karma: 2
Posts: 723
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Ok linux posso prenderlo su un altro pc di cui non posso disporre subito..

Cioè devo semplicemente salvarmi l'optiboot.h originale, posizionarmi sulla cartella che contiene questo file che stiamo modificando e lanciare il comando?
Poi suppongo che debba fare un burn bootloader with arduino as isp?
Logged

Pages: 1 [2] 3   Go Up
Jump to: