目次

定番プログラム

 ワンチップマイコンで、C言語の「Hello , World !」に
 相当する定番プログラムは、8個のLEDを使って、一列に
 並べた左右に光が流れるようにすることでしょう。

 LED表示器をテスト基板に接続して、左右に光を
 流してみます。

 利用した基板は、以下。



 プログラムは、次のようにしてみます。

;
;	TEST program for 8048 ( PROASM-II )
;	Copyright (C) 2017 Kensuke Ooyu
;
	INCLUDE 8048.LIB

;****************
; define symbols
;****************
ENTRY	equ	0h
E_INT	equ	3h
E_TIM	equ	7h

;*******************
; interrupt vectors
;*******************
	org	ENTRY
	jmp	START

	; external interrupt
	org	E_INT
	retr

	; timer interrupt
	org	E_TIM
	retr

	org	10h
;**************
; sub routines
;**************
INIT:
	; disable external interrupt
	dis	i
	; disable timer interrupt
	dis	tcnti
	; initialize I/O
	mov	a,#0
	outl	p1,a
	outl	p2,a
	;
	ret

WAIT:
	; set counter
	mov	R7,#0
WAITL:
	nop
	djnz	R7,WAITL
	;
	ret

;**************
; main routine
;**************
	org	100h
START:
	call	INIT
	;
MAIN:
	; set counter
	mov	R5,#8
	mov	R6,#1
MAIN1:
	; impress
	xch	a,R6
	outl	P1,a
	; delay
	call	WAIT
	; rotate
	rl	a
	xch	a,R6
	;
	djnz	R5,MAIN1

	; set counter
	mov	R5,#8
	mov	R6,#128
MAIN2:
	; impress
	xch	a,R6
	outl	P1,a
	; delay
	call	WAIT
	; rotate
	rr	a
	xch	a,R6
	;
	djnz	R5,MAIN2
	;
	jmp	MAIN

	end

 8048では、割込みベクタのアドレスが固定なので
 以下の3エントリーアドレスを使います。

 10hより若いアドレスにあるコードは、Vectorに
 なっているとして、3エントリーアドレスのみに
 限定します。

 8048では、プログラムをページ単位で処理する方が
 作成効率がよいので、32バイト、64バイトの範囲に
 収まるように、サブルーチンを構成しました。

 10hからFFhまでの240バイトに、サブルーチンをおく
 構成にし、100hから主ルーチンを配置。



 今回用意したサブルーチンは、初期化と遅延の2種。

 初期化サブルーチンでは、3種の処理をまとめました。

 遅延では、汎用レジスタR7に値を設定し
 djnz命令で、ゼロになるまでnopを実行。

 この程度のコードであれば、サブルーチン
 ひとつに32バイトもいらないでしょう。

 ワンチップマイコンのプログラミングでは
 サブルーチンを定義して、それを呼び出す
 構成が開発効率を上げることになります。

 主ルーチンでは、LEDの点灯位置が左右に
 移動するようにしました。



 アキュムレータから表示パターンをポートに転送
 すればよいので、汎用レジスタにLSB、MSBが1と
 なるパターンを入れておきます。

 汎用レジスタの値を、アキュムレータに転送して
 回転させつつ、ポートへ出力するカラクリを構成
 してみました。

 左から右、右から左と別のルーチンにしています。

 主ルーチンでの動作を理解しやすくするために
 左から右、右から左のパターン変化を、個別に
 扱うこともできます。

;
;	TEST program for 8048 ( PROASM-II )
;	Copyright (C) 2017 Kensuke Ooyu
;
	INCLUDE 8048.LIB

;****************
; define symbols
;****************
ENTRY	equ	0h
E_INT	equ	3h
E_TIM	equ	7h

;*******************
; interrupt vectors
;*******************
	org	ENTRY
	jmp	START

	; external interrupt
	org	E_INT
	retr

	; timer interrupt
	org	E_TIM
	retr

	org	10h
;**************
; sub routines
;**************
INIT:
	; disable external interrupt
	dis	i
	; disable timer interrupt
	dis	tcnti
	; initialize I/O
	mov	a,#0
	outl	p1,a
	outl	p2,a
	;
	ret

WAIT:
	; set counter
	mov	R7,#0
WAITL:
	nop
	djnz	R7,WAITL
	;
	ret

SFTL:
	; set counter
	mov	R5,#8
	mov	R6,#1
SFTL1:
	; impress
	xch	a,R6
	outl	P1,a
	; delay
	call	WAIT
	; rotate
	rl	a
	xch	a,R6
	;
	djnz	R5,SFTL1
	;
	ret

SFTR:
	; set counter
	mov	R5,#8
	mov	R6,#128
SFTR1:
	; impress
	xch	a,R6
	outl	P1,a
	; delay
	call	WAIT
	; rotate
	rr	a
	xch	a,R6
	;
	djnz	R5,SFTR1
	;
	ret

;**************
; main routine
;**************
	org	100h
START:
	call	INIT
	;
MAIN:
	; left shift
	call	SFTL
	; right shift
	call	SFTR
	;
	jmp	MAIN

	end

 主ルーチンは、サブルーチンに対して
 指示を与えるだけで対応できています。

 アセンブルした結果は、以下。

0000          	;
0000          	;	TEST program for 8048 ( PROASM-II )
0000          	;	Copyright (C) 2017 Kensuke Ooyu
0000          	;
0000          		INCLUDE 8048.LIB
0000          		list
0000          	
0000          	;****************
0000          	; define symbols
0000          	;****************
0000          	ENTRY	equ	0h
0003          	E_INT	equ	3h
0007          	E_TIM	equ	7h
0000          	
0000          	;*******************
0000          	; interrupt vectors
0000          	;*******************
0000          		org	ENTRY
0000 2400    +		jmp	START
0002          	
0002          		; external interrupt
0002          		org	E_INT
0003 93      +		retr
0004          	
0004          		; timer interrupt
0004          		org	E_TIM
0007 93      +		retr
0008          	
0008          		org	10h
0010          	;**************
0010          	; sub routines
0010          	;**************
0010          	INIT:
0010          		; disable external interrupt
0010 15      +		dis	i
0011          		; disable timer interrupt
0011 35      +		dis	tcnti
0012          		; initialize I/O
0012 2300    +		mov	a,#0
0014 39      +		outl	p1,a
0015 3A      +		outl	p2,a
0016          		;
0016 83      +		ret
0017          	
0017          	WAIT:
0017          		; set counter
0017 BF00    +		mov	R7,#0
0019          	WAITL:
0019 00      +		nop
001A EF19    +		djnz	R7,WAITL
001C          		;
001C 83      +		ret
001D          	
001D          	SFTL:
001D          		; set counter
001D BD08    +		mov	R5,#8
001F BE01    +		mov	R6,#1
0021          	SFTL1:
0021          		; impress
0021 2E      +		xch	a,R6
0022 39      +		outl	P1,a
0023          		; delay
0023 1417    +		call	WAIT
0025          		; rotate
0025 E7      +		rl	a
0026 2E      +		xch	a,R6
0027          		;
0027 ED21    +		djnz	R5,SFTL1
0029          		;
0029 83      +		ret
002A          	
002A          	SFTR:
002A          		; set counter
002A BD08    +		mov	R5,#8
002C BE80    +		mov	R6,#128
002E          	SFTR1:
002E          		; impress
002E 2E      +		xch	a,R6
002F 39      +		outl	P1,a
0030          		; delay
0030 1417    +		call	WAIT
0032          		; rotate
0032 77      +		rr	a
0033 2E      +		xch	a,R6
0034          		;
0034 ED2E    +		djnz	R5,SFTR1
0036          		;
0036 83      +		ret
0037          	
0037          	;**************
0037          	; main routine
0037          	;**************
0037          		org	100h
0100          	START:
0100 1410    +		call	INIT
0102          		;
0102          	MAIN:
0102          		; left shift
0102 141D    +		call	SFTL
0104          		; right shift
0104 142A    +		call	SFTR
0106          		;
0106 2402    +		jmp	MAIN
0108          	
0108          		end

 各サブルーチンは、16バイトにも満たないので
 ページを跨ぐような奇抜な処理も取られてません。

 主ルーチンは指示を与えるだけにして
 実際の処理はサブルーチンに任せると
 段階的詳細化ができます。


目次

inserted by FC2 system