mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik UART: bit 7 in UDR macht sich selbstständig!?


Autor: jupp (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
hi,


ich arbeite eben zum ersten mal mit der uart schnittstelle (mega644).
habe ein kleines testprog das kontinuierlich ein zeichen sendet (unten).
ich schreibe also ein byte in UDR0.

wenn in dem byte bit7 nicht gesetzt ist, macht sich das selbstständig, 
zb:


ich sende 8 mal: UDR0 = 0x01;
ich empfange: \x01\x81\x81\x01\x01\x01\x01\x81


ist bit7 gesetzt, kein problem:

UDR0 = 0x80;
\x80\x80\x80\x80\x80\x80\x80\x80\x80


was passiert da nur?
ja, ich habe "17.10.1 UDRn – USART I/O Data Register n" durchgelesen, da 
steht nix was auf dieses verhalten schliessen lässt...!?

der takt (1000000UL) sollte stimmen, alles default:
CKSEL = 0010, SUT = 10, CKDIV8 = 0

cfg beim empfänger sollte auch stimmen:
Serial<id=0xb53550, open=True>(port='COM1', baudrate=9600, bytesize=8, 
parity='N', stopbits=1, timeout=None, xonxoff=0, rtscts=0, dsrdtr=0)


jemand ne idee? danke schonmal!







#define F_CPU       1000000UL

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

#define BAUD_RATE          9600UL

int main(void) {

  OSCCAL = 0x9b;

  UBRR0H=(uint8_t)((F_CPU / (16 * BAUD_RATE)) - 1)>>8;
  UBRR0L=(uint8_t)(F_CPU / (16 * BAUD_RATE)) - 1;

  UCSR0C = (1<<UCSZ01) | (1<<UCSZ00);    // async, 8N1
  UCSR0B = (1<<TXEN0);

  while(1){
    loop_until_bit_is_set(UCSR0A, UDRE0);
    UDR0 = 0x01;
    _delay_ms(100);
  }
}

Autor: Stefan B. (stefan) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
jupp wrote:

> wenn in dem byte bit7 nicht gesetzt ist, macht sich das selbstständig,
> zb:

Hört sich nach ungenauer Baudrate an.

> der takt (1000000UL) sollte stimmen, alles default:
> CKSEL = 0010, SUT = 10, CKDIV8 = 0

Und das bestärkt den Verdacht. Interne RC-Oszillator? Wenn ja, 
wiederhole alles mit externem Quarz und melde dich wieder, wenn der 
Fehler bestehen bleibt.

Autor: jupp (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
ist das wirklich derartig ungenau?
im datenblatt steht, dass der interne osc nach calibrieren genau genug 
ist.

da ich anfänger bin habe ich eigentlich keine lust jetzt die sache noch 
zu verkomplizieren...
brigt es was den osc vom stk 500 zu nutzen?


danke!

Autor: spess53 (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hi

>brigt es was den osc vom stk 500 zu nutzen

Ja,aber nur mit Quarz.

MfG Spess

Autor: Stefan B. (stefan) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hast du kalibriert?
Osc. vom STK500 müsste statt externem Quarz auch gehen.

Autor: jupp (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
ja, ich habe calibriert:

in avr: cal. for frequency (8Mhz, ist doch richtig auch wenn CKDIV8 = 
0), read cal byte, im prog dann:

OSCCAL = 0x9b;


stk 500 ist dann eine externe clock, fuse also folgendermaßen:

CKSEL3..0 = 0000?

richtig?


ich habe jetzt noch in nem anderen thread gelesen, dass folgendes bei 
niedriger clock sinnvoll wäre:

UCSR0A = (1<<U2X0);
UBRR0H = (uint8_t) ((F_CPU / (8 * baudrate)) - 1)>>8;
UBRR0L = (uint8_t) (F_CPU / (8 * baudrate)) - 1;

im datenblatt steht aber das gegenteil!?

Autor: Stefan B. (stefan) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
jupp wrote:

> ja, ich habe calibriert:
> OSCCAL = 0x9b;

Wie bist du auf den Wert gekommen? Hoffentlich nicht gemäß STK500 
Handbuch 5.3.4.2 bis 5.3.4.4.

> stk 500 ist dann eine externe clock, fuse also folgendermaßen:
> CKSEL3..0 = 0000?
> richtig?

Wenn du externe clock auf dem STK500 einstellst, ja. Aber oben hat Spess 
empfohlen vom STK500 den externen Quarz zu nehmen. Auswahl über Jumper 
XTAL1 und OSCSEL. Ich habe kein STK500 und weiss nicht wie genau die 
externe Clock vom STK500 ist.

> ich habe jetzt noch in nem anderen thread gelesen, dass folgendes bei
> niedriger clock sinnvoll wäre:
>
> UCSR0A = (1<<U2X0);
> UBRR0H = (uint8_t) ((F_CPU / (8 * baudrate)) - 1)>>8;
> UBRR0L = (uint8_t) (F_CPU / (8 * baudrate)) - 1;
>
> im datenblatt steht aber das gegenteil!?

Rechne es aus. Im Datenblatt (17.11 Examples of Baud Rate Setting) meine 
ich eine Tendenz zu erkennen, dass UCSR0A = (1<<U2X0); eher Vorteile 
hat. Aber gerade bei 9600 Baud @ 1 MHz ist -7,0% Baudratenfehler (kein 
UCSR0A = (1<<U2X0)) gegen 0,2% (UCSR0A = (1<<U2X0)) enorm! Es ist hier 
also auf jeden Fall ratsam. Das würde ich sogar vor der Umstellung der 
Taktrate einmal testen.

Autor: spess53 (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hi

>Ich habe kein STK500 und weiss nicht wie genau die externe Clock vom >STK500 ist.

Ich habe das mal vor einiger Zeit nachgemessen. Den vom Controller des 
STK generierten Takt kann man vergessen.

MfG Spess

Autor: Urs (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Tip: <util/setbaud.h> verwenden, das benutzt auch den Prescaler, wenn es 
damit bessere Ergebnisse gibt.

Kleiner Fallstrick noch: Beim Mega644 ist das zwar nicht der Fall, aber 
einige andere AVRs (Mega8 z.B.) haben für UBRR*H und UCSR*C die gleiche 
Adresse, die Unterscheidung folgt über das Bit URSEL, das beim Zugriff 
auf UCSR*C gesetzt sein muss, sonst passiert Baudsalat.

Autor: jupp (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
>> ja, ich habe calibriert:
>> OSCCAL = 0x9b;

>Wie bist du auf den Wert gekommen? Hoffentlich nicht gemäß STK500
>Handbuch 5.3.4.2 bis 5.3.4.4.

im avr studio auf der advanced im abschnitt "oscillator calibration 
byte" read cal byte geclickt. habe das irgendwo gelesen. das scheint 
aber nur das register auszulesen. macht also wenig sinn!?
wie macht man das also?



>>Ich habe kein STK500 und weiss nicht wie genau die externe Clock vom >>STK500 
ist.

>Ich habe das mal vor einiger Zeit nachgemessen. Den vom Controller des
>STK generierten Takt kann man vergessen.

dann werde ich wohl nicht drumrumkommen einen quarz zu benutzen. scheint 
ja recht idiotensicher zu sein mit dem stk500. (um die elkos muss ich 
mich da ja nicht kümmern, sind schon auf dem board?)


danke euch!

Autor: Stefan B. (stefan) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Habe ich mir gedacht. Damit kalibierst du IMHO die Software Clock des 
STK500, nicht die des eingesteckten AVRs.

Den eingesteckten AVR könntest du kalibrieren, in dem du darauf einen 
Zeitgeber programmierst und dessen Ausgabe mit einer bekannten, genauen 
Zeitquelle vergleichst. Die Abweichung ist dann ein Maß für das 
Kalibrierbyte. Das ist so grundlegend für einen µC, dass es eine 
application note von Atmel dazu geben müsste.

Autor: jupp (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
ich habe mich vorgestern das erste mal ernsthaft mit einem atmega 
datenblatt auseinander gesetzt und ich muss sagen, das ist wirklich sehr 
gut geschrieben. habe eigentlich alles auf anhieb geblickt.

aber...

>Das ist so grundlegend für einen µC, dass es eine
>application note von Atmel dazu geben müsste.

genau...
da wird man irgenwie allein gelassen.

Autor: Stefan B. (stefan) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hehe, so habe ich das nicht gemeint. SUCHEN solltest du ;-)

AVR053 - Calibration of the internal RC oscillator
http://www.atmel.com/dyn/resources/prod_documents/...

Autor: jupp (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
scherzkeks

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.