Ach, es geht um Servoimpulse, alles klar.

Vielleicht wäre das eine Basis:
Code:
// Servoansteuerung mit 16Bit-Timer1 (mit arexx cat16)             mic 18.1.2011

// Die 8 Servos werden an Port B und C angeschlossen:
// Servo0 - PB0
// Servo1 - PB1
// Servo2 - PC2
// Servo3 - PC3
// Servo4 - PC4
// Servo5 - PC5
// Servo6 - PC6
// Servo7 - PC7

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

volatile uint8_t count_20ms;
volatile uint16_t servo[9] ={1700, 1700, 1700, 1700, 1700, 1700, 1111, 1111, 40000}; // Servopositionen

void sleep(uint8_t pause);                    // 1/50 Sekunde blockierende Pause

int main(void)
{
	cli();

	// für 16MHz-ATMega16
	TCCR1A = (0<<WGM11)|(0<<WGM10);       		// CTC-Mode 4
	TCCR1B = (0<<WGM13)|(1<<WGM12);
	TCCR1B |= (0<<CS12)|(1<<CS11)|(0<<CS10);	// prescaler /8
	TIMSK = (1<<OCIE1A);                      // MatchCompare-Interrupt erlauben

	DDRB = 0b00000011;                        // Datenrichtung Servoausgänge setzen
	DDRC = 0b11111100;

	sei();
	sleep(100);

	while(1)                                  // Demo
	{
		cli();
		servo[0]=2500;
		servo[1]=servo[2]=1600;
		sei();
		sleep(50);

		cli();
		servo[0]=servo[1]=servo[2]=1700;
		sei();
		sleep(50);
	}
	return(0);
}

ISR(TIMER1_COMPA_vect)
{
	static uint8_t nr=8;                      // Nummer des aktuellen Servos

	PORTB &= ~0b00000011;                     // alle Servoimpulse low
	PORTC &= ~0b11111100;

	if(nr < 3)                                // Impuls für Servo oder Pause? (8 Servos)
	{
		if(nr<2) PORTB |= (1<<nr);             // Impulsleitung des aktuellen Servos
			else PORTC |= (1<<nr);              // auf High setzen und
		OCR1A = servo[nr];                     // Impulslänge in OCR1A laden
		servo[8] -= servo[nr];                 // Impulslänge von der Pause abziehen
		nr++;                                  // nächstes Servo
	}
	else
	{
		OCR1A = servo[8];                      // servo[8] ist die Impulspause
		servo[8] = 40000;                      // Startwert 20ms laden
		nr = 0;             							// beim nächsten ISR-Aufruf Impuls
															// für Servo 0 erzeugen
		if(count_20ms) count_20ms--;           // blockierende Pause aktiv?
	}
}
void sleep(uint8_t pause)                    // 1/50 Sekunde blockierende Pause
{
   count_20ms=pause+1;
   while(count_20ms);
}
(Aus https://www.roboternetz.de/community...l=1#post522751)

Das Programm wurde für einen 16MHz-Mega16 geschrieben, sollte aber auch auf dem Mega32 laufen. Der Timer1 läuft im CTC-Mode mit Prescaler/8 von 0 bis 40000 in 20ms. Während eines Zyklus werden nacheinander jeweils die Impulse für bis zu 8 Servos erzeugt. Die Servopositionen sind in servo[0] bis servo[7] gespeichert, 2000 sind eine Millisekunde (0,001s). In servo[8] ist der Wert für das Zyklusende gespeichert, ein kleinerer Wert (muss aber größer als die Summe der Servos sein, z.B TCNT1+=10) erhöht die Wiederholfrequenz. Mit if(nr < 3) kann man die Anzahl der verwendeten Servos ändern.

Gruß

mic