Code:
;===================================================================================
; Speicherbelegung
;r14 low-Byte der ADC-Wandlung (lsb)
;r15 high-Byte der ADC-Wandlung: Beide ergeben einen Wert zwischen 0...1023
;r16 Mehrzweck, high-Byte in Pausen "pause_an", "pause_aus", "led_ende" u.ä.
;r17 low-Byte in Pausen, s.o.
;
;r18 -- --
;r19 -- --
;r20 -- --
;
;r21 Byte Steuerbyte. Es werden nur Bits ausgewertet
; "Rampe" an-aus, 1=Rampe an, bit 1 = Servo 1 , bit 5 = Servo 2
; Übernahme Rampenwert, 1=Daten wurden noch nicht übernommen vom
; Hauptprogramm in die ISR, 0=ISR hat Daten abgeholt und zwar
; bit 2 = Servo 1 , bit 6 = Servo 2
;r22 1/2 Word lsb Zeitwert Rampe aus auf-ab-Rechnerei im Hauptprogramm
;r23 1/2 Word msb zu r26
;r24 1/2 Word LSB Zeitwert Rampe aus ADC/Poti im Hauptprogramm
;r25 1/2 Word MSB wird vom r14/15 geholt und zurechtgerechnet
;
;r26 1/2 Word LSB GESAMTDAUER Servoimpuls MUSS in r26/27 sein wegen sbiw
;r27 1/2 Word MSB Zeitwert für GESAMTDAUER Servoimpuls, etwa 500 Takte ?
;
;r28 1/2 Word lsb LSB RampenCOUNTER Servo1, wird in ISR runtergezählt
;r29 1/2 Word msb MSB Counter stammt vom ADC
;r30 1/2 Word lsb LSB Auf-ab-COUNTER Servo2, wird in ISR runtergezählt
;r31 1/2 Word msb MSB
;
;===================================================================================
; ..................
;===================================================================================
; Deklarationen für den Praeprozessor
; Konstanten ####### evtl. auch keine Konstanten definiert
;
#define a r16 ;Kurzbezeichung für Allzweckregister r16
;
; Anschlussbelegung, vgl. srv-adc+pwm-x29b.asm
#define servo1 3 ;Servo 1 auf Port PB3
#define potiadc 2 ;Poti 1 am Port PB4 geht auf ADC-Kanal 2
;
;Festwerte und div. Daten für adcdat etc ====>
#define adcpsc 7 ; =7 ==> Clock/128, 9,6 MHz werden 75 kHz, vgl. doc, S93
;#define adcdat 3 ;Dummywert vom ADC ###>>> "Nur" 8Bit-Wandlung ! ? !
#define msges 5000 ;Gesamtzeit der Rampe: 5000 ISR-Zyklen sind 20 ms
#define mstest 1000 ;Test ergibt mit mstest 500 und tmprs 40: für 2,0 ms
; das heisst: 4 µs Interrupt-Abstand (Fehler +4%)
#define msmin 100 ;Minimalwert für Rampe: 0,5 ms
#define tmrprs 38 ;Preset im Timer-Register (hoffentlich für CTC)
;
;===================================================================================
; Hauptprogramm
;===================================================================================
;
anfang:
; .......
;===================================================================================
;
;
isr_ctc: ;=== Immer wieder Veränderungen
;
sbiw r27:r26,1 ;Pointer von 5000 runterzählen
; für EINEN Servoimpuls von 20 ms
breq i_neu ; .. und Spezialfall "null" ==> Daten umschaufeln
; und Rampe einschalten. WENN keine neuen Daten da
; sind, dann alte Daten nehmen :(
;
; Jetzt wird nachgesehen, ob eine der Rampen ausgeschaltet werden muss. Das steht
; im Portbit ddrb
;
isr_nn: ;=== Zähler der ISR steht nicht auf Null
s1_pran: ;=== Servo1: Prüfe, ob Rampe ist an
in r20,portb
sbrs r20,servo1 ;Ist Rampe von servo1 an?
rjmp i_raus ;Wenn Rampe nicht an ist, dann gleich raus
;
sbiw r29:r28,1 ;Decrementiere Rampenwert
brne i_raus ;weiter, wenn noch nicht Null zu servo2
cbi portb,servo1 ; Sonst Lösche Rampe für Servo1
;
rjmp i_raus sbiw r29:r28,1
breq i_neu
rjmp i_raus
i_neu: ;Daten neu in Register und port servo1 umschalten
ldi r28,low(msmin)
ldi r29,high(msmin)
; mov r17,r15 ;Es ist adlar gesetzt, das ADCLH ist in r15
ldi r18,0
add r28,r15
adc r29,r18
;Und ADC-Wert gleich nochmal draufaddieren
; aber nur die Hälfte
clc ;Clear carry für anschliessende Division /2
ror r15 ;
add r28,r15
adc r29,r18
;
ldi r26,low(msges) ;Loopgrenzen für Gesamtloop 20 msec
ldi r27,high(msges)
sbi portb,servo1 ; Und setze Rampe für Servo1. FERTIG
;
i_raus:
reti ;=====----->>>>>
;
;===================================================================================
; Ende des Quellcodes
;===================================================================================
Lesezeichen