Category : Assembly Language Source Code
Archive   : EASTER.ZIP
Filename : EASTER.ASM
; given year
;
;Written by Scott R. Houck 12 Sept 88
;
;Usage: EASTER
;
;For example: EASTER 1988 (must be 4 digits)
CODE SEGMENT
ASSUME cs:CODE, ds:CODE
ORG 100h
start: jmp main
CR equ 0Dh
LF equ 0Ah
A dw ?
B dw ?
C dw ?
D dw ?
E dw ?
H dw ?
M dw ?
March db 'March ',0
April db 'April ',0
usage db 'Usage: EASTER
errmsg db 'Invalid year',CR,LF,0
div_by macro number
xor dx,dx
mov bx,number
div bx
endm
;---------------------------------------------------------------------
main PROC NEAR
mov di,80h ;PSP parameter byte count pointer
mov cl,[di] ;move byte count to CL
xor ch,ch
jcxz no_params
jmp short scan
no_params: lea si,usage
call dstring
jmp exit
invalid: lea si,errmsg
call dstring
jmp exit
scan: inc di
mov al,' '
cld
repe scasb ;scan for first non-space char
dec di
inc cx
jcxz no_params
cmp cx,4 ;must be a 4-digit year
jne invalid
mov si,di
mov dl,10 ;used in multiplication below
xor bx,bx
convert: lodsb ;move digit to AL
sub al,'0'
jl invalid ;was the digit less than '0' ?
cmp al,9
jg invalid ;was the digit greater than '9' ?
cbw ;convert to word
push ax ;save digit
mov al,bl
mul dl ;AX = AL * 10
mov bx,ax ;result in BX
pop ax ;restore digit
add bx,ax ;add in digit
loop convert
push bx ;save the year
mov ax,bx ;A = year % 19
div_by 19
mov A,dx
pop ax ;B = year / 100
div_by 100 ;C = year % 100
mov B,ax
mov C,dx
div_by 4 ;D = B / 4
mov D,ax ;E = B % 4
mov E,dx
mov ax,B ;F = (B + 8) / 25
add ax,8
div_by 25
neg ax ;G = (1 - F + B) / 3
inc ax
add ax,B
div_by 3
neg ax ;H = (15 - G - D + B + 19*A) % 30
add ax,15
add ax,B
sub ax,D
push ax
mov ax,A
mov bl,19
mul bl
pop bx
add ax,bx
div_by 30
mov H,dx
mov ax,C ;J = C / 4
div_by 4 ;K = C % 4
shl ax,1 ;M = (32 - H - K + 2*J + 2*E) % 7
sub ax,dx
mov bx,E
shl bx,1
add ax,bx
sub ax,H
add ax,32
div_by 7
mov M,dx
mov bx,11 ;N = (22*M + 11*H + A) / 451
mov ax,H
mul bx
mov cx,ax
shl bx,1
mov ax,M
mul bx
add ax,cx
add ax,A
div_by 451
mov bl,-7 ;P = 114 - 7*N + M + H
imul bl
add ax,114
add ax,M
add ax,H
div_by 31 ;month = P / 31
inc dx ;day = (P % 31) + 1
xchg ax,dx ;AX = day, DX = month
cmp dx,3
jne month4
lea si,March
jmp short print_month
month4: lea si,April
print_month: call dstring
call decout ;print the day
mov al,CR
call stdout
mov al,LF
call stdout
exit: int 20h
main ENDP
;---------------------------------------------------------------------
;STDOUT -- Display a character to the screen
;
;Upon entry, the character to be displayed is in AL
stdout PROC NEAR
push ax
push dx
mov dl,al
mov ah,2
int 21h
pop dx
pop ax
ret
stdout ENDP
;---------------------------------------------------------------------
;DSTRING -- display an ASCIIZ string
;
;Upon entry, DS:SI points to the string
dstring PROC NEAR
push ax
push si
cld
dstring1: lodsb
or al,al
jz dstring2
call stdout
jmp short dstring1
dstring2: pop si
pop ax
ret
dstring ENDP
;---------------------------------------------------------------------
;DECOUT -- prints a 16-bit binary number in AX, converts it to
; ASCII decimal form and displays it on the screen
;
;Upon entry, the number to be displayed is in AX
decout PROC NEAR
push ax
push bx
push cx
push dx
xor cx,cx ;counts digits to print
mov bx,10
decout1: inc cx ;increment counter
xor dx,dx ;prepare to divide
div bx ;divide by ten
push dx ;push remainder
or ax,ax ;is the quotient zero?
jnz decout1 ;if not, more numbers to convert
decout2: pop ax ;retrieve digit from stack
add al,'0' ;convert to ASCII
call stdout ;print the character
loop decout2 ;do all of the digits
pop dx
pop cx
pop bx
pop ax
ret
decout ENDP
;---------------------------------------------------------------------
CODE ENDS
END start
Very nice! Thank you for this wonderful archive. I wonder why I found it only now. Long live the BBS file archives!
This is so awesome! 😀 I’d be cool if you could download an entire archive of this at once, though.
But one thing that puzzles me is the “mtswslnkmcjklsdlsbdmMICROSOFT” string. There is an article about it here. It is definitely worth a read: http://www.os2museum.com/wp/mtswslnk/