misc/rtctrnstest.s
;========================================================================================
; rtctrnstest.s
; Copyright (C) 2003-2026 Makoto Kamada
;
; This file is part of the XEiJ (X68000 Emulator in Java).
; You can use, modify and redistribute the XEiJ if the conditions are met.
; Read the XEiJ License for more details.
; https://stdkmd.net/xeij/
;========================================================================================
;----------------------------------------------------------------
; 名前
; rtctrnstest.x
; 機能
; RTCのカウンタが実機と同じように遷移しているか確認します
; 環境
; X680x0シリーズ全機種およびエミュレータ
; 注意
; 時計が狂います。終了後に時計を合わせてください
; 操作
; A>rtctrnstest.x
; RTCのカウンタが実機と同じように遷移しているか確認します
; ....................................................................................
; 8495 成功, 0 失敗
; 時計を合わせてください
; A>
;----------------------------------------------------------------
.include control2.mac
.include doscall.mac
.include misc.mac
.include ppi.equ
.include push2.mac
.include rtc.equ
;レジスタ
dWH reg d1 ;書き込む値
dWL reg d2
dPH reg d3 ;前回読み出した値
dPL reg d4
dRH reg d5 ;読み出した値
dRL reg d6
dT reg d7 ;テンポラリ
aTRY reg a2 ;試行回数
aOH reg a3 ;前々回読み出した値
aOL reg a4
;ウェイト
aPPIA reg a5
lea.l PPI_PORT_A,aPPIA
wait .macro
tst.b (aPPIA)
tst.b (aPPIA)
.endm
;RTCアクセス
aRTC reg a6
lea.l RTC_0_ONE_SECOND,aRTC
rtc reg -RTC_0_ONE_SECOND(aRTC)
read_rtc .macro src,dst
moveq.l #$0F,dst
and.b (src)rtc,dst
wait
.endm
write_rtc .macro src,dst
move.b src,(dst)rtc
wait
.endm
;モード
mode_clear .macro mask
read_rtc RTC_MODE,dT
and.b #.notb.(mask),dT
write_rtc dT,RTC_MODE
.endm
mode_set .macro mask
read_rtc RTC_MODE,dT
or.b #(mask),dT
write_rtc dT,RTC_MODE
.endm
clock_stop .macro
mode_clear RTC_MODE_CLOCK_MASK
.endm
clock_start .macro
mode_set RTC_MODE_CLOCK_MASK
.endm
bank_0 .macro
mode_clear RTC_MODE_BANK_MASK
.endm
bank_1 .macro
mode_set RTC_MODE_BANK_MASK
.endm
;リセット
clock_reset .macro
write_rtc #RTC_RESET_16HZ_MASK|RTC_RESET_CLOCK_MASK,RTC_RESET
write_rtc #RTC_RESET_16HZ_MASK,RTC_RESET
.endm
;タイトル
lea.l title_message,a0
jbsr print
;データ
move.l #data_table,data_pointer
clr.l passed_counter
clr.l failed_counter
;スーパーバイザモード
supervisormode
;カウンタ停止
clock_stop
;カウンタ保存
bsr read_counters
move.l dRH,saved_counters
move.l dRL,saved_counters+4
;書き込む値のループ
move.w #100,dot_counter
dostart
move.l (a0)+,dWL
move.l a0,data_pointer
;3回続けて失敗したら遷移が間違っていると判断する
movea.w #3-1,aTRY
do
;カウンタに書き込む
bsr write_counters
;秒テスト準備
moveq.l #$0F,dPL
and.b dWL,dPL
;秒テスト開始
di
write_rtc #1,RTC_TEST
;1秒カウンタが変化するまで待つ
do
read_rtc RTC_0_ONE_SECOND,dRL
while <cmp.b dPL,dRL>,eq
;秒テスト終了
write_rtc #0,RTC_TEST
ei
;前回読み出した値をダミーに
moveq.l #-1,dPH
moveq.l #-1,dPL
;読み出した値をダミーに
moveq.l #-1,dRH
moveq.l #-1,dRL
;3回続けて同じ値が読み出されるまで繰り返す
do
;前回読み出した値を前々回読み出した値にコピー
movea.l dPH,aOH
movea.l dPL,aOL
;読み出した値を前回読み出した値にコピー
move.l dRH,dPH
move.l dRL,dPL
;カウンタから読み出す
bsr read_counters
whileor <cmp.l aOH,dRH>,ne,<cmp.l aOL,dRL>,ne
;確認
move.l dWL,-(sp)
move.l dWH,-(sp)
jbsr increment
move.l (sp)+,dPH
move.l (sp)+,dPL
breakand <cmp.l dPH,dRH>,eq,<cmp.l dPL,dRL>,eq ;成功
subq.w #1,aTRY
move.w aTRY,d0
while pl
if eq ;成功
addq.l #1,passed_counter
else ;失敗
if <tst.l failed_counter>,eq ;初回
;ヘッダ表示
lea.l header_message,a0
jbsr print
endif
addq.l #1,failed_counter
;エラー表示
lea.l string_buffer,a0
;input
move.l dWH,d0
jbsr h8tos
move.b #':',(a0)+
move.l dWL,d0
jbsr h8tos
;expected output
move.b #' ',(a0)+
move.l dPH,d0
jbsr h8tos
move.b #':',(a0)+
move.l dPL,d0
jbsr h8tos
;observed output
move.b #' ',(a0)+
move.l dRH,d0
jbsr h8tos
move.b #':',(a0)+
move.l dRL,d0
jbsr h8tos
lea.l error_message,a1
jbsr strcpy
lea.l string_buffer,a0
jbsr print
endif
;ドット表示
subq.w #1,dot_counter
if eq
lea.l dot_message,a0
jbsr print
;カウンタ停止(念のため)
clock_stop
move.w #100,dot_counter
endif
start
movea.l data_pointer,a0
move.l (a0)+,dWH
while pl
;カウンタ復元
; 気休め。時間がかかったぶん遅れるので修正すること
move.l saved_counters,dWH
move.l saved_counters+4,dWL
bsr write_counters
;カウンタ動作
clock_start
;ユーザモード
usermode
;結果表示
lea.l string_buffer,a0
jbsr crlf
move.l passed_counter,d0
jbsr utos
lea.l passed_message,a1
jbsr strcpy
move.l failed_counter,d0
jbsr utos
lea.l failed_message,a1
jbsr strcpy
lea.l string_buffer,a0
jbsr print
;終了
DOS _EXIT
;カウンタから読み出す
;>dRL.l:読み出した値(下位)
;>dRH.l:読み出した値(上位)
read_counters:
;カウンタから読み出す(上位)
bank_1
read_rtc RTC_1_LEAP_YEAR,dRH ;_______L
bank_0
read_rtc RTC_0_DAY_OF_WEEK,dT
lsl.l #4,dRH
or.b dT,dRH ;______LW
read_rtc RTC_0_TEN_YEARS,dT
lsl.l #4,dRH
or.b dT,dRH ;_____LWY
read_rtc RTC_0_ONE_YEAR,dT
lsl.l #4,dRH
or.b dT,dRH ;____LWYY
read_rtc RTC_0_TEN_MONTHS,dT
lsl.l #4,dRH
or.b dT,dRH ;___LWYYM
read_rtc RTC_0_ONE_MONTH,dT
lsl.l #4,dRH
or.b dT,dRH ;__LWYYMM
read_rtc RTC_0_TEN_DAYS,dT
lsl.l #4,dRH
or.b dT,dRH ;_LWYYMMD
read_rtc RTC_0_ONE_DAY,dT
lsl.l #4,dRH
or.b dT,dRH ;LWYYMMDD
;カウンタから読み出す(下位)
bank_1
read_rtc RTC_1_TWENTY_FOUR,dRL ;_______t
bank_0
read_rtc RTC_0_TEN_HOURS,dT
lsl.l #4,dRL
or.b dT,dRL ;______th
read_rtc RTC_0_ONE_HOUR,dT
lsl.l #4,dRL
or.b dT,dRL ;_____thh
read_rtc RTC_0_TEN_MINUTES,dT
lsl.l #4,dRL
or.b dT,dRL ;____thhm
read_rtc RTC_0_ONE_MINUTE,dT
lsl.l #4,dRL
or.b dT,dRL ;___thhmm
read_rtc RTC_0_TEN_SECONDS,dT
lsl.l #4,dRL
or.b dT,dRL ;__thhmms
read_rtc RTC_0_ONE_SECOND,dT
lsl.l #4,dRL
or.b dT,dRL ;_thhmmss
rts
;カウンタに書き込む
;<dWL.l:書き込む値(下位)
;<dWH.l:書き込む値(上位)
write_counters:
;カウンタに書き込む(上位)
bank_1
rol.l #4,dWH ;WYYMMDDL
write_rtc dWH,RTC_1_LEAP_YEAR
bank_0
rol.l #4,dWH ;YYMMDDLW
write_rtc dWH,RTC_0_DAY_OF_WEEK
rol.l #4,dWH ;YMMDDLWY
write_rtc dWH,RTC_0_TEN_YEARS
rol.l #4,dWH ;MMDDLWYY
write_rtc dWH,RTC_0_ONE_YEAR
rol.l #4,dWH ;MDDLWYYM
write_rtc dWH,RTC_0_TEN_MONTHS
rol.l #4,dWH ;DDLWYYMM
write_rtc dWH,RTC_0_ONE_MONTH
rol.l #4,dWH ;DLWYYMMD
write_rtc dWH,RTC_0_TEN_DAYS
rol.l #4,dWH ;LWYYMMDD
write_rtc dWH,RTC_0_ONE_DAY
;カウンタに書き込む(下位)
bank_1
rol.l #8,dWL ;hhmmss_t
write_rtc dWL,RTC_1_TWENTY_FOUR
bank_0
rol.l #4,dWL ;hmmss_th
write_rtc dWL,RTC_0_TEN_HOURS
rol.l #4,dWL ;mmss_thh
write_rtc dWL,RTC_0_ONE_HOUR
rol.l #4,dWL ;mss_thhm
write_rtc dWL,RTC_0_TEN_MINUTES
rol.l #4,dWL ;ss_thhmm
write_rtc dWL,RTC_0_ONE_MINUTE
rol.l #4,dWL ;s_thhmms
write_rtc dWL,RTC_0_TEN_SECONDS
rol.l #4,dWL ;_thhmmss
write_rtc dWL,RTC_0_ONE_SECOND
rts
;インクリメント
; 0 1 2 3 4 5 6 7
; $LWYYMMDD,$_thhmmss
;<4(sp).q:入力
;>4(sp).q:出力
increment:
regs reg d0-d2/a0
push regs
base = .sizeof.(regs)+4
do
;oneseco
move.b base+7(sp),d0 ;ss
moveq.l #$0F,d1
and.b d0,d1
eor.b d1,d0
lea.l nine(pc),a0
move.b (a0,d1.w),d1
moveq.l #$0F,d2
and.b d1,d2
or.b d2,d0
move.b d0,base+7(sp) ;ss
eor.b d2,d1
break eq
;tenseco
move.b base+7(sp),d0 ;ss
ror.b #4,d0
moveq.l #$07,d1
and.b d0,d1
eor.b d1,d0
lea.l five(pc),a0
move.b (a0,d1.w),d1
moveq.l #$0F,d2
and.b d1,d2
or.b d2,d0
rol.b #4,d0
move.b d0,base+7(sp) ;ss
eor.b d2,d1
break eq
;oneminu
move.b base+6(sp),d0 ;mm
moveq.l #$0F,d1
and.b d0,d1
eor.b d1,d0
lea.l nine(pc),a0
move.b (a0,d1.w),d1
moveq.l #$0F,d2
and.b d1,d2
or.b d2,d0
move.b d0,base+6(sp) ;mm
eor.b d2,d1
break eq
;tenminu
move.b base+6(sp),d0 ;mm
ror.b #4,d0
moveq.l #$07,d1
and.b d0,d1
eor.b d1,d0
lea.l five(pc),a0
move.b (a0,d1.w),d1
moveq.l #$0F,d2
and.b d1,d2
or.b d2,d0
rol.b #4,d0
move.b d0,base+6(sp) ;mm
eor.b d2,d1
break eq
;hour
moveq.l #$01,d0
and.b base+4(sp),d0 ;_t
lsl.w #2,d0
lea.l hour(pc),a0
movea.l (a0,d0.w),a0 ;hour_t0 .. hour_t1
moveq.l #$3F,d0
and.b base+5(sp),d0 ;hh
add.w d0,d0
move.w (a0,d0.w),d0
move.b d0,base+5(sp) ;hh
and.w #$0100,d0
break eq
;wday
move.b base+0(sp),d0 ;LW
moveq.l #$07,d1
and.b d0,d1
eor.b d1,d0
lea.l wday(pc),a0
or.b (a0,d1.w),d0
move.b d0,base+0(sp) ;LW
;mday
moveq.l #$30,d0
and.b base+0(sp),d0 ;LW
lsr.b #4-2,d0
lea.l mday(pc),a0
movea.l (a0,d0.w),a0 ;mday_l0 .. mday_l3
moveq.l #$1F,d0
and.b base+2(sp),d0 ;MM
lsl.w #2,d0
movea.l (a0,d0.w),a0 ;mday_28 .. mday_31
moveq.l #$3F,d0
and.b base+3(sp),d0 ;DD
add.w d0,d0
move.w (a0,d0.w),d0
move.b d0,base+3(sp) ;DD
and.w #$0100,d0
break eq
;mont
moveq.l #$1F,d0
and.b base+2(sp),d0 ;MM
add.w d0,d0
lea.l mont(pc),a0
move.w (a0,d0.w),d0
move.b d0,base+2(sp) ;MM
and.w #$0100,d0
break eq
;leap
move.b base+0(sp),d0 ;LW
ror.b #4,d0
moveq.l #$03,d1
and.b d0,d1
eor.b d1,d0
lea.l leap(pc),a0
or.b (a0,d1.w),d0
rol.b #4,d0
move.b d0,base+0(sp) ;LW
;oneyear
move.b base+1(sp),d0 ;YY
moveq.l #$0F,d1
and.b d0,d1
eor.b d1,d0
lea.l nine(pc),a0
move.b (a0,d1.w),d1
moveq.l #$0F,d2
and.b d1,d2
or.b d2,d0
move.b d0,base+1(sp) ;YY
eor.b d2,d1
break eq
;tenyear
move.b base+1(sp),d0 ;YY
ror.b #4,d0
moveq.l #$0F,d1
and.b d0,d1
eor.b d1,d0
lea.l nine(pc),a0
move.b (a0,d1.w),d1
moveq.l #$0F,d2
and.b d1,d2
or.b d2,d0
rol.b #4,d0
move.b d0,base+1(sp) ;YY
eor.b d2,d1
while f
pop
rts
;カウンタ遷移表
nine:
; 0 1 2 3 4 5 6 7
.dc.b $01, $02, $03, $04, $05, $06, $07, $08
; 8 9 A B C D E F
.dc.b $09, $10, $0B, $16, $0D, $14, $0F, $12
five:
; 0 1 2 3 4 5 6 7
.dc.b $01, $02, $03, $04, $05, $10, $07, $12
hour_t0:
; 00 01 02 03 04 05 06 07
.dc.w $001, $002, $003, $004, $005, $006, $007, $008
; 08 09 0A 0B 0C 0D 0E 0F
.dc.w $009, $010, $00B, $016, $00D, $014, $00F, $012
; 10 11 12 13 14 15 16 17
.dc.w $011, $020, $013, $026, $015, $024, $017, $02A
; 18 19 1A 1B 1C 1D 1E 1F
.dc.w $019, $020, $01B, $026, $01D, $024, $01F, $022
; 20 21 22 23 24 25 26 27
.dc.w $021, $022, $023, $024, $025, $026, $027, $028
; 28 29 2A 2B 2C 2D 2E 2F
.dc.w $029, $030, $02B, $036, $02D, $034, $02F, $032
; 30 31 32 33 34 35 36 37
.dc.w $031, $100, $033, $106, $035, $104, $037, $10A
; 38 39 3A 3B 3C 3D 3E 3F
.dc.w $039, $100, $03B, $106, $03D, $104, $03F, $102
hour_t1:
; 00 01 02 03 04 05 06 07
.dc.w $001, $002, $003, $004, $005, $006, $007, $008
; 08 09 0A 0B 0C 0D 0E 0F
.dc.w $009, $010, $00B, $016, $00D, $014, $00F, $012
; 10 11 12 13 14 15 16 17
.dc.w $011, $012, $013, $014, $015, $016, $017, $018
; 18 19 1A 1B 1C 1D 1E 1F
.dc.w $019, $020, $01B, $026, $01D, $024, $01F, $022
; 20 21 22 23 24 25 26 27
.dc.w $021, $022, $023, $100, $025, $026, $027, $10C
; 28 29 2A 2B 2C 2D 2E 2F
.dc.w $029, $030, $02B, $112, $02D, $034, $02F, $116
; 30 31 32 33 34 35 36 37
.dc.w $031, $032, $033, $110, $035, $036, $037, $11C
; 38 39 3A 3B 3C 3D 3E 3F
.dc.w $039, $000, $03B, $102, $03D, $004, $03F, $106
hour:
.dc.l hour_t0,hour_t1
wday:
; 0 1 2 3 4 5 6 7
.dc.b $1, $2, $3, $4, $5, $6, $0, $1
mday_28:
; 00 01 02 03 04 05 06 07
.dc.w $001, $002, $003, $004, $005, $006, $007, $008
; 08 09 0A 0B 0C 0D 0E 0F
.dc.w $009, $010, $00B, $016, $00D, $014, $00F, $012
; 10 11 12 13 14 15 16 17
.dc.w $011, $012, $013, $014, $015, $016, $017, $018
; 18 19 1A 1B 1C 1D 1E 1F
.dc.w $019, $020, $01B, $026, $01D, $024, $01F, $022
; 20 21 22 23 24 25 26 27
.dc.w $021, $022, $023, $024, $025, $026, $027, $028
; 28 29 2A 2B 2C 2D 2E 2F
.dc.w $101, $110, $103, $116, $105, $114, $107, $112
; 30 31 32 33 34 35 36 37
.dc.w $031, $101, $033, $107, $035, $105, $037, $10B
; 38 39 3A 3B 3C 3D 3E 3F
.dc.w $111, $101, $113, $107, $115, $105, $117, $103
mday_29:
; 00 01 02 03 04 05 06 07
.dc.w $001, $002, $003, $004, $005, $006, $007, $008
; 08 09 0A 0B 0C 0D 0E 0F
.dc.w $009, $010, $00B, $016, $00D, $014, $00F, $012
; 10 11 12 13 14 15 16 17
.dc.w $011, $012, $013, $014, $015, $016, $017, $018
; 18 19 1A 1B 1C 1D 1E 1F
.dc.w $019, $020, $01B, $026, $01D, $024, $01F, $022
; 20 21 22 23 24 25 26 27
.dc.w $021, $022, $023, $024, $025, $026, $027, $028
; 28 29 2A 2B 2C 2D 2E 2F
.dc.w $029, $101, $02B, $107, $02D, $105, $02F, $103
; 30 31 32 33 34 35 36 37
.dc.w $031, $101, $033, $107, $035, $105, $037, $10B
; 38 39 3A 3B 3C 3D 3E 3F
.dc.w $039, $101, $03B, $107, $03D, $105, $03F, $103
mday_30:
; 00 01 02 03 04 05 06 07
.dc.w $001, $002, $003, $004, $005, $006, $007, $008
; 08 09 0A 0B 0C 0D 0E 0F
.dc.w $009, $010, $00B, $016, $00D, $014, $00F, $012
; 10 11 12 13 14 15 16 17
.dc.w $011, $012, $013, $014, $015, $016, $017, $018
; 18 19 1A 1B 1C 1D 1E 1F
.dc.w $019, $020, $01B, $026, $01D, $024, $01F, $022
; 20 21 22 23 24 25 26 27
.dc.w $021, $022, $023, $024, $025, $026, $027, $028
; 28 29 2A 2B 2C 2D 2E 2F
.dc.w $029, $030, $02B, $036, $02D, $034, $02F, $032
; 30 31 32 33 34 35 36 37
.dc.w $101, $101, $103, $107, $105, $105, $107, $10B
; 38 39 3A 3B 3C 3D 3E 3F
.dc.w $109, $101, $10B, $107, $10D, $105, $10F, $103
mday_31:
; 00 01 02 03 04 05 06 07
.dc.w $001, $002, $003, $004, $005, $006, $007, $008
; 08 09 0A 0B 0C 0D 0E 0F
.dc.w $009, $010, $00B, $016, $00D, $014, $00F, $012
; 10 11 12 13 14 15 16 17
.dc.w $011, $012, $013, $014, $015, $016, $017, $018
; 18 19 1A 1B 1C 1D 1E 1F
.dc.w $019, $020, $01B, $026, $01D, $024, $01F, $022
; 20 21 22 23 24 25 26 27
.dc.w $021, $022, $023, $024, $025, $026, $027, $028
; 28 29 2A 2B 2C 2D 2E 2F
.dc.w $029, $030, $02B, $036, $02D, $034, $02F, $032
; 30 31 32 33 34 35 36 37
.dc.w $031, $101, $033, $107, $035, $105, $037, $10B
; 38 39 3A 3B 3C 3D 3E 3F
.dc.w $039, $101, $03B, $107, $03D, $105, $03F, $103
mday_l0:
; 00 01 02 03 04 05 06 07
.dc.l mday_31, mday_31, mday_29, mday_31, mday_30, mday_31, mday_30, mday_31
; 08 09 0A 0B 0C 0D 0E 0F
.dc.l mday_31, mday_30, mday_31, mday_30, mday_30, mday_30, mday_30, mday_30
; 10 11 12 13 14 15 16 17
.dc.l mday_31, mday_30, mday_31, mday_30, mday_30, mday_30, mday_30, mday_30
; 18 19 1A 1B 1C 1D 1E 1F
.dc.l mday_31, mday_30, mday_31, mday_30, mday_30, mday_30, mday_30, mday_30
mday_l1:
; 00 01 02 03 04 05 06 07
.dc.l mday_31, mday_31, mday_28, mday_31, mday_30, mday_31, mday_30, mday_31
; 08 09 0A 0B 0C 0D 0E 0F
.dc.l mday_31, mday_30, mday_31, mday_30, mday_30, mday_30, mday_30, mday_30
; 10 11 12 13 14 15 16 17
.dc.l mday_31, mday_30, mday_31, mday_30, mday_30, mday_30, mday_30, mday_30
; 18 19 1A 1B 1C 1D 1E 1F
.dc.l mday_31, mday_30, mday_31, mday_30, mday_30, mday_30, mday_30, mday_30
mday:
; 0 1 2 3
.dc.l mday_l0, mday_l1, mday_l1, mday_l1
mont:
; 00 01 02 03 04 05 06 07
.dc.w $001, $002, $003, $004, $005, $006, $007, $008
; 08 09 0A 0B 0C 0D 0E 0F
.dc.w $009, $010, $00B, $016, $00D, $014, $00F, $012
; 10 11 12 13 14 15 16 17
.dc.w $011, $012, $101, $104, $015, $016, $105, $108
; 18 19 1A 1B 1C 1D 1E 1F
.dc.w $019, $000, $109, $104, $01D, $004, $10D, $100
leap:
; 0 1 2 3
.dc.b $1, $2, $3, $0
;カウンタに書き込む値
; $LWYYMMDD,$_thhmmss
COUNTER .macro L,W,YY,MM,DD,t,hh,mm,ss
.dc.l ((L)<<28)+((W)<<24)+((YY)<<16)+((MM)<<8)+(DD)
.dc.l ((t)<<24)+((hh)<<16)+((mm)<<8)+(ss)
.endm
data_table:
;秒
.irp ss10,0,4,5,6,7
.irp ss1,0,8,9,10,11,12,13,14,15
COUNTER 0,0,$00,$01,$01,1,$00,$00,(ss10<<4)+ss1
.endm
.endm
;分
.irp mm10,0,4,5,6,7
.irp mm1,0,8,9,10,11,12,13,14,15
COUNTER 0,0,$00,$01,$01,1,$00,(mm10<<4)+mm1,$59
.endm
.endm
;12/24、時
.irp t,0,1
hh:=$00
.rept $3F-$00+1
COUNTER 0,0,$00,$01,$01,t,hh,$59,$59
hh:=hh+1
.endm
.endm
;閏年、月、日
.irp L,0,1,2,3
MM:=$00
.rept $1F-$00+1
DD:=$00
.rept $3F-$00+1
COUNTER L,0,$00,MM,DD,1,$23,$59,$59
DD:=DD+1
.endm
MM:=MM+1
.endm
.endm
;年
.irp yy10,0,8,9,10,11,12,13,14,15
.irp yy1,0,8,9,10,11,12,13,14,15
COUNTER 0,0,(yy10<<4)+yy1,$12,$31,1,$23,$59,$59
.endm
.endm
;曜日
.irp W,0,5,6,7
COUNTER 0,W,$00,$01,$01,1,$23,$59,$59
.endm
;
.dc.l -1
title_message:
.dc.b 'RTCのカウンタが実機と同じように遷移しているか確認します',13,10,0
header_message:
.dc.b ' 入力 期待された出力 観測された出力',13,10
.dc.b 'LWYYMMDD:_thhmmss LWYYMMDD:_thhmmss LWYYMMDD:_thhmmss',13,10,0
dot_message:
.dc.b '.',0
error_message:
.dc.b ' 失敗',13,10,0
passed_message:
.dc.b ' 成功, ',0
failed_message:
.dc.b ' 失敗',13,10
.dc.b '時計を合わせてください',13,10,0
.even
.bss
.even
passed_counter:
.ds.l 1
failed_counter:
.ds.l 1
saved_counters:
.ds.l 2
data_pointer:
.ds.l 1
dot_counter:
.ds.w 1
string_buffer:
.ds.b 256
.text
.even
;----------------------------------------------------------------
;改行をコピーする
;<a0.l:コピー先
;>a0.l:コピー先の0の位置
crlf::
move.b #13,(a0)+
move.b #10,(a0)+
clr.b (a0)
rts
;----------------------------------------------------------------
;符号なし整数を16進数8桁の文字列に変換する
;<d0.l:符号なし整数
;<a0.l:バッファ。16進数8桁の文字列の先頭
;>a0.l:16進数8桁の文字列の末尾の0の位置
h8tos::
push d1-d2
moveq.l #8-1,d1
for d1
rol.l #4,d0
moveq.l #15,d2
and.w d0,d2
move.b 100f(pc,d2.w),(a0)+
next
clr.b (a0)
pop
rts
100: .dc.b '0123456789ABCDEF'
;----------------------------------------------------------------
;文字列を表示する
;<a0.l:文字列
print::
push d0
jbsr strlen
move.l d0,-(sp)
move.l a0,-(sp)
move.w #1,-(sp)
DOS _WRITE
lea.l (10,sp),sp
pop
rts
;----------------------------------------------------------------
;文字列をコピーする
;<a0.l:コピー先
;<a1.l:コピー元
;>a0.l:コピー先の0の位置
;>a1.l:コピー元の0の次の位置
strcpy::
do
move.b (a1)+,(a0)+
while ne ;0でなければ繰り返す
subq.l #1,a0 ;進み過ぎた分戻る
rts
;----------------------------------------------------------------
;文字列の長さを数える
;<a0.l:文字列
;>d0.l:長さ
strlen::
move.l a0,d0 ;d0=先頭
do
tst.b (a0)+
while ne ;0でなければ繰り返す
subq.l #1,a0 ;進み過ぎた分戻る。a0=末尾
exg.l d0,a0 ;d0=末尾,a0=先頭
sub.l a0,d0 ;d0=末尾-先頭=長さ
rts
;----------------------------------------------------------------
;32ビット符号なし整数を10進数の文字列に変換する
;<d0.l:符号なし整数
;<a0.l:バッファ。10進数の文字列の先頭
;>a0.l:10進数の文字列の末尾の0の位置
utos::
if <tst.l d0>,eq ;0
move.b #'0',(a0)+
else ;0以外
push d0-d2/a1
lea.l utos_table(pc),a1
do
move.l (a1)+,d1
while <cmp.l d1,d0>,lo ;引けるところまで進む。ゼロサプレス
do
moveq.l #'0'-1,d2
do
addq.b #1,d2
sub.l d1,d0
while hs ;引ける回数を数える
move.b d2,(a0)+
add.l d1,d0 ;引き過ぎた分を加え戻す
move.l (a1)+,d1
while ne
pop
endif
clr.b (a0)
rts
utos_table::
.dc.l 1000000000
.dc.l 100000000
.dc.l 10000000
.dc.l 1000000
.dc.l 100000
.dc.l 10000
.dc.l 1000
.dc.l 100
.dc.l 10
.dc.l 1
.dc.l 0