/***   [asms.s]
*
*	アセンブリ いろいろ	(C)ささがわ
*
*	For GNU Assembler (GAS)
*
***/

	.text

/* int Get_curdir(int drivenum, char *path) */
	.align	2
_Get_curdir:
	.globl	_Get_curdir
	enter	$0, $0
	pushl	%esi
	
	movb	$0x47, %ah
	movl	12(%ebp), %esi
	movb	8(%ebp), %dl
	int	$0x21
	jc	cd_e
	movw	$0, %ax
cd_e:
	movzwl	%ax, %eax
	
	popl	%esi
	leave
	ret

/* void Get_cdexinf(int *n, int *letter) */
	.align	2
_Get_cdexinf:
	.globl	_Get_cdexinf
	enter	$0, $0
	pushl	%esi
	pushl	%ebx
	
	movw	$0x1500, %ax
	xorw	%bx, %bx
	int	$0x2f
	movl	8(%ebp), %esi
	movzwl	%bx, %ebx
	movl	%ebx, (%esi)
	movl	12(%ebp), %esi
	movzwl	%cx, %ecx
	movl	%ecx, (%esi)
	
	popl	%ebx
	popl	%esi
	leave
	ret

/* void _Pixelx(void *buf, int count, const void *table) */
	.align	2
__Pixelx:
	.globl	__Pixelx
	enter	$0, $0
	pushl	%edi
	pushl	%ebx
	
	cld
	pushl	%ds
	popl	%es
	movl	8(%ebp), %edi
	movl	12(%ebp), %ecx
	movl	16(%ebp), %ebx
	cmpl	$0, %ecx
	jle	pixel_end
pixel_l:
	movb	(%edi), %al
	xlatb
	stosb
	loop	pixel_l
	
pixel_end:
	popl	%ebx
	popl	%edi
	leave
	ret

/* void _Pixelstr(void *buf, const void *str, int n) */
	.align	2
__Pixelstr:
	.globl	__Pixelstr
	enter	$0, $0
	pushl	%edi
	pushl	%esi
	pushl	%ebx
	
	movl	12(%ebp), %edi
	xorl	%ecx, %ecx
Pixel_str_loop:
	cmpl	16(%ebp), %ecx
	jae	Pixel_str_fin
	
	movb	(%edi, %ecx), %al
	cmpb	$0x81, %al
	jb	Pixel_str_han
	cmpb	$0x9f, %al
	jbe	Pixel_str_zen
	cmpb	$0xe0, %al
	jb	Pixel_str_han
	cmpb	$0xfc, %al
	jbe	Pixel_str_zen
	jmp	Pixel_str_han
	
Pixel_str_han:
	movb	(%edi, %ecx), %bl
	movzbw	%bl, %bx
	call	_Get_fntadr
	
	pushl	%ecx
	pushl	%edi
	
	movl	8(%ebp), %edi
	addl	%ecx, %edi
	movl	16(%ebp), %edx
	movl	$16, %ecx
Pixel_str_l3:
	movb	%es:(%esi), %al
	incl	%esi
	movb	%al, (%edi)
	addl	%edx, %edi
	loop	Pixel_str_l3
	
	popl	%edi
	popl	%ecx
	incl	%ecx
	jmp	Pixel_str_loop
	
Pixel_str_zen:
	movw	(%edi, %ecx), %bx
	xchgb	%bl, %bh
	call	_Get_fntadr
	
	pushl	%ecx
	pushl	%edi
	
	movl	8(%ebp), %edi
	addl	%ecx, %edi
	movl	16(%ebp), %edx
	movl	$16, %ecx
Pixel_str_l4:
	movw	%es:(%esi), %ax
	incl	%esi
	incl	%esi
	movw	%ax, (%edi)
	addl	%edx, %edi
	loop	Pixel_str_l4
	
	popl	%edi
	popl	%ecx
	incl	%ecx
	incl	%ecx
	jmp	Pixel_str_loop
	
Pixel_str_fin:
	popl	%ebx
	popl	%esi
	popl	%edi
	leave
	ret

/* void _Pixelstr2(void *buf, const void *str, const void *table, int n) */
	.align	2
__Pixelstr2:
	.globl	__Pixelstr2
	enter	$4, $0
	pushl	%edi
	pushl	%esi
	pushl	%ebx
	
	movl	12(%ebp), %edi
	movl	20(%ebp), %ecx
	shl	$2, %ecx
	movl	%ecx, -4(%ebp)
	
	xorl	%ecx, %ecx
Pixel_str2_loop:
	cmpl	20(%ebp), %ecx
	jae	Pixel_str2_fin
	
	movb	(%edi, %ecx), %al
	cmpb	$0x81, %al
	jb	Pixel_str2_han
	cmpb	$0x9f, %al
	jbe	Pixel_str2_zen
	cmpb	$0xe0, %al
	jb	Pixel_str2_han
	cmpb	$0xfc, %al
	jbe	Pixel_str2_zen
	jmp	Pixel_str2_han
	
Pixel_str2_han:
	movb	(%edi, %ecx), %bl
	movzbw	%bl, %bx
	call	_Get_fntadr
	
	pushl	%ecx
	pushl	%edi
	
	movl	-4(%ebp), %edx
	movl	8(%ebp), %edi
	movl	16(%ebp), %ebx
	movl	$16, %ecx
Pixel_str2_l3:
	movb	%es:(%esi), %al
	incl	%esi
	movzbl	%al, %eax
	movl	(%ebx, %eax, 4), %eax
	movl	%eax, (%edi)
	addl	%edx, %edi
	loop	Pixel_str2_l3
	
	popl	%edi
	popl	%ecx
	addl	$4, 8(%ebp)
	incl	%ecx
	jmp	Pixel_str2_loop
	
Pixel_str2_zen:
	movw	(%edi, %ecx), %bx
	xchgb	%bl, %bh
	call	_Get_fntadr
	
	pushl	%ecx
	pushl	%edi
	
	movl	-4(%ebp), %edx
	movl	8(%ebp), %edi
	movl	16(%ebp), %ebx
	movl	$16, %ecx
Pixel_str2_l4:
	movb	%es:(%esi), %al
	incl	%esi
	movzbl	%al, %eax
	movl	(%ebx, %eax, 4), %eax
	movl	%eax, (%edi)
	movb	%es:(%esi), %al
	incl	%esi
	movzbl	%al, %eax
	movl	(%ebx, %eax, 4), %eax
	movl	%eax, 4(%edi)
	addl	%edx, %edi
	loop	Pixel_str2_l4
	
	popl	%edi
	popl	%ecx
	addl	$8, 8(%ebp)
	incl	%ecx
	incl	%ecx
	jmp	Pixel_str2_loop
	
Pixel_str2_fin:
	popl	%ebx
	popl	%esi
	popl	%edi
	leave
	ret

	.align	2
_Get_fntadr:
	.globl	_Get_fntadr
	pushl	%edx
	pushl	%ds
	
	cmpw	$0xff, %bx
	ja	_Get_fntadr_zen
	
	movb	$0x00, %ah
	movb	$0, %al
	movb	$8, %dh
	movb	$16, %dl
	pushl	$0x0110
	popl	%fs
	lcall	%fs:(0xa0)
	pushl	%ds
	popl	%es
	jmp	_Get_fntadr_fin
	
_Get_fntadr_zen:
	cmpw	$0xec40, %bx
	jl	_skip
	movw	$0x8140, %bx
_skip:
	
	movb	$0x02, %ah
	pushl	$0x0110
	popl	%fs
	lcall	%fs:(0xa0)
	
	movb	$0x01, %ah
	movb	$0, %al
	movb	$16, %dh
	movb	$16, %dl
	pushl	$0x0110
	popl	%fs
	lcall	%fs:(0xa0)
	pushl	%ds
	popl	%es
	
_Get_fntadr_fin:
	popl	%ds
	popl	%edx
	ret



/* segpatch */
	.align	2
_segpatch:
	.globl	_segpatch
	pushl	%ds
	popl	%es
	pushl	%ds
	popl	%fs
	pushl	%ds
	popl	%gs
	ret



	.align	2
__TIMER_reset:
	.globl	__TIMER_reset
	enter	$0, $0
	movl	$0, __TIMER_flag
	movl	$0, __TIMER_count
	movl	8(%ebp), %eax
	movl	%eax, __TIMER_count_max
	leave
	ret

	.align	2
__TIMER_sub:
	.globl	__TIMER_sub
	pushl	%eax
	pushl	%edi
	
	movb	$0x17, %ah	/* FM ﾀｲﾏ A 再ｽﾀｰﾄ */
	pushl	%ds
	popl	%gs
	movl	SND_work, %edi
	pushl	$0x0110
	popl	%fs
	lcall	%fs:(0x80)
	
	cmpl	$0, __TIMER_flag
	jne	__TIMER_sub_end
	incl	__TIMER_count
	movl	__TIMER_count, %eax
	cmpl	__TIMER_count_max, %eax
	jb	__TIMER_sub_end
	movl	$1, __TIMER_flag
__TIMER_sub_end:
	popl	%edi
	popl	%eax
	ret

	.data
__TIMER_flag:	.long 0
	.globl	__TIMER_flag
__TIMER_count:	.long 0
__TIMER_count_max:
		.long 0
