Hallo Leute!

Wir arbeiten mit dem ATmega 32 mit der Taktfrequenz von 3,6864 Mhz und versuchen ein Display Powerdip Pc1602d a anzusteuern. Dazu haben wir uns ein Testprogramm heruntergeladen.

Wir lassen folgendes im Main.c ausgeben:

LCD_Print(0,0,"Servas");
_delay_ms(5000);


das ist das C File dazu
Code:
/*
 Copyright:      Radig Ulrich  mailto: mail@ulrichradig.de
 Author:         Radig Ulrich
 Remarks:        
 known Problems: none
 Version:        28.05.2004
 Description:    Programm zur Ansteuerung eines Standart LCD
				 (HD44870),(SED1278F) und kompatible
*/

#include <lcd.h>

//Prototypes
void Write_LCD (char,char);
char Read_LCD (char);
void LCD_Init (void);
void LCD_Clear (void);
void LCD_Print (char,char,char *Buffer,...);

void LCD_Init (void)
{	
	char tmp = Init_LCD_Zeilen;
	//Set Port Direction Register to Output for LCD Databus und LCD Steuerbus
	LCD_Port_DDR = LCD_DataOutput+(1<<LCD_RS | 1<<LCD_RW | 1<<LCD_E);
	//Wait a short Time afer Power on
	for (int a=0;a<3000;a++)
		{
		
		}	
	Write_LCD (0x22,0);	//Init in 4 Bit Mode
	//Wait a short Time afer Power on
	for (int a=0;a<3000;a++)
		{
		for (int b=0;b<100;b++);
		}	
	Write_LCD (0x22,0);	//Init in 4 Bit Mode (Zur Sicherheit nochmal)	
	if (tmp == 1)
		{
		Write_LCD (0x20,0);	//1 Zeilen
		}
		else
		{
		Write_LCD (0x28,0);	//mehrere Zeilen
		}
	Write_LCD (0x0C,0);	//Display On
	Write_LCD (0x80,0);	//Set DD-Ram Adresse = 0
}

void Write_LCD (char Data,char CD)
{
	//Set Port Direction Register to Output for LCD Databus und LCD Steuerbus
	LCD_Port_DDR = LCD_DataOutput+(1<<LCD_RS | 1<<LCD_RW | 1<<LCD_E);
	//Soll ins Seuer oder Datenregister geschrieben werden?
	if (CD == 0)
		{
		cbi(LCD_Port_Write,LCD_RS); //RS = 0 Steuerregister
		}
		else
		{
		sbi(LCD_Port_Write,LCD_RS); //RS = 1 Dataregister
		}
	//Schreibsignal setzen
	cbi(LCD_Port_Write,LCD_RW); //Zum Schreiben RW-Pin = Low
	//Schreiben der 1. 4Bit an das LCD Display
	LCD_Port_Write = (LCD_Port_Write&0xF0) + ((Data&0xF0)>>4); //Write Nibbel MSB
	sbi(LCD_Port_Write,LCD_E);
	cbi(LCD_Port_Write,LCD_E);
	//Schreiben der 2. 4Bit an das LCD Display	
	LCD_Port_Write = (LCD_Port_Write&0xF0) + (Data&0x0F); //Write Nibbel LSB
	sbi(LCD_Port_Write,LCD_E);
	cbi(LCD_Port_Write,LCD_E);
	
	
}

char Read_LCD (char CD)
{
	char Data;
	//Set Port Direction Register to Output for LCD Databus und LCD Steuerbus
	LCD_Port_DDR = LCD_DataInput+(1<<LCD_RS | 1<<LCD_RW | 1<<LCD_E);
	//Lesesignal setzen
	sbi(LCD_Port_Write,LCD_RW); //Zum Lesen RW-Pin = High
	//Soll ins Seuer oder Datenregister geschrieben werden?
	if (CD == 0)
		{
		cbi(LCD_Port_Write,LCD_RS); //RS = 0 Steuerregister
		}
		else
		{
		sbi(LCD_Port_Write,LCD_RS); //RS = 1 Dataregister
		}
	sbi(LCD_Port_Write,LCD_E); //Daten stehen an wenn Enable = High
	for (int a=0;a<100;a++) 	//Wartet ein bisschen bis daten anliegen
	{
	}
	Data = (LCD_Port_Read&0x0F)<<4; //Lesen des 1. Nibble (MSB)
	cbi(LCD_Port_Write,LCD_E);	
	
	sbi(LCD_Port_Write,LCD_E); //Daten stehen an wenn Enable = High
	for (int a=0;a<100;a++) 	//Wartet ein bisschen bis daten anliegen
	{
	}	
	Data += (LCD_Port_Read&0x0F); //Lesen des 2. Nibble (LSB)
	cbi(LCD_Port_Write,LCD_E);	
return(Data);
}

void LCD_Print (char zeile,char spalte,char *Buffer,...)
{
	// Hilfsvariable zum Zählen der ausgegebenen Zeichen
	char nFieldWidth = 0;

	struct {
		char     fLeftJust:1;   // Feldausrichtung links oder rechts
		char     fNegative:1;   // Auszugebende Zahl ist negativ.
	} flags;

	#define SCRATCH 16
	unsigned char scratch[SCRATCH];
	unsigned char format_flag;
	unsigned int u_val=0, base=0;
	unsigned char *ptr;
	char     hexA = 'a';
	char *p;
	int   n;
	int nLen;
	va_list ap;
		
	va_start (ap, Buffer);	
	//Berechnet Adresse für die Zeile und schreibt sie ins DD-Ram
	if (zeile >= Init_LCD_Zeilen) //wurden mehr Zeilen angegeben als Initialisiert
		{
		zeile = Init_LCD_Zeilen - 1;
		}
	zeile = 0x80/Init_LCD_Zeilen*zeile;
	zeile += spalte;
	if (zeile >= 0x80) //ist der Wert ausserhalb des DD-Ram Adresse
		{
		zeile = 0x7F;
		}
	zeile += 0x80;
	Write_LCD (zeile,0);
	
	while (*Buffer != 0)
		{
		if (*Buffer == '%')
			{
			*Buffer++;
			switch (format_flag = *Buffer++){
 
				case 'c':
				   format_flag = va_arg(ap,int);
				   Write_LCD (format_flag++,1);
				   
				case 'i':
				case 'd':
				case 'u':
                base = 10;
                goto CONVERSION_LOOP;
				case 'o':
                base = 8;
                goto CONVERSION_LOOP;
				
				case 'X':
                hexA = 'A';
                // Weiter wie 'x'
				case 'x':
                base = 16;
				 }

				CONVERSION_LOOP:
                u_val = va_arg (ap, int);
				n = u_val;
                flags.fNegative = 0;
                if (format_flag == 'd' || format_flag == 'i') {
                    // Negative Werte auswerten
                    if (((int) u_val) < 0) {
                        flags.fNegative = 1;
                        u_val = -u_val;
                    }
                }
                // Der Scratchpuffer wird von rechts nach links aufgefüllt
                // beginnend mit dem niederwertigsten Digit.
                ptr = scratch + SCRATCH;
                *--ptr = 0;     // Abschliessendes NULL-Byte eintragen
                do 
				{
					char ch = u_val % base + '0';
                    if (ch > '9') ch += hexA - '9' - 1;
                    *--ptr = ch;
					u_val /= base;
                } while (u_val);
				
				if (n < base) *--ptr = '0';
                if (flags.fNegative) *--ptr = '-';
			    // Länge bestimmen
			    p = ptr;
			    nLen = 0;
			    while (*p++) nLen++;
				// Feld bei Bedarf links auffüllen
				if (!flags.fLeftJust) {
				for (n=nLen; n < nFieldWidth; n++) Write_LCD (' ',1);
				}
				// Pufferinhalt schreiben
				for (n=0; n < nLen; n++) Write_LCD (*ptr++,1);
				// Feld bei Bedarf rechts auffüllen
				if (flags.fLeftJust) {
				for (n=nLen; n < nFieldWidth; n++) Write_LCD (' ',1);
				}				
			}				
		Write_LCD (*Buffer++,1);
		}
	va_end(ap);
}

void LCD_Clear (void)
{
	Write_LCD (1,0); //Clear Display
	Write_LCD (0x80,0);	//Set DD-Ram Adresse = 0
}
Die Header DAtei zum festelgen der Ports und so
Code:
//LCD_D0 - LCD_D3 connect to GND
//Im 4Bit Mode LCD_D4-->PORTx.0 ........ LCD_D7-->PORTx.3
//LCD_RS --> PORTx.4 | LCD_RW --> PORTx.5 | LCD_E --> PORTx.6 | PORTx.7-->NotConnect

#define Init_LCD_Zeilen			2 		//Anzahl der Zeilen 1,2 oder 4

#define LCD_Port_DDR			DDRA	//Port an dem das Display angeschlossen wurde
#define LCD_Port_Write			PORTA
#define LCD_Port_Read			PINA

#define LCD_RS					4 		//Pin für RS
#define LCD_RW					5		//Pin für Read/Write
#define LCD_E					6 		//Pin für Enable

#define LCD_DataOutput			0x0f
#define LCD_DataInput			0x00

#define BusyBit					7

Das Programm funktioniert soweit, dass wir am Display was sehen, aber es gibt folgendes aus:

evs<--<--0_HxWWt0__Unterstrich

<-- ist ein Zeichen und ein Pfeil nach links
_ist ein Abstand am Display
Unterstrich ist ein Unterstrich am Display

Danke für eure Hilfe

MfG

saschisch