PDA

Archiv verlassen und diese Seite im Standarddesign anzeigen : wait forever funktioniert nicht auf atm128



a//b
03.01.2006, 12:13
Hallo,

ich habe hier ein mir unerkärliches Phänomen. Ich möchte genau ein Byte übertragen. Deshalb habe ich nach dem Transfer eine Schleife, die in sich alle Ewigkeit wiederholen sollte.
Die While-Schleife davor
while (!(PIND & (1<<1))) funktioniert auch. Aber solange PD1==1 ist, läuft das Programm immer wieder von vorne durch und überträgt ein 0xAA nach dem anderen. Warum?

Das Pogramm ist ganz einfach. Sobald sich jemand mit dem Bluetooth-Modul verbunden hat, setzt das Modul PD1 auf High. Anschließend wird das Byte 0xAA übertragen.


#define F_CPU 14745600

#include <avr/io.h>
#include <avr/signal.h>
#include <avr/interrupt.h>
#include <avr/delay.h>


unsigned char c=0; // Zähler für empfangene Bytes

void UART1_Transmit( unsigned char data ) {
/* Wait for empty transmit buffer */
while ( !( UCSR1A & (1<<UDRE1)) )
;
/* Put data into buffer, sends the data */
UDR1 = data;
}

unsigned char UART1_Receive( void )
{
while ( !(UCSR1A & (1<<RXC1)) )
; // wait for Receive Complete
return UDR1;
}


// =================
// Interrupts
// =================

SIGNAL (SIG_UART1_RECV)
{
// zählt die Anzahl der eingehenden Datenbytes und gibt
// die Zahl auf die LEDs aus
unsigned char temp;
temp = UDR1;
c++;
PORTC = c;
}

// ===============
// Main program
// ===============
int main (void){
DDRC = 0xFF; // LEDs als out
PORTC = 0; // LEDs ausschalten

DDRD = 0x09; //
PORTD = (1<<0); // Bluetooth-Modul aktivieren

// Blinken und Meldung des BTM überbrücken
int i;
for (i=10;i!=0;i--){
PORTC ^= 0x01;
_delay_ms(200);
_delay_ms(200);
_delay_ms(200);
_delay_ms(200);
}


// ===================================
// Konfiguration für UART1 - Bluetooth
// ===================================
//UBRR1 = 7; // für 115200 Baud bei 14MHz
UBRR1H = 0x00;
UBRR1L = 0x07;

// 7 : 1 RXC-Int
// 6 : 1 TXC-Int
// 5 : 0 Buffer-Empty Int
// 4 : 1 Rx Enable
// 3 : 1 Tx Enable
// 2 : 0 8 Bit Paylod
// 1 : 0 9th Data Bit
// 0 : 0 9th Data Bit
// => 1101 1000 = 0xD8
UCSR1B = 0xD8;

// 7 : 0 not used
// 6 : 0 asyncr.
// 5,4 : 00 Parity disabled
// 3 : 0 1 Stop Bit
// 2,1 : 11 8 Bit Payload
// 0 : 0 not used for asyncr.
// => 0000 0110 = 0x06
UCSR1C = 0x06;

sei(); // Global enable interrupts

while (!(PIND & (1<<1)))
; // wait

PORTC = 0xFF;
UART1_Transmit(0xAA);

// wait forever
while (1){
PORTC ^= 0x02;
}

return 0;
} // main


Irgendwie hängt das mit dem UART-Kram zusammen. Ich habe ja das Gefühl, dass die Schleife einfach wegoptimiert wird oder so. Deshalb habe ich auch schon Assembler-no-operations eingefügt. Hat aber nix verändert.

Irgendwelche Ideen?

Arne

askazo
03.01.2006, 12:58
Der Fehler liegt hier:

// 7 : 1 RXC-Int
// 6 : 1 TXC-Int <--- !!!
// 5 : 0 Buffer-Empty Int
// 4 : 1 Rx Enable
// 3 : 1 Tx Enable
// 2 : 0 8 Bit Paylod
// 1 : 0 9th Data Bit
// 0 : 0 9th Data Bit
// => 1101 1000 = 0xD8
UCSR1B = 0xD8;
Du hast den Sende-Interrupt aktiviert, aber keine Interrupt-Routine dafür geschrieben. Was passiert? Es kommt ein Interrupt, der Program-Counter springt auf die Adresse des Interrupt-Vektors, findet dort aber nur NOPs und landet letztendlich wieder an der Startadresse des Hauptprogramms. Dann geht das ganze wieder von vorne los...

Also einfach Sende-Interrupt deaktivieren und weitermachen ;)

askazo

a//b
03.01.2006, 13:07
Ah. Danke schön. So einfach kann das also sein.

Arne