![]() ![]() INFO - FAQ - CC2-Forum - CCPro-Forum |
|
Hallo zusammen, ich habe wieder einen kleinen Demo-Sourcecode für die Open-Macro erstellt: ' =========================================================================== ' BEEP während normaler Programmausführung auf der Open-Macro ' In OCBASIC 1.08a von Dietmar Harlos am 18. April 2012 ' =========================================================================== ' Dieses Beispiel zeigt, wie ein Assemblerprogramm in den Timer1-Interrupt ' eingebunden wird, um den PORT[2] (eigentlich TCH1) schnell zu toggeln, so ' daß ein daran angeschlossener Piezo-Schallwandler einen Ton ausgibt. ' Diese Tonausgabe findet im Hintergrund, während der normalen Programm- ' abarbeitung statt. Allerdings deaktivieren einige Befehle (PRINT, GET, ' usw.) die Interrupts für einen kurzen Moment, so daß die Tonausgabe ' durch diese Befehle verzerrt wird. ' Die Variable für die Tonhöhe ("ton") darf Werte von 2 bis 1000 annehmen. ' Die erzeugte Frequenz in Hertz berechnet sich aus 50000/(2*ton). Der ' höchste Ton von 12,5 kHz ergibt sich bei "ton=2". ' Nachteile dieses Verfahrens: ' * TMOD auf $ffff (den Defaultwert nach Reset) würde dieses Programm ' erheblich vereinfachen, aber der Wert von 1000 ist vom OS vorgegeben. ' * Der Timer-Counter wird mit nur 3.2E6/64 = 50 kHz getaktet. Dadurch ' ergibt sich eine schlechte Abstufung und es können nur relativ geringe ' Frequenzen erzeugt werden. Auf der Original-C-Control (Version 1.1) ' dürfte der Timer-Counter mit 500 kHz arbeiten. Natürlich kann der ' Timer-Takt auf den OM-Controllern erhöht werden, aber evt. würden ' dann einige Treiber nicht mehr korrekt arbeiten. ' --------------------------------------------------------------------------- INCLUDE "omac.def" 'Definitionen für die Open-Macro DEFINE led PORT[4] 'diese LED wird im Hauptprogramm in BASIC getoggelt DIM ton WORD 'Variable für die Tonhöhe ' --------------------------------------------------------------------------- ' Die folgende PROCEDURE steht am Programmbeginn und es ist das Schlüssel- ' wort INLASM angegeben. Es handelt sich daher um eine IIAR. Also um eine ' Assembler-Interruptroutine, die bei einem aktivierten User-Interrupt ge- ' startet wird. Wenn mehr als eine IIAR in das System eingebunden werden ' soll, muß die Interruptquelle unterschieden und gegebenenfalls zur ' nächsten IIAR gesprungen werden (siehe dazu zum Beispiel DTMFRECT.BAS). PROCEDURE iiar_tim1 INLASM ! pusha 'Platz für Highbyte ! lda TCH1L ! add ton+1 ! pusha 'Lowbyte ! pusha ! lda TCH1H ! adc ton ! sta 3,sp 'Highbyte ! tax ! popa ! sub #$e8 ! pusha ! poph 'Lowbyte ins H-Register ! txa ! sbc #$03 ! bcs iiar_tim1_1 ! sta 2,sp 'Highbyte ! popa ! pushh #iiar_tim1_1 ! popx ! poph ! sthx TCH1H ! clc 'Diese Assemblerroutine übergibt nun wieder an ! rts 'das Betriebssystem. Dazu wird Carry geloescht. END PROCEDURE PROCEDURE init_tim1 INLASM ! bset bTSTOP,TSC 'Before changing a channel function by writing to ! bset bTRST,TSC ' the MSxB or MSxA bit, set the TSTOP and TRST bits. ! mov #&b01010100,TSC1 ! lda #$ff ! sta TCH1H 'TSC1: CH1F CH1IE 0 MS1A ELS1B ELS1A TOV1 CH1MAX ! sta TCH1L ! bclr bTSTOP,TSC ! rts END PROCEDURE PROCEDURE setbeep(ton) IF ton=0 THEN TCH1H=&hff 'Tonausgabe deaktivieren TCH1L=&hff ELSE TCH1H=0 'Tonausgabe aktivieren TCH1L=0 END IF RETURN END PROCEDURE ' --------------------------------------------------------------------------- #main UIRTim1=ON 'wir wollen den Timer1-User-Interrupt nutzen init_tim1 'Timer1 initialisieren und Interrupt aktivieren setbeep 2 'einmalig "setbeep" aufrufen led=ON WHILE ton<1000 PRINT ton TOG led 'eine LED blinken lassen PAUSE 25 ADD ton,1+ton/10 'jetzt kann einfach "ton" modifiziert werden WEND setbeep 0 'hiermit Tonausgabe beenden End2Host=ON 'und in den Host-Mode END Viel Spaß mit den OM-Controllern Dietmar Meine Homepage: http://ccintern.dharlos.de |
Antwort schreiben |