Skocz do zawartości

Pomocna odpowiedź

Napisano

Witam.

Mam układzik z atmega8L i chciałbym wysyłać po uart dane z czujników. Jednak Wszystko ustawiłem a dane wysyłane to same zera. Mam wrażanie, że coś nie tak jest z synchronizacją ale nie jestem pewien 🙂. Fuse bity mam ustawione: hFuse= D9, lFuse=E1 czyli taktowanie wewn oscylatorem 1Mhz.

Do uc podłączony jest kwarc ale nie jest używany.

Program wygląda tak:

main.c:

#define F_CPU 1000000UL
#include <avr/io.h>
#include <util/delay.h>  
#include <stdio.h>
#include <stdlib.h>
#include <avr/interrupt.h>
#include <compat/twi.h>
#include "hmc5883l.h"
#include "TWI_lib.h"
#include "UART_ATM8.h"

#define SetBit(x,y)	x |= (1<<y)
#define ClrBit(x,y) x &= ~(1<<y)
#define NegBit(x,y) x ^= (1<<y)

volatile unsigned char bufor_RXD=0;
volatile int receive=0;

ISR (USART_RXC_vect)
{
	bufor_RXD = UDR;
receive=1;
}

int main(void)
{
DDRB =	0b00000111; 
DDRC =	0b00001111; 
DDRD =	0b11000010;
PORTB =	0b00000001;
PORTC =	0b00110000;
PORTD =	0b00111100; 

int HMC_X=100;
int num=1234;
char buf[10];
USART_Init();
sei();
//TWI_Init();

   while(1)
   {
	//HMC_X = HMC_Read('X');
	//char buf[3];
	//itoa(HMC_X, buf, 10);
		sprintf(buf,"%d %d\n ", num, num);
		USART_send_string(buf);
		_delay_ms(1000);
   }
}

UART_ATM8.h

#ifndef UART_ATM8_H_
#define UART_ATM8_H_

#define FOSC 1000000UL// Clock Speed
#define BAUD 2400
#define ubrr (FOSC/(16*BAUD))-1

void USART_Init();
void USART_send_string(char *string);

#endif

UART_ATM8.c

#include <avr/io.h>
#include <stdio.h>
#include "UART_ATM8.h"

void USART_Init()
{
/* Set baud rate */
UBRRH = (unsigned char)(ubrr>>8);
UBRRL = (unsigned char)ubrr;
/* Enable Receiver and Transmitter */
UCSRB = (1<<RXEN)|(1<<TXEN);
/* Set frame format: 8data, 2stop bit */
UCSRC = (1<<URSEL)|(1<<USBS)|(3<<UCSZ0);
}

void USART_send_string(char *string)
{
  char znak;
  while (0!=(znak=*(string++)))
  {
	while ( !( UCSRA & (1<<UDRE)) );
	UDR=znak;
  }
} 

Czy widzi ktoś z was jakiś błąd?

Hmm. Gdzie masz odblokowane zezwolenie na przerwanie od USART_RXC.??

[ Dodano: 05-02-2012, 12:44 ]

Spróbuj dodać

UCSRB |= (1<<RXCIE);

Z przerwanie odbioru na razie nie korzystałem dlatego nie jest ustawione. (metoda małych kroczków 🙂 ).

Co do GND to oczywiście jest podłączone.

A baud obliczam w taki sposób:

#define FOSC 1000000UL// Clock Speed
#define BAUD 2400
#define ubrr (FOSC/(16*BAUD))-1

Czyli wg tego wzoru z datasheet:

Asynchronus Normal Mode, 3 kolumna.

No i wynik przypisuje do rejestr UBRR

	UBRRH = (unsigned char)(ubrr>>8);
UBRRL = (unsigned char)ubrr;

Więc wydaje mi się, że dobrze jest ustawione.

Wg mojej oceny problem leży w ciekawym warunku pętli while.

Otóż kiedy do niej wchodzisz, pętla while w kółko sprawdza warunek ale podczas wykonywania obliczenia wartości tego wyrażenia podstawiasz za każdym razem do zmiennej znak KOLEJNY znak ze stringu. Operator ++ wykonuje się wiele razy i de facto robisz poszukiwanie końca łańcucha 🙂 Jak już go znajdziesz i wreszcie nadajnik będzie gotowy, wysyłasz otatni znaleziony znak czyli 0x00.

Nie, chyba bzdury popisałem...

Hmm. A spróbuj wpisać po prostu do rejestru UBRR liczbę 25 (odpowiada prędkości 2400bps).

Czyli zamień

UBRRH = (unsigned char)(ubrr>>8);

UBRRL = (unsigned char)ubrr;

na

UBRRH=0;

UBRRL=25;

I czy na pewno masz ustawiona na kompie prędkość 2400bps??

  • Pomogłeś! 1
A ile "zer" wypisuje się po wysłaniu stringu o znanej długości?

Takie coś wysyła co sekundę:

<0>˙<0><0><0><0><0><0>˙<0><0><0><0>˙<0><0><0><0>˙<0><0><0><0><0><0>˙<0><0><0><0>˙<0><0><0>˙<0><0><0>

Wg mojej oceny problem leży w ciekawym warunku pętli while.

Otóż kiedy do niej wchodzisz, pętla while w kółko sprawdza warunek ale podczas wykonywania obliczenia wartości tego wyrażenia podstawiasz za każdym razem do zmiennej znak KOLEJNY znak ze stringu. Operator ++ wykonuje się wiele razy i de facto robisz poszukiwanie końca łańcucha 🙂 Jak już go znajdziesz i wreszcie nadajnik będzie gotowy, wysyłasz otatni znaleziony znak czyli 0x00.

Nie, chyba bzdury popisałem...

W innych programach takie coś mi działało więc chyba nie w tym jest problem.

Hmm. A spróbuj wpisać po prostu do rejestru UBRR liczbę 25 (odpowiada prędkości 2400bps).

Czyli zamień

UBRRH = (unsigned char)(ubrr>>8);

UBRRL = (unsigned char)ubrr;

na

UBRRH=0;

UBRRL=25;

I czy na pewno masz ustawiona na kompie prędkość 2400bps??

Działa ! 🙂

Źle byłą przypisywana wartość do UBRRH, UBRRL przez co BaudRate był źle ustawiony 🙂.

Wpisałem tak jak mi napisał davidpi i działa. Nie jest to perfekcyjne i eleganckie ale na razie wystarczy 😉.

Wpisałem tak jak mi napisał davidpi i działa.

Hmm na forum jest możliwość wyrażania wdzięczności 😉

__________

Komentarz dodany przez: Bobby

Nieobowiązkowa 😉

  • Lubię! 2
  • 2 miesiące później...

Wielkie dzięki za podpowiedź, miałem podobny problem z komunikacją przy uzyciu transmiterów Mobot - RCR2. Po postąpieniu jak powyżej, czyli wpisaniu "od ręki" wartości UBRRL i UBRRH wszystko ruszyło. Dzięki za pomoc!! 🙂

Bądź aktywny - zaloguj się lub utwórz konto!

Tylko zarejestrowani użytkownicy mogą komentować zawartość tej strony

Utwórz konto w ~20 sekund!

Zarejestruj nowe konto, to proste!

Zarejestruj się »

Zaloguj się

Posiadasz własne konto? Użyj go!

Zaloguj się »
×
×
  • Utwórz nowe...