So hier ist der ganze Code:

1. der Header

Code:
#ifndef __funktion.h__
#define __funktion.h__

#include<avr/io.h>				//allgemeine Header
#include<math.h>				//Header für pow() funktion
#include<string.h>
#include<avr/signal.h>
//#include <avr/interrupt.h>

//----------------------------ADC-------------------------------

inline void adc_init(void);

float adc(unsigned char);

//--------------------------------------------------------------



//---------------------------UART-------------------------------

inline void uart_init(void);

void receive(void);				//zum erhalten der Daten

void senden(char sende_string[]);					//wenn printf, wird das nicht benötigt

//void string_empf(void);

//--------------------------------------------------------------



//---------------------------8Bit Timer-------------------------

inline void timer8_init(void);

//--------------------------------------------------------------


//---------------------------PWM-------------------------------

void pwm_init(void);

inline void pwm_vergleichswert(int);

//-------------------------------------------------------------



//---------------------------Regler---------------------------

int regler_funct (float, float, float, float);

//------------------------------------------------------------

//------------------------- Protokoll-------------------

char BCC (char pc_daten[]);

void auswerten(void);

float zeichentofloat_daten(unsigned char string_teil[],char start, char stop);

void nachricht(void);

//void werte_schicken(unsigned char);

//------------------------- Variablen-------------------------
 #define DATEN_LEN_MAX 20
 
 extern float prozent_wert;					//Prozent wert nach ADC
 extern int vergleichswert;			//Der vergleichwert bei PWM(OCR1A), in Regler.c verwendet
 //unsigned char kanal;					//Variable wird bei der Funktion adc(kanal) übergeben
 extern unsigned char pc_daten[DATEN_LEN_MAX];				//Das Feld in der ich die einzelnen Zeichen die ich vom PC bekomme reinspeichere, in protokoll.c verwendet
 extern char fehler;					//in protokoll.c, Die Variable in der das Ergebnis von BCC(pc_daten) gespeichert wird
 extern char start_brenn;				//in Regler.c verwendet
 //extern char mein_bcc;					
 extern float kurven_temp[10];			//in Protokoll.c verwendet, zum abspeichern der erhaltenen Temperatur Daten
 extern float kurven_zeit[10]; 			//in Protokoll.c verwendet, zum abspeichern der erhaltenen Zeit Daten
 extern unsigned char sende_string[20];	//für nachricht(), zum string generieren, in protokoll.c
 extern unsigned char j;                 //für string empfangen, in receive()
 extern unsigned char zeichen_empf;		//in Regler.c verwendet,(UART Interrupt)
 extern unsigned char zeit_abfrage;		//in Regler.c verwendet, für zeit abfrage
 extern unsigned char anz;				//in Protokoll.C verwendet
 extern int zaehlen;						//in Regler.C verwendet(Timer Interrupt)
 extern int zeit;							//in Regler.C verwendet (Timer Interrupt)
 extern float aktuelle_zeit;					//in Regler.C verwendet
 extern char uebert_beendet;				//in Regler.c, Hilfsvariable zum erkennen wann der erhaltene String zu Ende ist
 
//Regler_funct.c Variablen
 
 
 extern float prozent_istwert;			//Nach ADC wandlung, auf Prozent*100 umgerechnet, Das ist der Istwert des Reglers
 extern float prozent_sollwert;		//Nach ADC wandlung, auf Prozent*100 umgerechnet, Das ist der Sollwert des Reglers
 extern float kp;						//die Reglerverstärkung
 extern float tn;						//die Nachstellzeit, für I-Anteil

 
//------------------------------------------------------------
#endif
2. Das Hauptprogramm:
Code:
#include "funktion.h"

int vergleichswert;			//Der vergleichwert bei PWM(OCR1A)
char start_brenn;
unsigned char zeit_abfrage;
char uebert_beendet;
float hzeit;
unsigned char m;
unsigned char zeichen_empf;
int zaehlen;
int zeit;
float aktuelle_zeit;


int main(void)
	{
	
	
	
	SREG|=(1<<7);					//das I-Bit auf "1" setzen, für Overflow Interrupt
	
	DDRB=0x00;						//Datenrichtung von PORTB (Eingang)
	DDRC=0xFF;						//Datenrichtung von PORTC (Ausgang)
	DDRD=0xFF;						//Datenrichtung von PORTD (Ausgang) für PWM(PD5)
	DDRA=0x00;						//Datenrichtung von PORTA (Eingang) für ADC(PA0)
	
	PORTC=0x01;
	
	/*Variablen Dekleration*/	
	PORTB=0xFF;																	//PortB auf Pull up setzen
	//kanal=0;																	//Kanal auf 0 (PA0) verwenden
	aktuelle_zeit=0;
	start_brenn=0;
	anz=0;										//Feldindex für kurven_temp und kurven_zeit, damit nur bei erhalten eines ganzen
												//strings die Variable hinaufgezählt wird
	zaehlen=0;
	PORTC=0x01;
	m=0;
	zeit=0;
	j=0;
	uebert_beendet=0;
	zeit_abfrage=0;
	
	kp=2;										//angenommenes kp
	tn=0.6;										//angenommene Tn

	//PORTC=0x01;
	
	
	
	adc_init();						//Funktion: ADC initialisieren(Register)

	uart_init();					//Funktion: UART initialisieren(Register)
	
	
	sende_string[0]='\0';
		

	
	
	/*
	kurven_zeit[0]=2.00;				kurven_temp[0]=50;
	kurven_zeit[1]=300;				kurven_temp[1]=50;
	kurven_zeit[2]=500;				kurven_temp[2]=100;
	
	start_brenn=1;
	
	PORTC=0x00;
	hzeit=kurven_zeit[0];
	*/
	start_brenn=1;
	
	while(1)
		{
		pwm_init();
		if(start_brenn==0&&uebert_beendet==0)
			{
			
			while(uebert_beendet==0)						//Es wird solange receive() aufgerufen bis die übertragung beendet ist
				{											// solange bis ein 'y' gesendet worden ist
				PORTC=0xF0;
				
				if(zeichen_empf==1)
					{
					receive();
					zeichen_empf=0;
					}
				}
			
				
			uebert_beendet=0;							//danach wird die Variable wieder auf 0 gesetzt wür das nächste mal
			j=0;
			
			if(start_brenn==0)
				{
				fehler=BCC(pc_daten);						//Beim erhaltenen String wird gleich BCC bestimmt, und mit dem erhaltenen verglichen
				auswerten();								// zum abspeichern der Daten
				}
			
			if(start_brenn==1)
				{
				fehler=BCC(pc_daten);						//Beim erhaltenen String wird gleich BCC bestimmt, und mit dem erhaltenen verglichen
				auswerten();								//zum abspeichern der Daten
				}
			}
			
			
			
			
		
		if(start_brenn==1)
			{
			PORTC=0xF0;
			//pwm_init();					//Funktion: 10 Bit PWM mit Phasen Correct Mode (Register)
			//OCR1A=512;
			timer8_init();						//Funktion: 8 Bit Timer initialisieren(Register)
			
			if(zeichen_empf==1)
				{
				PORTC=0x0F;
				while(uebert_beendet==0)						//Es wird solange receive() aufgerufen bis die übertragung beendet ist
					{											// solange bis ein 'y' gesendet worden ist
					//PORTC=0x80;
				
					if(zeichen_empf==1)
						{
						receive();
						zeichen_empf=0;
						}
					}
				uebert_beendet=0;							//danach wird die Variable wieder auf 0 gesetzt wür das nächste mal
				}
			
			if(zeit_abfrage==1)
				{
				fehler=BCC(pc_daten);						//Beim erhaltenen String wird gleich BCC bestimmt, und mit dem erhaltenen verglichen
				auswerten();								//Die Funktion auswerten() wird auch aufgerufen
				
				zeit_abfrage=0;
				//PORTC=0x01;
				}
			
			if(aktuelle_zeit<=hzeit)
				{
				prozent_sollwert=kurven_temp[m];
				}
			else
				{ 
				m++;
				prozent_sollwert=kurven_temp[m];
				hzeit=kurven_zeit[m];		
				}
			
			}
		
		}
	}
	
	
	
//___________________________________________RXC Interrupt____________________________________________________________________


SIGNAL(SIG_UART_RECV)
	{
	zeichen_empf=1;
	}

//__________________________________________TIMER0 Overflow____________________________________________________________________________


SIGNAL (SIG_OVERFLOW0)
	{
	zaehlen++;
		
	
	
	if(zaehlen==30)								//ausgerechnet für  Sekunde pro Timer overflow
		{			
		//OCR1A=0;
		
		if(zeit==0)
			zeit=1;
		else
			zeit=zeit+1;  						//zeit in sek.
		
		prozent_istwert=adc(1);			//den wert von der Funktion adc() in Prozent istwert schreiben
		//prozent_sollwert=adc(2);		
		
		vergleichswert=regler_funct(prozent_istwert,prozent_sollwert,kp,tn);
				
		pwm_vergleichswert(vergleichswert);
		
		//prozent_istwert=0;
		zaehlen=0; 

		//PORTC=0xFF;
		
		}	
	aktuelle_zeit=(zeit*100)/60;			//Mit Franz vereinbart, Minuten mal 100

	}
3. Unterprogramme(pwm_init, pwm_vergleichswert):
Code:
//_________________________________________Initialisieren des Timers________________________________________________

void pwm_init(void)
	{
										//Für Puslweiten, Datenrichtung für PD5 auf Ausgang
	PORTC=0x0F;
	
	TCCR1A=(1<<COM1A1)|(1<<COM1A0); 			// wird OC1A/OC1B zum vergleichen, clear bei TOP
	
	//zum auswählen von Phasen Correct Mode
	TCCR1A|=(1<<WGM11)|(1<<WGM10);
	

	TCCR1B=(1<<CS10);						//Takt: Im Timer ControlRegister den Takt für den Prescaler festlegen
											//jetzt wird die Oszillator Freqzenz verwendet (8 MHz)    
	//OCR1A=512;

	}
//__________________________________________________________________________________________________________________



//________________________________________Vergleichswert bestimmen__________________________________________________

void pwm_vergleichswert(int vergleichswert)
	{
	int hilfpwm;
	
	//hilfpwm=1024-vergleichswert;
	hilfpwm=vergleichswert;
	if(hilfpwm<=10)
		{
		hilfpwm=21;
		}
	
	if(hilfpwm>=1000)
		{
		hilfpwm=1023;
		}
	
	//OCR1A= hilfpwm-10;
	OCR1A=hilfpwm;
	//OCR1A=512;
	}
4.UnterprogrammeBCC, auswerten, zeichentofloat_daten, nachricht)

Code:
#include "funktion.h"					//Header für meine eigen angelegten Funktione
#include <stdlib.h>

unsigned char pc_daten[DATEN_LEN_MAX];						//Das Feld in der ich die einzelnen Zeichen die ich vom PC bekomme reinspeichere (auswerten)
float kurven_temp[10];
float kurven_zeit[10];
char fehler;           					//Die Variable in der das Ergebnis von BCC(pc_daten) gespeichert wird
unsigned char sende_string[20];
unsigned char anz;


char BCC(char string[])				//Es werden die pc_daten übergeben
	{ 
	char ergebnis;						//Variable in der das Ergebnis des BCC abgespeichert wird
	unsigned char n;							//Laufvariablen
	char ok;							//sollte eine Variable zum überprüfen sein
  
	ok=0;								//Am Anfang auf "0" gesetzt
	ergebnis='\0';
	
	for( n=0;n<30;n++)
		{
		if(string[n]=='x')				//das Daten feld wird durchgelaufen, und überprüft ob ein 'x' drinnen ist
			{   						//wenn ja, dann wird OK=1 gesetzt und die For schleife verlassen
			ok=1;
			break;	
			}
		}

	if (ok==1)							//wenn 'x' drinnen ist, dann geht er in diesen Zweig
		{ 
		for(unsigned char k=n+1;k<60;k++)
			{
			if(k==n+1)					//wenn er das erste mal die Forschleife durchläuft, dann soll er als ergebnis
				{						//das nächste zeichen nach dem 'x' übernehmen
				ergebnis=string[k];
				}
			else						//wenn er die For schleife nicht zum ersten mal durchläuft, dann
				{
				ergebnis=ergebnis^string[k];		//soll er das ergebnis mit dem Zeichen EXOR verknüpfen
				}

			if(string[k]=='y')		//Wenn das übernächste Zeichen ein 'y' ist, dann soll er die For schleife verlassen
				break;
			}
		}
	
	return(ergebnis);					//als char soll er ergebnis zurück liefern
	}



void auswerten(void)					
	{
	unsigned char i;
	//unsigned char l;
	char stelle_z, stelle_y, stelle_i,stelle_komma; 
	unsigned char stelle_bcc,r;
	char bcc_ok;
	
	
	stelle_komma=stelle_bcc=stelle_z=stelle_i=bcc_ok=stelle_y=0; 
	
	
	for(unsigned char l=0;l<60;l++)					// In dieser Schleife speichere ich jeweils die Stelle von 'z', 'i', und 'd' ab
		{
		
		switch(pc_daten[l])
			{
			case 'z': stelle_z=l;		//zum herausfinden, an welcher stelle der jeweilige Buchstabe abgespeichert ist
					   
			case 'i': stelle_i=l;
					   
			//default: break;
			}
		
		if(pc_daten[l]=='y')			//Hier wird die Stelle von Bcc herausgefunden
			{
			stelle_y=l;
			stelle_bcc=l+1;				//Hier wird die Stelle vom BCC hinein gespeichert	
			
			if(fehler==pc_daten[stelle_bcc]&&zeit_abfrage==0)		//Wenn das vorher ausgerechnete eigene BCC gleich dem erhaltenen ist
				{
				sende_string[0]='x'; sende_string[1]='y';  sende_string[2]='\0';
				senden(sende_string);
				sende_string[0]='\0';
				bcc_ok=1;
				break;
				}
				
			if(fehler==pc_daten[stelle_bcc]&&zeit_abfrage==1)
				{
				nachricht();
				senden(sende_string);
				sende_string[0]='\0';
				break;
				}
			else
				{
				bcc_ok=0;
				sende_string[0]='B'; sende_string[1]='C';  sende_string[2]='C';  sende_string[3]=fehler;   sende_string[4]=pc_daten[stelle_bcc];  sende_string[5]='\0'; 
				senden(sende_string);
				sende_string[0]='\0';
				break;
				}
			
			}
		}
	for(r=0;r<60;r++)
		{
		
		if(pc_daten[r]=='x')
			break;
		}
	
	if(pc_daten[0+r]=='x'&&bcc_ok==1&&start_brenn==0)	
		{								//wenn das erste Zeichen ein 'x' ist soll er in diesen Zweig gehen
		
		for(i=1+r;i<60;i++)
			{
			
			switch(pc_daten[i])		//Es wird überprüft wo ein 't','z','p','i','d'
				{
				case 't': //	if(fehler!='t'&&pc_daten[i-1]!='y')
								{
								kurven_temp[anz]=zeichentofloat_daten(pc_daten,stelle_z,i);  	//es wird pc_daten, die stelle vom z und die aktuelle stelle(i) übergeben
								break;	
								}
									
				case 'z':	//if(fehler!='z'&&pc_daten[i-1]!='y')
								{
								kurven_zeit[anz]=zeichentofloat_daten(pc_daten,stelle_y,i);	//es wird pc_daten, die stelle vom bcc und die aktuelle stelle(i) übergeben
								//PORTC=0x0F;
								/*
								werte_schicken(anz);
								senden(sende_string);
								sende_string[0]='\0';
								PORTC=0x0F;
								*/
								anz++;
								break;	
								}
				
				case 'p':  if(fehler!='p'&&pc_daten[i-1]!='y')
								{
								kp=zeichentofloat_daten(pc_daten,stelle_i,i);					//es wird pc_daten, die stelle vom i und die aktuelle stelle(i) übergeben
								break;
								}
				
				case 'i':  if(fehler!='i'&&pc_daten[i-1]!='y')
								{
								tn=zeichentofloat_daten(pc_daten,stelle_y,i);					//es wird pc_daten, die stelle vom d und die aktuelle stelle(i) übergeben
								break;
								}
				
				default: break;
				}
								
			if(fehler==pc_daten[i+1])
				break;
				
			}
		
		}
		bcc_ok=0;
	
	}
	

float zeichentofloat_daten(unsigned char string_teil[],char stop, char start)			//Funktion: Aus Zeichen wird eine Gleitpunktzahl gemacht
	{
	unsigned char k,m,n, stelle_komma;				
	float ganzzahl;
	float kommazahl;
	float gleitpunktzahl;
	double zw_speicher;
	m=0;										//muss am anfang auf 0 sein!
	n=1;										//muss am anfang auf 1 sein!
	stelle_komma=kommazahl=ganzzahl=0;			//am anfang sicherheitshalber auf 0 gesetzt
	
	for(k=start+1;k<stop;k++)					//hier wird überprüft, ob in dem Teilstring von start bis stop ein Komma vorliegt
		{
		if(string_teil[k]==',')
			{
			stelle_komma=k;						//wenn ja, dann wird die Stelle abgespeichert
			break;
			}
		}

	if(stelle_komma>0)							//ist ein komma vorhanden, dann wird eine For Schleife gestartet, von
		{										//Komma+1 weg bis stop
		for(k=stelle_komma+1;k<stop;k++)
			{
			zw_speicher=pow(10,-n);
			kommazahl=kommazahl+zw_speicher*(string_teil[k]-48);		//es wird immer zur kommazahl, das aktuelle zeichen mit 10 hoch -n multipliziert, -48 wegen Hex auf Dec
			n++;												//ist die Wertigkeit für pow() funktion
			}
		
		for(k=stelle_komma-1;k>start;k--)		//Komma-1 weg bis start
			{
			zw_speicher=pow(10,m);
			ganzzahl=ganzzahl+zw_speicher*(string_teil[k]-48);			//es wird immer zur kommazahl, das aktuelle zeichen mit 10 hoch -n multipliziert, -48 wegen Hex auf Dec
			if(m==0)
				ganzzahl=ganzzahl*2;
			m++;													//ist die Wertigkeit für pow() funktion
			}
		}
	else										//ist kein komma vorhanden, dann wird eine For Schleife gestartet, von				
		{
		for(k=stop-1;k>start;k--)		//Komma-1 weg bis start
			{
			ganzzahl=ganzzahl+pow(10,m)*(string_teil[k]-48);			//es wird immer zur kommazahl, das aktuelle zeichen mit 10 hoch -n multipliziert, -48 wegen Hex auf Dec
			if(m==0)
				ganzzahl=ganzzahl*2;
			m++;													//ist die Wertigkeit für pow() funktion
			}
		}

	
	gleitpunktzahl=ganzzahl+kommazahl;				
		
	return( gleitpunktzahl );				//als float return geliefert
	}



void nachricht(void)
	{
	
	unsigned char hstring[5],bcc_senden;
	unsigned char laenge1,laenge;
	int zw_speicher_istwert,zw_speicher_aktuellezeit;
	
	for(unsigned char i=0;i<20;i++)
		{
		sende_string[i]='\0';
		}
	
	sende_string[0]='x';
	sende_string[1]='t';
	
	zw_speicher_istwert=prozent_istwert*10;
	
	itoa(zw_speicher_istwert,hstring,10);
	
	strcat(sende_string,hstring);
	
	laenge=strlen(sende_string);
	sende_string[laenge]='z';
	
	zw_speicher_aktuellezeit=aktuelle_zeit;
	itoa(aktuelle_zeit,hstring,10);
	
	strcat(sende_string,hstring);
	
	laenge1=strlen(sende_string);
 	sende_string[laenge1]='y';
	
	bcc_senden=BCC(sende_string);
	sende_string[laenge1+1]=bcc_senden;

	}

Bei der nächsten Nachricht geht es weiter, darf nicht mehr wie 20000 Zeichen!