6-6 タイマー0を使った割り込み


タイマー0を使って1秒ごとの割り込みを発生させます。割り込みが発生したことは、音で知らせます。

このプログラムの本質は、78〜93行目のT0Mode2Initルーチンです。タイマー0のモード2、プリスケーラ付き16ビットカウンタを利用します。タイマーには32KHzが入るので、それをプリスケーラおよびカウンタで約1秒ごとにオーバーフローを起こすように設定します。

タイマー0はオーバーフローで割り込みを発生するので、その割り込みハンドラを用意します。割り込みハンドラ内では、カウントアップを行い、割り込み要因フラグを0にリセットして、割り込み処理を終了します。

メインルーチンでは、カウンタの値が偶数か奇数かを判定し、高い音と低い音を交互に出力します。61行目では、CPUをHALTモードにし、割り込みが発生するまで動作を停止します。タイマー0割り込みやポート3割り込みが発生すると、次の行から動作を開始します。

●GHEAD.ASM

001	chip	LC868700
002	world	external
003	; *-----------------------------------------------------*
004	; *	External header program Ver 1.00		*
005	; *					05/20-'98	*
006	; *-----------------------------------------------------*
007	
008	public	fm_wrt_ex_exit,fm_vrf_ex_exit
009	public	fm_prd_ex_exit,timer_ex_exit,_game_start,_game_end
010	other_side_symbol	fm_wrt_in,fm_vrf_in
011	other_side_symbol	fm_prd_in,timer_in,game_end
012	
013	extern	main			;ユーザープログラム側にあるシンボル
014	extern	int_T0H			;ユーザープログラム側にあるシンボル
015	
016	; *-----------------------------------------------------*
017	; *	Vector table(?)					*
018	; *-----------------------------------------------------*
019	cseg
020	org	0000h
021	_game_start:
022	;reset:
023			jmpf	main		; main program jump
024	org	0003h
025	;int_03:
026			jmp	int_03
027	org	000bh
028	;int_0b:
029			jmp	int_0b
030	org	0013h
031	;int_13:
032			jmp	int_13
033	org	001bh
034	;int_1b:
035			jmp	int_1b
036	org	0023h
037	;int_23:
038			jmp	int_23
039	org	002bh
040	;int_2b:
041			jmp	int_2b
042	org	0033h
043	;int_33:
044			jmp	int_33
045	org	003bh
046	;int_3b:
047			jmp	int_3b
048	org	0043h
049	;int_43:
050			jmp	int_43
051	org	004bh
052	;int_4b:
053			jmp	int_4b
054	; *-----------------------------------------------------*
055	; *	interrupt programs				*
056	; *-----------------------------------------------------*
057	int_03:
058			reti
059	int_0b:
060			reti
061	int_13:
062			reti
063	int_23:
064			jmp		int_T0H	;(ユーザー側割り込み処理へ)
065	int_2b:
066			reti
067	int_33:
068			reti
069	int_3b:
070			reti
071	; *-----------------------------------------------------*
072	int_43:
073			reti
074	int_4b:
075			clr1	p3int,1		;interrupt flag clear
076			reti
077	
078	org	0100h
079	; *-----------------------------------------------------*
080	; *	flash memory write external program		*
081	; *-----------------------------------------------------*
082	fm_wrt_ex:
083			change	fm_wrt_in
084		fm_wrt_ex_exit:
085			ret
086	org	0110h
087	; *-----------------------------------------------------*
088	; *	flash memory verify external program		*
089	; *-----------------------------------------------------*
090	fm_vrf_ex:
091			change	fm_vrf_in
092		fm_vrf_ex_exit:
093			ret
094	
095	org	0120h
096	; *-----------------------------------------------------*
097	; *	flash memory page read external program		*
098	; *-----------------------------------------------------*
099	fm_prd_ex:
100			change	fm_prd_in
101		fm_prd_ex_exit:
102			ret
103	
104	org	0130h
105	; *-----------------------------------------------------*
106	; *	flash memory => timer call external program	*
107	; *-----------------------------------------------------*
108	int_1b:
109	timer_ex:
110			push	ie
111			clr1	ie,7		;interrupt prohibition
112			change	timer_in
113		timer_ex_exit:
114			pop	ie
115			reti
116	
117	org	01f0h
118	_game_end:
119			change	game_end
120	end
●TIMER1.ASM
001	; Tab width = 4
002	
003	;----------------------------------------------------------------------------
004	; ** タイマ/カウンタT0割り込み使用サンプル1 **
005	;
006	; ・ブザー音を断続的(2秒周期)に出力する
007	;----------------------------------------------------------------------------
008	; 1.01 990208 SEGA Enterprises,LTD.
009	;----------------------------------------------------------------------------
010	
011	chip	LC868700			; チップの種類をアセンブラに指定
012	world	external			; 外部メモリ用プログラム
013	
014	public	main				; ghead.asm から参照されるシンボル
015	public	int_T0H				; ghead.asm から参照されるシンボル
016	
017	extern	_game_end			; アプリケーション終了
018	
019	
020	; **** システム定数の定義 ***************************************************
021	
022								; OCR(発振制御レジスタ)設定値
023	osc_rc		equ 04dh		;	システムクロックに内蔵RC発振を指定
024	osc_xt		equ 0efh		;	システムクロックに水晶発振を指定
025	
026	
027	; *** データセグメント ******************************************************
028	
029			dseg				; データセグメント開始
030	
031	r0:		ds		1			; 間接アドレッシングレジスタ r0
032	r1:		ds		1			; 間接アドレッシングレジスタ r1
033	r2:		ds		1			; 間接アドレッシングレジスタ r2
034	r3:		ds		1			; 間接アドレッシングレジスタ r3
035			ds		12			; その他のシステム予約レジスタ
036	
037	counter: ds		1			; タイマ割り込みカウンタ
038	
039	
040	; *** コードセグメント ******************************************************
041	
042			cseg				; コードセグメント開始
043			
044	; *-------------------------------------------------------------------------*
045	; * ユーザープログラム														*
046	; *-------------------------------------------------------------------------*
047	main:
048			call	SndInit		; 音声出力初期化
049			call	T0Mode2Init ; タイマ(T0)の初期化
050			mov		#0,counter	; カウンタのクリア
051			
052	loop0:	
053			ld		counter		; カウンタの値を読み込む
054			bp		acc,1,next1	; カウンタのbit0が1ならnext1へ
055			
056			call	Snd2Start	; 発音開始
057			br		next2
058	next1:
059			call	SndStop		; 音停止
060	next2:
061			set1	PCON,0		; 次の割り込みまでHALT
062	
063	
064								; ** [M](モード)ボタンチェック **
065			ld		P3
066			bn		acc,6,finish ; [M]ボタンが押されていたらアプリ終了
067	
068			br		loop0		; 繰り返し
069			
070	finish:						; ** アプリケーション終了処理 **
071			jmp		_game_end	; アプリケーション終了
072	
073	
074	; *-------------------------------------------------------------------------*
075	; * タイマ/カウンタT0 の初期化												*
076	; *   モード2(16bitカウンタ)で、約1秒毎に割り込みをかける					*
077	; *-------------------------------------------------------------------------*
078	T0Mode2Init:
079			mov		#255,T0PRR	; プリスケーラ値セット
080								;   8bitプリスケーラなので
081								;   周期 = (256-255)*0.000183 = 0.000183 (sec)
082			mov		#high(65536-5464),T0HR ; プリセット値(H)セット
083			mov		#low(65536-5464),T0LR  ; プリセット値(L)セット
084								;   プリスケーラとセットで
085								;   0.000183 * 5464 = 0.999912 (≒1sec)
086								;   1秒毎にオーバーフローが起こる
087			mov		#0ffh,T0L	; 最初すぐにオーバーフローするようにする
088			mov		#0ffh,T0H	;
089			mov		#0e4h,T0CNT	; モード2 (16bitカウンタ)
090								; T0Hオーバーフローで割り込みを発生させる
091								; T0動作開始
092		
093			ret					; T0Mode2Init終わり
094	
095	
096	T0HStop:					; *** T0Hタイマ停止 ***
097	
098			clr1	T0CNT,7		; T0Hカウント動作停止
099			ret
100	
101	
102	; *-------------------------------------------------------------------------*
103	; * タイマT0H割り込みハンドラ												*
104	; *-------------------------------------------------------------------------*
105	int_T0H:					; *** T0H割り込みハンドラ ***
106			inc		counter
107	
108			clr1	T0CNT,3		; タイマT0H割り込み要因クリア
109			reti
110	
111	
112	; *-------------------------------------------------------------------------*
113	; * 音声出力関係															*
114	; *-------------------------------------------------------------------------*
115	SndInit:					; *** 音声出力ハードの初期化 ***
116			clr1	P1,7		; 音声出力ポートセット
117		
118			ret
119			
120	Snd1Start:					; *** 約342Hz の発音開始 ***
121			mov		#0f0h,T1LR	; 周期 = 100h-0f0h = 16
122			mov		#0f8h,T1LC	; Lレベル幅 = 100h-0f8h = 8
123			mov		#0D4h,T1CNT	; 音声出力開始
124			
125			ret
126	
127	Snd2Start:					; *** 約781Hz の発音開始 ***
128			mov		#0f9h,T1LR	; 周期 = 100h-0f9h = 7
129			mov		#0fch,T1LC	; Lレベル幅 = 100h-0fch = 4
130			mov		#0D4h,T1CNT	; 音声出力開始
131			
132			ret
133	
134	SndStop:					; *** 発音停止 ***
135			mov		#0,T1CNT	; 音声出力停止
136			
137			ret

[]   [INDEX]   []

(C)SEGA ENTERPRISES, LTD., 1998