CnC_Remastered_Collection

Command and Conquer: Red Alert
Log | Files | Refs | README | LICENSE

WINASM.ASM (16240B)


      1 ;
      2 ; Copyright 2020 Electronic Arts Inc.
      3 ;
      4 ; TiberianDawn.DLL and RedAlert.dll and corresponding source code is free 
      5 ; software: you can redistribute it and/or modify it under the terms of 
      6 ; the GNU General Public License as published by the Free Software Foundation, 
      7 ; either version 3 of the License, or (at your option) any later version.
      8 
      9 ; TiberianDawn.DLL and RedAlert.dll and corresponding source code is distributed 
     10 ; in the hope that it will be useful, but with permitted additional restrictions 
     11 ; under Section 7 of the GPL. See the GNU General Public License in LICENSE.TXT 
     12 ; distributed with this program. You should have received a copy of the 
     13 ; GNU General Public License along with permitted additional restrictions 
     14 ; with this program. If not, see [https://github.com/electronicarts/CnC_Remastered_Collection]>.
     15 
     16 
     17 ;***************************************************************************
     18 ;**   C O N F I D E N T I A L --- W E S T W O O D   S T U D I O S  I N C  **
     19 ;***************************************************************************
     20 ;*                                                                         *
     21 ;*                 Project Name : Command & Conquer                        *
     22 ;*                                                                         *
     23 ;*                    File Name : WINSAM.ASM                               *
     24 ;*                                                                         *
     25 ;*                   Programmer : Steve Tall                               *
     26 ;*                                                                         *
     27 ;*                   Start Date : October 26th, 1995                       *
     28 ;*                                                                         *
     29 ;*                  Last Update : October 26th, 1995  [ST]                 *
     30 ;*                                                                         *
     31 ;*-------------------------------------------------------------------------*
     32 ;* Functions:                                                              *
     33 ;* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - *
     34 
     35 
     36 IDEAL
     37 P386
     38 MODEL USE32 FLAT
     39 
     40 global	C _AbortModemFunctionPtr:dword
     41 global	C Memory_Error_Exit	:dword
     42 global	C MouseQX		:dword
     43 global	C MouseQY		:dword
     44 
     45 global	FastGetPortHardware_	:near
     46 global	FastSetPortHardware_	:near
     47 global	PortOpenGreenleafFast_	:near
     48 global	HMWaitForOK_		:near
     49 global	HMSetDialingMethod_	:near
     50 global	HMDial_			:near
     51 global	HMInputLine_		:near
     52 global	HMAnswer_		:near
     53 global	PortKillTime_		:near
     54 global	HMSendStringNoWait_	:near
     55 global	HMSetUpEchoRoutine_	:near
     56 global	HMSetUpAbortKey_	:near
     57 global	SetAbortModemFunctionPtr_:near
     58 global	Change8259Priority_	:near
     59 global	HMSendString_		:near
     60 global	C Stop_Execution	:near
     61 
     62 
     63 global	_IPX_Initialise:near
     64 global	_ASM_IPX_Initialise:near
     65 
     66 
     67 		codeseg
     68 
     69 proc _ASM_IPX_Initialise near
     70 
     71 		int	3
     72 		jmp	_IPX_Initialise
     73 
     74 endp
     75 
     76 
     77 
     78 
     79 global _Int3:near
     80 proc _Int3 near
     81 	;int	3
     82 	ret
     83 endp
     84 
     85 
     86 proc Stop_Execution C near
     87 
     88 	nop
     89 	ret
     90 
     91 endp
     92 
     93 
     94 
     95 ;
     96 ; Stuff needed from the shape library
     97 ;
     98 ;
     99 ;
    100 
    101 
    102 INCLUDE "shape.inc"
    103 
    104 
    105 
    106 
    107 ;***************************************************************************
    108 ;* ModeX_Blit -- Copy a 320x200 graphic view port to a modex screen        *
    109 ;*                                                                         *
    110 ;*                                                                         *
    111 ;* INPUT:	eax - graphic view port                                    *
    112 ;*                                                                         *
    113 ;* OUTPUT:      none                                                       *
    114 ;*                                                                         *
    115 ;* PROTO:       extern "C" void ModeX_Blit (GraphicBufferClass *source);   *
    116 ;*                                                                         *
    117 ;* HISTORY:                                                                *
    118 ;*   10/26/1994 PWG : Created.                                             *
    119 ;*=========================================================================*
    120 
    121 SEQUENCER	=3c4h	; sequencer port
    122 MAP_MASK	=2	; map mask register
    123 
    124 		INCLUDE "gbuffer.inc"
    125 		global	ModeX_Blit_:near
    126 
    127 
    128 proc        	ModeX_Blit_ NEAR
    129 
    130 		pushad
    131 		mov	ebx,eax
    132 
    133 		mov	esi,[(GraphicViewPort ebx).GVPOffset]
    134 		mov	eax,[(GraphicViewPort ebx).GVPXAdd]
    135 		add	eax,[(GraphicViewPort ebx).GVPPitch]
    136 		mov	edi,0a0000h
    137 		mov	ebx,eax
    138 
    139 		mov	al,MAP_MASK
    140 
    141 		mov	ebp,200
    142 
    143 ??each_line_lp:	mov	ah,1		;1st plane
    144 		push	ebx
    145 		push	esi
    146 
    147 ??each_plane_lp:mov	edx,SEQUENCER
    148 		out	dx,ax
    149 
    150 		push	esi
    151 		push	edi
    152 		push	eax
    153 
    154 		rept	10
    155 		mov	al,[esi]
    156 		mov	bl,[esi+8]
    157 		mov	cl,[esi+16]
    158 		mov	dl,[esi+24]
    159 		mov	ah,[esi+4]
    160 		mov	bh,[esi+12]
    161 		mov	ch,[esi+20]
    162 		mov	dh,[esi+28]
    163 		shl	ebx,16
    164 		shl	edx,16
    165 		or	ebx,eax
    166 		or	edx,ecx
    167 		mov	[edi],ebx
    168 		mov	[edi+4],edx
    169 		add	esi,32
    170 		add	edi,8
    171 		endm
    172 
    173 		pop	eax
    174 		pop	edi
    175 		pop	esi
    176 		inc	esi
    177 		shl	ah,1
    178 		cmp	ah,16
    179 		jl	??each_plane_lp
    180 
    181 
    182 		pop	esi
    183 		pop	ebx
    184 		lea	esi,[esi+ebx+320]
    185 		add	edi,80
    186 		dec	ebp
    187 		jnz	??each_line_lp
    188 
    189 		popad
    190 
    191 		ret
    192 
    193 endp		ModeX_Blit_
    194 
    195 
    196 
    197 
    198 
    199 
    200 ifdef cuts
    201 		pushad
    202 		mov	ebx,eax
    203 
    204 		mov	esi,[(GraphicViewPort ebx).GVPOffset]
    205 		mov	eax,[(GraphicViewPort ebx).GVPXAdd]
    206 		add	eax,[(GraphicViewPort ebx).GVPPitch]
    207 		mov	edi,0a0000h
    208 		mov	ebx,eax
    209 
    210 		mov	al,MAP_MASK
    211 		mov	ah,1		;1st plane
    212 
    213 ??each_plane_lp:mov	edx,SEQUENCER
    214 		out	dx,ax
    215 		mov	ebp,200		;do 200 lines
    216 		push	esi
    217 		push	edi
    218 
    219 ??each_line_lp:	mov	ecx,320/4
    220 
    221 ??each_pixel_lp:mov	dl,[esi]
    222 		mov	[edi],dl
    223 		add	esi,4
    224 		inc	edi
    225 		dec	ecx
    226 		jnz	??each_pixel_lp
    227 
    228 		add	esi,ebx
    229 		dec	ebp
    230 		jnz	??each_line_lp
    231 
    232 		pop	edi
    233 		pop	esi
    234 		inc	esi
    235 		shl	ah,1
    236 
    237 		cmp	ah,16
    238 		jl	??each_plane_lp
    239 endif
    240 
    241 
    242 
    243 
    244 
    245 
    246 
    247 
    248 
    249 
    250 proc FastGetPortHardware_ NEAR
    251 endp
    252 
    253 proc FastSetPortHardware_ NEAR
    254 endp
    255 
    256 proc PortOpenGreenleafFast_ NEAR
    257 endp
    258 
    259 proc HMWaitForOK_ NEAR
    260 endp
    261 
    262 proc HMSetDialingMethod_ NEAR
    263 endp
    264 
    265 proc HMDial_ NEAR
    266 endp
    267 
    268 proc HMInputLine_ NEAR
    269 endp
    270 
    271 proc HMAnswer_ NEAR
    272 endp
    273 
    274 proc PortKillTime_ NEAR
    275 endp
    276 
    277 proc HMSendStringNoWait_ NEAR
    278 endp
    279 
    280 proc HMSetUpEchoRoutine_ NEAR
    281 endp
    282 
    283 proc HMSetUpAbortKey_ NEAR
    284 endp
    285 
    286 proc SetAbortModemFunctionPtr_ NEAR
    287 endp
    288 
    289 proc Change8259Priority_ NEAR
    290 endp
    291 
    292 proc HMSendString_ NEAR
    293 endp
    294 
    295 		ret
    296 
    297 
    298 
    299 
    300 
    301 
    302 
    303 	masm
    304 ;
    305 ; Change a DAC colour register directly
    306 ;
    307 ; register number in al
    308 ;
    309 ; bh=red bl=green cl=blue
    310 ;
    311 
    312 set_dac_col proc near
    313 		pushad
    314 		cli
    315 		push	eax
    316 		mov	dx,03dah
    317 		in	al,dx
    318 		jmp	@@1
    319 @@1:		mov	dx,03c8h
    320 		pop	eax
    321 		out	dx,al
    322 		jmp	@@2
    323 @@2:		inc	dl
    324 		mov	al,bh
    325 		out	dx,al
    326 		jmp	@@3
    327 @@3:		mov	al,bl
    328 		out	dx,al
    329 		jmp	@@4
    330 @@4:		mov	al,cl
    331 		out	dx,al
    332 		jmp	@@5
    333 @@5:		sti
    334 		popad
    335 		ret
    336 set_dac_col endp
    337 
    338 	ideal
    339 
    340 
    341 global	Set_Palette_Register_:near
    342 
    343 
    344 proc Set_Palette_Register_ near
    345 
    346 		pushad
    347 		and	cl,63
    348 		mov	bh,dl
    349 		and	bh,63
    350 		and	bl,63
    351 		call	set_dac_col
    352 		popad
    353 		ret
    354 
    355 endp Set_Palette_Register_
    356 
    357 
    358 
    359 
    360 		locals	??
    361 
    362 
    363 
    364 		ends
    365 
    366 		dataseg
    367 
    368 LineBuffer		dd	640 dup (?)
    369 		ends
    370 
    371 
    372 
    373 		segment mycode page public use32 'code'	; Need stricter segment alignment
    374 
    375 global		C	Asm_Interpolate:near
    376 global		C	Asm_Interpolate_Line_Double:near
    377 global		C	Asm_Interpolate_Line_Interpolate:near
    378 global		C	PaletteInterpolationTable:byte
    379 
    380 
    381 ;*********************************************************************************************
    382 ;* Asm_Interpolate -- interpolate a 320x200 buffer to a 640x400 screen                       *
    383 ;*                                                                                           *
    384 ;* INPUT:	ptr to source buffer (320x200 image)                                         *
    385 ;*              ptr to dest buffer (640x400)                                                 *
    386 ;*              height of source buffer                                                      *
    387 ;*              width of source buffer                                                        *
    388 ;*              width of dest buffer                                                         *
    389 ;*                                                                                           *
    390 ;*                                                                                           *
    391 ;* OUTPUT:      none                                                                         *
    392 ;*                                                                                           *
    393 ;* Warnings:                                                                                 *
    394 ;*                                                                                           *
    395 ;* HISTORY:                                                                                  *
    396 ;*   12/15/95 ST : Created.                                                                  *
    397 ;*===========================================================================================*
    398 
    399 PROC		Asm_Interpolate C near
    400 
    401 		ARG	src_ptr:dword
    402 		ARG	dest_ptr:dword
    403 		ARG	source_height:dword
    404 		ARG	source_width:dword
    405 		ARG	dest_width:dword
    406 
    407 		LOCAL	old_dest:dword
    408 
    409 		pushad
    410 
    411 		mov	eax,[dest_ptr]
    412 		mov	[old_dest],eax
    413 
    414 		mov	esi,[src_ptr]
    415 
    416 ??each_line_loop:
    417 		mov	ecx,[source_width]
    418 		sub	ecx,2
    419 		shr	ecx,1
    420 		mov	edi,[old_dest]
    421 		jmp	??interpolate_loop
    422 
    423 		align	32
    424 ;
    425 ; convert 2 pixels of source into 4 pixels of destination
    426 ; so we can write to video memory with dwords
    427 ;
    428 ??interpolate_loop:
    429 		mov	eax,[esi]
    430 		lea	esi,[esi+2]
    431 		mov	edx,eax
    432 		mov	ebx,eax
    433 		and	edx,65535
    434 		ror	ebx,8
    435 		mov	bl,[edx+PaletteInterpolationTable]
    436 		mov	bh,ah
    437 		and	eax,000ffff00h
    438 		ror	ebx,8
    439 
    440 ;1st 3 pixels now in ebx
    441 
    442 		shr	eax,8
    443 		mov	bh,[eax+PaletteInterpolationTable]
    444 		ror	ebx,16
    445 		mov	[edi],ebx
    446 		add	edi,4
    447 
    448 		dec	ecx
    449 		jnz	??interpolate_loop
    450 
    451 ; do the last three pixels and a blank on the end of a row
    452 		xor	eax,eax
    453 		mov	ax,[esi]
    454 		mov	[edi],al
    455 		inc	edi
    456 		lea	esi,[esi+2]
    457 		mov	al,[eax+PaletteInterpolationTable]
    458 		mov	[edi],al
    459 		inc	edi
    460 		mov	[edi],ah
    461 		inc	edi
    462 		mov	[byte edi],0
    463 
    464 		mov	edi,[dest_width]
    465 		add	[old_dest],edi
    466 
    467 		dec	[source_height]
    468 		jnz	??each_line_loop
    469 
    470 		popad
    471 		ret
    472 
    473 endp		Asm_Interpolate
    474 
    475 
    476 
    477 
    478 
    479 
    480 
    481 
    482 
    483 
    484 
    485 
    486 
    487 
    488 PROC		Asm_Interpolate_Line_Double C near
    489 		ARG	src_ptr:dword
    490 		ARG	dest_ptr:dword
    491 		ARG	source_height:dword
    492 		ARG	source_width:dword
    493 		ARG	dest_width:dword
    494 
    495 		LOCAL	old_dest:dword
    496 		LOCAL	width_counter:dword
    497 		LOCAL	pixel_count:dword
    498 
    499 		pushad
    500 
    501 		mov	eax,[dest_ptr]
    502 		mov	[old_dest],eax
    503 
    504 		mov	esi,[src_ptr]
    505 		mov	edi,[dest_ptr]
    506 
    507 ??each_line_loop:
    508 		mov	[width_counter],0
    509 		mov	ecx,[source_width]
    510 		sub	ecx,2
    511 		shr	ecx,1
    512 		mov	[pixel_count],ecx
    513 		mov	ecx,offset LineBuffer
    514 		mov	edi,[old_dest]
    515 		jmp	??interpolate_loop
    516 		align	16
    517 
    518 ; convert 2 pixels of source into 4 pixels of destination
    519 ??interpolate_loop:
    520 		mov	eax,[esi]
    521 		lea	esi,[esi+2]
    522 		mov	edx,eax
    523 		mov	ebx,eax
    524 		and	edx,65535
    525 		ror	ebx,8
    526 		mov	bl,[edx+PaletteInterpolationTable]
    527 		mov	bh,ah
    528 		and	eax,000ffff00h
    529 		ror	ebx,8
    530 
    531 		;1st 3 pixels now in ebx
    532 		shr	eax,8
    533 		mov	bh,[eax+PaletteInterpolationTable]
    534 		ror	ebx,16
    535 		mov	[edi],ebx
    536 		mov	[ecx],ebx
    537 		add	edi,4
    538 		add	ecx,4
    539 
    540 		dec	[pixel_count]
    541 		jnz	??interpolate_loop
    542 
    543 ; do the last three pixels and a blank
    544 
    545 		xor	eax,eax
    546 		mov	ax,[esi]
    547 		mov	[edi],al
    548 		mov	[ecx],al
    549 		inc	edi
    550 		inc	ecx
    551 		lea	esi,[esi+2]
    552 		mov	al,[eax+PaletteInterpolationTable]
    553 		mov	[edi],al
    554 		mov	[ecx],al
    555 		inc	edi
    556 		inc	ecx
    557 		mov	[edi],ah
    558 		mov	[ecx],ah
    559 		inc	edi
    560 		inc	ecx
    561 		mov	[byte edi],0
    562 		mov	[byte ecx],0
    563 
    564 		mov	edi,[dest_width]
    565 		shr	edi,1
    566 		add	[old_dest],edi
    567 		push	esi
    568 		push	edi
    569 		mov	esi,offset LineBuffer
    570 		mov	edi,[old_dest]
    571 		mov	ecx,[source_width]
    572 		shr	ecx,1
    573 		rep	movsd
    574 		pop	edi
    575 		pop	esi
    576 		add	[old_dest],edi
    577 		mov	edi,[old_dest]
    578 
    579 		dec	[source_height]
    580 		jnz	??each_line_loop
    581 
    582 		popad
    583 		ret
    584 
    585 endp		Asm_Interpolate_Line_Double
    586 
    587 
    588 
    589 
    590 
    591 
    592 
    593 
    594 
    595 		ends
    596 
    597 		dataseg
    598 
    599 TopLine		dd	640 dup (?)
    600 BottomLine	dd	640 dup (?)
    601 
    602 
    603 		segment mycode page public use32 'code'	; Need stricter segment alignment
    604 
    605 
    606 proc		Interpolate_Single_Line C near
    607 
    608 		ARG	source_ptr:dword
    609 		ARG	dest_ptr:dword
    610 		ARG	source_width:dword
    611 
    612 		pushad
    613 
    614 		mov	ecx,[source_width]
    615 		sub	ecx,2
    616 		shr	ecx,1
    617 
    618 		mov	esi,[source_ptr]
    619 		mov	edi,[dest_ptr]
    620 
    621 ??interpolate_loop:
    622 		mov	eax,[esi]
    623 		lea	esi,[esi+2]
    624 		mov	edx,eax
    625 		mov	ebx,eax
    626 		and	edx,65535
    627 		ror	ebx,8
    628 		mov	bl,[edx+PaletteInterpolationTable]
    629 		mov	bh,ah
    630 		and	eax,000ffff00h
    631 		ror	ebx,8
    632 
    633 		;1st 3 pixels now in ebx
    634 		shr	eax,8
    635 		mov	bh,[eax+PaletteInterpolationTable]
    636 		ror	ebx,16
    637 		mov	[edi],ebx
    638 		add	edi,4
    639 
    640 		dec	ecx
    641 		jnz	??interpolate_loop
    642 
    643 ; do the last three pixels and a blank
    644 
    645 		xor	eax,eax
    646 		mov	ax,[esi]
    647 		mov	[edi],al
    648 		inc	edi
    649 		mov	al,[eax+PaletteInterpolationTable]
    650 		mov	[edi],al
    651 		inc	edi
    652 		mov	[edi],ah
    653 		inc	edi
    654 		mov	[byte edi],0
    655 
    656 		popad
    657 		ret
    658 
    659 
    660 endp		Interpolate_Single_Line
    661 
    662 
    663 proc		Interpolate_Between_Lines C near
    664 
    665 		ARG	source1:dword
    666 		ARG	source2:dword
    667 		ARG	destination:dword
    668 		ARG	source_width:dword
    669 
    670 		pushad
    671 		mov	esi,[source1]
    672 		mov	edi,[destination]
    673 		mov	ebx,[source2]
    674 		xor	eax,eax
    675 		mov	ecx,[source_width]
    676 		add	ecx,ecx
    677 
    678 ??interpolate_each_pixel_loop:
    679 		mov	al,[esi]
    680 		mov	ah,[ebx]
    681 		inc	esi
    682 		inc	ebx
    683 		mov	dl,[eax+PaletteInterpolationTable]
    684 		mov	[edi],dl
    685 		inc	edi
    686 		dec	ecx
    687 		jnz	??interpolate_each_pixel_loop
    688 
    689 		popad
    690 		ret
    691 
    692 endp		Interpolate_Between_Lines
    693 
    694 
    695 
    696 
    697 macro		Lineswp
    698 		push	[next_line]
    699 		push	[last_line]
    700 		pop	[next_line]
    701 		pop	[last_line]
    702 endm
    703 
    704 
    705 PROC		Asm_Interpolate_Line_Interpolate C near
    706 
    707 
    708 		ARG	src_ptr:dword
    709 		ARG	dest_ptr:dword
    710 		ARG	source_lines:dword
    711 		ARG	source_width:dword
    712 		ARG	dest_width:dword
    713 
    714 		LOCAL	old_dest:dword
    715 		LOCAL	pixel_count:dword
    716 		LOCAL	next_line:dword
    717 		LOCAL	last_line:dword
    718 
    719 		pushad
    720 
    721 		mov	eax,[dest_ptr]
    722 		mov	[old_dest],eax
    723 
    724 		mov	[next_line],offset TopLine
    725 		mov	[last_line],offset BottomLine
    726 		mov	ecx,[source_width]
    727 		shr	ecx,1
    728 		mov	[pixel_count],ecx
    729 		shr	[dest_width],1
    730 
    731 		call	Interpolate_Single_Line C,[src_ptr],[next_line],[source_width]
    732 		mov	esi,[source_width]
    733 		Lineswp
    734 		add	[src_ptr],esi
    735 		dec	[source_lines]
    736 
    737 
    738 ??each_line_pair_loop:
    739 		call	Interpolate_Single_Line C,[src_ptr],[next_line],[source_width]
    740 		call	Interpolate_Between_Lines C,[last_line],[next_line],offset LineBuffer,[source_width]
    741 
    742 		mov	esi,[last_line]
    743 		mov	edi,[old_dest]
    744 		mov	ecx,[pixel_count]
    745 		rep	movsd
    746 
    747 		mov	edi,[old_dest]
    748 		mov	esi,offset LineBuffer
    749 		add	edi,[dest_width]
    750 		mov	ecx,[pixel_count]
    751 		mov	[old_dest],edi
    752 		rep	movsd
    753 
    754 		mov	edi,[old_dest]
    755 		mov	esi,[source_width]
    756 		add	edi,[dest_width]
    757 		add	[src_ptr],esi
    758 		mov	[old_dest],edi
    759 
    760 		Lineswp
    761 		dec	[source_lines]
    762 		jnz	??each_line_pair_loop
    763 
    764 		call	Interpolate_Single_Line C,[src_ptr],[next_line],[source_width]
    765 		mov	esi,[next_line]
    766 		mov	edi,[old_dest]
    767 		mov	ecx,[pixel_count]
    768 		rep	movsd
    769 
    770 		popad
    771 		ret
    772 
    773 
    774 endp		Asm_Interpolate_Line_Interpolate
    775 
    776 		ends	mycode
    777 
    778 
    779 
    780 
    781 global		C Asm_Create_Palette_Interpolation_Table:near
    782 global		C InterpolationPalette:dword
    783 
    784 		codeseg
    785 
    786 
    787 proc		Asm_Create_Palette_Interpolation_Table C near
    788 
    789 		LOCAL	palette_counter:dword
    790 		LOCAL	first_palette:dword
    791 		LOCAL	second_palette:dword
    792 		LOCAL	dest_ptr:dword
    793 		LOCAL	count:dword
    794 		LOCAL	closest_colour:dword
    795 		LOCAL	distance_of_closest:dword
    796 
    797 		pushad
    798 
    799 		mov	[dest_ptr],0
    800 		mov	[palette_counter],256
    801 		mov	esi,[InterpolationPalette]
    802 
    803 ??palette_outer_loop:
    804 		mov	edi,[InterpolationPalette]
    805 		mov	ecx,256
    806 
    807 ??palette_inner_loop:
    808 		mov	bl,[esi]
    809 		add	bl,[edi]
    810 		shr	bl,1
    811 
    812 		mov	bh,[esi+1]
    813 		add	bh,[edi+1]
    814 		shr	bh,1
    815 
    816 		mov	dl,[esi+2]
    817 		add	dl,[edi+2]
    818 		shr	dl,1
    819 
    820 		mov	[closest_colour],0
    821 		mov	[distance_of_closest],-1
    822 
    823 		push	edi
    824 		push	ecx
    825 		mov	edi,[InterpolationPalette]
    826 		mov	[count],0
    827 
    828 ??cmp_pal_lp:	xor	eax,eax
    829 		xor	ecx,ecx
    830 		mov	al,[edi]
    831 		sub	al,bl
    832 		imul	al
    833 		mov	ecx,eax
    834 		mov	al,[edi+1]
    835 		sub	al,bh
    836 		imul	al
    837 		add	ecx,eax
    838 		mov	al,[edi+2]
    839 		sub	al,dl
    840 		imul	al
    841 		add	ecx,eax
    842 
    843 		cmp	ecx,[distance_of_closest]
    844 		ja	??end_cmp_lp
    845 		mov	[distance_of_closest],ecx
    846 		mov	eax,[count]
    847 		mov	[closest_colour],eax
    848 		test	ecx,ecx
    849 		jz	??got_perfect
    850 
    851 ??end_cmp_lp:	lea	edi,[edi+3]
    852 		inc	[count]
    853 		cmp	[count],256
    854 		jb	??cmp_pal_lp
    855 
    856 
    857 ??got_perfect:	mov	edi,[dest_ptr]
    858 		mov	eax,[closest_colour]
    859 		mov	[edi+PaletteInterpolationTable],al
    860 		inc	[dest_ptr]
    861 
    862 		pop	ecx
    863 		pop	edi
    864 		lea	edi,[edi+3]
    865 		dec	ecx
    866 		jnz	??palette_inner_loop
    867 
    868 		lea	esi,[esi+3]
    869 		dec	[palette_counter]
    870 		jnz	??palette_outer_loop
    871 
    872 		popad
    873 		ret
    874 
    875 endp		Asm_Create_Palette_Interpolation_Table
    876 
    877 
    878 
    879 
    880 	DATASEG
    881 
    882 _AbortModemFunctionPtr	dd	0
    883 Memory_Error_Exit	dd	0
    884 MouseQX			dd	0
    885 MouseQY			dd	0
    886 
    887 end